aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorCherry Mui <cherryyz@google.com>2026-02-18 15:25:22 -0500
committerCherry Mui <cherryyz@google.com>2026-02-19 12:22:50 -0800
commit839cd82fa53ec481ffcd02e139b3d77c2724892e (patch)
tree64d9fa2aee670156b52333cacf83ca91818426cd /src
parent06dc5db75d4c2548c0187f34ce79389678be7ca0 (diff)
downloadgo-839cd82fa53ec481ffcd02e139b3d77c2724892e.tar.xz
cmd/cgo/internal/test: add a test for C calling into Go before init done
Test that C code can call back into Go (on a separate thread) before init is done. The callback should wait for the init done. And this should not cause a false race. This corresponds to the runtime fix in CL 746581. Change-Id: I10e6a9d5fe056be16143f5f6a322f51e56fc9fdf Reviewed-on: https://go-review.googlesource.com/c/go/+/746780 Reviewed-by: Mark Freeman <markfreeman@google.com> LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com> Reviewed-by: Ian Lance Taylor <iant@golang.org>
Diffstat (limited to 'src')
-rw-r--r--src/cmd/cgo/internal/test/cgo_test.go1
-rw-r--r--src/cmd/cgo/internal/test/cthread_unix.c15
-rw-r--r--src/cmd/cgo/internal/test/cthread_windows.c16
-rw-r--r--src/cmd/cgo/internal/test/testx.go26
4 files changed, 58 insertions, 0 deletions
diff --git a/src/cmd/cgo/internal/test/cgo_test.go b/src/cmd/cgo/internal/test/cgo_test.go
index 17f5f3531c..17f9225cf9 100644
--- a/src/cmd/cgo/internal/test/cgo_test.go
+++ b/src/cmd/cgo/internal/test/cgo_test.go
@@ -78,6 +78,7 @@ func TestBoolAlign(t *testing.T) { testBoolAlign(t) }
func TestCallGoWithString(t *testing.T) { testCallGoWithString(t) }
func TestCallback(t *testing.T) { testCallback(t) }
func TestCallbackCallers(t *testing.T) { testCallbackCallers(t) }
+func TestCallbackInInit(t *testing.T) { testCallbackInInit(t) }
func TestCallbackGC(t *testing.T) { testCallbackGC(t) }
func TestCallbackPanic(t *testing.T) { testCallbackPanic(t) }
func TestCallbackPanicLocked(t *testing.T) { testCallbackPanicLocked(t) }
diff --git a/src/cmd/cgo/internal/test/cthread_unix.c b/src/cmd/cgo/internal/test/cthread_unix.c
index d0da643158..1901c6437f 100644
--- a/src/cmd/cgo/internal/test/cthread_unix.c
+++ b/src/cmd/cgo/internal/test/cthread_unix.c
@@ -56,3 +56,18 @@ callGoInCThread(int max)
return max;
}
+
+static void*
+callbackInInitCThread(void* unused)
+{
+ callbackInInit();
+ return NULL;
+}
+
+void
+callbackInInitC(void)
+{
+ pthread_t thread;
+
+ pthread_create(&thread, NULL, callbackInInitCThread, NULL);
+}
diff --git a/src/cmd/cgo/internal/test/cthread_windows.c b/src/cmd/cgo/internal/test/cthread_windows.c
index 4e52209dee..5bfc6f2c48 100644
--- a/src/cmd/cgo/internal/test/cthread_windows.c
+++ b/src/cmd/cgo/internal/test/cthread_windows.c
@@ -57,3 +57,19 @@ callGoInCThread(int max)
CloseHandle((HANDLE)thread_id);
return max;
}
+
+__stdcall
+static unsigned int
+callbackInInitCThread(void* unused)
+{
+ callbackInInit();
+ return 0;
+}
+
+void
+callbackInInitC(void)
+{
+ uintptr_t thread_id;
+ thread_id = _beginthreadex(0, 0, callbackInInitCThread, NULL, 0, 0);
+ CloseHandle((HANDLE)thread_id);
+}
diff --git a/src/cmd/cgo/internal/test/testx.go b/src/cmd/cgo/internal/test/testx.go
index 5a6f42e44e..1c5ac99bd2 100644
--- a/src/cmd/cgo/internal/test/testx.go
+++ b/src/cmd/cgo/internal/test/testx.go
@@ -26,6 +26,7 @@ import (
// threads
extern void doAdd(int, int);
extern int callGoInCThread(int);
+extern void callbackInInitC(void);
// issue 1328
void IntoC(void);
@@ -622,3 +623,28 @@ func ditCallback() uint8 {
}
return 0
}
+
+// Test C calling back into Go before init is done.
+// In particular, this does not trigger false race
+// (the fix is in CL 746581).
+
+var callbackInInitVar int
+
+func init() {
+ C.callbackInInitC()
+ callbackInInitVar = 123
+}
+
+var callbackInInitChan = make(chan int)
+
+//export callbackInInit
+func callbackInInit() {
+ if callbackInInitVar != 123 {
+ panic("callbackInInitVar not initialized to 123")
+ }
+ callbackInInitChan <- 1
+}
+
+func testCallbackInInit(t *testing.T) {
+ <-callbackInInitChan // make sure callbackInInit runs
+}