authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2016-02-01 17:25:38-07:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2016-02-01 17:25:38-07:00
log06f6acb4b19cab55dd8637a41c11501bf8e7158e
tree9d8226f9f2128a91b3038d9b6d739c3b36ee15cf
parent122b7b99660f2ce354930749ca545b363bf7849d

inline is a keyword instead of a directive


10 files changed, 81 insertions(+), 77 deletions(-)

doc/langref.md+1-1
...@@ -35,7 +35,7 @@ Directive = "#" "Symbol" "(" "String" ")"...@@ -35,7 +35,7 @@ Directive = "#" "Symbol" "(" "String" ")"
3535
36VisibleMod = "pub" | "export"36VisibleMod = "pub" | "export"
3737
38FnDef = FnProto Block38FnDef = option("inline") FnProto Block
3939
40ParamDeclList = "(" list(ParamDecl, ",") ")"40ParamDeclList = "(" list(ParamDecl, ",") ")"
4141
src/all_types.hpp+2-1
...@@ -174,13 +174,14 @@ enum VisibMod {...@@ -174,13 +174,14 @@ enum VisibMod {
174};174};
175175
176struct AstNodeFnProto {176struct AstNodeFnProto {
177 ZigList<AstNode *> *directives;177 ZigList<AstNode *> *directives; // can be null if no directives
178 VisibMod visib_mod;178 VisibMod visib_mod;
179 Buf name;179 Buf name;
180 ZigList<AstNode *> params;180 ZigList<AstNode *> params;
181 AstNode *return_type;181 AstNode *return_type;
182 bool is_var_args;182 bool is_var_args;
183 bool is_extern;183 bool is_extern;
184 bool is_inline;
184185
185 // populated by semantic analyzer:186 // populated by semantic analyzer:
186187
src/analyze.cpp+25-20
...@@ -714,29 +714,32 @@ static void resolve_function_proto(CodeGen *g, AstNode *node, FnTableEntry *fn_t...@@ -714,29 +714,32 @@ static void resolve_function_proto(CodeGen *g, AstNode *node, FnTableEntry *fn_t
714 return;714 return;
715 }715 }
716716
717 fn_table_entry->is_inline = fn_proto->is_inline;
718
717 bool is_naked = false;719 bool is_naked = false;
718 for (int i = 0; i < fn_proto->directives->length; i += 1) {720
719 AstNode *directive_node = fn_proto->directives->at(i);721 if (fn_proto->directives) {
720 Buf *name = &directive_node->data.directive.name;722 for (int i = 0; i < fn_proto->directives->length; i += 1) {
721723 AstNode *directive_node = fn_proto->directives->at(i);
722 if (buf_eql_str(name, "attribute")) {724 Buf *name = &directive_node->data.directive.name;
723 Buf *attr_name = &directive_node->data.directive.param;725
724 if (fn_table_entry->fn_def_node) {726 if (buf_eql_str(name, "attribute")) {
725 if (buf_eql_str(attr_name, "naked")) {727 Buf *attr_name = &directive_node->data.directive.param;
726 is_naked = true;728 if (fn_table_entry->fn_def_node) {
727 } else if (buf_eql_str(attr_name, "inline")) {729 if (buf_eql_str(attr_name, "naked")) {
728 fn_table_entry->is_inline = true;730 is_naked = true;
731 } else {
732 add_node_error(g, directive_node,
733 buf_sprintf("invalid function attribute: '%s'", buf_ptr(name)));
734 }
729 } else {735 } else {
730 add_node_error(g, directive_node,736 add_node_error(g, directive_node,
731 buf_sprintf("invalid function attribute: '%s'", buf_ptr(name)));737 buf_sprintf("invalid function attribute: '%s'", buf_ptr(name)));
732 }738 }
733 } else {739 } else {
734 add_node_error(g, directive_node,740 add_node_error(g, directive_node,
735 buf_sprintf("invalid function attribute: '%s'", buf_ptr(name)));741 buf_sprintf("invalid directive: '%s'", buf_ptr(name)));
736 }742 }
737 } else {
738 add_node_error(g, directive_node,
739 buf_sprintf("invalid directive: '%s'", buf_ptr(name)));
740 }743 }
741 }744 }
742745
...@@ -5174,11 +5177,13 @@ void semantic_analyze(CodeGen *g) {...@@ -5174,11 +5177,13 @@ void semantic_analyze(CodeGen *g) {
5174 for (int i = 0; i < import->root->data.root.top_level_decls.length; i += 1) {5177 for (int i = 0; i < import->root->data.root.top_level_decls.length; i += 1) {
5175 AstNode *child = import->root->data.root.top_level_decls.at(i);5178 AstNode *child = import->root->data.root.top_level_decls.at(i);
5176 if (child->type == NodeTypeImport) {5179 if (child->type == NodeTypeImport) {
5177 for (int i = 0; i < child->data.import.directives->length; i += 1) {5180 if (child->data.import.directives) {
5178 AstNode *directive_node = child->data.import.directives->at(i);5181 for (int i = 0; i < child->data.import.directives->length; i += 1) {
5179 Buf *name = &directive_node->data.directive.name;5182 AstNode *directive_node = child->data.import.directives->at(i);
5180 add_node_error(g, directive_node,5183 Buf *name = &directive_node->data.directive.name;
5181 buf_sprintf("invalid directive: '%s'", buf_ptr(name)));5184 add_node_error(g, directive_node,
5185 buf_sprintf("invalid directive: '%s'", buf_ptr(name)));
5186 }
5182 }5187 }
51835188
5184 ImportTableEntry *target_import = child->data.import.import;5189 ImportTableEntry *target_import = child->data.import.import;
src/ast_render.cpp+10-3
...@@ -77,6 +77,10 @@ static const char *extern_string(bool is_extern) {...@@ -77,6 +77,10 @@ static const char *extern_string(bool is_extern) {
77 return is_extern ? "extern " : "";77 return is_extern ? "extern " : "";
78}78}
7979
80static const char *inline_string(bool is_inline) {
81 return is_inline ? "inline " : "";
82}
83
80static const char *const_or_var_string(bool is_const) {84static const char *const_or_var_string(bool is_const) {
81 return is_const ? "const" : "var";85 return is_const ? "const" : "var";
82}86}
...@@ -553,7 +557,8 @@ static void render_node(AstRender *ar, AstNode *node) {...@@ -553,7 +557,8 @@ static void render_node(AstRender *ar, AstNode *node) {
553 const char *fn_name = buf_ptr(&node->data.fn_proto.name);557 const char *fn_name = buf_ptr(&node->data.fn_proto.name);
554 const char *pub_str = visib_mod_string(node->data.fn_proto.visib_mod);558 const char *pub_str = visib_mod_string(node->data.fn_proto.visib_mod);
555 const char *extern_str = extern_string(node->data.fn_proto.is_extern);559 const char *extern_str = extern_string(node->data.fn_proto.is_extern);
556 fprintf(ar->f, "%s%sfn %s(", pub_str, extern_str, fn_name);560 const char *inline_str = inline_string(node->data.fn_proto.is_inline);
561 fprintf(ar->f, "%s%s%sfn %s(", pub_str, inline_str, extern_str, fn_name);
557 int arg_count = node->data.fn_proto.params.length;562 int arg_count = node->data.fn_proto.params.length;
558 bool is_var_args = node->data.fn_proto.is_var_args;563 bool is_var_args = node->data.fn_proto.is_var_args;
559 for (int arg_i = 0; arg_i < arg_count; arg_i += 1) {564 for (int arg_i = 0; arg_i < arg_count; arg_i += 1) {
...@@ -583,8 +588,10 @@ static void render_node(AstRender *ar, AstNode *node) {...@@ -583,8 +588,10 @@ static void render_node(AstRender *ar, AstNode *node) {
583 break;588 break;
584 }589 }
585 case NodeTypeFnDef:590 case NodeTypeFnDef:
586 for (int i = 0; i < node->data.fn_def.fn_proto->data.fn_proto.directives->length; i += 1) {591 if (node->data.fn_def.fn_proto->data.fn_proto.directives) {
587 render_node(ar, node->data.fn_def.fn_proto->data.fn_proto.directives->at(i));592 for (int i = 0; i < node->data.fn_def.fn_proto->data.fn_proto.directives->length; i += 1) {
593 render_node(ar, node->data.fn_def.fn_proto->data.fn_proto.directives->at(i));
594 }
588 }595 }
589 render_node(ar, node->data.fn_def.fn_proto);596 render_node(ar, node->data.fn_def.fn_proto);
590 fprintf(ar->f, " ");597 fprintf(ar->f, " ");
src/codegen.cpp+16-13
...@@ -3338,20 +3338,23 @@ static ImportTableEntry *codegen_add_code(CodeGen *g, Buf *abs_full_path,...@@ -3338,20 +3338,23 @@ static ImportTableEntry *codegen_add_code(CodeGen *g, Buf *abs_full_path,
3338 add_node_error(g, top_level_decl,3338 add_node_error(g, top_level_decl,
3339 buf_sprintf("root export declaration only valid in root source file"));3339 buf_sprintf("root export declaration only valid in root source file"));
3340 } else {3340 } else {
3341 for (int i = 0; i < top_level_decl->data.root_export_decl.directives->length; i += 1) {3341 ZigList<AstNode *> *directives = top_level_decl->data.root_export_decl.directives;
3342 AstNode *directive_node = top_level_decl->data.root_export_decl.directives->at(i);3342 if (directives) {
3343 Buf *name = &directive_node->data.directive.name;3343 for (int i = 0; i < directives->length; i += 1) {
3344 Buf *param = &directive_node->data.directive.param;3344 AstNode *directive_node = directives->at(i);
3345 if (buf_eql_str(name, "version")) {3345 Buf *name = &directive_node->data.directive.name;
3346 set_root_export_version(g, param, directive_node);3346 Buf *param = &directive_node->data.directive.param;
3347 } else if (buf_eql_str(name, "link")) {3347 if (buf_eql_str(name, "version")) {
3348 g->link_table.put(param, true);3348 set_root_export_version(g, param, directive_node);
3349 if (buf_eql_str(param, "c")) {3349 } else if (buf_eql_str(name, "link")) {
3350 g->link_libc = true;3350 g->link_table.put(param, true);
3351 if (buf_eql_str(param, "c")) {
3352 g->link_libc = true;
3353 }
3354 } else {
3355 add_node_error(g, directive_node,
3356 buf_sprintf("invalid directive: '%s'", buf_ptr(name)));
3351 }3357 }
3352 } else {
3353 add_node_error(g, directive_node,
3354 buf_sprintf("invalid directive: '%s'", buf_ptr(name)));
3355 }3358 }
3356 }3359 }
33573360
src/parseh.cpp+2-19
...@@ -115,10 +115,6 @@ static AstNode *create_field_access_node(Context *c, const char *lhs, const char...@@ -115,10 +115,6 @@ static AstNode *create_field_access_node(Context *c, const char *lhs, const char
115 return node;115 return node;
116}116}
117117
118static ZigList<AstNode *> *create_empty_directives(Context *c) {
119 return allocate<ZigList<AstNode*>>(1);
120}
121
122static AstNode *create_typed_var_decl_node(Context *c, bool is_const, const char *var_name,118static AstNode *create_typed_var_decl_node(Context *c, bool is_const, const char *var_name,
123 AstNode *type_node, AstNode *init_node)119 AstNode *type_node, AstNode *init_node)
124{120{
...@@ -127,7 +123,7 @@ static AstNode *create_typed_var_decl_node(Context *c, bool is_const, const char...@@ -127,7 +123,7 @@ static AstNode *create_typed_var_decl_node(Context *c, bool is_const, const char
127 node->data.variable_declaration.is_const = is_const;123 node->data.variable_declaration.is_const = is_const;
128 node->data.variable_declaration.visib_mod = c->visib_mod;124 node->data.variable_declaration.visib_mod = c->visib_mod;
129 node->data.variable_declaration.expr = init_node;125 node->data.variable_declaration.expr = init_node;
130 node->data.variable_declaration.directives = create_empty_directives(c);126 node->data.variable_declaration.directives = nullptr;
131 node->data.variable_declaration.type = type_node;127 node->data.variable_declaration.type = type_node;
132 normalize_parent_ptrs(node);128 normalize_parent_ptrs(node);
133 return node;129 return node;
...@@ -150,7 +146,6 @@ static AstNode *create_struct_field_node(Context *c, const char *name, AstNode *...@@ -150,7 +146,6 @@ static AstNode *create_struct_field_node(Context *c, const char *name, AstNode *
150 assert(type_node);146 assert(type_node);
151 AstNode *node = create_node(c, NodeTypeStructField);147 AstNode *node = create_node(c, NodeTypeStructField);
152 buf_init_from_str(&node->data.struct_field.name, name);148 buf_init_from_str(&node->data.struct_field.name, name);
153 node->data.struct_field.directives = create_empty_directives(c);
154 node->data.struct_field.visib_mod = VisibModPub;149 node->data.struct_field.visib_mod = VisibModPub;
155 node->data.struct_field.type = type_node;150 node->data.struct_field.type = type_node;
156151
...@@ -197,18 +192,10 @@ static AstNode *create_num_lit_signed(Context *c, int64_t x) {...@@ -197,18 +192,10 @@ static AstNode *create_num_lit_signed(Context *c, int64_t x) {
197 return create_prefix_node(c, PrefixOpNegation, num_lit_node);192 return create_prefix_node(c, PrefixOpNegation, num_lit_node);
198}193}
199194
200static AstNode *create_directive_node(Context *c, const char *name, const char *value) {
201 AstNode *node = create_node(c, NodeTypeDirective);
202 buf_init_from_str(&node->data.directive.name, name);
203 buf_init_from_str(&node->data.directive.param, value);
204 return node;
205}
206
207static AstNode *create_type_decl_node(Context *c, const char *name, AstNode *child_type_node) {195static AstNode *create_type_decl_node(Context *c, const char *name, AstNode *child_type_node) {
208 AstNode *node = create_node(c, NodeTypeTypeDecl);196 AstNode *node = create_node(c, NodeTypeTypeDecl);
209 buf_init_from_str(&node->data.type_decl.symbol, name);197 buf_init_from_str(&node->data.type_decl.symbol, name);
210 node->data.type_decl.visib_mod = c->visib_mod;198 node->data.type_decl.visib_mod = c->visib_mod;
211 node->data.type_decl.directives = create_empty_directives(c);
212 node->data.type_decl.child_type = child_type_node;199 node->data.type_decl.child_type = child_type_node;
213200
214 normalize_parent_ptrs(node);201 normalize_parent_ptrs(node);
...@@ -224,8 +211,7 @@ static AstNode *make_type_node(Context *c, TypeTableEntry *type_entry) {...@@ -224,8 +211,7 @@ static AstNode *make_type_node(Context *c, TypeTableEntry *type_entry) {
224static AstNode *create_fn_proto_node(Context *c, Buf *name, TypeTableEntry *fn_type) {211static AstNode *create_fn_proto_node(Context *c, Buf *name, TypeTableEntry *fn_type) {
225 assert(fn_type->id == TypeTableEntryIdFn);212 assert(fn_type->id == TypeTableEntryIdFn);
226 AstNode *node = create_node(c, NodeTypeFnProto);213 AstNode *node = create_node(c, NodeTypeFnProto);
227 node->data.fn_proto.directives = create_empty_directives(c);214 node->data.fn_proto.is_inline = true;
228 node->data.fn_proto.directives->append(create_directive_node(c, "attribute", "inline"));
229 node->data.fn_proto.visib_mod = c->visib_mod;215 node->data.fn_proto.visib_mod = c->visib_mod;
230 buf_init_from_buf(&node->data.fn_proto.name, name);216 buf_init_from_buf(&node->data.fn_proto.name, name);
231 node->data.fn_proto.return_type = make_type_node(c, fn_type->data.fn.fn_type_id.return_type);217 node->data.fn_proto.return_type = make_type_node(c, fn_type->data.fn.fn_type_id.return_type);
...@@ -642,7 +628,6 @@ static void visit_fn_decl(Context *c, const FunctionDecl *fn_decl) {...@@ -642,7 +628,6 @@ static void visit_fn_decl(Context *c, const FunctionDecl *fn_decl) {
642628
643 node->data.fn_proto.is_extern = fn_type->data.fn.fn_type_id.is_extern;629 node->data.fn_proto.is_extern = fn_type->data.fn.fn_type_id.is_extern;
644 node->data.fn_proto.visib_mod = c->visib_mod;630 node->data.fn_proto.visib_mod = c->visib_mod;
645 node->data.fn_proto.directives = create_empty_directives(c);
646 node->data.fn_proto.is_var_args = fn_type->data.fn.fn_type_id.is_var_args;631 node->data.fn_proto.is_var_args = fn_type->data.fn.fn_type_id.is_var_args;
647 node->data.fn_proto.return_type = make_type_node(c, fn_type->data.fn.fn_type_id.return_type);632 node->data.fn_proto.return_type = make_type_node(c, fn_type->data.fn.fn_type_id.return_type);
648633
...@@ -826,7 +811,6 @@ static void visit_enum_decl(Context *c, const EnumDecl *enum_decl) {...@@ -826,7 +811,6 @@ static void visit_enum_decl(Context *c, const EnumDecl *enum_decl) {
826 buf_init_from_buf(&enum_node->data.struct_decl.name, full_type_name);811 buf_init_from_buf(&enum_node->data.struct_decl.name, full_type_name);
827 enum_node->data.struct_decl.kind = ContainerKindEnum;812 enum_node->data.struct_decl.kind = ContainerKindEnum;
828 enum_node->data.struct_decl.visib_mod = VisibModExport;813 enum_node->data.struct_decl.visib_mod = VisibModExport;
829 enum_node->data.struct_decl.directives = create_empty_directives(c);
830 enum_node->data.struct_decl.type_entry = enum_type;814 enum_node->data.struct_decl.type_entry = enum_type;
831815
832 for (uint32_t i = 0; i < field_count; i += 1) {816 for (uint32_t i = 0; i < field_count; i += 1) {
...@@ -998,7 +982,6 @@ static void visit_record_decl(Context *c, const RecordDecl *record_decl) {...@@ -998,7 +982,6 @@ static void visit_record_decl(Context *c, const RecordDecl *record_decl) {
998 buf_init_from_buf(&struct_node->data.struct_decl.name, &struct_type->name);982 buf_init_from_buf(&struct_node->data.struct_decl.name, &struct_type->name);
999 struct_node->data.struct_decl.kind = ContainerKindStruct;983 struct_node->data.struct_decl.kind = ContainerKindStruct;
1000 struct_node->data.struct_decl.visib_mod = VisibModExport;984 struct_node->data.struct_decl.visib_mod = VisibModExport;
1001 struct_node->data.struct_decl.directives = create_empty_directives(c);
1002 struct_node->data.struct_decl.type_entry = struct_type;985 struct_node->data.struct_decl.type_entry = struct_type;
1003986
1004 for (uint32_t i = 0; i < struct_type->data.structure.src_field_count; i += 1) {987 for (uint32_t i = 0; i < struct_type->data.structure.src_field_count; i += 1) {
src/parser.cpp+19-17
...@@ -82,13 +82,6 @@ static AstNode *ast_create_node(ParseContext *pc, NodeType type, Token *first_to...@@ -82,13 +82,6 @@ static AstNode *ast_create_node(ParseContext *pc, NodeType type, Token *first_to
82 return node;82 return node;
83}83}
8484
85static AstNode *ast_create_node_with_node(ParseContext *pc, NodeType type, AstNode *other_node) {
86 AstNode *node = ast_create_node_no_line_info(pc, type);
87 node->line = other_node->line;
88 node->column = other_node->column;
89 return node;
90}
91
92static AstNode *ast_create_void_type_node(ParseContext *pc, Token *token) {85static AstNode *ast_create_void_type_node(ParseContext *pc, Token *token) {
93 AstNode *node = ast_create_node(pc, NodeTypeSymbol, token);86 AstNode *node = ast_create_node(pc, NodeTypeSymbol, token);
94 buf_init_from_str(&node->data.symbol_expr.symbol, "void");87 buf_init_from_str(&node->data.symbol_expr.symbol, "void");
...@@ -2240,15 +2233,26 @@ static AstNode *ast_parse_fn_proto(ParseContext *pc, int *token_index, bool mand...@@ -2240,15 +2233,26 @@ static AstNode *ast_parse_fn_proto(ParseContext *pc, int *token_index, bool mand
2240}2233}
22412234
2242/*2235/*
2243FnDef : FnProto Block2236FnDef = option("inline") FnProto Block
2244*/2237*/
2245static AstNode *ast_parse_fn_def(ParseContext *pc, int *token_index, bool mandatory,2238static AstNode *ast_parse_fn_def(ParseContext *pc, int *token_index, bool mandatory,
2246 ZigList<AstNode*> *directives, VisibMod visib_mod)2239 ZigList<AstNode*> *directives, VisibMod visib_mod)
2247{2240{
2241 Token *first_token = &pc->tokens->at(*token_index);
2242 bool is_inline;
2243 if (first_token->id == TokenIdKeywordInline) {
2244 *token_index += 1;
2245 is_inline = true;
2246 } else {
2247 is_inline = false;
2248 }
2249
2248 AstNode *fn_proto = ast_parse_fn_proto(pc, token_index, mandatory, directives, visib_mod);2250 AstNode *fn_proto = ast_parse_fn_proto(pc, token_index, mandatory, directives, visib_mod);
2249 if (!fn_proto)2251 if (!fn_proto)
2250 return nullptr;2252 return nullptr;
2251 AstNode *node = ast_create_node_with_node(pc, NodeTypeFnDef, fn_proto);2253 AstNode *node = ast_create_node(pc, NodeTypeFnDef, first_token);
2254
2255 fn_proto->data.fn_proto.is_inline = is_inline;
22522256
2253 node->data.fn_def.fn_proto = fn_proto;2257 node->data.fn_def.fn_proto = fn_proto;
2254 node->data.fn_def.body = ast_parse_block(pc, token_index, true);2258 node->data.fn_def.body = ast_parse_block(pc, token_index, true);
...@@ -2646,8 +2650,10 @@ static void set_field(AstNode **field) {...@@ -2646,8 +2650,10 @@ static void set_field(AstNode **field) {
2646}2650}
26472651
2648static void set_list_fields(ZigList<AstNode*> *list) {2652static void set_list_fields(ZigList<AstNode*> *list) {
2649 for (int i = 0; i < list->length; i += 1) {2653 if (list) {
2650 set_field(&list->at(i));2654 for (int i = 0; i < list->length; i += 1) {
2655 set_field(&list->at(i));
2656 }
2651 }2657 }
2652}2658}
26532659
...@@ -2661,9 +2667,7 @@ void normalize_parent_ptrs(AstNode *node) {...@@ -2661,9 +2667,7 @@ void normalize_parent_ptrs(AstNode *node) {
2661 break;2667 break;
2662 case NodeTypeFnProto:2668 case NodeTypeFnProto:
2663 set_field(&node->data.fn_proto.return_type);2669 set_field(&node->data.fn_proto.return_type);
2664 if (node->data.fn_proto.directives) {2670 set_list_fields(node->data.fn_proto.directives);
2665 set_list_fields(node->data.fn_proto.directives);
2666 }
2667 set_list_fields(&node->data.fn_proto.params);2671 set_list_fields(&node->data.fn_proto.params);
2668 break;2672 break;
2669 case NodeTypeFnDef:2673 case NodeTypeFnDef:
...@@ -2686,9 +2690,7 @@ void normalize_parent_ptrs(AstNode *node) {...@@ -2686,9 +2690,7 @@ void normalize_parent_ptrs(AstNode *node) {
2686 set_field(&node->data.return_expr.expr);2690 set_field(&node->data.return_expr.expr);
2687 break;2691 break;
2688 case NodeTypeVariableDeclaration:2692 case NodeTypeVariableDeclaration:
2689 if (node->data.variable_declaration.directives) {2693 set_list_fields(node->data.variable_declaration.directives);
2690 set_list_fields(node->data.variable_declaration.directives);
2691 }
2692 set_field(&node->data.variable_declaration.type);2694 set_field(&node->data.variable_declaration.type);
2693 set_field(&node->data.variable_declaration.expr);2695 set_field(&node->data.variable_declaration.expr);
2694 break;2696 break;
src/tokenizer.cpp+4-1
...@@ -101,7 +101,7 @@ const char * zig_keywords[] = {...@@ -101,7 +101,7 @@ const char * zig_keywords[] = {
101 "true", "false", "null", "fn", "return", "var", "const", "extern",101 "true", "false", "null", "fn", "return", "var", "const", "extern",
102 "pub", "export", "import", "c_import", "if", "else", "goto", "asm",102 "pub", "export", "import", "c_import", "if", "else", "goto", "asm",
103 "volatile", "struct", "enum", "while", "for", "continue", "break",103 "volatile", "struct", "enum", "while", "for", "continue", "break",
104 "null", "noalias", "switch", "undefined", "error", "type"104 "null", "noalias", "switch", "undefined", "error", "type", "inline",
105};105};
106106
107bool is_zig_keyword(Buf *buf) {107bool is_zig_keyword(Buf *buf) {
...@@ -273,6 +273,8 @@ static void end_token(Tokenize *t) {...@@ -273,6 +273,8 @@ static void end_token(Tokenize *t) {
273 t->cur_tok->id = TokenIdKeywordError;273 t->cur_tok->id = TokenIdKeywordError;
274 } else if (mem_eql_str(token_mem, token_len, "type")) {274 } else if (mem_eql_str(token_mem, token_len, "type")) {
275 t->cur_tok->id = TokenIdKeywordType;275 t->cur_tok->id = TokenIdKeywordType;
276 } else if (mem_eql_str(token_mem, token_len, "inline")) {
277 t->cur_tok->id = TokenIdKeywordInline;
276 }278 }
277279
278 t->cur_tok = nullptr;280 t->cur_tok = nullptr;
...@@ -1087,6 +1089,7 @@ const char * token_name(TokenId id) {...@@ -1087,6 +1089,7 @@ const char * token_name(TokenId id) {
1087 case TokenIdKeywordUndefined: return "undefined";1089 case TokenIdKeywordUndefined: return "undefined";
1088 case TokenIdKeywordError: return "error";1090 case TokenIdKeywordError: return "error";
1089 case TokenIdKeywordType: return "type";1091 case TokenIdKeywordType: return "type";
1092 case TokenIdKeywordInline: return "inline";
1090 case TokenIdLParen: return "(";1093 case TokenIdLParen: return "(";
1091 case TokenIdRParen: return ")";1094 case TokenIdRParen: return ")";
1092 case TokenIdComma: return ",";1095 case TokenIdComma: return ",";
src/tokenizer.hpp+1
...@@ -41,6 +41,7 @@ enum TokenId {...@@ -41,6 +41,7 @@ enum TokenId {
41 TokenIdKeywordUndefined,41 TokenIdKeywordUndefined,
42 TokenIdKeywordError,42 TokenIdKeywordError,
43 TokenIdKeywordType,43 TokenIdKeywordType,
44 TokenIdKeywordInline,
44 TokenIdLParen,45 TokenIdLParen,
45 TokenIdRParen,46 TokenIdRParen,
46 TokenIdComma,47 TokenIdComma,
test/run_tests.cpp+1-2
...@@ -2114,8 +2114,7 @@ extern void (*fn_ptr)(void);...@@ -2114,8 +2114,7 @@ extern void (*fn_ptr)(void);
2114#define foo fn_ptr2114#define foo fn_ptr
2115 )SOURCE", 2,2115 )SOURCE", 2,
2116 "pub extern var fn_ptr: ?extern fn();",2116 "pub extern var fn_ptr: ?extern fn();",
2117 R"SOURCE(#attribute("inline")2117 R"SOURCE(pub inline fn foo() {
2118pub fn foo() {
2119 (??fn_ptr)()2118 (??fn_ptr)()
2120})SOURCE");2119})SOURCE");
2121}2120}