static type_t *type_const_char = NULL;
static type_t *type_string = NULL;
static type_t *type_void = NULL;
+static type_t *type_void_ptr = NULL;
static type_t *type_size_t = NULL;
static type_t *type_ptrdiff_t = NULL;
const_t *cnst = allocate_ast_zero(sizeof(cnst[0]));
cnst->expression.type = EXPR_CONST;
- cnst->expression.datatype = type_int;
+ cnst->expression.datatype = token.datatype;
cnst->v.int_value = token.v.intvalue;
next_token();
const_t *cnst = allocate_ast_zero(sizeof(cnst[0]));
cnst->expression.type = EXPR_CONST;
- cnst->expression.datatype = type_double;
+ cnst->expression.datatype = token.datatype;
cnst->v.float_value = token.v.floatvalue;
next_token();
return (expression_t*) expression;
}
+static type_t *make_function_1_type(type_t *result_type, type_t *argument_type)
+{
+ function_parameter_t *parameter = allocate_type_zero(sizeof(parameter[0]));
+ parameter->type = argument_type;
+
+ function_type_t *type = allocate_type_zero(sizeof(type[0]));
+ type->type.type = TYPE_FUNCTION;
+ type->result_type = result_type;
+ type->parameters = parameter;
+
+ type_t *result = typehash_insert((type_t*) type);
+ if(result != (type_t*) type) {
+ free_type(type);
+ }
+
+ return result;
+}
+
static expression_t *parse_builtin_symbol(void)
{
builtin_symbol_expression_t *expression
= allocate_ast_zero(sizeof(expression[0]));
expression->expression.type = EXPR_BUILTIN_SYMBOL;
- /* TODO: set datatype */
-
expression->symbol = token.v.symbol;
+ type_t *type;
+ switch(token.type) {
+ case T___builtin_alloca:
+ type = make_function_1_type(type_void_ptr, type_size_t);
+ break;
+ }
+
next_token();
+ expression->expression.datatype = type;
return (expression_t*) expression;
}
return parse_offsetof();
case T___builtin_va_arg:
return parse_va_arg();
+ case T___builtin_alloca:
case T___builtin_expect:
case T___builtin_va_start:
case T___builtin_va_end:
eat('[');
+ expression_t *index = parse_expression();
+
array_access_expression_t *array_access
= allocate_ast_zero(sizeof(array_access[0]));
- array_access->expression.type = EXPR_ARRAY_ACCESS;
- array_access->array_ref = array_ref;
- array_access->index = parse_expression();
+ array_access->expression.type = EXPR_ARRAY_ACCESS;
+ array_access->array_ref = array_ref;
+ array_access->index = index;
- type_t *type = array_ref->datatype;
- if(type != NULL) {
- if(type->type == TYPE_POINTER) {
- pointer_type_t *pointer = (pointer_type_t*) type;
+ type_t *type_left = skip_typeref(array_ref->datatype);
+ type_t *type_right = skip_typeref(index->datatype);
+
+ if(type_left != NULL && type_right != NULL) {
+ if(type_left->type == TYPE_POINTER) {
+ pointer_type_t *pointer = (pointer_type_t*) type_left;
+ array_access->expression.datatype = pointer->points_to;
+ } else if(type_left->type == TYPE_ARRAY) {
+ array_type_t *array_type = (array_type_t*) type_left;
+ array_access->expression.datatype = array_type->element_type;
+ } else if(type_right->type == TYPE_POINTER) {
+ pointer_type_t *pointer = (pointer_type_t*) type_right;
array_access->expression.datatype = pointer->points_to;
- } else if(type->type == TYPE_ARRAY) {
- array_type_t *array_type = (array_type_t*) type;
+ } else if(type_right->type == TYPE_ARRAY) {
+ array_type_t *array_type = (array_type_t*) type_right;
array_access->expression.datatype = array_type->element_type;
} else {
parser_print_error_prefix();
- fprintf(stderr, "array access on object with non-pointer type ");
- print_type_quoted(type);
+ fprintf(stderr, "array access on object with non-pointer types ");
+ print_type_quoted(type_left);
+ fprintf(stderr, ", ");
+ print_type_quoted(type_right);
fprintf(stderr, "\n");
}
}
label->expression = parse_expression();
expect(':');
- label->statement.next = parse_statement();
+ label->label_statement = parse_statement();
return (statement_t*) label;
}
label->statement.source_position = token.source_position;
expect(':');
- label->statement.next = parse_statement();
+ label->label_statement = parse_statement();
return (statement_t*) label;
}
type_ptrdiff_t = make_atomic_type(ATOMIC_TYPE_LONG, 0);
type_const_char = make_atomic_type(ATOMIC_TYPE_CHAR, TYPE_QUALIFIER_CONST);
type_void = make_atomic_type(ATOMIC_TYPE_VOID, 0);
+ type_void_ptr = make_pointer_type(type_void, 0);
type_string = make_pointer_type(type_const_char, 0);
}