Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1318 lines
33 KiB

  1. /* Copyright (C) Boris Nikolaus, Germany, 1996-1997. All rights reserved. */
  2. /* Copyright (C) Microsoft Corporation, 1997-1998. All rights reserved. */
  3. #include "precomp.h"
  4. #define IDCHRSET "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_"
  5. #define INDENT 4
  6. #define TABSIZE 8
  7. static FILE *fout;
  8. static int xcurrindent = 0;
  9. static int xindentflag = 0;
  10. static char *xbuf = 0;
  11. static int xbufsize = 0;
  12. static int xbuflen = 0;
  13. static int ycurrindent = 1;
  14. static char *ybuf = 0;
  15. static int ybufsize = 0;
  16. static int ybuflen = 0;
  17. void xputc(char c);
  18. void xputs(char *s);
  19. void xflush();
  20. void yputc(char c);
  21. void yputs(char *s);
  22. void yflush();
  23. /* set the output file */
  24. void
  25. setoutfile(FILE *f)
  26. {
  27. xflush();
  28. fout = f;
  29. }
  30. /* print indentation up to current indentation level */
  31. static void
  32. findent()
  33. {
  34. int indent;
  35. indent = xcurrindent * INDENT;
  36. while (indent >= TABSIZE) {
  37. xputc('\t');
  38. indent -= TABSIZE;
  39. }
  40. while (indent-- > 0)
  41. xputc(' ');
  42. }
  43. /* print indentation up to current indentation level */
  44. /* but expect one character to be printed already */
  45. static void
  46. findent1()
  47. {
  48. int indent;
  49. indent = xcurrindent * INDENT;
  50. if (indent > 0 && indent < TABSIZE)
  51. indent--;
  52. while (indent >= TABSIZE) {
  53. xputc('\t');
  54. indent -= TABSIZE;
  55. }
  56. while (indent-- > 0)
  57. xputc(' ');
  58. }
  59. /* output function doing indentation automatically */
  60. void
  61. outputv(const char *format, va_list args)
  62. {
  63. static char buf[4098];
  64. static int pos = 0;
  65. char *p, *q;
  66. int l;
  67. /* get the string to write */
  68. vsprintf(buf + pos, format, args);
  69. /* print it line by line */
  70. for (p = buf; *p; p = q) {
  71. q = strchr(p, '\n');
  72. if (!q) {
  73. for (q = buf; *p;)
  74. *q++ = *p++;
  75. *q = 0;
  76. pos = q - buf;
  77. return;
  78. }
  79. *q++ = 0;
  80. /* examine the first character for correct indentation */
  81. if (strchr(IDCHRSET, *p)) {
  82. l = strspn(p, IDCHRSET);
  83. } else if (*p == '{' || *p == '}' || *p == '*' || *p == '&' ||
  84. *p == '(' || *p == ')' || *p == '#') {
  85. l = 1;
  86. } else {
  87. l = 0;
  88. }
  89. if (!l) {
  90. /* no indentation at all */
  91. xputs(p);
  92. xputc('\n');
  93. continue;
  94. }
  95. if (p[0] == '#') {
  96. /* preprocessor directive: indent after # */
  97. xputc('#');
  98. findent1();
  99. xputs(p + 1);
  100. xputc('\n');
  101. continue;
  102. }
  103. /* closing brace? then unindent */
  104. if (p[0] == '}')
  105. xcurrindent--;
  106. /* print the indentation, but labels will be less indented */
  107. if (p[strlen(p) - 1] == ':') {
  108. xcurrindent--;
  109. findent();
  110. xcurrindent++;
  111. } else {
  112. findent();
  113. }
  114. /* output the line */
  115. xputs(p);
  116. xputc('\n');
  117. /* back at indentation level 0? then we can flush our buffers */
  118. /* first the variables then the other lines */
  119. if (!xcurrindent) {
  120. yflush();
  121. xflush();
  122. }
  123. /* undo indentation of non-braced if/else/switch/for/while/do stmt */
  124. if (xindentflag) {
  125. xcurrindent--;
  126. xindentflag = 0;
  127. }
  128. /* indent after opening brace */
  129. if (p[strlen(p) - 1] == '{') {
  130. xcurrindent++;
  131. xindentflag = 0;
  132. /* indent one line after if/else/switch/for/while/do stmt */
  133. } else if (l == 2 && !memcmp(p, "if", l) ||
  134. l == 4 && !memcmp(p, "else", l) ||
  135. l == 6 && !memcmp(p, "switch", l) ||
  136. l == 3 && !memcmp(p, "for", l) ||
  137. l == 5 && !memcmp(p, "while", l) ||
  138. l == 2 && !memcmp(p, "do", l)) {
  139. xcurrindent++;
  140. xindentflag = 1;
  141. }
  142. }
  143. /* empty buffer after printing */
  144. pos = 0;
  145. }
  146. /* output function doing indentation automatically */
  147. /*PRINTFLIKE1*/
  148. void
  149. output(const char *format, ...)
  150. {
  151. va_list args;
  152. va_start(args, format);
  153. outputv(format, args);
  154. va_end(args);
  155. }
  156. /* output function without indentation */
  157. void
  158. outputniv(const char *format, va_list args)
  159. {
  160. static char buf[512];
  161. vsprintf(buf, format, args);
  162. xputs(buf);
  163. }
  164. /* output function without indentation */
  165. /*PRINTFLIKE1*/
  166. void
  167. outputni(const char *format, ...)
  168. {
  169. va_list args;
  170. va_start(args, format);
  171. outputniv(format, args);
  172. va_end(args);
  173. }
  174. /* output an intx value definition */
  175. void
  176. outputintx(const char *name, intx_t *val)
  177. {
  178. outputoctets(name, val->length, val->value);
  179. output("static ASN1intx_t %s = { %d, %s_octets };\n",
  180. name, val->length, name);
  181. }
  182. /* output an real value definition */
  183. void
  184. outputreal(const char *name, real_t *val)
  185. {
  186. char buf[256];
  187. switch (val->type) {
  188. case eReal_Normal:
  189. sprintf(buf, "%s_mantissa", name);
  190. outputoctets(buf, val->mantissa.length, val->mantissa.value);
  191. sprintf(buf, "%s_exponent", name);
  192. outputoctets(buf, val->exponent.length, val->exponent.value);
  193. output("ASN1real_t %s = { eReal_Normal, { %u, %s_mantissa_octets }, %u, { %u, %s_exponent_octets } };\n",
  194. name, val->mantissa.length, name,
  195. val->base, val->exponent.length, name);
  196. break;
  197. case eReal_PlusInfinity:
  198. output("ASN1real_t %s = { eReal_PlusInfinity };\n", name);
  199. break;
  200. case eReal_MinusInfinity:
  201. output("ASN1real_t %s = { eReal_MinusInfinity };\n", name);
  202. break;
  203. }
  204. }
  205. /* output an octet array definition */
  206. void
  207. outputoctets(const char *name, uint32_t length, octet_t *val)
  208. {
  209. uint32_t i;
  210. char buf[1024];
  211. char *p;
  212. p = buf;
  213. for (i = 0; i < length; i++) {
  214. sprintf(p, "0x%02x", val[i]);
  215. p += 4;
  216. if (i < length - 1) {
  217. sprintf(p, ", ");
  218. p += 2;
  219. }
  220. }
  221. *p = 0;
  222. output("static ASN1octet_t %s_octets[%u] = { %s };\n",
  223. name, length, buf);
  224. }
  225. /* output an uint32 array definition */
  226. void
  227. outputuint32s(const char *name, uint32_t length, uint32_t *val)
  228. {
  229. uint32_t i;
  230. char buf[256];
  231. char *p;
  232. p = buf;
  233. for (i = 0; i < length; i++) {
  234. sprintf(p, "%u", val[i]);
  235. p += strlen(p);
  236. if (i < length - 1) {
  237. sprintf(p, ", ");
  238. p += 2;
  239. }
  240. }
  241. *p = 0;
  242. output("static ASN1uint32_t %s_elems[%u] = { %s };\n",
  243. name, length, buf);
  244. }
  245. /* output forward declaration for a value */
  246. void
  247. outputvalue0(AssignmentList_t ass, char *ideref, char *typeref, Value_t *value)
  248. {
  249. Type_t *type;
  250. char buf[256];
  251. char *itype;
  252. int32_t noctets;
  253. uint32_t zero;
  254. uint32_t i;
  255. Value_t *values;
  256. Component_t *components;
  257. NamedValue_t *namedvalue;
  258. int32_t sign;
  259. char *pszStatic = "extern";
  260. value = GetValue(ass, value);
  261. type = GetType(ass, value->Type);
  262. value = GetValue(ass, value);
  263. switch (type->Type) {
  264. case eType_Integer:
  265. itype = GetIntegerType(ass, type, &sign);
  266. if (!strcmp(itype, "ASN1intx_t")) {
  267. output("%s ASN1octet_t %s_octets[%u];\n", pszStatic,
  268. ideref, value->U.Integer.Value.length);
  269. }
  270. break;
  271. case eType_Real:
  272. itype = GetRealType(type);
  273. if (!strcmp(itype, "ASN1real_t"))
  274. {
  275. switch (value->U.Real.Value.type) {
  276. case eReal_Normal:
  277. output("%s ASN1octet_t %s_mantissa_octets[%u];\n", pszStatic,
  278. ideref, value->U.Real.Value.mantissa.length);
  279. output("%s ASN1octet_t %s_exponent_octets[%u];\n", pszStatic,
  280. ideref, value->U.Real.Value.exponent.length);
  281. break;
  282. }
  283. }
  284. break;
  285. case eType_BitString:
  286. output("%s ASN1octet_t %s_octets[%u];\n", pszStatic,
  287. ideref, (value->U.BitString.Value.length + 7) / 8);
  288. break;
  289. case eType_OctetString:
  290. output("%s ASN1octet_t %s_octets[%u];\n", pszStatic,
  291. ideref, value->U.OctetString.Value.length);
  292. break;
  293. case eType_UTF8String:
  294. output("%s ASN1wchar_t %s_wchars[%u];\n", pszStatic,
  295. ideref, value->U.UTF8String.Value.length);
  296. break;
  297. case eType_ObjectIdentifier:
  298. if (type->PrivateDirectives.fOidPacked ||
  299. type->PrivateDirectives.fOidArray || g_fOidArray)
  300. {
  301. // doing nothing
  302. }
  303. else
  304. {
  305. output("%s ASN1uint32_t %s_elems[%u];\n", pszStatic,
  306. ideref, value->U.ObjectIdentifier.Value.length);
  307. }
  308. break;
  309. case eType_BMPString:
  310. case eType_GeneralString:
  311. case eType_GraphicString:
  312. case eType_IA5String:
  313. case eType_ISO646String:
  314. case eType_NumericString:
  315. case eType_PrintableString:
  316. case eType_TeletexString:
  317. case eType_T61String:
  318. case eType_UniversalString:
  319. case eType_VideotexString:
  320. case eType_VisibleString:
  321. case eType_RestrictedString:
  322. itype = GetStringType(ass, type, &noctets, &zero);
  323. switch (noctets) {
  324. case 1:
  325. output("%s ASN1char_t %s_chars[%u];\n", pszStatic,
  326. ideref, value->U.RestrictedString.Value.length + zero);
  327. break;
  328. case 2:
  329. output("%s ASN1char16_t %s_chars[%u];\n", pszStatic,
  330. ideref, value->U.RestrictedString.Value.length + zero);
  331. break;
  332. case 4:
  333. output("%s ASN1char32_t %s_chars[%u];\n", pszStatic,
  334. ideref, value->U.RestrictedString.Value.length + zero);
  335. break;
  336. }
  337. break;
  338. case eType_ObjectDescriptor:
  339. output("%s ASN1char_t %s_chars[%u];\n", pszStatic,
  340. ideref, value->U.ObjectDescriptor.Value.length + 1);
  341. break;
  342. case eType_SequenceOf:
  343. case eType_SetOf:
  344. if (type->Rules & (eTypeRules_LengthPointer | eTypeRules_FixedArray))
  345. {
  346. for (i = 0, values = value->U.SS.Values; values;
  347. i++, values = values->Next) {}
  348. if (value->U.SS.Values) {
  349. for (i = 0, values = value->U.SS.Values; values;
  350. i++, values = values->Next) {
  351. sprintf(buf, "%s_value%d", ideref, i);
  352. outputvalue0(ass, buf,
  353. GetTypeName(ass, type->U.SS.Type), values);
  354. }
  355. output("%s %s %s_values[%u];\n", pszStatic,
  356. GetTypeName(ass, type->U.SS.Type),
  357. ideref, i);
  358. }
  359. }
  360. else
  361. if (type->Rules & (eTypeRules_SinglyLinkedList | eTypeRules_DoublyLinkedList))
  362. {
  363. for (i = 0, values = value->U.SS.Values; values;
  364. i++, values = values->Next) {
  365. sprintf(buf, "%s_element%d", ideref, i);
  366. outputvalue0(ass, buf, GetTypeName(ass, type->U.SS.Type),
  367. values);
  368. output("%s %s_Element %s_value%d;\n", pszStatic,
  369. typeref, ideref, i);
  370. }
  371. }
  372. else
  373. {
  374. MyAbort();
  375. }
  376. break;
  377. case eType_Sequence:
  378. case eType_Set:
  379. case eType_External:
  380. case eType_EmbeddedPdv:
  381. case eType_CharacterString:
  382. case eType_InstanceOf:
  383. for (components = type->U.SSC.Components; components;
  384. components = components->Next) {
  385. switch (components->Type) {
  386. case eComponent_Normal:
  387. case eComponent_Optional:
  388. case eComponent_Default:
  389. namedvalue = FindNamedValue(value->U.SSC.NamedValues,
  390. components->U.NOD.NamedType->Identifier);
  391. if (!namedvalue)
  392. break;
  393. sprintf(buf, "%s_%s", ideref,
  394. Identifier2C(components->U.NOD.NamedType->Identifier));
  395. outputvalue0(ass, buf,
  396. GetTypeName(ass, components->U.NOD.NamedType->Type),
  397. namedvalue->Value);
  398. break;
  399. }
  400. }
  401. break;
  402. }
  403. }
  404. /* output definitions of value components */
  405. void
  406. outputvalue1(AssignmentList_t ass, char *ideref, char *typeref, Value_t *value)
  407. {
  408. static uint32_t nOidPackedCount = 0;
  409. Type_t *type;
  410. char buf[256];
  411. char *itype;
  412. int32_t noctets;
  413. uint32_t zero;
  414. uint32_t i;
  415. Value_t *values;
  416. Component_t *components;
  417. NamedValue_t *namedvalue;
  418. int32_t sign;
  419. value = GetValue(ass, value);
  420. type = GetType(ass, value->Type);
  421. value = GetValue(ass, value);
  422. switch (type->Type) {
  423. case eType_Integer:
  424. itype = GetIntegerType(ass, type, &sign);
  425. if (!strcmp(itype, "ASN1intx_t")) {
  426. outputoctets(ideref, value->U.Integer.Value.length,
  427. value->U.Integer.Value.value);
  428. }
  429. break;
  430. case eType_Real:
  431. itype = GetRealType(type);
  432. if (!strcmp(itype, "ASN1real_t")) {
  433. switch (value->U.Real.Value.type) {
  434. case eReal_Normal:
  435. sprintf(buf, "%s_mantissa", ideref);
  436. outputoctets(buf, value->U.Real.Value.mantissa.length,
  437. value->U.Real.Value.mantissa.value);
  438. sprintf(buf, "%s_exponent", ideref);
  439. outputoctets(buf, value->U.Real.Value.exponent.length,
  440. value->U.Real.Value.exponent.value);
  441. break;
  442. }
  443. }
  444. break;
  445. case eType_BitString:
  446. outputoctets(ideref, (value->U.BitString.Value.length + 7) / 8,
  447. value->U.BitString.Value.value);
  448. break;
  449. case eType_OctetString:
  450. outputoctets(ideref, value->U.OctetString.Value.length,
  451. value->U.OctetString.Value.value);
  452. break;
  453. case eType_UTF8String:
  454. itype = GetStringType(ass, type, &noctets, &zero);
  455. output("static ASN1wchar_t %s_wchars[%u] = { ",
  456. ideref, value->U.UTF8String.Value.length + zero);
  457. for (i = 0; i < value->U.UTF8String.Value.length; i++) {
  458. output("0x%x", value->U.UTF8String.Value.value[i]);
  459. if (i < value->U.UTF8String.Value.length - 1)
  460. output(", ");
  461. }
  462. if (zero) {
  463. if (value->U.UTF8String.Value.length)
  464. output(", 0x0");
  465. else
  466. output("0x0");
  467. }
  468. output(" };\n");
  469. break;
  470. case eType_ObjectIdentifier:
  471. if (type->PrivateDirectives.fOidPacked)
  472. {
  473. uint32_t length = value->U.ObjectIdentifier.Value.length;
  474. uint32_t *val = value->U.ObjectIdentifier.Value.value;
  475. uint32_t i, j, cb;
  476. uint32_t count = 0;
  477. uint32_t node;
  478. unsigned char aLittleEndian[16];
  479. char buf[1024];
  480. char *p = buf;
  481. sprintf(p, "{");
  482. p += strlen(p);
  483. for (i = 0; i < length; i++)
  484. {
  485. // get node value
  486. node = val[i];
  487. // special case for the first node
  488. if (0 == i && length > 1)
  489. {
  490. i++;
  491. node = node * 40 + val[1];
  492. }
  493. // encode this node
  494. ZeroMemory(aLittleEndian, sizeof(aLittleEndian));
  495. for (j = 0; node != 0; j++)
  496. {
  497. aLittleEndian[j] = (unsigned char) (node & 0x7f);
  498. if (j != 0)
  499. {
  500. aLittleEndian[j] |= (unsigned char) 0x80;
  501. }
  502. node >>= 7;
  503. }
  504. cb = j ? j : 1; // at least one byte for zero value
  505. // print out the values
  506. for (j = 0; j < cb; j ++)
  507. {
  508. count++;
  509. sprintf(p, " %u,", (unsigned char) aLittleEndian[cb - j - 1]);
  510. p += strlen(p);
  511. }
  512. }
  513. --p; // remove the last ','
  514. strcpy(p, " }");
  515. output("static ASN1octet_t s_oid%u[] = %s;\n", nOidPackedCount, buf);
  516. output("ASN1encodedOID_t %s = { %u, s_oid%u };\n", ideref, count, nOidPackedCount);
  517. nOidPackedCount++;
  518. }
  519. else
  520. if (type->PrivateDirectives.fOidArray || g_fOidArray)
  521. {
  522. uint32_t length = value->U.ObjectIdentifier.Value.length;
  523. uint32_t *val = value->U.ObjectIdentifier.Value.value;
  524. uint32_t i;
  525. char buf[1024];
  526. char *p = buf;
  527. sprintf(p, "{ ");
  528. p += strlen(p);
  529. for (i = 0; i < length; i++)
  530. {
  531. if (i == length - 1)
  532. {
  533. sprintf(p, "%u }", val[i]);
  534. }
  535. else
  536. {
  537. sprintf(p, "%u, ", val[i]);
  538. }
  539. p += strlen(p);
  540. }
  541. *p = 0;
  542. output("ASN1objectidentifier2_t %s = {\n%u, %s\n};\n", ideref, length, buf);
  543. }
  544. else
  545. {
  546. uint32_t length = value->U.ObjectIdentifier.Value.length;
  547. uint32_t *val = value->U.ObjectIdentifier.Value.value;
  548. uint32_t i;
  549. char buf[1024];
  550. char *p = buf;
  551. for (i = 0; i < length; i++)
  552. {
  553. if (i == length - 1)
  554. {
  555. sprintf(p, "{ NULL, %u }", val[i]);
  556. }
  557. else
  558. {
  559. sprintf(p, "{ (ASN1objectidentifier_t) &(%s_list[%u]), %u },\n", ideref, i+1, val[i]);
  560. }
  561. p += strlen(p);
  562. }
  563. *p = 0;
  564. output("static const struct ASN1objectidentifier_s %s_list[%u] = {\n%s\n};\n",
  565. ideref, length, buf);
  566. }
  567. break;
  568. case eType_BMPString:
  569. case eType_GeneralString:
  570. case eType_GraphicString:
  571. case eType_IA5String:
  572. case eType_ISO646String:
  573. case eType_NumericString:
  574. case eType_PrintableString:
  575. case eType_TeletexString:
  576. case eType_T61String:
  577. case eType_UniversalString:
  578. case eType_VideotexString:
  579. case eType_VisibleString:
  580. case eType_RestrictedString:
  581. itype = GetStringType(ass, type, &noctets, &zero);
  582. switch (noctets) {
  583. case 1:
  584. output("static ASN1char_t %s_chars[%u] = { ",
  585. ideref, value->U.RestrictedString.Value.length + zero);
  586. break;
  587. case 2:
  588. output("static ASN1char16_t %s_chars[%u] = { ",
  589. ideref, value->U.RestrictedString.Value.length + zero);
  590. break;
  591. case 4:
  592. output("static ASN1char32_t %s_chars[%u] = { ",
  593. ideref, value->U.RestrictedString.Value.length + zero);
  594. break;
  595. }
  596. for (i = 0; i < value->U.RestrictedString.Value.length; i++) {
  597. output("0x%x", value->U.RestrictedString.Value.value[i]);
  598. if (i < value->U.RestrictedString.Value.length - 1)
  599. output(", ");
  600. }
  601. if (zero) {
  602. if (value->U.RestrictedString.Value.length)
  603. output(", 0x0");
  604. else
  605. output("0x0");
  606. }
  607. output(" };\n");
  608. break;
  609. case eType_ObjectDescriptor:
  610. output("static ASN1char_t %s_chars[%u] = { ",
  611. ideref, value->U.ObjectDescriptor.Value.length + 1);
  612. for (i = 0; i < value->U.ObjectDescriptor.Value.length; i++) {
  613. output("0x%x, ", value->U.ObjectDescriptor.Value.value[i]);
  614. }
  615. output("0x0 };\n");
  616. break;
  617. case eType_SequenceOf:
  618. case eType_SetOf:
  619. if (type->Rules &
  620. (eTypeRules_LengthPointer | eTypeRules_FixedArray)) {
  621. if (value->U.SS.Values) {
  622. for (i = 0, values = value->U.SS.Values; values;
  623. i++, values = values->Next) {
  624. sprintf(buf, "%s_value%d", ideref, i);
  625. outputvalue1(ass, buf,
  626. GetTypeName(ass, type->U.SS.Type),
  627. values);
  628. }
  629. output("static %s %s_values[%u] = { ",
  630. GetTypeName(ass, type->U.SS.Type),
  631. ideref, i);
  632. for (i = 0, values = value->U.SS.Values; values;
  633. i++, values = values->Next) {
  634. if (i)
  635. output(", ");
  636. sprintf(buf, "%s_value%d", ideref, i);
  637. outputvalue2(ass, buf, values);
  638. }
  639. output(" };\n");
  640. }
  641. } else if (type->Rules &
  642. (eTypeRules_SinglyLinkedList | eTypeRules_DoublyLinkedList)) {
  643. for (i = 0, values = value->U.SS.Values; values;
  644. i++, values = values->Next) {
  645. sprintf(buf, "%s_element%d", ideref, i);
  646. outputvalue1(ass, buf, GetTypeName(ass, type->U.SS.Type),
  647. values);
  648. }
  649. for (i = 0, values = value->U.SS.Values; values;
  650. i++, values = values->Next) {
  651. output("static %s_Element %s_value%d = { ",
  652. typeref, ideref, i);
  653. if (values->Next)
  654. output("&%s_value%d, ", ideref, i + 1);
  655. else
  656. output("0, ");
  657. if (type->Rules & eTypeRules_DoublyLinkedList) {
  658. if (i)
  659. output("&%s_value%d, ", ideref, i - 1);
  660. else
  661. output("0, ");
  662. }
  663. sprintf(buf, "%s_element%d", ideref, i);
  664. outputvalue2(ass, buf, values);
  665. output(" };\n");
  666. }
  667. } else {
  668. MyAbort();
  669. }
  670. break;
  671. case eType_Sequence:
  672. case eType_Set:
  673. case eType_External:
  674. case eType_EmbeddedPdv:
  675. case eType_CharacterString:
  676. case eType_InstanceOf:
  677. for (components = type->U.SSC.Components; components;
  678. components = components->Next) {
  679. switch (components->Type) {
  680. case eComponent_Normal:
  681. case eComponent_Optional:
  682. case eComponent_Default:
  683. namedvalue = FindNamedValue(value->U.SSC.NamedValues,
  684. components->U.NOD.NamedType->Identifier);
  685. if (!namedvalue)
  686. break;
  687. sprintf(buf, "%s_%s", ideref,
  688. Identifier2C(components->U.NOD.NamedType->Identifier));
  689. outputvalue1(ass, buf,
  690. GetTypeName(ass, components->U.NOD.NamedType->Type),
  691. namedvalue->Value);
  692. break;
  693. }
  694. }
  695. break;
  696. case eType_Choice:
  697. namedvalue = value->U.Choice.NamedValues;
  698. components = FindComponent(ass, type->U.Choice.Components,
  699. namedvalue->Identifier);
  700. sprintf(buf, "%s_%s", ideref,
  701. Identifier2C(components->U.NOD.NamedType->Identifier));
  702. outputvalue1(ass, buf, GetTypeName(ass,
  703. components->U.NOD.NamedType->Type),
  704. namedvalue->Value);
  705. output("static %s %s = ",
  706. GetTypeName(ass, components->U.NOD.NamedType->Type), buf);
  707. outputvalue2(ass, buf, namedvalue->Value);
  708. output(";\n");
  709. break;
  710. }
  711. }
  712. /* output definition of value */
  713. void
  714. outputvalue2(AssignmentList_t ass, char *ideref, Value_t *value)
  715. {
  716. Type_t *type;
  717. char buf[256];
  718. char *itype;
  719. int32_t noctets;
  720. uint32_t zero;
  721. uint32_t i;
  722. Value_t *values;
  723. Component_t *components;
  724. NamedValue_t *namedvalue;
  725. char *comma;
  726. uint32_t ext;
  727. uint32_t opt;
  728. int32_t sign;
  729. value = GetValue(ass, value);
  730. type = GetType(ass, value->Type);
  731. value = GetValue(ass, value);
  732. switch (type->Type) {
  733. case eType_Boolean:
  734. output("%d", value->U.Boolean.Value);
  735. break;
  736. case eType_Integer:
  737. itype = GetIntegerType(ass, type, &sign);
  738. if (!strcmp(itype, "ASN1intx_t")) {
  739. output("{ %d, %s_octets }", value->U.Integer.Value.length, ideref);
  740. } else if (sign > 0) {
  741. output("%u", intx2uint32(&value->U.Integer.Value));
  742. } else {
  743. output("%d", intx2int32(&value->U.Integer.Value));
  744. }
  745. break;
  746. case eType_Enumerated:
  747. output("%u", value->U.Enumerated.Value);
  748. break;
  749. case eType_Real:
  750. itype = GetRealType(type);
  751. if (!strcmp(itype, "ASN1real_t")) {
  752. switch (value->U.Real.Value.type) {
  753. case eReal_Normal:
  754. output("{ eReal_Normal, { %u, %s_mantissa_octets }, %u, { %u, %s_exponent_octets } }",
  755. value->U.Real.Value.mantissa.length, ideref,
  756. value->U.Real.Value.base,
  757. value->U.Real.Value.exponent.length, ideref);
  758. break;
  759. case eReal_PlusInfinity:
  760. output("{ eReal_PlusInfinity }");
  761. break;
  762. case eReal_MinusInfinity:
  763. output("{ eReal_MinusInfinity }");
  764. break;
  765. }
  766. }
  767. else
  768. {
  769. switch (value->U.Real.Value.type) {
  770. case eReal_Normal:
  771. output("%g", real2double(&value->U.Real.Value));
  772. break;
  773. case eReal_PlusInfinity:
  774. case eReal_MinusInfinity:
  775. output("0.0");
  776. break;
  777. }
  778. }
  779. break;
  780. case eType_BitString:
  781. output("{ %u, %s_octets }",
  782. value->U.BitString.Value.length, ideref);
  783. break;
  784. case eType_OctetString:
  785. output("{ %u, %s_octets }",
  786. value->U.OctetString.Value.length, ideref);
  787. break;
  788. case eType_UTF8String:
  789. output("{ %u, %s_utf8chars }",
  790. value->U.UTF8String.Value.length, ideref);
  791. break;
  792. case eType_ObjectIdentifier:
  793. if (type->PrivateDirectives.fOidPacked)
  794. {
  795. // doing nothing
  796. }
  797. else
  798. if (type->PrivateDirectives.fOidArray || g_fOidArray)
  799. {
  800. output("(ASN1objectidentifier2_t *) &%s_list", ideref);
  801. }
  802. else
  803. {
  804. output("(ASN1objectidentifier_t) %s_list", ideref);
  805. }
  806. break;
  807. case eType_BMPString:
  808. case eType_GeneralString:
  809. case eType_GraphicString:
  810. case eType_IA5String:
  811. case eType_ISO646String:
  812. case eType_NumericString:
  813. case eType_PrintableString:
  814. case eType_TeletexString:
  815. case eType_T61String:
  816. case eType_UniversalString:
  817. case eType_VideotexString:
  818. case eType_VisibleString:
  819. case eType_RestrictedString:
  820. itype = GetStringType(ass, type, &noctets, &zero);
  821. if (zero) {
  822. output("%s_chars", ideref);
  823. } else {
  824. output("{ %u, %s_chars }",
  825. value->U.RestrictedString.Value.length, ideref);
  826. }
  827. break;
  828. case eType_ObjectDescriptor:
  829. output("%s_chars", ideref);
  830. break;
  831. case eType_GeneralizedTime:
  832. output("{ %d, %d, %d, %d, %d, %d, %d, %d, %d }",
  833. value->U.GeneralizedTime.Value.year,
  834. value->U.GeneralizedTime.Value.month,
  835. value->U.GeneralizedTime.Value.day,
  836. value->U.GeneralizedTime.Value.hour,
  837. value->U.GeneralizedTime.Value.minute,
  838. value->U.GeneralizedTime.Value.second,
  839. value->U.GeneralizedTime.Value.millisecond,
  840. value->U.GeneralizedTime.Value.universal,
  841. value->U.GeneralizedTime.Value.diff);
  842. break;
  843. case eType_UTCTime:
  844. output("{ %d, %d, %d, %d, %d, %d, %d, %d }",
  845. value->U.UTCTime.Value.year,
  846. value->U.UTCTime.Value.month,
  847. value->U.UTCTime.Value.day,
  848. value->U.UTCTime.Value.hour,
  849. value->U.UTCTime.Value.minute,
  850. value->U.UTCTime.Value.second,
  851. value->U.UTCTime.Value.universal,
  852. value->U.UTCTime.Value.diff);
  853. break;
  854. case eType_SequenceOf:
  855. case eType_SetOf:
  856. if (type->Rules &
  857. (eTypeRules_LengthPointer | eTypeRules_FixedArray)) {
  858. if (value->U.SS.Values) {
  859. for (i = 0, values = value->U.SS.Values; values;
  860. i++, values = values->Next) {}
  861. output("{ %d, %s_values }", i, ideref);
  862. } else {
  863. output("{ 0, NULL }");
  864. }
  865. } else if (type->Rules &
  866. (eTypeRules_SinglyLinkedList | eTypeRules_DoublyLinkedList)) {
  867. output("&%s_value0", ideref);
  868. } else {
  869. MyAbort();
  870. }
  871. break;
  872. case eType_Sequence:
  873. case eType_Set:
  874. case eType_External:
  875. case eType_EmbeddedPdv:
  876. case eType_CharacterString:
  877. case eType_InstanceOf:
  878. comma = "";
  879. output("{ ");
  880. if (type->U.SSC.Optionals || type->U.SSC.Extensions) {
  881. output("{ ");
  882. ext = 0;
  883. opt = 0;
  884. i = 0;
  885. comma = "";
  886. for (components = type->U.SSC.Components; components;
  887. components = components->Next) {
  888. switch (components->Type) {
  889. case eComponent_Normal:
  890. if (!ext)
  891. break;
  892. /*FALLTHROUGH*/
  893. case eComponent_Optional:
  894. case eComponent_Default:
  895. namedvalue = FindNamedValue(value->U.SSC.NamedValues,
  896. components->U.NOD.NamedType->Identifier);
  897. if (namedvalue)
  898. opt |= (0x80 >> i);
  899. if (++i > 7) {
  900. output("%s0x%02x", comma, opt);
  901. opt = 0;
  902. i = 0;
  903. comma = ", ";
  904. }
  905. break;
  906. case eComponent_ExtensionMarker:
  907. if (i) {
  908. output("%s0x%02x", comma, opt);
  909. opt = 0;
  910. i = 0;
  911. comma = ", ";
  912. }
  913. ext = 1;
  914. break;
  915. }
  916. }
  917. if (i)
  918. output("%s0x%02x", comma, opt);
  919. output(" }");
  920. comma = ", ";
  921. }
  922. for (components = type->U.SSC.Components; components;
  923. components = components->Next) {
  924. switch (components->Type) {
  925. case eComponent_Normal:
  926. case eComponent_Optional:
  927. case eComponent_Default:
  928. namedvalue = FindNamedValue(value->U.SSC.NamedValues,
  929. components->U.NOD.NamedType->Identifier);
  930. if (!namedvalue) {
  931. output("%s0", comma);
  932. } else {
  933. output("%s", comma);
  934. sprintf(buf, "%s_%s", ideref,
  935. Identifier2C(components->U.NOD.NamedType->Identifier));
  936. outputvalue2(ass, buf, namedvalue->Value);
  937. }
  938. comma = ", ";
  939. break;
  940. }
  941. }
  942. output(" }");
  943. break;
  944. case eType_Choice:
  945. i = ASN1_CHOICE_BASE;
  946. for (components = type->U.SSC.Components; components;
  947. components = components->Next) {
  948. switch (components->Type) {
  949. case eComponent_Normal:
  950. if (!strcmp(value->U.SSC.NamedValues->Identifier,
  951. components->U.NOD.NamedType->Identifier))
  952. break;
  953. i++;
  954. continue;
  955. case eComponent_ExtensionMarker:
  956. continue;
  957. default:
  958. MyAbort();
  959. }
  960. break;
  961. }
  962. output("{ %d }", i);
  963. }
  964. }
  965. /* output assignments needed in initialization function */
  966. void
  967. outputvalue3(AssignmentList_t ass, char *ideref, char *valref, Value_t *value)
  968. {
  969. Type_t *type;
  970. NamedValue_t *named;
  971. Value_t *values;
  972. int i;
  973. char idebuf[256];
  974. char valbuf[256];
  975. char *itype;
  976. value = GetValue(ass, value);
  977. type = GetType(ass, value->Type);
  978. switch (type->Type) {
  979. case eType_SequenceOf:
  980. case eType_SetOf:
  981. for (values = value->U.SS.Values, i = 0; values;
  982. values = values->Next, i++) {
  983. if (type->Rules &
  984. (eTypeRules_LengthPointer | eTypeRules_FixedArray)) {
  985. sprintf(idebuf, "%s.value[%d]", ideref, i);
  986. } else if (type->Rules &
  987. (eTypeRules_SinglyLinkedList | eTypeRules_DoublyLinkedList)) {
  988. sprintf(idebuf, "%s_value%d", ideref, i);
  989. } else {
  990. MyAbort();
  991. }
  992. sprintf(valbuf, "%s_value%d", valref, i);
  993. outputvalue3(ass, idebuf, valbuf, values);
  994. }
  995. break;
  996. case eType_Choice:
  997. output("%s.u.%s = %s_%s;\n",
  998. ideref, Identifier2C(value->U.SSC.NamedValues->Identifier),
  999. valref, Identifier2C(value->U.SSC.NamedValues->Identifier));
  1000. /*FALLTHROUGH*/
  1001. case eType_Sequence:
  1002. case eType_Set:
  1003. case eType_External:
  1004. case eType_EmbeddedPdv:
  1005. case eType_CharacterString:
  1006. case eType_InstanceOf:
  1007. for (named = value->U.SSC.NamedValues; named; named = named->Next) {
  1008. sprintf(idebuf, "%s.%s", ideref,
  1009. Identifier2C(named->Identifier));
  1010. sprintf(valbuf, "%s_%s", valref,
  1011. Identifier2C(named->Identifier));
  1012. outputvalue3(ass, idebuf, valbuf, named->Value);
  1013. }
  1014. break;
  1015. case eType_Real:
  1016. itype = GetRealType(type);
  1017. if (strcmp(itype, "ASN1real_t"))
  1018. {
  1019. switch (value->U.Real.Value.type) {
  1020. case eReal_Normal:
  1021. break;
  1022. case eReal_PlusInfinity:
  1023. output("%s = ASN1double_pinf();\n", ideref);
  1024. break;
  1025. case eReal_MinusInfinity:
  1026. output("%s = ASN1double_minf();\n", ideref);
  1027. break;
  1028. }
  1029. }
  1030. }
  1031. }
  1032. /* print indentation up to current indentation level for variables */
  1033. static void
  1034. findentvar()
  1035. {
  1036. int indent;
  1037. indent = ycurrindent * INDENT;
  1038. while (indent >= TABSIZE) {
  1039. yputc('\t');
  1040. indent -= TABSIZE;
  1041. }
  1042. while (indent--)
  1043. yputc(' ');
  1044. }
  1045. /* print indentation up to current indentation level for variables */
  1046. void
  1047. outputvarv(const char *format, va_list args)
  1048. {
  1049. static char buf[512];
  1050. static int pos = 0;
  1051. char *p, *q;
  1052. int l;
  1053. /* get the string to write */
  1054. vsprintf(buf + pos, format, args);
  1055. /* print it line by line */
  1056. for (p = buf; *p; p = q) {
  1057. q = strchr(p, '\n');
  1058. if (!q) {
  1059. for (q = buf; *p;)
  1060. *q++ = *p++;
  1061. *q = 0;
  1062. pos = q - buf;
  1063. return;
  1064. }
  1065. *q++ = 0;
  1066. /* output every variable only once */
  1067. if (ycurrindent == 1) {
  1068. l = 0;
  1069. while (l < ybuflen) {
  1070. if (!memcmp(ybuf + l + INDENT / TABSIZE + INDENT % TABSIZE,
  1071. p, strlen(p)))
  1072. break;
  1073. l += (strchr(ybuf + l, '\n') - (ybuf + l)) + 1;
  1074. }
  1075. if (l < ybuflen)
  1076. continue;
  1077. }
  1078. /* examine the first character for correct indentation */
  1079. if (strchr(IDCHRSET, *p)) {
  1080. l = strspn(p, IDCHRSET);
  1081. } else if (*p == '{' || *p == '}') {
  1082. l = 1;
  1083. } else {
  1084. l = 0;
  1085. }
  1086. if (!l) {
  1087. /* no indentation at all */
  1088. yputs(p);
  1089. yputc('\n');
  1090. continue;
  1091. }
  1092. /* closing brace? then unindent */
  1093. if (p[0] == '}')
  1094. ycurrindent--;
  1095. /* print indentation */
  1096. findentvar();
  1097. /* output the line */
  1098. yputs(p);
  1099. yputc('\n');
  1100. /* indent after opening brace */
  1101. if (p[strlen(p) - 1] == '{') {
  1102. ycurrindent++;
  1103. }
  1104. }
  1105. pos = 0;
  1106. }
  1107. /* print indentation up to current indentation level for variables */
  1108. /*PRINTFLIKE1*/
  1109. void
  1110. outputvar(const char *format, ...)
  1111. {
  1112. va_list args;
  1113. va_start(args, format);
  1114. outputvarv(format, args);
  1115. va_end(args);
  1116. }
  1117. /* output an octet array definition for variables */
  1118. void
  1119. outputvaroctets(const char *name, uint32_t length, octet_t *val)
  1120. {
  1121. uint32_t i;
  1122. char buf[256];
  1123. char *p;
  1124. p = buf;
  1125. for (i = 0; i < length; i++) {
  1126. sprintf(p, "0x%02x", val[i]);
  1127. p += 4;
  1128. if (i < length - 1) {
  1129. sprintf(p, ", ");
  1130. p += 2;
  1131. }
  1132. }
  1133. outputvar("static ASN1octet_t %s_octets[%u] = { %s };\n",
  1134. name, length, buf);
  1135. }
  1136. /* output an intx value definition for variables */
  1137. void outputvarintx(const char *name, intx_t *val)
  1138. {
  1139. outputvaroctets(name, val->length, val->value);
  1140. outputvar("static ASN1intx_t %s = { %d, %s_octets };\n",
  1141. name, val->length, name);
  1142. }
  1143. /* output an real value definition for variables */
  1144. void outputvarreal(const char *name, real_t *val)
  1145. {
  1146. char buf[256];
  1147. switch (val->type) {
  1148. case eReal_Normal:
  1149. sprintf(buf, "%s_mantissa", name);
  1150. outputvaroctets(buf, val->mantissa.length, val->mantissa.value);
  1151. sprintf(buf, "%s_exponent", name);
  1152. outputvaroctets(buf, val->exponent.length, val->exponent.value);
  1153. outputvar("ASN1real_t %s = { eReal_Normal, { %u, %s_mantissa_octets }, %u, { %u, %s_exponent_octets } };\n",
  1154. name, val->mantissa.length, name,
  1155. val->base, val->exponent.length, name);
  1156. break;
  1157. case eReal_PlusInfinity:
  1158. outputvar("ASN1real_t %s = { eReal_PlusInfinity };\n", name);
  1159. break;
  1160. case eReal_MinusInfinity:
  1161. outputvar("ASN1real_t %s = { eReal_MinusInfinity };\n", name);
  1162. break;
  1163. }
  1164. }
  1165. /* output a character of the function body */
  1166. void xputc(char c)
  1167. {
  1168. if (xbuflen + 1 > xbufsize) {
  1169. xbufsize += 1024;
  1170. if (!xbuf)
  1171. xbuf = (char *)malloc(xbufsize);
  1172. else
  1173. xbuf = (char *)realloc(xbuf, xbufsize);
  1174. }
  1175. xbuf[xbuflen++] = c;
  1176. }
  1177. /* output a string of the function body */
  1178. void xputs(char *s)
  1179. {
  1180. int sl;
  1181. sl = strlen(s);
  1182. if (xbuflen + sl > xbufsize) {
  1183. while (xbuflen + sl > xbufsize)
  1184. xbufsize += 1024;
  1185. if (!xbuf)
  1186. xbuf = (char *)malloc(xbufsize);
  1187. else
  1188. xbuf = (char *)realloc(xbuf, xbufsize);
  1189. }
  1190. memcpy(xbuf + xbuflen, s, sl);
  1191. xbuflen += sl;
  1192. }
  1193. /* flush the function body into the output file */
  1194. void xflush()
  1195. {
  1196. if (xbuflen) {
  1197. fwrite(xbuf, xbuflen, 1, fout);
  1198. #if 0
  1199. fflush(fout);
  1200. #endif
  1201. xbuflen = 0;
  1202. }
  1203. }
  1204. /* output a character of the function variables */
  1205. void yputc(char c)
  1206. {
  1207. if (ybuflen + 1 > ybufsize) {
  1208. ybufsize += 1024;
  1209. if (!ybuf)
  1210. ybuf = (char *)malloc(ybufsize);
  1211. else
  1212. ybuf = (char *)realloc(ybuf, ybufsize);
  1213. }
  1214. ybuf[ybuflen++] = c;
  1215. }
  1216. /* output a string of the function variables */
  1217. void yputs(char *s)
  1218. {
  1219. int sl;
  1220. sl = strlen(s);
  1221. if (ybuflen + sl > ybufsize) {
  1222. while (ybuflen + sl > ybufsize)
  1223. ybufsize += 1024;
  1224. if (!ybuf)
  1225. ybuf = (char *)malloc(ybufsize);
  1226. else
  1227. ybuf = (char *)realloc(ybuf, ybufsize);
  1228. }
  1229. memcpy(ybuf + ybuflen, s, sl);
  1230. ybuflen += sl;
  1231. }
  1232. /* flush the function variables into the output file */
  1233. void yflush()
  1234. {
  1235. if (ybuflen) {
  1236. fwrite(ybuf, ybuflen, 1, fout);
  1237. #if 0
  1238. fflush(fout);
  1239. #endif
  1240. ybuflen = 0;
  1241. }
  1242. }