~ubuntu-branches/ubuntu/trusty/erlang/trusty

« back to all changes in this revision

Viewing changes to lib/dialyzer/test/r9c_tests_SUITE_data/src/asn1/asn1ct_parser2.erl

  • Committer: Bazaar Package Importer
  • Author(s): Clint Byrum
  • Date: 2011-05-05 15:48:43 UTC
  • mfrom: (3.5.13 sid)
  • Revision ID: james.westby@ubuntu.com-20110505154843-0om6ekzg6m7ugj27
Tags: 1:14.b.2-dfsg-3ubuntu1
* Merge from debian unstable.  Remaining changes:
  - Drop libwxgtk2.8-dev build dependency. Wx isn't in main, and not
    supposed to.
  - Drop erlang-wx binary.
  - Drop erlang-wx dependency from -megaco, -common-test, and -reltool, they
    do not really need wx. Also drop it from -debugger; the GUI needs wx,
    but it apparently has CLI bits as well, and is also needed by -megaco,
    so let's keep the package for now.
  - debian/patches/series: Do what I meant, and enable build-options.patch
    instead.
* Additional changes:
  - Drop erlang-wx from -et
* Dropped Changes:
  - patches/pcre-crash.patch: CVE-2008-2371: outer level option with
    alternatives caused crash. (Applied Upstream)
  - fix for ssl certificate verification in newSSL: 
    ssl_cacertfile_fix.patch (Applied Upstream)
  - debian/patches/series: Enable native.patch again, to get stripped beam
    files and reduce the package size again. (build-options is what
    actually accomplished this)
  - Remove build-options.patch on advice from upstream and because it caused
    odd build failures.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
%% ``The contents of this file are subject to the Erlang Public License,
 
2
%% Version 1.1, (the "License"); you may not use this file except in
 
3
%% compliance with the License. You should have received a copy of the
 
4
%% Erlang Public License along with this software. If not, it can be
 
5
%% retrieved via the world wide web at http://www.erlang.org/.
 
6
%% 
 
7
%% Software distributed under the License is distributed on an "AS IS"
 
8
%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
 
9
%% the License for the specific language governing rights and limitations
 
10
%% under the License.
 
11
%% 
 
12
%% The Initial Developer of the Original Code is Ericsson Utvecklings AB.
 
13
%% Portions created by Ericsson are Copyright 2000, Ericsson Utvecklings
 
14
%% AB. All Rights Reserved.''
 
15
%% 
 
16
%%     $Id: asn1ct_parser2.erl,v 1.1 2008/12/17 09:53:30 mikpe Exp $
 
17
%%
 
18
-module(asn1ct_parser2).
 
19
 
 
20
-export([parse/1]).
 
21
-include("asn1_records.hrl").
 
22
 
 
23
%% parse all types in module
 
24
parse(Tokens) ->
 
25
    case catch parse_ModuleDefinition(Tokens) of
 
26
        {'EXIT',Reason} ->
 
27
            {error,{{undefined,get(asn1_module),
 
28
                    [internal,error,'when',parsing,module,definition,Reason]},
 
29
                    hd(Tokens)}};
 
30
        {asn1_error,Reason} ->
 
31
            {error,{Reason,hd(Tokens)}};
 
32
        {ModuleDefinition,Rest1} ->
 
33
            {Types,Rest2} = parse_AssignmentList(Rest1),
 
34
            case Rest2 of
 
35
                [{'END',_}|_Rest3] ->
 
36
                    {ok,ModuleDefinition#module{typeorval = Types}};
 
37
                _  ->
 
38
                    {error,{{get_line(hd(Rest2)),get(asn1_module),
 
39
                             [got,get_token(hd(Rest2)),expected,'END']},
 
40
                            hd(Rest2)}}
 
41
            end
 
42
    end.
 
43
 
 
44
parse_ModuleDefinition([{typereference,L1,ModuleIdentifier}|Rest0]) ->
 
45
    put(asn1_module,ModuleIdentifier),
 
46
    {_DefinitiveIdentifier,Rest02} = 
 
47
        case Rest0 of
 
48
            [{'{',_}|_Rest01] ->
 
49
                parse_ObjectIdentifierValue(Rest0);
 
50
            _ ->
 
51
                {[],Rest0}
 
52
        end,
 
53
    Rest = case Rest02 of
 
54
               [{'DEFINITIONS',_}|Rest03] ->
 
55
                   Rest03;
 
56
               _ ->
 
57
                   throw({asn1_error,{get_line(hd(Rest02)),get(asn1_module),
 
58
                                      [got,get_token(hd(Rest02)),
 
59
                                       expected,'DEFINITIONS']}})
 
60
           end,
 
61
    {TagDefault,Rest2} = 
 
62
        case Rest of
 
63
            [{'EXPLICIT',_L3},{'TAGS',_L4}|Rest1] ->
 
64
                put(tagdefault,'EXPLICIT'), {'EXPLICIT',Rest1};
 
65
            [{'IMPLICIT',_L3},{'TAGS',_L4}|Rest1] ->
 
66
                put(tagdefault,'IMPLICIT'), {'IMPLICIT',Rest1};
 
67
            [{'AUTOMATIC',_L3},{'TAGS',_L4}|Rest1] ->
 
68
                put(tagdefault,'AUTOMATIC'), {'AUTOMATIC',Rest1};
 
69
            Rest1 ->
 
70
                put(tagdefault,'EXPLICIT'), {'EXPLICIT',Rest1} % The default
 
71
        end,
 
72
    {ExtensionDefault,Rest3} = 
 
73
        case Rest2 of
 
74
            [{'EXTENSIBILITY',_L5}, {'IMPLIED',_L6}|Rest21] -> 
 
75
                {'IMPLIED',Rest21};
 
76
            _  -> {false,Rest2}
 
77
        end,
 
78
    case Rest3 of
 
79
        [{'::=',_L7}, {'BEGIN',_L8}|Rest4] ->
 
80
            {Exports, Rest5} = parse_Exports(Rest4),
 
81
            {Imports, Rest6} = parse_Imports(Rest5),
 
82
            {#module{ pos = L1,
 
83
                     name = ModuleIdentifier,
 
84
                     defid = [], % fix this
 
85
                     tagdefault = TagDefault,
 
86
                     extensiondefault = ExtensionDefault,
 
87
                     exports = Exports,
 
88
                     imports = Imports},Rest6};
 
89
        _ -> throw({asn1_error,{get_line(hd(Rest3)),get(asn1_module),
 
90
                                [got,get_token(hd(Rest3)),expected,"::= BEGIN"]}})
 
91
    end;
 
92
parse_ModuleDefinition(Tokens) ->
 
93
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
94
                       [got,get_token(hd(Tokens)),expected,typereference]}}).
 
95
    
 
96
parse_Exports([{'EXPORTS',_L1},{';',_L2}|Rest]) ->
 
97
    {{exports,[]},Rest};
 
98
parse_Exports([{'EXPORTS',_L1}|Rest]) ->
 
99
    {SymbolList,Rest2} = parse_SymbolList(Rest),
 
100
    case Rest2 of
 
101
        [{';',_}|Rest3] ->    
 
102
            {{exports,SymbolList},Rest3};
 
103
        _ ->
 
104
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
105
                               [got,get_token(hd(Rest2)),expected,';']}})
 
106
    end;
 
107
parse_Exports(Rest) ->
 
108
    {{exports,all},Rest}.
 
109
 
 
110
parse_SymbolList(Tokens) ->
 
111
    parse_SymbolList(Tokens,[]).
 
112
 
 
113
parse_SymbolList(Tokens,Acc) ->
 
114
    {Symbol,Rest} = parse_Symbol(Tokens),
 
115
    case Rest of 
 
116
        [{',',_L1}|Rest2] ->
 
117
            parse_SymbolList(Rest2,[Symbol|Acc]);
 
118
        Rest2  ->
 
119
            {lists:reverse([Symbol|Acc]),Rest2}
 
120
    end.
 
121
 
 
122
parse_Symbol(Tokens) ->
 
123
    parse_Reference(Tokens).
 
124
 
 
125
parse_Reference([{typereference,L1,TrefName},{'{',_L2},{'}',_L3}|Rest]) ->
 
126
%    {Tref,Rest};
 
127
    {tref2Exttref(L1,TrefName),Rest};
 
128
parse_Reference([Tref1 = {typereference,_,_},{'.',_},Tref2 = {typereference,_,_},
 
129
                 {'{',_L2},{'}',_L3}|Rest]) ->
 
130
%    {{Tref1,Tref2},Rest};
 
131
    {{tref2Exttref(Tref1),tref2Exttref(Tref2)},Rest};
 
132
parse_Reference([Tref = {typereference,_L1,_TrefName}|Rest]) ->
 
133
    {tref2Exttref(Tref),Rest};
 
134
parse_Reference([Vref = {identifier,_L1,_VName}|Rest]) ->
 
135
    {identifier2Extvalueref(Vref),Rest};
 
136
parse_Reference(Tokens) ->
 
137
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
138
                       [got,get_token(hd(Tokens)),expected,
 
139
                        [typereference,identifier]]}}).
 
140
 
 
141
parse_Imports([{'IMPORTS',_L1},{';',_L2}|Rest]) ->
 
142
    {{imports,[]},Rest};
 
143
parse_Imports([{'IMPORTS',_L1}|Rest]) ->
 
144
    {SymbolsFromModuleList,Rest2} = parse_SymbolsFromModuleList(Rest),
 
145
    case Rest2 of
 
146
        [{';',_L2}|Rest3] ->
 
147
            {{imports,SymbolsFromModuleList},Rest3};
 
148
        Rest3 ->
 
149
            throw({asn1_error,{get_line(hd(Rest3)),get(asn1_module),
 
150
                               [got,get_token(hd(Rest3)),expected,';']}})
 
151
    end;
 
152
parse_Imports(Tokens) ->
 
153
    {{imports,[]},Tokens}.
 
154
 
 
155
parse_SymbolsFromModuleList(Tokens) ->
 
156
    parse_SymbolsFromModuleList(Tokens,[]).
 
157
 
 
158
parse_SymbolsFromModuleList(Tokens,Acc) ->
 
159
    {SymbolsFromModule,Rest} = parse_SymbolsFromModule(Tokens),
 
160
    case (catch parse_SymbolsFromModule(Rest)) of 
 
161
        {Sl,_Rest2} when record(Sl,'SymbolsFromModule') ->
 
162
            parse_SymbolsFromModuleList(Rest,[SymbolsFromModule|Acc]);
 
163
        _  ->
 
164
            {lists:reverse([SymbolsFromModule|Acc]),Rest}
 
165
    end.
 
166
    
 
167
parse_SymbolsFromModule(Tokens) ->
 
168
    SetRefModuleName =
 
169
        fun(N) ->
 
170
                fun(X) when record(X,'Externaltypereference')->
 
171
                        X#'Externaltypereference'{module=N};
 
172
                   (X) when record(X,'Externalvaluereference')->
 
173
                        X#'Externalvaluereference'{module=N} 
 
174
                end
 
175
        end,
 
176
    {SymbolList,Rest} = parse_SymbolList(Tokens),
 
177
    case Rest of
 
178
        %%How does this case correspond to x.680 ?
 
179
        [{'FROM',_L1},Tref = {typereference,_,_},Ref={identifier,_L2,_Id},C={',',_}|Rest2] ->
 
180
            {#'SymbolsFromModule'{symbols=SymbolList,
 
181
                                  module=tref2Exttref(Tref)},[Ref,C|Rest2]};
 
182
        %%How does this case correspond to x.680 ?
 
183
        [{'FROM',_L1},Tref = {typereference,_,_},{identifier,_L2,_Id}|Rest2] ->
 
184
            {#'SymbolsFromModule'{symbols=SymbolList,
 
185
                                  module=tref2Exttref(Tref)},Rest2}; 
 
186
        [{'FROM',_L1},Tref = {typereference,_,Name},Brace = {'{',_}|Rest2] ->
 
187
            {_ObjIdVal,Rest3} = parse_ObjectIdentifierValue([Brace|Rest2]), % value not used yet, fix me
 
188
            NewSymbolList = lists:map(SetRefModuleName(Name),SymbolList),
 
189
            {#'SymbolsFromModule'{symbols=NewSymbolList,
 
190
                                  module=tref2Exttref(Tref)},Rest3}; 
 
191
        [{'FROM',_L1},Tref = {typereference,_,Name}|Rest2] ->
 
192
            NewSymbolList = lists:map(SetRefModuleName(Name),SymbolList),
 
193
            {#'SymbolsFromModule'{symbols=NewSymbolList,
 
194
                                  module=tref2Exttref(Tref)},Rest2};
 
195
        _ ->
 
196
            throw({asn1_error,{get_line(hd(Rest)),get(asn1_module),
 
197
                               [got,get_token(hd(Rest)),expected,
 
198
                                ['FROM typerefernece identifier ,',
 
199
                                 'FROM typereference identifier',
 
200
                                 'FROM typereference {',
 
201
                                 'FROM typereference']]}})
 
202
    end.
 
203
 
 
204
parse_ObjectIdentifierValue([{'{',_}|Rest]) ->
 
205
    parse_ObjectIdentifierValue(Rest,[]).
 
206
 
 
207
parse_ObjectIdentifierValue([{number,_,Num}|Rest],Acc) ->
 
208
    parse_ObjectIdentifierValue(Rest,[Num|Acc]);
 
209
parse_ObjectIdentifierValue([{identifier,_,Id},{'(',_}, {number,_,Num}, {')',_}|Rest],Acc) ->
 
210
    parse_ObjectIdentifierValue(Rest,[{'NamedNumber',Id,Num}|Acc]);
 
211
parse_ObjectIdentifierValue([{identifier,_,Id},{'(',_}, {identifier,_,Id2}, {')',_}|Rest],Acc) ->
 
212
    parse_ObjectIdentifierValue(Rest,[{'NamedNumber',Id,Id2}|Acc]);
 
213
parse_ObjectIdentifierValue([{identifier,_,Id},{'(',_}, {typereference,_,Tref},{'.',_},{identifier,_,Id2}, {')',_}|Rest],Acc) ->
 
214
    parse_ObjectIdentifierValue(Rest,[{'NamedNumber',Id,{'ExternalValue',Tref,Id2}}|Acc]);
 
215
parse_ObjectIdentifierValue([Id = {identifier,_,_}|Rest],Acc) ->
 
216
    parse_ObjectIdentifierValue(Rest,[identifier2Extvalueref(Id)|Acc]);
 
217
parse_ObjectIdentifierValue([{'}',_}|Rest],Acc) ->
 
218
    {lists:reverse(Acc),Rest};
 
219
parse_ObjectIdentifierValue([H|_T],_Acc) ->
 
220
    throw({asn1_error,{get_line(H),get(asn1_module),
 
221
                       [got,get_token(H),expected,
 
222
                        ['{ some of the following }',number,'identifier ( number )',
 
223
                         'identifier ( identifier )',
 
224
                         'identifier ( typereference.identifier)',identifier]]}}).
 
225
    
 
226
parse_AssignmentList(Tokens = [{'END',_}|_Rest]) ->
 
227
    {[],Tokens};
 
228
parse_AssignmentList(Tokens = [{'$end',_}|_Rest]) ->
 
229
    {[],Tokens};
 
230
parse_AssignmentList(Tokens) ->
 
231
    parse_AssignmentList(Tokens,[]).
 
232
 
 
233
parse_AssignmentList(Tokens= [{'END',_}|_Rest],Acc) ->
 
234
    {lists:reverse(Acc),Tokens};
 
235
parse_AssignmentList(Tokens= [{'$end',_}|_Rest],Acc) ->
 
236
    {lists:reverse(Acc),Tokens};
 
237
parse_AssignmentList(Tokens,Acc) ->
 
238
    case (catch parse_Assignment(Tokens)) of
 
239
        {'EXIT',Reason} ->
 
240
            exit(Reason);
 
241
        {asn1_error,R} ->
 
242
%           [H|T] = Tokens,
 
243
            throw({error,{R,hd(Tokens)}});
 
244
        {Assignment,Rest} ->
 
245
            parse_AssignmentList(Rest,[Assignment|Acc])
 
246
    end.
 
247
 
 
248
parse_Assignment(Tokens) ->
 
249
    Flist = [fun parse_TypeAssignment/1,
 
250
             fun parse_ValueAssignment/1,
 
251
             fun parse_ObjectClassAssignment/1,
 
252
             fun parse_ObjectAssignment/1,
 
253
             fun parse_ObjectSetAssignment/1,
 
254
             fun parse_ParameterizedAssignment/1,
 
255
             fun parse_ValueSetTypeAssignment/1],
 
256
    case (catch parse_or(Tokens,Flist)) of
 
257
        {'EXIT',Reason} ->
 
258
            exit(Reason);
 
259
        AsnErr = {asn1_error,_} ->
 
260
            throw(AsnErr);
 
261
        {asn1_assignment_error,Reason} ->
 
262
            throw({asn1_error,Reason});
 
263
        Result ->
 
264
            Result
 
265
    end.
 
266
 
 
267
 
 
268
parse_or(Tokens,Flist) ->
 
269
        parse_or(Tokens,Flist,[]).
 
270
 
 
271
parse_or(_Tokens,[],ErrList) ->
 
272
    case ErrList of
 
273
        [] ->
 
274
            throw({asn1_error,{parse_or,ErrList}});
 
275
        L when list(L) ->
 
276
%%%         throw({asn1_error,{parse_or,hd(lists:reverse(ErrList))}});
 
277
            %% chose to throw 1) the error with the highest line no,
 
278
            %% 2) the last error which is not a asn1_assignment_error or
 
279
            %% 3) the last error.
 
280
            throw(prioritize_error(ErrList));
 
281
        Other ->
 
282
            throw({asn1_error,{parse_or,Other}})
 
283
    end;
 
284
parse_or(Tokens,[Fun|Frest],ErrList) ->
 
285
    case (catch Fun(Tokens)) of
 
286
        Exit = {'EXIT',_Reason} ->
 
287
            parse_or(Tokens,Frest,[Exit|ErrList]);
 
288
        AsnErr = {asn1_error,_} ->
 
289
            parse_or(Tokens,Frest,[AsnErr|ErrList]);
 
290
        AsnAssErr = {asn1_assignment_error,_} ->
 
291
            parse_or(Tokens,Frest,[AsnAssErr|ErrList]);
 
292
        Result = {_,L} when list(L) ->
 
293
            Result;
 
294
%       Result ->
 
295
%           Result
 
296
        Error  ->
 
297
            parse_or(Tokens,Frest,[Error|ErrList])
 
298
    end.
 
299
 
 
300
parse_TypeAssignment([{typereference,L1,Tref},{'::=',_}|Rest]) ->       
 
301
    {Type,Rest2} = parse_Type(Rest),
 
302
    {#typedef{pos=L1,name=Tref,typespec=Type},Rest2};
 
303
parse_TypeAssignment([H1,H2|_Rest]) ->
 
304
    throw({asn1_assignment_error,{get_line(H1),get(asn1_module),
 
305
                                  [got,[get_token(H1),get_token(H2)], expected,
 
306
                                   typereference,'::=']}});
 
307
parse_TypeAssignment([H|_T]) ->
 
308
    throw({asn1_assignment_error,{get_line(H),get(asn1_module),
 
309
                                  [got,get_token(H),expected,
 
310
                                   typereference]}}).
 
311
 
 
312
parse_Type(Tokens) ->
 
313
    {Tag,Rest3} = case Tokens of
 
314
                      [Lbr= {'[',_}|Rest] ->
 
315
                          parse_Tag([Lbr|Rest]);
 
316
                      Rest-> {[],Rest}
 
317
                  end,
 
318
    {Tag2,Rest4} = case Rest3 of
 
319
                       [{'IMPLICIT',_}|Rest31] when record(Tag,tag)->
 
320
                           {[Tag#tag{type='IMPLICIT'}],Rest31};
 
321
                       [{'EXPLICIT',_}|Rest31] when record(Tag,tag)->
 
322
                           {[Tag#tag{type='EXPLICIT'}],Rest31};
 
323
                       Rest31 when record(Tag,tag) ->
 
324
                           {[Tag#tag{type={default,get(tagdefault)}}],Rest31};
 
325
                       Rest31 ->
 
326
                           {Tag,Rest31}
 
327
                   end,
 
328
    Flist = [fun parse_BuiltinType/1,fun parse_ReferencedType/1,fun parse_TypeWithConstraint/1],
 
329
    {Type,Rest5} = case (catch parse_or(Rest4,Flist)) of
 
330
                      {'EXIT',Reason} ->
 
331
                          exit(Reason);
 
332
                        AsnErr = {asn1_error,_Reason} ->
 
333
                         throw(AsnErr);
 
334
                      Result ->
 
335
                          Result
 
336
                  end,
 
337
    case hd(Rest5) of
 
338
        {'(',_} ->
 
339
            {Constraints,Rest6} = parse_Constraints(Rest5),
 
340
            if record(Type,type) ->
 
341
                    {Type#type{constraint=merge_constraints(Constraints),
 
342
                               tag=Tag2},Rest6};
 
343
               true ->
 
344
                    {#type{def=Type,constraint=merge_constraints(Constraints),
 
345
                           tag=Tag2},Rest6}
 
346
            end;
 
347
        _ ->
 
348
            if record(Type,type) ->
 
349
                    {Type#type{tag=Tag2},Rest5};
 
350
               true ->
 
351
                    {#type{def=Type,tag=Tag2},Rest5}
 
352
            end
 
353
    end.
 
354
 
 
355
parse_BuiltinType([{'BIT',_},{'STRING',_}|Rest]) ->
 
356
    case Rest of 
 
357
        [{'{',_}|Rest2] ->
 
358
            {NamedNumberList,Rest3} = parse_NamedNumberList(Rest2),
 
359
            case Rest3 of
 
360
                [{'}',_}|Rest4] ->
 
361
                    {#type{def={'BIT STRING',NamedNumberList}},Rest4};
 
362
                _ ->
 
363
                    throw({asn1_error,{get_line(hd(Rest3)),get(asn1_module),
 
364
                                       [got,get_token(hd(Rest3)),expected,'}']}})
 
365
            end;
 
366
         _ ->
 
367
            {{'BIT STRING',[]},Rest}
 
368
    end;
 
369
parse_BuiltinType([{'BOOLEAN',_}|Rest]) ->
 
370
    {#type{def='BOOLEAN'},Rest};
 
371
%% CharacterStringType ::= RestrictedCharacterStringType | 
 
372
%%                         UnrestrictedCharacterStringType
 
373
parse_BuiltinType([{restrictedcharacterstringtype,_,StringName}|Rest]) ->
 
374
    {#type{def=StringName},Rest};
 
375
parse_BuiltinType([{'CHARACTER',_},{'STRING',_}|Rest]) ->
 
376
    {#type{def='CHARACTER STRING'},Rest};
 
377
 
 
378
parse_BuiltinType([{'CHOICE',_},{'{',_}|Rest]) ->
 
379
    {AlternativeTypeLists,Rest2} = parse_AlternativeTypeLists(Rest),
 
380
    case Rest2 of
 
381
        [{'}',_}|Rest3] ->
 
382
            {#type{def={'CHOICE',AlternativeTypeLists}},Rest3};
 
383
        _  ->
 
384
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
385
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
386
    end;
 
387
parse_BuiltinType([{'EMBEDDED',_},{'PDV',_}|Rest]) ->
 
388
    {#type{def='EMBEDDED PDV'},Rest};
 
389
parse_BuiltinType([{'ENUMERATED',_},{'{',_}|Rest]) ->
 
390
    {Enumerations,Rest2} = parse_Enumerations(Rest),
 
391
    case Rest2 of
 
392
        [{'}',_}|Rest3] ->
 
393
            {#type{def={'ENUMERATED',Enumerations}},Rest3};
 
394
        _ ->
 
395
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
396
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
397
    end;
 
398
parse_BuiltinType([{'EXTERNAL',_}|Rest]) ->
 
399
    {#type{def='EXTERNAL'},Rest};
 
400
 
 
401
% InstanceOfType
 
402
parse_BuiltinType([{'INSTANCE',_},{'OF',_}|Rest]) ->
 
403
    {DefinedObjectClass,Rest2} = parse_DefinedObjectClass(Rest),
 
404
    case Rest2 of
 
405
        [{'(',_}|_] ->
 
406
            {Constraint,Rest3} = parse_Constraint(Rest2),
 
407
            {#type{def={'INSTANCE OF',DefinedObjectClass,Constraint}},Rest3};
 
408
        _ ->
 
409
            {#type{def={'INSTANCE OF',DefinedObjectClass,[]}},Rest2}
 
410
    end;
 
411
 
 
412
% parse_BuiltinType(Tokens) ->
 
413
    
 
414
parse_BuiltinType([{'INTEGER',_}|Rest]) ->
 
415
    case Rest of 
 
416
        [{'{',_}|Rest2] ->
 
417
            {NamedNumberList,Rest3} = parse_NamedNumberList(Rest2),
 
418
            case Rest3 of
 
419
                [{'}',_}|Rest4] ->
 
420
                    {#type{def={'INTEGER',NamedNumberList}},Rest4};
 
421
                _ ->
 
422
                    throw({asn1_error,{get_line(hd(Rest3)),get(asn1_module),
 
423
                                       [got,get_token(hd(Rest3)),expected,'}']}})
 
424
            end;
 
425
         _ ->
 
426
            {#type{def='INTEGER'},Rest}
 
427
    end;
 
428
parse_BuiltinType([{'NULL',_}|Rest]) ->
 
429
    {#type{def='NULL'},Rest};
 
430
 
 
431
% ObjectClassFieldType fix me later
 
432
 
 
433
parse_BuiltinType([{'OBJECT',_},{'IDENTIFIER',_}|Rest]) ->
 
434
    {#type{def='OBJECT IDENTIFIER'},Rest};
 
435
parse_BuiltinType([{'OCTET',_},{'STRING',_}|Rest]) ->
 
436
    {#type{def='OCTET STRING'},Rest};
 
437
parse_BuiltinType([{'REAL',_}|Rest]) ->
 
438
    {#type{def='REAL'},Rest};
 
439
parse_BuiltinType([{'SEQUENCE',_},{'{',_},{'...',Line},{'}',_}|Rest]) ->
 
440
    {#type{def=#'SEQUENCE'{components=[{'EXTENSIONMARK',Line,undefined}]}},
 
441
     Rest};
 
442
parse_BuiltinType([{'SEQUENCE',_},{'{',_},{'...',Line},{'!',_}|Rest]) ->
 
443
    {ExceptionIdentification,Rest2} = parse_ExceptionIdentification(Rest),
 
444
    case Rest2 of
 
445
        [{'}',_}|Rest3] ->
 
446
            {#type{def=#'SEQUENCE'{components=[{'EXTENSIONMARK',
 
447
                                                Line,
 
448
                                                ExceptionIdentification}]}},
 
449
             Rest3};
 
450
        _ ->
 
451
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
452
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
453
    end;
 
454
parse_BuiltinType([{'SEQUENCE',_},{'{',_}|Rest]) ->
 
455
    {ComponentTypeLists,Rest2} = parse_ComponentTypeLists(Rest),
 
456
    case Rest2  of
 
457
        [{'}',_}|Rest3] ->
 
458
            {#type{def=#'SEQUENCE'{components=ComponentTypeLists}},Rest3};
 
459
        _ ->
 
460
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
461
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
462
    end;
 
463
parse_BuiltinType([{'SEQUENCE',_},{'OF',_}|Rest]) ->
 
464
    {Type,Rest2} = parse_Type(Rest),
 
465
    {#type{def={'SEQUENCE OF',Type}},Rest2};
 
466
 
 
467
 
 
468
parse_BuiltinType([{'SET',_},{'{',_},{'...',Line},{'}',_}|Rest]) ->
 
469
    {#type{def=#'SET'{components=[{'EXTENSIONMARK',Line,undefined}]}},Rest};
 
470
parse_BuiltinType([{'SET',_},{'{',_},{'...',Line},{'!',_}|Rest]) ->
 
471
    {ExceptionIdentification,Rest2} = parse_ExceptionIdentification(Rest),
 
472
    case Rest2 of
 
473
        [{'}',_}|Rest3] ->
 
474
            {#type{def=#'SET'{components=
 
475
                              [{'EXTENSIONMARK',Line,ExceptionIdentification}]}},
 
476
             Rest3};
 
477
        _ ->
 
478
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
479
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
480
    end;
 
481
parse_BuiltinType([{'SET',_},{'{',_}|Rest]) ->
 
482
    {ComponentTypeLists,Rest2} = parse_ComponentTypeLists(Rest),
 
483
    case Rest2  of
 
484
        [{'}',_}|Rest3] ->
 
485
            {#type{def=#'SET'{components=ComponentTypeLists}},Rest3};
 
486
        _ ->
 
487
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
488
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
489
    end;
 
490
parse_BuiltinType([{'SET',_},{'OF',_}|Rest]) ->
 
491
    {Type,Rest2} = parse_Type(Rest),
 
492
    {#type{def={'SET OF',Type}},Rest2};
 
493
 
 
494
%% The so called Useful types
 
495
parse_BuiltinType([{'GeneralizedTime',_}|Rest]) ->
 
496
    {#type{def='GeneralizedTime'},Rest};
 
497
parse_BuiltinType([{'UTCTime',_}|Rest]) ->
 
498
    {#type{def='UTCTime'},Rest};
 
499
parse_BuiltinType([{'ObjectDescriptor',_}|Rest]) ->
 
500
    {#type{def='ObjectDescriptor'},Rest};
 
501
 
 
502
%% For compatibility with old standard
 
503
parse_BuiltinType([{'ANY',_},{'DEFINED',_},{'BY',_},{identifier,_,Id}|Rest]) ->
 
504
    {#type{def={'ANY_DEFINED_BY',Id}},Rest};
 
505
parse_BuiltinType([{'ANY',_}|Rest]) ->
 
506
    {#type{def='ANY'},Rest};
 
507
 
 
508
parse_BuiltinType(Tokens) ->
 
509
    parse_ObjectClassFieldType(Tokens).
 
510
%    throw({asn1_error,unhandled_type}).
 
511
 
 
512
 
 
513
parse_TypeWithConstraint([{'SEQUENCE',_},Lpar = {'(',_}|Rest]) ->
 
514
    {Constraint,Rest2} = parse_Constraint([Lpar|Rest]),
 
515
    case Rest2 of
 
516
        [{'OF',_}|Rest3] ->
 
517
            {Type,Rest4} = parse_Type(Rest3),
 
518
            {#type{def = {'SEQUENCE OF',Type}, constraint = merge_constraints([Constraint])},Rest4};
 
519
        _ ->
 
520
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
521
                               [got,get_token(hd(Rest2)),expected,'OF']}})
 
522
    end;
 
523
parse_TypeWithConstraint([{'SEQUENCE',_},{'SIZE',_},Lpar = {'(',_}|Rest]) ->
 
524
    {Constraint,Rest2} = parse_Constraint([Lpar|Rest]),
 
525
    Constraint2 =
 
526
        case Constraint of
 
527
            #constraint{c=C} ->
 
528
                Constraint#constraint{c={'SizeConstraint',C}};
 
529
            _ -> Constraint
 
530
        end,
 
531
    case Rest2 of
 
532
        [{'OF',_}|Rest3] ->
 
533
            {Type,Rest4} = parse_Type(Rest3),
 
534
            {#type{def = {'SEQUENCE OF',Type}, constraint = merge_constraints([Constraint2])},Rest4};
 
535
        _ ->
 
536
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
537
                               [got,get_token(hd(Rest2)),expected,'OF']}})
 
538
    end;
 
539
parse_TypeWithConstraint([{'SET',_},Lpar = {'(',_}|Rest]) ->
 
540
    {Constraint,Rest2} = parse_Constraint([Lpar|Rest]),
 
541
    case Rest2 of
 
542
        [{'OF',_}|Rest3] ->
 
543
            {Type,Rest4} = parse_Type(Rest3),
 
544
            {#type{def = {'SET OF',Type}, constraint = merge_constraints([Constraint])},Rest4};
 
545
        _ ->
 
546
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
547
                               [got,get_token(hd(Rest2)),expected,'OF']}})
 
548
    end;
 
549
parse_TypeWithConstraint([{'SET',_},{'SIZE',_},Lpar = {'(',_}|Rest]) ->
 
550
    {Constraint,Rest2} = parse_Constraint([Lpar|Rest]),
 
551
    Constraint2 =
 
552
        case Constraint of
 
553
            #constraint{c=C} ->
 
554
                Constraint#constraint{c={'SizeConstraint',C}};
 
555
            _ -> Constraint
 
556
        end,
 
557
    case Rest2 of
 
558
        [{'OF',_}|Rest3] ->
 
559
            {Type,Rest4} = parse_Type(Rest3),
 
560
            {#type{def = {'SET OF',Type}, constraint = merge_constraints([Constraint2])},Rest4};
 
561
        _ ->
 
562
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
563
                               [got,get_token(hd(Rest2)),expected,'OF']}})
 
564
    end;
 
565
parse_TypeWithConstraint(Tokens) ->
 
566
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
567
                       [got,get_token(hd(Tokens)),expected,
 
568
                       ['SEQUENCE','SEQUENCE SIZE','SET','SET SIZE'],
 
569
                       followed,by,a,constraint]}}).
 
570
 
 
571
 
 
572
%% --------------------------
 
573
 
 
574
parse_ReferencedType(Tokens) ->
 
575
    Flist = [fun parse_DefinedType/1,
 
576
             fun parse_SelectionType/1,
 
577
             fun parse_TypeFromObject/1,
 
578
             fun parse_ValueSetFromObjects/1],
 
579
    case (catch parse_or(Tokens,Flist)) of
 
580
        {'EXIT',Reason} ->
 
581
            exit(Reason);
 
582
        AsnErr = {asn1_error,_} ->
 
583
            throw(AsnErr);
 
584
        Result ->
 
585
            Result
 
586
    end.
 
587
    
 
588
parse_DefinedType(Tokens=[{typereference,_,_},{'{',_}|_Rest]) ->
 
589
    parse_ParameterizedType(Tokens);
 
590
parse_DefinedType(Tokens=[{typereference,L1,TypeName},
 
591
                          T2={typereference,_,_},T3={'{',_}|Rest]) ->
 
592
    case (catch parse_ParameterizedType(Tokens)) of
 
593
        {'EXIT',_Reason} ->
 
594
            Rest2 = [T2,T3|Rest],
 
595
            {#type{def = #'Externaltypereference'{pos=L1,
 
596
                                                  module=get(asn1_module),
 
597
                                                  type=TypeName}},Rest2};
 
598
        {asn1_error,_} ->
 
599
            Rest2 = [T2,T3|Rest],
 
600
            {#type{def = #'Externaltypereference'{pos=L1,
 
601
                                                  module=get(asn1_module),
 
602
                                                  type=TypeName}},Rest2};
 
603
        Result ->
 
604
            Result
 
605
    end;
 
606
parse_DefinedType([{typereference,L1,Module},{'.',_},{typereference,_,TypeName}|Rest]) ->
 
607
    {#type{def = #'Externaltypereference'{pos=L1,module=Module,type=TypeName}},Rest};
 
608
parse_DefinedType([{typereference,L1,TypeName}|Rest]) ->
 
609
    {#type{def = #'Externaltypereference'{pos=L1,module=get(asn1_module),
 
610
                                          type=TypeName}},Rest};
 
611
parse_DefinedType(Tokens) ->
 
612
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
613
                       [got,get_token(hd(Tokens)),expected,
 
614
                        [typereference,'typereference.typereference',
 
615
                         'typereference typereference']]}}).
 
616
 
 
617
parse_SelectionType([{identifier,_,Name},{'<',_}|Rest]) ->    
 
618
    {Type,Rest2} = parse_Type(Rest),
 
619
    {{'SelectionType',Name,Type},Rest2};
 
620
parse_SelectionType(Tokens) ->
 
621
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
622
                       [got,get_token(hd(Tokens)),expected,'identifier <']}}).
 
623
    
 
624
 
 
625
%% --------------------------
 
626
 
 
627
 
 
628
%% This should probably be removed very soon 
 
629
% parse_ConstrainedType(Tokens) ->
 
630
%     case (catch parse_TypeWithConstraint(Tokens)) of
 
631
%       {'EXIT',Reason} ->
 
632
%           {Type,Rest} = parse_Type(Tokens),
 
633
%           {Constraint,Rest2} = parse_Constraint(Rest),
 
634
%           {Type#type{constraint=Constraint},Rest2};
 
635
%       {asn1_error,Reason2} ->
 
636
%           {Type,Rest} = parse_Type(Tokens),
 
637
%           {Constraint,Rest2} = parse_Constraint(Rest),
 
638
%           {Type#type{constraint=Constraint},Rest2};
 
639
%       Result ->
 
640
%           Result
 
641
%     end.
 
642
 
 
643
parse_Constraints(Tokens) ->
 
644
    parse_Constraints(Tokens,[]).
 
645
 
 
646
parse_Constraints(Tokens,Acc) ->
 
647
    {Constraint,Rest} = parse_Constraint(Tokens),
 
648
    case Rest of
 
649
        [{'(',_}|_Rest2] ->
 
650
            parse_Constraints(Rest,[Constraint|Acc]);
 
651
        _ ->
 
652
            {lists:reverse([Constraint|Acc]),Rest}
 
653
    end.
 
654
 
 
655
parse_Constraint([{'(',_}|Rest]) ->
 
656
    {Constraint,Rest2} = parse_ConstraintSpec(Rest),
 
657
    {Exception,Rest3} = parse_ExceptionSpec(Rest2),
 
658
    case Rest3 of
 
659
        [{')',_}|Rest4] ->
 
660
            {#constraint{c=Constraint,e=Exception},Rest4};
 
661
        [H|_T] ->
 
662
            throw({asn1_error,{get_line(H),get(asn1_module),
 
663
                               [got,get_token(H),expected,')']}})
 
664
    end;
 
665
parse_Constraint(Tokens) ->
 
666
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
667
                       [got,get_token(hd(Tokens)),expected,'(']}}).
 
668
 
 
669
parse_ConstraintSpec(Tokens) ->
 
670
    Flist = [fun parse_GeneralConstraint/1,
 
671
             fun parse_SubtypeConstraint/1],
 
672
    case (catch parse_or(Tokens,Flist)) of
 
673
        {'EXIT',Reason} ->
 
674
            exit(Reason);
 
675
        {asn1_error,Reason2} ->
 
676
            throw({asn1_error,Reason2});
 
677
        Result ->
 
678
            Result
 
679
    end.
 
680
 
 
681
parse_ExceptionSpec([LPar={')',_}|Rest]) ->
 
682
    {undefined,[LPar|Rest]};
 
683
parse_ExceptionSpec([{'!',_}|Rest]) ->
 
684
    parse_ExceptionIdentification(Rest);
 
685
parse_ExceptionSpec(Tokens) ->
 
686
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
687
                       [got,get_token(hd(Tokens)),expected,[')','!']]}}).
 
688
 
 
689
parse_ExceptionIdentification(Tokens) ->
 
690
    Flist = [fun parse_SignedNumber/1,
 
691
             fun parse_DefinedValue/1,
 
692
             fun parse_TypeColonValue/1],
 
693
    case (catch parse_or(Tokens,Flist)) of
 
694
        {'EXIT',Reason} ->
 
695
            exit(Reason);
 
696
        {asn1_error,Reason2} ->
 
697
            throw({asn1_error,Reason2});
 
698
        Result ->
 
699
            Result
 
700
    end.
 
701
 
 
702
parse_TypeColonValue(Tokens) ->
 
703
    {Type,Rest} = parse_Type(Tokens),
 
704
    case Rest of
 
705
        [{':',_}|Rest2] ->
 
706
            {Value,Rest3} = parse_Value(Rest2),
 
707
            {{Type,Value},Rest3};
 
708
        [H|_T] ->
 
709
            throw({asn1_error,{get_line(H),get(asn1_module),
 
710
                               [got,get_token(H),expected,':']}})
 
711
    end.
 
712
 
 
713
parse_SubtypeConstraint(Tokens) ->
 
714
    parse_ElementSetSpecs(Tokens).
 
715
 
 
716
parse_ElementSetSpecs([{'...',_}|Rest]) ->
 
717
    {Elements,Rest2} = parse_ElementSetSpec(Rest),
 
718
    {{[],Elements},Rest2};
 
719
parse_ElementSetSpecs(Tokens) ->
 
720
    {RootElems,Rest} = parse_ElementSetSpec(Tokens),
 
721
    case Rest of
 
722
        [{',',_},{'...',_},{',',_}|Rest2] ->
 
723
            {AdditionalElems,Rest3} = parse_ElementSetSpec(Rest2),
 
724
            {{RootElems,AdditionalElems},Rest3};
 
725
        [{',',_},{'...',_}|Rest2] ->
 
726
            {{RootElems,[]},Rest2};
 
727
        _ ->
 
728
            {RootElems,Rest}
 
729
    end.
 
730
 
 
731
parse_ElementSetSpec([{'ALL',_},{'EXCEPT',_}|Rest]) ->
 
732
    {Exclusions,Rest2} = parse_Elements(Rest),
 
733
    {{'ALL',{'EXCEPT',Exclusions}},Rest2};
 
734
parse_ElementSetSpec(Tokens) ->
 
735
    parse_Unions(Tokens).
 
736
 
 
737
 
 
738
parse_Unions(Tokens) ->
 
739
    {InterSec,Rest} = parse_Intersections(Tokens),
 
740
    {Unions,Rest2} = parse_UnionsRec(Rest),
 
741
    case {InterSec,Unions} of
 
742
        {InterSec,[]} ->
 
743
            {InterSec,Rest2};
 
744
        {{'SingleValue',V1},{'SingleValue',V2}} ->
 
745
            {{'SingleValue',ordsets:union(to_set(V1),to_set(V2))},Rest2};
 
746
        {V1,V2} when list(V2) ->
 
747
            {[V1] ++ [union|V2],Rest2};
 
748
        {V1,V2} ->
 
749
            {[V1,union,V2],Rest2}
 
750
%       Other ->
 
751
%           throw(Other)
 
752
    end.
 
753
 
 
754
parse_UnionsRec([{'|',_}|Rest]) ->
 
755
    {InterSec,Rest2} = parse_Intersections(Rest),
 
756
    {URec,Rest3} = parse_UnionsRec(Rest2),
 
757
    case {InterSec,URec} of
 
758
        {V1,[]} ->
 
759
            {V1,Rest3};
 
760
        {{'SingleValue',V1},{'SingleValue',V2}} ->
 
761
            {{'SingleValue',ordsets:union(to_set(V1),to_set(V2))},Rest3};
 
762
        {V1,V2} when list(V2) ->
 
763
            {[V1] ++ V2,Rest3};
 
764
        {V1,V2} ->
 
765
            {[V1,V2],Rest3}
 
766
        end;
 
767
parse_UnionsRec([{'UNION',_}|Rest]) ->
 
768
    {InterSec,Rest2} = parse_Intersections(Rest),
 
769
    {URec,Rest3} = parse_UnionsRec(Rest2),
 
770
    case {InterSec,URec} of
 
771
        {V1,[]} ->
 
772
            {V1,Rest3};
 
773
        {{'SingleValue',V1},{'SingleValue',V2}} ->
 
774
            {{'SingleValue',ordsets:union(to_set(V1),to_set(V2))},Rest3};
 
775
        {V1,V2} when list(V2) ->
 
776
            {[V1] ++ V2,Rest3};
 
777
        {V1,V2} ->
 
778
            {[V1,V2],Rest3}
 
779
        end;
 
780
parse_UnionsRec(Tokens) ->
 
781
    {[],Tokens}.
 
782
 
 
783
parse_Intersections(Tokens) ->
 
784
    {InterSec,Rest} = parse_IntersectionElements(Tokens),
 
785
    {IRec,Rest2} = parse_IElemsRec(Rest),
 
786
    case {InterSec,IRec} of
 
787
        {V1,[]} ->
 
788
            {V1,Rest2};
 
789
        {{'SingleValue',V1},{'SingleValue',V2}} ->
 
790
            {{'SingleValue',
 
791
              ordsets:intersection(to_set(V1),to_set(V2))},Rest2};
 
792
        {V1,V2} when list(V2) ->
 
793
            {[V1] ++ [intersection|V2],Rest2};
 
794
        {V1,V2} ->
 
795
            {[V1,intersection,V2],Rest2};
 
796
        _ ->
 
797
            throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
798
                               [got,get_token(hd(Tokens)),expected,'a Union']}})
 
799
    end.
 
800
 
 
801
parse_IElemsRec([{'^',_}|Rest]) ->
 
802
    {InterSec,Rest2} = parse_IntersectionElements(Rest),
 
803
    {IRec,Rest3} = parse_IElemsRec(Rest2),
 
804
    case {InterSec,IRec} of
 
805
        {{'SingleValue',V1},{'SingleValue',V2}} ->
 
806
            {{'SingleValue',
 
807
              ordsets:intersection(to_set(V1),to_set(V2))},Rest3};
 
808
        {V1,[]} ->
 
809
            {V1,Rest3};
 
810
        {V1,V2} when list(V2) ->
 
811
            {[V1] ++ V2,Rest3};
 
812
        {V1,V2} ->
 
813
            {[V1,V2],Rest3};
 
814
        _ ->
 
815
            throw({asn1_error,{get_line(hd(Rest)),get(asn1_module),
 
816
                               [got,get_token(hd(Rest)),expected,'an Intersection']}})
 
817
    end;
 
818
parse_IElemsRec([{'INTERSECTION',_}|Rest]) ->
 
819
    {InterSec,Rest2} = parse_IntersectionElements(Rest),
 
820
    {IRec,Rest3} = parse_IElemsRec(Rest2),
 
821
    case {InterSec,IRec} of
 
822
        {{'SingleValue',V1},{'SingleValue',V2}} ->
 
823
            {{'SingleValue',
 
824
              ordsets:intersection(to_set(V1),to_set(V2))},Rest3};
 
825
        {V1,[]} ->
 
826
            {V1,Rest3};
 
827
        {V1,V2} when list(V2) ->
 
828
            {[V1] ++ V2,Rest3};
 
829
        {V1,V2} ->
 
830
            {[V1,V2],Rest3};
 
831
        _ ->
 
832
            throw({asn1_error,{get_line(hd(Rest)),get(asn1_module),
 
833
                               [got,get_token(hd(Rest)),expected,'an Intersection']}})
 
834
    end;
 
835
parse_IElemsRec(Tokens) ->
 
836
    {[],Tokens}.
 
837
 
 
838
parse_IntersectionElements(Tokens) ->
 
839
    {InterSec,Rest} = parse_Elements(Tokens),
 
840
    case Rest of
 
841
        [{'EXCEPT',_}|Rest2] ->
 
842
            {Exclusion,Rest3} = parse_Elements(Rest2),
 
843
            {{InterSec,{'EXCEPT',Exclusion}},Rest3};
 
844
        Rest ->
 
845
            {InterSec,Rest}
 
846
    end.
 
847
 
 
848
parse_Elements([{'(',_}|Rest]) ->
 
849
    {Elems,Rest2} = parse_ElementSetSpec(Rest),
 
850
    case Rest2 of
 
851
        [{')',_}|Rest3] ->
 
852
            {Elems,Rest3};
 
853
        [H|_T] ->
 
854
            throw({asn1_error,{get_line(H),get(asn1_module),
 
855
                               [got,get_token(H),expected,')']}})
 
856
    end;
 
857
parse_Elements(Tokens) ->
 
858
    Flist = [fun parse_SubtypeElements/1,
 
859
             fun parse_ObjectSetElements/1],
 
860
    case (catch parse_or(Tokens,Flist)) of
 
861
        {'EXIT',Reason} ->
 
862
            exit(Reason);
 
863
        Err = {asn1_error,_} ->
 
864
            throw(Err);
 
865
        Result ->
 
866
            Result
 
867
    end.
 
868
    
 
869
 
 
870
    
 
871
 
 
872
%% --------------------------
 
873
 
 
874
parse_DefinedObjectClass([{typereference,_,_ModName},{'.',_},Tr={typereference,_,_ObjClName}|Rest]) ->
 
875
%%    {{objectclassname,ModName,ObjClName},Rest};
 
876
%    {{objectclassname,tref2Exttref(Tr)},Rest};
 
877
    {tref2Exttref(Tr),Rest};
 
878
parse_DefinedObjectClass([Tr={typereference,_,_ObjClName}|Rest]) ->
 
879
%    {{objectclassname,tref2Exttref(Tr)},Rest};
 
880
    {tref2Exttref(Tr),Rest};
 
881
parse_DefinedObjectClass([{'TYPE-IDENTIFIER',_}|Rest]) ->
 
882
    {'TYPE-IDENTIFIER',Rest};
 
883
parse_DefinedObjectClass([{'ABSTRACT-SYNTAX',_}|Rest]) ->
 
884
    {'ABSTRACT-SYNTAX',Rest};
 
885
parse_DefinedObjectClass(Tokens) ->
 
886
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
887
                       [got,get_token(hd(Tokens)),expected,
 
888
                        ['typereference . typereference',
 
889
                         typereference,
 
890
                         'TYPE-IDENTIFIER',
 
891
                         'ABSTRACT-SYNTAX']]}}).
 
892
 
 
893
parse_ObjectClassAssignment([{typereference,L1,ObjClName},{'::=',_}|Rest]) ->
 
894
    {Type,Rest2} = parse_ObjectClass(Rest),
 
895
    {#classdef{pos=L1,name=ObjClName,typespec=Type},Rest2};
 
896
parse_ObjectClassAssignment(Tokens) ->
 
897
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
898
                                  [got,get_token(hd(Tokens)),expected,
 
899
                                   'typereference ::=']}}).
 
900
 
 
901
parse_ObjectClass(Tokens) ->
 
902
    Flist = [fun parse_DefinedObjectClass/1,
 
903
             fun parse_ObjectClassDefn/1,
 
904
             fun parse_ParameterizedObjectClass/1],
 
905
    case (catch parse_or(Tokens,Flist)) of
 
906
        {'EXIT',Reason} ->
 
907
            exit(Reason);
 
908
        {asn1_error,Reason2} ->
 
909
            throw({asn1_error,Reason2});
 
910
        Result ->
 
911
            Result
 
912
    end.
 
913
 
 
914
parse_ObjectClassDefn([{'CLASS',_},{'{',_}|Rest]) ->
 
915
    {Type,Rest2} = parse_FieldSpec(Rest),
 
916
    {WithSyntaxSpec,Rest3} = parse_WithSyntaxSpec(Rest2),
 
917
    {#objectclass{fields=Type,syntax=WithSyntaxSpec},Rest3};
 
918
parse_ObjectClassDefn(Tokens) ->
 
919
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
920
                       [got,get_token(hd(Tokens)),expected,'CLASS {']}}).
 
921
 
 
922
parse_FieldSpec(Tokens) ->
 
923
    parse_FieldSpec(Tokens,[]).
 
924
 
 
925
parse_FieldSpec(Tokens,Acc) ->
 
926
    Flist = [fun parse_FixedTypeValueFieldSpec/1,
 
927
             fun parse_VariableTypeValueFieldSpec/1,
 
928
             fun parse_ObjectFieldSpec/1,
 
929
             fun parse_FixedTypeValueSetFieldSpec/1,
 
930
             fun parse_VariableTypeValueSetFieldSpec/1,
 
931
             fun parse_TypeFieldSpec/1,
 
932
             fun parse_ObjectSetFieldSpec/1],
 
933
    case (catch parse_or(Tokens,Flist)) of
 
934
        {'EXIT',Reason} ->
 
935
            exit(Reason);
 
936
        AsnErr = {asn1_error,_} ->
 
937
            throw(AsnErr);
 
938
        {Type,[{'}',_}|Rest]} ->
 
939
            {lists:reverse([Type|Acc]),Rest};
 
940
        {Type,[{',',_}|Rest2]} ->
 
941
            parse_FieldSpec(Rest2,[Type|Acc]);
 
942
        {_,[H|_T]}  ->
 
943
            throw({asn1_error,{get_line(H),get(asn1_module),
 
944
                               [got,get_token(H),expected,'}']}})
 
945
    end.
 
946
 
 
947
parse_PrimitiveFieldName([{typefieldreference,_,FieldName}|Rest]) ->
 
948
    {{typefieldreference,FieldName},Rest};
 
949
parse_PrimitiveFieldName([{valuefieldreference,_,FieldName}|Rest]) ->
 
950
    {{valuefieldreference,FieldName},Rest};
 
951
parse_PrimitiveFieldName(Tokens) ->
 
952
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
953
                       [got,get_token(hd(Tokens)),expected,
 
954
                        [typefieldreference,valuefieldreference]]}}).
 
955
 
 
956
parse_FieldName(Tokens) ->
 
957
    {Field,Rest} = parse_PrimitiveFieldName(Tokens),
 
958
    parse_FieldName(Rest,[Field]).
 
959
 
 
960
parse_FieldName([{'.',_}|Rest],Acc) ->
 
961
    case (catch parse_PrimitiveFieldName(Rest)) of
 
962
        {'EXIT',Reason} ->
 
963
            exit(Reason);
 
964
        AsnErr = {asn1_error,_} ->
 
965
            throw(AsnErr);
 
966
        {FieldName,Rest2} ->
 
967
            parse_FieldName(Rest2,[FieldName|Acc])
 
968
    end;
 
969
parse_FieldName(Tokens,Acc) ->
 
970
    {lists:reverse(Acc),Tokens}.
 
971
    
 
972
parse_FixedTypeValueFieldSpec([{valuefieldreference,L1,VFieldName}|Rest]) ->
 
973
    {Type,Rest2} = parse_Type(Rest),
 
974
    {Unique,Rest3} = 
 
975
        case Rest2 of
 
976
            [{'UNIQUE',_}|Rest4] ->
 
977
                {'UNIQUE',Rest4};
 
978
            _  ->
 
979
                {undefined,Rest2}
 
980
        end,
 
981
    {OptionalitySpec,Rest5} = parse_ValueOptionalitySpec(Rest3),
 
982
    case Unique of
 
983
        'UNIQUE' ->
 
984
            case OptionalitySpec of 
 
985
                {'DEFAULT',_} ->
 
986
                    throw({asn1_error,
 
987
                           {L1,get(asn1_module),
 
988
                            ['UNIQUE and DEFAULT in same field',VFieldName]}});
 
989
                _ ->
 
990
                    {{fixedtypevaluefield,VFieldName,Type,Unique,OptionalitySpec},Rest5}
 
991
            end;
 
992
        _ ->
 
993
            {{object_or_fixedtypevalue_field,VFieldName,Type,Unique,OptionalitySpec},Rest5}
 
994
    end;
 
995
parse_FixedTypeValueFieldSpec(Tokens) ->
 
996
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
997
                       [got,get_token(hd(Tokens)),expected,valuefieldreference]}}).
 
998
 
 
999
parse_VariableTypeValueFieldSpec([{valuefieldreference,_,VFieldName}|Rest]) ->
 
1000
    {FieldRef,Rest2} = parse_FieldName(Rest),
 
1001
    {OptionalitySpec,Rest3} = parse_ValueOptionalitySpec(Rest2),
 
1002
    {{variabletypevaluefield,VFieldName,FieldRef,OptionalitySpec},Rest3};
 
1003
parse_VariableTypeValueFieldSpec(Tokens) ->
 
1004
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1005
                       [got,get_token(hd(Tokens)),expected,valuefieldreference]}}).
 
1006
 
 
1007
parse_ObjectFieldSpec([{valuefieldreference,_,VFieldName}|Rest]) ->
 
1008
    {Class,Rest2} = parse_DefinedObjectClass(Rest),
 
1009
    {OptionalitySpec,Rest3} = parse_ObjectOptionalitySpec(Rest2),
 
1010
    {{objectfield,VFieldName,Class,OptionalitySpec},Rest3};
 
1011
parse_ObjectFieldSpec(Tokens) ->
 
1012
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1013
                       [got,get_token(hd(Tokens)),expected,valuefieldreference]}}).
 
1014
 
 
1015
parse_TypeFieldSpec([{typefieldreference,_,TFieldName}|Rest]) ->
 
1016
    {OptionalitySpec,Rest2} = parse_TypeOptionalitySpec(Rest),
 
1017
    {{typefield,TFieldName,OptionalitySpec},Rest2};
 
1018
parse_TypeFieldSpec(Tokens) ->
 
1019
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1020
                       [got,get_token(hd(Tokens)),expected,typefieldreference]}}).
 
1021
 
 
1022
parse_FixedTypeValueSetFieldSpec([{typefieldreference,_,TFieldName}|Rest]) ->
 
1023
    {Type,Rest2} = parse_Type(Rest),
 
1024
    {OptionalitySpec,Rest3} = parse_ValueSetOptionalitySpec(Rest2),
 
1025
    {{objectset_or_fixedtypevalueset_field,TFieldName,Type,
 
1026
      OptionalitySpec},Rest3};
 
1027
parse_FixedTypeValueSetFieldSpec(Tokens) ->
 
1028
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1029
                       [got,get_token(hd(Tokens)),expected,typefieldreference]}}).
 
1030
 
 
1031
parse_VariableTypeValueSetFieldSpec([{typefieldreference,_,TFieldName}|Rest]) ->
 
1032
    {FieldRef,Rest2} = parse_FieldName(Rest),
 
1033
    {OptionalitySpec,Rest3} = parse_ValueSetOptionalitySpec(Rest2),
 
1034
    {{variabletypevaluesetfield,TFieldName,FieldRef,OptionalitySpec},Rest3};
 
1035
parse_VariableTypeValueSetFieldSpec(Tokens) ->
 
1036
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1037
                       [got,get_token(hd(Tokens)),expected,typefieldreference]}}).
 
1038
 
 
1039
parse_ObjectSetFieldSpec([{typefieldreference,_,TFieldName}|Rest]) ->
 
1040
    {Class,Rest2} = parse_DefinedObjectClass(Rest),
 
1041
    {OptionalitySpec,Rest3} = parse_ObjectSetOptionalitySpec(Rest2),
 
1042
    {{objectsetfield,TFieldName,Class,OptionalitySpec},Rest3};
 
1043
parse_ObjectSetFieldSpec(Tokens) ->
 
1044
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1045
                       [got,get_token(hd(Tokens)),expected,typefieldreference]}}).
 
1046
 
 
1047
parse_ValueOptionalitySpec(Tokens)->
 
1048
    case Tokens of
 
1049
        [{'OPTIONAL',_}|Rest] -> {'OPTIONAL',Rest};
 
1050
        [{'DEFAULT',_}|Rest] ->
 
1051
            {Value,Rest2} = parse_Value(Rest),
 
1052
            {{'DEFAULT',Value},Rest2};
 
1053
        _  -> {'MANDATORY',Tokens}
 
1054
    end.
 
1055
 
 
1056
parse_ObjectOptionalitySpec(Tokens) ->
 
1057
    case Tokens of
 
1058
        [{'OPTIONAL',_}|Rest] -> {'OPTIONAL',Rest};
 
1059
        [{'DEFAULT',_}|Rest] ->
 
1060
            {Object,Rest2} = parse_Object(Rest),
 
1061
            {{'DEFAULT',Object},Rest2};
 
1062
        _  -> {'MANDATORY',Tokens}
 
1063
    end.
 
1064
 
 
1065
parse_TypeOptionalitySpec(Tokens) ->
 
1066
    case Tokens of
 
1067
        [{'OPTIONAL',_}|Rest] -> {'OPTIONAL',Rest};
 
1068
        [{'DEFAULT',_}|Rest] ->
 
1069
            {Type,Rest2} = parse_Type(Rest),
 
1070
            {{'DEFAULT',Type},Rest2};
 
1071
        _  -> {'MANDATORY',Tokens}
 
1072
    end.
 
1073
 
 
1074
parse_ValueSetOptionalitySpec(Tokens) ->
 
1075
    case Tokens of
 
1076
        [{'OPTIONAL',_}|Rest] -> {'OPTIONAL',Rest};
 
1077
        [{'DEFAULT',_}|Rest] ->
 
1078
            {ValueSet,Rest2} = parse_ValueSet(Rest),
 
1079
            {{'DEFAULT',ValueSet},Rest2};
 
1080
        _  -> {'MANDATORY',Tokens}
 
1081
    end.
 
1082
 
 
1083
parse_ObjectSetOptionalitySpec(Tokens) ->
 
1084
        case Tokens of
 
1085
        [{'OPTIONAL',_}|Rest] -> {'OPTIONAL',Rest};
 
1086
        [{'DEFAULT',_}|Rest] ->
 
1087
            {ObjectSet,Rest2} = parse_ObjectSet(Rest),
 
1088
            {{'DEFAULT',ObjectSet},Rest2};
 
1089
        _  -> {'MANDATORY',Tokens}
 
1090
    end.
 
1091
 
 
1092
parse_WithSyntaxSpec([{'WITH',_},{'SYNTAX',_}|Rest]) ->
 
1093
    {SyntaxList,Rest2} = parse_SyntaxList(Rest),
 
1094
    {{'WITH SYNTAX',SyntaxList},Rest2};
 
1095
parse_WithSyntaxSpec(Tokens) ->
 
1096
    {[],Tokens}.
 
1097
 
 
1098
parse_SyntaxList([{'{',_},{'}',_}|Rest]) ->
 
1099
    {[],Rest};
 
1100
parse_SyntaxList([{'{',_}|Rest]) ->
 
1101
    parse_SyntaxList(Rest,[]);
 
1102
parse_SyntaxList(Tokens) ->
 
1103
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1104
                       [got,get_token(hd(Tokens)),expected,['{}','{']]}}).
 
1105
 
 
1106
parse_SyntaxList(Tokens,Acc) ->
 
1107
    {SyntaxList,Rest} = parse_TokenOrGroupSpec(Tokens),
 
1108
    case Rest of
 
1109
        [{'}',_}|Rest2] -> 
 
1110
            {lists:reverse([SyntaxList|Acc]),Rest2};
 
1111
        _ ->
 
1112
            parse_SyntaxList(Rest,[SyntaxList|Acc])
 
1113
    end.
 
1114
 
 
1115
parse_TokenOrGroupSpec(Tokens) ->
 
1116
    Flist = [fun parse_RequiredToken/1,
 
1117
             fun parse_OptionalGroup/1],
 
1118
    case (catch parse_or(Tokens,Flist)) of
 
1119
        {'EXIT',Reason} ->
 
1120
            exit(Reason);
 
1121
        AsnErr = {asn1_error,_} ->
 
1122
            throw(AsnErr);
 
1123
        Result ->
 
1124
            Result
 
1125
    end.
 
1126
 
 
1127
parse_RequiredToken([{typereference,L1,WordName}|Rest]) ->
 
1128
    case is_word(WordName) of
 
1129
        false ->
 
1130
            throw({asn1_error,{L1,get(asn1_module),
 
1131
                               [got,WordName,expected,a,'Word']}});
 
1132
        true ->
 
1133
            {WordName,Rest}
 
1134
    end;
 
1135
parse_RequiredToken([{',',L1}|Rest]) ->
 
1136
    {{',',L1},Rest};
 
1137
parse_RequiredToken([{WordName,L1}|Rest]) ->
 
1138
    case is_word(WordName) of
 
1139
        false ->
 
1140
            throw({asn1_error,{L1,get(asn1_module),
 
1141
                               [got,WordName,expected,a,'Word']}});
 
1142
        true ->
 
1143
            {WordName,Rest}
 
1144
    end;
 
1145
parse_RequiredToken(Tokens) ->
 
1146
    parse_PrimitiveFieldName(Tokens).
 
1147
 
 
1148
parse_OptionalGroup([{'[',_}|Rest]) ->
 
1149
    {Spec,Rest2} = parse_TokenOrGroupSpec(Rest),
 
1150
    {SpecList,Rest3} = parse_OptionalGroup(Rest2,[Spec]),
 
1151
    {SpecList,Rest3}.
 
1152
 
 
1153
parse_OptionalGroup([{']',_}|Rest],Acc) ->
 
1154
    {lists:reverse(Acc),Rest};
 
1155
parse_OptionalGroup(Tokens,Acc) ->
 
1156
    {Spec,Rest} = parse_TokenOrGroupSpec(Tokens),
 
1157
    parse_OptionalGroup(Rest,[Spec|Acc]).
 
1158
 
 
1159
parse_DefinedObject([Id={identifier,_,_ObjName}|Rest]) ->
 
1160
    {{object,identifier2Extvalueref(Id)},Rest};
 
1161
parse_DefinedObject([{typereference,L1,ModName},{'.',_},{identifier,_,ObjName}|Rest]) ->
 
1162
    {{object, #'Externaltypereference'{pos=L1,module=ModName,type=ObjName}},Rest};
 
1163
parse_DefinedObject(Tokens) ->
 
1164
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1165
                       [got,get_token(hd(Tokens)),expected,
 
1166
                       [identifier,'typereference.identifier']]}}).
 
1167
 
 
1168
parse_ObjectAssignment([{identifier,L1,ObjName}|Rest]) ->
 
1169
    {Class,Rest2} = parse_DefinedObjectClass(Rest),
 
1170
    case Rest2 of
 
1171
        [{'::=',_}|Rest3] ->
 
1172
            {Object,Rest4} = parse_Object(Rest3),
 
1173
            {#typedef{pos=L1,name=ObjName,
 
1174
                      typespec=#'Object'{classname=Class,def=Object}},Rest4};
 
1175
        [H|_T]  -> 
 
1176
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1177
                               [got,get_token(H),expected,'::=']}});
 
1178
        Other ->
 
1179
            throw({asn1_error,{L1,get(asn1_module),
 
1180
                               [got,Other,expected,'::=']}})
 
1181
    end;
 
1182
parse_ObjectAssignment(Tokens) ->
 
1183
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1184
                                  [got,get_token(hd(Tokens)),expected,identifier]}}).
 
1185
 
 
1186
parse_Object(Tokens) ->
 
1187
    Flist=[fun parse_ObjectDefn/1,
 
1188
           fun parse_ObjectFromObject/1,
 
1189
           fun parse_ParameterizedObject/1,
 
1190
           fun parse_DefinedObject/1],
 
1191
    case (catch parse_or(Tokens,Flist)) of
 
1192
        {'EXIT',Reason} ->
 
1193
            exit(Reason);
 
1194
        AsnErr = {asn1_error,_} ->
 
1195
            throw(AsnErr);
 
1196
        Result ->
 
1197
            Result
 
1198
    end.
 
1199
 
 
1200
parse_ObjectDefn(Tokens) ->
 
1201
    Flist=[fun parse_DefaultSyntax/1,
 
1202
           fun parse_DefinedSyntax/1],
 
1203
    case (catch parse_or(Tokens,Flist)) of
 
1204
        {'EXIT',Reason} ->
 
1205
            exit(Reason);
 
1206
        AsnErr = {asn1_error,_} ->
 
1207
            throw(AsnErr);
 
1208
        Result ->
 
1209
            Result
 
1210
    end.
 
1211
 
 
1212
parse_DefaultSyntax([{'{',_},{'}',_}|Rest]) ->
 
1213
    {{object,defaultsyntax,[]},Rest};
 
1214
parse_DefaultSyntax([{'{',_}|Rest]) ->
 
1215
    parse_DefaultSyntax(Rest,[]);
 
1216
parse_DefaultSyntax(Tokens) ->
 
1217
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1218
                       [got,get_token(hd(Tokens)),expected,['{}','{']]}}).
 
1219
 
 
1220
parse_DefaultSyntax(Tokens,Acc) ->
 
1221
    {Setting,Rest} = parse_FieldSetting(Tokens),
 
1222
    case Rest of
 
1223
        [{',',_}|Rest2] ->
 
1224
            parse_DefaultSyntax(Rest2,[Setting|Acc]);
 
1225
        [{'}',_}|Rest3] ->
 
1226
            {{object,defaultsyntax,lists:reverse([Setting|Acc])},Rest3};
 
1227
        [H|_T] ->
 
1228
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1229
                               [got,get_token(H),expected,[',','}']]}})
 
1230
    end.
 
1231
 
 
1232
parse_FieldSetting(Tokens) ->
 
1233
    {{_,PrimFieldName},Rest} = parse_PrimitiveFieldName(Tokens),
 
1234
    {Setting,Rest2} = parse_Setting(Rest),
 
1235
    {{PrimFieldName,Setting},Rest2}.
 
1236
 
 
1237
parse_DefinedSyntax([{'{',_}|Rest]) ->
 
1238
    parse_DefinedSyntax(Rest,[]).
 
1239
 
 
1240
parse_DefinedSyntax(Tokens,Acc) ->
 
1241
    case Tokens of
 
1242
        [{'}',_}|Rest2] ->
 
1243
            {{object,definedsyntax,lists:reverse(Acc)},Rest2};
 
1244
        _ ->
 
1245
            {DefSynTok,Rest3} = parse_DefinedSyntaxToken(Tokens),
 
1246
            parse_DefinedSyntax(Rest3,[DefSynTok|Acc])
 
1247
    end.
 
1248
 
 
1249
parse_DefinedSyntaxToken([{',',L1}|Rest]) ->
 
1250
    {{',',L1},Rest};
 
1251
parse_DefinedSyntaxToken([{typereference,L1,Name}|Rest]) ->
 
1252
    case is_word(Name) of
 
1253
        false ->
 
1254
            {{setting,L1,Name},Rest};
 
1255
        true ->
 
1256
            {{word_or_setting,L1,Name},Rest}
 
1257
    end;
 
1258
parse_DefinedSyntaxToken(Tokens) ->
 
1259
    case catch parse_Setting(Tokens) of
 
1260
        {asn1_error,_} ->
 
1261
            parse_Word(Tokens);
 
1262
        {'EXIT',Reason} ->
 
1263
            exit(Reason);
 
1264
        Result ->
 
1265
            Result
 
1266
    end.
 
1267
 
 
1268
parse_Word([{Name,Pos}|Rest]) ->
 
1269
    case is_word(Name) of
 
1270
        false ->
 
1271
            throw({asn1_error,{Pos,get(asn1_module),
 
1272
                               [got,Name, expected,a,'Word']}});
 
1273
        true ->
 
1274
            {{word_or_setting,Pos,Name},Rest}
 
1275
    end.
 
1276
 
 
1277
parse_Setting(Tokens) ->
 
1278
    Flist = [fun parse_Type/1,
 
1279
             fun parse_Value/1,
 
1280
             fun parse_Object/1,
 
1281
             fun parse_ObjectSet/1],
 
1282
    case (catch parse_or(Tokens,Flist)) of
 
1283
        {'EXIT',Reason} ->
 
1284
            exit(Reason);
 
1285
        AsnErr = {asn1_error,_} ->
 
1286
            throw(AsnErr);
 
1287
        Result ->
 
1288
            Result
 
1289
    end.
 
1290
 
 
1291
parse_DefinedObjectSet([{typereference,L1,ModuleName},{'.',_},
 
1292
                        {typereference,L2,ObjSetName}|Rest]) ->
 
1293
    {{objectset,L1,#'Externaltypereference'{pos=L2,module=ModuleName,
 
1294
                                            type=ObjSetName}},Rest};
 
1295
parse_DefinedObjectSet([{typereference,L1,ObjSetName}|Rest]) ->
 
1296
    {{objectset,L1,#'Externaltypereference'{pos=L1,module=get(asn1_module),
 
1297
                                            type=ObjSetName}},Rest};
 
1298
parse_DefinedObjectSet(Tokens) ->
 
1299
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1300
                       [got,get_token(hd(Tokens)),expected,
 
1301
                        [typereference,'typereference.typereference']]}}).
 
1302
 
 
1303
parse_ObjectSetAssignment([{typereference,L1,ObjSetName}|Rest]) ->
 
1304
    {Class,Rest2} = parse_DefinedObjectClass(Rest),
 
1305
    case Rest2 of
 
1306
        [{'::=',_}|Rest3] ->
 
1307
            {ObjectSet,Rest4} = parse_ObjectSet(Rest3),
 
1308
            {#typedef{pos=L1,name=ObjSetName,
 
1309
                      typespec=#'ObjectSet'{class=Class,
 
1310
                                            set=ObjectSet}},Rest4};
 
1311
        [H|_T]  -> 
 
1312
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1313
                               [got,get_token(H),expected,'::=']}})
 
1314
%%%     Other ->
 
1315
%%%         throw(Other)
 
1316
    end;
 
1317
parse_ObjectSetAssignment(Tokens) ->
 
1318
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1319
                                  [got,get_token(hd(Tokens)),expected,
 
1320
                                   typereference]}}).
 
1321
 
 
1322
parse_ObjectSet([{'{',_}|Rest]) ->
 
1323
    {ObjSetSpec,Rest2} = parse_ObjectSetSpec(Rest),
 
1324
    case Rest2 of
 
1325
        [{'}',_}|Rest3] ->
 
1326
            {ObjSetSpec,Rest3};
 
1327
        [H|_T] ->
 
1328
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1329
                               [got,get_token(H),expected,'}']}})
 
1330
    end;
 
1331
parse_ObjectSet(Tokens) ->
 
1332
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1333
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
1334
 
 
1335
parse_ObjectSetSpec([{'...',_}|Rest]) ->
 
1336
    {['EXTENSIONMARK'],Rest};
 
1337
parse_ObjectSetSpec(Tokens) ->
 
1338
    parse_ElementSetSpecs(Tokens).
 
1339
 
 
1340
parse_ObjectSetElements(Tokens) ->
 
1341
    Flist = [fun parse_Object/1,
 
1342
             fun parse_DefinedObjectSet/1,
 
1343
             fun parse_ObjectSetFromObjects/1,
 
1344
             fun parse_ParameterizedObjectSet/1],
 
1345
    case (catch parse_or(Tokens,Flist)) of
 
1346
        {'EXIT',Reason} ->
 
1347
            exit(Reason);
 
1348
        AsnErr = {asn1_error,_} ->
 
1349
            throw(AsnErr);
 
1350
        Result ->
 
1351
            Result
 
1352
    end.
 
1353
 
 
1354
parse_ObjectClassFieldType(Tokens) ->
 
1355
    {Class,Rest} = parse_DefinedObjectClass(Tokens),
 
1356
    case Rest of
 
1357
        [{'.',_}|Rest2] ->
 
1358
            {FieldName,Rest3} = parse_FieldName(Rest2),
 
1359
            OCFT = #'ObjectClassFieldType'{
 
1360
              classname=Class,
 
1361
              class=Class,fieldname=FieldName},
 
1362
            {#type{def=OCFT},Rest3};
 
1363
        [H|_T] ->
 
1364
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1365
                               [got,get_token(H),expected,'.']}})
 
1366
%%%     Other ->
 
1367
%%%         throw(Other)
 
1368
    end.
 
1369
 
 
1370
%parse_ObjectClassFieldValue(Tokens) ->
 
1371
%    Flist = [fun parse_OpenTypeFieldVal/1,
 
1372
%            fun parse_FixedTypeFieldVal/1],
 
1373
%    case (catch parse_or(Tokens,Flist)) of
 
1374
%       {'EXIT',Reason} ->
 
1375
%           throw(Reason);
 
1376
%       AsnErr = {asn1_error,_} ->
 
1377
%           throw(AsnErr);
 
1378
%       Result ->
 
1379
%           Result
 
1380
%    end.
 
1381
 
 
1382
parse_ObjectClassFieldValue(Tokens) ->
 
1383
    parse_OpenTypeFieldVal(Tokens).
 
1384
 
 
1385
parse_OpenTypeFieldVal(Tokens) ->
 
1386
    {Type,Rest} = parse_Type(Tokens),
 
1387
    case Rest of
 
1388
        [{':',_}|Rest2] ->
 
1389
            {Value,Rest3} = parse_Value(Rest2),
 
1390
            {{opentypefieldvalue,Type,Value},Rest3};
 
1391
        [H|_T] ->
 
1392
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1393
                               [got,get_token(H),expected,':']}})
 
1394
    end.
 
1395
 
 
1396
% parse_FixedTypeFieldVal(Tokens) ->
 
1397
%     parse_Value(Tokens).
 
1398
 
 
1399
% parse_InformationFromObjects(Tokens) ->
 
1400
%     Flist = [fun parse_ValueFromObject/1,
 
1401
%            fun parse_ValueSetFromObjects/1,
 
1402
%            fun parse_TypeFromObject/1,
 
1403
%            fun parse_ObjectFromObject/1],
 
1404
%     case (catch parse_or(Tokens,Flist)) of
 
1405
%       {'EXIT',Reason} ->
 
1406
%           throw(Reason);
 
1407
%       AsnErr = {asn1_error,_} ->
 
1408
%           throw(AsnErr);
 
1409
%       Result ->
 
1410
%           Result
 
1411
%     end.
 
1412
 
 
1413
parse_ReferencedObjects(Tokens) ->
 
1414
    Flist = [fun parse_DefinedObject/1,
 
1415
             fun parse_DefinedObjectSet/1,
 
1416
             fun parse_ParameterizedObject/1,
 
1417
             fun parse_ParameterizedObjectSet/1],
 
1418
        case (catch parse_or(Tokens,Flist)) of
 
1419
        {'EXIT',Reason} ->
 
1420
            exit(Reason);
 
1421
        AsnErr = {asn1_error,_} ->
 
1422
            throw(AsnErr);
 
1423
        Result ->
 
1424
            Result
 
1425
    end.
 
1426
 
 
1427
parse_ValueFromObject(Tokens) ->
 
1428
    {Objects,Rest} = parse_ReferencedObjects(Tokens),
 
1429
    case Rest of
 
1430
        [{'.',_}|Rest2] ->
 
1431
            {Name,Rest3} = parse_FieldName(Rest2),
 
1432
            case lists:last(Name) of
 
1433
                {valuefieldreference,_} ->
 
1434
                    {{'ValueFromObject',Objects,Name},Rest3};
 
1435
                _ ->
 
1436
                    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1437
                                       [got,typefieldreference,expected,
 
1438
                                        valuefieldreference]}})
 
1439
            end;
 
1440
        [H|_T] ->
 
1441
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1442
                               [got,get_token(H),expected,'.']}})
 
1443
%%%     Other ->
 
1444
%%%         throw({asn1_error,{got,Other,expected,'.'}})
 
1445
    end.
 
1446
 
 
1447
parse_ValueSetFromObjects(Tokens) ->
 
1448
    {Objects,Rest} = parse_ReferencedObjects(Tokens),
 
1449
    case Rest of
 
1450
        [{'.',_}|Rest2] ->
 
1451
            {Name,Rest3} = parse_FieldName(Rest2),
 
1452
            case lists:last(Name) of
 
1453
                {typefieldreference,_FieldName} ->
 
1454
                    {{'ValueSetFromObjects',Objects,Name},Rest3};
 
1455
                _ ->
 
1456
                    throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
1457
                                       [got,get_token(hd(Rest2)),expected,
 
1458
                                        typefieldreference]}})
 
1459
            end;
 
1460
        [H|_T] ->
 
1461
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1462
                               [got,get_token(H),expected,'.']}})
 
1463
%%%     Other ->
 
1464
%%%         throw({asn1_error,{got,Other,expected,'.'}})
 
1465
    end.
 
1466
 
 
1467
parse_TypeFromObject(Tokens) ->
 
1468
    {Objects,Rest} = parse_ReferencedObjects(Tokens),
 
1469
    case Rest of
 
1470
        [{'.',_}|Rest2] ->
 
1471
            {Name,Rest3} = parse_FieldName(Rest2),
 
1472
            case lists:last(Name) of
 
1473
                {typefieldreference,_FieldName} ->
 
1474
                    {{'TypeFromObject',Objects,Name},Rest3};
 
1475
                _ ->
 
1476
                    throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
1477
                                       [got,get_token(hd(Rest2)),expected,
 
1478
                                        typefieldreference]}})
 
1479
            end;
 
1480
        [H|_T] ->
 
1481
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1482
                               [got,get_token(H),expected,'.']}})
 
1483
%%%     Other ->
 
1484
%%%         throw({asn1_error,{got,Other,expected,'.'}})
 
1485
    end.
 
1486
 
 
1487
parse_ObjectFromObject(Tokens) ->
 
1488
    {Objects,Rest} = parse_ReferencedObjects(Tokens),
 
1489
    case Rest of
 
1490
        [{'.',_}|Rest2] ->
 
1491
            {Name,Rest3} = parse_FieldName(Rest2),
 
1492
            {{'ObjectFromObject',Objects,Name},Rest3};
 
1493
        [H|_T] ->
 
1494
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1495
                               [got,get_token(H),expected,'.']}})
 
1496
%%%     Other ->
 
1497
%%%         throw({asn1_error,{got,Other,expected,'.'}})
 
1498
    end.
 
1499
 
 
1500
parse_ObjectSetFromObjects(Tokens) ->
 
1501
    {Objects,Rest} = parse_ReferencedObjects(Tokens),
 
1502
    case Rest of
 
1503
        [{'.',_}|Rest2] ->
 
1504
            {Name,Rest3} = parse_FieldName(Rest2),
 
1505
            {{'ObjectSetFromObjects',Objects,Name},Rest3};
 
1506
        [H|_T] ->
 
1507
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1508
                               [got,get_token(H),expected,'.']}})
 
1509
%%%     Other ->
 
1510
%%%         throw({asn1_error,{got,Other,expected,'.'}})
 
1511
    end.
 
1512
 
 
1513
% parse_InstanceOfType([{'INSTANCE',_},{'OF',_}|Rest]) ->
 
1514
%     {Class,Rest2} = parse_DefinedObjectClass(Rest),
 
1515
%     {{'InstanceOfType',Class},Rest2}.
 
1516
 
 
1517
% parse_InstanceOfValue(Tokens) ->
 
1518
%     parse_Value(Tokens).
 
1519
 
 
1520
 
 
1521
 
 
1522
%% X.682 constraint specification
 
1523
 
 
1524
parse_GeneralConstraint(Tokens) ->
 
1525
    Flist = [fun parse_UserDefinedConstraint/1,
 
1526
             fun parse_TableConstraint/1],
 
1527
    case (catch parse_or(Tokens,Flist)) of
 
1528
        {'EXIT',Reason} ->
 
1529
            exit(Reason);
 
1530
        AsnErr = {asn1_error,_} ->
 
1531
            throw(AsnErr);
 
1532
        Result ->
 
1533
            Result
 
1534
    end.
 
1535
 
 
1536
parse_UserDefinedConstraint([{'CONSTRAINED',_},{'BY',_},{'{',_},{'}',_}|Rest])->
 
1537
    {{constrained_by,[]},Rest};
 
1538
parse_UserDefinedConstraint([{'CONSTRAINED',_},
 
1539
                             {'BY',_},
 
1540
                             {'{',_}|Rest]) ->
 
1541
    {Param,Rest2} = parse_UserDefinedConstraintParameter(Rest),
 
1542
    case Rest2 of
 
1543
        [{'}',_}|Rest3] ->
 
1544
            {{constrained_by,Param},Rest3};
 
1545
        [H|_T] ->
 
1546
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1547
                               [got,get_token(H),expected,'}']}})
 
1548
    end;
 
1549
parse_UserDefinedConstraint(Tokens) ->
 
1550
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1551
                       [got,get_token(hd(Tokens)),expected,
 
1552
                        ['CONSTRAINED BY {}','CONSTRAINED BY {']]}}).
 
1553
 
 
1554
parse_UserDefinedConstraintParameter(Tokens) ->
 
1555
    parse_UserDefinedConstraintParameter(Tokens,[]).
 
1556
parse_UserDefinedConstraintParameter(Tokens,Acc) ->
 
1557
    Flist = [fun parse_GovernorAndActualParameter/1,
 
1558
             fun parse_ActualParameter/1],
 
1559
    case (catch parse_or(Tokens,Flist)) of
 
1560
        {'EXIT',Reason} ->
 
1561
            exit(Reason);
 
1562
        AsnErr = {asn1_error,_} ->
 
1563
            throw(AsnErr);
 
1564
        {Result,Rest} ->
 
1565
            case Rest of
 
1566
                [{',',_}|_Rest2] ->
 
1567
                    parse_UserDefinedConstraintParameter(Tokens,[Result|Acc]);
 
1568
                _  ->
 
1569
                    {lists:reverse([Result|Acc]),Rest}
 
1570
            end
 
1571
    end.
 
1572
 
 
1573
parse_GovernorAndActualParameter(Tokens) ->
 
1574
    {Governor,Rest} = parse_Governor(Tokens),
 
1575
    case Rest of
 
1576
        [{':',_}|Rest2] ->
 
1577
            {Params,Rest3} = parse_ActualParameter(Rest2),
 
1578
            {{'Governor_Params',Governor,Params},Rest3};
 
1579
        [H|_T] ->
 
1580
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1581
                               [got,get_token(H),expected,':']}})
 
1582
    end.
 
1583
 
 
1584
parse_TableConstraint(Tokens) ->
 
1585
    Flist = [fun parse_ComponentRelationConstraint/1,
 
1586
             fun parse_SimpleTableConstraint/1],
 
1587
    case (catch parse_or(Tokens,Flist)) of
 
1588
        {'EXIT',Reason} ->
 
1589
            exit(Reason);
 
1590
        AsnErr = {asn1_error,_} ->
 
1591
            throw(AsnErr);
 
1592
        Result ->
 
1593
            Result
 
1594
    end.
 
1595
 
 
1596
parse_SimpleTableConstraint(Tokens) ->
 
1597
    {ObjectSet,Rest} = parse_ObjectSet(Tokens),
 
1598
    {{simpletable,ObjectSet},Rest}.
 
1599
 
 
1600
parse_ComponentRelationConstraint([{'{',_}|Rest]) ->
 
1601
    {ObjectSet,Rest2} = parse_DefinedObjectSet(Rest),
 
1602
    case Rest2 of
 
1603
        [{'}',_},{'{',_}|Rest3] ->
 
1604
            {AtNot,Rest4} = parse_AtNotationList(Rest3,[]),
 
1605
            case Rest4 of
 
1606
                [{'}',_}|Rest5] ->
 
1607
                    {{componentrelation,ObjectSet,AtNot},Rest5};
 
1608
                [H|_T]  ->
 
1609
                    throw({asn1_error,{get_line(H),get(asn1_module),
 
1610
                                       [got,get_token(H),expected,'}']}})
 
1611
            end;
 
1612
        [H|_T]  ->
 
1613
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1614
                               [got,get_token(H),expected,
 
1615
                                'ComponentRelationConstraint',ended,with,'}']}})
 
1616
%%%     Other ->
 
1617
%%%         throw(Other)
 
1618
    end;
 
1619
parse_ComponentRelationConstraint(Tokens) ->
 
1620
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1621
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
1622
 
 
1623
parse_AtNotationList(Tokens,Acc) ->
 
1624
    {AtNot,Rest} = parse_AtNotation(Tokens),
 
1625
    case Rest of
 
1626
        [{',',_}|Rest2] ->
 
1627
            parse_AtNotationList(Rest2,[AtNot|Acc]);
 
1628
        _  ->
 
1629
            {lists:reverse([AtNot|Acc]),Rest}
 
1630
    end.
 
1631
 
 
1632
parse_AtNotation([{'@',_},{'.',_}|Rest]) ->
 
1633
    {CIdList,Rest2} = parse_ComponentIdList(Rest),
 
1634
    {{innermost,CIdList},Rest2};
 
1635
parse_AtNotation([{'@',_}|Rest]) ->
 
1636
    {CIdList,Rest2} = parse_ComponentIdList(Rest),
 
1637
    {{outermost,CIdList},Rest2};
 
1638
parse_AtNotation(Tokens) ->
 
1639
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1640
                       [got,get_token(hd(Tokens)),expected,['@','@.']]}}).
 
1641
 
 
1642
parse_ComponentIdList(Tokens) ->
 
1643
    parse_ComponentIdList(Tokens,[]).
 
1644
 
 
1645
parse_ComponentIdList([Id = {identifier,_,_},{'.',_}|Rest],Acc) ->
 
1646
    parse_ComponentIdList(Rest,[identifier2Extvalueref(Id)|Acc]);
 
1647
parse_ComponentIdList([Id = {identifier,_,_}|Rest],Acc) ->
 
1648
    {lists:reverse([identifier2Extvalueref(Id)|Acc]),Rest};
 
1649
parse_ComponentIdList(Tokens,_) ->
 
1650
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1651
                       [got,get_token(hd(Tokens)),expected,
 
1652
                        [identifier,'identifier.']]}}).
 
1653
 
 
1654
    
 
1655
 
 
1656
 
 
1657
 
 
1658
% X.683 Parameterization of ASN.1 specifications
 
1659
 
 
1660
parse_Governor(Tokens) ->
 
1661
    Flist = [fun parse_Type/1,
 
1662
             fun parse_DefinedObjectClass/1],
 
1663
    case (catch parse_or(Tokens,Flist)) of
 
1664
        {'EXIT',Reason} ->
 
1665
            exit(Reason);
 
1666
        AsnErr = {asn1_error,_} ->
 
1667
            throw(AsnErr);
 
1668
        Result ->
 
1669
            Result
 
1670
    end.
 
1671
 
 
1672
parse_ActualParameter(Tokens) ->
 
1673
    Flist = [fun parse_Type/1,
 
1674
             fun parse_Value/1,
 
1675
             fun parse_ValueSet/1,
 
1676
             fun parse_DefinedObjectClass/1,
 
1677
             fun parse_Object/1,
 
1678
             fun parse_ObjectSet/1],
 
1679
    case (catch parse_or(Tokens,Flist)) of
 
1680
        {'EXIT',Reason} ->
 
1681
            exit(Reason);
 
1682
        AsnErr = {asn1_error,_} ->
 
1683
            throw(AsnErr);
 
1684
        Result ->
 
1685
            Result
 
1686
    end.
 
1687
 
 
1688
parse_ParameterizedAssignment(Tokens) ->
 
1689
    Flist = [fun parse_ParameterizedTypeAssignment/1,
 
1690
             fun parse_ParameterizedValueAssignment/1,
 
1691
             fun parse_ParameterizedValueSetTypeAssignment/1,
 
1692
             fun parse_ParameterizedObjectClassAssignment/1,
 
1693
             fun parse_ParameterizedObjectAssignment/1,
 
1694
             fun parse_ParameterizedObjectSetAssignment/1],
 
1695
    case (catch parse_or(Tokens,Flist)) of
 
1696
        {'EXIT',Reason} ->
 
1697
            exit(Reason);
 
1698
        AsnErr = {asn1_error,_} ->
 
1699
            throw(AsnErr);
 
1700
        AsnAssErr = {asn1_assignment_error,_} ->
 
1701
            throw(AsnAssErr);
 
1702
        Result ->
 
1703
            Result
 
1704
    end.
 
1705
 
 
1706
parse_ParameterizedTypeAssignment([{typereference,L1,Name}|Rest]) ->
 
1707
    {ParameterList,Rest2} = parse_ParameterList(Rest),
 
1708
    case Rest2 of
 
1709
        [{'::=',_}|Rest3] ->
 
1710
            {Type,Rest4} = parse_Type(Rest3),
 
1711
            {#ptypedef{pos=L1,name=Name,args=ParameterList,typespec=Type},
 
1712
             Rest4};
 
1713
        [H|_T] ->
 
1714
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1715
                               [got,get_token(H),expected,'::=']}})
 
1716
    end;
 
1717
parse_ParameterizedTypeAssignment(Tokens) ->
 
1718
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1719
                                  [got,get_token(hd(Tokens)),expected,
 
1720
                                   typereference]}}).
 
1721
 
 
1722
parse_ParameterizedValueAssignment([{identifier,L1,Name}|Rest]) ->
 
1723
    {ParameterList,Rest2} = parse_ParameterList(Rest),
 
1724
    {Type,Rest3} = parse_Type(Rest2),
 
1725
    case Rest3 of
 
1726
        [{'::=',_}|Rest4] ->
 
1727
            {Value,Rest5} = parse_Value(Rest4),
 
1728
            {#pvaluedef{pos=L1,name=Name,args=ParameterList,type=Type,
 
1729
                         value=Value},Rest5};
 
1730
        [H|_T] ->
 
1731
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1732
                               [got,get_token(H),expected,'::=']}})
 
1733
    end;
 
1734
parse_ParameterizedValueAssignment(Tokens) ->
 
1735
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1736
                                  [got,get_token(hd(Tokens)),expected,identifier]}}).
 
1737
 
 
1738
parse_ParameterizedValueSetTypeAssignment([{typereference,L1,Name}|Rest]) ->
 
1739
    {ParameterList,Rest2} = parse_ParameterList(Rest),
 
1740
    {Type,Rest3} = parse_Type(Rest2),
 
1741
    case Rest3 of
 
1742
        [{'::=',_}|Rest4] ->
 
1743
            {ValueSet,Rest5} = parse_ValueSet(Rest4),
 
1744
            {#pvaluesetdef{pos=L1,name=Name,args=ParameterList,
 
1745
                           type=Type,valueset=ValueSet},Rest5};
 
1746
        [H|_T] ->
 
1747
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1748
                               [got,get_token(H),expected,'::=']}})
 
1749
    end;
 
1750
parse_ParameterizedValueSetTypeAssignment(Tokens) ->
 
1751
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1752
                                  [got,get_token(hd(Tokens)),expected,
 
1753
                                   typereference]}}).
 
1754
 
 
1755
parse_ParameterizedObjectClassAssignment([{typereference,L1,Name}|Rest]) ->
 
1756
    {ParameterList,Rest2} = parse_ParameterList(Rest),
 
1757
    case Rest2 of
 
1758
        [{'::=',_}|Rest3] ->
 
1759
            {Class,Rest4} = parse_ObjectClass(Rest3),
 
1760
            {#ptypedef{pos=L1,name=Name,args=ParameterList,typespec=Class},
 
1761
             Rest4};
 
1762
        [H|_T] ->
 
1763
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1764
                               [got,get_token(H),expected,'::=']}})
 
1765
    end;
 
1766
parse_ParameterizedObjectClassAssignment(Tokens) ->
 
1767
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1768
                                  [got,get_token(hd(Tokens)),expected,
 
1769
                                   typereference]}}).
 
1770
 
 
1771
parse_ParameterizedObjectAssignment([{identifier,L1,Name}|Rest]) ->
 
1772
    {ParameterList,Rest2} = parse_ParameterList(Rest),
 
1773
    {Class,Rest3} = parse_DefinedObjectClass(Rest2),
 
1774
    case Rest3 of
 
1775
        [{'::=',_}|Rest4] ->
 
1776
            {Object,Rest5} = parse_Object(Rest4),
 
1777
            {#pobjectdef{pos=L1,name=Name,args=ParameterList,
 
1778
                         class=Class,def=Object},Rest5};
 
1779
        [H|_T] ->
 
1780
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1781
                               [got,get_token(H),expected,'::=']}})
 
1782
%%%     Other ->
 
1783
%%%         throw(Other)
 
1784
    end;
 
1785
parse_ParameterizedObjectAssignment(Tokens) ->
 
1786
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1787
                                  [got,get_token(hd(Tokens)),expected,identifier]}}).
 
1788
 
 
1789
parse_ParameterizedObjectSetAssignment([{typereference,L1,Name}|Rest]) ->
 
1790
    {ParameterList,Rest2} = parse_ParameterList(Rest),
 
1791
    {Class,Rest3} = parse_DefinedObjectClass(Rest2),
 
1792
    case Rest3 of
 
1793
        [{'::=',_}|Rest4] ->
 
1794
            {ObjectSet,Rest5} = parse_ObjectSet(Rest4),
 
1795
            {#pobjectsetdef{pos=L1,name=Name,args=ParameterList,
 
1796
                            class=Class,def=ObjectSet},Rest5};
 
1797
        [H|_T] ->
 
1798
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1799
                               [got,get_token(H),expected,'::=']}})
 
1800
%%%     Other ->
 
1801
%%%         throw(Other)
 
1802
    end;
 
1803
parse_ParameterizedObjectSetAssignment(Tokens) ->
 
1804
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
1805
                                  [got,get_token(hd(Tokens)),expected,
 
1806
                                   typereference]}}).
 
1807
 
 
1808
parse_ParameterList([{'{',_}|Rest]) ->
 
1809
    parse_ParameterList(Rest,[]);
 
1810
parse_ParameterList(Tokens) ->
 
1811
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1812
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
1813
 
 
1814
parse_ParameterList(Tokens,Acc) ->
 
1815
    {Parameter,Rest} = parse_Parameter(Tokens),
 
1816
    case Rest of
 
1817
        [{',',_}|Rest2] ->
 
1818
            parse_ParameterList(Rest2,[Parameter|Acc]);
 
1819
        [{'}',_}|Rest3] ->
 
1820
            {lists:reverse([Parameter|Acc]),Rest3};
 
1821
        [H|_T]  ->
 
1822
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1823
                               [got,get_token(H),expected,[',','}']]}})
 
1824
    end.
 
1825
 
 
1826
parse_Parameter(Tokens) ->
 
1827
    Flist = [fun parse_ParamGovAndRef/1,
 
1828
             fun parse_Reference/1],
 
1829
    case (catch parse_or(Tokens,Flist)) of
 
1830
        {'EXIT',Reason} ->
 
1831
            exit(Reason);
 
1832
        AsnErr = {asn1_error,_} ->
 
1833
            throw(AsnErr);
 
1834
        Result ->
 
1835
            Result
 
1836
    end.
 
1837
 
 
1838
parse_ParamGovAndRef(Tokens) ->
 
1839
    {ParamGov,Rest} = parse_ParamGovernor(Tokens),
 
1840
    case Rest of
 
1841
        [{':',_}|Rest2] ->
 
1842
            {Ref,Rest3} = parse_Reference(Rest2),
 
1843
            {{ParamGov,Ref},Rest3};
 
1844
        [H|_T] ->
 
1845
           throw({asn1_error,{get_line(H),get(asn1_module),
 
1846
                              [got,get_token(H),expected,':']}})
 
1847
    end.
 
1848
 
 
1849
parse_ParamGovernor(Tokens) ->
 
1850
    Flist = [fun parse_Governor/1,
 
1851
             fun parse_Reference/1],
 
1852
    case (catch parse_or(Tokens,Flist)) of
 
1853
        {'EXIT',Reason} ->
 
1854
            exit(Reason);
 
1855
        AsnErr = {asn1_error,_} ->
 
1856
            throw(AsnErr);
 
1857
        Result ->
 
1858
            Result
 
1859
    end.
 
1860
 
 
1861
% parse_ParameterizedReference(Tokens) ->
 
1862
%     {Ref,Rest} = parse_Reference(Tokens),
 
1863
%     case Rest of
 
1864
%       [{'{',_},{'}',_}|Rest2] ->
 
1865
%           {{ptref,Ref},Rest2};
 
1866
%       _  ->
 
1867
%           {{ptref,Ref},Rest}
 
1868
%     end.
 
1869
 
 
1870
parse_SimpleDefinedType([{typereference,L1,ModuleName},{'.',_},
 
1871
                         {typereference,_,TypeName}|Rest]) ->
 
1872
    {#'Externaltypereference'{pos=L1,module=ModuleName,
 
1873
                                                 type=TypeName},Rest};
 
1874
parse_SimpleDefinedType([Tref={typereference,_,_}|Rest]) ->
 
1875
%    {#'Externaltypereference'{pos=L2,module=get(asn1_module),
 
1876
%                                                type=TypeName},Rest};
 
1877
    {tref2Exttref(Tref),Rest};
 
1878
parse_SimpleDefinedType(Tokens) ->
 
1879
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1880
                       [got,get_token(hd(Tokens)),expected,
 
1881
                        [typereference,'typereference.typereference']]}}).
 
1882
 
 
1883
parse_SimpleDefinedValue([{typereference,L1,ModuleName},{'.',_},
 
1884
                          {identifier,_,Value}|Rest]) ->
 
1885
    {{simpledefinedvalue,#'Externalvaluereference'{pos=L1,module=ModuleName,
 
1886
                                                   value=Value}},Rest};
 
1887
parse_SimpleDefinedValue([{identifier,L2,Value}|Rest]) ->
 
1888
    {{simpledefinedvalue,L2,Value},Rest};
 
1889
parse_SimpleDefinedValue(Tokens) ->
 
1890
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1891
                       [got,get_token(hd(Tokens)),expected,
 
1892
                        ['typereference.identifier',identifier]]}}).
 
1893
 
 
1894
parse_ParameterizedType(Tokens) ->
 
1895
    {Type,Rest} = parse_SimpleDefinedType(Tokens),
 
1896
    {Params,Rest2} = parse_ActualParameterList(Rest),
 
1897
    {{pt,Type,Params},Rest2}.
 
1898
 
 
1899
parse_ParameterizedValue(Tokens) ->
 
1900
    {Value,Rest} = parse_SimpleDefinedValue(Tokens),
 
1901
    {Params,Rest2} = parse_ActualParameterList(Rest),
 
1902
    {{pv,Value,Params},Rest2}.
 
1903
 
 
1904
parse_ParameterizedObjectClass(Tokens) ->
 
1905
    {Type,Rest} = parse_DefinedObjectClass(Tokens),
 
1906
    {Params,Rest2} = parse_ActualParameterList(Rest),
 
1907
    {{poc,Type,Params},Rest2}.
 
1908
 
 
1909
parse_ParameterizedObjectSet(Tokens) ->
 
1910
    {ObjectSet,Rest} = parse_DefinedObjectSet(Tokens),
 
1911
    {Params,Rest2} = parse_ActualParameterList(Rest),
 
1912
    {{pos,ObjectSet,Params},Rest2}.
 
1913
 
 
1914
parse_ParameterizedObject(Tokens) ->
 
1915
    {Object,Rest} = parse_DefinedObject(Tokens),
 
1916
    {Params,Rest2} = parse_ActualParameterList(Rest),
 
1917
    {{po,Object,Params},Rest2}.
 
1918
 
 
1919
parse_ActualParameterList([{'{',_}|Rest]) ->
 
1920
    parse_ActualParameterList(Rest,[]);
 
1921
parse_ActualParameterList(Tokens) ->
 
1922
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
1923
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
1924
 
 
1925
parse_ActualParameterList(Tokens,Acc) ->
 
1926
    {Parameter,Rest} = parse_ActualParameter(Tokens),
 
1927
    case Rest of
 
1928
        [{',',_}|Rest2] ->
 
1929
            parse_ActualParameterList(Rest2,[Parameter|Acc]);
 
1930
        [{'}',_}|Rest3] ->
 
1931
            {lists:reverse([Parameter|Acc]),Rest3};
 
1932
        [H|_T] ->
 
1933
            throw({asn1_error,{get_line(H),get(asn1_module),
 
1934
                               [got,get_token(H),expected,[',','}']]}})
 
1935
%%%     Other ->
 
1936
%%%         throw(Other)
 
1937
    end.
 
1938
 
 
1939
 
 
1940
 
 
1941
 
 
1942
 
 
1943
 
 
1944
 
 
1945
%-------------------------
 
1946
 
 
1947
is_word(Token) ->
 
1948
    case not_allowed_word(Token) of
 
1949
        true -> false;
 
1950
        _ ->
 
1951
            if
 
1952
                atom(Token) ->
 
1953
                    Item = atom_to_list(Token),
 
1954
                    is_word(Item);
 
1955
                list(Token), length(Token) == 1 ->
 
1956
                    check_one_char_word(Token);
 
1957
                list(Token) ->
 
1958
                    [A|Rest] = Token,
 
1959
                    case check_first(A) of
 
1960
                        true ->
 
1961
                            check_rest(Rest);
 
1962
                        _ -> 
 
1963
                            false
 
1964
                    end
 
1965
            end
 
1966
    end.
 
1967
 
 
1968
not_allowed_word(Name) ->
 
1969
    lists:member(Name,["BIT",
 
1970
                       "BOOLEAN",
 
1971
                       "CHARACTER",
 
1972
                       "CHOICE",
 
1973
                       "EMBEDDED",
 
1974
                       "END",
 
1975
                       "ENUMERATED",
 
1976
                       "EXTERNAL",
 
1977
                       "FALSE",
 
1978
                       "INSTANCE",
 
1979
                       "INTEGER",
 
1980
                       "INTERSECTION",
 
1981
                       "MINUS-INFINITY",
 
1982
                       "NULL",
 
1983
                       "OBJECT",
 
1984
                       "OCTET",
 
1985
                       "PLUS-INFINITY",
 
1986
                       "REAL",
 
1987
                       "SEQUENCE",
 
1988
                       "SET",
 
1989
                       "TRUE",
 
1990
                       "UNION"]).
 
1991
 
 
1992
check_one_char_word([A]) when $A =< A, $Z >= A ->
 
1993
    true;
 
1994
check_one_char_word([_]) ->
 
1995
    false. %% unknown item in SyntaxList
 
1996
 
 
1997
check_first(A) when $A =< A, $Z >= A ->
 
1998
    true;
 
1999
check_first(_) ->
 
2000
    false. %% unknown item in SyntaxList
 
2001
 
 
2002
check_rest([R,R|_Rs]) when $- == R ->
 
2003
    false; %% two consecutive hyphens are not allowed in a word
 
2004
check_rest([R]) when $- == R ->
 
2005
    false; %% word cannot end with hyphen
 
2006
check_rest([R|Rs]) when $A=<R, $Z>=R; $-==R ->
 
2007
    check_rest(Rs);
 
2008
check_rest([]) ->
 
2009
    true;
 
2010
check_rest(_) ->
 
2011
    false.
 
2012
 
 
2013
 
 
2014
to_set(V) when list(V) ->
 
2015
        ordsets:list_to_set(V);
 
2016
to_set(V) ->
 
2017
        ordsets:list_to_set([V]).
 
2018
 
 
2019
 
 
2020
parse_AlternativeTypeLists(Tokens) ->
 
2021
    {AlternativeTypeList,Rest1} = parse_AlternativeTypeList(Tokens),
 
2022
    {ExtensionAndException,Rest2} = 
 
2023
        case Rest1 of
 
2024
            [{',',_},{'...',L1},{'!',_}|Rest12] ->
 
2025
                {_,Rest13} = parse_ExceptionIdentification(Rest12),
 
2026
                %% Exception info is currently thrown away
 
2027
                {[#'EXTENSIONMARK'{pos=L1}],Rest13};
 
2028
            [{',',_},{'...',L1}|Rest12] ->
 
2029
                {[#'EXTENSIONMARK'{pos=L1}],Rest12};
 
2030
            _ ->
 
2031
                {[],Rest1}
 
2032
        end,
 
2033
    case ExtensionAndException of
 
2034
        [] ->
 
2035
            {AlternativeTypeList,Rest2};
 
2036
        _ ->
 
2037
            {ExtensionAddition,Rest3} = 
 
2038
                case Rest2 of
 
2039
                    [{',',_}|Rest23] ->
 
2040
                        parse_ExtensionAdditionAlternativeList(Rest23);
 
2041
                    _ ->
 
2042
                        {[],Rest2}
 
2043
                end,
 
2044
            {OptionalExtensionMarker,Rest4} =
 
2045
                case Rest3 of
 
2046
                    [{',',_},{'...',L3}|Rest31] ->
 
2047
                        {[#'EXTENSIONMARK'{pos=L3}],Rest31};
 
2048
                    _ ->
 
2049
                        {[],Rest3}
 
2050
                end,
 
2051
            {AlternativeTypeList ++ ExtensionAndException ++ ExtensionAddition ++ OptionalExtensionMarker, Rest4}
 
2052
    end.
 
2053
    
 
2054
 
 
2055
parse_AlternativeTypeList(Tokens) ->
 
2056
    parse_AlternativeTypeList(Tokens,[]).
 
2057
 
 
2058
parse_AlternativeTypeList(Tokens,Acc) ->
 
2059
    {NamedType,Rest} = parse_NamedType(Tokens),
 
2060
    case Rest of
 
2061
        [{',',_},Id = {identifier,_,_}|Rest2] ->
 
2062
            parse_AlternativeTypeList([Id|Rest2],[NamedType|Acc]);
 
2063
        _ ->
 
2064
            {lists:reverse([NamedType|Acc]),Rest}
 
2065
    end.
 
2066
 
 
2067
    
 
2068
 
 
2069
parse_ExtensionAdditionAlternativeList(Tokens) ->
 
2070
    parse_ExtensionAdditionAlternativeList(Tokens,[]).
 
2071
    
 
2072
parse_ExtensionAdditionAlternativeList(Tokens,Acc) ->
 
2073
    {Element,Rest0} =
 
2074
        case Tokens of
 
2075
            [{identifier,_,_}|_Rest] ->
 
2076
                parse_NamedType(Tokens);
 
2077
            [{'[[',_}|_] ->
 
2078
                parse_ExtensionAdditionAlternatives(Tokens)
 
2079
        end,
 
2080
    case Rest0 of
 
2081
        [{',',_}|Rest01] ->
 
2082
            parse_ExtensionAdditionAlternativeList(Rest01,[Element|Acc]);
 
2083
        _  ->
 
2084
            {lists:reverse([Element|Acc]),Rest0}
 
2085
    end.
 
2086
 
 
2087
parse_ExtensionAdditionAlternatives([{'[[',_}|Rest]) ->
 
2088
    parse_ExtensionAdditionAlternatives(Rest,[]);
 
2089
parse_ExtensionAdditionAlternatives(Tokens) ->
 
2090
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2091
                       [got,get_token(hd(Tokens)),expected,'[[']}}).
 
2092
 
 
2093
parse_ExtensionAdditionAlternatives([Id = {identifier,_,_}|Rest],Acc) ->
 
2094
    {NamedType, Rest2} = parse_NamedType([Id|Rest]),
 
2095
    case Rest2 of
 
2096
        [{',',_}|Rest21] ->
 
2097
            parse_ExtensionAdditionAlternatives(Rest21,[NamedType|Acc]);
 
2098
        [{']]',_}|Rest21] ->
 
2099
            {lists:reverse(Acc),Rest21};
 
2100
        _ ->
 
2101
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
2102
                               [got,get_token(hd(Rest2)),expected,[',',']]']]}})
 
2103
    end.
 
2104
 
 
2105
parse_NamedType([{identifier,L1,Idname}|Rest]) ->
 
2106
    {Type,Rest2} = parse_Type(Rest),
 
2107
    {#'ComponentType'{pos=L1,name=Idname,typespec=Type,prop=mandatory},Rest2};
 
2108
parse_NamedType(Tokens) ->
 
2109
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2110
                       [got,get_token(hd(Tokens)),expected,identifier]}}).
 
2111
 
 
2112
 
 
2113
parse_ComponentTypeLists(Tokens) ->
 
2114
%    Resulting tuple {ComponentTypeList,Rest1} is returned
 
2115
    case Tokens of 
 
2116
        [{identifier,_,_}|_Rest0] ->
 
2117
            {Clist,Rest01} = parse_ComponentTypeList(Tokens),
 
2118
            case Rest01 of
 
2119
                [{',',_}|Rest02] -> 
 
2120
                    parse_ComponentTypeLists(Rest02,Clist);
 
2121
                _ ->
 
2122
                    {Clist,Rest01}
 
2123
            end;
 
2124
        [{'COMPONENTS',_},{'OF',_}|_Rest] ->
 
2125
            {Clist,Rest01} = parse_ComponentTypeList(Tokens),
 
2126
            case Rest01 of
 
2127
                [{',',_}|Rest02] -> 
 
2128
                    parse_ComponentTypeLists(Rest02,Clist);
 
2129
                _ ->
 
2130
                    {Clist,Rest01}
 
2131
            end;
 
2132
        _ ->
 
2133
            parse_ComponentTypeLists(Tokens,[])
 
2134
    end.
 
2135
 
 
2136
parse_ComponentTypeLists([{'...',L1},{'!',_}|Rest],Clist1) ->
 
2137
    {_,Rest2} = parse_ExceptionIdentification(Rest),
 
2138
    %% Exception info is currently thrown away
 
2139
    parse_ComponentTypeLists2(Rest2,Clist1++[#'EXTENSIONMARK'{pos=L1}]);
 
2140
parse_ComponentTypeLists([{'...',L1}|Rest],Clist1) ->
 
2141
    parse_ComponentTypeLists2(Rest,Clist1++[#'EXTENSIONMARK'{pos=L1}]);
 
2142
parse_ComponentTypeLists(Tokens,Clist1) ->
 
2143
    {Clist1,Tokens}.
 
2144
 
 
2145
 
 
2146
parse_ComponentTypeLists2(Tokens,Clist1) ->
 
2147
    {ExtensionAddition,Rest2} = 
 
2148
        case Tokens of
 
2149
            [{',',_}|Rest1] ->
 
2150
                parse_ExtensionAdditionList(Rest1);
 
2151
            _ ->
 
2152
                {[],Tokens}
 
2153
        end,
 
2154
    {OptionalExtensionMarker,Rest3} =
 
2155
        case Rest2 of
 
2156
            [{',',_},{'...',L2}|Rest21] ->
 
2157
                {[#'EXTENSIONMARK'{pos=L2}],Rest21};
 
2158
            _ ->
 
2159
                {[],Rest2}
 
2160
        end,
 
2161
    {RootComponentTypeList,Rest4} =
 
2162
        case Rest3 of
 
2163
            [{',',_}|Rest31] ->
 
2164
                parse_ComponentTypeList(Rest31);
 
2165
            _ ->
 
2166
                {[],Rest3}
 
2167
        end,
 
2168
    {Clist1 ++ ExtensionAddition ++ OptionalExtensionMarker ++ RootComponentTypeList, Rest4}.
 
2169
    
 
2170
 
 
2171
parse_ComponentTypeList(Tokens) ->
 
2172
    parse_ComponentTypeList(Tokens,[]).
 
2173
 
 
2174
parse_ComponentTypeList(Tokens,Acc) ->
 
2175
    {ComponentType,Rest} = parse_ComponentType(Tokens),
 
2176
    case Rest of
 
2177
        [{',',_},Id = {identifier,_,_}|Rest2] ->
 
2178
            parse_ComponentTypeList([Id|Rest2],[ComponentType|Acc]);
 
2179
        [{',',_},C1={'COMPONENTS',_},C2={'OF',_}|Rest2] ->
 
2180
            parse_ComponentTypeList([C1,C2|Rest2],[ComponentType|Acc]);
 
2181
%       _ ->
 
2182
%           {lists:reverse([ComponentType|Acc]),Rest}
 
2183
        [{'}',_}|_] ->
 
2184
            {lists:reverse([ComponentType|Acc]),Rest};
 
2185
        [{',',_},{'...',_}|_] ->
 
2186
            {lists:reverse([ComponentType|Acc]),Rest};
 
2187
        _ ->
 
2188
            throw({asn1_error,
 
2189
                   {get_line(hd(Tokens)),get(asn1_module),
 
2190
                    [got,[get_token(hd(Rest)),get_token(hd(tl(Rest)))],
 
2191
                     expected,['}',', identifier']]}})
 
2192
    end.
 
2193
 
 
2194
    
 
2195
parse_ExtensionAdditionList(Tokens) ->
 
2196
    parse_ExtensionAdditionList(Tokens,[]).
 
2197
    
 
2198
parse_ExtensionAdditionList(Tokens,Acc) ->
 
2199
    {Element,Rest0} =
 
2200
        case Tokens of
 
2201
            [{identifier,_,_}|_Rest] ->
 
2202
                parse_ComponentType(Tokens);
 
2203
            [{'[[',_}|_] ->
 
2204
                parse_ExtensionAdditions(Tokens);
 
2205
            _ ->
 
2206
                throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2207
                                   [got,get_token(hd(Tokens)),expected,
 
2208
                                    [identifier,'[[']]}})
 
2209
        end,
 
2210
    case Rest0 of
 
2211
        [{',',_}|Rest01] ->
 
2212
            parse_ExtensionAdditionList(Rest01,[Element|Acc]);
 
2213
        _  ->
 
2214
            {lists:reverse([Element|Acc]),Rest0}
 
2215
    end.
 
2216
 
 
2217
parse_ExtensionAdditions([{'[[',_}|Rest]) ->
 
2218
    parse_ExtensionAdditions(Rest,[]);
 
2219
parse_ExtensionAdditions(Tokens) ->
 
2220
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2221
                       [got,get_token(hd(Tokens)),expected,'[[']}}).
 
2222
 
 
2223
parse_ExtensionAdditions([Id = {identifier,_,_}|Rest],Acc) ->
 
2224
    {ComponentType, Rest2} = parse_ComponentType([Id|Rest]),
 
2225
    case Rest2 of
 
2226
        [{',',_}|Rest21] ->
 
2227
            parse_ExtensionAdditions(Rest21,[ComponentType|Acc]);
 
2228
        [{']]',_}|Rest21] ->
 
2229
            {lists:reverse(Acc),Rest21};
 
2230
        _ ->
 
2231
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
2232
                               [got,get_token(hd(Rest2)),expected,[',',']]']]}})
 
2233
    end;
 
2234
parse_ExtensionAdditions(Tokens,_) ->
 
2235
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2236
                       [got,get_token(hd(Tokens)),expected,identifier]}}).
 
2237
 
 
2238
parse_ComponentType([{'COMPONENTS',_},{'OF',_}|Rest]) ->
 
2239
    {Type,Rest2} = parse_Type(Rest),
 
2240
    {{'COMPONENTS OF',Type},Rest2};
 
2241
parse_ComponentType(Tokens) ->
 
2242
    {NamedType,Rest} = parse_NamedType(Tokens),
 
2243
    case Rest of
 
2244
        [{'OPTIONAL',_}|Rest2] ->
 
2245
            {NamedType#'ComponentType'{prop='OPTIONAL'},Rest2};
 
2246
        [{'DEFAULT',_}|Rest2] ->
 
2247
            {Value,Rest21} = parse_Value(Rest2),
 
2248
            {NamedType#'ComponentType'{prop={'DEFAULT',Value}},Rest21};
 
2249
        _ ->
 
2250
            {NamedType,Rest}
 
2251
    end.
 
2252
 
 
2253
            
 
2254
 
 
2255
parse_SignedNumber([{number,_,Value}|Rest]) ->
 
2256
    {Value,Rest};
 
2257
parse_SignedNumber([{'-',_},{number,_,Value}|Rest]) ->
 
2258
    {-Value,Rest};
 
2259
parse_SignedNumber(Tokens) ->
 
2260
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2261
                       [got,get_token(hd(Tokens)),expected,
 
2262
                        [number,'-number']]}}).
 
2263
 
 
2264
parse_Enumerations(Tokens=[{identifier,_,_}|_Rest]) ->
 
2265
    parse_Enumerations(Tokens,[]);
 
2266
parse_Enumerations([H|_T]) ->
 
2267
    throw({asn1_error,{get_line(H),get(asn1_module),
 
2268
                       [got,get_token(H),expected,identifier]}}).
 
2269
 
 
2270
parse_Enumerations(Tokens = [{identifier,_,_},{'(',_}|_Rest], Acc) ->
 
2271
    {NamedNumber,Rest2} = parse_NamedNumber(Tokens),
 
2272
    case Rest2 of
 
2273
        [{',',_}|Rest3] ->
 
2274
            parse_Enumerations(Rest3,[NamedNumber|Acc]);
 
2275
        _ ->
 
2276
            {lists:reverse([NamedNumber|Acc]),Rest2}
 
2277
    end;
 
2278
parse_Enumerations([{identifier,_,Id}|Rest], Acc) ->
 
2279
    case Rest of
 
2280
        [{',',_}|Rest2] ->
 
2281
            parse_Enumerations(Rest2,[Id|Acc]);
 
2282
        _ ->
 
2283
            {lists:reverse([Id|Acc]),Rest}
 
2284
    end;
 
2285
parse_Enumerations([{'...',_}|Rest], Acc) ->
 
2286
    case Rest of
 
2287
        [{',',_}|Rest2] ->
 
2288
            parse_Enumerations(Rest2,['EXTENSIONMARK'|Acc]);
 
2289
        _ ->
 
2290
            {lists:reverse(['EXTENSIONMARK'|Acc]),Rest}
 
2291
    end;
 
2292
parse_Enumerations([H|_T],_) ->
 
2293
    throw({asn1_error,{get_line(H),get(asn1_module),
 
2294
                       [got,get_token(H),expected,identifier]}}).
 
2295
 
 
2296
parse_NamedNumberList(Tokens) ->
 
2297
    parse_NamedNumberList(Tokens,[]).
 
2298
 
 
2299
parse_NamedNumberList(Tokens,Acc) ->
 
2300
    {NamedNum,Rest} = parse_NamedNumber(Tokens),
 
2301
    case Rest of
 
2302
        [{',',_}|Rest2] ->
 
2303
            parse_NamedNumberList(Rest2,[NamedNum|Acc]);
 
2304
        _ ->
 
2305
            {lists:reverse([NamedNum|Acc]),Rest}
 
2306
    end.
 
2307
 
 
2308
parse_NamedNumber([{identifier,_,Name},{'(',_}|Rest]) ->
 
2309
    Flist = [fun parse_SignedNumber/1,
 
2310
             fun parse_DefinedValue/1],
 
2311
    case (catch parse_or(Rest,Flist)) of
 
2312
        {'EXIT',Reason} ->
 
2313
            exit(Reason);
 
2314
        AsnErr = {asn1_error,_} ->
 
2315
            throw(AsnErr);
 
2316
        {NamedNum,[{')',_}|Rest2]} ->
 
2317
            {{'NamedNumber',Name,NamedNum},Rest2};
 
2318
        _ ->
 
2319
            throw({asn1_error,{get_line(hd(Rest)),get(asn1_module),
 
2320
                               [got,get_token(hd(Rest)),expected,'NamedNumberList']}})
 
2321
    end;
 
2322
parse_NamedNumber(Tokens) ->
 
2323
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2324
                       [got,get_token(hd(Tokens)),expected,identifier]}}).
 
2325
 
 
2326
 
 
2327
parse_Tag([{'[',_}|Rest]) ->
 
2328
    {Class,Rest2} = parse_Class(Rest),
 
2329
    {ClassNumber,Rest3} = 
 
2330
        case Rest2 of
 
2331
            [{number,_,Num}|Rest21] ->
 
2332
                {Num,Rest21};
 
2333
            _ ->
 
2334
                parse_DefinedValue(Rest2)
 
2335
        end,
 
2336
    case Rest3 of
 
2337
        [{']',_}|Rest4] ->
 
2338
            {#tag{class=Class,number=ClassNumber},Rest4};
 
2339
        _ ->
 
2340
            throw({asn1_error,{get_line(hd(Rest3)),get(asn1_module),
 
2341
                               [got,get_token(hd(Rest3)),expected,']']}})
 
2342
    end;
 
2343
parse_Tag(Tokens) ->
 
2344
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2345
                       [got,get_token(hd(Tokens)),expected,'[']}}).
 
2346
 
 
2347
parse_Class([{'UNIVERSAL',_}|Rest]) ->
 
2348
    {'UNIVERSAL',Rest};
 
2349
parse_Class([{'APPLICATION',_}|Rest]) ->
 
2350
    {'APPLICATION',Rest};
 
2351
parse_Class([{'PRIVATE',_}|Rest]) ->
 
2352
    {'PRIVATE',Rest};
 
2353
parse_Class(Tokens) ->
 
2354
    {'CONTEXT',Tokens}.
 
2355
 
 
2356
parse_Value(Tokens) ->
 
2357
    Flist = [fun parse_BuiltinValue/1,
 
2358
             fun parse_ValueFromObject/1,
 
2359
             fun parse_DefinedValue/1],
 
2360
 
 
2361
    case (catch parse_or(Tokens,Flist)) of
 
2362
        {'EXIT',Reason} ->
 
2363
            exit(Reason);
 
2364
        AsnErr = {asn1_error,_} ->
 
2365
            throw(AsnErr);
 
2366
        Result ->
 
2367
            Result
 
2368
    end.
 
2369
 
 
2370
parse_BuiltinValue([{bstring,_,Bstr}|Rest]) ->
 
2371
    {{bstring,Bstr},Rest};
 
2372
parse_BuiltinValue([{hstring,_,Hstr}|Rest]) ->
 
2373
    {{hstring,Hstr},Rest};
 
2374
parse_BuiltinValue([{'{',_},{'}',_}|Rest]) ->
 
2375
    {[],Rest};
 
2376
parse_BuiltinValue(Tokens = [{'{',_}|_Rest]) ->
 
2377
    Flist = [
 
2378
             fun parse_SequenceOfValue/1, 
 
2379
             fun parse_SequenceValue/1, 
 
2380
             fun parse_ObjectIdentifierValue/1],
 
2381
    case (catch parse_or(Tokens,Flist)) of
 
2382
        {'EXIT',Reason} ->
 
2383
            exit(Reason);
 
2384
        AsnErr = {asn1_error,_} ->
 
2385
            throw(AsnErr);
 
2386
        Result ->
 
2387
            Result
 
2388
    end;
 
2389
parse_BuiltinValue([{identifier,_,IdName},{':',_}|Rest]) ->
 
2390
    {Value,Rest2} = parse_Value(Rest),
 
2391
    {{'CHOICE',{IdName,Value}},Rest2};
 
2392
parse_BuiltinValue([{'NULL',_}|Rest]) ->
 
2393
    {'NULL',Rest};
 
2394
parse_BuiltinValue([{'TRUE',_}|Rest]) ->
 
2395
    {true,Rest};
 
2396
parse_BuiltinValue([{'FALSE',_}|Rest]) ->
 
2397
    {false,Rest};
 
2398
parse_BuiltinValue([{'PLUS-INFINITY',_}|Rest]) ->
 
2399
    {'PLUS-INFINITY',Rest};
 
2400
parse_BuiltinValue([{'MINUS-INFINITY',_}|Rest]) ->
 
2401
    {'MINUS-INFINITY',Rest};
 
2402
parse_BuiltinValue([{cstring,_,Cstr}|Rest]) ->
 
2403
    {Cstr,Rest};
 
2404
parse_BuiltinValue([{number,_,Num}|Rest]) ->
 
2405
    {Num,Rest};
 
2406
parse_BuiltinValue([{'-',_},{number,_,Num}|Rest]) ->
 
2407
    {- Num,Rest};
 
2408
parse_BuiltinValue(Tokens) ->
 
2409
    parse_ObjectClassFieldValue(Tokens).
 
2410
 
 
2411
%% Externalvaluereference
 
2412
parse_DefinedValue([{typereference,L1,Tname},{'.',_},{identifier,_,Idname}|Rest]) ->
 
2413
    {#'Externalvaluereference'{pos=L1,module=Tname,value=Idname},Rest};
 
2414
%% valuereference
 
2415
parse_DefinedValue([Id = {identifier,_,_}|Rest]) ->
 
2416
    {identifier2Extvalueref(Id),Rest};
 
2417
%% ParameterizedValue
 
2418
parse_DefinedValue(Tokens) ->
 
2419
    parse_ParameterizedValue(Tokens).
 
2420
 
 
2421
 
 
2422
parse_SequenceValue([{'{',_}|Tokens]) ->
 
2423
    parse_SequenceValue(Tokens,[]);
 
2424
parse_SequenceValue(Tokens) ->
 
2425
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2426
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
2427
 
 
2428
parse_SequenceValue([{identifier,_,IdName}|Rest],Acc) ->
 
2429
    {Value,Rest2} = parse_Value(Rest),
 
2430
    case Rest2 of
 
2431
        [{',',_}|Rest3] ->
 
2432
            parse_SequenceValue(Rest3,[{IdName,Value}|Acc]);
 
2433
        [{'}',_}|Rest3] ->
 
2434
            {lists:reverse([{IdName,Value}|Acc]),Rest3};
 
2435
        _ ->
 
2436
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
2437
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
2438
    end;
 
2439
parse_SequenceValue(Tokens,_Acc) ->
 
2440
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2441
                       [got,get_token(hd(Tokens)),expected,identifier]}}).
 
2442
 
 
2443
parse_SequenceOfValue([{'{',_}|Tokens]) ->
 
2444
    parse_SequenceOfValue(Tokens,[]);
 
2445
parse_SequenceOfValue(Tokens) ->
 
2446
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2447
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
2448
 
 
2449
parse_SequenceOfValue(Tokens,Acc) ->
 
2450
    {Value,Rest2} = parse_Value(Tokens),
 
2451
    case Rest2 of
 
2452
        [{',',_}|Rest3] ->
 
2453
            parse_SequenceOfValue(Rest3,[Value|Acc]);
 
2454
        [{'}',_}|Rest3] ->
 
2455
            {lists:reverse([Value|Acc]),Rest3};
 
2456
        _ ->
 
2457
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
2458
                               [got,get_token(hd(Rest2)),expected,'}']}})
 
2459
    end.
 
2460
 
 
2461
parse_ValueSetTypeAssignment([{typereference,L1,Name}|Rest]) ->
 
2462
    {Type,Rest2} = parse_Type(Rest),
 
2463
    case Rest2 of
 
2464
        [{'::=',_}|Rest3] ->
 
2465
            {ValueSet,Rest4} = parse_ValueSet(Rest3),
 
2466
            {#valuedef{pos=L1,name=Name,type=Type,value=ValueSet},Rest4};
 
2467
        [H|_T] ->
 
2468
            throw({asn1_error,{get_line(L1),get(asn1_module),
 
2469
                               [got,get_token(H),expected,'::=']}})
 
2470
    end;
 
2471
parse_ValueSetTypeAssignment(Tokens) ->
 
2472
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
2473
                                  [got,get_token(hd(Tokens)),expected,
 
2474
                                   typereference]}}).
 
2475
 
 
2476
parse_ValueSet([{'{',_}|Rest]) ->
 
2477
    {Elems,Rest2} = parse_ElementSetSpecs(Rest),
 
2478
    case Rest2 of
 
2479
        [{'}',_}|Rest3] ->
 
2480
            {{valueset,Elems},Rest3};
 
2481
        [H|_T] ->
 
2482
            throw({asn1_error,{get_line(H),get(asn1_module),
 
2483
                               [got,get_token(H),expected,'}']}})
 
2484
    end;
 
2485
parse_ValueSet(Tokens) ->
 
2486
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2487
                       [got,get_token(hd(Tokens)),expected,'{']}}).
 
2488
 
 
2489
parse_ValueAssignment([{identifier,L1,IdName}|Rest]) ->
 
2490
    {Type,Rest2} = parse_Type(Rest),
 
2491
    case Rest2 of
 
2492
        [{'::=',_}|Rest3] ->
 
2493
            {Value,Rest4} = parse_Value(Rest3),
 
2494
            case lookahead_assignment(Rest4) of
 
2495
                ok ->
 
2496
                    {#valuedef{pos=L1,name=IdName,type=Type,value=Value},Rest4};
 
2497
                _ ->
 
2498
                    throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
2499
                                       [got,get_token(hd(Rest2)),expected,'::=']}})
 
2500
            end;
 
2501
        _ ->
 
2502
            throw({asn1_error,{get_line(hd(Rest2)),get(asn1_module),
 
2503
                               [got,get_token(hd(Rest2)),expected,'::=']}})
 
2504
    end;
 
2505
parse_ValueAssignment(Tokens) ->
 
2506
    throw({asn1_assignment_error,{get_line(hd(Tokens)),get(asn1_module),
 
2507
                                  [got,get_token(hd(Tokens)),expected,identifier]}}).
 
2508
 
 
2509
%% SizeConstraint
 
2510
parse_SubtypeElements([{'SIZE',_}|Tokens]) ->
 
2511
    {Constraint,Rest} = parse_Constraint(Tokens),
 
2512
    {{'SizeConstraint',Constraint#constraint.c},Rest};
 
2513
%% PermittedAlphabet
 
2514
parse_SubtypeElements([{'FROM',_}|Tokens]) ->
 
2515
    {Constraint,Rest} = parse_Constraint(Tokens),
 
2516
    {{'PermittedAlphabet',Constraint#constraint.c},Rest};
 
2517
%% InnerTypeConstraints
 
2518
parse_SubtypeElements([{'WITH',_},{'COMPONENT',_}|Tokens]) ->
 
2519
    {Constraint,Rest} = parse_Constraint(Tokens),
 
2520
    {{'WITH COMPONENT',Constraint},Rest};
 
2521
parse_SubtypeElements([{'WITH',_},{'COMPONENTS',_},{'{',_},{'...',_},{',',_}|Tokens]) ->
 
2522
    {Constraint,Rest} = parse_TypeConstraints(Tokens),
 
2523
    case Rest of
 
2524
        [{'}',_}|Rest2] ->
 
2525
            {{'WITH COMPONENTS',{'PartialSpecification',Constraint}},Rest2};
 
2526
        _ ->
 
2527
            throw({asn1_error,{get_line(hd(Rest)),get(asn1_module),
 
2528
                               [got,get_token(hd(Rest)),expected,'}']}})
 
2529
    end;
 
2530
parse_SubtypeElements([{'WITH',_},{'COMPONENTS',_},{'{',_}|Tokens]) ->
 
2531
    {Constraint,Rest} = parse_TypeConstraints(Tokens),
 
2532
    case Rest of
 
2533
        [{'}',_}|Rest2] ->
 
2534
            {{'WITH COMPONENTS',{'FullSpecification',Constraint}},Rest2};
 
2535
        _ ->
 
2536
            throw({asn1_error,{get_line(hd(Rest)),get(asn1_module),
 
2537
                               [got,get_token(hd(Rest)),expected,'}']}})
 
2538
    end;
 
2539
%% SingleValue
 
2540
%% ContainedSubtype
 
2541
%% ValueRange
 
2542
%% TypeConstraint
 
2543
parse_SubtypeElements(Tokens) ->
 
2544
    Flist = [fun parse_ContainedSubtype/1,
 
2545
             fun parse_Value/1, 
 
2546
             fun([{'MIN',_}|T]) -> {'MIN',T} end,
 
2547
             fun parse_Type/1],
 
2548
    case (catch parse_or(Tokens,Flist)) of
 
2549
        {'EXIT',Reason} ->
 
2550
            exit(Reason);
 
2551
        {asn1_error,Reason} ->
 
2552
            throw(Reason);
 
2553
        Result = {Val,_} when record(Val,type) ->
 
2554
            Result;
 
2555
        {Lower,[{'..',_}|Rest]} ->
 
2556
            {Upper,Rest2} = parse_UpperEndpoint(Rest),
 
2557
            {{'ValueRange',{Lower,Upper}},Rest2};
 
2558
        {Lower,[{'<',_},{'..',_}|Rest]} ->
 
2559
            {Upper,Rest2} = parse_UpperEndpoint(Rest),
 
2560
            {{'ValueRange',{{gt,Lower},Upper}},Rest2};
 
2561
        {Res={'ContainedSubtype',_Type},Rest} ->
 
2562
            {Res,Rest};
 
2563
        {Value,Rest} ->
 
2564
            {{'SingleValue',Value},Rest}
 
2565
    end.
 
2566
 
 
2567
parse_ContainedSubtype([{'INCLUDES',_}|Rest]) ->
 
2568
    {Type,Rest2} = parse_Type(Rest),
 
2569
    {{'ContainedSubtype',Type},Rest2};
 
2570
parse_ContainedSubtype(Tokens) ->
 
2571
    throw({asn1_error,{get_line(hd(Tokens)),get(asn1_module),
 
2572
                       [got,get_token(hd(Tokens)),expected,'INCLUDES']}}).
 
2573
%%parse_ContainedSubtype(Tokens) -> %this option is moved to parse_SubtypeElements
 
2574
%%    parse_Type(Tokens).
 
2575
 
 
2576
parse_UpperEndpoint([{'<',_}|Rest]) ->
 
2577
    parse_UpperEndpoint(lt,Rest);
 
2578
parse_UpperEndpoint(Tokens) ->
 
2579
    parse_UpperEndpoint(false,Tokens).
 
2580
 
 
2581
parse_UpperEndpoint(Lt,Tokens) ->
 
2582
    Flist = [ fun([{'MAX',_}|T]) -> {'MAX',T} end,
 
2583
              fun parse_Value/1],
 
2584
    case (catch parse_or(Tokens,Flist)) of
 
2585
        {'EXIT',Reason} ->
 
2586
            exit(Reason);
 
2587
        AsnErr = {asn1_error,_} ->
 
2588
            throw(AsnErr);
 
2589
        {Value,Rest2} when Lt == lt ->
 
2590
            {{lt,Value},Rest2};
 
2591
        {Value,Rest2} ->
 
2592
            {Value,Rest2}
 
2593
    end.
 
2594
 
 
2595
parse_TypeConstraints(Tokens) ->
 
2596
    parse_TypeConstraints(Tokens,[]).
 
2597
 
 
2598
parse_TypeConstraints([{identifier,_,_}|Rest],Acc) ->
 
2599
    {ComponentConstraint,Rest2} = parse_ComponentConstraint(Rest),
 
2600
    case Rest2 of
 
2601
        [{',',_}|Rest3] ->
 
2602
            parse_TypeConstraints(Rest3,[ComponentConstraint|Acc]);
 
2603
        _ ->
 
2604
            {lists:reverse([ComponentConstraint|Acc]),Rest2}
 
2605
    end;
 
2606
parse_TypeConstraints([H|_T],_) ->
 
2607
    throw({asn1_error,{get_line(H),get(asn1_module),
 
2608
                       [got,get_token(H),expected,identifier]}}).
 
2609
 
 
2610
parse_ComponentConstraint(Tokens = [{'(',_}|_Rest]) ->
 
2611
    {ValueConstraint,Rest2} = parse_Constraint(Tokens),
 
2612
    {PresenceConstraint,Rest3} = parse_PresenceConstraint(Rest2),
 
2613
    {{ValueConstraint,PresenceConstraint},Rest3};
 
2614
parse_ComponentConstraint(Tokens) ->
 
2615
    {PresenceConstraint,Rest} = parse_PresenceConstraint(Tokens),
 
2616
    {{asn1_empty,PresenceConstraint},Rest}.
 
2617
 
 
2618
parse_PresenceConstraint([{'PRESENT',_}|Rest]) ->
 
2619
    {'PRESENT',Rest};
 
2620
parse_PresenceConstraint([{'ABSENT',_}|Rest]) ->
 
2621
    {'ABSENT',Rest};
 
2622
parse_PresenceConstraint([{'OPTIONAL',_}|Rest]) ->
 
2623
    {'OPTIONAL',Rest};
 
2624
parse_PresenceConstraint(Tokens) ->
 
2625
    {asn1_empty,Tokens}.
 
2626
 
 
2627
 
 
2628
merge_constraints({Rlist,ExtList}) -> % extensionmarker in constraint
 
2629
    {merge_constraints(Rlist,[],[]),
 
2630
     merge_constraints(ExtList,[],[])};
 
2631
        
 
2632
merge_constraints(Clist) ->
 
2633
    merge_constraints(Clist, [], []).
 
2634
 
 
2635
merge_constraints([Ch|Ct],Cacc, Eacc) ->
 
2636
    NewEacc = case Ch#constraint.e of
 
2637
                  undefined -> Eacc;
 
2638
                  E -> [E|Eacc]
 
2639
              end,
 
2640
    merge_constraints(Ct,[fixup_constraint(Ch#constraint.c)|Cacc],NewEacc);
 
2641
 
 
2642
merge_constraints([],Cacc,[]) ->
 
2643
%%    lists:flatten(Cacc);
 
2644
    lists:reverse(Cacc);
 
2645
merge_constraints([],Cacc,Eacc) ->
 
2646
%%    lists:flatten(Cacc) ++ [{'Errors',Eacc}].
 
2647
    lists:reverse(Cacc) ++ [{'Errors',Eacc}].
 
2648
 
 
2649
fixup_constraint(C) ->
 
2650
    case C of
 
2651
        {'SingleValue',SubType} when element(1,SubType) == 'ContainedSubtype' ->
 
2652
            SubType;
 
2653
        {'SingleValue',V} when list(V) ->
 
2654
            C;
 
2655
        %%          [C,{'ValueRange',{lists:min(V),lists:max(V)}}]; 
 
2656
        %% bug, turns wrong when an element in V is a reference to a defined value
 
2657
        {'PermittedAlphabet',{'SingleValue',V}} when list(V) ->
 
2658
            %%sort and remove duplicates
 
2659
            V2 = {'SingleValue',
 
2660
                  ordsets:list_to_set(lists:flatten(V))},
 
2661
            {'PermittedAlphabet',V2};
 
2662
        {'PermittedAlphabet',{'SingleValue',V}} ->
 
2663
            V2 = {'SingleValue',[V]},
 
2664
            {'PermittedAlphabet',V2};
 
2665
        {'SizeConstraint',Sc} ->
 
2666
            {'SizeConstraint',fixup_size_constraint(Sc)};
 
2667
        
 
2668
        List when list(List) ->  %% In This case maybe a union or intersection
 
2669
            [fixup_constraint(Xc)||Xc <- List];
 
2670
        Other ->
 
2671
            Other
 
2672
    end.
 
2673
 
 
2674
fixup_size_constraint({'ValueRange',{Lb,Ub}}) ->
 
2675
        {Lb,Ub};
 
2676
fixup_size_constraint({{'ValueRange',R},[]}) ->
 
2677
        {R,[]};
 
2678
fixup_size_constraint({[],{'ValueRange',R}}) ->
 
2679
        {[],R};
 
2680
fixup_size_constraint({{'ValueRange',R1},{'ValueRange',R2}}) ->
 
2681
        {R1,R2};
 
2682
fixup_size_constraint({'SingleValue',[Sv]}) ->
 
2683
        fixup_size_constraint({'SingleValue',Sv});
 
2684
fixup_size_constraint({'SingleValue',L}) when list(L) ->
 
2685
        ordsets:list_to_set(L);
 
2686
fixup_size_constraint({'SingleValue',L}) ->
 
2687
        {L,L};
 
2688
fixup_size_constraint({C1,C2}) ->
 
2689
        {fixup_size_constraint(C1), fixup_size_constraint(C2)}.
 
2690
   
 
2691
get_line({_,Pos,Token}) when integer(Pos),atom(Token) ->
 
2692
    Pos;
 
2693
get_line({Token,Pos}) when integer(Pos),atom(Token) ->
 
2694
    Pos;
 
2695
get_line(_) ->
 
2696
    undefined.
 
2697
 
 
2698
get_token({_,Pos,Token}) when integer(Pos),atom(Token) ->
 
2699
    Token;
 
2700
get_token({'$end',Pos}) when integer(Pos) ->
 
2701
    undefined;
 
2702
get_token({Token,Pos}) when integer(Pos),atom(Token) ->
 
2703
    Token;
 
2704
get_token(_) ->
 
2705
    undefined.
 
2706
 
 
2707
prioritize_error(ErrList) ->
 
2708
    case lists:keymember(asn1_error,1,ErrList) of
 
2709
        false -> % only asn1_assignment_error -> take the last
 
2710
            lists:last(ErrList);
 
2711
        true -> % contains errors from deeper in a Type
 
2712
            NewErrList = [_Err={_,_}|_RestErr] =
 
2713
                lists:filter(fun({asn1_error,_})->true;(_)->false end,
 
2714
                             ErrList),
 
2715
            SplitErrs =
 
2716
                lists:splitwith(fun({_,X})->
 
2717
                                        case element(1,X) of
 
2718
                                            Int when integer(Int) -> true;
 
2719
                                            _ -> false
 
2720
                                        end
 
2721
                                end,
 
2722
                                NewErrList),
 
2723
            case SplitErrs of
 
2724
                {[],UndefPosErrs} -> % if no error with Positon exists
 
2725
                    lists:last(UndefPosErrs);
 
2726
                {IntPosErrs,_} ->
 
2727
                    IntPosReasons = lists:map(fun(X)->element(2,X) end,IntPosErrs),
 
2728
                    SortedReasons = lists:keysort(1,IntPosReasons),
 
2729
                    {asn1_error,lists:last(SortedReasons)}
 
2730
            end
 
2731
    end.
 
2732
 
 
2733
%% most_prio_error([H={_,Reason}|T],Atom,Err) when atom(Atom) ->
 
2734
%%     most_prio_error(T,element(1,Reason),H);
 
2735
%% most_prio_error([H={_,Reason}|T],Greatest,Err) ->
 
2736
%%     case element(1,Reason) of
 
2737
%%      Pos when integer(Pos),Pos>Greatest ->
 
2738
%%          most_prio_error(
 
2739
 
 
2740
 
 
2741
tref2Exttref(#typereference{pos=Pos,val=Name}) ->
 
2742
    #'Externaltypereference'{pos=Pos,
 
2743
                             module=get(asn1_module),
 
2744
                             type=Name}.
 
2745
 
 
2746
tref2Exttref(Pos,Name) ->
 
2747
    #'Externaltypereference'{pos=Pos,
 
2748
                             module=get(asn1_module),
 
2749
                             type=Name}.
 
2750
 
 
2751
identifier2Extvalueref(#identifier{pos=Pos,val=Name}) ->
 
2752
    #'Externalvaluereference'{pos=Pos,
 
2753
                              module=get(asn1_module),
 
2754
                              value=Name}.
 
2755
 
 
2756
%% lookahead_assignment/1 checks that the next sequence of tokens
 
2757
%% in Token contain a valid assignment or the
 
2758
%% 'END' token. Otherwise an exception is thrown.
 
2759
lookahead_assignment([{'END',_}|_Rest]) ->
 
2760
    ok;
 
2761
lookahead_assignment(Tokens) ->
 
2762
    parse_Assignment(Tokens),
 
2763
    ok.
 
2764