authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2017-08-31 16:54:20-04:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2017-08-31 16:54:20-04:00
logc42e809f132d91fca1f96da2ecff7d78e1085c3f
treecebe89ba65d63fa5518a08977725553a0b374b8c
parent67b6dd28ec70937a29176719b56457ee17b1c136

setEvalBranchQuota must be called from top of comptime stack


3 files changed, 19 insertions(+), 3 deletions(-)

src/all_types.hpp-1
...@@ -50,7 +50,6 @@ struct IrExecutable {...@@ -50,7 +50,6 @@ struct IrExecutable {
50 size_t next_debug_id;50 size_t next_debug_id;
51 size_t *backward_branch_count;51 size_t *backward_branch_count;
52 size_t backward_branch_quota;52 size_t backward_branch_quota;
53 bool reported_quota_exceeded;
54 bool invalid;53 bool invalid;
55 ZigList<LabelTableEntry *> all_labels;54 ZigList<LabelTableEntry *> all_labels;
56 ZigList<IrGotoItem> goto_list;55 ZigList<IrGotoItem> goto_list;
src/ir.cpp+8-2
...@@ -7604,13 +7604,13 @@ static bool ir_emit_backward_branch(IrAnalyze *ira, IrInstruction *source_instru...@@ -7604,13 +7604,13 @@ static bool ir_emit_backward_branch(IrAnalyze *ira, IrInstruction *source_instru
7604 size_t *bbc = ira->new_irb.exec->backward_branch_count;7604 size_t *bbc = ira->new_irb.exec->backward_branch_count;
7605 size_t quota = ira->new_irb.exec->backward_branch_quota;7605 size_t quota = ira->new_irb.exec->backward_branch_quota;
76067606
7607 if (ira->new_irb.exec->reported_quota_exceeded) {7607 // If we're already over quota, we've already given an error message for this.
7608 if (*bbc > quota) {
7608 return false;7609 return false;
7609 }7610 }
76107611
7611 *bbc += 1;7612 *bbc += 1;
7612 if (*bbc > quota) {7613 if (*bbc > quota) {
7613 ira->new_irb.exec->reported_quota_exceeded = true;
7614 ir_add_error(ira, source_instruction, buf_sprintf("evaluation exceeded %" ZIG_PRI_usize " backwards branches", quota));7614 ir_add_error(ira, source_instruction, buf_sprintf("evaluation exceeded %" ZIG_PRI_usize " backwards branches", quota));
7615 return false;7615 return false;
7616 }7616 }
...@@ -13285,6 +13285,12 @@ static TypeTableEntry *ir_analyze_instruction_type_id(IrAnalyze *ira,...@@ -13285,6 +13285,12 @@ static TypeTableEntry *ir_analyze_instruction_type_id(IrAnalyze *ira,
13285static TypeTableEntry *ir_analyze_instruction_set_eval_branch_quota(IrAnalyze *ira,13285static TypeTableEntry *ir_analyze_instruction_set_eval_branch_quota(IrAnalyze *ira,
13286 IrInstructionSetEvalBranchQuota *instruction)13286 IrInstructionSetEvalBranchQuota *instruction)
13287{13287{
13288 if (ira->new_irb.exec->parent_exec != nullptr) {
13289 ir_add_error(ira, &instruction->base,
13290 buf_sprintf("@setEvalBranchQuota must be called from the top of the comptime stack"));
13291 return ira->codegen->builtin_types.entry_invalid;
13292 }
13293
13288 uint64_t new_quota;13294 uint64_t new_quota;
13289 if (!ir_resolve_usize(ira, instruction->new_quota->other, &new_quota))13295 if (!ir_resolve_usize(ira, instruction->new_quota->other, &new_quota))
13290 return ira->codegen->builtin_types.entry_invalid;13296 return ira->codegen->builtin_types.entry_invalid;
test/compile_errors.zig+11
...@@ -2068,4 +2068,15 @@ pub fn addCases(cases: &tests.CompileErrorContext) {...@@ -2068,4 +2068,15 @@ pub fn addCases(cases: &tests.CompileErrorContext) {
2068 ,2068 ,
2069 ".tmp_source.zig:2:24: error: expected [2]u8 literal, found [3]u8 literal");2069 ".tmp_source.zig:2:24: error: expected [2]u8 literal, found [3]u8 literal");
20702070
2071 cases.add("@setEvalBranchQuota in non-root comptime execution context",
2072 \\comptime {
2073 \\ foo();
2074 \\}
2075 \\fn foo() {
2076 \\ @setEvalBranchQuota(1001);
2077 \\}
2078 ,
2079 ".tmp_source.zig:5:5: error: @setEvalBranchQuota must be called from the top of the comptime stack",
2080 ".tmp_source.zig:2:8: note: called from here",
2081 ".tmp_source.zig:1:10: note: called from here");
2071}2082}