mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-24 10:45:42 +00:00
Bug 1516697 - Make AsmJSParser a template typedef and {Module,Function}Validator template classes. r=arai
This commit is contained in:
parent
ea1a7af6af
commit
fcdd8f5160
@ -204,6 +204,7 @@ class AsmJSGlobal {
|
||||
CacheableChars field_;
|
||||
|
||||
friend class ModuleValidatorShared;
|
||||
template <typename Unit>
|
||||
friend class ModuleValidator;
|
||||
|
||||
public:
|
||||
@ -645,7 +646,8 @@ static inline ParseNode* NextNonEmptyStatement(ParseNode* pn) {
|
||||
return SkipEmptyStatements(pn->pn_next);
|
||||
}
|
||||
|
||||
static bool GetToken(AsmJSParser& parser, TokenKind* tkp) {
|
||||
template <typename Unit>
|
||||
static bool GetToken(AsmJSParser<Unit>& parser, TokenKind* tkp) {
|
||||
auto& ts = parser.tokenStream;
|
||||
TokenKind tk;
|
||||
while (true) {
|
||||
@ -660,7 +662,8 @@ static bool GetToken(AsmJSParser& parser, TokenKind* tkp) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool PeekToken(AsmJSParser& parser, TokenKind* tkp) {
|
||||
template <typename Unit>
|
||||
static bool PeekToken(AsmJSParser<Unit>& parser, TokenKind* tkp) {
|
||||
auto& ts = parser.tokenStream;
|
||||
TokenKind tk;
|
||||
while (true) {
|
||||
@ -676,7 +679,9 @@ static bool PeekToken(AsmJSParser& parser, TokenKind* tkp) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool ParseVarOrConstStatement(AsmJSParser& parser, ParseNode** var) {
|
||||
template <typename Unit>
|
||||
static bool ParseVarOrConstStatement(AsmJSParser<Unit>& parser,
|
||||
ParseNode** var) {
|
||||
TokenKind tk;
|
||||
if (!PeekToken(parser, &tk)) {
|
||||
return false;
|
||||
@ -1196,6 +1201,7 @@ class MOZ_STACK_CLASS JS_HAZ_ROOTED ModuleValidatorShared {
|
||||
} u;
|
||||
|
||||
friend class ModuleValidatorShared;
|
||||
template <typename Unit>
|
||||
friend class ModuleValidator;
|
||||
friend class js::LifoAlloc;
|
||||
|
||||
@ -1876,13 +1882,14 @@ class MOZ_STACK_CLASS JS_HAZ_ROOTED ModuleValidatorShared {
|
||||
//
|
||||
// ModuleValidator is marked as rooted in the rooting analysis. Don't add
|
||||
// non-JSAtom pointers, or this will break!
|
||||
template <typename Unit>
|
||||
class MOZ_STACK_CLASS JS_HAZ_ROOTED ModuleValidator
|
||||
: public ModuleValidatorShared {
|
||||
private:
|
||||
AsmJSParser& parser_;
|
||||
AsmJSParser<Unit>& parser_;
|
||||
|
||||
public:
|
||||
ModuleValidator(JSContext* cx, AsmJSParser& parser,
|
||||
ModuleValidator(JSContext* cx, AsmJSParser<Unit>& parser,
|
||||
CodeNode* moduleFunctionNode)
|
||||
: ModuleValidatorShared(cx, moduleFunctionNode), parser_(parser) {}
|
||||
|
||||
@ -1972,7 +1979,7 @@ class MOZ_STACK_CLASS JS_HAZ_ROOTED ModuleValidator
|
||||
return true;
|
||||
}
|
||||
|
||||
AsmJSParser& parser() const { return parser_; }
|
||||
AsmJSParser<Unit>& parser() const { return parser_; }
|
||||
|
||||
auto tokenStream() const -> decltype(parser_.tokenStream)& {
|
||||
return parser_.tokenStream;
|
||||
@ -2349,7 +2356,7 @@ class MOZ_STACK_CLASS FunctionValidatorShared {
|
||||
using LocalMap = HashMap<PropertyName*, Local>;
|
||||
using LabelMap = HashMap<PropertyName*, uint32_t>;
|
||||
|
||||
// This is also a ModuleValidator& after the appropriate static_cast<>.
|
||||
// This is also a ModuleValidator<Unit>& after the appropriate static_cast<>.
|
||||
ModuleValidatorShared& m_;
|
||||
|
||||
ParseNode* fn_;
|
||||
@ -2382,7 +2389,9 @@ class MOZ_STACK_CLASS FunctionValidatorShared {
|
||||
ret_(ExprType::Limit) {}
|
||||
|
||||
protected:
|
||||
FunctionValidatorShared(ModuleValidator& m, ParseNode* fn, JSContext* cx)
|
||||
template <typename Unit>
|
||||
FunctionValidatorShared(ModuleValidator<Unit>& m, ParseNode* fn,
|
||||
JSContext* cx)
|
||||
: FunctionValidatorShared(static_cast<ModuleValidatorShared&>(m), fn,
|
||||
cx) {}
|
||||
|
||||
@ -2614,14 +2623,15 @@ class MOZ_STACK_CLASS FunctionValidatorShared {
|
||||
// Encapsulates the building of an asm bytecode function from an asm.js function
|
||||
// source code, packing the asm.js code into the asm bytecode form that can
|
||||
// be decoded and compiled with a FunctionCompiler.
|
||||
template <typename Unit>
|
||||
class MOZ_STACK_CLASS FunctionValidator : public FunctionValidatorShared {
|
||||
public:
|
||||
FunctionValidator(ModuleValidator& m, ParseNode* fn)
|
||||
FunctionValidator(ModuleValidator<Unit>& m, ParseNode* fn)
|
||||
: FunctionValidatorShared(m, fn, m.cx()) {}
|
||||
|
||||
public:
|
||||
ModuleValidator& m() const {
|
||||
return static_cast<ModuleValidator&>(FunctionValidatorShared::m());
|
||||
ModuleValidator<Unit>& m() const {
|
||||
return static_cast<ModuleValidator<Unit>&>(FunctionValidatorShared::m());
|
||||
}
|
||||
|
||||
MOZ_MUST_USE bool writeCall(ParseNode* pn, Op op) {
|
||||
@ -3078,7 +3088,8 @@ static bool CheckModuleGlobal(ModuleValidatorShared& m, ParseNode* var,
|
||||
return m.fail(initNode, "unsupported import expression");
|
||||
}
|
||||
|
||||
static bool CheckModuleProcessingDirectives(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckModuleProcessingDirectives(ModuleValidator<Unit>& m) {
|
||||
auto& ts = m.parser().tokenStream;
|
||||
while (true) {
|
||||
bool matched;
|
||||
@ -3105,7 +3116,8 @@ static bool CheckModuleProcessingDirectives(ModuleValidator& m) {
|
||||
}
|
||||
}
|
||||
|
||||
static bool CheckModuleGlobals(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckModuleGlobals(ModuleValidator<Unit>& m) {
|
||||
while (true) {
|
||||
ParseNode* varStmt;
|
||||
if (!ParseVarOrConstStatement(m.parser(), &varStmt)) {
|
||||
@ -3331,9 +3343,11 @@ static bool CheckVariables(FunctionValidatorShared& f, ParseNode** stmtIter) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckExpr(FunctionValidator& f, ParseNode* op, Type* type);
|
||||
template <typename Unit>
|
||||
static bool CheckExpr(FunctionValidator<Unit>& f, ParseNode* op, Type* type);
|
||||
|
||||
static bool CheckNumericLiteral(FunctionValidator& f, ParseNode* num,
|
||||
template <typename Unit>
|
||||
static bool CheckNumericLiteral(FunctionValidator<Unit>& f, ParseNode* num,
|
||||
Type* type) {
|
||||
NumLit lit = ExtractNumericLiteral(f.m(), num);
|
||||
if (!lit.valid()) {
|
||||
@ -3397,7 +3411,8 @@ static inline bool IsLiteralOrConstInt(FunctionValidatorShared& f,
|
||||
|
||||
static const int32_t NoMask = -1;
|
||||
|
||||
static bool CheckArrayAccess(FunctionValidator& f, ParseNode* viewName,
|
||||
template <typename Unit>
|
||||
static bool CheckArrayAccess(FunctionValidator<Unit>& f, ParseNode* viewName,
|
||||
ParseNode* indexExpr, Scalar::Type* viewType) {
|
||||
if (!viewName->isKind(ParseNodeKind::Name)) {
|
||||
return f.fail(viewName,
|
||||
@ -3502,7 +3517,9 @@ static bool WriteArrayAccessFlags(FunctionValidatorShared& f,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckLoadArray(FunctionValidator& f, ParseNode* elem, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckLoadArray(FunctionValidator<Unit>& f, ParseNode* elem,
|
||||
Type* type) {
|
||||
Scalar::Type viewType;
|
||||
|
||||
if (!CheckArrayAccess(f, ElemBase(elem), ElemIndex(elem), &viewType)) {
|
||||
@ -3562,7 +3579,8 @@ static bool CheckLoadArray(FunctionValidator& f, ParseNode* elem, Type* type) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckStoreArray(FunctionValidator& f, ParseNode* lhs,
|
||||
template <typename Unit>
|
||||
static bool CheckStoreArray(FunctionValidator<Unit>& f, ParseNode* lhs,
|
||||
ParseNode* rhs, Type* type) {
|
||||
Scalar::Type viewType;
|
||||
if (!CheckArrayAccess(f, ElemBase(lhs), ElemIndex(lhs), &viewType)) {
|
||||
@ -3654,7 +3672,8 @@ static bool CheckStoreArray(FunctionValidator& f, ParseNode* lhs,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckAssignName(FunctionValidator& f, ParseNode* lhs,
|
||||
template <typename Unit>
|
||||
static bool CheckAssignName(FunctionValidator<Unit>& f, ParseNode* lhs,
|
||||
ParseNode* rhs, Type* type) {
|
||||
RootedPropertyName name(f.cx(), lhs->as<NameNode>().name());
|
||||
|
||||
@ -3709,7 +3728,9 @@ static bool CheckAssignName(FunctionValidator& f, ParseNode* lhs,
|
||||
name);
|
||||
}
|
||||
|
||||
static bool CheckAssign(FunctionValidator& f, ParseNode* assign, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckAssign(FunctionValidator<Unit>& f, ParseNode* assign,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(assign->isKind(ParseNodeKind::AssignExpr));
|
||||
|
||||
ParseNode* lhs = BinaryLeft(assign);
|
||||
@ -3728,7 +3749,9 @@ static bool CheckAssign(FunctionValidator& f, ParseNode* assign, Type* type) {
|
||||
"left-hand side of assignment must be a variable or array access");
|
||||
}
|
||||
|
||||
static bool CheckMathIMul(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckMathIMul(FunctionValidator<Unit>& f, ParseNode* call,
|
||||
Type* type) {
|
||||
if (CallArgListLength(call) != 2) {
|
||||
return f.fail(call, "Math.imul must be passed 2 arguments");
|
||||
}
|
||||
@ -3757,7 +3780,9 @@ static bool CheckMathIMul(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
return f.encoder().writeOp(Op::I32Mul);
|
||||
}
|
||||
|
||||
static bool CheckMathClz32(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckMathClz32(FunctionValidator<Unit>& f, ParseNode* call,
|
||||
Type* type) {
|
||||
if (CallArgListLength(call) != 1) {
|
||||
return f.fail(call, "Math.clz32 must be passed 1 argument");
|
||||
}
|
||||
@ -3777,7 +3802,9 @@ static bool CheckMathClz32(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
return f.encoder().writeOp(Op::I32Clz);
|
||||
}
|
||||
|
||||
static bool CheckMathAbs(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckMathAbs(FunctionValidator<Unit>& f, ParseNode* call,
|
||||
Type* type) {
|
||||
if (CallArgListLength(call) != 1) {
|
||||
return f.fail(call, "Math.abs must be passed 1 argument");
|
||||
}
|
||||
@ -3808,7 +3835,9 @@ static bool CheckMathAbs(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
argType.toChars());
|
||||
}
|
||||
|
||||
static bool CheckMathSqrt(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckMathSqrt(FunctionValidator<Unit>& f, ParseNode* call,
|
||||
Type* type) {
|
||||
if (CallArgListLength(call) != 1) {
|
||||
return f.fail(call, "Math.sqrt must be passed 1 argument");
|
||||
}
|
||||
@ -3834,7 +3863,8 @@ static bool CheckMathSqrt(FunctionValidator& f, ParseNode* call, Type* type) {
|
||||
argType.toChars());
|
||||
}
|
||||
|
||||
static bool CheckMathMinMax(FunctionValidator& f, ParseNode* callNode,
|
||||
template <typename Unit>
|
||||
static bool CheckMathMinMax(FunctionValidator<Unit>& f, ParseNode* callNode,
|
||||
bool isMax, Type* type) {
|
||||
if (CallArgListLength(callNode) < 2) {
|
||||
return f.fail(callNode, "Math.min/max must be passed at least 2 arguments");
|
||||
@ -3894,8 +3924,8 @@ static bool CheckMathMinMax(FunctionValidator& f, ParseNode* callNode,
|
||||
using CheckArgType = bool (*)(FunctionValidatorShared& f, ParseNode* argNode,
|
||||
Type type);
|
||||
|
||||
template <CheckArgType checkArg>
|
||||
static bool CheckCallArgs(FunctionValidator& f, ParseNode* callNode,
|
||||
template <CheckArgType checkArg, typename Unit>
|
||||
static bool CheckCallArgs(FunctionValidator<Unit>& f, ParseNode* callNode,
|
||||
ValTypeVector* args) {
|
||||
ParseNode* argNode = CallArgList(callNode);
|
||||
for (unsigned i = 0; i < CallArgListLength(callNode);
|
||||
@ -3943,7 +3973,8 @@ static bool CheckSignatureAgainstExisting(ModuleValidatorShared& m,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFunctionSignature(ModuleValidator& m, ParseNode* usepn,
|
||||
template <typename Unit>
|
||||
static bool CheckFunctionSignature(ModuleValidator<Unit>& m, ParseNode* usepn,
|
||||
FuncType&& sig, PropertyName* name,
|
||||
ModuleValidatorShared::Func** func) {
|
||||
if (sig.args().length() > MaxParams) {
|
||||
@ -3978,7 +4009,8 @@ static bool CheckIsArgType(FunctionValidatorShared& f, ParseNode* argNode,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckInternalCall(FunctionValidator& f, ParseNode* callNode,
|
||||
template <typename Unit>
|
||||
static bool CheckInternalCall(FunctionValidator<Unit>& f, ParseNode* callNode,
|
||||
PropertyName* calleeName, Type ret, Type* type) {
|
||||
MOZ_ASSERT(ret.isCanonical());
|
||||
|
||||
@ -4007,7 +4039,8 @@ static bool CheckInternalCall(FunctionValidator& f, ParseNode* callNode,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFuncPtrTableAgainstExisting(ModuleValidator& m,
|
||||
template <typename Unit>
|
||||
static bool CheckFuncPtrTableAgainstExisting(ModuleValidator<Unit>& m,
|
||||
ParseNode* usepn,
|
||||
PropertyName* name, FuncType&& sig,
|
||||
unsigned mask,
|
||||
@ -4044,7 +4077,8 @@ static bool CheckFuncPtrTableAgainstExisting(ModuleValidator& m,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFuncPtrCall(FunctionValidator& f, ParseNode* callNode,
|
||||
template <typename Unit>
|
||||
static bool CheckFuncPtrCall(FunctionValidator<Unit>& f, ParseNode* callNode,
|
||||
Type ret, Type* type) {
|
||||
MOZ_ASSERT(ret.isCanonical());
|
||||
|
||||
@ -4124,7 +4158,8 @@ static bool CheckIsExternType(FunctionValidatorShared& f, ParseNode* argNode,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFFICall(FunctionValidator& f, ParseNode* callNode,
|
||||
template <typename Unit>
|
||||
static bool CheckFFICall(FunctionValidator<Unit>& f, ParseNode* callNode,
|
||||
unsigned ffiIndex, Type ret, Type* type) {
|
||||
MOZ_ASSERT(ret.isCanonical());
|
||||
|
||||
@ -4179,10 +4214,12 @@ static bool CheckFloatCoercionArg(FunctionValidatorShared& f,
|
||||
inputType.toChars());
|
||||
}
|
||||
|
||||
static bool CheckCoercedCall(FunctionValidator& f, ParseNode* call, Type ret,
|
||||
Type* type);
|
||||
template <typename Unit>
|
||||
static bool CheckCoercedCall(FunctionValidator<Unit>& f, ParseNode* call,
|
||||
Type ret, Type* type);
|
||||
|
||||
static bool CheckCoercionArg(FunctionValidator& f, ParseNode* arg,
|
||||
template <typename Unit>
|
||||
static bool CheckCoercionArg(FunctionValidator<Unit>& f, ParseNode* arg,
|
||||
Type expected, Type* type) {
|
||||
MOZ_ASSERT(expected.isCanonicalValType());
|
||||
|
||||
@ -4207,7 +4244,8 @@ static bool CheckCoercionArg(FunctionValidator& f, ParseNode* arg,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckMathFRound(FunctionValidator& f, ParseNode* callNode,
|
||||
template <typename Unit>
|
||||
static bool CheckMathFRound(FunctionValidator<Unit>& f, ParseNode* callNode,
|
||||
Type* type) {
|
||||
if (CallArgListLength(callNode) != 1) {
|
||||
return f.fail(callNode, "Math.fround must be passed 1 argument");
|
||||
@ -4224,7 +4262,9 @@ static bool CheckMathFRound(FunctionValidator& f, ParseNode* callNode,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckMathBuiltinCall(FunctionValidator& f, ParseNode* callNode,
|
||||
template <typename Unit>
|
||||
static bool CheckMathBuiltinCall(FunctionValidator<Unit>& f,
|
||||
ParseNode* callNode,
|
||||
AsmJSMathBuiltinFunction func, Type* type) {
|
||||
unsigned arity = 0;
|
||||
Op f32 = Op::Limit;
|
||||
@ -4375,7 +4415,8 @@ static bool CheckMathBuiltinCall(FunctionValidator& f, ParseNode* callNode,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckUncoercedCall(FunctionValidator& f, ParseNode* expr,
|
||||
template <typename Unit>
|
||||
static bool CheckUncoercedCall(FunctionValidator<Unit>& f, ParseNode* expr,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(expr->isKind(ParseNodeKind::CallExpr));
|
||||
|
||||
@ -4444,7 +4485,8 @@ static bool CoerceResult(FunctionValidatorShared& f, ParseNode* expr,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckCoercedMathBuiltinCall(FunctionValidator& f,
|
||||
template <typename Unit>
|
||||
static bool CheckCoercedMathBuiltinCall(FunctionValidator<Unit>& f,
|
||||
ParseNode* callNode,
|
||||
AsmJSMathBuiltinFunction func, Type ret,
|
||||
Type* type) {
|
||||
@ -4455,8 +4497,9 @@ static bool CheckCoercedMathBuiltinCall(FunctionValidator& f,
|
||||
return CoerceResult(f, callNode, ret, actual, type);
|
||||
}
|
||||
|
||||
static bool CheckCoercedCall(FunctionValidator& f, ParseNode* call, Type ret,
|
||||
Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckCoercedCall(FunctionValidator<Unit>& f, ParseNode* call,
|
||||
Type ret, Type* type) {
|
||||
MOZ_ASSERT(ret.isCanonical());
|
||||
|
||||
if (!CheckRecursionLimitDontReport(f.cx())) {
|
||||
@ -4506,7 +4549,8 @@ static bool CheckCoercedCall(FunctionValidator& f, ParseNode* call, Type ret,
|
||||
return CheckInternalCall(f, call, calleeName, ret, type);
|
||||
}
|
||||
|
||||
static bool CheckPos(FunctionValidator& f, ParseNode* pos, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckPos(FunctionValidator<Unit>& f, ParseNode* pos, Type* type) {
|
||||
MOZ_ASSERT(pos->isKind(ParseNodeKind::PosExpr));
|
||||
ParseNode* operand = UnaryKid(pos);
|
||||
|
||||
@ -4522,7 +4566,8 @@ static bool CheckPos(FunctionValidator& f, ParseNode* pos, Type* type) {
|
||||
return CoerceResult(f, operand, Type::Double, actual, type);
|
||||
}
|
||||
|
||||
static bool CheckNot(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckNot(FunctionValidator<Unit>& f, ParseNode* expr, Type* type) {
|
||||
MOZ_ASSERT(expr->isKind(ParseNodeKind::NotExpr));
|
||||
ParseNode* operand = UnaryKid(expr);
|
||||
|
||||
@ -4540,7 +4585,8 @@ static bool CheckNot(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
return f.encoder().writeOp(Op::I32Eqz);
|
||||
}
|
||||
|
||||
static bool CheckNeg(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckNeg(FunctionValidator<Unit>& f, ParseNode* expr, Type* type) {
|
||||
MOZ_ASSERT(expr->isKind(ParseNodeKind::NegExpr));
|
||||
ParseNode* operand = UnaryKid(expr);
|
||||
|
||||
@ -4568,7 +4614,8 @@ static bool CheckNeg(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
operandType.toChars());
|
||||
}
|
||||
|
||||
static bool CheckCoerceToInt(FunctionValidator& f, ParseNode* expr,
|
||||
template <typename Unit>
|
||||
static bool CheckCoerceToInt(FunctionValidator<Unit>& f, ParseNode* expr,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(expr->isKind(ParseNodeKind::BitNotExpr));
|
||||
ParseNode* operand = UnaryKid(expr);
|
||||
@ -4594,7 +4641,9 @@ static bool CheckCoerceToInt(FunctionValidator& f, ParseNode* expr,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckBitNot(FunctionValidator& f, ParseNode* neg, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckBitNot(FunctionValidator<Unit>& f, ParseNode* neg,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(neg->isKind(ParseNodeKind::BitNotExpr));
|
||||
ParseNode* operand = UnaryKid(neg);
|
||||
|
||||
@ -4620,9 +4669,13 @@ static bool CheckBitNot(FunctionValidator& f, ParseNode* neg, Type* type) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckAsExprStatement(FunctionValidator& f, ParseNode* exprStmt);
|
||||
template <typename Unit>
|
||||
static bool CheckAsExprStatement(FunctionValidator<Unit>& f,
|
||||
ParseNode* exprStmt);
|
||||
|
||||
static bool CheckComma(FunctionValidator& f, ParseNode* comma, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckComma(FunctionValidator<Unit>& f, ParseNode* comma,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(comma->isKind(ParseNodeKind::CommaExpr));
|
||||
ParseNode* operands = ListHead(comma);
|
||||
|
||||
@ -4654,7 +4707,8 @@ static bool CheckComma(FunctionValidator& f, ParseNode* comma, Type* type) {
|
||||
return f.encoder().writeOp(Op::End);
|
||||
}
|
||||
|
||||
static bool CheckConditional(FunctionValidator& f, ParseNode* ternary,
|
||||
template <typename Unit>
|
||||
static bool CheckConditional(FunctionValidator<Unit>& f, ParseNode* ternary,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(ternary->isKind(ParseNodeKind::ConditionalExpr));
|
||||
|
||||
@ -4711,7 +4765,9 @@ static bool CheckConditional(FunctionValidator& f, ParseNode* ternary,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool IsValidIntMultiplyConstant(ModuleValidator& m, ParseNode* expr) {
|
||||
template <typename Unit>
|
||||
static bool IsValidIntMultiplyConstant(ModuleValidator<Unit>& m,
|
||||
ParseNode* expr) {
|
||||
if (!IsNumericLiteral(m, expr)) {
|
||||
return false;
|
||||
}
|
||||
@ -4734,7 +4790,9 @@ static bool IsValidIntMultiplyConstant(ModuleValidator& m, ParseNode* expr) {
|
||||
MOZ_MAKE_COMPILER_ASSUME_IS_UNREACHABLE("Bad literal");
|
||||
}
|
||||
|
||||
static bool CheckMultiply(FunctionValidator& f, ParseNode* star, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckMultiply(FunctionValidator<Unit>& f, ParseNode* star,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(star->isKind(ParseNodeKind::MulExpr));
|
||||
ParseNode* lhs = MultiplyLeft(star);
|
||||
ParseNode* rhs = MultiplyRight(star);
|
||||
@ -4774,8 +4832,9 @@ static bool CheckMultiply(FunctionValidator& f, ParseNode* star, Type* type) {
|
||||
star, "multiply operands must be both int, both double? or both float?");
|
||||
}
|
||||
|
||||
static bool CheckAddOrSub(FunctionValidator& f, ParseNode* expr, Type* type,
|
||||
unsigned* numAddOrSubOut = nullptr) {
|
||||
template <typename Unit>
|
||||
static bool CheckAddOrSub(FunctionValidator<Unit>& f, ParseNode* expr,
|
||||
Type* type, unsigned* numAddOrSubOut = nullptr) {
|
||||
if (!CheckRecursionLimitDontReport(f.cx())) {
|
||||
return f.m().failOverRecursed();
|
||||
}
|
||||
@ -4854,7 +4913,9 @@ static bool CheckAddOrSub(FunctionValidator& f, ParseNode* expr, Type* type,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckDivOrMod(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckDivOrMod(FunctionValidator<Unit>& f, ParseNode* expr,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(expr->isKind(ParseNodeKind::DivExpr) ||
|
||||
expr->isKind(ParseNodeKind::ModExpr));
|
||||
|
||||
@ -4905,7 +4966,9 @@ static bool CheckDivOrMod(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
lhsType.toChars(), rhsType.toChars());
|
||||
}
|
||||
|
||||
static bool CheckComparison(FunctionValidator& f, ParseNode* comp, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckComparison(FunctionValidator<Unit>& f, ParseNode* comp,
|
||||
Type* type) {
|
||||
MOZ_ASSERT(comp->isKind(ParseNodeKind::LtExpr) ||
|
||||
comp->isKind(ParseNodeKind::LeExpr) ||
|
||||
comp->isKind(ParseNodeKind::GtExpr) ||
|
||||
@ -5036,7 +5099,9 @@ static bool CheckComparison(FunctionValidator& f, ParseNode* comp, Type* type) {
|
||||
return f.encoder().writeOp(stmt);
|
||||
}
|
||||
|
||||
static bool CheckBitwise(FunctionValidator& f, ParseNode* bitwise, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckBitwise(FunctionValidator<Unit>& f, ParseNode* bitwise,
|
||||
Type* type) {
|
||||
ParseNode* lhs = BitwiseLeft(bitwise);
|
||||
ParseNode* rhs = BitwiseRight(bitwise);
|
||||
|
||||
@ -5151,7 +5216,8 @@ static bool CheckBitwise(FunctionValidator& f, ParseNode* bitwise, Type* type) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckExpr(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
template <typename Unit>
|
||||
static bool CheckExpr(FunctionValidator<Unit>& f, ParseNode* expr, Type* type) {
|
||||
if (!CheckRecursionLimitDontReport(f.cx())) {
|
||||
return f.m().failOverRecursed();
|
||||
}
|
||||
@ -5214,9 +5280,11 @@ static bool CheckExpr(FunctionValidator& f, ParseNode* expr, Type* type) {
|
||||
return f.fail(expr, "unsupported expression");
|
||||
}
|
||||
|
||||
static bool CheckStatement(FunctionValidator& f, ParseNode* stmt);
|
||||
template <typename Unit>
|
||||
static bool CheckStatement(FunctionValidator<Unit>& f, ParseNode* stmt);
|
||||
|
||||
static bool CheckAsExprStatement(FunctionValidator& f, ParseNode* expr) {
|
||||
template <typename Unit>
|
||||
static bool CheckAsExprStatement(FunctionValidator<Unit>& f, ParseNode* expr) {
|
||||
if (expr->isKind(ParseNodeKind::CallExpr)) {
|
||||
Type ignored;
|
||||
return CheckCoercedCall(f, expr, Type::Void, &ignored);
|
||||
@ -5236,12 +5304,16 @@ static bool CheckAsExprStatement(FunctionValidator& f, ParseNode* expr) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckExprStatement(FunctionValidator& f, ParseNode* exprStmt) {
|
||||
template <typename Unit>
|
||||
static bool CheckExprStatement(FunctionValidator<Unit>& f,
|
||||
ParseNode* exprStmt) {
|
||||
MOZ_ASSERT(exprStmt->isKind(ParseNodeKind::ExpressionStmt));
|
||||
return CheckAsExprStatement(f, UnaryKid(exprStmt));
|
||||
}
|
||||
|
||||
static bool CheckLoopConditionOnEntry(FunctionValidator& f, ParseNode* cond) {
|
||||
template <typename Unit>
|
||||
static bool CheckLoopConditionOnEntry(FunctionValidator<Unit>& f,
|
||||
ParseNode* cond) {
|
||||
uint32_t maybeLit;
|
||||
if (IsLiteralInt(f.m(), cond, &maybeLit) && maybeLit) {
|
||||
return true;
|
||||
@ -5267,7 +5339,8 @@ static bool CheckLoopConditionOnEntry(FunctionValidator& f, ParseNode* cond) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckWhile(FunctionValidator& f, ParseNode* whileStmt,
|
||||
template <typename Unit>
|
||||
static bool CheckWhile(FunctionValidator<Unit>& f, ParseNode* whileStmt,
|
||||
const LabelVector* labels = nullptr) {
|
||||
MOZ_ASSERT(whileStmt->isKind(ParseNodeKind::WhileStmt));
|
||||
ParseNode* cond = BinaryLeft(whileStmt);
|
||||
@ -5308,7 +5381,8 @@ static bool CheckWhile(FunctionValidator& f, ParseNode* whileStmt,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFor(FunctionValidator& f, ParseNode* forStmt,
|
||||
template <typename Unit>
|
||||
static bool CheckFor(FunctionValidator<Unit>& f, ParseNode* forStmt,
|
||||
const LabelVector* labels = nullptr) {
|
||||
MOZ_ASSERT(forStmt->isKind(ParseNodeKind::ForStmt));
|
||||
ParseNode* forHead = BinaryLeft(forStmt);
|
||||
@ -5393,7 +5467,8 @@ static bool CheckFor(FunctionValidator& f, ParseNode* forStmt,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckDoWhile(FunctionValidator& f, ParseNode* whileStmt,
|
||||
template <typename Unit>
|
||||
static bool CheckDoWhile(FunctionValidator<Unit>& f, ParseNode* whileStmt,
|
||||
const LabelVector* labels = nullptr) {
|
||||
MOZ_ASSERT(whileStmt->isKind(ParseNodeKind::DoWhileStmt));
|
||||
ParseNode* body = BinaryLeft(whileStmt);
|
||||
@ -5450,10 +5525,12 @@ static bool CheckDoWhile(FunctionValidator& f, ParseNode* whileStmt,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckStatementList(FunctionValidator& f, ParseNode*,
|
||||
template <typename Unit>
|
||||
static bool CheckStatementList(FunctionValidator<Unit>& f, ParseNode*,
|
||||
const LabelVector* = nullptr);
|
||||
|
||||
static bool CheckLabel(FunctionValidator& f, ParseNode* labeledStmt) {
|
||||
template <typename Unit>
|
||||
static bool CheckLabel(FunctionValidator<Unit>& f, ParseNode* labeledStmt) {
|
||||
MOZ_ASSERT(labeledStmt->isKind(ParseNodeKind::LabelStmt));
|
||||
|
||||
LabelVector labels;
|
||||
@ -5492,7 +5569,8 @@ static bool CheckLabel(FunctionValidator& f, ParseNode* labeledStmt) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckIf(FunctionValidator& f, ParseNode* ifStmt) {
|
||||
template <typename Unit>
|
||||
static bool CheckIf(FunctionValidator<Unit>& f, ParseNode* ifStmt) {
|
||||
uint32_t numIfEnd = 1;
|
||||
|
||||
recurse:
|
||||
@ -5622,7 +5700,8 @@ static bool CheckSwitchRange(FunctionValidatorShared& f, ParseNode* stmt,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckSwitchExpr(FunctionValidator& f, ParseNode* switchExpr) {
|
||||
template <typename Unit>
|
||||
static bool CheckSwitchExpr(FunctionValidator<Unit>& f, ParseNode* switchExpr) {
|
||||
Type exprType;
|
||||
if (!CheckExpr(f, switchExpr, &exprType)) {
|
||||
return false;
|
||||
@ -5646,7 +5725,8 @@ static bool CheckSwitchExpr(FunctionValidator& f, ParseNode* switchExpr) {
|
||||
// matches the sequential order of cases.
|
||||
// - one block for the br_table, so that the first break goes to the first
|
||||
// case's block.
|
||||
static bool CheckSwitch(FunctionValidator& f, ParseNode* switchStmt) {
|
||||
template <typename Unit>
|
||||
static bool CheckSwitch(FunctionValidator<Unit>& f, ParseNode* switchStmt) {
|
||||
MOZ_ASSERT(switchStmt->isKind(ParseNodeKind::SwitchStmt));
|
||||
|
||||
ParseNode* switchExpr = BinaryLeft(switchStmt);
|
||||
@ -5808,7 +5888,8 @@ static bool CheckReturnType(FunctionValidatorShared& f, ParseNode* usepn,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckReturn(FunctionValidator& f, ParseNode* returnStmt) {
|
||||
template <typename Unit>
|
||||
static bool CheckReturn(FunctionValidator<Unit>& f, ParseNode* returnStmt) {
|
||||
ParseNode* expr = ReturnExpr(returnStmt);
|
||||
|
||||
if (!expr) {
|
||||
@ -5837,7 +5918,8 @@ static bool CheckReturn(FunctionValidator& f, ParseNode* returnStmt) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckStatementList(FunctionValidator& f, ParseNode* stmtList,
|
||||
template <typename Unit>
|
||||
static bool CheckStatementList(FunctionValidator<Unit>& f, ParseNode* stmtList,
|
||||
const LabelVector* labels /*= nullptr */) {
|
||||
MOZ_ASSERT(stmtList->isKind(ParseNodeKind::StatementList));
|
||||
|
||||
@ -5857,7 +5939,8 @@ static bool CheckStatementList(FunctionValidator& f, ParseNode* stmtList,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckLexicalScope(FunctionValidator& f, ParseNode* node) {
|
||||
template <typename Unit>
|
||||
static bool CheckLexicalScope(FunctionValidator<Unit>& f, ParseNode* node) {
|
||||
LexicalScopeNode* lexicalScope = &node->as<LexicalScopeNode>();
|
||||
if (!lexicalScope->isEmptyScope()) {
|
||||
return f.fail(lexicalScope, "cannot have 'let' or 'const' declarations");
|
||||
@ -5874,7 +5957,8 @@ static bool CheckBreakOrContinue(FunctionValidatorShared& f, bool isBreak,
|
||||
return f.writeUnlabeledBreakOrContinue(isBreak);
|
||||
}
|
||||
|
||||
static bool CheckStatement(FunctionValidator& f, ParseNode* stmt) {
|
||||
template <typename Unit>
|
||||
static bool CheckStatement(FunctionValidator<Unit>& f, ParseNode* stmt) {
|
||||
if (!CheckRecursionLimitDontReport(f.cx())) {
|
||||
return f.m().failOverRecursed();
|
||||
}
|
||||
@ -5912,7 +5996,8 @@ static bool CheckStatement(FunctionValidator& f, ParseNode* stmt) {
|
||||
return f.fail(stmt, "unexpected statement kind");
|
||||
}
|
||||
|
||||
static bool ParseFunction(ModuleValidator& m, CodeNode** funNodeOut,
|
||||
template <typename Unit>
|
||||
static bool ParseFunction(ModuleValidator<Unit>& m, CodeNode** funNodeOut,
|
||||
unsigned* line) {
|
||||
auto& tokenStream = m.tokenStream();
|
||||
|
||||
@ -5981,11 +6066,12 @@ static bool ParseFunction(ModuleValidator& m, CodeNode** funNodeOut,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFunction(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckFunction(ModuleValidator<Unit>& m) {
|
||||
// asm.js modules can be quite large when represented as parse trees so pop
|
||||
// the backing LifoAlloc after parsing/compiling each function. Release the
|
||||
// parser's lifo memory after the last use of a parse node.
|
||||
AsmJSParser::Mark mark = m.parser().mark();
|
||||
frontend::ParserBase::Mark mark = m.parser().mark();
|
||||
auto releaseMark =
|
||||
mozilla::MakeScopeExit([&m, &mark] { m.parser().release(mark); });
|
||||
|
||||
@ -5999,7 +6085,7 @@ static bool CheckFunction(ModuleValidator& m) {
|
||||
return false;
|
||||
}
|
||||
|
||||
FunctionValidator f(m, funNode);
|
||||
FunctionValidator<Unit> f(m, funNode);
|
||||
|
||||
ParseNode* stmtIter = ListHead(FunctionStatementList(funNode));
|
||||
|
||||
@ -6057,7 +6143,8 @@ static bool CheckAllFunctionsDefined(ModuleValidatorShared& m) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFunctions(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckFunctions(ModuleValidator<Unit>& m) {
|
||||
while (true) {
|
||||
TokenKind tk;
|
||||
if (!PeekToken(m.parser(), &tk)) {
|
||||
@ -6076,7 +6163,8 @@ static bool CheckFunctions(ModuleValidator& m) {
|
||||
return CheckAllFunctionsDefined(m);
|
||||
}
|
||||
|
||||
static bool CheckFuncPtrTable(ModuleValidator& m, ParseNode* var) {
|
||||
template <typename Unit>
|
||||
static bool CheckFuncPtrTable(ModuleValidator<Unit>& m, ParseNode* var) {
|
||||
if (!var->isKind(ParseNodeKind::Name)) {
|
||||
return m.fail(var, "function-pointer table name is not a plain name");
|
||||
}
|
||||
@ -6144,7 +6232,8 @@ static bool CheckFuncPtrTable(ModuleValidator& m, ParseNode* var) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckFuncPtrTables(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckFuncPtrTables(ModuleValidator<Unit>& m) {
|
||||
while (true) {
|
||||
ParseNode* varStmt;
|
||||
if (!ParseVarOrConstStatement(m.parser(), &varStmt)) {
|
||||
@ -6215,7 +6304,8 @@ static bool CheckModuleExportObject(ModuleValidatorShared& m,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckModuleReturn(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckModuleReturn(ModuleValidator<Unit>& m) {
|
||||
TokenKind tk;
|
||||
if (!GetToken(m.parser(), &tk)) {
|
||||
return false;
|
||||
@ -6252,7 +6342,8 @@ static bool CheckModuleReturn(ModuleValidator& m) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool CheckModuleEnd(ModuleValidator& m) {
|
||||
template <typename Unit>
|
||||
static bool CheckModuleEnd(ModuleValidator<Unit>& m) {
|
||||
TokenKind tk;
|
||||
if (!GetToken(m.parser(), &tk)) {
|
||||
return false;
|
||||
@ -6267,14 +6358,15 @@ static bool CheckModuleEnd(ModuleValidator& m) {
|
||||
return true;
|
||||
}
|
||||
|
||||
static SharedModule CheckModule(JSContext* cx, AsmJSParser& parser,
|
||||
template <typename Unit>
|
||||
static SharedModule CheckModule(JSContext* cx, AsmJSParser<Unit>& parser,
|
||||
ParseNode* stmtList, UniqueLinkData* linkData,
|
||||
unsigned* time) {
|
||||
int64_t before = PRMJ_Now();
|
||||
|
||||
CodeNode* moduleFunctionNode = parser.pc->functionBox()->functionNode;
|
||||
|
||||
ModuleValidator m(cx, parser, moduleFunctionNode);
|
||||
ModuleValidator<Unit> m(cx, parser, moduleFunctionNode);
|
||||
if (!m.init()) {
|
||||
return nullptr;
|
||||
}
|
||||
@ -7031,11 +7123,11 @@ class ModuleChars {
|
||||
Vector<CacheableChars, 0, SystemAllocPolicy> funCtorArgs_;
|
||||
|
||||
public:
|
||||
static uint32_t beginOffset(AsmJSParser& parser) {
|
||||
static uint32_t beginOffset(AsmJSParser<char16_t>& parser) {
|
||||
return parser.pc->functionBox()->functionNode->pn_pos.begin;
|
||||
}
|
||||
|
||||
static uint32_t endOffset(AsmJSParser& parser) {
|
||||
static uint32_t endOffset(AsmJSParser<char16_t>& parser) {
|
||||
TokenPos pos(0, 0); // initialize to silence GCC warning
|
||||
MOZ_ALWAYS_TRUE(
|
||||
parser.tokenStream.peekTokenPos(&pos, TokenStreamShared::Operand));
|
||||
@ -7049,7 +7141,7 @@ class ModuleCharsForStore : ModuleChars {
|
||||
Vector<char, 0, SystemAllocPolicy> compressedBuffer_;
|
||||
|
||||
public:
|
||||
bool init(AsmJSParser& parser) {
|
||||
bool init(AsmJSParser<char16_t>& parser) {
|
||||
MOZ_ASSERT(beginOffset(parser) < endOffset(parser));
|
||||
|
||||
uncompressedSize_ =
|
||||
@ -7152,7 +7244,7 @@ class ModuleCharsForLookup : ModuleChars {
|
||||
return cursor;
|
||||
}
|
||||
|
||||
bool match(AsmJSParser& parser) const {
|
||||
bool match(AsmJSParser<char16_t>& parser) const {
|
||||
const char16_t* parseBegin =
|
||||
parser.tokenStream.codeUnitPtrAt(beginOffset(parser));
|
||||
const char16_t* parseLimit = parser.tokenStream.rawLimit();
|
||||
@ -7229,10 +7321,9 @@ struct ScopedCacheEntryOpenedForRead {
|
||||
|
||||
} // unnamed namespace
|
||||
|
||||
static JS::AsmJSCacheResult StoreAsmJSModuleInCache(AsmJSParser& parser,
|
||||
const Module& module,
|
||||
const LinkData& linkData,
|
||||
JSContext* cx) {
|
||||
static JS::AsmJSCacheResult StoreAsmJSModuleInCache(
|
||||
AsmJSParser<char16_t>& parser, const Module& module,
|
||||
const LinkData& linkData, JSContext* cx) {
|
||||
ModuleCharsForStore moduleChars;
|
||||
if (!moduleChars.init(parser)) {
|
||||
return JS::AsmJSCache_InternalError;
|
||||
@ -7283,7 +7374,8 @@ static JS::AsmJSCacheResult StoreAsmJSModuleInCache(AsmJSParser& parser,
|
||||
return JS::AsmJSCache_Success;
|
||||
}
|
||||
|
||||
static bool LookupAsmJSModuleInCache(JSContext* cx, AsmJSParser& parser,
|
||||
static bool LookupAsmJSModuleInCache(JSContext* cx,
|
||||
AsmJSParser<char16_t>& parser,
|
||||
bool* loadedFromCache,
|
||||
SharedModule* module,
|
||||
UniqueChars* compilationTimeReport) {
|
||||
@ -7385,11 +7477,12 @@ static bool NoExceptionPending(JSContext* cx) {
|
||||
return cx->helperThread() || !cx->isExceptionPending();
|
||||
}
|
||||
|
||||
static bool SuccessfulValidation(AsmJSParser& parser, UniqueChars str) {
|
||||
static bool SuccessfulValidation(frontend::ParserBase& parser,
|
||||
UniqueChars str) {
|
||||
return parser.warningNoOffset(JSMSG_USE_ASM_TYPE_OK, str.get());
|
||||
}
|
||||
|
||||
static bool TypeFailureWarning(AsmJSParser& parser, const char* str) {
|
||||
static bool TypeFailureWarning(frontend::ParserBase& parser, const char* str) {
|
||||
if (parser.options().throwOnAsmJSValidationFailureOption) {
|
||||
parser.errorNoOffset(JSMSG_USE_ASM_TYPE_FAIL, str ? str : "");
|
||||
return false;
|
||||
@ -7402,7 +7495,8 @@ static bool TypeFailureWarning(AsmJSParser& parser, const char* str) {
|
||||
return false;
|
||||
}
|
||||
|
||||
static bool EstablishPreconditions(JSContext* cx, AsmJSParser& parser) {
|
||||
static bool EstablishPreconditions(JSContext* cx,
|
||||
frontend::ParserBase& parser) {
|
||||
// asm.js requires Ion.
|
||||
if (!HasCompilerSupport(cx) || !IonCanCompile()) {
|
||||
return TypeFailureWarning(parser, "Disabled by lack of compiler support");
|
||||
@ -7489,8 +7583,8 @@ static UniqueChars BuildConsoleMessage(unsigned time,
|
||||
#endif
|
||||
}
|
||||
|
||||
bool js::CompileAsmJS(JSContext* cx, AsmJSParser& parser, ParseNode* stmtList,
|
||||
bool* validated) {
|
||||
bool js::CompileAsmJS(JSContext* cx, AsmJSParser<char16_t>& parser,
|
||||
ParseNode* stmtList, bool* validated) {
|
||||
*validated = false;
|
||||
|
||||
// Various conditions disable asm.js optimizations.
|
||||
|
@ -50,7 +50,8 @@ class FullParseHandler;
|
||||
|
||||
} // namespace frontend
|
||||
|
||||
using AsmJSParser = frontend::Parser<frontend::FullParseHandler, char16_t>;
|
||||
template <typename Unit>
|
||||
using AsmJSParser = frontend::Parser<frontend::FullParseHandler, Unit>;
|
||||
|
||||
// This function takes over parsing of a function starting with "use asm". The
|
||||
// return value indicates whether an error was reported which the caller should
|
||||
@ -59,7 +60,8 @@ using AsmJSParser = frontend::Parser<frontend::FullParseHandler, char16_t>;
|
||||
// indeterminate amount and the entire function should be reparsed from the
|
||||
// beginning.
|
||||
|
||||
extern MOZ_MUST_USE bool CompileAsmJS(JSContext* cx, AsmJSParser& parser,
|
||||
extern MOZ_MUST_USE bool CompileAsmJS(JSContext* cx,
|
||||
AsmJSParser<char16_t>& parser,
|
||||
frontend::ParseNode* stmtList,
|
||||
bool* validated);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user