Commit d27b76fc31

Andrew Kelley <superjoe30@gmail.com>
2016-01-27 20:28:05
add error for `@typeof` or `&` of number literal
closes #85
1 parent fe0c6a3
Changed files (2)
src/analyze.cpp
@@ -3426,10 +3426,30 @@ static TypeTableEntry *analyze_builtin_fn_call_expr(CodeGen *g, ImportTableEntry
                 AstNode *expr_node = node->data.fn_call_expr.params.at(0);
                 TypeTableEntry *type_entry = analyze_expression(g, import, context, nullptr, expr_node);
 
-                if (type_entry->id == TypeTableEntryIdInvalid) {
-                    return g->builtin_types.entry_invalid;
-                } else {
-                    return resolve_expr_const_val_as_type(g, node, type_entry);
+                switch (type_entry->id) {
+                    case TypeTableEntryIdInvalid:
+                        return type_entry;
+                    case TypeTableEntryIdNumLitFloat:
+                    case TypeTableEntryIdNumLitInt:
+                    case TypeTableEntryIdUndefLit:
+                        add_node_error(g, expr_node,
+                                buf_sprintf("type '%s' not eligible for @typeof", buf_ptr(&type_entry->name)));
+                        return g->builtin_types.entry_invalid;
+                    case TypeTableEntryIdMetaType:
+                    case TypeTableEntryIdVoid:
+                    case TypeTableEntryIdBool:
+                    case TypeTableEntryIdUnreachable:
+                    case TypeTableEntryIdInt:
+                    case TypeTableEntryIdFloat:
+                    case TypeTableEntryIdPointer:
+                    case TypeTableEntryIdArray:
+                    case TypeTableEntryIdStruct:
+                    case TypeTableEntryIdMaybe:
+                    case TypeTableEntryIdErrorUnion:
+                    case TypeTableEntryIdPureError:
+                    case TypeTableEntryIdEnum:
+                    case TypeTableEntryIdFn:
+                        return resolve_expr_const_val_as_type(g, node, type_entry);
                 }
             }
         case BuiltinFnIdCInclude:
@@ -3729,6 +3749,12 @@ static TypeTableEntry *analyze_prefix_op_expr(CodeGen *g, ImportTableEntry *impo
                         return resolve_expr_const_val_as_type(g, node,
                                 get_pointer_to_type(g, meta_type, is_const));
                     }
+                } else if (child_type->id == TypeTableEntryIdNumLitInt ||
+                           child_type->id == TypeTableEntryIdNumLitFloat)
+                {
+                    add_node_error(g, expr_node,
+                        buf_sprintf("unable to get address of type '%s'", buf_ptr(&child_type->name)));
+                    return g->builtin_types.entry_invalid;
                 } else {
                     return get_pointer_to_type(g, child_type, is_const);
                 }
test/run_tests.cpp
@@ -999,7 +999,7 @@ pub fn main(args: [][]u8) -> %void {
 
     add_simple_case("order-independent declarations", R"SOURCE(
 import "std.zig";
-const z : @typeof(stdin_fileno) = 0;
+const z = stdin_fileno;
 const x : @typeof(y) = 1234;
 const y : u16 = 5678;
 pub fn main(args: [][]u8) -> %void {
@@ -1683,6 +1683,18 @@ c_import {
     add_compile_fail_case("empty file", "",
             1, ".tmp_source.zig:1:1: error: missing export declaration and output name not provided");
 
+    add_compile_fail_case("address of number literal", R"SOURCE(
+const x = 3;
+const y = &x;
+    )SOURCE", 1, ".tmp_source.zig:3:12: error: unable to get address of type '(integer literal)'");
+
+    add_compile_fail_case("@typeof number literal", R"SOURCE(
+const x = 3;
+struct Foo {
+    index: @typeof(x),
+}
+    )SOURCE", 1, ".tmp_source.zig:4:20: error: type '(integer literal)' not eligible for @typeof");
+
 }
 
 static void print_compiler_invocation(TestCase *test_case) {