1#!/bin/sh 2 3# 4# Copyright (c) 2013 EMC Corp. 5# All rights reserved. 6# 7# Redistribution and use in source and binary forms, with or without 8# modification, are permitted provided that the following conditions 9# are met: 10# 1. Redistributions of source code must retain the above copyright 11# notice, this list of conditions and the following disclaimer. 12# 2. Redistributions in binary form must reproduce the above copyright 13# notice, this list of conditions and the following disclaimer in the 14# documentation and/or other materials provided with the distribution. 15# 16# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 17# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26# SUCH DAMAGE. 27# 28 29# Regression test for kern/142757, race condition in traced process signal 30# handling. Fixed in r202692. 31 32# Test scenario by Tijl Coosemans, tijl@ 33 34. ../default.cfg 35 36cd /tmp 37 38cat > race1.c <<EOF 39#include <sys/types.h> 40#include <sys/ptrace.h> 41#include <sys/wait.h> 42#include <signal.h> 43#include <stdio.h> 44#include <unistd.h> 45 46int 47main(void) 48{ 49 pid_t pid; 50 int i, status; 51 52 alarm(120); 53 /* fork dummy child process */ 54 pid = fork(); 55 if (pid == 0) { 56 /* child does nothing */ 57 for (;;) { 58 sleep(1); 59 } 60 } else { 61 /* parent */ 62 sleep(1); 63 for (i = 0; i < 100000; i++) { 64 /* loop: attach, wait, detach */ 65 printf("attach "); 66 fflush(stdout); 67 ptrace(PT_ATTACH, pid, (caddr_t) 0, 0); 68 69 printf("wait "); 70 fflush(stdout); 71 wait4(pid, &status, 0, NULL); 72 73 printf("detach "); 74 fflush(stdout); 75 ptrace(PT_DETACH, pid, (caddr_t) 1, 0); 76 77 printf("ok\n"); 78 fflush(stdout); 79 } 80 } 81 kill(pid, SIGINT); 82 83 return (0); 84} 85EOF 86 87cat > race2.c <<EOF 88#include <sys/types.h> 89#include <sys/ptrace.h> 90#include <sys/wait.h> 91#include <signal.h> 92#include <stdio.h> 93#include <unistd.h> 94 95int 96main(void) 97{ 98 pid_t pid; 99 int i, status; 100 101 alarm(120); 102 /* fork dummy child process */ 103 pid = fork(); 104 if (pid == 0) { 105 /* child does nothing */ 106 for (;;) { 107 sleep(1); 108 } 109 } else { 110 /* parent */ 111 sleep(1); 112 ptrace(PT_ATTACH, pid, (caddr_t) 0, 0); 113 wait4(pid, &status, 0, NULL); 114 for (i = 0; i < 100000; i++) { 115 /* loop: continue, kill, wait */ 116 printf("continue "); 117 fflush(stdout); 118 ptrace(PT_CONTINUE, pid, (caddr_t) 1, 0); 119 120 printf("kill "); 121 fflush(stdout); 122 kill(pid, SIGINT); 123 124 printf("wait "); 125 fflush(stdout); 126 wait4(pid, &status, 0, NULL); 127 128 printf("ok\n"); 129 fflush(stdout); 130 } 131 } 132 133 return (0); 134} 135EOF 136 137mycc -o race1 -Wall -Wextra race1.c 138mycc -o race2 -Wall -Wextra race2.c 139 140./race1 > /dev/null || echo "FAIL #1" 141./race2 > /dev/null || echo "FAIL #2" 142 143rm -f race1.c race1 race2.c race2 144