Commit graph

254 commits

Author SHA1 Message Date
Andreas Kling
c833885fb5 LibJS: Keep cached this value in a call frame register
Just moving more things to call frame registers..
2023-09-28 06:09:16 +02:00
Andreas Kling
4c5b9fa6a2 LibJS: Remove unused SetVariable::InitializationMode::InitializeOrSet 2023-09-26 09:38:32 +02:00
Shannon Booth
30ab198b40 LibJS: Create const variables in ForIn/OfBodyEvaluation in strict mode
Our implementation of environment.CreateImmutableBinding(name, true)
in this AO was not correctly initializing const variables in strict
mode. This would mean that constant declarations in for loop bodies
would not throw if they were modified.

To fix this, add a new parameter to CreateVariable to set strict mode.
Also remove the vm.is_strict mode check here, as it doesn't look like
anywhere in the spec will change strict mode depending on whether the
script itself is running in script mode or not.

This fixes two of our test-js tests, no change to test262.
2023-09-21 16:19:05 +02:00
Timothy Flynn
54d1f4e234 LibJS: Stop propagating small OOM errors from the Error object 2023-09-09 13:03:25 -04:00
Luke Wilde
b3fa79e64d LibJS: Cover all property kinds when stringifying Put bytecode ops 2023-08-29 21:38:54 -04:00
Luke Wilde
2aaae6fc70 LibJS: Avoid ToPropertyKey for spreading in PutByValue(WithThis)
This is not we're supposed to do according to https://tc39.es/ecma262/#sec-runtime-semantics-propertydefinitionevaluation
Furthermore, this was observable by ToPrimitive looking up toString and
valueOf and potentially calling them if they exist. The big ticket
issue however is that for objects without toString and valueOf, such as
null-proto objects, this would unexpectedly throw.
2023-08-29 21:38:54 -04:00
Andreas Kling
97ebfd9f0f LibJS: Make Value::to_string_without_side_effects() infallible
Work towards #20449.
2023-08-09 17:09:16 +02:00
Andreas Kling
1a27c525d5 LibJS: Make PrimitiveString::create() infallible
Work towards #20449.
2023-08-09 17:09:16 +02:00
Andreas Kling
e91bdedc93 LibJS: Use correct this value when callee is a with binding
If we're inside of a `with` statement scope, we have to take care to
extract the correct `this` value for use in calls when calling a method
on the binding object via an Identifier instead of a MemberExpression.

This makes Vue.js work way better in the bytecode VM. :^)

Also, 1 new pass on test262.
2023-08-01 16:08:21 +02:00
Aliaksandr Kalenik
2bdc69c42c LibJS: Add caching of this value in ResolveThisBinding instruction
Because "this" value cannot be changed during function execution it is
safe to compute it once and then use for future access.

This optimization makes ai-astar.js run 8% faster.
2023-07-29 04:23:49 +02:00
Timothy Flynn
77d7f715e3 LibJS+CI: Remove bytecode optimization passes for now
These passes have not been shown to actually optimize any JS, and tests
have become very flaky with optimizations enabled. Until some measurable
benefit is shown, remove the optimization passes to reduce overhead of
maintaining bytecode operations and to reduce CI churn. The framework
for optimizations will live on in git history, and can be restored once
proven useful.
2023-07-21 19:47:36 +03:30
Andreas Kling
c90bf22d29 LibJS/Bytecode: Use primitive this for strict mode GetByValue
GetByValue now shares code with GetById to elide the synthetic wrapper
objects for primitive values in strict mode.

Fixes 2 test-js tests in bytecode mode. :^)
2023-07-21 14:14:00 +02:00
Andreas Kling
7253d021fc LibJS/Bytecode: Factor out determining the base object from GetById
This will allow us to use the same logic in GetByValue (in a subsequent
commit.)
2023-07-21 14:14:00 +02:00
Timothy Flynn
9d7215c636 LibJS+LibWeb: Move IteratorOperations.h AOs to Iterator.h
Rather than splitting the Iterator type and its AOs into two files,
let's combine them into one file to match every other JS runtime object
that we have.
2023-07-19 14:11:43 +01:00
Luke Wilde
d66eb4e3ba LibJS/Bytecode: Add Await and AsyncIteratorClose instructions 2023-07-15 01:08:52 +02:00
Gabriel Dinner-David
d29bd55b48 LibJS: Implement import.meta for bytecode 2023-07-14 06:06:04 +02:00
Andreas Kling
c0f985ffcf LibJS/Bytecode: Don't reparse regular expressions on instantiation
The RegExpLiteral AST node already has the parsed regex::Parser::Result
so let's plumb that over to the bytecode executable instead of reparsing
the regex every time NewRegExp is executed.

~12% speed-up on language/literals/regexp/S7.8.5_A2.1_T2.js in test262.
2023-07-13 13:30:49 +02:00
Andreas Kling
640d48255b LibJS: Remove unhelpful environment lookup optimization for globals
This optimization was no longer helpful after the bug fix for missing
invalidation on global delete was introduced in 331f6a9e6, since we
now have to check bindings for presence in the global environment every
time anyway.

Since the bytecode VM now has fast GetGlobal in most cases, let's not
even worry about this and just remove the unhelpful "optimization".

In fact, removing this is actually an *optimization*, since we avoid
a redundant has_binding() check on every global variable access. :^)
2023-07-13 10:56:59 +02:00
Aliaksandr Kalenik
3661d674ae LibJS: Add optimized GetGlobal instruction to access global variables
Using a special instruction to access global variables allows skipping
the environment chain traversal for them and going directly to the
module/global environment. Currently, this instruction only caches the
offset for bindings that belong to the global object environment.
However, there is also an opportunity to cache the offset in the global
declarative record.

This change results in a 57% increase in speed for
imaging-gaussian-blur.js in Kraken.
2023-07-12 16:03:16 +02:00
Andreas Kling
cf6792ec40 LibJS/Bytecode: Invalidate inline caches on unique shape mutation
Since we can't rely on shape identity (i.e its pointer address) for
unique shapes, give them a serial number that increments whenever a
mutation occurs.

Inline caches can then compare this serial number against what they
have seen before.
2023-07-11 00:14:50 +02:00
Andreas Kling
e0b2757f95 LibJS/Bytecode: Always make own properties in object expressions
When building an object from an object expression, we don't want to
go through the full property setting machinery. This patch adds a new
PropertyKind::DirectKeyValue for PutById which guarantees that the
property becomes an own property.

This fixes an issue where setting the "__proto__" property in object
expressions wasn't working right.

12 new passes on test262. :^)
2023-07-10 09:29:54 +01:00
Andreas Kling
de8e4b1853 LibJS/Bytecode: Cache object own property accesses
The instructions GetById and GetByIdWithThis now remember the last-seen
Shape, and if we see the same object again, we reuse the property offset
from last time without doing a new lookup.

This allows us to use Object::get_direct(), bypassing the entire lookup
machinery and saving lots of time.

~23% speed-up on Kraken/ai-astar.js :^)
2023-07-09 12:54:06 +02:00
Timothy Flynn
c911781c21 Everywhere: Remove needless trailing semi-colons after functions
This is a new option in clang-format-16.
2023-07-08 10:32:56 +01:00
Timothy Flynn
23daf5097b LibJS/Bytecode: Generate bytecode for deleting super properties 2023-07-07 18:11:51 +02:00
Timothy Flynn
621d55ad65 LibJS/Bytecode: Do note coerce referenced values to an Object too early
Converting a base value to an Object is performed by Reference::delete_.
Doing this early in the bytecode operator could be observable, although
it would likely be the first observable step in Reference::delete_
anyways. This will just align these operators with upcoming operators
for super references, where doing this coercion first will be observable
(we need to throw an exception for deleting a super property before this
coercion).
2023-07-07 18:11:51 +02:00
Daniel Bertalan
c6c20d3bf3 LibJS/Bytecode: Use CopyDataProperties AO for destructuring
The previous ad-hoc implementation ignored the non-enumerable flag.
2023-07-06 12:11:02 +01:00
Daniel Bertalan
b39d8af5a6 LibJS/Bytecode: Remove redundant property uniqueness check
This invariant is enforced by virtue of `items` being a HashTable.
2023-07-06 10:30:42 +02:00
Daniel Bertalan
d0dce5c60f LibJS/Bytecode: Handle shadowed non-enumerable properties in for-in
Invariants 5 and 6 of the `EnumerateObjectProperties` AO mean that we
must not include an enumerate property if there is a non-enumerable
property higher up the prototype chain with the same name. The previous
implementation did not adhere to this, as `EnumerableOwnPropertyNames`
does not carry information about present but non-enumerable properties.
2023-07-06 10:30:42 +02:00
Luke Wilde
442ca4f9b4 LibJS: Avoid RequireObjectCoercible when creating super references
This is part of an old normative change that happened soon after
Andreas made `super` closer to spec in 1270df2.
See https://github.com/tc39/ecma262/pull/2267/

This was introduced into bytecode by virtue of copy and paste :^)

Bytecode results:
Summary:
    Diff Tests:
        +2     -2 
2023-07-06 08:54:46 +02:00
Luke Wilde
b271d9a6bf LibJS/Bytecode: Use proper this for receiver in get/set for super expr
Summary:
    Diff Tests:
        +14     -2     -12 📝
2023-07-06 08:54:46 +02:00
Aliaksandr Kalenik
ae3a7fd4b8 LibJS: Update bytecode generator to use local variables
- Update ECMAScriptFunctionObject::function_declaration_instantiation
  to initialize local variables
- Introduce GetLocal, SetLocal, TypeofLocal that will be used to
  operate on local variables.
- Update bytecode generator to emit instructions for local variables
2023-07-05 21:03:01 +02:00
Aliaksandr Kalenik
7765ebb5f2 LibJS+LibWeb: Plumb local variables names to ECMAScriptFunctionObject
Saving vector of local variables names in ECMAScriptFunctionObject
will allow to get a name by index in case message of ReferenceError
needs to contain a variable name.
2023-07-05 21:03:01 +02:00
Andreas Kling
e87d84f883 LibJS/Bytecode: Support in binary operator for private fields
11 new passes on test262. :^)
2023-07-05 15:39:25 +02:00
Daniel Bertalan
d165590809 LibJS/Bytecode: Do not coerce the receiver to Object for internal_set
This makes the behavior of `Symbol` correct in strict mode, wherein if
the receiver is a symbol primitive, assigning new properties should
throw a TypeError.
2023-07-02 22:08:48 +01:00
Andreas Kling
c37b204ce1 LibJS/Bytecode: Add Call opcode for fixed-argument-count calls
This avoids the overhead of allocating a new Array on every function
call, saving a substantial amount of time and avoiding GC thrash.

This patch only makes use of Op::Call in CallExpression. There are other
places we should codegen this op. We should also do the same for super
expression calls.

~5% speed-up on Kraken/stanford-crypto-ccm.js
2023-07-02 18:30:02 +02:00
Andreas Kling
7eb87dec9f LibJS/Bytecode: Rename Call and SuperCall to &WithArgumentArray
Forcing every function call to allocate a new Array just to accommodate
spread parameters is not very nice, so let's start moving towards making
this a special case rather than the general (and only) case.
2023-07-02 18:30:02 +02:00
Aliaksandr Kalenik
1550e7c421 LibJS: Stop using execute_ast_node in NewClass instruction
This change replaces usage of `execute_ast_node` to evaluate super
expression in NewClass by generating instructions instead.
2023-06-29 07:14:14 +02:00
Hendiadyoin1
37067cf3ca LibJS: Use the IdentifierTable for NewFunction and NewClass lhs names
This makes them trivially copyable, which is an assumption multiple
optimizations use when rebuilding the instruction stream.

This fixes most optimized crashes in the test262 suite.
2023-06-29 05:32:08 +02:00
Luke Wilde
363bf114c0 LibJS/Bytecode: Implement for await of
Summary:
    Diff Tests:
        +391    +15    +2 💥️    -408 📝
2023-06-27 21:04:22 +02:00
Timothy Flynn
4977000fa0 LibJS: Rename JS::Iterator to JS::IteratorRecord
This is in preparation for an upcoming implementation of the Iterator
Helpers proposal. That proposal will require a JS::Object type named
"Iterator", so this rename is to avoid conflicts.
2023-06-26 10:39:07 +02:00
Andreas Kling
ad15a1e3e2 LibJS/Bytecode: Don't assert on eval() without arguments
3 new passes on test262. :^)
2023-06-25 19:41:53 +02:00
Andreas Kling
ceb5199225 LibJS/Bytecode: Don't clobber accumulator in Put/Delete instructions
The fact that side effects clobbers the accumulator isn't just annoying
inside the instruction handler, but also really counter-intuitive in
the bytecode program itself.

17 new passes on test262. :^)
2023-06-25 19:14:30 +02:00
Andreas Kling
8450948458 LibJS: Make class definition evaluation work in bytecode mode
Instead of assuming that there's an active AST interpreter, this code
now takes VM& everywhere and invokes the appropriate interpreter.

92 new passes on test262. :^)
2023-06-25 18:28:44 +02:00
Andreas Kling
66936a0d61 LibJS/Bytecode: Fix non-string keys not being excluded in rest object
By converting the excluded names to PropertyKey before filtering, we
ensure that non-string keys get excluded as needed.

14 new passes on test262. :^)
2023-06-25 18:02:37 +02:00
Andreas Kling
8873bf5016 LibJS/Bytecode: Use ToString instead of generic add() in ConcatString
This avoids invoking valueOf() on the values, which is observable.

48 new passes on test262. :^)
2023-06-25 11:20:05 +02:00
Andreas Kling
8021048bc9 LibJS/Bytecode: Throw on destructuring object assignment to nullish LHS
24 new passes on test262. :^)
2023-06-25 09:19:53 +02:00
Aliaksandr Kalenik
331f6a9e60 LibJS: Invalidate cached environment coordinate after delete in global
Fixes the bug in interpreter when cached environment coordinate is not
invalidated after `delete` operator usage on global `this`.
2023-06-24 18:33:44 +02:00
Andreas Kling
8a5e71256d LibJS/Bytecode: Add codegen for ImportCall
Also moved most of the AST ImportCall::execute() into a helper so we can
share the code.
2023-06-24 17:13:30 +02:00
Andreas Kling
85a3a1c085 LibJS/Bytecode: Add codegen for "named evaluation if anonymous function"
This gives anonymous functions the name from the LHS they are being
assigned to.

171 new passes on test262. :^)
2023-06-23 16:09:33 +02:00
Andreas Kling
e5c7d8407b LibJS/Bytecode: Support private class fields
This is accomplished with two new instructions:
- GetPrivateById
- PutPrivateById

Looks like 1616 new passes on test262. :^)
2023-06-23 08:53:10 +02:00