Use the new Non-trapping float-to-int conversions for Java like behavior.

This commit is contained in:
Volker 2018-08-11 15:46:20 +02:00
parent 0822d9af8c
commit d7c13c018e
5 changed files with 76 additions and 9 deletions

View File

@ -628,19 +628,19 @@ public class BinaryModuleWriter extends ModuleWriter implements InstructionOpcod
op = F64_CONVERT_S_I64; op = F64_CONVERT_S_I64;
break; break;
case f2i: case f2i:
op = I32_TRUNC_S_F32; op = I32_TRUNC_S_SAT_F32;
break; break;
case f2l: case f2l:
op = I64_TRUNC_S_F32; op = I64_TRUNC_S_SAT_F32;
break; break;
case f2d: case f2d:
op = F64_PROMOTE_F32; op = F64_PROMOTE_F32;
break; break;
case d2i: case d2i:
op = I32_TRUNC_S_F64; op = I32_TRUNC_S_SAT_F64;
break; break;
case d2l: case d2l:
op = I64_TRUNC_S_F64; op = I64_TRUNC_S_SAT_F64;
break; break;
case d2f: case d2f:
op = F32_DEMOTE_F64; op = F32_DEMOTE_F64;
@ -654,6 +654,9 @@ public class BinaryModuleWriter extends ModuleWriter implements InstructionOpcod
default: default:
throw new Error( "Unknown cast: " + cast ); throw new Error( "Unknown cast: " + cast );
} }
if( op > 255 ) {
codeStream.write( op >> 8 );
}
codeStream.write( op ); codeStream.write( op );
} }

View File

@ -352,4 +352,22 @@ interface InstructionOpcodes {
static final int REF_NULL = 0xD0; static final int REF_NULL = 0xD0;
static final int REF_ISNULL = 0xD1; static final int REF_ISNULL = 0xD1;
// === Non-trapping float-to-int conversions ====== https://github.com/WebAssembly/design/issues/1143
static final int I32_TRUNC_S_SAT_F32 = 0xFC00;
static final int I32_TRUNC_U_SAT_F32 = 0xFC01;
static final int I32_TRUNC_S_SAT_F64 = 0xFC02;
static final int I32_TRUNC_U_SAT_F64 = 0xFC03;
static final int I64_TRUNC_S_SAT_F32 = 0xFC04;
static final int I64_TRUNC_U_SAT_F32 = 0xFC05;
static final int I64_TRUNC_S_SAT_F64 = 0xFC06;
static final int I64_TRUNC_U_SAT_F64 = 0xFC07;
} }

View File

@ -188,19 +188,19 @@ public class TextModuleWriter extends ModuleWriter {
op = "f64.convert_s/i64"; op = "f64.convert_s/i64";
break; break;
case f2i: case f2i:
op = "i32.trunc_s/f32"; op = "i32.trunc_s:sat/f32";
break; break;
case f2l: case f2l:
op = "i64.trunc_s/f32"; op = "i64.trunc_s:sat/f32";
break; break;
case f2d: case f2d:
op = "f64.promote/f32"; op = "f64.promote/f32";
break; break;
case d2i: case d2i:
op = "i32.trunc_s/f64"; op = "i32.trunc_s:sat/f64";
break; break;
case d2l: case d2l:
op = "i64.trunc_s/f64"; op = "i64.trunc_s:sat/f64";
break; break;
case d2f: case d2f:
op = "f32.demote/f64"; op = "f32.demote/f64";

View File

@ -279,7 +279,7 @@ public class WasmRule extends TemporaryFolder {
command += "/bin/node"; command += "/bin/node";
} }
} }
return new ProcessBuilder( command, "--experimental-wasm-se", nodeScript.getAbsolutePath() ); return new ProcessBuilder( command, "--experimental-wasm-se", "--experimental-wasm-sat-f2i-conversions", nodeScript.getAbsolutePath() );
} }
/** /**

View File

@ -63,6 +63,7 @@ public class MathOperations extends AbstractBaseTest {
addParam( list, script, "byteDec", (byte)-128 ); addParam( list, script, "byteDec", (byte)-128 );
addParam( list, script, "shortInc", (short)-32768 ); addParam( list, script, "shortInc", (short)-32768 );
addParam( list, script, "charOp", (char)0xFFFF ); addParam( list, script, "charOp", (char)0xFFFF );
addParam( list, script, "castNumberOverflow" );
} }
return list; return list;
} }
@ -242,5 +243,50 @@ public class MathOperations extends AbstractBaseTest {
a += 60; a += 60;
return a; return a;
} }
@Export
static int castNumberOverflow() {
int result = 0;
float f = 2E30F;
double d = f;
int i = (int)f;
if( i == Integer.MAX_VALUE) {
result |= 0x1;
}
i = (int)-f;
if( i == Integer.MIN_VALUE) {
result |= 0x2;
}
long l = (long)f;
if( l == Long.MAX_VALUE) {
result |= 0x4;
}
l = (long)-f;
if( l == Long.MIN_VALUE) {
result |= 0x8;
}
i = (int)d;
if( i == Integer.MAX_VALUE) {
result |= 0x10;
}
i = (int)-d;
if( i == Integer.MIN_VALUE) {
result |= 0x20;
}
l = (long)d;
if( l == Long.MAX_VALUE) {
result |= 0x40;
}
l = (long)-d;
if( l == Long.MIN_VALUE) {
result |= 0x80;
}
return result;
}
} }
} }