@@ -56,29 +56,113 @@ void*(__cdecl* readSetting_org)(void*, void*, int, void*);
5656void * __cdecl readSetting_hook (void * out_qv, void * setting, int a3, void * a4)
5757{
5858 static auto QVariant_QVariant_from_bool = GetExport<void *(__thiscall*)(void *, bool )>(Qt5Core, " ??0QVariant@@QAE@_N@Z" );
59+ static auto QVariant_QVariant_from_cchar = GetExport<void *(__thiscall*)(void *, const char *)>(Qt5Core, " ??0QVariant@@QAE@PBD@Z" );
60+ static auto QVariant_destroy = GetExport<void *(__thiscall*)(void *)>(Qt5Core, " ??1QVariant@@QAE@XZ" );
61+
5962 static auto SETTING_MigrationDisabled = GetExport<void *>(OriginClient, " ?SETTING_MigrationDisabled@Services@Origin@@3VSetting@12@A" ); // non-const symbol
6063 if (!SETTING_MigrationDisabled)
6164 SETTING_MigrationDisabled = GetExport<void *>(OriginClient, " ?SETTING_MigrationDisabled@Services@Origin@@3VSetting@12@B" ); // const symbol
65+ static auto SETTING_REMEMBER_ME_PROD = GetExport<void *>(OriginClient, " ?SETTING_REMEMBER_ME_PROD@Services@Origin@@3VSetting@12@A" ); // non-const symbol
66+ if (!SETTING_REMEMBER_ME_PROD)
67+ SETTING_REMEMBER_ME_PROD = GetExport<void *>(OriginClient, " ?SETTING_REMEMBER_ME_PROD@Services@Origin@@3VSetting@12@B" ); // const symbol
68+
69+ static auto Origin_Services_Variant_operator_QString = GetExport<void * (__thiscall*)(void *, void *)>(OriginClient, " ??BVariant@Services@Origin@@QBE?AVQString@@XZ" );
70+ static auto QString_destroy = GetExport<void (__thiscall*)(void *)>(Qt5Core, " ??1QString@@QAE@XZ" );
71+ static auto QString_toStdString = GetExport<void * (__thiscall*)(void *, std::string*)>(Qt5Core, " ?toStdString@QString@@QBE?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@XZ" );
6272
6373 static bool didWarnAboutMissingAlready = false ;
64- if (!didWarnAboutMissingAlready && (!QVariant_QVariant_from_bool || !SETTING_MigrationDisabled)) [[unlikely]]
74+ if (!didWarnAboutMissingAlready && (!QVariant_QVariant_from_bool || !QVariant_QVariant_from_cchar || !QVariant_destroy
75+ || !SETTING_MigrationDisabled || !SETTING_REMEMBER_ME_PROD || !Origin_Services_Variant_operator_QString || !QString_destroy
76+ || !QString_toStdString)) [[unlikely]]
6577 {
6678 didWarnAboutMissingAlready = true ;
6779 MessageBoxA (nullptr , (" Error in Origin::Services::readSetting: one of the exports could not have been resolved, we may crash\n "
68- " \n QVariant_QVariant_from_bool: " + std::to_string (uintptr_t (QVariant_QVariant_from_bool))
69- + " \n SETTING_MigrationDisabled: " + std::to_string (uintptr_t (SETTING_MigrationDisabled))
80+ " \n QVariant_QVariant_from_bool: " + std::format (" {:#010x}" , uintptr_t (QVariant_QVariant_from_bool))
81+ + " \n QVariant_QVariant_from_cchar: " + std::format (" {:#010x}" , uintptr_t (QVariant_QVariant_from_cchar))
82+ + " \n QVariant_destroy: " + std::format (" {:#010x}" , uintptr_t (QVariant_destroy))
83+ + " \n SETTING_MigrationDisabled: " + std::format (" {:#010x}" , uintptr_t (SETTING_MigrationDisabled))
84+ + " \n SETTING_REMEMBER_ME_PROD: " + std::format (" {:#010x}" , uintptr_t (SETTING_REMEMBER_ME_PROD))
85+ + " \n Origin_Services_Variant_operator_QString: " + std::format (" {:#010x}" , uintptr_t (Origin_Services_Variant_operator_QString))
86+ + " \n QString_destroy: " + std::format (" {:#010x}" , uintptr_t (QString_destroy))
87+ + " \n QString_toStdString: " + std::format (" {:#010x}" , uintptr_t (QString_toStdString))
7088 ).c_str (),
7189 ERROR_MSGBOX_CAPTION, MB_ICONERROR);
7290 }
91+
92+ void * ret = readSetting_org (out_qv, setting, a3, a4);
93+
94+ if (IsDebuggerPresent ())
95+ {
96+
97+ if (Origin_Services_Variant_operator_QString && QString_destroy && QString_toStdString)
98+ {
99+ char qs[4 ] = { 0 };
100+ Origin_Services_Variant_operator_QString (ret, qs);
101+
102+ std::string qss;
103+ QString_toStdString (qs, &qss);
104+
105+ std::string setting_name;
106+ QString_toStdString ((void *)(uintptr_t (setting) + 8 ), &setting_name);
107+ OutputDebugStringA ((" readSetting: " + setting_name + " =" + qss).c_str ());
108+
109+ /* if (setting_name == "RememberMeProd")
110+ {
111+ QVariant_destroy(ret);
112+ static auto QVariant_QVariant_from_cchar = GetExport<void* (__thiscall*)(void*, const char*)>(Qt5Core, "??0QVariant@@QAE@PBD@Z");
113+ QVariant_QVariant_from_cchar(out_qv, "TUU...||accounts.ea.com||2025-03-11T21:21:02Z||/connect");
114+ OutputDebugStringA("overriding!");
115+ }*/
116+
117+ QString_destroy (qs);
118+ }
119+ }
73120
74121 if (setting == SETTING_MigrationDisabled)
75122 {
76123 // override to true
124+ QVariant_destroy (ret);
77125 QVariant_QVariant_from_bool (out_qv, true ); // caller will destruct this
78126 return out_qv;
79127 }
128+
129+ if (setting == SETTING_REMEMBER_ME_PROD)
130+ {
131+ OutputDebugStringA (" [Origin::Services::readSetting] SETTING_REMEMBER_ME_PROD" );
132+ char qs[4 ] = { 0 };
133+ Origin_Services_Variant_operator_QString (ret, qs);
134+
135+ std::string qss;
136+ QString_toStdString (qs, &qss);
137+ QString_destroy (qs);
138+ // OutputDebugStringA(("[Origin::Services::readSetting] qss: " + qss).c_str());
139+
140+ std::vector<std::string> parts;
141+ for (const auto word : std::views::split (qss, " ||" sv))
142+ parts.push_back (std::string{ word.begin (), word.end () });
143+
144+ if (parts.size () >= 2 )
145+ {
146+ // OutputDebugStringA(("[Origin::Services::readSetting] parts[1]: " + parts[1]).c_str());
147+ if (parts[1 ] == " .ea.com" )
148+ {
149+ OutputDebugStringA (" [Origin::Services::readSetting] Fixing domain name to accounts.ea.com for cookie remid" );
150+ parts[1 ] = " accounts.ea.com" ;
151+
152+ qss.clear ();
153+ for (auto word : parts)
154+ qss += " ||" + word;
155+ qss.erase (0 , 2 );
156+
157+ QVariant_destroy (ret);
158+ QVariant_QVariant_from_cchar (out_qv, qss.c_str ()); // caller will destruct this
159+ // OutputDebugStringA(("[Origin::Services::readSetting] final value: " + qss).c_str());
160+ return out_qv;
161+ }
162+ }
163+ }
80164
81- return readSetting_org (out_qv, setting, a3, a4) ;
165+ return ret ;
82166}
83167
84168// Origin::Engine::Content::LocalContent::treatUpdatesAsMandatory
@@ -97,129 +181,6 @@ void __fastcall checkForUpdate_hook(void* thisptr /*ecx*/)
97181 // downloaded upon next Origin launch by thin setup.
98182}
99183
100- #if 0
101- // NOTE: This hook is completely broken, but also not needed...
102- // QString::compare
103- bool(__thiscall* qstring_compare_org)(void*, void*, int);
104- bool __fastcall qstring_compare_hook(void* thisptr /*ecx*/, void* /*edx*/, void* comparee, int a3)
105- {
106- if (a3 == 1)
107- {
108- static auto QString_startsWith = GetExport<void* (__thiscall*)(void*, void*, int)>(Qt5Core, "?startsWith@QString@@QBE_NABV1@W4CaseSensitivity@Qt@@@Z");
109- static auto QString_QString = GetExport<void* (__thiscall*)(void*, const char*)>(Qt5Core, "??0QString@@QAE@PBD@Z");
110- static int ten = 0;
111- static int twelve = 0;
112- if (ten == 0) QString_QString(&twelve, "10.5.");
113- if (twelve == 0) QString_QString(&twelve, "12.");
114- if (QString_startsWith(comparee, &twelve, 0) && QString_startsWith(thisptr, &ten, 0))
115- return 0;
116- }
117- return qstring_compare_org(thisptr, comparee, a3);
118- }
119- #endif
120-
121- #if 0
122- // Origin::Client::LoginViewController::init
123- void(__thiscall* loginViewController_init_org)(void*, DWORD*, /* Origin::Client::AuthenticationJsHelper* */ void*, int);
124- void __fastcall loginViewController_init_hook(void* thisptr /*ecx*/, void* /*edx*/, DWORD* a2, void* a3, int a4)
125- {
126- loginViewController_init_org(thisptr, a2, a3, a4);
127- ////*(bool*)((uintptr_t)thisptr + 166) = true; // make it think we've loaded all cookies already
128- //*(bool*)((uintptr_t)thisptr + 167) = true; // make it think Trusted Clock is already initialized
129- loginViewController_init_org(thisptr, a2, a3, a4);
130-
131- // this does NOT seem to work here!
132- // Origin::Client::LoginViewController::killSplashScreenAndShowLoginWindow
133- //static auto killSplashScreenAndShowLoginWindow = GetExport<void(__thiscall*)(void*)>(OriginClient, "?killSplashScreenAndShowLoginWindow@LoginViewController@Client@Origin@@AAEXXZ");
134- //killSplashScreenAndShowLoginWindow(thisptr);
135- }
136-
137- // Origin::Services::TrustedClock::isInitialized
138- bool(__thiscall* trustedClock_isInitialized_org)(void*);
139- bool __fastcall trustedClock_isInitialized_hook(void* thisptr /*ecx*/)
140- {
141- return true;
142- }
143-
144- // Origin::Client::LoginViewController::loadLoginPage
145- void(__thiscall* loginViewController_loadLoginPage_org)(void*, int);
146- void __fastcall loginViewController_loadLoginPage_hook(void* thisptr /*ecx*/, void* /*edx*/, int a2)
147- {
148- loginViewController_loadLoginPage_org(thisptr, a2);
149-
150- static auto killSplashScreenAndShowLoginWindow = GetExport<void(__thiscall*)(void*)>(OriginClient, "?killSplashScreenAndShowLoginWindow@LoginViewController@Client@Origin@@AAEXXZ");
151-
152- static bool didWarnAboutMissingAlready = false;
153- if (!didWarnAboutMissingAlready && (!killSplashScreenAndShowLoginWindow)) [[unlikely]]
154- {
155- didWarnAboutMissingAlready = true;
156- MessageBoxA(nullptr, "Error in Origin::Client::LoginViewController::loadLoginPage: killSplashScreenAndShowLoginWindow was not found, your Origin client will probably be stuck on splash screen\n"
157- "\nRight-click Origin icon in your tray and click Open Origin as a workaround.",
158- ERROR_MSGBOX_CAPTION, MB_ICONERROR);
159- }
160-
161- // well it seems someone forgot to call this func in a reasonable place like here
162- if (killSplashScreenAndShowLoginWindow)
163- killSplashScreenAndShowLoginWindow(thisptr);
164- }
165- #endif
166-
167- // QWebEngineCookieStore::setCookie
168- void (__thiscall* QWebEngineCookieStore_setCookie_org)(void *, /* QNetworkCookie */ void *, /* QUrl */ void *);
169- void __fastcall QWebEngineCookieStore_setCookie_hook (void * thisptr /* ecx*/ , void * /* edx*/ , void * cookie, void * url)
170- {
171- static auto QString_destroy = GetExport<void (__thiscall*)(void *)>(Qt5Core, " ??1QString@@QAE@XZ" );
172- static auto QString_QString_from_cchar = GetExport<void * (__thiscall*)(void *, const char *)>(Qt5Core, " ??0QString@@QAE@PBD@Z" );
173- static auto QString_toStdString = GetExport<void * (__thiscall*)(void *, std::string*)>(Qt5Core, " ?toStdString@QString@@QBE?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@XZ" );
174- static auto QByteArray_toStdString = GetExport<void * (__thiscall*)(void *, std::string*)>(Qt5Core, " ?toStdString@QByteArray@@QBE?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@XZ" );
175- static auto QByteArray_destroy = GetExport<void * (__thiscall*)(void *)>(Qt5Core, " ??1QByteArray@@QAE@XZ" );
176- static auto QNetworkCookie_setDomain = GetExport<void (__thiscall*)(void *, void *)>(Qt5Network, " ?setDomain@QNetworkCookie@@QAEXABVQString@@@Z" );
177- static auto QNetworkCookie_domain = GetExport<void (__thiscall*)(void *, void *)>(Qt5Network, " ?domain@QNetworkCookie@@QBE?AVQString@@XZ" );
178- static auto QNetworkCookie_name = GetExport<void (__thiscall*)(void *, void *)>(Qt5Network, " ?name@QNetworkCookie@@QBE?AVQByteArray@@XZ" );
179-
180- OutputDebugStringA (" [QWebEngineCookieStore::setCookie] Howdy" );
181-
182- if (QString_destroy && QString_QString_from_cchar && QString_toStdString && QByteArray_toStdString && QByteArray_destroy && QNetworkCookie_setDomain && QNetworkCookie_domain)
183- {
184- char qs_cookie_domain[4 ] = { 0 };
185- char qba_cookie_name[4 ] = { 0 };
186- std::string cookie_domain;
187- std::string cookie_name;
188-
189- QNetworkCookie_domain (cookie, qs_cookie_domain);
190- QString_toStdString (qs_cookie_domain, &cookie_domain);
191-
192- QNetworkCookie_name (cookie, qba_cookie_name);
193- QByteArray_toStdString (qba_cookie_name, &cookie_name);
194-
195- OutputDebugStringA ((" [QWebEngineCookieStore::setCookie] name=" + cookie_name + " domain=" + cookie_domain).c_str ());
196- // __debugbreak();
197-
198- if (cookie_name == " remid" && cookie_domain == " " )
199- {
200- OutputDebugStringA (" [QWebEngineCookieStore::setCookie] Fixing domain name to accounts.ea.com for cookie remid" );
201- char qs_cookie_domain_new[4 ] = { 0 };
202- QString_QString_from_cchar (qs_cookie_domain_new, " accounts.ea.com" );
203- QNetworkCookie_setDomain (cookie, qs_cookie_domain_new);
204- QString_destroy (qs_cookie_domain_new);
205- }
206-
207- QString_destroy (qs_cookie_domain);
208- QByteArray_destroy (qba_cookie_name);
209- }
210- else
211- {
212- static bool didWarnAboutMissingAlready = false ;
213- if (!didWarnAboutMissingAlready) [[unlikely]]
214- {
215- didWarnAboutMissingAlready = true ;
216- MessageBoxA (nullptr , " Error in QWebEngineCookieStore::setCookie: one of the exports could not have been resolved!" , ERROR_MSGBOX_CAPTION, MB_ICONERROR);
217- }
218- }
219-
220- QWebEngineCookieStore_setCookie_org (thisptr, cookie, url);
221- }
222-
223184void DoOriginClientDllPatches ()
224185{
225186 {
@@ -259,13 +220,4 @@ void DoOriginClientDllPatches()
259220
260221 // This checks for update to nag the user in the UI and auto-download the update zip, we don't ever need that
261222 CreateHookNamed (" OriginClient" , " ?checkForUpdate@SelfUpdateService@Services@Origin@@QAEXXZ" , checkForUpdate_hook, reinterpret_cast <LPVOID*>(&checkForUpdate_org));
262- // CreateHookNamed("Qt5Core", "?compare@QString@@QBEHABV1@W4CaseSensitivity@Qt@@@Z", qstring_compare_hook, reinterpret_cast<LPVOID*>(&qstring_compare_org));
263-
264- // Patches around broken login screen due to missing cookie (hopefully it's a temporary thing?)
265- // /CreateHookNamed("OriginClient", "?init@LoginViewController@Client@Origin@@QAEXABW4StartupState@@W4IconType@OriginBanner@UIToolkit@3@ABVQString@@@Z", loginViewController_init_hook, reinterpret_cast<LPVOID*>(&loginViewController_init_org));
266- // CreateHookNamed("OriginClient", "?isInitialized@TrustedClock@Services@Origin@@QBE_NXZ", trustedClock_isInitialized_hook, reinterpret_cast<LPVOID*>(&trustedClock_isInitialized_org));
267- // /CreateHookNamed("OriginClient", "?loadLoginPage@LoginViewController@Client@Origin@@IAEX_N@Z", loginViewController_loadLoginPage_hook, reinterpret_cast<LPVOID*>(&loginViewController_loadLoginPage_org));
268-
269- //
270- // CreateHookNamed("Qt5WebEngineCore", "?setCookie@QWebEngineCookieStore@@QAEXABVQNetworkCookie@@ABVQUrl@@@Z", QWebEngineCookieStore_setCookie_hook, reinterpret_cast<LPVOID*>(&QWebEngineCookieStore_setCookie_org));
271223}
0 commit comments