xref: /haiku/src/tests/system/libroot/posix/signal_in_allocator_test.cpp (revision fc8aebca3b0c201aeb4e3f65c67a0a8146a399f2)
12873ace1SIngo Weinhold /*
22873ace1SIngo Weinhold  * Copyright 2008, Ingo Weinhold, ingo_weinhold@gmx.de.
32873ace1SIngo Weinhold  * Distributed under the terms of the MIT License.
42873ace1SIngo Weinhold  */
52873ace1SIngo Weinhold 
62873ace1SIngo Weinhold #include <errno.h>
72873ace1SIngo Weinhold #include <signal.h>
82873ace1SIngo Weinhold #include <stdio.h>
92873ace1SIngo Weinhold #include <stdlib.h>
102873ace1SIngo Weinhold #include <signal.h>
112873ace1SIngo Weinhold #include <string.h>
122873ace1SIngo Weinhold 
132873ace1SIngo Weinhold #include <OS.h>
142873ace1SIngo Weinhold 
152873ace1SIngo Weinhold 
162873ace1SIngo Weinhold static int64 sHandledSignals = 0;
172873ace1SIngo Weinhold 
182873ace1SIngo Weinhold 
192873ace1SIngo Weinhold static status_t
signal_pusher(void * data)202873ace1SIngo Weinhold signal_pusher(void* data)
212873ace1SIngo Weinhold {
222873ace1SIngo Weinhold 	team_info teamInfo;
232873ace1SIngo Weinhold 	get_team_info(B_CURRENT_TEAM, &teamInfo);
242873ace1SIngo Weinhold 	thread_id mainThread = teamInfo.team;
252873ace1SIngo Weinhold 
262873ace1SIngo Weinhold 	while (true) {
272873ace1SIngo Weinhold 		send_signal(mainThread, SIGUSR1);
282873ace1SIngo Weinhold 		snooze(1000);
292873ace1SIngo Weinhold 	}
302873ace1SIngo Weinhold 
312873ace1SIngo Weinhold 	return B_OK;
322873ace1SIngo Weinhold }
332873ace1SIngo Weinhold 
342873ace1SIngo Weinhold 
352873ace1SIngo Weinhold static void
signal_handler(int signal)362873ace1SIngo Weinhold signal_handler(int signal)
372873ace1SIngo Weinhold {
382873ace1SIngo Weinhold 	free(malloc(10));
392873ace1SIngo Weinhold 	sHandledSignals++;
402873ace1SIngo Weinhold }
412873ace1SIngo Weinhold 
422873ace1SIngo Weinhold 
432873ace1SIngo Weinhold int
main()442873ace1SIngo Weinhold main()
452873ace1SIngo Weinhold {
462873ace1SIngo Weinhold 	const int testSeconds = 2;
472873ace1SIngo Weinhold 	printf("Trying to provoke allocator deadlock in signal handler.\n");
482873ace1SIngo Weinhold 	printf("If successful test will finish in %d seconds...\n", testSeconds);
492873ace1SIngo Weinhold 
502873ace1SIngo Weinhold 	// install signal handler
512873ace1SIngo Weinhold 	if (signal(SIGUSR1, signal_handler) == SIG_ERR) {
522873ace1SIngo Weinhold 		fprintf(stderr, "Error: Failed to install signal handler: %s\n",
532873ace1SIngo Weinhold 			strerror(errno));
542873ace1SIngo Weinhold 		exit(1);
552873ace1SIngo Weinhold 	}
562873ace1SIngo Weinhold 
572873ace1SIngo Weinhold 	// start signal thread
582873ace1SIngo Weinhold 	thread_id signalThread = spawn_thread(&signal_pusher, "signal pusher",
592873ace1SIngo Weinhold 		B_NORMAL_PRIORITY, NULL);
602873ace1SIngo Weinhold 	resume_thread(signalThread);
612873ace1SIngo Weinhold 
622873ace1SIngo Weinhold 	bigtime_t endTime = system_time() + 1000000 * (bigtime_t)testSeconds;
632873ace1SIngo Weinhold 	while (system_time() < endTime) {
642873ace1SIngo Weinhold 		const int allocationCount = 1000;
652873ace1SIngo Weinhold 		void* allocations[allocationCount];
662873ace1SIngo Weinhold 		for (int i = 0; i < allocationCount; i++)
672873ace1SIngo Weinhold 			allocations[i] = malloc(rand() % 50);
682873ace1SIngo Weinhold 		for (int i = 0; i < allocationCount; i++)
692873ace1SIngo Weinhold 			free(allocations[i]);
702873ace1SIngo Weinhold 	}
712873ace1SIngo Weinhold 
722873ace1SIngo Weinhold 	kill_thread(signalThread);
732873ace1SIngo Weinhold 	snooze(1000);
742873ace1SIngo Weinhold 
75*fc8aebcaSAlexander von Gluck IV 	printf("test successful, handled %" B_PRId64 " signals\n", sHandledSignals);
762873ace1SIngo Weinhold 
772873ace1SIngo Weinhold 	return 0;
782873ace1SIngo Weinhold }
79