PIPS
genC.c File Reference
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>
#include "genC.h"
#include "newgen_include.h"
+ Include dependency graph for genC.c:

Go to the source code of this file.

Macros

#define FIELD   "" /**was: "field_" */
 
#define STRUCT   "_newgen_struct_" /**structure names */
 
#define OPTIMIZE_NEWGEN   "OPTIMIZE_NEWGEN"
 
#define IS_TAB(x)   ((x)==Tabulated_bp)
 
#define TYPE(bp)   (bp-Domains-Number_imports-Current_start)
 non user domain must be taken care from outside? More...
 
#define DomainNumberError
 
#define same_size(t)   (sizeof(t)==sizeof(gen_chunk))
 
#define DONT_TOUCH
 

Functions

static int sharp_ifopt (FILE *out)
 Might be used to generate optimized versions (say macros instead of functions). More...
 
static int sharp_else (FILE *out)
 
static int sharp_endif (FILE *out)
 
int gen_size (int domain)
 GEN_SIZE returns the size (in gen_chunks) of an object of type defined by the BP type. More...
 
static string strup (string s)
 returns s duplicated and case-uppered. More...
 
static bool inline_directly (union domain *dp)
 
static string int_type (void)
 bof... More...
 
static string int_type_access_complement (void)
 
static string newgen_type_name (union domain *dp)
 newgen type name for holder. More...
 
static string newgen_argument_type_name (union domain *dp)
 C type name for generated function arguments. More...
 
static string newgen_type_name_close (union domain *dp)
 
static char newgen_access_name (union domain *dp)
 what to add to the field to access a given primitive type, which was typically declared as a gen_chunk. More...
 
static string newgen_kind_label (union domain *dp)
 just to generate comprehensive comments. More...
 
static void generate_make (FILE *header, FILE *code, struct gen_binding *bp, int domain_type, int operator)
 make is bigger, thus I put it in a separate function. More...
 
static void generate_struct_members (FILE *out, struct gen_binding *bp, int domain_type, int operator)
 generate the struct for bp. More...
 
static void generate_union_type_descriptor (FILE *out, struct gen_binding *bp, int domain_type, int operator)
 
static void generate_union_as_string (FILE *header, FILE *code, struct gen_binding *bp, int domain_type, int operator)
 introspection function. More...
 
static void generate_access_members (FILE *out, struct gen_binding *bp, int domain_type, int operator)
 access to members are managed thru macros. More...
 
static void generate_constructed (FILE *header, FILE *code, struct gen_binding *bp, int operator)
 constructed types: + x (and ->...) More...
 
static void generate_not_constructed (FILE *header, FILE *code, struct gen_binding *bp, int domain_type)
 other types (direct * {} []) More...
 
static void generate_arrow (FILE *header, FILE *code, struct gen_binding *bp)
 newgen function (->) specific stuff More...
 
static void generate_safe_definition (FILE *out, struct gen_binding *bp, string file)
 generates a needed type declaration. More...
 
static void generate_domain (FILE *header, FILE *code, struct gen_binding *bp)
 generate the needed stuff for bp. More...
 
static FILE * fopen_suffix (string prefix, string suffix)
 fopen prefix + suffix. More...
 
void gencode (string file)
 generate the code necessary to manipulate every internal non-inlinable type in the Domains table. More...
 

Macro Definition Documentation

◆ DomainNumberError

#define DomainNumberError
Value:
"\"[newgen internal error]\"" \
"\"inconsistent domain number for %s: %%d (expecting %%d)\\n\""

Definition at line 52 of file genC.c.

◆ DONT_TOUCH

#define DONT_TOUCH
Value:
"/**n" \
" * THIS FILE HAS BEEN AUTOMATICALLY GENERATED BY NEWGEN.\n" \
" *\n" \
" * PLEASE DO NOT MODIFY IT.\n" \
" */\n\n"

Definition at line 918 of file genC.c.

◆ FIELD

#define FIELD   "" /**was: "field_" */

Definition at line 41 of file genC.c.

◆ IS_TAB

#define IS_TAB (   x)    ((x)==Tabulated_bp)

Definition at line 46 of file genC.c.

◆ OPTIMIZE_NEWGEN

#define OPTIMIZE_NEWGEN   "OPTIMIZE_NEWGEN"

Definition at line 44 of file genC.c.

◆ same_size

#define same_size (   t)    (sizeof(t)==sizeof(gen_chunk))

Definition at line 117 of file genC.c.

◆ STRUCT

#define STRUCT   "_newgen_struct_" /**structure names */

Definition at line 42 of file genC.c.

◆ TYPE

#define TYPE (   bp)    (bp-Domains-Number_imports-Current_start)

non user domain must be taken care from outside?

#define FIRST_USER_DOMAIN (7)

Definition at line 50 of file genC.c.

Function Documentation

◆ fopen_suffix()

static FILE* fopen_suffix ( string  prefix,
string  suffix 
)
static

fopen prefix + suffix.

Definition at line 905 of file genC.c.

906 {
907  FILE * f;
908  string r = (string) malloc(strlen(prefix)+strlen(suffix)+1);
909  if (r==NULL) fatal("[fopen_suffix] no more memory\n");
910  strcpy(r, prefix);
911  strcat(r, suffix);
912  f = fopen(r, "w");
913  if (f==NULL) fatal("[fopen_suffix] of %s failed\n", r);
914  free(r);
915  return f;
916 }
void * malloc(YYSIZE_T)
void free(void *)
void fatal(char *,...)
char * string
STRING.
Definition: newgen_types.h:39
int f(int off1, int off2, int n, float r[n], float a[n], float b[n])
Definition: offsets.c:15
static const char * prefix

References f(), fatal(), free(), malloc(), and prefix.

Referenced by gencode().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ gen_size()

int gen_size ( int  domain)

GEN_SIZE returns the size (in gen_chunks) of an object of type defined by the BP type.

to avoid a gcc warning

OTREACHED

Definition at line 71 of file genC.c.

72 {
73  struct gen_binding * bp = Domains+domain;
74  int overhead = GEN_HEADER + IS_TABULATED(bp);
75 
76  switch (bp->domain->ba.type)
77  {
78  case BASIS_DT:
79  case ARRAY_DT:
80  case LIST_DT:
81  case SET_DT:
82  return overhead + 1;
83  case CONSTRUCTED_DT:
84  if (bp->domain->co.op == OR_OP)
85  return overhead + 2;
86  else if (bp->domain->co.op == AND_OP)
87  {
88  int size ;
89  struct domainlist * dlp = bp->domain->co.components ;
90  for( size=0 ; dlp != NULL ; dlp=dlp->cdr, size++ );
91  return overhead + size;
92  }
93  else if (bp->domain->co.op == ARROW_OP)
94  return overhead+1;
95  else
96  {
97  fatal("gen_size: unknown constructed domain operator %d\n",
98  bp->domain->co.op);
99  return -1;
100  }
101  default:
102  fatal( "gen_size: Unknown type %s\n", i2a( bp->domain->ba.type )) ;
103  return -1; /* to avoid a gcc warning */
104  /*NOTREACHED*/
105  }
106 }
#define GEN_HEADER
include <sys/stdtypes.h>
Definition: genC.h:45
struct gen_binding Domains[MAX_DOMAIN]
in build.c
Definition: genspec_yacc.c:114
char * i2a(int)
I2A (Integer TO Ascii) yields a string for a given Integer.
Definition: string.c:121
@ ARROW_OP
@ OR_OP
@ AND_OP
@ SET_DT
@ ARRAY_DT
@ LIST_DT
@ BASIS_DT
@ CONSTRUCTED_DT
#define IS_TABULATED(bp)
union domain * domain
enum domain_operator op
struct domainlist * components
struct domain::@7 co
int type
EXTERNAL.
struct domain::@3 ba

References AND_OP, ARRAY_DT, ARROW_OP, domain::ba, BASIS_DT, domain::co, domain::components, CONSTRUCTED_DT, gen_binding::domain, Domains, fatal(), GEN_HEADER, i2a(), IS_TABULATED, LIST_DT, domain::op, OR_OP, SET_DT, gen_binding::size, and domain::type.

Referenced by allocated_memory_obj_in(), compile(), copy_obj_in(), gen_enter_tabulated(), and generate_make().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ gencode()

void gencode ( string  file)

generate the code necessary to manipulate every internal non-inlinable type in the Domains table.

header = fopen_suffix(file, ".h");

first generate protected forward declarations.

then generate actual declarations.

fclose(header);

Definition at line 928 of file genC.c.

929 {
930  // Just a hack to pretend we use these functions
931  void * no_warning = &sharp_ifopt - &sharp_else + &sharp_endif;
932  int i;
933  FILE * header, * code;
934 
935  if (file==NULL)
936  fatal("[gencode] no file name specified (%p)\n", no_warning);
937 
938  if (sizeof(void *)!=sizeof(gen_chunk))
939  fatal("[gencode] newgen fundamental layout hypothesis broken\n");
940 
941  /* header = fopen_suffix(file, ".h"); */
942  header = stdout;
943  code = fopen_suffix(file, ".c");
944 
945  fprintf(header, DONT_TOUCH);
947 
948  for (i=0; i<MAX_DOMAIN; i++) {
949  struct gen_binding * bp = &Domains[i];
950  if (bp->name && !IS_INLINABLE(bp) && !IS_TAB(bp))
951  if (IS_EXTERNAL(bp))
952  fprintf(code, "typedef void * %s;\n", bp->name);
953  }
954 
955  fprintf(code,
956  "\n"
957  "#include <stdio.h>\n"
958  "#include <stdlib.h>\n"
959  "#include <string.h>\n"
960  "#include \"genC.h\"\n"
961  "#include \"%s.h\"\n"
962  "\n",
963  file);
964 
965  /* first generate protected forward declarations.
966  */
967  for (i=0; i<MAX_DOMAIN; i++) {
968  struct gen_binding * bp = &Domains[i];
969  if (bp->name && !IS_INLINABLE(bp) && !IS_TAB(bp))
970  generate_safe_definition(header, bp, file);
971  }
972 
973  /* then generate actual declarations.
974  */
975  for (i=0; i<MAX_DOMAIN; i++) {
976  struct gen_binding * bp = &Domains[i];
977  if (bp->name && !IS_INLINABLE(bp) && !IS_IMPORT(bp) && !IS_TAB(bp))
978  generate_domain(header, code, bp);
979  }
980 
981  /* fclose(header); */
982  fclose(code);
983 }
static int sharp_ifopt(FILE *out)
Might be used to generate optimized versions (say macros instead of functions).
Definition: genC.c:59
#define DONT_TOUCH
Definition: genC.c:918
static int sharp_endif(FILE *out)
Definition: genC.c:65
static void generate_safe_definition(FILE *out, struct gen_binding *bp, string file)
generates a needed type declaration.
Definition: genC.c:661
static int sharp_else(FILE *out)
Definition: genC.c:62
#define IS_TAB(x)
Definition: genC.c:46
static void generate_domain(FILE *header, FILE *code, struct gen_binding *bp)
generate the needed stuff for bp.
Definition: genC.c:711
static FILE * fopen_suffix(string prefix, string suffix)
fopen prefix + suffix.
Definition: genC.c:905
#define IS_EXTERNAL(bp)
#define IS_INLINABLE(bp)
Different kinds of BINDING structure pointers.
#define MAX_DOMAIN
MAX_DOMAIN is the maximum number of entries in the DOMAINS table.
#define IS_IMPORT(bp)
struct _newgen_struct_code_ * code
Definition: ri.h:79
int fprintf()
test sc_min : ce test s'appelle par : programme fichier1.data fichier2.data ...
A gen_chunk is used to store every object.
Definition: genC.h:58

References Domains, DONT_TOUCH, fatal(), fopen_suffix(), fprintf(), generate_domain(), generate_safe_definition(), IS_EXTERNAL, IS_IMPORT, IS_INLINABLE, IS_TAB, MAX_DOMAIN, gen_binding::name, sharp_else(), sharp_endif(), and sharp_ifopt().

Referenced by build().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_access_members()

static void generate_access_members ( FILE *  out,
struct gen_binding bp,
int  domain_type,
int  operator 
)
static

access to members are managed thru macros.

cannot be functions because assign would not be possible. it would be better to avoid having field names that appear twice...

accesses...

Definition at line 490 of file genC.c.

495 {
496  union domain * dom = bp->domain;
497  struct domainlist * dlp;
498  bool in_between;
499  string name=bp->name;
500 
501  fprintf(out,
502  "#define %s_domain_number(x) ((x)->_type_%s)\n",
504 
505  if (domain_type==CONSTRUCTED_DT && operator==OR_OP) {
506  in_between = true;
507  fprintf(out,
508  "#define %s_tag(x) ((x)->_%s_tag__%s)\n",
509  name, name, int_type_access_complement());
510  }
511  else in_between = false;
512 
513  if (domain_type==CONSTRUCTED_DT && operator==ARROW_OP)
514  fprintf(out, "#define %s_hash_table(x) ((x)->_%s_holder_)\n",
515  name, name);
516 
517  if (domain_type==LIST_DT || domain_type==SET_DT)
518  fprintf(out, "#define %s_%s(x) ((x)->_%s_holder_)\n",
519  name, dom->ba.constructor, name);
520 
521  if (domain_type==ARRAY_DT)
522  fprintf(out, "#define %s_%s(x) ((x)->_%s_%s_" FIELD "\n",
523  name, dom->ba.constructor,
524  name, dom->ba.constructor);
525 
526  if (domain_type==CONSTRUCTED_DT && operator!=ARROW_OP) {
527 
528  /* accesses... */
529  for (dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr) {
530  char c;
531  if(operator==OR_OP) {
532  string field = dlp->domain->ba.constructor;
533  fprintf(out,
534  "#define %s_%s_p(x) (%s_tag(x)==is_%s_%s)\n",
535  name, field, name, name, field);
536  }
537  fprintf(out,
538  "#define %s_%s_(x) %s_%s(x) /* old hack compatible */\n"
539  "#define %s_%s(x) ((x)->",
540  name, dlp->domain->ba.constructor,
541  name, dlp->domain->ba.constructor,
542  name, dlp->domain->ba.constructor);
543  if (in_between) fprintf(out, "_%s_union_.", name);
544  fprintf(out, "_%s_%s_" FIELD, name, dlp->domain->ba.constructor);
545  c = newgen_access_name(dlp->domain);
546  if (c && !inline_directly(dlp->domain))
547  fprintf(out, ".%c", c);
548  fprintf(out, ")\n");
549  }
550  }
551 }
static FILE * out
Definition: alias_check.c:128
static bool inline_directly(union domain *dp)
Definition: genC.c:119
static string int_type_access_complement(void)
Definition: genC.c:140
#define FIELD
Definition: genC.c:41
static char newgen_access_name(union domain *dp)
what to add to the field to access a given primitive type, which was typically declared as a gen_chun...
Definition: genC.c:206
A DOMAIN union describes the structure of a user type.
char * constructor

References ARRAY_DT, ARROW_OP, domain::ba, domain::co, domain::components, CONSTRUCTED_DT, domain::constructor, gen_binding::domain, FIELD, fprintf(), inline_directly(), int_type_access_complement(), LIST_DT, gen_binding::name, newgen_access_name(), OR_OP, out, and SET_DT.

Referenced by generate_constructed(), and generate_not_constructed().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_arrow()

static void generate_arrow ( FILE *  header,
FILE *  code,
struct gen_binding bp 
)
static

newgen function (->) specific stuff

how to extract the key and value from the hash_table chunks.

apply

update

extend

delete

bound_p

Definition at line 585 of file genC.c.

589 {
590  union domain * dom, * key, * val;
591  string name, kname, vname, Name;
592  char kc, vc;
593 
594  dom = bp->domain;
595  key = dom->co.components->domain;
596  val = dom->co.components->cdr->domain;
597 
598  name = bp->name;
599  Name = strup(name);
600  // To deal with long int version:
601  kname = newgen_argument_type_name(key);
602  vname = newgen_argument_type_name(val);
603 
604  /* how to extract the key and value from the hash_table chunks.
605  */
606  kc = newgen_access_name(key);
607  if (kc=='\0') kc = 'p';
608  vc = newgen_access_name(val);
609  if (vc=='\0') vc = 'p';
610 
611  fprintf(
612  header,
613  "#define %s_key_type %s\n"
614  "#define %s_value_type %s\n"
615  "#define %s_MAP(k,v,c,f) FUNCTION_MAP(%s,%c,%c,k,v,c,f)\n"
616  "#define %s_FOREACH(k,v,f) FUNCTION_FOREACH(%s,%c,%c,k,v,f)\n"
617  "extern %s apply_%s(%s, %s);\n"
618  "extern void update_%s(%s, %s, %s);\n"
619  "extern void extend_%s(%s, %s, %s);\n"
620  "extern %s delete_%s(%s, %s);\n"
621  "extern bool bound_%s_p(%s, %s);\n",
622  name, kname, // key type
623  name, vname, // val type
624  Name, name, kc, vc, // MAP
625  Name, name, kc, vc, // FUNCTION
626  vname, name, name, kname, // apply
627  name, name, kname, vname, // update
628  name, name, kname, vname, // extend
629  vname, name, name, kname, // delete
630  name, name, kname // bound_p
631  );
632 
633  fprintf(code,
634  "%s apply_%s(%s f, %s k) {\n"
635  " return (%s) (intptr_t)HASH_GET(%c, %c, %s_hash_table(f), k);\n"
636  "}\n"
637  "void update_%s(%s f, %s k, %s v) {\n"
638  " HASH_UPDATE(%c, %c, %s_hash_table(f), k, (intptr_t)v);\n"
639  "}\n"
640  "void extend_%s(%s f, %s k, %s v) {\n"
641  " HASH_EXTEND(%c, %c, %s_hash_table(f), k, (intptr_t)v);\n"
642  "}\n"
643  "%s delete_%s(%s f, %s k) {\n"
644  " return (%s)(intptr_t) HASH_DELETE(%c, %c, %s_hash_table(f), k);\n"
645  "}\n"
646  "bool bound_%s_p(%s f, %s k) {\n"
647  " return (intptr_t)HASH_BOUND_P(%c, %c, %s_hash_table(f), k);\n"
648  "}\n",
649  vname, name, name, kname, vname, kc, vc, name, /* apply */
650  name, name, kname, vname, kc, vc, name, /* update */
651  name, name, kname, vname, kc, vc, name, /* extend */
652  vname, name, name, kname, vname, kc, vc, name, /* delete */
653  name, name, kname, kc, vc, name /* bound_p */);
654 
655  free(Name);
656 }
static string strup(string s)
returns s duplicated and case-uppered.
Definition: genC.c:110
static string newgen_argument_type_name(union domain *dp)
C type name for generated function arguments.
Definition: genC.c:179

References domain::co, domain::components, gen_binding::domain, fprintf(), free(), gen_binding::name, newgen_access_name(), newgen_argument_type_name(), and strup().

Referenced by generate_domain().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_constructed()

static void generate_constructed ( FILE *  header,
FILE *  code,
struct gen_binding bp,
int  operator 
)
static

constructed types: + x (and ->...)

Definition at line 555 of file genC.c.

560 {
561  generate_union_type_descriptor(header, bp, CONSTRUCTED_DT, operator);
562  generate_union_as_string(header, code, bp, CONSTRUCTED_DT, operator);
563  generate_make(header, code, bp, CONSTRUCTED_DT, operator);
564  fprintf(header, "\n");
565  generate_struct_members(header, bp, CONSTRUCTED_DT, operator);
566  generate_access_members(header, bp, CONSTRUCTED_DT, operator);
567 }
static void generate_struct_members(FILE *out, struct gen_binding *bp, int domain_type, int operator)
generate the struct for bp.
Definition: genC.c:370
static void generate_union_as_string(FILE *header, FILE *code, struct gen_binding *bp, int domain_type, int operator)
introspection function.
Definition: genC.c:454
static void generate_union_type_descriptor(FILE *out, struct gen_binding *bp, int domain_type, int operator)
Definition: genC.c:428
static void generate_make(FILE *header, FILE *code, struct gen_binding *bp, int domain_type, int operator)
make is bigger, thus I put it in a separate function.
Definition: genC.c:228
static void generate_access_members(FILE *out, struct gen_binding *bp, int domain_type, int operator)
access to members are managed thru macros.
Definition: genC.c:490

References CONSTRUCTED_DT, fprintf(), generate_access_members(), generate_make(), generate_struct_members(), generate_union_as_string(), and generate_union_type_descriptor().

Referenced by generate_domain().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_domain()

static void generate_domain ( FILE *  header,
FILE *  code,
struct gen_binding bp 
)
static

generate the needed stuff for bp.

assumes a preceeding safe definition. non specific (and/or...) stuff.

what about assignment with checks? something like: #define FOO_assign(r,v) \ { FOO * _p = &(r), _v = (v); \ FOO_check(r); FOO_check(v); \ *_p = _v; \ }

tabulated

find

write

read

find

write

read

NOT tabulated

write

read

write

read

nothing to generate at the time.

Definition at line 711 of file genC.c.

715 {
716  union domain * dp = bp->domain;
717  string name = bp->name, Name = strup(bp->name);
718 
719  if (!IS_EXTERNAL(bp)) {
720  /* assumes a preceeding safe definition.
721  * non specific (and/or...) stuff.
722  */
723  fprintf(header,
724  "/* %s\n */\n"
725  "#define %s(x) ((%s)((x).p))\n"
726  // foo_CAST FOO_CAST
727  "#define %s_CAST(x) %s(x)\n"
728  "#define %s_CAST(x) %s(x)\n"
729  "#define %s_(x) ((x).e)\n"
730  // foo_TYPE FOO_TYPE
731  "#define %s_TYPE %s\n"
732  "#define %s_TYPE %s\n"
733  "#define %s_undefined ((%s)gen_chunk_undefined)\n"
734  "#define %s_undefined_p(x) ((x)==%s_undefined)\n"
735  /* what about assignment with checks?
736  // something like:
737  // #define FOO_assign(r,v) \
738  // { FOO * _p = &(r), _v = (v); \
739  // FOO_check(r); FOO_check(v); \
740  // *_p = _v; \
741  // }
742  */
743  "\n"
744  "extern %s copy_%s(%s);\n"
745  "extern void free_%s(%s);\n"
746  "extern %s check_%s(%s);\n"
747  "extern bool %s_consistent_p(%s);\n"
748  "extern bool %s_defined_p(%s);\n"
749  "#define gen_%s_cons gen_%s_cons\n"
750  "extern list gen_%s_cons(%s, list);\n"
751  "extern void %s_assign_contents(%s, %s);\n"
752  "extern void %s_non_recursive_free(%s);\n",
753  Name, // comments
754  Name, name, // defines...
755  name, Name,
756  Name, Name,
757  Name,
758  Name, name, // XXX_TYPE
759  name, name, // xxx_TYPE
760  name, name,
761  name, name,
762  name, name, name, // copy
763  name, name, // free
764  name, name, name, // check
765  name, name, // consistent
766  name, name, // defined
767  Name, name, // gen cons
768  name, name,
769  name, name, name, // assign contents
770  name, name // non recursive free
771  );
772 
773  fprintf(code,
774  "/* %s\n */\n"
775  "%s copy_%s(%s p) {\n"
776  " return (%s) gen_copy_tree((gen_chunk*) p);\n"
777  "}\n"
778  "void free_%s(%s p) {\n"
779  " gen_free((gen_chunk*) p);\n"
780  "}\n"
781  "%s check_%s(%s p) {\n"
782  " return (%s) gen_check((gen_chunk*) p, %s_domain);\n"
783  "}\n"
784  "bool %s_consistent_p(%s p) {\n"
785  " check_%s(p);\n"
786  " return gen_consistent_p((gen_chunk*) p);\n"
787  "}\n"
788  "bool %s_defined_p(%s p) {\n"
789  " return gen_defined_p((gen_chunk*) p);\n"
790  "}\n"
791  "list gen_%s_cons(%s p, list l) {\n"
792  " return gen_typed_cons(%s_NEWGEN_DOMAIN, p, l);\n"
793  "}\n"
794  "void %s_assign_contents(%s r, %s v) {\n"
795  " check_%s(r);\n"
796  " check_%s(v);\n"
797  " message_assert(\"defined references to domain %s\",\n"
798  " %s_defined_p(r) && %s_defined_p(v));\n"
799  " memcpy(r, v, sizeof(struct " STRUCT "%s_));\n"
800  "}\n"
801  "void %s_non_recursive_free(%s p) {\n"
802  " // should clear up contents...\n"
803  " free(p);\n"
804  "}\n",
805  Name, // comments
806  name, name, name, name, // copy
807  name, name, // free
808  name, name, name, name, name, // check
809  name, name, name, // consistent
810  name, name, // consistent
811  name, name, Name, // gen cons
812  name, name, name, // assign contents
813  name, name, name, name, name, name,
814  name, name // non recursive free
815  );
816 
817  if (IS_TABULATED(bp)) {
818  /* tabulated */
819  fprintf(header,
820  "extern %s gen_find_%s(char *);\n"
821  "extern void write_tabulated_%s(FILE *);\n"
822  "extern void read_tabulated_%s(FILE *);\n",
823  name, name, /* find */
824  name, /* write */
825  name /* read */);
826  fprintf(code,
827  "%s gen_find_%s(char* s) {\n"
828  " return (%s) gen_find_tabulated(s, %s_domain);\n"
829  "}\n"
830  "void write_tabulated_%s(FILE* f) {\n"
831  " (void) gen_write_tabulated(f, %s_domain);\n"
832  "}\n"
833  "void read_tabulated_%s(FILE* f) {\n"
834  " int domain = gen_read_tabulated(f, 0);\n"
835  " if (domain!=%s_domain) {\n"
836  " fprintf(stderr, " DomainNumberError ",\n"
837  " domain, %s_domain);\n"
838  " abort();\n"
839  " }\n"
840  "}\n",
841  name, name, name, name, /* find */
842  name, name, /* write */
843  name, name, name, name /* read */);
844  }
845  else {
846  /* NOT tabulated */
847  fprintf(header,
848  "extern void write_%s(FILE*, %s);\n"
849  "extern %s read_%s(FILE*);\n",
850  name, name, /* write */
851  name, name /* read */);
852  fprintf(code,
853  "void write_%s(FILE* f, %s p) {\n"
854  " gen_write(f, (gen_chunk*) p);\n"
855  "}\n"
856  "%s read_%s(FILE* f) {\n"
857  " return (%s) gen_read(f);\n"
858  "}\n",
859  name, name, /* write */
860  name, name, name /* read */);
861  }
862  }
863 
864  switch (dp->ba.type) {
865  case CONSTRUCTED_DT:
866  switch (dp->co.op) {
867  case AND_OP:
868  generate_constructed(header, code, bp, AND_OP);
869  break;
870  case OR_OP:
871  generate_constructed(header, code, bp, OR_OP);
872  break;
873  case ARROW_OP:
874  generate_constructed(header, code, bp, ARROW_OP);
875  generate_arrow(header, code, bp);
876  break;
877  default:
878  fatal("[generate_domain] unexpected constructed %d\n", dp->co.op);
879  }
880  break;
881  case LIST_DT:
882  generate_not_constructed(header, code, bp, LIST_DT);
883  break;
884  case SET_DT:
885  generate_not_constructed(header, code, bp, SET_DT);
886  break;
887  case ARRAY_DT:
888  generate_not_constructed(header, code, bp, ARRAY_DT);
889  break;
890  case EXTERNAL_DT:
891  /* nothing to generate at the time. */
892  break;
893  default:
894  fatal("[generate_domain] unexpected domain type %d\n", dp->ba.type);
895  }
896 
897  fprintf(header, "\n");
898  fprintf(code, "\n");
899 
900  free(Name);
901 }
static void generate_arrow(FILE *header, FILE *code, struct gen_binding *bp)
newgen function (->) specific stuff
Definition: genC.c:585
#define DomainNumberError
Definition: genC.c:52
#define STRUCT
Definition: genC.c:42
static void generate_not_constructed(FILE *header, FILE *code, struct gen_binding *bp, int domain_type)
other types (direct * {} [])
Definition: genC.c:571
static void generate_constructed(FILE *header, FILE *code, struct gen_binding *bp, int operator)
constructed types: + x (and ->...)
Definition: genC.c:555
@ EXTERNAL_DT

References AND_OP, ARRAY_DT, ARROW_OP, domain::ba, domain::co, CONSTRUCTED_DT, gen_binding::domain, DomainNumberError, EXTERNAL_DT, fatal(), fprintf(), free(), generate_arrow(), generate_constructed(), generate_not_constructed(), IS_EXTERNAL, IS_TABULATED, LIST_DT, gen_binding::name, domain::op, OR_OP, SET_DT, STRUCT, strup(), and domain::type.

Referenced by gencode().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_make()

static void generate_make ( FILE *  header,
FILE *  code,
struct gen_binding bp,
int  domain_type,
int  operator 
)
static

make is bigger, thus I put it in a separate function.

HEADER

CODE

additionnal constructors for OR, so as to improve type checking.

check for unit...

UNIT case

header

code

header

code

Definition at line 228 of file genC.c.

234 {
235  string name = bp->name;
236  union domain * dom = bp->domain;
237  struct domainlist * dlp;
238  int domain = bp-Domains;
239  int i;
240 
241  /* HEADER
242  */
243  fprintf(header, "extern %s make_%s(", name, name);
244 
245  switch (domain_type) {
246  case CONSTRUCTED_DT:
247  switch (operator) {
248  case AND_OP:
249  for (i=1, dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr, i++)
250  fprintf(header, "%s%s%s", i==1? "": ", ",
251  newgen_argument_type_name(dlp->domain),
252  newgen_type_name_close(dlp->domain));
253  break;
254  case OR_OP:
255  fprintf(header, "enum %s_utype, void *", name);
256  break;
257  case ARROW_OP:
258  fprintf(header, "void");
259  break;
260  }
261  break;
262  case LIST_DT:
263  case SET_DT:
264  case ARRAY_DT:
265  fprintf(header, "%s%s",
268  break;
269  default:
270  fatal("[generate_make] unexpected domain type tag %d\n", domain_type);
271  }
272 
273  fprintf(header, ");\n");
274 
275  /* CODE
276  */
277  fprintf(code, "%s make_%s(", name, name);
278  switch (domain_type) {
279  case CONSTRUCTED_DT:
280  switch (operator) {
281  case AND_OP:
282  for (i=1, dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr, i++)
283  fprintf(code, "%s%s%s a%d", i==1? "": ", ",
284  newgen_argument_type_name(dlp->domain),
285  newgen_type_name_close(dlp->domain), i);
286  break;
287  case OR_OP:
288  fprintf(code, "enum %s_utype tag, void * val", name);
289  break;
290  case ARROW_OP:
291  fprintf(code, "void");
292  break;
293  }
294  break;
295  case LIST_DT:
296  case SET_DT:
297  case ARRAY_DT:
298  fprintf(code, "%s%s a",
301  break;
302  }
303 
304  fprintf(code,
305  ") {\n"
306  " return (%s) "
307  "gen_alloc(%d*sizeof(gen_chunk), GEN_CHECK_ALLOC, %s_domain",
308  name, gen_size(domain), name);
309  switch (domain_type) {
310  case CONSTRUCTED_DT:
311  switch (operator) {
312  case AND_OP:
313  for (i=1, dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr, i++)
314  fprintf(code, ", a%d", i);
315  break;
316  case OR_OP:
317  fprintf(code, ", tag, val");
318  break;
319  case ARROW_OP:
320  break;
321  }
322  break;
323  case LIST_DT:
324  case SET_DT:
325  case ARRAY_DT:
326  fprintf(code, ", a");
327  break;
328  }
329  fprintf(code, ");\n}\n");
330 
331  /* additionnal constructors for OR,
332  so as to improve type checking.
333  */
334  if (domain_type==CONSTRUCTED_DT && operator==OR_OP) {
335  for (dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr) {
336  /* check for unit... */
337  string field = dlp->domain->ba.constructor;
338  string typen = newgen_argument_type_name(dlp->domain);
339  if(!strcmp(typen, UNIT_TYPE_NAME)) {
340  /* UNIT case */
341  /* header */
342  fprintf(header,
343  "extern %s make_%s_%s(void);\n",
344  name, name, field);
345  /* code */
346  fprintf(code,
347  "%s make_%s_%s(void) {\n"
348  " return make_%s(is_%s_%s, UU);\n"
349  "}\n",
350  name, name, field, name, name, field);
351  }
352  else {
353  /* header */
354  fprintf(header, "extern %s make_%s_%s(%s);\n",
355  name, name, field, typen);
356  /* code */
357  fprintf(code,
358  "%s make_%s_%s(%s _field_) {\n"
359  " return make_%s(is_%s_%s, (void*)(intptr_t) _field_);\n"
360  "}\n",
361  name, name, field, typen,
362  name, name, field);
363  }
364  }
365  }
366 }
int gen_size(int domain)
GEN_SIZE returns the size (in gen_chunks) of an object of type defined by the BP type.
Definition: genC.c:71
static string newgen_type_name_close(union domain *dp)
Definition: genC.c:196
#define UNIT_TYPE_NAME
The UNIT_TYPE_NAME is the used to type expressions which only perform side-effects.

References AND_OP, ARRAY_DT, ARROW_OP, domain::co, domain::components, CONSTRUCTED_DT, gen_binding::domain, Domains, fatal(), fprintf(), gen_size(), LIST_DT, gen_binding::name, newgen_argument_type_name(), newgen_type_name_close(), OR_OP, SET_DT, and UNIT_TYPE_NAME.

Referenced by generate_constructed(), and generate_not_constructed().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_not_constructed()

static void generate_not_constructed ( FILE *  header,
FILE *  code,
struct gen_binding bp,
int  domain_type 
)
static

other types (direct * {} [])

Definition at line 571 of file genC.c.

576 {
577  generate_make(header, code, bp, domain_type, UNDEF_OP);
578  fprintf(header, "\n");
579  generate_struct_members(header, bp, domain_type, UNDEF_OP);
580  generate_access_members(header, bp, domain_type, UNDEF_OP);
581 }
@ UNDEF_OP

References fprintf(), generate_access_members(), generate_make(), generate_struct_members(), and UNDEF_OP.

Referenced by generate_domain().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_safe_definition()

static void generate_safe_definition ( FILE *  out,
struct gen_binding bp,
string  file 
)
static

generates a needed type declaration.

kind of a bug here: if the very same externals appears several times, they are not sure to be attributed the same number in different files with different include orders. externals should really be global?

should not run if IS_IMPORT(bp)???

Definition at line 661 of file genC.c.

665 {
666  string name = bp->name, Name = strup(name);
667  int index = TYPE(bp);
668 
669  if (!IS_EXTERNAL(bp) && !IS_IMPORT(bp))
670  fprintf(out,
671  "#define %s_domain (_gen_%s_start+%d)\n",
672  name, file, index);
673 
674  fprintf(out,
675  "#if !defined(_newgen_%s_domain_defined_)\n"
676  "#define _newgen_%s_domain_defined_\n",
677  name, name);
678 
679  if (IS_EXTERNAL(bp))
680  /* kind of a bug here: if the very same externals appears
681  * several times, they are not sure to be attributed the same
682  * number in different files with different include orders.
683  * externals should really be global?
684  */
685  fprintf(out,
686  "#define newgen_%s(p) (p) /* old hack compatible */\n"
687  "#define %s_NEWGEN_EXTERNAL (_gen_%s_start+%d)\n"
688  "#define %s_NEWGEN_DOMAIN (%s_NEWGEN_EXTERNAL)\n"
689  "#define %s_NEWGEN_DOMAIN (%s_NEWGEN_EXTERNAL)\n",
690  name,
691  Name, file, index,
692  Name, Name,
693  name, Name);
694  else
695  /* should not run if IS_IMPORT(bp)??? */
696  fprintf(out,
697  "#define %s_NEWGEN_DOMAIN (%s_domain)\n"
698  "#define %s_NEWGEN_DOMAIN (%s_domain)\n"
699  "typedef struct " STRUCT "%s_ * %s;\n",
700  Name, name,
701  name, name,
702  name, name);
703 
704  fprintf(out, "#endif /* _newgen_%s_domain_defined_ */\n\n", name);
705  free(Name);
706 }
#define TYPE(bp)
non user domain must be taken care from outside?
Definition: genC.c:50

References fprintf(), free(), IS_EXTERNAL, IS_IMPORT, gen_binding::name, out, STRUCT, strup(), and TYPE.

Referenced by gencode().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_struct_members()

static void generate_struct_members ( FILE *  out,
struct gen_binding bp,
int  domain_type,
int  operator 
)
static

generate the struct for bp.

generate the structure

there is an additionnal field in tabulated domains.

generate struct fields

Definition at line 370 of file genC.c.

375 {
376  union domain * dom = bp->domain;
377  struct domainlist * dlp;
378  string offset = "";
379 
380  /* generate the structure
381  */
382  fprintf(out,
383  "struct " STRUCT "%s_ {\n"
384  " %s _type_;\n",
385  bp->name, int_type());
386 
387  /* there is an additionnal field in tabulated domains.
388  */
389  if (IS_TABULATED(bp))
390  fprintf(out,
391  " %s _%s_index__;\n",
392  int_type(), bp->name);
393 
394  if (domain_type==CONSTRUCTED_DT && operator==OR_OP) {
395  fprintf(out,
396  " enum %s_utype _%s_tag__;\n"
397  " union {\n",
398  bp->name, bp->name);
399  offset = " ";
400  }
401 
402  if ((domain_type==CONSTRUCTED_DT && operator==ARROW_OP) ||
403  domain_type==LIST_DT ||
404  domain_type==SET_DT)
405  fprintf(out,
406  " %s _%s_holder_;\n",
407  newgen_type_name(dom), bp->name);
408 
409  if (domain_type==CONSTRUCTED_DT && operator!=ARROW_OP) {
410  /* generate struct fields */
411  for (dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr)
412  fprintf(out, "%s %s%s _%s_%s_" FIELD "; /* %s:%s%s */\n",
413  offset,
414  newgen_type_name(dlp->domain),
415  newgen_type_name_close(dlp->domain),
416  bp->name, dlp->domain->ba.constructor,
417  dlp->domain->ba.constructor,
418  dlp->domain->ba.constructand->name,
419  newgen_kind_label(dlp->domain));
420  }
421 
422  if (domain_type==CONSTRUCTED_DT && operator==OR_OP)
423  fprintf(out, " } _%s_union_;\n", bp->name);
424 
425  fprintf(out, "};\n\n");
426 }
static Value offset
Definition: translation.c:283
static string int_type(void)
bof...
Definition: genC.c:135
static string newgen_kind_label(union domain *dp)
just to generate comprehensive comments.
Definition: genC.c:216
static string newgen_type_name(union domain *dp)
newgen type name for holder.
Definition: genC.c:148

References ARROW_OP, domain::co, domain::components, CONSTRUCTED_DT, gen_binding::domain, FIELD, fprintf(), int_type(), IS_TABULATED, LIST_DT, gen_binding::name, newgen_kind_label(), newgen_type_name(), newgen_type_name_close(), offset, OR_OP, out, SET_DT, and STRUCT.

Referenced by generate_constructed(), and generate_not_constructed().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_union_as_string()

static void generate_union_as_string ( FILE *  header,
FILE *  code,
struct gen_binding bp,
int  domain_type,
int  operator 
)
static

introspection function.

could be a dynamic function in genClib...

Definition at line 454 of file genC.c.

460 {
461  union domain * dom = bp->domain;
462  struct domainlist * dlp;
463  string name=bp->name;
464 
465  if (domain_type==CONSTRUCTED_DT &&
466  operator==OR_OP && dom->co.components!=NULL)
467  {
468  fprintf(header, "extern string %s_tag_as_string(enum %s_utype);\n",
469  name, name);
470  fprintf(code, "string %s_tag_as_string(enum %s_utype tag) {\n"
471  " switch (tag) {\n",
472  name, name);
473  for (dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr) {
474  string field = dlp->domain->ba.constructor;
475  fprintf(code,
476  " case is_%s_%s: return \"%s\";\n",
477  name, field, field);
478  }
479  fprintf(code,
480  " default: return string_undefined;\n"
481  " }\n"
482  "}\n");
483  }
484 }

References domain::co, domain::components, CONSTRUCTED_DT, gen_binding::domain, fprintf(), gen_binding::name, and OR_OP.

Referenced by generate_constructed().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ generate_union_type_descriptor()

static void generate_union_type_descriptor ( FILE *  out,
struct gen_binding bp,
int  domain_type,
int  operator 
)
static

Definition at line 428 of file genC.c.

433 {
434  union domain * dom = bp->domain;
435  struct domainlist * dlp;
436  string name=bp->name;
437 
438  if (domain_type==CONSTRUCTED_DT &&
439  operator==OR_OP && dom->co.components!=NULL)
440  {
441  fprintf(out,"enum %s_utype {\n", name);
442  for (dlp=dom->co.components; dlp!=NULL; dlp=dlp->cdr) {
443  string field = dlp->domain->ba.constructor;
444  fprintf(out,
445  " is_%s_%s%s\n",
446  name, field, (dlp->cdr == NULL)? "": ",");
447  }
448  fprintf(out,"};\n");
449  }
450 }

References domain::co, domain::components, CONSTRUCTED_DT, gen_binding::domain, fprintf(), gen_binding::name, OR_OP, and out.

Referenced by generate_constructed().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ inline_directly()

static bool inline_directly ( union domain dp)
static

Definition at line 119 of file genC.c.

120 {
121  if (dp->ba.type==BASIS_DT)
122  {
123  struct gen_binding * bp = dp->ba.constructand;
124  string name = bp->name;
125  if (!IS_INLINABLE(bp)) return false;
126  if ((same_string_p(name, "int") && same_size(intptr_t)) ||
127  (same_string_p(name, "string") && same_size(string)) ||
128  (same_string_p(name, "unit") && same_size(unit)))
129  return true;
130  }
131  return false;
132 }
#define same_size(t)
Definition: genC.c:117
#define same_string_p(s1, s2)
int unit
UNIT.
Definition: newgen_types.h:97
#define intptr_t
Definition: stdint.in.h:294
struct gen_binding * constructand

References domain::ba, BASIS_DT, domain::constructand, intptr_t, IS_INLINABLE, gen_binding::name, same_size, same_string_p, and domain::type.

Referenced by generate_access_members(), and newgen_type_name().

+ Here is the caller graph for this function:

◆ int_type()

static string int_type ( void  )
static

bof...

Definition at line 135 of file genC.c.

136 {
137  return same_size(intptr_t) ? "intptr_t": "gen_chunk";
138 }

References intptr_t, and same_size.

Referenced by generate_struct_members(), newgen_argument_type_name(), and newgen_type_name().

+ Here is the caller graph for this function:

◆ int_type_access_complement()

static string int_type_access_complement ( void  )
static

Definition at line 140 of file genC.c.

141 {
142  return same_size(intptr_t) ? "": ".i";
143 }

References intptr_t, and same_size.

Referenced by generate_access_members().

+ Here is the caller graph for this function:

◆ newgen_access_name()

static char newgen_access_name ( union domain dp)
static

what to add to the field to access a given primitive type, which was typically declared as a gen_chunk.

the field is the first char of the type name.

Definition at line 206 of file genC.c.

207 {
208  if (dp->ba.type==BASIS_DT && IS_INLINABLE(dp->ba.constructand))
209  return dp->ba.constructand->name[0];
210  else
211  return '\0';
212 }

References domain::ba, BASIS_DT, domain::constructand, IS_INLINABLE, gen_binding::name, and domain::type.

Referenced by generate_access_members(), and generate_arrow().

+ Here is the caller graph for this function:

◆ newgen_argument_type_name()

static string newgen_argument_type_name ( union domain dp)
static

C type name for generated function arguments.

Even if the NewGen name is int, the C name can be intptr_t:

Definition at line 179 of file genC.c.

180 {
181  switch (dp->ba.type) {
182  case BASIS_DT:
183  if (same_string_p(dp->ba.constructand->name, "int"))
184  /* Even if the NewGen name is int, the C name can be intptr_t: */
185  return int_type();
186  return dp->ba.constructand->name;
187  case LIST_DT: return "list";
188  case SET_DT: return "set";
189  case ARRAY_DT: return dp->ar.element->name;
190  default: fatal("[newgen_argument_type_name] unexpected domain type %d\n",
191  dp->ba.type);
192  }
193  return NULL;
194 }
struct gen_binding * element
struct domain::@6 ar

References domain::ar, ARRAY_DT, domain::ba, BASIS_DT, domain::constructand, domain::element, fatal(), int_type(), LIST_DT, gen_binding::name, same_string_p, SET_DT, and domain::type.

Referenced by generate_arrow(), and generate_make().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ newgen_kind_label()

static string newgen_kind_label ( union domain dp)
static

just to generate comprehensive comments.

Definition at line 216 of file genC.c.

217 {
218  switch (dp->ba.type) {
219  case SET_DT: return "{}";
220  case LIST_DT: return "*";
221  case ARRAY_DT: return "[]";
222  default: return "";
223  }
224 }

References ARRAY_DT, domain::ba, LIST_DT, SET_DT, and domain::type.

Referenced by generate_struct_members().

+ Here is the caller graph for this function:

◆ newgen_type_name()

static string newgen_type_name ( union domain dp)
static

newgen type name for holder.

could/should always be gen_chunk?

Even if the NewGen name is int, the C name can be intptr_t:

FALLTHRU

Definition at line 148 of file genC.c.

149 {
150  switch (dp->ba.type) {
151  case BASIS_DT: {
152  struct gen_binding * bp = dp->ba.constructand;
153  if (IS_INLINABLE(bp))
154  if (!inline_directly(dp))
155  return "gen_chunk";
156  if (same_string_p(bp->name, "int"))
157  /* Even if the NewGen name is int, the C name can be intptr_t: */
158  return int_type();
159  return bp->name;
160  }
161  case SET_DT: return "set";
162  case LIST_DT: return "list";
163  case ARRAY_DT: return dp->ar.element->name;
164  case CONSTRUCTED_DT:
165  switch (dp->co.op) {
166  case ARROW_OP: return "hash_table";
167  default:
168  break;
169  }
170  /* FALLTHRU */
171  default:
172  fatal("[newgen_type_name] unexpected domain type %d\n", dp->ba.type);
173  }
174  return NULL;
175 }

References domain::ar, ARRAY_DT, ARROW_OP, domain::ba, BASIS_DT, domain::co, domain::constructand, CONSTRUCTED_DT, domain::element, fatal(), inline_directly(), int_type(), IS_INLINABLE, LIST_DT, gen_binding::name, domain::op, same_string_p, SET_DT, and domain::type.

Referenced by generate_struct_members().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ newgen_type_name_close()

static string newgen_type_name_close ( union domain dp)
static

pointer

Definition at line 196 of file genC.c.

197 {
198  if (dp->ba.type==ARRAY_DT) return " *"; /* pointer */
199  return "";
200 }

References ARRAY_DT, domain::ba, and domain::type.

Referenced by generate_make(), and generate_struct_members().

+ Here is the caller graph for this function:

◆ sharp_else()

static int sharp_else ( FILE *  out)
static

Definition at line 62 of file genC.c.

63 { return fprintf(out, "#else\n"); }

References fprintf(), and out.

Referenced by gencode().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ sharp_endif()

static int sharp_endif ( FILE *  out)
static

Definition at line 65 of file genC.c.

66 { return fprintf(out, "#endif /* " OPTIMIZE_NEWGEN " */\n"); }
#define OPTIMIZE_NEWGEN
Definition: genC.c:44

References fprintf(), OPTIMIZE_NEWGEN, and out.

Referenced by gencode().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ sharp_ifopt()

static int sharp_ifopt ( FILE *  out)
static

Might be used to generate optimized versions (say macros instead of functions).

Definition at line 59 of file genC.c.

60 { return fprintf(out, "#if defined(" OPTIMIZE_NEWGEN ")\n"); }

References fprintf(), OPTIMIZE_NEWGEN, and out.

Referenced by gencode().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ strup()

static string strup ( string  s)
static

returns s duplicated and case-uppered.

Definition at line 110 of file genC.c.

111 {
112  string r = strdup(s), p=r;
113  while (*p) *p=toupper(*p), p++;
114  return r;
115 }
char * strdup()

References strdup().

Referenced by generate_arrow(), generate_domain(), and generate_safe_definition().

+ Here is the call graph for this function:
+ Here is the caller graph for this function: