1; RUN: llc < %s -march=avr -verify-machineinstrs | FileCheck %s 2 3; Optimize for speed. 4; CHECK-LABEL: shift_i8_i8_speed 5define i8 @shift_i8_i8_speed(i8 %a, i8 %b) { 6 ; CHECK: dec r22 7 ; CHECK-NEXT: brmi .LBB0_2 8 ; CHECK-NEXT: .LBB0_1: 9 ; CHECK-NEXT: lsl r24 10 ; CHECK-NEXT: dec r22 11 ; CHECK-NEXT: brpl .LBB0_1 12 ; CHECK-NEXT: .LBB0_2: 13 ; CHECK-NEXT: ret 14 %result = shl i8 %a, %b 15 ret i8 %result 16} 17 18; Optimize for size (producing slightly smaller code). 19; CHECK-LABEL: shift_i8_i8_size 20define i8 @shift_i8_i8_size(i8 %a, i8 %b) optsize { 21 ; CHECK: .LBB1_1: 22 ; CHECK-NEXT: dec r22 23 ; CHECK-NEXT: brmi .LBB1_3 24 ; CHECK: lsl r24 25 ; CHECK-NEXT: rjmp .LBB1_1 26 ; CHECK-NEXT: .LBB1_3: 27 ; CHECK-NEXT: ret 28 %result = shl i8 %a, %b 29 ret i8 %result 30} 31 32; CHECK-LABEL: shift_i16_i16 33define i16 @shift_i16_i16(i16 %a, i16 %b) { 34 ; CHECK: dec r22 35 ; CHECK-NEXT: brmi .LBB2_2 36 ; CHECK-NEXT: .LBB2_1: 37 ; CHECK-NEXT: lsl r24 38 ; CHECK-NEXT: rol r25 39 ; CHECK-NEXT: dec r22 40 ; CHECK-NEXT: brpl .LBB2_1 41 ; CHECK-NEXT: .LBB2_2: 42 ; CHECK-NEXT: ret 43 %result = shl i16 %a, %b 44 ret i16 %result 45} 46 47; CHECK-LABEL: shift_i64_i64 48define i64 @shift_i64_i64(i64 %a, i64 %b) { 49 ; CHECK: call __ashldi3 50 %result = shl i64 %a, %b 51 ret i64 %result 52} 53 54define i8 @lsl_i8_1(i8 %a) { 55; CHECK-LABEL: lsl_i8_1: 56; CHECK: lsl r24 57 %res = shl i8 %a, 1 58 ret i8 %res 59} 60 61define i8 @lsl_i8_2(i8 %a) { 62; CHECK-LABEL: lsl_i8_2: 63; CHECK: lsl r24 64; CHECK-NEXT: lsl r24 65 %res = shl i8 %a, 2 66 ret i8 %res 67} 68 69define i8 @lsl_i8_3(i8 %a) { 70; CHECK-LABEL: lsl_i8_3: 71; CHECK: lsl r24 72; CHECK-NEXT: lsl r24 73; CHECK-NEXT: lsl r24 74 %res = shl i8 %a, 3 75 ret i8 %res 76} 77 78define i8 @lsl_i8_4(i8 %a) { 79; CHECK-LABEL: lsl_i8_4: 80; CHECK: swap r24 81; CHECK-NEXT: andi r24, -16 82 %res = shl i8 %a, 4 83 ret i8 %res 84} 85 86define i8 @lsl_i8_5(i8 %a) { 87; CHECK-LABEL: lsl_i8_5: 88; CHECK: swap r24 89; CHECK-NEXT: andi r24, -16 90; CHECK-NEXT: lsl r24 91 %res = shl i8 %a, 5 92 ret i8 %res 93} 94 95define i8 @lsl_i8_6(i8 %a) { 96; CHECK-LABEL: lsl_i8_6: 97; CHECK: swap r24 98; CHECK-NEXT: andi r24, -16 99; CHECK-NEXT: lsl r24 100; CHECK-NEXT: lsl r24 101 %res = shl i8 %a, 6 102 ret i8 %res 103} 104 105define i8 @lsr_i8_1(i8 %a) { 106; CHECK-LABEL: lsr_i8_1: 107; CHECK: lsr r24 108 %res = lshr i8 %a, 1 109 ret i8 %res 110} 111 112define i8 @lsr_i8_2(i8 %a) { 113; CHECK-LABEL: lsr_i8_2: 114; CHECK: lsr r24 115; CHECK-NEXT: lsr r24 116 %res = lshr i8 %a, 2 117 ret i8 %res 118} 119 120define i8 @lsr_i8_3(i8 %a) { 121; CHECK-LABEL: lsr_i8_3: 122; CHECK: lsr r24 123; CHECK-NEXT: lsr r24 124; CHECK-NEXT: lsr r24 125 %res = lshr i8 %a, 3 126 ret i8 %res 127} 128 129define i8 @lsr_i8_4(i8 %a) { 130; CHECK-LABEL: lsr_i8_4: 131; CHECK: swap r24 132; CHECK-NEXT: andi r24, 15 133 %res = lshr i8 %a, 4 134 ret i8 %res 135} 136 137define i8 @lsr_i8_5(i8 %a) { 138; CHECK-LABEL: lsr_i8_5: 139; CHECK: swap r24 140; CHECK-NEXT: andi r24, 15 141; CHECK-NEXT: lsr r24 142 %res = lshr i8 %a, 5 143 ret i8 %res 144} 145 146define i8 @lsr_i8_6(i8 %a) { 147; CHECK-LABEL: lsr_i8_6: 148; CHECK: swap r24 149; CHECK-NEXT: andi r24, 15 150; CHECK-NEXT: lsr r24 151; CHECK-NEXT: lsr r24 152 %res = lshr i8 %a, 6 153 ret i8 %res 154} 155 156define i8 @lsl_i8_7(i8 %a) { 157; CHECK-LABEL: lsl_i8_7 158; CHECK: ror r24 159; CHECK-NEXT: clr r24 160; CHECK-NEXT: ror r24 161 %result = shl i8 %a, 7 162 ret i8 %result 163} 164 165define i8 @lsr_i8_7(i8 %a) { 166; CHECK-LABEL: lsr_i8_7 167; CHECK: rol r24 168; CHECK-NEXT: clr r24 169; CHECK-NEXT: rol r24 170 %result = lshr i8 %a, 7 171 ret i8 %result 172} 173 174define i8 @asr_i8_6(i8 %a) { 175; CHECK-LABEL: asr_i8_6 176; CHECK: bst r24, 6 177; CHECK-NEXT: lsl r24 178; CHECK-NEXT: sbc r24, r24 179; CHECK-NEXT: bld r24, 0 180 %result = ashr i8 %a, 6 181 ret i8 %result 182} 183 184define i8 @asr_i8_7(i8 %a) { 185; CHECK-LABEL: asr_i8_7 186; CHECK: lsl r24 187; CHECK-NEXT: sbc r24, r24 188 %result = ashr i8 %a, 7 189 ret i8 %result 190} 191 192define i16 @lsl_i16_5(i16 %a) { 193; CHECK-LABEL: lsl_i16_5 194; CHECK: swap r25 195; CHECK-NEXT: swap r24 196; CHECK-NEXT: andi r25, 240 197; CHECK-NEXT: eor r25, r24 198; CHECK-NEXT: andi r24, 240 199; CHECK-NEXT: eor r25, r24 200; CHECK-NEXT: lsl r24 201; CHECK-NEXT: rol r25 202; CHECK-NEXT: ret 203 %result = shl i16 %a, 5 204 ret i16 %result 205} 206 207define i16 @lsl_i16_6(i16 %a, i16 %b, i16 %c, i16 %d, i16 %e, i16 %f) { 208; CHECK-LABEL: lsl_i16_6 209; CHECK: mov r24, r14 210; CHECK-NEXT: mov r25, r15 211; CHECK-NEXT: swap r25 212; CHECK-NEXT: swap r24 213; CHECK-NEXT: andi r25, 240 214; CHECK-NEXT: eor r25, r24 215; CHECK-NEXT: andi r24, 240 216; CHECK-NEXT: eor r25, r24 217; CHECK-NEXT: lsl r24 218; CHECK-NEXT: rol r25 219; CHECK-NEXT: lsl r24 220; CHECK-NEXT: rol r25 221; CHECK-NEXT: ret 222 %result = shl i16 %f, 6 223 ret i16 %result 224} 225 226define i16 @lsl_i16_9(i16 %a) { 227; CHECK-LABEL: lsl_i16_9 228; CHECK: mov r25, r24 229; CHECK-NEXT: clr r24 230; CHECK-NEXT: lsl r25 231; CHECK-NEXT: ret 232 %result = shl i16 %a, 9 233 ret i16 %result 234} 235 236define i16 @lsl_i16_13(i16 %a) { 237; CHECK-LABEL: lsl_i16_13 238; CHECK: mov r25, r24 239; CHECK-NEXT: swap r25 240; CHECK-NEXT: andi r25, 240 241; CHECK-NEXT: clr r24 242; CHECK-NEXT: lsl r25 243; CHECK-NEXT: ret 244 %result = shl i16 %a, 13 245 ret i16 %result 246} 247 248define i16 @lsr_i16_5(i16 %a) { 249; CHECK-LABEL: lsr_i16_5 250; CHECK: swap r25 251; CHECK-NEXT: swap r24 252; CHECK-NEXT: andi r24, 15 253; CHECK-NEXT: eor r24, r25 254; CHECK-NEXT: andi r25, 15 255; CHECK-NEXT: eor r24, r25 256; CHECK-NEXT: lsr r25 257; CHECK-NEXT: ror r24 258; CHECK-NEXT: ret 259 %result = lshr i16 %a, 5 260 ret i16 %result 261} 262 263define i16 @lsr_i16_6(i16 %a, i16 %b, i16 %c, i16 %d, i16 %e, i16 %f) { 264; CHECK-LABEL: lsr_i16_6 265; CHECK: mov r24, r14 266; CHECK-NEXT: mov r25, r15 267; CHECK-NEXT: swap r25 268; CHECK-NEXT: swap r24 269; CHECK-NEXT: andi r24, 15 270; CHECK-NEXT: eor r24, r25 271; CHECK-NEXT: andi r25, 15 272; CHECK-NEXT: eor r24, r25 273; CHECK-NEXT: lsr r25 274; CHECK-NEXT: ror r24 275; CHECK-NEXT: lsr r25 276; CHECK-NEXT: ror r24 277; CHECK-NEXT: ret 278 %result = lshr i16 %f, 6 279 ret i16 %result 280} 281 282define i16 @lsr_i16_9(i16 %a) { 283; CHECK-LABEL: lsr_i16_9 284; CHECK: mov r24, r25 285; CHECK-NEXT: clr r25 286; CHECK-NEXT: lsr r24 287; CHECK-NEXT: ret 288 %result = lshr i16 %a, 9 289 ret i16 %result 290} 291 292define i16 @lsr_i16_13(i16 %a) { 293; CHECK-LABEL: lsr_i16_13 294; CHECK: mov r24, r25 295; CHECK-NEXT: swap r24 296; CHECK-NEXT: andi r24, 15 297; CHECK-NEXT: clr r25 298; CHECK-NEXT: lsr r24 299; CHECK-NEXT: ret 300 %result = lshr i16 %a, 13 301 ret i16 %result 302} 303 304define i16 @asr_i16_7(i16 %a) { 305; CHECK-LABEL: asr_i16_7 306; CHECK: lsl r24 307; CHECK-NEXT: mov r24, r25 308; CHECK-NEXT: rol r24 309; CHECK-NEXT: sbc r25, r25 310; CHECK-NEXT: ret 311 %result = ashr i16 %a, 7 312 ret i16 %result 313} 314 315define i16 @asr_i16_9(i16 %a) { 316; CHECK-LABEL: asr_i16_9 317; CHECK: mov r24, r25 318; CHECK-NEXT: lsl r25 319; CHECK-NEXT: sbc r25, r25 320; CHECK-NEXT: asr r24 321; CHECK-NEXT: ret 322 %result = ashr i16 %a, 9 323 ret i16 %result 324} 325 326define i16 @asr_i16_12(i16 %a) { 327; CHECK-LABEL: asr_i16_12 328; CHECK: mov r24, r25 329; CHECK-NEXT: lsl r25 330; CHECK-NEXT: sbc r25, r25 331; CHECK-NEXT: asr r24 332; CHECK-NEXT: asr r24 333; CHECK-NEXT: asr r24 334; CHECK-NEXT: asr r24 335; CHECK-NEXT: ret 336 %result = ashr i16 %a, 12 337 ret i16 %result 338} 339 340define i16 @asr_i16_14(i16 %a) { 341; CHECK-LABEL: asr_i16_14 342; CHECK: lsl r25 343; CHECK-NEXT: sbc r24, r24 344; CHECK-NEXT: lsl r25 345; CHECK-NEXT: mov r25, r24 346; CHECK-NEXT: rol r24 347; CHECK-NEXT: ret 348 %result = ashr i16 %a, 14 349 ret i16 %result 350} 351 352define i16 @asr_i16_15(i16 %a) { 353; CHECK-LABEL: asr_i16_15 354; CHECK: lsl r25 355; CHECK-NEXT: sbc r25, r25 356; CHECK-NEXT: mov r24, r25 357; CHECK-NEXT: ret 358 %result = ashr i16 %a, 15 359 ret i16 %result 360} 361