Commit 6b335712 authored by Russ Cox's avatar Russ Cox

build: add all-qemu.bash, handful of arm fixes

R=r
CC=golang-dev
https://golang.org/cl/4313051
parent dacd1cad
......@@ -8,7 +8,7 @@ all: index.html
include ../../../src/Make.common
CLEANFILES+=index.html srcextract.bin htmlify.bin
CLEANFILES+=index.html srcextract.bin htmlify.bin get.bin
index.html: srcextract.bin htmlify.bin
PATH=.:$$PATH awk '/^!/{system(substr($$0,2)); next} {print}' < wiki.html | tr -d '\r' > index.html
......
#!/usr/bin/env bash
# Copyright 2011 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.
# Run all.bash but exclude tests that depend on functionality
# missing in QEMU's system call emulation.
export DISABLE_NET_TESTS=1 # no external network
export NOTEST=""
NOTEST="$NOTEST big" # xxx
NOTEST="$NOTEST http net rpc syslog websocket" # no localhost network
NOTEST="$NOTEST os" # 64-bit seek fails
./all.bash
......@@ -169,7 +169,7 @@ DIRS+=\
endif
NOTEST=\
NOTEST+=\
crypto\
crypto/openpgp/error\
debug/proc\
......@@ -196,7 +196,7 @@ NOTEST=\
../cmd/goyacc\
../cmd/hgpatch\
NOBENCH=\
NOBENCH+=\
container/vector\
# Disable tests that depend on an external network.
......
......@@ -114,7 +114,7 @@ func check(t *testing.T, source, golden string, mode checkMode) {
// start a timer to produce a time-out signal
tc := make(chan int)
go func() {
time.Sleep(2e9) // plenty of a safety margin, even for very slow machines
time.Sleep(10e9) // plenty of a safety margin, even for very slow machines
tc <- 0
}()
......
......@@ -135,6 +135,8 @@ sigaction(int32 i, void (*fn)(int32, Siginfo*, void*, G*), bool restart)
sa.sa_flags |= SA_RESTART;
sa.sa_mask = ~0ULL;
sa.sa_restorer = (void*)runtime·sigreturn;
if(fn == runtime·sighandler)
fn = (void*)runtime·sigtramp;
sa.sa_handler = fn;
runtime·rt_sigaction(i, &sa, nil, 8);
}
......
......@@ -13,7 +13,7 @@ SigTab runtime·sigtab[] = {
/* 1 */ Q+R, "SIGHUP: terminal line hangup",
/* 2 */ Q+R, "SIGINT: interrupt",
/* 3 */ C, "SIGQUIT: quit",
/* 4 */ C, "SIGILL: illegal instruction",
/* 4 */ C+P, "SIGILL: illegal instruction",
/* 5 */ C, "SIGTRAP: trace trap",
/* 6 */ C, "SIGABRT: abort",
/* 7 */ C+P, "SIGBUS: bus error",
......
......@@ -25,6 +25,7 @@ casfail:
RET
TEXT ·armCompareAndSwapUint64(SB),7,$0
BL fastCheck64<>(SB)
MOVW valptr+0(FP), R1
MOVW oldlo+4(FP), R2
MOVW oldhi+8(FP), R3
......@@ -62,6 +63,7 @@ addloop:
RET
TEXT ·armAddUint64(SB),7,$0
BL fastCheck64<>(SB)
MOVW valptr+0(FP), R1
MOVW deltalo+4(FP), R2
MOVW deltahi+8(FP), R3
......@@ -76,3 +78,42 @@ add64loop:
MOVW R4, retlo+12(FP)
MOVW R5, rethi+16(FP)
RET
// Check for broken 64-bit LDREXD as found in QEMU.
// LDREXD followed by immediate STREXD should succeed.
// If it fails, try a few times just to be sure (maybe our thread got
// rescheduled between the two instructions) and then panic.
// A bug in some copies of QEMU makes STREXD never succeed,
// which will make uses of the 64-bit atomic operations loop forever.
// If things are working, set okLDREXD to avoid future checks.
// https://bugs.launchpad.net/qemu/+bug/670883.
TEXT check64<>(SB),7,$8
MOVW $10, R1
loop:
LDREXD (SP), R2
STREXD R2, (SP), R0
CMP $0, R0
BEQ ok
SUB $1, R1
CMP $0, R1
BNE loop
// Must be buggy QEMU.
BL ·panic64(SB)
ok:
RET
// Fast, cached version of check. No frame, just MOVW CMP RET after first time.
TEXT fastCheck64<>(SB),7,$-4
MOVW ok64<>(SB), R0
CMP $0, R0 // have we been here before?
RET.NE
B slowCheck64<>(SB)
TEXT slowCheck64<>(SB),7,$0
BL check64<>(SB)
// Still here, must be okay.
MOVW $1, R0
MOVW R0, ok64<>(SB)
RET
GLOBL ok64<>(SB), $4
......@@ -2,10 +2,11 @@
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package atomic
package atomic_test
import (
"runtime"
. "sync/atomic"
"testing"
"unsafe"
)
......@@ -27,6 +28,16 @@ const (
magic64 = 0xdeddeadbeefbeef
)
// Do the 64-bit functions panic? If so, don't bother testing.
var test64err = func() (err interface{}) {
defer func() {
err = recover()
}()
var x int64
AddInt64(&x, 1)
return nil
}()
func TestAddInt32(t *testing.T) {
var x struct {
before int32
......@@ -70,6 +81,10 @@ func TestAddUint32(t *testing.T) {
}
func TestAddInt64(t *testing.T) {
if test64err != nil {
t.Logf("Skipping 64-bit tests: %v", test64err)
return
}
var x struct {
before int64
i int64
......@@ -91,6 +106,10 @@ func TestAddInt64(t *testing.T) {
}
func TestAddUint64(t *testing.T) {
if test64err != nil {
t.Logf("Skipping 64-bit tests: %v", test64err)
return
}
var x struct {
before uint64
i uint64
......@@ -193,6 +212,10 @@ func TestCompareAndSwapUint32(t *testing.T) {
}
func TestCompareAndSwapInt64(t *testing.T) {
if test64err != nil {
t.Logf("Skipping 64-bit tests: %v", test64err)
return
}
var x struct {
before int64
i int64
......@@ -222,6 +245,10 @@ func TestCompareAndSwapInt64(t *testing.T) {
}
func TestCompareAndSwapUint64(t *testing.T) {
if test64err != nil {
t.Logf("Skipping 64-bit tests: %v", test64err)
return
}
var x struct {
before uint64
i uint64
......@@ -479,6 +506,10 @@ func hammerCompareAndSwapUintptr64(uval *uint64, count int) {
}
func TestHammer64(t *testing.T) {
if test64err != nil {
t.Logf("Skipping 64-bit tests: %v", test64err)
return
}
const p = 4
n := 100000
if testing.Short() {
......
......@@ -55,3 +55,8 @@ func AddUint64(val *uint64, delta uint64) (new uint64)
// AddUintptr atomically adds delta to *val and returns the new value.
func AddUintptr(val *uintptr, delta uintptr) (new uintptr)
// Helper for ARM. Linker will discard on other systems
func panic64() {
panic("sync/atomic: broken 64-bit atomic operations (buggy QEMU)")
}
......@@ -98,6 +98,7 @@ time gomake ogle
time ./run
) || exit $?
[ "$GOARCH" == arm ] || # uses network, fails under QEMU
(xcd ../doc/codelab/wiki
gomake clean
gomake
......
......@@ -6,12 +6,14 @@
package main
import (
"net"
)
import "os"
// Issue 481: closures and var declarations
// with multiple variables assigned from one
// function call.
func main() {
var listen, _ = net.Listen("tcp", "127.0.0.1:0")
var listen, _ = Listen("tcp", "127.0.0.1:0")
go func() {
for {
......@@ -20,6 +22,31 @@ func main() {
}
}()
var conn, _ = net.Dial("tcp", "", listen.Addr().String())
var conn, _ = Dial("tcp", "", listen.Addr().String())
_ = conn
}
// Simulated net interface to exercise bug
// without involving a real network.
type T chan int
var global T
func Listen(x, y string) (T, string) {
global = make(chan int)
return global, y
}
func (t T) Addr() os.Error {
return os.ErrorString("stringer")
}
func (t T) Accept() (int, string) {
return <-t, ""
}
func Dial(x, y, z string) (int, string) {
global <- 1
return 0, ""
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment