LCOV - code coverage report
Current view: top level - third_party/openssl/crypto/objects - obj_dat.c (source / functions) Hit Total Coverage
Test: tmp.zDYK9MVh93 Lines: 46 336 13.7 %
Date: 2015-10-10 Functions: 9 30 30.0 %

          Line data    Source code
       1             : /* crypto/objects/obj_dat.c */
       2             : /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
       3             :  * All rights reserved.
       4             :  *
       5             :  * This package is an SSL implementation written
       6             :  * by Eric Young (eay@cryptsoft.com).
       7             :  * The implementation was written so as to conform with Netscapes SSL.
       8             :  *
       9             :  * This library is free for commercial and non-commercial use as long as
      10             :  * the following conditions are aheared to.  The following conditions
      11             :  * apply to all code found in this distribution, be it the RC4, RSA,
      12             :  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
      13             :  * included with this distribution is covered by the same copyright terms
      14             :  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
      15             :  *
      16             :  * Copyright remains Eric Young's, and as such any Copyright notices in
      17             :  * the code are not to be removed.
      18             :  * If this package is used in a product, Eric Young should be given attribution
      19             :  * as the author of the parts of the library used.
      20             :  * This can be in the form of a textual message at program startup or
      21             :  * in documentation (online or textual) provided with the package.
      22             :  *
      23             :  * Redistribution and use in source and binary forms, with or without
      24             :  * modification, are permitted provided that the following conditions
      25             :  * are met:
      26             :  * 1. Redistributions of source code must retain the copyright
      27             :  *    notice, this list of conditions and the following disclaimer.
      28             :  * 2. Redistributions in binary form must reproduce the above copyright
      29             :  *    notice, this list of conditions and the following disclaimer in the
      30             :  *    documentation and/or other materials provided with the distribution.
      31             :  * 3. All advertising materials mentioning features or use of this software
      32             :  *    must display the following acknowledgement:
      33             :  *    "This product includes cryptographic software written by
      34             :  *     Eric Young (eay@cryptsoft.com)"
      35             :  *    The word 'cryptographic' can be left out if the rouines from the library
      36             :  *    being used are not cryptographic related :-).
      37             :  * 4. If you include any Windows specific code (or a derivative thereof) from
      38             :  *    the apps directory (application code) you must include an acknowledgement:
      39             :  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
      40             :  *
      41             :  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
      42             :  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
      43             :  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
      44             :  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
      45             :  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
      46             :  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
      47             :  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
      48             :  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
      49             :  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
      50             :  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
      51             :  * SUCH DAMAGE.
      52             :  *
      53             :  * The licence and distribution terms for any publically available version or
      54             :  * derivative of this code cannot be changed.  i.e. this code cannot simply be
      55             :  * copied and put under another distribution licence
      56             :  * [including the GNU Public Licence.]
      57             :  */
      58             : 
      59             : #include <stdio.h>
      60             : #include <ctype.h>
      61             : #include <limits.h>
      62             : #include "cryptlib.h"
      63             : #include <openssl/lhash.h>
      64             : #include <openssl/asn1.h>
      65             : #include <openssl/objects.h>
      66             : #include <openssl/bn.h>
      67             : 
      68             : /* obj_dat.h is generated from objects.h by obj_dat.pl */
      69             : #ifndef OPENSSL_NO_OBJECT
      70             : # include "obj_dat.h"
      71             : #else
      72             : /* You will have to load all the objects needed manually in the application */
      73             : # define NUM_NID 0
      74             : # define NUM_SN 0
      75             : # define NUM_LN 0
      76             : # define NUM_OBJ 0
      77             : static const unsigned char lvalues[1];
      78             : static const ASN1_OBJECT nid_objs[1];
      79             : static const unsigned int sn_objs[1];
      80             : static const unsigned int ln_objs[1];
      81             : static const unsigned int obj_objs[1];
      82             : #endif
      83             : 
      84             : DECLARE_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, sn);
      85             : DECLARE_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, ln);
      86             : DECLARE_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, obj);
      87             : 
      88             : #define ADDED_DATA      0
      89             : #define ADDED_SNAME     1
      90             : #define ADDED_LNAME     2
      91             : #define ADDED_NID       3
      92             : 
      93             : typedef struct added_obj_st {
      94             :     int type;
      95             :     ASN1_OBJECT *obj;
      96             : } ADDED_OBJ;
      97             : DECLARE_LHASH_OF(ADDED_OBJ);
      98             : 
      99             : static int new_nid = NUM_NID;
     100             : static LHASH_OF(ADDED_OBJ) *added = NULL;
     101             : 
     102             : static int sn_cmp(const ASN1_OBJECT *const *a, const unsigned int *b)
     103             : {
     104           0 :     return (strcmp((*a)->sn, nid_objs[*b].sn));
     105             : }
     106             : 
     107           0 : IMPLEMENT_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, sn);
     108             : 
     109             : static int ln_cmp(const ASN1_OBJECT *const *a, const unsigned int *b)
     110             : {
     111           0 :     return (strcmp((*a)->ln, nid_objs[*b].ln));
     112             : }
     113             : 
     114           0 : IMPLEMENT_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, ln);
     115             : 
     116           0 : static unsigned long added_obj_hash(const ADDED_OBJ *ca)
     117             : {
     118             :     const ASN1_OBJECT *a;
     119             :     int i;
     120             :     unsigned long ret = 0;
     121             :     unsigned char *p;
     122             : 
     123           0 :     a = ca->obj;
     124           0 :     switch (ca->type) {
     125             :     case ADDED_DATA:
     126           0 :         ret = a->length << 20L;
     127           0 :         p = (unsigned char *)a->data;
     128           0 :         for (i = 0; i < a->length; i++)
     129           0 :             ret ^= p[i] << ((i * 3) % 24);
     130             :         break;
     131             :     case ADDED_SNAME:
     132           0 :         ret = lh_strhash(a->sn);
     133           0 :         break;
     134             :     case ADDED_LNAME:
     135           0 :         ret = lh_strhash(a->ln);
     136           0 :         break;
     137             :     case ADDED_NID:
     138           0 :         ret = a->nid;
     139           0 :         break;
     140             :     default:
     141             :         /* abort(); */
     142             :         return 0;
     143             :     }
     144           0 :     ret &= 0x3fffffffL;
     145           0 :     ret |= ((unsigned long)ca->type) << 30L;
     146           0 :     return (ret);
     147             : }
     148             : 
     149           0 : static IMPLEMENT_LHASH_HASH_FN(added_obj, ADDED_OBJ)
     150             : 
     151           0 : static int added_obj_cmp(const ADDED_OBJ *ca, const ADDED_OBJ *cb)
     152             : {
     153             :     ASN1_OBJECT *a, *b;
     154             :     int i;
     155             : 
     156           0 :     i = ca->type - cb->type;
     157           0 :     if (i)
     158             :         return (i);
     159           0 :     a = ca->obj;
     160           0 :     b = cb->obj;
     161           0 :     switch (ca->type) {
     162             :     case ADDED_DATA:
     163           0 :         i = (a->length - b->length);
     164           0 :         if (i)
     165             :             return (i);
     166           0 :         return (memcmp(a->data, b->data, (size_t)a->length));
     167             :     case ADDED_SNAME:
     168           0 :         if (a->sn == NULL)
     169             :             return (-1);
     170           0 :         else if (b->sn == NULL)
     171             :             return (1);
     172             :         else
     173           0 :             return (strcmp(a->sn, b->sn));
     174             :     case ADDED_LNAME:
     175           0 :         if (a->ln == NULL)
     176             :             return (-1);
     177           0 :         else if (b->ln == NULL)
     178             :             return (1);
     179             :         else
     180           0 :             return (strcmp(a->ln, b->ln));
     181             :     case ADDED_NID:
     182           0 :         return (a->nid - b->nid);
     183             :     default:
     184             :         /* abort(); */
     185             :         return 0;
     186             :     }
     187             : }
     188             : 
     189           0 : static IMPLEMENT_LHASH_COMP_FN(added_obj, ADDED_OBJ)
     190             : 
     191           0 : static int init_added(void)
     192             : {
     193           0 :     if (added != NULL)
     194             :         return (1);
     195           0 :     added = lh_ADDED_OBJ_new();
     196           0 :     return (added != NULL);
     197             : }
     198             : 
     199             : static void cleanup1_doall(ADDED_OBJ *a)
     200             : {
     201           0 :     a->obj->nid = 0;
     202           0 :     a->obj->flags |= ASN1_OBJECT_FLAG_DYNAMIC |
     203             :         ASN1_OBJECT_FLAG_DYNAMIC_STRINGS | ASN1_OBJECT_FLAG_DYNAMIC_DATA;
     204             : }
     205             : 
     206             : static void cleanup2_doall(ADDED_OBJ *a)
     207             : {
     208           0 :     a->obj->nid++;
     209             : }
     210             : 
     211           0 : static void cleanup3_doall(ADDED_OBJ *a)
     212             : {
     213           0 :     if (--a->obj->nid == 0)
     214           0 :         ASN1_OBJECT_free(a->obj);
     215           0 :     OPENSSL_free(a);
     216           0 : }
     217             : 
     218           0 : static IMPLEMENT_LHASH_DOALL_FN(cleanup1, ADDED_OBJ)
     219           0 : static IMPLEMENT_LHASH_DOALL_FN(cleanup2, ADDED_OBJ)
     220           0 : static IMPLEMENT_LHASH_DOALL_FN(cleanup3, ADDED_OBJ)
     221             : 
     222             : /*
     223             :  * The purpose of obj_cleanup_defer is to avoid EVP_cleanup() attempting to
     224             :  * use freed up OIDs. If neccessary the actual freeing up of OIDs is delayed.
     225             :  */
     226             : int obj_cleanup_defer = 0;
     227             : 
     228       17908 : void check_defer(int nid)
     229             : {
     230       17908 :     if (!obj_cleanup_defer && nid >= NUM_NID)
     231           0 :         obj_cleanup_defer = 1;
     232       17908 : }
     233             : 
     234           0 : void OBJ_cleanup(void)
     235             : {
     236           0 :     if (obj_cleanup_defer) {
     237           0 :         obj_cleanup_defer = 2;
     238           0 :         return;
     239             :     }
     240           0 :     if (added == NULL)
     241             :         return;
     242           0 :     lh_ADDED_OBJ_down_load(added) = 0;
     243           0 :     lh_ADDED_OBJ_doall(added, LHASH_DOALL_FN(cleanup1)); /* zero counters */
     244           0 :     lh_ADDED_OBJ_doall(added, LHASH_DOALL_FN(cleanup2)); /* set counters */
     245           0 :     lh_ADDED_OBJ_doall(added, LHASH_DOALL_FN(cleanup3)); /* free objects */
     246           0 :     lh_ADDED_OBJ_free(added);
     247           0 :     added = NULL;
     248             : }
     249             : 
     250           0 : int OBJ_new_nid(int num)
     251             : {
     252             :     int i;
     253             : 
     254           0 :     i = new_nid;
     255           0 :     new_nid += num;
     256           0 :     return (i);
     257             : }
     258             : 
     259           0 : int OBJ_add_object(const ASN1_OBJECT *obj)
     260             : {
     261             :     ASN1_OBJECT *o;
     262           0 :     ADDED_OBJ *ao[4] = { NULL, NULL, NULL, NULL }, *aop;
     263             :     int i;
     264             : 
     265           0 :     if (added == NULL)
     266           0 :         if (!init_added())
     267             :             return (0);
     268           0 :     if ((o = OBJ_dup(obj)) == NULL)
     269             :         goto err;
     270           0 :     if (!(ao[ADDED_NID] = (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
     271             :         goto err2;
     272           0 :     if ((o->length != 0) && (obj->data != NULL))
     273           0 :         if (!
     274           0 :             (ao[ADDED_DATA] = (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
     275             :             goto err2;
     276           0 :     if (o->sn != NULL)
     277           0 :         if (!
     278           0 :             (ao[ADDED_SNAME] =
     279           0 :              (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
     280             :             goto err2;
     281           0 :     if (o->ln != NULL)
     282           0 :         if (!
     283           0 :             (ao[ADDED_LNAME] =
     284           0 :              (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
     285             :             goto err2;
     286             : 
     287           0 :     for (i = ADDED_DATA; i <= ADDED_NID; i++) {
     288           0 :         if (ao[i] != NULL) {
     289           0 :             ao[i]->type = i;
     290           0 :             ao[i]->obj = o;
     291           0 :             aop = lh_ADDED_OBJ_insert(added, ao[i]);
     292             :             /* memory leak, buit should not normally matter */
     293           0 :             if (aop != NULL)
     294           0 :                 OPENSSL_free(aop);
     295             :         }
     296             :     }
     297           0 :     o->flags &=
     298             :         ~(ASN1_OBJECT_FLAG_DYNAMIC | ASN1_OBJECT_FLAG_DYNAMIC_STRINGS |
     299             :           ASN1_OBJECT_FLAG_DYNAMIC_DATA);
     300             : 
     301           0 :     return (o->nid);
     302             :  err2:
     303           0 :     OBJerr(OBJ_F_OBJ_ADD_OBJECT, ERR_R_MALLOC_FAILURE);
     304             :  err:
     305           0 :     for (i = ADDED_DATA; i <= ADDED_NID; i++)
     306           0 :         if (ao[i] != NULL)
     307           0 :             OPENSSL_free(ao[i]);
     308           0 :     if (o != NULL)
     309           0 :         OPENSSL_free(o);
     310             :     return (NID_undef);
     311             : }
     312             : 
     313       40106 : ASN1_OBJECT *OBJ_nid2obj(int n)
     314             : {
     315             :     ADDED_OBJ ad, *adp;
     316             :     ASN1_OBJECT ob;
     317             : 
     318       40106 :     if ((n >= 0) && (n < NUM_NID)) {
     319       40106 :         if ((n != NID_undef) && (nid_objs[n].nid == NID_undef)) {
     320           0 :             OBJerr(OBJ_F_OBJ_NID2OBJ, OBJ_R_UNKNOWN_NID);
     321           0 :             return (NULL);
     322             :         }
     323       40106 :         return ((ASN1_OBJECT *)&(nid_objs[n]));
     324           0 :     } else if (added == NULL)
     325             :         return (NULL);
     326             :     else {
     327           0 :         ad.type = ADDED_NID;
     328           0 :         ad.obj = &ob;
     329           0 :         ob.nid = n;
     330           0 :         adp = lh_ADDED_OBJ_retrieve(added, &ad);
     331           0 :         if (adp != NULL)
     332           0 :             return (adp->obj);
     333             :         else {
     334           0 :             OBJerr(OBJ_F_OBJ_NID2OBJ, OBJ_R_UNKNOWN_NID);
     335           0 :             return (NULL);
     336             :         }
     337             :     }
     338             : }
     339             : 
     340       26247 : const char *OBJ_nid2sn(int n)
     341             : {
     342             :     ADDED_OBJ ad, *adp;
     343             :     ASN1_OBJECT ob;
     344             : 
     345       26247 :     if ((n >= 0) && (n < NUM_NID)) {
     346       26247 :         if ((n != NID_undef) && (nid_objs[n].nid == NID_undef)) {
     347           0 :             OBJerr(OBJ_F_OBJ_NID2SN, OBJ_R_UNKNOWN_NID);
     348           0 :             return (NULL);
     349             :         }
     350       26247 :         return (nid_objs[n].sn);
     351           0 :     } else if (added == NULL)
     352             :         return (NULL);
     353             :     else {
     354           0 :         ad.type = ADDED_NID;
     355           0 :         ad.obj = &ob;
     356           0 :         ob.nid = n;
     357           0 :         adp = lh_ADDED_OBJ_retrieve(added, &ad);
     358           0 :         if (adp != NULL)
     359           0 :             return (adp->obj->sn);
     360             :         else {
     361           0 :             OBJerr(OBJ_F_OBJ_NID2SN, OBJ_R_UNKNOWN_NID);
     362           0 :             return (NULL);
     363             :         }
     364             :     }
     365             : }
     366             : 
     367       17908 : const char *OBJ_nid2ln(int n)
     368             : {
     369             :     ADDED_OBJ ad, *adp;
     370             :     ASN1_OBJECT ob;
     371             : 
     372       17908 :     if ((n >= 0) && (n < NUM_NID)) {
     373       17908 :         if ((n != NID_undef) && (nid_objs[n].nid == NID_undef)) {
     374           0 :             OBJerr(OBJ_F_OBJ_NID2LN, OBJ_R_UNKNOWN_NID);
     375           0 :             return (NULL);
     376             :         }
     377       17908 :         return (nid_objs[n].ln);
     378           0 :     } else if (added == NULL)
     379             :         return (NULL);
     380             :     else {
     381           0 :         ad.type = ADDED_NID;
     382           0 :         ad.obj = &ob;
     383           0 :         ob.nid = n;
     384           0 :         adp = lh_ADDED_OBJ_retrieve(added, &ad);
     385           0 :         if (adp != NULL)
     386           0 :             return (adp->obj->ln);
     387             :         else {
     388           0 :             OBJerr(OBJ_F_OBJ_NID2LN, OBJ_R_UNKNOWN_NID);
     389           0 :             return (NULL);
     390             :         }
     391             :     }
     392             : }
     393             : 
     394      333406 : static int obj_cmp(const ASN1_OBJECT *const *ap, const unsigned int *bp)
     395             : {
     396             :     int j;
     397      333406 :     const ASN1_OBJECT *a = *ap;
     398      333406 :     const ASN1_OBJECT *b = &nid_objs[*bp];
     399             : 
     400      333406 :     j = (a->length - b->length);
     401      333406 :     if (j)
     402             :         return (j);
     403      214129 :     if (a->length == 0)
     404             :         return 0;
     405      214129 :     return (memcmp(a->data, b->data, a->length));
     406             : }
     407             : 
     408      333406 : IMPLEMENT_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, obj);
     409             : 
     410       39269 : int OBJ_obj2nid(const ASN1_OBJECT *a)
     411             : {
     412             :     const unsigned int *op;
     413             :     ADDED_OBJ ad, *adp;
     414             : 
     415       39269 :     if (a == NULL)
     416             :         return (NID_undef);
     417       39269 :     if (a->nid != 0)
     418             :         return (a->nid);
     419             : 
     420       39269 :     if (a->length == 0)
     421             :         return NID_undef;
     422             : 
     423       39269 :     if (added != NULL) {
     424           0 :         ad.type = ADDED_DATA;
     425           0 :         ad.obj = (ASN1_OBJECT *)a; /* XXX: ugly but harmless */
     426           0 :         adp = lh_ADDED_OBJ_retrieve(added, &ad);
     427           0 :         if (adp != NULL)
     428           0 :             return (adp->obj->nid);
     429             :     }
     430             :     op = OBJ_bsearch_obj(&a, obj_objs, NUM_OBJ);
     431       39269 :     if (op == NULL)
     432             :         return (NID_undef);
     433       39269 :     return (nid_objs[*op].nid);
     434             : }
     435             : 
     436             : /*
     437             :  * Convert an object name into an ASN1_OBJECT if "noname" is not set then
     438             :  * search for short and long names first. This will convert the "dotted" form
     439             :  * into an object: unlike OBJ_txt2nid it can be used with any objects, not
     440             :  * just registered ones.
     441             :  */
     442             : 
     443           0 : ASN1_OBJECT *OBJ_txt2obj(const char *s, int no_name)
     444             : {
     445             :     int nid = NID_undef;
     446             :     ASN1_OBJECT *op = NULL;
     447             :     unsigned char *buf;
     448             :     unsigned char *p;
     449             :     const unsigned char *cp;
     450             :     int i, j;
     451             : 
     452           0 :     if (!no_name) {
     453           0 :         if (((nid = OBJ_sn2nid(s)) != NID_undef) ||
     454             :             ((nid = OBJ_ln2nid(s)) != NID_undef))
     455           0 :             return OBJ_nid2obj(nid);
     456             :     }
     457             : 
     458             :     /* Work out size of content octets */
     459           0 :     i = a2d_ASN1_OBJECT(NULL, 0, s, -1);
     460           0 :     if (i <= 0) {
     461             :         /* Don't clear the error */
     462             :         /*
     463             :          * ERR_clear_error();
     464             :          */
     465             :         return NULL;
     466             :     }
     467             :     /* Work out total size */
     468           0 :     j = ASN1_object_size(0, i, V_ASN1_OBJECT);
     469             : 
     470           0 :     if ((buf = (unsigned char *)OPENSSL_malloc(j)) == NULL)
     471             :         return NULL;
     472             : 
     473           0 :     p = buf;
     474             :     /* Write out tag+length */
     475           0 :     ASN1_put_object(&p, 0, i, V_ASN1_OBJECT, V_ASN1_UNIVERSAL);
     476             :     /* Write out contents */
     477           0 :     a2d_ASN1_OBJECT(p, i, s, -1);
     478             : 
     479           0 :     cp = buf;
     480           0 :     op = d2i_ASN1_OBJECT(NULL, &cp, j);
     481           0 :     OPENSSL_free(buf);
     482           0 :     return op;
     483             : }
     484             : 
     485           0 : int OBJ_obj2txt(char *buf, int buf_len, const ASN1_OBJECT *a, int no_name)
     486             : {
     487             :     int i, n = 0, len, nid, first, use_bn;
     488             :     BIGNUM *bl;
     489             :     unsigned long l;
     490             :     const unsigned char *p;
     491             :     char tbuf[DECIMAL_SIZE(i) + DECIMAL_SIZE(l) + 2];
     492             : 
     493             :     /* Ensure that, at every state, |buf| is NUL-terminated. */
     494           0 :     if (buf && buf_len > 0)
     495           0 :         buf[0] = '\0';
     496             : 
     497           0 :     if ((a == NULL) || (a->data == NULL))
     498             :         return (0);
     499             : 
     500           0 :     if (!no_name && (nid = OBJ_obj2nid(a)) != NID_undef) {
     501             :         const char *s;
     502           0 :         s = OBJ_nid2ln(nid);
     503           0 :         if (s == NULL)
     504           0 :             s = OBJ_nid2sn(nid);
     505           0 :         if (s) {
     506           0 :             if (buf)
     507           0 :                 BUF_strlcpy(buf, s, buf_len);
     508           0 :             n = strlen(s);
     509           0 :             return n;
     510             :         }
     511             :     }
     512             : 
     513           0 :     len = a->length;
     514           0 :     p = a->data;
     515             : 
     516             :     first = 1;
     517             :     bl = NULL;
     518             : 
     519           0 :     while (len > 0) {
     520             :         l = 0;
     521             :         use_bn = 0;
     522             :         for (;;) {
     523           0 :             unsigned char c = *p++;
     524           0 :             len--;
     525           0 :             if ((len == 0) && (c & 0x80))
     526             :                 goto err;
     527           0 :             if (use_bn) {
     528           0 :                 if (!BN_add_word(bl, c & 0x7f))
     529             :                     goto err;
     530             :             } else
     531           0 :                 l |= c & 0x7f;
     532           0 :             if (!(c & 0x80))
     533             :                 break;
     534           0 :             if (!use_bn && (l > (ULONG_MAX >> 7L))) {
     535           0 :                 if (!bl && !(bl = BN_new()))
     536             :                     goto err;
     537           0 :                 if (!BN_set_word(bl, l))
     538             :                     goto err;
     539             :                 use_bn = 1;
     540             :             }
     541           0 :             if (use_bn) {
     542           0 :                 if (!BN_lshift(bl, bl, 7))
     543             :                     goto err;
     544             :             } else
     545           0 :                 l <<= 7L;
     546             :         }
     547             : 
     548           0 :         if (first) {
     549             :             first = 0;
     550           0 :             if (l >= 80) {
     551             :                 i = 2;
     552           0 :                 if (use_bn) {
     553           0 :                     if (!BN_sub_word(bl, 80))
     554             :                         goto err;
     555             :                 } else
     556           0 :                     l -= 80;
     557             :             } else {
     558           0 :                 i = (int)(l / 40);
     559           0 :                 l -= (long)(i * 40);
     560             :             }
     561           0 :             if (buf && (buf_len > 1)) {
     562           0 :                 *buf++ = i + '0';
     563           0 :                 *buf = '\0';
     564           0 :                 buf_len--;
     565             :             }
     566           0 :             n++;
     567             :         }
     568             : 
     569           0 :         if (use_bn) {
     570             :             char *bndec;
     571           0 :             bndec = BN_bn2dec(bl);
     572           0 :             if (!bndec)
     573             :                 goto err;
     574           0 :             i = strlen(bndec);
     575           0 :             if (buf) {
     576           0 :                 if (buf_len > 1) {
     577           0 :                     *buf++ = '.';
     578           0 :                     *buf = '\0';
     579           0 :                     buf_len--;
     580             :                 }
     581           0 :                 BUF_strlcpy(buf, bndec, buf_len);
     582           0 :                 if (i > buf_len) {
     583           0 :                     buf += buf_len;
     584             :                     buf_len = 0;
     585             :                 } else {
     586           0 :                     buf += i;
     587           0 :                     buf_len -= i;
     588             :                 }
     589             :             }
     590           0 :             n++;
     591           0 :             n += i;
     592           0 :             OPENSSL_free(bndec);
     593             :         } else {
     594           0 :             BIO_snprintf(tbuf, sizeof tbuf, ".%lu", l);
     595           0 :             i = strlen(tbuf);
     596           0 :             if (buf && (buf_len > 0)) {
     597           0 :                 BUF_strlcpy(buf, tbuf, buf_len);
     598           0 :                 if (i > buf_len) {
     599           0 :                     buf += buf_len;
     600             :                     buf_len = 0;
     601             :                 } else {
     602           0 :                     buf += i;
     603           0 :                     buf_len -= i;
     604             :                 }
     605             :             }
     606           0 :             n += i;
     607             :             l = 0;
     608             :         }
     609             :     }
     610             : 
     611           0 :     if (bl)
     612           0 :         BN_free(bl);
     613           0 :     return n;
     614             : 
     615             :  err:
     616           0 :     if (bl)
     617           0 :         BN_free(bl);
     618             :     return -1;
     619             : }
     620             : 
     621           0 : int OBJ_txt2nid(const char *s)
     622             : {
     623             :     ASN1_OBJECT *obj;
     624             :     int nid;
     625           0 :     obj = OBJ_txt2obj(s, 0);
     626           0 :     nid = OBJ_obj2nid(obj);
     627           0 :     ASN1_OBJECT_free(obj);
     628           0 :     return nid;
     629             : }
     630             : 
     631           0 : int OBJ_ln2nid(const char *s)
     632             : {
     633             :     ASN1_OBJECT o;
     634           0 :     const ASN1_OBJECT *oo = &o;
     635             :     ADDED_OBJ ad, *adp;
     636             :     const unsigned int *op;
     637             : 
     638           0 :     o.ln = s;
     639           0 :     if (added != NULL) {
     640           0 :         ad.type = ADDED_LNAME;
     641           0 :         ad.obj = &o;
     642           0 :         adp = lh_ADDED_OBJ_retrieve(added, &ad);
     643           0 :         if (adp != NULL)
     644           0 :             return (adp->obj->nid);
     645             :     }
     646             :     op = OBJ_bsearch_ln(&oo, ln_objs, NUM_LN);
     647           0 :     if (op == NULL)
     648             :         return (NID_undef);
     649           0 :     return (nid_objs[*op].nid);
     650             : }
     651             : 
     652           0 : int OBJ_sn2nid(const char *s)
     653             : {
     654             :     ASN1_OBJECT o;
     655           0 :     const ASN1_OBJECT *oo = &o;
     656             :     ADDED_OBJ ad, *adp;
     657             :     const unsigned int *op;
     658             : 
     659           0 :     o.sn = s;
     660           0 :     if (added != NULL) {
     661           0 :         ad.type = ADDED_SNAME;
     662           0 :         ad.obj = &o;
     663           0 :         adp = lh_ADDED_OBJ_retrieve(added, &ad);
     664           0 :         if (adp != NULL)
     665           0 :             return (adp->obj->nid);
     666             :     }
     667             :     op = OBJ_bsearch_sn(&oo, sn_objs, NUM_SN);
     668           0 :     if (op == NULL)
     669             :         return (NID_undef);
     670           0 :     return (nid_objs[*op].nid);
     671             : }
     672             : 
     673       26358 : const void *OBJ_bsearch_(const void *key, const void *base, int num, int size,
     674             :                          int (*cmp) (const void *, const void *))
     675             : {
     676       65627 :     return OBJ_bsearch_ex_(key, base, num, size, cmp, 0);
     677             : }
     678             : 
     679       67911 : const void *OBJ_bsearch_ex_(const void *key, const void *base_, int num,
     680             :                             int size,
     681             :                             int (*cmp) (const void *, const void *),
     682             :                             int flags)
     683             : {
     684             :     const char *base = base_;
     685             :     int l, h, i = 0, c = 0;
     686             :     const char *p = NULL;
     687             : 
     688       67911 :     if (num == 0)
     689             :         return (NULL);
     690             :     l = 0;
     691             :     h = num;
     692      435678 :     while (l < h) {
     693      434932 :         i = (l + h) / 2;
     694      434932 :         p = &(base[i * size]);
     695      434932 :         c = (*cmp) (key, p);
     696      434932 :         if (c < 0)
     697             :             h = i;
     698      209107 :         else if (c > 0)
     699      143486 :             l = i + 1;
     700             :         else
     701             :             break;
     702             :     }
     703             : #ifdef CHARSET_EBCDIC
     704             :     /*
     705             :      * THIS IS A KLUDGE - Because the *_obj is sorted in ASCII order, and I
     706             :      * don't have perl (yet), we revert to a *LINEAR* search when the object
     707             :      * wasn't found in the binary search.
     708             :      */
     709             :     if (c != 0) {
     710             :         for (i = 0; i < num; ++i) {
     711             :             p = &(base[i * size]);
     712             :             c = (*cmp) (key, p);
     713             :             if (c == 0 || (c < 0 && (flags & OBJ_BSEARCH_VALUE_ON_NOMATCH)))
     714             :                 return p;
     715             :         }
     716             :     }
     717             : #endif
     718       66367 :     if (c != 0 && !(flags & OBJ_BSEARCH_VALUE_ON_NOMATCH))
     719             :         p = NULL;
     720       65621 :     else if (c == 0 && (flags & OBJ_BSEARCH_FIRST_VALUE_ON_MATCH)) {
     721         740 :         while (i > 0 && (*cmp) (key, &(base[(i - 1) * size])) == 0)
     722             :             i--;
     723         740 :         p = &(base[i * size]);
     724             :     }
     725       66367 :     return (p);
     726             : }
     727             : 
     728           0 : int OBJ_create_objects(BIO *in)
     729             : {
     730             :     MS_STATIC char buf[512];
     731             :     int i, num = 0;
     732             :     char *o, *s, *l = NULL;
     733             : 
     734             :     for (;;) {
     735             :         s = o = NULL;
     736           0 :         i = BIO_gets(in, buf, 512);
     737           0 :         if (i <= 0)
     738             :             return (num);
     739           0 :         buf[i - 1] = '\0';
     740           0 :         if (!isalnum((unsigned char)buf[0]))
     741             :             return (num);
     742             :         o = s = buf;
     743           0 :         while (isdigit((unsigned char)*s) || (*s == '.'))
     744           0 :             s++;
     745           0 :         if (*s != '\0') {
     746           0 :             *(s++) = '\0';
     747           0 :             while (isspace((unsigned char)*s))
     748           0 :                 s++;
     749           0 :             if (*s == '\0')
     750             :                 s = NULL;
     751             :             else {
     752             :                 l = s;
     753           0 :                 while ((*l != '\0') && !isspace((unsigned char)*l))
     754           0 :                     l++;
     755           0 :                 if (*l != '\0') {
     756           0 :                     *(l++) = '\0';
     757           0 :                     while (isspace((unsigned char)*l))
     758           0 :                         l++;
     759           0 :                     if (*l == '\0')
     760             :                         l = NULL;
     761             :                 } else
     762             :                     l = NULL;
     763             :             }
     764             :         } else
     765             :             s = NULL;
     766           0 :         if ((o == NULL) || (*o == '\0'))
     767             :             return (num);
     768           0 :         if (!OBJ_create(o, s, l))
     769             :             return (num);
     770           0 :         num++;
     771           0 :     }
     772             :     /* return(num); */
     773             : }
     774             : 
     775           0 : int OBJ_create(const char *oid, const char *sn, const char *ln)
     776             : {
     777             :     int ok = 0;
     778             :     ASN1_OBJECT *op = NULL;
     779             :     unsigned char *buf;
     780             :     int i;
     781             : 
     782           0 :     i = a2d_ASN1_OBJECT(NULL, 0, oid, -1);
     783           0 :     if (i <= 0)
     784             :         return (0);
     785             : 
     786           0 :     if ((buf = (unsigned char *)OPENSSL_malloc(i)) == NULL) {
     787           0 :         OBJerr(OBJ_F_OBJ_CREATE, ERR_R_MALLOC_FAILURE);
     788           0 :         return (0);
     789             :     }
     790           0 :     i = a2d_ASN1_OBJECT(buf, i, oid, -1);
     791           0 :     if (i == 0)
     792             :         goto err;
     793           0 :     op = (ASN1_OBJECT *)ASN1_OBJECT_create(OBJ_new_nid(1), buf, i, sn, ln);
     794           0 :     if (op == NULL)
     795             :         goto err;
     796           0 :     ok = OBJ_add_object(op);
     797             :  err:
     798           0 :     ASN1_OBJECT_free(op);
     799           0 :     OPENSSL_free(buf);
     800           0 :     return (ok);
     801             : }

Generated by: LCOV version 1.10