#include #include void error(char *msg, ...) { } extern "C" void TouchCalibrate(); DWORD iid_ConfigManager[4] ={0x483B6126, 0x493B59B4, 0x2B97E3A9, 0x41B3FEDA}; // {483B6126-59B4-493B-A9E3-972BDAFEB341} DWORD clsid_ConfigManager[4] ={0x67C73FBF, 0x44DD999E, 0x0E4832AF, 0xA37ECB86}; // {67C73FBF-999E-44DD-AF32-480E86CB7EA3} DWORD iid_XMLDOMDocument[4] ={0x2933BF81, 0x11D27B36, 0xC0000EB2, 0x603E984F}; // {2933BF81-7B36-11D2-B20E-00C04F983E60} DWORD clsid_DOMDocument[4] ={0x2933BF90, 0x11D27B36, 0xC0000EB2, 0x603E984F}; // {2933BF90-7B36-11D2-B20E-00C04F983E60} /* vtbl[58] : HRESULT ( STDMETHODCALLTYPE __RPC_FAR *load )( // [helpstring][id] IXMLDOMDocument __RPC_FAR * This, VARIANT xmlSource, // [in] VARIANT_BOOL __RPC_FAR *isSuccessful); // [retval][out] */ typedef HRESULT (*PFFUNC)(...); void ParseConfigXml(TCHAR *filename) { if (CoInitializeEx(0,0)<0) return; struct cfgmgr { PFFUNC *vtbl; } *cfgmgr=NULL; if (CoCreateInstance((REFCLSID)clsid_ConfigManager, 0, 1, (REFCLSID)iid_ConfigManager, (void**)&cfgmgr)<0) return; if (cfgmgr->vtbl[7](cfgmgr, -1)>=0) { struct domdoc { PFFUNC *vtbl; } *domdoc=NULL; if (CoCreateInstance((REFCLSID)clsid_DOMDocument, 0, 1, (REFCLSID)iid_XMLDOMDocument, (void**)&domdoc)>=0) { VARIANT ole_filename; VariantInit(&ole_filename); ole_filename.vt= VT_BSTR; ole_filename.bstrVal= SysAllocString(filename); VARIANT_BOOL success; if (domdoc->vtbl[58](domdoc, ole_filename, &success)>=0) { cfgmgr->vtbl[3](cfgmgr, domdoc, 1); } domdoc->vtbl[2](domdoc); VariantClear(&ole_filename); } } cfgmgr->vtbl[2](cfgmgr); return ; } // the idea is to have adaptrom retrieve and store certain registry settings from the deviece, // and store them in rom. and have welcome.exe recover them. // this should be timestamped somehow, such that this data is only valid for a brief period of time. // typedef struct RomRegistryRecord { DWORD reclen; DWORD hive; DWORD keylen; DWORD valnamelen; DWORD type; DWORD datalen; BYTE data[1]; } RomRegistryRecord; bool ParseRomRegistrySettings() { RomRegistryRecord *romreg= (RomRegistryRecord *)0x81925800; while (romreg->reclen) { TCHAR *key = (TCHAR*)romreg->data;; TCHAR *valname= (TCHAR*)key[romreg->keylen+1]; BYTE *data= (BYTE*)valname[romreg->valnamelen+1]; DWORD disp; HKEY hk; // doc says it needs a 'class' string, everybody else says class don't exist. if (ERROR_SUCCESS!=RegCreateKeyEx((HKEY)romreg->hive, key, 0, L"??", 0, 0, NULL, &hk, &disp)) { error("RegCreateKeyEx"); return false; } if (ERROR_SUCCESS!=RegSetValueEx(hk, valname, 0, romreg->type, data, romreg->datalen)) { error("RegSetValueEx"); return false; } RegCloseKey(hk); romreg= (RomRegistryRecord *)romreg->data[romreg->reclen - 6*sizeof(DWORD)]; } return true; } int KillApp(TCHAR *szProcName) { HANDLE hTH= CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); int res=0; PROCESSENTRY32 pe; pe.dwSize= sizeof(PROCESSENTRY32); if (Process32First(hTH, &pe)) { do { if (wcsicmp(szProcName, pe.szExeFile)==0) { res++; HANDLE hProc= OpenProcess(0, 0, pe.th32ProcessID); if (TerminateProcess(hProc, 0)) res++; CloseHandle(hProc); break; } } while (Process32Next(hTH, &pe)); } CloseToolhelp32Snapshot(hTH); return res; } int FindApp(TCHAR *szProcName) { HANDLE hTH= CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); bool bRes= false; PROCESSENTRY32 pe; pe.dwSize= sizeof(PROCESSENTRY32); if (Process32First(hTH, &pe)) { do { if (wcsicmp(szProcName, pe.szExeFile)==0) { bRes= true; break; } } while (Process32Next(hTH, &pe)); } CloseToolhelp32Snapshot(hTH); return bRes; } void RunApp(TCHAR *szAppname, TCHAR *szCommandLine) { SHELLEXECUTEINFO exec; memset(&exec, 0, sizeof(SHELLEXECUTEINFO)); exec.cbSize= sizeof(SHELLEXECUTEINFO); exec.lpFile= szAppname; exec.lpParameters= szCommandLine; exec.lpVerb= L"open"; exec.nShow= SW_SHOW; exec.fMask= SEE_MASK_FLAG_NO_UI|SEE_MASK_NOCLOSEPROCESS; ShellExecuteEx(&exec); } extern "C" BOOL KernelIoControl(DWORD dwIoControlCode, LPVOID lpInBuf, DWORD nInBufSize, LPVOID lpOutBuf, DWORD nOutBufSize, LPDWORD lpBytesReturned); int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow) { ImmDisableIME(0); HWND hTaskWnd= FindWindow(L"HHTaskBar", 0); if (hTaskWnd) ShowWindow(hTaskWnd, SW_HIDE); TouchCalibrate(); DeleteFile(L"\\Windows\\StartUp\\Welcome.lnk"); if (hTaskWnd) { ShowWindow(hTaskWnd, SW_SHOWNOACTIVATE); PostMessage(hTaskWnd, WM_COMMAND, 0x3f0, 0); //PostMessage(hTaskWnd, WM_COMMAND, 0x3ec, 0); } ParseConfigXml(L"\\windows\\defaultconfig.xml"); CopyFile(L"\\Windows\\Switch.lnk", L"\\Windows\\Startup\\Switch.lnk", false); SetFileAttributes(L"\\Windows\\Startup\\Switch.lnk", FILE_ATTRIBUTE_NORMAL); // RunApp(L"\\Windows\\Startup\\Switch.lnk", L""); KillApp(L"cprog.exe"); RunApp(L"\\Windows\\XDAUnlock.exe", L"-q"); Sleep(200); // should be sufficient time for app to startup while (FindApp(L"XDAUnlock.exe")) { Sleep(200); SystemIdleTimerReset(); KillApp(L"cprog.exe"); } RunApp(L"\\Windows\\AutoConfig.exe", L""); Sleep(1000); // should be sufficient time for app to startup while (FindApp(L"AutoConfig.exe")) { Sleep(200); SystemIdleTimerReset(); KillApp(L"cprog.exe"); } // reboot KernelIoControl(0x0101003c, 0, 0, 0, 0, 0); /* --- alternative ways to run programs: //CreateProcess(L"\\Windows\\XDA Unlock.exe", L"-q", NULL, NULL, false, 0, NULL, NULL, NULL, NULL); //ShellExecute(0, L"open", L"\\Windows\\XDA Unlock.exe", L"-q", NULL, SW_SHOW); SYSTEMTIME systime; GetLocalTime(&systime); TIME_ZONE_INFORMATION tz; GetTimeZoneInformation(&tz); SYSTEMTIME runtime; GetNextRunTime(&tz, &systime, 0, &runtime); // not sure about 3rd parameter CeRunAppAtTime(L"\\Windows\\XDAUnlock.lnk", &runtime); // must use link, with exe + parameter in .lnk file */ return 0; }