add unions

This commit is contained in:
Bill Currie 2002-06-20 20:28:01 +00:00
parent f8e4215ba9
commit f8dee80355
4 changed files with 27 additions and 3 deletions

View file

@ -51,6 +51,7 @@ struct_field_t *new_struct_field (struct type_s *strct, struct type_s *type,
struct_field_t *struct_find_field (struct type_s *strct, const char *name); struct_field_t *struct_find_field (struct type_s *strct, const char *name);
int struct_compare_fields (struct type_s *s1, struct type_s *s2); int struct_compare_fields (struct type_s *s1, struct type_s *s2);
struct type_s *new_struct (const char *name); struct type_s *new_struct (const char *name);
struct type_s *new_union (const char *name);
struct type_s *find_struct (const char *name); struct type_s *find_struct (const char *name);
void copy_struct_fields (struct type_s *dst, struct type_s *src); void copy_struct_fields (struct type_s *dst, struct type_s *src);

View file

@ -278,6 +278,7 @@ static keyword_t keywords[] = {
{"default", DEFAULT, 0, 0, PROG_ID_VERSION}, {"default", DEFAULT, 0, 0, PROG_ID_VERSION},
{"NIL", NIL, 0, 0, PROG_ID_VERSION}, {"NIL", NIL, 0, 0, PROG_ID_VERSION},
{"struct", STRUCT, 0, 0, PROG_VERSION}, {"struct", STRUCT, 0, 0, PROG_VERSION},
{"union", UNION, 0, 0, PROG_VERSION},
{"enum", ENUM, 0, 0, PROG_ID_VERSION}, {"enum", ENUM, 0, 0, PROG_ID_VERSION},
{"typedef", TYPEDEF, 0, 0, PROG_ID_VERSION}, {"typedef", TYPEDEF, 0, 0, PROG_ID_VERSION},
{"super", SUPER, 0, 0, PROG_VERSION}, {"super", SUPER, 0, 0, PROG_VERSION},

View file

@ -126,7 +126,7 @@ void free_local_inits (hashtab_t *def_list);
%token LOCAL RETURN WHILE DO IF ELSE FOR BREAK CONTINUE ELLIPSIS NIL %token LOCAL RETURN WHILE DO IF ELSE FOR BREAK CONTINUE ELLIPSIS NIL
%token IFBE IFB IFAE IFA %token IFBE IFB IFAE IFA
%token SWITCH CASE DEFAULT STRUCT ENUM TYPEDEF SUPER SELF THIS %token SWITCH CASE DEFAULT STRUCT UNION ENUM TYPEDEF SUPER SELF THIS
%token ARGC ARGV %token ARGC ARGV
%token ELE_START %token ELE_START
%token <type> TYPE %token <type> TYPE
@ -197,6 +197,8 @@ def
: type { current_type = $1; } def_list : type { current_type = $1; } def_list
| STRUCT NAME | STRUCT NAME
{ struct_type = new_struct ($2); } '=' '{' struct_defs '}' { struct_type = new_struct ($2); } '=' '{' struct_defs '}'
| UNION NAME
{ struct_type = new_union ($2); } '=' '{' struct_defs '}'
| ENUM '{' enum_list opt_comma '}' | ENUM '{' enum_list opt_comma '}'
{ process_enum ($3); } { process_enum ($3); }
| TYPEDEF type NAME | TYPEDEF type NAME
@ -1216,6 +1218,7 @@ reserved_word
| DEFAULT { $$ = strdup (yytext); } | DEFAULT { $$ = strdup (yytext); }
| NIL { $$ = strdup (yytext); } | NIL { $$ = strdup (yytext); }
| STRUCT { $$ = strdup (yytext); } | STRUCT { $$ = strdup (yytext); }
| UNION { $$ = strdup (yytext); }
| ENUM { $$ = strdup (yytext); } | ENUM { $$ = strdup (yytext); }
| TYPEDEF { $$ = strdup (yytext); } | TYPEDEF { $$ = strdup (yytext); }
| SUPER { $$ = strdup (yytext); } | SUPER { $$ = strdup (yytext); }

View file

@ -57,6 +57,7 @@ static const char rcsid[] =
typedef struct { typedef struct {
const char *name; const char *name;
type_t *type; type_t *type;
int is_union;
} struct_t; } struct_t;
typedef struct { typedef struct {
@ -97,8 +98,14 @@ new_struct_field (type_t *strct, type_t *type, const char *name,
field->visibility = visibility; field->visibility = visibility;
field->name = name; field->name = name;
field->type = type; field->type = type;
if (((struct_t *) strct->class)->is_union) {
int size = type_size (type);
field->offset = 0;
strct->num_parms = strct->num_parms > size ? strct->num_parms : size;
} else {
field->offset = strct->num_parms; field->offset = strct->num_parms;
strct->num_parms += type_size (type); strct->num_parms += type_size (type);
}
field->next = 0; field->next = 0;
*strct->struct_tail = field; *strct->struct_tail = field;
strct->struct_tail = &field->next; strct->struct_tail = &field->next;
@ -136,6 +143,8 @@ new_struct (const char *name)
strct->type->type = ev_struct; strct->type->type = ev_struct;
strct->type->struct_tail = &strct->type->struct_head; strct->type->struct_tail = &strct->type->struct_head;
strct->type->struct_fields = Hash_NewTable (61, struct_field_get_key, 0, 0); strct->type->struct_fields = Hash_NewTable (61, struct_field_get_key, 0, 0);
strct->type->class = (struct class_s *)strct;
strct->is_union = 0;
if (name) { if (name) {
strct->type->name = strdup (name); strct->type->name = strdup (name);
Hash_Add (structs, strct); Hash_Add (structs, strct);
@ -143,6 +152,16 @@ new_struct (const char *name)
return strct->type; return strct->type;
} }
type_t *
new_union (const char *name)
{
type_t *un = new_struct (name);
if (un)
((struct_t *) un->class)->is_union = 1;
return un;
}
type_t * type_t *
find_struct (const char *name) find_struct (const char *name)
{ {