#include <stdio.h>
#include "asn-incl.h"
#include "mem.h"
#include "asn1module.h"
#include "rules.h"
#include "define.h"
#include "str-util.h"
#include "gen-vals.h"
#include "lib-types.h"
#include "gen-any.h"
int anyEnumValG = 0;
void PrintCAnyEnum PROTO ((FILE *hdr, Module *m, CRules *r));
void PrintCAnyHashInitRoutine PROTO ((FILE *src, FILE *hdr, ModuleList *mods, Module *m, CRules *r));
void
PrintCAnyCode PARAMS ((src, hdr, r, mods, m),
FILE *src _AND_
FILE *hdr _AND_
CRules *r _AND_
ModuleList *mods _AND_
Module *m)
{
if (!m->hasAnys)
return;
PrintCAnyEnum (hdr, m, r);
PrintCAnyHashInitRoutine (src, hdr, mods, m, r);
}
void
PrintCAnyEnum PARAMS ((hdr, m, r),
FILE *hdr _AND_
Module *m _AND_
CRules *r)
{
TypeDef *td;
AnyRef *ar;
AnyRefList *arl;
int i;
int firstPrinted = TRUE;
char *modName;
modName = Asn1TypeName2CTypeName (m->modId->name);
fprintf (hdr,"typedef enum %sAnyId\n", modName);
fprintf (hdr,"{\n");
for (i = BASICTYPE_BOOLEAN; i < BASICTYPE_MACRODEF; i++)
{
arl = LIBTYPE_GET_ANY_REFS (i);
if (arl != NULL)
{
FOR_EACH_LIST_ELMT (ar, arl)
{
if (!firstPrinted)
fprintf (hdr,",\n");
fprintf (hdr," %s = %d", ar->anyIdName, anyEnumValG++);
firstPrinted = FALSE;
}
}
}
FOR_EACH_LIST_ELMT (td, m->typeDefs)
{
if (td->anyRefs != NULL)
{
FOR_EACH_LIST_ELMT (ar, td->anyRefs)
{
if (!firstPrinted)
fprintf (hdr,",\n");
fprintf (hdr," %s = %d", ar->anyIdName, anyEnumValG++);
firstPrinted = FALSE;
}
}
}
if (firstPrinted)
fprintf (hdr,"/* NO INTEGER or OBJECT IDENTIFIER to ANY type relationships were defined (via MACROs or other mechanism) */\n???\n");
fprintf (hdr,"} %sAnyId;\n\n\n", modName);
Free (modName);
}
void
PrintCAnyHashInitRoutine PARAMS ((src, hdr, mods, m, r),
FILE *src _AND_
FILE *hdr _AND_
ModuleList *mods _AND_
Module *m _AND_
CRules *r)
{
TypeDef *td;
AnyRef *ar;
AnyRefList *arl;
char *modName;
CTDI *ctdi;
int i,j;
enum BasicTypeChoiceId typeId;
char *encRoutineName;
char *decRoutineName;
char *freeRoutineName;
char *printRoutineName;
int installedSomeHashes = FALSE;
modName = Asn1TypeName2CTypeName (m->modId->name);
fprintf (hdr,"void InitAny%s();\n\n", modName);
fprintf (src,"void\nInitAny%s()\n", modName);
fprintf (src,"{\n");
i = 0;
for (j = BASICTYPE_BOOLEAN; j < BASICTYPE_MACRODEF; j++)
{
arl = LIBTYPE_GET_ANY_REFS (j);
if (arl != NULL)
{
FOR_EACH_LIST_ELMT (ar, arl)
{
installedSomeHashes = TRUE;
if (ar->id->choiceId == OIDORINT_OID)
{
fprintf (src," %s oid%d =", r->typeConvTbl[BASICTYPE_OID].cTypeName, i++);
PrintCOidValue (src, r, ar->id->a.oid);
fprintf (src,";\n");
}
}
}
}
FOR_EACH_LIST_ELMT (td, m->typeDefs)
{
if (td->anyRefs != NULL)
{
ctdi = td->cTypeDefInfo;
FOR_EACH_LIST_ELMT (ar, td->anyRefs)
{
installedSomeHashes = TRUE;
if (ar->id->choiceId == OIDORINT_OID)
{
fprintf (src," %s oid%d =", r->typeConvTbl[BASICTYPE_OID].cTypeName, i++);
PrintCOidValue (src, r, ar->id->a.oid);
fprintf (src,";\n");
}
}
}
}
fprintf (src,"\n\n");
i = 0;
for (j = BASICTYPE_BOOLEAN; j < BASICTYPE_MACRODEF; j++)
{
arl = LIBTYPE_GET_ANY_REFS (j);
if (arl != NULL)
{
FOR_EACH_LIST_ELMT (ar, arl)
{
encRoutineName = r->typeConvTbl[j].encodeRoutineName;
decRoutineName = r->typeConvTbl[j].decodeRoutineName;
printRoutineName = r->typeConvTbl[j].printRoutineName;
switch (j)
{
case BASICTYPE_BOOLEAN:
case BASICTYPE_INTEGER:
case BASICTYPE_NULL:
case BASICTYPE_REAL:
case BASICTYPE_ENUMERATED:
freeRoutineName = "NULL";
break;
default:
freeRoutineName = r->typeConvTbl[j].freeRoutineName;
}
if (ar->id->choiceId == OIDORINT_OID)
fprintf (src," InstallAnyByOid (%s, &oid%d, sizeof (%s), (EncodeFcn) B%s, (DecodeFcn)B%s, (FreeFcn)%s, (PrintFcn)%s);\n\n", ar->anyIdName, i++, r->typeConvTbl[j].cTypeName, encRoutineName, decRoutineName, freeRoutineName, printRoutineName);
else
fprintf (src," InstallAnyByInt (%s, %d, sizeof (%s), (EncodeFcn) B%s, (DecodeFcn)B%s, (FreeFcn)%s, (PrintFcn)%s);\n\n", ar->anyIdName, ar->id->a.intId, r->typeConvTbl[j].cTypeName, encRoutineName, decRoutineName, freeRoutineName, printRoutineName);
}
}
}
FOR_EACH_LIST_ELMT (td, m->typeDefs)
{
if (td->anyRefs != NULL)
{
ctdi = td->cTypeDefInfo;
FOR_EACH_LIST_ELMT (ar, td->anyRefs)
{
typeId = GetBuiltinType (td->type);
encRoutineName = ctdi->encodeRoutineName;
decRoutineName = ctdi->decodeRoutineName;
printRoutineName = ctdi->printRoutineName;
switch (typeId)
{
case BASICTYPE_BOOLEAN:
case BASICTYPE_INTEGER:
case BASICTYPE_NULL:
case BASICTYPE_REAL:
case BASICTYPE_ENUMERATED:
freeRoutineName = "NULL";
break;
default:
freeRoutineName = ctdi->freeRoutineName;
}
if (ar->id->choiceId == OIDORINT_OID)
fprintf (src," InstallAnyByOid (%s, &oid%d, sizeof (%s), (EncodeFcn) B%s, (DecodeFcn)B%s, (FreeFcn)%s, (PrintFcn)%s);\n\n", ar->anyIdName, i++, ctdi->cTypeName, encRoutineName, decRoutineName, freeRoutineName, printRoutineName);
else
fprintf (src," InstallAnyByInt (%s, %d, sizeof (%s), (EncodeFcn) B%s, (DecodeFcn)B%s, (FreeFcn)%s, (PrintFcn)%s);\n\n", ar->anyIdName, ar->id->a.intId, ctdi->cTypeName, encRoutineName, decRoutineName, freeRoutineName, printRoutineName);
}
}
}
if (!installedSomeHashes)
{
fprintf (src," /* Since no INTEGER/OID to ANY type relations were defined\n");
fprintf (src," * (usually done via MACROs) you must manually do the code\n");
fprintf (src," * to fill the hash tbl.\n");
fprintf (src," * if the ids are INTEGER use the following:\n");
fprintf (src," * InstallAnyByInt (??_ANY_ID, intVal, sizeof (Foo), (EncodeFcn) BEncFoo, (DecodeFcn)BDecFoo, (FreeFcn)FreeFoo, (PrintFcn)PrintFoo);\n");
fprintf (src," * if the ids are OBJECT IDENTIFIERs use the following:\n");
fprintf (src," * InstallAnyByOid (??_ANY_ID, oidVal, sizeof (Foo), (EncodeFcn) BEncFoo, (DecodeFcn)BDecFoo, (FreeFcn)FreeFoo, (PrintFcn)PrintFoo);\n");
fprintf (src," * put the ??_ANY_IDs in the AnyId enum.\n\n");
fprintf (src," * For example if you have some thing like\n");
fprintf (src," * T1 ::= SEQUENCE { id INTEGER, ANY DEFINED BY id }\n");
fprintf (src," * and the id 1 maps to the type BOOLEAN use the following:\n");
fprintf (src," * InstallAnyByInt (SOMEBOOL_ANY_ID, 1, sizeof (AsnBool), (EncodeFcn) BEncAsnBool, (DecodeFcn)BDecAsnBool, (FreeFcn)NULL, (PrintFcn)PrintAsnBool);;\n");
fprintf (src," */\n ???????\n");
}
fprintf (src,"} /* InitAny%s */\n\n\n", modName);
Free (modName);
}