Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(573)

Side by Side Diff: src/wasm/asm-wasm-builder.cc

Issue 1729833002: Add wasm internal opcodes for asm.js stdlib functions we're missing. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: fix Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/snapshot/serializer-common.cc ('k') | src/wasm/ast-decoder.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2015 the V8 project authors. All rights reserved. 1 // Copyright 2015 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/v8.h" 5 #include "src/v8.h"
6 6
7 // Required to get M_E etc. in MSVC. 7 // Required to get M_E etc. in MSVC.
8 #if defined(_WIN32) 8 #if defined(_WIN32)
9 #define _USE_MATH_DEFINES 9 #define _USE_MATH_DEFINES
10 #endif 10 #endif
(...skipping 828 matching lines...) Expand 10 before | Expand all | Expand 10 after
839 Variable* var = expr->var(); 839 Variable* var = expr->var();
840 AsmTyper::StandardMember standard_object = 840 AsmTyper::StandardMember standard_object =
841 typer_->VariableAsStandardMember(var); 841 typer_->VariableAsStandardMember(var);
842 ZoneList<Expression*>* args = call->arguments(); 842 ZoneList<Expression*>* args = call->arguments();
843 LocalType call_type = TypeOf(call); 843 LocalType call_type = TypeOf(call);
844 switch (standard_object) { 844 switch (standard_object) {
845 case AsmTyper::kNone: { 845 case AsmTyper::kNone: {
846 return false; 846 return false;
847 } 847 }
848 case AsmTyper::kMathAcos: { 848 case AsmTyper::kMathAcos: {
849 UNREACHABLE(); 849 DCHECK_EQ(kAstF64, call_type);
850 break; // TODO(bradnelson): Implement as external. 850 current_function_builder_->Emit(kExprF64Acos);
851 break;
851 } 852 }
852 case AsmTyper::kMathAsin: { 853 case AsmTyper::kMathAsin: {
853 UNREACHABLE(); 854 DCHECK_EQ(kAstF64, call_type);
854 break; // TODO(bradnelson): Implement as external. 855 current_function_builder_->Emit(kExprF64Asin);
856 break;
855 } 857 }
856 case AsmTyper::kMathAtan: { 858 case AsmTyper::kMathAtan: {
857 UNREACHABLE(); 859 DCHECK_EQ(kAstF64, call_type);
858 break; // TODO(bradnelson): Implement as external. 860 current_function_builder_->Emit(kExprF64Atan);
861 break;
859 } 862 }
860 case AsmTyper::kMathCos: { 863 case AsmTyper::kMathCos: {
861 UNREACHABLE(); 864 DCHECK_EQ(kAstF64, call_type);
862 break; // TODO(bradnelson): Implement as external. 865 current_function_builder_->Emit(kExprF64Cos);
866 break;
863 } 867 }
864 case AsmTyper::kMathSin: { 868 case AsmTyper::kMathSin: {
865 UNREACHABLE(); 869 DCHECK_EQ(kAstF64, call_type);
866 break; // TODO(bradnelson): Implement as external. 870 current_function_builder_->Emit(kExprF64Sin);
871 break;
867 } 872 }
868 case AsmTyper::kMathTan: { 873 case AsmTyper::kMathTan: {
869 UNREACHABLE(); 874 DCHECK_EQ(kAstF64, call_type);
870 break; // TODO(bradnelson): Implement as external. 875 current_function_builder_->Emit(kExprF64Tan);
876 break;
871 } 877 }
872 case AsmTyper::kMathExp: { 878 case AsmTyper::kMathExp: {
873 UNREACHABLE(); 879 DCHECK_EQ(kAstF64, call_type);
874 break; // TODO(bradnelson): Implement as external. 880 current_function_builder_->Emit(kExprF64Exp);
881 break;
875 } 882 }
876 case AsmTyper::kMathLog: { 883 case AsmTyper::kMathLog: {
877 UNREACHABLE(); 884 DCHECK_EQ(kAstF64, call_type);
878 break; // TODO(bradnelson): Implement as external. 885 current_function_builder_->Emit(kExprF64Log);
886 break;
879 } 887 }
880 case AsmTyper::kMathCeil: { 888 case AsmTyper::kMathCeil: {
881 if (call_type == kAstF32) { 889 if (call_type == kAstF32) {
882 current_function_builder_->Emit(kExprF32Ceil); 890 current_function_builder_->Emit(kExprF32Ceil);
883 } else if (call_type == kAstF64) { 891 } else if (call_type == kAstF64) {
884 current_function_builder_->Emit(kExprF64Ceil); 892 current_function_builder_->Emit(kExprF64Ceil);
885 } else { 893 } else {
886 UNREACHABLE(); 894 UNREACHABLE();
887 } 895 }
888 break; 896 break;
(...skipping 12 matching lines...) Expand all
901 if (call_type == kAstF32) { 909 if (call_type == kAstF32) {
902 current_function_builder_->Emit(kExprF32Sqrt); 910 current_function_builder_->Emit(kExprF32Sqrt);
903 } else if (call_type == kAstF64) { 911 } else if (call_type == kAstF64) {
904 current_function_builder_->Emit(kExprF64Sqrt); 912 current_function_builder_->Emit(kExprF64Sqrt);
905 } else { 913 } else {
906 UNREACHABLE(); 914 UNREACHABLE();
907 } 915 }
908 break; 916 break;
909 } 917 }
910 case AsmTyper::kMathAbs: { 918 case AsmTyper::kMathAbs: {
911 // TODO(bradnelson): Handle signed. 919 // TODO(bradnelson): Should this be cast to float?
912 if (call_type == kAstF32) { 920 if (call_type == kAstI32) {
921 current_function_builder_->Emit(kExprIfElse);
922 current_function_builder_->Emit(kExprI32LtS);
923 Visit(args->at(0));
924 byte code[] = {WASM_I8(0)};
925 current_function_builder_->EmitCode(code, sizeof(code));
926 current_function_builder_->Emit(kExprI32Sub);
927 current_function_builder_->EmitCode(code, sizeof(code));
928 Visit(args->at(0));
929 } else if (call_type == kAstF32) {
913 current_function_builder_->Emit(kExprF32Abs); 930 current_function_builder_->Emit(kExprF32Abs);
914 } else if (call_type == kAstF64) { 931 } else if (call_type == kAstF64) {
915 current_function_builder_->Emit(kExprF64Abs); 932 current_function_builder_->Emit(kExprF64Abs);
916 } else { 933 } else {
917 UNREACHABLE(); 934 UNREACHABLE();
918 } 935 }
919 break; 936 break;
920 } 937 }
921 case AsmTyper::kMathMin: { 938 case AsmTyper::kMathMin: {
922 // TODO(bradnelson): Handle signed.
923 // TODO(bradnelson): Change wasm to match Math.min in asm.js mode. 939 // TODO(bradnelson): Change wasm to match Math.min in asm.js mode.
924 if (call_type == kAstF32) { 940 if (call_type == kAstI32) {
941 current_function_builder_->Emit(kExprIfElse);
942 current_function_builder_->Emit(kExprI32LeS);
943 Visit(args->at(0));
944 Visit(args->at(1));
945 } else if (call_type == kAstF32) {
925 current_function_builder_->Emit(kExprF32Min); 946 current_function_builder_->Emit(kExprF32Min);
926 } else if (call_type == kAstF64) { 947 } else if (call_type == kAstF64) {
927 current_function_builder_->Emit(kExprF64Min); 948 current_function_builder_->Emit(kExprF64Min);
928 } else { 949 } else {
929 UNREACHABLE(); 950 UNREACHABLE();
930 } 951 }
931 break; 952 break;
932 } 953 }
933 case AsmTyper::kMathMax: { 954 case AsmTyper::kMathMax: {
934 // TODO(bradnelson): Handle signed.
935 // TODO(bradnelson): Change wasm to match Math.max in asm.js mode. 955 // TODO(bradnelson): Change wasm to match Math.max in asm.js mode.
936 if (call_type == kAstF32) { 956 if (call_type == kAstI32) {
957 current_function_builder_->Emit(kExprIfElse);
958 current_function_builder_->Emit(kExprI32GtS);
959 Visit(args->at(0));
960 Visit(args->at(1));
961 } else if (call_type == kAstF32) {
937 current_function_builder_->Emit(kExprF32Max); 962 current_function_builder_->Emit(kExprF32Max);
938 } else if (call_type == kAstF64) { 963 } else if (call_type == kAstF64) {
939 current_function_builder_->Emit(kExprF64Max); 964 current_function_builder_->Emit(kExprF64Max);
940 } else { 965 } else {
941 UNREACHABLE(); 966 UNREACHABLE();
942 } 967 }
943 break; 968 break;
944 } 969 }
945 case AsmTyper::kMathAtan2: { 970 case AsmTyper::kMathAtan2: {
946 UNREACHABLE(); 971 DCHECK_EQ(kAstF64, call_type);
947 break; // TODO(bradnelson): Implement as external. 972 current_function_builder_->Emit(kExprF64Atan2);
973 break;
948 } 974 }
949 case AsmTyper::kMathPow: { 975 case AsmTyper::kMathPow: {
950 UNREACHABLE(); 976 DCHECK_EQ(kAstF64, call_type);
951 break; // TODO(bradnelson): Implement as external. 977 current_function_builder_->Emit(kExprF64Pow);
978 break;
952 } 979 }
953 case AsmTyper::kMathImul: { 980 case AsmTyper::kMathImul: {
954 current_function_builder_->Emit(kExprI32Mul); 981 current_function_builder_->Emit(kExprI32Mul);
955 break; 982 break;
956 } 983 }
957 case AsmTyper::kMathFround: { 984 case AsmTyper::kMathFround: {
958 DCHECK(args->length() == 1); 985 DCHECK(args->length() == 1);
959 Literal* literal = args->at(0)->AsLiteral(); 986 Literal* literal = args->at(0)->AsLiteral();
960 if (literal != nullptr) { 987 if (literal != nullptr) {
961 if (literal->raw_value()->IsNumber()) { 988 if (literal->raw_value()->IsNumber()) {
(...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after
1236 BINOP_CASE(Token::SHL, Shl, NON_SIGNED_INT_BINOP, true); 1263 BINOP_CASE(Token::SHL, Shl, NON_SIGNED_INT_BINOP, true);
1237 BINOP_CASE(Token::SAR, ShrS, NON_SIGNED_INT_BINOP, true); 1264 BINOP_CASE(Token::SAR, ShrS, NON_SIGNED_INT_BINOP, true);
1238 BINOP_CASE(Token::SHR, ShrU, NON_SIGNED_INT_BINOP, true); 1265 BINOP_CASE(Token::SHR, ShrU, NON_SIGNED_INT_BINOP, true);
1239 case Token::MOD: { 1266 case Token::MOD: {
1240 TypeIndex type = TypeIndexOf(expr->left(), expr->right(), false); 1267 TypeIndex type = TypeIndexOf(expr->left(), expr->right(), false);
1241 if (type == kInt32) { 1268 if (type == kInt32) {
1242 current_function_builder_->Emit(kExprI32RemS); 1269 current_function_builder_->Emit(kExprI32RemS);
1243 } else if (type == kUint32) { 1270 } else if (type == kUint32) {
1244 current_function_builder_->Emit(kExprI32RemU); 1271 current_function_builder_->Emit(kExprI32RemU);
1245 } else if (type == kFloat64) { 1272 } else if (type == kFloat64) {
1246 ModF64(expr); 1273 current_function_builder_->Emit(kExprF64Mod);
1247 return; 1274 return;
1248 } else { 1275 } else {
1249 UNREACHABLE(); 1276 UNREACHABLE();
1250 } 1277 }
1251 break; 1278 break;
1252 } 1279 }
1253 case Token::COMMA: { 1280 case Token::COMMA: {
1254 current_function_builder_->EmitWithU8(kExprBlock, 2); 1281 current_function_builder_->EmitWithU8(kExprBlock, 2);
1255 break; 1282 break;
1256 } 1283 }
1257 default: 1284 default:
1258 UNREACHABLE(); 1285 UNREACHABLE();
1259 } 1286 }
1260 RECURSE(Visit(expr->left())); 1287 RECURSE(Visit(expr->left()));
1261 RECURSE(Visit(expr->right())); 1288 RECURSE(Visit(expr->right()));
1262 } 1289 }
1263 } 1290 }
1264 1291
1265 void ModF64(BinaryOperation* expr) {
1266 current_function_builder_->EmitWithU8(kExprBlock, 3);
1267 uint16_t index_0 = current_function_builder_->AddLocal(kAstF64);
1268 uint16_t index_1 = current_function_builder_->AddLocal(kAstF64);
1269 current_function_builder_->Emit(kExprSetLocal);
1270 AddLeb128(index_0, true);
1271 RECURSE(Visit(expr->left()));
1272 current_function_builder_->Emit(kExprSetLocal);
1273 AddLeb128(index_1, true);
1274 RECURSE(Visit(expr->right()));
1275 current_function_builder_->Emit(kExprF64Sub);
1276 current_function_builder_->Emit(kExprGetLocal);
1277 AddLeb128(index_0, true);
1278 current_function_builder_->Emit(kExprF64Mul);
1279 current_function_builder_->Emit(kExprGetLocal);
1280 AddLeb128(index_1, true);
1281 // Use trunc instead of two casts
1282 current_function_builder_->Emit(kExprF64SConvertI32);
1283 current_function_builder_->Emit(kExprI32SConvertF64);
1284 current_function_builder_->Emit(kExprF64Div);
1285 current_function_builder_->Emit(kExprGetLocal);
1286 AddLeb128(index_0, true);
1287 current_function_builder_->Emit(kExprGetLocal);
1288 AddLeb128(index_1, true);
1289 }
1290
1291 void AddLeb128(uint32_t index, bool is_local) { 1292 void AddLeb128(uint32_t index, bool is_local) {
1292 std::vector<uint8_t> index_vec = UnsignedLEB128From(index); 1293 std::vector<uint8_t> index_vec = UnsignedLEB128From(index);
1293 if (is_local) { 1294 if (is_local) {
1294 uint32_t pos_of_index[1] = {0}; 1295 uint32_t pos_of_index[1] = {0};
1295 current_function_builder_->EmitCode( 1296 current_function_builder_->EmitCode(
1296 &index_vec[0], static_cast<uint32_t>(index_vec.size()), pos_of_index, 1297 &index_vec[0], static_cast<uint32_t>(index_vec.size()), pos_of_index,
1297 1); 1298 1);
1298 } else { 1299 } else {
1299 current_function_builder_->EmitCode( 1300 current_function_builder_->EmitCode(
1300 &index_vec[0], static_cast<uint32_t>(index_vec.size())); 1301 &index_vec[0], static_cast<uint32_t>(index_vec.size()));
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after
1511 // that zone in constructor may be thrown away once wasm module is written. 1512 // that zone in constructor may be thrown away once wasm module is written.
1512 WasmModuleIndex* AsmWasmBuilder::Run() { 1513 WasmModuleIndex* AsmWasmBuilder::Run() {
1513 AsmWasmBuilderImpl impl(isolate_, zone_, literal_, foreign_, typer_); 1514 AsmWasmBuilderImpl impl(isolate_, zone_, literal_, foreign_, typer_);
1514 impl.Compile(); 1515 impl.Compile();
1515 WasmModuleWriter* writer = impl.builder_->Build(zone_); 1516 WasmModuleWriter* writer = impl.builder_->Build(zone_);
1516 return writer->WriteTo(zone_); 1517 return writer->WriteTo(zone_);
1517 } 1518 }
1518 } // namespace wasm 1519 } // namespace wasm
1519 } // namespace internal 1520 } // namespace internal
1520 } // namespace v8 1521 } // namespace v8
OLDNEW
« no previous file with comments | « src/snapshot/serializer-common.cc ('k') | src/wasm/ast-decoder.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698