diff --git a/dist/popnhax/popnhax.xml b/dist/popnhax/popnhax.xml index 4d39158..4886490 100644 --- a/dist/popnhax/popnhax.xml +++ b/dist/popnhax/popnhax.xml @@ -46,14 +46,16 @@ - + 0 - + + + 1 0 diff --git a/popnhax/config.h b/popnhax/config.h index eba6272..ab89793 100644 --- a/popnhax/config.h +++ b/popnhax/config.h @@ -27,6 +27,7 @@ struct popnhax_config { bool patch_xml_auto; char patch_xml_filename[MAX_PATH]; char force_datecode[11]; + bool network_datecode; int8_t keysound_offset; int8_t beam_brightness; bool fps_uncap; diff --git a/popnhax/dllmain.cc b/popnhax/dllmain.cc index afe8e2a..4cf1be0 100644 --- a/popnhax/dllmain.cc +++ b/popnhax/dllmain.cc @@ -125,6 +125,8 @@ PSMAP_MEMBER_REQ(PSMAP_PROPERTY_TYPE_BOOL, struct popnhax_config, practice_mode, "/popnhax/practice_mode") PSMAP_MEMBER_REQ(PSMAP_PROPERTY_TYPE_STR, struct popnhax_config, force_datecode, "/popnhax/force_datecode") +PSMAP_MEMBER_REQ(PSMAP_PROPERTY_TYPE_BOOL, struct popnhax_config, network_datecode, + "/popnhax/network_datecode") PSMAP_MEMBER_REQ(PSMAP_PROPERTY_TYPE_S8, struct popnhax_config, keysound_offset, "/popnhax/keysound_offset") PSMAP_MEMBER_REQ(PSMAP_PROPERTY_TYPE_S8, struct popnhax_config, beam_brightness, @@ -187,6 +189,47 @@ void asm_patch_datecode() { real_asm_patch_datecode(); } +/* retrieve destination address when it checks for "soft/ext", then wait next iteration to overwrite */ +uint8_t g_libavs_datecode_patch_state = 0; +char *datecode_property_ptr; +uint32_t eaxsave; +void (*real_asm_patch_datecode_libavs)(); +void asm_patch_datecode_libavs() { + if (g_libavs_datecode_patch_state == 2) + __asm("jmp leave_datecode_patch\n"); + + if (g_libavs_datecode_patch_state == 1) + { + __asm("push edx\n"); + __asm("push eax\n"); + __asm("push ecx\n"); + /* memcpy(datecode_property_ptr, g_datecode_override, 10);*/ + __asm("mov edx,_g_datecode_override\n"); + __asm("mov eax,_datecode_property_ptr\n"); + __asm("mov ecx,dword ptr ds:[edx] \n"); + __asm("mov dword ptr ds:[eax],ecx \n"); + __asm("mov ecx,dword ptr ds:[edx+4] \n"); + __asm("mov dword ptr ds:[eax+4],ecx \n"); + __asm("movzx edx,word ptr ds:[edx+8] \n"); + __asm("mov word ptr ds:[eax+8],dx \n"); + __asm("pop ecx\n"); + __asm("pop eax\n"); + __asm("pop edx\n"); + + g_libavs_datecode_patch_state++; + __asm("jmp leave_datecode_patch\n"); + } + + __asm("mov %0, [esp+0x38]\n":"=a"(datecode_property_ptr):); + if ((uint32_t)datecode_property_ptr > 0x200000 && datecode_property_ptr[0] == 's'&& datecode_property_ptr[5] == 'e'&& datecode_property_ptr[7] == 't') + { + __asm("mov %0, ecx\n":"=c"(datecode_property_ptr):); + g_libavs_datecode_patch_state++; + } + __asm("leave_datecode_patch:\n"); + real_asm_patch_datecode_libavs(); +} + void (*real_omnimix_patch_jbx)(); void omnimix_patch_jbx() { __asm("mov al, 'X'\n"); @@ -774,13 +817,41 @@ static bool patch_datecode(char *datecode) { MH_CreateHook((LPVOID)patch_addr, (LPVOID)asm_patch_datecode, (void **)&real_asm_patch_datecode); - printf("popnhax: datecode set to %s\n",g_datecode_override); - return true; + printf("popnhax: datecode set to %s",g_datecode_override); } else { printf("popnhax: Couldn't patch datecode\n"); return false; } } + + if (!config.network_datecode) + { + printf("\n"); + return true; + } + + /* network_datecode is on: also patch libavs so that forced datecode shows in network packets */ + DWORD avsdllSize = 0; + char *avsdata = getDllData("libavs-win32.dll", &avsdllSize); + { + fuzzy_search_task task; + + FUZZY_START(task, 1) + FUZZY_CODE(task, 0, "\x57\x56\x89\x34\x24\x8B\xF2\x8B\xD0\x0F\xB6\x46\x2E", 13) + + int64_t pattern_offset = find_block(avsdata, avsdllSize, &task, 0); + if (pattern_offset != -1) { + uint64_t patch_addr = (int64_t)avsdata + pattern_offset; + MH_CreateHook((LPVOID)patch_addr, (LPVOID)asm_patch_datecode_libavs, + (void **)&real_asm_patch_datecode_libavs); + + printf("(including network)\n"); + } else { + printf("(WARNING: failed to apply to network)\n"); + return false; + } + } + return true; } static bool patch_database(uint8_t force_unlocks) { @@ -2163,7 +2234,7 @@ uint16_t *g_course_song_id_ptr; void (*real_parse_ranking_info)(); void score_challenge_retrieve_addr() { - /* only set pointer if g_course_id_ptr is not set yet, + /* only set pointer if g_course_id_ptr is not set yet, * to avoid overwriting with past challenge data which * is sent afterwards */ @@ -2184,7 +2255,7 @@ void (*score_challenge_test_if_normal_mode)(); void (*real_make_score_challenge_category)(); void make_score_challenge_category() -{ +{ __asm("push ecx\n"); __asm("push ebx\n"); __asm("push edi\n"); @@ -2216,7 +2287,7 @@ void make_score_challenge_category() __asm("pop ecx\n"); } -/* all code handling score challenge is still in the game but the +/* all code handling score challenge is still in the game but the * function responsible for building and adding the score challenge * category to song selection has been stubbed. let's rewrite it */