1 /* 2 * Copyright (C) 2012 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #include <errno.h> 18 #include <signal.h> 19 #include <sys/syscall.h> 20 #include <sys/types.h> 21 #include <unistd.h> 22 23 #include <gtest/gtest.h> 24 25 #include "ScopedSignalHandler.h" 26 27 static size_t SIGNAL_MIN() { 28 return 1; // Signals start at 1 (SIGHUP), not 0. 29 } 30 31 static size_t SIGNAL_MAX() { 32 size_t result = SIGRTMAX; 33 34 #if defined(__BIONIC__) && !defined(__mips__) && !defined(__LP64__) 35 // 32-bit bionic's sigset_t is too small for ARM and x86: 32 bits instead of 64. 36 // This means you can't refer to any of the real-time signals. 37 // See http://b/3038348 and http://b/5828899. 38 result = 32; 39 #else 40 // Otherwise, C libraries should be perfectly capable of using their largest signal. 41 if (sizeof(sigset_t) * 8 < static_cast<size_t>(SIGRTMAX)) { 42 abort(); 43 } 44 #endif 45 46 return result; 47 } 48 49 template <typename Fn> 50 static void TestSigSet1(Fn fn) { 51 // NULL sigset_t*. 52 sigset_t* set_ptr = NULL; 53 errno = 0; 54 ASSERT_EQ(-1, fn(set_ptr)); 55 ASSERT_EQ(EINVAL, errno); 56 57 // Non-NULL. 58 sigset_t set; 59 errno = 0; 60 ASSERT_EQ(0, fn(&set)); 61 ASSERT_EQ(0, errno); 62 } 63 64 template <typename Fn> 65 static void TestSigSet2(Fn fn) { 66 // NULL sigset_t*. 67 sigset_t* set_ptr = NULL; 68 errno = 0; 69 ASSERT_EQ(-1, fn(set_ptr, SIGSEGV)); 70 ASSERT_EQ(EINVAL, errno); 71 72 sigset_t set; 73 sigemptyset(&set); 74 75 // Bad signal number: too small. 76 errno = 0; 77 ASSERT_EQ(-1, fn(&set, 0)); 78 ASSERT_EQ(EINVAL, errno); 79 80 // Bad signal number: too high. 81 errno = 0; 82 ASSERT_EQ(-1, fn(&set, SIGNAL_MAX() + 1)); 83 ASSERT_EQ(EINVAL, errno); 84 85 // Good signal numbers, low and high ends of range. 86 errno = 0; 87 ASSERT_EQ(0, fn(&set, SIGNAL_MIN())); 88 ASSERT_EQ(0, errno); 89 ASSERT_EQ(0, fn(&set, SIGNAL_MAX())); 90 ASSERT_EQ(0, errno); 91 } 92 93 TEST(signal, sigismember_invalid) { 94 TestSigSet2(sigismember); 95 } 96 97 TEST(signal, sigaddset_invalid) { 98 TestSigSet2(sigaddset); 99 } 100 101 TEST(signal, sigdelset_invalid) { 102 TestSigSet2(sigdelset); 103 } 104 105 TEST(signal, sigemptyset_invalid) { 106 TestSigSet1(sigemptyset); 107 } 108 109 TEST(signal, sigfillset_invalid) { 110 TestSigSet1(sigfillset); 111 } 112 113 TEST(signal, raise_invalid) { 114 errno = 0; 115 ASSERT_EQ(-1, raise(-1)); 116 ASSERT_EQ(EINVAL, errno); 117 } 118 119 static void raise_in_signal_handler_helper(int signal_number) { 120 ASSERT_EQ(SIGALRM, signal_number); 121 static int count = 0; 122 if (++count == 1) { 123 raise(SIGALRM); 124 } 125 } 126 127 TEST(signal, raise_in_signal_handler) { 128 ScopedSignalHandler ssh(SIGALRM, raise_in_signal_handler_helper); 129 raise(SIGALRM); 130 } 131 132 static void HandleSIGALRM(int signal_number) { 133 ASSERT_EQ(SIGALRM, signal_number); 134 } 135 136 TEST(signal, sigwait) { 137 ScopedSignalHandler ssh(SIGALRM, HandleSIGALRM); 138 139 sigset_t wait_set; 140 sigemptyset(&wait_set); 141 sigaddset(&wait_set, SIGALRM); 142 143 alarm(1); 144 145 int received_signal; 146 errno = 0; 147 ASSERT_EQ(0, sigwait(&wait_set, &received_signal)); 148 ASSERT_EQ(0, errno); 149 ASSERT_EQ(SIGALRM, received_signal); 150 } 151 152 static int g_sigsuspend_test_helper_call_count = 0; 153 154 static void SigSuspendTestHelper(int) { 155 ++g_sigsuspend_test_helper_call_count; 156 } 157 158 TEST(signal, sigsuspend_sigpending) { 159 // Block SIGALRM. 160 sigset_t just_SIGALRM; 161 sigemptyset(&just_SIGALRM); 162 sigaddset(&just_SIGALRM, SIGALRM); 163 sigset_t original_set; 164 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, &just_SIGALRM, &original_set)); 165 166 ScopedSignalHandler ssh(SIGALRM, SigSuspendTestHelper); 167 168 // There should be no pending signals. 169 sigset_t pending; 170 sigemptyset(&pending); 171 ASSERT_EQ(0, sigpending(&pending)); 172 for (size_t i = SIGNAL_MIN(); i <= SIGNAL_MAX(); ++i) { 173 EXPECT_FALSE(sigismember(&pending, i)) << i; 174 } 175 176 // Raise SIGALRM and check our signal handler wasn't called. 177 raise(SIGALRM); 178 ASSERT_EQ(0, g_sigsuspend_test_helper_call_count); 179 180 // We should now have a pending SIGALRM but nothing else. 181 sigemptyset(&pending); 182 ASSERT_EQ(0, sigpending(&pending)); 183 for (size_t i = SIGNAL_MIN(); i <= SIGNAL_MAX(); ++i) { 184 EXPECT_EQ((i == SIGALRM), sigismember(&pending, i)); 185 } 186 187 // Use sigsuspend to block everything except SIGALRM... 188 sigset_t not_SIGALRM; 189 sigfillset(¬_SIGALRM); 190 sigdelset(¬_SIGALRM, SIGALRM); 191 ASSERT_EQ(-1, sigsuspend(¬_SIGALRM)); 192 ASSERT_EQ(EINTR, errno); 193 // ...and check that we now receive our pending SIGALRM. 194 ASSERT_EQ(1, g_sigsuspend_test_helper_call_count); 195 196 // Restore the original set. 197 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, &original_set, NULL)); 198 } 199 200 static void EmptySignalHandler(int) {} 201 static void EmptySignalAction(int, siginfo_t*, void*) {} 202 203 TEST(signal, sigaction) { 204 // Both bionic and glibc set SA_RESTORER when talking to the kernel on arm, 205 // arm64, x86, and x86-64. The version of glibc we're using also doesn't 206 // define SA_RESTORER, but luckily it's the same value everywhere, and mips 207 // doesn't use the bit for anything. 208 static const unsigned sa_restorer = 0x4000000; 209 210 // See what's currently set for SIGALRM. 211 struct sigaction original_sa; 212 memset(&original_sa, 0, sizeof(original_sa)); 213 ASSERT_EQ(0, sigaction(SIGALRM, NULL, &original_sa)); 214 ASSERT_TRUE(original_sa.sa_handler == NULL); 215 ASSERT_TRUE(original_sa.sa_sigaction == NULL); 216 ASSERT_EQ(0U, original_sa.sa_flags & ~sa_restorer); 217 218 // Set a traditional sa_handler signal handler. 219 struct sigaction sa; 220 memset(&sa, 0, sizeof(sa)); 221 sigaddset(&sa.sa_mask, SIGALRM); 222 sa.sa_flags = SA_ONSTACK; 223 sa.sa_handler = EmptySignalHandler; 224 ASSERT_EQ(0, sigaction(SIGALRM, &sa, NULL)); 225 226 // Check that we can read it back. 227 memset(&sa, 0, sizeof(sa)); 228 ASSERT_EQ(0, sigaction(SIGALRM, NULL, &sa)); 229 ASSERT_TRUE(sa.sa_handler == EmptySignalHandler); 230 ASSERT_TRUE((void*) sa.sa_sigaction == (void*) sa.sa_handler); 231 ASSERT_EQ(static_cast<unsigned>(SA_ONSTACK), sa.sa_flags & ~sa_restorer); 232 233 // Set a new-style sa_sigaction signal handler. 234 memset(&sa, 0, sizeof(sa)); 235 sigaddset(&sa.sa_mask, SIGALRM); 236 sa.sa_flags = SA_ONSTACK | SA_SIGINFO; 237 sa.sa_sigaction = EmptySignalAction; 238 ASSERT_EQ(0, sigaction(SIGALRM, &sa, NULL)); 239 240 // Check that we can read it back. 241 memset(&sa, 0, sizeof(sa)); 242 ASSERT_EQ(0, sigaction(SIGALRM, NULL, &sa)); 243 ASSERT_TRUE(sa.sa_sigaction == EmptySignalAction); 244 ASSERT_TRUE((void*) sa.sa_sigaction == (void*) sa.sa_handler); 245 ASSERT_EQ(static_cast<unsigned>(SA_ONSTACK | SA_SIGINFO), sa.sa_flags & ~sa_restorer); 246 247 // Put everything back how it was. 248 ASSERT_EQ(0, sigaction(SIGALRM, &original_sa, NULL)); 249 } 250 251 TEST(signal, sys_signame) { 252 #if defined(__BIONIC__) 253 ASSERT_TRUE(sys_signame[0] == NULL); 254 ASSERT_STREQ("HUP", sys_signame[SIGHUP]); 255 #else 256 GTEST_LOG_(INFO) << "This test does nothing.\n"; 257 #endif 258 } 259 260 TEST(signal, sys_siglist) { 261 ASSERT_TRUE(sys_siglist[0] == NULL); 262 ASSERT_STREQ("Hangup", sys_siglist[SIGHUP]); 263 } 264 265 TEST(signal, limits) { 266 // This comes from the kernel. 267 ASSERT_EQ(32, __SIGRTMIN); 268 269 // We reserve a non-zero number at the bottom for ourselves. 270 ASSERT_GT(SIGRTMIN, __SIGRTMIN); 271 272 // MIPS has more signals than everyone else. 273 #if defined(__mips__) 274 ASSERT_EQ(128, __SIGRTMAX); 275 #else 276 ASSERT_EQ(64, __SIGRTMAX); 277 #endif 278 279 // We don't currently reserve any at the top. 280 ASSERT_EQ(SIGRTMAX, __SIGRTMAX); 281 } 282 283 static int g_sigqueue_signal_handler_call_count = 0; 284 285 static void SigqueueSignalHandler(int signum, siginfo_t* info, void*) { 286 ASSERT_EQ(SIGALRM, signum); 287 ASSERT_EQ(SIGALRM, info->si_signo); 288 ASSERT_EQ(SI_QUEUE, info->si_code); 289 ASSERT_EQ(1, info->si_value.sival_int); 290 ++g_sigqueue_signal_handler_call_count; 291 } 292 293 TEST(signal, sigqueue) { 294 ScopedSignalHandler ssh(SIGALRM, SigqueueSignalHandler, SA_SIGINFO); 295 sigval_t sigval; 296 sigval.sival_int = 1; 297 errno = 0; 298 ASSERT_EQ(0, sigqueue(getpid(), SIGALRM, sigval)); 299 ASSERT_EQ(0, errno); 300 ASSERT_EQ(1, g_sigqueue_signal_handler_call_count); 301 } 302 303 TEST(signal, sigwaitinfo) { 304 // Block SIGALRM. 305 sigset_t just_SIGALRM; 306 sigemptyset(&just_SIGALRM); 307 sigaddset(&just_SIGALRM, SIGALRM); 308 sigset_t original_set; 309 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, &just_SIGALRM, &original_set)); 310 311 // Raise SIGALRM. 312 sigval_t sigval; 313 sigval.sival_int = 1; 314 ASSERT_EQ(0, sigqueue(getpid(), SIGALRM, sigval)); 315 316 // Get pending SIGALRM. 317 siginfo_t info; 318 errno = 0; 319 ASSERT_EQ(SIGALRM, sigwaitinfo(&just_SIGALRM, &info)); 320 ASSERT_EQ(0, errno); 321 ASSERT_EQ(SIGALRM, info.si_signo); 322 ASSERT_EQ(1, info.si_value.sival_int); 323 324 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, &original_set, NULL)); 325 } 326 327 TEST(signal, sigtimedwait) { 328 // Block SIGALRM. 329 sigset_t just_SIGALRM; 330 sigemptyset(&just_SIGALRM); 331 sigaddset(&just_SIGALRM, SIGALRM); 332 sigset_t original_set; 333 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, &just_SIGALRM, &original_set)); 334 335 // Raise SIGALRM. 336 sigval_t sigval; 337 sigval.sival_int = 1; 338 ASSERT_EQ(0, sigqueue(getpid(), SIGALRM, sigval)); 339 340 // Get pending SIGALRM. 341 siginfo_t info; 342 struct timespec timeout; 343 timeout.tv_sec = 2; 344 timeout.tv_nsec = 0; 345 errno = 0; 346 ASSERT_EQ(SIGALRM, sigtimedwait(&just_SIGALRM, &info, &timeout)); 347 ASSERT_EQ(0, errno); 348 349 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, &original_set, NULL)); 350 } 351 352 static int64_t NanoTime() { 353 struct timespec t; 354 t.tv_sec = t.tv_nsec = 0; 355 clock_gettime(CLOCK_MONOTONIC, &t); 356 return static_cast<int64_t>(t.tv_sec) * 1000000000LL + t.tv_nsec; 357 } 358 359 TEST(signal, sigtimedwait_timeout) { 360 // Block SIGALRM. 361 sigset_t just_SIGALRM; 362 sigemptyset(&just_SIGALRM); 363 sigaddset(&just_SIGALRM, SIGALRM); 364 sigset_t original_set; 365 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, &just_SIGALRM, &original_set)); 366 367 // Wait timeout. 368 int64_t start_time = NanoTime(); 369 siginfo_t info; 370 struct timespec timeout; 371 timeout.tv_sec = 0; 372 timeout.tv_nsec = 1000000; 373 errno = 0; 374 ASSERT_EQ(-1, sigtimedwait(&just_SIGALRM, &info, &timeout)); 375 ASSERT_EQ(EAGAIN, errno); 376 ASSERT_GE(NanoTime() - start_time, 1000000); 377 378 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, &original_set, NULL)); 379 } 380 381 #if defined(__BIONIC__) 382 TEST(signal, rt_tgsigqueueinfo) { 383 // Test whether rt_tgsigqueueinfo allows sending arbitrary si_code values to self. 384 // If this fails, your kernel needs commit 66dd34a to be backported. 385 static constexpr char error_msg[] = 386 "\nPlease ensure that the following kernel patch has been applied:\n" 387 "* https://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/commit/?id=66dd34ad31e5963d72a700ec3f2449291d322921\n"; 388 static siginfo received; 389 390 struct sigaction handler; 391 memset(&handler, 0, sizeof(handler)); 392 handler.sa_sigaction = [](int, siginfo_t* siginfo, void*) { received = *siginfo; }; 393 handler.sa_flags = SA_SIGINFO; 394 395 ASSERT_EQ(0, sigaction(SIGUSR1, &handler, nullptr)); 396 397 siginfo sent; 398 memset(&sent, 0, sizeof(sent)); 399 400 sent.si_code = SI_TKILL; 401 ASSERT_EQ(0, syscall(SYS_rt_tgsigqueueinfo, getpid(), gettid(), SIGUSR1, &sent)) 402 << "rt_tgsigqueueinfo failed: " << strerror(errno) << error_msg; 403 ASSERT_EQ(sent.si_code, received.si_code) << "rt_tgsigqueueinfo modified si_code, expected " 404 << sent.si_code << ", received " << received.si_code 405 << error_msg; 406 407 sent.si_code = SI_USER; 408 ASSERT_EQ(0, syscall(SYS_rt_tgsigqueueinfo, getpid(), gettid(), SIGUSR1, &sent)) 409 << "rt_tgsigqueueinfo failed: " << strerror(errno) << error_msg; 410 ASSERT_EQ(sent.si_code, received.si_code) << "rt_tgsigqueueinfo modified si_code, expected " 411 << sent.si_code << ", received " << received.si_code 412 << error_msg; 413 } 414 415 #if defined(__arm__) || defined(__aarch64__) || defined(__i386__) || defined(__x86_64__) 416 TEST(signal, sigset_size) { 417 // The setjmp implementations for ARM, AArch64, x86, and x86_64 assume that sigset_t can fit in a 418 // long. This is true because ARM and x86 have broken rt signal support, and AArch64 and x86_64 419 // both have a SIGRTMAX defined as 64. 420 static_assert(sizeof(sigset_t) <= sizeof(long), "sigset_t doesn't fit in a long"); 421 } 422 423 #endif 424 #endif 425 426 TEST(signal, sigignore_EINVAL) { 427 errno = 0; 428 ASSERT_EQ(-1, sigignore(99999)); 429 ASSERT_EQ(EINVAL, errno); 430 } 431 432 TEST(signal, sigignore) { 433 errno = 0; 434 EXPECT_EQ(-1, sigignore(SIGKILL)); 435 EXPECT_EQ(errno, EINVAL); 436 437 errno = 0; 438 EXPECT_EQ(-1, sigignore(SIGSTOP)); 439 EXPECT_EQ(errno, EINVAL); 440 441 ScopedSignalHandler sigalrm{SIGALRM}; 442 ASSERT_EQ(0, sigignore(SIGALRM)); 443 444 struct sigaction sa; 445 ASSERT_EQ(0, sigaction(SIGALRM, nullptr, &sa)); 446 EXPECT_EQ(SIG_IGN, sa.sa_handler); 447 } 448 449 TEST(signal, sighold_EINVAL) { 450 errno = 0; 451 ASSERT_EQ(-1, sighold(99999)); 452 ASSERT_EQ(EINVAL, errno); 453 } 454 455 TEST(signal, sigpause_EINVAL) { 456 errno = 0; 457 ASSERT_EQ(-1, sigpause(99999)); 458 ASSERT_EQ(EINVAL, errno); 459 } 460 461 TEST(signal, sigrelse_EINVAL) { 462 errno = 0; 463 ASSERT_EQ(-1, sigpause(99999)); 464 ASSERT_EQ(EINVAL, errno); 465 } 466 467 TEST(signal, sighold_sigpause_sigrelse) { 468 static int sigalrm_handler_call_count; 469 auto sigalrm_handler = [](int) { sigalrm_handler_call_count++; }; 470 ScopedSignalHandler sigalrm{SIGALRM, sigalrm_handler}; 471 ScopedSignalMask mask; 472 sigset_t set; 473 474 // sighold(SIGALRM) should add SIGALRM to the signal mask ... 475 ASSERT_EQ(0, sighold(SIGALRM)); 476 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, 0, &set)); 477 EXPECT_TRUE(sigismember(&set, SIGALRM)); 478 479 // ... preventing our SIGALRM handler from running ... 480 raise(SIGALRM); 481 ASSERT_EQ(0, sigalrm_handler_call_count); 482 // ... until sigpause(SIGALRM) temporarily unblocks it. 483 ASSERT_EQ(-1, sigpause(SIGALRM)); 484 ASSERT_EQ(EINTR, errno); 485 ASSERT_EQ(1, sigalrm_handler_call_count); 486 487 // But sigpause(SIGALRM) shouldn't permanently unblock SIGALRM. 488 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, 0, &set)); 489 EXPECT_TRUE(sigismember(&set, SIGALRM)); 490 491 ASSERT_EQ(0, sigrelse(SIGALRM)); 492 ASSERT_EQ(0, sigprocmask(SIG_SETMASK, 0, &set)); 493 EXPECT_FALSE(sigismember(&set, SIGALRM)); 494 } 495 496 TEST(signal, sigset_EINVAL) { 497 errno = 0; 498 ASSERT_EQ(SIG_ERR, sigset(99999, SIG_DFL)); 499 ASSERT_EQ(EINVAL, errno); 500 } 501 502 TEST(signal, sigset) { 503 auto sigalrm_handler = [](int) { }; 504 ScopedSignalHandler sigalrm{SIGALRM, sigalrm_handler}; 505 ScopedSignalMask mask; 506 507 // block SIGALRM so the next sigset(SIGARLM) call will return SIG_HOLD 508 sigset_t sigalrm_set; 509 sigemptyset(&sigalrm_set); 510 sigaddset(&sigalrm_set, SIGALRM); 511 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, &sigalrm_set, nullptr)); 512 513 sigset_t set; 514 ASSERT_EQ(SIG_HOLD, sigset(SIGALRM, sigalrm_handler)); 515 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, nullptr, &set)); 516 EXPECT_FALSE(sigismember(&set, SIGALRM)); 517 518 ASSERT_EQ(sigalrm_handler, sigset(SIGALRM, SIG_IGN)); 519 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, nullptr, &set)); 520 EXPECT_FALSE(sigismember(&set, SIGALRM)); 521 522 ASSERT_EQ(SIG_IGN, sigset(SIGALRM, SIG_DFL)); 523 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, nullptr, &set)); 524 EXPECT_FALSE(sigismember(&set, SIGALRM)); 525 526 ASSERT_EQ(SIG_DFL, sigset(SIGALRM, SIG_HOLD)); 527 ASSERT_EQ(0, sigprocmask(SIG_BLOCK, nullptr, &set)); 528 EXPECT_TRUE(sigismember(&set, SIGALRM)); 529 } 530