Add new dynamic array syntax.
This commit is contained in:
parent
f08e53f5d2
commit
039572060e
@ -157,6 +157,7 @@ static void inst_datetime_defines(void);
|
||||
static void inst_binary_name(char *binfname);
|
||||
static int operatorname(char *name);
|
||||
static int parse_new_typename(const token_t *tok);
|
||||
static bool parse_new_typename(const token_t *tok, int *outp);
|
||||
static int parse_new_decl(declinfo_t *decl, const token_t *first, int flags);
|
||||
static int reparse_old_decl(declinfo_t *decl, int flags);
|
||||
static int reparse_new_decl(declinfo_t *decl, int flags);
|
||||
@ -2184,6 +2185,30 @@ static void declloc(int tokid)
|
||||
genarray(1, false);
|
||||
ldconst((cur_lit + glb_declared) * sizeof(cell), sPRI);
|
||||
copyarray(sym, cells * sizeof(cell));
|
||||
} else if (matchtoken(tNEW)) {
|
||||
int tag = 0;
|
||||
if (parse_new_typename(NULL, &tag)) {
|
||||
if (tag != type->tag)
|
||||
error(164, pc_typename(tag), pc_typename(type->tag));
|
||||
}
|
||||
|
||||
for (int i = 0; i < type->numdim; i++) {
|
||||
if (!needtoken('['))
|
||||
break;
|
||||
|
||||
value val;
|
||||
symbol *child;
|
||||
int ident = doexpr2(
|
||||
TRUE, FALSE, TRUE, FALSE,
|
||||
&type->idxtag[i],
|
||||
&child, 0, &val);
|
||||
pushreg(sPRI);
|
||||
|
||||
if (!needtoken(']'))
|
||||
break;
|
||||
}
|
||||
|
||||
genarray(type->numdim, true);
|
||||
} else if (lexpeek('{')) {
|
||||
// Dynamic array with fixed initializer.
|
||||
error(160);
|
||||
@ -3064,6 +3089,16 @@ static int parse_new_typename(const token_t *tok)
|
||||
return -1;
|
||||
}
|
||||
|
||||
static bool parse_new_typename(const token_t *tok, int *tagp)
|
||||
{
|
||||
int tag = parse_new_typename(tok);
|
||||
if (tag >= 0)
|
||||
*tagp = tag;
|
||||
else
|
||||
*tagp = 0;
|
||||
return true;
|
||||
}
|
||||
|
||||
static int parse_new_typeexpr(typeinfo_t *type, const token_t *first, int flags)
|
||||
{
|
||||
token_t tok;
|
||||
@ -3080,8 +3115,7 @@ static int parse_new_typeexpr(typeinfo_t *type, const token_t *first, int flags)
|
||||
lextok(&tok);
|
||||
}
|
||||
|
||||
type->tag = parse_new_typename(&tok);
|
||||
if (type->tag == -1)
|
||||
if (!parse_new_typename(&tok, &type->tag))
|
||||
goto err_out;
|
||||
|
||||
// Note: we could have already filled in the prefix array bits, so we check
|
||||
@ -4224,7 +4258,7 @@ static void parse_function_type(functag_t *type)
|
||||
int lparen = matchtoken('(');
|
||||
needtoken(tFUNCTION);
|
||||
|
||||
type->ret_tag = parse_new_typename(NULL);
|
||||
parse_new_typename(NULL, &type->ret_tag);
|
||||
type->usage = uPUBLIC;
|
||||
|
||||
needtoken('(');
|
||||
|
@ -207,6 +207,7 @@ static const char *errmsg[] = {
|
||||
/*161*/ "brackets after variable name indicate a fixed-size array, but a dynamic size was given - did you mean to use 'new %s[size]' syntax?\n",
|
||||
/*162*/ "cannot create dynamic arrays in global scope - did you mean to create a fixed-length array with brackets after the variable name?\n",
|
||||
/*163*/ "indeterminate array size in \"sizeof\" expression (symbol \"%s\")\n",
|
||||
/*164*/ "allocated array type '%s' doesn't match original type '%s'\n",
|
||||
#else
|
||||
"\315e\306\227\266k\217:\235\277bu\201fo\220\204\223\012",
|
||||
"\202l\224\250s\205g\346\356e\233\201(\243\315\214\267\202) \253 f\255low ea\305 \042c\353e\042\012",
|
||||
|
4
sourcepawn/compiler/tests/fail-dynamic-array-bad-type.sp
Normal file
4
sourcepawn/compiler/tests/fail-dynamic-array-bad-type.sp
Normal file
@ -0,0 +1,4 @@
|
||||
public main()
|
||||
{
|
||||
int[] x = new float[3];
|
||||
}
|
@ -0,0 +1 @@
|
||||
(3) : error 164: allocated array type 'float' doesn't match original type 'int'
|
10
sourcepawn/compiler/tests/ok-new-dynamic-array-syntax.sp
Normal file
10
sourcepawn/compiler/tests/ok-new-dynamic-array-syntax.sp
Normal file
@ -0,0 +1,10 @@
|
||||
native printnum(num);
|
||||
|
||||
public main()
|
||||
{
|
||||
new x = 4;
|
||||
new y = 8;
|
||||
int[][] v = new int[4][8];
|
||||
v[2][3] = 9;
|
||||
printnum(v[2][3]);
|
||||
}
|
Loading…
Reference in New Issue
Block a user