From aa7a4e1d06c5f424b71cb0ce9bef197dc2a0d75b Mon Sep 17 00:00:00 2001 From: kkapsner Date: Thu, 19 Sep 2019 00:47:52 +0200 Subject: [PATCH] Added protection for getParameter (webGL) Fixes #329 --- _locales/de/messages.json | 32 ++++++++ _locales/en/messages.json | 33 ++++++++ lib/modifiedCanvasAPI.js | 157 +++++++++++++++++++++++++++++++++++++ lib/settingDefinitions.js | 18 ++++- options/settingsDisplay.js | 32 ++++++++ releaseNotes.txt | 1 + versions/updates.json | 4 + 7 files changed, 276 insertions(+), 1 deletion(-) diff --git a/_locales/de/messages.json b/_locales/de/messages.json index 3592ece..bce8160 100644 --- a/_locales/de/messages.json +++ b/_locales/de/messages.json @@ -551,6 +551,38 @@ "message": "Aktiviert das Vortäuschen des Alpha-Kanals (Transparenz).", "description": "" }, + "webGLVendor_title": { + "message": "Verwendeter webGL \"vendor\"", + "description": "" + }, + "webGLVendor_description": { + "message": "Dieser Wert wird in der webGL-Funktion \"getParameter\" für \"vendor\" verwendet. Leer lassen, um den Originalwert zu verwenden.", + "description": "" + }, + "webGLRenderer_title": { + "message": "Verwendeter webGL \"renderer\"", + "description": "" + }, + "webGLRenderer_description": { + "message": "Dieser Wert wird in der webGL-Funktion \"getParameter\" für \"renderer\" verwendet. Leer lassen, um den Originalwert zu verwenden.", + "description": "" + }, + "webGLUnmaskedVendor_title": { + "message": "Verwendeter webGL \"unmasked vendor\"", + "description": "" + }, + "webGLUnmaskedVendor_description": { + "message": "Dieser Wert wird in der webGL-Funktion \"getParameter\" für \"unmasked vendor\" verwendet. Leer lassen, um den Originalwert zu verwenden.", + "description": "" + }, + "webGLUnmaskedRenderer_title": { + "message": "Verwendeter webGL \"unmasked renderer\"", + "description": "" + }, + "webGLUnmaskedRenderer_description": { + "message": "Dieser Wert wird in der webGL-Funktion \"getParameter\" für \"unmasked renderer\" verwendet. Leer lassen, um den Originalwert zu verwenden.", + "description": "" + }, "useCanvasCache_title": { "message": "Zwischenspeicher für Canvas verwenden", "description": "" diff --git a/_locales/en/messages.json b/_locales/en/messages.json index eb99e7e..83d9caf 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -581,6 +581,39 @@ "description": "" }, + "webGLVendor_title": { + "message": "Reported webGL vendor", + "description": "" + }, + "webGLVendor_description": { + "message": "Value to be reported in the webGL function \"getParameter\" for the \"vendor\". Leave empty to use the original value.", + "description": "" + }, + "webGLRenderer_title": { + "message": "Reported webGL renderer", + "description": "" + }, + "webGLRenderer_description": { + "message": "Value to be reported in the webGL function \"getParameter\" for the \"renderer\". Leave empty to use the original value.", + "description": "" + }, + "webGLUnmaskedVendor_title": { + "message": "Reported webGL unmasked vendor", + "description": "" + }, + "webGLUnmaskedVendor_description": { + "message": "Value to be reported in the webGL function \"getParameter\" for the \"unmasked vendor\". Leave empty to use the original value.", + "description": "" + }, + "webGLUnmaskedRenderer_title": { + "message": "Reported webGL unmasked renderer", + "description": "" + }, + "webGLUnmaskedRenderer_description": { + "message": "Value to be reported in the webGL function \"getParameter\" for the \"unmasked renderer\". Leave empty to use the original value.", + "description": "" + }, + "useCanvasCache_title": { "message": "Use canvas cache", "description": "" diff --git a/lib/modifiedCanvasAPI.js b/lib/modifiedCanvasAPI.js index f96ea17..8a9e153 100644 --- a/lib/modifiedCanvasAPI.js +++ b/lib/modifiedCanvasAPI.js @@ -511,6 +511,163 @@ }); }; } + }, + getParameter: { + type: "readout", + getStatus: function(obj, status, prefs){ + const protectedPartChecker = getProtectedPartChecker(prefs, status.url); + status = Object.create(status); + status.active = protectedPartChecker(["readout", "input"]); + return status; + }, + object: ["WebGLRenderingContext", "WebGL2RenderingContext"], + fakeGenerator: function(checker){ + function getNumber(originalValue, max, index, window){ + const bitLength = Math.floor(Math.log2(max) + 1); + const rng = randomSupply.getBitRng(bitLength, window); + let value = 0; + for (let i = 0; i < bitLength; i += 1){ + value <<= 1; + value ^= rng(originalValue, index + i); + } + return value; + } + const types = { + decimal: function(originalValue, definition, window){ + const int = Math.floor(originalValue); + if (int !== originalValue){ + const decimal = originalValue - int; + const rng = randomSupply.getRng(1, window); + const newDecimal = decimal * (rng(definition.pname) / 0xFFFFFFFF); + return int + newDecimal; + } + else { + return originalValue; + } + }, + shift: function(originalValue, definition, window){ + const value = getNumber(originalValue, definition.max, definition.pname, window); + return originalValue >>> value; + }, + "-": function(originalValue, definition, window){ + const value = getNumber(originalValue, definition.max, definition.pname, window) * + (definition.factor || 1); + if (value > originalValue){ + return 0; + } + return originalValue - value; + } + }; + const changeDefinition = { + 2928: {name: "DEPTH_RANGE", type: "decimal", isArray: true}, + 3379: {name: "MAX_TEXTURE_SIZE", type: "shift", max: 1}, + 3386: {name: "MAX_VIEWPORT_DIMS", type: "shift", max: 1, isArray: true}, + 32883: {name: "MAX_3D_TEXTURE_SIZE", type: "shift", max: 1}, + 33000: {name: "MAX_ELEMENTS_VERTICES", type: "-", max: 3, factor: 50}, + 33001: {name: "MAX_ELEMENTS_INDICES", type: "-", max: 3, factor: 50}, + 33901: {name: "ALIASED_POINT_SIZE_RANGE", type: "decimal", isArray: true}, + 33902: {name: "ALIASED_LINE_WIDTH_RANGE", type: "decimal", isArray: true}, + 34024: {name: "MAX_RENDERBUFFER_SIZE", type: "shift", max: 1}, + 34045: {name: "MAX_TEXTURE_LOD_BIAS", type: "-", max: 1, factor: 1}, + 34076: {name: "MAX_CUBE_MAP_TEXTURE_SIZE", type: "shift", max: 1}, + 34921: {name: "MAX_VERTEX_ATTRIBS", type: "shift", max: 1}, + 34930: {name: "MAX_TEXTURE_IMAGE_UNITS", type: "shift", max: 1}, + 35071: {name: "MAX_ARRAY_TEXTURE_LAYERS", type: "shift", max: 1}, + 35371: {name: "MAX_VERTEX_UNIFORM_BLOCKS", type: "-", max: 1, factor: 1}, + 35373: {name: "MAX_FRAGMENT_UNIFORM_BLOCKS", type: "-", max: 1, factor: 1}, + 35374: {name: "MAX_COMBINED_UNIFORM_BLOCKS", type: "-", max: 3, factor: 1}, + 35375: {name: "MAX_UNIFORM_BUFFER_BINDINGS", type: "-", max: 3, factor: 1}, + 35376: {name: "MAX_UNIFORM_BLOCK_SIZE", type: "shift", max: 1}, + 35377: {name: "MAX_COMBINED_VERTEX_UNIFORM_COMPONENTS", type: "-", max: 7, factor: 10}, + 35379: {name: "MAX_COMBINED_FRAGMENT_UNIFORM_COMPONENTS", type: "-", max: 7, factor: 10}, + 35657: {name: "MAX_FRAGMENT_UNIFORM_COMPONENTS", type: "shift", max: 1}, + 35658: {name: "MAX_VERTEX_UNIFORM_COMPONENTS", type: "shift", max: 1}, + 35659: {name: "MAX_VARYING_COMPONENTS", type: "shift", max: 1}, + 35660: {name: "MAX_VERTEX_TEXTURE_IMAGE_UNITS", type: "shift", max: 1}, + 35661: {name: "MAX_COMBINED_TEXTURE_IMAGE_UNITS", type: "-", max: 1, factor: 2}, + 35968: {name: "MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS", type: "shift", max: 1}, + 35978: {name: "MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS", type: "shift", max: 1}, + 36203: {name: "MAX_ELEMENT_INDEX", type: "-", max: 15, factor: 1}, + 36347: {name: "MAX_VERTEX_UNIFORM_VECTORS", type: "shift", max: 1}, + 36348: {name: "MAX_VARYING_VECTORS", type: "shift", max: 1}, + 36349: {name: "MAX_FRAGMENT_UNIFORM_VECTORS", type: "shift", max: 1}, + 37154: {name: "MAX_VERTEX_OUTPUT_COMPONENTS", type: "shift", max: 1}, + 37157: {name: "MAX_FRAGMENT_INPUT_COMPONENTS", type: "shift", max: 1}, + 7936: {name: "VENDOR", fake: function(originalValue, window, prefs){ + const settingValue = prefs("webGLVendor") || originalValue; + return {value: settingValue, faked: settingValue === originalValue}; + }}, + 7937: {name: "RENDERER", fake: function(originalValue, window, prefs){ + const settingValue = prefs("webGLRenderer") || originalValue; + return {value: settingValue, faked: settingValue === originalValue}; + }}, + 37445: {name: "UNMASKED_VENDOR_WEBGL", fake: function(originalValue, window, prefs){ + const settingValue = prefs("webGLUnmaskedVendor") || originalValue; + return {value: settingValue, faked: settingValue === originalValue}; + }}, + 37446: {name: "UNMASKED_RENDERER_WEBGL", fake: function(originalValue, window, prefs){ + const settingValue = prefs("webGLUnmaskedRenderer") || originalValue; + return {value: settingValue, faked: settingValue === originalValue}; + }} + }; + const parameterNames = Object.keys(changeDefinition); + parameterNames.forEach(function(parameterName){ + const definition = changeDefinition[parameterName]; + definition.pname = parameterName; + if (!definition.fake){ + definition.fake = definition.isArray? + function fake(originalValue, window){ + let faked = false; + let fakedValue = []; + for (var i = 0; i < originalValue.length; i += 1){ + fakedValue[i] = types[this.type](originalValue[i], this, window); + faked |= originalValue[i] === fakedValue[i]; + originalValue[i] = fakedValue[i]; + } + this.fake = function(originalValue){ + if (faked){ + for (var i = 0; i < originalValue.length; i += 1){ + originalValue[i] = fakedValue[i]; + } + } + return { + value: originalValue, + faked + }; + }; + return { + value: originalValue, + faked + }; + }: + function fake(originalValue, window){ + let value = types[this.type](originalValue, this, window); + let faked = value === originalValue; + this.fake = function(){ + return {value, faked}; + }; + return {value, faked}; + }; + } + }); + return function getParameter(pname){ + return checkerWrapper(checker, this, arguments, function(args, check){ + var {prefs, notify, window, original} = check; + const originalValue = original.apply(this, window.Array.from(args)); + if (changeDefinition[pname]){ + const definition = changeDefinition[pname]; + const {value, faked} = definition.fake(originalValue, window, prefs); + if (faked){ + notify("fakedReadout"); + } + return value; + } + else { + return originalValue; + } + }); + }; + } } }; Object.keys(scope.changedFunctions).forEach(function(key){ diff --git a/lib/settingDefinitions.js b/lib/settingDefinitions.js index a0c3f44..519a0ae 100644 --- a/lib/settingDefinitions.js +++ b/lib/settingDefinitions.js @@ -98,7 +98,7 @@ {message: "input", level: 2}, "fillText", "strokeText", {name: "webGL", level: 2}, - "readPixels", + "readPixels", "getParameter", {name: "Audio-API", level: 1}, "getFloatFrequencyData", "getByteFrequencyData", "getFloatTimeDomainData", "getByteTimeDomainData", "getChannelData", "copyFromChannel", @@ -148,6 +148,22 @@ name: "fakeAlphaChannel", defaultValue: false }, + { + name: "webGLVendor", + defaultValue: "" + }, + { + name: "webGLRenderer", + defaultValue: "" + }, + { + name: "webGLUnmaskedVendor", + defaultValue: "" + }, + { + name: "webGLUnmaskedRenderer", + defaultValue: "" + }, { name: "persistentRndStorage", defaultValue: "" diff --git a/options/settingsDisplay.js b/options/settingsDisplay.js index c70d5d9..d388332 100644 --- a/options/settingsDisplay.js +++ b/options/settingsDisplay.js @@ -403,6 +403,38 @@ } ] }, + { + "name": "webGLVendor", + "displayDependencies": [ + { + "displayAdvancedSettings": [true] + } + ] + }, + { + "name": "webGLRenderer", + "displayDependencies": [ + { + "displayAdvancedSettings": [true] + } + ] + }, + { + "name": "webGLUnmaskedVendor", + "displayDependencies": [ + { + "displayAdvancedSettings": [true] + } + ] + }, + { + "name": "webGLUnmaskedRenderer", + "displayDependencies": [ + { + "displayAdvancedSettings": [true] + } + ] + }, ] }, { diff --git a/releaseNotes.txt b/releaseNotes.txt index 2bad36e..337650f 100644 --- a/releaseNotes.txt +++ b/releaseNotes.txt @@ -4,6 +4,7 @@ Version 0.5.14: new features: - remove iframe protection from whitelisted pages + - added protection for getParameter (webGL) fixes: - improved option pages on mobile diff --git a/versions/updates.json b/versions/updates.json index 6f7408a..1d9d406 100644 --- a/versions/updates.json +++ b/versions/updates.json @@ -69,6 +69,10 @@ { "version": "0.5.14Alpha20190912", "update_link": "https://canvasblocker.kkapsner.de/versions/canvasblocker_beta-0.5.14Alpha20190912-an+fx.xpi" + }, + { + "version": "0.5.14Alpha20190918", + "update_link": "https://canvasblocker.kkapsner.de/versions/canvasblocker_beta-0.5.14Alpha20190918-an+fx.xpi" } ] }