Source file src/cmd/cgo/internal/testsanitizers/cshared_test.go

     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  
     5  //go:build linux || (freebsd && amd64)
     6  
     7  package sanitizers_test
     8  
     9  import (
    10  	"fmt"
    11  	"internal/platform"
    12  	"internal/testenv"
    13  	"os"
    14  	"strings"
    15  	"testing"
    16  )
    17  
    18  func TestShared(t *testing.T) {
    19  	testenv.MustHaveGoBuild(t)
    20  	testenv.MustHaveCGO(t)
    21  	testenv.MustHaveBuildMode(t, "c-shared")
    22  
    23  	t.Parallel()
    24  	requireOvercommit(t)
    25  
    26  	GOOS, err := goEnv("GOOS")
    27  	if err != nil {
    28  		t.Fatal(err)
    29  	}
    30  
    31  	GOARCH, err := goEnv("GOARCH")
    32  	if err != nil {
    33  		t.Fatal(err)
    34  	}
    35  
    36  	libExt := "so"
    37  	if GOOS == "darwin" {
    38  		libExt = "dylib"
    39  	}
    40  
    41  	cases := []struct {
    42  		src       string
    43  		sanitizer string
    44  	}{
    45  		{
    46  			src:       "msan_shared.go",
    47  			sanitizer: "memory",
    48  		},
    49  		{
    50  			src:       "tsan_shared.go",
    51  			sanitizer: "thread",
    52  		},
    53  	}
    54  
    55  	for _, tc := range cases {
    56  		tc := tc
    57  		name := strings.TrimSuffix(tc.src, ".go")
    58  		//The memory sanitizer tests require support for the -msan option.
    59  		if tc.sanitizer == "memory" && !platform.MSanSupported(GOOS, GOARCH) {
    60  			t.Logf("skipping %s test on %s/%s; -msan option is not supported.", name, GOOS, GOARCH)
    61  			continue
    62  		}
    63  		if tc.sanitizer == "thread" && !compilerRequiredTsanVersion(GOOS, GOARCH) {
    64  			t.Logf("skipping %s test on %s/%s; compiler version too old for -tsan.", name, GOOS, GOARCH)
    65  			continue
    66  		}
    67  
    68  		t.Run(name, func(t *testing.T) {
    69  			t.Parallel()
    70  			config := configure(tc.sanitizer)
    71  			config.skipIfCSanitizerBroken(t)
    72  
    73  			dir := newTempDir(t)
    74  			defer dir.RemoveAll(t)
    75  
    76  			lib := dir.Join(fmt.Sprintf("lib%s.%s", name, libExt))
    77  			mustRun(t, config.goCmd("build", "-buildmode=c-shared", "-o", lib, srcPath(tc.src)))
    78  
    79  			cSrc := dir.Join("main.c")
    80  			if err := os.WriteFile(cSrc, cMain, 0600); err != nil {
    81  				t.Fatalf("failed to write C source file: %v", err)
    82  			}
    83  
    84  			dstBin := dir.Join(name)
    85  			cmd, err := cc(config.cFlags...)
    86  			if err != nil {
    87  				t.Fatal(err)
    88  			}
    89  			cmd.Args = append(cmd.Args, config.ldFlags...)
    90  			cmd.Args = append(cmd.Args, "-o", dstBin, cSrc, lib)
    91  			mustRun(t, cmd)
    92  
    93  			cmd = hangProneCmd(dstBin)
    94  			replaceEnv(cmd, "LD_LIBRARY_PATH", ".")
    95  			mustRun(t, cmd)
    96  		})
    97  	}
    98  }
    99  

View as plain text