2 * Copyright (c) 2000-2001 Apple Computer, Inc. All Rights Reserved.
4 * The contents of this file constitute Original Code as defined in and are
5 * subject to the Apple Public Source License Version 1.2 (the 'License').
6 * You may not use this file except in compliance with the License. Please obtain
7 * a copy of the License at http://www.apple.com/publicsource and read it before
10 * This Original Code and all software distributed under the License are
11 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS
12 * OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, INCLUDING WITHOUT
13 * LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
14 * PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. Please see the License for the
15 * specific language governing rights and limitations under the License.
20 * compiler/back-ends/c-gen/gen-print.c - routines for printing C hierachical print routines
24 * Copyright (C) 1991, 1992 Michael Sample
25 * and the University of British Columbia
27 * This program is free software; you can redistribute it and/or modify
28 * it under the terms of the GNU General Public License as published by
29 * the Free Software Foundation; either version 2 of the License, or
30 * (at your option) any later version.
32 * $Header: /cvs/Darwin/Security/SecuritySNACCRuntime/compiler/back-ends/c-gen/gen-print.c,v 1.1.1.1 2001/05/18 23:14:09 mb Exp $
33 * $Log: gen-print.c,v $
34 * Revision 1.1.1.1 2001/05/18 23:14:09 mb
35 * Move from private repository to open source repository
37 * Revision 1.2 2001/05/05 00:59:28 rmurphy
38 * Adding darwin license headers
40 * Revision 1.1.1.1 1999/03/16 18:06:42 aram
41 * Originals from SMIME Free Library.
43 * Revision 1.3 1995/07/25 18:43:18 rj
44 * file name has been shortened for redundant part: c-gen/gen-c-print -> c-gen/gen-print.
46 * changed `_' to `-' in file names.
48 * Revision 1.2 1994/09/01 00:23:43 rj
49 * snacc_config.h and other superfluous .h files removed.
51 * Revision 1.1 1994/08/28 09:48:28 rj
52 * first check-in. for a list of changes to the snacc-1.1 distribution please refer to the ChangeLog.
59 #include "asn1module.h"
63 #include "type-info.h"
66 #include "gen-print.h"
68 static char *returnTypeG
= "void";
69 static char *valueArgNameG
= "v";
70 static char *fileTypeNameG
= "FILE*";
71 static char *indentTypeNameG
= "unsigned short int";
72 static CRules
*genPrintCRulesG
;
73 /* non-exported prototypes */
75 static void PrintCPrintPrototype
PROTO ((FILE *hdr
, TypeDef
*td
));
76 static void PrintCPrintDeclaration
PROTO ((FILE *src
, TypeDef
*td
));
77 static void PrintCPrintDefine
PROTO ((FILE *hdr
, TypeDef
*td
));
78 static void PrintCPrintLocals
PROTO ((FILE *src
,TypeDef
*td
));
80 static void PrintCPrintElmts PROTO ((FILE *src, TypeDef *td, Type *parent, NamedTypeList *elmts, char *varName));
82 static void PrintCChoiceElmtPrint
PROTO ((FILE *src
, TypeDef
*td
, Type
*parent
, NamedTypeList
*elmts
, NamedType
*e
, char *varName
));
85 static void PrintCElmtPrintWithIndent
PROTO ((FILE *src
, TypeDef
*td
, Type
*parent
, NamedTypeList
*elmts
, NamedType
*e
, char *varName
, int allOpt
));
87 static void PrintCChoicePrintRoutine
PROTO ((FILE *src
, FILE *hdr
, CRules
*r
, ModuleList
*mods
, Module
*m
, TypeDef
*td
));
89 static void PrintCSetPrintRoutine
PROTO ((FILE *src
, FILE *hdr
, CRules
*r
, ModuleList
*mods
, Module
*m
, TypeDef
*td
));
90 static void PrintCSeqPrintRoutine
PROTO ((FILE *src
, FILE *hdr
, CRules
*r
, ModuleList
*mods
, Module
*m
, TypeDef
*td
));
91 static void PrintCSeqOfPrintRoutine
PROTO ((FILE *src
, FILE *hdr
, CRules
*r
, ModuleList
*mods
, Module
*m
, TypeDef
*td
));
92 static void PrintCSetOfPrintRoutine
PROTO ((FILE *src
, FILE *hdr
, CRules
*r
, ModuleList
*mods
, Module
*m
, TypeDef
*td
));
97 PrintCPrinter
PARAMS ((src
, hdr
, r
, mods
, m
, td
),
101 ModuleList
*mods _AND_
105 if ((td
->cTypeDefInfo
== NULL
) || !(td
->cTypeDefInfo
->genPrintRoutine
))
109 switch (td
->type
->basicType
->choiceId
)
111 case BASICTYPE_IMPORTTYPEREF
: /* type references */
112 case BASICTYPE_LOCALTYPEREF
:
113 case BASICTYPE_BOOLEAN
: /* library type */
114 case BASICTYPE_REAL
: /* library type */
115 case BASICTYPE_OCTETSTRING
: /* library type */
116 case BASICTYPE_NULL
: /* library type */
117 case BASICTYPE_OID
: /* library type */
118 case BASICTYPE_INTEGER
: /* library type */
119 case BASICTYPE_BITSTRING
: /* library type */
120 case BASICTYPE_ENUMERATED
: /* library type */
121 case BASICTYPE_ANYDEFINEDBY
: /* ANY types */
123 PrintCPrintDefine (hdr
, td
);
124 fprintf (hdr
, "\n\n");
127 case BASICTYPE_SETOF
:
128 PrintCSetOfPrintRoutine (src
, hdr
, r
, mods
, m
, td
);
131 case BASICTYPE_SEQUENCEOF
:
132 PrintCSeqOfPrintRoutine (src
, hdr
, r
, mods
, m
, td
);
135 case BASICTYPE_CHOICE
:
136 PrintCChoicePrintRoutine (src
, hdr
, r
, mods
, m
, td
);
140 PrintCSetPrintRoutine (src
, hdr
, r
, mods
, m
, td
);
144 case BASICTYPE_SEQUENCE
:
145 PrintCSeqPrintRoutine (src
, hdr
, r
, mods
, m
, td
);
155 * Prints prototype for encode routine in hdr file
158 PrintCPrintPrototype
PARAMS ((hdr
, td
),
164 ctdi
= td
->cTypeDefInfo
;
165 fprintf (hdr
,"%s %s PROTO ((%s f, %s *v, %s indent));\n", returnTypeG
, ctdi
->printRoutineName
, fileTypeNameG
, ctdi
->cTypeName
, indentTypeNameG
);
167 } /* PrintCPrintPrototype */
172 * Prints declarations of encode routine for the given type def
175 PrintCPrintDeclaration
PARAMS ((src
, td
),
181 ctdi
= td
->cTypeDefInfo
;
182 fprintf (src
,"%s\n%s PARAMS ((f, v, indent),\n%s f _AND_\n%s *v _AND_\n%s indent)\n", returnTypeG
, ctdi
->printRoutineName
, fileTypeNameG
, ctdi
->cTypeName
, indentTypeNameG
);
184 } /* PrintCPrintDeclaration */
190 PrintCPrintDefine
PARAMS ((hdr
, td
),
194 fprintf(hdr
, "#define %s %s", td
->cTypeDefInfo
->printRoutineName
, td
->type
->cTypeRefInfo
->printRoutineName
);
196 fprintf(hdr, "#define %s(f, v, indent) ", td->cTypeDefInfo->printRoutineName);
197 fprintf (hdr, "%s (f, v, indent)", td->type->cTypeRefInfo->printRoutineName);
199 } /* PrintCPrintDefine */
205 PrintCPrintLocals
PARAMS ((src
, td
),
210 } /* PrintCPrintLocals */
215 PrintCPrintElmts PARAMS ((src, td, parent, elmts, varName),
219 NamedTypeList *elmts _AND_
225 FOR_EACH_LIST_ELMT (e, elmts)
226 PrintCElmtPrint (src, td, parent, elmts, e, varName);
227 } PrintCBerElmtsEncodeCode */
232 * Prints code for printing a CHOICE element
236 PrintCChoiceElmtPrint
PARAMS ((src
, td
, parent
, elmts
, e
, varName
),
240 NamedTypeList
*elmts _AND_
245 char elmtVarRef
[MAX_VAR_REF
];
249 ctri
= e
->type
->cTypeRefInfo
;
252 /* build ref to the elmt */
253 MakeVarPtrRef (genPrintCRulesG
, td
, parent
, e
->type
, varName
, elmtVarRef
);
255 if (e
->fieldName
!= NULL
)
257 fprintf (src
," fprintf (f,\"%s \");\n", e
->fieldName
);
258 fprintf (src
," %s (f, %s, indent + stdIndentG);\n", e
->type
->cTypeRefInfo
->printRoutineName
, elmtVarRef
);
262 fprintf (src
," %s (f, %s, indent + stdIndentG);\n", e
->type
->cTypeRefInfo
->printRoutineName
, elmtVarRef
);
265 } /* PrintCChoiceElmtPrint */
268 * Prints code for printing an elmt of a SEQ or SET
270 * Does funny things to print commas correctly
271 * eg for the following type
274 * A, --> print A ",\n"
276 * C OPTIONAL, C ",\n" if C present
279 * F, F <- nothing after last non-opt
281 * G OPTIONAL, ",\n" G
282 * H OPTIONAL ",\n" H "\n"
287 PrintCElmtPrintWithIndent
PARAMS ((src
, td
, parent
, elmts
, e
, varName
, allOpt
),
291 NamedTypeList
*elmts _AND_
297 char elmtVarRef
[MAX_VAR_REF
];
301 ctri
= e
->type
->cTypeRefInfo
;
303 /* this assumes the elmts->curr == e */
304 inTailOpts
= IsTailOptional (elmts
);
306 /* build ref to the elmt */
307 MakeVarPtrRef (genPrintCRulesG
, td
, parent
, e
->type
, varName
, elmtVarRef
);
309 /* if optional then put in NULL check */
310 if (e
->type
->optional
|| (e
->type
->defaultVal
!= NULL
))
311 fprintf (src
, " if (%s (%s))\n {\n", ctri
->optTestRoutineName
, elmtVarRef
);
315 if (e
!= FIRST_LIST_ELMT (elmts
))
317 fprintf (src
, " if (!nonePrinted)\n");
318 fprintf (src
, " fprintf (f,\",\\n\");\n");
320 fprintf (src
, " nonePrinted = FALSE;\n");
322 else if ((inTailOpts
) && (e
!= FIRST_LIST_ELMT (elmts
)))
323 fprintf (src
, " fprintf (f,\",\\n\");\n");
325 fprintf (src
," Indent (f, indent + stdIndentG);\n");
327 if (e
->fieldName
!= NULL
)
328 fprintf (src
," fprintf (f,\"%s \");\n", e
->fieldName
);
330 fprintf (src
," %s (f, %s, indent + stdIndentG);\n", e
->type
->cTypeRefInfo
->printRoutineName
, elmtVarRef
);
332 if ((e
!= LAST_LIST_ELMT (elmts
)) &&
334 (!NextIsTailOptional (elmts
)))
335 fprintf (src
," fprintf (f, \",\\n\");\n");
338 /* write closing brkt for NULL check for optional elmts */
339 if (e
->type
->optional
|| (e
->type
->defaultVal
!= NULL
))
340 fprintf (src
, " }\n");
342 if (e
== LAST_LIST_ELMT (elmts
))
343 fprintf (src
," fprintf (f,\"\\n\");\n");
345 } /* PrintCElmtPrintWithIndent */
349 PrintCChoicePrintRoutine
PARAMS ((src
, hdr
, r
, mods
, m
, td
),
353 ModuleList
*mods _AND_
359 PrintCPrintPrototype (hdr
,td
);
361 PrintCPrintDeclaration (src
, td
);
363 PrintCPrintLocals (src
,td
);
364 fprintf (src
," switch (%s->%s)\n", valueArgNameG
, td
->type
->cTypeRefInfo
->choiceIdEnumFieldName
);
365 fprintf (src
," {\n");
367 FOR_EACH_LIST_ELMT (e
, td
->type
->basicType
->a
.choice
)
369 fprintf (src
," case %s:\n",e
->type
->cTypeRefInfo
->choiceIdSymbol
);
371 PrintCChoiceElmtPrint (src
, td
, td
->type
, td
->type
->basicType
->a
.choice
, e
, valueArgNameG
);
372 fprintf (src
," break;\n\n");
374 fprintf (src
," }\n");
375 /* fprintf (src," fprintf (f,\"\\n\");\n"); */
377 fprintf (src
,"} /* %s */\n\n", td
->cTypeDefInfo
->printRoutineName
);
379 } /* PrintCChoicePrintRoutine */
384 PrintCSetPrintRoutine
PARAMS ((src
, hdr
, r
, mods
, m
, td
),
388 ModuleList
*mods _AND_
395 PrintCPrintPrototype (hdr
,td
);
397 PrintCPrintDeclaration (src
, td
);
399 PrintCPrintLocals (src
,td
);
401 allOpt
= AllElmtsOptional (td
->type
->basicType
->a
.set
);
403 * print extra local variable so commas are handled correctly
404 * when all elements are optional
407 fprintf (src
," int nonePrinted = TRUE;\n\n");
409 fprintf (src
," if (%s == NULL)\n", valueArgNameG
);
410 fprintf (src
," return;\n\n");
412 fprintf (src
," fprintf (f,\"{ -- SET --\\n\");\n\n");
415 FOR_EACH_LIST_ELMT (e
, td
->type
->basicType
->a
.set
)
417 PrintCElmtPrintWithIndent (src
, td
, td
->type
, td
->type
->basicType
->a
.set
, e
, valueArgNameG
, allOpt
);
419 fprintf (src
," Indent (f, indent);\n");
420 fprintf (src
," fprintf (f,\"}\");\n");
422 fprintf (src
,"} /* %s */\n\n", td
->cTypeDefInfo
->printRoutineName
);
424 } /* PrintCSetPrintRoutine */
429 PrintCSeqPrintRoutine
PARAMS ((src
, hdr
, r
, mods
, m
, td
),
433 ModuleList
*mods _AND_
440 PrintCPrintPrototype (hdr
,td
);
442 PrintCPrintDeclaration (src
, td
);
444 PrintCPrintLocals (src
,td
);
446 allOpt
= AllElmtsOptional (td
->type
->basicType
->a
.set
);
448 * print extra local variable so commas are handled correctly
449 * when all elements are optional
452 fprintf (src
," int nonePrinted = TRUE;\n\n");
454 fprintf (src
," if (%s == NULL)\n", valueArgNameG
);
455 fprintf (src
," return;\n\n");
457 fprintf (src
," fprintf (f,\"{ -- SEQUENCE --\\n\");\n\n");
459 FOR_EACH_LIST_ELMT (e
, td
->type
->basicType
->a
.sequence
)
461 PrintCElmtPrintWithIndent (src
, td
, td
->type
, td
->type
->basicType
->a
.sequence
, e
, valueArgNameG
, allOpt
);
463 fprintf (src
," Indent (f, indent);\n");
464 fprintf (src
," fprintf (f,\"}\");\n");
466 fprintf (src
,"} /* %s */\n\n", td
->cTypeDefInfo
->printRoutineName
);
467 } /* PrintCSeqPrintRoutine */
472 PrintCSetOfPrintRoutine
PARAMS ((src
, hdr
, r
, mods
, m
, td
),
476 ModuleList
*mods _AND_
482 PrintCPrintPrototype (hdr
,td
);
484 PrintCPrintDeclaration (src
, td
);
486 PrintCPrintLocals (src
,td
);
488 fprintf (src
," %s *tmp;\n", td
->type
->basicType
->a
.setOf
->cTypeRefInfo
->cTypeName
);
490 fprintf (src
," if (%s == NULL)\n", valueArgNameG
);
491 fprintf (src
," return;\n");
493 fprintf (src
," fprintf (f,\"{ -- SET OF -- \\n\");\n");
495 fprintf (src
," FOR_EACH_LIST_ELMT (tmp, %s)\n", valueArgNameG
);
496 fprintf (src
," {\n");
497 fprintf (src
," Indent (f, indent+ stdIndentG);\n");
498 fprintf (src
," %s (f, tmp, indent + stdIndentG);\n", td
->type
->basicType
->a
.setOf
->cTypeRefInfo
->printRoutineName
);
499 fprintf (src
," if (tmp != (%s*)LAST_LIST_ELMT (%s))\n", td
->type
->basicType
->a
.setOf
->cTypeRefInfo
->cTypeName
, valueArgNameG
);
500 fprintf (src
," fprintf (f,\",\\n\");\n");
501 fprintf (src
," }\n");
502 fprintf (src
," fprintf (f,\"\\n\");\n");
503 fprintf (src
," Indent (f, indent);\n");
504 fprintf (src
," fprintf (f,\"}\");\n");
506 fprintf (src
,"} /* %s */\n\n", td
->cTypeDefInfo
->printRoutineName
);
508 } /* PrintCSetOfPrintRoutine */
511 PrintCSeqOfPrintRoutine
PARAMS ((src
, hdr
, r
, mods
, m
, td
),
515 ModuleList
*mods _AND_
521 PrintCPrintPrototype (hdr
,td
);
523 PrintCPrintDeclaration (src
, td
);
525 PrintCPrintLocals (src
,td
);
527 fprintf (src
," %s *tmp;\n", td
->type
->basicType
->a
.setOf
->cTypeRefInfo
->cTypeName
);
529 fprintf (src
," if (%s == NULL)\n", valueArgNameG
);
530 fprintf (src
," return;\n");
532 fprintf (src
," fprintf (f,\"{ -- SEQUENCE OF -- \\n\");\n");
534 fprintf (src
," FOR_EACH_LIST_ELMT (tmp, %s)\n", valueArgNameG
);
535 fprintf (src
," {\n");
536 fprintf (src
," Indent (f, indent+ stdIndentG);\n");
537 fprintf (src
," %s (f, tmp, indent + stdIndentG);\n", td
->type
->basicType
->a
.setOf
->cTypeRefInfo
->printRoutineName
);
538 fprintf (src
," if (tmp != (%s*)LAST_LIST_ELMT (%s))\n", td
->type
->basicType
->a
.setOf
->cTypeRefInfo
->cTypeName
, valueArgNameG
);
539 fprintf (src
," fprintf (f,\",\\n\");\n");
540 fprintf (src
," }\n");
541 fprintf (src
," fprintf (f,\"\\n\");\n");
542 fprintf (src
," Indent (f, indent);\n");
543 fprintf (src
," fprintf (f,\"}\");\n");
545 fprintf (src
,"} /* %s */\n\n", td
->cTypeDefInfo
->printRoutineName
);
547 } /* PrintCSeqOfPrintRoutine */