Skip to content

Commit

Permalink
[DYNAREC] Some light rework of the hotpage handling
Browse files Browse the repository at this point in the history
  • Loading branch information
ptitSeb committed Dec 23, 2024
1 parent da0820c commit 48db759
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 17 deletions.
25 changes: 21 additions & 4 deletions src/custommem.c
Original file line number Diff line number Diff line change
Expand Up @@ -1482,20 +1482,37 @@ int isprotectedDB(uintptr_t addr, size_t size)
return 1;
}

uintptr_t hotpage = 0;
int hotpage_cnt = 0;
static uintptr_t hotpage = 0;
static int hotpage_cnt = 0;
static int repeated_count = 0;
static uintptr_t repeated_page = 0;
#define HOTPAGE_MARK 64
void SetHotPage(uintptr_t addr)
{
hotpage = addr&~(box64_pagesize-1);
hotpage_cnt = HOTPAGE_MARK;
}
void CheckHotPage(uintptr_t addr)
{
uintptr_t page = (uintptr_t)addr&~(box64_pagesize-1);
if(repeated_count==1 && repeated_page==page) {
dynarec_log(LOG_DEBUG, "Detecting a Hotpage at %p (%d)\n", (void*)repeated_page, repeated_count);
SetHotPage(repeated_page);
repeated_count = 0;
repeated_page = 0;
} else {
repeated_count = 1;
repeated_page = page;
}
}
int isInHotPage(uintptr_t addr)
{
if(!hotpage_cnt)
return 0;
--hotpage_cnt;
return (addr>=hotpage) && (addr<hotpage+box64_pagesize);
int ret = (addr>=hotpage) && (addr<hotpage+box64_pagesize);
if(ret)
--hotpage_cnt;
return ret;
}
int checkInHotPage(uintptr_t addr)
{
Expand Down
14 changes: 1 addition & 13 deletions src/libtools/signals.c
Original file line number Diff line number Diff line change
Expand Up @@ -1478,21 +1478,9 @@ void my_box64signalhandler(int32_t sig, siginfo_t* info, void * ucntx)
// check if SMC inside block
db = FindDynablockFromNativeAddress(pc);
db_searched = 1;
static uintptr_t repeated_page = 0;
dynarec_log(LOG_DEBUG, "SIGSEGV with Access error on %p for %p , db=%p(%p), prot=0x%hhx (old page=%p)\n", pc, addr, db, db?((void*)db->x64_addr):NULL, prot, (void*)repeated_page);
static int repeated_count = 0;
if(repeated_page == ((uintptr_t)addr&~(box64_pagesize-1))) {
++repeated_count; // Access eoor multiple time on same page, disable dynarec on this page a few time...
if(repeated_count>1) {
dynarec_log(LOG_DEBUG, "Detecting a Hotpage at %p (%d)\n", (void*)repeated_page, repeated_count);
SetHotPage(repeated_page);
}
} else {
repeated_page = (uintptr_t)addr&~(box64_pagesize-1);
repeated_count = 0;
}
// access error, unprotect the block (and mark them dirty)
unprotectDB((uintptr_t)addr, 1, 1); // unprotect 1 byte... But then, the whole page will be unprotected
if(db) CheckHotPage((uintptr_t)addr);
int db_need_test = db?getNeedTest((uintptr_t)db->x64_addr):0;
if(db && ((addr>=db->x64_addr && addr<(db->x64_addr+db->x64_size)) || db_need_test)) {
emu = getEmuSignal(emu, p, db);
Expand Down

0 comments on commit 48db759

Please sign in to comment.