github.com/peggyl/go@v0.0.0-20151008231540-ae315999c2d5/src/cmd/asm/internal/arch/arm64.go (about)

     1  // Copyright 2015 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  // This file encapsulates some of the odd characteristics of the ARM64
     6  // instruction set, to minimize its interaction with the core of the
     7  // assembler.
     8  
     9  package arch
    10  
    11  import (
    12  	"cmd/internal/obj"
    13  	"cmd/internal/obj/arm64"
    14  )
    15  
    16  var arm64LS = map[string]uint8{
    17  	"P": arm64.C_XPOST,
    18  	"W": arm64.C_XPRE,
    19  }
    20  
    21  var arm64Jump = map[string]bool{
    22  	"B":     true,
    23  	"BL":    true,
    24  	"BEQ":   true,
    25  	"BNE":   true,
    26  	"BCS":   true,
    27  	"BHS":   true,
    28  	"BCC":   true,
    29  	"BLO":   true,
    30  	"BMI":   true,
    31  	"BPL":   true,
    32  	"BVS":   true,
    33  	"BVC":   true,
    34  	"BHI":   true,
    35  	"BLS":   true,
    36  	"BGE":   true,
    37  	"BLT":   true,
    38  	"BGT":   true,
    39  	"BLE":   true,
    40  	"CALL":  true,
    41  	"CBZ":   true,
    42  	"CBZW":  true,
    43  	"CBNZ":  true,
    44  	"CBNZW": true,
    45  	"JMP":   true,
    46  }
    47  
    48  func jumpArm64(word string) bool {
    49  	return arm64Jump[word]
    50  }
    51  
    52  // IsARM64CMP reports whether the op (as defined by an arm.A* constant) is
    53  // one of the comparison instructions that require special handling.
    54  func IsARM64CMP(op int) bool {
    55  	switch op {
    56  	case arm64.ACMN, arm64.ACMP, arm64.ATST,
    57  		arm64.ACMNW, arm64.ACMPW, arm64.ATSTW:
    58  		return true
    59  	}
    60  	return false
    61  }
    62  
    63  // IsARM64STLXR reports whether the op (as defined by an arm64.A*
    64  // constant) is one of the STLXR-like instructions that require special
    65  // handling.
    66  func IsARM64STLXR(op int) bool {
    67  	switch op {
    68  	case arm64.ASTLXRB, arm64.ASTLXRH, arm64.ASTLXRW, arm64.ASTLXR:
    69  		return true
    70  	}
    71  	return false
    72  }
    73  
    74  // ARM64Suffix handles the special suffix for the ARM64.
    75  // It returns a boolean to indicate success; failure means
    76  // cond was unrecognized.
    77  func ARM64Suffix(prog *obj.Prog, cond string) bool {
    78  	if cond == "" {
    79  		return true
    80  	}
    81  	bits, ok := ParseARM64Suffix(cond)
    82  	if !ok {
    83  		return false
    84  	}
    85  	prog.Scond = bits
    86  	return true
    87  }
    88  
    89  // ParseARM64Suffix parses the suffix attached to an ARM64 instruction.
    90  // The input is a single string consisting of period-separated condition
    91  // codes, such as ".P.W". An initial period is ignored.
    92  func ParseARM64Suffix(cond string) (uint8, bool) {
    93  	if cond == "" {
    94  		return 0, true
    95  	}
    96  	return parseARMCondition(cond, arm64LS, nil)
    97  }
    98  
    99  func arm64RegisterNumber(name string, n int16) (int16, bool) {
   100  	switch name {
   101  	case "F":
   102  		if 0 <= n && n <= 31 {
   103  			return arm64.REG_F0 + n, true
   104  		}
   105  	case "R":
   106  		if 0 <= n && n <= 30 { // not 31
   107  			return arm64.REG_R0 + n, true
   108  		}
   109  	case "V":
   110  		if 0 <= n && n <= 31 {
   111  			return arm64.REG_V0 + n, true
   112  		}
   113  	}
   114  	return 0, false
   115  }