Skip to content

Commit 30de1ba

Browse files
committed
druntime can pass the current stack as a range when scannign globals. Make sure we scan it eagerly so we no not miss the trash register's content.
1 parent 3420b53 commit 30de1ba

File tree

1 file changed

+21
-1
lines changed

1 file changed

+21
-1
lines changed

sdlib/d/gc/scanner.d

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,7 @@ public:
7777
auto worker = Worker(&this);
7878

7979
// Scan the roots.
80-
__sd_gc_global_scan(worker.addToWorkList);
80+
__sd_gc_global_scan(worker.processRootRange);
8181

8282
// Now send this thread marking!
8383
worker.runMark();
@@ -261,6 +261,26 @@ public:
261261
}
262262
}
263263

264+
void processRootRange(const(void*)[] range) {
265+
/**
266+
* This specialized function either adds the range to the work
267+
* list, or scans directly the range, depending if the range
268+
* contains the Worker `this` pointer. If the range contains
269+
* the Worker `this` pointer, then we are scanning our own
270+
* stack. This can only happen in cases where a custom function
271+
* has decided to scan our stack, and has pushed registers
272+
* (i.e. druntime). In this case, we need to scan immediately,
273+
* to avoid losing the register data!
274+
*/
275+
if (range.contains(&this)) {
276+
scan(range);
277+
} else {
278+
// Either a TLS range, or the stack of a suspended
279+
// thread. Can be scanned at any time.
280+
addToWorkList(range);
281+
}
282+
}
283+
264284
void addToWorkList(WorkItem[] items) {
265285
scanner.addToWorkList(items);
266286
}

0 commit comments

Comments
 (0)