mirror of
https://github.com/heygen-com/hyperframes.git
synced 2026-09-03 12:54:29 +00:00
perf(distributed): skip eager probe session when chunkWorkerCount > 1 (#916)
This commit is contained in:
@@ -165,6 +165,8 @@ export {
|
||||
BROWSER_GPU_NOT_SOFTWARE,
|
||||
} from "./utils/assertSwiftShader.js";
|
||||
|
||||
export { readWebGlVendorInfoFromCanvas } from "./utils/readWebGlVendorInfoFromCanvas.js";
|
||||
|
||||
export {
|
||||
extractMediaMetadata,
|
||||
extractVideoMetadata,
|
||||
|
||||
@@ -23,6 +23,8 @@ import {
|
||||
type BeforeCaptureHook,
|
||||
} from "./frameCapture.js";
|
||||
import { DEFAULT_CONFIG, type EngineConfig } from "../config.js";
|
||||
import { assertSwiftShader } from "../utils/assertSwiftShader.js";
|
||||
import { readWebGlVendorInfoFromCanvas } from "../utils/readWebGlVendorInfoFromCanvas.js";
|
||||
|
||||
export interface WorkerTask {
|
||||
workerId: number;
|
||||
@@ -205,6 +207,19 @@ async function executeWorkerTask(
|
||||
createBeforeCaptureHook(),
|
||||
config,
|
||||
);
|
||||
// Per-worker SwiftShader assertion: when the caller declares
|
||||
// `browserGpuMode: "software"`, every worker session must verify Chrome's
|
||||
// WebGL backend is actually SwiftShader before the first frame. Hosts
|
||||
// that fall back to a hardware GL backend (or silently fail to load
|
||||
// SwiftShader) would otherwise produce non-deterministic pixels and
|
||||
// break the distributed byte-identical-retry contract — the parallel
|
||||
// branch wouldn't catch it via the pre-warmup probe (renderChunk now
|
||||
// skips that when chunkWorkerCount > 1). The canvas-based reader works
|
||||
// on both regular Chrome and chrome-headless-shell (which serves
|
||||
// `chrome://gpu` as an empty document).
|
||||
if (config?.browserGpuMode === "software") {
|
||||
await assertSwiftShader(session.page, readWebGlVendorInfoFromCanvas);
|
||||
}
|
||||
await initializeSession(session);
|
||||
|
||||
const outputOffset = task.outputFrameOffset ?? 0;
|
||||
|
||||
@@ -0,0 +1,52 @@
|
||||
/**
|
||||
* Read SwiftShader vendor/renderer via a 1×1 WebGL canvas + the
|
||||
* `WEBGL_debug_renderer_info` extension. Used as the `readInfo` override
|
||||
* for {@link assertSwiftShader} when the worker is running on
|
||||
* `chrome-headless-shell` — that build serves `chrome://gpu` as an empty
|
||||
* document so the default `chrome://gpu`-based info reader trips
|
||||
* `net::ERR_FAILED` even when the GL backend is in fact SwiftShader.
|
||||
*
|
||||
* The canvas-based probe runs against whatever page the caller hands in
|
||||
* (we use a fresh `about:blank` so it doesn't depend on the composition
|
||||
* URL being navigated yet). The renderer string returned matches the
|
||||
* format `assertSwiftShader` expects (substring match against
|
||||
* `"swiftshader"`).
|
||||
*/
|
||||
|
||||
import type { Page } from "puppeteer-core";
|
||||
|
||||
export async function readWebGlVendorInfoFromCanvas(
|
||||
page: Page,
|
||||
): Promise<{ vendor: string; renderer: string }> {
|
||||
await page.goto("about:blank", { waitUntil: "domcontentloaded", timeout: 30_000 });
|
||||
return page.evaluate((): { vendor: string; renderer: string } => {
|
||||
try {
|
||||
const canvas = document.createElement("canvas");
|
||||
const gl =
|
||||
(canvas.getContext("webgl") as WebGLRenderingContext | null) ??
|
||||
(canvas.getContext("experimental-webgl") as WebGLRenderingContext | null);
|
||||
if (!gl) {
|
||||
return { vendor: "", renderer: "" };
|
||||
}
|
||||
const ext = gl.getExtension("WEBGL_debug_renderer_info") as {
|
||||
UNMASKED_VENDOR_WEBGL: number;
|
||||
UNMASKED_RENDERER_WEBGL: number;
|
||||
} | null;
|
||||
if (!ext) {
|
||||
return {
|
||||
vendor: String(gl.getParameter(gl.VENDOR) ?? ""),
|
||||
renderer: String(gl.getParameter(gl.RENDERER) ?? ""),
|
||||
};
|
||||
}
|
||||
// Older Chrome builds expose the unmasked strings under the literal
|
||||
// numeric constants 0x9245 / 0x9246. The extension surface above is
|
||||
// identical across builds — read through it.
|
||||
return {
|
||||
vendor: String(gl.getParameter(ext.UNMASKED_VENDOR_WEBGL) ?? ""),
|
||||
renderer: String(gl.getParameter(ext.UNMASKED_RENDERER_WEBGL) ?? ""),
|
||||
};
|
||||
} catch {
|
||||
return { vendor: "", renderer: "" };
|
||||
}
|
||||
});
|
||||
}
|
||||
Reference in New Issue
Block a user