diff options
author | Andrew Bartlett <abartlet@samba.org> | 2005-08-09 03:04:47 +0000 |
---|---|---|
committer | Gerald (Jerry) Carter <jerry@samba.org> | 2007-10-10 13:31:33 -0500 |
commit | c0e8144c5d1e402b36ebe04b843eba62e7ab9958 (patch) | |
tree | 1b885ceee1a88e8cb2822051690b023c8f8acb78 /source4/heimdal/lib/asn1/gen_copy.c | |
parent | 4b93e377cd9809199487e20fa53d8a2c98ad32ea (diff) | |
download | samba-c0e8144c5d1e402b36ebe04b843eba62e7ab9958.tar.gz samba-c0e8144c5d1e402b36ebe04b843eba62e7ab9958.tar.bz2 samba-c0e8144c5d1e402b36ebe04b843eba62e7ab9958.zip |
r9221: Try to merge Heimdal across from lorikeet-heimdal to samba4.
This is my first attempt at this, so there may be a few rough edges.
Andrew Bartlett
(This used to be commit 9a1d2f2fec67930975da856a2d365345cec46216)
Diffstat (limited to 'source4/heimdal/lib/asn1/gen_copy.c')
-rw-r--r-- | source4/heimdal/lib/asn1/gen_copy.c | 281 |
1 files changed, 185 insertions, 96 deletions
diff --git a/source4/heimdal/lib/asn1/gen_copy.c b/source4/heimdal/lib/asn1/gen_copy.c index a8421fea6a..07b7efba2c 100644 --- a/source4/heimdal/lib/asn1/gen_copy.c +++ b/source4/heimdal/lib/asn1/gen_copy.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2005 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,125 +33,214 @@ #include "gen_locl.h" -RCSID("$Id: gen_copy.c,v 1.15 2005/06/16 20:03:38 lha Exp $"); +RCSID("$Id: gen_copy.c,v 1.16 2005/07/12 06:27:26 lha Exp $"); + +static int used_fail; static void copy_primitive (const char *typename, const char *from, const char *to) { - fprintf (codefile, "if(copy_%s(%s, %s)) return ENOMEM;\n", + fprintf (codefile, "if(copy_%s(%s, %s)) goto fail;\n", typename, from, to); + used_fail++; } static void -copy_type (const char *from, const char *to, const Type *t) +copy_type (const char *from, const char *to, const Type *t, int preserve) { - switch (t->type) { - case TType: + switch (t->type) { + case TType: #if 0 - copy_type (from, to, t->symbol->type); + copy_type (from, to, t->symbol->type, preserve); #endif - fprintf (codefile, "if(copy_%s(%s, %s)) return ENOMEM;\n", - t->symbol->gen_name, from, to); - break; - case TInteger: - case TUInteger: - case TBoolean: - case TEnumerated : - fprintf(codefile, "*(%s) = *(%s);\n", to, from); - break; - case TOctetString: - copy_primitive ("octet_string", from, to); - break; - case TOID: - copy_primitive ("oid", from, to); - break; - case TBitString: { - fprintf(codefile, "*(%s) = *(%s);\n", to, from); - break; - } - case TSequence: { - Member *m; - int tag = -1; - - if (t->members == NULL) - break; + fprintf (codefile, "if(copy_%s(%s, %s)) goto fail;\n", + t->symbol->gen_name, from, to); + used_fail++; + break; + case TInteger: + if (t->range == NULL && t->members == NULL) { + copy_primitive ("heim_integer", from, to); + break; + } + case TBoolean: + case TEnumerated : + fprintf(codefile, "*(%s) = *(%s);\n", to, from); + break; + case TOctetString: + copy_primitive ("octet_string", from, to); + break; + case TBitString: + if (ASN1_TAILQ_EMPTY(t->members)) + copy_primitive ("bit_string", from, to); + else + fprintf(codefile, "*(%s) = *(%s);\n", to, from); + break; + case TSet: + case TSequence: + case TChoice: { + Member *m, *have_ellipsis = NULL; + + if(t->members == NULL) + break; - for (m = t->members; m && tag != m->val; m = m->next) { - char *fn; - char *tn; - - asprintf (&fn, "%s(%s)->%s", - m->optional ? "" : "&", from, m->gen_name); - asprintf (&tn, "%s(%s)->%s", - m->optional ? "" : "&", to, m->gen_name); - if(m->optional){ - fprintf(codefile, "if(%s) {\n", fn); - fprintf(codefile, "%s = malloc(sizeof(*%s));\n", tn, tn); - fprintf(codefile, "if(%s == NULL) return ENOMEM;\n", tn); - } - copy_type (fn, tn, m->type); - if(m->optional){ - fprintf(codefile, "}else\n"); - fprintf(codefile, "%s = NULL;\n", tn); - } - if (tag == -1) - tag = m->val; - free (fn); - free (tn); - } - break; - } - case TSequenceOf: { - char *f; - char *T; - - fprintf (codefile, "if(((%s)->val = " - "malloc((%s)->len * sizeof(*(%s)->val))) == NULL && (%s)->len != 0)\n", - to, from, to, from); - fprintf (codefile, "return ENOMEM;\n"); - fprintf(codefile, - "for((%s)->len = 0; (%s)->len < (%s)->len; (%s)->len++){\n", - to, to, from, to); - asprintf(&f, "&(%s)->val[(%s)->len]", from, to); - asprintf(&T, "&(%s)->val[(%s)->len]", to, to); - copy_type(f, T, t->subtype); - fprintf(codefile, "}\n"); - free(f); - free(T); - break; - } - case TGeneralizedTime: - fprintf(codefile, "*(%s) = *(%s);\n", to, from); - break; - case TGeneralString: - copy_primitive ("general_string", from, to); - break; - case TUTF8String: - copy_primitive ("utf8string", from, to); - break; - case TNull: - break; - case TApplication: - copy_type (from, to, t->subtype); - break; - default : - abort (); - } + if ((t->type == TSequence || t->type == TChoice) && preserve) { + fprintf(codefile, + "{ int ret;\n" + "ret = copy_octet_string(&(%s)->_save, &(%s)->_save);\n" + "if (ret) goto fail;\n" + "}\n", + from, to); + used_fail++; + } + + if(t->type == TChoice) { + fprintf(codefile, "(%s)->element = (%s)->element;\n", to, from); + fprintf(codefile, "switch((%s)->element) {\n", from); + } + + ASN1_TAILQ_FOREACH(m, t->members, members) { + char *fs; + char *ts; + + if (m->ellipsis) { + have_ellipsis = m; + continue; + } + + if(t->type == TChoice) + fprintf(codefile, "case %s:\n", m->label); + + asprintf (&fs, "%s(%s)->%s%s", + m->optional ? "" : "&", from, + t->type == TChoice ? "u." : "", m->gen_name); + if (fs == NULL) + errx(1, "malloc"); + asprintf (&ts, "%s(%s)->%s%s", + m->optional ? "" : "&", to, + t->type == TChoice ? "u." : "", m->gen_name); + if (ts == NULL) + errx(1, "malloc"); + if(m->optional){ + fprintf(codefile, "if(%s) {\n", fs); + fprintf(codefile, "%s = malloc(sizeof(*%s));\n", ts, ts); + fprintf(codefile, "if(%s == NULL) goto fail;\n", ts); + used_fail++; + } + copy_type (fs, ts, m->type, FALSE); + if(m->optional){ + fprintf(codefile, "}else\n"); + fprintf(codefile, "%s = NULL;\n", ts); + } + free (fs); + free (ts); + if(t->type == TChoice) + fprintf(codefile, "break;\n"); + } + if(t->type == TChoice) { + if (have_ellipsis) { + fprintf(codefile, "case %s: {\n" + "int ret;\n" + "ret = copy_octet_string(&(%s)->u.%s, &(%s)->u.%s);\n" + "if (ret) goto fail;\n" + "break;\n" + "}\n", + have_ellipsis->label, + from, have_ellipsis->gen_name, + to, have_ellipsis->gen_name); + used_fail++; + } + fprintf(codefile, "}\n"); + } + break; + } + case TSetOf: + case TSequenceOf: { + char *f; + char *T; + + fprintf (codefile, "if(((%s)->val = " + "malloc((%s)->len * sizeof(*(%s)->val))) == NULL && (%s)->len != 0)\n", + to, from, to, from); + fprintf (codefile, "goto fail;\n"); + used_fail++; + fprintf(codefile, + "for((%s)->len = 0; (%s)->len < (%s)->len; (%s)->len++){\n", + to, to, from, to); + asprintf(&f, "&(%s)->val[(%s)->len]", from, to); + if (f == NULL) + errx(1, "malloc"); + asprintf(&T, "&(%s)->val[(%s)->len]", to, to); + if (T == NULL) + errx(1, "malloc"); + copy_type(f, T, t->subtype, FALSE); + fprintf(codefile, "}\n"); + free(f); + free(T); + break; + } + case TGeneralizedTime: + fprintf(codefile, "*(%s) = *(%s);\n", to, from); + break; + case TGeneralString: + copy_primitive ("general_string", from, to); + break; + case TUTCTime: + fprintf(codefile, "*(%s) = *(%s);\n", to, from); + break; + case TUTF8String: + copy_primitive ("utf8string", from, to); + break; + case TPrintableString: + copy_primitive ("printable_string", from, to); + break; + case TIA5String: + copy_primitive ("ia5_string", from, to); + break; + case TBMPString: + copy_primitive ("bmp_string", from, to); + break; + case TUniversalString: + copy_primitive ("universal_string", from, to); + break; + case TTag: + copy_type (from, to, t->subtype, preserve); + break; + case TOID: + copy_primitive ("oid", from, to); + break; + case TNull: + break; + default : + abort (); + } } void generate_type_copy (const Symbol *s) { + int preserve = preserve_type(s->name) ? TRUE : FALSE; + + used_fail = 0; + fprintf (headerfile, "int copy_%s (const %s *, %s *);\n", s->gen_name, s->gen_name, s->gen_name); fprintf (codefile, "int\n" "copy_%s(const %s *from, %s *to)\n" - "{\n", + "{\n" + "memset(to, 0, sizeof(*to));\n", s->gen_name, s->gen_name, s->gen_name); + copy_type ("from", "to", s->type, preserve); + fprintf (codefile, "return 0;\n"); + + if (used_fail) + fprintf (codefile, "fail:\n" + "free_%s(to);\n" + "return ENOMEM;\n", + s->gen_name); - copy_type ("from", "to", s->type); - fprintf (codefile, "return 0;\n}\n\n"); + fprintf(codefile, + "}\n\n"); } |