ScopedArgumentsTable moved out of Primitive Gigacage
72272dc
Source/JavaScriptCore/runtime/ScopedArgumentsTable.cpp
- result->m_length = length;
- result->m_arguments = ArgumentsPtr::tryCreate(length);
- if (!result->m_arguments) [[unlikely]]
+ if (!result->m_arguments.tryGrow(length)) [[unlikely]]
return nullptr;
- result->m_watchpointSets.fill(nullptr, length);
+ if (!result->m_watchpointSets.tryGrow(length)) [[unlikely]]
+ return nullptr;
+ std::ranges::fill(result->m_watchpointSets.mutableSpan(), nullptr);
...
- m_watchpointSets.resize(newLength); // 잠긴(immutable) 테이블을 변경함
- for (unsigned i = std::min(m_length, newLength); i--;) {
- result->at(i) = this->at(i);
+ for (unsigned i = std::min<uint32_t>(m_arguments.size(), newLength); i--;) {
+ result->m_arguments[i] = this->m_arguments[i];
result->m_watchpointSets[i] = this->m_watchpointSets[i];
}
Gigacage는 JSC의 공간 안전성 완화 기법으로, 특정 heap allocation을 예약된 가상 주소 영역 안에 격리합니다. 이 cage에 한정된 pointer는 손상되더라도 해당 영역 밖으로 탈출할 수 없습니다. Primitive cage는 TypedArray storage, ArrayBuffer 내용 등 사용자 페이로드 버퍼만을 위한 전용 공간입니다. ScopeOffset은 함수의 인자 목록에서 named argument의 위치를 JSLexicalEnvironment 내부의 변수 슬롯 인덱스로 매핑하는 engine 내부 메타데이터입니다.
이 commit은 ScopedArgumentsTable::m_arguments를 CagedUniquePtr<ScopeOffset, Gigacage::Primitive>에서 일반 Vector<ScopeOffset>으로 변경했습니다. 이를 통해 engine 내부 scope 메타데이터가 Primitive Gigacage 밖으로 이동되었습니다. 아울러 trySetLength에서 잠겨 있어야 할(immutable) 테이블 인스턴스를 변경하던 낡은 m_watchpointSets.resize(newLength) 호출도 함께 제거되었습니다.
Significance
이 변경은 알려진 cage-pivot 경로를 차단합니다. 기존에는 Primitive Gigacage에 대한 write primitive(예: 손상된 TypedArray backing store를 통한 경우)로 ScopeOffset 메타데이터에 도달하는 것이 이론적으로 가능했습니다. 이 경우 해당 값이 JSLexicalEnvironment::variables()에 대한 unchecked index로 전환되어, 범위를 벗어난 변수 슬롯 접근이 발생할 수 있었습니다.
Audit directions
a Aaaaa Aaaaa Aa Aaaaaa Aaaaaa Aaaa Aa Aaaaaaaaaaaaaaaaaa Aaaaaaaaaaaaaaaaaaaaa Aaaaaaa a Aaaaaaa Aa Aaa Aaa Aaaaa Aaaaaa Aaaaaa Aaa Aaaaa Aa Aa Aaaa Aaaaa Aaaaaaaaaaaaaaaaaaaaaaaaa Aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Aaaaa Aa Aaa Aaa Aa Aaaa Aaa Aaa Aaaaaa Aa Aaaa Aaaaaaaa Aaa Aaaa Aaaa
a Aaaaaaaaaaa Aaaaaa Aaaaa Aaa Aaaa Aaaaaa Aaaaaaaaaaaaaaaaaaaaaa Aaa Aaa Aaaaaaaaaaaaaaaaaaaaaaaaaa Aaaaaaaaaaaaaaaaaaaaaaaa Aaaa Aaa Aaaaaa Aaaaa Aaaaaaaaaaaaaaaaaaaaaaaa a Aaaaaaaaaaa Aaaaaaaaaaaaaaaa a Aaaa a Aaaaaaaaaa Aaaaaaaa a Aaaaaaa Aaaa Aa Aaa Aaaaaaa Aaa Aaaaa Aaaaaaaa Aaaa Aaaa Aa Aaaaaaaaaa Aaa a Aa Aaaaaa Aaaaa Aaa Aaaaaa
a Aaaaaaaaaaaaaa Aaaaaaaaa Aaaaa Aa Aaaaaaaaaaaaaaaaaaaaaaaaaaa Aaa Aaa Aaaaaaaaaaaa Aaaaaaaaaa Aaa Aaa Aaaa Aaaa Aaaaaa Aaaaaaaaa Aa Aaaaa Aaa Aaaaa Aa Aaa Aaa Aaaa Aa Aaaaaaaaaaaaaaaaaaaaaa Aaaa Aaa Aaaa Aaaa Aaa Aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Aaaa Aa Aa Aaaa Aa Aaa Aaa Aaaa Aaaa Aaaaa Aa Aaaaaaaaaaaaaaaa Aaaaaaa Aaaa Aaa a Aaaaa Aaa Aaaaaa
🔒Cage-mismatch pattern may recur elsewhere in JSC; JIT layout assumptions and locked-table invariants have additional audit-worthy edge cases.
더 확인하려면 구독해 주세요