remove the scope parameter of setFloatMode
also document that scopes inherit this value. See #367 See #1283master
parent
9ac9633b10
commit
7c3636aaa3
|
@ -734,7 +734,7 @@ export fn foo_strict(x: f64) f64 {
|
|||
}
|
||||
|
||||
export fn foo_optimized(x: f64) f64 {
|
||||
@setFloatMode(this, builtin.FloatMode.Optimized);
|
||||
@setFloatMode(builtin.FloatMode.Optimized);
|
||||
return x + big - big;
|
||||
}
|
||||
{#code_end#}
|
||||
|
@ -6030,17 +6030,20 @@ test "foo" {
|
|||
{#see_also|comptime#}
|
||||
{#header_close#}
|
||||
{#header_open|@setFloatMode#}
|
||||
<pre><code class="zig">@setFloatMode(scope, mode: @import("builtin").FloatMode)</code></pre>
|
||||
<pre><code class="zig">@setFloatMode(mode: @import("builtin").FloatMode)</code></pre>
|
||||
<p>
|
||||
Sets the floating point mode for a given scope. Possible values are:
|
||||
Sets the floating point mode of the current scope. Possible values are:
|
||||
</p>
|
||||
{#code_begin|syntax#}
|
||||
pub const FloatMode = enum {
|
||||
Optimized,
|
||||
Strict,
|
||||
Optimized,
|
||||
};
|
||||
{#code_end#}
|
||||
<ul>
|
||||
<li>
|
||||
<code>Strict</code> (default) - Floating point operations follow strict IEEE compliance.
|
||||
</li>
|
||||
<li>
|
||||
<code>Optimized</code> - Floating point operations may do all of the following:
|
||||
<ul>
|
||||
|
@ -6053,10 +6056,11 @@ pub const FloatMode = enum {
|
|||
</ul>
|
||||
This is equivalent to <code>-ffast-math</code> in GCC.
|
||||
</li>
|
||||
<li>
|
||||
<code>Strict</code> (default) - Floating point operations follow strict IEEE compliance.
|
||||
</li>
|
||||
</ul>
|
||||
<p>
|
||||
The floating point mode is inherited by child scopes, and can be overridden in any scope.
|
||||
You can set the floating point mode in a struct or module scope by using a comptime block.
|
||||
</p>
|
||||
{#see_also|Floating Point Operations#}
|
||||
{#header_close#}
|
||||
{#header_open|@setGlobalLinkage#}
|
||||
|
|
|
@ -3287,8 +3287,8 @@ static const size_t stack_trace_ptr_count = 30;
|
|||
|
||||
|
||||
enum FloatMode {
|
||||
FloatModeOptimized,
|
||||
FloatModeStrict,
|
||||
FloatModeOptimized,
|
||||
};
|
||||
|
||||
enum FnWalkId {
|
||||
|
|
|
@ -6729,7 +6729,7 @@ static void define_builtin_fns(CodeGen *g) {
|
|||
create_builtin_fn(g, BuiltinFnIdIntType, "IntType", 2); // TODO rename to Int
|
||||
create_builtin_fn(g, BuiltinFnIdSetCold, "setCold", 1);
|
||||
create_builtin_fn(g, BuiltinFnIdSetRuntimeSafety, "setRuntimeSafety", 1);
|
||||
create_builtin_fn(g, BuiltinFnIdSetFloatMode, "setFloatMode", 2);
|
||||
create_builtin_fn(g, BuiltinFnIdSetFloatMode, "setFloatMode", 1);
|
||||
create_builtin_fn(g, BuiltinFnIdPanic, "panic", 1);
|
||||
create_builtin_fn(g, BuiltinFnIdPtrCast, "ptrCast", 2);
|
||||
create_builtin_fn(g, BuiltinFnIdBitCast, "bitCast", 2);
|
||||
|
@ -7115,11 +7115,11 @@ Buf *codegen_generate_builtin_source(CodeGen *g) {
|
|||
{
|
||||
buf_appendf(contents,
|
||||
"pub const FloatMode = enum {\n"
|
||||
" Optimized,\n"
|
||||
" Strict,\n"
|
||||
" Optimized,\n"
|
||||
"};\n\n");
|
||||
assert(FloatModeOptimized == 0);
|
||||
assert(FloatModeStrict == 1);
|
||||
assert(FloatModeStrict == 0);
|
||||
assert(FloatModeOptimized == 1);
|
||||
}
|
||||
{
|
||||
buf_appendf(contents,
|
||||
|
@ -7127,8 +7127,8 @@ Buf *codegen_generate_builtin_source(CodeGen *g) {
|
|||
" Big,\n"
|
||||
" Little,\n"
|
||||
"};\n\n");
|
||||
assert(FloatModeOptimized == 0);
|
||||
assert(FloatModeStrict == 1);
|
||||
//assert(EndianBig == 0);
|
||||
//assert(EndianLittle == 1);
|
||||
}
|
||||
{
|
||||
const char *endian_str = g->is_big_endian ? "Endian.Big" : "Endian.Little";
|
||||
|
|
72
src/ir.cpp
72
src/ir.cpp
|
@ -1577,13 +1577,11 @@ static IrInstruction *ir_build_set_runtime_safety(IrBuilder *irb, Scope *scope,
|
|||
}
|
||||
|
||||
static IrInstruction *ir_build_set_float_mode(IrBuilder *irb, Scope *scope, AstNode *source_node,
|
||||
IrInstruction *scope_value, IrInstruction *mode_value)
|
||||
IrInstruction *mode_value)
|
||||
{
|
||||
IrInstructionSetFloatMode *instruction = ir_build_instruction<IrInstructionSetFloatMode>(irb, scope, source_node);
|
||||
instruction->scope_value = scope_value;
|
||||
instruction->mode_value = mode_value;
|
||||
|
||||
ir_ref_instruction(scope_value, irb->current_basic_block);
|
||||
ir_ref_instruction(mode_value, irb->current_basic_block);
|
||||
|
||||
return &instruction->base;
|
||||
|
@ -3959,12 +3957,7 @@ static IrInstruction *ir_gen_builtin_fn_call(IrBuilder *irb, Scope *scope, AstNo
|
|||
if (arg0_value == irb->codegen->invalid_instruction)
|
||||
return arg0_value;
|
||||
|
||||
AstNode *arg1_node = node->data.fn_call_expr.params.at(1);
|
||||
IrInstruction *arg1_value = ir_gen_node(irb, arg1_node, scope);
|
||||
if (arg1_value == irb->codegen->invalid_instruction)
|
||||
return arg1_value;
|
||||
|
||||
IrInstruction *set_float_mode = ir_build_set_float_mode(irb, scope, node, arg0_value, arg1_value);
|
||||
IrInstruction *set_float_mode = ir_build_set_float_mode(irb, scope, node, arg0_value);
|
||||
return ir_lval_wrap(irb, scope, set_float_mode, lval);
|
||||
}
|
||||
case BuiltinFnIdSizeof:
|
||||
|
@ -15379,6 +15372,7 @@ static ZigType *ir_analyze_instruction_set_cold(IrAnalyze *ira, IrInstructionSet
|
|||
ir_build_const_from(ira, &instruction->base);
|
||||
return ira->codegen->builtin_types.entry_void;
|
||||
}
|
||||
|
||||
static ZigType *ir_analyze_instruction_set_runtime_safety(IrAnalyze *ira,
|
||||
IrInstructionSetRuntimeSafety *set_runtime_safety_instruction)
|
||||
{
|
||||
|
@ -15439,14 +15433,6 @@ static ZigType *ir_analyze_instruction_set_runtime_safety(IrAnalyze *ira,
|
|||
static ZigType *ir_analyze_instruction_set_float_mode(IrAnalyze *ira,
|
||||
IrInstructionSetFloatMode *instruction)
|
||||
{
|
||||
IrInstruction *target_instruction = instruction->scope_value->other;
|
||||
ZigType *target_type = target_instruction->value.type;
|
||||
if (type_is_invalid(target_type))
|
||||
return ira->codegen->builtin_types.entry_invalid;
|
||||
ConstExprValue *target_val = ir_resolve_const(ira, target_instruction, UndefBad);
|
||||
if (!target_val)
|
||||
return ira->codegen->builtin_types.entry_invalid;
|
||||
|
||||
if (ira->new_irb.exec->is_inline) {
|
||||
// ignore setFloatMode when running functions at compile time
|
||||
ir_build_const_from(ira, &instruction->base);
|
||||
|
@ -15455,40 +15441,34 @@ static ZigType *ir_analyze_instruction_set_float_mode(IrAnalyze *ira,
|
|||
|
||||
bool *fast_math_on_ptr;
|
||||
AstNode **fast_math_set_node_ptr;
|
||||
if (target_type->id == ZigTypeIdBlock) {
|
||||
ScopeBlock *block_scope = (ScopeBlock *)target_val->data.x_block;
|
||||
fast_math_on_ptr = &block_scope->fast_math_on;
|
||||
fast_math_set_node_ptr = &block_scope->fast_math_set_node;
|
||||
} else if (target_type->id == ZigTypeIdFn) {
|
||||
assert(target_val->data.x_ptr.special == ConstPtrSpecialFunction);
|
||||
ZigFn *target_fn = target_val->data.x_ptr.data.fn.fn_entry;
|
||||
assert(target_fn->def_scope);
|
||||
fast_math_on_ptr = &target_fn->def_scope->fast_math_on;
|
||||
fast_math_set_node_ptr = &target_fn->def_scope->fast_math_set_node;
|
||||
} else if (target_type->id == ZigTypeIdMetaType) {
|
||||
ScopeDecls *decls_scope;
|
||||
ZigType *type_arg = target_val->data.x_type;
|
||||
if (type_arg->id == ZigTypeIdStruct) {
|
||||
decls_scope = type_arg->data.structure.decls_scope;
|
||||
} else if (type_arg->id == ZigTypeIdEnum) {
|
||||
decls_scope = type_arg->data.enumeration.decls_scope;
|
||||
} else if (type_arg->id == ZigTypeIdUnion) {
|
||||
decls_scope = type_arg->data.unionation.decls_scope;
|
||||
|
||||
Scope *scope = instruction->base.scope;
|
||||
while (scope != nullptr) {
|
||||
if (scope->id == ScopeIdBlock) {
|
||||
ScopeBlock *block_scope = (ScopeBlock *)scope;
|
||||
fast_math_on_ptr = &block_scope->fast_math_on;
|
||||
fast_math_set_node_ptr = &block_scope->fast_math_set_node;
|
||||
break;
|
||||
} else if (scope->id == ScopeIdFnDef) {
|
||||
ScopeFnDef *def_scope = (ScopeFnDef *)scope;
|
||||
ZigFn *target_fn = def_scope->fn_entry;
|
||||
assert(target_fn->def_scope != nullptr);
|
||||
fast_math_on_ptr = &target_fn->def_scope->fast_math_on;
|
||||
fast_math_set_node_ptr = &target_fn->def_scope->fast_math_set_node;
|
||||
break;
|
||||
} else if (scope->id == ScopeIdDecls) {
|
||||
ScopeDecls *decls_scope = (ScopeDecls *)scope;
|
||||
fast_math_on_ptr = &decls_scope->fast_math_on;
|
||||
fast_math_set_node_ptr = &decls_scope->fast_math_set_node;
|
||||
break;
|
||||
} else {
|
||||
ir_add_error_node(ira, target_instruction->source_node,
|
||||
buf_sprintf("expected scope reference, found type '%s'", buf_ptr(&type_arg->name)));
|
||||
return ira->codegen->builtin_types.entry_invalid;
|
||||
scope = scope->parent;
|
||||
continue;
|
||||
}
|
||||
fast_math_on_ptr = &decls_scope->fast_math_on;
|
||||
fast_math_set_node_ptr = &decls_scope->fast_math_set_node;
|
||||
} else {
|
||||
ir_add_error_node(ira, target_instruction->source_node,
|
||||
buf_sprintf("expected scope reference, found type '%s'", buf_ptr(&target_type->name)));
|
||||
return ira->codegen->builtin_types.entry_invalid;
|
||||
}
|
||||
assert(scope != nullptr);
|
||||
|
||||
IrInstruction *float_mode_value = instruction->mode_value->other;
|
||||
|
||||
FloatMode float_mode_scalar;
|
||||
if (!ir_resolve_float_mode(ira, float_mode_value, &float_mode_scalar))
|
||||
return ira->codegen->builtin_types.entry_invalid;
|
||||
|
|
|
@ -275,7 +275,7 @@ test "eval @setFloatMode at compile-time" {
|
|||
}
|
||||
|
||||
fn fnWithFloatMode() f32 {
|
||||
@setFloatMode(this, builtin.FloatMode.Strict);
|
||||
@setFloatMode(builtin.FloatMode.Strict);
|
||||
return 1234.0;
|
||||
}
|
||||
|
||||
|
|
|
@ -3996,8 +3996,8 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
|||
cases.add(
|
||||
"@setFloatMode twice for same scope",
|
||||
\\export fn foo() void {
|
||||
\\ @setFloatMode(this, @import("builtin").FloatMode.Optimized);
|
||||
\\ @setFloatMode(this, @import("builtin").FloatMode.Optimized);
|
||||
\\ @setFloatMode(@import("builtin").FloatMode.Optimized);
|
||||
\\ @setFloatMode(@import("builtin").FloatMode.Optimized);
|
||||
\\}
|
||||
,
|
||||
".tmp_source.zig:3:5: error: float mode set twice for same scope",
|
||||
|
|
Loading…
Reference in New Issue