rc_compat.c (2661B)
1 #include "rc_compat.h" 2 3 #include <ctype.h> 4 #include <stdarg.h> 5 6 #ifdef RC_C89_HELPERS 7 8 int rc_strncasecmp(const char* left, const char* right, size_t length) 9 { 10 while (length) 11 { 12 if (*left != *right) 13 { 14 const int diff = tolower(*left) - tolower(*right); 15 if (diff != 0) 16 return diff; 17 } 18 19 ++left; 20 ++right; 21 --length; 22 } 23 24 return 0; 25 } 26 27 int rc_strcasecmp(const char* left, const char* right) 28 { 29 while (*left || *right) 30 { 31 if (*left != *right) 32 { 33 const int diff = tolower(*left) - tolower(*right); 34 if (diff != 0) 35 return diff; 36 } 37 38 ++left; 39 ++right; 40 } 41 42 return 0; 43 } 44 45 char* rc_strdup(const char* str) 46 { 47 const size_t length = strlen(str); 48 char* buffer = (char*)malloc(length + 1); 49 if (buffer) 50 memcpy(buffer, str, length + 1); 51 return buffer; 52 } 53 54 int rc_snprintf(char* buffer, size_t size, const char* format, ...) 55 { 56 int result; 57 va_list args; 58 59 va_start(args, format); 60 61 #ifdef __STDC_WANT_SECURE_LIB__ 62 result = vsprintf_s(buffer, size, format, args); 63 #else 64 /* assume buffer is large enough and ignore size */ 65 (void)size; 66 result = vsprintf(buffer, format, args); 67 #endif 68 69 va_end(args); 70 71 return result; 72 } 73 74 #endif 75 76 #ifndef __STDC_WANT_SECURE_LIB__ 77 78 struct tm* rc_gmtime_s(struct tm* buf, const time_t* timer) 79 { 80 struct tm* tm = gmtime(timer); 81 memcpy(buf, tm, sizeof(*tm)); 82 return buf; 83 } 84 85 #endif 86 87 #ifndef RC_NO_THREADS 88 89 #if defined(_WIN32) 90 91 /* https://gist.github.com/roxlu/1c1af99f92bafff9d8d9 */ 92 93 #define WIN32_LEAN_AND_MEAN 94 #include <windows.h> 95 96 void rc_mutex_init(rc_mutex_t* mutex) 97 { 98 /* default security, not owned by calling thread, unnamed */ 99 mutex->handle = CreateMutex(NULL, FALSE, NULL); 100 } 101 102 void rc_mutex_destroy(rc_mutex_t* mutex) 103 { 104 CloseHandle(mutex->handle); 105 } 106 107 void rc_mutex_lock(rc_mutex_t* mutex) 108 { 109 WaitForSingleObject(mutex->handle, 0xFFFFFFFF); 110 } 111 112 void rc_mutex_unlock(rc_mutex_t* mutex) 113 { 114 ReleaseMutex(mutex->handle); 115 } 116 117 #elif defined(GEKKO) 118 119 /* https://github.com/libretro/RetroArch/pull/16116 */ 120 121 void rc_mutex_init(rc_mutex_t* mutex) 122 { 123 LWP_MutexInit(mutex, NULL); 124 } 125 126 void rc_mutex_destroy(rc_mutex_t* mutex) 127 { 128 LWP_MutexDestroy(mutex); 129 } 130 131 void rc_mutex_lock(rc_mutex_t* mutex) 132 { 133 LWP_MutexLock(mutex); 134 } 135 136 void rc_mutex_unlock(rc_mutex_t* mutex) 137 { 138 LWP_MutexUnlock(mutex); 139 } 140 141 #else 142 143 void rc_mutex_init(rc_mutex_t* mutex) 144 { 145 pthread_mutex_init(mutex, NULL); 146 } 147 148 void rc_mutex_destroy(rc_mutex_t* mutex) 149 { 150 pthread_mutex_destroy(mutex); 151 } 152 153 void rc_mutex_lock(rc_mutex_t* mutex) 154 { 155 pthread_mutex_lock(mutex); 156 } 157 158 void rc_mutex_unlock(rc_mutex_t* mutex) 159 { 160 pthread_mutex_unlock(mutex); 161 } 162 163 #endif 164 #endif /* RC_NO_THREADS */