tests: autogenerated test to confirm attribute strings
Test helps verify our attribute types match the macros in textflag.h. Discovered https://golang.org/issue/29487 in the process. Updates #2
This commit is contained in:
20
attr.go
20
attr.go
@@ -83,14 +83,14 @@ func (a Attribute) split() ([]string, Attribute) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
var attrname = map[Attribute]string{
|
var attrname = map[Attribute]string{
|
||||||
NOPROF: "NOPROF",
|
NOPROF: "NOPROF",
|
||||||
DUPOK: "DUPOK",
|
DUPOK: "DUPOK",
|
||||||
NOSPLIT: "NOSPLIT",
|
NOSPLIT: "NOSPLIT",
|
||||||
RODATA: "RODATA",
|
RODATA: "RODATA",
|
||||||
NOPTR: "NOPTR",
|
NOPTR: "NOPTR",
|
||||||
WRAPPER: "WRAPPER",
|
WRAPPER: "WRAPPER",
|
||||||
NEEDCTXT: "NEEDCTXT",
|
NEEDCTXT: "NEEDCTXT",
|
||||||
TLSBSS: "TLSBSS",
|
TLSBSS: "TLSBSS",
|
||||||
NOFRAME: "NOFRAME",
|
NOFRAME: "NOFRAME",
|
||||||
REFLECTMETHOD: "REFLECTMETHOD",
|
// REFLECTMETHOD excluded due to https://golang.org/issue/29487
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -13,7 +13,8 @@ func TestAttributeAsm(t *testing.T) {
|
|||||||
{DUPOK, "DUPOK"},
|
{DUPOK, "DUPOK"},
|
||||||
{RODATA | NOSPLIT, "NOSPLIT|RODATA"},
|
{RODATA | NOSPLIT, "NOSPLIT|RODATA"},
|
||||||
{WRAPPER | 16384 | NOPTR, "NOPTR|WRAPPER|16384"},
|
{WRAPPER | 16384 | NOPTR, "NOPTR|WRAPPER|16384"},
|
||||||
{NEEDCTXT + NOFRAME + TLSBSS + REFLECTMETHOD, "NEEDCTXT|TLSBSS|NOFRAME|REFLECTMETHOD"},
|
{NEEDCTXT + NOFRAME + TLSBSS, "NEEDCTXT|TLSBSS|NOFRAME"},
|
||||||
|
{REFLECTMETHOD, "1024"}, // REFLECTMETHOD special case due to https://golang.org/issue/29487
|
||||||
}
|
}
|
||||||
for _, c := range cases {
|
for _, c := range cases {
|
||||||
got := c.Attribute.Asm()
|
got := c.Attribute.Asm()
|
||||||
|
|||||||
13
tests/textflag/attrtest_test.go
Normal file
13
tests/textflag/attrtest_test.go
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
package textflag
|
||||||
|
|
||||||
|
import "testing"
|
||||||
|
|
||||||
|
//go:generate go run make_attrtest.go -output zattrtest.s -seed 42 -num 256
|
||||||
|
|
||||||
|
func AttrTest() bool
|
||||||
|
|
||||||
|
func TestAttributes(t *testing.T) {
|
||||||
|
if !AttrTest() {
|
||||||
|
t.Fail()
|
||||||
|
}
|
||||||
|
}
|
||||||
88
tests/textflag/make_attrtest.go
Normal file
88
tests/textflag/make_attrtest.go
Normal file
@@ -0,0 +1,88 @@
|
|||||||
|
// +build ignore
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
|
"io"
|
||||||
|
"log"
|
||||||
|
"math/rand"
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
|
"runtime"
|
||||||
|
|
||||||
|
"github.com/mmcloughlin/avo"
|
||||||
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
output = flag.String("output", "", "path to output file (default stdout)")
|
||||||
|
seed = flag.Int64("seed", 0, "random seed")
|
||||||
|
num = flag.Int("num", 32, "number of attributes to generate")
|
||||||
|
)
|
||||||
|
|
||||||
|
func GenerateAttributes(n int) []avo.Attribute {
|
||||||
|
as := make([]avo.Attribute, 0, n)
|
||||||
|
|
||||||
|
// Include each bitlevel.
|
||||||
|
for i := 0; i < 16 && i < n; i++ {
|
||||||
|
a := avo.Attribute(1 << uint(i))
|
||||||
|
as = append(as, a)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add randomly generated attributes.
|
||||||
|
for len(as) < n {
|
||||||
|
a := avo.Attribute(rand.Uint32())
|
||||||
|
as = append(as, a)
|
||||||
|
}
|
||||||
|
|
||||||
|
return as
|
||||||
|
}
|
||||||
|
|
||||||
|
func PrintAttributesTest(w io.Writer, as []avo.Attribute) {
|
||||||
|
_, self, _, _ := runtime.Caller(0)
|
||||||
|
fmt.Fprintf(w, "// Code generated by %s. DO NOT EDIT.\n\n", filepath.Base(self))
|
||||||
|
fmt.Fprintf(w, "#include \"textflag.h\"\n\n")
|
||||||
|
fmt.Fprintf(w, "TEXT ·AttrTest(SB), $0-1\n")
|
||||||
|
fmt.Fprintf(w, "\tMOVB $0, ret+0(FP)\n")
|
||||||
|
|
||||||
|
for i, a := range as {
|
||||||
|
fmt.Fprintf(w, "\tMOVW $(%d), R8\n", a)
|
||||||
|
fmt.Fprintf(w, "\tMOVW $(%s), R9\n", a.Asm())
|
||||||
|
fmt.Fprintf(w, "\tCMPW R8, R9\n")
|
||||||
|
|
||||||
|
cont := fmt.Sprintf("cont%d", i)
|
||||||
|
fmt.Fprintf(w, "\tJE %s\n", cont)
|
||||||
|
fmt.Fprintf(w, "\tRET\n")
|
||||||
|
|
||||||
|
fmt.Fprintf(w, "%s:\n", cont)
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Fprintf(w, "\tMOVB $1, ret+0(FP)\n")
|
||||||
|
fmt.Fprintf(w, "\tRET\n")
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
flag.Parse()
|
||||||
|
|
||||||
|
w := os.Stdout
|
||||||
|
if *output != "" {
|
||||||
|
f, err := os.Create(*output)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
defer f.Close()
|
||||||
|
w = f
|
||||||
|
}
|
||||||
|
|
||||||
|
rand.Seed(*seed)
|
||||||
|
as := GenerateAttributes(*num)
|
||||||
|
|
||||||
|
buf := bytes.NewBuffer(nil)
|
||||||
|
PrintAttributesTest(buf, as)
|
||||||
|
|
||||||
|
if _, err := w.Write(buf.Bytes()); err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
}
|
||||||
1544
tests/textflag/zattrtest.s
Normal file
1544
tests/textflag/zattrtest.s
Normal file
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user