Source file test/codegen/bool.go
1 // asmcheck 2 3 // Copyright 2020 The Go Authors. All rights reserved. 4 // Use of this source code is governed by a BSD-style 5 // license that can be found in the LICENSE file. 6 7 package codegen 8 9 import ( 10 "math/bits" 11 ) 12 13 // This file contains codegen tests related to boolean simplifications/optimizations. 14 15 func convertNeq0B(x uint8, c bool) bool { 16 // amd64:"ANDL\t[$]1",-"SETNE" 17 // ppc64x:"RLDICL",-"CMPW",-"ISEL" 18 b := x&1 != 0 19 return c && b 20 } 21 22 func convertNeq0W(x uint16, c bool) bool { 23 // amd64:"ANDL\t[$]1",-"SETNE" 24 // ppc64x:"RLDICL",-"CMPW",-"ISEL" 25 b := x&1 != 0 26 return c && b 27 } 28 29 func convertNeq0L(x uint32, c bool) bool { 30 // amd64:"ANDL\t[$]1",-"SETB" 31 // ppc64x:"RLDICL",-"CMPW",-"ISEL" 32 b := x&1 != 0 33 return c && b 34 } 35 36 func convertNeq0Q(x uint64, c bool) bool { 37 // amd64:"ANDL\t[$]1",-"SETB" 38 // ppc64x:"RLDICL",-"CMP",-"ISEL" 39 b := x&1 != 0 40 return c && b 41 } 42 43 func convertNeqBool32(x uint32) bool { 44 // ppc64x:"RLDICL",-"CMPW",-"ISEL" 45 return x&1 != 0 46 } 47 48 func convertEqBool32(x uint32) bool { 49 // ppc64x:"RLDICL",-"CMPW","XOR",-"ISEL" 50 // amd64:"ANDL","XORL",-"BTL",-"SETCC" 51 return x&1 == 0 52 } 53 54 func convertNeqBool64(x uint64) bool { 55 // ppc64x:"RLDICL",-"CMP",-"ISEL" 56 return x&1 != 0 57 } 58 59 func convertEqBool64(x uint64) bool { 60 // ppc64x:"RLDICL","XOR",-"CMP",-"ISEL" 61 // amd64:"ANDL","XORL",-"BTL",-"SETCC" 62 return x&1 == 0 63 } 64 65 func phiAnd(a, b bool) bool { 66 var x bool 67 // amd64:-"TESTB" 68 if a { 69 x = b 70 } else { 71 x = a 72 } 73 // amd64:"ANDL" 74 return x 75 } 76 77 func phiOr(a, b bool) bool { 78 var x bool 79 // amd64:-"TESTB" 80 if a { 81 x = a 82 } else { 83 x = b 84 } 85 // amd64:"ORL" 86 return x 87 } 88 89 func TestSetEq64(x uint64, y uint64) bool { 90 // ppc64x/power10:"SETBC\tCR0EQ",-"ISEL" 91 // ppc64x/power9:"CMP","ISEL",-"SETBC\tCR0EQ" 92 // ppc64x/power8:"CMP","ISEL",-"SETBC\tCR0EQ" 93 b := x == y 94 return b 95 } 96 func TestSetNeq64(x uint64, y uint64) bool { 97 // ppc64x/power10:"SETBCR\tCR0EQ",-"ISEL" 98 // ppc64x/power9:"CMP","ISEL",-"SETBCR\tCR0EQ" 99 // ppc64x/power8:"CMP","ISEL",-"SETBCR\tCR0EQ" 100 b := x != y 101 return b 102 } 103 func TestSetLt64(x uint64, y uint64) bool { 104 // ppc64x/power10:"SETBC\tCR0GT",-"ISEL" 105 // ppc64x/power9:"CMP","ISEL",-"SETBC\tCR0GT" 106 // ppc64x/power8:"CMP","ISEL",-"SETBC\tCR0GT" 107 b := x < y 108 return b 109 } 110 func TestSetLe64(x uint64, y uint64) bool { 111 // ppc64x/power10:"SETBCR\tCR0LT",-"ISEL" 112 // ppc64x/power9:"CMP","ISEL",-"SETBCR\tCR0LT" 113 // ppc64x/power8:"CMP","ISEL",-"SETBCR\tCR0LT" 114 b := x <= y 115 return b 116 } 117 func TestSetGt64(x uint64, y uint64) bool { 118 // ppc64x/power10:"SETBC\tCR0LT",-"ISEL" 119 // ppc64x/power9:"CMP","ISEL",-"SETBC\tCR0LT" 120 // ppc64x/power8:"CMP","ISEL",-"SETBC\tCR0LT" 121 b := x > y 122 return b 123 } 124 func TestSetGe64(x uint64, y uint64) bool { 125 // ppc64x/power10:"SETBCR\tCR0GT",-"ISEL" 126 // ppc64x/power9:"CMP","ISEL",-"SETBCR\tCR0GT" 127 // ppc64x/power8:"CMP","ISEL",-"SETBCR\tCR0GT" 128 b := x >= y 129 return b 130 } 131 func TestSetLtFp64(x float64, y float64) bool { 132 // ppc64x/power10:"SETBC\tCR0LT",-"ISEL" 133 // ppc64x/power9:"FCMP","ISEL",-"SETBC\tCR0LT" 134 // ppc64x/power8:"FCMP","ISEL",-"SETBC\tCR0LT" 135 b := x < y 136 return b 137 } 138 func TestSetLeFp64(x float64, y float64) bool { 139 // ppc64x/power10:"SETBC\tCR0LT","SETBC\tCR0EQ","OR",-"ISEL",-"ISEL" 140 // ppc64x/power9:"ISEL","ISEL",-"SETBC\tCR0LT",-"SETBC\tCR0EQ","OR" 141 // ppc64x/power8:"ISEL","ISEL",-"SETBC\tCR0LT",-"SETBC\tCR0EQ","OR" 142 b := x <= y 143 return b 144 } 145 func TestSetGtFp64(x float64, y float64) bool { 146 // ppc64x/power10:"SETBC\tCR0LT",-"ISEL" 147 // ppc64x/power9:"FCMP","ISEL",-"SETBC\tCR0LT" 148 // ppc64x/power8:"FCMP","ISEL",-"SETBC\tCR0LT" 149 b := x > y 150 return b 151 } 152 func TestSetGeFp64(x float64, y float64) bool { 153 // ppc64x/power10:"SETBC\tCR0LT","SETBC\tCR0EQ","OR",-"ISEL",-"ISEL" 154 // ppc64x/power9:"ISEL","ISEL",-"SETBC\tCR0LT",-"SETBC\tCR0EQ","OR" 155 // ppc64x/power8:"ISEL","ISEL",-"SETBC\tCR0LT",-"SETBC\tCR0EQ","OR" 156 b := x >= y 157 return b 158 } 159 func TestSetInvEq64(x uint64, y uint64) bool { 160 // ppc64x/power10:"SETBCR\tCR0EQ",-"ISEL" 161 // ppc64x/power9:"CMP","ISEL",-"SETBCR\tCR0EQ" 162 // ppc64x/power8:"CMP","ISEL",-"SETBCR\tCR0EQ" 163 b := !(x == y) 164 return b 165 } 166 func TestSetInvNeq64(x uint64, y uint64) bool { 167 // ppc64x/power10:"SETBC\tCR0EQ",-"ISEL" 168 // ppc64x/power9:"CMP","ISEL",-"SETBC\tCR0EQ" 169 // ppc64x/power8:"CMP","ISEL",-"SETBC\tCR0EQ" 170 b := !(x != y) 171 return b 172 } 173 func TestSetInvLt64(x uint64, y uint64) bool { 174 // ppc64x/power10:"SETBCR\tCR0GT",-"ISEL" 175 // ppc64x/power9:"CMP","ISEL",-"SETBCR\tCR0GT" 176 // ppc64x/power8:"CMP","ISEL",-"SETBCR\tCR0GT" 177 b := !(x < y) 178 return b 179 } 180 func TestSetInvLe64(x uint64, y uint64) bool { 181 // ppc64x/power10:"SETBC\tCR0LT",-"ISEL" 182 // ppc64x/power9:"CMP","ISEL",-"SETBC\tCR0LT" 183 // ppc64x/power8:"CMP","ISEL",-"SETBC\tCR0LT" 184 b := !(x <= y) 185 return b 186 } 187 func TestSetInvGt64(x uint64, y uint64) bool { 188 // ppc64x/power10:"SETBCR\tCR0LT",-"ISEL" 189 // ppc64x/power9:"CMP","ISEL",-"SETBCR\tCR0LT" 190 // ppc64x/power8:"CMP","ISEL",-"SETBCR\tCR0LT" 191 b := !(x > y) 192 return b 193 } 194 func TestSetInvGe64(x uint64, y uint64) bool { 195 // ppc64x/power10:"SETBC\tCR0GT",-"ISEL" 196 // ppc64x/power9:"CMP","ISEL",-"SETBC\tCR0GT" 197 // ppc64x/power8:"CMP","ISEL",-"SETBC\tCR0GT" 198 b := !(x >= y) 199 return b 200 } 201 202 func TestSetInvEqFp64(x float64, y float64) bool { 203 // ppc64x/power10:"SETBCR\tCR0EQ",-"ISEL" 204 // ppc64x/power9:"FCMP","ISEL",-"SETBCR\tCR0EQ" 205 // ppc64x/power8:"FCMP","ISEL",-"SETBCR\tCR0EQ" 206 b := !(x == y) 207 return b 208 } 209 func TestSetInvNeqFp64(x float64, y float64) bool { 210 // ppc64x/power10:"SETBC\tCR0EQ",-"ISEL" 211 // ppc64x/power9:"FCMP","ISEL",-"SETBC\tCR0EQ" 212 // ppc64x/power8:"FCMP","ISEL",-"SETBC\tCR0EQ" 213 b := !(x != y) 214 return b 215 } 216 func TestSetInvLtFp64(x float64, y float64) bool { 217 // ppc64x/power10:"SETBCR\tCR0LT",-"ISEL" 218 // ppc64x/power9:"FCMP","ISEL",-"SETBCR\tCR0LT" 219 // ppc64x/power8:"FCMP","ISEL",-"SETBCR\tCR0LT" 220 b := !(x < y) 221 return b 222 } 223 func TestSetInvLeFp64(x float64, y float64) bool { 224 // ppc64x/power10:"SETBC\tCR0LT",-"ISEL" 225 // ppc64x/power9:"FCMP","ISEL",-"SETBC\tCR0LT" 226 // ppc64x/power8:"FCMP","ISEL",-"SETBC\tCR0LT" 227 b := !(x <= y) 228 return b 229 } 230 func TestSetInvGtFp64(x float64, y float64) bool { 231 // ppc64x/power10:"SETBCR\tCR0LT",-"ISEL" 232 // ppc64x/power9:"FCMP","ISEL",-"SETBCR\tCR0LT" 233 // ppc64x/power8:"FCMP","ISEL",-"SETBCR\tCR0LT" 234 b := !(x > y) 235 return b 236 } 237 func TestSetInvGeFp64(x float64, y float64) bool { 238 // ppc64x/power10:"SETBC\tCR0LT",-"ISEL" 239 // ppc64x/power9:"FCMP","ISEL",-"SETBC\tCR0LT" 240 // ppc64x/power8:"FCMP","ISEL",-"SETBC\tCR0LT" 241 b := !(x >= y) 242 return b 243 } 244 func TestLogicalCompareZero(x *[64]uint64) { 245 // ppc64x:"ANDCC",^"AND" 246 b := x[0] & 3 247 if b != 0 { 248 x[0] = b 249 } 250 // ppc64x:"ANDCC",^"AND" 251 b = x[1] & x[2] 252 if b != 0 { 253 x[1] = b 254 } 255 // ppc64x:"ANDNCC",^"ANDN" 256 b = x[1] &^ x[2] 257 if b != 0 { 258 x[1] = b 259 } 260 // ppc64x:"ORCC",^"OR" 261 b = x[3] | x[4] 262 if b != 0 { 263 x[3] = b 264 } 265 // ppc64x:"SUBCC",^"SUB" 266 b = x[5] - x[6] 267 if b != 0 { 268 x[5] = b 269 } 270 // ppc64x:"NORCC",^"NOR" 271 b = ^(x[5] | x[6]) 272 if b != 0 { 273 x[5] = b 274 } 275 // ppc64x:"XORCC",^"XOR" 276 b = x[7] ^ x[8] 277 if b != 0 { 278 x[7] = b 279 } 280 // ppc64x:"ADDCC",^"ADD" 281 b = x[9] + x[10] 282 if b != 0 { 283 x[9] = b 284 } 285 // ppc64x:"NEGCC",^"NEG" 286 b = -x[11] 287 if b != 0 { 288 x[11] = b 289 } 290 // ppc64x:"CNTLZDCC",^"CNTLZD" 291 b = uint64(bits.LeadingZeros64(x[12])) 292 if b != 0 { 293 x[12] = b 294 } 295 296 // ppc64x:"ADDCCC\t[$]4," 297 c := int64(x[12]) + 4 298 if c <= 0 { 299 x[12] = uint64(c) 300 } 301 302 // ppc64x:"MULHDUCC",^"MULHDU" 303 hi, _ := bits.Mul64(x[13], x[14]) 304 if hi != 0 { 305 x[14] = hi 306 } 307 308 } 309 310 func constantWrite(b bool, p *bool) { 311 if b { 312 // amd64:`MOVB\t[$]1, \(` 313 *p = b 314 } 315 } 316