[Prev] [Contents] [Next]

pthread_signal_to_cancel_np()--Convert Signals to Cancel Requests

Syntax

#include <pthread.h>
#include <sched.h>
int pthread_signal_to_cancel_np(sigset_t *set, pthread_t *thread);
Threadsafe: Yes
Signal Safe: No

The pthread_signal_to_cancel_np() function causes a pthread_cancel() to be delivered to the target thread, when the first signal specified in set arrives.

All threads in the process should have the signals specified by set blocked from the time of the call to pthread_signal_to_cancel_np() until the time when the pthread_cancel() is delivered to the target thread.

If pthread_signal_to_cancel_np() has been called, but no signal has been converted to a pthread_cancel() yet, a subsequent call to pthread_signal_to_cancel_np() will override the first call.

The pthread_signal_to_cancel_np() function creates a service thread (called the SignalToCancel thread) to perform the signal to cancel conversion. This conversion occurs asynchronously to the thread that called pthread_signal_to_cancel_np().

The SignalToCancel thread blocks all signals and performs a sigwait() on the set of signals specified by set. When sigwait() returns, indicating that one of the signals in set was synchronously received, the SignalToCancel thread calls pthread_cancel() using the thread specified as the target.

Since the SignalToCancel thread processing occurs asynchronously, the caller of pthread_signal_to_cancel_np() will not be notified of errors that may occur during the processing of the SignalToCancel thread. If the target thread has terminated, or the signals specified by set are invalid, no notification will occur to the caller of pthread_signal_to_cancel_np().

This function is not portable

Parameters

set
(Input) The set of signals that will be converted to pthread_cancel() requests.
thread
(Input) The thread that will be canceled when a signal in set arrives.

Authorities and Locks

None.

Return Value

0
pthread_signal_to_cancel_np() was successful.
value
pthread_signal_to_cancel_np() was not successful. value is set to indicate the error condition.

Error Conditions

If pthread_signal_to_cancel_np() was not successful, the error condition returned usually indicates one of the following errors. Under some conditions, the value returned could indicate an error other than those listed here.

[EINVAL]
The value specified for the argument is not correct.

Related Information

Example

#define _MULTI_THREADED
#include <pthread.h>
#include <stdio.h>
#include <sys/signal.h>
#include "check.h"

void sighand(int signo);

void cancelationCleanup(void *parm) { printf("Thread was canceled\n"); }

void *threadfunc(void *parm)
{
  pthread_t             self = pthread_self();
  pthread_id_np_t       tid;
  int                   rc;
  int                   i=5;

  pthread_getunique_np(&self, &tid);
  printf("Thread 0x%.8x %.8x entered\n", tid);
  while (i--) {
    printf("Thread 0x%.8x %.8x looping\n",
           tid, rc, errno);
    sleep(2);
    pthread_testcancel();
  }
  printf("Thread 0x%.8x %.8x didn't expect to get here\n",
         tid);
  return NULL;
}


int main(int argc, char **argv)
{
  int                     rc;
  int                     i;
  pthread_t               thread;
  struct sigaction        actions;
  sigset_t                mask;
  void                   *status;
  pthread_t               self;
  pthread_id_np_t         tid;

  printf("Enter Testcase - %s\n", argv[0]);

  printf("Set up the alarm handler for the process\n");
  memset(&actions, 0, sizeof(actions));
  sigemptyset(&actions.sa_mask);
  actions.sa_flags = 0;
  actions.sa_handler = sighand;

  rc = sigaction(SIGALRM,&actions,NULL);
  checkResults("sigaction\n", rc);

  printf("Block all signals in the parent so they can be inherited\n");
  sigfillset(&mask); /* Mask all allowed signals */
  rc = pthread_sigmask(SIG_BLOCK, &mask, NULL);
  checkResults("pthread_sigmask()\n", rc);

  printf("Create thread that inherits blocking mask\n");
  /* Thread will inherit blocking mask */
  rc = pthread_create(&thread, NULL, threadfunc, NULL);
  checkResults("pthread_create()\n", rc);

  /* Convert signals to cancels */
  rc = pthread_signal_to_cancel_np(&mask, &thread);
  checkResults("pthread_signal_to_cancel()\n", rc);

  sleep(3);
  self = pthread_self();
  pthread_getunique_np(&self, &tid);

  printf("Thread 0x%.8x %.8x sending a signal to the process\n", tid);
  kill(getpid(), SIGALRM);
  checkResults("kill()\n", rc);

  printf("Wait for masked and unmasked threads to complete\n");
  rc = pthread_join(thread, &status);
  checkResults("pthread_join()\n", rc);

  if (status != PTHREAD_CANCELED) {
    printf("Got an incorrect thread status\n");
    return 1;
  }
  printf("The target thread was canceled\n");
  printf("Main completed\n");
  return 0;
}

void sighand(int signo)
{
  pthread_t             self = pthread_self();
  pthread_id_np_t       tid;

  pthread_getunique_np(&self, &tid);
  printf("Thread 0x%.8x %.8x in signal handler\n",
         tid);
  return;
}

Output

Enter Testcase - QP0WTEST/TPSIG2C0
Set up the alarm handler for the process
Block all signals in the parent so they can be inherited
Create thread that inherits blocking mask
Thread 0x00000000 00000007 entered
Thread 0x00000000 00000007 looping
Thread 0x00000000 00000007 looping
Thread 0x00000000 00000006 sending a signal to the process
Wait for masked and unmasked threads to complete
The target thread was canceled
Main completed




[Prev] [Contents] [Next]
Copyright © 1998, IBM Corporation. All rights reserved.
Comments? Contact
rchthrds@us.ibm.com