diff --git a/Libraries/LibJS/AST.cpp b/Libraries/LibJS/AST.cpp index b3daa4eb3b..a20b90d028 100644 --- a/Libraries/LibJS/AST.cpp +++ b/Libraries/LibJS/AST.cpp @@ -66,8 +66,9 @@ Value CallExpression::execute(Interpreter& interpreter) const if (interpreter.exception()) return {}; - ASSERT(callee.is_object()); - ASSERT(callee.as_object()->is_function()); + if (!callee.is_object() || !callee.as_object()->is_function()) + return interpreter.throw_exception("TypeError", String::format("%s is not a function", callee.to_string().characters())); + auto* function = static_cast(callee.as_object()); auto& call_frame = interpreter.push_call_frame(); diff --git a/Libraries/LibJS/Tests/function-TypeError.js b/Libraries/LibJS/Tests/function-TypeError.js new file mode 100644 index 0000000000..90cae589a4 --- /dev/null +++ b/Libraries/LibJS/Tests/function-TypeError.js @@ -0,0 +1,31 @@ +function assert(x) { if (!x) throw 1; } + +try { + try { + var b = true; + b(); + } catch(e) { + assert(e.name === "TypeError"); + assert(e.message === "true is not a function"); + } + + try { + var n = 100 + 20 + 3; + n(); + } catch(e) { + assert(e.name === "TypeError"); + assert(e.message === "123 is not a function"); + } + + try { + var o = {}; + o.a(); + } catch(e) { + assert(e.name === "TypeError"); + assert(e.message === "undefined is not a function"); + } + + console.log("PASS"); +} catch(e) { + console.log("FAIL: " + e); +}