From: Wanlong G. <gao...@cn...> - 2011-07-13 01:16:27
|
The v3 patch initials the variable number curr to zero. According to this v2 patch, just linux be effected, so it's portable. Can you apply this now? According to the Linux kernel code, we know that the sigqueue is allocated and queue the signal to it's list by the system call rt_sigqueueinfo(2) which called by sigqueue(3) in this test code. Meanwhile, if the signal is queued, it increase the user's sigpending field. Then if it going to queue another signal, it read the rlimit of the sigpending from the task's signal->rlim[] member and compare with the user's current sigpending number. So, it's the issue. The user who is running this code may have other pending signals before this, and actually it does. This patch read the pending signal's number from the /proc/<pid>/status and minus it. Eliminate the impact of other pending signals. Signed-off-by: Wanlong Gao <gao...@cn...> Signed-off-by: Peng Haitao <pe...@cn...> --- .../conformance/interfaces/sigqueue/9-1.c | 66 ++++++++++++++++++-- 1 files changed, 61 insertions(+), 5 deletions(-) diff --git a/testcases/open_posix_testsuite/conformance/interfaces/sigqueue/9-1.c b/testcases/open_posix_testsuite/conformance/interfaces/sigqueue/9-1.c index 6320384..189a726 100644 --- a/testcases/open_posix_testsuite/conformance/interfaces/sigqueue/9-1.c +++ b/testcases/open_posix_testsuite/conformance/interfaces/sigqueue/9-1.c @@ -29,17 +29,73 @@ #include <unistd.h> #include <stdlib.h> #include <errno.h> +#include <string.h> +#include <fcntl.h> #include "posixtest.h" void myhandler(int signo, siginfo_t *info, void *context) { printf ("Inside Handler\n"); } +#ifndef __linux +void get_sigpending(int pid, long *current) {}; +#else +void get_sigpending(int pid, long *current) +{ + int fd, len; + char procdir[128] = ""; + char line[1024] = ""; + char *pos, *pos2, *sig; + + snprintf(procdir, sizeof(procdir) - 1, "/proc/%d/status", pid); + procdir[sizeof(procdir) - 1] = '\0'; + + fd = open(procdir, O_RDONLY); + if (fd == -1) { + perror("Can't open the proc file"); + return; + } + + len = read(fd, line, sizeof(line) - 1); + close(fd); + + if (len <= 0) { + perror("Read file error"); + return; + } else { + line[len] = '\0'; + } + + pos = strstr(line, "SigQ:"); + if (pos == NULL) { + printf("Can't find the SigQ: string.\n"); + return; + } + + pos2 = strchr(pos, '\n'); + if (pos2 == NULL) { + printf("Can't get the position of the newline character.\n"); + return; + } + + sig = pos; + sig[pos2 - pos] = '\0'; + sig = strrchr(sig, '\t'); + if (sig == NULL) { + printf("Can't find the tab character.\n"); + return; + } + + if (sscanf(sig, "%ld", current) != 1) + perror("Can't get the current value"); +} +#endif + int main() { - int pid, i; - long syslimit; + int pid; + long curr = 0, syslimit; union sigval value; struct sigaction act; @@ -63,8 +119,8 @@ int main() " not a bug.\n"); return PTS_PASS; } - - for (i=0; i<syslimit; i++) { + get_sigpending(pid, &curr); + for (; curr < syslimit; curr++) { if (sigqueue(pid, SIGTOTEST, value) != 0) { printf("Test UNRESOLVED: call to sigqueue did not return success\n"); return PTS_UNRESOLVED; @@ -81,4 +137,4 @@ int main() } return PTS_PASS; -} \ No newline at end of file +} -- 1.7.6 |