tsan_shared.go 1.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
  1. // Copyright 2017 The Go Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package main
  5. // This program failed with SIGSEGV when run under the C/C++ ThreadSanitizer.
  6. // The Go runtime had re-registered the C handler with the wrong flags due to a
  7. // typo, resulting in null pointers being passed for the info and context
  8. // parameters to the handler.
  9. /*
  10. #cgo CFLAGS: -fsanitize=thread
  11. #cgo LDFLAGS: -fsanitize=thread
  12. #include <signal.h>
  13. #include <stdio.h>
  14. #include <stdlib.h>
  15. #include <string.h>
  16. #include <ucontext.h>
  17. void check_params(int signo, siginfo_t *info, void *context) {
  18. ucontext_t* uc = (ucontext_t*)(context);
  19. if (info->si_signo != signo) {
  20. fprintf(stderr, "info->si_signo does not match signo.\n");
  21. abort();
  22. }
  23. if (uc->uc_stack.ss_size == 0) {
  24. fprintf(stderr, "uc_stack has size 0.\n");
  25. abort();
  26. }
  27. }
  28. // Set up the signal handler in a high priority constructor, so
  29. // that it is installed before the Go code starts.
  30. static void register_handler(void) __attribute__ ((constructor (200)));
  31. static void register_handler() {
  32. struct sigaction sa;
  33. memset(&sa, 0, sizeof(sa));
  34. sigemptyset(&sa.sa_mask);
  35. sa.sa_flags = SA_SIGINFO;
  36. sa.sa_sigaction = check_params;
  37. if (sigaction(SIGUSR1, &sa, NULL) != 0) {
  38. perror("failed to register SIGUSR1 handler");
  39. exit(EXIT_FAILURE);
  40. }
  41. }
  42. */
  43. import "C"
  44. import "syscall"
  45. func init() {
  46. C.raise(C.int(syscall.SIGUSR1))
  47. }
  48. func main() {}