Bug 1274618 - Experimental WASM text format. r=sunfish

MozReview-Commit-ID: 1Bi5x74h4CP

--HG--
extra : transplant_source : %3A%B4o%9D%CC%E6g%1F%E6%9F%2B%0B%C7%AC%E6%F4%B3Y%89%5E
This commit is contained in:
Yury Delendik 2016-05-23 17:03:24 -05:00
parent 975ff077c2
commit 854f7f6882
6 changed files with 1803 additions and 5 deletions

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,57 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
* vim: set ts=8 sts=4 et sw=4 tw=99:
*
* Copyright 2015 Mozilla Foundation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef wasm_binary_to_experimental_text_h
#define wasm_binary_to_experimental_text_h
#include "NamespaceImports.h"
#include "gc/Rooting.h"
#include "js/Class.h"
namespace js {
class StringBuffer;
namespace wasm {
struct ExperimentalTextFormatting
{
bool allowAsciiOperators:1;
bool reduceParens:1;
bool groupBlocks:1;
ExperimentalTextFormatting()
: allowAsciiOperators(true),
reduceParens(true),
groupBlocks(true)
{}
};
// Translate the given binary representation of a wasm module into the module's textual
// representation.
MOZ_MUST_USE bool
BinaryToExperimentalText(JSContext* cx, const uint8_t* bytes, size_t length, StringBuffer& buffer,
const ExperimentalTextFormatting& formatting);
} // namespace wasm
} // namespace js
#endif // namespace wasm_binary_to_experimental_text_h

View File

@ -25,6 +25,7 @@
#include "jsprf.h"
#include "asmjs/WasmBinaryToExperimentalText.h"
#include "asmjs/WasmBinaryToText.h"
#include "asmjs/WasmSerialize.h"
#include "builtin/AtomicsObject.h"
@ -1673,7 +1674,7 @@ Module::createText(JSContext* cx)
if (!source_.empty()) {
if (!buffer.append(experimentalWarning))
return nullptr;
if (!BinaryToText(cx, source_.begin(), source_.length(), buffer))
if (!BinaryToExperimentalText(cx, source_.begin(), source_.length(), buffer, ExperimentalTextFormatting()))
return nullptr;
} else {
if (!buffer.append(enabledMessage))

View File

@ -21,6 +21,7 @@
#include "asmjs/AsmJS.h"
#include "asmjs/Wasm.h"
#include "asmjs/WasmBinaryToExperimentalText.h"
#include "asmjs/WasmBinaryToText.h"
#include "asmjs/WasmTextToBinary.h"
#include "builtin/Promise.h"
@ -580,11 +581,30 @@ WasmBinaryToText(JSContext* cx, unsigned argc, Value* vp)
bytes = copy.begin();
}
bool experimental = false;
if (args.length() > 1) {
JSString* opt = JS::ToString(cx, args[1]);
if (!opt)
return false;
bool match;
if (!JS_StringEqualsAscii(cx, opt, "experimental", &match))
return false;
experimental = match;
}
StringBuffer buffer(cx);
if (!wasm::BinaryToText(cx, bytes, length, buffer)) {
if (!cx->isExceptionPending())
JS_ReportErrorNumber(cx, GetErrorMessage, nullptr, JSMSG_WASM_FAIL, "print error");
return false;
if (experimental) {
if (!wasm::BinaryToExperimentalText(cx, bytes, length, buffer, wasm::ExperimentalTextFormatting())) {
if (!cx->isExceptionPending())
JS_ReportErrorNumber(cx, GetErrorMessage, nullptr, JSMSG_WASM_FAIL, "print error");
return false;
}
} else {
if (!wasm::BinaryToText(cx, bytes, length, buffer)) {
if (!cx->isExceptionPending())
JS_ReportErrorNumber(cx, GetErrorMessage, nullptr, JSMSG_WASM_FAIL, "print error");
return false;
}
}
JSString* result = buffer.finishString();

View File

@ -0,0 +1,72 @@
if (!wasmIsSupported())
quit();
load(libdir + "asserts.js");
function runTest(code, expected) {
var binary = wasmTextToBinary(code);
var s = wasmBinaryToText(binary, "experimental");
s = s.replace(/\s+/g, ' ');
print("TEXT: " + s);
assertEq(expected, s);
}
// Smoke test
runTest(`
(module
(func (param i32) (result f64)
(local $l f32)
(block
(set_local $l (f32.const 0.0))
(loop $exit $cont
(br_if $exit (get_local 0))
(br 2)
)
(if (i32.const 1)
(f64.min (f64.neg (f64.const 1)) (f64.const 0))
(f64.add (f64.const 0.5) (f64.load offset=0 (i32.const 0)) )
)
)
(i32.store16 (i32.const 8) (i32.const 128))
(return (f64.const 0))
)
(export "test" 0)
(memory 1 10)
)`,
"type $type$0 of function (i32) : (f64) " +
"export $func$0 as \"test\" " +
"function $func$0($var$0:i32) : (f64) {" +
" var $var$1:f32 { $var$1 = 0.0f loop { br_if $var$0,$label$0 br $label$1 $label$0: }" +
" if (1) { f64.min -1.0 0.0 } else { 0.5 + f64.load [0] } $label$1: }" +
" i32.store16 [8],128 return 0.0 "+
"} memory 1,10 {} ");
// function calls
runTest(`
(module
(type $type1 (func (param i32) (result i32)))
(import $import1 "mod" "test" (param f32) (result f32))
(table $func1 $func2)
(func $func1 (param i32) (param f32) (nop))
(func $func2 (param i32) (result i32) (get_local 0))
(func $test
(call $func1
(call_indirect $type1 (i32.const 1) (i32.const 2))
(call_import $import1 (f32.const 1.0))
)
)
(export "test" $test)
(memory 1 65535)
)`,
"type $type$0 of function (i32) : (i32) " +
"type $type$1 of function (f32) : (f32) " +
"type $type$2 of function (i32,f32) : () " +
"type $type$3 of function () : () " +
"import \"test\" as $import$0 from \"mod\" typeof function (f32) : (f32) " +
"table [$func$0,$func$1] export $func$2 as \"test\" " +
"function $func$0($var$0:i32,$var$1:f32) : () { nop } " +
"function $func$1($var$0:i32) : (i32) { $var$0 } " +
"function $func$2() : () {" +
" call $func$0 (call_indirect $type$0 [1] (2),call_import $import$0 (1.0f)) " +
"} memory 1,65535 {} ");

View File

@ -158,6 +158,7 @@ UNIFIED_SOURCES += [
'asmjs/WasmBinary.cpp',
'asmjs/WasmBinaryIterator.cpp',
'asmjs/WasmBinaryToAST.cpp',
'asmjs/WasmBinaryToExperimentalText.cpp',
'asmjs/WasmBinaryToText.cpp',
'asmjs/WasmFrameIterator.cpp',
'asmjs/WasmGenerator.cpp',