Mercurial > foo_out_sdl
comparison foosdk/sdk/foobar2000/helpers/win32_misc.cpp @ 1:20d02a178406 default tip
*: check in everything else
yay
| author | Paper <paper@tflc.us> |
|---|---|
| date | Mon, 05 Jan 2026 02:15:46 -0500 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| 0:e9bb126753e7 | 1:20d02a178406 |
|---|---|
| 1 #include "StdAfx.h" | |
| 2 #include "win32_misc.h" | |
| 3 | |
| 4 #ifdef FOOBAR2000_MOBILE_WINDOWS | |
| 5 #include <pfc/pp-winapi.h> | |
| 6 #endif | |
| 7 | |
| 8 #ifdef _WIN32 | |
| 9 | |
| 10 #include <SDK/modeless_dialog.h> | |
| 11 | |
| 12 mutexScope::mutexScope(HANDLE hMutex_, abort_callback & abort) : hMutex(hMutex_) { | |
| 13 HANDLE h[2] = { hMutex, abort.get_abort_event() }; | |
| 14 switch (WaitForMultipleObjectsEx(2, h, FALSE, INFINITE, FALSE)) { | |
| 15 case WAIT_OBJECT_0: | |
| 16 break; // and enter | |
| 17 case WAIT_OBJECT_0 + 1: | |
| 18 throw exception_aborted(); | |
| 19 default: | |
| 20 uBugCheck(); | |
| 21 } | |
| 22 } | |
| 23 mutexScope::~mutexScope() { | |
| 24 ReleaseMutex(hMutex); | |
| 25 } | |
| 26 | |
| 27 CMutex::CMutex(const TCHAR * name) { | |
| 28 WIN32_OP_CRITICAL("CreateMutex", m_hMutex = CreateMutex(NULL, FALSE, name)); | |
| 29 } | |
| 30 CMutex::~CMutex() { | |
| 31 CloseHandle(m_hMutex); | |
| 32 } | |
| 33 | |
| 34 void CMutex::AcquireByHandle(HANDLE hMutex, abort_callback & aborter) { | |
| 35 SetLastError(0); | |
| 36 HANDLE hWait[2] = { hMutex, aborter.get_abort_event() }; | |
| 37 switch (WaitForMultipleObjects(2, hWait, FALSE, INFINITE)) { | |
| 38 case WAIT_FAILED: | |
| 39 WIN32_OP_FAIL_CRITICAL("WaitForSingleObject"); | |
| 40 case WAIT_OBJECT_0: | |
| 41 return; | |
| 42 case WAIT_OBJECT_0 + 1: | |
| 43 PFC_ASSERT(aborter.is_aborting()); | |
| 44 throw exception_aborted(); | |
| 45 default: | |
| 46 uBugCheck(); | |
| 47 } | |
| 48 } | |
| 49 | |
| 50 void CMutex::Acquire(abort_callback& aborter) { | |
| 51 AcquireByHandle(Handle(), aborter); | |
| 52 } | |
| 53 | |
| 54 void CMutex::Release() { | |
| 55 ReleaseMutex(Handle()); | |
| 56 } | |
| 57 | |
| 58 | |
| 59 CMutexScope::CMutexScope(CMutex & mutex, DWORD timeOutMS, const char * timeOutBugMsg) : m_mutex(mutex) { | |
| 60 SetLastError(0); | |
| 61 const unsigned div = 4; | |
| 62 for (unsigned walk = 0; walk < div; ++walk) { | |
| 63 switch (WaitForSingleObject(m_mutex.Handle(), timeOutMS / div)) { | |
| 64 case WAIT_FAILED: | |
| 65 WIN32_OP_FAIL_CRITICAL("WaitForSingleObject"); | |
| 66 case WAIT_OBJECT_0: | |
| 67 return; | |
| 68 case WAIT_TIMEOUT: | |
| 69 break; | |
| 70 default: | |
| 71 uBugCheck(); | |
| 72 } | |
| 73 } | |
| 74 TRACK_CODE(timeOutBugMsg, uBugCheck()); | |
| 75 } | |
| 76 | |
| 77 CMutexScope::CMutexScope(CMutex & mutex) : m_mutex(mutex) { | |
| 78 SetLastError(0); | |
| 79 switch (WaitForSingleObject(m_mutex.Handle(), INFINITE)) { | |
| 80 case WAIT_FAILED: | |
| 81 WIN32_OP_FAIL_CRITICAL("WaitForSingleObject"); | |
| 82 case WAIT_OBJECT_0: | |
| 83 return; | |
| 84 default: | |
| 85 uBugCheck(); | |
| 86 } | |
| 87 } | |
| 88 | |
| 89 CMutexScope::CMutexScope(CMutex & mutex, abort_callback & aborter) : m_mutex(mutex) { | |
| 90 mutex.Acquire(aborter); | |
| 91 } | |
| 92 | |
| 93 CMutexScope::~CMutexScope() { | |
| 94 ReleaseMutex(m_mutex.Handle()); | |
| 95 } | |
| 96 | |
| 97 #endif | |
| 98 | |
| 99 #ifdef FOOBAR2000_DESKTOP_WINDOWS | |
| 100 | |
| 101 void registerclass_scope_delayed::toggle_on(UINT p_style,WNDPROC p_wndproc,int p_clsextra,int p_wndextra,HICON p_icon,HCURSOR p_cursor,HBRUSH p_background,const TCHAR * p_class_name,const TCHAR * p_menu_name) { | |
| 102 toggle_off(); | |
| 103 WNDCLASS wc = {}; | |
| 104 wc.style = p_style; | |
| 105 wc.lpfnWndProc = p_wndproc; | |
| 106 wc.cbClsExtra = p_clsextra; | |
| 107 wc.cbWndExtra = p_wndextra; | |
| 108 wc.hInstance = core_api::get_my_instance(); | |
| 109 wc.hIcon = p_icon; | |
| 110 wc.hCursor = p_cursor; | |
| 111 wc.hbrBackground = p_background; | |
| 112 wc.lpszMenuName = p_menu_name; | |
| 113 wc.lpszClassName = p_class_name; | |
| 114 WIN32_OP_CRITICAL("RegisterClass", (m_class = RegisterClass(&wc)) != 0); | |
| 115 } | |
| 116 | |
| 117 void registerclass_scope_delayed::toggle_off() { | |
| 118 if (m_class != 0) { | |
| 119 UnregisterClass((LPCTSTR)m_class,core_api::get_my_instance()); | |
| 120 m_class = 0; | |
| 121 } | |
| 122 } | |
| 123 | |
| 124 void CModelessDialogEntry::Set(HWND p_new) { | |
| 125 auto api = modeless_dialog_manager::get(); | |
| 126 if (m_wnd) api->remove(m_wnd); | |
| 127 m_wnd = p_new; | |
| 128 if (m_wnd) api->add(m_wnd); | |
| 129 } | |
| 130 | |
| 131 OleInitializeScope::OleInitializeScope() { | |
| 132 if (FAILED(OleInitialize(NULL))) throw pfc::exception("OleInitialize() failure"); | |
| 133 } | |
| 134 OleInitializeScope::~OleInitializeScope() { | |
| 135 OleUninitialize(); | |
| 136 } | |
| 137 | |
| 138 CoInitializeScope::CoInitializeScope() { | |
| 139 if (FAILED(CoInitialize(NULL))) throw pfc::exception("CoInitialize() failed"); | |
| 140 } | |
| 141 CoInitializeScope::CoInitializeScope(DWORD params) { | |
| 142 if (FAILED(CoInitializeEx(NULL, params))) throw pfc::exception("CoInitialize() failed"); | |
| 143 } | |
| 144 CoInitializeScope::~CoInitializeScope() { | |
| 145 CoUninitialize(); | |
| 146 } | |
| 147 | |
| 148 void winLocalFileScope::open(const char * inPath, file::ptr inReader, abort_callback & aborter) { | |
| 149 close(); | |
| 150 if (inPath != nullptr) { | |
| 151 if (_extract_native_path_ptr(inPath)) { | |
| 152 pfc::string8 prefixed; | |
| 153 pfc::winPrefixPath(prefixed, inPath); | |
| 154 m_path = pfc::stringcvt::string_wide_from_utf8(prefixed); | |
| 155 m_isTemp = false; | |
| 156 return; | |
| 157 } | |
| 158 } | |
| 159 | |
| 160 pfc::string8 tempPath; tempPath.prealloc(1024); | |
| 161 if (!uGetTempPath(tempPath)) uBugCheck(); | |
| 162 tempPath.add_filename(PFC_string_formatter() << pfc::print_guid(pfc::createGUID()) ); | |
| 163 if ( inPath != nullptr ) { | |
| 164 auto ext = pfc::string_extension(inPath); | |
| 165 if (ext.length() > 0) tempPath << "." << ext; | |
| 166 } | |
| 167 | |
| 168 m_path = pfc::stringcvt::string_wide_from_utf8(tempPath); | |
| 169 | |
| 170 if (inReader.is_empty()) { | |
| 171 if (inPath == NULL) uBugCheck(); | |
| 172 inReader = fileOpenReadExisting(inPath, aborter, 1.0); | |
| 173 } | |
| 174 | |
| 175 file::ptr writer = fileOpenWriteNew(PFC_string_formatter() << "file://" << tempPath, aborter, 1.0); | |
| 176 file::g_transfer_file(inReader, writer, aborter); | |
| 177 m_isTemp = true; | |
| 178 } | |
| 179 void winLocalFileScope::close() { | |
| 180 if (m_isTemp && m_path.length() > 0) { | |
| 181 pfc::lores_timer timer; | |
| 182 timer.start(); | |
| 183 for (;;) { | |
| 184 if (DeleteFile(m_path.c_str())) break; | |
| 185 if (timer.query() > 1.0) break; | |
| 186 Sleep(10); | |
| 187 } | |
| 188 } | |
| 189 m_path.clear(); | |
| 190 } | |
| 191 | |
| 192 bool IsWindowsS() { | |
| 193 bool ret = false; | |
| 194 #if FB2K_TARGET_MICROSOFT_STORE | |
| 195 static bool cached = false; | |
| 196 static bool inited = false; | |
| 197 if ( inited ) { | |
| 198 ret = cached; | |
| 199 } else { | |
| 200 HKEY key; | |
| 201 if (RegOpenKey(HKEY_LOCAL_MACHINE, L"SYSTEM\\CurrentControlSet\\Control\\CI\\Policy", &key) == 0) { | |
| 202 DWORD dwVal = 0, dwType; | |
| 203 DWORD valSize; | |
| 204 valSize = sizeof(dwVal); | |
| 205 if (RegQueryValueEx(key, L"SkuPolicyRequired", nullptr, &dwType, (LPBYTE)&dwVal, &valSize) == 0) { | |
| 206 if (dwType == REG_DWORD && dwVal != 0) ret = true; | |
| 207 } | |
| 208 RegCloseKey(key); | |
| 209 } | |
| 210 cached = ret; | |
| 211 inited = true; | |
| 212 } | |
| 213 #endif | |
| 214 return ret; | |
| 215 } | |
| 216 | |
| 217 WORD GetOSVersion() { | |
| 218 // wrap libPPUI function | |
| 219 return ::GetOSVersionCode(); | |
| 220 } | |
| 221 #endif // FOOBAR2000_DESKTOP_WINDOWS |
