mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2025-04-16 06:11:15 +00:00
[qfcc] Use type expressions for generic types
This gets type lists and generic name references semi-implemented.
This commit is contained in:
parent
434bcdebbb
commit
f7ed55d317
3 changed files with 71 additions and 29 deletions
|
@ -847,6 +847,8 @@ const expr_t *new_param_expr (const type_t *type, int num);
|
|||
expr_t *new_memset_expr (const expr_t *dst, const expr_t *val,
|
||||
const expr_t *count);
|
||||
|
||||
expr_t *new_type_expr (const type_t *type);
|
||||
|
||||
/** Convert a name to an expression of the appropriate type.
|
||||
|
||||
Converts the expression in-place. If the exprssion is not a name
|
||||
|
|
|
@ -1402,6 +1402,15 @@ new_memset_expr (const expr_t *dst, const expr_t *val, const expr_t *count)
|
|||
return e;
|
||||
}
|
||||
|
||||
expr_t *
|
||||
new_type_expr (const type_t *type)
|
||||
{
|
||||
expr_t *e = new_expr ();
|
||||
e->type = ex_type;
|
||||
e->typ.type = type;
|
||||
return e;
|
||||
}
|
||||
|
||||
expr_t *
|
||||
append_expr (expr_t *block, const expr_t *e)
|
||||
{
|
||||
|
|
|
@ -178,7 +178,8 @@ int yylex (YYSTYPE *yylval, YYLTYPE *yylloc);
|
|||
%type <spec> absdecl absdecl1 direct_absdecl typename ptr_spec copy_spec
|
||||
%type <spec> qc_comma
|
||||
%type <symbol> generic_param
|
||||
%type <type> type_param type_expr type_ref
|
||||
%type <expr> type_param type_expr type_ref generic_type
|
||||
%type <mut_expr> type_list
|
||||
|
||||
%type <attribute> attribute_list attribute
|
||||
|
||||
|
@ -913,7 +914,7 @@ typespec
|
|||
|
||||
typespec_reserved
|
||||
: TYPE_SPEC
|
||||
| type_expr { $$ = make_spec ($1, 0, 0, 0); }
|
||||
| type_expr { $$ = make_spec ($1->typ.type, 0, 0, 0); }
|
||||
| algebra_specifier %prec LOW
|
||||
| algebra_specifier '.' attribute
|
||||
{
|
||||
|
@ -1069,44 +1070,62 @@ generic_param
|
|||
;
|
||||
|
||||
generic_type
|
||||
: type_expr
|
||||
| '[' type_list ']'
|
||||
: type_expr { $$ = $1; }
|
||||
| '[' type_list ']' { $$ = $2; }
|
||||
;
|
||||
|
||||
type_expr
|
||||
: AT_FIELD '(' type_param ')' { $$ = field_type ($3); }
|
||||
| AT_POINTER '(' type_param ')' { $$ = pointer_type ($3); }
|
||||
| AT_ARRAY '(' type_param ')' { $$ = array_type ($3, 0); }
|
||||
: AT_FIELD '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (field_type ($3->typ.type));
|
||||
}
|
||||
| AT_POINTER '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (pointer_type ($3->typ.type));
|
||||
}
|
||||
| AT_ARRAY '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (array_type ($3->typ.type, 0));
|
||||
}
|
||||
| AT_ARRAY '(' type_param ',' expr ')'
|
||||
{
|
||||
auto count = $5;
|
||||
auto type = $3;
|
||||
auto type = $3->typ.type;
|
||||
if (!is_int_val (count)) {
|
||||
error (count, "count must be an int constant");
|
||||
} else {
|
||||
type = vector_type (type, expr_int (count));
|
||||
}
|
||||
$$ = type;
|
||||
$$ = new_type_expr (type);
|
||||
}
|
||||
| AT_BASE '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (base_type ($3->typ.type));
|
||||
}
|
||||
| AT_VECTOR '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (vector_type ($3->typ.type, 0));
|
||||
}
|
||||
| AT_BASE '(' type_param ')' { $$ = base_type ($3); }
|
||||
| AT_VECTOR '(' type_param ')' { $$ = vector_type ($3, 0); }
|
||||
| AT_VECTOR '(' type_param ',' expr ')'
|
||||
{
|
||||
auto width = $5;
|
||||
auto type = $3;
|
||||
auto type = $3->typ.type;
|
||||
if (!is_int_val (width)) {
|
||||
error (width, "width must be an int constant");
|
||||
} else {
|
||||
type = vector_type (type, expr_int (width));
|
||||
}
|
||||
$$ = type;
|
||||
$$ = new_type_expr (type);
|
||||
}
|
||||
| AT_MATRIX '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (matrix_type ($3->typ.type, 0, 0));
|
||||
}
|
||||
| AT_MATRIX '(' type_param ')' { $$ = matrix_type ($3, 0, 0); }
|
||||
| AT_MATRIX '(' type_param ',' expr ',' expr ')'
|
||||
{
|
||||
auto cols = $5;
|
||||
auto rows = $7;
|
||||
auto type = $3;
|
||||
auto type = $3->typ.type;
|
||||
if (!is_int_val (cols)) {
|
||||
error (cols, "cols must be an int constant");
|
||||
} else if (!is_int_val (rows)) {
|
||||
|
@ -1114,12 +1133,24 @@ type_expr
|
|||
} else {
|
||||
type = matrix_type (type, expr_int (cols), expr_int (rows));
|
||||
}
|
||||
$$ = type;
|
||||
$$ = new_type_expr (type);
|
||||
}
|
||||
| AT_INT '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (int_type ($3->typ.type));
|
||||
}
|
||||
| AT_UINT '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (uint_type ($3->typ.type));
|
||||
}
|
||||
| AT_BOOL '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (bool_type ($3->typ.type));
|
||||
}
|
||||
| AT_FLOAT '(' type_param ')'
|
||||
{
|
||||
$$ = new_type_expr (float_type ($3->typ.type));
|
||||
}
|
||||
| AT_INT '(' type_param ')' { $$ = int_type ($3); }
|
||||
| AT_UINT '(' type_param ')' { $$ = uint_type ($3); }
|
||||
| AT_BOOL '(' type_param ')' { $$ = bool_type ($3); }
|
||||
| AT_FLOAT '(' type_param ')' { $$ = float_type ($3); }
|
||||
;
|
||||
|
||||
type_param
|
||||
|
@ -1128,15 +1159,15 @@ type_param
|
|||
;
|
||||
|
||||
type_list
|
||||
: type_ref
|
||||
| type_list ',' type_ref
|
||||
: type_ref { $$ = new_list_expr ($1); }
|
||||
| type_list ',' type_ref { $$ = expr_append_expr ($1, $3); }
|
||||
;
|
||||
|
||||
type_ref
|
||||
: TYPE_SPEC { $$ = $1.type; }
|
||||
| TYPE_NAME { $$ = $1.type; }
|
||||
| CLASS_NAME { $$ = $1->type; }
|
||||
| NAME { internal_error (nullptr, "not implemented"); }
|
||||
: TYPE_SPEC { $$ = new_type_expr ($1.type); }
|
||||
| TYPE_NAME { $$ = new_type_expr ($1.type); }
|
||||
| CLASS_NAME { $$ = new_type_expr ($1->type); }
|
||||
| NAME { $$ = new_symbol_expr ($1); }
|
||||
;
|
||||
|
||||
attribute_list
|
||||
|
@ -1861,15 +1892,15 @@ unary_expr
|
|||
}
|
||||
| AT_WIDTH '(' type_param ')'
|
||||
{
|
||||
$$ = new_int_expr (type_width ($3), false);
|
||||
$$ = new_int_expr (type_width ($3->typ.type), false);
|
||||
}
|
||||
| AT_ROWS '(' type_param ')'
|
||||
{
|
||||
$$ = new_int_expr (type_rows ($3), false);
|
||||
$$ = new_int_expr (type_rows ($3->typ.type), false);
|
||||
}
|
||||
| AT_COLS '(' type_param ')'
|
||||
{
|
||||
$$ = new_int_expr (type_cols ($3), false);
|
||||
$$ = new_int_expr (type_cols ($3->typ.type), false);
|
||||
}
|
||||
| vector_expr { $$ = new_vector_list ($1); }
|
||||
| obj_expr { $$ = $1; }
|
||||
|
|
Loading…
Reference in a new issue