brintos

brintos / llvm-project-archived public Read only

0
0
Text · 37.7 KiB · 00cc06f Raw
839 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py2; RUN: opt < %s -passes=instcombine -S | FileCheck %s3target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"4 5define i32 @test2(float %f) {6; CHECK-LABEL: @test2(7; CHECK-NEXT:    [[T5:%.*]] = fmul float [[F:%.*]], [[F]]8; CHECK-NEXT:    [[T21:%.*]] = bitcast float [[T5]] to i329; CHECK-NEXT:    ret i32 [[T21]]10;11  %t5 = fmul float %f, %f12  %t9 = insertelement <4 x float> poison, float %t5, i32 013  %t10 = insertelement <4 x float> %t9, float 0.000000e+00, i32 114  %t11 = insertelement <4 x float> %t10, float 0.000000e+00, i32 215  %t12 = insertelement <4 x float> %t11, float 0.000000e+00, i32 316  %t19 = bitcast <4 x float> %t12 to <4 x i32>17  %t21 = extractelement <4 x i32> %t19, i32 018  ret i32 %t2119}20 21define void @get_image() nounwind {22; CHECK-LABEL: @get_image(23; CHECK-NEXT:  entry:24; CHECK-NEXT:    [[TMP0:%.*]] = call i32 @fgetc(ptr null) #[[ATTR0:[0-9]+]]25; CHECK-NEXT:    br i1 false, label [[BB2:%.*]], label [[BB3:%.*]]26; CHECK:       bb2:27; CHECK-NEXT:    br label [[BB3]]28; CHECK:       bb3:29; CHECK-NEXT:    unreachable30;31entry:32  %0 = call i32 @fgetc(ptr null) nounwind33  %1 = trunc i32 %0 to i834  %t2 = insertelement <100 x i8> zeroinitializer, i8 %1, i32 135  %t1 = extractelement <100 x i8> %t2, i32 036  %2 = icmp eq i8 %t1, 8037  br i1 %2, label %bb2, label %bb338 39bb2:            ; preds = %entry40  br label %bb341 42bb3:            ; preds = %bb2, %entry43  unreachable44}45 46; PR434047define void @vac(ptr nocapture %a) nounwind {48; CHECK-LABEL: @vac(49; CHECK-NEXT:  entry:50; CHECK-NEXT:    store <4 x float> zeroinitializer, ptr [[A:%.*]], align 1651; CHECK-NEXT:    ret void52;53entry:54  %t1 = load <4 x float>, ptr %a		; <<4 x float>> [#uses=1]55  %vecins = insertelement <4 x float> %t1, float 0.000000e+00, i32 0	; <<4 x float>> [#uses=1]56  %vecins4 = insertelement <4 x float> %vecins, float 0.000000e+00, i32 1; <<4 x float>> [#uses=1]57  %vecins6 = insertelement <4 x float> %vecins4, float 0.000000e+00, i32 2; <<4 x float>> [#uses=1]58  %vecins8 = insertelement <4 x float> %vecins6, float 0.000000e+00, i32 3; <<4 x float>> [#uses=1]59  store <4 x float> %vecins8, ptr %a60  ret void61}62 63declare i32 @fgetc(ptr)64 65define <4 x float> @dead_shuffle_elt(<4 x float> %x, <2 x float> %y) nounwind {66; CHECK-LABEL: @dead_shuffle_elt(67; CHECK-NEXT:    [[SHUFFLE_I:%.*]] = shufflevector <2 x float> [[Y:%.*]], <2 x float> poison, <4 x i32> <i32 0, i32 1, i32 poison, i32 poison>68; CHECK-NEXT:    [[SHUFFLE9_I:%.*]] = shufflevector <4 x float> [[SHUFFLE_I]], <4 x float> [[X:%.*]], <4 x i32> <i32 0, i32 1, i32 6, i32 7>69; CHECK-NEXT:    ret <4 x float> [[SHUFFLE9_I]]70;71  %shuffle.i = shufflevector <2 x float> %y, <2 x float> %y, <4 x i32> <i32 0, i32 1, i32 0, i32 1>72  %shuffle9.i = shufflevector <4 x float> %x, <4 x float> %shuffle.i, <4 x i32> <i32 4, i32 5, i32 2, i32 3>73  ret <4 x float> %shuffle9.i74}75 76define <2 x float> @test_fptrunc(double %f) {77; CHECK-LABEL: @test_fptrunc(78; CHECK-NEXT:    [[TMP1:%.*]] = insertelement <2 x double> <double poison, double 0.000000e+00>, double [[F:%.*]], i64 079; CHECK-NEXT:    [[RET:%.*]] = fptrunc <2 x double> [[TMP1]] to <2 x float>80; CHECK-NEXT:    ret <2 x float> [[RET]]81;82  %t9 = insertelement <4 x double> poison, double %f, i32 083  %t10 = insertelement <4 x double> %t9, double 0.000000e+00, i32 184  %t11 = insertelement <4 x double> %t10, double 0.000000e+00, i32 285  %t12 = insertelement <4 x double> %t11, double 0.000000e+00, i32 386  %t5 = fptrunc <4 x double> %t12 to <4 x float>87  %ret = shufflevector <4 x float> %t5, <4 x float> poison, <2 x i32> <i32 0, i32 1>88  ret <2 x float> %ret89}90 91define <2 x double> @test_fpext(float %f) {92; CHECK-LABEL: @test_fpext(93; CHECK-NEXT:    [[TMP1:%.*]] = insertelement <2 x float> <float poison, float 0.000000e+00>, float [[F:%.*]], i64 094; CHECK-NEXT:    [[RET:%.*]] = fpext <2 x float> [[TMP1]] to <2 x double>95; CHECK-NEXT:    ret <2 x double> [[RET]]96;97  %t9 = insertelement <4 x float> poison, float %f, i32 098  %t10 = insertelement <4 x float> %t9, float 0.000000e+00, i32 199  %t11 = insertelement <4 x float> %t10, float 0.000000e+00, i32 2100  %t12 = insertelement <4 x float> %t11, float 0.000000e+00, i32 3101  %t5 = fpext <4 x float> %t12 to <4 x double>102  %ret = shufflevector <4 x double> %t5, <4 x double> poison, <2 x i32> <i32 0, i32 1>103  ret <2 x double> %ret104}105 106define <4 x double> @test_shuffle(<4 x double> %f) {107; CHECK-LABEL: @test_shuffle(108; CHECK-NEXT:    [[RET1:%.*]] = insertelement <4 x double> [[F:%.*]], double 1.000000e+00, i64 3109; CHECK-NEXT:    ret <4 x double> [[RET1]]110;111  %ret = shufflevector <4 x double> %f, <4 x double> <double undef, double 1.0, double undef, double undef>, <4 x i32> <i32 0, i32 1, i32 2, i32 5>112  ret <4 x double> %ret113}114 115define <4 x float> @test_select(float %f, float %g) {116; CHECK-LABEL: @test_select(117; CHECK-NEXT:    [[A3:%.*]] = insertelement <4 x float> <float poison, float poison, float poison, float 3.000000e+00>, float [[F:%.*]], i64 0118; CHECK-NEXT:    [[RET:%.*]] = shufflevector <4 x float> [[A3]], <4 x float> <float poison, float 4.000000e+00, float 5.000000e+00, float poison>, <4 x i32> <i32 0, i32 5, i32 6, i32 3>119; CHECK-NEXT:    ret <4 x float> [[RET]]120;121  %a0 = insertelement <4 x float> poison, float %f, i32 0122  %a1 = insertelement <4 x float> %a0, float 1.000000e+00, i32 1123  %a2 = insertelement <4 x float> %a1, float 2.000000e+00, i32 2124  %a3 = insertelement <4 x float> %a2, float 3.000000e+00, i32 3125  %b0 = insertelement <4 x float> poison, float %g, i32 0126  %b1 = insertelement <4 x float> %b0, float 4.000000e+00, i32 1127  %b2 = insertelement <4 x float> %b1, float 5.000000e+00, i32 2128  %b3 = insertelement <4 x float> %b2, float 6.000000e+00, i32 3129  %ret = select <4 x i1> <i1 true, i1 false, i1 false, i1 true>, <4 x float> %a3, <4 x float> %b3130  ret <4 x float> %ret131}132 133; Check that instcombine doesn't wrongly fold away the select completely.134 135define <2 x i64> @PR24922(<2 x i64> %v) {136; CHECK-LABEL: @PR24922(137; CHECK-NEXT:    [[RESULT:%.*]] = select <2 x i1> <i1 ptrtoint (ptr @PR24922 to i1), i1 true>, <2 x i64> [[V:%.*]], <2 x i64> <i64 0, i64 poison>138; CHECK-NEXT:    ret <2 x i64> [[RESULT]]139;140  %result = select <2 x i1> <i1 ptrtoint (ptr @PR24922 to i1), i1 true>, <2 x i64> %v, <2 x i64> zeroinitializer141  ret <2 x i64> %result142}143 144; The shuffle only demands the 0th (undef) element of 'out123', so everything should fold away.145 146define <4 x float> @inselt_shuf_no_demand(float %a1, float %a2, float %a3) {147; CHECK-LABEL: @inselt_shuf_no_demand(148; CHECK-NEXT:    ret <4 x float> poison149;150  %out1 = insertelement <4 x float> poison, float %a1, i32 1151  %out12 = insertelement <4 x float> %out1, float %a2, i32 2152  %out123 = insertelement <4 x float> %out12, float %a3, i32 3153  %shuffle = shufflevector <4 x float> %out123, <4 x float> poison, <4 x i32> <i32 0, i32 undef, i32 undef, i32 undef>154  ret <4 x float> %shuffle155}156 157; The shuffle only demands the 0th (undef) element of 'out123', so everything should fold away.158 159define <4 x float> @inselt_shuf_no_demand_commute(float %a1, float %a2, float %a3) {160; CHECK-LABEL: @inselt_shuf_no_demand_commute(161; CHECK-NEXT:    ret <4 x float> poison162;163  %out1 = insertelement <4 x float> poison, float %a1, i32 1164  %out12 = insertelement <4 x float> %out1, float %a2, i32 2165  %out123 = insertelement <4 x float> %out12, float %a3, i32 3166  %shuffle = shufflevector <4 x float> undef, <4 x float> %out123, <4 x i32> <i32 4, i32 undef, i32 undef, i32 undef>167  ret <4 x float> %shuffle168}169 170; The add uses 'out012' giving it multiple uses after the shuffle is transformed to also171; use 'out012'. The analysis should be able to see past that.172 173define <4 x i32> @inselt_shuf_no_demand_multiuse(i32 %a0, i32 %a1, <4 x i32> %b) {174; CHECK-LABEL: @inselt_shuf_no_demand_multiuse(175; CHECK-NEXT:    [[OUT0:%.*]] = insertelement <4 x i32> poison, i32 [[A0:%.*]], i64 0176; CHECK-NEXT:    [[OUT01:%.*]] = insertelement <4 x i32> [[OUT0]], i32 [[A1:%.*]], i64 1177; CHECK-NEXT:    [[FOO:%.*]] = add <4 x i32> [[OUT01]], [[B:%.*]]178; CHECK-NEXT:    [[SHUFFLE:%.*]] = shufflevector <4 x i32> [[FOO]], <4 x i32> poison, <4 x i32> <i32 0, i32 1, i32 poison, i32 poison>179; CHECK-NEXT:    ret <4 x i32> [[SHUFFLE]]180;181  %out0 = insertelement <4 x i32> poison, i32 %a0, i32 0182  %out01 = insertelement <4 x i32> %out0, i32 %a1, i32 1183  %out012 = insertelement <4 x i32> %out01, i32 %a0, i32 2184  %foo = add <4 x i32> %out012, %b185  %out0123 = insertelement <4 x i32> %foo, i32 %a1, i32 3186  %shuffle = shufflevector <4 x i32> %out0123, <4 x i32> poison, <4 x i32> <i32 0, i32 1, i32 undef, i32 undef>187  ret <4 x i32> %shuffle188}189 190define <4 x float> @inselt_shuf_no_demand_bogus_insert_index_in_chain(float %a1, float %a2, float %a3, i32 %variable_index) {191; CHECK-LABEL: @inselt_shuf_no_demand_bogus_insert_index_in_chain(192; CHECK-NEXT:    [[OUT12:%.*]] = insertelement <4 x float> poison, float [[A2:%.*]], i32 [[VARIABLE_INDEX:%.*]]193; CHECK-NEXT:    [[SHUFFLE:%.*]] = shufflevector <4 x float> [[OUT12]], <4 x float> poison, <4 x i32> <i32 0, i32 poison, i32 poison, i32 poison>194; CHECK-NEXT:    ret <4 x float> [[SHUFFLE]]195;196  %out1 = insertelement <4 x float> poison, float %a1, i32 1197  %out12 = insertelement <4 x float> %out1, float %a2, i32 %variable_index ; something unexpected198  %out123 = insertelement <4 x float> %out12, float %a3, i32 3199  %shuffle = shufflevector <4 x float> %out123, <4 x float> poison, <4 x i32> <i32 0, i32 undef, i32 undef, i32 undef>200  ret <4 x float> %shuffle201}202 203; Test undef replacement in constant vector elements with binops.204 205define <3 x i8> @shuf_add(<3 x i8> %x) {206; CHECK-LABEL: @shuf_add(207; CHECK-NEXT:    [[BO:%.*]] = add nsw <3 x i8> [[X:%.*]], <i8 poison, i8 2, i8 3>208; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 1, i32 poison, i32 2>209; CHECK-NEXT:    ret <3 x i8> [[R]]210;211  %bo = add nsw <3 x i8> %x, <i8 1, i8 2, i8 3>212  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 1, i32 undef, i32 2>213  ret <3 x i8> %r214}215 216define <3 x i8> @shuf_sub(<3 x i8> %x) {217; CHECK-LABEL: @shuf_sub(218; CHECK-NEXT:    [[BO:%.*]] = sub nuw <3 x i8> <i8 1, i8 poison, i8 3>, [[X:%.*]]219; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 0, i32 poison, i32 2>220; CHECK-NEXT:    ret <3 x i8> [[R]]221;222  %bo = sub nuw <3 x i8> <i8 1, i8 2, i8 3>, %x223  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 0, i32 undef, i32 2>224  ret <3 x i8> %r225}226 227define <3 x i8> @shuf_mul(<3 x i8> %x) {228; CHECK-LABEL: @shuf_mul(229; CHECK-NEXT:    [[BO:%.*]] = mul nsw <3 x i8> [[X:%.*]], <i8 1, i8 poison, i8 3>230; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 0, i32 2, i32 0>231; CHECK-NEXT:    ret <3 x i8> [[R]]232;233  %bo = mul nsw <3 x i8> %x, <i8 1, i8 2, i8 3>234  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 0, i32 2, i32 0>235  ret <3 x i8> %r236}237 238define <3 x i8> @shuf_and(<3 x i8> %x) {239; CHECK-LABEL: @shuf_and(240; CHECK-NEXT:    [[BO:%.*]] = and <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 poison>241; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 1, i32 1, i32 0>242; CHECK-NEXT:    ret <3 x i8> [[R]]243;244  %bo = and <3 x i8> %x, <i8 1, i8 2, i8 3>245  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 1, i32 1, i32 0>246  ret <3 x i8> %r247}248 249define <3 x i8> @shuf_or(<3 x i8> %x) {250; CHECK-LABEL: @shuf_or(251; CHECK-NEXT:    [[BO:%.*]] = or <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 poison>252; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 1, i32 poison, i32 0>253; CHECK-NEXT:    ret <3 x i8> [[R]]254;255  %bo = or <3 x i8> %x, <i8 1, i8 2, i8 3>256  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 1, i32 undef, i32 0>257  ret <3 x i8> %r258}259 260define <3 x i8> @shuf_xor(<3 x i8> %x) {261; CHECK-LABEL: @shuf_xor(262; CHECK-NEXT:    [[BO:%.*]] = xor <3 x i8> [[X:%.*]], <i8 1, i8 poison, i8 3>263; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 poison, i32 0>264; CHECK-NEXT:    ret <3 x i8> [[R]]265;266  %bo = xor <3 x i8> %x, <i8 1, i8 2, i8 3>267  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 undef, i32 0>268  ret <3 x i8> %r269}270 271define <3 x i8> @shuf_lshr_const_op0(<3 x i8> %x) {272; CHECK-LABEL: @shuf_lshr_const_op0(273; CHECK-NEXT:    [[BO:%.*]] = lshr <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]274; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 1, i32 poison>275; CHECK-NEXT:    ret <3 x i8> [[R]]276;277  %bo = lshr <3 x i8> <i8 1, i8 2, i8 3>, %x278  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 1, i32 undef>279  ret <3 x i8> %r280}281 282define <3 x i8> @shuf_lshr_const_op1(<3 x i8> %x) {283; CHECK-LABEL: @shuf_lshr_const_op1(284; CHECK-NEXT:    [[BO:%.*]] = lshr exact <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>285; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 1, i32 poison>286; CHECK-NEXT:    ret <3 x i8> [[R]]287;288  %bo = lshr exact <3 x i8> %x, <i8 1, i8 2, i8 3>289  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 1, i32 undef>290  ret <3 x i8> %r291}292 293define <3 x i8> @shuf_ashr_const_op0(<3 x i8> %x) {294; CHECK-LABEL: @shuf_ashr_const_op0(295; CHECK-NEXT:    [[BO:%.*]] = lshr <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]296; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 0, i32 poison, i32 1>297; CHECK-NEXT:    ret <3 x i8> [[R]]298;299  %bo = ashr <3 x i8> <i8 1, i8 2, i8 3>, %x300  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 0, i32 undef, i32 1>301  ret <3 x i8> %r302}303 304define <3 x i8> @shuf_ashr_const_op1(<3 x i8> %x) {305; CHECK-LABEL: @shuf_ashr_const_op1(306; CHECK-NEXT:    [[BO:%.*]] = ashr exact <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>307; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 0, i32 poison, i32 1>308; CHECK-NEXT:    ret <3 x i8> [[R]]309;310  %bo = ashr exact <3 x i8> %x, <i8 1, i8 2, i8 3>311  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 0, i32 undef, i32 1>312  ret <3 x i8> %r313}314 315define <3 x i8> @shuf_shl_const_op0(<3 x i8> %x) {316; CHECK-LABEL: @shuf_shl_const_op0(317; CHECK-NEXT:    [[BO:%.*]] = shl nsw <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]318; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 poison, i32 0>319; CHECK-NEXT:    ret <3 x i8> [[R]]320;321  %bo = shl nsw <3 x i8> <i8 1, i8 2, i8 3>, %x322  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 undef, i32 0>323  ret <3 x i8> %r324}325 326define <3 x i8> @shuf_shl_const_op1(<3 x i8> %x) {327; CHECK-LABEL: @shuf_shl_const_op1(328; CHECK-NEXT:    [[BO:%.*]] = shl nuw <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>329; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 poison, i32 0>330; CHECK-NEXT:    ret <3 x i8> [[R]]331;332  %bo = shl nuw <3 x i8> %x, <i8 1, i8 2, i8 3>333  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 undef, i32 0>334  ret <3 x i8> %r335}336 337define <3 x i8> @shuf_sdiv_const_op0(<3 x i8> %x) {338; CHECK-LABEL: @shuf_sdiv_const_op0(339; CHECK-NEXT:    [[BO:%.*]] = sdiv exact <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]340; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 0, i32 poison, i32 1>341; CHECK-NEXT:    ret <3 x i8> [[R]]342;343  %bo = sdiv exact <3 x i8> <i8 1, i8 2, i8 3>, %x344  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 0, i32 undef, i32 1>345  ret <3 x i8> %r346}347 348define <3 x i8> @shuf_sdiv_const_op1(<3 x i8> %x) {349; CHECK-LABEL: @shuf_sdiv_const_op1(350; CHECK-NEXT:    [[BO:%.*]] = sdiv <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>351; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 1, i32 poison, i32 0>352; CHECK-NEXT:    ret <3 x i8> [[R]]353;354  %bo = sdiv <3 x i8> %x, <i8 1, i8 2, i8 3>355  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 1, i32 undef, i32 0>356  ret <3 x i8> %r357}358 359define <3 x i8> @shuf_srem_const_op0(<3 x i8> %x) {360; CHECK-LABEL: @shuf_srem_const_op0(361; CHECK-NEXT:    [[BO:%.*]] = srem <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]362; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 1, i32 poison, i32 2>363; CHECK-NEXT:    ret <3 x i8> [[R]]364;365  %bo = srem <3 x i8> <i8 1, i8 2, i8 3>, %x366  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 1, i32 undef, i32 2>367  ret <3 x i8> %r368}369 370define <3 x i8> @shuf_srem_const_op1(<3 x i8> %x) {371; CHECK-LABEL: @shuf_srem_const_op1(372; CHECK-NEXT:    [[BO:%.*]] = srem <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>373; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 poison, i32 1>374; CHECK-NEXT:    ret <3 x i8> [[R]]375;376  %bo = srem <3 x i8> %x, <i8 1, i8 2, i8 3>377  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 undef, i32 1>378  ret <3 x i8> %r379}380 381define <3 x i8> @shuf_udiv_const_op0(<3 x i8> %x) {382; CHECK-LABEL: @shuf_udiv_const_op0(383; CHECK-NEXT:    [[BO:%.*]] = udiv exact <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]384; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 poison, i32 0>385; CHECK-NEXT:    ret <3 x i8> [[R]]386;387  %bo = udiv exact <3 x i8> <i8 1, i8 2, i8 3>, %x388  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 undef, i32 0>389  ret <3 x i8> %r390}391 392define <3 x i8> @shuf_udiv_const_op1(<3 x i8> %x) {393; CHECK-LABEL: @shuf_udiv_const_op1(394; CHECK-NEXT:    [[BO:%.*]] = udiv <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>395; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 poison, i32 0>396; CHECK-NEXT:    ret <3 x i8> [[R]]397;398  %bo = udiv <3 x i8> %x, <i8 1, i8 2, i8 3>399  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 undef, i32 0>400  ret <3 x i8> %r401}402 403define <3 x i8> @shuf_urem_const_op0(<3 x i8> %x) {404; CHECK-LABEL: @shuf_urem_const_op0(405; CHECK-NEXT:    [[BO:%.*]] = urem <3 x i8> <i8 1, i8 2, i8 3>, [[X:%.*]]406; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 2, i32 1, i32 poison>407; CHECK-NEXT:    ret <3 x i8> [[R]]408;409  %bo = urem <3 x i8> <i8 1, i8 2, i8 3>, %x410  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 2, i32 1, i32 undef>411  ret <3 x i8> %r412}413 414define <3 x i8> @shuf_urem_const_op1(<3 x i8> %x) {415; CHECK-LABEL: @shuf_urem_const_op1(416; CHECK-NEXT:    [[BO:%.*]] = urem <3 x i8> [[X:%.*]], <i8 1, i8 2, i8 3>417; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x i8> [[BO]], <3 x i8> poison, <3 x i32> <i32 poison, i32 1, i32 0>418; CHECK-NEXT:    ret <3 x i8> [[R]]419;420  %bo = urem <3 x i8> %x, <i8 1, i8 2, i8 3>421  %r = shufflevector <3 x i8> %bo, <3 x i8> poison, <3 x i32> <i32 undef, i32 1, i32 0>422  ret <3 x i8> %r423}424 425define <3 x float> @shuf_fadd(<3 x float> %x) {426; CHECK-LABEL: @shuf_fadd(427; CHECK-NEXT:    [[BO:%.*]] = fadd <3 x float> [[X:%.*]], <float 1.000000e+00, float 2.000000e+00, float poison>428; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 poison, i32 1, i32 0>429; CHECK-NEXT:    ret <3 x float> [[R]]430;431  %bo = fadd <3 x float> %x, <float 1.0, float 2.0, float 3.0>432  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 undef, i32 1, i32 0>433  ret <3 x float> %r434}435 436define <3 x float> @shuf_fsub(<3 x float> %x) {437; CHECK-LABEL: @shuf_fsub(438; CHECK-NEXT:    [[BO:%.*]] = fsub fast <3 x float> <float 1.000000e+00, float poison, float 3.000000e+00>, [[X:%.*]]439; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 poison, i32 0, i32 2>440; CHECK-NEXT:    ret <3 x float> [[R]]441;442  %bo = fsub fast <3 x float> <float 1.0, float 2.0, float 3.0>, %x443  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 undef, i32 0, i32 2>444  ret <3 x float> %r445}446 447define <3 x float> @shuf_fmul(<3 x float> %x) {448; CHECK-LABEL: @shuf_fmul(449; CHECK-NEXT:    [[BO:%.*]] = fmul reassoc <3 x float> [[X:%.*]], <float 1.000000e+00, float 2.000000e+00, float poison>450; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 poison, i32 1, i32 0>451; CHECK-NEXT:    ret <3 x float> [[R]]452;453  %bo = fmul reassoc <3 x float> %x, <float 1.0, float 2.0, float 3.0>454  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 undef, i32 1, i32 0>455  ret <3 x float> %r456}457 458define <3 x float> @shuf_fdiv_const_op0(<3 x float> %x) {459; CHECK-LABEL: @shuf_fdiv_const_op0(460; CHECK-NEXT:    [[BO:%.*]] = fdiv reassoc ninf <3 x float> <float 1.000000e+00, float poison, float 3.000000e+00>, [[X:%.*]]461; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 poison, i32 0, i32 2>462; CHECK-NEXT:    ret <3 x float> [[R]]463;464  %bo = fdiv ninf reassoc <3 x float> <float 1.0, float 2.0, float 3.0>, %x465  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 undef, i32 0, i32 2>466  ret <3 x float> %r467}468 469define <3 x float> @shuf_fdiv_const_op1(<3 x float> %x) {470; CHECK-LABEL: @shuf_fdiv_const_op1(471; CHECK-NEXT:    [[BO:%.*]] = fdiv nnan ninf <3 x float> [[X:%.*]], <float 1.000000e+00, float 2.000000e+00, float poison>472; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 poison, i32 1, i32 0>473; CHECK-NEXT:    ret <3 x float> [[R]]474;475  %bo = fdiv ninf nnan <3 x float> %x, <float 1.0, float 2.0, float 3.0>476  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 undef, i32 1, i32 0>477  ret <3 x float> %r478}479 480define <3 x float> @shuf_frem_const_op0(<3 x float> %x) {481; CHECK-LABEL: @shuf_frem_const_op0(482; CHECK-NEXT:    [[BO:%.*]] = frem nnan <3 x float> <float 1.000000e+00, float poison, float 3.000000e+00>, [[X:%.*]]483; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 poison, i32 2, i32 0>484; CHECK-NEXT:    ret <3 x float> [[R]]485;486  %bo = frem nnan <3 x float> <float 1.0, float 2.0, float 3.0>, %x487  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 undef, i32 2, i32 0>488  ret <3 x float> %r489}490 491define <3 x float> @shuf_frem_const_op1(<3 x float> %x) {492; CHECK-LABEL: @shuf_frem_const_op1(493; CHECK-NEXT:    [[BO:%.*]] = frem reassoc ninf <3 x float> [[X:%.*]], <float poison, float 2.000000e+00, float 3.000000e+00>494; CHECK-NEXT:    [[R:%.*]] = shufflevector <3 x float> [[BO]], <3 x float> poison, <3 x i32> <i32 1, i32 poison, i32 2>495; CHECK-NEXT:    ret <3 x float> [[R]]496;497  %bo = frem ninf reassoc <3 x float> %x, <float 1.0, float 2.0, float 3.0>498  %r = shufflevector <3 x float> %bo, <3 x float> poison, <3 x i32> <i32 1, i32 undef, i32 2>499  ret <3 x float> %r500}501 502define ptr @gep_vbase_w_s_idx(<2 x ptr> %base, i64 %index) {503; CHECK-LABEL: @gep_vbase_w_s_idx(504; CHECK-NEXT:    [[TMP1:%.*]] = extractelement <2 x ptr> [[BASE:%.*]], i64 1505; CHECK-NEXT:    [[EE:%.*]] = getelementptr i32, ptr [[TMP1]], i64 [[INDEX:%.*]]506; CHECK-NEXT:    ret ptr [[EE]]507;508  %gep = getelementptr i32, <2 x ptr> %base, i64 %index509  %ee = extractelement <2 x ptr> %gep, i32 1510  ret ptr %ee511}512 513define ptr @gep_splat_base_w_s_idx(ptr %base) {514; CHECK-LABEL: @gep_splat_base_w_s_idx(515; CHECK-NEXT:    [[EE:%.*]] = getelementptr i8, ptr [[BASE:%.*]], i64 4516; CHECK-NEXT:    ret ptr [[EE]]517;518  %basevec1 = insertelement <2 x ptr> poison, ptr %base, i32 0519  %basevec2 = shufflevector <2 x ptr> %basevec1, <2 x ptr> poison, <2 x i32> zeroinitializer520  %gep = getelementptr i32, <2 x ptr> %basevec2, i64 1521  %ee = extractelement <2 x ptr> %gep, i32 1522  ret ptr %ee523}524 525 526define ptr @gep_splat_base_w_cv_idx(ptr %base) {527; CHECK-LABEL: @gep_splat_base_w_cv_idx(528; CHECK-NEXT:    [[EE:%.*]] = getelementptr i8, ptr [[BASE:%.*]], i64 4529; CHECK-NEXT:    ret ptr [[EE]]530;531  %basevec1 = insertelement <2 x ptr> poison, ptr %base, i32 0532  %basevec2 = shufflevector <2 x ptr> %basevec1, <2 x ptr> poison, <2 x i32> zeroinitializer533  %gep = getelementptr i32, <2 x ptr> %basevec2, <2 x i64> <i64 0, i64 1>534  %ee = extractelement <2 x ptr> %gep, i32 1535  ret ptr %ee536}537 538define ptr @gep_splat_base_w_vidx(ptr %base, <2 x i64> %idxvec) {539; CHECK-LABEL: @gep_splat_base_w_vidx(540; CHECK-NEXT:    [[TMP1:%.*]] = extractelement <2 x i64> [[IDXVEC:%.*]], i64 1541; CHECK-NEXT:    [[EE:%.*]] = getelementptr i32, ptr [[BASE:%.*]], i64 [[TMP1]]542; CHECK-NEXT:    ret ptr [[EE]]543;544  %basevec1 = insertelement <2 x ptr> poison, ptr %base, i32 0545  %basevec2 = shufflevector <2 x ptr> %basevec1, <2 x ptr> poison, <2 x i32> zeroinitializer546  %gep = getelementptr i32, <2 x ptr> %basevec2, <2 x i64> %idxvec547  %ee = extractelement <2 x ptr> %gep, i32 1548  ret ptr %ee549}550 551 552@GLOBAL = internal global i32 zeroinitializer553 554define ptr @gep_cvbase_w_s_idx(<2 x ptr> %base, i64 %raw_addr) {555; CHECK-LABEL: @gep_cvbase_w_s_idx(556; CHECK-NEXT:    [[EE:%.*]] = getelementptr i32, ptr @GLOBAL, i64 [[RAW_ADDR:%.*]]557; CHECK-NEXT:    ret ptr [[EE]]558;559  %gep = getelementptr i32, <2 x ptr> <ptr @GLOBAL, ptr @GLOBAL>, i64 %raw_addr560  %ee = extractelement <2 x ptr> %gep, i32 1561  ret ptr %ee562}563 564define ptr @gep_cvbase_w_cv_idx(<2 x ptr> %base, i64 %raw_addr) {565; CHECK-LABEL: @gep_cvbase_w_cv_idx(566; CHECK-NEXT:    ret ptr getelementptr inbounds nuw (i8, ptr @GLOBAL, i64 4)567;568  %gep = getelementptr i32, <2 x ptr> <ptr @GLOBAL, ptr @GLOBAL>, <2 x i64> <i64 0, i64 1>569  %ee = extractelement <2 x ptr> %gep, i32 1570  ret ptr %ee571}572 573 574define ptr @gep_sbase_w_cv_idx(ptr %base) {575; CHECK-LABEL: @gep_sbase_w_cv_idx(576; CHECK-NEXT:    [[EE:%.*]] = getelementptr i8, ptr [[BASE:%.*]], i64 4577; CHECK-NEXT:    ret ptr [[EE]]578;579  %gep = getelementptr i32, ptr %base, <2 x i64> <i64 0, i64 1>580  %ee = extractelement <2 x ptr> %gep, i32 1581  ret ptr %ee582}583 584define ptr @gep_sbase_w_splat_idx(ptr %base, i64 %idx) {585; CHECK-LABEL: @gep_sbase_w_splat_idx(586; CHECK-NEXT:    [[EE:%.*]] = getelementptr i32, ptr [[BASE:%.*]], i64 [[IDX:%.*]]587; CHECK-NEXT:    ret ptr [[EE]]588;589  %idxvec1 = insertelement <2 x i64> poison, i64 %idx, i32 0590  %idxvec2 = shufflevector <2 x i64> %idxvec1, <2 x i64> poison, <2 x i32> zeroinitializer591  %gep = getelementptr i32, ptr %base, <2 x i64> %idxvec2592  %ee = extractelement <2 x ptr> %gep, i32 1593  ret ptr %ee594}595define ptr @gep_splat_both(ptr %base, i64 %idx) {596; CHECK-LABEL: @gep_splat_both(597; CHECK-NEXT:    [[EE:%.*]] = getelementptr i32, ptr [[BASE:%.*]], i64 [[IDX:%.*]]598; CHECK-NEXT:    ret ptr [[EE]]599;600  %basevec1 = insertelement <2 x ptr> poison, ptr %base, i32 0601  %basevec2 = shufflevector <2 x ptr> %basevec1, <2 x ptr> poison, <2 x i32> zeroinitializer602  %idxvec1 = insertelement <2 x i64> poison, i64 %idx, i32 0603  %idxvec2 = shufflevector <2 x i64> %idxvec1, <2 x i64> poison, <2 x i32> zeroinitializer604  %gep = getelementptr i32, <2 x ptr> %basevec2, <2 x i64> %idxvec2605  %ee = extractelement <2 x ptr> %gep, i32 1606  ret ptr %ee607}608 609define <2 x ptr> @gep_all_lanes_undef(ptr %base, i64 %idx) {;610; CHECK-LABEL: @gep_all_lanes_undef(611; CHECK-NEXT:    [[BASEVEC:%.*]] = insertelement <2 x ptr> poison, ptr [[BASE:%.*]], i64 0612; CHECK-NEXT:    [[IDXVEC:%.*]] = insertelement <2 x i64> poison, i64 [[IDX:%.*]], i64 1613; CHECK-NEXT:    [[GEP:%.*]] = getelementptr i32, <2 x ptr> [[BASEVEC]], <2 x i64> [[IDXVEC]]614; CHECK-NEXT:    ret <2 x ptr> [[GEP]]615;616  %basevec = insertelement <2 x ptr> poison, ptr %base, i32 0617  %idxvec = insertelement <2 x i64> poison, i64 %idx, i32 1618  %gep = getelementptr i32, <2 x ptr> %basevec, <2 x i64> %idxvec619  ret <2 x ptr> %gep620}621 622define ptr @gep_demanded_lane_undef(ptr %base, i64 %idx) {623; CHECK-LABEL: @gep_demanded_lane_undef(624; CHECK-NEXT:    ret ptr poison625;626  %basevec = insertelement <2 x ptr> poison, ptr %base, i32 0627  %idxvec = insertelement <2 x i64> poison, i64 %idx, i32 1628  %gep = getelementptr i32, <2 x ptr> %basevec, <2 x i64> %idxvec629  %ee = extractelement <2 x ptr> %gep, i32 1630  ret ptr %ee631}632 633 634;; LangRef has an odd quirk around FCAs which make it illegal to use undef635;; indices.636define ptr @PR41624(<2 x ptr> %a) {637; CHECK-LABEL: @PR41624(638; CHECK-NEXT:    [[R:%.*]] = extractelement <2 x ptr> [[W:%.*]], i64 0639; CHECK-NEXT:    [[R1:%.*]] = getelementptr i8, ptr [[R]], i64 40640; CHECK-NEXT:    ret ptr [[R1]]641;642  %w = getelementptr { i32, i32 }, <2 x ptr> %a, <2 x i64> <i64 5, i64 5>, <2 x i32> zeroinitializer643  %r = extractelement <2 x ptr> %w, i32 0644  ret ptr %r645}646 647@global = external global [0 x i32], align 4648 649; Make sure we don't get stuck in a loop turning the zeroinitializer into650; <0, undef, undef, undef> and then changing it back.651define ptr @zero_sized_type_extract(<4 x i64> %arg, i64 %arg1) {652; CHECK-LABEL: @zero_sized_type_extract(653; CHECK-NEXT:  bb:654; CHECK-NEXT:    [[TMP0:%.*]] = extractelement <4 x i64> [[ARG:%.*]], i64 0655; CHECK-NEXT:    [[T2:%.*]] = getelementptr inbounds i32, ptr @global, i64 [[TMP0]]656; CHECK-NEXT:    ret ptr [[T2]]657;658bb:659  %t = getelementptr inbounds [0 x i32], <4 x ptr> <ptr @global, ptr @global, ptr @global, ptr @global>, <4 x i64> zeroinitializer, <4 x i64> %arg660  %t2 = extractelement <4 x ptr> %t, i64 0661  ret ptr %t2662}663 664; The non-zero elements of the result are always 'y', so the splat is unnecessary.665 666define <4 x i8> @select_cond_with_eq_true_false_elts(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {667; CHECK-LABEL: @select_cond_with_eq_true_false_elts(668; CHECK-NEXT:    [[SEL:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]]669; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x i8> [[SEL]], <4 x i8> [[Y]], <4 x i32> <i32 0, i32 5, i32 6, i32 7>670; CHECK-NEXT:    ret <4 x i8> [[R]]671;672  %tval = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 6, i32 7>673  %splat = shufflevector <4 x i1> %cmp, <4 x i1> poison, <4 x i32> zeroinitializer674  %r = select <4 x i1> %splat, <4 x i8> %tval, <4 x i8> %y675  ret <4 x i8> %r676}677 678; First element of the result is always x[0], so first element of select condition is unnecessary.679 680define <4 x i8> @select_cond_with_eq_true_false_elts2(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {681; CHECK-LABEL: @select_cond_with_eq_true_false_elts2(682; CHECK-NEXT:    [[COND:%.*]] = shufflevector <4 x i1> [[CMP:%.*]], <4 x i1> poison, <4 x i32> <i32 poison, i32 1, i32 0, i32 1>683; CHECK-NEXT:    [[SEL:%.*]] = select <4 x i1> [[COND]], <4 x i8> [[Y:%.*]], <4 x i8> [[X:%.*]]684; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x i8> [[X]], <4 x i8> [[SEL]], <4 x i32> <i32 0, i32 5, i32 6, i32 7>685; CHECK-NEXT:    ret <4 x i8> [[R]]686;687  %tval = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 6, i32 7>688  %cond = shufflevector <4 x i1> %cmp, <4 x i1> poison, <4 x i32> <i32 0, i32 1, i32 0, i32 1>689  %r = select <4 x i1> %cond, <4 x i8> %tval, <4 x i8> %x690  ret <4 x i8> %r691}692 693; Second element of the result is always x[3], so second element of select condition is unnecessary.694; Fourth element of the result is always undef, so fourth element of select condition is unnecessary.695 696define <4 x float> @select_cond_with_eq_true_false_elts3(<4 x float> %x, <4 x float> %y, <4 x i1> %cmp) {697; CHECK-LABEL: @select_cond_with_eq_true_false_elts3(698; CHECK-NEXT:    [[TVAL:%.*]] = shufflevector <4 x float> [[X:%.*]], <4 x float> [[Y:%.*]], <4 x i32> <i32 1, i32 3, i32 5, i32 poison>699; CHECK-NEXT:    [[FVAL:%.*]] = shufflevector <4 x float> [[Y]], <4 x float> [[X]], <4 x i32> <i32 0, i32 7, i32 6, i32 poison>700; CHECK-NEXT:    [[COND:%.*]] = shufflevector <4 x i1> [[CMP:%.*]], <4 x i1> poison, <4 x i32> <i32 poison, i32 1, i32 2, i32 3>701; CHECK-NEXT:    [[R:%.*]] = select <4 x i1> [[COND]], <4 x float> [[TVAL]], <4 x float> [[FVAL]]702; CHECK-NEXT:    ret <4 x float> [[R]]703;704  %tval = shufflevector <4 x float> %x, <4 x float> %y, <4 x i32> <i32 1, i32 3, i32 5, i32 undef>705  %fval = shufflevector <4 x float> %y, <4 x float> %x, <4 x i32> <i32 0, i32 7, i32 6, i32 undef>706  %cond = shufflevector <4 x i1> %cmp, <4 x i1> poison, <4 x i32> <i32 undef, i32 1, i32 2, i32 3>707  %r = select <4 x i1> %cond, <4 x float> %tval, <4 x float> %fval708  ret <4 x float> %r709}710 711define <4 x i8> @select_cond_with_undef_true_false_elts(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {712; CHECK-LABEL: @select_cond_with_undef_true_false_elts(713; CHECK-NEXT:    [[TVAL:%.*]] = shufflevector <4 x i8> [[Y:%.*]], <4 x i8> poison, <4 x i32> <i32 poison, i32 1, i32 2, i32 3>714; CHECK-NEXT:    [[COND:%.*]] = shufflevector <4 x i1> [[CMP:%.*]], <4 x i1> poison, <4 x i32> <i32 0, i32 1, i32 0, i32 1>715; CHECK-NEXT:    [[R:%.*]] = select <4 x i1> [[COND]], <4 x i8> [[TVAL]], <4 x i8> [[X:%.*]]716; CHECK-NEXT:    ret <4 x i8> [[R]]717;718  %tval = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 undef, i32 5, i32 6, i32 7>719  %cond = shufflevector <4 x i1> %cmp, <4 x i1> poison, <4 x i32> <i32 0, i32 1, i32 0, i32 1>720  %r = select <4 x i1> %cond, <4 x i8> %tval, <4 x i8> %x721  ret <4 x i8> %r722}723 724; The insert can be safely eliminated because the shuffle blocks poison from cmp[0].725 726define <4 x i8> @select_cond_(<4 x i8> %x, <4 x i8> %min, <4 x i1> %cmp, i1 %poison_blocker) {727; CHECK-LABEL: @select_cond_(728; CHECK-NEXT:    [[SEL:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[MIN:%.*]], <4 x i8> [[X:%.*]]729; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x i8> [[X]], <4 x i8> [[SEL]], <4 x i32> <i32 0, i32 5, i32 6, i32 7>730; CHECK-NEXT:    ret <4 x i8> [[R]]731;732  %ins = insertelement <4 x i1> %cmp, i1 %poison_blocker, i32 0733  %vecins = shufflevector <4 x i8> %x, <4 x i8> %min, <4 x i32> <i32 0, i32 5, i32 6, i32 7>734  %r = select <4 x i1> %ins, <4 x i8> %vecins, <4 x i8> %x735  ret <4 x i8> %r736}737 738define <4 x float> @ins_of_ext(<4 x float> %x, float %y) {739; CHECK-LABEL: @ins_of_ext(740; CHECK-NEXT:    [[I1:%.*]] = insertelement <4 x float> [[X:%.*]], float [[Y:%.*]], i64 1741; CHECK-NEXT:    [[I2:%.*]] = insertelement <4 x float> [[I1]], float [[Y]], i64 2742; CHECK-NEXT:    [[I3:%.*]] = insertelement <4 x float> [[I2]], float [[Y]], i64 3743; CHECK-NEXT:    ret <4 x float> [[I3]]744;745  %e0 = extractelement <4 x float> %x, i32 0746  %i0 = insertelement <4 x float> poison, float %e0, i32 0747  %i1 = insertelement <4 x float> %i0, float %y, i32 1748  %i2 = insertelement <4 x float> %i1, float %y, i32 2749  %i3 = insertelement <4 x float> %i2, float %y, i32 3750  ret <4 x float> %i3751}752 753define <4 x float> @ins_of_ext_twice(<4 x float> %x, float %y) {754; CHECK-LABEL: @ins_of_ext_twice(755; CHECK-NEXT:    [[I2:%.*]] = insertelement <4 x float> [[X:%.*]], float [[Y:%.*]], i64 2756; CHECK-NEXT:    [[I3:%.*]] = insertelement <4 x float> [[I2]], float [[Y]], i64 3757; CHECK-NEXT:    ret <4 x float> [[I3]]758;759  %e0 = extractelement <4 x float> %x, i32 0760  %i0 = insertelement <4 x float> poison, float %e0, i32 0761  %e1 = extractelement <4 x float> %x, i32 1762  %i1 = insertelement <4 x float> %i0, float %e1, i32 1763  %i2 = insertelement <4 x float> %i1, float %y, i32 2764  %i3 = insertelement <4 x float> %i2, float %y, i32 3765  ret <4 x float> %i3766}767 768; Negative test - element 3 of the result must be undef to be poison safe.769; TODO: Could convert insert/extract to identity shuffle with undef mask elements.770 771define <4 x float> @ins_of_ext_wrong_demand(<4 x float> %x, float %y) {772; CHECK-LABEL: @ins_of_ext_wrong_demand(773; CHECK-NEXT:    [[E0:%.*]] = extractelement <4 x float> [[X:%.*]], i64 0774; CHECK-NEXT:    [[I0:%.*]] = insertelement <4 x float> poison, float [[E0]], i64 0775; CHECK-NEXT:    [[I1:%.*]] = insertelement <4 x float> [[I0]], float [[Y:%.*]], i64 1776; CHECK-NEXT:    [[I2:%.*]] = insertelement <4 x float> [[I1]], float [[Y]], i64 2777; CHECK-NEXT:    ret <4 x float> [[I2]]778;779  %e0 = extractelement <4 x float> %x, i32 0780  %i0 = insertelement <4 x float> poison, float %e0, i32 0781  %i1 = insertelement <4 x float> %i0, float %y, i32 1782  %i2 = insertelement <4 x float> %i1, float %y, i32 2783  ret <4 x float> %i2784}785 786; Negative test - can't replace i0 with x.787; TODO: Could convert insert/extract to identity shuffle with undef mask elements.788 789define <4 x float> @ins_of_ext_wrong_type(<5 x float> %x, float %y) {790; CHECK-LABEL: @ins_of_ext_wrong_type(791; CHECK-NEXT:    [[E0:%.*]] = extractelement <5 x float> [[X:%.*]], i64 0792; CHECK-NEXT:    [[I0:%.*]] = insertelement <4 x float> poison, float [[E0]], i64 0793; CHECK-NEXT:    [[I1:%.*]] = insertelement <4 x float> [[I0]], float [[Y:%.*]], i64 1794; CHECK-NEXT:    [[I2:%.*]] = insertelement <4 x float> [[I1]], float [[Y]], i64 2795; CHECK-NEXT:    [[I3:%.*]] = insertelement <4 x float> [[I2]], float [[Y]], i64 3796; CHECK-NEXT:    ret <4 x float> [[I3]]797;798  %e0 = extractelement <5 x float> %x, i32 0799  %i0 = insertelement <4 x float> poison, float %e0, i32 0800  %i1 = insertelement <4 x float> %i0, float %y, i32 1801  %i2 = insertelement <4 x float> %i1, float %y, i32 2802  %i3 = insertelement <4 x float> %i2, float %y, i32 3803  ret <4 x float> %i3804}805 806; This should reduce, but the shuffle mask must remain as-is (no extra undef).807 808define <4 x i4> @ins_of_ext_undef_elts_propagation(<4 x i4> %v, <4 x i4> %v2, i4 %x) {809; CHECK-LABEL: @ins_of_ext_undef_elts_propagation(810; CHECK-NEXT:    [[T2:%.*]] = insertelement <4 x i4> [[V:%.*]], i4 [[X:%.*]], i64 2811; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x i4> [[T2]], <4 x i4> [[V2:%.*]], <4 x i32> <i32 0, i32 6, i32 2, i32 7>812; CHECK-NEXT:    ret <4 x i4> [[R]]813;814  %v0 = extractelement <4 x i4> %v, i32 0815  %t0 = insertelement <4 x i4> poison, i4 %v0, i32 0816  %t2 = insertelement <4 x i4> %t0, i4 %x, i32 2817  %r = shufflevector <4 x i4> %t2, <4 x i4> %v2, <4 x i32> <i32 0, i32 6, i32 2, i32 7>818  ret <4 x i4> %r819}820 821; Similar to above, but more ops/uses to verify things work in more complicated cases.822 823define <8 x i4> @ins_of_ext_undef_elts_propagation2(<8 x i4> %v, <8 x i4> %v2, i4 %x) {824; CHECK-LABEL: @ins_of_ext_undef_elts_propagation2(825; CHECK-NEXT:    [[I19:%.*]] = insertelement <8 x i4> [[V:%.*]], i4 [[X:%.*]], i64 2826; CHECK-NEXT:    [[I20:%.*]] = shufflevector <8 x i4> [[I19]], <8 x i4> [[V2:%.*]], <8 x i32> <i32 0, i32 1, i32 2, i32 11, i32 10, i32 9, i32 8, i32 poison>827; CHECK-NEXT:    [[I21:%.*]] = shufflevector <8 x i4> [[I20]], <8 x i4> [[V]], <8 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 15>828; CHECK-NEXT:    ret <8 x i4> [[I21]]829;830  %i15 = extractelement <8 x i4> %v, i32 0831  %i16 = insertelement <8 x i4> poison, i4 %i15, i32 0832  %i17 = extractelement <8 x i4> %v, i32 1833  %i18 = insertelement <8 x i4> %i16, i4 %i17, i32 1834  %i19 = insertelement <8 x i4> %i18, i4 %x, i32 2835  %i20 = shufflevector <8 x i4> %i19, <8 x i4> %v2, <8 x i32> <i32 0, i32 1, i32 2, i32 11, i32 10, i32 9, i32 8, i32 undef>836  %i21 = shufflevector <8 x i4> %i20, <8 x i4> %v, <8 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 15>837  ret <8 x i4> %i21838}839