Changeset 3055
- Timestamp:
- 19/01/2012 18:27:44 (4 months ago)
- Location:
- box/invisnet/vs2010/0.11
- Files:
-
- 23 added
- 1 deleted
- 22 edited
-
bin/bbackupd/BackupClientDirectoryRecord.cpp (modified) (1 diff)
-
bin/bbackupd/Win32ServiceFunctions.cpp (modified) (3 diffs)
-
bin/bbackupd/bbackupd.cpp (modified) (1 diff)
-
bin/bbackupquery/bbackupquery.cpp (modified) (3 diffs)
-
lib/backupclient/BackupClientFileAttributes.cpp (modified) (1 diff)
-
lib/backupclient/BackupClientRestore.cpp (modified) (1 diff)
-
lib/common/Box.h (modified) (1 diff)
-
lib/common/BoxConfig-MSVC.h (modified) (1 diff)
-
lib/common/BoxPlatform.h (modified) (2 diffs)
-
lib/common/FileStream.cpp (modified) (1 diff)
-
lib/common/Logging.cpp (modified) (1 diff)
-
lib/common/Logging.h (modified) (2 diffs)
-
lib/common/Timer.cpp (modified) (2 diffs)
-
lib/common/WaitForEvent.cpp (modified) (1 diff)
-
lib/server/Daemon.cpp (modified) (1 diff)
-
lib/server/LocalProcessStream.cpp (modified) (2 diffs)
-
lib/server/SocketStream.cpp (modified) (2 diffs)
-
lib/server/SocketStreamTLS.cpp (modified) (1 diff)
-
lib/server/WinNamedPipeStream.cpp (modified) (1 diff)
-
lib/win32/Win32BaseException.txt (added)
-
lib/win32/_sys (added)
-
lib/win32/_sys/_iovec.h (added)
-
lib/win32/_sys/mount.cpp (added)
-
lib/win32/_sys/mount.h (added)
-
lib/win32/_sys/resource.cpp (added)
-
lib/win32/_sys/resource.h (added)
-
lib/win32/_sys/stat.cpp (added)
-
lib/win32/_sys/stat.h (added)
-
lib/win32/_sys/time.cpp (added)
-
lib/win32/_sys/time.h (added)
-
lib/win32/_sys/uio.cpp (added)
-
lib/win32/_sys/uio.h (added)
-
lib/win32/dirent.cpp (added)
-
lib/win32/dirent.h (added)
-
lib/win32/emu.cpp (modified) (2 diffs)
-
lib/win32/emu.h (modified) (9 diffs)
-
lib/win32/getopt.h (modified) (1 diff)
-
lib/win32/pch.cpp (deleted)
-
lib/win32/poll.cpp (added)
-
lib/win32/poll.h (added)
-
lib/win32/pwd.cpp (added)
-
lib/win32/pwd.h (added)
-
lib/win32/unistd.cpp (added)
-
lib/win32/unistd.h (added)
-
lib/win32/win32.cpp (added)
-
lib/win32/win32.h (added)
Legend:
- Unmodified
- Added
- Removed
-
box/invisnet/vs2010/0.11/bin/bbackupd/BackupClientDirectoryRecord.cpp
r2714 r3055 291 291 // DT_DIR, etc, but we only use it here and 292 292 // prefer S_IFREG, S_IFDIR... 293 int type = en->d_type; 293 int type = 0; 294 type = (DT_DIR == en->d_type) ? S_IFDIR : type; 295 type = (DT_REG == en->d_type) ? S_IFREG : type; 294 296 #else 295 297 if(EMU_LSTAT(filename.c_str(), &file_st) != 0) -
box/invisnet/vs2010/0.11/bin/bbackupd/Win32ServiceFunctions.cpp
r2771 r3055 22 22 #endif 23 23 24 using namespace Win32; 25 24 26 extern void TerminateService(void); 25 27 extern unsigned int WINAPI RunService(LPVOID lpParameter); … … 101 103 { 102 104 // initialise service status 103 gServiceStatus.dwServiceType = SERVICE_WIN32 ;105 gServiceStatus.dwServiceType = SERVICE_WIN32_OWN_PROCESS; 104 106 gServiceStatus.dwCurrentState = SERVICE_STOPPED; 105 107 gServiceStatus.dwControlsAccepted = 0; … … 191 193 if (!success) 192 194 { 193 ErrorHandler("Failed to start service. Did you start "194 "Box Backup from the Service Control Manager? "195 "(StartServiceCtrlDispatcher)", GetLastError());195 // ErrorHandler("Failed to start service. Did you start " 196 // "Box Backup from the Service Control Manager? " 197 // "(StartServiceCtrlDispatcher)", GetLastError()); 196 198 return 1; 197 199 } -
box/invisnet/vs2010/0.11/bin/bbackupd/bbackupd.cpp
r2180 r3055 36 36 #ifdef WIN32 37 37 38 EnableBackupRights();38 Win32::EnableBackupRights(); 39 39 40 40 gpDaemonService = new Win32BackupService(); -
box/invisnet/vs2010/0.11/bin/bbackupquery/bbackupquery.cpp
r2663 r3055 59 59 #include "MemLeakFindOn.h" 60 60 61 #ifdef WIN32 62 using namespace Win32; 63 #endif 64 61 65 void PrintUsageAndExit() 62 66 { … … 293 297 return 1; 294 298 } 299 #ifdef WIN32 300 char path[MAX_PATH]; 301 302 if(FAILED(SHGetFolderPath(NULL,CSIDL_COMMON_APPDATA,NULL,0,path)) || !PathAppend(path,"Box Backup")) 303 { 304 BOX_FATAL("Can't build DataDirectory"); 305 return 1; 306 } 307 308 config->AddKeyValue("DataDirectory",path); 309 #endif 295 310 // Easier coding 296 311 const Configuration &conf(*config); … … 301 316 // Read in the certificates creating a TLS context 302 317 TLSContext tlsContext; 318 #ifdef WIN32 319 std::string certFile(conf.GetKeyValue("AccountNumber")); 320 std::string keyFile; 321 std::string caFile; 322 std::string keysFile; 323 #else 303 324 std::string certFile(conf.GetKeyValue("CertificateFile")); 304 325 std::string keyFile(conf.GetKeyValue("PrivateKeyFile")); 305 326 std::string caFile(conf.GetKeyValue("TrustedCAsFile")); 327 std::string keysFile(conf.GetKeyValue("KeysFile")); 328 #endif 306 329 tlsContext.Initialise(false /* as client */, certFile.c_str(), keyFile.c_str(), caFile.c_str()); 307 330 308 331 // Initialise keys 309 BackupClientCryptoKeys_Setup( conf.GetKeyValue("KeysFile").c_str());332 BackupClientCryptoKeys_Setup(keysFile.c_str()); 310 333 311 334 // 2. Connect to server -
box/invisnet/vs2010/0.11/lib/backupclient/BackupClientFileAttributes.cpp
r2811 r3055 844 844 845 845 // Try to apply 846 if( ::utimes(Filename, times) != 0)846 if(EMU_UTIMES(Filename, times) != 0) 847 847 { 848 848 BOX_LOG_SYS_ERROR("Failed to change times of " -
box/invisnet/vs2010/0.11/lib/backupclient/BackupClientRestore.cpp
r2813 r3055 386 386 if((exists == ObjectExists_NoObject || 387 387 exists == ObjectExists_File) && 388 ::mkdir(rLocalDirectoryName.c_str(), S_IRWXU) != 0)388 EMU_MKDIR(rLocalDirectoryName.c_str(), S_IRWXU) != 0) 389 389 { 390 390 BOX_LOG_SYS_ERROR("Failed to create directory '" << -
box/invisnet/vs2010/0.11/lib/common/Box.h
r2663 r3055 182 182 inline int8_t ntoh(int8_t in) { return in; } 183 183 184 using namespace BoxBackup; 185 184 186 #endif // BOX__H 185 187 -
box/invisnet/vs2010/0.11/lib/common/BoxConfig-MSVC.h
r2067 r3055 204 204 205 205 /* Define to 1 if you have the <stdint.h> header file. */ 206 //#define HAVE_STDINT_H 1206 #define HAVE_STDINT_H 1 207 207 208 208 /* Define to 1 if you have the <stdlib.h> header file. */ -
box/invisnet/vs2010/0.11/lib/common/BoxPlatform.h
r2801 r3055 121 121 #endif 122 122 123 #if defined WIN32 && !defined __MINGW32__124 typedef __int8 int8_t;125 typedef __int16 int16_t;126 typedef __int32 int32_t;127 typedef __int64 int64_t;128 129 typedef unsigned __int8 u_int8_t;130 typedef unsigned __int16 u_int16_t;131 typedef unsigned __int32 u_int32_t;132 typedef unsigned __int64 u_int64_t;133 134 #define HAVE_U_INT8_T135 #define HAVE_U_INT16_T136 #define HAVE_U_INT32_T137 #define HAVE_U_INT64_T138 #endif // WIN32 && !__MINGW32__139 140 123 // Define missing types 141 124 #ifndef HAVE_UINT8_T … … 181 164 #endif 182 165 183 #ifdef WIN32184 #define WIN32_LEAN_AND_MEAN185 #endif186 187 166 #include "emu.h" 188 167 -
box/invisnet/vs2010/0.11/lib/common/FileStream.cpp
r2792 r3055 68 68 MEMLEAKFINDER_NOT_A_LEAK(this); 69 69 70 #ifdef WIN32 71 BOX_LOG_WIN_WARNING_NUMBER("Failed to open file: " << 72 mFileName, winerrno); 73 #else 70 #ifndef WIN32 74 71 BOX_LOG_SYS_WARNING("Failed to open file: " << 75 72 mFileName); -
box/invisnet/vs2010/0.11/lib/common/Logging.cpp
r2663 r3055 17 17 #include <cstdio> 18 18 19 #ifdef HAVE_PROCESS_H 20 #include <process.h> 21 #endif 19 22 #ifdef HAVE_SYSLOG_H 20 23 #include <syslog.h> -
box/invisnet/vs2010/0.11/lib/common/Logging.h
r2663 r3055 60 60 { 61 61 #ifdef WIN32 62 return GetErrorMessage(GetLastError());62 return BoxBackup::Win32::GetErrorMessage(GetLastError()); 63 63 #else 64 64 std::ostringstream _box_log_line; … … 70 70 #ifdef WIN32 71 71 #define BOX_LOG_WIN_ERROR(stuff) \ 72 BOX_ERROR(stuff << ": " << GetErrorMessage(GetLastError()))72 BOX_ERROR(stuff << ": " << Win32::GetErrorMessage(GetLastError())) 73 73 #define BOX_LOG_WIN_WARNING(stuff) \ 74 BOX_WARNING(stuff << ": " << GetErrorMessage(GetLastError()))74 BOX_WARNING(stuff << ": " << Win32::GetErrorMessage(GetLastError())) 75 75 #define BOX_LOG_WIN_ERROR_NUMBER(stuff, number) \ 76 BOX_ERROR(stuff << ": " << GetErrorMessage(number))76 BOX_ERROR(stuff << ": " << Win32::GetErrorMessage(number)) 77 77 #define BOX_LOG_WIN_WARNING_NUMBER(stuff, number) \ 78 BOX_WARNING(stuff << ": " << GetErrorMessage(number))78 BOX_WARNING(stuff << ": " << Win32::GetErrorMessage(number)) 79 79 #define BOX_LOG_NATIVE_ERROR(stuff) BOX_LOG_WIN_ERROR(stuff) 80 80 #define BOX_LOG_NATIVE_WARNING(stuff) BOX_LOG_WIN_WARNING(stuff) -
box/invisnet/vs2010/0.11/lib/common/Timer.cpp
r2767 r3055 429 429 == FALSE) 430 430 { 431 BOX_ERROR(TIMER_ID "failed to create timer: " << 432 GetErrorMessage(GetLastError())); 431 BOX_LOG_WIN_ERROR(TIMER_ID "failed to create timer"); 433 432 mTimerHandle = INVALID_HANDLE_VALUE; 434 433 } … … 455 454 INVALID_HANDLE_VALUE) == FALSE) 456 455 { 457 BOX_ERROR(TIMER_ID "failed to delete timer: " << 458 GetErrorMessage(GetLastError())); 456 BOX_LOG_WIN_ERROR(TIMER_ID "failed to delete timer"); 459 457 } 460 458 mTimerHandle = INVALID_HANDLE_VALUE; -
box/invisnet/vs2010/0.11/lib/common/WaitForEvent.cpp
r456 r3055 164 164 165 165 // Poll! 166 switch( ::poll(mpPollInfo, mItems.size(), mTimeout))166 switch(EMU_POLL(mpPollInfo, mItems.size(), mTimeout)) 167 167 { 168 168 case -1: -
box/invisnet/vs2010/0.11/lib/server/Daemon.cpp
r2500 r3055 10 10 #include "Box.h" 11 11 12 #ifdef HAVE_PROCESS_H 13 #include <process.h> 14 #endif 12 15 #ifdef HAVE_UNISTD_H 13 16 #include <unistd.h> -
box/invisnet/vs2010/0.11/lib/server/LocalProcessStream.cpp
r2659 r3055 122 122 if(!CreatePipe(&readFromChild, &writeInChild, &secAttr, 0)) 123 123 { 124 BOX_ERROR("Failed to CreatePipe for child process: " << 125 GetErrorMessage(GetLastError())); 124 BOX_LOG_WIN_ERROR("Failed to CreatePipe for child process"); 126 125 THROW_EXCEPTION(ServerException, SocketPairFailed) 127 126 } … … 157 156 if(!result) 158 157 { 159 BOX_ERROR("Failed to CreateProcess: '" << rCommandLine << 160 "': " << GetErrorMessage(GetLastError())); 158 BOX_LOG_WIN_ERROR("Failed to CreateProcess: '" << rCommandLine); 161 159 CloseHandle(writeInChild); 162 160 CloseHandle(readFromChild); -
box/invisnet/vs2010/0.11/lib/server/SocketStream.cpp
r2451 r3055 214 214 p.events = POLLIN; 215 215 p.revents = 0; 216 switch( ::poll(&p, 1, (Timeout == IOStream::TimeOutInfinite)?INFTIM:Timeout))216 switch(EMU_POLL(&p, 1, (Timeout == IOStream::TimeOutInfinite)?INFTIM:Timeout)) 217 217 { 218 218 case -1: … … 333 333 p.revents = 0; 334 334 335 if( ::poll(&p, 1, 16000 /* 16 seconds */) == -1)335 if(EMU_POLL(&p, 1, 16000 /* 16 seconds */) == -1) 336 336 { 337 337 // Don't exception if it's just a signal -
box/invisnet/vs2010/0.11/lib/server/SocketStreamTLS.cpp
r2792 r3055 262 262 poll_timeout = INFTIM; 263 263 } 264 result = ::poll(&p, 1, poll_timeout);264 result = EMU_POLL(&p, 1, poll_timeout); 265 265 } 266 266 while(result == -1 && errno == EINTR); -
box/invisnet/vs2010/0.11/lib/server/WinNamedPipeStream.cpp
r2792 r3055 26 26 27 27 #include "MemLeakFindOn.h" 28 29 using namespace Win32; 28 30 29 31 std::string WinNamedPipeStream::sPipeNamePrefix = "\\\\.\\pipe\\"; -
box/invisnet/vs2010/0.11/lib/win32/emu.cpp
r2790 r3055 1 // Box Backup Win32 native port by Nick Knight 1 #include "Box.h" 2 2 3 // Need at least 0x0500 to use GetFileSizeEx on Cygwin/MinGW 4 #define WINVER 0x0500 3 #include <cstdio> 5 4 6 #include "emu.h"7 5 8 #ifdef WIN32 6 using namespace Win32; 9 7 10 #include <assert.h>11 #include <fcntl.h>12 #include <process.h>13 #include <windows.h>14 #include "Shlobj.h"15 #include "Shlwapi.h"16 8 17 #ifdef HAVE_UNISTD_H18 #include <unistd.h>19 #endif20 21 #include <string>22 #include <list>23 #include <sstream>24 25 // message resource definitions for syslog()26 #include "messages.h"27 28 DWORD winerrno;29 9 struct passwd gTempPasswd; 30 10 31 bool EnableBackupRights()32 {33 HANDLE hToken;34 TOKEN_PRIVILEGES token_priv;35 36 //open current process to adjust privileges37 if(!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES,38 &hToken))39 {40 ::syslog(LOG_ERR, "Failed to open process token: %s",41 GetErrorMessage(GetLastError()).c_str());42 return false;43 }44 45 //let's build the token privilege struct -46 //first, look up the LUID for the backup privilege47 48 if (!LookupPrivilegeValue(49 NULL, //this system50 SE_BACKUP_NAME, //the name of the privilege51 &( token_priv.Privileges[0].Luid ))) //result52 {53 ::syslog(LOG_ERR, "Failed to lookup backup privilege: %s",54 GetErrorMessage(GetLastError()).c_str());55 CloseHandle(hToken);56 return false;57 }58 59 token_priv.PrivilegeCount = 1;60 token_priv.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;61 62 // now set the privilege63 // because we're going exit right after dumping the streams, there isn't64 // any need to save current state65 66 if (!AdjustTokenPrivileges(67 hToken, //our process token68 false, //we're not disabling everything69 &token_priv, //address of structure70 sizeof(token_priv), //size of structure71 NULL, NULL)) //don't save current state72 {73 //this function is a little tricky - if we were adjusting74 //more than one privilege, it could return success but not75 //adjust them all - in the general case, you need to trap this76 ::syslog(LOG_ERR, "Failed to enable backup privilege: %s",77 GetErrorMessage(GetLastError()).c_str());78 CloseHandle(hToken);79 return false;80 81 }82 83 CloseHandle(hToken);84 return true;85 }86 87 // forward declaration88 char* ConvertFromWideString(const WCHAR* pString, unsigned int codepage);89 11 90 12 // -------------------------------------------------------------------------- … … 99 21 // 100 22 // -------------------------------------------------------------------------- 101 std::string GetDefaultConfigFilePath(const std::string& rName) 23 std::string GetDefaultConfigFilePath(const std::string& rName) throw() 102 24 { 103 25 // we just ask the system where to get the file... 104 charpath[MAX_PATH];26 wchar_t path[MAX_PATH]; 105 27 106 if(FAILED(SHGetFolderPath(NULL,CSIDL_COMMON_APPDATA,NULL,0,path)) 107 || FALSE == PathAppend(path,"Box Backup") 108 || FALSE == PathAppend(path,rName.c_str())) 28 try 109 29 { 110 return ""; 111 } 112 113 return std::string(path); 114 } 115 116 // -------------------------------------------------------------------------- 117 // 118 // Function 119 // Name: ConvertToWideString 120 // Purpose: Converts a string from specified codepage to 121 // a wide string (WCHAR*). Returns a buffer which 122 // MUST be freed by the caller with delete[]. 123 // In case of fire, logs the error and returns NULL. 124 // Created: 4th February 2006 125 // 126 // -------------------------------------------------------------------------- 127 WCHAR* ConvertToWideString(const char* pString, unsigned int codepage, 128 bool logErrors) 129 { 130 int len = MultiByteToWideChar 131 ( 132 codepage, // source code page 133 0, // character-type options 134 pString, // string to map 135 -1, // number of bytes in string - auto detect 136 NULL, // wide-character buffer 137 0 // size of buffer - work out 138 // how much space we need 139 ); 140 141 if (len == 0) 142 { 143 winerrno = GetLastError(); 144 if (logErrors) 30 if(SUCCEEDED(SHGetFolderPathW(NULL,CSIDL_COMMON_APPDATA,NULL,0,path)) 31 && PathAppendW(path,L"Box Backup") 32 && PathAppendW(path,multi2wide(rName.c_str()).c_str())) 145 33 { 146 ::syslog(LOG_WARNING, 147 "Failed to convert string to wide string: " 148 "%s", GetErrorMessage(winerrno).c_str()); 149 } 150 errno = EINVAL; 151 return NULL; 152 } 153 154 WCHAR* buffer = new WCHAR[len]; 155 156 if (buffer == NULL) 157 { 158 if (logErrors) 159 { 160 ::syslog(LOG_WARNING, 161 "Failed to convert string to wide string: " 162 "out of memory"); 163 } 164 winerrno = ERROR_OUTOFMEMORY; 165 errno = ENOMEM; 166 return NULL; 167 } 168 169 len = MultiByteToWideChar 170 ( 171 codepage, // source code page 172 0, // character-type options 173 pString, // string to map 174 -1, // number of bytes in string - auto detect 175 buffer, // wide-character buffer 176 len // size of buffer 177 ); 178 179 if (len == 0) 180 { 181 winerrno = GetLastError(); 182 if (logErrors) 183 { 184 ::syslog(LOG_WARNING, 185 "Failed to convert string to wide string: " 186 "%s", GetErrorMessage(winerrno).c_str()); 187 } 188 errno = EACCES; 189 delete [] buffer; 190 return NULL; 191 } 192 193 return buffer; 194 } 195 196 // -------------------------------------------------------------------------- 197 // 198 // Function 199 // Name: ConvertUtf8ToWideString 200 // Purpose: Converts a string from UTF-8 to a wide string. 201 // Returns a buffer which MUST be freed by the caller 202 // with delete[]. 203 // In case of fire, logs the error and returns NULL. 204 // Created: 4th February 2006 205 // 206 // -------------------------------------------------------------------------- 207 WCHAR* ConvertUtf8ToWideString(const char* pString) 208 { 209 return ConvertToWideString(pString, CP_UTF8, true); 210 } 211 212 // -------------------------------------------------------------------------- 213 // 214 // Function 215 // Name: ConvertFromWideString 216 // Purpose: Converts a wide string to a narrow string in the 217 // specified code page. Returns a buffer which MUST 218 // be freed by the caller with delete[]. 219 // In case of fire, logs the error and returns NULL. 220 // Created: 4th February 2006 221 // 222 // -------------------------------------------------------------------------- 223 char* ConvertFromWideString(const WCHAR* pString, unsigned int codepage) 224 { 225 int len = WideCharToMultiByte 226 ( 227 codepage, // destination code page 228 0, // character-type options 229 pString, // string to map 230 -1, // number of bytes in string - auto detect 231 NULL, // output buffer 232 0, // size of buffer - work out 233 // how much space we need 234 NULL, // replace unknown chars with system default 235 NULL // don't tell us when that happened 236 ); 237 238 if (len == 0) 239 { 240 ::syslog(LOG_WARNING, 241 "Failed to convert wide string to narrow: " 242 "error %d", GetLastError()); 243 errno = EINVAL; 244 return NULL; 245 } 246 247 char* buffer = new char[len]; 248 249 if (buffer == NULL) 250 { 251 ::syslog(LOG_WARNING, 252 "Failed to convert wide string to narrow: " 253 "out of memory"); 254 errno = ENOMEM; 255 return NULL; 256 } 257 258 len = WideCharToMultiByte 259 ( 260 codepage, // source code page 261 0, // character-type options 262 pString, // string to map 263 -1, // number of bytes in string - auto detect 264 buffer, // output buffer 265 len, // size of buffer 266 NULL, // replace unknown chars with system default 267 NULL // don't tell us when that happened 268 ); 269 270 if (len == 0) 271 { 272 ::syslog(LOG_WARNING, 273 "Failed to convert wide string to narrow: " 274 "error %i", GetLastError()); 275 errno = EACCES; 276 delete [] buffer; 277 return NULL; 278 } 279 280 return buffer; 281 } 282 283 // -------------------------------------------------------------------------- 284 // 285 // Function 286 // Name: ConvertEncoding(const std::string&, int, 287 // std::string&, int) 288 // Purpose: Converts a string from one code page to another. 289 // On success, replaces contents of rDest and returns 290 // true. In case of fire, logs the error and returns 291 // false. 292 // Created: 15th October 2006 293 // 294 // -------------------------------------------------------------------------- 295 bool ConvertEncoding(const std::string& rSource, int sourceCodePage, 296 std::string& rDest, int destCodePage) 297 { 298 WCHAR* pWide = ConvertToWideString(rSource.c_str(), sourceCodePage, 299 true); 300 if (pWide == NULL) 301 { 302 ::syslog(LOG_ERR, "Failed to convert string '%s' from " 303 "current code page %d to wide string: %s", 304 rSource.c_str(), sourceCodePage, 305 GetErrorMessage(GetLastError()).c_str()); 306 return false; 307 } 308 309 char* pConsole = ConvertFromWideString(pWide, destCodePage); 310 delete [] pWide; 311 312 if (!pConsole) 313 { 314 // Error should have been logged by ConvertFromWideString 315 return false; 316 } 317 318 rDest = pConsole; 319 delete [] pConsole; 320 321 return true; 322 } 323 324 bool ConvertToUtf8(const std::string& rSource, std::string& rDest, 325 int sourceCodePage) 326 { 327 return ConvertEncoding(rSource, sourceCodePage, rDest, CP_UTF8); 328 } 329 330 bool ConvertFromUtf8(const std::string& rSource, std::string& rDest, 331 int destCodePage) 332 { 333 return ConvertEncoding(rSource, CP_UTF8, rDest, destCodePage); 334 } 335 336 bool ConvertConsoleToUtf8(const std::string& rSource, std::string& rDest) 337 { 338 return ConvertToUtf8(rSource, rDest, GetConsoleCP()); 339 } 340 341 bool ConvertUtf8ToConsole(const std::string& rSource, std::string& rDest) 342 { 343 return ConvertFromUtf8(rSource, rDest, GetConsoleOutputCP()); 344 } 345 346 // -------------------------------------------------------------------------- 347 // 348 // Function 349 // Name: ConvertPathToAbsoluteUnicode 350 // Purpose: Converts relative paths to absolute (with unicode marker) 351 // Created: 4th February 2006 352 // 353 // -------------------------------------------------------------------------- 354 std::string ConvertPathToAbsoluteUnicode(const char *pFileName) 355 { 356 std::string filename; 357 for (int i = 0; pFileName[i] != 0; i++) 358 { 359 if (pFileName[i] == '/') 360 { 361 filename += '\\'; 362 } 363 else 364 { 365 filename += pFileName[i]; 34 return wide2multi(path); 366 35 } 367 36 } 368 369 std::string tmpStr("\\\\?\\"); 370 371 // Is the path relative or absolute? 372 // Absolute paths on Windows are always a drive letter 373 // followed by ':' 374 375 char wd[PATH_MAX]; 376 if (::getcwd(wd, PATH_MAX) == 0) 377 { 378 ::syslog(LOG_WARNING, 379 "Failed to open '%s': path too long", 380 pFileName); 381 errno = ENAMETOOLONG; 382 winerrno = ERROR_INVALID_NAME; 383 tmpStr = ""; 384 return tmpStr; 385 } 386 387 if (filename.length() > 2 && filename[0] == '\\' && 388 filename[1] == '\\') 389 { 390 tmpStr += "UNC\\"; 391 filename.replace(0, 2, ""); 392 // \\?\UNC\<server>\<share> 393 // see http://msdn2.microsoft.com/en-us/library/aa365247.aspx 394 } 395 else if (filename.length() >= 1 && filename[0] == '\\') 396 { 397 // root directory of current drive. 398 tmpStr = wd; 399 tmpStr.resize(2); // drive letter and colon 400 } 401 else if (filename.length() >= 2 && filename[1] != ':') 402 { 403 // Must be relative. We need to get the 404 // current directory to make it absolute. 405 tmpStr += wd; 406 if (tmpStr[tmpStr.length()] != '\\') 407 { 408 tmpStr += '\\'; 409 } 410 } 411 412 tmpStr += filename; 413 414 // We are using direct filename access, which does not support .., 415 // so we need to implement it ourselves. 416 417 for (std::string::size_type i = 1; i < tmpStr.size() - 3; i++) 418 { 419 if (tmpStr.substr(i, 3) == "\\..") 420 { 421 std::string::size_type lastSlash = 422 tmpStr.rfind('\\', i - 1); 423 424 if (lastSlash == std::string::npos) 425 { 426 // no previous directory, ignore it, 427 // CreateFile will fail with error 123 428 } 429 else 430 { 431 tmpStr.replace(lastSlash, i + 3 - lastSlash, 432 ""); 433 } 434 435 i = lastSlash; 436 } 437 } 438 439 return tmpStr; 440 } 441 442 std::string GetErrorMessage(DWORD errorCode) 443 { 444 char* pMsgBuf = NULL; 445 446 DWORD chars = FormatMessage 447 ( 448 FORMAT_MESSAGE_ALLOCATE_BUFFER | 449 FORMAT_MESSAGE_FROM_SYSTEM, 450 NULL, 451 errorCode, 452 MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), 453 (char *)(&pMsgBuf), 454 0, NULL 455 ); 456 457 if (chars == 0 || pMsgBuf == NULL) 458 { 459 return std::string("failed to get error message"); 460 } 461 462 // remove embedded newline 463 pMsgBuf[chars - 1] = 0; 464 pMsgBuf[chars - 2] = 0; 465 466 std::ostringstream line; 467 line << pMsgBuf << " (" << errorCode << ")"; 468 LocalFree(pMsgBuf); 469 470 return line.str(); 471 } 472 473 // -------------------------------------------------------------------------- 474 // 475 // Function 476 // Name: openfile 477 // Purpose: replacement for any open calls - handles unicode 478 // filenames - supplied in utf8 479 // Created: 25th October 2004 480 // 481 // -------------------------------------------------------------------------- 482 HANDLE openfile(const char *pFileName, int flags, int mode) 483 { 484 winerrno = ERROR_INVALID_FUNCTION; 485 486 std::string AbsPathWithUnicode = 487 ConvertPathToAbsoluteUnicode(pFileName); 488 489 if (AbsPathWithUnicode.size() == 0) 490 { 491 // error already logged by ConvertPathToAbsoluteUnicode() 492 return INVALID_HANDLE_VALUE; 493 } 494 495 WCHAR* pBuffer = ConvertUtf8ToWideString(AbsPathWithUnicode.c_str()); 496 // We are responsible for freeing pBuffer 497 498 if (pBuffer == NULL) 499 { 500 // error already logged by ConvertUtf8ToWideString() 501 return INVALID_HANDLE_VALUE; 502 } 503 504 // flags could be O_WRONLY | O_CREAT | O_RDONLY 505 DWORD createDisposition = OPEN_EXISTING; 506 DWORD shareMode = FILE_SHARE_READ | FILE_SHARE_WRITE 507 | FILE_SHARE_DELETE; 508 DWORD accessRights = FILE_READ_ATTRIBUTES | FILE_LIST_DIRECTORY 509 | FILE_READ_EA; 510 511 if (flags & O_WRONLY) 512 { 513 accessRights = FILE_WRITE_DATA; 514 } 515 else if (flags & O_RDWR) 516 { 517 accessRights |= FILE_WRITE_ATTRIBUTES 518 | FILE_WRITE_DATA | FILE_WRITE_EA; 519 } 520 521 if (flags & O_CREAT) 522 { 523 createDisposition = OPEN_ALWAYS; 524 } 525 526 if (flags & O_TRUNC) 527 { 528 createDisposition = CREATE_ALWAYS; 529 } 530 531 if ((flags & O_CREAT) && (flags & O_EXCL)) 532 { 533 createDisposition = CREATE_NEW; 534 } 535 536 if (flags & O_LOCK) 537 { 538 shareMode = 0; 539 } 540 541 DWORD winFlags = FILE_FLAG_BACKUP_SEMANTICS; 542 if (flags & O_TEMPORARY) 543 { 544 winFlags |= FILE_FLAG_DELETE_ON_CLOSE; 545 } 546 547 HANDLE hdir = CreateFileW(pBuffer, 548 accessRights, 549 shareMode, 550 NULL, 551 createDisposition, 552 winFlags, 553 NULL); 554 555 delete [] pBuffer; 556 557 if (hdir == INVALID_HANDLE_VALUE) 558 { 559 winerrno = GetLastError(); 560 switch(winerrno) 561 { 562 case ERROR_SHARING_VIOLATION: 563 errno = EBUSY; 564 break; 565 566 default: 567 errno = EINVAL; 568 } 569 570 ::syslog(LOG_WARNING, "Failed to open file '%s': " 571 "%s", pFileName, 572 GetErrorMessage(GetLastError()).c_str()); 573 574 return INVALID_HANDLE_VALUE; 575 } 576 577 if (flags & O_APPEND) 578 { 579 if (SetFilePointer(hdir, 0, NULL, FILE_END) == 580 INVALID_SET_FILE_POINTER) 581 { 582 winerrno = GetLastError(); 583 errno = EINVAL; 584 CloseHandle(hdir); 585 return INVALID_HANDLE_VALUE; 586 } 587 } 588 589 winerrno = NO_ERROR; 590 return hdir; 591 } 592 593 // -------------------------------------------------------------------------- 594 // 595 // Function 596 // Name: emu_fstat 597 // Purpose: replacement for fstat. Supply a windows handle. 598 // Returns a struct emu_stat to have room for 64-bit 599 // file identifier in st_ino (mingw allows only 16!) 600 // Created: 25th October 2004 601 // 602 // -------------------------------------------------------------------------- 603 int emu_fstat(HANDLE hdir, struct emu_stat * st) 604 { 605 if (hdir == INVALID_HANDLE_VALUE) 606 { 607 ::syslog(LOG_ERR, "Error: invalid file handle in emu_fstat()"); 608 errno = EBADF; 609 return -1; 610 } 611 612 BY_HANDLE_FILE_INFORMATION fi; 613 if (!GetFileInformationByHandle(hdir, &fi)) 614 { 615 ::syslog(LOG_WARNING, "Failed to read file information: " 616 "%s", GetErrorMessage(GetLastError()).c_str()); 617 errno = EACCES; 618 return -1; 619 } 620 621 if (INVALID_FILE_ATTRIBUTES == fi.dwFileAttributes) 622 { 623 ::syslog(LOG_WARNING, "Failed to get file attributes: " 624 "%s", GetErrorMessage(GetLastError()).c_str()); 625 errno = EACCES; 626 return -1; 627 } 628 629 memset(st, 0, sizeof(*st)); 630 631 // This is how we get our INODE (equivalent) information 632 ULARGE_INTEGER conv; 633 conv.HighPart = fi.nFileIndexHigh; 634 conv.LowPart = fi.nFileIndexLow; 635 st->st_ino = conv.QuadPart; 636 637 // get the time information 638 st->st_ctime = ConvertFileTimeToTime_t(&fi.ftCreationTime); 639 st->st_atime = ConvertFileTimeToTime_t(&fi.ftLastAccessTime); 640 st->st_mtime = ConvertFileTimeToTime_t(&fi.ftLastWriteTime); 641 642 if (fi.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) 643 { 644 st->st_size = 0; 645 } 646 else 647 { 648 conv.HighPart = fi.nFileSizeHigh; 649 conv.LowPart = fi.nFileSizeLow; 650 st->st_size = (_off_t)conv.QuadPart; 651 } 652 653 // at the mo 654 st->st_uid = 0; 655 st->st_gid = 0; 656 st->st_nlink = 1; 657 658 // the mode of the file 659 // mode zero will make it impossible to restore on Unix 660 // (no access to anybody, including the owner). 661 // we'll fake a sensible mode: 662 // all objects get user read (0400) 663 // if it's a directory it gets user execute (0100) 664 // if it's not read-only it gets user write (0200) 665 st->st_mode = S_IREAD; 666 667 if (fi.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) 668 { 669 st->st_mode |= S_IFDIR | S_IEXEC; 670 } 671 else 672 { 673 st->st_mode |= S_IFREG; 674 } 675 676 if (!(fi.dwFileAttributes & FILE_ATTRIBUTE_READONLY)) 677 { 678 st->st_mode |= S_IWRITE; 679 } 680 681 // st_dev is normally zero, regardless of the drive letter, 682 // since backup locations can't normally span drives. However, 683 // a reparse point does allow all kinds of weird stuff to happen. 684 // We set st_dev to 1 for a reparse point, so that Box will detect 685 // a change of device number (from 0) and refuse to recurse down 686 // the reparse point (which could lead to havoc). 687 688 if (fi.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) 689 { 690 st->st_dev = 1; 691 } 692 else 693 { 694 st->st_dev = 0; 695 } 696 697 return 0; 698 } 699 700 // -------------------------------------------------------------------------- 701 // 702 // Function 703 // Name: OpenFileByNameUtf8 704 // Purpose: Converts filename to Unicode and returns 705 // a handle to it. In case of error, sets errno, 706 // logs the error and returns NULL. 707 // Created: 10th December 2004 708 // 709 // -------------------------------------------------------------------------- 710 HANDLE OpenFileByNameUtf8(const char* pFileName, DWORD flags) 711 { 712 std::string AbsPathWithUnicode = 713 ConvertPathToAbsoluteUnicode(pFileName); 714 715 if (AbsPathWithUnicode.size() == 0) 716 { 717 // error already logged by ConvertPathToAbsoluteUnicode() 718 return NULL; 719 } 720 721 WCHAR* pBuffer = ConvertUtf8ToWideString(AbsPathWithUnicode.c_str()); 722 // We are responsible for freeing pBuffer 723 724 if (pBuffer == NULL) 725 { 726 // error already logged by ConvertUtf8ToWideString() 727 return NULL; 728 } 729 730 HANDLE handle = CreateFileW(pBuffer, 731 flags, 732 FILE_SHARE_READ | FILE_SHARE_DELETE | FILE_SHARE_WRITE, 733 NULL, 734 OPEN_EXISTING, 735 FILE_FLAG_BACKUP_SEMANTICS, 736 NULL); 737 738 if (handle == INVALID_HANDLE_VALUE) 739 { 740 // if our open fails we should always be able to 741 // open in this mode - to get the inode information 742 // at least one process must have the file open - 743 // in this case someone else does. 744 handle = CreateFileW(pBuffer, 745 READ_CONTROL, 746 FILE_SHARE_READ, 747 NULL, 748 OPEN_EXISTING, 749 FILE_FLAG_BACKUP_SEMANTICS, 750 NULL); 751 } 752 753 delete [] pBuffer; 754 755 if (handle == INVALID_HANDLE_VALUE) 756 { 757 DWORD err = GetLastError(); 758 759 if (err == ERROR_FILE_NOT_FOUND || 760 err == ERROR_PATH_NOT_FOUND) 761 { 762 errno = ENOENT; 763 } 764 else 765 { 766 ::syslog(LOG_WARNING, "Failed to open '%s': " 767 "%s", pFileName, 768 GetErrorMessage(err).c_str()); 769 errno = EACCES; 770 } 771 772 return NULL; 773 } 774 775 return handle; 776 } 777 778 // -------------------------------------------------------------------------- 779 // 780 // Function 781 // Name: emu_stat 782 // Purpose: replacement for the lstat and stat functions. 783 // Works with unicode filenames supplied in utf8. 784 // Returns a struct emu_stat to have room for 64-bit 785 // file identifier in st_ino (mingw allows only 16!) 786 // Created: 25th October 2004 787 // 788 // -------------------------------------------------------------------------- 789 int emu_stat(const char * pName, struct emu_stat * st) 790 { 791 HANDLE handle = OpenFileByNameUtf8(pName, 792 FILE_READ_ATTRIBUTES | FILE_READ_EA); 793 794 if (handle == NULL) 795 { 796 // errno already set and error logged by OpenFileByNameUtf8() 797 return -1; 798 } 799 800 int retVal = emu_fstat(handle, st); 801 if (retVal != 0) 802 { 803 // error logged, but without filename 804 ::syslog(LOG_WARNING, "Failed to get file information " 805 "for '%s'", pName); 806 } 807 808 // close the handle 809 CloseHandle(handle); 810 811 return retVal; 812 } 813 814 // -------------------------------------------------------------------------- 815 // 816 // Function 817 // Name: statfs 818 // Purpose: returns the mount point of where a file is located - 819 // in this case the volume serial number 820 // Created: 25th October 2004 821 // 822 // -------------------------------------------------------------------------- 823 int statfs(const char * pName, struct statfs * s) 824 { 825 HANDLE handle = OpenFileByNameUtf8(pName, 826 FILE_READ_ATTRIBUTES | FILE_READ_EA); 827 828 if (handle == NULL) 829 { 830 // errno already set and error logged by OpenFileByNameUtf8() 831 return -1; 832 } 833 834 BY_HANDLE_FILE_INFORMATION fi; 835 if (!GetFileInformationByHandle(handle, &fi)) 836 { 837 ::syslog(LOG_WARNING, "Failed to get file information " 838 "for '%s': %s", pName, 839 GetErrorMessage(GetLastError()).c_str()); 840 CloseHandle(handle); 841 errno = EACCES; 842 return -1; 843 } 844 845 // convert volume serial number to a string 846 _ui64toa(fi.dwVolumeSerialNumber, s->f_mntonname + 1, 16); 847 848 // pseudo unix mount point 849 s->f_mntonname[0] = '\\'; 850 851 CloseHandle(handle); // close the handle 852 853 return 0; 854 } 855 856 // -------------------------------------------------------------------------- 857 // 858 // Function 859 // Name: emu_utimes 860 // Purpose: replacement for the POSIX utimes() function, 861 // works with unicode filenames supplied in utf8 format, 862 // sets creation time instead of last access time. 863 // Created: 25th July 2006 864 // 865 // -------------------------------------------------------------------------- 866 int emu_utimes(const char * pName, const struct timeval times[]) 867 { 868 FILETIME creationTime; 869 if (!ConvertTime_tToFileTime(times[0].tv_sec, &creationTime)) 870 { 871 errno = EINVAL; 872 return -1; 873 } 874 875 FILETIME modificationTime; 876 if (!ConvertTime_tToFileTime(times[1].tv_sec, &modificationTime)) 877 { 878 errno = EINVAL; 879 return -1; 880 } 881 882 HANDLE handle = OpenFileByNameUtf8(pName, FILE_WRITE_ATTRIBUTES); 883 884 if (handle == NULL) 885 { 886 // errno already set and error logged by OpenFileByNameUtf8() 887 return -1; 888 } 889 890 if (!SetFileTime(handle, &creationTime, NULL, &modificationTime)) 891 { 892 ::syslog(LOG_ERR, "Failed to set times on '%s': %s", pName, 893 GetErrorMessage(GetLastError()).c_str()); 894 CloseHandle(handle); 895 return 1; 896 } 897 898 CloseHandle(handle); 899 return 0; 900 } 901 902 // -------------------------------------------------------------------------- 903 // 904 // Function 905 // Name: emu_chmod 906 // Purpose: replacement for the POSIX chmod function, 907 // works with unicode filenames supplied in utf8 format 908 // Created: 26th July 2006 909 // 910 // -------------------------------------------------------------------------- 911 int emu_chmod(const char * pName, mode_t mode) 912 { 913 std::string AbsPathWithUnicode = 914 ConvertPathToAbsoluteUnicode(pName); 915 916 if (AbsPathWithUnicode.size() == 0) 917 { 918 // error already logged by ConvertPathToAbsoluteUnicode() 919 return -1; 920 } 921 922 WCHAR* pBuffer = ConvertUtf8ToWideString(AbsPathWithUnicode.c_str()); 923 // We are responsible for freeing pBuffer 924 925 if (pBuffer == NULL) 926 { 927 // error already logged by ConvertUtf8ToWideString() 928 free(pBuffer); 929 return -1; 930 } 931 932 DWORD attribs = GetFileAttributesW(pBuffer); 933 if (attribs == INVALID_FILE_ATTRIBUTES) 934 { 935 ::syslog(LOG_ERR, "Failed to get file attributes of '%s': %s", 936 pName, GetErrorMessage(GetLastError()).c_str()); 937 errno = EACCES; 938 free(pBuffer); 939 return -1; 940 } 941 942 if (mode & S_IWRITE) 943 { 944 attribs &= ~FILE_ATTRIBUTE_READONLY; 945 } 946 else 947 { 948 attribs |= FILE_ATTRIBUTE_READONLY; 949 } 950 951 if (!SetFileAttributesW(pBuffer, attribs)) 952 { 953 ::syslog(LOG_ERR, "Failed to set file attributes of '%s': %s", 954 pName, GetErrorMessage(GetLastError()).c_str()); 955 errno = EACCES; 956 free(pBuffer); 957 return -1; 958 } 959 960 delete [] pBuffer; 961 return 0; 37 EMU_EXCEPTION_HANDLING_RETURN("") 962 38 } 963 39 964 40 965 // -------------------------------------------------------------------------- 966 // 967 // Function 968 // Name: opendir 969 // Purpose: replacement for unix function, uses win32 findfirst routines 970 // Created: 25th October 2004 971 // 972 // -------------------------------------------------------------------------- 973 DIR *opendir(const char *name) 41 int console_read(char* pBuffer, const size_t BufferSize) throw() 974 42 { 975 if (!name || !name[0]) 976 { 977 errno = EINVAL; 978 return NULL; 979 } 980 981 std::string dirName(name); 982 983 //append a '\' win32 findfirst is sensitive to this 984 if ( dirName[dirName.size()-1] != '\\' || dirName[dirName.size()-1] != '/' ) 985 { 986 dirName += '\\'; 987 } 988 989 // what is the search string? - everything 990 dirName += '*'; 991 992 DIR *pDir = new DIR; 993 if (pDir == NULL) 994 { 995 errno = ENOMEM; 996 return NULL; 997 } 998 999 pDir->name = ConvertUtf8ToWideString(dirName.c_str()); 1000 // We are responsible for freeing dir->name with delete[] 1001 1002 if (pDir->name == NULL) 1003 { 1004 delete pDir; 1005 return NULL; 1006 } 1007 1008 pDir->fd = _wfindfirst((const wchar_t*)pDir->name, &(pDir->info)); 1009 1010 if (pDir->fd == -1) 1011 { 1012 delete [] pDir->name; 1013 delete pDir; 1014 return NULL; 1015 } 1016 1017 pDir->result.d_name = 0; 1018 return pDir; 1019 } 1020 1021 // this kinda makes it not thread friendly! 1022 // but I don't think it needs to be. 1023 char tempbuff[MAX_PATH]; 1024 1025 // -------------------------------------------------------------------------- 1026 // 1027 // Function 1028 // Name: readdir 1029 // Purpose: as function above 1030 // Created: 25th October 2004 1031 // 1032 // -------------------------------------------------------------------------- 1033 struct dirent *readdir(DIR *dp) 1034 { 43 HANDLE hConsole; 44 1035 45 try 1036 46 { 1037 struct dirent *den = NULL; 47 if (INVALID_HANDLE_VALUE == (hConsole = GetStdHandle(STD_INPUT_HANDLE))) 48 throw Win32Exception(Win32Exception::API_GetStdHandle); 1038 49 1039 if (dp && dp->fd != -1) 1040 { 1041 if (!dp->result.d_name || 1042 _wfindnext(dp->fd, &dp->info) != -1) 1043 { 1044 den = &dp->result; 1045 std::wstring input(dp->info.name); 1046 memset(tempbuff, 0, sizeof(tempbuff)); 1047 WideCharToMultiByte(CP_UTF8, 0, dp->info.name, 1048 -1, &tempbuff[0], sizeof (tempbuff), 1049 NULL, NULL); 1050 //den->d_name = (char *)dp->info.name; 1051 den->d_name = &tempbuff[0]; 1052 if (dp->info.attrib & FILE_ATTRIBUTE_DIRECTORY) 1053 { 1054 den->d_type = S_IFDIR; 1055 } 1056 else 1057 { 1058 den->d_type = S_IFREG; 1059 } 1060 } 1061 } 1062 else 1063 { 1064 errno = EBADF; 1065 } 1066 return den; 50 size_t wideSize = BufferSize / 5; 51 std::unique_ptr<wchar_t[]> wide(new wchar_t[wideSize+1]); 52 53 DWORD numCharsRead = 0; 54 if (!ReadConsoleW(hConsole,wide.get(),static_cast<DWORD>(wideSize),&numCharsRead,NULL)) 55 throw Win32Exception(Win32Exception::API_ReadConsole); 56 57 wide[numCharsRead] = '\0'; 58 std::string multi(wide2multi(wide.get())); 59 strcpy(pBuffer,multi.c_str()); 60 61 return static_cast<int>(multi.size()); 1067 62 } 1068 catch (...) 1069 { 1070 printf("Caught readdir"); 1071 } 1072 return NULL; 63 EMU_EXCEPTION_HANDLING_RETURN(-1) 1073 64 } 1074 1075 // --------------------------------------------------------------------------1076 //1077 // Function1078 // Name: closedir1079 // Purpose: as function above1080 // Created: 25th October 20041081 //1082 // --------------------------------------------------------------------------1083 int closedir(DIR *dp)1084 {1085 try1086 {1087 int finres = -1;1088 if (dp)1089 {1090 if(dp->fd != -1)1091 {1092 finres = _findclose(dp->fd);1093 }1094 1095 delete [] dp->name;1096 delete dp;1097 }1098 1099 if (finres == -1) // errors go to EBADF1100 {1101 errno = EBADF;1102 }1103 1104 return finres;1105 }1106 catch (...)1107 {1108 printf("Caught closedir");1109 }1110 return -1;1111 }1112 1113 // --------------------------------------------------------------------------1114 //1115 // Function1116 // Name: poll1117 // Purpose: a weak implimentation (just enough for box)1118 // of the unix poll for winsock21119 // Created: 25th October 20041120 //1121 // --------------------------------------------------------------------------1122 int poll (struct pollfd *ufds, unsigned long nfds, int timeout)1123 {1124 try1125 {1126 fd_set readfd;1127 fd_set writefd;1128 1129 FD_ZERO(&readfd);1130 FD_ZERO(&writefd);1131 1132 // struct pollfd *ufdsTmp = ufds;1133 1134 timeval timOut;1135 timeval *tmpptr;1136 1137 if (timeout == INFTIM)1138 tmpptr = NULL;1139 else1140 tmpptr = &timOut;1141 1142 timOut.tv_sec = timeout / 1000;1143 timOut.tv_usec = timeout * 1000;1144 1145 for (unsigned long i = 0; i < nfds; i++)1146 {1147 struct pollfd* ufd = &(ufds[i]);1148 1149 if (ufd->events & POLLIN)1150 {1151 FD_SET(ufd->fd, &readfd);1152 }1153 1154 if (ufd->events & POLLOUT)1155 {1156 FD_SET(ufd->fd, &writefd);1157 }1158 1159 if (ufd->events & ~(POLLIN | POLLOUT))1160 {1161 printf("Unsupported poll bits %d",1162 ufd->events);1163 return -1;1164 }1165 }1166 1167 int nready = select(0, &readfd, &writefd, 0, tmpptr);1168 1169 if (nready == SOCKET_ERROR)1170 {1171 // int errval = WSAGetLastError();1172 1173 struct pollfd* pufd = ufds;1174 for (unsigned long i = 0; i < nfds; i++)1175 {1176 pufd->revents = POLLERR;1177 pufd++;1178 }1179 return (-1);1180 }1181 else if (nready > 0)1182 {1183 for (unsigned long i = 0; i < nfds; i++)1184 {1185 struct pollfd *ufd = &(ufds[i]);1186 1187 if (FD_ISSET(ufd->fd, &readfd))1188 {1189 ufd->revents |= POLLIN;1190 }1191 1192 if (FD_ISSET(ufd->fd, &writefd))1193 {1194 ufd->revents |= POLLOUT;1195 }1196 }1197 }1198 1199 return nready;1200 }1201 catch (...)1202 {1203 printf("Caught poll");1204 }1205 1206 return -1;1207 }1208 1209 // copied from MSDN: http://msdn.microsoft.com/library/default.asp?url=/library/en-us/eventlog/base/adding_a_source_to_the_registry.asp1210 1211 BOOL AddEventSource1212 (1213 LPTSTR pszSrcName, // event source name1214 DWORD dwNum // number of categories1215 )1216 {1217 // Work out the executable file name, to register ourselves1218 // as the event source1219 1220 WCHAR cmd[MAX_PATH];1221 DWORD len = GetModuleFileNameW(NULL, cmd, MAX_PATH);1222 1223 if (len == 0)1224 {1225 ::syslog(LOG_ERR, "Failed to get the program file name: %s",1226 GetErrorMessage(GetLastError()).c_str());1227 return FALSE;1228 }1229 1230 // Create the event source as a subkey of the log.1231 1232 std::string regkey("SYSTEM\\CurrentControlSet\\Services\\EventLog\\"1233 "Application\\");1234 regkey += pszSrcName;1235 1236 HKEY hk;1237 DWORD dwDisp;1238 1239 if (RegCreateKeyEx(HKEY_LOCAL_MACHINE, regkey.c_str(),1240 0, NULL, REG_OPTION_NON_VOLATILE,1241 KEY_WRITE, NULL, &hk, &dwDisp))1242 {1243 ::syslog(LOG_ERR, "Failed to create the registry key: %s",1244 GetErrorMessage(GetLastError()).c_str());1245 return FALSE;1246 }1247 1248 // Set the name of the message file.1249 1250 if (RegSetValueExW(hk, // subkey handle1251 L"EventMessageFile", // value name1252 0, // must be zero1253 REG_EXPAND_SZ, // value type1254 (LPBYTE)cmd, // pointer to value data1255 len*sizeof(WCHAR))) // data size1256 {1257 ::syslog(LOG_ERR, "Failed to set the event message file: %s",1258 GetErrorMessage(GetLastError()).c_str());1259 RegCloseKey(hk);1260 return FALSE;1261 }1262 1263 // Set the supported event types.1264 1265 DWORD dwData = EVENTLOG_ERROR_TYPE | EVENTLOG_WARNING_TYPE |1266 EVENTLOG_INFORMATION_TYPE;1267 1268 if (RegSetValueEx(hk, // subkey handle1269 "TypesSupported", // value name1270 0, // must be zero1271 REG_DWORD, // value type1272 (LPBYTE) &dwData, // pointer to value data1273 sizeof(DWORD))) // length of value data1274 {1275 ::syslog(LOG_ERR, "Failed to set the supported types: %s",1276 GetErrorMessage(GetLastError()).c_str());1277 RegCloseKey(hk);1278 return FALSE;1279 }1280 1281 // Set the category message file and number of categories.1282 1283 if (RegSetValueExW(hk, // subkey handle1284 L"CategoryMessageFile", // value name1285 0, // must be zero1286 REG_EXPAND_SZ, // value type1287 (LPBYTE)cmd, // pointer to value data1288 len*sizeof(WCHAR))) // data size1289 {1290 ::syslog(LOG_ERR, "Failed to set the category message file: "1291 "%s", GetErrorMessage(GetLastError()).c_str());1292 RegCloseKey(hk);1293 return FALSE;1294 }1295 1296 if (RegSetValueEx(hk, // subkey handle1297 "CategoryCount", // value name1298 0, // must be zero1299 REG_DWORD, // value type1300 (LPBYTE) &dwNum, // pointer to value data1301 sizeof(DWORD))) // length of value data1302 {1303 ::syslog(LOG_ERR, "Failed to set the category count: %s",1304 GetErrorMessage(GetLastError()).c_str());1305 RegCloseKey(hk);1306 return FALSE;1307 }1308 1309 RegCloseKey(hk);1310 return TRUE;1311 }1312 1313 static HANDLE gSyslogH = 0;1314 static bool sHaveWarnedEventLogFull = false;1315 1316 void openlog(const char * daemonName, int, int)1317 {1318 std::string nameStr = "Box Backup (";1319 nameStr += daemonName;1320 nameStr += ")";1321 1322 // register a default event source, so that we can1323 // log errors with the process of adding or registering our own.1324 gSyslogH = RegisterEventSource(1325 NULL, // uses local computer1326 nameStr.c_str()); // source name1327 if (gSyslogH == NULL)1328 {1329 }1330 1331 char* name = strdup(nameStr.c_str());1332 BOOL success = AddEventSource(name, 0);1333 free(name);1334 1335 if (!success)1336 {1337 ::syslog(LOG_ERR, "Failed to add our own event source");1338 return;1339 }1340 1341 HANDLE newSyslogH = RegisterEventSource(NULL, nameStr.c_str());1342 if (newSyslogH == NULL)1343 {1344 ::syslog(LOG_ERR, "Failed to register our own event source: "1345 "%s", GetErrorMessage(GetLastError()).c_str());1346 return;1347 }1348 1349 DeregisterEventSource(gSyslogH);1350 gSyslogH = newSyslogH;1351 }1352 1353 void closelog(void)1354 {1355 DeregisterEventSource(gSyslogH);1356 }1357 1358 void syslog(int loglevel, const char *frmt, ...)1359 {1360 WORD errinfo;1361 char buffer[1024];1362 std::string sixfour(frmt);1363 1364 switch (loglevel)1365 {1366 case LOG_INFO:1367 errinfo = EVENTLOG_INFORMATION_TYPE;1368 break;1369 case LOG_ERR:1370 errinfo = EVENTLOG_ERROR_TYPE;1371 break;1372 case LOG_WARNING:1373 errinfo = EVENTLOG_WARNING_TYPE;1374 break;1375 default:1376 errinfo = EVENTLOG_WARNING_TYPE;1377 break;1378 }1379 1380 // taken from MSDN1381 int sixfourpos;1382 while ( (sixfourpos = (int)sixfour.find("%ll")) != -1 )1383 {1384 // maintain portability - change the 64 bit formater...1385 std::string temp = sixfour.substr(0,sixfourpos);1386 temp += "%I64";1387 temp += sixfour.substr(sixfourpos+3, sixfour.length());1388 sixfour = temp;1389 }1390 1391 // printf("parsed string is:%s\r\n", sixfour.c_str());1392 1393 va_list args;1394 va_start(args, frmt);1395 1396 int len = vsnprintf(buffer, sizeof(buffer)-1, sixfour.c_str(), args);1397 assert(len >= 0);1398 if (len < 0)1399 {1400 printf("%s\r\n", buffer);1401 fflush(stdout);1402 return;1403 }1404 1405 assert((size_t)len < sizeof(buffer));1406 buffer[sizeof(buffer)-1] = 0;1407 1408 va_end(args);1409 1410 if (gSyslogH == 0)1411 {1412 printf("%s\r\n", buffer);1413 fflush(stdout);1414 return;1415 }1416 1417 WCHAR* pWide = ConvertToWideString(buffer, CP_UTF8, false);1418 // must delete[] pWide1419 1420 DWORD result;1421 1422 if (pWide == NULL)1423 {1424 std::string buffer2 = buffer;1425 buffer2 += " (failed to convert string encoding)";1426 LPCSTR strings[] = { buffer2.c_str(), NULL };1427 1428 result = ReportEventA(gSyslogH, // event log handle1429 errinfo, // event type1430 0, // category zero1431 MSG_ERR, // event identifier -1432 // we will call them all the same1433 NULL, // no user security identifier1434 1, // one substitution string1435 0, // no data1436 strings, // pointer to string array1437 NULL); // pointer to data1438 }1439 else1440 {1441 LPCWSTR strings[] = { pWide, NULL };1442 result = ReportEventW(gSyslogH, // event log handle1443 errinfo, // event type1444 0, // category zero1445 MSG_ERR, // event identifier -1446 // we will call them all the same1447 NULL, // no user security identifier1448 1, // one substitution string1449 0, // no data1450 strings, // pointer to string array1451 NULL); // pointer to data1452 delete [] pWide;1453 }1454 1455 if (result == 0)1456 {1457 DWORD err = GetLastError();1458 if (err == ERROR_LOG_FILE_FULL)1459 {1460 if (!sHaveWarnedEventLogFull)1461 {1462 printf("Unable to send message to Event Log "1463 "(Event Log is full):\r\n");1464 fflush(stdout);1465 sHaveWarnedEventLogFull = TRUE;1466 }1467 }1468 else1469 {1470 printf("Unable to send message to Event Log: %s:\r\n",1471 GetErrorMessage(err).c_str());1472 fflush(stdout);1473 }1474 }1475 else1476 {1477 sHaveWarnedEventLogFull = false;1478 }1479 }1480 1481 int emu_chdir(const char* pDirName)1482 {1483 /*1484 std::string AbsPathWithUnicode =1485 ConvertPathToAbsoluteUnicode(pDirName);1486 1487 if (AbsPathWithUnicode.size() == 0)1488 {1489 // error already logged by ConvertPathToAbsoluteUnicode()1490 return -1;1491 }1492 1493 WCHAR* pBuffer = ConvertUtf8ToWideString(AbsPathWithUnicode.c_str());1494 */1495 1496 WCHAR* pBuffer = ConvertUtf8ToWideString(pDirName);1497 if (!pBuffer) return -1;1498 1499 int result = SetCurrentDirectoryW(pBuffer);1500 delete [] pBuffer;1501 1502 if (result != 0) return 0;1503 1504 errno = EACCES;1505 fprintf(stderr, "Failed to change directory to '%s': %s\n",1506 pDirName, GetErrorMessage(GetLastError()).c_str());1507 return -1;1508 }1509 1510 char* emu_getcwd(char* pBuffer, int BufSize)1511 {1512 DWORD len = GetCurrentDirectoryW(0, NULL);1513 if (len == 0)1514 {1515 errno = EINVAL;1516 return NULL;1517 }1518 1519 if ((int)len > BufSize)1520 {1521 errno = ENAMETOOLONG;1522 return NULL;1523 }1524 1525 WCHAR* pWide = new WCHAR [len];1526 if (!pWide)1527 {1528 errno = ENOMEM;1529 return NULL;1530 }1531 1532 DWORD result = GetCurrentDirectoryW(len, pWide);1533 if (result <= 0 || result >= len)1534 {1535 errno = EACCES;1536 delete [] pWide;1537 return NULL;1538 }1539 1540 char* pUtf8 = ConvertFromWideString(pWide, CP_UTF8);1541 delete [] pWide;1542 1543 if (!pUtf8)1544 {1545 return NULL;1546 }1547 1548 strncpy(pBuffer, pUtf8, BufSize - 1);1549 pBuffer[BufSize - 1] = 0;1550 delete [] pUtf8;1551 1552 return pBuffer;1553 }1554 1555 int emu_mkdir(const char* pPathName)1556 {1557 std::string AbsPathWithUnicode =1558 ConvertPathToAbsoluteUnicode(pPathName);1559 1560 if (AbsPathWithUnicode.size() == 0)1561 {1562 // error already logged by ConvertPathToAbsoluteUnicode()1563 return -1;1564 }1565 1566 WCHAR* pBuffer = ConvertUtf8ToWideString(AbsPathWithUnicode.c_str());1567 if (!pBuffer)1568 {1569 return -1;1570 }1571 1572 BOOL result = CreateDirectoryW(pBuffer, NULL);1573 delete [] pBuffer;1574 1575 if (!result)1576 {1577 errno = EACCES;1578 return -1;1579 }1580 1581 return 0;1582 }1583 1584 int emu_unlink(const char* pFileName)1585 {1586 std::string AbsPathWithUnicode =1587 ConvertPathToAbsoluteUnicode(pFileName);1588 1589 if (AbsPathWithUnicode.size() == 0)1590 {1591 // error already logged by ConvertPathToAbsoluteUnicode()1592 return -1;1593 }1594 1595 WCHAR* pBuffer = ConvertUtf8ToWideString(AbsPathWithUnicode.c_str());1596 if (!pBuffer)1597 {1598 return -1;1599 }1600 1601 BOOL result = DeleteFileW(pBuffer);1602 DWORD err = GetLastError();1603 delete [] pBuffer;1604 1605 if (!result)1606 {1607 if (err == ERROR_FILE_NOT_FOUND || err == ERROR_PATH_NOT_FOUND)1608 {1609 errno = ENOENT;1610 }1611 else if (err == ERROR_SHARING_VIOLATION)1612 {1613 errno = EBUSY;1614 }1615 else if (err == ERROR_ACCESS_DENIED)1616 {1617 errno = EACCES;1618 }1619 else1620 {1621 ::syslog(LOG_WARNING, "Failed to delete file "1622 "'%s': %s", pFileName,1623 GetErrorMessage(err).c_str());1624 errno = ENOSYS;1625 }1626 return -1;1627 }1628 1629 return 0;1630 }1631 1632 int emu_rename(const char* pOldFileName, const char* pNewFileName)1633 {1634 std::string OldPathWithUnicode =1635 ConvertPathToAbsoluteUnicode(pOldFileName);1636 1637 if (OldPathWithUnicode.size() == 0)1638 {1639 // error already logged by ConvertPathToAbsoluteUnicode()1640 return -1;1641 }1642 1643 WCHAR* pOldBuffer = ConvertUtf8ToWideString(OldPathWithUnicode.c_str());1644 if (!pOldBuffer)1645 {1646 return -1;1647 }1648 1649 std::string NewPathWithUnicode =1650 ConvertPathToAbsoluteUnicode(pNewFileName);1651 1652 if (NewPathWithUnicode.size() == 0)1653 {1654 // error already logged by ConvertPathToAbsoluteUnicode()1655 delete [] pOldBuffer;1656 return -1;1657 }1658 1659 WCHAR* pNewBuffer = ConvertUtf8ToWideString(NewPathWithUnicode.c_str());1660 if (!pNewBuffer)1661 {1662 delete [] pOldBuffer;1663 return -1;1664 }1665 1666 BOOL result = MoveFileW(pOldBuffer, pNewBuffer);1667 DWORD err = GetLastError();1668 delete [] pOldBuffer;1669 delete [] pNewBuffer;1670 1671 if (!result)1672 {1673 if (err == ERROR_FILE_NOT_FOUND || err == ERROR_PATH_NOT_FOUND)1674 {1675 errno = ENOENT;1676 }1677 else if (err == ERROR_SHARING_VIOLATION)1678 {1679 errno = EBUSY;1680 }1681 else if (err == ERROR_ACCESS_DENIED)1682 {1683 errno = EACCES;1684 }1685 else1686 {1687 ::syslog(LOG_WARNING, "Failed to rename file "1688 "'%s' to '%s': %s", pOldFileName, pNewFileName,1689 GetErrorMessage(err).c_str());1690 errno = ENOSYS;1691 }1692 return -1;1693 }1694 1695 return 0;1696 }1697 1698 int console_read(char* pBuffer, size_t BufferSize)1699 {1700 HANDLE hConsole = GetStdHandle(STD_INPUT_HANDLE);1701 1702 if (hConsole == INVALID_HANDLE_VALUE)1703 {1704 ::fprintf(stderr, "Failed to get a handle on standard input: "1705 "%s", GetErrorMessage(GetLastError()).c_str());1706 return -1;1707 }1708 1709 size_t WideSize = BufferSize / 5;1710 WCHAR* pWideBuffer = new WCHAR [WideSize + 1];1711 1712 if (!pWideBuffer)1713 {1714 ::perror("Failed to allocate wide character buffer");1715 return -1;1716 }1717 1718 DWORD numCharsRead = 0;1719 1720 if (!ReadConsoleW(1721 hConsole,1722 pWideBuffer,1723 WideSize, // will not be null terminated by ReadConsole1724 &numCharsRead,1725 NULL // reserved1726 ))1727 {1728 ::fprintf(stderr, "Failed to read from console: %s\n",1729 GetErrorMessage(GetLastError()).c_str());1730 return -1;1731 }1732 1733 pWideBuffer[numCharsRead] = 0;1734 1735 char* pUtf8 = ConvertFromWideString(pWideBuffer, GetConsoleCP());1736 delete [] pWideBuffer;1737 1738 strncpy(pBuffer, pUtf8, BufferSize);1739 delete [] pUtf8;1740 1741 return strlen(pBuffer);1742 }1743 1744 int readv (int filedes, const struct iovec *vector, size_t count)1745 {1746 int bytes = 0;1747 1748 for (size_t i = 0; i < count; i++)1749 {1750 int result = read(filedes, vector[i].iov_base,1751 vector[i].iov_len);1752 if (result < 0)1753 {1754 return result;1755 }1756 bytes += result;1757 }1758 1759 return bytes;1760 }1761 1762 int writev(int filedes, const struct iovec *vector, size_t count)1763 {1764 int bytes = 0;1765 1766 for (size_t i = 0; i < count; i++)1767 {1768 int result = write(filedes, vector[i].iov_base,1769 vector[i].iov_len);1770 if (result < 0)1771 {1772 return result;1773 }1774 bytes += result;1775 }1776 1777 return bytes;1778 }1779 1780 // need this for conversions1781 time_t ConvertFileTimeToTime_t(FILETIME *fileTime)1782 {1783 SYSTEMTIME stUTC;1784 struct tm timeinfo;1785 1786 // Convert the last-write time to local time.1787 FileTimeToSystemTime(fileTime, &stUTC);1788 1789 memset(&timeinfo, 0, sizeof(timeinfo));1790 timeinfo.tm_sec = stUTC.wSecond;1791 timeinfo.tm_min = stUTC.wMinute;1792 timeinfo.tm_hour = stUTC.wHour;1793 timeinfo.tm_mday = stUTC.wDay;1794 timeinfo.tm_wday = stUTC.wDayOfWeek;1795 timeinfo.tm_mon = stUTC.wMonth - 1;1796 // timeinfo.tm_yday = ...;1797 timeinfo.tm_year = stUTC.wYear - 1900;1798 1799 time_t retVal = mktime(&timeinfo) - _timezone;1800 return retVal;1801 }1802 1803 bool ConvertTime_tToFileTime(const time_t from, FILETIME *pTo)1804 {1805 time_t adjusted = from + _timezone;1806 struct tm *time_breakdown = gmtime(&adjusted);1807 if (time_breakdown == NULL)1808 {1809 ::syslog(LOG_ERR, "Error: failed to convert time format: "1810 "%d is not a valid time\n", from);1811 return false;1812 }1813 1814 SYSTEMTIME stUTC;1815 stUTC.wSecond = time_breakdown->tm_sec;1816 stUTC.wMinute = time_breakdown->tm_min;1817 stUTC.wHour = time_breakdown->tm_hour;1818 stUTC.wDay = time_breakdown->tm_mday;1819 stUTC.wDayOfWeek = time_breakdown->tm_wday;1820 stUTC.wMonth = time_breakdown->tm_mon + 1;1821 stUTC.wYear = time_breakdown->tm_year + 1900;1822 stUTC.wMilliseconds = 0;1823 1824 // Convert the last-write time to local time.1825 if (!SystemTimeToFileTime(&stUTC, pTo))1826 {1827 syslog(LOG_ERR, "Failed to convert between time formats: %s",1828 GetErrorMessage(GetLastError()).c_str());1829 return false;1830 }1831 1832 return true;1833 }1834 1835 #endif // WIN321836 -
box/invisnet/vs2010/0.11/lib/win32/emu.h
r2773 r3055 1 // emulates unix syscalls to win32 functions 1 #ifndef EMU_INCLUDE 2 # define EMU_INCLUDE 2 3 3 #ifdef WIN32 4 #define EMU_STRUCT_STAT struct emu_stat 5 #define EMU_STAT emu_stat 6 #define EMU_FSTAT emu_fstat 7 #define EMU_LSTAT emu_stat 8 #else 9 #define EMU_STRUCT_STAT struct stat 10 #define EMU_STAT ::stat 11 #define EMU_FSTAT ::fstat 12 #define EMU_LSTAT ::lstat 13 #endif 4 # ifdef WIN32 5 # pragma once 14 6 15 #if ! defined EMU_INCLUDE && defined WIN32 16 #define EMU_INCLUDE 7 # include "win32.h" 8 # include "dirent.h" 9 # include "getopt.h" 10 # include "poll.h" 11 # include "pwd.h" 12 # include "unicode.h" 13 # include "unistd.h" 14 15 # include "_sys/mount.h" 16 # include "_sys/resource.h" 17 # include "_sys/socket.h" 18 # include "_sys/stat.h" 19 # include "_sys/syslog.h" 20 # include "_sys/time.h" 21 # include "_sys/uio.h" 22 23 24 extern passwd gTempPasswd; 25 26 27 # define EMU_EXCEPTION_HANDLING \ 28 catch(std::bad_alloc &e) \ 29 { \ 30 (void)e; /* make the compiler happy */ \ 31 errno = ENOMEM; \ 32 } \ 33 catch(Win32Exception &e) \ 34 { \ 35 BOX_LOG_WIN_ERROR_NUMBER(e.GetMessage(),e.GetLastError()); \ 36 } \ 37 catch(...) \ 38 { \ 39 BOX_FATAL("Unexpected exception") \ 40 } 41 42 # define EMU_EXCEPTION_HANDLING_RETURN(rv) \ 43 catch(std::bad_alloc &e) \ 44 { \ 45 (void)e; /* make the compiler happy */ \ 46 errno = ENOMEM; \ 47 } \ 48 catch(Win32Exception &e) \ 49 { \ 50 BOX_LOG_WIN_ERROR_NUMBER(e.GetMessage(),e.GetLastError()); \ 51 } \ 52 catch(...) \ 53 { \ 54 BOX_FATAL("Unexpected exception") \ 55 } \ 56 return rv; 57 58 17 59 18 60 // basic types, may be required by other headers since we 19 61 // don't include sys/types.h 20 62 21 #ifdef __MINGW32__22 #include <stdint.h>23 #else // MSVC24 typedef unsigned __int64 u_int64_t;25 typedef unsigned __int64 uint64_t;26 typedef __int64 int64_t;27 typedef unsigned __int32 uint32_t;28 typedef unsigned __int32 u_int32_t;29 typedef __int32 int32_t;30 typedef unsigned __int16 uint16_t;31 typedef __int16 int16_t;32 typedef unsigned __int8 uint8_t;33 typedef __int8 int8_t;34 #endif35 63 36 64 // emulated types, present on MinGW but not MSVC or vice versa … … 39 67 typedef uint32_t u_int32_t; 40 68 #else 41 typedef unsigned int mode_t;42 typedef unsigned int pid_t;43 69 #endif 44 45 // set up to include the necessary parts of Windows headers46 47 #define WIN32_LEAN_AND_MEAN48 49 #ifndef __MSVCRT_VERSION__50 #define __MSVCRT_VERSION__ 0x060151 #endif52 53 // Windows headers54 55 #include <winsock2.h>56 #include <fcntl.h>57 #include <sys/stat.h>58 #include <direct.h>59 #include <errno.h>60 #include <io.h>61 #include <stdlib.h>62 #include <string.h>63 #include <stdio.h>64 #include <stdarg.h>65 #include <time.h>66 67 #include <string>68 70 69 71 // emulated functions … … 75 77 #define ITIMER_REAL 0 76 78 77 struct passwd {78 char *pw_name;79 char *pw_passwd;80 int pw_uid;81 int pw_gid;82 time_t pw_change;83 char *pw_class;84 char *pw_gecos;85 char *pw_dir;86 char *pw_shell;87 time_t pw_expire;88 };89 79 90 extern passwd gTempPasswd;91 inline struct passwd * getpwnam(const char * name)92 {93 //for the mo pretend to be root94 gTempPasswd.pw_uid = 0;95 gTempPasswd.pw_gid = 0;96 80 97 return &gTempPasswd;98 }99 81 100 #define S_IRWXG 1101 #define S_IRWXO 2102 #define S_ISUID 4103 #define S_ISGID 8104 #define S_ISVTX 16105 82 106 #ifndef __MINGW32__107 //not sure if these are correct108 //S_IWRITE - writing permitted109 //_S_IREAD - reading permitted110 //_S_IREAD | _S_IWRITE -111 #define S_IRUSR S_IWRITE112 #define S_IWUSR S_IREAD113 #define S_IRWXU (S_IREAD|S_IWRITE|S_IEXEC)114 115 #define S_ISREG(x) (S_IFREG & x)116 #define S_ISDIR(x) (S_IFDIR & x)117 #endif118 119 inline int chown(const char * Filename, u_int32_t uid, u_int32_t gid)120 {121 //important - this needs implementing122 //If a large restore is required then123 //it needs to restore files AND permissions124 //reference AdjustTokenPrivileges125 //GetAccountSid126 //InitializeSecurityDescriptor127 //SetSecurityDescriptorOwner128 //The next function looks like the guy to use...129 //SetFileSecurity130 131 //indicate success132 return 0;133 }134 135 // Windows and Unix owners and groups are pretty fundamentally different.136 // Ben prefers that we kludge here rather than litter the code with #ifdefs.137 // Pretend to be root, and pretend that set...() operations succeed.138 inline int setegid(int)139 {140 return true;141 }142 inline int seteuid(int)143 {144 return true;145 }146 inline int setgid(int)147 {148 return true;149 }150 inline int setuid(int)151 {152 return true;153 }154 inline int getgid(void)155 {156 return 0;157 }158 inline int getuid(void)159 {160 return 0;161 }162 inline int geteuid(void)163 {164 return 0;165 }166 83 167 84 #ifndef PATH_MAX … … 169 86 #endif 170 87 171 // MinGW provides a getopt implementation172 #ifndef __MINGW32__173 #include "getopt.h"174 #endif // !__MINGW32__175 176 88 #define timespec timeval 177 89 178 90 //win32 deals in usec not nsec - so need to ensure this follows through 179 91 #define tv_nsec tv_usec 180 181 #ifndef __MINGW32__182 typedef int socklen_t;183 #endif184 92 185 93 #define S_IRGRP S_IWRITE … … 208 116 #endif 209 117 210 struct dirent211 {212 char *d_name;213 unsigned long d_type;214 };215 216 struct DIR217 {218 intptr_t fd; // filedescriptor219 // struct _finddata_t info;220 struct _wfinddata_t info;221 // struct _finddata_t info;222 struct dirent result; // d_name (first time null)223 wchar_t *name; // null-terminated byte string224 };225 226 DIR *opendir(const char *name);227 struct dirent *readdir(DIR *dp);228 int closedir(DIR *dp);229 230 118 // local constant to open file exclusively without shared access 231 119 #define O_LOCK 0x10000 232 120 233 extern DWORD winerrno; /* used to report errors from openfile() */234 121 HANDLE openfile(const char *filename, int flags, int mode); 235 122 inline int closefile(HANDLE handle) … … 243 130 } 244 131 245 #define LOG_DEBUG LOG_INFO246 #define LOG_INFO 6247 #define LOG_NOTICE LOG_INFO248 #define LOG_WARNING 4249 #define LOG_ERR 3250 #define LOG_CRIT LOG_ERR251 #define LOG_PID 0252 #define LOG_LOCAL5 0253 #define LOG_LOCAL6 0254 255 void openlog (const char * daemonName, int, int);256 void closelog(void);257 void syslog (int loglevel, const char *fmt, ...);258 259 #define LOG_LOCAL0 0260 #define LOG_LOCAL1 0261 #define LOG_LOCAL2 0262 #define LOG_LOCAL3 0263 #define LOG_LOCAL4 0264 #define LOG_LOCAL5 0265 #define LOG_LOCAL6 0266 #define LOG_DAEMON 0267 132 268 133 #ifndef __MINGW32__ … … 270 135 #endif 271 136 272 inline unsigned int sleep(unsigned int secs)273 {274 Sleep(secs*1000);275 return(ERROR_SUCCESS);276 }277 137 278 #define INFTIM -1279 #if(_WIN32_WINNT < 0x0600)280 #define POLLIN 0x1281 #define POLLERR 0x8282 #define POLLOUT 0x4283 #endif284 138 285 #define SHUT_RDWR SD_BOTH286 #define SHUT_RD SD_RECEIVE287 #define SHUT_WR SD_SEND288 139 289 #if(_WIN32_WINNT < 0x0600)290 struct pollfd291 {292 SOCKET fd;293 short int events;294 short int revents;295 };296 #endif297 298 inline int ioctl(SOCKET sock, int flag, int * something)299 {300 //indicate success301 return 0;302 }303 304 extern "C" inline int getpid()305 {306 return (int)GetCurrentProcessId();307 }308 309 inline int waitpid(pid_t pid, int *status, int)310 {311 return 0;312 }313 314 //this shouldn't be needed.315 struct statfs316 {317 TCHAR f_mntonname[MAX_PATH];318 };319 320 struct emu_stat {321 int st_dev;322 uint64_t st_ino;323 DWORD st_mode;324 short st_nlink;325 short st_uid;326 short st_gid;327 //_dev_t st_rdev;328 uint64_t st_size;329 time_t st_atime;330 time_t st_mtime;331 time_t st_ctime;332 };333 334 // need this for conversions335 time_t ConvertFileTimeToTime_t(FILETIME *fileTime);336 bool ConvertTime_tToFileTime(const time_t from, FILETIME *pTo);337 338 int emu_chdir (const char* pDirName);339 int emu_mkdir (const char* pPathName);340 int emu_unlink (const char* pFileName);341 int emu_fstat (HANDLE file, struct emu_stat* st);342 int emu_stat (const char* pName, struct emu_stat* st);343 int emu_utimes (const char* pName, const struct timeval[]);344 int emu_chmod (const char* pName, mode_t mode);345 char* emu_getcwd (char* pBuffer, int BufSize);346 int emu_rename (const char* pOldName, const char* pNewName);347 348 #define chdir(directory) emu_chdir (directory)349 #define mkdir(path, mode) emu_mkdir (path)350 #define unlink(file) emu_unlink (file)351 #define utimes(buffer, times) emu_utimes (buffer, times)352 #define chmod(file, mode) emu_chmod (file, mode)353 #define getcwd(buffer, size) emu_getcwd (buffer, size)354 #define rename(oldname, newname) emu_rename (oldname, newname)355 356 // Not safe to replace stat/fstat/lstat on mingw at least, as struct stat357 // has a 16-bit st_ino and we need a 64-bit one.358 //359 // #define stat(filename, struct) emu_stat (filename, struct)360 // #define lstat(filename, struct) emu_stat (filename, struct)361 // #define fstat(handle, struct) emu_fstat (handle, struct)362 //363 // But lstat doesn't exist on Windows, so we have to provide something:364 365 #define lstat(filename, struct) stat(filename, struct)366 367 int statfs(const char * name, struct statfs * s);368 369 int poll(struct pollfd *ufds, unsigned long nfds, int timeout);370 371 struct iovec {372 void *iov_base; /* Starting address */373 size_t iov_len; /* Number of bytes */374 };375 376 int readv (int filedes, const struct iovec *vector, size_t count);377 int writev(int filedes, const struct iovec *vector, size_t count);378 140 379 141 // The following functions are not emulations, but utilities for other … … 383 145 bool EnableBackupRights( void ); 384 146 385 bool ConvertEncoding (const std::string& rSource, int sourceCodePage,386 std::string& rDest, int destCodePage);387 bool ConvertToUtf8 (const std::string& rSource, std::string& rDest,388 int sourceCodePage);389 bool ConvertFromUtf8 (const std::string& rSource, std::string& rDest,390 int destCodePage);391 bool ConvertUtf8ToConsole(const std::string& rSource, std::string& rDest);392 bool ConvertConsoleToUtf8(const std::string& rSource, std::string& rDest);393 394 147 // Utility function which returns a default config file name, 395 148 // based on the path of the current executable. 396 149 std::string GetDefaultConfigFilePath(const std::string& rName); 397 398 // GetErrorMessage() returns a system error message, like strerror()399 // but for Windows error codes.400 std::string GetErrorMessage(DWORD errorCode);401 150 402 151 // console_read() is a replacement for _cgetws which requires a … … 405 154 406 155 #endif // !EMU_INCLUDE && WIN32 156 157 #endif -
box/invisnet/vs2010/0.11/lib/win32/getopt.h
r946 r3055 37 37 * POSSIBILITY OF SUCH DAMAGE. 38 38 */ 39 40 #ifdef WIN32 41 # pragma once 42 # ifdef __MINGW32__ 43 # define _GETOPT_H_ 44 # else 45 46 # endif 47 #endif 39 48 40 49 #ifndef _GETOPT_H_
Note: See TracChangeset
for help on using the changeset viewer.
