1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py 2; RUN: opt < %s -passes=instcombine -S | FileCheck %s 3 4target datalayout = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-a0:0:64-f80:128:128-n8:16:32" 5 6define i32 @test1(i32 %i) { 7; CHECK-LABEL: @test1( 8; CHECK-NEXT: [[T12:%.*]] = call i32 @llvm.bswap.i32(i32 [[I:%.*]]) 9; CHECK-NEXT: ret i32 [[T12]] 10; 11 %t1 = lshr i32 %i, 24 12 %t3 = lshr i32 %i, 8 13 %t4 = and i32 %t3, 65280 14 %t5 = or i32 %t1, %t4 15 %t7 = shl i32 %i, 8 16 %t8 = and i32 %t7, 16711680 17 %t9 = or i32 %t5, %t8 18 %t11 = shl i32 %i, 24 19 %t12 = or i32 %t9, %t11 20 ret i32 %t12 21} 22 23define <2 x i32> @test1_vector(<2 x i32> %i) { 24; CHECK-LABEL: @test1_vector( 25; CHECK-NEXT: [[T12:%.*]] = call <2 x i32> @llvm.bswap.v2i32(<2 x i32> [[I:%.*]]) 26; CHECK-NEXT: ret <2 x i32> [[T12]] 27; 28 %t1 = lshr <2 x i32> %i, <i32 24, i32 24> 29 %t3 = lshr <2 x i32> %i, <i32 8, i32 8> 30 %t4 = and <2 x i32> %t3, <i32 65280, i32 65280> 31 %t5 = or <2 x i32> %t1, %t4 32 %t7 = shl <2 x i32> %i, <i32 8, i32 8> 33 %t8 = and <2 x i32> %t7, <i32 16711680, i32 16711680> 34 %t9 = or <2 x i32> %t5, %t8 35 %t11 = shl <2 x i32> %i, <i32 24, i32 24> 36 %t12 = or <2 x i32> %t9, %t11 37 ret <2 x i32> %t12 38} 39 40define i16 @test1_trunc(i32 %i) { 41; CHECK-LABEL: @test1_trunc( 42; CHECK-NEXT: [[T1:%.*]] = lshr i32 [[I:%.*]], 24 43; CHECK-NEXT: [[T3:%.*]] = lshr i32 [[I]], 8 44; CHECK-NEXT: [[T4:%.*]] = and i32 [[T3]], 65280 45; CHECK-NEXT: [[T5:%.*]] = or disjoint i32 [[T1]], [[T4]] 46; CHECK-NEXT: [[T13:%.*]] = trunc nuw i32 [[T5]] to i16 47; CHECK-NEXT: ret i16 [[T13]] 48; 49 %t1 = lshr i32 %i, 24 50 %t3 = lshr i32 %i, 8 51 %t4 = and i32 %t3, 65280 52 %t5 = or i32 %t1, %t4 53 %t13 = trunc i32 %t5 to i16 54 ret i16 %t13 55} 56 57define i16 @test1_trunc_extra_use(i32 %i) { 58; CHECK-LABEL: @test1_trunc_extra_use( 59; CHECK-NEXT: [[T1:%.*]] = lshr i32 [[I:%.*]], 24 60; CHECK-NEXT: [[T3:%.*]] = lshr i32 [[I]], 8 61; CHECK-NEXT: [[T4:%.*]] = and i32 [[T3]], 65280 62; CHECK-NEXT: [[T5:%.*]] = or disjoint i32 [[T1]], [[T4]] 63; CHECK-NEXT: call void @extra_use(i32 [[T5]]) 64; CHECK-NEXT: [[T13:%.*]] = trunc nuw i32 [[T5]] to i16 65; CHECK-NEXT: ret i16 [[T13]] 66; 67 %t1 = lshr i32 %i, 24 68 %t3 = lshr i32 %i, 8 69 %t4 = and i32 %t3, 65280 70 %t5 = or i32 %t1, %t4 71 call void @extra_use(i32 %t5) 72 %t13 = trunc i32 %t5 to i16 73 ret i16 %t13 74} 75 76define i32 @test2(i32 %arg) { 77; CHECK-LABEL: @test2( 78; CHECK-NEXT: [[T14:%.*]] = call i32 @llvm.bswap.i32(i32 [[ARG:%.*]]) 79; CHECK-NEXT: ret i32 [[T14]] 80; 81 %t2 = shl i32 %arg, 24 82 %t4 = shl i32 %arg, 8 83 %t5 = and i32 %t4, 16711680 84 %t6 = or i32 %t2, %t5 85 %t8 = lshr i32 %arg, 8 86 %t9 = and i32 %t8, 65280 87 %t10 = or i32 %t6, %t9 88 %t12 = lshr i32 %arg, 24 89 %t14 = or i32 %t10, %t12 90 ret i32 %t14 91} 92 93define <2 x i32> @test2_vector(<2 x i32> %arg) { 94; CHECK-LABEL: @test2_vector( 95; CHECK-NEXT: [[T14:%.*]] = call <2 x i32> @llvm.bswap.v2i32(<2 x i32> [[ARG:%.*]]) 96; CHECK-NEXT: ret <2 x i32> [[T14]] 97; 98 %t2 = shl <2 x i32> %arg, <i32 24, i32 24> 99 %t4 = shl <2 x i32> %arg, <i32 8, i32 8> 100 %t5 = and <2 x i32> %t4, <i32 16711680, i32 16711680> 101 %t6 = or <2 x i32> %t2, %t5 102 %t8 = lshr <2 x i32> %arg, <i32 8, i32 8> 103 %t9 = and <2 x i32> %t8, <i32 65280, i32 65280> 104 %t10 = or <2 x i32> %t6, %t9 105 %t12 = lshr <2 x i32> %arg, <i32 24, i32 24> 106 %t14 = or <2 x i32> %t10, %t12 107 ret <2 x i32> %t14 108} 109 110define <2 x i32> @test2_vector_poison(<2 x i32> %arg) { 111; CHECK-LABEL: @test2_vector_poison( 112; CHECK-NEXT: [[T2:%.*]] = shl <2 x i32> [[ARG:%.*]], <i32 24, i32 poison> 113; CHECK-NEXT: [[T4:%.*]] = shl <2 x i32> [[ARG]], splat (i32 8) 114; CHECK-NEXT: [[T5:%.*]] = and <2 x i32> [[T4]], <i32 16711680, i32 poison> 115; CHECK-NEXT: [[T6:%.*]] = or disjoint <2 x i32> [[T2]], [[T5]] 116; CHECK-NEXT: [[T8:%.*]] = lshr <2 x i32> [[ARG]], splat (i32 8) 117; CHECK-NEXT: [[T9:%.*]] = and <2 x i32> [[T8]], <i32 65280, i32 poison> 118; CHECK-NEXT: [[T10:%.*]] = or disjoint <2 x i32> [[T6]], [[T9]] 119; CHECK-NEXT: [[T12:%.*]] = lshr <2 x i32> [[ARG]], <i32 24, i32 poison> 120; CHECK-NEXT: [[T14:%.*]] = or disjoint <2 x i32> [[T10]], [[T12]] 121; CHECK-NEXT: ret <2 x i32> [[T14]] 122; 123 %t2 = shl <2 x i32> %arg, <i32 24, i32 poison> 124 %t4 = shl <2 x i32> %arg, <i32 8, i32 8> 125 %t5 = and <2 x i32> %t4, <i32 16711680, i32 poison> 126 %t6 = or <2 x i32> %t2, %t5 127 %t8 = lshr <2 x i32> %arg, <i32 8, i32 8> 128 %t9 = and <2 x i32> %t8, <i32 65280, i32 poison> 129 %t10 = or <2 x i32> %t6, %t9 130 %t12 = lshr <2 x i32> %arg, <i32 24, i32 poison> 131 %t14 = or <2 x i32> %t10, %t12 132 ret <2 x i32> %t14 133} 134 135define i16 @test3(i16 %s) { 136; CHECK-LABEL: @test3( 137; CHECK-NEXT: [[T5:%.*]] = call i16 @llvm.bswap.i16(i16 [[S:%.*]]) 138; CHECK-NEXT: ret i16 [[T5]] 139; 140 %t2 = lshr i16 %s, 8 141 %t4 = shl i16 %s, 8 142 %t5 = or i16 %t2, %t4 143 ret i16 %t5 144} 145 146define <2 x i16> @test3_vector(<2 x i16> %s) { 147; CHECK-LABEL: @test3_vector( 148; CHECK-NEXT: [[T5:%.*]] = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> [[S:%.*]]) 149; CHECK-NEXT: ret <2 x i16> [[T5]] 150; 151 %t2 = lshr <2 x i16> %s, <i16 8, i16 8> 152 %t4 = shl <2 x i16> %s, <i16 8, i16 8> 153 %t5 = or <2 x i16> %t2, %t4 154 ret <2 x i16> %t5 155} 156 157define <2 x i16> @test3_vector_poison(<2 x i16> %s) { 158; CHECK-LABEL: @test3_vector_poison( 159; CHECK-NEXT: [[T5:%.*]] = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> [[S:%.*]]) 160; CHECK-NEXT: ret <2 x i16> [[T5]] 161; 162 %t2 = lshr <2 x i16> %s, <i16 poison, i16 8> 163 %t4 = shl <2 x i16> %s, <i16 8, i16 poison> 164 %t5 = or <2 x i16> %t2, %t4 165 ret <2 x i16> %t5 166} 167 168define i16 @test4(i16 %s) { 169; CHECK-LABEL: @test4( 170; CHECK-NEXT: [[T5:%.*]] = call i16 @llvm.bswap.i16(i16 [[S:%.*]]) 171; CHECK-NEXT: ret i16 [[T5]] 172; 173 %t2 = lshr i16 %s, 8 174 %t4 = shl i16 %s, 8 175 %t5 = or i16 %t4, %t2 176 ret i16 %t5 177} 178 179define <2 x i16> @test4_vector(<2 x i16> %s) { 180; CHECK-LABEL: @test4_vector( 181; CHECK-NEXT: [[T5:%.*]] = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> [[S:%.*]]) 182; CHECK-NEXT: ret <2 x i16> [[T5]] 183; 184 %t2 = lshr <2 x i16> %s, <i16 8, i16 8> 185 %t4 = shl <2 x i16> %s, <i16 8, i16 8> 186 %t5 = or <2 x i16> %t4, %t2 187 ret <2 x i16> %t5 188} 189 190define i16 @test5(i16 %a) { 191; CHECK-LABEL: @test5( 192; CHECK-NEXT: [[T_UPGRD_3:%.*]] = call i16 @llvm.bswap.i16(i16 [[A:%.*]]) 193; CHECK-NEXT: ret i16 [[T_UPGRD_3]] 194; 195 %t = zext i16 %a to i32 196 %t1 = and i32 %t, 65280 197 %t2 = ashr i32 %t1, 8 198 %t2.upgrd.1 = trunc i32 %t2 to i16 199 %t4 = and i32 %t, 255 200 %t5 = shl i32 %t4, 8 201 %t5.upgrd.2 = trunc i32 %t5 to i16 202 %t.upgrd.3 = or i16 %t2.upgrd.1, %t5.upgrd.2 203 %t6 = bitcast i16 %t.upgrd.3 to i16 204 %t6.upgrd.4 = zext i16 %t6 to i32 205 %retval = trunc i32 %t6.upgrd.4 to i16 206 ret i16 %retval 207} 208 209define <2 x i16> @test5_vector(<2 x i16> %a) { 210; CHECK-LABEL: @test5_vector( 211; CHECK-NEXT: [[T_UPGRD_3:%.*]] = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> [[A:%.*]]) 212; CHECK-NEXT: ret <2 x i16> [[T_UPGRD_3]] 213; 214 %t = zext <2 x i16> %a to <2 x i32> 215 %t1 = and <2 x i32> %t, <i32 65280, i32 65280> 216 %t2 = ashr <2 x i32> %t1, <i32 8, i32 8> 217 %t2.upgrd.1 = trunc <2 x i32> %t2 to <2 x i16> 218 %t4 = and <2 x i32> %t, <i32 255, i32 255> 219 %t5 = shl <2 x i32> %t4, <i32 8, i32 8> 220 %t5.upgrd.2 = trunc <2 x i32> %t5 to <2 x i16> 221 %t.upgrd.3 = or <2 x i16> %t2.upgrd.1, %t5.upgrd.2 222 %t6 = bitcast <2 x i16> %t.upgrd.3 to <2 x i16> 223 %t6.upgrd.4 = zext <2 x i16> %t6 to <2 x i32> 224 %retval = trunc <2 x i32> %t6.upgrd.4 to <2 x i16> 225 ret <2 x i16> %retval 226} 227 228; PR2842 229define i32 @test6(i32 %x) nounwind readnone { 230; CHECK-LABEL: @test6( 231; CHECK-NEXT: [[T7:%.*]] = call i32 @llvm.bswap.i32(i32 [[X:%.*]]) 232; CHECK-NEXT: ret i32 [[T7]] 233; 234 %t = shl i32 %x, 16 235 %x.mask = and i32 %x, 65280 236 %t1 = lshr i32 %x, 16 237 %t2 = and i32 %t1, 255 238 %t3 = or i32 %x.mask, %t 239 %t4 = or i32 %t3, %t2 240 %t5 = shl i32 %t4, 8 241 %t6 = lshr i32 %x, 24 242 %t7 = or i32 %t5, %t6 243 ret i32 %t7 244} 245 246define <2 x i32> @test6_vector(<2 x i32> %x) nounwind readnone { 247; CHECK-LABEL: @test6_vector( 248; CHECK-NEXT: [[T7:%.*]] = call <2 x i32> @llvm.bswap.v2i32(<2 x i32> [[X:%.*]]) 249; CHECK-NEXT: ret <2 x i32> [[T7]] 250; 251 %t = shl <2 x i32> %x, <i32 16, i32 16> 252 %x.mask = and <2 x i32> %x, <i32 65280, i32 65280> 253 %t1 = lshr <2 x i32> %x, <i32 16, i32 16> 254 %t2 = and <2 x i32> %t1, <i32 255, i32 255> 255 %t3 = or <2 x i32> %x.mask, %t 256 %t4 = or <2 x i32> %t3, %t2 257 %t5 = shl <2 x i32> %t4, <i32 8, i32 8> 258 %t6 = lshr <2 x i32> %x, <i32 24, i32 24> 259 %t7 = or <2 x i32> %t5, %t6 260 ret <2 x i32> %t7 261} 262 263declare void @extra_use(i32) 264 265; swaphalf = (x << 16 | x >> 16) 266; ((swaphalf & 0x00ff00ff) << 8) | ((swaphalf >> 8) & 0x00ff00ff) 267 268define i32 @bswap32_and_first(i32 %x) { 269; CHECK-LABEL: @bswap32_and_first( 270; CHECK-NEXT: [[BSWAP:%.*]] = call i32 @llvm.bswap.i32(i32 [[X:%.*]]) 271; CHECK-NEXT: ret i32 [[BSWAP]] 272; 273 %shl = shl i32 %x, 16 274 %shr = lshr i32 %x, 16 275 %swaphalf = or i32 %shl, %shr 276 %t = and i32 %swaphalf, 16711935 277 %tshl = shl nuw i32 %t, 8 278 %b = lshr i32 %swaphalf, 8 279 %band = and i32 %b, 16711935 280 %bswap = or i32 %tshl, %band 281 ret i32 %bswap 282} 283 284; Extra use should not prevent matching to bswap. 285; swaphalf = (x << 16 | x >> 16) 286; ((swaphalf & 0x00ff00ff) << 8) | ((swaphalf >> 8) & 0x00ff00ff) 287 288define i32 @bswap32_and_first_extra_use(i32 %x) { 289; CHECK-LABEL: @bswap32_and_first_extra_use( 290; CHECK-NEXT: [[SWAPHALF:%.*]] = call i32 @llvm.fshl.i32(i32 [[X:%.*]], i32 [[X]], i32 16) 291; CHECK-NEXT: [[T:%.*]] = and i32 [[SWAPHALF]], 16711935 292; CHECK-NEXT: [[BSWAP:%.*]] = call i32 @llvm.bswap.i32(i32 [[X]]) 293; CHECK-NEXT: call void @extra_use(i32 [[T]]) 294; CHECK-NEXT: ret i32 [[BSWAP]] 295; 296 %shl = shl i32 %x, 16 297 %shr = lshr i32 %x, 16 298 %swaphalf = or i32 %shl, %shr 299 %t = and i32 %swaphalf, 16711935 300 %tshl = shl nuw i32 %t, 8 301 %b = lshr i32 %swaphalf, 8 302 %band = and i32 %b, 16711935 303 %bswap = or i32 %tshl, %band 304 call void @extra_use(i32 %t) 305 ret i32 %bswap 306} 307 308; swaphalf = (x << 16 | x >> 16) 309; ((swaphalf << 8) & 0xff00ff00) | ((swaphalf >> 8) & 0x00ff00ff) 310 311; PR23863 312define i32 @bswap32_shl_first(i32 %x) { 313; CHECK-LABEL: @bswap32_shl_first( 314; CHECK-NEXT: [[BSWAP:%.*]] = call i32 @llvm.bswap.i32(i32 [[X:%.*]]) 315; CHECK-NEXT: ret i32 [[BSWAP]] 316; 317 %shl = shl i32 %x, 16 318 %shr = lshr i32 %x, 16 319 %swaphalf = or i32 %shl, %shr 320 %t = shl i32 %swaphalf, 8 321 %tand = and i32 %t, -16711936 322 %b = lshr i32 %swaphalf, 8 323 %band = and i32 %b, 16711935 324 %bswap = or i32 %tand, %band 325 ret i32 %bswap 326} 327 328; Extra use should not prevent matching to bswap. 329; swaphalf = (x << 16 | x >> 16) 330; ((swaphalf << 8) & 0xff00ff00) | ((swaphalf >> 8) & 0x00ff00ff) 331 332define i32 @bswap32_shl_first_extra_use(i32 %x) { 333; CHECK-LABEL: @bswap32_shl_first_extra_use( 334; CHECK-NEXT: [[SWAPHALF:%.*]] = call i32 @llvm.fshl.i32(i32 [[X:%.*]], i32 [[X]], i32 16) 335; CHECK-NEXT: [[T:%.*]] = shl i32 [[SWAPHALF]], 8 336; CHECK-NEXT: [[BSWAP:%.*]] = call i32 @llvm.bswap.i32(i32 [[X]]) 337; CHECK-NEXT: call void @extra_use(i32 [[T]]) 338; CHECK-NEXT: ret i32 [[BSWAP]] 339; 340 %shl = shl i32 %x, 16 341 %shr = lshr i32 %x, 16 342 %swaphalf = or i32 %shl, %shr 343 %t = shl i32 %swaphalf, 8 344 %tand = and i32 %t, -16711936 345 %b = lshr i32 %swaphalf, 8 346 %band = and i32 %b, 16711935 347 %bswap = or i32 %tand, %band 348 call void @extra_use(i32 %t) 349 ret i32 %bswap 350} 351 352define i16 @test8(i16 %a) { 353; CHECK-LABEL: @test8( 354; CHECK-NEXT: [[OR:%.*]] = call i16 @llvm.bswap.i16(i16 [[A:%.*]]) 355; CHECK-NEXT: ret i16 [[OR]] 356; 357 %conv = zext i16 %a to i32 358 %shr = lshr i16 %a, 8 359 %shl = shl i32 %conv, 8 360 %conv1 = zext i16 %shr to i32 361 %or = or i32 %conv1, %shl 362 %conv2 = trunc i32 %or to i16 363 ret i16 %conv2 364} 365 366define i16 @test9(i16 %a) { 367; CHECK-LABEL: @test9( 368; CHECK-NEXT: [[OR:%.*]] = call i16 @llvm.bswap.i16(i16 [[A:%.*]]) 369; CHECK-NEXT: ret i16 [[OR]] 370; 371 %conv = zext i16 %a to i32 372 %shr = lshr i32 %conv, 8 373 %shl = shl i32 %conv, 8 374 %or = or i32 %shr, %shl 375 %conv2 = trunc i32 %or to i16 376 ret i16 %conv2 377} 378 379define i16 @test10(i32 %a) { 380; CHECK-LABEL: @test10( 381; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[A:%.*]] to i16 382; CHECK-NEXT: [[REV:%.*]] = call i16 @llvm.bswap.i16(i16 [[TRUNC]]) 383; CHECK-NEXT: ret i16 [[REV]] 384; 385 %shr1 = lshr i32 %a, 8 386 %and1 = and i32 %shr1, 255 387 %and2 = shl i32 %a, 8 388 %shl1 = and i32 %and2, 65280 389 %or = or i32 %and1, %shl1 390 %conv = trunc i32 %or to i16 391 ret i16 %conv 392} 393 394define <2 x i16> @test10_vector(<2 x i32> %a) { 395; CHECK-LABEL: @test10_vector( 396; CHECK-NEXT: [[TRUNC:%.*]] = trunc <2 x i32> [[A:%.*]] to <2 x i16> 397; CHECK-NEXT: [[REV:%.*]] = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> [[TRUNC]]) 398; CHECK-NEXT: ret <2 x i16> [[REV]] 399; 400 %shr1 = lshr <2 x i32> %a, <i32 8, i32 8> 401 %and1 = and <2 x i32> %shr1, <i32 255, i32 255> 402 %and2 = shl <2 x i32> %a, <i32 8, i32 8> 403 %shl1 = and <2 x i32> %and2, <i32 65280, i32 65280> 404 %or = or <2 x i32> %and1, %shl1 405 %conv = trunc <2 x i32> %or to <2 x i16> 406 ret <2 x i16> %conv 407} 408 409define i64 @PR39793_bswap_u64_as_u32(i64 %0) { 410; CHECK-LABEL: @PR39793_bswap_u64_as_u32( 411; CHECK-NEXT: [[TRUNC:%.*]] = trunc i64 [[TMP0:%.*]] to i32 412; CHECK-NEXT: [[REV:%.*]] = call i32 @llvm.bswap.i32(i32 [[TRUNC]]) 413; CHECK-NEXT: [[TMP2:%.*]] = zext i32 [[REV]] to i64 414; CHECK-NEXT: ret i64 [[TMP2]] 415; 416 %2 = lshr i64 %0, 24 417 %3 = and i64 %2, 255 418 %4 = lshr i64 %0, 8 419 %5 = and i64 %4, 65280 420 %6 = or i64 %3, %5 421 %7 = shl i64 %0, 8 422 %8 = and i64 %7, 16711680 423 %9 = or i64 %6, %8 424 %10 = shl i64 %0, 24 425 %11 = and i64 %10, 4278190080 426 %12 = or i64 %9, %11 427 ret i64 %12 428} 429 430define i16 @PR39793_bswap_u64_as_u32_trunc(i64 %0) { 431; CHECK-LABEL: @PR39793_bswap_u64_as_u32_trunc( 432; CHECK-NEXT: [[TRUNC:%.*]] = trunc i64 [[TMP0:%.*]] to i32 433; CHECK-NEXT: [[REV:%.*]] = call i32 @llvm.bswap.i32(i32 [[TRUNC]]) 434; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[REV]] to i16 435; CHECK-NEXT: ret i16 [[TMP2]] 436; 437 %2 = lshr i64 %0, 24 438 %3 = and i64 %2, 255 439 %4 = lshr i64 %0, 8 440 %5 = and i64 %4, 65280 441 %6 = or i64 %3, %5 442 %7 = shl i64 %0, 8 443 %8 = and i64 %7, 16711680 444 %9 = or i64 %6, %8 445 %10 = shl i64 %0, 24 446 %11 = and i64 %10, 4278190080 447 %12 = or i64 %9, %11 448 %13 = trunc i64 %12 to i16 449 ret i16 %13 450} 451 452define i64 @PR39793_bswap_u64_as_u16(i64 %0) { 453; CHECK-LABEL: @PR39793_bswap_u64_as_u16( 454; CHECK-NEXT: [[TRUNC:%.*]] = trunc i64 [[TMP0:%.*]] to i16 455; CHECK-NEXT: [[REV:%.*]] = call i16 @llvm.bswap.i16(i16 [[TRUNC]]) 456; CHECK-NEXT: [[TMP2:%.*]] = zext i16 [[REV]] to i64 457; CHECK-NEXT: ret i64 [[TMP2]] 458; 459 %2 = lshr i64 %0, 8 460 %3 = and i64 %2, 255 461 %4 = shl i64 %0, 8 462 %5 = and i64 %4, 65280 463 %6 = or i64 %3, %5 464 ret i64 %6 465} 466 467define <2 x i64> @PR39793_bswap_u64_as_u16_vector(<2 x i64> %0) { 468; CHECK-LABEL: @PR39793_bswap_u64_as_u16_vector( 469; CHECK-NEXT: [[TRUNC:%.*]] = trunc <2 x i64> [[TMP0:%.*]] to <2 x i16> 470; CHECK-NEXT: [[REV:%.*]] = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> [[TRUNC]]) 471; CHECK-NEXT: [[TMP2:%.*]] = zext <2 x i16> [[REV]] to <2 x i64> 472; CHECK-NEXT: ret <2 x i64> [[TMP2]] 473; 474 %2 = lshr <2 x i64> %0, <i64 8, i64 8> 475 %3 = and <2 x i64> %2, <i64 255, i64 255> 476 %4 = shl <2 x i64> %0, <i64 8, i64 8> 477 %5 = and <2 x i64> %4, <i64 65280, i64 65280> 478 %6 = or <2 x i64> %3, %5 479 ret <2 x i64> %6 480} 481 482define i8 @PR39793_bswap_u64_as_u16_trunc(i64 %0) { 483; CHECK-LABEL: @PR39793_bswap_u64_as_u16_trunc( 484; CHECK-NEXT: [[REV1:%.*]] = lshr i64 [[TMP0:%.*]], 8 485; CHECK-NEXT: [[TMP2:%.*]] = trunc i64 [[REV1]] to i8 486; CHECK-NEXT: ret i8 [[TMP2]] 487; 488 %2 = lshr i64 %0, 8 489 %3 = and i64 %2, 255 490 %4 = shl i64 %0, 8 491 %5 = and i64 %4, 65280 492 %6 = or i64 %3, %5 493 %7 = trunc i64 %6 to i8 494 ret i8 %7 495} 496 497define i50 @PR39793_bswap_u50_as_u16(i50 %0) { 498; CHECK-LABEL: @PR39793_bswap_u50_as_u16( 499; CHECK-NEXT: [[TRUNC:%.*]] = trunc i50 [[TMP0:%.*]] to i16 500; CHECK-NEXT: [[REV:%.*]] = call i16 @llvm.bswap.i16(i16 [[TRUNC]]) 501; CHECK-NEXT: [[TMP2:%.*]] = zext i16 [[REV]] to i50 502; CHECK-NEXT: ret i50 [[TMP2]] 503; 504 %2 = lshr i50 %0, 8 505 %3 = and i50 %2, 255 506 %4 = shl i50 %0, 8 507 %5 = and i50 %4, 65280 508 %6 = or i50 %3, %5 509 ret i50 %6 510} 511 512define i32 @PR39793_bswap_u32_as_u16(i32 %0) { 513; CHECK-LABEL: @PR39793_bswap_u32_as_u16( 514; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[TMP0:%.*]] to i16 515; CHECK-NEXT: [[REV:%.*]] = call i16 @llvm.bswap.i16(i16 [[TRUNC]]) 516; CHECK-NEXT: [[TMP2:%.*]] = zext i16 [[REV]] to i32 517; CHECK-NEXT: ret i32 [[TMP2]] 518; 519 %2 = lshr i32 %0, 8 520 %3 = and i32 %2, 255 521 %4 = shl i32 %0, 8 522 %5 = and i32 %4, 65280 523 %6 = or i32 %3, %5 524 ret i32 %6 525} 526 527define i8 @PR39793_bswap_u32_as_u16_trunc(i32 %0) { 528; CHECK-LABEL: @PR39793_bswap_u32_as_u16_trunc( 529; CHECK-NEXT: [[REV1:%.*]] = lshr i32 [[TMP0:%.*]], 8 530; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[REV1]] to i8 531; CHECK-NEXT: ret i8 [[TMP2]] 532; 533 %2 = lshr i32 %0, 8 534 %3 = and i32 %2, 255 535 %4 = shl i32 %0, 8 536 %5 = and i32 %4, 65280 537 %6 = or i32 %3, %5 538 %7 = trunc i32 %6 to i8 539 ret i8 %7 540} 541 542define i32 @partial_bswap(i32 %x) { 543; CHECK-LABEL: @partial_bswap( 544; CHECK-NEXT: [[R:%.*]] = call i32 @llvm.bswap.i32(i32 [[X:%.*]]) 545; CHECK-NEXT: ret i32 [[R]] 546; 547 %x3 = shl i32 %x, 24 548 %a2 = shl i32 %x, 8 549 %x2 = and i32 %a2, 16711680 550 %x32 = or i32 %x3, %x2 551 %t1 = and i32 %x, -65536 552 %t2 = call i32 @llvm.bswap.i32(i32 %t1) 553 %r = or i32 %x32, %t2 554 ret i32 %r 555} 556declare i32 @llvm.bswap.i32(i32) 557 558define <2 x i32> @partial_bswap_vector(<2 x i32> %x) { 559; CHECK-LABEL: @partial_bswap_vector( 560; CHECK-NEXT: [[R:%.*]] = call <2 x i32> @llvm.bswap.v2i32(<2 x i32> [[X:%.*]]) 561; CHECK-NEXT: ret <2 x i32> [[R]] 562; 563 %x3 = shl <2 x i32> %x, <i32 24, i32 24> 564 %a2 = shl <2 x i32> %x, <i32 8, i32 8> 565 %x2 = and <2 x i32> %a2, <i32 16711680, i32 16711680> 566 %x32 = or <2 x i32> %x3, %x2 567 %t1 = and <2 x i32> %x, <i32 -65536, i32 -65536> 568 %t2 = call <2 x i32> @llvm.bswap.v2i32(<2 x i32> %t1) 569 %r = or <2 x i32> %x32, %t2 570 ret <2 x i32> %r 571} 572declare <2 x i32> @llvm.bswap.v2i32(<2 x i32>) 573 574define i16 @partial_bitreverse(i16 %x) { 575; CHECK-LABEL: @partial_bitreverse( 576; CHECK-NEXT: [[OR:%.*]] = call i16 @llvm.bswap.i16(i16 [[X:%.*]]) 577; CHECK-NEXT: ret i16 [[OR]] 578; 579 %rev= call i16 @llvm.bitreverse.i16(i16 %x) 580 %lo = and i16 %rev, 255 581 %hi = and i16 %rev, -256 582 %revlo = call i16 @llvm.bitreverse.i16(i16 %lo) 583 %revhi = call i16 @llvm.bitreverse.i16(i16 %hi) 584 %newlo = lshr i16 %revlo, 8 585 %newhi = shl i16 %revhi, 8 586 %or = or i16 %newlo, %newhi 587 ret i16 %or 588} 589declare i16 @llvm.bitreverse.i16(i16) 590 591define i64 @bswap_and_mask_0(i64 %0) { 592; CHECK-LABEL: @bswap_and_mask_0( 593; CHECK-NEXT: [[TMP2:%.*]] = and i64 [[TMP0:%.*]], -72057594037927681 594; CHECK-NEXT: [[TMP3:%.*]] = call i64 @llvm.bswap.i64(i64 [[TMP2]]) 595; CHECK-NEXT: ret i64 [[TMP3]] 596; 597 %2 = lshr i64 %0, 56 598 %3 = shl i64 %0, 56 599 %4 = or i64 %2, %3 600 ret i64 %4 601} 602 603define i64 @bswap_and_mask_1(i64 %0) { 604; CHECK-LABEL: @bswap_and_mask_1( 605; CHECK-NEXT: [[TMP2:%.*]] = lshr i64 [[TMP0:%.*]], 56 606; CHECK-NEXT: [[TMP3:%.*]] = lshr i64 [[TMP0]], 40 607; CHECK-NEXT: [[TMP4:%.*]] = and i64 [[TMP3]], 65280 608; CHECK-NEXT: [[TMP5:%.*]] = or disjoint i64 [[TMP4]], [[TMP2]] 609; CHECK-NEXT: ret i64 [[TMP5]] 610; 611 %2 = lshr i64 %0, 56 612 %3 = lshr i64 %0, 40 613 %4 = and i64 %3, 65280 614 %5 = or i64 %4, %2 615 ret i64 %5 616} 617 618define i64 @bswap_and_mask_2(i64 %0) { 619; CHECK-LABEL: @bswap_and_mask_2( 620; CHECK-NEXT: [[TMP2:%.*]] = and i64 [[TMP0:%.*]], -72057594037862401 621; CHECK-NEXT: [[TMP3:%.*]] = call i64 @llvm.bswap.i64(i64 [[TMP2]]) 622; CHECK-NEXT: ret i64 [[TMP3]] 623; 624 %2 = lshr i64 %0, 56 625 %3 = shl i64 %0, 56 626 %4 = or i64 %2, %3 627 %5 = shl i64 %0, 40 628 %6 = and i64 %5, 71776119061217280 629 %7 = or i64 %4, %6 630 ret i64 %7 631} 632 633define i64 @bswap_trunc(i64 %x01234567) { 634; CHECK-LABEL: @bswap_trunc( 635; CHECK-NEXT: [[X76543210:%.*]] = call i64 @llvm.bswap.i64(i64 [[X01234567:%.*]]) 636; CHECK-NEXT: ret i64 [[X76543210]] 637; 638 %x7zzzzzzz = shl i64 %x01234567, 56 639 %xz0123456 = lshr i64 %x01234567, 8 640 %xzzzzz012 = lshr i64 %x01234567, 40 641 %x3456 = trunc i64 %xz0123456 to i32 642 %xz012 = trunc i64 %xzzzzz012 to i32 643 %x6543 = call i32 @llvm.bswap.i32(i32 %x3456) 644 %x210z = call i32 @llvm.bswap.i32(i32 %xz012) 645 %xz210 = lshr i32 %x210z, 8 646 %xzzzz6543 = zext i32 %x6543 to i64 647 %xzzzzz210 = zext i32 %xz210 to i64 648 %xz6543zzz = shl i64 %xzzzz6543, 24 649 %xz6543210 = or i64 %xzzzzz210, %xz6543zzz 650 %x76543210 = or i64 %xz6543210, %x7zzzzzzz 651 ret i64 %x76543210 652} 653 654define i32 @shuf_4bytes(<4 x i8> %x) { 655; CHECK-LABEL: @shuf_4bytes( 656; CHECK-NEXT: [[TMP1:%.*]] = bitcast <4 x i8> [[X:%.*]] to i32 657; CHECK-NEXT: [[CAST:%.*]] = call i32 @llvm.bswap.i32(i32 [[TMP1]]) 658; CHECK-NEXT: ret i32 [[CAST]] 659; 660 %bswap = shufflevector <4 x i8> %x, <4 x i8> poison, <4 x i32> <i32 3, i32 2, i32 1, i32 0> 661 %cast = bitcast <4 x i8> %bswap to i32 662 ret i32 %cast 663} 664 665define i32 @shuf_load_4bytes(ptr %p) { 666; CHECK-LABEL: @shuf_load_4bytes( 667; CHECK-NEXT: [[X1:%.*]] = load i32, ptr [[P:%.*]], align 4 668; CHECK-NEXT: [[CAST:%.*]] = call i32 @llvm.bswap.i32(i32 [[X1]]) 669; CHECK-NEXT: ret i32 [[CAST]] 670; 671 %x = load <4 x i8>, ptr %p 672 %bswap = shufflevector <4 x i8> %x, <4 x i8> poison, <4 x i32> <i32 3, i32 2, i32 poison, i32 0> 673 %cast = bitcast <4 x i8> %bswap to i32 674 ret i32 %cast 675} 676 677define i32 @shuf_bitcast_twice_4bytes(i32 %x) { 678; CHECK-LABEL: @shuf_bitcast_twice_4bytes( 679; CHECK-NEXT: [[CAST2:%.*]] = call i32 @llvm.bswap.i32(i32 [[X:%.*]]) 680; CHECK-NEXT: ret i32 [[CAST2]] 681; 682 %cast1 = bitcast i32 %x to <4 x i8> 683 %bswap = shufflevector <4 x i8> %cast1, <4 x i8> poison, <4 x i32> <i32 poison, i32 2, i32 1, i32 0> 684 %cast2 = bitcast <4 x i8> %bswap to i32 685 ret i32 %cast2 686} 687 688; Negative test - extra use 689declare void @use(<4 x i8>) 690 691define i32 @shuf_4bytes_extra_use(<4 x i8> %x) { 692; CHECK-LABEL: @shuf_4bytes_extra_use( 693; CHECK-NEXT: [[BSWAP:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> poison, <4 x i32> <i32 3, i32 2, i32 1, i32 0> 694; CHECK-NEXT: call void @use(<4 x i8> [[BSWAP]]) 695; CHECK-NEXT: [[CAST:%.*]] = bitcast <4 x i8> [[BSWAP]] to i32 696; CHECK-NEXT: ret i32 [[CAST]] 697; 698 %bswap = shufflevector <4 x i8> %x, <4 x i8> poison, <4 x i32> <i32 3, i32 2, i32 1, i32 0> 699 call void @use(<4 x i8> %bswap) 700 %cast = bitcast <4 x i8> %bswap to i32 701 ret i32 %cast 702} 703 704; Negative test - scalar type is not in the data layout 705 706define i128 @shuf_16bytes(<16 x i8> %x) { 707; CHECK-LABEL: @shuf_16bytes( 708; CHECK-NEXT: [[BSWAP:%.*]] = shufflevector <16 x i8> [[X:%.*]], <16 x i8> poison, <16 x i32> <i32 15, i32 14, i32 13, i32 12, i32 11, i32 10, i32 9, i32 8, i32 7, i32 6, i32 5, i32 4, i32 3, i32 2, i32 1, i32 0> 709; CHECK-NEXT: [[CAST:%.*]] = bitcast <16 x i8> [[BSWAP]] to i128 710; CHECK-NEXT: ret i128 [[CAST]] 711; 712 %bswap = shufflevector <16 x i8> %x, <16 x i8> poison, <16 x i32> <i32 15, i32 14, i32 13, i32 12, i32 11, i32 10, i32 9, i32 8, i32 7, i32 6, i32 5, i32 4, i32 3, i32 2, i32 1, i32 0> 713 %cast = bitcast <16 x i8> %bswap to i128 714 ret i128 %cast 715} 716 717; Negative test - don't touch widening shuffles (for now) 718 719define i32 @shuf_2bytes_widening(<2 x i8> %x) { 720; CHECK-LABEL: @shuf_2bytes_widening( 721; CHECK-NEXT: [[BSWAP:%.*]] = shufflevector <2 x i8> [[X:%.*]], <2 x i8> poison, <4 x i32> <i32 1, i32 0, i32 poison, i32 poison> 722; CHECK-NEXT: [[CAST:%.*]] = bitcast <4 x i8> [[BSWAP]] to i32 723; CHECK-NEXT: ret i32 [[CAST]] 724; 725 %bswap = shufflevector <2 x i8> %x, <2 x i8> poison, <4 x i32> <i32 1, i32 0, i32 poison, i32 poison> 726 %cast = bitcast <4 x i8> %bswap to i32 727 ret i32 %cast 728} 729 730declare i32 @llvm.fshl.i32(i32, i32, i32) 731declare i32 @llvm.fshr.i32(i32, i32, i32) 732 733define i32 @funnel_unary(i32 %abcd) { 734; CHECK-LABEL: @funnel_unary( 735; CHECK-NEXT: [[DCBA:%.*]] = call i32 @llvm.bswap.i32(i32 [[ABCD:%.*]]) 736; CHECK-NEXT: ret i32 [[DCBA]] 737; 738 %dabc = call i32 @llvm.fshl.i32(i32 %abcd, i32 %abcd, i32 24) 739 %bcda = call i32 @llvm.fshr.i32(i32 %abcd, i32 %abcd, i32 24) 740 %dzbz = and i32 %dabc, -16711936 741 %zcza = and i32 %bcda, 16711935 742 %dcba = or i32 %dzbz, %zcza 743 ret i32 %dcba 744} 745 746define i32 @funnel_binary(i32 %abcd) { 747; CHECK-LABEL: @funnel_binary( 748; CHECK-NEXT: [[DCBA:%.*]] = call i32 @llvm.bswap.i32(i32 [[ABCD:%.*]]) 749; CHECK-NEXT: ret i32 [[DCBA]] 750; 751 %cdzz = shl i32 %abcd, 16 752 %dcdz = call i32 @llvm.fshl.i32(i32 %abcd, i32 %cdzz, i32 24) 753 %zzab = lshr i32 %abcd, 16 754 %zaba = call i32 @llvm.fshr.i32(i32 %zzab, i32 %abcd, i32 24) 755 %dczz = and i32 %dcdz, -65536 756 %zzba = and i32 %zaba, 65535 757 %dcba = or i32 %dczz, %zzba 758 ret i32 %dcba 759} 760 761define i32 @funnel_and(i32 %abcd) { 762; CHECK-LABEL: @funnel_and( 763; CHECK-NEXT: [[DCBA:%.*]] = call i32 @llvm.bswap.i32(i32 [[ABCD:%.*]]) 764; CHECK-NEXT: ret i32 [[DCBA]] 765; 766 %zzcz = and i32 %abcd, 65280 767 %zcza = call i32 @llvm.fshl.i32(i32 %zzcz, i32 %abcd, i32 8) 768 %zbzz = and i32 %abcd, 16711680 769 %dzbz = call i32 @llvm.fshl.i32(i32 %abcd, i32 %zbzz, i32 24) 770 %dcba = or i32 %zcza, %dzbz 771 ret i32 %dcba 772} 773 774; Don't attempt to collectBitParts from >128 bit integers 775define i16 @trunc_bswap_i160(ptr %a0) { 776; CHECK-LABEL: @trunc_bswap_i160( 777; CHECK-NEXT: [[LOAD:%.*]] = load i160, ptr [[A0:%.*]], align 4 778; CHECK-NEXT: [[LSHR1:%.*]] = lshr i160 [[LOAD]], 136 779; CHECK-NEXT: [[CAST1:%.*]] = trunc i160 [[LSHR1]] to i16 780; CHECK-NEXT: [[AND1:%.*]] = and i16 [[CAST1]], 255 781; CHECK-NEXT: [[SH_DIFF:%.*]] = lshr i160 [[LOAD]], 120 782; CHECK-NEXT: [[TR_SH_DIFF:%.*]] = trunc i160 [[SH_DIFF]] to i16 783; CHECK-NEXT: [[SHL:%.*]] = and i16 [[TR_SH_DIFF]], -256 784; CHECK-NEXT: [[OR:%.*]] = or disjoint i16 [[AND1]], [[SHL]] 785; CHECK-NEXT: ret i16 [[OR]] 786; 787 %load = load i160, ptr %a0, align 4 788 %lshr0 = lshr i160 %load, 128 789 %lshr1 = lshr i160 %load, 136 790 %cast0 = trunc i160 %lshr0 to i16 791 %cast1 = trunc i160 %lshr1 to i16 792 %and0 = and i16 %cast0, 255 793 %and1 = and i16 %cast1, 255 794 %shl = shl i16 %and0, 8 795 %or = or i16 %and1, %shl 796 ret i16 %or 797} 798 799; PR47191 - deep IR trees prevent ADD/XOR instructions being simplified to OR. 800 801define i64 @PR47191_problem1(i64 %0) { 802; CHECK-LABEL: @PR47191_problem1( 803; CHECK-NEXT: [[TMP2:%.*]] = call i64 @llvm.bswap.i64(i64 [[TMP0:%.*]]) 804; CHECK-NEXT: ret i64 [[TMP2]] 805; 806 %2 = lshr i64 %0, 56 807 %3 = lshr i64 %0, 40 808 %4 = and i64 %3, 65280 809 %5 = lshr i64 %0, 24 810 %6 = and i64 %5, 16711680 811 %7 = lshr i64 %0, 8 812 %8 = and i64 %7, 4278190080 813 %9 = shl i64 %0, 56 814 %10 = shl i64 %0, 40 815 %11 = and i64 %10, 71776119061217280 816 %12 = shl i64 %0, 24 817 %13 = and i64 %12, 280375465082880 818 %14 = or i64 %9, %2 819 %15 = or i64 %14, %4 820 %16 = or i64 %15, %6 821 %17 = or i64 %16, %8 822 %18 = or i64 %17, %11 823 %19 = or i64 %18, %13 824 %20 = shl i64 %0, 8 825 %21 = and i64 %20, 1095216660480 826 %22 = add i64 %19, %21 827 ret i64 %22 828} 829 830define i64 @PR47191_problem2(i64 %0) { 831; CHECK-LABEL: @PR47191_problem2( 832; CHECK-NEXT: [[TMP2:%.*]] = call i64 @llvm.bswap.i64(i64 [[TMP0:%.*]]) 833; CHECK-NEXT: ret i64 [[TMP2]] 834; 835 %2 = lshr i64 %0, 56 836 %3 = lshr i64 %0, 40 837 %4 = and i64 %3, 65280 838 %5 = lshr i64 %0, 24 839 %6 = and i64 %5, 16711680 840 %7 = lshr i64 %0, 8 841 %8 = and i64 %7, 4278190080 842 %9 = shl i64 %0, 56 843 %10 = shl i64 %0, 40 844 %11 = and i64 %10, 71776119061217280 845 %12 = or i64 %9, %2 846 %13 = or i64 %12, %4 847 %14 = or i64 %13, %6 848 %15 = or i64 %14, %8 849 %16 = or i64 %15, %11 850 %17 = shl i64 %0, 24 851 %18 = and i64 %17, 280375465082880 852 %19 = shl i64 %0, 8 853 %20 = and i64 %19, 1095216660480 854 %21 = or i64 %20, %18 855 %22 = xor i64 %21, %16 856 ret i64 %22 857} 858 859define i64 @PR47191_problem3(i64 %0) { 860; CHECK-LABEL: @PR47191_problem3( 861; CHECK-NEXT: [[TMP2:%.*]] = call i64 @llvm.bswap.i64(i64 [[TMP0:%.*]]) 862; CHECK-NEXT: ret i64 [[TMP2]] 863; 864 %2 = lshr i64 %0, 56 865 %3 = lshr i64 %0, 40 866 %4 = and i64 %3, 65280 867 %5 = lshr i64 %0, 24 868 %6 = and i64 %5, 16711680 869 %7 = lshr i64 %0, 8 870 %8 = and i64 %7, 4278190080 871 %9 = shl i64 %0, 56 872 %10 = shl i64 %0, 40 873 %11 = and i64 %10, 71776119061217280 874 %12 = or i64 %9, %2 875 %13 = or i64 %12, %4 876 %14 = or i64 %13, %6 877 %15 = or i64 %14, %8 878 %16 = or i64 %15, %11 879 %17 = shl i64 %0, 24 880 %18 = and i64 %17, 280375465082880 881 %19 = shl i64 %0, 8 882 %20 = and i64 %19, 1095216660480 883 %21 = or i64 %20, %18 884 %22 = xor i64 %21, %16 885 ret i64 %22 886} 887 888define i64 @PR47191_problem4(i64 %0) { 889; CHECK-LABEL: @PR47191_problem4( 890; CHECK-NEXT: [[TMP2:%.*]] = call i64 @llvm.bswap.i64(i64 [[TMP0:%.*]]) 891; CHECK-NEXT: ret i64 [[TMP2]] 892; 893 %2 = lshr i64 %0, 56 894 %3 = shl i64 %0, 56 895 %4 = or i64 %2, %3 896 %5 = lshr i64 %0, 40 897 %6 = and i64 %5, 65280 898 %7 = or i64 %4, %6 899 %8 = shl i64 %0, 40 900 %9 = and i64 %8, 71776119061217280 901 %10 = or i64 %7, %9 902 %11 = lshr i64 %0, 24 903 %12 = and i64 %11, 16711680 904 %13 = or i64 %10, %12 905 %14 = shl i64 %0, 24 906 %15 = and i64 %14, 280375465082880 907 %16 = or i64 %13, %15 908 %17 = lshr i64 %0, 8 909 %18 = and i64 %17, 4278190080 910 %19 = or i64 %16, %18 911 %20 = shl i64 %0, 8 912 %21 = and i64 %20, 1095216660480 913 %22 = add i64 %19, %21 914 ret i64 %22 915} 916 917declare i64 @llvm.bswap.i64(i64) 918 919define i32 @PR50910(i64 %t0) { 920; CHECK-LABEL: @PR50910( 921; CHECK-NEXT: [[T5:%.*]] = call i64 @llvm.bswap.i64(i64 [[T0:%.*]]) 922; CHECK-NEXT: [[T6:%.*]] = trunc i64 [[T5]] to i32 923; CHECK-NEXT: ret i32 [[T6]] 924; 925 %t2 = and i64 %t0, 72057594037927935 926 %t3 = call i64 @llvm.bswap.i64(i64 %t2) 927 %t4 = lshr i64 %t0, 56 928 %t5 = or i64 %t3, %t4 929 %t6 = trunc i64 %t5 to i32 930 ret i32 %t6 931} 932 933define i64 @PR60690_call_fshl(i64 %result) { 934; CHECK-LABEL: @PR60690_call_fshl( 935; CHECK-NEXT: [[OR_I12:%.*]] = call i64 @llvm.bswap.i64(i64 [[RESULT:%.*]]) 936; CHECK-NEXT: ret i64 [[OR_I12]] 937; 938 %and.i = lshr i64 %result, 8 939 %shr.i = and i64 %and.i, 71777214294589695 940 %and1.i = shl i64 %result, 8 941 %shl.i = and i64 %and1.i, -71777214294589696 942 %or.i = or i64 %shr.i, %shl.i 943 %and.i7 = shl i64 %or.i, 16 944 %shl.i8 = and i64 %and.i7, -281470681808896 945 %and1.i9 = lshr i64 %or.i, 16 946 %shr.i10 = and i64 %and1.i9, 281470681808895 947 %or.i11 = or i64 %shl.i8, %shr.i10 948 %or.i12 = tail call i64 @llvm.fshl.i64(i64 %or.i11, i64 %or.i11, i64 32) 949 ret i64 %or.i12 950} 951declare i64 @llvm.fshl.i64(i64, i64, i64) 952 953define i64 @PR60690_call_fshr(i64 %result) { 954; CHECK-LABEL: @PR60690_call_fshr( 955; CHECK-NEXT: [[OR_I12:%.*]] = call i64 @llvm.bswap.i64(i64 [[RESULT:%.*]]) 956; CHECK-NEXT: ret i64 [[OR_I12]] 957; 958 %and.i = lshr i64 %result, 8 959 %shr.i = and i64 %and.i, 71777214294589695 960 %and1.i = shl i64 %result, 8 961 %shl.i = and i64 %and1.i, -71777214294589696 962 %or.i = or i64 %shr.i, %shl.i 963 %and.i7 = shl i64 %or.i, 16 964 %shl.i8 = and i64 %and.i7, -281470681808896 965 %and1.i9 = lshr i64 %or.i, 16 966 %shr.i10 = and i64 %and1.i9, 281470681808895 967 %or.i11 = or i64 %shl.i8, %shr.i10 968 %or.i12 = tail call i64 @llvm.fshr.i64(i64 %or.i11, i64 %or.i11, i64 32) 969 ret i64 %or.i12 970} 971declare i64 @llvm.fshr.i64(i64, i64, i64) 972