This patch adds a fast path to the PutByValue bytecode op that bypasses
a ton of things *if* a set of assumptions hold:
- The property key must be a non-negative Int32
- The base object must not interfere with indexed property access
- The base object must have simple indexed property storage
- The property key must already be present as an own property
- The existing value must not have any accessors defined
If this holds (which it should in many common cases), we can skip all
kinds of checks and poke directly at the property storage, saving time.
16% speed-up on the entire Kraken benchmark :^)
(including: 88% speed-up on Kraken/imaging-desaturate.js)
(including: 55% speed-up on Kraken/audio-fft.js)
(including: 54% speed-up on Kraken/audio-beat-detection.js)
This patch adds a fast path to the GetByValue bytecode op that bypasses
a ton of things *if* a set of assumptions hold:
- The property key must be a non-negative Int32
- The base object must not interfere with indexed property access
- The property key must already be present as an own property
- The existing value must not have any accessors defined
If this holds (which it should in the common case), we can poke directly
at the indexed property storage and save a boatload of time.
10% speed-up on the entire Kraken benchmark :^)
(including: 31% speed-up on Kraken/audio-dft.js)
(including: 23% speed-up on Kraken/stanford-crypto-aes.js)
This function must return true if the object may intercept and customize
access to indexed properties (properties where the property name is a
non-negative integer.)
This will be used to implement fast path optimizations for array-like
accesses in subsequent commits.
The "dependency" lines really belong to the main port entry, it doesn't
make sense logically to represent them separately and handling them
together will also allow easier dependency management later on. This
commit greatly simplifies the port database parsing to facilitate this,
and removes the -d option from the command line. Instead, ports are
listed with their dependencies, if they have any.
The strings will get deduplicated when actually turned into
PrimitiveString objects at runtime anyway, and keeping the string
tables deduplicated was actually wasting a lot of time.
4.4% speed-up on Kraken/stanford-crypto-ccm.js :^)
Color::lightened() and Color::darkened() multiply the color values, so
they don't work for black. So for simplicity, we use a semi-transparent
white or black instead.
The following snippet would cause "i" to be incremented twice(!):
let a = []
let i = 0
a[++i] += 0
This patch solves the issue by remembering the base object and property
name for computed MemberExpression LHS in codegen. We the store the
result of the assignment to the same object and property (instead of
computing the LHS again).
3 new passes on test262. :^)
When the spec says to call "! TrimString", we should use MUST instead
of TRY. (We were previously using TRY in order to propagate OOM errors,
but we don't care about such OOMs anymore.)
Hand-drawn face/court cards for traditional French-suited playing cards.
For each of the four suits (Clubs, Hearts, Diamonds & Spades) there is a
corresponding King, Queen, Jack and a standalone symbol which can be
used for the numeral card patterns, including Ace. There is a special
Ace of Spades card. Also included is a Joker card.
Alter the card dimensions to be 80x110px with a corner radius of 7px.
This is inspired by the dimensions of physical playing cards. It gives
12px of padding between the illustration and the card's border.
Move the card letter and symbol closer to the edge to make space.
Adjust the Club symbol to have the same dimensions as the other symbols.
The program now terminates with an error if the command passed to
`-exec` is not terminated with a semicolon.
This commit also ensures that the argument containing the terminating
semicolon must be 1 byte long. Previously, any argument whose first
byte was a semicolon was treated as a valid terminator.
This behaves identically to the `-exec` option but prompts the user
for confirmation before executing the specified command.
A command is executed if a line beginning with 'y' or 'Y' is entered
by the user. This matches the behavior of `find` on Linux and FreeBSD
when using the POSIX locale.
According to multiboot spec if flag for framebuffer isn't
set then corresponding fields are invalid. In reality they're set
to 0 but let's be defensive.
Loaders try to put modules as low as reasonable but on
EFI often "reasonable" is much higher than on BIOS. As
a result target can be easily higher than source.
Then we have 2 problems:
* memmove compares virtual address and since target
is mapped higher it ends up going backwards which
is wrong if target is physically below source
* order of copying of sections must be inverted if
target is below source
Prekernel code currently assumes that mapping until MAX_KERNEL_SIZE
is enough to make the modules accessible. GRUB tries to load as low
as possible but higher than 1 MiB. Hence this is usually true.
However on EFI some ranges may already be used by boot services and
GRUB tries to avoid them if possible. This pushes modules higher.
The simplest solution is to map entire 4 GiB space.
As an additional benefit it makes the framebuffer accessible that
can be used for the debugging.
About half of the Processor code is common across architectures, so
let's share it with a templated base class. Also, other code that can be
shared in some ways, like FPUState and TrapFrame functions, is adjusted
here. Functions which cannot be shared trivially (without internal
refactoring) are left alone for now.
Previously, we would divide the widget width and height by the tile size
and round up, which did not result in enough tiles to cover the entire
widget. Although this calculation is correct if you starting drawing
tiles in the top left corner, we have an additional offset to account
for.
Now, we take the number of tiles that fit in the widget completely and
pad it with 2 tiles to account for the partial left/right and top/bottom
sides. An additional tile is added to account for the iterator
translating by width / 2, which rounds down again.
The resulting tile rects are always intersected with the widget
dimensions, so even if we're generating more tile coordinates than
strictly necessary, we're not performing the actual download or draw
operations.
The `operator++` of the spiraling tile iterator was repeating the first
coordinates (`0, 0`) instead of moving to the next tile on the first
iteration. Swapping the move and check ensures we get to the end of the
iterator, fixing gray tiles that would sometimes pop up in the lower
right.
Since we never return from `operator++` without setting a valid
position, we can drop `current_x` and `current_y` and just use the
`Gfx::Point<T>` directly.
Since we divide the width and height of the downscaled tiles by 2,
bilinear blending is identical to box sampling and should be preferred
since it's the simpler one of the two algorithms.
Renaming the DeprecatedString version of this function to
deprecated_tag_name. A FlyString is used here as we often need to
perform equality checks here, and the HTMLParser already has tag_name as
a FlyString.
Remove a FIXME while we're at it - we were already following the spec
there, and we still are :^)
Which pretty much needs to be done together due to the amount of places
where they are compared together.
This also involves porting over StackOfOpenElements over to FlyString
from DeprecatedFly string to prevent a gazillion calls to
`.to_deprecated_fly_string` calls in HTMLParser.