CriticalSectionCreate(CRITSECT_HANDLE * CritSection)1 static inline bool CriticalSectionCreate(CRITSECT_HANDLE *CritSection)
2 {
3 #ifdef _WIN_ALL
4 InitializeCriticalSection(CritSection);
5 return true;
6 #elif defined(_UNIX)
7 return pthread_mutex_init(CritSection,NULL)==0;
8 #endif
9 }
10
11
CriticalSectionDelete(CRITSECT_HANDLE * CritSection)12 static inline void CriticalSectionDelete(CRITSECT_HANDLE *CritSection)
13 {
14 #ifdef _WIN_ALL
15 DeleteCriticalSection(CritSection);
16 #elif defined(_UNIX)
17 pthread_mutex_destroy(CritSection);
18 #endif
19 }
20
21
CriticalSectionStart(CRITSECT_HANDLE * CritSection)22 static inline void CriticalSectionStart(CRITSECT_HANDLE *CritSection)
23 {
24 #ifdef _WIN_ALL
25 EnterCriticalSection(CritSection);
26 #elif defined(_UNIX)
27 pthread_mutex_lock(CritSection);
28 #endif
29 }
30
31
CriticalSectionEnd(CRITSECT_HANDLE * CritSection)32 static inline void CriticalSectionEnd(CRITSECT_HANDLE *CritSection)
33 {
34 #ifdef _WIN_ALL
35 LeaveCriticalSection(CritSection);
36 #elif defined(_UNIX)
37 pthread_mutex_unlock(CritSection);
38 #endif
39 }
40
41
ThreadCreate(NATIVE_THREAD_PTR Proc,void * Data)42 static THREAD_HANDLE ThreadCreate(NATIVE_THREAD_PTR Proc,void *Data)
43 {
44 #ifdef _UNIX
45 /*
46 pthread_attr_t attr;
47 pthread_attr_init(&attr);
48 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
49 */
50 pthread_t pt;
51 int Code=pthread_create(&pt,NULL/*&attr*/,Proc,Data);
52 if (Code!=0)
53 {
54 wchar Msg[100];
55 swprintf(Msg,ASIZE(Msg),L"\npthread_create failed, code %d\n",Code);
56 ErrHandler.GeneralErrMsg(Msg);
57 ErrHandler.SysErrMsg();
58 ErrHandler.Exit(RARX_FATAL);
59 }
60 return pt;
61 #else
62 DWORD ThreadId;
63 HANDLE hThread=CreateThread(NULL,0x10000,Proc,Data,0,&ThreadId);
64 if (hThread==NULL)
65 {
66 ErrHandler.GeneralErrMsg(L"CreateThread failed");
67 ErrHandler.SysErrMsg();
68 ErrHandler.Exit(RARX_FATAL);
69 }
70 return hThread;
71 #endif
72 }
73
74
ThreadClose(THREAD_HANDLE hThread)75 static void ThreadClose(THREAD_HANDLE hThread)
76 {
77 #ifdef _UNIX
78 pthread_join(hThread,NULL);
79 #else
80 CloseHandle(hThread);
81 #endif
82 }
83
84
85 #ifdef _WIN_ALL
CWaitForSingleObject(HANDLE hHandle)86 static void CWaitForSingleObject(HANDLE hHandle)
87 {
88 DWORD rc=WaitForSingleObject(hHandle,INFINITE);
89 if (rc==WAIT_FAILED)
90 {
91 ErrHandler.GeneralErrMsg(L"\nWaitForMultipleObjects error %d, GetLastError %d",rc,GetLastError());
92 ErrHandler.Exit(RARX_FATAL);
93 }
94 }
95 #endif
96
97
98 #ifdef _UNIX
cpthread_cond_wait(pthread_cond_t * cond,pthread_mutex_t * mutex)99 static void cpthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex)
100 {
101 int rc=pthread_cond_wait(cond,mutex);
102 if (rc!=0)
103 {
104 ErrHandler.GeneralErrMsg(L"\npthread_cond_wait error %d",rc);
105 ErrHandler.Exit(RARX_FATAL);
106 }
107 }
108 #endif
109
110
GetNumberOfCPU()111 uint GetNumberOfCPU()
112 {
113 #ifndef RAR_SMP
114 return 1;
115 #else
116 #ifdef _UNIX
117 #ifdef _SC_NPROCESSORS_ONLN
118 uint Count=(uint)sysconf(_SC_NPROCESSORS_ONLN);
119 return Count<1 ? 1:Count;
120 #elif defined(_APPLE)
121 uint Count;
122 size_t Size=sizeof(Count);
123 return sysctlbyname("hw.ncpu",&Count,&Size,NULL,0)==0 ? Count:1;
124 #endif
125 #else // !_UNIX
126 DWORD_PTR ProcessMask;
127 DWORD_PTR SystemMask;
128
129 if (!GetProcessAffinityMask(GetCurrentProcess(),&ProcessMask,&SystemMask))
130 return 1;
131 uint Count=0;
132 for (DWORD_PTR Mask=1;Mask!=0;Mask<<=1)
133 if ((ProcessMask & Mask)!=0)
134 Count++;
135 return Count<1 ? 1:Count;
136 #endif
137
138 #endif // RAR_SMP
139 }
140
141
GetNumberOfThreads()142 uint GetNumberOfThreads()
143 {
144 uint NumCPU=GetNumberOfCPU();
145 if (NumCPU<1)
146 return 1;
147 if (NumCPU>MaxPoolThreads)
148 return MaxPoolThreads;
149 return NumCPU;
150 }
151
152