#include <ctype.h>
#include <stdio.h>
#include "asn-incl.h"
#include "define.h"
#include "asn1module.h"
#include "mem.h"
#include "snacc-util.h"
#include "str-util.h"
#include "rules.h"
#include "c++-gen/kwd.h"
#include "types.h"
extern Module *usefulTypeModG;
static DefinedObj *definedNamesG;
void FillIDLTypeDefInfo PROTO ((IDLRules *r, Module *m, TypeDef *td));
static void FillIDLFieldNames PROTO ((IDLRules *r, NamedTypeList *firstSibling));
static void FillIDLTypeRefInfo PROTO ((IDLRules *r, Module *m, TypeDef *td, Type *parent, Type *t));
static void FillIDLStructElmts PROTO ((IDLRules *r, Module *m, TypeDef *td, Type *parent, NamedTypeList *t));
static void FillIDLChoiceElmts PROTO ((IDLRules *r, Module *m, TypeDef *td, Type *parent, NamedTypeList *first));
static int IsIDLPtr PROTO ((IDLRules *r, TypeDef *td, Type *parent, Type *t));
void FillIDLTDIDefaults PROTO ((IDLRules *r, IDLTDI *ctdi, TypeDef *td));
void
FillIDLTypeInfo PARAMS ((r, modList),
IDLRules *r _AND_
ModuleList *modList)
{
TypeDef *td;
Module *m;
definedNamesG = NULL;
if (usefulTypeModG != NULL)
{
FOR_EACH_LIST_ELMT (td, usefulTypeModG->typeDefs)
FillIDLTypeDefInfo (r, usefulTypeModG, td);
}
FOR_EACH_LIST_ELMT (m, modList)
{
FOR_EACH_LIST_ELMT (td, m->typeDefs)
FillIDLTypeDefInfo (r, m, td);
}
if (usefulTypeModG != NULL)
{
FOR_EACH_LIST_ELMT (td, usefulTypeModG->typeDefs)
FillIDLTypeRefInfo (r, usefulTypeModG, td, NULL, td->type);
}
FOR_EACH_LIST_ELMT (m, modList)
{
FOR_EACH_LIST_ELMT (td, m->typeDefs)
FillIDLTypeRefInfo (r, m, td, NULL, td->type);
}
FreeDefinedObjs (&definedNamesG);
}
void
FillIDLTypeDefInfo PARAMS ((r, m, td),
IDLRules *r _AND_
Module *m _AND_
TypeDef *td)
{
int digit;
int len;
char *tmpName;
IDLTDI *idltdi;
if (td->idlTypeDefInfo != NULL)
return;
idltdi = MT (IDLTDI);
td->idlTypeDefInfo = idltdi;
FillIDLTDIDefaults (r, idltdi, td);
if ((td->type->basicType->choiceId == BASICTYPE_LOCALTYPEREF) ||
(td->type->basicType->choiceId == BASICTYPE_IMPORTTYPEREF))
{
FillIDLTypeDefInfo (r, td->type->basicType->a.localTypeRef->module, td->type->basicType->a.localTypeRef->link);
tmpName = idltdi->typeName;
*idltdi = *td->type->basicType->a.localTypeRef->link->idlTypeDefInfo;
idltdi->typeName = tmpName;
}
}
static void
FillIDLTypeRefInfo PARAMS ((r, m, td, parent, t),
IDLRules *r _AND_
Module *m _AND_
TypeDef *td _AND_
Type *parent _AND_
Type *t)
{
IDLTRI *idltri;
IDLTDI *tmpidltdi;
ValueDef *namedElmt;
CNamedElmt *cne;
CNamedElmt **cneHndl;
char *elmtName;
char *listName;
char *choiceName;
char *unionName;
Type *tmpT;
int len, digit;
enum BasicTypeChoiceId
basicTypeId;
if (t->idlTypeRefInfo == NULL)
{
idltri = MT (IDLTRI);
t->idlTypeRefInfo = idltri;
}
else
idltri = t->idlTypeRefInfo;
basicTypeId = t->basicType->choiceId;
tmpidltdi = &r->typeConvTbl[basicTypeId];
idltri->isEnc = tmpidltdi->isEnc;
idltri->typeName = tmpidltdi->typeName;
idltri->optTestRoutineName = tmpidltdi->optTestRoutineName;
if ((basicTypeId == BASICTYPE_INTEGER || basicTypeId == BASICTYPE_ENUMERATED || basicTypeId == BASICTYPE_BITSTRING) && !(LIST_EMPTY (t->basicType->a.integer)))
{
idltri->namedElmts = AsnListNew (sizeof (void *));
FOR_EACH_LIST_ELMT (namedElmt, t->basicType->a.integer)
{
cneHndl = (CNamedElmt **)AsnListAppend (idltri->namedElmts);
cne = *cneHndl = MT (CNamedElmt);
elmtName = Asn1ValueName2CValueName (namedElmt->definedName);
#if 0
if (basicTypeId == BASICTYPE_BITSTRING)
#endif
{
len = strlen (elmtName);
cne->name = Malloc (len + 1 + r->maxDigitsToAppend);
strcpy (cne->name, elmtName);
}
#if 0
else
{
len = strlen (idltri->typeName) + 7 + strlen (elmtName);
cne->name = Malloc (len + 1 + r->maxDigitsToAppend);
strcpy (cne->name, idltri->typeName);
strcat (cne->name, "Choice_");
strcat (cne->name, elmtName);
}
#endif
Free (elmtName);
if (namedElmt->value->basicValue->choiceId == BASICVALUE_INTEGER)
cne->value = namedElmt->value->basicValue->a.integer;
else
{
fprintf (stderr, "Warning: unlinked defined value. Using -9999999\n");
cne->value = -9999999;
}
if (r->capitalizeNamedElmts)
Str2UCase (cne->name, len);
MakeCxxStrUnique (definedNamesG, cne->name, r->maxDigitsToAppend, 1);
DefineObj (&definedNamesG, cne->name);
}
}
switch (basicTypeId)
{
case BASICTYPE_BOOLEAN:
case BASICTYPE_INTEGER:
case BASICTYPE_BITSTRING:
case BASICTYPE_OCTETSTRING:
case BASICTYPE_NULL:
case BASICTYPE_OID:
case BASICTYPE_REAL:
case BASICTYPE_ENUMERATED:
break;
case BASICTYPE_SEQUENCEOF:
case BASICTYPE_SETOF:
FillIDLTypeRefInfo (r, m, td, t, t->basicType->a.setOf);
break;
case BASICTYPE_IMPORTTYPEREF:
case BASICTYPE_LOCALTYPEREF:
if (t->basicType->a.localTypeRef->link != NULL)
{
tmpidltdi= t->basicType->a.localTypeRef->link->idlTypeDefInfo;
idltri->typeName = tmpidltdi->typeName;
idltri->isEnc = tmpidltdi->isEnc;
idltri->optTestRoutineName = tmpidltdi->optTestRoutineName;
}
break;
case BASICTYPE_ANYDEFINEDBY:
break;
case BASICTYPE_ANY:
#if 0
PrintErrLoc (m->asn1SrcFileName, t->lineNo);
fprintf (stderr, "Warning - generated code for the \"ANY\" type in type \"%s\" will need modification by YOU.", td->definedName);
fprintf (stderr, " The source files will have a \"/* ANY - Fix Me! */\" comment before related code.\n\n");
#endif
break;
case BASICTYPE_CHOICE:
FillIDLFieldNames (r, t->basicType->a.choice);
FillIDLChoiceElmts (r, m, td, t, t->basicType->a.choice);
break;
case BASICTYPE_SET:
case BASICTYPE_SEQUENCE:
FillIDLStructElmts (r, m, td, t, t->basicType->a.set);
FillIDLFieldNames (r, t->basicType->a.set);
break;
case BASICTYPE_COMPONENTSOF:
case BASICTYPE_SELECTION:
fprintf (stderr, "Compiler error - COMPONENTS OF or SELECTION type slipped through normalizing phase.\n");
break;
case BASICTYPE_UNKNOWN:
case BASICTYPE_MACRODEF:
case BASICTYPE_MACROTYPE:
break;
}
idltri->isPtr = IsIDLPtr (r, td, parent, t);
}
static void
FillIDLStructElmts PARAMS ((r, m, td, parent, elmts),
IDLRules *r _AND_
Module *m _AND_
TypeDef *td _AND_
Type *parent _AND_
NamedTypeList *elmts)
{
NamedType *et;
FOR_EACH_LIST_ELMT (et, elmts)
{
FillIDLTypeRefInfo (r, m, td, parent, et->type);
}
}
static void
FillIDLChoiceElmts PARAMS ((r, m, td, parent, elmts),
IDLRules *r _AND_
Module *m _AND_
TypeDef *td _AND_
Type *parent _AND_
NamedTypeList *elmts)
{
NamedType *et;
int idCount = 0;
IDLTRI *idltri;
int len;
FOR_EACH_LIST_ELMT (et, elmts)
FillIDLTypeRefInfo (r, m, td, parent, et->type);
FOR_EACH_LIST_ELMT (et, elmts)
{
idltri = et->type->idlTypeRefInfo;
if (idltri == NULL)
continue;
idltri->choiceIdValue = idCount++;
len = strlen (td->idlTypeDefInfo->typeName) + strlen (idltri->fieldName);
idltri->choiceIdSymbol = Malloc (len + 6 + 1);
strcpy (idltri->choiceIdSymbol, td->idlTypeDefInfo->typeName);
strcat (idltri->choiceIdSymbol, "Choice_");
strcat (idltri->choiceIdSymbol, idltri->fieldName);
if (r->capitalizeNamedElmts)
Str2UCase (idltri->choiceIdSymbol, len);
Str2LCase (idltri->choiceIdSymbol, 1);
}
}
static void
FillIDLFieldNames PARAMS ((r, elmts),
IDLRules *r _AND_
NamedTypeList *elmts)
{
NamedType *et;
IDLTRI *idltri;
DefinedObj *fieldNames;
int len, num, digit, i, tmpLen;
char *tmpName;
char *asn1FieldName;
char *cFieldName;
fieldNames = NewObjList();
FOR_EACH_LIST_ELMT (et, elmts)
{
idltri = et->type->idlTypeRefInfo;
if (idltri == NULL)
{
idltri = MT (IDLTRI);
et->type->idlTypeRefInfo = idltri;
}
if (et->fieldName != NULL)
{
asn1FieldName = et->fieldName;
tmpName = Asn1FieldName2CFieldName (asn1FieldName);
idltri->fieldName = Malloc (strlen (tmpName) + 1 + r->maxDigitsToAppend);
strcpy (idltri->fieldName, tmpName);
Free (tmpName);
MakeCxxStrUnique (fieldNames, idltri->fieldName, r->maxDigitsToAppend, 1);
DefineObj (&fieldNames, idltri->fieldName);
}
}
FOR_EACH_LIST_ELMT (et, elmts)
{
idltri = et->type->idlTypeRefInfo;
if (idltri->fieldName == NULL)
{
if ((et->type->basicType->choiceId == BASICTYPE_LOCALTYPEREF) ||
(et->type->basicType->choiceId == BASICTYPE_IMPORTTYPEREF))
{
tmpName = et->type->basicType->a.localTypeRef->link->idlTypeDefInfo->typeName;
tmpName = Asn1TypeName2CTypeName (tmpName);
cFieldName = Malloc (strlen (tmpName) + r->maxDigitsToAppend +1);
strcpy (cFieldName, tmpName);
Free (tmpName);
if (isupper (cFieldName[0]))
cFieldName[0] = tolower (cFieldName[0]);
}
else
{
tmpName = r->typeConvTbl[et->type->basicType->choiceId].defaultFieldName;
cFieldName = Malloc (strlen (tmpName) + r->maxDigitsToAppend +1);
strcpy (cFieldName, tmpName);
if (isupper (cFieldName[0]))
cFieldName[0] = tolower (cFieldName[0]);
}
len = strlen (cFieldName);
MakeCxxStrUnique (fieldNames, cFieldName, r->maxDigitsToAppend, 1);
DefineObj (&fieldNames, cFieldName);
idltri->fieldName = cFieldName;
}
}
FreeDefinedObjs (&fieldNames);
}
static int
IsIDLPtr PARAMS ((r, td, parent, t),
IDLRules *r _AND_
TypeDef *td _AND_
Type *parent _AND_
Type *t)
{
IDLTDI *idltdi;
int retVal = FALSE;
if ((t->basicType->choiceId == BASICTYPE_LOCALTYPEREF) ||
(t->basicType->choiceId == BASICTYPE_IMPORTTYPEREF))
{
idltdi = t->basicType->a.localTypeRef->link->idlTypeDefInfo;
}
else
idltdi = &r->typeConvTbl[GetBuiltinType (t)];
if ((parent == NULL) && (idltdi->isPtrForTypeDef))
retVal = TRUE;
else if ((parent != NULL) &&
((parent->basicType->choiceId == BASICTYPE_SET) ||
(parent->basicType->choiceId == BASICTYPE_SEQUENCE)) &&
(idltdi->isPtrInSetAndSeq))
retVal = TRUE;
else if ((parent != NULL) &&
((parent->basicType->choiceId == BASICTYPE_SETOF) ||
(parent->basicType->choiceId == BASICTYPE_SEQUENCEOF)) &&
(idltdi->isPtrInList))
retVal = TRUE;
else if ((parent != NULL) &&
(parent->basicType->choiceId == BASICTYPE_CHOICE) &&
(idltdi->isPtrInChoice))
retVal = TRUE;
else if (((t->optional) || (t->defaultVal != NULL)) && (idltdi->isPtrForOpt))
retVal = TRUE;
return retVal;
}
void
FillIDLTDIDefaults PARAMS ((r, idltdi, td),
IDLRules *r _AND_
IDLTDI *idltdi _AND_
TypeDef *td)
{
IDLTDI *tblidltdi;
int typeIndex;
char *tmpName;
typeIndex = GetBuiltinType (td->type);
if (typeIndex < 0)
return;
tblidltdi = &r->typeConvTbl[typeIndex];
memcpy (idltdi, tblidltdi, sizeof (IDLTDI));
tmpName = Asn1TypeName2CTypeName (td->definedName);
idltdi->typeName = Malloc (strlen (tmpName) + 2 + r->maxDigitsToAppend +1);
strcpy (idltdi->typeName, tmpName);
if (tblidltdi->asn1TypeId != BASICTYPE_CHOICE)
strcat (idltdi->typeName, "_T");
Free (tmpName);
MakeCxxStrUnique (definedNamesG, idltdi->typeName, r->maxDigitsToAppend, 1);
DefineObj (&definedNamesG, idltdi->typeName);
}