2
0

obj_dat.c 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772
  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. #include <stdio.h>
  59. #include <ctype.h>
  60. #include <limits.h>
  61. #include "cryptlib.h"
  62. #include <openssl/lhash.h>
  63. #include <openssl/asn1.h>
  64. #include <openssl/objects.h>
  65. #include <openssl/bn.h>
  66. /* obj_dat.h is generated from objects.h by obj_dat.pl */
  67. #ifndef OPENSSL_NO_OBJECT
  68. # include "obj_dat.h"
  69. #else
  70. /* You will have to load all the objects needed manually in the application */
  71. # define NUM_NID 0
  72. # define NUM_SN 0
  73. # define NUM_LN 0
  74. # define NUM_OBJ 0
  75. static unsigned char lvalues[1];
  76. static ASN1_OBJECT nid_objs[1];
  77. static ASN1_OBJECT *sn_objs[1];
  78. static ASN1_OBJECT *ln_objs[1];
  79. static ASN1_OBJECT *obj_objs[1];
  80. #endif
  81. static int sn_cmp(const void *a, const void *b);
  82. static int ln_cmp(const void *a, const void *b);
  83. static int obj_cmp(const void *a, const void *b);
  84. #define ADDED_DATA 0
  85. #define ADDED_SNAME 1
  86. #define ADDED_LNAME 2
  87. #define ADDED_NID 3
  88. typedef struct added_obj_st {
  89. int type;
  90. ASN1_OBJECT *obj;
  91. } ADDED_OBJ;
  92. static int new_nid = NUM_NID;
  93. static LHASH *added = NULL;
  94. static int sn_cmp(const void *a, const void *b)
  95. {
  96. const ASN1_OBJECT *const *ap = a, *const *bp = b;
  97. return (strcmp((*ap)->sn, (*bp)->sn));
  98. }
  99. static int ln_cmp(const void *a, const void *b)
  100. {
  101. const ASN1_OBJECT *const *ap = a, *const *bp = b;
  102. return (strcmp((*ap)->ln, (*bp)->ln));
  103. }
  104. /* static unsigned long add_hash(ADDED_OBJ *ca) */
  105. static unsigned long add_hash(const void *ca_void)
  106. {
  107. const ASN1_OBJECT *a;
  108. int i;
  109. unsigned long ret = 0;
  110. unsigned char *p;
  111. const ADDED_OBJ *ca = (const ADDED_OBJ *)ca_void;
  112. a = ca->obj;
  113. switch (ca->type) {
  114. case ADDED_DATA:
  115. ret = a->length << 20L;
  116. p = (unsigned char *)a->data;
  117. for (i = 0; i < a->length; i++)
  118. ret ^= p[i] << ((i * 3) % 24);
  119. break;
  120. case ADDED_SNAME:
  121. ret = lh_strhash(a->sn);
  122. break;
  123. case ADDED_LNAME:
  124. ret = lh_strhash(a->ln);
  125. break;
  126. case ADDED_NID:
  127. ret = a->nid;
  128. break;
  129. default:
  130. /* abort(); */
  131. return 0;
  132. }
  133. ret &= 0x3fffffffL;
  134. ret |= ca->type << 30L;
  135. return (ret);
  136. }
  137. /* static int add_cmp(ADDED_OBJ *ca, ADDED_OBJ *cb) */
  138. static int add_cmp(const void *ca_void, const void *cb_void)
  139. {
  140. ASN1_OBJECT *a, *b;
  141. int i;
  142. const ADDED_OBJ *ca = (const ADDED_OBJ *)ca_void;
  143. const ADDED_OBJ *cb = (const ADDED_OBJ *)cb_void;
  144. i = ca->type - cb->type;
  145. if (i)
  146. return (i);
  147. a = ca->obj;
  148. b = cb->obj;
  149. switch (ca->type) {
  150. case ADDED_DATA:
  151. i = (a->length - b->length);
  152. if (i)
  153. return (i);
  154. return (memcmp(a->data, b->data, (size_t)a->length));
  155. case ADDED_SNAME:
  156. if (a->sn == NULL)
  157. return (-1);
  158. else if (b->sn == NULL)
  159. return (1);
  160. else
  161. return (strcmp(a->sn, b->sn));
  162. case ADDED_LNAME:
  163. if (a->ln == NULL)
  164. return (-1);
  165. else if (b->ln == NULL)
  166. return (1);
  167. else
  168. return (strcmp(a->ln, b->ln));
  169. case ADDED_NID:
  170. return (a->nid - b->nid);
  171. default:
  172. /* abort(); */
  173. return 0;
  174. }
  175. }
  176. static int init_added(void)
  177. {
  178. if (added != NULL)
  179. return (1);
  180. added = lh_new(add_hash, add_cmp);
  181. return (added != NULL);
  182. }
  183. static void cleanup1(ADDED_OBJ *a)
  184. {
  185. a->obj->nid = 0;
  186. a->obj->flags |= ASN1_OBJECT_FLAG_DYNAMIC |
  187. ASN1_OBJECT_FLAG_DYNAMIC_STRINGS | ASN1_OBJECT_FLAG_DYNAMIC_DATA;
  188. }
  189. static void cleanup2(ADDED_OBJ *a)
  190. {
  191. a->obj->nid++;
  192. }
  193. static void cleanup3(ADDED_OBJ *a)
  194. {
  195. if (--a->obj->nid == 0)
  196. ASN1_OBJECT_free(a->obj);
  197. OPENSSL_free(a);
  198. }
  199. static IMPLEMENT_LHASH_DOALL_FN(cleanup1, ADDED_OBJ *)
  200. static IMPLEMENT_LHASH_DOALL_FN(cleanup2, ADDED_OBJ *)
  201. static IMPLEMENT_LHASH_DOALL_FN(cleanup3, ADDED_OBJ *)
  202. void OBJ_cleanup(void)
  203. {
  204. if (added == NULL)
  205. return;
  206. added->down_load = 0;
  207. lh_doall(added, LHASH_DOALL_FN(cleanup1)); /* zero counters */
  208. lh_doall(added, LHASH_DOALL_FN(cleanup2)); /* set counters */
  209. lh_doall(added, LHASH_DOALL_FN(cleanup3)); /* free objects */
  210. lh_free(added);
  211. added = NULL;
  212. }
  213. int OBJ_new_nid(int num)
  214. {
  215. int i;
  216. i = new_nid;
  217. new_nid += num;
  218. return (i);
  219. }
  220. int OBJ_add_object(const ASN1_OBJECT *obj)
  221. {
  222. ASN1_OBJECT *o;
  223. ADDED_OBJ *ao[4] = { NULL, NULL, NULL, NULL }, *aop;
  224. int i;
  225. if (added == NULL)
  226. if (!init_added())
  227. return (0);
  228. if ((o = OBJ_dup(obj)) == NULL)
  229. goto err;
  230. if (!(ao[ADDED_NID] = (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
  231. goto err2;
  232. if ((o->length != 0) && (obj->data != NULL))
  233. if (!
  234. (ao[ADDED_DATA] = (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
  235. goto err2;
  236. if (o->sn != NULL)
  237. if (!
  238. (ao[ADDED_SNAME] =
  239. (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
  240. goto err2;
  241. if (o->ln != NULL)
  242. if (!
  243. (ao[ADDED_LNAME] =
  244. (ADDED_OBJ *)OPENSSL_malloc(sizeof(ADDED_OBJ))))
  245. goto err2;
  246. for (i = ADDED_DATA; i <= ADDED_NID; i++) {
  247. if (ao[i] != NULL) {
  248. ao[i]->type = i;
  249. ao[i]->obj = o;
  250. aop = (ADDED_OBJ *)lh_insert(added, ao[i]);
  251. /* memory leak, buit should not normally matter */
  252. if (aop != NULL)
  253. OPENSSL_free(aop);
  254. }
  255. }
  256. o->flags &=
  257. ~(ASN1_OBJECT_FLAG_DYNAMIC | ASN1_OBJECT_FLAG_DYNAMIC_STRINGS |
  258. ASN1_OBJECT_FLAG_DYNAMIC_DATA);
  259. return (o->nid);
  260. err2:
  261. OBJerr(OBJ_F_OBJ_ADD_OBJECT, ERR_R_MALLOC_FAILURE);
  262. err:
  263. for (i = ADDED_DATA; i <= ADDED_NID; i++)
  264. if (ao[i] != NULL)
  265. OPENSSL_free(ao[i]);
  266. if (o != NULL)
  267. OPENSSL_free(o);
  268. return (NID_undef);
  269. }
  270. ASN1_OBJECT *OBJ_nid2obj(int n)
  271. {
  272. ADDED_OBJ ad, *adp;
  273. ASN1_OBJECT ob;
  274. if ((n >= 0) && (n < NUM_NID)) {
  275. if ((n != NID_undef) && (nid_objs[n].nid == NID_undef)) {
  276. OBJerr(OBJ_F_OBJ_NID2OBJ, OBJ_R_UNKNOWN_NID);
  277. return (NULL);
  278. }
  279. return ((ASN1_OBJECT *)&(nid_objs[n]));
  280. } else if (added == NULL)
  281. return (NULL);
  282. else {
  283. ad.type = ADDED_NID;
  284. ad.obj = &ob;
  285. ob.nid = n;
  286. adp = (ADDED_OBJ *)lh_retrieve(added, &ad);
  287. if (adp != NULL)
  288. return (adp->obj);
  289. else {
  290. OBJerr(OBJ_F_OBJ_NID2OBJ, OBJ_R_UNKNOWN_NID);
  291. return (NULL);
  292. }
  293. }
  294. }
  295. const char *OBJ_nid2sn(int n)
  296. {
  297. ADDED_OBJ ad, *adp;
  298. ASN1_OBJECT ob;
  299. if ((n >= 0) && (n < NUM_NID)) {
  300. if ((n != NID_undef) && (nid_objs[n].nid == NID_undef)) {
  301. OBJerr(OBJ_F_OBJ_NID2SN, OBJ_R_UNKNOWN_NID);
  302. return (NULL);
  303. }
  304. return (nid_objs[n].sn);
  305. } else if (added == NULL)
  306. return (NULL);
  307. else {
  308. ad.type = ADDED_NID;
  309. ad.obj = &ob;
  310. ob.nid = n;
  311. adp = (ADDED_OBJ *)lh_retrieve(added, &ad);
  312. if (adp != NULL)
  313. return (adp->obj->sn);
  314. else {
  315. OBJerr(OBJ_F_OBJ_NID2SN, OBJ_R_UNKNOWN_NID);
  316. return (NULL);
  317. }
  318. }
  319. }
  320. const char *OBJ_nid2ln(int n)
  321. {
  322. ADDED_OBJ ad, *adp;
  323. ASN1_OBJECT ob;
  324. if ((n >= 0) && (n < NUM_NID)) {
  325. if ((n != NID_undef) && (nid_objs[n].nid == NID_undef)) {
  326. OBJerr(OBJ_F_OBJ_NID2LN, OBJ_R_UNKNOWN_NID);
  327. return (NULL);
  328. }
  329. return (nid_objs[n].ln);
  330. } else if (added == NULL)
  331. return (NULL);
  332. else {
  333. ad.type = ADDED_NID;
  334. ad.obj = &ob;
  335. ob.nid = n;
  336. adp = (ADDED_OBJ *)lh_retrieve(added, &ad);
  337. if (adp != NULL)
  338. return (adp->obj->ln);
  339. else {
  340. OBJerr(OBJ_F_OBJ_NID2LN, OBJ_R_UNKNOWN_NID);
  341. return (NULL);
  342. }
  343. }
  344. }
  345. int OBJ_obj2nid(const ASN1_OBJECT *a)
  346. {
  347. ASN1_OBJECT **op;
  348. ADDED_OBJ ad, *adp;
  349. if (a == NULL)
  350. return (NID_undef);
  351. if (a->nid != 0)
  352. return (a->nid);
  353. if (added != NULL) {
  354. ad.type = ADDED_DATA;
  355. ad.obj = (ASN1_OBJECT *)a; /* XXX: ugly but harmless */
  356. adp = (ADDED_OBJ *)lh_retrieve(added, &ad);
  357. if (adp != NULL)
  358. return (adp->obj->nid);
  359. }
  360. op = (ASN1_OBJECT **)OBJ_bsearch((const char *)&a, (const char *)obj_objs,
  361. NUM_OBJ, sizeof(ASN1_OBJECT *), obj_cmp);
  362. if (op == NULL)
  363. return (NID_undef);
  364. return ((*op)->nid);
  365. }
  366. /*
  367. * Convert an object name into an ASN1_OBJECT if "noname" is not set then
  368. * search for short and long names first. This will convert the "dotted" form
  369. * into an object: unlike OBJ_txt2nid it can be used with any objects, not
  370. * just registered ones.
  371. */
  372. ASN1_OBJECT *OBJ_txt2obj(const char *s, int no_name)
  373. {
  374. int nid = NID_undef;
  375. ASN1_OBJECT *op = NULL;
  376. unsigned char *buf;
  377. unsigned char *p;
  378. const unsigned char *cp;
  379. int i, j;
  380. if (!no_name) {
  381. if (((nid = OBJ_sn2nid(s)) != NID_undef) ||
  382. ((nid = OBJ_ln2nid(s)) != NID_undef))
  383. return OBJ_nid2obj(nid);
  384. }
  385. /* Work out size of content octets */
  386. i = a2d_ASN1_OBJECT(NULL, 0, s, -1);
  387. if (i <= 0) {
  388. /* Don't clear the error */
  389. /*
  390. * ERR_clear_error();
  391. */
  392. return NULL;
  393. }
  394. /* Work out total size */
  395. j = ASN1_object_size(0, i, V_ASN1_OBJECT);
  396. if ((buf = (unsigned char *)OPENSSL_malloc(j)) == NULL)
  397. return NULL;
  398. p = buf;
  399. /* Write out tag+length */
  400. ASN1_put_object(&p, 0, i, V_ASN1_OBJECT, V_ASN1_UNIVERSAL);
  401. /* Write out contents */
  402. a2d_ASN1_OBJECT(p, i, s, -1);
  403. cp = buf;
  404. op = d2i_ASN1_OBJECT(NULL, &cp, j);
  405. OPENSSL_free(buf);
  406. return op;
  407. }
  408. int OBJ_obj2txt(char *buf, int buf_len, const ASN1_OBJECT *a, int no_name)
  409. {
  410. int i, n = 0, len, nid, first, use_bn;
  411. BIGNUM *bl;
  412. unsigned long l;
  413. unsigned char *p;
  414. char tbuf[DECIMAL_SIZE(i) + DECIMAL_SIZE(l) + 2];
  415. /* Ensure that, at every state, |buf| is NUL-terminated. */
  416. if (buf && buf_len > 0)
  417. buf[0] = '\0';
  418. if ((a == NULL) || (a->data == NULL))
  419. return (0);
  420. if (!no_name && (nid = OBJ_obj2nid(a)) != NID_undef) {
  421. const char *s;
  422. s = OBJ_nid2ln(nid);
  423. if (s == NULL)
  424. s = OBJ_nid2sn(nid);
  425. if (s) {
  426. if (buf)
  427. BUF_strlcpy(buf, s, buf_len);
  428. n = strlen(s);
  429. return n;
  430. }
  431. }
  432. len = a->length;
  433. p = a->data;
  434. first = 1;
  435. bl = NULL;
  436. while (len > 0) {
  437. l = 0;
  438. use_bn = 0;
  439. for (;;) {
  440. unsigned char c = *p++;
  441. len--;
  442. if ((len == 0) && (c & 0x80))
  443. goto err;
  444. if (use_bn) {
  445. if (!BN_add_word(bl, c & 0x7f))
  446. goto err;
  447. } else
  448. l |= c & 0x7f;
  449. if (!(c & 0x80))
  450. break;
  451. if (!use_bn && (l > (ULONG_MAX >> 7L))) {
  452. if (!bl && !(bl = BN_new()))
  453. goto err;
  454. if (!BN_set_word(bl, l))
  455. goto err;
  456. use_bn = 1;
  457. }
  458. if (use_bn) {
  459. if (!BN_lshift(bl, bl, 7))
  460. goto err;
  461. } else
  462. l <<= 7L;
  463. }
  464. if (first) {
  465. first = 0;
  466. if (l >= 80) {
  467. i = 2;
  468. if (use_bn) {
  469. if (!BN_sub_word(bl, 80))
  470. goto err;
  471. } else
  472. l -= 80;
  473. } else {
  474. i = (int)(l / 40);
  475. l -= (long)(i * 40);
  476. }
  477. if (buf && (buf_len > 1)) {
  478. *buf++ = i + '0';
  479. *buf = '\0';
  480. buf_len--;
  481. }
  482. n++;
  483. }
  484. if (use_bn) {
  485. char *bndec;
  486. bndec = BN_bn2dec(bl);
  487. if (!bndec)
  488. goto err;
  489. i = strlen(bndec);
  490. if (buf) {
  491. if (buf_len > 1) {
  492. *buf++ = '.';
  493. *buf = '\0';
  494. buf_len--;
  495. }
  496. BUF_strlcpy(buf, bndec, buf_len);
  497. if (i > buf_len) {
  498. buf += buf_len;
  499. buf_len = 0;
  500. } else {
  501. buf += i;
  502. buf_len -= i;
  503. }
  504. }
  505. n++;
  506. n += i;
  507. OPENSSL_free(bndec);
  508. } else {
  509. BIO_snprintf(tbuf, sizeof tbuf, ".%lu", l);
  510. i = strlen(tbuf);
  511. if (buf && (buf_len > 0)) {
  512. BUF_strlcpy(buf, tbuf, buf_len);
  513. if (i > buf_len) {
  514. buf += buf_len;
  515. buf_len = 0;
  516. } else {
  517. buf += i;
  518. buf_len -= i;
  519. }
  520. }
  521. n += i;
  522. l = 0;
  523. }
  524. }
  525. if (bl)
  526. BN_free(bl);
  527. return n;
  528. err:
  529. if (bl)
  530. BN_free(bl);
  531. return -1;
  532. }
  533. int OBJ_txt2nid(const char *s)
  534. {
  535. ASN1_OBJECT *obj;
  536. int nid;
  537. obj = OBJ_txt2obj(s, 0);
  538. nid = OBJ_obj2nid(obj);
  539. ASN1_OBJECT_free(obj);
  540. return nid;
  541. }
  542. int OBJ_ln2nid(const char *s)
  543. {
  544. ASN1_OBJECT o, *oo = &o, **op;
  545. ADDED_OBJ ad, *adp;
  546. o.ln = s;
  547. if (added != NULL) {
  548. ad.type = ADDED_LNAME;
  549. ad.obj = &o;
  550. adp = (ADDED_OBJ *)lh_retrieve(added, &ad);
  551. if (adp != NULL)
  552. return (adp->obj->nid);
  553. }
  554. op = (ASN1_OBJECT **)OBJ_bsearch((char *)&oo, (char *)ln_objs, NUM_LN,
  555. sizeof(ASN1_OBJECT *), ln_cmp);
  556. if (op == NULL)
  557. return (NID_undef);
  558. return ((*op)->nid);
  559. }
  560. int OBJ_sn2nid(const char *s)
  561. {
  562. ASN1_OBJECT o, *oo = &o, **op;
  563. ADDED_OBJ ad, *adp;
  564. o.sn = s;
  565. if (added != NULL) {
  566. ad.type = ADDED_SNAME;
  567. ad.obj = &o;
  568. adp = (ADDED_OBJ *)lh_retrieve(added, &ad);
  569. if (adp != NULL)
  570. return (adp->obj->nid);
  571. }
  572. op = (ASN1_OBJECT **)OBJ_bsearch((char *)&oo, (char *)sn_objs, NUM_SN,
  573. sizeof(ASN1_OBJECT *), sn_cmp);
  574. if (op == NULL)
  575. return (NID_undef);
  576. return ((*op)->nid);
  577. }
  578. static int obj_cmp(const void *ap, const void *bp)
  579. {
  580. int j;
  581. const ASN1_OBJECT *a = *(ASN1_OBJECT *const *)ap;
  582. const ASN1_OBJECT *b = *(ASN1_OBJECT *const *)bp;
  583. j = (a->length - b->length);
  584. if (j)
  585. return (j);
  586. return (memcmp(a->data, b->data, a->length));
  587. }
  588. const char *OBJ_bsearch(const char *key, const char *base, int num, int size,
  589. int (*cmp) (const void *, const void *))
  590. {
  591. return OBJ_bsearch_ex(key, base, num, size, cmp, 0);
  592. }
  593. const char *OBJ_bsearch_ex(const char *key, const char *base, int num,
  594. int size, int (*cmp) (const void *, const void *),
  595. int flags)
  596. {
  597. int l, h, i = 0, c = 0;
  598. const char *p = NULL;
  599. if (num == 0)
  600. return (NULL);
  601. l = 0;
  602. h = num;
  603. while (l < h) {
  604. i = (l + h) / 2;
  605. p = &(base[i * size]);
  606. c = (*cmp) (key, p);
  607. if (c < 0)
  608. h = i;
  609. else if (c > 0)
  610. l = i + 1;
  611. else
  612. break;
  613. }
  614. #ifdef CHARSET_EBCDIC
  615. /*
  616. * THIS IS A KLUDGE - Because the *_obj is sorted in ASCII order, and I
  617. * don't have perl (yet), we revert to a *LINEAR* search when the object
  618. * wasn't found in the binary search.
  619. */
  620. if (c != 0) {
  621. for (i = 0; i < num; ++i) {
  622. p = &(base[i * size]);
  623. c = (*cmp) (key, p);
  624. if (c == 0 || (c < 0 && (flags & OBJ_BSEARCH_VALUE_ON_NOMATCH)))
  625. return p;
  626. }
  627. }
  628. #endif
  629. if (c != 0 && !(flags & OBJ_BSEARCH_VALUE_ON_NOMATCH))
  630. p = NULL;
  631. else if (c == 0 && (flags & OBJ_BSEARCH_FIRST_VALUE_ON_MATCH)) {
  632. while (i > 0 && (*cmp) (key, &(base[(i - 1) * size])) == 0)
  633. i--;
  634. p = &(base[i * size]);
  635. }
  636. return (p);
  637. }
  638. int OBJ_create_objects(BIO *in)
  639. {
  640. MS_STATIC char buf[512];
  641. int i, num = 0;
  642. char *o, *s, *l = NULL;
  643. for (;;) {
  644. s = o = NULL;
  645. i = BIO_gets(in, buf, 512);
  646. if (i <= 0)
  647. return (num);
  648. buf[i - 1] = '\0';
  649. if (!isalnum((unsigned char)buf[0]))
  650. return (num);
  651. o = s = buf;
  652. while (isdigit((unsigned char)*s) || (*s == '.'))
  653. s++;
  654. if (*s != '\0') {
  655. *(s++) = '\0';
  656. while (isspace((unsigned char)*s))
  657. s++;
  658. if (*s == '\0')
  659. s = NULL;
  660. else {
  661. l = s;
  662. while ((*l != '\0') && !isspace((unsigned char)*l))
  663. l++;
  664. if (*l != '\0') {
  665. *(l++) = '\0';
  666. while (isspace((unsigned char)*l))
  667. l++;
  668. if (*l == '\0')
  669. l = NULL;
  670. } else
  671. l = NULL;
  672. }
  673. } else
  674. s = NULL;
  675. if ((o == NULL) || (*o == '\0'))
  676. return (num);
  677. if (!OBJ_create(o, s, l))
  678. return (num);
  679. num++;
  680. }
  681. /* return(num); */
  682. }
  683. int OBJ_create(const char *oid, const char *sn, const char *ln)
  684. {
  685. int ok = 0;
  686. ASN1_OBJECT *op = NULL;
  687. unsigned char *buf;
  688. int i;
  689. i = a2d_ASN1_OBJECT(NULL, 0, oid, -1);
  690. if (i <= 0)
  691. return (0);
  692. if ((buf = (unsigned char *)OPENSSL_malloc(i)) == NULL) {
  693. OBJerr(OBJ_F_OBJ_CREATE, ERR_R_MALLOC_FAILURE);
  694. return (0);
  695. }
  696. i = a2d_ASN1_OBJECT(buf, i, oid, -1);
  697. if (i == 0)
  698. goto err;
  699. op = (ASN1_OBJECT *)ASN1_OBJECT_create(OBJ_new_nid(1), buf, i, sn, ln);
  700. if (op == NULL)
  701. goto err;
  702. ok = OBJ_add_object(op);
  703. err:
  704. ASN1_OBJECT_free(op);
  705. OPENSSL_free(buf);
  706. return (ok);
  707. }