HotSpot VM генерирует карту GC для каждой скомпилированной подпрограммы, которая содержит информацию о том, где находятся корни. Например, предположим, что он скомпилировал подпрограмму для машинного кода (принцип такой же для байтового кода) длиной 120 байт, тогда карта GC для него может выглядеть примерно так:
0 : [RAX, RBX]
4 : [RAX, [RSP+0]]
10 : [RBX, RSI, [RSP+0]]
...
120 : [[RSP+0],[RSP+8]]
Здесь [RSP+x]
должно указывать расположение стеков и R??
регистров. Таким образом, если поток останавливается в инструкции по сборке со смещением 10 и выполняется цикл gc, то HotSpot знает, что три корня находятся в RBX
, RSI
и [RSP+0]
. Он отслеживает эти корни и обновляет указатели, если ему нужно переместить объекты.
Формат, который я описал для карты GC, просто для демонстрации принципа и, очевидно, не тот, который на самом деле использует HotSpot. Он не является полным, поскольку он не содержит информации о регистрах и слотах стека, которые содержат примитивные действующие значения, и неэффективно использовать список для каждого смещения инструкции. Есть много способов, которыми вы можете упаковать информацию гораздо более эффективным способом.