2007-03-26 Zack Weinberg <zackw@panix.com>
+ * gengtype.h (struct type): Replace 'sc' with boolean, scalar_is_char.
+ (string_type): Don't declare.
+ (do_scalar_typedef): Declare.
+ (create_scalar_type): Update prototype.
+ * gengtype.c (string_type): Make static.
+ (scalar_nonchar, scalar_char): New.
+ (do_scalar_typedef): Export. Always use scalar_nonchar for the type.
+ (resolve_typedef): Use scalar_nonchar for error recovery.
+ (create_scalar_type): Remove name_len field. Return scalar_char
+ or scalar_nonchar as appropriate.
+ (adjust_field_type): Look at scalar_is_char boolean to decide whether
+ to use string_type.
+ (throughout): Use scalar_nonchar instead of calling create_scalar_type,
+ whenever possible.
+ (main): Initialize scalar_char and scalar_nonchar before calling
+ gen_rtx_next.
+ * gengtype-lex.l: Adjust for removal of second argument to
+ create_scalar_type. Use yylval.s instead of yylval.t when
+ returning SCALAR.
+ * gengtype-yacc.y: Type of SCALAR is string. Call
+ create_scalar_type from type:SCALAR rule. Adjust for removal of
+ second argument to create_scalar_type.
+
* vec.h: Remove all #if IN_GENGTYPE blocks.
Add comment saying that changes may require adjustments to gengtype.
* gengtype.c: Don't include coretypes.h or tm.h.
char *namestart;
size_t namelen;
- struct type *t;
char *typestart;
size_t typelen;
ISSPACE (typestart[typelen-1]);
typelen--)
;
+ typestart[typelen] = '\0';
- t = create_scalar_type (typestart, typelen);
- do_typedef ((const char *) xmemdup (namestart, namelen, namelen+1), t,
+ do_typedef ((const char *) xmemdup (namestart, namelen, namelen+1),
+ create_scalar_type (typestart),
&lexer_line);
update_lineno (yytext, yyleng);
}
[^[:alnum:]_]typedef{WS}{ID}{WS}{ID}{WS}"(" {
char *namestart;
size_t namelen;
- struct type *t;
for (namestart = yytext + yyleng - 2; ISSPACE (*namestart); namestart--)
;
;
namestart -= namelen - 1;
- t = create_scalar_type ("function type", sizeof ("function type")-1);
- do_typedef ((const char *) xmemdup (namestart, namelen, namelen+1), t,
- &lexer_line);
+ do_scalar_typedef ((const char *) xmemdup (namestart, namelen, namelen+1),
+ &lexer_line);
update_lineno (yytext, yyleng);
}
[^[:alnum:]_]typedef{WS}{ID}{WS}?"*"?{WS}?"("{WS}?"*"{WS}?{ID}{WS}?")"{WS}?"(" {
char *namestart;
size_t namelen;
- struct type *t;
for (namestart = yytext + yyleng - 2; !ISIDNUM (*namestart); namestart--)
;
;
namestart -= namelen - 1;
- t = create_scalar_type ("function type", sizeof ("function type")-1);
- do_typedef ((const char *) xmemdup (namestart, namelen, namelen+1), t,
- &lexer_line);
+ do_scalar_typedef ((const char *) xmemdup (namestart, namelen, namelen+1),
+ &lexer_line);
update_lineno (yytext, yyleng);
}
for (len = yyleng; ISSPACE (yytext[len-1]); len--)
;
- yylval.t = create_scalar_type (yytext, len);
+ yylval.s = (const char *) xmemdup (yytext, len, len+1);
update_lineno (yytext, yyleng);
return SCALAR;
}
/* The one and only TYPE_STRING. */
-struct type string_type = {
- TYPE_STRING, NULL, NULL, GC_USED, {0}
+static struct type string_type = {
+ TYPE_STRING, 0, 0, GC_USED, {0}
+};
+
+/* The two and only TYPE_SCALARs. Their u.scalar_is_char flags are
+ set to appropriate values at the beginning of main. */
+
+static struct type scalar_nonchar = {
+ TYPE_SCALAR, 0, 0, GC_USED, {0}
+};
+static struct type scalar_char = {
+ TYPE_SCALAR, 0, 0, GC_USED, {0}
};
/* Lists of various things. */
static type_p param_structs;
static pair_p variables;
-static void do_scalar_typedef (const char *, struct fileloc *);
static type_p find_param_structure
(type_p t, type_p param[NUM_PARAM]);
static type_p adjust_field_tree_exp (type_p t, options_p opt);
typedefs = p;
}
-/* Define S as a typename of a scalar. */
+/* Define S as a typename of a scalar. Cannot be used to define
+ typedefs of 'char'. Note: is also used for pointer-to-function
+ typedefs (which are therefore not treated as pointers). */
-static void
+void
do_scalar_typedef (const char *s, struct fileloc *pos)
{
- do_typedef (s, create_scalar_type (s, strlen (s)), pos);
+ do_typedef (s, &scalar_nonchar, pos);
}
/* Return the type previously defined for S. Use POS to report errors. */
if (strcmp (p->name, s) == 0)
return p->type;
error_at_line (pos, "unidentified type `%s'", s);
- return create_scalar_type ("char", 4);
+ return &scalar_nonchar; /* treat as "int" */
}
/* Create and return a new structure with tag NAME (or a union iff
/* Return a scalar type with name NAME. */
type_p
-create_scalar_type (const char *name, size_t name_len)
+create_scalar_type (const char *name)
{
- type_p r = XCNEW (struct type);
- r->kind = TYPE_SCALAR;
- r->u.sc = (char *) xmemdup (name, name_len, name_len + 1);
- return r;
+ if (!strcmp (name, "char") || !strcmp (name, "unsigned char"))
+ return &scalar_char;
+ else
+ return &scalar_nonchar;
}
/* Return a pointer to T. */
bitmap_tp = create_pointer (find_structure ("bitmap_element_def", 0));
basic_block_tp = create_pointer (find_structure ("basic_block_def", 0));
constant_tp = create_pointer (find_structure ("constant_descriptor_rtx", 0));
- scalar_tp = create_scalar_type ("rtunion scalar", 14);
+ scalar_tp = &scalar_nonchar; /* rtunion int */
{
pair_p note_flds = NULL;
if (! length_p
&& pointer_p
&& t->u.p->kind == TYPE_SCALAR
- && (strcmp (t->u.p->u.sc, "char") == 0
- || strcmp (t->u.p->u.sc, "unsigned char") == 0))
+ && t->u.p->u.scalar_is_char)
return &string_type;
if (t->kind == TYPE_ARRAY && t->u.a.p->kind == TYPE_POINTER
&& t->u.a.p->u.p->kind == TYPE_SCALAR
- && (strcmp (t->u.a.p->u.p->u.sc, "char") == 0
- || strcmp (t->u.a.p->u.p->u.sc, "unsigned char") == 0))
+ && t->u.a.p->u.p->u.scalar_is_char)
return create_array (&string_type, t->u.a.len);
return t;
if (is_scalar)
{
- t = create_scalar_type (typename, strlen (typename));
+ t = create_scalar_type (typename);
o = 0;
}
else
fields = f;
f = XNEW (struct pair);
- f->type = adjust_field_type (create_scalar_type ("unsigned", 8), 0);
+ f->type = adjust_field_type (create_scalar_type ("unsigned"), 0);
f->name = "alloc";
f->opt = 0;
f->line = *pos;
fields = f;
f = XNEW (struct pair);
- f->type = adjust_field_type (create_scalar_type ("unsigned", 8), 0);
+ f->type = adjust_field_type (create_scalar_type ("unsigned"), 0);
f->name = "num";
f->opt = 0;
f->line = *pos;
static struct fileloc pos = { __FILE__, __LINE__ };
unsigned j;
- gen_rtx_next ();
-
srcdir_len = strlen (srcdir);
+ scalar_char.u.scalar_is_char = true;
+ scalar_nonchar.u.scalar_is_char = false;
+
+ gen_rtx_next ();
+
do_scalar_typedef ("CUMULATIVE_ARGS", &pos);
do_scalar_typedef ("REAL_VALUE_TYPE", &pos);
do_scalar_typedef ("double_int", &pos);
do_typedef ("PTR", create_pointer (resolve_typedef ("void", &pos)), &pos);
- do_typedef ("HARD_REG_SET", create_array (
- create_scalar_type ("unsigned long", strlen ("unsigned long")),
- "2"), &pos);
+ do_typedef ("HARD_REG_SET", create_array (&scalar_nonchar, "2"), &pos);
for (i = 0; i < NUM_GT_FILES; i++)
{
lang_bitmap bitmap;
type_p lang_struct;
} s;
- char *sc;
+ bool scalar_is_char;
struct {
type_p p;
const char *len;
|| (x)->kind == TYPE_STRUCT \
|| (x)->kind == TYPE_LANG_STRUCT)
-/* The one and only TYPE_STRING. */
-extern struct type string_type;
-
/* Variables used to communicate between the lexer and the parser. */
extern int lexer_toplevel_done;
extern struct fileloc lexer_line;
/* Constructor routines for types. */
extern void do_typedef (const char *s, type_p t, struct fileloc *pos);
+extern void do_scalar_typedef (const char *s, struct fileloc *pos);
extern type_p resolve_typedef (const char *s, struct fileloc *pos);
extern type_p new_structure (const char *name, int isunion,
struct fileloc *pos, pair_p fields,
options_p o);
extern type_p find_structure (const char *s, int isunion);
-extern type_p create_scalar_type (const char *name, size_t name_len);
+extern type_p create_scalar_type (const char *name);
extern type_p create_pointer (type_p t);
extern type_p create_array (type_p t, const char *len);
extern options_p create_option (options_p, const char *name, const void *info);