remotion-dev/remotion · error

LUT shader link failed

Error message

LUT shader link failed: ${log ?? '(no log)'}

What it means

createProgram() compiles and links the LUT vertex/fragment shaders into a WebGLProgram. When gl.getProgramParameter(program, gl.LINK_STATUS) is false, the GPU driver refused to link the shaders, and this Error is thrown with the driver's info log (or '(no log)' when the driver provides none). The failed program is deleted before throwing to avoid leaking GPU resources.

Solutions

  1. Inspect the info log embedded in the error message to identify which shader/limit the driver rejected
  2. Update GPU drivers and the browser to a current version with full WebGL2 support
  3. Verify the context is WebGL2 (gl instanceof WebGL2RenderingContext); the shaders use GLSL ES 3.0 syntax
  4. Test in another browser (Chrome/Firefox/Safari) to isolate a driver-specific shader translation bug
  5. If it persists on one machine, fall back to software rendering or flag the device as unsupported

Example fix

// before: assuming any WebGL context works
const gl = canvas.getContext('webgl');
// after: require WebGL2 and check shader support up front
const gl = canvas.getContext('webgl2');
if (!gl) throw new Error('WebGL2 required for LUT effects');
Defensive patterns

Strategy: try-catch

Validate before calling

const gl = canvas.getContext('webgl2');
if (!gl) throw new Error('WebGL2 required for the LUT effect');

Try / catch

try {
  state = setupLut({ gl, width, height, lutContent });
} catch (e) {
  if (String(e.message).startsWith('LUT shader link failed')) {
    // log e.message (contains driver info log) and disable the LUT effect
  }
}

Prevention

When it happens

Trigger: Calling <Lut effect> (which calls setupLut -> createProgram) on a browser/GPU whose WebGL2 implementation rejects the built-in LUT shaders; running on a driver with broken shader translation; using a very old browser with incomplete WebGL2/GLSL ES 3.0 support.

Common situations: Older or virtualized GPU drivers (VMs, remote desktops, software renderers like SwiftShader misconfigurations) fail to translate the shaders; browser bugs in specific GPU/driver combinations; headless rendering environments with missing GPU support.

Related errors


AI-assisted analysis of remotion-dev/remotion@46a3a6bf13 (2026-09-18). Data as JSON: /api/errors/b3bb334966ccbed5. Report an issue: GitHub.

Appendix: source

Thrown at packages/effects/src/lut/lut-runtime.ts:66

		gl,
		gl.FRAGMENT_SHADER,
		LUT_FRAGMENT_SHADER,
	);
	const program = gl.createProgram();
	if (!program) {
		throw new Error('Failed to create LUT shader program');
	}

	gl.attachShader(program, vertexShader);
	gl.attachShader(program, fragmentShader);
	gl.linkProgram(program);
	gl.deleteShader(vertexShader);
	gl.deleteShader(fragmentShader);

	if (!gl.getProgramParameter(program, gl.LINK_STATUS)) {
		const log = gl.getProgramInfoLog(program);
		gl.deleteProgram(program);
		throw new Error(`LUT shader link failed: ${log ?? '(no log)'}`);
	}

	return program;
};

const createSourceTexture = (gl: WebGL2RenderingContext): WebGLTexture => {
	const texture = gl.createTexture();
	if (!texture) {
		throw new Error('Failed to create LUT source texture');
	}

	gl.bindTexture(gl.TEXTURE_2D, texture);
	gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
	gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR);
	gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
	gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
	gl.bindTexture(gl.TEXTURE_2D, null);
	return texture;

View on GitHub (pinned to 46a3a6bf13)