1 /*        $NetBSD: asn1parse.y,v 1.2 2017/01/28 21:31:45 christos Exp $         */
2 
3 /*
4  * Copyright (c) 1997 - 2007 Kungliga Tekniska Högskolan
5  * (Royal Institute of Technology, Stockholm, Sweden).
6  * All rights reserved.
7  *
8  * Portions Copyright (c) 2009 Apple Inc. All rights reserved.
9  *
10  * Redistribution and use in source and binary forms, with or without
11  * modification, are permitted provided that the following conditions
12  * are met:
13  *
14  * 1. Redistributions of source code must retain the above copyright
15  *    notice, this list of conditions and the following disclaimer.
16  *
17  * 2. Redistributions in binary form must reproduce the above copyright
18  *    notice, this list of conditions and the following disclaimer in the
19  *    documentation and/or other materials provided with the distribution.
20  *
21  * 3. Neither the name of the Institute nor the names of its contributors
22  *    may be used to endorse or promote products derived from this software
23  *    without specific prior written permission.
24  *
25  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
26  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
29  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35  * SUCH DAMAGE.
36  */
37 
38 /* Id */
39 
40 %{
41 
42 #include <config.h>
43 
44 #include <stdio.h>
45 #include <stdlib.h>
46 #include <stdint.h>
47 #include <string.h>
48 #include "symbol.h"
49 #include "lex.h"
50 #include "gen_locl.h"
51 #include "der.h"
52 
53 static Type *new_type (Typetype t);
54 static struct constraint_spec *new_constraint_spec(enum ctype);
55 static Type *new_tag(int tagclass, int tagvalue, int tagenv, Type *oldtype);
56 void yyerror (const char *);
57 static struct objid *new_objid(const char *label, int value);
58 static void add_oid_to_tail(struct objid *, struct objid *);
59 static void fix_labels(Symbol *s);
60 
61 struct string_list {
62     char *string;
63     struct string_list *next;
64 };
65 
66 static int default_tag_env = TE_EXPLICIT;
67 
68 /* Declarations for Bison */
69 #define YYMALLOC malloc
70 #define YYFREE   free
71 
72 %}
73 
74 %union {
75     int64_t constant;
76     struct value *value;
77     struct range *range;
78     char *name;
79     Type *type;
80     Member *member;
81     struct objid *objid;
82     char *defval;
83     struct string_list *sl;
84     struct tagtype tag;
85     struct memhead *members;
86     struct constraint_spec *constraint_spec;
87 }
88 
89 %token kw_ABSENT
90 %token kw_ABSTRACT_SYNTAX
91 %token kw_ALL
92 %token kw_APPLICATION
93 %token kw_AUTOMATIC
94 %token kw_BEGIN
95 %token kw_BIT
96 %token kw_BMPString
97 %token kw_BOOLEAN
98 %token kw_BY
99 %token kw_CHARACTER
100 %token kw_CHOICE
101 %token kw_CLASS
102 %token kw_COMPONENT
103 %token kw_COMPONENTS
104 %token kw_CONSTRAINED
105 %token kw_CONTAINING
106 %token kw_DEFAULT
107 %token kw_DEFINITIONS
108 %token kw_EMBEDDED
109 %token kw_ENCODED
110 %token kw_END
111 %token kw_ENUMERATED
112 %token kw_EXCEPT
113 %token kw_EXPLICIT
114 %token kw_EXPORTS
115 %token kw_EXTENSIBILITY
116 %token kw_EXTERNAL
117 %token kw_FALSE
118 %token kw_FROM
119 %token kw_GeneralString
120 %token kw_GeneralizedTime
121 %token kw_GraphicString
122 %token kw_IA5String
123 %token kw_IDENTIFIER
124 %token kw_IMPLICIT
125 %token kw_IMPLIED
126 %token kw_IMPORTS
127 %token kw_INCLUDES
128 %token kw_INSTANCE
129 %token kw_INTEGER
130 %token kw_INTERSECTION
131 %token kw_ISO646String
132 %token kw_MAX
133 %token kw_MIN
134 %token kw_MINUS_INFINITY
135 %token kw_NULL
136 %token kw_NumericString
137 %token kw_OBJECT
138 %token kw_OCTET
139 %token kw_OF
140 %token kw_OPTIONAL
141 %token kw_ObjectDescriptor
142 %token kw_PATTERN
143 %token kw_PDV
144 %token kw_PLUS_INFINITY
145 %token kw_PRESENT
146 %token kw_PRIVATE
147 %token kw_PrintableString
148 %token kw_REAL
149 %token kw_RELATIVE_OID
150 %token kw_SEQUENCE
151 %token kw_SET
152 %token kw_SIZE
153 %token kw_STRING
154 %token kw_SYNTAX
155 %token kw_T61String
156 %token kw_TAGS
157 %token kw_TRUE
158 %token kw_TYPE_IDENTIFIER
159 %token kw_TeletexString
160 %token kw_UNION
161 %token kw_UNIQUE
162 %token kw_UNIVERSAL
163 %token kw_UTCTime
164 %token kw_UTF8String
165 %token kw_UniversalString
166 %token kw_VideotexString
167 %token kw_VisibleString
168 %token kw_WITH
169 
170 %token RANGE
171 %token EEQUAL
172 %token ELLIPSIS
173 
174 %token <name> IDENTIFIER  referencename
175 %token <name> STRING
176 
177 %token <constant> NUMBER
178 %type <constant> SignedNumber
179 %type <constant> Class tagenv
180 
181 %type <value> Value
182 %type <value> BuiltinValue
183 %type <value> IntegerValue
184 %type <value> BooleanValue
185 %type <value> ObjectIdentifierValue
186 %type <value> CharacterStringValue
187 %type <value> NullValue
188 %type <value> DefinedValue
189 %type <value> ReferencedValue
190 %type <value> Valuereference
191 
192 %type <type> Type
193 %type <type> BuiltinType
194 %type <type> BitStringType
195 %type <type> BooleanType
196 %type <type> ChoiceType
197 %type <type> ConstrainedType
198 %type <type> EnumeratedType
199 %type <type> IntegerType
200 %type <type> NullType
201 %type <type> OctetStringType
202 %type <type> SequenceType
203 %type <type> SequenceOfType
204 %type <type> SetType
205 %type <type> SetOfType
206 %type <type> TaggedType
207 %type <type> ReferencedType
208 %type <type> DefinedType
209 %type <type> UsefulType
210 %type <type> ObjectIdentifierType
211 %type <type> CharacterStringType
212 %type <type> RestrictedCharactedStringType
213 
214 %type <tag> Tag
215 
216 %type <member> ComponentType
217 %type <member> NamedBit
218 %type <member> NamedNumber
219 %type <member> NamedType
220 %type <members> ComponentTypeList
221 %type <members> Enumerations
222 %type <members> NamedBitList
223 %type <members> NamedNumberList
224 
225 %type <objid> objid objid_list objid_element objid_opt
226 %type <range> range size
227 
228 %type <sl> referencenames
229 
230 %type <constraint_spec> Constraint
231 %type <constraint_spec> ConstraintSpec
232 %type <constraint_spec> GeneralConstraint
233 %type <constraint_spec> ContentsConstraint
234 %type <constraint_spec> UserDefinedConstraint
235 
236 
237 
238 %start ModuleDefinition
239 
240 %%
241 
242 ModuleDefinition: IDENTIFIER objid_opt kw_DEFINITIONS TagDefault ExtensionDefault
243                               EEQUAL kw_BEGIN ModuleBody kw_END
244                     {
245                               checkundefined();
246                     }
247                     ;
248 
249 TagDefault          : kw_EXPLICIT kw_TAGS
250                               { default_tag_env = TE_EXPLICIT; }
251                     | kw_IMPLICIT kw_TAGS
252                               { default_tag_env = TE_IMPLICIT; }
253                     | kw_AUTOMATIC kw_TAGS
254                           { lex_error_message("automatic tagging is not supported"); }
255                     | /* empty */
256                     ;
257 
258 ExtensionDefault: kw_EXTENSIBILITY kw_IMPLIED
259                           { lex_error_message("no extensibility options supported"); }
260                     | /* empty */
261                     ;
262 
263 ModuleBody          : Exports Imports AssignmentList
264                     | /* empty */
265                     ;
266 
267 Imports             : kw_IMPORTS SymbolsImported ';'
268                     | /* empty */
269                     ;
270 
271 SymbolsImported     : SymbolsFromModuleList
272                     | /* empty */
273                     ;
274 
275 SymbolsFromModuleList: SymbolsFromModule
276                     | SymbolsFromModuleList SymbolsFromModule
277                     ;
278 
279 SymbolsFromModule: referencenames kw_FROM IDENTIFIER objid_opt
280                     {
281                         struct string_list *sl;
282                         for(sl = $1; sl != NULL; sl = sl->next) {
283                               Symbol *s = addsym(sl->string);
284                               s->stype = Stype;
285                               gen_template_import(s);
286                         }
287                         add_import($3);
288                     }
289                     ;
290 
291 Exports             : kw_EXPORTS referencenames ';'
292                     {
293                         struct string_list *sl;
294                         for(sl = $2; sl != NULL; sl = sl->next)
295                               add_export(sl->string);
296                     }
297                     | kw_EXPORTS kw_ALL
298                     | /* empty */
299                     ;
300 
301 AssignmentList      : Assignment
302                     | Assignment AssignmentList
303                     ;
304 
305 Assignment          : TypeAssignment
306                     | ValueAssignment
307                     ;
308 
309 referencenames      : IDENTIFIER ',' referencenames
310                     {
311                         $$ = emalloc(sizeof(*$$));
312                         $$->string = $1;
313                         $$->next = $3;
314                     }
315                     | IDENTIFIER
316                     {
317                         $$ = emalloc(sizeof(*$$));
318                         $$->string = $1;
319                         $$->next = NULL;
320                     }
321                     ;
322 
323 TypeAssignment      : IDENTIFIER EEQUAL Type
324                     {
325                         Symbol *s = addsym ($1);
326                         s->stype = Stype;
327                         s->type = $3;
328                         fix_labels(s);
329                         generate_type (s);
330                     }
331                     ;
332 
333 Type                : BuiltinType
334                     | ReferencedType
335                     | ConstrainedType
336                     ;
337 
338 BuiltinType         : BitStringType
339                     | BooleanType
340                     | CharacterStringType
341                     | ChoiceType
342                     | EnumeratedType
343                     | IntegerType
344                     | NullType
345                     | ObjectIdentifierType
346                     | OctetStringType
347                     | SequenceType
348                     | SequenceOfType
349                     | SetType
350                     | SetOfType
351                     | TaggedType
352                     ;
353 
354 BooleanType         : kw_BOOLEAN
355                     {
356                               $$ = new_tag(ASN1_C_UNIV, UT_Boolean,
357                                              TE_EXPLICIT, new_type(TBoolean));
358                     }
359                     ;
360 
361 range               : '(' Value RANGE Value ')'
362                     {
363                         if($2->type != integervalue)
364                               lex_error_message("Non-integer used in first part of range");
365                         if($2->type != integervalue)
366                               lex_error_message("Non-integer in second part of range");
367                         $$ = ecalloc(1, sizeof(*$$));
368                         $$->min = $2->u.integervalue;
369                         $$->max = $4->u.integervalue;
370                     }
371                     | '(' Value RANGE kw_MAX ')'
372                     {
373                         if($2->type != integervalue)
374                               lex_error_message("Non-integer in first part of range");
375                         $$ = ecalloc(1, sizeof(*$$));
376                         $$->min = $2->u.integervalue;
377                         $$->max = INT_MAX;
378                     }
379                     | '(' kw_MIN RANGE Value ')'
380                     {
381                         if($4->type != integervalue)
382                               lex_error_message("Non-integer in second part of range");
383                         $$ = ecalloc(1, sizeof(*$$));
384                         $$->min = INT_MIN;
385                         $$->max = $4->u.integervalue;
386                     }
387                     | '(' Value ')'
388                     {
389                         if($2->type != integervalue)
390                               lex_error_message("Non-integer used in limit");
391                         $$ = ecalloc(1, sizeof(*$$));
392                         $$->min = $2->u.integervalue;
393                         $$->max = $2->u.integervalue;
394                     }
395                     ;
396 
397 
398 IntegerType         : kw_INTEGER
399                     {
400                               $$ = new_tag(ASN1_C_UNIV, UT_Integer,
401                                              TE_EXPLICIT, new_type(TInteger));
402                     }
403                     | kw_INTEGER range
404                     {
405                               $$ = new_type(TInteger);
406                               $$->range = $2;
407                               $$ = new_tag(ASN1_C_UNIV, UT_Integer, TE_EXPLICIT, $$);
408                     }
409                     | kw_INTEGER '{' NamedNumberList '}'
410                     {
411                       $$ = new_type(TInteger);
412                       $$->members = $3;
413                       $$ = new_tag(ASN1_C_UNIV, UT_Integer, TE_EXPLICIT, $$);
414                     }
415                     ;
416 
417 NamedNumberList     : NamedNumber
418                     {
419                               $$ = emalloc(sizeof(*$$));
420                               ASN1_TAILQ_INIT($$);
421                               ASN1_TAILQ_INSERT_HEAD($$, $1, members);
422                     }
423                     | NamedNumberList ',' NamedNumber
424                     {
425                               ASN1_TAILQ_INSERT_TAIL($1, $3, members);
426                               $$ = $1;
427                     }
428                     | NamedNumberList ',' ELLIPSIS
429                               { $$ = $1; } /* XXX used for Enumerations */
430                     ;
431 
432 NamedNumber         : IDENTIFIER '(' SignedNumber ')'
433                     {
434                               $$ = emalloc(sizeof(*$$));
435                               $$->name = $1;
436                               $$->gen_name = estrdup($1);
437                               output_name ($$->gen_name);
438                               $$->val = $3;
439                               $$->optional = 0;
440                               $$->ellipsis = 0;
441                               $$->type = NULL;
442                     }
443                     ;
444 
445 EnumeratedType      : kw_ENUMERATED '{' Enumerations '}'
446                     {
447                       $$ = new_type(TInteger);
448                       $$->members = $3;
449                       $$ = new_tag(ASN1_C_UNIV, UT_Enumerated, TE_EXPLICIT, $$);
450                     }
451                     ;
452 
453 Enumerations        : NamedNumberList /* XXX */
454                     ;
455 
456 BitStringType       : kw_BIT kw_STRING
457                     {
458                       $$ = new_type(TBitString);
459                       $$->members = emalloc(sizeof(*$$->members));
460                       ASN1_TAILQ_INIT($$->members);
461                       $$ = new_tag(ASN1_C_UNIV, UT_BitString, TE_EXPLICIT, $$);
462                     }
463                     | kw_BIT kw_STRING '{' NamedBitList '}'
464                     {
465                       $$ = new_type(TBitString);
466                       $$->members = $4;
467                       $$ = new_tag(ASN1_C_UNIV, UT_BitString, TE_EXPLICIT, $$);
468                     }
469                     ;
470 
471 ObjectIdentifierType: kw_OBJECT kw_IDENTIFIER
472                     {
473                               $$ = new_tag(ASN1_C_UNIV, UT_OID,
474                                              TE_EXPLICIT, new_type(TOID));
475                     }
476                     ;
477 OctetStringType     : kw_OCTET kw_STRING size
478                     {
479                         Type *t = new_type(TOctetString);
480                         t->range = $3;
481                         if (t->range) {
482                               if (t->range->min < 0)
483                                   lex_error_message("can't use a negative SIZE range "
484                                                         "length for OCTET STRING");
485                         }
486                         $$ = new_tag(ASN1_C_UNIV, UT_OctetString,
487                                          TE_EXPLICIT, t);
488                     }
489                     ;
490 
491 NullType  : kw_NULL
492                     {
493                               $$ = new_tag(ASN1_C_UNIV, UT_Null,
494                                              TE_EXPLICIT, new_type(TNull));
495                     }
496                     ;
497 
498 size                :
499                     { $$ = NULL; }
500                     | kw_SIZE range
501                     { $$ = $2; }
502                     ;
503 
504 
505 SequenceType        : kw_SEQUENCE '{' /* ComponentTypeLists */ ComponentTypeList '}'
506                     {
507                       $$ = new_type(TSequence);
508                       $$->members = $3;
509                       $$ = new_tag(ASN1_C_UNIV, UT_Sequence, default_tag_env, $$);
510                     }
511                     | kw_SEQUENCE '{' '}'
512                     {
513                       $$ = new_type(TSequence);
514                       $$->members = NULL;
515                       $$ = new_tag(ASN1_C_UNIV, UT_Sequence, default_tag_env, $$);
516                     }
517                     ;
518 
519 SequenceOfType      : kw_SEQUENCE size kw_OF Type
520                     {
521                       $$ = new_type(TSequenceOf);
522                       $$->range = $2;
523                       if ($$->range) {
524                           if ($$->range->min < 0)
525                                 lex_error_message("can't use a negative SIZE range "
526                                                       "length for SEQUENCE OF");
527                         }
528 
529                       $$->subtype = $4;
530                       $$ = new_tag(ASN1_C_UNIV, UT_Sequence, default_tag_env, $$);
531                     }
532                     ;
533 
534 SetType             : kw_SET '{' /* ComponentTypeLists */ ComponentTypeList '}'
535                     {
536                       $$ = new_type(TSet);
537                       $$->members = $3;
538                       $$ = new_tag(ASN1_C_UNIV, UT_Set, default_tag_env, $$);
539                     }
540                     | kw_SET '{' '}'
541                     {
542                       $$ = new_type(TSet);
543                       $$->members = NULL;
544                       $$ = new_tag(ASN1_C_UNIV, UT_Set, default_tag_env, $$);
545                     }
546                     ;
547 
548 SetOfType : kw_SET kw_OF Type
549                     {
550                       $$ = new_type(TSetOf);
551                       $$->subtype = $3;
552                       $$ = new_tag(ASN1_C_UNIV, UT_Set, default_tag_env, $$);
553                     }
554                     ;
555 
556 ChoiceType          : kw_CHOICE '{' /* AlternativeTypeLists */ ComponentTypeList '}'
557                     {
558                       $$ = new_type(TChoice);
559                       $$->members = $3;
560                     }
561                     ;
562 
563 ReferencedType      : DefinedType
564                     | UsefulType
565                     ;
566 
567 DefinedType         : IDENTIFIER
568                     {
569                       Symbol *s = addsym($1);
570                       $$ = new_type(TType);
571                       if(s->stype != Stype && s->stype != SUndefined)
572                         lex_error_message ("%s is not a type\n", $1);
573                       else
574                         $$->symbol = s;
575                     }
576                     ;
577 
578 UsefulType          : kw_GeneralizedTime
579                     {
580                               $$ = new_tag(ASN1_C_UNIV, UT_GeneralizedTime,
581                                              TE_EXPLICIT, new_type(TGeneralizedTime));
582                     }
583                     | kw_UTCTime
584                     {
585                               $$ = new_tag(ASN1_C_UNIV, UT_UTCTime,
586                                              TE_EXPLICIT, new_type(TUTCTime));
587                     }
588                     ;
589 
590 ConstrainedType     : Type Constraint
591                     {
592                         /* if (Constraint.type == contentConstrant) {
593                            assert(Constraint.u.constraint.type == octetstring|bitstring-w/o-NamedBitList); // remember to check type reference too
594                            if (Constraint.u.constraint.type) {
595                              assert((Constraint.u.constraint.type.length % 8) == 0);
596                            }
597                           }
598                           if (Constraint.u.constraint.encoding) {
599                             type == der-oid|ber-oid
600                           }
601                         */
602                     }
603                     ;
604 
605 
606 Constraint          : '(' ConstraintSpec ')'
607                     {
608                         $$ = $2;
609                     }
610                     ;
611 
612 ConstraintSpec      : GeneralConstraint
613                     ;
614 
615 GeneralConstraint: ContentsConstraint
616                     | UserDefinedConstraint
617                     ;
618 
619 ContentsConstraint: kw_CONTAINING Type
620                     {
621                         $$ = new_constraint_spec(CT_CONTENTS);
622                         $$->u.content.type = $2;
623                         $$->u.content.encoding = NULL;
624                     }
625                     | kw_ENCODED kw_BY Value
626                     {
627                         if ($3->type != objectidentifiervalue)
628                               lex_error_message("Non-OID used in ENCODED BY constraint");
629                         $$ = new_constraint_spec(CT_CONTENTS);
630                         $$->u.content.type = NULL;
631                         $$->u.content.encoding = $3;
632                     }
633                     | kw_CONTAINING Type kw_ENCODED kw_BY Value
634                     {
635                         if ($5->type != objectidentifiervalue)
636                               lex_error_message("Non-OID used in ENCODED BY constraint");
637                         $$ = new_constraint_spec(CT_CONTENTS);
638                         $$->u.content.type = $2;
639                         $$->u.content.encoding = $5;
640                     }
641                     ;
642 
643 UserDefinedConstraint: kw_CONSTRAINED kw_BY '{' '}'
644                     {
645                         $$ = new_constraint_spec(CT_USER);
646                     }
647                     ;
648 
649 TaggedType          : Tag tagenv Type
650                     {
651                               $$ = new_type(TTag);
652                               $$->tag = $1;
653                               $$->tag.tagenv = $2;
654                               if (template_flag) {
655                                   $$->subtype = $3;
656                               } else {
657                                   if($3->type == TTag && $2 == TE_IMPLICIT) {
658                                         $$->subtype = $3->subtype;
659                                         free($3);
660                                   } else {
661                                         $$->subtype = $3;
662                                   }
663                               }
664                     }
665                     ;
666 
667 Tag                 : '[' Class NUMBER ']'
668                     {
669                               $$.tagclass = $2;
670                               $$.tagvalue = $3;
671                               $$.tagenv = default_tag_env;
672                     }
673                     ;
674 
675 Class               : /* */
676                     {
677                               $$ = ASN1_C_CONTEXT;
678                     }
679                     | kw_UNIVERSAL
680                     {
681                               $$ = ASN1_C_UNIV;
682                     }
683                     | kw_APPLICATION
684                     {
685                               $$ = ASN1_C_APPL;
686                     }
687                     | kw_PRIVATE
688                     {
689                               $$ = ASN1_C_PRIVATE;
690                     }
691                     ;
692 
693 tagenv              : /* */
694                     {
695                               $$ = default_tag_env;
696                     }
697                     | kw_EXPLICIT
698                     {
699                               $$ = default_tag_env;
700                     }
701                     | kw_IMPLICIT
702                     {
703                               $$ = TE_IMPLICIT;
704                     }
705                     ;
706 
707 
708 ValueAssignment     : IDENTIFIER Type EEQUAL Value
709                     {
710                               Symbol *s;
711                               s = addsym ($1);
712 
713                               s->stype = SValue;
714                               s->value = $4;
715                               generate_constant (s);
716                     }
717                     ;
718 
719 CharacterStringType: RestrictedCharactedStringType
720                     ;
721 
722 RestrictedCharactedStringType: kw_GeneralString
723                     {
724                               $$ = new_tag(ASN1_C_UNIV, UT_GeneralString,
725                                              TE_EXPLICIT, new_type(TGeneralString));
726                     }
727                     | kw_TeletexString
728                     {
729                               $$ = new_tag(ASN1_C_UNIV, UT_TeletexString,
730                                              TE_EXPLICIT, new_type(TTeletexString));
731                     }
732                     | kw_UTF8String
733                     {
734                               $$ = new_tag(ASN1_C_UNIV, UT_UTF8String,
735                                              TE_EXPLICIT, new_type(TUTF8String));
736                     }
737                     | kw_PrintableString
738                     {
739                               $$ = new_tag(ASN1_C_UNIV, UT_PrintableString,
740                                              TE_EXPLICIT, new_type(TPrintableString));
741                     }
742                     | kw_VisibleString
743                     {
744                               $$ = new_tag(ASN1_C_UNIV, UT_VisibleString,
745                                              TE_EXPLICIT, new_type(TVisibleString));
746                     }
747                     | kw_IA5String
748                     {
749                               $$ = new_tag(ASN1_C_UNIV, UT_IA5String,
750                                              TE_EXPLICIT, new_type(TIA5String));
751                     }
752                     | kw_BMPString
753                     {
754                               $$ = new_tag(ASN1_C_UNIV, UT_BMPString,
755                                              TE_EXPLICIT, new_type(TBMPString));
756                     }
757                     | kw_UniversalString
758                     {
759                               $$ = new_tag(ASN1_C_UNIV, UT_UniversalString,
760                                              TE_EXPLICIT, new_type(TUniversalString));
761                     }
762 
763                     ;
764 
765 ComponentTypeList: ComponentType
766                     {
767                               $$ = emalloc(sizeof(*$$));
768                               ASN1_TAILQ_INIT($$);
769                               ASN1_TAILQ_INSERT_HEAD($$, $1, members);
770                     }
771                     | ComponentTypeList ',' ComponentType
772                     {
773                               ASN1_TAILQ_INSERT_TAIL($1, $3, members);
774                               $$ = $1;
775                     }
776                     | ComponentTypeList ',' ELLIPSIS
777                     {
778                             struct member *m = ecalloc(1, sizeof(*m));
779                               m->name = estrdup("...");
780                               m->gen_name = estrdup("asn1_ellipsis");
781                               m->ellipsis = 1;
782                               ASN1_TAILQ_INSERT_TAIL($1, m, members);
783                               $$ = $1;
784                     }
785                     ;
786 
787 NamedType : IDENTIFIER Type
788                     {
789                       $$ = emalloc(sizeof(*$$));
790                       $$->name = $1;
791                       $$->gen_name = estrdup($1);
792                       output_name ($$->gen_name);
793                       $$->type = $2;
794                       $$->ellipsis = 0;
795                     }
796                     ;
797 
798 ComponentType       : NamedType
799                     {
800                               $$ = $1;
801                               $$->optional = 0;
802                               $$->defval = NULL;
803                     }
804                     | NamedType kw_OPTIONAL
805                     {
806                               $$ = $1;
807                               $$->optional = 1;
808                               $$->defval = NULL;
809                     }
810                     | NamedType kw_DEFAULT Value
811                     {
812                               $$ = $1;
813                               $$->optional = 0;
814                               $$->defval = $3;
815                     }
816                     ;
817 
818 NamedBitList        : NamedBit
819                     {
820                               $$ = emalloc(sizeof(*$$));
821                               ASN1_TAILQ_INIT($$);
822                               ASN1_TAILQ_INSERT_HEAD($$, $1, members);
823                     }
824                     | NamedBitList ',' NamedBit
825                     {
826                               ASN1_TAILQ_INSERT_TAIL($1, $3, members);
827                               $$ = $1;
828                     }
829                     ;
830 
831 NamedBit  : IDENTIFIER '(' NUMBER ')'
832                     {
833                       $$ = emalloc(sizeof(*$$));
834                       $$->name = $1;
835                       $$->gen_name = estrdup($1);
836                       output_name ($$->gen_name);
837                       $$->val = $3;
838                       $$->optional = 0;
839                       $$->ellipsis = 0;
840                       $$->type = NULL;
841                     }
842                     ;
843 
844 objid_opt : objid
845                     | /* empty */ { $$ = NULL; }
846                     ;
847 
848 objid               : '{' objid_list '}'
849                     {
850                               $$ = $2;
851                     }
852                     ;
853 
854 objid_list          :  /* empty */
855                     {
856                               $$ = NULL;
857                     }
858                     | objid_element objid_list
859                     {
860                             if ($2) {
861                                         $$ = $2;
862                                         add_oid_to_tail($2, $1);
863                               } else {
864                                         $$ = $1;
865                               }
866                     }
867                     ;
868 
869 objid_element       : IDENTIFIER '(' NUMBER ')'
870                     {
871                               $$ = new_objid($1, $3);
872                     }
873                     | IDENTIFIER
874                     {
875                         Symbol *s = addsym($1);
876                         if(s->stype != SValue ||
877                            s->value->type != objectidentifiervalue) {
878                               lex_error_message("%s is not an object identifier\n",
879                                               s->name);
880                               exit(1);
881                         }
882                         $$ = s->value->u.objectidentifiervalue;
883                     }
884                     | NUMBER
885                     {
886                         $$ = new_objid(NULL, $1);
887                     }
888                     ;
889 
890 Value               : BuiltinValue
891                     | ReferencedValue
892                     ;
893 
894 BuiltinValue        : BooleanValue
895                     | CharacterStringValue
896                     | IntegerValue
897                     | ObjectIdentifierValue
898                     | NullValue
899                     ;
900 
901 ReferencedValue     : DefinedValue
902                     ;
903 
904 DefinedValue        : Valuereference
905                     ;
906 
907 Valuereference      : IDENTIFIER
908                     {
909                               Symbol *s = addsym($1);
910                               if(s->stype != SValue)
911                                         lex_error_message ("%s is not a value\n",
912                                                             s->name);
913                               else
914                                         $$ = s->value;
915                     }
916                     ;
917 
918 CharacterStringValue: STRING
919                     {
920                               $$ = emalloc(sizeof(*$$));
921                               $$->type = stringvalue;
922                               $$->u.stringvalue = $1;
923                     }
924                     ;
925 
926 BooleanValue        : kw_TRUE
927                     {
928                               $$ = emalloc(sizeof(*$$));
929                               $$->type = booleanvalue;
930                               $$->u.booleanvalue = 0;
931                     }
932                     | kw_FALSE
933                     {
934                               $$ = emalloc(sizeof(*$$));
935                               $$->type = booleanvalue;
936                               $$->u.booleanvalue = 0;
937                     }
938                     ;
939 
940 IntegerValue        : SignedNumber
941                     {
942                               $$ = emalloc(sizeof(*$$));
943                               $$->type = integervalue;
944                               $$->u.integervalue = $1;
945                     }
946                     ;
947 
948 SignedNumber        : NUMBER
949                     ;
950 
951 NullValue : kw_NULL
952                     {
953                     }
954                     ;
955 
956 ObjectIdentifierValue: objid
957                     {
958                               $$ = emalloc(sizeof(*$$));
959                               $$->type = objectidentifiervalue;
960                               $$->u.objectidentifiervalue = $1;
961                     }
962                     ;
963 
964 %%
965 
966 void
967 yyerror (const char *s)
968 {
969      lex_error_message ("%s\n", s);
970 }
971 
972 static Type *
new_tag(int tagclass,int tagvalue,int tagenv,Type * oldtype)973 new_tag(int tagclass, int tagvalue, int tagenv, Type *oldtype)
974 {
975     Type *t;
976     if(oldtype->type == TTag && oldtype->tag.tagenv == TE_IMPLICIT) {
977           t = oldtype;
978           oldtype = oldtype->subtype; /* XXX */
979     } else
980           t = new_type (TTag);
981 
982     t->tag.tagclass = tagclass;
983     t->tag.tagvalue = tagvalue;
984     t->tag.tagenv = tagenv;
985     t->subtype = oldtype;
986     return t;
987 }
988 
989 static struct objid *
new_objid(const char * label,int value)990 new_objid(const char *label, int value)
991 {
992     struct objid *s;
993     s = emalloc(sizeof(*s));
994     s->label = label;
995     s->value = value;
996     s->next = NULL;
997     return s;
998 }
999 
1000 static void
add_oid_to_tail(struct objid * head,struct objid * tail)1001 add_oid_to_tail(struct objid *head, struct objid *tail)
1002 {
1003     struct objid *o;
1004     o = head;
1005     while (o->next)
1006           o = o->next;
1007     o->next = tail;
1008 }
1009 
1010 static unsigned long idcounter;
1011 
1012 static Type *
new_type(Typetype tt)1013 new_type (Typetype tt)
1014 {
1015     Type *t = ecalloc(1, sizeof(*t));
1016     t->type = tt;
1017     t->id = idcounter++;
1018     return t;
1019 }
1020 
1021 static struct constraint_spec *
new_constraint_spec(enum ctype ct)1022 new_constraint_spec(enum ctype ct)
1023 {
1024     struct constraint_spec *c = ecalloc(1, sizeof(*c));
1025     c->ctype = ct;
1026     return c;
1027 }
1028 
1029 static void fix_labels2(Type *t, const char *prefix);
fix_labels1(struct memhead * members,const char * prefix)1030 static void fix_labels1(struct memhead *members, const char *prefix)
1031 {
1032     Member *m;
1033 
1034     if(members == NULL)
1035           return;
1036     ASN1_TAILQ_FOREACH(m, members, members) {
1037           if (asprintf(&m->label, "%s_%s", prefix, m->gen_name) < 0)
1038               errx(1, "malloc");
1039           if (m->label == NULL)
1040               errx(1, "malloc");
1041           if(m->type != NULL)
1042               fix_labels2(m->type, m->label);
1043     }
1044 }
1045 
fix_labels2(Type * t,const char * prefix)1046 static void fix_labels2(Type *t, const char *prefix)
1047 {
1048     for(; t; t = t->subtype)
1049           fix_labels1(t->members, prefix);
1050 }
1051 
1052 static void
fix_labels(Symbol * s)1053 fix_labels(Symbol *s)
1054 {
1055     char *p = NULL;
1056     if (asprintf(&p, "choice_%s", s->gen_name) < 0 || p == NULL)
1057           errx(1, "malloc");
1058     fix_labels2(s->type, p);
1059     free(p);
1060 }
1061