Main Page | Class Hierarchy | Alphabetical List | Class List | File List | Class Members

CArchMiscWindows.cpp

00001 /*
00002  * synergy -- mouse and keyboard sharing utility
00003  * Copyright (C) 2002 Chris Schoeneman
00004  * 
00005  * This package is free software; you can redistribute it and/or
00006  * modify it under the terms of the GNU General Public License
00007  * found in the file COPYING that should have accompanied this file.
00008  * 
00009  * This package is distributed in the hope that it will be useful,
00010  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012  * GNU General Public License for more details.
00013  */
00014 
00015 #include "CArchMiscWindows.h"
00016 #include "CArchDaemonWindows.h"
00017 
00018 #ifndef ES_SYSTEM_REQUIRED
00019 #define ES_SYSTEM_REQUIRED  ((DWORD)0x00000001)
00020 #endif
00021 #ifndef ES_DISPLAY_REQUIRED
00022 #define ES_DISPLAY_REQUIRED ((DWORD)0x00000002)
00023 #endif
00024 #ifndef ES_CONTINUOUS
00025 #define ES_CONTINUOUS       ((DWORD)0x80000000)
00026 #endif
00027 typedef DWORD EXECUTION_STATE;
00028 
00029 //
00030 // CArchMiscWindows
00031 //
00032 
00033 CArchMiscWindows::CDialogs* CArchMiscWindows::s_dialogs   = NULL;
00034 DWORD                       CArchMiscWindows::s_busyState = 0;
00035 CArchMiscWindows::STES_t    CArchMiscWindows::s_stes      = NULL;
00036 HICON                       CArchMiscWindows::s_largeIcon = NULL;
00037 HICON                       CArchMiscWindows::s_smallIcon = NULL;
00038 
00039 void
00040 CArchMiscWindows::init()
00041 {
00042     s_dialogs = new CDialogs;
00043     isWindows95Family();
00044 }
00045 
00046 bool
00047 CArchMiscWindows::isWindows95Family()
00048 {
00049     static bool init   = false;
00050     static bool result = false;
00051 
00052     if (!init) {
00053         OSVERSIONINFO version;
00054         version.dwOSVersionInfoSize = sizeof(version);
00055         if (GetVersionEx(&version) == 0) {
00056             // cannot determine OS;  assume windows 95 family
00057             result = true;
00058         }
00059         else {
00060             result = (version.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS);
00061         }
00062         init = true;
00063     }
00064     return result;
00065 }
00066 
00067 bool
00068 CArchMiscWindows::isWindowsModern()
00069 {
00070     static bool init   = false;
00071     static bool result = false;
00072 
00073     if (!init) {
00074         OSVERSIONINFO version;
00075         version.dwOSVersionInfoSize = sizeof(version);
00076         if (GetVersionEx(&version) == 0) {
00077             // cannot determine OS;  assume not modern
00078             result = false;
00079         }
00080         else {
00081             result = ((version.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS &&
00082                         version.dwMajorVersion == 4 &&
00083                         version.dwMinorVersion > 0) ||
00084                         (version.dwPlatformId == VER_PLATFORM_WIN32_NT &&
00085                         version.dwMajorVersion > 4));
00086         }
00087         init = true;
00088     }
00089     return result;
00090 }
00091 
00092 void
00093 CArchMiscWindows::setIcons(HICON largeIcon, HICON smallIcon)
00094 {
00095     s_largeIcon = largeIcon;
00096     s_smallIcon = smallIcon;
00097 }
00098 
00099 void
00100 CArchMiscWindows::getIcons(HICON& largeIcon, HICON& smallIcon)
00101 {
00102     largeIcon = s_largeIcon;
00103     smallIcon = s_smallIcon;
00104 }
00105 
00106 int
00107 CArchMiscWindows::runDaemon(RunFunc runFunc)
00108 {
00109     return CArchDaemonWindows::runDaemon(runFunc);
00110 }
00111 
00112 void
00113 CArchMiscWindows::daemonRunning(bool running)
00114 {
00115     CArchDaemonWindows::daemonRunning(running);
00116 }
00117 
00118 void
00119 CArchMiscWindows::daemonFailed(int result)
00120 {
00121     CArchDaemonWindows::daemonFailed(result);
00122 }
00123 
00124 UINT
00125 CArchMiscWindows::getDaemonQuitMessage()
00126 {
00127     return CArchDaemonWindows::getDaemonQuitMessage();
00128 }
00129 
00130 HKEY
00131 CArchMiscWindows::openKey(HKEY key, const TCHAR* keyName)
00132 {
00133     return openKey(key, keyName, false);
00134 }
00135 
00136 HKEY
00137 CArchMiscWindows::openKey(HKEY key, const TCHAR* const* keyNames)
00138 {
00139     return openKey(key, keyNames, false);
00140 }
00141 
00142 HKEY
00143 CArchMiscWindows::addKey(HKEY key, const TCHAR* keyName)
00144 {
00145     return openKey(key, keyName, true);
00146 }
00147 
00148 HKEY
00149 CArchMiscWindows::addKey(HKEY key, const TCHAR* const* keyNames)
00150 {
00151     return openKey(key, keyNames, true);
00152 }
00153 
00154 HKEY
00155 CArchMiscWindows::openKey(HKEY key, const TCHAR* keyName, bool create)
00156 {
00157     // ignore if parent is NULL
00158     if (key == NULL) {
00159         return NULL;
00160     }
00161 
00162     // open next key
00163     HKEY newKey;
00164     LONG result = RegOpenKeyEx(key, keyName, 0,
00165                                 KEY_WRITE | KEY_QUERY_VALUE, &newKey);
00166     if (result != ERROR_SUCCESS && create) {
00167         DWORD disp;
00168         result = RegCreateKeyEx(key, keyName, 0, TEXT(""),
00169                                 0, KEY_WRITE | KEY_QUERY_VALUE,
00170                                 NULL, &newKey, &disp);
00171     }
00172     if (result != ERROR_SUCCESS) {
00173         RegCloseKey(key);
00174         return NULL;
00175     }
00176 
00177     // switch to new key
00178     RegCloseKey(key);
00179     return newKey;
00180 }
00181 
00182 HKEY
00183 CArchMiscWindows::openKey(HKEY key, const TCHAR* const* keyNames, bool create)
00184 {
00185     for (size_t i = 0; key != NULL && keyNames[i] != NULL; ++i) {
00186         // open next key
00187         key = openKey(key, keyNames[i], create);
00188     }
00189     return key;
00190 }
00191 
00192 void
00193 CArchMiscWindows::closeKey(HKEY key)
00194 {
00195     assert(key  != NULL);
00196     RegCloseKey(key);
00197 }
00198 
00199 void
00200 CArchMiscWindows::deleteKey(HKEY key, const TCHAR* name)
00201 {
00202     assert(key  != NULL);
00203     assert(name != NULL);
00204     RegDeleteKey(key, name);
00205 }
00206 
00207 void
00208 CArchMiscWindows::deleteValue(HKEY key, const TCHAR* name)
00209 {
00210     assert(key  != NULL);
00211     assert(name != NULL);
00212     RegDeleteValue(key, name);
00213 }
00214 
00215 bool
00216 CArchMiscWindows::hasValue(HKEY key, const TCHAR* name)
00217 {
00218     DWORD type;
00219     LONG result = RegQueryValueEx(key, name, 0, &type, NULL, NULL);
00220     return (result == ERROR_SUCCESS &&
00221             (type == REG_DWORD || type == REG_SZ));
00222 }
00223 
00224 CArchMiscWindows::EValueType
00225 CArchMiscWindows::typeOfValue(HKEY key, const TCHAR* name)
00226 {
00227     DWORD type;
00228     LONG result = RegQueryValueEx(key, name, 0, &type, NULL, NULL);
00229     if (result != ERROR_SUCCESS) {
00230         return kNO_VALUE;
00231     }
00232     switch (type) {
00233     case REG_DWORD:
00234         return kUINT;
00235 
00236     case REG_SZ:
00237         return kSTRING;
00238 
00239     case REG_BINARY:
00240         return kBINARY;
00241 
00242     default:
00243         return kUNKNOWN;
00244     }
00245 }
00246 
00247 void
00248 CArchMiscWindows::setValue(HKEY key,
00249                 const TCHAR* name, const std::string& value)
00250 {
00251     assert(key  != NULL);
00252     assert(name != NULL);
00253     RegSetValueEx(key, name, 0, REG_SZ,
00254                                 reinterpret_cast<const BYTE*>(value.c_str()),
00255                                 value.size() + 1);
00256 }
00257 
00258 void
00259 CArchMiscWindows::setValue(HKEY key, const TCHAR* name, DWORD value)
00260 {
00261     assert(key  != NULL);
00262     assert(name != NULL);
00263     RegSetValueEx(key, name, 0, REG_DWORD,
00264                                 reinterpret_cast<CONST BYTE*>(&value),
00265                                 sizeof(DWORD));
00266 }
00267 
00268 void
00269 CArchMiscWindows::setValueBinary(HKEY key,
00270                 const TCHAR* name, const std::string& value)
00271 {
00272     assert(key  != NULL);
00273     assert(name != NULL);
00274     RegSetValueEx(key, name, 0, REG_BINARY,
00275                                 reinterpret_cast<const BYTE*>(value.data()),
00276                                 value.size());
00277 }
00278 
00279 std::string
00280 CArchMiscWindows::readBinaryOrString(HKEY key, const TCHAR* name, DWORD type)
00281 {
00282     // get the size of the string
00283     DWORD actualType;
00284     DWORD size = 0;
00285     LONG result = RegQueryValueEx(key, name, 0, &actualType, NULL, &size);
00286     if (result != ERROR_SUCCESS || actualType != type) {
00287         return std::string();
00288     }
00289 
00290     // if zero size then return empty string
00291     if (size == 0) {
00292         return std::string();
00293     }
00294 
00295     // allocate space
00296     char* buffer = new char[size];
00297 
00298     // read it
00299     result = RegQueryValueEx(key, name, 0, &actualType,
00300                                 reinterpret_cast<BYTE*>(buffer), &size);
00301     if (result != ERROR_SUCCESS || actualType != type) {
00302         delete[] buffer;
00303         return std::string();
00304     }
00305 
00306     // clean up and return value
00307     if (type == REG_SZ && buffer[size - 1] == '\0') {
00308         // don't include terminating nul;  std::string will add one.
00309         --size;
00310     }
00311     std::string value(buffer, size);
00312     delete[] buffer;
00313     return value;
00314 }
00315 
00316 std::string
00317 CArchMiscWindows::readValueString(HKEY key, const TCHAR* name)
00318 {
00319     return readBinaryOrString(key, name, REG_SZ);
00320 }
00321 
00322 std::string
00323 CArchMiscWindows::readValueBinary(HKEY key, const TCHAR* name)
00324 {
00325     return readBinaryOrString(key, name, REG_BINARY);
00326 }
00327 
00328 DWORD
00329 CArchMiscWindows::readValueInt(HKEY key, const TCHAR* name)
00330 {
00331     DWORD type;
00332     DWORD value;
00333     DWORD size = sizeof(value);
00334     LONG result = RegQueryValueEx(key, name, 0, &type,
00335                                 reinterpret_cast<BYTE*>(&value), &size);
00336     if (result != ERROR_SUCCESS || type != REG_DWORD) {
00337         return 0;
00338     }
00339     return value;
00340 }
00341 
00342 void
00343 CArchMiscWindows::addDialog(HWND hwnd)
00344 {
00345     s_dialogs->insert(hwnd);
00346 }
00347 
00348 void
00349 CArchMiscWindows::removeDialog(HWND hwnd)
00350 {
00351     s_dialogs->erase(hwnd);
00352 }
00353 
00354 bool
00355 CArchMiscWindows::processDialog(MSG* msg)
00356 {
00357     for (CDialogs::const_iterator index = s_dialogs->begin();
00358                             index != s_dialogs->end(); ++index) {
00359         if (IsDialogMessage(*index, msg)) {
00360             return true;
00361         }
00362     }
00363     return false;
00364 }
00365 
00366 void
00367 CArchMiscWindows::addBusyState(DWORD busyModes)
00368 {
00369     s_busyState |= busyModes;
00370     setThreadExecutionState(s_busyState);
00371 }
00372 
00373 void
00374 CArchMiscWindows::removeBusyState(DWORD busyModes)
00375 {
00376     s_busyState &= ~busyModes;
00377     setThreadExecutionState(s_busyState);
00378 }
00379 
00380 void
00381 CArchMiscWindows::setThreadExecutionState(DWORD busyModes)
00382 {
00383     // look up function dynamically so we work on older systems
00384     if (s_stes == NULL) {
00385         HINSTANCE kernel = LoadLibrary("kernel32.dll");
00386         if (kernel != NULL) {
00387             s_stes = reinterpret_cast<STES_t>(GetProcAddress(kernel,
00388                             "SetThreadExecutionState"));
00389         }
00390         if (s_stes == NULL) {
00391             s_stes = &CArchMiscWindows::dummySetThreadExecutionState;
00392         }
00393     }
00394 
00395     // convert to STES form
00396     EXECUTION_STATE state = 0;
00397     if ((busyModes & kSYSTEM) != 0) {
00398         state |= ES_SYSTEM_REQUIRED;
00399     }
00400     if ((busyModes & kDISPLAY) != 0) {
00401         state |= ES_DISPLAY_REQUIRED;
00402     }
00403     if (state != 0) {
00404         state |= ES_CONTINUOUS;
00405     }
00406 
00407     // do it
00408     s_stes(state);
00409 }
00410 
00411 DWORD
00412 CArchMiscWindows::dummySetThreadExecutionState(DWORD)
00413 {
00414     // do nothing
00415     return 0;
00416 }
00417 
00418 void
00419 CArchMiscWindows::wakeupDisplay()
00420 {
00421     // We can't use ::setThreadExecutionState here because it sets
00422     // ES_CONTINUOUS, which we don't want.
00423 
00424     if (s_stes == NULL) {
00425         HINSTANCE kernel = LoadLibrary("kernel32.dll");
00426         if (kernel != NULL) {
00427             s_stes = reinterpret_cast<STES_t>(GetProcAddress(kernel,
00428                             "SetThreadExecutionState"));
00429         }
00430         if (s_stes == NULL) {
00431             s_stes = &CArchMiscWindows::dummySetThreadExecutionState;
00432         }
00433     }
00434 
00435     s_stes(ES_DISPLAY_REQUIRED);
00436 
00437     // restore the original execution states
00438     setThreadExecutionState(s_busyState);
00439 }

Generated on Fri Nov 6 00:21:13 2009 for synergy-plus by  doxygen 1.3.9.1