summaryrefslogtreecommitdiff
path: root/src/pkg/runtime/syscall_windows_test.go
diff options
context:
space:
mode:
Diffstat (limited to 'src/pkg/runtime/syscall_windows_test.go')
-rw-r--r--src/pkg/runtime/syscall_windows_test.go451
1 files changed, 0 insertions, 451 deletions
diff --git a/src/pkg/runtime/syscall_windows_test.go b/src/pkg/runtime/syscall_windows_test.go
deleted file mode 100644
index fabf935d8..000000000
--- a/src/pkg/runtime/syscall_windows_test.go
+++ /dev/null
@@ -1,451 +0,0 @@
-// Copyright 2010 The Go Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style
-// license that can be found in the LICENSE file.
-
-package runtime_test
-
-import (
- "fmt"
- "io/ioutil"
- "os"
- "os/exec"
- "path/filepath"
- "runtime"
- "strings"
- "syscall"
- "testing"
- "unsafe"
-)
-
-type DLL struct {
- *syscall.DLL
- t *testing.T
-}
-
-func GetDLL(t *testing.T, name string) *DLL {
- d, e := syscall.LoadDLL(name)
- if e != nil {
- t.Fatal(e)
- }
- return &DLL{DLL: d, t: t}
-}
-
-func (d *DLL) Proc(name string) *syscall.Proc {
- p, e := d.FindProc(name)
- if e != nil {
- d.t.Fatal(e)
- }
- return p
-}
-
-func TestStdCall(t *testing.T) {
- type Rect struct {
- left, top, right, bottom int32
- }
- res := Rect{}
- expected := Rect{1, 1, 40, 60}
- a, _, _ := GetDLL(t, "user32.dll").Proc("UnionRect").Call(
- uintptr(unsafe.Pointer(&res)),
- uintptr(unsafe.Pointer(&Rect{10, 1, 14, 60})),
- uintptr(unsafe.Pointer(&Rect{1, 2, 40, 50})))
- if a != 1 || res.left != expected.left ||
- res.top != expected.top ||
- res.right != expected.right ||
- res.bottom != expected.bottom {
- t.Error("stdcall USER32.UnionRect returns", a, "res=", res)
- }
-}
-
-func Test64BitReturnStdCall(t *testing.T) {
-
- const (
- VER_BUILDNUMBER = 0x0000004
- VER_MAJORVERSION = 0x0000002
- VER_MINORVERSION = 0x0000001
- VER_PLATFORMID = 0x0000008
- VER_PRODUCT_TYPE = 0x0000080
- VER_SERVICEPACKMAJOR = 0x0000020
- VER_SERVICEPACKMINOR = 0x0000010
- VER_SUITENAME = 0x0000040
-
- VER_EQUAL = 1
- VER_GREATER = 2
- VER_GREATER_EQUAL = 3
- VER_LESS = 4
- VER_LESS_EQUAL = 5
-
- ERROR_OLD_WIN_VERSION syscall.Errno = 1150
- )
-
- type OSVersionInfoEx struct {
- OSVersionInfoSize uint32
- MajorVersion uint32
- MinorVersion uint32
- BuildNumber uint32
- PlatformId uint32
- CSDVersion [128]uint16
- ServicePackMajor uint16
- ServicePackMinor uint16
- SuiteMask uint16
- ProductType byte
- Reserve byte
- }
-
- d := GetDLL(t, "kernel32.dll")
-
- var m1, m2 uintptr
- VerSetConditionMask := d.Proc("VerSetConditionMask")
- m1, m2, _ = VerSetConditionMask.Call(m1, m2, VER_MAJORVERSION, VER_GREATER_EQUAL)
- m1, m2, _ = VerSetConditionMask.Call(m1, m2, VER_MINORVERSION, VER_GREATER_EQUAL)
- m1, m2, _ = VerSetConditionMask.Call(m1, m2, VER_SERVICEPACKMAJOR, VER_GREATER_EQUAL)
- m1, m2, _ = VerSetConditionMask.Call(m1, m2, VER_SERVICEPACKMINOR, VER_GREATER_EQUAL)
-
- vi := OSVersionInfoEx{
- MajorVersion: 5,
- MinorVersion: 1,
- ServicePackMajor: 2,
- ServicePackMinor: 0,
- }
- vi.OSVersionInfoSize = uint32(unsafe.Sizeof(vi))
- r, _, e2 := d.Proc("VerifyVersionInfoW").Call(
- uintptr(unsafe.Pointer(&vi)),
- VER_MAJORVERSION|VER_MINORVERSION|VER_SERVICEPACKMAJOR|VER_SERVICEPACKMINOR,
- m1, m2)
- if r == 0 && e2 != ERROR_OLD_WIN_VERSION {
- t.Errorf("VerifyVersionInfo failed: %s", e2)
- }
-}
-
-func TestCDecl(t *testing.T) {
- var buf [50]byte
- fmtp, _ := syscall.BytePtrFromString("%d %d %d")
- a, _, _ := GetDLL(t, "user32.dll").Proc("wsprintfA").Call(
- uintptr(unsafe.Pointer(&buf[0])),
- uintptr(unsafe.Pointer(fmtp)),
- 1000, 2000, 3000)
- if string(buf[:a]) != "1000 2000 3000" {
- t.Error("cdecl USER32.wsprintfA returns", a, "buf=", buf[:a])
- }
-}
-
-func TestEnumWindows(t *testing.T) {
- d := GetDLL(t, "user32.dll")
- isWindows := d.Proc("IsWindow")
- counter := 0
- cb := syscall.NewCallback(func(hwnd syscall.Handle, lparam uintptr) uintptr {
- if lparam != 888 {
- t.Error("lparam was not passed to callback")
- }
- b, _, _ := isWindows.Call(uintptr(hwnd))
- if b == 0 {
- t.Error("USER32.IsWindow returns FALSE")
- }
- counter++
- return 1 // continue enumeration
- })
- a, _, _ := d.Proc("EnumWindows").Call(cb, 888)
- if a == 0 {
- t.Error("USER32.EnumWindows returns FALSE")
- }
- if counter == 0 {
- t.Error("Callback has been never called or your have no windows")
- }
-}
-
-func callback(hwnd syscall.Handle, lparam uintptr) uintptr {
- (*(*func())(unsafe.Pointer(&lparam)))()
- return 0 // stop enumeration
-}
-
-// nestedCall calls into Windows, back into Go, and finally to f.
-func nestedCall(t *testing.T, f func()) {
- c := syscall.NewCallback(callback)
- d := GetDLL(t, "user32.dll")
- defer d.Release()
- d.Proc("EnumWindows").Call(c, uintptr(*(*unsafe.Pointer)(unsafe.Pointer(&f))))
-}
-
-func TestCallback(t *testing.T) {
- var x = false
- nestedCall(t, func() { x = true })
- if !x {
- t.Fatal("nestedCall did not call func")
- }
-}
-
-func TestCallbackGC(t *testing.T) {
- nestedCall(t, runtime.GC)
-}
-
-func TestCallbackPanicLocked(t *testing.T) {
- runtime.LockOSThread()
- defer runtime.UnlockOSThread()
-
- if !runtime.LockedOSThread() {
- t.Fatal("runtime.LockOSThread didn't")
- }
- defer func() {
- s := recover()
- if s == nil {
- t.Fatal("did not panic")
- }
- if s.(string) != "callback panic" {
- t.Fatal("wrong panic:", s)
- }
- if !runtime.LockedOSThread() {
- t.Fatal("lost lock on OS thread after panic")
- }
- }()
- nestedCall(t, func() { panic("callback panic") })
- panic("nestedCall returned")
-}
-
-func TestCallbackPanic(t *testing.T) {
- // Make sure panic during callback unwinds properly.
- if runtime.LockedOSThread() {
- t.Fatal("locked OS thread on entry to TestCallbackPanic")
- }
- defer func() {
- s := recover()
- if s == nil {
- t.Fatal("did not panic")
- }
- if s.(string) != "callback panic" {
- t.Fatal("wrong panic:", s)
- }
- if runtime.LockedOSThread() {
- t.Fatal("locked OS thread on exit from TestCallbackPanic")
- }
- }()
- nestedCall(t, func() { panic("callback panic") })
- panic("nestedCall returned")
-}
-
-func TestCallbackPanicLoop(t *testing.T) {
- // Make sure we don't blow out m->g0 stack.
- for i := 0; i < 100000; i++ {
- TestCallbackPanic(t)
- }
-}
-
-func TestBlockingCallback(t *testing.T) {
- c := make(chan int)
- go func() {
- for i := 0; i < 10; i++ {
- c <- <-c
- }
- }()
- nestedCall(t, func() {
- for i := 0; i < 10; i++ {
- c <- i
- if j := <-c; j != i {
- t.Errorf("out of sync %d != %d", j, i)
- }
- }
- })
-}
-
-func TestCallbackInAnotherThread(t *testing.T) {
- // TODO: test a function which calls back in another thread: QueueUserAPC() or CreateThread()
-}
-
-type cbDLLFunc int // int determines number of callback parameters
-
-func (f cbDLLFunc) stdcallName() string {
- return fmt.Sprintf("stdcall%d", f)
-}
-
-func (f cbDLLFunc) cdeclName() string {
- return fmt.Sprintf("cdecl%d", f)
-}
-
-func (f cbDLLFunc) buildOne(stdcall bool) string {
- var funcname, attr string
- if stdcall {
- funcname = f.stdcallName()
- attr = "__stdcall"
- } else {
- funcname = f.cdeclName()
- attr = "__cdecl"
- }
- typename := "t" + funcname
- p := make([]string, f)
- for i := range p {
- p[i] = "void*"
- }
- params := strings.Join(p, ",")
- for i := range p {
- p[i] = fmt.Sprintf("%d", i+1)
- }
- args := strings.Join(p, ",")
- return fmt.Sprintf(`
-typedef void %s (*%s)(%s);
-void %s(%s f, void *n) {
- int i;
- for(i=0;i<(int)n;i++){
- f(%s);
- }
-}
- `, attr, typename, params, funcname, typename, args)
-}
-
-func (f cbDLLFunc) build() string {
- return f.buildOne(false) + f.buildOne(true)
-}
-
-var cbFuncs = [...]interface{}{
- 2: func(i1, i2 uintptr) uintptr {
- if i1+i2 != 3 {
- panic("bad input")
- }
- return 0
- },
- 3: func(i1, i2, i3 uintptr) uintptr {
- if i1+i2+i3 != 6 {
- panic("bad input")
- }
- return 0
- },
- 4: func(i1, i2, i3, i4 uintptr) uintptr {
- if i1+i2+i3+i4 != 10 {
- panic("bad input")
- }
- return 0
- },
- 5: func(i1, i2, i3, i4, i5 uintptr) uintptr {
- if i1+i2+i3+i4+i5 != 15 {
- panic("bad input")
- }
- return 0
- },
- 6: func(i1, i2, i3, i4, i5, i6 uintptr) uintptr {
- if i1+i2+i3+i4+i5+i6 != 21 {
- panic("bad input")
- }
- return 0
- },
- 7: func(i1, i2, i3, i4, i5, i6, i7 uintptr) uintptr {
- if i1+i2+i3+i4+i5+i6+i7 != 28 {
- panic("bad input")
- }
- return 0
- },
- 8: func(i1, i2, i3, i4, i5, i6, i7, i8 uintptr) uintptr {
- if i1+i2+i3+i4+i5+i6+i7+i8 != 36 {
- panic("bad input")
- }
- return 0
- },
- 9: func(i1, i2, i3, i4, i5, i6, i7, i8, i9 uintptr) uintptr {
- if i1+i2+i3+i4+i5+i6+i7+i8+i9 != 45 {
- panic("bad input")
- }
- return 0
- },
-}
-
-type cbDLL struct {
- name string
- buildArgs func(out, src string) []string
-}
-
-func (d *cbDLL) buildSrc(t *testing.T, path string) {
- f, err := os.Create(path)
- if err != nil {
- t.Fatalf("failed to create source file: %v", err)
- }
- defer f.Close()
-
- for i := 2; i < 10; i++ {
- fmt.Fprint(f, cbDLLFunc(i).build())
- }
-}
-
-func (d *cbDLL) build(t *testing.T, dir string) string {
- srcname := d.name + ".c"
- d.buildSrc(t, filepath.Join(dir, srcname))
- outname := d.name + ".dll"
- args := d.buildArgs(outname, srcname)
- cmd := exec.Command(args[0], args[1:]...)
- cmd.Dir = dir
- out, err := cmd.CombinedOutput()
- if err != nil {
- t.Fatalf("failed to build dll: %v - %v", err, string(out))
- }
- return filepath.Join(dir, outname)
-}
-
-var cbDLLs = []cbDLL{
- {
- "test",
- func(out, src string) []string {
- return []string{"gcc", "-shared", "-s", "-o", out, src}
- },
- },
- {
- "testO2",
- func(out, src string) []string {
- return []string{"gcc", "-shared", "-s", "-o", out, "-O2", src}
- },
- },
-}
-
-type cbTest struct {
- n int // number of callback parameters
- param uintptr // dll function parameter
-}
-
-func (test *cbTest) run(t *testing.T, dllpath string) {
- dll := syscall.MustLoadDLL(dllpath)
- defer dll.Release()
- cb := cbFuncs[test.n]
- stdcall := syscall.NewCallback(cb)
- f := cbDLLFunc(test.n)
- test.runOne(t, dll, f.stdcallName(), stdcall)
- cdecl := syscall.NewCallbackCDecl(cb)
- test.runOne(t, dll, f.cdeclName(), cdecl)
-}
-
-func (test *cbTest) runOne(t *testing.T, dll *syscall.DLL, proc string, cb uintptr) {
- defer func() {
- if r := recover(); r != nil {
- t.Errorf("dll call %v(..., %d) failed: %v", proc, test.param, r)
- }
- }()
- dll.MustFindProc(proc).Call(cb, test.param)
-}
-
-var cbTests = []cbTest{
- {2, 1},
- {2, 10000},
- {3, 3},
- {4, 5},
- {4, 6},
- {5, 2},
- {6, 7},
- {6, 8},
- {7, 6},
- {8, 1},
- {9, 8},
- {9, 10000},
- {3, 4},
- {5, 3},
- {7, 7},
- {8, 2},
- {9, 9},
-}
-
-func TestStdcallAndCDeclCallbacks(t *testing.T) {
- tmp, err := ioutil.TempDir("", "TestCDeclCallback")
- if err != nil {
- t.Fatal("TempDir failed: ", err)
- }
- defer os.RemoveAll(tmp)
-
- for _, dll := range cbDLLs {
- dllPath := dll.build(t, tmp)
- for _, test := range cbTests {
- test.run(t, dllPath)
- }
- }
-}