Skip to content

Commit 702b50d

Browse files
author
meister
committed
Speed up snapshot save by using a set and not sorting
1 parent 1b60c69 commit 702b50d

File tree

1 file changed

+57
-40
lines changed

1 file changed

+57
-40
lines changed

src/gctools/snapshotSaveLoad.cc

Lines changed: 57 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -2135,54 +2135,66 @@ void prepareRelocationTableForSave(Fixup* fixup, SymbolLookup& symbolLookup) {
21352135
public:
21362136
OrderByAddress() {}
21372137
bool operator()(const PointerBase& x, const PointerBase& y) { return x._address <= y._address; }
2138-
};
2139-
OrderByAddress orderer;
2140-
DBG_SLS("Step1\n");
2141-
for (size_t idx = 0; idx < fixup->_Libraries.size(); idx++) {
2142-
DBG_SLS("Adding library #%lu: %s\n", idx, fixup->_Libraries[idx]._Name.c_str());
2143-
symbolLookup.addLibrary(fixup->_Libraries[idx]._Name);
2144-
auto pointersBegin = fixup->_Libraries[idx]._InternalPointers.begin();
2145-
auto pointersEnd = fixup->_Libraries[idx]._InternalPointers.end();
2146-
if (pointersBegin < pointersEnd) {
2147-
DBG_SLS("About to quickSortFirstCheckOrder _Pointers.size(): %lu\n", fixup->_Libraries[idx]._InternalPointers.size());
2148-
sort::quickSortFirstCheckOrder(pointersBegin, pointersEnd, orderer);
2138+
void addLibraries(Fixup* fixup, SymbolLookup& symbolLookup) {
2139+
for (size_t idx = 0; idx < fixup->_Libraries.size(); idx++) {
2140+
DBG_SLS("Adding library #%lu: %s\n", idx, fixup->_Libraries[idx]._Name.c_str());
2141+
symbolLookup.addLibrary(fixup->_Libraries[idx]._Name);
2142+
auto pointersBegin = fixup->_Libraries[idx]._InternalPointers.begin();
2143+
auto pointersEnd = fixup->_Libraries[idx]._InternalPointers.end();
2144+
if (pointersBegin < pointersEnd) {
2145+
DBG_SLS("About to quickSortFirstCheckOrder _Pointers.size(): %lu\n", fixup->_Libraries[idx]._InternalPointers.size());
2146+
}
2147+
}
21492148
}
2150-
}
2151-
DBG_SLS("Step2 - there are %lu libraries with function pointers that need relocating\n", fixup->_Libraries.size());
2152-
for (size_t idx = 0; idx < fixup->_Libraries.size(); idx++) {
2153-
int groupPointerIdx = -1;
2154-
ISLLibrary& curLib = fixup->_Libraries[idx];
2149+
void identifyUnique(Fixup* fixup, SymbolLookup& symbolLookup) {
2150+
for (size_t idx = 0; idx < fixup->_Libraries.size(); idx++) {
2151+
int groupPointerIdx = -1;
2152+
ISLLibrary& curLib = fixup->_Libraries[idx];
21552153
// printf("%s:%d:%s Dealing with library#%lu: %s @%p\n", __FILE__, __LINE__, __FUNCTION__, idx, curLib._Name.c_str(), &curLib
21562154
// ); printf("%s:%d:%s Number of pointers before extracting unique pointers: %lu\n", __FILE__, __LINE__, __FUNCTION__,
21572155
// curLib._InternalPointers.size() );
2158-
for (size_t ii = 0; ii < curLib._InternalPointers.size(); ii++) {
2159-
if (groupPointerIdx < 0 || curLib._InternalPointers[ii]._address != curLib._InternalPointers[ii - 1]._address) {
2160-
curLib._GroupedPointers.emplace_back(curLib._InternalPointers[ii]._pointerType, curLib._InternalPointers[ii]._address);
2161-
groupPointerIdx++;
2162-
}
2156+
std::map<uintptr_t,int> uniques;
2157+
for (size_t ii = 0; ii < curLib._InternalPointers.size(); ii++) {
2158+
auto it = uniques.find(curLib._InternalPointers[ii]._address);
2159+
if (it==uniques.end()) {
2160+
groupPointerIdx = curLib._GroupedPointers.size();
2161+
uniques[curLib._InternalPointers[ii]._address] = groupPointerIdx;
2162+
curLib._GroupedPointers.emplace_back(curLib._InternalPointers[ii]._pointerType, curLib._InternalPointers[ii]._address);
2163+
} else {
2164+
groupPointerIdx = it->second;
2165+
}
21632166
// Now encode the relocation
2164-
void** addr = (void**)curLib._InternalPointers[ii]._ptrptr;
2165-
uint8_t* uint8ptr = (uint8_t*)*addr;
2167+
void** addr = (void**)curLib._InternalPointers[ii]._ptrptr;
2168+
uint8_t* uint8ptr = (uint8_t*)*addr;
21662169
// printf("%s:%d:%s Relocation @%p group: %d from %p\n", __FILE__, __LINE__, __FUNCTION__,
21672170
// curLib._InternalPointers[ii]._ptrptr, groupPointerIdx, uint8ptr );
2168-
uint8_t firstByte = *uint8ptr;
2169-
*curLib._InternalPointers[ii]._ptrptr = encodeRelocation_(firstByte, idx, groupPointerIdx);
2171+
uint8_t firstByte = *uint8ptr;
2172+
*curLib._InternalPointers[ii]._ptrptr = encodeRelocation_(firstByte, idx, groupPointerIdx);
21702173
// printf("%s:%d:%s to %p\n", __FILE__, __LINE__, __FUNCTION__,
21712174
// (void*)*curLib._InternalPointers[ii]._ptrptr );
2172-
}
2173-
core::lisp_write(fmt::format("{} unique pointers need to be passed to dladdr\n", curLib._GroupedPointers.size()));
2174-
SaveSymbolCallback thing(curLib);
2175-
curLib._SymbolInfo.resize(curLib._GroupedPointers.size(), SymbolInfo());
2176-
thing.generateSymbolTable(fixup, symbolLookup);
2177-
core::lisp_write(
2178-
fmt::format("Library #{} {} contains {} unique pointers\n", idx, curLib._Name, curLib._GroupedPointers.size()));
2179-
for (size_t ii = 0; ii < curLib._SymbolInfo.size(); ii++) {
2180-
if (curLib._SymbolInfo[ii]._SymbolLength < 0) {
2181-
printf("%s:%d:%s The _SymbolInfo[%lu] does not have a length\n", __FILE__, __LINE__, __FUNCTION__, ii);
2175+
}
2176+
core::lisp_write(fmt::format("{} unique pointers need to be passed to dladdr\n", curLib._GroupedPointers.size()));
2177+
SaveSymbolCallback thing(curLib);
2178+
curLib._SymbolInfo.resize(curLib._GroupedPointers.size(), SymbolInfo());
2179+
thing.generateSymbolTable(fixup, symbolLookup);
2180+
core::lisp_write(
2181+
fmt::format("Library #{} {} contains {} unique pointers\n", idx, curLib._Name, curLib._GroupedPointers.size()));
2182+
for (size_t ii = 0; ii < curLib._SymbolInfo.size(); ii++) {
2183+
if (curLib._SymbolInfo[ii]._SymbolLength < 0) {
2184+
printf("%s:%d:%s The _SymbolInfo[%lu] does not have a length\n", __FILE__, __LINE__, __FUNCTION__, ii);
2185+
}
2186+
}
2187+
core::lisp_write(fmt::format("Done with library #{} at {}\n", curLib._Name, (void*)&curLib));
21822188
}
21832189
}
2184-
core::lisp_write(fmt::format("Done with library #{} at {}\n", curLib._Name, (void*)&curLib));
2185-
}
2190+
};
2191+
OrderByAddress orderer;
2192+
DBG_SLS("Step1\n");
2193+
core::lisp_write(fmt::format("Add libraries to classify unique pointers\n"));
2194+
orderer.addLibraries(fixup,symbolLookup);
2195+
DBG_SLS("Step2 - there are %lu libraries with function pointers that need relocating\n", fixup->_Libraries.size());
2196+
core::lisp_write(fmt::format("Encoding relocation data for all pointers and identifying unique pointers\n"));
2197+
orderer.identifyUnique(fixup,symbolLookup);
21862198
DBG_SLS("Step done\n");
21872199
}
21882200

@@ -2257,9 +2269,10 @@ size_t memory_test(bool dosleep, FILE* fout, const char* message) {
22572269
//
22582270
// For saving we may want to save snapshots and not die - so use noStomp forwarding.
22592271
//
2260-
core::lisp_write(fmt::format("Running memory test and gathering objects\n"));
2272+
core::lisp_write(fmt::format("Gathering base pointers for objects in memory\n"));
22612273
gctools::GatherObjects gather(gctools::room_test);
22622274
gctools::gatherAllObjects(gather);
2275+
core::lisp_write(fmt::format("Done gathering base pointers\n"));
22632276

22642277
#if 0
22652278
// this will write out headers of ALL objects
@@ -2274,7 +2287,7 @@ size_t memory_test(bool dosleep, FILE* fout, const char* message) {
22742287

22752288
size_t result = gather._corruptObjects.size();
22762289
if (result == 0) {
2277-
core::lisp_write(fmt::format("Passed the memory test with zero corrupt objects\n"));
2290+
core::lisp_write(fmt::format("Gathered base pointers with zero corrupt objects detected\n"));
22782291
if (message)
22792292
core::lisp_write(fmt::format(" {}\n", message));
22802293
} else if (result > 0) {
@@ -2550,15 +2563,18 @@ void* snapshot_save_impl(void* data) {
25502563
// printf("%s:%d:%s Setting up SymbolLookup\n", __FILE__, __LINE__, __FUNCTION__ );
25512564
SymbolLookup lookup;
25522565
DBG_SL_STEP(12, " prepareRelocationTableForSave\n");
2566+
core::lisp_write(fmt::format("Prepare relocation table for save\n"));
25532567
prepareRelocationTableForSave(&fixup, lookup);
25542568

25552569
DBG_SL_STEP(13, "Calculating library sizes\n");
2570+
core::lisp_write(fmt::format("Calculate library sizes\n"));
25562571
size_t librarySize = 0;
25572572
for (size_t idx = 0; idx < fixup._Libraries.size(); idx++) {
25582573
librarySize += fixup._Libraries[idx].writeSize();
25592574
}
25602575
DBG_SL_STEP(14, "copy_buffer_t\n");
25612576
snapshot._Libraries = new copy_buffer_t(librarySize);
2577+
core::lisp_write(fmt::format("Copy buffer\n"));
25622578
for (size_t idx = 0; idx < fixup._Libraries.size(); idx++) {
25632579
size_t alignedLen = fixup._Libraries[idx].nameSize();
25642580
char* buffer = (char*)malloc(alignedLen);
@@ -2592,6 +2608,7 @@ void* snapshot_save_impl(void* data) {
25922608

25932609
DBG_SL_STEP(15, "Generating fileHeader\n");
25942610

2611+
core::lisp_write(fmt::format("Generating fileHeader\n"));
25952612
ISLFileHeader* fileHeader = snapshot._FileHeader;
25962613
uintptr_t offset = snapshot._HeaderBuffer->_Size;
25972614
fileHeader->_LibrariesOffset = offset;
@@ -2630,7 +2647,7 @@ void* snapshot_save_impl(void* data) {
26302647
}
26312648
filename = tfbuffer;
26322649
}
2633-
printf("Writing snapshot to temporary file %s filedes = %d\n", filename.c_str(), filedes);
2650+
core::lisp_write(fmt::format("Writing snapshot to temporary file {} filedes = {}\n", filename.c_str(), filedes));
26342651
snapshot._HeaderBuffer->write_to_filedes(filedes);
26352652
snapshot._Libraries->write_to_filedes(filedes);
26362653
snapshot._Memory->write_to_filedes(filedes);

0 commit comments

Comments
 (0)