ObjFW  Check-in [d7fd999fee]

Overview
Comment:{condition,mutex,thread}.m: Set errno on error
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA3-256: d7fd999feea8b67279712cc9b18c2ff51434cdaa218df310db12d9503006cbf7
User & Date: js on 2019-09-01 12:50:08
Other Links: manifest | tags
Context
2019-09-01
13:49
OFCondition: Support waiting for Exec Signals check-in: 92d63d6367 user: js tags: trunk
12:50
{condition,mutex,thread}.m: Set errno on error check-in: d7fd999fee user: js tags: trunk
2019-08-31
17:13
Make -[OFKernelEventObserver cancel] work on Amiga check-in: 8941b1d974 user: js tags: trunk
Changes

Modified src/OFCondition.m from [42e8f34c96] to [f1fb27ae31].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFCondition.h"
#import "OFDate.h"

#import "OFConditionBroadcastFailedException.h"
#import "OFConditionSignalFailedException.h"
#import "OFConditionStillWaitingException.h"







>
>







12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <errno.h>

#import "OFCondition.h"
#import "OFDate.h"

#import "OFConditionBroadcastFailedException.h"
#import "OFConditionSignalFailedException.h"
#import "OFConditionStillWaitingException.h"
45
46
47
48
49
50
51
52
53


54
55


56
57
58
59
60
61
62
63
64

65
66
67
68
69









70
71
72
73
74
75
76
77
78
79
80
81
82

83
84
85
86
87
88
89

90
91
	_conditionInitialized = true;

	return self;
}

- (void)dealloc
{
	if (_conditionInitialized)
		if (!of_condition_free(&_condition))


			@throw [OFConditionStillWaitingException
			    exceptionWithCondition: self];



	[super dealloc];
}

- (void)wait
{
	if (!of_condition_wait(&_condition, &_mutex))
		@throw [OFConditionWaitFailedException
		    exceptionWithCondition: self];

}

- (bool)waitForTimeInterval: (of_time_interval_t)timeInterval
{
	return of_condition_timed_wait(&_condition, &_mutex, timeInterval);









}

- (bool)waitUntilDate: (OFDate *)date
{
	return of_condition_timed_wait(&_condition, &_mutex,
	    date.timeIntervalSinceNow);
}

- (void)signal
{
	if (!of_condition_signal(&_condition))
		@throw [OFConditionSignalFailedException
		    exceptionWithCondition: self];

}

- (void)broadcast
{
	if (!of_condition_broadcast(&_condition))
		@throw [OFConditionBroadcastFailedException
		    exceptionWithCondition: self];

}
@end







|
|
>
>


>
>








|
>




|
>
>
>
>
>
>
>
>
>




<
|






|
>






|
>


47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89

90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
	_conditionInitialized = true;

	return self;
}

- (void)dealloc
{
	if (_conditionInitialized) {
		if (!of_condition_free(&_condition)) {
			OF_ENSURE(errno == EBUSY);

			@throw [OFConditionStillWaitingException
			    exceptionWithCondition: self];
		}
	}

	[super dealloc];
}

- (void)wait
{
	if (!of_condition_wait(&_condition, &_mutex))
		@throw [OFConditionWaitFailedException
		    exceptionWithCondition: self
				     errNo: errno];
}

- (bool)waitForTimeInterval: (of_time_interval_t)timeInterval
{
	if (!of_condition_timed_wait(&_condition, &_mutex, timeInterval)) {
		if (errno == ETIMEDOUT)
			return false;
		else
			@throw [OFConditionWaitFailedException
			    exceptionWithCondition: self
					     errNo: errno];
	}

	return true;
}

- (bool)waitUntilDate: (OFDate *)date
{

	return [self waitForTimeInterval: date.timeIntervalSinceNow];
}

- (void)signal
{
	if (!of_condition_signal(&_condition))
		@throw [OFConditionSignalFailedException
		    exceptionWithCondition: self
				     errNo: errno];
}

- (void)broadcast
{
	if (!of_condition_broadcast(&_condition))
		@throw [OFConditionBroadcastFailedException
		    exceptionWithCondition: self
				     errNo: errno];
}
@end

Modified src/OFMutex.m from [99a3d0e9e5] to [2faea18a32].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFMutex.h"
#import "OFString.h"

#import "OFInitializationFailedException.h"
#import "OFLockFailedException.h"
#import "OFStillLockedException.h"







>
>







12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <errno.h>

#import "OFMutex.h"
#import "OFString.h"

#import "OFInitializationFailedException.h"
#import "OFLockFailedException.h"
#import "OFStillLockedException.h"
46
47
48
49
50
51
52
53
54


55


56
57
58
59
60
61
62
63
64
65

66
67
68
69
70








71
72
73
74
75
76

77
78
79
80
81
82
83
84
85
86
	_initialized = true;

	return self;
}

- (void)dealloc
{
	if (_initialized)
		if (!of_mutex_free(&_mutex))


			@throw [OFStillLockedException exceptionWithLock: self];



	[_name release];

	[super dealloc];
}

- (void)lock
{
	if (!of_mutex_lock(&_mutex))
		@throw [OFLockFailedException exceptionWithLock: self];

}

- (bool)tryLock
{
	return of_mutex_trylock(&_mutex);








}

- (void)unlock
{
	if (!of_mutex_unlock(&_mutex))
		@throw [OFUnlockFailedException exceptionWithLock: self];

}

- (OFString *)description
{
	if (_name == nil)
		return super.description;

	return [OFString stringWithFormat: @"<%@: %@>", self.className, _name];
}
@end







|
|
>
>

>
>









|
>




|
>
>
>
>
>
>
>
>





|
>










48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
	_initialized = true;

	return self;
}

- (void)dealloc
{
	if (_initialized) {
		if (!of_mutex_free(&_mutex)) {
			OF_ENSURE(errno == EBUSY);

			@throw [OFStillLockedException exceptionWithLock: self];
		}
	}

	[_name release];

	[super dealloc];
}

- (void)lock
{
	if (!of_mutex_lock(&_mutex))
		@throw [OFLockFailedException exceptionWithLock: self
							  errNo: errno];
}

- (bool)tryLock
{
	if (!of_mutex_trylock(&_mutex)) {
		if (errno == EBUSY)
			return false;
		else
			@throw [OFLockFailedException exceptionWithLock: self
								  errNo: errno];
	}

	return true;
}

- (void)unlock
{
	if (!of_mutex_unlock(&_mutex))
		@throw [OFUnlockFailedException exceptionWithLock: self
							    errNo: errno];
}

- (OFString *)description
{
	if (_name == nil)
		return super.description;

	return [OFString stringWithFormat: @"<%@: %@>", self.className, _name];
}
@end

Modified src/OFRecursiveMutex.m from [2beeb530a3] to [9a715b3943].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFRecursiveMutex.h"
#import "OFString.h"

#import "OFInitializationFailedException.h"
#import "OFLockFailedException.h"
#import "OFStillLockedException.h"







>
>







12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <errno.h>

#import "OFRecursiveMutex.h"
#import "OFString.h"

#import "OFInitializationFailedException.h"
#import "OFLockFailedException.h"
#import "OFStillLockedException.h"
46
47
48
49
50
51
52
53
54


55


56
57
58
59
60
61
62
63
64
65

66
67
68
69
70








71
72
73
74
75
76

77
78
79
80
81
82
83
84
85
86
	_initialized = true;

	return self;
}

- (void)dealloc
{
	if (_initialized)
		if (!of_rmutex_free(&_rmutex))


			@throw [OFStillLockedException exceptionWithLock: self];



	[_name release];

	[super dealloc];
}

- (void)lock
{
	if (!of_rmutex_lock(&_rmutex))
		@throw [OFLockFailedException exceptionWithLock: self];

}

- (bool)tryLock
{
	return of_rmutex_trylock(&_rmutex);








}

- (void)unlock
{
	if (!of_rmutex_unlock(&_rmutex))
		@throw [OFUnlockFailedException exceptionWithLock: self];

}

- (OFString *)description
{
	if (_name == nil)
		return super.description;

	return [OFString stringWithFormat: @"<%@: %@>", self.className, _name];
}
@end







|
|
>
>

>
>









|
>




|
>
>
>
>
>
>
>
>





|
>










48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
	_initialized = true;

	return self;
}

- (void)dealloc
{
	if (_initialized) {
		if (!of_rmutex_free(&_rmutex)) {
			OF_ENSURE(errno == EBUSY);

			@throw [OFStillLockedException exceptionWithLock: self];
		}
	}

	[_name release];

	[super dealloc];
}

- (void)lock
{
	if (!of_rmutex_lock(&_rmutex))
		@throw [OFLockFailedException exceptionWithLock: self
							  errNo: errno];
}

- (bool)tryLock
{
	if (!of_rmutex_trylock(&_rmutex)) {
		if (errno == EBUSY)
			return false;
		else
			@throw [OFLockFailedException exceptionWithLock: self
								  errNo: errno];
	}

	return true;
}

- (void)unlock
{
	if (!of_rmutex_unlock(&_rmutex))
		@throw [OFUnlockFailedException exceptionWithLock: self
							    errNo: errno];
}

- (OFString *)description
{
	if (_name == nil)
		return super.description;

	return [OFString stringWithFormat: @"<%@: %@>", self.className, _name];
}
@end

Modified src/OFThread.m from [d2706d56fe] to [fe6d085eae].

16
17
18
19
20
21
22


23
24
25
26
27
28
29
 */

#define OF_THREAD_M
#define _POSIX_TIMERS
#define __NO_EXT_QNX

#include "config.h"



#include <stdlib.h>
#include <math.h>
#include <time.h>

#ifdef OF_HAVE_SCHED_YIELD
# include <sched.h>







>
>







16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
 */

#define OF_THREAD_M
#define _POSIX_TIMERS
#define __NO_EXT_QNX

#include "config.h"

#include <errno.h>

#include <stdlib.h>
#include <math.h>
#include <time.h>

#ifdef OF_HAVE_SCHED_YIELD
# include <sched.h>
411
412
413
414
415
416
417
418


419
420
421
422
423
424
425






426
427
428
429
430
431
432

	[self retain];

	_running = OF_THREAD_RUNNING;

	if (!of_thread_new(&_thread, callMain, self, &_attr)) {
		[self release];
		@throw [OFThreadStartFailedException exceptionWithThread: self];


	}
}

- (id)join
{
	if (_running == OF_THREAD_NOT_RUNNING || !of_thread_join(_thread))
		@throw [OFThreadJoinFailedException exceptionWithThread: self];







	_running = OF_THREAD_NOT_RUNNING;

	return _returnValue;
}

- (id)copy







|
>
>





|
|
>
>
>
>
>
>







413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442

	[self retain];

	_running = OF_THREAD_RUNNING;

	if (!of_thread_new(&_thread, callMain, self, &_attr)) {
		[self release];
		@throw [OFThreadStartFailedException
		    exceptionWithThread: self
				  errNo: errno];
	}
}

- (id)join
{
	if (_running == OF_THREAD_NOT_RUNNING)
		@throw [OFThreadJoinFailedException
		    exceptionWithThread: self
				  errNo: EINVAL];

	if (!of_thread_join(_thread))
		@throw [OFThreadJoinFailedException exceptionWithThread: self
								  errNo: errno];

	_running = OF_THREAD_NOT_RUNNING;

	return _returnValue;
}

- (id)copy

Modified src/condition_amiga.m from [3b25e0b426] to [e20e2745b3].

10
11
12
13
14
15
16


17
18
19
20
21
22
23
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */



#include <proto/exec.h>
#include <devices/timer.h>
#ifndef OF_AMIGAOS4
# include <clib/alib_protos.h>
#endif








>
>







10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <errno.h>

#include <proto/exec.h>
#include <devices/timer.h>
#ifndef OF_AMIGAOS4
# include <clib/alib_protos.h>
#endif

74
75
76
77
78
79
80
81

82

83
84
85
86
87
88
89
{
	struct of_condition_waiting_task waitingTask = {
		.task = FindTask(NULL),
		.sigBit = AllocSignal(-1)
	};
	bool ret;

	if (waitingTask.sigBit == -1)

		return false;


	Forbid();

	if (!of_mutex_unlock(mutex)) {
		FreeSignal(waitingTask.sigBit);
		return false;
	}







|
>

>







76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
{
	struct of_condition_waiting_task waitingTask = {
		.task = FindTask(NULL),
		.sigBit = AllocSignal(-1)
	};
	bool ret;

	if (waitingTask.sigBit == -1) {
		errno = EAGAIN;
		return false;
	}

	Forbid();

	if (!of_mutex_unlock(mutex)) {
		FreeSignal(waitingTask.sigBit);
		return false;
	}
146
147
148
149
150
151
152
153

154
155

156
157

158

159
160
161
162
163
164
165
166
167
168
169
170
171

172
173











174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207

208

209
210
211
212
213
214
		}
	};
	ULONG mask;
	bool ret;

	NewList(&port.mp_MsgList);

	if (waitingTask.sigBit == -1 || port.mp_SigBit == -1)

		goto fail;


	if (OpenDevice("timer.device", UNIT_MICROHZ,
	    (struct IORequest *)&request, 0) != 0)

		goto fail;


	Forbid();

	if (!of_mutex_unlock(mutex)) {
		Permit();
		goto fail;
	}

	waitingTask.next = condition->waitingTasks;
	condition->waitingTasks = &waitingTask;

	SendIO((struct IORequest *)&request);


	mask = Wait((1 << waitingTask.sigBit) | (1 << port.mp_SigBit));
	ret = of_mutex_lock(mutex);












	condition->waitingTasks = waitingTask.next;

	if (!CheckIO((struct IORequest *)&request)) {
		AbortIO((struct IORequest *)&request);
		WaitIO((struct IORequest *)&request);
	}
	CloseDevice((struct IORequest *)&request);

	Permit();

	if (!(mask & (1 << waitingTask.sigBit)))
		goto fail;

	FreeSignal(waitingTask.sigBit);
	FreeSignal(port.mp_SigBit);

	return ret;

fail:
	if (waitingTask.sigBit != -1)
		FreeSignal(waitingTask.sigBit);
	if (port.mp_SigBit != -1)
		FreeSignal(port.mp_SigBit);

	return false;
}

bool
of_condition_free(of_condition_t *condition)
{
	Forbid();
	@try {
		if (condition->waitingTasks != NULL)

			return false;

	} @finally {
		Permit();
	}

	return true;
}







|
>

|
>

|
>

>













>
|
|
>
>
>
>
>
>
>
>
>
>
>











<
<
<



















|
>

>






150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204



205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
		}
	};
	ULONG mask;
	bool ret;

	NewList(&port.mp_MsgList);

	if (waitingTask.sigBit == -1 || port.mp_SigBit == -1) {
		errno = EAGAIN;
		goto fail;
	}

	if (OpenDevice("timer.device", UNIT_MICROHZ,
	    (struct IORequest *)&request, 0) != 0) {
		errno = EAGAIN;
		goto fail;
	}

	Forbid();

	if (!of_mutex_unlock(mutex)) {
		Permit();
		goto fail;
	}

	waitingTask.next = condition->waitingTasks;
	condition->waitingTasks = &waitingTask;

	SendIO((struct IORequest *)&request);

	mask = Wait((1ul << waitingTask.sigBit) | (1ul << port.mp_SigBit));
	if (mask & (1ul << waitingTask.sigBit))
		ret = of_mutex_lock(mutex);
	else if (mask & (1ul << port.mp_SigBit)) {
		ret = false;
		errno = ETIMEDOUT;
	} else {
		/*
		 * This should not happen - it means something interrupted the
		 * Wait(), so the best we can do is return EINTR.
		 */
		ret = false;
		errno = EINTR;
	}

	condition->waitingTasks = waitingTask.next;

	if (!CheckIO((struct IORequest *)&request)) {
		AbortIO((struct IORequest *)&request);
		WaitIO((struct IORequest *)&request);
	}
	CloseDevice((struct IORequest *)&request);

	Permit();




	FreeSignal(waitingTask.sigBit);
	FreeSignal(port.mp_SigBit);

	return ret;

fail:
	if (waitingTask.sigBit != -1)
		FreeSignal(waitingTask.sigBit);
	if (port.mp_SigBit != -1)
		FreeSignal(port.mp_SigBit);

	return false;
}

bool
of_condition_free(of_condition_t *condition)
{
	Forbid();
	@try {
		if (condition->waitingTasks != NULL) {
			errno = EBUSY;
			return false;
		}
	} @finally {
		Permit();
	}

	return true;
}

Modified src/condition_winapi.m from [ed44bca861] to [5ca478d4cb].

11
12
13
14
15
16
17


18
19
20
21
22
23

24

25
26
27
28
29
30
31
32










33
34
35
36
37
38
39
40
41



42





43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58


59




60


61

62

63
64
65
66
67
68
69
70
71
72
73
74
75
76
77


78


79







80

81

82
83
84
85
86
87

88

89
90
91
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */



bool
of_condition_new(of_condition_t *condition)
{
	condition->count = 0;

	if ((condition->event = CreateEvent(NULL, FALSE, 0, NULL)) == NULL)

		return false;


	return true;
}

bool
of_condition_signal(of_condition_t *condition)
{
	return SetEvent(condition->event);










}

bool
of_condition_broadcast(of_condition_t *condition)
{
	int count = condition->count;

	for (int i = 0; i < count; i++)
		if (!SetEvent(condition->event))



			return false;






	return true;
}

bool
of_condition_wait(of_condition_t *condition, of_mutex_t *mutex)
{
	DWORD status;

	if (!of_mutex_unlock(mutex))
		return false;

	of_atomic_int_inc(&condition->count);
	status = WaitForSingleObject(condition->event, INFINITE);
	of_atomic_int_dec(&condition->count);



	if (!of_mutex_lock(mutex))




		return false;




	return (status == WAIT_OBJECT_0);

}

bool
of_condition_timed_wait(of_condition_t *condition, of_mutex_t *mutex,
    of_time_interval_t timeout)
{
	DWORD status;

	if (!of_mutex_unlock(mutex))
		return false;

	of_atomic_int_inc(&condition->count);
	status = WaitForSingleObject(condition->event, timeout * 1000);
	of_atomic_int_dec(&condition->count);



	if (!of_mutex_lock(mutex))


		return false;









	return (status == WAIT_OBJECT_0);

}

bool
of_condition_free(of_condition_t *condition)
{
	if (condition->count != 0)

		return false;


	return CloseHandle(condition->event);
}







>
>





|
>

>







|
>
>
>
>
>
>
>
>
>
>







|
|
>
>
>
|
>
>
>
>
>
















>
>
|
>
>
>
>
|
>
>
|
>
|
>















>
>
|
>
>

>
>
>
>
>
>
>
|
>
|
>





|
>

>



11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <errno.h>

bool
of_condition_new(of_condition_t *condition)
{
	condition->count = 0;

	if ((condition->event = CreateEvent(NULL, FALSE, 0, NULL)) == NULL) {
		errno = EAGAIN;
		return false;
	}

	return true;
}

bool
of_condition_signal(of_condition_t *condition)
{
	if (!SetEvent(condition->event)) {
		switch (GetLastError()) {
		case ERROR_INVALID_HANDLE:
			errno = EINVAL;
			return false;
		default:
			OF_ENSURE(0);
		}
	}

	return true;
}

bool
of_condition_broadcast(of_condition_t *condition)
{
	int count = condition->count;

	for (int i = 0; i < count; i++) {
		if (!SetEvent(condition->event)) {
			switch (GetLastError()) {
			case ERROR_INVALID_HANDLE:
				errno = EINVAL;
				return false;
			default:
				OF_ENSURE(0);
			}
		}
	}

	return true;
}

bool
of_condition_wait(of_condition_t *condition, of_mutex_t *mutex)
{
	DWORD status;

	if (!of_mutex_unlock(mutex))
		return false;

	of_atomic_int_inc(&condition->count);
	status = WaitForSingleObject(condition->event, INFINITE);
	of_atomic_int_dec(&condition->count);

	switch (status) {
	case WAIT_OBJECT_0:
		return of_mutex_lock(mutex);
	case WAIT_FAILED:
		switch (GetLastError()) {
		case ERROR_INVALID_HANDLE:
			errno = EINVAL;
			return false;
		default:
			OF_ENSURE(0);
		}
	default:
		OF_ENSURE(0);
	}
}

bool
of_condition_timed_wait(of_condition_t *condition, of_mutex_t *mutex,
    of_time_interval_t timeout)
{
	DWORD status;

	if (!of_mutex_unlock(mutex))
		return false;

	of_atomic_int_inc(&condition->count);
	status = WaitForSingleObject(condition->event, timeout * 1000);
	of_atomic_int_dec(&condition->count);

	switch (status) {
	case WAIT_OBJECT_0:
		return of_mutex_lock(mutex);
	case WAIT_TIMEOUT:
		errno = ETIMEDOUT;
		return false;
	case WAIT_FAILED:
		switch (GetLastError()) {
		case ERROR_INVALID_HANDLE:
			errno = EINVAL;
			return false;
		default:
			OF_ENSURE(0);
		}
	default:
		OF_ENSURE(0);
	}
}

bool
of_condition_free(of_condition_t *condition)
{
	if (condition->count != 0) {
		errno = EBUSY;
		return false;
	}

	return CloseHandle(condition->event);
}

Modified src/exceptions/OFConditionBroadcastFailedException.h from [dc014de8a0] to [920bf682d2].

31
32
33
34
35
36
37

38
39
40
41
42
43
44





45
46
47
48

49
50
51

52
53
54
55
56

57
58
59
60


61
62
63
 *	  ObjFW/OFConditionBroadcastFailedException.h
 *
 * @brief An exception indicating broadcasting a condition failed.
 */
@interface OFConditionBroadcastFailedException: OFException
{
	OFCondition *_condition;

}

/*!
 * @brief The condition which could not be broadcasted.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFCondition *condition;






/*!
 * @brief Returns a new, autoreleased condition broadcast failed exception.
 *
 * @param condition The condition which could not be broadcasted

 * @return A new, autoreleased condition broadcast failed exception
 */
+ (instancetype)exceptionWithCondition: (nullable OFCondition *)condition;


/*!
 * @brief Initializes an already allocated condition broadcast failed exception.
 *
 * @param condition The condition which could not be broadcasted

 * @return An initialized condition broadcast failed exception
 */
- (instancetype)initWithCondition: (nullable OFCondition *)condition
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
 *	  ObjFW/OFConditionBroadcastFailedException.h
 *
 * @brief An exception indicating broadcasting a condition failed.
 */
@interface OFConditionBroadcastFailedException: OFException
{
	OFCondition *_condition;
	int _errNo;
}

/*!
 * @brief The condition which could not be broadcasted.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFCondition *condition;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Returns a new, autoreleased condition broadcast failed exception.
 *
 * @param condition The condition which could not be broadcasted
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased condition broadcast failed exception
 */
+ (instancetype)exceptionWithCondition: (nullable OFCondition *)condition
				 errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated condition broadcast failed exception.
 *
 * @param condition The condition which could not be broadcasted
 * @param errNo The errno of the error that occurred
 * @return An initialized condition broadcast failed exception
 */
- (instancetype)initWithCondition: (nullable OFCondition *)condition
			    errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFConditionBroadcastFailedException.m from [c0d37d74d8] to [104e48ed3e].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26
27

28
29
30
31
32
33
34
35
36
37

38
39
40
41

42
43
44





45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFConditionBroadcastFailedException.h"
#import "OFString.h"
#import "OFCondition.h"

@implementation OFConditionBroadcastFailedException
@synthesize condition = _condition;

+ (instancetype)exceptionWithCondition: (OFCondition *)condition

{
	return [[[self alloc] initWithCondition: condition] autorelease];
}

- (instancetype)init
{
	return [self initWithCondition: nil];
}

- (instancetype)initWithCondition: (OFCondition *)condition

{
	self = [super init];

	_condition = [condition retain];


	return self;
}






- (void)dealloc
{
	[_condition release];

	[super dealloc];
}

- (OFString *)description
{
	if (_condition != nil)
		return [OFString stringWithFormat:
		    @"Broadcasting a condition of type %@ failed!",
		    _condition.class];
	else
		return @"Broadcasting a condition failed!";
}
@end







>
>






|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
|
<
<


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

33



34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60

61
62
63


64
65
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFConditionBroadcastFailedException.h"
#import "OFString.h"
#import "OFCondition.h"

@implementation OFConditionBroadcastFailedException
@synthesize condition = _condition, errNo = _errNo;

+ (instancetype)exceptionWithCondition: (OFCondition *)condition
				 errNo: (int)errNo
{
	return [[[self alloc] initWithCondition: condition

					  errNo: errNo] autorelease];



}

- (instancetype)initWithCondition: (OFCondition *)condition
			    errNo: (int)errNo
{
	self = [super init];

	_condition = [condition retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_condition release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"Broadcasting a condition of type %@ failed: %s",
	    _condition.class, strerror(_errNo)];


}
@end

Modified src/exceptions/OFConditionSignalFailedException.h from [ad564741e9] to [136fb7b9ad].

31
32
33
34
35
36
37

38
39
40
41
42
43
44





45
46
47
48

49
50
51

52
53
54
55
56

57
58
59
60


61
62
63
 *	  ObjFW/OFConditionSignalFailedException.h
 *
 * @brief An exception indicating signaling a condition failed.
 */
@interface OFConditionSignalFailedException: OFException
{
	OFCondition *_condition;

}

/*!
 * @brief The condition which could not be signaled.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFCondition *condition;






/*!
 * @brief Creates a new, autoreleased condition signal failed exception.
 *
 * @param condition The condition which could not be signaled

 * @return A new, autoreleased condition signal failed exception
 */
+ (instancetype)exceptionWithCondition: (nullable OFCondition *)condition;


/*!
 * @brief Initializes an already allocated condition signal failed exception.
 *
 * @param condition The condition which could not be signaled

 * @return An initialized condition signal failed exception
 */
- (instancetype)initWithCondition: (nullable OFCondition *)condition
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
 *	  ObjFW/OFConditionSignalFailedException.h
 *
 * @brief An exception indicating signaling a condition failed.
 */
@interface OFConditionSignalFailedException: OFException
{
	OFCondition *_condition;
	int _errNo;
}

/*!
 * @brief The condition which could not be signaled.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFCondition *condition;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Creates a new, autoreleased condition signal failed exception.
 *
 * @param condition The condition which could not be signaled
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased condition signal failed exception
 */
+ (instancetype)exceptionWithCondition: (nullable OFCondition *)condition
				 errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated condition signal failed exception.
 *
 * @param condition The condition which could not be signaled
 * @param errNo The errno of the error that occurred
 * @return An initialized condition signal failed exception
 */
- (instancetype)initWithCondition: (nullable OFCondition *)condition
			    errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFConditionSignalFailedException.m from [a0b8d7c91b] to [9350bdc58e].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26
27

28
29
30
31
32
33
34
35
36
37

38
39
40
41

42
43
44





45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFConditionSignalFailedException.h"
#import "OFString.h"
#import "OFCondition.h"

@implementation OFConditionSignalFailedException
@synthesize condition = _condition;

+ (instancetype)exceptionWithCondition: (OFCondition *)condition

{
	return [[[self alloc] initWithCondition: condition] autorelease];
}

- (instancetype)init
{
	return [self initWithCondition: nil];
}

- (instancetype)initWithCondition: (OFCondition *)condition

{
	self = [super init];

	_condition = [condition retain];


	return self;
}






- (void)dealloc
{
	[_condition release];

	[super dealloc];
}

- (OFString *)description
{
	if (_condition != nil)
		return [OFString stringWithFormat:
		    @"Signaling a condition of type %@ failed!",
		    _condition.class];
	else
		return @"Signaling a condition failed!";
}
@end







>
>






|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
|
<
<


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

33



34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60

61
62
63


64
65
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFConditionSignalFailedException.h"
#import "OFString.h"
#import "OFCondition.h"

@implementation OFConditionSignalFailedException
@synthesize condition = _condition, errNo = _errNo;

+ (instancetype)exceptionWithCondition: (OFCondition *)condition
				 errNo: (int)errNo
{
	return [[[self alloc] initWithCondition: condition

					  errNo: errNo] autorelease];



}

- (instancetype)initWithCondition: (OFCondition *)condition
			    errNo: (int)errNo
{
	self = [super init];

	_condition = [condition retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_condition release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"Signaling a condition of type %@ failed: %s",
	    _condition.class, strerror(_errNo)];


}
@end

Modified src/exceptions/OFConditionWaitFailedException.h from [88cfdc9956] to [8d215a229f].

31
32
33
34
35
36
37

38
39
40
41
42
43
44





45
46
47
48

49
50
51

52
53
54
55
56

57
58
59
60


61
62
63
 *	  ObjFW/OFConditionWaitFailedException.h
 *
 * @brief An exception indicating waiting for a condition failed.
 */
@interface OFConditionWaitFailedException: OFException
{
	OFCondition *_condition;

}

/*!
 * @brief The condition for which could not be waited.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFCondition *condition;






/*!
 * @brief Creates a new, autoreleased condition wait failed exception.
 *
 * @param condition The condition for which could not be waited

 * @return A new, autoreleased condition wait failed exception
 */
+ (instancetype)exceptionWithCondition: (nullable OFCondition *)condition;


/*!
 * @brief Initializes an already allocated condition wait failed exception.
 *
 * @param condition The condition for which could not be waited

 * @return An initialized condition wait failed exception
 */
- (instancetype)initWithCondition: (nullable OFCondition *)condition
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
 *	  ObjFW/OFConditionWaitFailedException.h
 *
 * @brief An exception indicating waiting for a condition failed.
 */
@interface OFConditionWaitFailedException: OFException
{
	OFCondition *_condition;
	int _errNo;
}

/*!
 * @brief The condition for which could not be waited.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFCondition *condition;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Creates a new, autoreleased condition wait failed exception.
 *
 * @param condition The condition for which could not be waited
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased condition wait failed exception
 */
+ (instancetype)exceptionWithCondition: (nullable OFCondition *)condition
				 errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated condition wait failed exception.
 *
 * @param condition The condition for which could not be waited
 * @param errNo The errno of the error that occurred
 * @return An initialized condition wait failed exception
 */
- (instancetype)initWithCondition: (nullable OFCondition *)condition
			    errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFConditionWaitFailedException.m from [872efbe506] to [476d475e5f].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26
27

28
29
30
31
32
33
34
35
36
37

38
39
40
41

42
43
44





45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFConditionWaitFailedException.h"
#import "OFString.h"
#import "OFCondition.h"

@implementation OFConditionWaitFailedException
@synthesize condition = _condition;

+ (instancetype)exceptionWithCondition: (OFCondition *)condition

{
	return [[[self alloc] initWithCondition: condition] autorelease];
}

- (instancetype)init
{
	return [self initWithCondition: nil];
}

- (instancetype)initWithCondition: (OFCondition *)condition

{
	self = [super init];

	_condition = [condition retain];


	return self;
}






- (void)dealloc
{
	[_condition release];

	[super dealloc];
}

- (OFString *)description
{
	if (_condition != nil)
		return [OFString stringWithFormat:
		    @"Waiting for a condition of type %@ failed!",
		    _condition.class];
	else
		return @"Waiting for a condition failed!";
}
@end







>
>






|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
|
<
<


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

33



34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60

61
62
63


64
65
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFConditionWaitFailedException.h"
#import "OFString.h"
#import "OFCondition.h"

@implementation OFConditionWaitFailedException
@synthesize condition = _condition, errNo = _errNo;

+ (instancetype)exceptionWithCondition: (OFCondition *)condition
				 errNo: (int)errNo
{
	return [[[self alloc] initWithCondition: condition

					  errNo: errNo] autorelease];



}

- (instancetype)initWithCondition: (OFCondition *)condition
			    errNo: (int)errNo
{
	self = [super init];

	_condition = [condition retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_condition release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"Waiting for a condition of type %@ failed: %s",
	    _condition.class, strerror(_errNo)];


}
@end

Modified src/exceptions/OFLockFailedException.h from [5e9d7f5333] to [61223650f2].

25
26
27
28
29
30
31

32
33
34
35
36
37
38





39
40
41
42

43
44
45

46
47
48
49
50

51
52
53
54


55
56
57
 *	  OFLockFailedException.h ObjFW/OFLockFailedException.h
 *
 * @brief An exception indicating that locking a lock failed.
 */
@interface OFLockFailedException: OFException
{
	id <OFLocking> _lock;

}

/*!
 * @brief The lock which could not be locked.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) id <OFLocking> lock;






/*!
 * @brief Creates a new, autoreleased lock failed exception.
 *
 * @param lock The lock which could not be locked

 * @return A new, autoreleased lock failed exception
 */
+ (instancetype)exceptionWithLock: (nullable id <OFLocking>)lock;


/*!
 * @brief Initializes an already allocated lock failed exception.
 *
 * @param lock The lock which could not be locked

 * @return An initialized lock failed exception
 */
- (instancetype)initWithLock: (nullable id <OFLocking>)lock
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
 *	  OFLockFailedException.h ObjFW/OFLockFailedException.h
 *
 * @brief An exception indicating that locking a lock failed.
 */
@interface OFLockFailedException: OFException
{
	id <OFLocking> _lock;
	int _errNo;
}

/*!
 * @brief The lock which could not be locked.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) id <OFLocking> lock;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Creates a new, autoreleased lock failed exception.
 *
 * @param lock The lock which could not be locked
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased lock failed exception
 */
+ (instancetype)exceptionWithLock: (nullable id <OFLocking>)lock
			    errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated lock failed exception.
 *
 * @param lock The lock which could not be locked
 * @param errNo The errno of the error that occurred
 * @return An initialized lock failed exception
 */
- (instancetype)initWithLock: (nullable id <OFLocking>)lock
		       errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFLockFailedException.m from [5ebc5106e3] to [24e1bf0191].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26

27
28
29
30
31
32
33
34
35
36

37
38
39
40

41
42
43





44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFLockFailedException.h"
#import "OFString.h"

@implementation OFLockFailedException
@synthesize lock = _lock;

+ (instancetype)exceptionWithLock: (id <OFLocking>)lock

{
	return [[[self alloc] initWithLock: lock] autorelease];
}

- (instancetype)init
{
	return [self initWithLock: nil];
}

- (instancetype)initWithLock: (id <OFLocking>)lock

{
	self = [super init];

	_lock = [lock retain];


	return self;
}






- (void)dealloc
{
	[_lock release];

	[super dealloc];
}

- (OFString *)description
{
	if (_lock != nil)
		return [OFString stringWithFormat:
		    @"A lock of type %@ could not be locked!", _lock.class];
	else
		return @"A lock could not be locked!";
}
@end







>
>





|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
<
|


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

32



33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59

60
61

62
63
64
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFLockFailedException.h"
#import "OFString.h"

@implementation OFLockFailedException
@synthesize lock = _lock, errNo = _errNo;

+ (instancetype)exceptionWithLock: (id <OFLocking>)lock
			    errNo: (int)errNo
{
	return [[[self alloc] initWithLock: lock

				     errNo: errNo] autorelease];



}

- (instancetype)initWithLock: (id <OFLocking>)lock
		       errNo: (int)errNo
{
	self = [super init];

	_lock = [lock retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_lock release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"A lock of type %@ could not be locked: %s",

	    _lock.class, strerror(_errNo)];
}
@end

Modified src/exceptions/OFThreadJoinFailedException.h from [768679146c] to [c5fe31c2fe].

30
31
32
33
34
35
36

37
38
39
40
41
42
43





44
45
46
47

48
49
50

51
52
53
54
55

56
57
58
59


60
61
62
 *	  OFThreadJoinFailedException.h ObjFW/OFThreadJoinFailedException.h
 *
 * @brief An exception indicating that joining a thread failed.
 */
@interface OFThreadJoinFailedException: OFException
{
	OFThread *_thread;

}

/*!
 * @brief The thread which could not be joined.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFThread *thread;






/*!
 * @brief Creates a new, autoreleased thread join failed exception.
 *
 * @param thread The thread which could not be joined

 * @return A new, autoreleased thread join failed exception
 */
+ (instancetype)exceptionWithThread: (nullable OFThread *)thread;


/*!
 * @brief Initializes an already allocated thread join failed exception.
 *
 * @param thread The thread which could not be joined

 * @return An initialized thread join failed exception
 */
- (instancetype)initWithThread: (nullable OFThread *)thread
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
 *	  OFThreadJoinFailedException.h ObjFW/OFThreadJoinFailedException.h
 *
 * @brief An exception indicating that joining a thread failed.
 */
@interface OFThreadJoinFailedException: OFException
{
	OFThread *_thread;
	int _errNo;
}

/*!
 * @brief The thread which could not be joined.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFThread *thread;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Creates a new, autoreleased thread join failed exception.
 *
 * @param thread The thread which could not be joined
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased thread join failed exception
 */
+ (instancetype)exceptionWithThread: (nullable OFThread *)thread
			      errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated thread join failed exception.
 *
 * @param thread The thread which could not be joined
 * @param errNo The errno of the error that occurred
 * @return An initialized thread join failed exception
 */
- (instancetype)initWithThread: (nullable OFThread *)thread
			 errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFThreadJoinFailedException.m from [8453050bf7] to [8a25fec565].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26
27

28
29
30
31
32
33
34
35
36
37

38
39
40
41

42
43
44





45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFThreadJoinFailedException.h"
#import "OFString.h"
#import "OFThread.h"

@implementation OFThreadJoinFailedException
@synthesize thread = _thread;

+ (instancetype)exceptionWithThread: (OFThread *)thread

{
	return [[[self alloc] initWithThread: thread] autorelease];
}

- (instancetype)init
{
	return [self initWithThread: nil];
}

- (instancetype)initWithThread: (OFThread *)thread

{
	self = [super init];

	_thread = [thread retain];


	return self;
}






- (void)dealloc
{
	[_thread release];

	[super dealloc];
}

- (OFString *)description
{
	if (_thread != nil)
		return [OFString stringWithFormat:
		    @"Joining a thread of type %@ failed! Most likely, another "
		    @"thread already waits for the thread to join.",
		    _thread.class];
	else
		return @"Joining a thread failed! Most likely, another thread "
		    @"already waits for the thread to join.";
}
@end







>
>






|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
<
|
<
<
<


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

33



34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60

61
62

63



64
65
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFThreadJoinFailedException.h"
#import "OFString.h"
#import "OFThread.h"

@implementation OFThreadJoinFailedException
@synthesize thread = _thread, errNo = _errNo;

+ (instancetype)exceptionWithThread: (OFThread *)thread
			      errNo: (int)errNo
{
	return [[[self alloc] initWithThread: thread

				       errNo: errNo] autorelease];



}

- (instancetype)initWithThread: (OFThread *)thread
			 errNo: (int)errNo
{
	self = [super init];

	_thread = [thread retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_thread release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"Joining a thread of type %@ failed: %s",

	    _thread.class, strerror(_errNo)];



}
@end

Modified src/exceptions/OFThreadStartFailedException.h from [716886073b] to [35f973a54c].

30
31
32
33
34
35
36

37
38
39
40
41
42
43





44
45
46
47

48
49
50

51
52
53
54
55

56
57
58
59


60
61
62
 *	  OFThreadStartFailedException.h ObjFW/OFThreadStartFailedException.h
 *
 * @brief An exception indicating that starting a thread failed.
 */
@interface OFThreadStartFailedException: OFException
{
	OFThread *_thread;

}

/*!
 * @brief The thread which could not be started.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFThread *thread;






/*!
 * @brief Creates a new, autoreleased thread start failed exception.
 *
 * @param thread The thread which could not be started

 * @return A new, autoreleased thread start failed exception
 */
+ (instancetype)exceptionWithThread: (nullable OFThread *)thread;


/*!
 * @brief Initializes an already allocated thread start failed exception.
 *
 * @param thread The thread which could not be started

 * @return An initialized thread start failed exception
 */
- (instancetype)initWithThread: (nullable OFThread *)thread
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
 *	  OFThreadStartFailedException.h ObjFW/OFThreadStartFailedException.h
 *
 * @brief An exception indicating that starting a thread failed.
 */
@interface OFThreadStartFailedException: OFException
{
	OFThread *_thread;
	int _errNo;
}

/*!
 * @brief The thread which could not be started.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) OFThread *thread;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Creates a new, autoreleased thread start failed exception.
 *
 * @param thread The thread which could not be started
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased thread start failed exception
 */
+ (instancetype)exceptionWithThread: (nullable OFThread *)thread
			      errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated thread start failed exception.
 *
 * @param thread The thread which could not be started
 * @param errNo The errno of the error that occurred
 * @return An initialized thread start failed exception
 */
- (instancetype)initWithThread: (nullable OFThread *)thread
			 errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFThreadStartFailedException.m from [0346f15b9f] to [deb7e0460d].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26
27

28
29
30
31
32
33
34
35
36
37

38
39
40
41

42
43
44





45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFThreadStartFailedException.h"
#import "OFString.h"
#import "OFThread.h"

@implementation OFThreadStartFailedException
@synthesize thread = _thread;

+ (instancetype)exceptionWithThread: (OFThread *)thread

{
	return [[[self alloc] initWithThread: thread] autorelease];
}

- (instancetype)init
{
	return [self initWithThread: nil];
}

- (instancetype)initWithThread: (OFThread *)thread

{
	self = [super init];

	_thread = [thread retain];


	return self;
}






- (void)dealloc
{
	[_thread release];

	[super dealloc];
}

- (OFString *)description
{
	if (_thread != nil)
		return [OFString stringWithFormat:
		    @"Starting a thread of type %@ failed!", _thread.class];
	else
		return @"Starting a thread failed!";
}
@end







>
>






|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
<
|


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

33



34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60

61
62

63
64
65
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFThreadStartFailedException.h"
#import "OFString.h"
#import "OFThread.h"

@implementation OFThreadStartFailedException
@synthesize thread = _thread, errNo = _errNo;

+ (instancetype)exceptionWithThread: (OFThread *)thread
			      errNo: (int)errNo
{
	return [[[self alloc] initWithThread: thread

				       errNo: errNo] autorelease];



}

- (instancetype)initWithThread: (OFThread *)thread
			 errNo: (int)errNo
{
	self = [super init];

	_thread = [thread retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_thread release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"Starting a thread of type %@ failed: %s",

	    _thread.class, strerror(_errNo)];
}
@end

Modified src/exceptions/OFUnlockFailedException.h from [d72ab1f15e] to [b92124414b].

25
26
27
28
29
30
31

32
33
34
35
36
37
38





39
40
41
42

43
44
45

46
47
48
49
50

51
52
53
54


55
56
57
 *	  OFUnlockFailedException.h ObjFW/OFUnlockFailedException.h
 *
 * @brief An exception indicating that unlocking a lock failed.
 */
@interface OFUnlockFailedException: OFException
{
	id <OFLocking> _lock;

}

/*!
 * @brief The lock which could not be unlocked.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) id <OFLocking> lock;






/*!
 * @brief Creates a new, autoreleased unlock failed exception.
 *
 * @param lock The lock which could not be unlocked

 * @return A new, autoreleased unlock failed exception
 */
+ (instancetype)exceptionWithLock: (nullable id <OFLocking>)lock;


/*!
 * @brief Initializes an already allocated unlock failed exception.
 *
 * @param lock The lock which could not be unlocked

 * @return An initialized unlock failed exception
 */
- (instancetype)initWithLock: (nullable id <OFLocking>)lock
    OF_DESIGNATED_INITIALIZER;


@end

OF_ASSUME_NONNULL_END







>







>
>
>
>
>




>


|
>





>



|
>
>



25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
 *	  OFUnlockFailedException.h ObjFW/OFUnlockFailedException.h
 *
 * @brief An exception indicating that unlocking a lock failed.
 */
@interface OFUnlockFailedException: OFException
{
	id <OFLocking> _lock;
	int _errNo;
}

/*!
 * @brief The lock which could not be unlocked.
 */
@property OF_NULLABLE_PROPERTY (readonly, nonatomic) id <OFLocking> lock;

/*!
 * @brief The errno of the error that occurred.
 */
@property (readonly, nonatomic) int errNo;

/*!
 * @brief Creates a new, autoreleased unlock failed exception.
 *
 * @param lock The lock which could not be unlocked
 * @param errNo The errno of the error that occurred
 * @return A new, autoreleased unlock failed exception
 */
+ (instancetype)exceptionWithLock: (nullable id <OFLocking>)lock
			    errNo: (int)errNo;

/*!
 * @brief Initializes an already allocated unlock failed exception.
 *
 * @param lock The lock which could not be unlocked
 * @param errNo The errno of the error that occurred
 * @return An initialized unlock failed exception
 */
- (instancetype)initWithLock: (nullable id <OFLocking>)lock
		       errNo: (int)errNo OF_DESIGNATED_INITIALIZER;

- (instancetype)init OF_UNAVAILABLE;
@end

OF_ASSUME_NONNULL_END

Modified src/exceptions/OFUnlockFailedException.m from [cdcb8469af] to [0a3af66f30].

12
13
14
15
16
17
18


19
20
21
22
23
24
25
26

27
28
29
30
31
32
33
34
35
36

37
38
39
40

41
42
43





44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"



#import "OFUnlockFailedException.h"
#import "OFString.h"

@implementation OFUnlockFailedException
@synthesize lock = _lock;

+ (instancetype)exceptionWithLock: (id <OFLocking>)lock

{
	return [[[self alloc] initWithLock: lock] autorelease];
}

- (instancetype)init
{
	return [self initWithLock: nil];
}

- (instancetype)initWithLock: (id <OFLocking>)lock

{
	self = [super init];

	_lock = [lock retain];


	return self;
}






- (void)dealloc
{
	[_lock release];

	[super dealloc];
}

- (OFString *)description
{
	if (_lock != nil)
		return [OFString stringWithFormat:
		    @"A lock of type %@ could not be unlocked!", _lock.class];
	else
		return @"A lock could not be unlocked!";
}
@end







>
>





|


>

|
<
|
<
<
<



>




>



>
>
>
>
>










<
|
|
<
|


12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

32



33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59

60
61

62
63
64
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include "config.h"

#include <string.h>

#import "OFUnlockFailedException.h"
#import "OFString.h"

@implementation OFUnlockFailedException
@synthesize lock = _lock, errNo = _errNo;

+ (instancetype)exceptionWithLock: (id <OFLocking>)lock
			    errNo: (int)errNo
{
	return [[[self alloc] initWithLock: lock

				     errNo: errNo] autorelease];



}

- (instancetype)initWithLock: (id <OFLocking>)lock
		       errNo: (int)errNo
{
	self = [super init];

	_lock = [lock retain];
	_errNo = errNo;

	return self;
}

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (void)dealloc
{
	[_lock release];

	[super dealloc];
}

- (OFString *)description
{

	return [OFString stringWithFormat:
	    @"A lock of type %@ could not be unlocked: %s",

	    _lock.class, strerror(_errNo)];
}
@end

Modified src/mutex_amiga.m from [07f9094daa] to [e81c361f63].

10
11
12
13
14
15
16


17
18
19
20
21
22
23
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */



#include <proto/exec.h>

bool
of_mutex_new(of_mutex_t *mutex)
{
	InitSemaphore(mutex);







>
>







10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <errno.h>

#include <proto/exec.h>

bool
of_mutex_new(of_mutex_t *mutex)
{
	InitSemaphore(mutex);
32
33
34
35
36
37
38
39





40
41
42
43
44
45
46

	return true;
}

bool
of_mutex_trylock(of_mutex_t *mutex)
{
	return AttemptSemaphore(mutex);





}

bool
of_mutex_unlock(of_mutex_t *mutex)
{
	ReleaseSemaphore(mutex);








|
>
>
>
>
>







34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53

	return true;
}

bool
of_mutex_trylock(of_mutex_t *mutex)
{
	if (!AttemptSemaphore(mutex)) {
		errno = EBUSY;
		return false;
	}

	return true;
}

bool
of_mutex_unlock(of_mutex_t *mutex)
{
	ReleaseSemaphore(mutex);

Modified src/mutex_winapi.m from [01cabee958] to [83475077c0].

11
12
13
14
15
16
17


18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37





38
39
40
41
42
43
44
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */



bool
of_mutex_new(of_mutex_t *mutex)
{
	InitializeCriticalSection(mutex);

	return true;
}

bool
of_mutex_lock(of_mutex_t *mutex)
{
	EnterCriticalSection(mutex);

	return true;
}

bool
of_mutex_trylock(of_mutex_t *mutex)
{
	return TryEnterCriticalSection(mutex);





}

bool
of_mutex_unlock(of_mutex_t *mutex)
{
	LeaveCriticalSection(mutex);








>
>



















|
>
>
>
>
>







11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <errno.h>

bool
of_mutex_new(of_mutex_t *mutex)
{
	InitializeCriticalSection(mutex);

	return true;
}

bool
of_mutex_lock(of_mutex_t *mutex)
{
	EnterCriticalSection(mutex);

	return true;
}

bool
of_mutex_trylock(of_mutex_t *mutex)
{
	if (!TryEnterCriticalSection(mutex)) {
		errno = EBUSY;
		return false;
	}

	return true;
}

bool
of_mutex_unlock(of_mutex_t *mutex)
{
	LeaveCriticalSection(mutex);

Modified src/thread_amiga.m from [d9382c6e08] to [669ee33a73].

10
11
12
13
14
15
16



17
18
19
20
21
22
23
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */




#include <dos/dostags.h>
#include <proto/dos.h>
#include <proto/exec.h>

#import "OFData.h"








>
>
>







10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <assert.h>
#include <errno.h>

#include <dos/dostags.h>
#include <proto/dos.h>
#include <proto/exec.h>

#import "OFData.h"

70
71
72
73
74
75
76
77

78

79
80
81
82
83
84
85

bool
of_thread_new(of_thread_t *thread, void (*function)(id), id object,
    const of_thread_attr_t *attr)
{
	OFMutableData *tags = nil;

	if ((*thread = calloc(1, sizeof(**thread))) == NULL)

		return false;


	@try {
		(*thread)->function = function;
		(*thread)->object = object;
		InitSemaphore(&(*thread)->semaphore);

		tags = [[OFMutableData alloc]







|
>

>







73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90

bool
of_thread_new(of_thread_t *thread, void (*function)(id), id object,
    const of_thread_attr_t *attr)
{
	OFMutableData *tags = nil;

	if ((*thread = calloc(1, sizeof(**thread))) == NULL) {
		errno = ENOMEM;
		return false;
	}

	@try {
		(*thread)->function = function;
		(*thread)->object = object;
		InitSemaphore(&(*thread)->semaphore);

		tags = [[OFMutableData alloc]
106
107
108
109
110
111
112
113

114

115
116
117
118
119
120
121
		ADD_TAG(NP_Output, ((struct Process *)FindTask(NULL))->pr_COS)
		ADD_TAG(NP_Error, ((struct Process *)FindTask(NULL))->pr_CES)
		ADD_TAG(NP_CloseInput, FALSE)
		ADD_TAG(NP_CloseOutput, FALSE)
		ADD_TAG(NP_CloseError, FALSE)

		if (attr != NULL && attr->priority != 0) {
			if (attr->priority < 1 || attr->priority > 1)

				return false;


			/*
			 * -1 should be -128 (lowest possible priority) while
			 * +1 should be +127 (highest possible priority).
			 */
			ADD_TAG(NP_Priority, (attr->priority > 0
			    ? attr->priority * 127 : attr->priority * 128))







|
>

>







111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
		ADD_TAG(NP_Output, ((struct Process *)FindTask(NULL))->pr_COS)
		ADD_TAG(NP_Error, ((struct Process *)FindTask(NULL))->pr_CES)
		ADD_TAG(NP_CloseInput, FALSE)
		ADD_TAG(NP_CloseOutput, FALSE)
		ADD_TAG(NP_CloseError, FALSE)

		if (attr != NULL && attr->priority != 0) {
			if (attr->priority < 1 || attr->priority > 1) {
				errno = EINVAL;
				return false;
			}

			/*
			 * -1 should be -128 (lowest possible priority) while
			 * +1 should be +127 (highest possible priority).
			 */
			ADD_TAG(NP_Priority, (attr->priority > 0
			    ? attr->priority * 127 : attr->priority * 128))
129
130
131
132
133
134
135

136
137
138
139
140
141
142

		ADD_TAG(TAG_DONE, 0)
#undef ADD_TAG

		(*thread)->task = (struct Task *)CreateNewProc(tags.items);
		if ((*thread)->task == NULL) {
			free(*thread);

			return false;
		}
	} @catch (id e) {
		free(*thread);
		@throw e;
	} @finally {
		[tags release];







>







136
137
138
139
140
141
142
143
144
145
146
147
148
149
150

		ADD_TAG(TAG_DONE, 0)
#undef ADD_TAG

		(*thread)->task = (struct Task *)CreateNewProc(tags.items);
		if ((*thread)->task == NULL) {
			free(*thread);
			errno = EAGAIN;
			return false;
		}
	} @catch (id e) {
		free(*thread);
		@throw e;
	} @finally {
		[tags release];
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166

167
168

169

170

171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
{
	return of_tlskey_get(threadKey);
}

bool
of_thread_join(of_thread_t thread)
{
	bool ret;

	ObtainSemaphore(&thread->semaphore);
	@try {
		if (thread->done) {
			free(thread);
			return true;
		}

		if (thread->detached || thread->joinTask != NULL)

			return false;


		if ((thread->joinSigBit = AllocSignal(-1)) == -1)

			return false;


		thread->joinTask = FindTask(NULL);
	} @finally {
		ReleaseSemaphore(&thread->semaphore);
	}

	Wait(1 << thread->joinSigBit);
	FreeSignal(thread->joinSigBit);

	ret = thread->done;
	free(thread);

	return ret;
}

bool
of_thread_detach(of_thread_t thread)
{
	ObtainSemaphore(&thread->semaphore);








<
<







|
>

|
>
|
>

>






|


|


|







158
159
160
161
162
163
164


165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
{
	return of_tlskey_get(threadKey);
}

bool
of_thread_join(of_thread_t thread)
{


	ObtainSemaphore(&thread->semaphore);
	@try {
		if (thread->done) {
			free(thread);
			return true;
		}

		if (thread->detached || thread->joinTask != NULL) {
			errno = EINVAL;
			return false;
		}

		if ((thread->joinSigBit = AllocSignal(-1)) == -1) {
			errno = EAGAIN;
			return false;
		}

		thread->joinTask = FindTask(NULL);
	} @finally {
		ReleaseSemaphore(&thread->semaphore);
	}

	Wait(1ul << thread->joinSigBit);
	FreeSignal(thread->joinSigBit);

	assert(thread->done);
	free(thread);

	return true;
}

bool
of_thread_detach(of_thread_t thread)
{
	ObtainSemaphore(&thread->semaphore);

Modified src/thread_pthread.m from [4bb0d2efdf] to [e8b813b448].

10
11
12
13
14
15
16


17
18
19
20
21
22
23
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */



#ifdef HAVE_PTHREAD_NP_H
# include <pthread_np.h>
#endif

#ifdef OF_HAIKU
# include <kernel/OS.h>







>
>







10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
 * the packaging of this file.
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <errno.h>

#ifdef HAVE_PTHREAD_NP_H
# include <pthread_np.h>
#endif

#ifdef OF_HAIKU
# include <kernel/OS.h>
110
111
112
113
114
115
116
117

118

119
120
121
122
123
124
125

	@try {
		struct thread_ctx *ctx;

		if (attr != NULL) {
			struct sched_param param;

			if (attr->priority < -1 || attr->priority > 1)

				return false;


#ifdef HAVE_PTHREAD_ATTR_SETINHERITSCHED
			if (pthread_attr_setinheritsched(&pattr,
			    PTHREAD_EXPLICIT_SCHED) != 0)
				return false;
#endif








|
>

>







112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129

	@try {
		struct thread_ctx *ctx;

		if (attr != NULL) {
			struct sched_param param;

			if (attr->priority < -1 || attr->priority > 1) {
				errno = EINVAL;
				return false;
			}

#ifdef HAVE_PTHREAD_ATTR_SETINHERITSCHED
			if (pthread_attr_setinheritsched(&pattr,
			    PTHREAD_EXPLICIT_SCHED) != 0)
				return false;
#endif

137
138
139
140
141
142
143
144

145

146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
			if (attr->stackSize > 0) {
				if (pthread_attr_setstacksize(&pattr,
				    attr->stackSize) != 0)
					return false;
			}
		}

		if ((ctx = malloc(sizeof(*ctx))) == NULL)

			return false;


		ctx->function = function;
		ctx->object = object;

		ret = (pthread_create(thread, &pattr,
		    functionWrapper, ctx) == 0);
	} @finally {
		pthread_attr_destroy(&pattr);
	}

	return ret;
}

bool
of_thread_join(of_thread_t thread)
{
	void *ret;

	if (pthread_join(thread, &ret) != 0)
		return false;

#ifdef PTHREAD_CANCELED
	return (ret != PTHREAD_CANCELED);
#else
	return true;
#endif
}

bool
of_thread_detach(of_thread_t thread)
{
	return (pthread_detach(thread) == 0);
}







|
>

>


















|
<
<
<
<
<
<
<







141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170







171
172
173
174
175
176
177
			if (attr->stackSize > 0) {
				if (pthread_attr_setstacksize(&pattr,
				    attr->stackSize) != 0)
					return false;
			}
		}

		if ((ctx = malloc(sizeof(*ctx))) == NULL) {
			errno = ENOMEM;
			return false;
		}

		ctx->function = function;
		ctx->object = object;

		ret = (pthread_create(thread, &pattr,
		    functionWrapper, ctx) == 0);
	} @finally {
		pthread_attr_destroy(&pattr);
	}

	return ret;
}

bool
of_thread_join(of_thread_t thread)
{
	void *ret;

	return (pthread_join(thread, &ret) == 0);







}

bool
of_thread_detach(of_thread_t thread)
{
	return (pthread_detach(thread) == 0);
}

Modified src/thread_winapi.m from [773437e43e] to [7f82a998d7].

11
12
13
14
15
16
17


18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36



37







38
39
40
41
42

43

44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64







65


66
67


68
69
70
71
72
73
74
75
76
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */



#import "macros.h"

bool
of_thread_attr_init(of_thread_attr_t *attr)
{
	attr->priority = 0;
	attr->stackSize = 0;

	return true;
}

bool
of_thread_new(of_thread_t *thread, void (*function)(id), id object,
    const of_thread_attr_t *attr)
{
	*thread = CreateThread(NULL, (attr != NULL ? attr->stackSize : 0),
	    (LPTHREAD_START_ROUTINE)function, (void *)object, 0, NULL);

	if (thread == NULL)



		return false;








	if (attr != NULL && attr->priority != 0) {
		DWORD priority;

		if (attr->priority < -1 || attr->priority > 1)

			return false;


		if (attr->priority < 0)
			priority = THREAD_PRIORITY_LOWEST +
			    (1.0 + attr->priority) *
			    (THREAD_PRIORITY_NORMAL - THREAD_PRIORITY_LOWEST);
		else
			priority = THREAD_PRIORITY_NORMAL +
			    attr->priority *
			    (THREAD_PRIORITY_HIGHEST - THREAD_PRIORITY_NORMAL);

		if (!SetThreadPriority(*thread, priority))
			return false;
	}

	return true;
}

bool
of_thread_join(of_thread_t thread)
{
	if (WaitForSingleObject(thread, INFINITE))







		return false;



	CloseHandle(thread);



	return true;
}

bool
of_thread_detach(of_thread_t thread)
{
	CloseHandle(thread);








>
>


















|
>
>
>
|
>
>
>
>
>
>
>




|
>

>










|
<








|
>
>
>
>
>
>
>
|
>
>
|
<
>
>
|
<







11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68

69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88

89
90
91

92
93
94
95
96
97
98
 *
 * Alternatively, it may be distributed under the terms of the GNU General
 * Public License, either version 2 or 3, which can be found in the file
 * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this
 * file.
 */

#include <errno.h>

#import "macros.h"

bool
of_thread_attr_init(of_thread_attr_t *attr)
{
	attr->priority = 0;
	attr->stackSize = 0;

	return true;
}

bool
of_thread_new(of_thread_t *thread, void (*function)(id), id object,
    const of_thread_attr_t *attr)
{
	*thread = CreateThread(NULL, (attr != NULL ? attr->stackSize : 0),
	    (LPTHREAD_START_ROUTINE)function, (void *)object, 0, NULL);

	if (thread == NULL) {
		switch (GetLastError()) {
		case ERROR_NOT_ENOUGH_MEMORY:
			errno = ENOMEM;
			return false;
		case ERROR_ACCESS_DENIED:
			errno = EACCES;
			return false;
		default:
			OF_ENSURE(0);
		}
	}

	if (attr != NULL && attr->priority != 0) {
		DWORD priority;

		if (attr->priority < -1 || attr->priority > 1) {
			errno = EINVAL;
			return false;
		}

		if (attr->priority < 0)
			priority = THREAD_PRIORITY_LOWEST +
			    (1.0 + attr->priority) *
			    (THREAD_PRIORITY_NORMAL - THREAD_PRIORITY_LOWEST);
		else
			priority = THREAD_PRIORITY_NORMAL +
			    attr->priority *
			    (THREAD_PRIORITY_HIGHEST - THREAD_PRIORITY_NORMAL);

		OF_ENSURE(!SetThreadPriority(*thread, priority));

	}

	return true;
}

bool
of_thread_join(of_thread_t thread)
{
	switch (WaitForSingleObject(thread, INFINITE)) {
	case WAIT_OBJECT_0:
		CloseHandle(thread);
		return true;
	case WAIT_FAILED:
		switch (GetLastError()) {
		case ERROR_INVALID_HANDLE:
			errno = EINVAL;
			return false;
		default:
			OF_ENSURE(0);
		}

	default:
		OF_ENSURE(0);
	}

}

bool
of_thread_detach(of_thread_t thread)
{
	CloseHandle(thread);