brintos

brintos / llvm-project-archived public Read only

0
0
Text · 12.5 KiB · 823539b Raw
329 lines · cpp
1// RUN: %clang_cc1 -std=c++17 -triple x86_64-unknown-linux-gnu -fclangir -emit-cir %s -o %t.cir2// RUN: FileCheck --input-file=%t.cir %s --check-prefix=CIR3// RUN: %clang_cc1 -std=c++17 -triple x86_64-unknown-linux-gnu -fclangir -emit-llvm %s -o %t-cir.ll4// RUN: FileCheck --input-file=%t-cir.ll %s --check-prefix=LLVM5// RUN: %clang_cc1 -std=c++17 -triple x86_64-unknown-linux-gnu -emit-llvm %s -o %t.ll6// RUN: FileCheck --input-file=%t.ll %s --check-prefix=OGCG7 8int if0(bool a) {9 10  if (a)11    return 2;12 13  return 3;14 15}16 17// CIR: cir.func{{.*}} @_Z3if0b(%arg0: !cir.bool loc({{.*}})) -> !s32i18// CIR: cir.scope {19// CIR:   %4 = cir.load{{.*}} %0 : !cir.ptr<!cir.bool>, !cir.bool20// CIR-NEXT: cir.if %4 {21// CIR-NEXT:   %5 = cir.const #cir.int<2> : !s32i22// CIR-NEXT:   cir.store{{.*}} %5, %1 : !s32i, !cir.ptr<!s32i>23// CIR-NEXT:   %6 = cir.load{{.*}} %1 : !cir.ptr<!s32i>, !s32i24// CIR-NEXT:   cir.return %6 : !s32i25// CIR-NEXT:   }26// CIR-NEXT:  }27 28 29// LLVM: define{{.*}} i32 @_Z3if0b(i1 %0)30// LLVM:   br label %[[ENTRY:.*]]31// LLVM: [[ENTRY]]:32// LLVM:   %6 = load i8, ptr %2, align 133// LLVM:   %7 = trunc i8 %6 to i134// LLVM:   br i1 %7, label %[[THEN:.*]], label %[[END:.*]]35// LLVM: [[THEN]]:36// LLVM:   store i32 2, ptr %3, align 437// LLVM:   %9 = load i32, ptr %3, align 438// LLVM:   ret i32 %939// LLVM: [[END]]:40// LLVM:   br label %[[LABEL4:.*]]41// LLVM: [[LABEL4]]:42// LLVM:   store i32 3, ptr %3, align 443// LLVM:   %12 = load i32, ptr %3, align 444// LLVM:   ret i32 %1245 46// OGCG: define{{.*}} i32 @_Z3if0b(i1 noundef zeroext %a)47// OGCG: entry:48// OGCG:   %[[RETVAL:.*]] = alloca i32, align 449// OGCG:   %[[A_ADDR:.*]] = alloca i8, align 150// OGCG:   %[[STOREDV:.*]] = zext i1 %a to i851// OGCG:   store i8 %[[STOREDV]], ptr %[[A_ADDR]], align 152// OGCG:   %[[LOADTMP:.*]] = load i8, ptr %[[A_ADDR]], align 153// OGCG:   %[[LOADEDV:.*]] = trunc i8 %[[LOADTMP]] to i154// OGCG:   br i1 %[[LOADEDV]], label %[[THEN_LABEL:.*]], label %[[END_LABEL:.*]]55// OGCG: [[THEN_LABEL]]:56// OGCG:   store i32 2, ptr %[[RETVAL]], align 457// OGCG:   br label %[[RETURN_LABEL:.*]]58// OGCG: [[END_LABEL]]:59// OGCG:   store i32 3, ptr %[[RETVAL]], align 460// OGCG:   br label %[[RETURN_LABEL]]61// OGCG: [[RETURN_LABEL]]:62// OGCG:   %[[FINALLOAD:.*]] = load i32, ptr %[[RETVAL]], align 463// OGCG:   ret i32 %[[FINALLOAD]]64 65void if1(int a) {66  int x = 0;67  if (a) {68    x = 3;69  } else {70    x = 4;71  }72}73 74// CIR: cir.func{{.*}} @_Z3if1i(%arg0: !s32i loc({{.*}}))75// CIR: cir.scope {76// CIR:   %3 = cir.load{{.*}} %0 : !cir.ptr<!s32i>, !s32i77// CIR:   %4 = cir.cast int_to_bool %3 : !s32i -> !cir.bool78// CIR-NEXT:   cir.if %4 {79// CIR-NEXT:     %5 = cir.const #cir.int<3> : !s32i80// CIR-NEXT:     cir.store{{.*}} %5, %1 : !s32i, !cir.ptr<!s32i>81// CIR-NEXT:   } else {82// CIR-NEXT:     %5 = cir.const #cir.int<4> : !s32i83// CIR-NEXT:     cir.store{{.*}} %5, %1 : !s32i, !cir.ptr<!s32i>84// CIR-NEXT:   }85// CIR: }86 87// LLVM: define{{.*}} void @_Z3if1i(i32 %0)88// LLVM: %[[A:.*]] = alloca i32, i64 1, align 489// LLVM: %[[X:.*]] = alloca i32, i64 1, align 490// LLVM: store i32 %0, ptr %[[A]], align 491// LLVM: store i32 0, ptr %[[X]], align 492// LLVM: br label %[[ENTRY:.*]]93// LLVM: [[ENTRY]]:94// LLVM:   %[[LOADED:.*]] = load i32, ptr %[[A]], align 495// LLVM:   %[[COND:.*]] = icmp ne i32 %[[LOADED]], 096// LLVM:   br i1 %[[COND]], label %[[THEN:.*]], label %[[ELSE:.*]]97// LLVM: [[THEN]]:98// LLVM:   store i32 3, ptr %[[X]], align 499// LLVM:   br label %[[END:.*]]100// LLVM: [[ELSE]]:101// LLVM:   store i32 4, ptr %[[X]], align 4102// LLVM:   br label %[[END]]103// LLVM: [[END]]:104// LLVM:   br label %[[EXIT:.*]]105// LLVM: [[EXIT]]:106// LLVM:   ret void107 108// OGCG: define{{.*}} void @_Z3if1i(i32 noundef %[[A:.*]])109// OGCG: entry:110// OGCG:   %[[A_ADDR:.*]] = alloca i32, align 4111// OGCG:   %[[X:.*]] = alloca i32, align 4112// OGCG:   store i32 %[[A]], ptr %[[A_ADDR]], align 4113// OGCG:   store i32 0, ptr %[[X]], align 4114// OGCG:   %[[LOADED_A:.*]] = load i32, ptr %[[A_ADDR]], align 4115// OGCG:   %[[TOBOOL:.*]] = icmp ne i32 %[[LOADED_A]], 0116// OGCG:   br i1 %[[TOBOOL]], label %[[THEN_LABEL:.*]], label %[[ELSE_LABEL:.*]]117// OGCG: [[THEN_LABEL]]:118// OGCG:   store i32 3, ptr %[[X]], align 4119// OGCG:   br label %[[END_LABEL:.*]]120// OGCG: [[ELSE_LABEL]]:121// OGCG:   store i32 4, ptr %[[X]], align 4122// OGCG:   br label %[[END_LABEL]]123// OGCG: [[END_LABEL]]:124// OGCG:   ret void125 126void if2(int a, bool b, bool c) {127  int x = 0;128  if (a) {129    x = 3;130    if (b) {131      x = 8;132    }133  } else {134    if (c) {135      x = 14;136    }137    x = 4;138  }139}140 141// CIR: cir.func{{.*}} @_Z3if2ibb(%arg0: !s32i loc({{.*}}), %arg1: !cir.bool loc({{.*}}), %arg2: !cir.bool loc({{.*}}))142// CIR: cir.scope {143// CIR:   %5 = cir.load{{.*}} %0 : !cir.ptr<!s32i>, !s32i144// CIR:   %6 = cir.cast int_to_bool %5 : !s32i -> !cir.bool145// CIR:   cir.if %6 {146// CIR:     %7 = cir.const #cir.int<3> : !s32i147// CIR:     cir.store{{.*}} %7, %3 : !s32i, !cir.ptr<!s32i>148// CIR:     cir.scope {149// CIR:       %8 = cir.load{{.*}} %1 : !cir.ptr<!cir.bool>, !cir.bool150// CIR-NEXT:       cir.if %8 {151// CIR-NEXT:         %9 = cir.const #cir.int<8> : !s32i152// CIR-NEXT:         cir.store{{.*}} %9, %3 : !s32i, !cir.ptr<!s32i>153// CIR-NEXT:       }154// CIR:     }155// CIR:   } else {156// CIR:     cir.scope {157// CIR:       %8 = cir.load{{.*}} %2 : !cir.ptr<!cir.bool>, !cir.bool158// CIR-NEXT:       cir.if %8 {159// CIR-NEXT:         %9 = cir.const #cir.int<14> : !s32i160// CIR-NEXT:         cir.store{{.*}} %9, %3 : !s32i, !cir.ptr<!s32i>161// CIR-NEXT:       }162// CIR:     }163// CIR:     %7 = cir.const #cir.int<4> : !s32i164// CIR:     cir.store{{.*}} %7, %3 : !s32i, !cir.ptr<!s32i>165// CIR:   }166// CIR: }167 168// LLVM: define{{.*}} void @_Z3if2ibb(i32 %[[A:.*]], i1 %[[B:.*]], i1 %[[C:.*]])169// LLVM:   %[[VARA:.*]] = alloca i32, i64 1, align 4170// LLVM:   %[[VARB:.*]] = alloca i8, i64 1, align 1171// LLVM:   %[[VARC:.*]] = alloca i8, i64 1, align 1172// LLVM:   %[[VARX:.*]] = alloca i32, i64 1, align 4173// LLVM:   store i32 %[[A]], ptr %[[VARA]], align 4174// LLVM:   %[[B_EXT:.*]] = zext i1 %[[B]] to i8175// LLVM:   store i8 %[[B_EXT]], ptr %[[VARB]], align 1176// LLVM:   %[[C_EXT:.*]] = zext i1 %[[C]] to i8177// LLVM:   store i8 %[[C_EXT]], ptr %[[VARC]], align 1178// LLVM:   store i32 0, ptr %[[VARX]], align 4179// LLVM:   br label %[[ENTRY:.*]]180// LLVM: [[ENTRY]]:181// LLVM:   %[[LOAD_A:.*]] = load i32, ptr %[[VARA]], align 4182// LLVM:   %[[CMP_A:.*]] = icmp ne i32 %[[LOAD_A]], 0183// LLVM:   br i1 %[[CMP_A]], label %[[IF_THEN:.*]], label %[[IF_ELSE:.*]]184// LLVM: [[IF_THEN]]:185// LLVM:   store i32 3, ptr %[[VARX]], align 4186// LLVM:   br label %[[LABEL14:.*]]187// LLVM: [[LABEL14]]:188// LLVM:   %[[LOAD_B:.*]] = load i8, ptr %[[VARB]], align 1189// LLVM:   %[[TRUNC_B:.*]] = trunc i8 %[[LOAD_B]] to i1190// LLVM:   br i1 %[[TRUNC_B]], label %[[IF_THEN2:.*]], label %[[IF_END2:.*]]191// LLVM: [[IF_THEN2]]:192// LLVM:   store i32 8, ptr %[[VARX]], align 4193// LLVM:   br label %[[IF_END2]]194// LLVM: [[IF_END2]]:195// LLVM:   br label %[[LABEL19:.*]]196// LLVM: [[LABEL19]]:197// LLVM:   br label %[[LABEL27:.*]]198// LLVM: [[IF_ELSE]]:199// LLVM:   br label %[[LABEL21:.*]]200// LLVM: [[LABEL21]]:201// LLVM:   %[[LOAD_C:.*]] = load i8, ptr %[[VARC]], align 1202// LLVM:   %[[TRUNC_C:.*]] = trunc i8 %[[LOAD_C]] to i1203// LLVM:   br i1 %[[TRUNC_C]], label %[[IF_THEN3:.*]], label %[[IF_END3:.*]]204// LLVM: [[IF_THEN3]]:205// LLVM:   store i32 14, ptr %[[VARX]], align 4206// LLVM:   br label %[[IF_END3]]207// LLVM: [[IF_END3]]:208// LLVM:   br label %[[LABEL26:.*]]209// LLVM: [[LABEL26]]:210// LLVM:   store i32 4, ptr %[[VARX]], align 4211// LLVM:   br label %[[LABEL27]]212// LLVM: [[LABEL27]]:213// LLVM:   br label %[[LABEL28:.*]]214// LLVM: [[LABEL28]]:215// LLVM:   ret void216 217// OGCG: define{{.*}} void @_Z3if2ibb(i32 noundef %[[A:.*]], i1 noundef zeroext %[[B:.*]], i1 noundef zeroext %[[C:.*]])218// OGCG: entry:219// OGCG:   %[[A_ADDR:.*]] = alloca i32, align 4220// OGCG:   %[[B_ADDR:.*]] = alloca i8, align 1221// OGCG:   %[[C_ADDR:.*]] = alloca i8, align 1222// OGCG:   %[[X:.*]] = alloca i32, align 4223// OGCG:   store i32 %[[A]], ptr %[[A_ADDR]], align 4224// OGCG:   %[[B_EXT:.*]] = zext i1 %[[B]] to i8225// OGCG:   store i8 %[[B_EXT]], ptr %[[B_ADDR]], align 1226// OGCG:   %[[C_EXT:.*]] = zext i1 %[[C]] to i8227// OGCG:   store i8 %[[C_EXT]], ptr %[[C_ADDR]], align 1228// OGCG:   store i32 0, ptr %[[X]], align 4229// OGCG:   %[[A_VAL:.*]] = load i32, ptr %[[A_ADDR]], align 4230// OGCG:   %[[A_BOOL:.*]] = icmp ne i32 %[[A_VAL]], 0231// OGCG:   br i1 %[[A_BOOL]], label %[[IF_THEN:.*]], label %[[IF_ELSE:.*]]232// OGCG: [[IF_THEN]]:233// OGCG:   store i32 3, ptr %[[X]], align 4234// OGCG:   %[[B_LOAD:.*]] = load i8, ptr %[[B_ADDR]], align 1235// OGCG:   %[[B_TRUNC:.*]] = trunc i8 %[[B_LOAD]] to i1236// OGCG:   br i1 %[[B_TRUNC]], label %[[IF_THEN2:.*]], label %[[IF_END:.*]]237// OGCG: [[IF_THEN2]]:238// OGCG:   store i32 8, ptr %[[X]], align 4239// OGCG:   br label %[[IF_END]]240// OGCG: [[IF_END]]:241// OGCG:   br label %[[IF_END6:.*]]242// OGCG: [[IF_ELSE]]:243// OGCG:   %[[C_LOAD:.*]] = load i8, ptr %[[C_ADDR]], align 1244// OGCG:   %[[C_TRUNC:.*]] = trunc i8 %[[C_LOAD]] to i1245// OGCG:   br i1 %[[C_TRUNC]], label %[[IF_THEN4:.*]], label %[[IF_END5:.*]]246// OGCG: [[IF_THEN4]]:247// OGCG:   store i32 14, ptr %[[X]], align 4248// OGCG:   br label %[[IF_END5]]249// OGCG: [[IF_END5]]:250// OGCG:   store i32 4, ptr %[[X]], align 4251// OGCG:   br label %[[IF_END6]]252// OGCG: [[IF_END6]]:253// OGCG:   ret void254 255int if_init() {256  if (int x = 42 ; x) {257    return x + 1; // x should be visible here258  } else {259    return x - 1; // x should also be visible here260  }261}262 263// CIR: cir.func{{.*}} @_Z7if_initv() -> !s32i264// CIR: %[[RETVAL:.*]] = cir.alloca !s32i, !cir.ptr<!s32i>265// CIR: cir.scope {266// CIR:   %[[X:.*]] = cir.alloca !s32i, !cir.ptr<!s32i>,267// CIR:   %[[CONST42:.*]] = cir.const #cir.int<42> : !s32i268// CIR:   cir.store{{.*}} %[[CONST42]], %[[X]] : !s32i, !cir.ptr<!s32i>269// CIR:   %[[X_VAL:.*]] = cir.load{{.*}} %[[X]] : !cir.ptr<!s32i>, !s32i270// CIR:   %[[COND:.*]] = cir.cast int_to_bool %[[X_VAL]] : !s32i -> !cir.bool271// CIR:   cir.if %[[COND]] {272// CIR:     %[[X_IF:.*]] = cir.load{{.*}} %[[X]] : !cir.ptr<!s32i>, !s32i273// CIR:     %[[ONE:.*]] = cir.const #cir.int<1> : !s32i274// CIR:     %[[ADD:.*]] = cir.binop(add, %[[X_IF]], %[[ONE]]) nsw : !s32i275// CIR:     cir.store{{.*}} %[[ADD]], %[[RETVAL]] : !s32i, !cir.ptr<!s32i>276// CIR:     %[[RETVAL_LOAD1:.*]] = cir.load{{.*}} %[[RETVAL]] : !cir.ptr<!s32i>, !s32i277// CIR:     cir.return %[[RETVAL_LOAD1]] : !s32i278// CIR:   } else {279// CIR:     %[[X_ELSE:.*]] = cir.load{{.*}} %[[X]] : !cir.ptr<!s32i>, !s32i280// CIR:     %[[ONE2:.*]] = cir.const #cir.int<1> : !s32i281// CIR:     %[[SUB:.*]] = cir.binop(sub, %[[X_ELSE]], %[[ONE2]]) nsw : !s32i282// CIR:     cir.store{{.*}} %[[SUB]], %[[RETVAL]] : !s32i, !cir.ptr<!s32i>283// CIR:     %[[RETVAL_LOAD2:.*]] = cir.load{{.*}} %[[RETVAL]] : !cir.ptr<!s32i>, !s32i284// CIR:     cir.return %[[RETVAL_LOAD2]] : !s32i285// CIR:   }286// CIR: }287 288// LLVM: define{{.*}} i32 @_Z7if_initv()289// LLVM: %[[X:.*]] = alloca i32, i64 1, align 4290// LLVM: %[[RETVAL:.*]] = alloca i32, i64 1, align 4291// LLVM: store i32 42, ptr %[[X]], align 4292// LLVM: %[[X_VAL:.*]] = load i32, ptr %[[X]], align 4293// LLVM: %[[COND:.*]] = icmp ne i32 %[[X_VAL]], 0294// LLVM: br i1 %[[COND]], label %[[THEN:.*]], label %[[ELSE:.*]]295// LLVM: [[THEN]]:296// LLVM:   %[[X_LOAD:.*]] = load i32, ptr %[[X]], align 4297// LLVM:   %[[ADD:.*]] = add nsw i32 %[[X_LOAD]], 1298// LLVM:   store i32 %[[ADD]], ptr %[[RETVAL]], align 4299// LLVM:   %[[RETVAL_LOAD1:.*]] = load i32, ptr %[[RETVAL]], align 4300// LLVM:   ret i32 %[[RETVAL_LOAD1]]301// LLVM: [[ELSE]]:302// LLVM:   %[[X_LOAD2:.*]] = load i32, ptr %[[X]], align 4303// LLVM:   %[[SUB:.*]] = sub nsw i32 %[[X_LOAD2]], 1304// LLVM:   store i32 %[[SUB]], ptr %[[RETVAL]], align 4305// LLVM:   %[[RETVAL_LOAD2:.*]] = load i32, ptr %[[RETVAL]], align 4306// LLVM:   ret i32 %[[RETVAL_LOAD2]]307 308// OGCG: define{{.*}} i32 @_Z7if_initv()309// OGCG: entry:310// OGCG:   %[[RETVAL:.*]] = alloca i32, align 4311// OGCG:   %[[X:.*]] = alloca i32, align 4312// OGCG:   store i32 42, ptr %[[X]], align 4313// OGCG:   %[[X_VAL:.*]] = load i32, ptr %[[X]], align 4314// OGCG:   %[[COND:.*]] = icmp ne i32 %[[X_VAL]], 0315// OGCG:   br i1 %[[COND]], label %[[THEN:.*]], label %[[ELSE:.*]]316// OGCG: [[THEN]]:317// OGCG:   %[[X_LOAD:.*]] = load i32, ptr %[[X]], align 4318// OGCG:   %[[ADD:.*]] = add nsw i32 %[[X_LOAD]], 1319// OGCG:   store i32 %[[ADD]], ptr %[[RETVAL]], align 4320// OGCG:   br label %[[RETURN:.*]]321// OGCG: [[ELSE]]:322// OGCG:   %[[X_LOAD2:.*]] = load i32, ptr %[[X]], align 4323// OGCG:   %[[SUB:.*]] = sub nsw i32 %[[X_LOAD2]], 1324// OGCG:   store i32 %[[SUB]], ptr %[[RETVAL]], align 4325// OGCG:   br label %[[RETURN]]326// OGCG: [[RETURN]]:327// OGCG:   %[[RETVAL_FINAL:.*]] = load i32, ptr %[[RETVAL]], align 4328// OGCG:   ret i32 %[[RETVAL_FINAL]]329