|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T f
Length: 12701 (0x319d) Types: TextFile Names: »fr.c«
└─⟦2d1937cfd⟧ Bits:30007241 EUUGD22: P.P 5.0 └─⟦041b9c0f8⟧ »EurOpenD22/isode/pepsy.system-6.0.Z« └─⟦d49939f05⟧ └─⟦6a28ec38e⟧ »pepsy.tar« └─⟦this⟧ »pepsy/fr.c«
/* Copyright 1989 CSIRO Division of Information Technology * May be given away but not sold for profit - See Copyright file for details */ /* * These routines are the driving routines for freeing of the data */ #include <stdio.h> #include "../h/psap.h" #include "pep.h" #include "pepdefs.h" extern tpe *next_tpe(); extern int _pverbose; #define NEXT_TPE(p) p = next_tpe(p) #define CHKTAG(mod, p, pe) ismatch(p, mod, pe->pe_class, pe->pe_id) /* * don't need this fre_f we just generate macros of the form * fre_obj(parm, mod->md_dtab[CONST], mod) */ #if 0 /* * free the data of specified type of the specified module */ fre_f(typ, mod, pe, explicit, len, buf, parm) /*ARGSUSED*/ int typ; /* which type it is */ modtyp *mod; /* Module it is from */ PE pe; int explicit; int *len; char **buf; char **parm; { tpe *p; if (typ < 0 || typ >= mod->md_nentries) ferrd(1, "fre_f:Illegal typ %d\n", typ); p = mod->md_dtab[typ]; if (p->pe_type != PE_START) ferr(1, "fre_f: missing PE_START\n"); if ((pe = fre_obj(parm, p, mod)) == NULLPE) return (NOTOK); return (OK); } #endif /* * free an objects data. Basic algorithm is to walk through it twice * first time freeing all the "children" of the data structure - then * the second time free the structure itself */ fre_obj(parm, p, mod) modtyp *mod; tpe *p; char *parm; { char *malptr = NULL; /* Have we seen a malloc */ if (p->pe_type != PE_START) ferr(1, "fre_obj: missing PE_START\n"); for (p++; p->pe_type != PE_END; NEXT_TPE(p)) { again: switch (p->pe_type) { case MALLOC: malptr = parm; break; case SET_START: case SEQ_START: fre_seq(parm, p, mod); break; case SETOF_START: case SEQOF_START: fre_seqof(parm, p, mod); break; case CHOICE_START: fre_choice(parm, p, mod); break; case OBJECT: case SOBJECT: fre_obj(parm, mod->md_dtab[p->pe_tag], mod); break; case SEXTOBJ: case EXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fr_obj: missing EXTMOD", p, mod); ferr(1, "fr_obj:internal error\n"); } fre_obj(parm, ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; case IMP_OBJ: p++; if (p->pe_type == EXTOBJ || p->pe_type == SEXTOBJ) { fre_obj(parm, ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); } else { if (p->pe_type == SOBJECT) { fre_obj(parm, mod->md_dtab[p->pe_tag], mod); } else fre_obj(parm, mod->md_dtab[p->pe_tag], mod); } break; case INTEGER: case BOOLEAN: case UCODE: break; case ETAG: p++; goto again; default: fre_type(parm, p, mod); break; } } if (malptr) /* If we saw a malloc free item */ free(malptr); } /* * Handle freeing of single type field. All the more general routines * fall back to this so we can put the code to free something just here once * and it will handle all the cases else where */ fre_type(parm, p, mod) char *parm; tpe *p; modtyp *mod; /* Module it is from */ { again: switch (p->pe_type) { case MALLOC: break; case PE_END: case PE_START: case UCODE: break; case DFLT_F: p++; goto again; case ETAG: switch (p->pe_ucode) { default: p++; fre_type(parm, p, mod); } break; case SEQ_START: case SET_START: fre_seq(*(char **) (parm + p->pe_ucode), p, mod); break; case SEQOF_START: case SETOF_START: fre_seqof(*(char **) (parm + p->pe_ucode), p, mod); break; case IMP_OBJ: p++; if (p->pe_type == EXTOBJ || p->pe_type == SEXTOBJ) fre_obj(*(char **) (parm + p->pe_ucode), ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); else if (p->pe_type == SOBJECT) { fre_obj((char *) parm, mod->md_dtab[p->pe_tag], mod); } else fre_obj(*(char **) (parm + p->pe_ucode), mod->md_dtab[p->pe_tag], mod); break; case SOBJECT: fre_obj((char *) parm, mod->md_dtab[p->pe_tag], mod); break; case OBJECT: fre_obj(*(char **) (parm + p->pe_ucode), mod->md_dtab[p->pe_tag], mod); break; case CHOICE_START: fre_choice(*(char **) (parm + p->pe_ucode), p, mod); break; case SEXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fre_type: missing EXTMOD", p, mod); ferr(1, "fre_type:internal error\n"); } fre_obj(parm, ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; case EXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fre_seq: missing EXTMOD", p, mod); ferr(1, "fre_seq:internal error\n"); } fre_obj(*(char **) (parm + p->pe_ucode), ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; case INTEGER: case BOOLEAN: case T_NULL: break; case SCONS_ANY: case SANY: /* These tests of the pointer don't appear necessary from the definition * of encoding and decoding but ISODE generates freeing code that * does these checks and ISODE's ps layer definitely requires it */ if (parm != NULL) pe_free((PE )parm); break; case CONS_ANY: case ANY: if (*(char *)(parm + p->pe_ucode) != NULL) pe_free(*(PE *) (parm + p->pe_ucode)); break; case SOCTETSTRING: if (parm != NULL) qb_free((struct qbuf *)parm); break; case OCTETSTRING: if (*(char *)(parm + p->pe_ucode) != NULL) qb_free(*(struct qbuf **)(parm + p->pe_ucode)); break; case SBITSTRING: if (parm != NULL) pe_free((PE )parm); break; case BITSTRING: if (*(char *)(parm + p->pe_ucode) != NULL) pe_free(*(PE *)(parm + p->pe_ucode)); break; case SOBJID: if (parm != NULL) oid_free((OID )parm); break; case OBJID: if (*(char *)(parm + p->pe_ucode) != NULL) oid_free(*(OID *)(parm + p->pe_ucode)); break; default: dmp_tpe("fre_type: type not implemented", p, mod); ferrd(1, "fre_type: %d not implemented\n", p->pe_type); break; } } /* * free elements of a sequential type. e.g. sequence or set */ fre_seq(parm, p, mod) char *parm; tpe *p; modtyp *mod; /* Module it is from */ { int *popt = NULL; /* Pointer to optional field */ int optcnt = 0; /* Number of optionals bits so far */ char *malptr = NULL; /* Have we seen a malloc */ if (p->pe_type != SEQ_START && p->pe_type != SET_START) ferrd(1, "fre_seq: bad starting item %d\n", p->pe_type); p++; if (p->pe_type == DFLT_B) p++; while (p->pe_type != PE_END) { if (ISDTYPE(p) && (OPTIONAL(p) || DEFAULT(p))) { switch (p->pe_type) { case INTEGER: case BOOLEAN: case T_NULL: if (DEFAULT(p)) { /* ISODE doesn't use bit map for defaults */ if (p[1].pe_type == DFLT_B && same(p, p + 1, parm, mod) || p[-1].pe_type == DFLT_F && same(p, p - 1, parm, mod)) goto next; break; } if (popt == NULL) ferr(1, "fre_seq:illegal table: no bitmap for optionals\n"); if (!TESTBIT(*popt, optcnt++)) goto next; /* Missing so skip */ break; case ETAG: if (!hasdata(parm, p + 1, mod, popt, optcnt)) goto next; break; case IMP_OBJ: if (p[1].pe_type == SOBJECT && parm == NULL || *((char **)(parm + p[1].pe_ucode)) == NULL) goto next; break; case SOBJECT: if (((char *)parm) == NULL) goto next; break; default: if (*((char **)(parm + p->pe_ucode)) == NULL) goto next; break; } } switch (p->pe_type) { case MALLOC: malptr = parm; break; case OPTL: popt = (int *)(parm + p->pe_ucode); break; case ETAG: p++; continue; case UCODE: break; case SET_START: case SEQ_START: fre_seq(*(char **) (parm + p->pe_ucode), p, mod); break; case SETOF_START: case SEQOF_START: fre_seqof(*(char **) (parm + p->pe_ucode), p, mod); break; case IMP_OBJ: p++; if (p->pe_type == EXTOBJ || p->pe_type == SEXTOBJ) fre_obj(*(char **) (parm + p->pe_ucode), ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); else if (p->pe_type == SOBJECT) { fre_obj((char *) parm, mod->md_dtab[p->pe_tag], mod); } else fre_obj(*(char **) (parm + p->pe_ucode), mod->md_dtab[p->pe_tag], mod); break; case SOBJECT: fre_obj((char *) parm, mod->md_dtab[p->pe_tag], mod); break; case OBJECT: fre_obj(*(char **) (parm + p->pe_ucode), mod->md_dtab[p->pe_tag], mod); break; case CHOICE_START: fre_choice(*(char **) (parm + p->pe_ucode), p, mod); break; case SEXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fre_seq: missing EXTMOD", p, mod); ferr(1, "fre_seq:internal error\n"); } fre_obj(parm, ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; case EXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fre_seq: missing EXTMOD", p, mod); ferr(1, "fre_seq:internal error\n"); } fre_obj(*(char **) (parm + p->pe_ucode), ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; default: fre_type(parm, p, mod); break; } next: NEXT_TPE(p); } if (malptr) /* If we saw a malloc free item */ free(malptr); } /* * free all the fields in a SET OF/SEQUENCE OF type structure. We must follow * the linked list until the end */ fre_seqof(parm, p, mod) char *parm; tpe *p; modtyp *mod; /* Module it is from */ { tpe *start; /* first entry in list */ char *oparm; if (p->pe_type != SEQOF_START && p->pe_type != SETOF_START) { dmp_tpe("fre_seqof: illegal field", p, mod); ferr(1, "fre_seqof: First field not xOF_START\n"); } for (start = p; (char *)parm != NULL; p = start) { p++; if (p->pe_type == DFLT_B) p++; while (p->pe_type != PE_END) { switch (p->pe_type) { case ETAG: p++; continue; case UCODE: break; case SEQ_START: case SET_START: fre_seq(*(char **) (parm + p->pe_ucode), p, mod); break; case SEQOF_START: case SETOF_START: fre_seqof(*(char **) (parm + p->pe_ucode), p, mod); break; case IMP_OBJ: p++; if (p->pe_type == EXTOBJ || p->pe_type == SEXTOBJ) fre_obj(*(char **) (parm + p->pe_ucode), ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); else if (p->pe_type == SOBJECT) { fre_obj((char *) parm, mod->md_dtab[p->pe_tag], mod); } else fre_obj(*(char **) (parm + p->pe_ucode), mod->md_dtab[p->pe_tag], mod); break; case SOBJECT: fre_obj(parm, mod->md_dtab[p->pe_tag], mod); break; case OBJECT: fre_obj(*(char **) (parm + p->pe_ucode), mod->md_dtab[p->pe_tag], mod); break; case CHOICE_START: fre_choice(*(char **) (parm + p->pe_ucode), p, mod); break; case SEXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fre_seqof: missing EXTMOD", p, mod); ferr(1, "fre_seqof:internal error\n"); } fre_obj(parm, ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; case EXTOBJ: if (p[1].pe_type != EXTMOD) { dmp_tpe("fre_seqof: missing EXTMOD", p, mod); ferr(1, "fre_seqof:internal error\n"); } fre_obj(*(char **) (parm + p->pe_ucode), ((modtyp *)p[1].pe_ucode)->md_dtab[p->pe_tag], (modtyp *)p[1].pe_ucode); break; default: fre_type(parm, p, mod); break; } NEXT_TPE(p); } oparm = parm; parm = *(char **)(parm + p->pe_ucode); /* Any more ? */ free(oparm); } } /* * free the item of the choice. Use the SCTRL field to determine which item * is present and then call the appropriate routine to free it */ fre_choice(parm, p, mod) char *parm; tpe *p; modtyp *mod; /* Module it is from */ { int cnt; char *malptr = NULL; /* Have we seen a malloc */ if (p->pe_type != CHOICE_START) { dmp_tpe("fre_choice:missing CHOICE_START", p, mod); ferrd(1, "fre_choice:illegal table entry %d\n", p->pe_type); } p++; if (p->pe_type == DFLT_B) p++; if (p->pe_type == MALLOC) { malptr = parm; p++; } if (p->pe_type != SCTRL) { dmp_tpe("fre_choice:missing SCTRL", p, mod); ferr(1, "fre_choice: missing SCTRL information\n"); } cnt = *(int *) (parm + p->pe_ucode); if (_pverbose > 5) printf("cnt is %d\n",cnt); if (cnt != 0) cnt--; if (cnt < 0) { dmp_tpe("fre_choice:offset negative", p, mod); return; } for (p++; p->pe_type != PE_END; NEXT_TPE(p)) { if (ISDTYPE(p)) { if (cnt == 0) { fre_type(parm, p, mod); if (malptr) /* If we saw a malloc free item */ free(malptr); return; } cnt--; } } dmp_tpe("fre_choice: no choice taken", p, mod); }