Skip to content

Commit 7ebc18f

Browse files
aduh95targos
authored andcommitted
lib: make safe primordials safe to iterate
PR-URL: #36391 Backport-PR-URL: #38703 Reviewed-By: Michaël Zasso <targos@protonmail.com> Reviewed-By: James M Snell <jasnell@gmail.com>
1 parent 8a60ae2 commit 7ebc18f

4 files changed

Lines changed: 55 additions & 18 deletions

File tree

‎lib/internal/per_context/primordials.js‎

Lines changed: 44 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -91,9 +91,52 @@ function copyPrototype(src, dest, prefix) {
9191
}
9292
}
9393

94+
constcreateSafeIterator=(factory,next)=>{
95+
classSafeIterator{
96+
constructor(iterable){
97+
this._iterator=factory(iterable);
98+
}
99+
next(){
100+
returnnext(this._iterator);
101+
}
102+
[Symbol.iterator](){
103+
returnthis;
104+
}
105+
}
106+
Object.setPrototypeOf(SafeIterator.prototype,null);
107+
Object.freeze(SafeIterator.prototype);
108+
Object.freeze(SafeIterator);
109+
returnSafeIterator;
110+
};
111+
94112
functionmakeSafe(unsafe,safe){
95-
copyProps(unsafe.prototype,safe.prototype);
113+
if(Symbol.iteratorinunsafe.prototype){
114+
constdummy=newunsafe();
115+
letnext;// We can reuse the same `next` method.
116+
117+
for(constkeyofReflect.ownKeys(unsafe.prototype)){
118+
if(!Reflect.getOwnPropertyDescriptor(safe.prototype,key)){
119+
constdesc=Reflect.getOwnPropertyDescriptor(unsafe.prototype,key);
120+
if(
121+
typeofdesc.value==='function'&&
122+
desc.value.length===0&&
123+
Symbol.iteratorin(desc.value.call(dummy)??{})
124+
){
125+
constcreateIterator=uncurryThis(desc.value);
126+
if(next==null)next=uncurryThis(createIterator(dummy).next);
127+
constSafeIterator=createSafeIterator(createIterator,next);
128+
desc.value=function(){
129+
returnnewSafeIterator(this);
130+
};
131+
}
132+
Reflect.defineProperty(safe.prototype,key,desc);
133+
}
134+
}
135+
}else{
136+
copyProps(unsafe.prototype,safe.prototype);
137+
}
96138
copyProps(unsafe,safe);
139+
97140
Object.setPrototypeOf(safe.prototype,null);
98141
Object.freeze(safe.prototype);
99142
Object.freeze(safe);

‎lib/internal/source_map/source_map_cache.js‎

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -7,17 +7,12 @@ const {
77
ObjectKeys,
88
ObjectGetOwnPropertyDescriptor,
99
ObjectPrototypeHasOwnProperty,
10-
Map,
11-
MapPrototypeEntries,
1210
RegExpPrototypeTest,
1311
SafeMap,
1412
StringPrototypeMatch,
1513
StringPrototypeSplit,
16-
uncurryThis,
1714
}=primordials;
1815

19-
constMapIteratorNext=uncurryThis(MapPrototypeEntries(newMap()).next);
20-
2116
functionObjectGetValueSafe(obj,key){
2217
constdesc=ObjectGetOwnPropertyDescriptor(obj,key);
2318
returnObjectPrototypeHasOwnProperty(desc,'value') ? desc.value : undefined;
@@ -195,11 +190,7 @@ function rekeySourceMap(cjsModuleInstance, newInstance) {
195190
functionsourceMapCacheToObject(){
196191
constobj=ObjectCreate(null);
197192

198-
constit=MapPrototypeEntries(esmSourceMapCache);
199-
letentry;
200-
while(!(entry=MapIteratorNext(it)).done){
201-
constk=entry.value[0];
202-
constv=entry.value[1];
193+
for(const{0: k,1: v}ofesmSourceMapCache){
203194
obj[k]=v;
204195
}
205196

‎lib/internal/worker/io.js‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
'use strict';
22

33
const{
4+
ArrayPrototypeForEach,
45
ArrayPrototypeMap,
56
ArrayPrototypePush,
67
FunctionPrototypeCall,
@@ -259,8 +260,7 @@ class WritableWorkerStdio extends Writable {
259260
[kStdioWantsMoreDataCallback](){
260261
constcbs=this[kWritableCallbacks];
261262
this[kWritableCallbacks]=[];
262-
for(constcbofcbs)
263-
cb();
263+
ArrayPrototypeForEach(cbs,(cb)=>cb());
264264
if((this[kPort][kWaitingStreams]-=cbs.length)===0)
265265
this[kPort].unref();
266266
}

‎test/parallel/test-worker-terminate-source-map.js‎

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -27,16 +27,19 @@ const { callCount } = workerData;
2727
functionincreaseCallCount(){callCount[0]++;}
2828

2929
// Increase the call count when a forbidden method is called.
30-
Object.getPrototypeOf((newMap()).entries()).next=increaseCallCount;
31-
Map.prototype.entries=increaseCallCount;
32-
Object.keys=increaseCallCount;
33-
Object.create=increaseCallCount;
34-
Object.hasOwnProperty=increaseCallCount;
3530
for(constpropertyof['_cache','lineLengths','url']){
3631
Object.defineProperty(Object.prototype,property,{
3732
get: increaseCallCount,
3833
set: increaseCallCount
3934
});
4035
}
36+
Object.getPrototypeOf([][Symbol.iterator]()).next=increaseCallCount;
37+
Object.getPrototypeOf((newMap()).entries()).next=increaseCallCount;
38+
Array.prototype[Symbol.iterator]=increaseCallCount;
39+
Map.prototype[Symbol.iterator]=increaseCallCount;
40+
Map.prototype.entries=increaseCallCount;
41+
Object.keys=increaseCallCount;
42+
Object.create=increaseCallCount;
43+
Object.hasOwnProperty=increaseCallCount;
4144

4245
parentPort.postMessage('done');

0 commit comments

Comments
 (0)