06:19
<snek>
yeah I've been wondering about ways to defang Function.prototype.constructor for a while
06:19
<snek>
would be neat if references in js engines could be poisoned somehow
06:23
<snek>
maybe being able to see whether a call to Function is "direct", like with eval, could be beneficial
15:17
<Jan Olaf Martin>
Trusted types could be some part of the answer but obviously as opt-in as CSPs or the all-or-nothing flag in nodejs to disallow string eval.
15:22
<Ashley Claymore>
maybe not a common use case, but if code is only using the Function constructor to feature check syntax - that only requires the constructor - and doesn't need to call the actual function AFAIK
15:23
<Ashley Claymore>
as a slightly less restrictive form of dissalow-eval that still prevents these exploits
15:33
<bakkot>
https://github.com/tc39/proposal-symbol-proto did discuss defanging Function.prototype.constructor as well
15:34
<bakkot>
though I don't think its ideas are actually workable as written
15:35
<bakkot>
I do kind of enjoy the idea of saying that you can only access Function.prototype.constructor by literal fn.constructor syntax, not fn['constructor'], even though that would be a crazy violation of the language invariants
15:46
<Ashley Claymore>
we can just say that it's kinda like { __proto__: null } and {["__proto__"]: null } being different and runway
18:26
<Mathieu Hofman>
yeah I've been wondering about ways to defang Function.prototype.constructor for a while
Does any legit code actually rely on Function.prototype.constructor being functional, or even matching Function? Why can't we just change it with something that doesn't evaluate? Possibly opt-in
18:27
<Mathieu Hofman>
we can just say that it's kinda like { __proto__: null } and {["__proto__"]: null } being different and runway
I think there's a difference between declaration and reference access. On the access side, only
eval behaves strangely.
18:31
<Michael Ficarra>
make it a function that's the same as the Function constructor but param lists must be simple and the body is prefixed with return?
18:55
<kriskowal>
In HardenedJS, we replace Function.prototype.constructor with an exception thrower. Users of HardenedJS do sometimes run into libraries that are not ecosystem compatible, but I don’t recall any cases where this was a relevant hindrance. It doesn’t break instanceof. Nobody seems to legitimately depend on (() => {}).constructor(code) to do what is much more easily accomplished with Function(code).
19:16
<bakkot>
lots of stuff depends on it matching; being functional is much rarer https://github.com/search?q=%28lang%3Ajs+OR+lang%3Ats%29+%22.constructor+%3D%3D%3D+Function%22&type=code
19:19
<bakkot>
has there been a proposal for like a parses(src: string): boolean method people could use instead of checking if calling Function throws?
19:19
<bakkot>
so that people could use it in no-eval contexts
19:19
<bakkot>
I guess ideally a parses(src: string, asModule: boolean)
21:54
<Ashley Claymore>
what I was suggesting was relaxing no-eval to throw when the code is actually evaluated - rather than when the function is constructed.
assuming the goal was to support existing code.
22:15
<bakkot>
Richard Gibson: re https://github.com/tc39/ecma262/pull/3087 Chrome used to have a flag for setting timezone but apparently no longer does https://issues.chromium.org/issues/341232991 (also I don't know if actually allowed sub-minute offsets; it might have just been named timezones)