diff options
Diffstat (limited to 'src/OSSupport')
-rw-r--r-- | src/OSSupport/CriticalSection.h | 2 | ||||
-rw-r--r-- | src/OSSupport/Errors.cpp | 2 | ||||
-rw-r--r-- | src/OSSupport/File.cpp | 102 | ||||
-rw-r--r-- | src/OSSupport/File.h | 25 | ||||
-rw-r--r-- | src/OSSupport/Network.h | 2 | ||||
-rw-r--r-- | src/OSSupport/Semaphore.h | 2 | ||||
-rw-r--r-- | src/OSSupport/TCPLinkImpl.cpp | 6 | ||||
-rw-r--r-- | src/OSSupport/UDPEndpointImpl.cpp | 2 |
8 files changed, 130 insertions, 13 deletions
diff --git a/src/OSSupport/CriticalSection.h b/src/OSSupport/CriticalSection.h index d52f049d2..a95a9a0cd 100644 --- a/src/OSSupport/CriticalSection.h +++ b/src/OSSupport/CriticalSection.h @@ -13,7 +13,7 @@ public: void Lock(void); void Unlock(void); - // IsLocked/IsLockedByCurrentThread are only used in ASSERT statements, but because of the changes with ASSERT they must always be defined + // IsLocked / IsLockedByCurrentThread are only used in ASSERT statements, but because of the changes with ASSERT they must always be defined // The fake versions (in Release) will not effect the program in any way #ifdef _DEBUG cCriticalSection(void); diff --git a/src/OSSupport/Errors.cpp b/src/OSSupport/Errors.cpp index a5361e1a6..407799495 100644 --- a/src/OSSupport/Errors.cpp +++ b/src/OSSupport/Errors.cpp @@ -22,7 +22,7 @@ AString GetOSErrorString( int a_ErrNo) // According to http://linux.die.net/man/3/strerror_r there are two versions of strerror_r(): - #if !defined(__APPLE__) && ( _GNU_SOURCE) && !defined(ANDROID_NDK) // GNU version of strerror_r() + #if !defined(__APPLE__) && defined( _GNU_SOURCE) && !defined(ANDROID_NDK) // GNU version of strerror_r() char * res = strerror_r( errno, buffer, ARRAYCOUNT(buffer)); if (res != nullptr) diff --git a/src/OSSupport/File.cpp b/src/OSSupport/File.cpp index 8957dfaef..43105b230 100644 --- a/src/OSSupport/File.cpp +++ b/src/OSSupport/File.cpp @@ -453,6 +453,108 @@ AString cFile::ReadWholeFile(const AString & a_FileName) +AString cFile::ChangeFileExt(const AString & a_FileName, const AString & a_NewExt) +{ + auto res = a_FileName; + + // If the path separator is the last character of the string, return the string unmodified (refers to a folder): + #if defined(_MSC_VER) + // Find either path separator - MSVC CRT accepts slashes as separators, too + auto LastPathSep = res.find_last_of("/\\"); + #elif defined(_WIN32) + // Windows with different CRTs support only the backslash separator + auto LastPathSep = res.rfind('\\'); + #else + // Linux supports only the slash separator + auto LastPathSep = res.rfind('/'); + #endif + if ((LastPathSep != AString::npos) && (LastPathSep + 1 == res.size())) + { + return res; + } + + // Append or replace the extension: + auto DotPos = res.rfind('.'); + if ( + (DotPos == AString::npos) || // No dot found + ((LastPathSep != AString::npos) && (LastPathSep > DotPos)) // Last dot is before the last path separator (-> in folder name) + ) + { + // No extension, just append the new one: + if (!a_NewExt.empty() && (a_NewExt[0] != '.')) + { + // a_NewExt doesn't start with a dot, insert one: + res.push_back('.'); + } + res.append(a_NewExt); + } + else + { + // Replace existing extension: + if (!a_NewExt.empty() && (a_NewExt[0] != '.')) + { + // a_NewExt doesn't start with a dot, keep the current one: + res.erase(DotPos + 1, AString::npos); + } + else + { + res.erase(DotPos, AString::npos); + } + res.append(a_NewExt); + } + return res; +} + + + + + +unsigned cFile::GetLastModificationTime(const AString & a_FileName) +{ + struct stat st; + if (stat(a_FileName.c_str(), &st) < 0) + { + return 0; + } + #ifdef _WIN32 + // Windows returns times in local time already + return static_cast<unsigned>(st.st_mtime); + #else + // Linux returns UTC time, convert to local timezone: + return static_cast<unsigned>(mktime(localtime(&st.st_mtime))); + #endif +} + + + + + +AString cFile::GetPathSeparator(void) +{ + #ifdef _WIN32 + return "\\"; + #else + return "/"; + #endif +} + + + + + +AString cFile::GetExecutableExt(void) +{ + #ifdef _WIN32 + return ".exe"; + #else + return ""; + #endif +} + + + + + int cFile::Printf(const char * a_Fmt, ...) { AString buf; diff --git a/src/OSSupport/File.h b/src/OSSupport/File.h index ac6d1ab21..1b5e71a17 100644 --- a/src/OSSupport/File.h +++ b/src/OSSupport/File.h @@ -62,7 +62,7 @@ public: { fmRead, // Read-only. If the file doesn't exist, object will not be valid fmWrite, // Write-only. If the file already exists, it will be overwritten - fmReadWrite, // Read/write. If the file already exists, it will be left intact; writing will overwrite the data from the beginning + fmReadWrite, // Read / write. If the file already exists, it will be left intact; writing will overwrite the data from the beginning fmAppend // Write-only. If the file already exists cursor will be moved to the end of the file } ; @@ -124,9 +124,30 @@ public: /** Creates a new folder with the specified name. Returns true if successful. Path may be relative or absolute */ static bool CreateFolder(const AString & a_FolderPath); - /** Returns the entire contents of the specified file as a string. Returns empty string on error. */ + // tolua_end + + /** Returns the entire contents of the specified file as a string. Returns empty string on error. + Exported manually in ManualBindings.cpp due to #1914 - ToLua code doesn't work well with binary files. */ static AString ReadWholeFile(const AString & a_FileName); + // tolua_begin + + /** Returns a_FileName with its extension changed to a_NewExt. + a_FileName may contain path specification. */ + static AString ChangeFileExt(const AString & a_FileName, const AString & a_NewExt); + + /** Returns the last modification time (in current timezone) of the specified file. + The value returned is in the same units as the value returned by time() function. + If the file is not found / accessible, zero is returned. */ + static unsigned GetLastModificationTime(const AString & a_FileName); + + /** Returns the path separator used by the current platform. + Note that the platform / CRT may support additional path separators (such as slashes on Windows), these don't get reported. */ + static AString GetPathSeparator(void); + + /** Returns the customary executable extension used by the current platform. */ + static AString GetExecutableExt(void); + // tolua_end /** Returns the list of all items in the specified folder (files, folders, nix pipes, whatever's there). */ diff --git a/src/OSSupport/Network.h b/src/OSSupport/Network.h index 95a935bbe..1162d7fc6 100644 --- a/src/OSSupport/Network.h +++ b/src/OSSupport/Network.h @@ -162,7 +162,7 @@ public: /** Returns the local port to which the underlying socket is bound. */ virtual UInt16 GetPort(void) const = 0; - /** Sends the specified payload in a single UDP datagram to the specified host+port combination. + /** Sends the specified payload in a single UDP datagram to the specified host + port combination. Note that in order to send to a broadcast address, you need to call EnableBroadcasts() first. */ virtual bool Send(const AString & a_Payload, const AString & a_Host, UInt16 a_Port) = 0; diff --git a/src/OSSupport/Semaphore.h b/src/OSSupport/Semaphore.h index adc531ed8..57fa4bdb2 100644 --- a/src/OSSupport/Semaphore.h +++ b/src/OSSupport/Semaphore.h @@ -9,7 +9,7 @@ public: void Wait(); void Signal(); private: - void* m_Handle; // HANDLE pointer + void * m_Handle; // HANDLE pointer #ifndef _WIN32 bool m_bNamed; diff --git a/src/OSSupport/TCPLinkImpl.cpp b/src/OSSupport/TCPLinkImpl.cpp index c6f1978ad..ae6ba04f1 100644 --- a/src/OSSupport/TCPLinkImpl.cpp +++ b/src/OSSupport/TCPLinkImpl.cpp @@ -23,7 +23,6 @@ cTCPLinkImpl::cTCPLinkImpl(cTCPLink::cCallbacksPtr a_LinkCallbacks): m_RemotePort(0), m_ShouldShutdown(false) { - LOGD("Created new cTCPLinkImpl at %p with BufferEvent at %p", this, m_BufferEvent); } @@ -38,8 +37,6 @@ cTCPLinkImpl::cTCPLinkImpl(evutil_socket_t a_Socket, cTCPLink::cCallbacksPtr a_L m_RemotePort(0), m_ShouldShutdown(false) { - LOGD("Created new cTCPLinkImpl at %p with BufferEvent at %p", this, m_BufferEvent); - // Update the endpoint addresses: UpdateLocalAddress(); UpdateAddress(a_Address, a_AddrLen, m_RemoteIP, m_RemotePort); @@ -51,7 +48,6 @@ cTCPLinkImpl::cTCPLinkImpl(evutil_socket_t a_Socket, cTCPLink::cCallbacksPtr a_L cTCPLinkImpl::~cTCPLinkImpl() { - LOGD("Deleting cTCPLinkImpl at %p with BufferEvent at %p", this, m_BufferEvent); bufferevent_free(m_BufferEvent); } @@ -216,8 +212,6 @@ void cTCPLinkImpl::WriteCallback(bufferevent * a_BufferEvent, void * a_Self) void cTCPLinkImpl::EventCallback(bufferevent * a_BufferEvent, short a_What, void * a_Self) { - LOGD("cTCPLink event callback for link %p, BEV %p; what = 0x%02x", a_Self, a_BufferEvent, a_What); - ASSERT(a_Self != nullptr); cTCPLinkImplPtr Self = static_cast<cTCPLinkImpl *>(a_Self)->m_Self; diff --git a/src/OSSupport/UDPEndpointImpl.cpp b/src/OSSupport/UDPEndpointImpl.cpp index 31ca107ce..68117e5a0 100644 --- a/src/OSSupport/UDPEndpointImpl.cpp +++ b/src/OSSupport/UDPEndpointImpl.cpp @@ -384,7 +384,7 @@ void cUDPEndpointImpl::Open(UInt16 a_Port) // Failed to create IPv6 socket, create an IPv4 one instead: m_IsMainSockIPv6 = false; err = EVUTIL_SOCKET_ERROR(); - LOGD("Failed to create IPv6 MainSock: %d (%s)", err, evutil_socket_error_to_string(err)); + LOGD("UDP: Failed to create IPv6 MainSock: %d (%s)", err, evutil_socket_error_to_string(err)); m_MainSock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); if (!IsValidSocket(m_MainSock)) { |