All of lore.kernel.org
 help / color / mirror / Atom feed
From: Wolfgang Grandegger <wg@domain.hid>
To: xenomai-help <xenomai@xenomai.org>
Subject: [Xenomai-help] pthread cancelation and scheduling magics
Date: Sun, 30 Nov 2008 22:34:45 +0100	[thread overview]
Message-ID: <493306F5.2080605@domain.hid> (raw)

[-- Attachment #1: Type: text/plain, Size: 523 bytes --]

Hello,

I have written the attached test program to cancel Xenomai POSIX
threads. The "calc_task" does some busy work, which the higher priority
task "ctrl_task" interrupts and aborts after some time. The program does
not behave like I expect and it also behaves differently on my PowerPC
and ARM test system. The "calc_task" continues after calling
pthread_cancel() in "ctrl_task". On ARM, the behaviour is even more
wired. Is there anything wrong in my test program or anything else I
should care of?

Thanks.

Wolfgang.

[-- Attachment #2: cancel-test.c --]
[-- Type: text/x-csrc, Size: 4762 bytes --]

/*
 * Test program for thread cancelation
 */

#include <execinfo.h>
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <time.h>
#include <sys/mman.h>

#ifndef __XENO__
#define rt_printf printf
#else
#include <rtdk.h>
#endif

#define USE_SIGXCPU
//#define USE_EXPLICIT_SCHED
#define CTRL_PRIO 39
#define CALC_PRIO 38

static pthread_t calc_thread;
static pthread_t ctrl_thread;

volatile unsigned long count = 0;
static int load_ms = 2500;

void check_err(char *string, int err)
{
	if (err) {
		printf("Failed with %d at %s", err, string);
		exit(1);
	}
}

static void create_load_100ms(void)
{
	struct timespec now, stop;

	clock_gettime(CLOCK_MONOTONIC, &stop);
	stop.tv_nsec += 100000000;
	if (stop.tv_nsec >= 1000000000) {
		stop.tv_nsec -= 1000000000;
		stop.tv_sec++;
	}

	while (1) {
		clock_gettime(CLOCK_MONOTONIC, &now);
		if (now.tv_sec > stop.tv_sec)
			break;
		else if (now.tv_sec == stop.tv_sec &&
			 now.tv_nsec >= stop.tv_nsec)
			break;
	}
}

void *ctrl_func(void *parm)
{
	struct timespec ts;
#ifndef USE_EXPLICIT_SCHED
	struct sched_param param;

	memset(&param, 0 , sizeof(param));
	param.sched_priority = CTRL_PRIO;
	pthread_setschedparam(pthread_self(), SCHED_FIFO, &param);
#endif
#ifdef __XENO__
	pthread_set_name_np(pthread_self(), __func__);
#ifdef USE_SIGXCPU
	pthread_set_mode_np(0, PTHREAD_WARNSW);
#endif
#endif
	rt_printf("%s: started at count %d\n", __func__, count);

	ts.tv_sec = load_ms / 1000;
	ts.tv_nsec = (load_ms % 1000) * 1000000;
	rt_printf("%s: sleeping for %dsec %dns\n", __func__,
		  ts.tv_sec, ts.tv_nsec);
	nanosleep(&ts, NULL);
	rt_printf("%s: cancel at count %ld\n", __func__, count);
	pthread_cancel(calc_thread);
	rt_printf("%s: stopped at count %ld\n", __func__, count);

	return NULL;
}
void *calc_func(void *parm)
{
	int rc , count_max;
#ifndef USE_EXPLICIT_SCHED
	struct sched_param param;
#endif

#ifndef USE_EXPLICIT_SCHED
	memset(&param, 0 , sizeof(param));
	param.sched_priority = CALC_PRIO;
	pthread_setschedparam(pthread_self(), SCHED_FIFO, &param);
#endif
#ifdef __XENO__
	pthread_set_name_np(pthread_self(), __func__);
#ifdef USE_SIGXCPU
	pthread_set_mode_np(0, PTHREAD_WARNSW);
#endif
#endif
	rc = pthread_setcanceltype(PTHREAD_CANCEL_ASYNCHRONOUS, NULL);
	check_err("pthread_setcanceltype()\n", rc);
	rc = pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL);
	check_err("pthread_setcanceltype()\n", rc);

	count_max = 2 * load_ms / 100;
	rt_printf("%s: counting till %d\n", __func__, count_max);
	while (count < count_max) {
		create_load_100ms();
		rt_printf("%s: at count %ld\n", __func__, count);
		count++;
	}

	rt_printf("%s: stopped at count %ld\n", __func__, count);

	return NULL;
}

#ifdef USE_SIGXCPU
void mode_switch_handler(int sig)
{
        void *bt[32];
        int nentries;

        /* Dump a backtrace of the frame which caused the switch to
           secondary mode: */
        nentries = backtrace(bt,sizeof(bt) / sizeof(bt[0]));
        backtrace_symbols_fd(bt, nentries, fileno(stdout));
}
#endif

int main(int argc, char **argv)
{
	int rc = 0;
	void *status;
#ifdef USE_EXPLICIT_SCHED
	pthread_attr_t calc_attr, ctrl_attr;
	struct sched_param calc_param, ctrl_param;
#endif

	if (argc == 2)
		load_ms = atoi(argv[1]);

	/* Lock process memory */
	mlockall(MCL_CURRENT | MCL_FUTURE);

#ifdef USE_SIGXCPU
	signal(SIGXCPU, mode_switch_handler);
#endif
#ifdef __XENO__
	/* We use rt_printf() for debugging real-time code */
	rt_print_auto_init(1);
	rt_printf("Real-Time debugging started\n");
#endif

#ifdef USE_EXPLICIT_SCHED
	memset(&ctrl_param, 0 , sizeof(ctrl_param));
	pthread_attr_init(&ctrl_attr);
	pthread_attr_setschedpolicy(&ctrl_attr, SCHED_FIFO);
 	ctrl_param.sched_priority = CTRL_PRIO;
	pthread_attr_setschedparam(&ctrl_attr, &ctrl_param);
	pthread_attr_setinheritsched(&ctrl_attr, PTHREAD_EXPLICIT_SCHED);
	rc = pthread_create(&ctrl_thread, &ctrl_attr, ctrl_func, NULL);
#else
	rc = pthread_create(&ctrl_thread, NULL, ctrl_func, NULL);
#endif
	check_err("pthread_create()\n", rc);

#ifdef USE_EXPLICIT_SCHED
	memset(&calc_param, 0 , sizeof(calc_param));
	pthread_attr_init(&calc_attr);
	pthread_attr_setschedpolicy(&calc_attr, SCHED_FIFO);
	calc_param.sched_priority = CALC_PRIO;
	pthread_attr_setschedparam(&calc_attr, &calc_param);
	pthread_attr_setinheritsched(&calc_attr, PTHREAD_EXPLICIT_SCHED);
	rc = pthread_create(&calc_thread, &calc_attr, calc_func, NULL);
#else
	rc = pthread_create(&calc_thread, NULL, calc_func, NULL);
#endif
	check_err("pthread_create()\n", rc);

	rc = pthread_join(calc_thread, &status);
	check_err("pthread_join()\n", rc);

	if (status != PTHREAD_CANCELED)
		printf("Unexpected thread status\n");

	printf("main terminating in 3 seconds...\n");
	sleep(3);
	return 0;
}

             reply	other threads:[~2008-11-30 21:34 UTC|newest]

Thread overview: 55+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2008-11-30 21:34 Wolfgang Grandegger [this message]
2008-11-30 21:46 ` [Xenomai-help] pthread cancelation and scheduling magics Gilles Chanteperdrix
2008-11-30 21:59 ` Gilles Chanteperdrix
2008-12-01 10:22   ` Gilles Chanteperdrix
2008-12-01 14:16     ` Wolfgang Grandegger
2008-12-01 14:15       ` Gilles Chanteperdrix
2008-12-01 15:10         ` Gilles Chanteperdrix
2008-12-02 15:59           ` Wolfgang Grandegger
2008-12-02 15:55             ` Gilles Chanteperdrix
2008-12-02 18:18               ` Wolfgang Grandegger
2008-12-02 18:35                 ` Gilles Chanteperdrix
2008-12-02 19:50                   ` Wolfgang Grandegger
2008-12-02 20:03                     ` Philippe Gerum
2008-12-07 16:05                   ` Wolfgang Grandegger
2008-12-10 11:16                     ` Wolfgang Grandegger
2008-12-11 15:26                       ` Jan Kiszka
2008-12-13 15:55                         ` Wolfgang Grandegger
2009-01-01 13:34                       ` Gilles Chanteperdrix
2009-01-01 17:07                         ` Philippe Gerum
2009-01-01 18:00                           ` Gilles Chanteperdrix
2009-01-09 13:08                           ` Gilles Chanteperdrix
2009-01-09 13:38                             ` Philippe Gerum
2009-01-01 17:10                         ` Wolfgang Grandegger
2009-01-01 18:11                           ` Gilles Chanteperdrix
2008-12-03 10:16                 ` Gilles Chanteperdrix
2008-12-03 11:19                   ` Wolfgang Grandegger
2008-12-03 13:30                     ` Gilles Chanteperdrix
2008-12-03 18:02                       ` Wolfgang Grandegger
2008-12-03 17:57                         ` Gilles Chanteperdrix
2008-12-03 18:37                           ` Wolfgang Grandegger
2008-12-03 18:32                             ` Gilles Chanteperdrix
2008-12-03 18:55                               ` Wolfgang Grandegger
2008-12-03 18:55                                 ` Gilles Chanteperdrix
2008-12-03 19:19                                   ` Wolfgang Grandegger
2008-12-03 19:19                                     ` Gilles Chanteperdrix
2008-12-03 20:02                                       ` Wolfgang Grandegger
2008-12-03 20:02                                         ` Gilles Chanteperdrix
2008-12-04 15:29                                           ` Wolfgang Grandegger
2008-12-04 15:38                                             ` Gilles Chanteperdrix
2008-12-04 15:42                                               ` Gilles Chanteperdrix
2008-12-04 16:31                                               ` Wolfgang Grandegger
2008-12-04 16:26                                                 ` Gilles Chanteperdrix
2008-12-04 16:49                                                   ` Wolfgang Grandegger
2008-12-04 17:02                                                     ` Gilles Chanteperdrix
2008-12-04 17:52                                                       ` Wolfgang Grandegger
2008-12-04 17:51                                                         ` Gilles Chanteperdrix
2008-12-05 14:58                                                       ` Wolfgang Grandegger
2008-12-03  8:04         ` Wolfgang Grandegger
2008-12-03 10:12           ` Gilles Chanteperdrix
2008-12-03 10:46             ` Wolfgang Grandegger
2008-12-03 10:40               ` Gilles Chanteperdrix
2008-12-03 11:16                 ` Wolfgang Grandegger
2008-12-03 11:11               ` Philippe Gerum
2008-12-03 11:22                 ` Wolfgang Grandegger
2008-12-01 13:31   ` Wolfgang Grandegger

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=493306F5.2080605@domain.hid \
    --to=wg@domain.hid \
    --cc=xenomai@xenomai.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.