Commit Graph
8613 Commits
Author SHA1 Message Date
Karl Seguin ff339f0342 chore: link to our daily wpt results 2026-08-13 20:04:35 +08:00
Karl Seguin fec340f079 Merge pull request #3184 from staylor/fix/mutation-termination-teardown
stability: clear V8 terminating state after a terminated microtask checkpoint
2026-08-13 14:51:32 +08:00
Karl Seguin 9c1998076c stability: cancel a termination only at a safe point
Cancel termination only when all context have a call_depth == 0. This ensures
that termination "sticks" all the way up a nested call. Without this, a nested
call could clear a terminate which targeted something up the stack.
2026-08-13 14:07:32 +08:00
Karl Seguin b7868c455b Merge pull request #3181 from lightpanda-io/getHTML
webapi: Element/ShadowRoot getHTML
2026-08-13 06:40:45 +08:00
Karl Seguin 85608c1051 Merge pull request #3180 from lightpanda-io/shadowdom-relocation
webapi: Track node relocation across shadow roots
2026-08-13 06:40:02 +08:00
Scott Taylor d0c145b0c9 Clear V8 terminating state after a terminated microtask checkpoint
A JS entry (JSEntry) clears V8's terminating state when the termination
exception unwinds past it, which is what tryCall and friends rely on.
A microtask checkpoint does not: when a requested termination (watchdog,
CDP-disconnect kill) lands inside a checkpoint-delivered callback such
as MutationObserver delivery, PerformCheckpoint returns with
IsExecutionTerminating still set and nothing ever clears it. Every
later V8 call in that isolate then runs against a terminating isolate
and can return empty where callers don't expect it, ending in SIGSEGV
during connection teardown.

Cancel the V8-level termination after a checkpoint in which a terminate
landed, keeping the sticky terminate_requested so the existing entry
gates keep refusing new JS, and skip the remaining context queues.

Production-observed sequence this covers (SIGSEGV/139 tails):
  watchdog stall -> MutObserver.deliverRecords err=ExecutionTerminated
  -> frame.deliverMutations -> closing connection (pending terminate)
  -> SIGSEGV

Assisted-By: devx/95b8cb7f-8baf-4a28-93bf-61bc21612890
2026-08-12 12:49:42 -04:00
Karl Seguin e443922788 webapi: Element/ShadowRoot getHTML
Adds the getHTML methods to Element and ShadowRoot. This is expected to add
another ~6K passing WPT tests (significantly improving out score in the
/shadow-dom/ category). It's also probably also a useful API to implement.
2026-08-12 17:23:20 +08:00
Karl Seguin 59be69b1f8 webapi: Track node relocation across shadow roots
All add/remove node operations come down to Frame.removeNode and
Frame._insertNodeRelative. But not all remove/insert are the same, e.g. removing
a disconnect node is different than removing a connected node. Also, a "move"
operation is a remove+insert, but some move operations appear more atomic than
others. There is both a correctness and an optimization side to these
differences.

Previously, removeNode took a will_be_reconnected: bool option and insert took
a child_already_connected: bool. Essentially, remove wants to know the
post-removal intention, and insert wants to know the pre-insert state.

The simple booleans work for simple cases, but fail for ShadowDOM: it isn't
enough to know if `will_be_reconnected`...we need to know in what root it'll
be reconnected. Both remove and insert become tristate:

1 - is staying in the same root
2 - is staying connected, but in a different root
3 - is becoming connected for the first time

This commits changes `will_be_reconnected: bool` to `reconnect_to: ?*Node` and
`child_already_connected: bool` to `previous_root: ?*Node`. So most callsites
had to be updated - which is why so many files were touched. But the bulk of
the change is in those two Frame method which must now handle the tristate.
2026-08-12 16:03:26 +08:00
Karl Seguin 23bba947da Merge pull request #3169 from lightpanda-io/eventtarget-bare-tag
mem: Swith EventTarget's _type to a bare tag
2026-08-12 09:48:16 +08:00
Karl Seguin a7d94c18b3 Merge pull request #3175 from staylor/fix/playwright-redirect-chain
Fix Playwright redirect routing chains
2026-08-12 09:22:10 +08:00
Karl Seguin bbf2493695 zig fmt 2026-08-12 08:01:17 +08:00
Karl Seguin 0f6ea46b2e mem: Swith EventTarget's _type to a bare tag
Same change as https://github.com/lightpanda-io/browser/pull/3128 but for
EventTarget. This shrinks all EventTargets (i.e. most WebAPI interfaces) by 8
bytes.
2026-08-12 08:01:12 +08:00
Karl Seguin efc7613768 Merge pull request #3172 from lightpanda-io/js_mem_gauge
metrics: Add js memory gauge
2026-08-12 07:46:21 +08:00
Scott Taylor ba01f0a963 cdp: scope redirect response to redirect events
Assisted-By: devx/c10f9997-2afd-4688-a7fa-f3839c4cc22e
2026-08-11 14:24:57 -04:00
Scott Taylor ff975b106f cdp: report redirect chains before interception
Assisted-By: devx/c10f9997-2afd-4688-a7fa-f3839c4cc22e
2026-08-11 14:15:09 -04:00
Karl Seguin 99bfc2fdeb Merge pull request #3167 from lightpanda-io/self-hosted
dev: add -Ddev_fast flag
2026-08-11 20:47:43 +08:00
Karl Seguin fff4b4b44d Merge pull request #3171 from lightpanda-io/nikneym/webkit-matches-selector
`Element`: alias `matches` with `webkitMatchesSelector`
2026-08-11 20:38:07 +08:00
Karl Seguin 5b3de8a400 Merge pull request #3168 from lightpanda-io/shadowroot-events
webapi: improve events from shadowroot
2026-08-11 20:34:03 +08:00
Karl Seguin 6dba13b218 metrics: Add js memory gauge
Unlike the histogram, which is only captured on page teardown, this attempts to
capture the live memory (at a few selected known points, e.g. "load").
2026-08-11 20:30:45 +08:00
Halil Durak 4d8c0f6d92 update tests 2026-08-11 14:46:48 +03:00
Halil Durak 4b70b9523a Element: alias matches with webkitMatchesSelector 2026-08-11 14:46:17 +03:00
Karl Seguin e1794b4768 webapi: improve events from shadowroot
Correctly encapsulate events that happen within a shadowroot to stop from
leaking out. This involves calculating the related_target relative to the
potential node receiving the event.

Also Event.composedPath now re-uses the same path-building logic as EventManager
(previously, the same-ish algo in both places, that were out of sync).

Some smaller changes:
- input.list getter (showed up in the shadow dom wpt tests)
- activeElement getter added to ShadowDOM
- document activeElement is ShadowDOM-aware and won't cross
2026-08-11 14:12:49 +08:00
Karl Seguin 5d2910034c update v8 dep 2026-08-11 09:54:33 +08:00
Karl Seguin 77ef54f0ac dev: add -Ddev_fast flag
Only works in Debug mode. Only works on x86_64 Linux.

sets use_llvm = false and forces glibc 2.43 (1), causes v8 to be dynamically
linked (https://github.com/lightpanda-io/zig-v8-fork/pull/197).

For me, zig build -Ddev_fast is about 6x faster (~60 seconds -> ~10 seconds)

(1) https://codeberg.org/ziglang/zig/issues/31272
2026-08-11 09:39:45 +08:00
Karl Seguin 6312d43d97 Merge pull request #3164 from lightpanda-io/report-ignore-url
mask url fields from crash report
2026-08-10 16:34:31 +08:00
Karl Seguin 859b5e4efe Merge pull request #3165 from lightpanda-io/test-tcp-nodelay
chore: speed up unit tests on linux
2026-08-10 16:34:15 +08:00
Karl Seguin 73de272755 chore: speed up unit tests on linux 2026-08-10 15:51:58 +08:00
Pierre Tachoire ec16da49e3 mask url fields from crash report 2026-08-10 09:30:55 +02:00
Karl Seguin 9eba476615 Merge pull request #3157 from lightpanda-io/http-cache-limit
Entry Limit for HTTP Cache
2026-08-10 13:14:30 +08:00
Karl Seguin 8691568f33 Merge pull request #3160 from lightpanda-io/cdp-idle-notifications
runner: advance idle notifications outside the wait-condition loop
2026-08-08 11:11:36 +08:00
Karl Seguin 94bcaf801f Merge pull request #3162 from lightpanda-io/iframe-srcdoc
webapi: add support for iframe srcdoc
2026-08-08 10:40:38 +08:00
Karl Seguin cfb2fc5e9c webapi: add support for iframe srcdoc
Came up in a handful of referrer-policy WPT tests.
2026-08-08 08:18:18 +08:00
Karl Seguin 4a157eea0f Merge pull request #3161 from lightpanda-io/referrer-policy-redirect
http: recalculate Referer header on each redirect
2026-08-08 08:15:18 +08:00
Karl Seguin 17c8df5aa5 Merge pull request #3159 from lightpanda-io/custom-element-errors
webapi: Report CustomElement errors via window.reportError
2026-08-08 08:15:06 +08:00
Karl Seguin 5c1c2a1b8b Merge pull request #3150 from lightpanda-io/cdp-post-data
cdp: add request post data
2026-08-08 08:14:52 +08:00
Muki Kiboigo 32364a26da use proper default on http_cache_entry_limit option 2026-08-07 08:01:55 -07:00
Muki Kiboigo f80aa2882c use a better query for evictOverflow 2026-08-07 08:01:54 -07:00
Karl Seguin abc6f1ef76 http: recalculate Referer header on each redirect
On a redirect, recalculate the Referer header based on the new target.

Also, allow SVG anchors to be clicked (doesn't seem related, but it came up
in referrer-policy WPT tests).
2026-08-07 16:19:41 +08:00
Adrià Arrufat bf02e41919 runner: advance idle notifications outside the wait-condition loop
checkIdleNotifications was only called for conditions still pending, but
an idle notification needs a check 500ms+ after the condition first held
(Frame.IdleNotification). On a quiet page the same tick both starts that
hold and resolves the condition via is_done, so nothing advanced the
state machine for the rest of the wait. The CDP pump waits in 1s slices
(CDP.pageWait), so Page.lifecycleEvent networkIdle/networkAlmostIdle was
starved until a later slice built a fresh condition.

That event is what puppeteer's networkidle0/networkidle2 and
playwright's networkidle block on. Measured with puppeteer against
lightpanda serve, goto(waitUntil: networkidle0) on example.com, median
of 5: 2001ms before, 595ms after (the page loads in ~100ms, so ~600ms is
the floor: load plus the 500ms hold). Every pre-fix run landed within
1999-2195ms - the stall is quantized to whole pump slices, not network
variance. An ad-heavy page is unaffected either way (3196ms vs 2859ms,
overlapping ranges): pending timers keep is_done false, so its condition
never resolved early to begin with.

Non-CDP waits are deliberately unchanged: waitForFrame(.networkidle) on
a quiet page still resolves immediately via is_done rather than serving
the 500ms hold. Agent/MCP waitForState and fetch --wait-until networkidle
want "settled now", not chrome's lifecycle heuristic.
2026-08-07 08:46:06 +02:00
Adrià Arrufat b04c99a911 Merge pull request #3154 from lightpanda-io/tools-backendnodeid-zero
tools: treat backendNodeId 0 as omitted, add recovery hints to errors
2026-08-07 07:36:08 +02:00
Karl Seguin 281a773cad Merge pull request #3090 from lightpanda-io/nikneym/connection-upgrade
Rework `Connection.upgrade` with `header_parser`
2026-08-07 12:23:58 +08:00
Karl Seguin d35aa90959 fix build 2026-08-07 12:00:05 +08:00
Karl Seguin 63a4283989 reset arena after use, verify user input 2026-08-07 11:45:50 +08:00
Karl Seguin 9a35a8b0b1 Merge pull request #3152 from lightpanda-io/fetch-default-load
fetch: default --wait-until to load
2026-08-07 08:43:44 +08:00
Karl Seguin 2e13262622 Merge pull request #3153 from lightpanda-io/fetch-exit-code
main: propagate worker-thread failures to the exit code
2026-08-07 08:37:09 +08:00
Karl Seguin 7107d0e132 webapi: Report CustomElement errors via window.reportError
Per spec, CustomElement creation/upgrade errors should be reported to the window

This also adds more (mostly edge case) validation, such as an element that fails
to be upgraded can never be upgraded again.
2026-08-07 07:37:09 +08:00
Karl Seguin 117f19b3c3 Merge pull request #3148 from lightpanda-io/leaf-node-proto-removal
mem: remove _proto field from leaf nodes
2026-08-07 07:15:39 +08:00
Karl Seguin df084b2cab Merge pull request #3146 from lightpanda-io/style-width-children-aware
render: CSS width/height are now children-content aware
2026-08-07 07:15:23 +08:00
Karl Seguin deb4eb3eef Merge pull request #3155 from lightpanda-io/zenai-bump
build: update zenai dependency
2026-08-07 07:14:57 +08:00
Muki Kiboigo 4f5bcec9a6 add max entry limiting to SqliteCache 2026-08-06 13:29:22 -07:00