902 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 52; RUN: opt -S -passes=aggressive-instcombine -mtriple=x86_64-unknown-linux-gnu < %s | FileCheck %s3 4declare void @use.i16(i16)5declare void @use.i32(i32)6 7define void @test_i16(i16 %x, ptr %p) {8; CHECK-LABEL: define void @test_i16(9; CHECK-SAME: i16 [[X:%.*]], ptr [[P:%.*]]) {10; CHECK-NEXT: store i16 [[X]], ptr [[P]], align 111; CHECK-NEXT: ret void12;13 %x.0 = trunc i16 %x to i814 store i8 %x.0, ptr %p15 %shr.1 = lshr i16 %x, 816 %x.1 = trunc i16 %shr.1 to i817 %gep.1 = getelementptr i8, ptr %p, i64 118 store i8 %x.1, ptr %gep.119 ret void20}21 22define void @test_i32_i8_parts(i32 %x, ptr %p) {23; CHECK-LABEL: define void @test_i32_i8_parts(24; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {25; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 126; CHECK-NEXT: ret void27;28 %x.0 = trunc i32 %x to i829 store i8 %x.0, ptr %p30 %shr.1 = lshr i32 %x, 831 %x.1 = trunc i32 %shr.1 to i832 %gep.1 = getelementptr i8, ptr %p, i64 133 store i8 %x.1, ptr %gep.134 %shr.2 = lshr i32 %x, 1635 %x.2 = trunc i32 %shr.2 to i836 %gep.2 = getelementptr i8, ptr %p, i64 237 store i8 %x.2, ptr %gep.238 %shr.3 = lshr i32 %x, 2439 %x.3 = trunc i32 %shr.3 to i840 %gep.3 = getelementptr i8, ptr %p, i64 341 store i8 %x.3, ptr %gep.342 ret void43}44 45define void @test_i32_i16_parts(i32 %x, ptr %p) {46; CHECK-LABEL: define void @test_i32_i16_parts(47; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {48; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 249; CHECK-NEXT: ret void50;51 %x.0 = trunc i32 %x to i1652 store i16 %x.0, ptr %p53 %shr.1 = lshr i32 %x, 1654 %x.1 = trunc i32 %shr.1 to i1655 %gep.1 = getelementptr i8, ptr %p, i64 256 store i16 %x.1, ptr %gep.157 ret void58}59 60define void @test_i32_mixed_parts(i32 %x, ptr %p) {61; CHECK-LABEL: define void @test_i32_mixed_parts(62; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {63; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 164; CHECK-NEXT: ret void65;66 %x.0 = trunc i32 %x to i867 store i8 %x.0, ptr %p68 %shr.1 = lshr i32 %x, 869 %x.1 = trunc i32 %shr.1 to i1670 %gep.1 = getelementptr i8, ptr %p, i64 171 store i16 %x.1, ptr %gep.172 %shr.3 = lshr i32 %x, 2473 %x.3 = trunc i32 %shr.3 to i874 %gep.3 = getelementptr i8, ptr %p, i64 375 store i8 %x.3, ptr %gep.376 ret void77}78 79define void @test_i64(i64 %x, ptr %p) {80; CHECK-LABEL: define void @test_i64(81; CHECK-SAME: i64 [[X:%.*]], ptr [[P:%.*]]) {82; CHECK-NEXT: store i64 [[X]], ptr [[P]], align 183; CHECK-NEXT: ret void84;85 %x.0 = trunc i64 %x to i886 store i8 %x.0, ptr %p87 %shr.1 = lshr i64 %x, 888 %x.1 = trunc i64 %shr.1 to i889 %gep.1 = getelementptr i8, ptr %p, i64 190 store i8 %x.1, ptr %gep.191 %shr.2 = lshr i64 %x, 1692 %x.2 = trunc i64 %shr.2 to i893 %gep.2 = getelementptr i8, ptr %p, i64 294 store i8 %x.2, ptr %gep.295 %shr.3 = lshr i64 %x, 2496 %x.3 = trunc i64 %shr.3 to i897 %gep.3 = getelementptr i8, ptr %p, i64 398 store i8 %x.3, ptr %gep.399 %shr.4 = lshr i64 %x, 32100 %x.4 = trunc i64 %shr.4 to i8101 %gep.4 = getelementptr i8, ptr %p, i64 4102 store i8 %x.4, ptr %gep.4103 %shr.5 = lshr i64 %x, 40104 %x.5 = trunc i64 %shr.5 to i8105 %gep.5 = getelementptr i8, ptr %p, i64 5106 store i8 %x.5, ptr %gep.5107 %shr.6 = lshr i64 %x, 48108 %x.6 = trunc i64 %shr.6 to i8109 %gep.6 = getelementptr i8, ptr %p, i64 6110 store i8 %x.6, ptr %gep.6111 %shr.7 = lshr i64 %x, 56112 %x.7 = trunc i64 %shr.7 to i8113 %gep.7 = getelementptr i8, ptr %p, i64 7114 store i8 %x.7, ptr %gep.7115 ret void116}117 118define void @test_i128(i128 %x, ptr %p) {119; CHECK-LABEL: define void @test_i128(120; CHECK-SAME: i128 [[X:%.*]], ptr [[P:%.*]]) {121; CHECK-NEXT: [[X_0:%.*]] = trunc i128 [[X]] to i8122; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1123; CHECK-NEXT: [[SHR_1:%.*]] = lshr i128 [[X]], 8124; CHECK-NEXT: [[X_1:%.*]] = trunc i128 [[SHR_1]] to i8125; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1126; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1127; CHECK-NEXT: [[SHR_2:%.*]] = lshr i128 [[X]], 16128; CHECK-NEXT: [[X_2:%.*]] = trunc i128 [[SHR_2]] to i8129; CHECK-NEXT: [[GEP_2:%.*]] = getelementptr i8, ptr [[P]], i64 2130; CHECK-NEXT: store i8 [[X_2]], ptr [[GEP_2]], align 1131; CHECK-NEXT: [[SHR_3:%.*]] = lshr i128 [[X]], 24132; CHECK-NEXT: [[X_3:%.*]] = trunc i128 [[SHR_3]] to i8133; CHECK-NEXT: [[GEP_3:%.*]] = getelementptr i8, ptr [[P]], i64 3134; CHECK-NEXT: store i8 [[X_3]], ptr [[GEP_3]], align 1135; CHECK-NEXT: [[SHR_4:%.*]] = lshr i128 [[X]], 32136; CHECK-NEXT: [[X_4:%.*]] = trunc i128 [[SHR_4]] to i8137; CHECK-NEXT: [[GEP_4:%.*]] = getelementptr i8, ptr [[P]], i64 4138; CHECK-NEXT: store i8 [[X_4]], ptr [[GEP_4]], align 1139; CHECK-NEXT: [[SHR_5:%.*]] = lshr i128 [[X]], 40140; CHECK-NEXT: [[X_5:%.*]] = trunc i128 [[SHR_5]] to i8141; CHECK-NEXT: [[GEP_5:%.*]] = getelementptr i8, ptr [[P]], i64 5142; CHECK-NEXT: store i8 [[X_5]], ptr [[GEP_5]], align 1143; CHECK-NEXT: [[SHR_6:%.*]] = lshr i128 [[X]], 48144; CHECK-NEXT: [[X_6:%.*]] = trunc i128 [[SHR_6]] to i8145; CHECK-NEXT: [[GEP_6:%.*]] = getelementptr i8, ptr [[P]], i64 6146; CHECK-NEXT: store i8 [[X_6]], ptr [[GEP_6]], align 1147; CHECK-NEXT: [[SHR_7:%.*]] = lshr i128 [[X]], 56148; CHECK-NEXT: [[X_7:%.*]] = trunc i128 [[SHR_7]] to i8149; CHECK-NEXT: [[GEP_7:%.*]] = getelementptr i8, ptr [[P]], i64 7150; CHECK-NEXT: store i8 [[X_7]], ptr [[GEP_7]], align 1151; CHECK-NEXT: [[SHR_8:%.*]] = lshr i128 [[X]], 64152; CHECK-NEXT: [[X_8:%.*]] = trunc i128 [[SHR_8]] to i8153; CHECK-NEXT: [[GEP_8:%.*]] = getelementptr i8, ptr [[P]], i64 8154; CHECK-NEXT: store i8 [[X_8]], ptr [[GEP_8]], align 1155; CHECK-NEXT: [[SHR_9:%.*]] = lshr i128 [[X]], 72156; CHECK-NEXT: [[X_9:%.*]] = trunc i128 [[SHR_9]] to i8157; CHECK-NEXT: [[GEP_9:%.*]] = getelementptr i8, ptr [[P]], i64 9158; CHECK-NEXT: store i8 [[X_9]], ptr [[GEP_9]], align 1159; CHECK-NEXT: [[SHR_10:%.*]] = lshr i128 [[X]], 80160; CHECK-NEXT: [[X_10:%.*]] = trunc i128 [[SHR_10]] to i8161; CHECK-NEXT: [[GEP_10:%.*]] = getelementptr i8, ptr [[P]], i64 10162; CHECK-NEXT: store i8 [[X_10]], ptr [[GEP_10]], align 1163; CHECK-NEXT: [[SHR_11:%.*]] = lshr i128 [[X]], 88164; CHECK-NEXT: [[X_11:%.*]] = trunc i128 [[SHR_11]] to i8165; CHECK-NEXT: [[GEP_11:%.*]] = getelementptr i8, ptr [[P]], i64 11166; CHECK-NEXT: store i8 [[X_11]], ptr [[GEP_11]], align 1167; CHECK-NEXT: [[SHR_12:%.*]] = lshr i128 [[X]], 96168; CHECK-NEXT: [[X_12:%.*]] = trunc i128 [[SHR_12]] to i8169; CHECK-NEXT: [[GEP_12:%.*]] = getelementptr i8, ptr [[P]], i64 12170; CHECK-NEXT: store i8 [[X_12]], ptr [[GEP_12]], align 1171; CHECK-NEXT: [[SHR_13:%.*]] = lshr i128 [[X]], 104172; CHECK-NEXT: [[X_13:%.*]] = trunc i128 [[SHR_13]] to i8173; CHECK-NEXT: [[GEP_13:%.*]] = getelementptr i8, ptr [[P]], i64 13174; CHECK-NEXT: store i8 [[X_13]], ptr [[GEP_13]], align 1175; CHECK-NEXT: [[SHR_14:%.*]] = lshr i128 [[X]], 112176; CHECK-NEXT: [[X_14:%.*]] = trunc i128 [[SHR_14]] to i8177; CHECK-NEXT: [[GEP_14:%.*]] = getelementptr i8, ptr [[P]], i64 14178; CHECK-NEXT: store i8 [[X_14]], ptr [[GEP_14]], align 1179; CHECK-NEXT: [[SHR_15:%.*]] = lshr i128 [[X]], 120180; CHECK-NEXT: [[X_15:%.*]] = trunc i128 [[SHR_15]] to i8181; CHECK-NEXT: [[GEP_15:%.*]] = getelementptr i8, ptr [[P]], i64 15182; CHECK-NEXT: store i8 [[X_15]], ptr [[GEP_15]], align 1183; CHECK-NEXT: ret void184;185 %x.0 = trunc i128 %x to i8186 store i8 %x.0, ptr %p187 %shr.1 = lshr i128 %x, 8188 %x.1 = trunc i128 %shr.1 to i8189 %gep.1 = getelementptr i8, ptr %p, i64 1190 store i8 %x.1, ptr %gep.1191 %shr.2 = lshr i128 %x, 16192 %x.2 = trunc i128 %shr.2 to i8193 %gep.2 = getelementptr i8, ptr %p, i64 2194 store i8 %x.2, ptr %gep.2195 %shr.3 = lshr i128 %x, 24196 %x.3 = trunc i128 %shr.3 to i8197 %gep.3 = getelementptr i8, ptr %p, i64 3198 store i8 %x.3, ptr %gep.3199 %shr.4 = lshr i128 %x, 32200 %x.4 = trunc i128 %shr.4 to i8201 %gep.4 = getelementptr i8, ptr %p, i64 4202 store i8 %x.4, ptr %gep.4203 %shr.5 = lshr i128 %x, 40204 %x.5 = trunc i128 %shr.5 to i8205 %gep.5 = getelementptr i8, ptr %p, i64 5206 store i8 %x.5, ptr %gep.5207 %shr.6 = lshr i128 %x, 48208 %x.6 = trunc i128 %shr.6 to i8209 %gep.6 = getelementptr i8, ptr %p, i64 6210 store i8 %x.6, ptr %gep.6211 %shr.7 = lshr i128 %x, 56212 %x.7 = trunc i128 %shr.7 to i8213 %gep.7 = getelementptr i8, ptr %p, i64 7214 store i8 %x.7, ptr %gep.7215 %shr.8 = lshr i128 %x, 64216 %x.8 = trunc i128 %shr.8 to i8217 %gep.8 = getelementptr i8, ptr %p, i64 8218 store i8 %x.8, ptr %gep.8219 %shr.9 = lshr i128 %x, 72220 %x.9 = trunc i128 %shr.9 to i8221 %gep.9 = getelementptr i8, ptr %p, i64 9222 store i8 %x.9, ptr %gep.9223 %shr.10 = lshr i128 %x, 80224 %x.10 = trunc i128 %shr.10 to i8225 %gep.10 = getelementptr i8, ptr %p, i64 10226 store i8 %x.10, ptr %gep.10227 %shr.11 = lshr i128 %x, 88228 %x.11 = trunc i128 %shr.11 to i8229 %gep.11 = getelementptr i8, ptr %p, i64 11230 store i8 %x.11, ptr %gep.11231 %shr.12 = lshr i128 %x, 96232 %x.12 = trunc i128 %shr.12 to i8233 %gep.12 = getelementptr i8, ptr %p, i64 12234 store i8 %x.12, ptr %gep.12235 %shr.13 = lshr i128 %x, 104236 %x.13 = trunc i128 %shr.13 to i8237 %gep.13 = getelementptr i8, ptr %p, i64 13238 store i8 %x.13, ptr %gep.13239 %shr.14 = lshr i128 %x, 112240 %x.14 = trunc i128 %shr.14 to i8241 %gep.14 = getelementptr i8, ptr %p, i64 14242 store i8 %x.14, ptr %gep.14243 %shr.15 = lshr i128 %x, 120244 %x.15 = trunc i128 %shr.15 to i8245 %gep.15 = getelementptr i8, ptr %p, i64 15246 store i8 %x.15, ptr %gep.15247 ret void248}249 250define void @test_i32_lo(i32 %x, ptr %p) {251; CHECK-LABEL: define void @test_i32_lo(252; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {253; CHECK-NEXT: [[TMP1:%.*]] = trunc i32 [[X]] to i16254; CHECK-NEXT: store i16 [[TMP1]], ptr [[P]], align 1255; CHECK-NEXT: ret void256;257 %x.0 = trunc i32 %x to i8258 store i8 %x.0, ptr %p259 %shr.1 = lshr i32 %x, 8260 %x.1 = trunc i32 %shr.1 to i8261 %gep.1 = getelementptr i8, ptr %p, i64 1262 store i8 %x.1, ptr %gep.1263 ret void264}265 266define void @test_i32_hi(i32 %x, ptr %p) {267; CHECK-LABEL: define void @test_i32_hi(268; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {269; CHECK-NEXT: [[SHR_0:%.*]] = lshr i32 [[X]], 16270; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[SHR_0]] to i16271; CHECK-NEXT: store i16 [[TMP2]], ptr [[P]], align 1272; CHECK-NEXT: ret void273;274 %shr.0 = lshr i32 %x, 16275 %x.0 = trunc i32 %shr.0 to i8276 store i8 %x.0, ptr %p277 %shr.1 = lshr i32 %x, 24278 %x.1 = trunc i32 %shr.1 to i8279 %gep.1 = getelementptr i8, ptr %p, i64 1280 store i8 %x.1, ptr %gep.1281 ret void282}283 284define void @test_i32_mid(i32 %x, ptr %p) {285; CHECK-LABEL: define void @test_i32_mid(286; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {287; CHECK-NEXT: [[TMP1:%.*]] = lshr i32 [[X]], 10288; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[TMP1]] to i16289; CHECK-NEXT: store i16 [[TMP2]], ptr [[P]], align 1290; CHECK-NEXT: ret void291;292 %shr.0 = lshr i32 %x, 10293 %x.0 = trunc i32 %shr.0 to i8294 store i8 %x.0, ptr %p295 %shr.1 = lshr i32 %x, 18296 %x.1 = trunc i32 %shr.1 to i8297 %gep.1 = getelementptr i8, ptr %p, i64 1298 store i8 %x.1, ptr %gep.1299 ret void300}301 302define void @test_i32_shift_in_zeros(i32 %x, ptr %p) {303; CHECK-LABEL: define void @test_i32_shift_in_zeros(304; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {305; CHECK-NEXT: [[SHR_0:%.*]] = lshr i32 [[X]], 20306; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[SHR_0]] to i16307; CHECK-NEXT: store i16 [[TMP2]], ptr [[P]], align 1308; CHECK-NEXT: ret void309;310 %shr.0 = lshr i32 %x, 20311 %x.0 = trunc i32 %shr.0 to i8312 store i8 %x.0, ptr %p313 %shr.1 = lshr i32 %x, 28314 %x.1 = trunc i32 %shr.1 to i8315 %gep.1 = getelementptr i8, ptr %p, i64 1316 store i8 %x.1, ptr %gep.1317 ret void318}319 320define void @test_base_ptr_with_offset(i32 %x, ptr %p) {321; CHECK-LABEL: define void @test_base_ptr_with_offset(322; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {323; CHECK-NEXT: [[TMP1:%.*]] = getelementptr i8, ptr [[P]], i64 7324; CHECK-NEXT: store i32 [[X]], ptr [[TMP1]], align 2325; CHECK-NEXT: ret void326;327 %x.0 = trunc i32 %x to i16328 %gep.0 = getelementptr i8, ptr %p, i64 7329 store i16 %x.0, ptr %gep.0330 %shr.1 = lshr i32 %x, 16331 %x.1 = trunc i32 %shr.1 to i16332 %gep.1 = getelementptr i8, ptr %p, i64 9333 store i16 %x.1, ptr %gep.1334 ret void335}336 337define void @test_aliasing_store(i16 %x, ptr %p, ptr %p2) {338; CHECK-LABEL: define void @test_aliasing_store(339; CHECK-SAME: i16 [[X:%.*]], ptr [[P:%.*]], ptr [[P2:%.*]]) {340; CHECK-NEXT: [[X_0:%.*]] = trunc i16 [[X]] to i8341; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1342; CHECK-NEXT: store i8 0, ptr [[P2]], align 1343; CHECK-NEXT: [[SHR_1:%.*]] = lshr i16 [[X]], 8344; CHECK-NEXT: [[X_1:%.*]] = trunc i16 [[SHR_1]] to i8345; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1346; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1347; CHECK-NEXT: ret void348;349 %x.0 = trunc i16 %x to i8350 store i8 %x.0, ptr %p351 store i8 0, ptr %p2352 %shr.1 = lshr i16 %x, 8353 %x.1 = trunc i16 %shr.1 to i8354 %gep.1 = getelementptr i8, ptr %p, i64 1355 store i8 %x.1, ptr %gep.1356 ret void357}358 359define void @test_non_aliasing_store(i16 %x, ptr noalias %p, ptr noalias %p2) {360; CHECK-LABEL: define void @test_non_aliasing_store(361; CHECK-SAME: i16 [[X:%.*]], ptr noalias [[P:%.*]], ptr noalias [[P2:%.*]]) {362; CHECK-NEXT: store i16 [[X]], ptr [[P]], align 1363; CHECK-NEXT: store i8 0, ptr [[P2]], align 1364; CHECK-NEXT: ret void365;366 %x.0 = trunc i16 %x to i8367 store i8 %x.0, ptr %p368 store i8 0, ptr %p2369 %shr.1 = lshr i16 %x, 8370 %x.1 = trunc i16 %shr.1 to i8371 %gep.1 = getelementptr i8, ptr %p, i64 1372 store i8 %x.1, ptr %gep.1373 ret void374}375 376define i8 @test_aliasing_load(i16 %x, ptr %p, ptr %p2) {377; CHECK-LABEL: define i8 @test_aliasing_load(378; CHECK-SAME: i16 [[X:%.*]], ptr [[P:%.*]], ptr [[P2:%.*]]) {379; CHECK-NEXT: [[X_0:%.*]] = trunc i16 [[X]] to i8380; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1381; CHECK-NEXT: [[V:%.*]] = load i8, ptr [[P2]], align 1382; CHECK-NEXT: [[SHR_1:%.*]] = lshr i16 [[X]], 8383; CHECK-NEXT: [[X_1:%.*]] = trunc i16 [[SHR_1]] to i8384; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1385; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1386; CHECK-NEXT: ret i8 [[V]]387;388 %x.0 = trunc i16 %x to i8389 store i8 %x.0, ptr %p390 %v = load i8, ptr %p2391 %shr.1 = lshr i16 %x, 8392 %x.1 = trunc i16 %shr.1 to i8393 %gep.1 = getelementptr i8, ptr %p, i64 1394 store i8 %x.1, ptr %gep.1395 ret i8 %v396}397 398define i8 @test_non_aliasing_load(i16 %x, ptr noalias %p, ptr noalias %p2) {399; CHECK-LABEL: define i8 @test_non_aliasing_load(400; CHECK-SAME: i16 [[X:%.*]], ptr noalias [[P:%.*]], ptr noalias [[P2:%.*]]) {401; CHECK-NEXT: store i16 [[X]], ptr [[P]], align 1402; CHECK-NEXT: [[V:%.*]] = load i8, ptr [[P2]], align 1403; CHECK-NEXT: ret i8 [[V]]404;405 %x.0 = trunc i16 %x to i8406 store i8 %x.0, ptr %p407 %v = load i8, ptr %p2408 %shr.1 = lshr i16 %x, 8409 %x.1 = trunc i16 %shr.1 to i8410 %gep.1 = getelementptr i8, ptr %p, i64 1411 store i8 %x.1, ptr %gep.1412 ret i8 %v413}414 415define i8 @test_aliasing_load_partially_mergeable(i32 %x, ptr %p, ptr %p2) {416; CHECK-LABEL: define i8 @test_aliasing_load_partially_mergeable(417; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]], ptr [[P2:%.*]]) {418; CHECK-NEXT: [[TMP1:%.*]] = trunc i32 [[X]] to i16419; CHECK-NEXT: store i16 [[TMP1]], ptr [[P]], align 1420; CHECK-NEXT: [[V:%.*]] = load i8, ptr [[P2]], align 1421; CHECK-NEXT: [[TMP4:%.*]] = getelementptr i8, ptr [[P]], i64 2422; CHECK-NEXT: [[TMP2:%.*]] = lshr i32 [[X]], 16423; CHECK-NEXT: [[TMP3:%.*]] = trunc i32 [[TMP2]] to i16424; CHECK-NEXT: store i16 [[TMP3]], ptr [[TMP4]], align 1425; CHECK-NEXT: ret i8 [[V]]426;427 %x.0 = trunc i32 %x to i8428 store i8 %x.0, ptr %p429 %shr.1 = lshr i32 %x, 8430 %x.1 = trunc i32 %shr.1 to i8431 %gep.1 = getelementptr i8, ptr %p, i64 1432 store i8 %x.1, ptr %gep.1433 %v = load i8, ptr %p2434 %shr.2 = lshr i32 %x, 16435 %x.2 = trunc i32 %shr.2 to i8436 %gep.2 = getelementptr i8, ptr %p, i64 2437 store i8 %x.2, ptr %gep.2438 %shr.3 = lshr i32 %x, 24439 %x.3 = trunc i32 %shr.3 to i8440 %gep.3 = getelementptr i8, ptr %p, i64 3441 store i8 %x.3, ptr %gep.3442 ret i8 %v443}444 445declare void @may_unwind() memory(none)446 447define void @test_unwind(i16 %x, ptr %p, ptr %p2) {448; CHECK-LABEL: define void @test_unwind(449; CHECK-SAME: i16 [[X:%.*]], ptr [[P:%.*]], ptr [[P2:%.*]]) {450; CHECK-NEXT: [[X_0:%.*]] = trunc i16 [[X]] to i8451; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1452; CHECK-NEXT: call void @may_unwind()453; CHECK-NEXT: [[SHR_1:%.*]] = lshr i16 [[X]], 8454; CHECK-NEXT: [[X_1:%.*]] = trunc i16 [[SHR_1]] to i8455; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1456; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1457; CHECK-NEXT: ret void458;459 %x.0 = trunc i16 %x to i8460 store i8 %x.0, ptr %p461 call void @may_unwind()462 %shr.1 = lshr i16 %x, 8463 %x.1 = trunc i16 %shr.1 to i8464 %gep.1 = getelementptr i8, ptr %p, i64 1465 store i8 %x.1, ptr %gep.1466 ret void467}468 469define void @test_multi_group(i16 %x, ptr %p1, i16 %y, ptr %p2) {470; CHECK-LABEL: define void @test_multi_group(471; CHECK-SAME: i16 [[X:%.*]], ptr [[P1:%.*]], i16 [[Y:%.*]], ptr [[P2:%.*]]) {472; CHECK-NEXT: store i16 [[X]], ptr [[P1]], align 1473; CHECK-NEXT: call void @may_unwind()474; CHECK-NEXT: store i16 [[Y]], ptr [[P2]], align 1475; CHECK-NEXT: ret void476;477 %x.0 = trunc i16 %x to i8478 store i8 %x.0, ptr %p1479 %shr.1 = lshr i16 %x, 8480 %x.1 = trunc i16 %shr.1 to i8481 %gep.1 = getelementptr i8, ptr %p1, i64 1482 store i8 %x.1, ptr %gep.1483 call void @may_unwind()484 %y.0 = trunc i16 %y to i8485 store i8 %y.0, ptr %p2486 %shr.2 = lshr i16 %y, 8487 %y.1 = trunc i16 %shr.2 to i8488 %gep.2 = getelementptr i8, ptr %p2, i64 1489 store i8 %y.1, ptr %gep.2490 ret void491}492 493define void @test_stores_out_of_order(i32 %x, ptr %p) {494; CHECK-LABEL: define void @test_stores_out_of_order(495; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {496; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 1497; CHECK-NEXT: ret void498;499 %shr.2 = lshr i32 %x, 16500 %x.2 = trunc i32 %shr.2 to i8501 %gep.2 = getelementptr i8, ptr %p, i64 2502 store i8 %x.2, ptr %gep.2503 %x.0 = trunc i32 %x to i8504 store i8 %x.0, ptr %p505 %shr.3 = lshr i32 %x, 24506 %x.3 = trunc i32 %shr.3 to i8507 %gep.3 = getelementptr i8, ptr %p, i64 3508 store i8 %x.3, ptr %gep.3509 %shr.1 = lshr i32 %x, 8510 %x.1 = trunc i32 %shr.1 to i8511 %gep.1 = getelementptr i8, ptr %p, i64 1512 store i8 %x.1, ptr %gep.1513 ret void514}515 516define void @test_i32_gap(i32 %x, ptr %p) {517; CHECK-LABEL: define void @test_i32_gap(518; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {519; CHECK-NEXT: [[SHR_0:%.*]] = lshr i32 [[X]], 7520; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[SHR_0]] to i8521; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1522; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 16523; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i8524; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1525; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1526; CHECK-NEXT: ret void527;528 %shr.0 = lshr i32 %x, 7529 %x.0 = trunc i32 %shr.0 to i8530 store i8 %x.0, ptr %p531 %shr.1 = lshr i32 %x, 16532 %x.1 = trunc i32 %shr.1 to i8533 %gep.1 = getelementptr i8, ptr %p, i64 1534 store i8 %x.1, ptr %gep.1535 ret void536}537 538define void @test_i32_non_byte_sized(i32 %x, ptr %p) {539; CHECK-LABEL: define void @test_i32_non_byte_sized(540; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {541; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[X]] to i15542; CHECK-NEXT: store i15 [[X_0]], ptr [[P]], align 2543; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 15544; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i17545; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 2546; CHECK-NEXT: store i17 [[X_1]], ptr [[GEP_1]], align 4547; CHECK-NEXT: ret void548;549 %x.0 = trunc i32 %x to i15550 store i15 %x.0, ptr %p551 %shr.1 = lshr i32 %x, 15552 %x.1 = trunc i32 %shr.1 to i17553 %gep.1 = getelementptr i8, ptr %p, i64 2554 store i17 %x.1, ptr %gep.1555 ret void556}557 558define void @test_i32_wrong_ptr_offset(i32 %x, ptr %p) {559; CHECK-LABEL: define void @test_i32_wrong_ptr_offset(560; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {561; CHECK-NEXT: [[SHR_0:%.*]] = lshr i32 [[X]], 8562; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[SHR_0]] to i8563; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1564; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 16565; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i8566; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 2567; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1568; CHECK-NEXT: ret void569;570 %shr.0 = lshr i32 %x, 8571 %x.0 = trunc i32 %shr.0 to i8572 store i8 %x.0, ptr %p573 %shr.1 = lshr i32 %x, 16574 %x.1 = trunc i32 %shr.1 to i8575 %gep.1 = getelementptr i8, ptr %p, i64 2576 store i8 %x.1, ptr %gep.1577 ret void578}579 580define void @test_i32_wrong_endian(i32 %x, ptr %p) {581; CHECK-LABEL: define void @test_i32_wrong_endian(582; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {583; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[X]] to i8584; CHECK-NEXT: [[GEP_0:%.*]] = getelementptr i8, ptr [[P]], i64 3585; CHECK-NEXT: store i8 [[X_0]], ptr [[GEP_0]], align 1586; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 8587; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i8588; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 2589; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1590; CHECK-NEXT: [[SHR_2:%.*]] = lshr i32 [[X]], 16591; CHECK-NEXT: [[X_2:%.*]] = trunc i32 [[SHR_2]] to i8592; CHECK-NEXT: [[GEP_2:%.*]] = getelementptr i8, ptr [[P]], i64 1593; CHECK-NEXT: store i8 [[X_2]], ptr [[GEP_2]], align 1594; CHECK-NEXT: [[SHR_3:%.*]] = lshr i32 [[X]], 24595; CHECK-NEXT: [[X_3:%.*]] = trunc i32 [[SHR_3]] to i8596; CHECK-NEXT: store i8 [[X_3]], ptr [[P]], align 1597; CHECK-NEXT: ret void598;599 %x.0 = trunc i32 %x to i8600 %gep.0 = getelementptr i8, ptr %p, i64 3601 store i8 %x.0, ptr %gep.0602 %shr.1 = lshr i32 %x, 8603 %x.1 = trunc i32 %shr.1 to i8604 %gep.1 = getelementptr i8, ptr %p, i64 2605 store i8 %x.1, ptr %gep.1606 %shr.2 = lshr i32 %x, 16607 %x.2 = trunc i32 %shr.2 to i8608 %gep.2 = getelementptr i8, ptr %p, i64 1609 store i8 %x.2, ptr %gep.2610 %shr.3 = lshr i32 %x, 24611 %x.3 = trunc i32 %shr.3 to i8612 store i8 %x.3, ptr %p613 ret void614}615 616define void @test_i32_volatile(i32 %x, ptr %p) {617; CHECK-LABEL: define void @test_i32_volatile(618; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {619; CHECK-NEXT: [[TMP1:%.*]] = lshr i32 [[X]], 8620; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[TMP1]] to i8621; CHECK-NEXT: store volatile i8 [[X_0]], ptr [[P]], align 1622; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 16623; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i8624; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1625; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1626; CHECK-NEXT: ret void627;628 %shr.0 = lshr i32 %x, 8629 %x.0 = trunc i32 %shr.0 to i8630 store volatile i8 %x.0, ptr %p631 %shr.1 = lshr i32 %x, 16632 %x.1 = trunc i32 %shr.1 to i8633 %gep.1 = getelementptr i8, ptr %p, i64 1634 store i8 %x.1, ptr %gep.1635 ret void636}637 638define void @test_i32_atomic(i32 %x, ptr %p) {639; CHECK-LABEL: define void @test_i32_atomic(640; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {641; CHECK-NEXT: [[SHR_0:%.*]] = lshr i32 [[X]], 8642; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[SHR_0]] to i8643; CHECK-NEXT: store atomic i8 [[X_0]], ptr [[P]] monotonic, align 1644; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 16645; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i8646; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 1647; CHECK-NEXT: store i8 [[X_1]], ptr [[GEP_1]], align 1648; CHECK-NEXT: ret void649;650 %shr.0 = lshr i32 %x, 8651 %x.0 = trunc i32 %shr.0 to i8652 store atomic i8 %x.0, ptr %p monotonic, align 1653 %shr.1 = lshr i32 %x, 16654 %x.1 = trunc i32 %shr.1 to i8655 %gep.1 = getelementptr i8, ptr %p, i64 1656 store i8 %x.1, ptr %gep.1657 ret void658}659 660define void @test_i32_multiple_pointers(i32 %x, i32 %y, ptr %p, ptr %p2) {661; CHECK-LABEL: define void @test_i32_multiple_pointers(662; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]], ptr [[P:%.*]], ptr [[P2:%.*]]) {663; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 2664; CHECK-NEXT: store i32 [[Y]], ptr [[P2]], align 2665; CHECK-NEXT: ret void666;667 %x.0 = trunc i32 %x to i16668 store i16 %x.0, ptr %p669 %shr.1 = lshr i32 %x, 16670 %x.1 = trunc i32 %shr.1 to i16671 %gep.1 = getelementptr i8, ptr %p, i64 2672 store i16 %x.1, ptr %gep.1673 674 %y.0 = trunc i32 %y to i16675 store i16 %y.0, ptr %p2676 %y.shr.1 = lshr i32 %y, 16677 %y.1 = trunc i32 %y.shr.1 to i16678 %p2.gep.1 = getelementptr i8, ptr %p2, i64 2679 store i16 %y.1, ptr %p2.gep.1680 ret void681}682 683define void @test_i32_multiple_pointers_interleaved(i32 %x, i32 %y, ptr noalias %p, ptr noalias %p2) {684; CHECK-LABEL: define void @test_i32_multiple_pointers_interleaved(685; CHECK-SAME: i32 [[X:%.*]], i32 [[Y:%.*]], ptr noalias [[P:%.*]], ptr noalias [[P2:%.*]]) {686; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[X]] to i16687; CHECK-NEXT: store i16 [[X_0]], ptr [[P]], align 2688; CHECK-NEXT: [[Y_0:%.*]] = trunc i32 [[Y]] to i16689; CHECK-NEXT: store i16 [[Y_0]], ptr [[P2]], align 2690; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 16691; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i16692; CHECK-NEXT: [[GEP_1:%.*]] = getelementptr i8, ptr [[P]], i64 2693; CHECK-NEXT: store i16 [[X_1]], ptr [[GEP_1]], align 2694; CHECK-NEXT: [[Y_SHR_1:%.*]] = lshr i32 [[Y]], 16695; CHECK-NEXT: [[Y_1:%.*]] = trunc i32 [[Y_SHR_1]] to i16696; CHECK-NEXT: [[P2_GEP_1:%.*]] = getelementptr i8, ptr [[P2]], i64 2697; CHECK-NEXT: store i16 [[Y_1]], ptr [[P2_GEP_1]], align 2698; CHECK-NEXT: ret void699;700 %x.0 = trunc i32 %x to i16701 store i16 %x.0, ptr %p702 %y.0 = trunc i32 %y to i16703 store i16 %y.0, ptr %p2704 705 %shr.1 = lshr i32 %x, 16706 %x.1 = trunc i32 %shr.1 to i16707 %gep.1 = getelementptr i8, ptr %p, i64 2708 store i16 %x.1, ptr %gep.1709 %y.shr.1 = lshr i32 %y, 16710 %y.1 = trunc i32 %y.shr.1 to i16711 %p2.gep.1 = getelementptr i8, ptr %p2, i64 2712 store i16 %y.1, ptr %p2.gep.1713 ret void714}715 716define void @test_i32_multi_use(i32 %x, ptr %p) {717; CHECK-LABEL: define void @test_i32_multi_use(718; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {719; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[X]] to i16720; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 2721; CHECK-NEXT: [[SHR_1:%.*]] = lshr i32 [[X]], 16722; CHECK-NEXT: [[X_1:%.*]] = trunc i32 [[SHR_1]] to i16723; CHECK-NEXT: call void @use.i16(i16 [[X_0]])724; CHECK-NEXT: call void @use.i16(i16 [[X_1]])725; CHECK-NEXT: call void @use.i32(i32 [[SHR_1]])726; CHECK-NEXT: ret void727;728 %x.0 = trunc i32 %x to i16729 store i16 %x.0, ptr %p730 %shr.1 = lshr i32 %x, 16731 %x.1 = trunc i32 %shr.1 to i16732 %gep.1 = getelementptr i8, ptr %p, i64 2733 store i16 %x.1, ptr %gep.1734 call void @use.i16(i16 %x.0)735 call void @use.i16(i16 %x.1)736 call void @use.i32(i32 %shr.1)737 ret void738}739 740define void @test_i32_scoped_aa_same(i32 %x, ptr %p) {741; CHECK-LABEL: define void @test_i32_scoped_aa_same(742; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {743; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 2, !noalias [[META0:![0-9]+]]744; CHECK-NEXT: ret void745;746 %x.0 = trunc i32 %x to i16747 store i16 %x.0, ptr %p, !noalias !0748 %shr.1 = lshr i32 %x, 16749 %x.1 = trunc i32 %shr.1 to i16750 %gep.1 = getelementptr i8, ptr %p, i64 2751 store i16 %x.1, ptr %gep.1, !noalias !0752 ret void753}754 755define void @test_i32_scoped_aa_different(i32 %x, ptr %p) {756; CHECK-LABEL: define void @test_i32_scoped_aa_different(757; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {758; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 2, !noalias [[META3:![0-9]+]]759; CHECK-NEXT: ret void760;761 %x.0 = trunc i32 %x to i16762 store i16 %x.0, ptr %p, !noalias !0763 %shr.1 = lshr i32 %x, 16764 %x.1 = trunc i32 %shr.1 to i16765 %gep.1 = getelementptr i8, ptr %p, i64 2766 store i16 %x.1, ptr %gep.1, !noalias !3767 ret void768}769 770define void @test_i32_tbaa(i32 %x, ptr %p) {771; CHECK-LABEL: define void @test_i32_tbaa(772; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {773; CHECK-NEXT: store i32 [[X]], ptr [[P]], align 2774; CHECK-NEXT: ret void775;776 %x.0 = trunc i32 %x to i16777 store i16 %x.0, ptr %p, !tbaa !6778 %shr.1 = lshr i32 %x, 16779 %x.1 = trunc i32 %shr.1 to i16780 %gep.1 = getelementptr i8, ptr %p, i64 2781 store i16 %x.1, ptr %gep.1, !tbaa !6782 ret void783}784 785define void @test_multiple_parts_with_gap1(i32 %x, ptr %p) {786; CHECK-LABEL: define void @test_multiple_parts_with_gap1(787; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {788; CHECK-NEXT: [[TMP1:%.*]] = trunc i32 [[X]] to i16789; CHECK-NEXT: store i16 [[TMP1]], ptr [[P]], align 1790; CHECK-NEXT: [[SHR_3:%.*]] = lshr i32 [[X]], 24791; CHECK-NEXT: [[X_3:%.*]] = trunc i32 [[SHR_3]] to i8792; CHECK-NEXT: [[GEP_3:%.*]] = getelementptr i8, ptr [[P]], i64 3793; CHECK-NEXT: store i8 [[X_3]], ptr [[GEP_3]], align 1794; CHECK-NEXT: ret void795;796 %x.0 = trunc i32 %x to i8797 store i8 %x.0, ptr %p798 %shr.1 = lshr i32 %x, 8799 %x.1 = trunc i32 %shr.1 to i8800 %gep.1 = getelementptr i8, ptr %p, i64 1801 store i8 %x.1, ptr %gep.1802 %shr.3 = lshr i32 %x, 24803 %x.3 = trunc i32 %shr.3 to i8804 %gep.3 = getelementptr i8, ptr %p, i64 3805 store i8 %x.3, ptr %gep.3806 ret void807}808 809define void @test_multiple_parts_with_gap2(i32 %x, ptr %p) {810; CHECK-LABEL: define void @test_multiple_parts_with_gap2(811; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {812; CHECK-NEXT: [[X_0:%.*]] = trunc i32 [[X]] to i8813; CHECK-NEXT: store i8 [[X_0]], ptr [[P]], align 1814; CHECK-NEXT: [[GEP_2:%.*]] = getelementptr i8, ptr [[P]], i64 1815; CHECK-NEXT: [[TMP1:%.*]] = lshr i32 [[X]], 16816; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[TMP1]] to i16817; CHECK-NEXT: store i16 [[TMP2]], ptr [[GEP_2]], align 1818; CHECK-NEXT: ret void819;820 %x.0 = trunc i32 %x to i8821 store i8 %x.0, ptr %p822 %shr.2 = lshr i32 %x, 16823 %x.2 = trunc i32 %shr.2 to i8824 %gep.2 = getelementptr i8, ptr %p, i64 1825 store i8 %x.2, ptr %gep.2826 %shr.3 = lshr i32 %x, 24827 %x.3 = trunc i32 %shr.3 to i8828 %gep.3 = getelementptr i8, ptr %p, i64 2829 store i8 %x.3, ptr %gep.3830 ret void831}832 833define void @test_multiple_parts_with_gap3(i64 %x, ptr %p) {834; CHECK-LABEL: define void @test_multiple_parts_with_gap3(835; CHECK-SAME: i64 [[X:%.*]], ptr [[P:%.*]]) {836; CHECK-NEXT: [[TMP1:%.*]] = trunc i64 [[X]] to i16837; CHECK-NEXT: store i16 [[TMP1]], ptr [[P]], align 1838; CHECK-NEXT: [[GEP_3:%.*]] = getelementptr i8, ptr [[P]], i64 3839; CHECK-NEXT: [[TMP2:%.*]] = lshr i64 [[X]], 24840; CHECK-NEXT: [[TMP3:%.*]] = trunc i64 [[TMP2]] to i16841; CHECK-NEXT: store i16 [[TMP3]], ptr [[GEP_3]], align 1842; CHECK-NEXT: ret void843;844 %x.0 = trunc i64 %x to i8845 store i8 %x.0, ptr %p846 %shr.1 = lshr i64 %x, 8847 %x.1 = trunc i64 %shr.1 to i8848 %gep.1 = getelementptr i8, ptr %p, i64 1849 store i8 %x.1, ptr %gep.1850 %shr.3 = lshr i64 %x, 24851 %x.3 = trunc i64 %shr.3 to i8852 %gep.3 = getelementptr i8, ptr %p, i64 3853 store i8 %x.3, ptr %gep.3854 %shr.4 = lshr i64 %x, 32855 %x.4 = trunc i64 %shr.4 to i8856 %gep.4 = getelementptr i8, ptr %p, i64 4857 store i8 %x.4, ptr %gep.4858 ret void859}860 861define void @test_store_same_parts_twice(i32 %x, ptr %p) {862; CHECK-LABEL: define void @test_store_same_parts_twice(863; CHECK-SAME: i32 [[X:%.*]], ptr [[P:%.*]]) {864; CHECK-NEXT: [[TMP1:%.*]] = trunc i32 [[X]] to i16865; CHECK-NEXT: store i16 [[TMP1]], ptr [[P]], align 1866; CHECK-NEXT: [[GEP_2:%.*]] = getelementptr i8, ptr [[P]], i64 2867; CHECK-NEXT: [[TMP2:%.*]] = trunc i32 [[X]] to i16868; CHECK-NEXT: store i16 [[TMP2]], ptr [[GEP_2]], align 1869; CHECK-NEXT: ret void870;871 %x.0 = trunc i32 %x to i8872 store i8 %x.0, ptr %p873 %shr.1 = lshr i32 %x, 8874 %x.1 = trunc i32 %shr.1 to i8875 %gep.1 = getelementptr i8, ptr %p, i64 1876 store i8 %x.1, ptr %gep.1877 %gep.2 = getelementptr i8, ptr %p, i64 2878 store i8 %x.0, ptr %gep.2879 %gep.3 = getelementptr i8, ptr %p, i64 3880 store i8 %x.1, ptr %gep.3881 ret void882}883 884!0 = !{!1}885!1 = !{!1, !2}886!2 = !{!2}887 888!3 = !{!4}889!4 = !{!4, !5}890!5 = !{!5}891 892!6 = !{!7, !7, i64 0}893!7 = !{!"short", !8, i64 0}894!8 = !{!"omnipotent char", !9, i64 0}895!9 = !{!"Simple C/C++ TBAA"}896;.897; CHECK: [[META0]] = !{[[META1:![0-9]+]]}898; CHECK: [[META1]] = distinct !{[[META1]], [[META2:![0-9]+]]}899; CHECK: [[META2]] = distinct !{[[META2]]}900; CHECK: [[META3]] = !{}901;.902