github.com/akaros/go-akaros@v0.0.0-20181004170632-85005d477eab/src/cmd/internal/rsc.io/x86/x86asm/plan9ext_test.go (about) 1 // Copyright 2014 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 package x86asm 6 7 import ( 8 "bytes" 9 "fmt" 10 "io" 11 "log" 12 "os" 13 "runtime" 14 "strconv" 15 "testing" 16 ) 17 18 const plan9Path = "testdata/libmach8db" 19 20 func testPlan9Arch(t *testing.T, arch int, generate func(func([]byte))) { 21 if testing.Short() { 22 t.Skip("skipping libmach test in short mode") 23 } 24 if runtime.GOOS == "akaros" { 25 t.Skip("skipping objdump test on akaros") 26 } 27 28 if _, err := os.Stat(plan9Path); err != nil { 29 t.Fatal(err) 30 } 31 32 testExtDis(t, "plan9", arch, plan9, generate, allowedMismatchPlan9) 33 } 34 35 func testPlan932(t *testing.T, generate func(func([]byte))) { 36 testPlan9Arch(t, 32, generate) 37 } 38 39 func testPlan964(t *testing.T, generate func(func([]byte))) { 40 testPlan9Arch(t, 64, generate) 41 } 42 43 func plan9(ext *ExtDis) error { 44 flag := "-8" 45 if ext.Arch == 64 { 46 flag = "-6" 47 } 48 b, err := ext.Run(plan9Path, flag, ext.File.Name()) 49 if err != nil { 50 return err 51 } 52 53 nmatch := 0 54 next := uint32(start) 55 var ( 56 addr uint32 57 encbuf [32]byte 58 enc []byte 59 text string 60 ) 61 62 for { 63 line, err := b.ReadSlice('\n') 64 if err != nil { 65 if err == io.EOF { 66 break 67 } 68 return fmt.Errorf("reading libmach8db output: %v", err) 69 } 70 if debug { 71 os.Stdout.Write(line) 72 } 73 nmatch++ 74 addr, enc, text = parseLinePlan9(line, encbuf[:0]) 75 if addr > next { 76 return fmt.Errorf("address out of sync expected <= %#x at %q in:\n%s", next, line, line) 77 } 78 if addr < next { 79 continue 80 } 81 if m := pcrelw.FindStringSubmatch(text); m != nil { 82 targ, _ := strconv.ParseUint(m[2], 16, 64) 83 text = fmt.Sprintf("%s .%+#x", m[1], int16(uint32(targ)-uint32(uint16(addr))-uint32(len(enc)))) 84 } 85 if m := pcrel.FindStringSubmatch(text); m != nil { 86 targ, _ := strconv.ParseUint(m[2], 16, 64) 87 text = fmt.Sprintf("%s .%+#x", m[1], int32(uint32(targ)-addr-uint32(len(enc)))) 88 } 89 ext.Dec <- ExtInst{addr, encbuf, len(enc), text} 90 encbuf = [32]byte{} 91 enc = nil 92 next += 32 93 } 94 if next != start+uint32(ext.Size) { 95 return fmt.Errorf("not enough results found [%d %d]", next, start+ext.Size) 96 } 97 if err := ext.Wait(); err != nil { 98 return fmt.Errorf("exec: %v", err) 99 } 100 101 return nil 102 } 103 104 func parseLinePlan9(line []byte, encstart []byte) (addr uint32, enc []byte, text string) { 105 i := bytes.IndexByte(line, ' ') 106 if i < 0 || line[0] != '0' || line[1] != 'x' { 107 log.Fatalf("cannot parse disassembly: %q", line) 108 } 109 j := bytes.IndexByte(line[i+1:], ' ') 110 if j < 0 { 111 log.Fatalf("cannot parse disassembly: %q", line) 112 } 113 j += i + 1 114 x, err := strconv.ParseUint(string(trimSpace(line[2:i])), 16, 32) 115 if err != nil { 116 log.Fatalf("cannot parse disassembly: %q", line) 117 } 118 addr = uint32(x) 119 enc, ok := parseHex(line[i+1:j], encstart) 120 if !ok { 121 log.Fatalf("cannot parse disassembly: %q", line) 122 } 123 return addr, enc, string(fixSpace(line[j+1:])) 124 }