Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(runtime): implement __proto__ getter, ignore and warn on setter #16775

Open
wants to merge 8 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions cli/tests/run_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1447,6 +1447,11 @@ mod run {
// output: "run/single_compile_with_reload.ts.out",
// });

itest!(proto_accessor {
args: "run run/proto_accessor.js",
output: "run/proto_accessor.js.out",
});

itest!(proto_exploit {
args: "run run/proto_exploit.js",
output: "run/proto_exploit.js.out",
Expand Down
5 changes: 5 additions & 0 deletions cli/tests/testdata/run/proto_accessor.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
class Test {}
const test = new Test();
Object.setPrototypeOf(test, { test: "test" });
console.log("Object.getPrototypeOf: ", Object.getPrototypeOf(test));
console.log("__proto__: ", test.__proto__);
2 changes: 2 additions & 0 deletions cli/tests/testdata/run/proto_accessor.js.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Object.getPrototypeOf: { test: "test" }
__proto__: { test: "test" }
2 changes: 2 additions & 0 deletions cli/tests/testdata/run/proto_exploit.js.out
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
Before: [object Object]
Error: Prototype access via __proto__ attempted; __proto__ is not implemented in Deno due to security reasons. Use Object.setPrototypeOf instead.
[WILDCARD]
After: [object Object]
23 changes: 19 additions & 4 deletions runtime/js/99_main.js
Original file line number Diff line number Diff line change
@@ -1,10 +1,6 @@
// Copyright 2018-2022 the Deno authors. All rights reserved. MIT license.
"use strict";

// Removes the `__proto__` for security reasons.
// https://tc39.es/ecma262/#sec-get-object.prototype.__proto__
delete Object.prototype.__proto__;

// Remove Intl.v8BreakIterator because it is a non-standard API.
delete Intl.v8BreakIterator;

Expand All @@ -25,6 +21,8 @@ delete Intl.v8BreakIterator;
ObjectDefineProperty,
ObjectDefineProperties,
ObjectFreeze,
ObjectGetPrototypeOf,
ObjectPrototype,
ObjectPrototypeIsPrototypeOf,
ObjectSetPrototypeOf,
PromiseResolve,
Expand Down Expand Up @@ -73,6 +71,23 @@ delete Intl.v8BreakIterator;
setLanguage,
} = window.__bootstrap.globalScope;

// Disables setting `__proto__` and emits a warning instead, for security reasons.
// https://tc39.es/ecma262/#sec-get-object.prototype.__proto__
ObjectDefineProperty(ObjectPrototype, "__proto__", {
configurable: true,
enumerable: false,
get() {
return ObjectGetPrototypeOf(this);
},
set(_) {
console.warn(
new Error(
"Prototype access via __proto__ attempted; __proto__ is not implemented in Deno due to security reasons. Use Object.setPrototypeOf instead.",
),
);
},
});

let windowIsClosing = false;

function windowClose() {
Expand Down