out = (ast_expression*)asbinstore;
break;
+ case opid3('l', 'e', 'n'):
+ if (exprs[0]->vtype != TYPE_STRING && exprs[0]->vtype != TYPE_ARRAY) {
+ ast_type_to_string(exprs[0], ty1, sizeof(ty1));
+ compile_error(ast_ctx(exprs[0]), "invalid type for length operator: %s", ty1);
+ return false;
+ }
+ /* strings must be const, arrays are statically sized */
+ if (exprs[0]->vtype == TYPE_STRING &&
+ !(((ast_value*)exprs[0])->hasvalue && ((ast_value*)exprs[0])->cvq == CV_CONST))
+ {
+ compile_error(ast_ctx(exprs[0]), "operand of length operator not a valid constant expression");
+ return false;
+ }
+ out = fold_op(parser->fold, op, exprs);
+ break;
+
case opid2('~', 'P'):
if (exprs[0]->vtype != TYPE_FLOAT && exprs[0]->vtype != TYPE_VECTOR) {
ast_type_to_string(exprs[0], ty1, sizeof(ty1));
if (parser->tok == TOKEN_IDENT)
typevar = parser_find_typedef(parser, parser_tokval(parser), 0);
if (typevar || parser->tok == TOKEN_TYPENAME) {
- if (!parse_variable(parser, block, false, CV_NONE, typevar, false, false, 0, NULL)) {
+ if (!parse_variable(parser, block, true, CV_NONE, typevar, false, false, 0, NULL)) {
ast_delete(switchnode);
return false;
}
ast_delete(switchnode);
return false;
}
- if (!parse_variable(parser, block, false, cvq, NULL, noref, is_static, qflags, NULL)) {
+ if (!parse_variable(parser, block, true, cvq, NULL, noref, is_static, qflags, NULL)) {
ast_delete(switchnode);
return false;
}
{
if (cvq == CV_WRONG)
return false;
- return parse_variable(parser, block, true, cvq, NULL, noref, is_static, qflags, vstring);
+ return parse_variable(parser, block, false, cvq, NULL, noref, is_static, qflags, vstring);
}
else if (parser->tok == TOKEN_KEYWORD)
{
{
if (cvq == CV_WRONG)
return false;
- return parse_variable(parser, NULL, true, cvq, NULL, noref, is_static, qflags, vstring);
+ return parse_variable(parser, NULL, false, cvq, NULL, noref, is_static, qflags, vstring);
}
else if (parser->tok == TOKEN_IDENT && !strcmp(parser_tokval(parser), "enum"))
{