1 //===---- CGBuiltin.cpp - Emit LLVM Code for builtins ---------------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This contains code to emit Builtin calls as LLVM code. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "CodeGenFunction.h" 15 #include "CGCXXABI.h" 16 #include "CGObjCRuntime.h" 17 #include "CGOpenCLRuntime.h" 18 #include "CodeGenModule.h" 19 #include "TargetInfo.h" 20 #include "clang/AST/ASTContext.h" 21 #include "clang/AST/Decl.h" 22 #include "clang/Basic/TargetBuiltins.h" 23 #include "clang/Basic/TargetInfo.h" 24 #include "clang/CodeGen/CGFunctionInfo.h" 25 #include "llvm/ADT/StringExtras.h" 26 #include "llvm/IR/CallSite.h" 27 #include "llvm/IR/DataLayout.h" 28 #include "llvm/IR/InlineAsm.h" 29 #include "llvm/IR/Intrinsics.h" 30 #include "llvm/IR/MDBuilder.h" 31 #include <sstream> 32 33 using namespace clang; 34 using namespace CodeGen; 35 using namespace llvm; 36 37 /// getBuiltinLibFunction - Given a builtin id for a function like 38 /// "__builtin_fabsf", return a Function* for "fabsf". 39 llvm::Value *CodeGenModule::getBuiltinLibFunction(const FunctionDecl *FD, 40 unsigned BuiltinID) { 41 assert(Context.BuiltinInfo.isLibFunction(BuiltinID)); 42 43 // Get the name, skip over the __builtin_ prefix (if necessary). 44 StringRef Name; 45 GlobalDecl D(FD); 46 47 // If the builtin has been declared explicitly with an assembler label, 48 // use the mangled name. This differs from the plain label on platforms 49 // that prefix labels. 50 if (FD->hasAttr<AsmLabelAttr>()) 51 Name = getMangledName(D); 52 else 53 Name = Context.BuiltinInfo.getName(BuiltinID) + 10; 54 55 llvm::FunctionType *Ty = 56 cast<llvm::FunctionType>(getTypes().ConvertType(FD->getType())); 57 58 return GetOrCreateLLVMFunction(Name, Ty, D, /*ForVTable=*/false); 59 } 60 61 /// Emit the conversions required to turn the given value into an 62 /// integer of the given size. 63 static Value *EmitToInt(CodeGenFunction &CGF, llvm::Value *V, 64 QualType T, llvm::IntegerType *IntType) { 65 V = CGF.EmitToMemory(V, T); 66 67 if (V->getType()->isPointerTy()) 68 return CGF.Builder.CreatePtrToInt(V, IntType); 69 70 assert(V->getType() == IntType); 71 return V; 72 } 73 74 static Value *EmitFromInt(CodeGenFunction &CGF, llvm::Value *V, 75 QualType T, llvm::Type *ResultType) { 76 V = CGF.EmitFromMemory(V, T); 77 78 if (ResultType->isPointerTy()) 79 return CGF.Builder.CreateIntToPtr(V, ResultType); 80 81 assert(V->getType() == ResultType); 82 return V; 83 } 84 85 /// Utility to insert an atomic instruction based on Instrinsic::ID 86 /// and the expression node. 87 static Value *MakeBinaryAtomicValue(CodeGenFunction &CGF, 88 llvm::AtomicRMWInst::BinOp Kind, 89 const CallExpr *E) { 90 QualType T = E->getType(); 91 assert(E->getArg(0)->getType()->isPointerType()); 92 assert(CGF.getContext().hasSameUnqualifiedType(T, 93 E->getArg(0)->getType()->getPointeeType())); 94 assert(CGF.getContext().hasSameUnqualifiedType(T, E->getArg(1)->getType())); 95 96 llvm::Value *DestPtr = CGF.EmitScalarExpr(E->getArg(0)); 97 unsigned AddrSpace = DestPtr->getType()->getPointerAddressSpace(); 98 99 llvm::IntegerType *IntType = 100 llvm::IntegerType::get(CGF.getLLVMContext(), 101 CGF.getContext().getTypeSize(T)); 102 llvm::Type *IntPtrType = IntType->getPointerTo(AddrSpace); 103 104 llvm::Value *Args[2]; 105 Args[0] = CGF.Builder.CreateBitCast(DestPtr, IntPtrType); 106 Args[1] = CGF.EmitScalarExpr(E->getArg(1)); 107 llvm::Type *ValueType = Args[1]->getType(); 108 Args[1] = EmitToInt(CGF, Args[1], T, IntType); 109 110 llvm::Value *Result = CGF.Builder.CreateAtomicRMW( 111 Kind, Args[0], Args[1], llvm::AtomicOrdering::SequentiallyConsistent); 112 return EmitFromInt(CGF, Result, T, ValueType); 113 } 114 115 static Value *EmitNontemporalStore(CodeGenFunction &CGF, const CallExpr *E) { 116 Value *Val = CGF.EmitScalarExpr(E->getArg(0)); 117 Value *Address = CGF.EmitScalarExpr(E->getArg(1)); 118 119 // Convert the type of the pointer to a pointer to the stored type. 120 Val = CGF.EmitToMemory(Val, E->getArg(0)->getType()); 121 Value *BC = CGF.Builder.CreateBitCast( 122 Address, llvm::PointerType::getUnqual(Val->getType()), "cast"); 123 LValue LV = CGF.MakeNaturalAlignAddrLValue(BC, E->getArg(0)->getType()); 124 LV.setNontemporal(true); 125 CGF.EmitStoreOfScalar(Val, LV, false); 126 return nullptr; 127 } 128 129 static Value *EmitNontemporalLoad(CodeGenFunction &CGF, const CallExpr *E) { 130 Value *Address = CGF.EmitScalarExpr(E->getArg(0)); 131 132 LValue LV = CGF.MakeNaturalAlignAddrLValue(Address, E->getType()); 133 LV.setNontemporal(true); 134 return CGF.EmitLoadOfScalar(LV, E->getExprLoc()); 135 } 136 137 static RValue EmitBinaryAtomic(CodeGenFunction &CGF, 138 llvm::AtomicRMWInst::BinOp Kind, 139 const CallExpr *E) { 140 return RValue::get(MakeBinaryAtomicValue(CGF, Kind, E)); 141 } 142 143 /// Utility to insert an atomic instruction based Instrinsic::ID and 144 /// the expression node, where the return value is the result of the 145 /// operation. 146 static RValue EmitBinaryAtomicPost(CodeGenFunction &CGF, 147 llvm::AtomicRMWInst::BinOp Kind, 148 const CallExpr *E, 149 Instruction::BinaryOps Op, 150 bool Invert = false) { 151 QualType T = E->getType(); 152 assert(E->getArg(0)->getType()->isPointerType()); 153 assert(CGF.getContext().hasSameUnqualifiedType(T, 154 E->getArg(0)->getType()->getPointeeType())); 155 assert(CGF.getContext().hasSameUnqualifiedType(T, E->getArg(1)->getType())); 156 157 llvm::Value *DestPtr = CGF.EmitScalarExpr(E->getArg(0)); 158 unsigned AddrSpace = DestPtr->getType()->getPointerAddressSpace(); 159 160 llvm::IntegerType *IntType = 161 llvm::IntegerType::get(CGF.getLLVMContext(), 162 CGF.getContext().getTypeSize(T)); 163 llvm::Type *IntPtrType = IntType->getPointerTo(AddrSpace); 164 165 llvm::Value *Args[2]; 166 Args[1] = CGF.EmitScalarExpr(E->getArg(1)); 167 llvm::Type *ValueType = Args[1]->getType(); 168 Args[1] = EmitToInt(CGF, Args[1], T, IntType); 169 Args[0] = CGF.Builder.CreateBitCast(DestPtr, IntPtrType); 170 171 llvm::Value *Result = CGF.Builder.CreateAtomicRMW( 172 Kind, Args[0], Args[1], llvm::AtomicOrdering::SequentiallyConsistent); 173 Result = CGF.Builder.CreateBinOp(Op, Result, Args[1]); 174 if (Invert) 175 Result = CGF.Builder.CreateBinOp(llvm::Instruction::Xor, Result, 176 llvm::ConstantInt::get(IntType, -1)); 177 Result = EmitFromInt(CGF, Result, T, ValueType); 178 return RValue::get(Result); 179 } 180 181 /// @brief Utility to insert an atomic cmpxchg instruction. 182 /// 183 /// @param CGF The current codegen function. 184 /// @param E Builtin call expression to convert to cmpxchg. 185 /// arg0 - address to operate on 186 /// arg1 - value to compare with 187 /// arg2 - new value 188 /// @param ReturnBool Specifies whether to return success flag of 189 /// cmpxchg result or the old value. 190 /// 191 /// @returns result of cmpxchg, according to ReturnBool 192 static Value *MakeAtomicCmpXchgValue(CodeGenFunction &CGF, const CallExpr *E, 193 bool ReturnBool) { 194 QualType T = ReturnBool ? E->getArg(1)->getType() : E->getType(); 195 llvm::Value *DestPtr = CGF.EmitScalarExpr(E->getArg(0)); 196 unsigned AddrSpace = DestPtr->getType()->getPointerAddressSpace(); 197 198 llvm::IntegerType *IntType = llvm::IntegerType::get( 199 CGF.getLLVMContext(), CGF.getContext().getTypeSize(T)); 200 llvm::Type *IntPtrType = IntType->getPointerTo(AddrSpace); 201 202 Value *Args[3]; 203 Args[0] = CGF.Builder.CreateBitCast(DestPtr, IntPtrType); 204 Args[1] = CGF.EmitScalarExpr(E->getArg(1)); 205 llvm::Type *ValueType = Args[1]->getType(); 206 Args[1] = EmitToInt(CGF, Args[1], T, IntType); 207 Args[2] = EmitToInt(CGF, CGF.EmitScalarExpr(E->getArg(2)), T, IntType); 208 209 Value *Pair = CGF.Builder.CreateAtomicCmpXchg( 210 Args[0], Args[1], Args[2], llvm::AtomicOrdering::SequentiallyConsistent, 211 llvm::AtomicOrdering::SequentiallyConsistent); 212 if (ReturnBool) 213 // Extract boolean success flag and zext it to int. 214 return CGF.Builder.CreateZExt(CGF.Builder.CreateExtractValue(Pair, 1), 215 CGF.ConvertType(E->getType())); 216 else 217 // Extract old value and emit it using the same type as compare value. 218 return EmitFromInt(CGF, CGF.Builder.CreateExtractValue(Pair, 0), T, 219 ValueType); 220 } 221 222 // Emit a simple mangled intrinsic that has 1 argument and a return type 223 // matching the argument type. 224 static Value *emitUnaryBuiltin(CodeGenFunction &CGF, 225 const CallExpr *E, 226 unsigned IntrinsicID) { 227 llvm::Value *Src0 = CGF.EmitScalarExpr(E->getArg(0)); 228 229 Value *F = CGF.CGM.getIntrinsic(IntrinsicID, Src0->getType()); 230 return CGF.Builder.CreateCall(F, Src0); 231 } 232 233 // Emit an intrinsic that has 2 operands of the same type as its result. 234 static Value *emitBinaryBuiltin(CodeGenFunction &CGF, 235 const CallExpr *E, 236 unsigned IntrinsicID) { 237 llvm::Value *Src0 = CGF.EmitScalarExpr(E->getArg(0)); 238 llvm::Value *Src1 = CGF.EmitScalarExpr(E->getArg(1)); 239 240 Value *F = CGF.CGM.getIntrinsic(IntrinsicID, Src0->getType()); 241 return CGF.Builder.CreateCall(F, { Src0, Src1 }); 242 } 243 244 // Emit an intrinsic that has 3 operands of the same type as its result. 245 static Value *emitTernaryBuiltin(CodeGenFunction &CGF, 246 const CallExpr *E, 247 unsigned IntrinsicID) { 248 llvm::Value *Src0 = CGF.EmitScalarExpr(E->getArg(0)); 249 llvm::Value *Src1 = CGF.EmitScalarExpr(E->getArg(1)); 250 llvm::Value *Src2 = CGF.EmitScalarExpr(E->getArg(2)); 251 252 Value *F = CGF.CGM.getIntrinsic(IntrinsicID, Src0->getType()); 253 return CGF.Builder.CreateCall(F, { Src0, Src1, Src2 }); 254 } 255 256 // Emit an intrinsic that has 1 float or double operand, and 1 integer. 257 static Value *emitFPIntBuiltin(CodeGenFunction &CGF, 258 const CallExpr *E, 259 unsigned IntrinsicID) { 260 llvm::Value *Src0 = CGF.EmitScalarExpr(E->getArg(0)); 261 llvm::Value *Src1 = CGF.EmitScalarExpr(E->getArg(1)); 262 263 Value *F = CGF.CGM.getIntrinsic(IntrinsicID, Src0->getType()); 264 return CGF.Builder.CreateCall(F, {Src0, Src1}); 265 } 266 267 /// EmitFAbs - Emit a call to @llvm.fabs(). 268 static Value *EmitFAbs(CodeGenFunction &CGF, Value *V) { 269 Value *F = CGF.CGM.getIntrinsic(Intrinsic::fabs, V->getType()); 270 llvm::CallInst *Call = CGF.Builder.CreateCall(F, V); 271 Call->setDoesNotAccessMemory(); 272 return Call; 273 } 274 275 /// Emit the computation of the sign bit for a floating point value. Returns 276 /// the i1 sign bit value. 277 static Value *EmitSignBit(CodeGenFunction &CGF, Value *V) { 278 LLVMContext &C = CGF.CGM.getLLVMContext(); 279 280 llvm::Type *Ty = V->getType(); 281 int Width = Ty->getPrimitiveSizeInBits(); 282 llvm::Type *IntTy = llvm::IntegerType::get(C, Width); 283 V = CGF.Builder.CreateBitCast(V, IntTy); 284 if (Ty->isPPC_FP128Ty()) { 285 // We want the sign bit of the higher-order double. The bitcast we just 286 // did works as if the double-double was stored to memory and then 287 // read as an i128. The "store" will put the higher-order double in the 288 // lower address in both little- and big-Endian modes, but the "load" 289 // will treat those bits as a different part of the i128: the low bits in 290 // little-Endian, the high bits in big-Endian. Therefore, on big-Endian 291 // we need to shift the high bits down to the low before truncating. 292 Width >>= 1; 293 if (CGF.getTarget().isBigEndian()) { 294 Value *ShiftCst = llvm::ConstantInt::get(IntTy, Width); 295 V = CGF.Builder.CreateLShr(V, ShiftCst); 296 } 297 // We are truncating value in order to extract the higher-order 298 // double, which we will be using to extract the sign from. 299 IntTy = llvm::IntegerType::get(C, Width); 300 V = CGF.Builder.CreateTrunc(V, IntTy); 301 } 302 Value *Zero = llvm::Constant::getNullValue(IntTy); 303 return CGF.Builder.CreateICmpSLT(V, Zero); 304 } 305 306 static RValue emitLibraryCall(CodeGenFunction &CGF, const FunctionDecl *Fn, 307 const CallExpr *E, llvm::Value *calleeValue) { 308 return CGF.EmitCall(E->getCallee()->getType(), calleeValue, E, 309 ReturnValueSlot(), Fn); 310 } 311 312 /// \brief Emit a call to llvm.{sadd,uadd,ssub,usub,smul,umul}.with.overflow.* 313 /// depending on IntrinsicID. 314 /// 315 /// \arg CGF The current codegen function. 316 /// \arg IntrinsicID The ID for the Intrinsic we wish to generate. 317 /// \arg X The first argument to the llvm.*.with.overflow.*. 318 /// \arg Y The second argument to the llvm.*.with.overflow.*. 319 /// \arg Carry The carry returned by the llvm.*.with.overflow.*. 320 /// \returns The result (i.e. sum/product) returned by the intrinsic. 321 static llvm::Value *EmitOverflowIntrinsic(CodeGenFunction &CGF, 322 const llvm::Intrinsic::ID IntrinsicID, 323 llvm::Value *X, llvm::Value *Y, 324 llvm::Value *&Carry) { 325 // Make sure we have integers of the same width. 326 assert(X->getType() == Y->getType() && 327 "Arguments must be the same type. (Did you forget to make sure both " 328 "arguments have the same integer width?)"); 329 330 llvm::Value *Callee = CGF.CGM.getIntrinsic(IntrinsicID, X->getType()); 331 llvm::Value *Tmp = CGF.Builder.CreateCall(Callee, {X, Y}); 332 Carry = CGF.Builder.CreateExtractValue(Tmp, 1); 333 return CGF.Builder.CreateExtractValue(Tmp, 0); 334 } 335 336 static Value *emitRangedBuiltin(CodeGenFunction &CGF, 337 unsigned IntrinsicID, 338 int low, int high) { 339 llvm::MDBuilder MDHelper(CGF.getLLVMContext()); 340 llvm::MDNode *RNode = MDHelper.createRange(APInt(32, low), APInt(32, high)); 341 Value *F = CGF.CGM.getIntrinsic(IntrinsicID, {}); 342 llvm::Instruction *Call = CGF.Builder.CreateCall(F); 343 Call->setMetadata(llvm::LLVMContext::MD_range, RNode); 344 return Call; 345 } 346 347 namespace { 348 struct WidthAndSignedness { 349 unsigned Width; 350 bool Signed; 351 }; 352 } 353 354 static WidthAndSignedness 355 getIntegerWidthAndSignedness(const clang::ASTContext &context, 356 const clang::QualType Type) { 357 assert(Type->isIntegerType() && "Given type is not an integer."); 358 unsigned Width = Type->isBooleanType() ? 1 : context.getTypeInfo(Type).Width; 359 bool Signed = Type->isSignedIntegerType(); 360 return {Width, Signed}; 361 } 362 363 // Given one or more integer types, this function produces an integer type that 364 // encompasses them: any value in one of the given types could be expressed in 365 // the encompassing type. 366 static struct WidthAndSignedness 367 EncompassingIntegerType(ArrayRef<struct WidthAndSignedness> Types) { 368 assert(Types.size() > 0 && "Empty list of types."); 369 370 // If any of the given types is signed, we must return a signed type. 371 bool Signed = false; 372 for (const auto &Type : Types) { 373 Signed |= Type.Signed; 374 } 375 376 // The encompassing type must have a width greater than or equal to the width 377 // of the specified types. Aditionally, if the encompassing type is signed, 378 // its width must be strictly greater than the width of any unsigned types 379 // given. 380 unsigned Width = 0; 381 for (const auto &Type : Types) { 382 unsigned MinWidth = Type.Width + (Signed && !Type.Signed); 383 if (Width < MinWidth) { 384 Width = MinWidth; 385 } 386 } 387 388 return {Width, Signed}; 389 } 390 391 Value *CodeGenFunction::EmitVAStartEnd(Value *ArgValue, bool IsStart) { 392 llvm::Type *DestType = Int8PtrTy; 393 if (ArgValue->getType() != DestType) 394 ArgValue = 395 Builder.CreateBitCast(ArgValue, DestType, ArgValue->getName().data()); 396 397 Intrinsic::ID inst = IsStart ? Intrinsic::vastart : Intrinsic::vaend; 398 return Builder.CreateCall(CGM.getIntrinsic(inst), ArgValue); 399 } 400 401 /// Checks if using the result of __builtin_object_size(p, @p From) in place of 402 /// __builtin_object_size(p, @p To) is correct 403 static bool areBOSTypesCompatible(int From, int To) { 404 // Note: Our __builtin_object_size implementation currently treats Type=0 and 405 // Type=2 identically. Encoding this implementation detail here may make 406 // improving __builtin_object_size difficult in the future, so it's omitted. 407 return From == To || (From == 0 && To == 1) || (From == 3 && To == 2); 408 } 409 410 static llvm::Value * 411 getDefaultBuiltinObjectSizeResult(unsigned Type, llvm::IntegerType *ResType) { 412 return ConstantInt::get(ResType, (Type & 2) ? 0 : -1, /*isSigned=*/true); 413 } 414 415 llvm::Value * 416 CodeGenFunction::evaluateOrEmitBuiltinObjectSize(const Expr *E, unsigned Type, 417 llvm::IntegerType *ResType) { 418 uint64_t ObjectSize; 419 if (!E->tryEvaluateObjectSize(ObjectSize, getContext(), Type)) 420 return emitBuiltinObjectSize(E, Type, ResType); 421 return ConstantInt::get(ResType, ObjectSize, /*isSigned=*/true); 422 } 423 424 /// Returns a Value corresponding to the size of the given expression. 425 /// This Value may be either of the following: 426 /// - A llvm::Argument (if E is a param with the pass_object_size attribute on 427 /// it) 428 /// - A call to the @llvm.objectsize intrinsic 429 llvm::Value * 430 CodeGenFunction::emitBuiltinObjectSize(const Expr *E, unsigned Type, 431 llvm::IntegerType *ResType) { 432 // We need to reference an argument if the pointer is a parameter with the 433 // pass_object_size attribute. 434 if (auto *D = dyn_cast<DeclRefExpr>(E->IgnoreParenImpCasts())) { 435 auto *Param = dyn_cast<ParmVarDecl>(D->getDecl()); 436 auto *PS = D->getDecl()->getAttr<PassObjectSizeAttr>(); 437 if (Param != nullptr && PS != nullptr && 438 areBOSTypesCompatible(PS->getType(), Type)) { 439 auto Iter = SizeArguments.find(Param); 440 assert(Iter != SizeArguments.end()); 441 442 const ImplicitParamDecl *D = Iter->second; 443 auto DIter = LocalDeclMap.find(D); 444 assert(DIter != LocalDeclMap.end()); 445 446 return EmitLoadOfScalar(DIter->second, /*volatile=*/false, 447 getContext().getSizeType(), E->getLocStart()); 448 } 449 } 450 451 // LLVM can't handle Type=3 appropriately, and __builtin_object_size shouldn't 452 // evaluate E for side-effects. In either case, we shouldn't lower to 453 // @llvm.objectsize. 454 if (Type == 3 || E->HasSideEffects(getContext())) 455 return getDefaultBuiltinObjectSizeResult(Type, ResType); 456 457 // LLVM only supports 0 and 2, make sure that we pass along that 458 // as a boolean. 459 auto *CI = ConstantInt::get(Builder.getInt1Ty(), (Type & 2) >> 1); 460 // FIXME: Get right address space. 461 llvm::Type *Tys[] = {ResType, Builder.getInt8PtrTy(0)}; 462 Value *F = CGM.getIntrinsic(Intrinsic::objectsize, Tys); 463 return Builder.CreateCall(F, {EmitScalarExpr(E), CI}); 464 } 465 466 RValue CodeGenFunction::EmitBuiltinExpr(const FunctionDecl *FD, 467 unsigned BuiltinID, const CallExpr *E, 468 ReturnValueSlot ReturnValue) { 469 // See if we can constant fold this builtin. If so, don't emit it at all. 470 Expr::EvalResult Result; 471 if (E->EvaluateAsRValue(Result, CGM.getContext()) && 472 !Result.hasSideEffects()) { 473 if (Result.Val.isInt()) 474 return RValue::get(llvm::ConstantInt::get(getLLVMContext(), 475 Result.Val.getInt())); 476 if (Result.Val.isFloat()) 477 return RValue::get(llvm::ConstantFP::get(getLLVMContext(), 478 Result.Val.getFloat())); 479 } 480 481 switch (BuiltinID) { 482 default: break; // Handle intrinsics and libm functions below. 483 case Builtin::BI__builtin___CFStringMakeConstantString: 484 case Builtin::BI__builtin___NSStringMakeConstantString: 485 return RValue::get(CGM.EmitConstantExpr(E, E->getType(), nullptr)); 486 case Builtin::BI__builtin_stdarg_start: 487 case Builtin::BI__builtin_va_start: 488 case Builtin::BI__va_start: 489 case Builtin::BI__builtin_va_end: 490 return RValue::get( 491 EmitVAStartEnd(BuiltinID == Builtin::BI__va_start 492 ? EmitScalarExpr(E->getArg(0)) 493 : EmitVAListRef(E->getArg(0)).getPointer(), 494 BuiltinID != Builtin::BI__builtin_va_end)); 495 case Builtin::BI__builtin_va_copy: { 496 Value *DstPtr = EmitVAListRef(E->getArg(0)).getPointer(); 497 Value *SrcPtr = EmitVAListRef(E->getArg(1)).getPointer(); 498 499 llvm::Type *Type = Int8PtrTy; 500 501 DstPtr = Builder.CreateBitCast(DstPtr, Type); 502 SrcPtr = Builder.CreateBitCast(SrcPtr, Type); 503 return RValue::get(Builder.CreateCall(CGM.getIntrinsic(Intrinsic::vacopy), 504 {DstPtr, SrcPtr})); 505 } 506 case Builtin::BI__builtin_abs: 507 case Builtin::BI__builtin_labs: 508 case Builtin::BI__builtin_llabs: { 509 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 510 511 Value *NegOp = Builder.CreateNeg(ArgValue, "neg"); 512 Value *CmpResult = 513 Builder.CreateICmpSGE(ArgValue, 514 llvm::Constant::getNullValue(ArgValue->getType()), 515 "abscond"); 516 Value *Result = 517 Builder.CreateSelect(CmpResult, ArgValue, NegOp, "abs"); 518 519 return RValue::get(Result); 520 } 521 case Builtin::BI__builtin_fabs: 522 case Builtin::BI__builtin_fabsf: 523 case Builtin::BI__builtin_fabsl: { 524 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::fabs)); 525 } 526 case Builtin::BI__builtin_fmod: 527 case Builtin::BI__builtin_fmodf: 528 case Builtin::BI__builtin_fmodl: { 529 Value *Arg1 = EmitScalarExpr(E->getArg(0)); 530 Value *Arg2 = EmitScalarExpr(E->getArg(1)); 531 Value *Result = Builder.CreateFRem(Arg1, Arg2, "fmod"); 532 return RValue::get(Result); 533 } 534 case Builtin::BI__builtin_copysign: 535 case Builtin::BI__builtin_copysignf: 536 case Builtin::BI__builtin_copysignl: { 537 return RValue::get(emitBinaryBuiltin(*this, E, Intrinsic::copysign)); 538 } 539 case Builtin::BI__builtin_ceil: 540 case Builtin::BI__builtin_ceilf: 541 case Builtin::BI__builtin_ceill: { 542 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::ceil)); 543 } 544 case Builtin::BI__builtin_floor: 545 case Builtin::BI__builtin_floorf: 546 case Builtin::BI__builtin_floorl: { 547 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::floor)); 548 } 549 case Builtin::BI__builtin_trunc: 550 case Builtin::BI__builtin_truncf: 551 case Builtin::BI__builtin_truncl: { 552 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::trunc)); 553 } 554 case Builtin::BI__builtin_rint: 555 case Builtin::BI__builtin_rintf: 556 case Builtin::BI__builtin_rintl: { 557 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::rint)); 558 } 559 case Builtin::BI__builtin_nearbyint: 560 case Builtin::BI__builtin_nearbyintf: 561 case Builtin::BI__builtin_nearbyintl: { 562 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::nearbyint)); 563 } 564 case Builtin::BI__builtin_round: 565 case Builtin::BI__builtin_roundf: 566 case Builtin::BI__builtin_roundl: { 567 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::round)); 568 } 569 case Builtin::BI__builtin_fmin: 570 case Builtin::BI__builtin_fminf: 571 case Builtin::BI__builtin_fminl: { 572 return RValue::get(emitBinaryBuiltin(*this, E, Intrinsic::minnum)); 573 } 574 case Builtin::BI__builtin_fmax: 575 case Builtin::BI__builtin_fmaxf: 576 case Builtin::BI__builtin_fmaxl: { 577 return RValue::get(emitBinaryBuiltin(*this, E, Intrinsic::maxnum)); 578 } 579 case Builtin::BI__builtin_conj: 580 case Builtin::BI__builtin_conjf: 581 case Builtin::BI__builtin_conjl: { 582 ComplexPairTy ComplexVal = EmitComplexExpr(E->getArg(0)); 583 Value *Real = ComplexVal.first; 584 Value *Imag = ComplexVal.second; 585 Value *Zero = 586 Imag->getType()->isFPOrFPVectorTy() 587 ? llvm::ConstantFP::getZeroValueForNegation(Imag->getType()) 588 : llvm::Constant::getNullValue(Imag->getType()); 589 590 Imag = Builder.CreateFSub(Zero, Imag, "sub"); 591 return RValue::getComplex(std::make_pair(Real, Imag)); 592 } 593 case Builtin::BI__builtin_creal: 594 case Builtin::BI__builtin_crealf: 595 case Builtin::BI__builtin_creall: 596 case Builtin::BIcreal: 597 case Builtin::BIcrealf: 598 case Builtin::BIcreall: { 599 ComplexPairTy ComplexVal = EmitComplexExpr(E->getArg(0)); 600 return RValue::get(ComplexVal.first); 601 } 602 603 case Builtin::BI__builtin_cimag: 604 case Builtin::BI__builtin_cimagf: 605 case Builtin::BI__builtin_cimagl: 606 case Builtin::BIcimag: 607 case Builtin::BIcimagf: 608 case Builtin::BIcimagl: { 609 ComplexPairTy ComplexVal = EmitComplexExpr(E->getArg(0)); 610 return RValue::get(ComplexVal.second); 611 } 612 613 case Builtin::BI__builtin_ctzs: 614 case Builtin::BI__builtin_ctz: 615 case Builtin::BI__builtin_ctzl: 616 case Builtin::BI__builtin_ctzll: { 617 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 618 619 llvm::Type *ArgType = ArgValue->getType(); 620 Value *F = CGM.getIntrinsic(Intrinsic::cttz, ArgType); 621 622 llvm::Type *ResultType = ConvertType(E->getType()); 623 Value *ZeroUndef = Builder.getInt1(getTarget().isCLZForZeroUndef()); 624 Value *Result = Builder.CreateCall(F, {ArgValue, ZeroUndef}); 625 if (Result->getType() != ResultType) 626 Result = Builder.CreateIntCast(Result, ResultType, /*isSigned*/true, 627 "cast"); 628 return RValue::get(Result); 629 } 630 case Builtin::BI__builtin_clzs: 631 case Builtin::BI__builtin_clz: 632 case Builtin::BI__builtin_clzl: 633 case Builtin::BI__builtin_clzll: { 634 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 635 636 llvm::Type *ArgType = ArgValue->getType(); 637 Value *F = CGM.getIntrinsic(Intrinsic::ctlz, ArgType); 638 639 llvm::Type *ResultType = ConvertType(E->getType()); 640 Value *ZeroUndef = Builder.getInt1(getTarget().isCLZForZeroUndef()); 641 Value *Result = Builder.CreateCall(F, {ArgValue, ZeroUndef}); 642 if (Result->getType() != ResultType) 643 Result = Builder.CreateIntCast(Result, ResultType, /*isSigned*/true, 644 "cast"); 645 return RValue::get(Result); 646 } 647 case Builtin::BI__builtin_ffs: 648 case Builtin::BI__builtin_ffsl: 649 case Builtin::BI__builtin_ffsll: { 650 // ffs(x) -> x ? cttz(x) + 1 : 0 651 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 652 653 llvm::Type *ArgType = ArgValue->getType(); 654 Value *F = CGM.getIntrinsic(Intrinsic::cttz, ArgType); 655 656 llvm::Type *ResultType = ConvertType(E->getType()); 657 Value *Tmp = 658 Builder.CreateAdd(Builder.CreateCall(F, {ArgValue, Builder.getTrue()}), 659 llvm::ConstantInt::get(ArgType, 1)); 660 Value *Zero = llvm::Constant::getNullValue(ArgType); 661 Value *IsZero = Builder.CreateICmpEQ(ArgValue, Zero, "iszero"); 662 Value *Result = Builder.CreateSelect(IsZero, Zero, Tmp, "ffs"); 663 if (Result->getType() != ResultType) 664 Result = Builder.CreateIntCast(Result, ResultType, /*isSigned*/true, 665 "cast"); 666 return RValue::get(Result); 667 } 668 case Builtin::BI__builtin_parity: 669 case Builtin::BI__builtin_parityl: 670 case Builtin::BI__builtin_parityll: { 671 // parity(x) -> ctpop(x) & 1 672 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 673 674 llvm::Type *ArgType = ArgValue->getType(); 675 Value *F = CGM.getIntrinsic(Intrinsic::ctpop, ArgType); 676 677 llvm::Type *ResultType = ConvertType(E->getType()); 678 Value *Tmp = Builder.CreateCall(F, ArgValue); 679 Value *Result = Builder.CreateAnd(Tmp, llvm::ConstantInt::get(ArgType, 1)); 680 if (Result->getType() != ResultType) 681 Result = Builder.CreateIntCast(Result, ResultType, /*isSigned*/true, 682 "cast"); 683 return RValue::get(Result); 684 } 685 case Builtin::BI__popcnt16: 686 case Builtin::BI__popcnt: 687 case Builtin::BI__popcnt64: 688 case Builtin::BI__builtin_popcount: 689 case Builtin::BI__builtin_popcountl: 690 case Builtin::BI__builtin_popcountll: { 691 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 692 693 llvm::Type *ArgType = ArgValue->getType(); 694 Value *F = CGM.getIntrinsic(Intrinsic::ctpop, ArgType); 695 696 llvm::Type *ResultType = ConvertType(E->getType()); 697 Value *Result = Builder.CreateCall(F, ArgValue); 698 if (Result->getType() != ResultType) 699 Result = Builder.CreateIntCast(Result, ResultType, /*isSigned*/true, 700 "cast"); 701 return RValue::get(Result); 702 } 703 case Builtin::BI_rotr8: 704 case Builtin::BI_rotr16: 705 case Builtin::BI_rotr: 706 case Builtin::BI_lrotr: 707 case Builtin::BI_rotr64: { 708 Value *Val = EmitScalarExpr(E->getArg(0)); 709 Value *Shift = EmitScalarExpr(E->getArg(1)); 710 711 llvm::Type *ArgType = Val->getType(); 712 Shift = Builder.CreateIntCast(Shift, ArgType, false); 713 unsigned ArgWidth = cast<llvm::IntegerType>(ArgType)->getBitWidth(); 714 Value *ArgTypeSize = llvm::ConstantInt::get(ArgType, ArgWidth); 715 Value *ArgZero = llvm::Constant::getNullValue(ArgType); 716 717 Value *Mask = llvm::ConstantInt::get(ArgType, ArgWidth - 1); 718 Shift = Builder.CreateAnd(Shift, Mask); 719 Value *LeftShift = Builder.CreateSub(ArgTypeSize, Shift); 720 721 Value *RightShifted = Builder.CreateLShr(Val, Shift); 722 Value *LeftShifted = Builder.CreateShl(Val, LeftShift); 723 Value *Rotated = Builder.CreateOr(LeftShifted, RightShifted); 724 725 Value *ShiftIsZero = Builder.CreateICmpEQ(Shift, ArgZero); 726 Value *Result = Builder.CreateSelect(ShiftIsZero, Val, Rotated); 727 return RValue::get(Result); 728 } 729 case Builtin::BI_rotl8: 730 case Builtin::BI_rotl16: 731 case Builtin::BI_rotl: 732 case Builtin::BI_lrotl: 733 case Builtin::BI_rotl64: { 734 Value *Val = EmitScalarExpr(E->getArg(0)); 735 Value *Shift = EmitScalarExpr(E->getArg(1)); 736 737 llvm::Type *ArgType = Val->getType(); 738 Shift = Builder.CreateIntCast(Shift, ArgType, false); 739 unsigned ArgWidth = cast<llvm::IntegerType>(ArgType)->getBitWidth(); 740 Value *ArgTypeSize = llvm::ConstantInt::get(ArgType, ArgWidth); 741 Value *ArgZero = llvm::Constant::getNullValue(ArgType); 742 743 Value *Mask = llvm::ConstantInt::get(ArgType, ArgWidth - 1); 744 Shift = Builder.CreateAnd(Shift, Mask); 745 Value *RightShift = Builder.CreateSub(ArgTypeSize, Shift); 746 747 Value *LeftShifted = Builder.CreateShl(Val, Shift); 748 Value *RightShifted = Builder.CreateLShr(Val, RightShift); 749 Value *Rotated = Builder.CreateOr(LeftShifted, RightShifted); 750 751 Value *ShiftIsZero = Builder.CreateICmpEQ(Shift, ArgZero); 752 Value *Result = Builder.CreateSelect(ShiftIsZero, Val, Rotated); 753 return RValue::get(Result); 754 } 755 case Builtin::BI__builtin_unpredictable: { 756 // Always return the argument of __builtin_unpredictable. LLVM does not 757 // handle this builtin. Metadata for this builtin should be added directly 758 // to instructions such as branches or switches that use it. 759 return RValue::get(EmitScalarExpr(E->getArg(0))); 760 } 761 case Builtin::BI__builtin_expect: { 762 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 763 llvm::Type *ArgType = ArgValue->getType(); 764 765 Value *ExpectedValue = EmitScalarExpr(E->getArg(1)); 766 // Don't generate llvm.expect on -O0 as the backend won't use it for 767 // anything. 768 // Note, we still IRGen ExpectedValue because it could have side-effects. 769 if (CGM.getCodeGenOpts().OptimizationLevel == 0) 770 return RValue::get(ArgValue); 771 772 Value *FnExpect = CGM.getIntrinsic(Intrinsic::expect, ArgType); 773 Value *Result = 774 Builder.CreateCall(FnExpect, {ArgValue, ExpectedValue}, "expval"); 775 return RValue::get(Result); 776 } 777 case Builtin::BI__builtin_assume_aligned: { 778 Value *PtrValue = EmitScalarExpr(E->getArg(0)); 779 Value *OffsetValue = 780 (E->getNumArgs() > 2) ? EmitScalarExpr(E->getArg(2)) : nullptr; 781 782 Value *AlignmentValue = EmitScalarExpr(E->getArg(1)); 783 ConstantInt *AlignmentCI = cast<ConstantInt>(AlignmentValue); 784 unsigned Alignment = (unsigned) AlignmentCI->getZExtValue(); 785 786 EmitAlignmentAssumption(PtrValue, Alignment, OffsetValue); 787 return RValue::get(PtrValue); 788 } 789 case Builtin::BI__assume: 790 case Builtin::BI__builtin_assume: { 791 if (E->getArg(0)->HasSideEffects(getContext())) 792 return RValue::get(nullptr); 793 794 Value *ArgValue = EmitScalarExpr(E->getArg(0)); 795 Value *FnAssume = CGM.getIntrinsic(Intrinsic::assume); 796 return RValue::get(Builder.CreateCall(FnAssume, ArgValue)); 797 } 798 case Builtin::BI__builtin_bswap16: 799 case Builtin::BI__builtin_bswap32: 800 case Builtin::BI__builtin_bswap64: { 801 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::bswap)); 802 } 803 case Builtin::BI__builtin_bitreverse8: 804 case Builtin::BI__builtin_bitreverse16: 805 case Builtin::BI__builtin_bitreverse32: 806 case Builtin::BI__builtin_bitreverse64: { 807 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::bitreverse)); 808 } 809 case Builtin::BI__builtin_object_size: { 810 unsigned Type = 811 E->getArg(1)->EvaluateKnownConstInt(getContext()).getZExtValue(); 812 auto *ResType = cast<llvm::IntegerType>(ConvertType(E->getType())); 813 814 // We pass this builtin onto the optimizer so that it can figure out the 815 // object size in more complex cases. 816 return RValue::get(emitBuiltinObjectSize(E->getArg(0), Type, ResType)); 817 } 818 case Builtin::BI__builtin_prefetch: { 819 Value *Locality, *RW, *Address = EmitScalarExpr(E->getArg(0)); 820 // FIXME: Technically these constants should of type 'int', yes? 821 RW = (E->getNumArgs() > 1) ? EmitScalarExpr(E->getArg(1)) : 822 llvm::ConstantInt::get(Int32Ty, 0); 823 Locality = (E->getNumArgs() > 2) ? EmitScalarExpr(E->getArg(2)) : 824 llvm::ConstantInt::get(Int32Ty, 3); 825 Value *Data = llvm::ConstantInt::get(Int32Ty, 1); 826 Value *F = CGM.getIntrinsic(Intrinsic::prefetch); 827 return RValue::get(Builder.CreateCall(F, {Address, RW, Locality, Data})); 828 } 829 case Builtin::BI__builtin_readcyclecounter: { 830 Value *F = CGM.getIntrinsic(Intrinsic::readcyclecounter); 831 return RValue::get(Builder.CreateCall(F)); 832 } 833 case Builtin::BI__builtin___clear_cache: { 834 Value *Begin = EmitScalarExpr(E->getArg(0)); 835 Value *End = EmitScalarExpr(E->getArg(1)); 836 Value *F = CGM.getIntrinsic(Intrinsic::clear_cache); 837 return RValue::get(Builder.CreateCall(F, {Begin, End})); 838 } 839 case Builtin::BI__builtin_trap: 840 return RValue::get(EmitTrapCall(Intrinsic::trap)); 841 case Builtin::BI__debugbreak: 842 return RValue::get(EmitTrapCall(Intrinsic::debugtrap)); 843 case Builtin::BI__builtin_unreachable: { 844 if (SanOpts.has(SanitizerKind::Unreachable)) { 845 SanitizerScope SanScope(this); 846 EmitCheck(std::make_pair(static_cast<llvm::Value *>(Builder.getFalse()), 847 SanitizerKind::Unreachable), 848 "builtin_unreachable", EmitCheckSourceLocation(E->getExprLoc()), 849 None); 850 } else 851 Builder.CreateUnreachable(); 852 853 // We do need to preserve an insertion point. 854 EmitBlock(createBasicBlock("unreachable.cont")); 855 856 return RValue::get(nullptr); 857 } 858 859 case Builtin::BI__builtin_powi: 860 case Builtin::BI__builtin_powif: 861 case Builtin::BI__builtin_powil: { 862 Value *Base = EmitScalarExpr(E->getArg(0)); 863 Value *Exponent = EmitScalarExpr(E->getArg(1)); 864 llvm::Type *ArgType = Base->getType(); 865 Value *F = CGM.getIntrinsic(Intrinsic::powi, ArgType); 866 return RValue::get(Builder.CreateCall(F, {Base, Exponent})); 867 } 868 869 case Builtin::BI__builtin_isgreater: 870 case Builtin::BI__builtin_isgreaterequal: 871 case Builtin::BI__builtin_isless: 872 case Builtin::BI__builtin_islessequal: 873 case Builtin::BI__builtin_islessgreater: 874 case Builtin::BI__builtin_isunordered: { 875 // Ordered comparisons: we know the arguments to these are matching scalar 876 // floating point values. 877 Value *LHS = EmitScalarExpr(E->getArg(0)); 878 Value *RHS = EmitScalarExpr(E->getArg(1)); 879 880 switch (BuiltinID) { 881 default: llvm_unreachable("Unknown ordered comparison"); 882 case Builtin::BI__builtin_isgreater: 883 LHS = Builder.CreateFCmpOGT(LHS, RHS, "cmp"); 884 break; 885 case Builtin::BI__builtin_isgreaterequal: 886 LHS = Builder.CreateFCmpOGE(LHS, RHS, "cmp"); 887 break; 888 case Builtin::BI__builtin_isless: 889 LHS = Builder.CreateFCmpOLT(LHS, RHS, "cmp"); 890 break; 891 case Builtin::BI__builtin_islessequal: 892 LHS = Builder.CreateFCmpOLE(LHS, RHS, "cmp"); 893 break; 894 case Builtin::BI__builtin_islessgreater: 895 LHS = Builder.CreateFCmpONE(LHS, RHS, "cmp"); 896 break; 897 case Builtin::BI__builtin_isunordered: 898 LHS = Builder.CreateFCmpUNO(LHS, RHS, "cmp"); 899 break; 900 } 901 // ZExt bool to int type. 902 return RValue::get(Builder.CreateZExt(LHS, ConvertType(E->getType()))); 903 } 904 case Builtin::BI__builtin_isnan: { 905 Value *V = EmitScalarExpr(E->getArg(0)); 906 V = Builder.CreateFCmpUNO(V, V, "cmp"); 907 return RValue::get(Builder.CreateZExt(V, ConvertType(E->getType()))); 908 } 909 910 case Builtin::BIfinite: 911 case Builtin::BI__finite: 912 case Builtin::BIfinitef: 913 case Builtin::BI__finitef: 914 case Builtin::BIfinitel: 915 case Builtin::BI__finitel: 916 case Builtin::BI__builtin_isinf: 917 case Builtin::BI__builtin_isfinite: { 918 // isinf(x) --> fabs(x) == infinity 919 // isfinite(x) --> fabs(x) != infinity 920 // x != NaN via the ordered compare in either case. 921 Value *V = EmitScalarExpr(E->getArg(0)); 922 Value *Fabs = EmitFAbs(*this, V); 923 Constant *Infinity = ConstantFP::getInfinity(V->getType()); 924 CmpInst::Predicate Pred = (BuiltinID == Builtin::BI__builtin_isinf) 925 ? CmpInst::FCMP_OEQ 926 : CmpInst::FCMP_ONE; 927 Value *FCmp = Builder.CreateFCmp(Pred, Fabs, Infinity, "cmpinf"); 928 return RValue::get(Builder.CreateZExt(FCmp, ConvertType(E->getType()))); 929 } 930 931 case Builtin::BI__builtin_isinf_sign: { 932 // isinf_sign(x) -> fabs(x) == infinity ? (signbit(x) ? -1 : 1) : 0 933 Value *Arg = EmitScalarExpr(E->getArg(0)); 934 Value *AbsArg = EmitFAbs(*this, Arg); 935 Value *IsInf = Builder.CreateFCmpOEQ( 936 AbsArg, ConstantFP::getInfinity(Arg->getType()), "isinf"); 937 Value *IsNeg = EmitSignBit(*this, Arg); 938 939 llvm::Type *IntTy = ConvertType(E->getType()); 940 Value *Zero = Constant::getNullValue(IntTy); 941 Value *One = ConstantInt::get(IntTy, 1); 942 Value *NegativeOne = ConstantInt::get(IntTy, -1); 943 Value *SignResult = Builder.CreateSelect(IsNeg, NegativeOne, One); 944 Value *Result = Builder.CreateSelect(IsInf, SignResult, Zero); 945 return RValue::get(Result); 946 } 947 948 case Builtin::BI__builtin_isnormal: { 949 // isnormal(x) --> x == x && fabsf(x) < infinity && fabsf(x) >= float_min 950 Value *V = EmitScalarExpr(E->getArg(0)); 951 Value *Eq = Builder.CreateFCmpOEQ(V, V, "iseq"); 952 953 Value *Abs = EmitFAbs(*this, V); 954 Value *IsLessThanInf = 955 Builder.CreateFCmpULT(Abs, ConstantFP::getInfinity(V->getType()),"isinf"); 956 APFloat Smallest = APFloat::getSmallestNormalized( 957 getContext().getFloatTypeSemantics(E->getArg(0)->getType())); 958 Value *IsNormal = 959 Builder.CreateFCmpUGE(Abs, ConstantFP::get(V->getContext(), Smallest), 960 "isnormal"); 961 V = Builder.CreateAnd(Eq, IsLessThanInf, "and"); 962 V = Builder.CreateAnd(V, IsNormal, "and"); 963 return RValue::get(Builder.CreateZExt(V, ConvertType(E->getType()))); 964 } 965 966 case Builtin::BI__builtin_fpclassify: { 967 Value *V = EmitScalarExpr(E->getArg(5)); 968 llvm::Type *Ty = ConvertType(E->getArg(5)->getType()); 969 970 // Create Result 971 BasicBlock *Begin = Builder.GetInsertBlock(); 972 BasicBlock *End = createBasicBlock("fpclassify_end", this->CurFn); 973 Builder.SetInsertPoint(End); 974 PHINode *Result = 975 Builder.CreatePHI(ConvertType(E->getArg(0)->getType()), 4, 976 "fpclassify_result"); 977 978 // if (V==0) return FP_ZERO 979 Builder.SetInsertPoint(Begin); 980 Value *IsZero = Builder.CreateFCmpOEQ(V, Constant::getNullValue(Ty), 981 "iszero"); 982 Value *ZeroLiteral = EmitScalarExpr(E->getArg(4)); 983 BasicBlock *NotZero = createBasicBlock("fpclassify_not_zero", this->CurFn); 984 Builder.CreateCondBr(IsZero, End, NotZero); 985 Result->addIncoming(ZeroLiteral, Begin); 986 987 // if (V != V) return FP_NAN 988 Builder.SetInsertPoint(NotZero); 989 Value *IsNan = Builder.CreateFCmpUNO(V, V, "cmp"); 990 Value *NanLiteral = EmitScalarExpr(E->getArg(0)); 991 BasicBlock *NotNan = createBasicBlock("fpclassify_not_nan", this->CurFn); 992 Builder.CreateCondBr(IsNan, End, NotNan); 993 Result->addIncoming(NanLiteral, NotZero); 994 995 // if (fabs(V) == infinity) return FP_INFINITY 996 Builder.SetInsertPoint(NotNan); 997 Value *VAbs = EmitFAbs(*this, V); 998 Value *IsInf = 999 Builder.CreateFCmpOEQ(VAbs, ConstantFP::getInfinity(V->getType()), 1000 "isinf"); 1001 Value *InfLiteral = EmitScalarExpr(E->getArg(1)); 1002 BasicBlock *NotInf = createBasicBlock("fpclassify_not_inf", this->CurFn); 1003 Builder.CreateCondBr(IsInf, End, NotInf); 1004 Result->addIncoming(InfLiteral, NotNan); 1005 1006 // if (fabs(V) >= MIN_NORMAL) return FP_NORMAL else FP_SUBNORMAL 1007 Builder.SetInsertPoint(NotInf); 1008 APFloat Smallest = APFloat::getSmallestNormalized( 1009 getContext().getFloatTypeSemantics(E->getArg(5)->getType())); 1010 Value *IsNormal = 1011 Builder.CreateFCmpUGE(VAbs, ConstantFP::get(V->getContext(), Smallest), 1012 "isnormal"); 1013 Value *NormalResult = 1014 Builder.CreateSelect(IsNormal, EmitScalarExpr(E->getArg(2)), 1015 EmitScalarExpr(E->getArg(3))); 1016 Builder.CreateBr(End); 1017 Result->addIncoming(NormalResult, NotInf); 1018 1019 // return Result 1020 Builder.SetInsertPoint(End); 1021 return RValue::get(Result); 1022 } 1023 1024 case Builtin::BIalloca: 1025 case Builtin::BI_alloca: 1026 case Builtin::BI__builtin_alloca: { 1027 Value *Size = EmitScalarExpr(E->getArg(0)); 1028 return RValue::get(Builder.CreateAlloca(Builder.getInt8Ty(), Size)); 1029 } 1030 case Builtin::BIbzero: 1031 case Builtin::BI__builtin_bzero: { 1032 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1033 Value *SizeVal = EmitScalarExpr(E->getArg(1)); 1034 EmitNonNullArgCheck(RValue::get(Dest.getPointer()), E->getArg(0)->getType(), 1035 E->getArg(0)->getExprLoc(), FD, 0); 1036 Builder.CreateMemSet(Dest, Builder.getInt8(0), SizeVal, false); 1037 return RValue::get(Dest.getPointer()); 1038 } 1039 case Builtin::BImemcpy: 1040 case Builtin::BI__builtin_memcpy: { 1041 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1042 Address Src = EmitPointerWithAlignment(E->getArg(1)); 1043 Value *SizeVal = EmitScalarExpr(E->getArg(2)); 1044 EmitNonNullArgCheck(RValue::get(Dest.getPointer()), E->getArg(0)->getType(), 1045 E->getArg(0)->getExprLoc(), FD, 0); 1046 EmitNonNullArgCheck(RValue::get(Src.getPointer()), E->getArg(1)->getType(), 1047 E->getArg(1)->getExprLoc(), FD, 1); 1048 Builder.CreateMemCpy(Dest, Src, SizeVal, false); 1049 return RValue::get(Dest.getPointer()); 1050 } 1051 1052 case Builtin::BI__builtin___memcpy_chk: { 1053 // fold __builtin_memcpy_chk(x, y, cst1, cst2) to memcpy iff cst1<=cst2. 1054 llvm::APSInt Size, DstSize; 1055 if (!E->getArg(2)->EvaluateAsInt(Size, CGM.getContext()) || 1056 !E->getArg(3)->EvaluateAsInt(DstSize, CGM.getContext())) 1057 break; 1058 if (Size.ugt(DstSize)) 1059 break; 1060 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1061 Address Src = EmitPointerWithAlignment(E->getArg(1)); 1062 Value *SizeVal = llvm::ConstantInt::get(Builder.getContext(), Size); 1063 Builder.CreateMemCpy(Dest, Src, SizeVal, false); 1064 return RValue::get(Dest.getPointer()); 1065 } 1066 1067 case Builtin::BI__builtin_objc_memmove_collectable: { 1068 Address DestAddr = EmitPointerWithAlignment(E->getArg(0)); 1069 Address SrcAddr = EmitPointerWithAlignment(E->getArg(1)); 1070 Value *SizeVal = EmitScalarExpr(E->getArg(2)); 1071 CGM.getObjCRuntime().EmitGCMemmoveCollectable(*this, 1072 DestAddr, SrcAddr, SizeVal); 1073 return RValue::get(DestAddr.getPointer()); 1074 } 1075 1076 case Builtin::BI__builtin___memmove_chk: { 1077 // fold __builtin_memmove_chk(x, y, cst1, cst2) to memmove iff cst1<=cst2. 1078 llvm::APSInt Size, DstSize; 1079 if (!E->getArg(2)->EvaluateAsInt(Size, CGM.getContext()) || 1080 !E->getArg(3)->EvaluateAsInt(DstSize, CGM.getContext())) 1081 break; 1082 if (Size.ugt(DstSize)) 1083 break; 1084 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1085 Address Src = EmitPointerWithAlignment(E->getArg(1)); 1086 Value *SizeVal = llvm::ConstantInt::get(Builder.getContext(), Size); 1087 Builder.CreateMemMove(Dest, Src, SizeVal, false); 1088 return RValue::get(Dest.getPointer()); 1089 } 1090 1091 case Builtin::BImemmove: 1092 case Builtin::BI__builtin_memmove: { 1093 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1094 Address Src = EmitPointerWithAlignment(E->getArg(1)); 1095 Value *SizeVal = EmitScalarExpr(E->getArg(2)); 1096 EmitNonNullArgCheck(RValue::get(Dest.getPointer()), E->getArg(0)->getType(), 1097 E->getArg(0)->getExprLoc(), FD, 0); 1098 EmitNonNullArgCheck(RValue::get(Src.getPointer()), E->getArg(1)->getType(), 1099 E->getArg(1)->getExprLoc(), FD, 1); 1100 Builder.CreateMemMove(Dest, Src, SizeVal, false); 1101 return RValue::get(Dest.getPointer()); 1102 } 1103 case Builtin::BImemset: 1104 case Builtin::BI__builtin_memset: { 1105 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1106 Value *ByteVal = Builder.CreateTrunc(EmitScalarExpr(E->getArg(1)), 1107 Builder.getInt8Ty()); 1108 Value *SizeVal = EmitScalarExpr(E->getArg(2)); 1109 EmitNonNullArgCheck(RValue::get(Dest.getPointer()), E->getArg(0)->getType(), 1110 E->getArg(0)->getExprLoc(), FD, 0); 1111 Builder.CreateMemSet(Dest, ByteVal, SizeVal, false); 1112 return RValue::get(Dest.getPointer()); 1113 } 1114 case Builtin::BI__builtin___memset_chk: { 1115 // fold __builtin_memset_chk(x, y, cst1, cst2) to memset iff cst1<=cst2. 1116 llvm::APSInt Size, DstSize; 1117 if (!E->getArg(2)->EvaluateAsInt(Size, CGM.getContext()) || 1118 !E->getArg(3)->EvaluateAsInt(DstSize, CGM.getContext())) 1119 break; 1120 if (Size.ugt(DstSize)) 1121 break; 1122 Address Dest = EmitPointerWithAlignment(E->getArg(0)); 1123 Value *ByteVal = Builder.CreateTrunc(EmitScalarExpr(E->getArg(1)), 1124 Builder.getInt8Ty()); 1125 Value *SizeVal = llvm::ConstantInt::get(Builder.getContext(), Size); 1126 Builder.CreateMemSet(Dest, ByteVal, SizeVal, false); 1127 return RValue::get(Dest.getPointer()); 1128 } 1129 case Builtin::BI__builtin_dwarf_cfa: { 1130 // The offset in bytes from the first argument to the CFA. 1131 // 1132 // Why on earth is this in the frontend? Is there any reason at 1133 // all that the backend can't reasonably determine this while 1134 // lowering llvm.eh.dwarf.cfa()? 1135 // 1136 // TODO: If there's a satisfactory reason, add a target hook for 1137 // this instead of hard-coding 0, which is correct for most targets. 1138 int32_t Offset = 0; 1139 1140 Value *F = CGM.getIntrinsic(Intrinsic::eh_dwarf_cfa); 1141 return RValue::get(Builder.CreateCall(F, 1142 llvm::ConstantInt::get(Int32Ty, Offset))); 1143 } 1144 case Builtin::BI__builtin_return_address: { 1145 Value *Depth = 1146 CGM.EmitConstantExpr(E->getArg(0), getContext().UnsignedIntTy, this); 1147 Value *F = CGM.getIntrinsic(Intrinsic::returnaddress); 1148 return RValue::get(Builder.CreateCall(F, Depth)); 1149 } 1150 case Builtin::BI_ReturnAddress: { 1151 Value *F = CGM.getIntrinsic(Intrinsic::returnaddress); 1152 return RValue::get(Builder.CreateCall(F, Builder.getInt32(0))); 1153 } 1154 case Builtin::BI__builtin_frame_address: { 1155 Value *Depth = 1156 CGM.EmitConstantExpr(E->getArg(0), getContext().UnsignedIntTy, this); 1157 Value *F = CGM.getIntrinsic(Intrinsic::frameaddress); 1158 return RValue::get(Builder.CreateCall(F, Depth)); 1159 } 1160 case Builtin::BI__builtin_extract_return_addr: { 1161 Value *Address = EmitScalarExpr(E->getArg(0)); 1162 Value *Result = getTargetHooks().decodeReturnAddress(*this, Address); 1163 return RValue::get(Result); 1164 } 1165 case Builtin::BI__builtin_frob_return_addr: { 1166 Value *Address = EmitScalarExpr(E->getArg(0)); 1167 Value *Result = getTargetHooks().encodeReturnAddress(*this, Address); 1168 return RValue::get(Result); 1169 } 1170 case Builtin::BI__builtin_dwarf_sp_column: { 1171 llvm::IntegerType *Ty 1172 = cast<llvm::IntegerType>(ConvertType(E->getType())); 1173 int Column = getTargetHooks().getDwarfEHStackPointer(CGM); 1174 if (Column == -1) { 1175 CGM.ErrorUnsupported(E, "__builtin_dwarf_sp_column"); 1176 return RValue::get(llvm::UndefValue::get(Ty)); 1177 } 1178 return RValue::get(llvm::ConstantInt::get(Ty, Column, true)); 1179 } 1180 case Builtin::BI__builtin_init_dwarf_reg_size_table: { 1181 Value *Address = EmitScalarExpr(E->getArg(0)); 1182 if (getTargetHooks().initDwarfEHRegSizeTable(*this, Address)) 1183 CGM.ErrorUnsupported(E, "__builtin_init_dwarf_reg_size_table"); 1184 return RValue::get(llvm::UndefValue::get(ConvertType(E->getType()))); 1185 } 1186 case Builtin::BI__builtin_eh_return: { 1187 Value *Int = EmitScalarExpr(E->getArg(0)); 1188 Value *Ptr = EmitScalarExpr(E->getArg(1)); 1189 1190 llvm::IntegerType *IntTy = cast<llvm::IntegerType>(Int->getType()); 1191 assert((IntTy->getBitWidth() == 32 || IntTy->getBitWidth() == 64) && 1192 "LLVM's __builtin_eh_return only supports 32- and 64-bit variants"); 1193 Value *F = CGM.getIntrinsic(IntTy->getBitWidth() == 32 1194 ? Intrinsic::eh_return_i32 1195 : Intrinsic::eh_return_i64); 1196 Builder.CreateCall(F, {Int, Ptr}); 1197 Builder.CreateUnreachable(); 1198 1199 // We do need to preserve an insertion point. 1200 EmitBlock(createBasicBlock("builtin_eh_return.cont")); 1201 1202 return RValue::get(nullptr); 1203 } 1204 case Builtin::BI__builtin_unwind_init: { 1205 Value *F = CGM.getIntrinsic(Intrinsic::eh_unwind_init); 1206 return RValue::get(Builder.CreateCall(F)); 1207 } 1208 case Builtin::BI__builtin_extend_pointer: { 1209 // Extends a pointer to the size of an _Unwind_Word, which is 1210 // uint64_t on all platforms. Generally this gets poked into a 1211 // register and eventually used as an address, so if the 1212 // addressing registers are wider than pointers and the platform 1213 // doesn't implicitly ignore high-order bits when doing 1214 // addressing, we need to make sure we zext / sext based on 1215 // the platform's expectations. 1216 // 1217 // See: http://gcc.gnu.org/ml/gcc-bugs/2002-02/msg00237.html 1218 1219 // Cast the pointer to intptr_t. 1220 Value *Ptr = EmitScalarExpr(E->getArg(0)); 1221 Value *Result = Builder.CreatePtrToInt(Ptr, IntPtrTy, "extend.cast"); 1222 1223 // If that's 64 bits, we're done. 1224 if (IntPtrTy->getBitWidth() == 64) 1225 return RValue::get(Result); 1226 1227 // Otherwise, ask the codegen data what to do. 1228 if (getTargetHooks().extendPointerWithSExt()) 1229 return RValue::get(Builder.CreateSExt(Result, Int64Ty, "extend.sext")); 1230 else 1231 return RValue::get(Builder.CreateZExt(Result, Int64Ty, "extend.zext")); 1232 } 1233 case Builtin::BI__builtin_setjmp: { 1234 // Buffer is a void**. 1235 Address Buf = EmitPointerWithAlignment(E->getArg(0)); 1236 1237 // Store the frame pointer to the setjmp buffer. 1238 Value *FrameAddr = 1239 Builder.CreateCall(CGM.getIntrinsic(Intrinsic::frameaddress), 1240 ConstantInt::get(Int32Ty, 0)); 1241 Builder.CreateStore(FrameAddr, Buf); 1242 1243 // Store the stack pointer to the setjmp buffer. 1244 Value *StackAddr = 1245 Builder.CreateCall(CGM.getIntrinsic(Intrinsic::stacksave)); 1246 Address StackSaveSlot = 1247 Builder.CreateConstInBoundsGEP(Buf, 2, getPointerSize()); 1248 Builder.CreateStore(StackAddr, StackSaveSlot); 1249 1250 // Call LLVM's EH setjmp, which is lightweight. 1251 Value *F = CGM.getIntrinsic(Intrinsic::eh_sjlj_setjmp); 1252 Buf = Builder.CreateBitCast(Buf, Int8PtrTy); 1253 return RValue::get(Builder.CreateCall(F, Buf.getPointer())); 1254 } 1255 case Builtin::BI__builtin_longjmp: { 1256 Value *Buf = EmitScalarExpr(E->getArg(0)); 1257 Buf = Builder.CreateBitCast(Buf, Int8PtrTy); 1258 1259 // Call LLVM's EH longjmp, which is lightweight. 1260 Builder.CreateCall(CGM.getIntrinsic(Intrinsic::eh_sjlj_longjmp), Buf); 1261 1262 // longjmp doesn't return; mark this as unreachable. 1263 Builder.CreateUnreachable(); 1264 1265 // We do need to preserve an insertion point. 1266 EmitBlock(createBasicBlock("longjmp.cont")); 1267 1268 return RValue::get(nullptr); 1269 } 1270 case Builtin::BI__sync_fetch_and_add: 1271 case Builtin::BI__sync_fetch_and_sub: 1272 case Builtin::BI__sync_fetch_and_or: 1273 case Builtin::BI__sync_fetch_and_and: 1274 case Builtin::BI__sync_fetch_and_xor: 1275 case Builtin::BI__sync_fetch_and_nand: 1276 case Builtin::BI__sync_add_and_fetch: 1277 case Builtin::BI__sync_sub_and_fetch: 1278 case Builtin::BI__sync_and_and_fetch: 1279 case Builtin::BI__sync_or_and_fetch: 1280 case Builtin::BI__sync_xor_and_fetch: 1281 case Builtin::BI__sync_nand_and_fetch: 1282 case Builtin::BI__sync_val_compare_and_swap: 1283 case Builtin::BI__sync_bool_compare_and_swap: 1284 case Builtin::BI__sync_lock_test_and_set: 1285 case Builtin::BI__sync_lock_release: 1286 case Builtin::BI__sync_swap: 1287 llvm_unreachable("Shouldn't make it through sema"); 1288 case Builtin::BI__sync_fetch_and_add_1: 1289 case Builtin::BI__sync_fetch_and_add_2: 1290 case Builtin::BI__sync_fetch_and_add_4: 1291 case Builtin::BI__sync_fetch_and_add_8: 1292 case Builtin::BI__sync_fetch_and_add_16: 1293 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Add, E); 1294 case Builtin::BI__sync_fetch_and_sub_1: 1295 case Builtin::BI__sync_fetch_and_sub_2: 1296 case Builtin::BI__sync_fetch_and_sub_4: 1297 case Builtin::BI__sync_fetch_and_sub_8: 1298 case Builtin::BI__sync_fetch_and_sub_16: 1299 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Sub, E); 1300 case Builtin::BI__sync_fetch_and_or_1: 1301 case Builtin::BI__sync_fetch_and_or_2: 1302 case Builtin::BI__sync_fetch_and_or_4: 1303 case Builtin::BI__sync_fetch_and_or_8: 1304 case Builtin::BI__sync_fetch_and_or_16: 1305 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Or, E); 1306 case Builtin::BI__sync_fetch_and_and_1: 1307 case Builtin::BI__sync_fetch_and_and_2: 1308 case Builtin::BI__sync_fetch_and_and_4: 1309 case Builtin::BI__sync_fetch_and_and_8: 1310 case Builtin::BI__sync_fetch_and_and_16: 1311 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::And, E); 1312 case Builtin::BI__sync_fetch_and_xor_1: 1313 case Builtin::BI__sync_fetch_and_xor_2: 1314 case Builtin::BI__sync_fetch_and_xor_4: 1315 case Builtin::BI__sync_fetch_and_xor_8: 1316 case Builtin::BI__sync_fetch_and_xor_16: 1317 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Xor, E); 1318 case Builtin::BI__sync_fetch_and_nand_1: 1319 case Builtin::BI__sync_fetch_and_nand_2: 1320 case Builtin::BI__sync_fetch_and_nand_4: 1321 case Builtin::BI__sync_fetch_and_nand_8: 1322 case Builtin::BI__sync_fetch_and_nand_16: 1323 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Nand, E); 1324 1325 // Clang extensions: not overloaded yet. 1326 case Builtin::BI__sync_fetch_and_min: 1327 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Min, E); 1328 case Builtin::BI__sync_fetch_and_max: 1329 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Max, E); 1330 case Builtin::BI__sync_fetch_and_umin: 1331 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::UMin, E); 1332 case Builtin::BI__sync_fetch_and_umax: 1333 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::UMax, E); 1334 1335 case Builtin::BI__sync_add_and_fetch_1: 1336 case Builtin::BI__sync_add_and_fetch_2: 1337 case Builtin::BI__sync_add_and_fetch_4: 1338 case Builtin::BI__sync_add_and_fetch_8: 1339 case Builtin::BI__sync_add_and_fetch_16: 1340 return EmitBinaryAtomicPost(*this, llvm::AtomicRMWInst::Add, E, 1341 llvm::Instruction::Add); 1342 case Builtin::BI__sync_sub_and_fetch_1: 1343 case Builtin::BI__sync_sub_and_fetch_2: 1344 case Builtin::BI__sync_sub_and_fetch_4: 1345 case Builtin::BI__sync_sub_and_fetch_8: 1346 case Builtin::BI__sync_sub_and_fetch_16: 1347 return EmitBinaryAtomicPost(*this, llvm::AtomicRMWInst::Sub, E, 1348 llvm::Instruction::Sub); 1349 case Builtin::BI__sync_and_and_fetch_1: 1350 case Builtin::BI__sync_and_and_fetch_2: 1351 case Builtin::BI__sync_and_and_fetch_4: 1352 case Builtin::BI__sync_and_and_fetch_8: 1353 case Builtin::BI__sync_and_and_fetch_16: 1354 return EmitBinaryAtomicPost(*this, llvm::AtomicRMWInst::And, E, 1355 llvm::Instruction::And); 1356 case Builtin::BI__sync_or_and_fetch_1: 1357 case Builtin::BI__sync_or_and_fetch_2: 1358 case Builtin::BI__sync_or_and_fetch_4: 1359 case Builtin::BI__sync_or_and_fetch_8: 1360 case Builtin::BI__sync_or_and_fetch_16: 1361 return EmitBinaryAtomicPost(*this, llvm::AtomicRMWInst::Or, E, 1362 llvm::Instruction::Or); 1363 case Builtin::BI__sync_xor_and_fetch_1: 1364 case Builtin::BI__sync_xor_and_fetch_2: 1365 case Builtin::BI__sync_xor_and_fetch_4: 1366 case Builtin::BI__sync_xor_and_fetch_8: 1367 case Builtin::BI__sync_xor_and_fetch_16: 1368 return EmitBinaryAtomicPost(*this, llvm::AtomicRMWInst::Xor, E, 1369 llvm::Instruction::Xor); 1370 case Builtin::BI__sync_nand_and_fetch_1: 1371 case Builtin::BI__sync_nand_and_fetch_2: 1372 case Builtin::BI__sync_nand_and_fetch_4: 1373 case Builtin::BI__sync_nand_and_fetch_8: 1374 case Builtin::BI__sync_nand_and_fetch_16: 1375 return EmitBinaryAtomicPost(*this, llvm::AtomicRMWInst::Nand, E, 1376 llvm::Instruction::And, true); 1377 1378 case Builtin::BI__sync_val_compare_and_swap_1: 1379 case Builtin::BI__sync_val_compare_and_swap_2: 1380 case Builtin::BI__sync_val_compare_and_swap_4: 1381 case Builtin::BI__sync_val_compare_and_swap_8: 1382 case Builtin::BI__sync_val_compare_and_swap_16: 1383 return RValue::get(MakeAtomicCmpXchgValue(*this, E, false)); 1384 1385 case Builtin::BI__sync_bool_compare_and_swap_1: 1386 case Builtin::BI__sync_bool_compare_and_swap_2: 1387 case Builtin::BI__sync_bool_compare_and_swap_4: 1388 case Builtin::BI__sync_bool_compare_and_swap_8: 1389 case Builtin::BI__sync_bool_compare_and_swap_16: 1390 return RValue::get(MakeAtomicCmpXchgValue(*this, E, true)); 1391 1392 case Builtin::BI__sync_swap_1: 1393 case Builtin::BI__sync_swap_2: 1394 case Builtin::BI__sync_swap_4: 1395 case Builtin::BI__sync_swap_8: 1396 case Builtin::BI__sync_swap_16: 1397 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Xchg, E); 1398 1399 case Builtin::BI__sync_lock_test_and_set_1: 1400 case Builtin::BI__sync_lock_test_and_set_2: 1401 case Builtin::BI__sync_lock_test_and_set_4: 1402 case Builtin::BI__sync_lock_test_and_set_8: 1403 case Builtin::BI__sync_lock_test_and_set_16: 1404 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Xchg, E); 1405 1406 case Builtin::BI__sync_lock_release_1: 1407 case Builtin::BI__sync_lock_release_2: 1408 case Builtin::BI__sync_lock_release_4: 1409 case Builtin::BI__sync_lock_release_8: 1410 case Builtin::BI__sync_lock_release_16: { 1411 Value *Ptr = EmitScalarExpr(E->getArg(0)); 1412 QualType ElTy = E->getArg(0)->getType()->getPointeeType(); 1413 CharUnits StoreSize = getContext().getTypeSizeInChars(ElTy); 1414 llvm::Type *ITy = llvm::IntegerType::get(getLLVMContext(), 1415 StoreSize.getQuantity() * 8); 1416 Ptr = Builder.CreateBitCast(Ptr, ITy->getPointerTo()); 1417 llvm::StoreInst *Store = 1418 Builder.CreateAlignedStore(llvm::Constant::getNullValue(ITy), Ptr, 1419 StoreSize); 1420 Store->setAtomic(llvm::AtomicOrdering::Release); 1421 return RValue::get(nullptr); 1422 } 1423 1424 case Builtin::BI__sync_synchronize: { 1425 // We assume this is supposed to correspond to a C++0x-style 1426 // sequentially-consistent fence (i.e. this is only usable for 1427 // synchonization, not device I/O or anything like that). This intrinsic 1428 // is really badly designed in the sense that in theory, there isn't 1429 // any way to safely use it... but in practice, it mostly works 1430 // to use it with non-atomic loads and stores to get acquire/release 1431 // semantics. 1432 Builder.CreateFence(llvm::AtomicOrdering::SequentiallyConsistent); 1433 return RValue::get(nullptr); 1434 } 1435 1436 case Builtin::BI__builtin_nontemporal_load: 1437 return RValue::get(EmitNontemporalLoad(*this, E)); 1438 case Builtin::BI__builtin_nontemporal_store: 1439 return RValue::get(EmitNontemporalStore(*this, E)); 1440 case Builtin::BI__c11_atomic_is_lock_free: 1441 case Builtin::BI__atomic_is_lock_free: { 1442 // Call "bool __atomic_is_lock_free(size_t size, void *ptr)". For the 1443 // __c11 builtin, ptr is 0 (indicating a properly-aligned object), since 1444 // _Atomic(T) is always properly-aligned. 1445 const char *LibCallName = "__atomic_is_lock_free"; 1446 CallArgList Args; 1447 Args.add(RValue::get(EmitScalarExpr(E->getArg(0))), 1448 getContext().getSizeType()); 1449 if (BuiltinID == Builtin::BI__atomic_is_lock_free) 1450 Args.add(RValue::get(EmitScalarExpr(E->getArg(1))), 1451 getContext().VoidPtrTy); 1452 else 1453 Args.add(RValue::get(llvm::Constant::getNullValue(VoidPtrTy)), 1454 getContext().VoidPtrTy); 1455 const CGFunctionInfo &FuncInfo = 1456 CGM.getTypes().arrangeBuiltinFunctionCall(E->getType(), Args); 1457 llvm::FunctionType *FTy = CGM.getTypes().GetFunctionType(FuncInfo); 1458 llvm::Constant *Func = CGM.CreateRuntimeFunction(FTy, LibCallName); 1459 return EmitCall(FuncInfo, Func, ReturnValueSlot(), Args); 1460 } 1461 1462 case Builtin::BI__atomic_test_and_set: { 1463 // Look at the argument type to determine whether this is a volatile 1464 // operation. The parameter type is always volatile. 1465 QualType PtrTy = E->getArg(0)->IgnoreImpCasts()->getType(); 1466 bool Volatile = 1467 PtrTy->castAs<PointerType>()->getPointeeType().isVolatileQualified(); 1468 1469 Value *Ptr = EmitScalarExpr(E->getArg(0)); 1470 unsigned AddrSpace = Ptr->getType()->getPointerAddressSpace(); 1471 Ptr = Builder.CreateBitCast(Ptr, Int8Ty->getPointerTo(AddrSpace)); 1472 Value *NewVal = Builder.getInt8(1); 1473 Value *Order = EmitScalarExpr(E->getArg(1)); 1474 if (isa<llvm::ConstantInt>(Order)) { 1475 int ord = cast<llvm::ConstantInt>(Order)->getZExtValue(); 1476 AtomicRMWInst *Result = nullptr; 1477 switch (ord) { 1478 case 0: // memory_order_relaxed 1479 default: // invalid order 1480 Result = Builder.CreateAtomicRMW(llvm::AtomicRMWInst::Xchg, Ptr, NewVal, 1481 llvm::AtomicOrdering::Monotonic); 1482 break; 1483 case 1: // memory_order_consume 1484 case 2: // memory_order_acquire 1485 Result = Builder.CreateAtomicRMW(llvm::AtomicRMWInst::Xchg, Ptr, NewVal, 1486 llvm::AtomicOrdering::Acquire); 1487 break; 1488 case 3: // memory_order_release 1489 Result = Builder.CreateAtomicRMW(llvm::AtomicRMWInst::Xchg, Ptr, NewVal, 1490 llvm::AtomicOrdering::Release); 1491 break; 1492 case 4: // memory_order_acq_rel 1493 1494 Result = Builder.CreateAtomicRMW(llvm::AtomicRMWInst::Xchg, Ptr, NewVal, 1495 llvm::AtomicOrdering::AcquireRelease); 1496 break; 1497 case 5: // memory_order_seq_cst 1498 Result = Builder.CreateAtomicRMW( 1499 llvm::AtomicRMWInst::Xchg, Ptr, NewVal, 1500 llvm::AtomicOrdering::SequentiallyConsistent); 1501 break; 1502 } 1503 Result->setVolatile(Volatile); 1504 return RValue::get(Builder.CreateIsNotNull(Result, "tobool")); 1505 } 1506 1507 llvm::BasicBlock *ContBB = createBasicBlock("atomic.continue", CurFn); 1508 1509 llvm::BasicBlock *BBs[5] = { 1510 createBasicBlock("monotonic", CurFn), 1511 createBasicBlock("acquire", CurFn), 1512 createBasicBlock("release", CurFn), 1513 createBasicBlock("acqrel", CurFn), 1514 createBasicBlock("seqcst", CurFn) 1515 }; 1516 llvm::AtomicOrdering Orders[5] = { 1517 llvm::AtomicOrdering::Monotonic, llvm::AtomicOrdering::Acquire, 1518 llvm::AtomicOrdering::Release, llvm::AtomicOrdering::AcquireRelease, 1519 llvm::AtomicOrdering::SequentiallyConsistent}; 1520 1521 Order = Builder.CreateIntCast(Order, Builder.getInt32Ty(), false); 1522 llvm::SwitchInst *SI = Builder.CreateSwitch(Order, BBs[0]); 1523 1524 Builder.SetInsertPoint(ContBB); 1525 PHINode *Result = Builder.CreatePHI(Int8Ty, 5, "was_set"); 1526 1527 for (unsigned i = 0; i < 5; ++i) { 1528 Builder.SetInsertPoint(BBs[i]); 1529 AtomicRMWInst *RMW = Builder.CreateAtomicRMW(llvm::AtomicRMWInst::Xchg, 1530 Ptr, NewVal, Orders[i]); 1531 RMW->setVolatile(Volatile); 1532 Result->addIncoming(RMW, BBs[i]); 1533 Builder.CreateBr(ContBB); 1534 } 1535 1536 SI->addCase(Builder.getInt32(0), BBs[0]); 1537 SI->addCase(Builder.getInt32(1), BBs[1]); 1538 SI->addCase(Builder.getInt32(2), BBs[1]); 1539 SI->addCase(Builder.getInt32(3), BBs[2]); 1540 SI->addCase(Builder.getInt32(4), BBs[3]); 1541 SI->addCase(Builder.getInt32(5), BBs[4]); 1542 1543 Builder.SetInsertPoint(ContBB); 1544 return RValue::get(Builder.CreateIsNotNull(Result, "tobool")); 1545 } 1546 1547 case Builtin::BI__atomic_clear: { 1548 QualType PtrTy = E->getArg(0)->IgnoreImpCasts()->getType(); 1549 bool Volatile = 1550 PtrTy->castAs<PointerType>()->getPointeeType().isVolatileQualified(); 1551 1552 Address Ptr = EmitPointerWithAlignment(E->getArg(0)); 1553 unsigned AddrSpace = Ptr.getPointer()->getType()->getPointerAddressSpace(); 1554 Ptr = Builder.CreateBitCast(Ptr, Int8Ty->getPointerTo(AddrSpace)); 1555 Value *NewVal = Builder.getInt8(0); 1556 Value *Order = EmitScalarExpr(E->getArg(1)); 1557 if (isa<llvm::ConstantInt>(Order)) { 1558 int ord = cast<llvm::ConstantInt>(Order)->getZExtValue(); 1559 StoreInst *Store = Builder.CreateStore(NewVal, Ptr, Volatile); 1560 switch (ord) { 1561 case 0: // memory_order_relaxed 1562 default: // invalid order 1563 Store->setOrdering(llvm::AtomicOrdering::Monotonic); 1564 break; 1565 case 3: // memory_order_release 1566 Store->setOrdering(llvm::AtomicOrdering::Release); 1567 break; 1568 case 5: // memory_order_seq_cst 1569 Store->setOrdering(llvm::AtomicOrdering::SequentiallyConsistent); 1570 break; 1571 } 1572 return RValue::get(nullptr); 1573 } 1574 1575 llvm::BasicBlock *ContBB = createBasicBlock("atomic.continue", CurFn); 1576 1577 llvm::BasicBlock *BBs[3] = { 1578 createBasicBlock("monotonic", CurFn), 1579 createBasicBlock("release", CurFn), 1580 createBasicBlock("seqcst", CurFn) 1581 }; 1582 llvm::AtomicOrdering Orders[3] = { 1583 llvm::AtomicOrdering::Monotonic, llvm::AtomicOrdering::Release, 1584 llvm::AtomicOrdering::SequentiallyConsistent}; 1585 1586 Order = Builder.CreateIntCast(Order, Builder.getInt32Ty(), false); 1587 llvm::SwitchInst *SI = Builder.CreateSwitch(Order, BBs[0]); 1588 1589 for (unsigned i = 0; i < 3; ++i) { 1590 Builder.SetInsertPoint(BBs[i]); 1591 StoreInst *Store = Builder.CreateStore(NewVal, Ptr, Volatile); 1592 Store->setOrdering(Orders[i]); 1593 Builder.CreateBr(ContBB); 1594 } 1595 1596 SI->addCase(Builder.getInt32(0), BBs[0]); 1597 SI->addCase(Builder.getInt32(3), BBs[1]); 1598 SI->addCase(Builder.getInt32(5), BBs[2]); 1599 1600 Builder.SetInsertPoint(ContBB); 1601 return RValue::get(nullptr); 1602 } 1603 1604 case Builtin::BI__atomic_thread_fence: 1605 case Builtin::BI__atomic_signal_fence: 1606 case Builtin::BI__c11_atomic_thread_fence: 1607 case Builtin::BI__c11_atomic_signal_fence: { 1608 llvm::SynchronizationScope Scope; 1609 if (BuiltinID == Builtin::BI__atomic_signal_fence || 1610 BuiltinID == Builtin::BI__c11_atomic_signal_fence) 1611 Scope = llvm::SingleThread; 1612 else 1613 Scope = llvm::CrossThread; 1614 Value *Order = EmitScalarExpr(E->getArg(0)); 1615 if (isa<llvm::ConstantInt>(Order)) { 1616 int ord = cast<llvm::ConstantInt>(Order)->getZExtValue(); 1617 switch (ord) { 1618 case 0: // memory_order_relaxed 1619 default: // invalid order 1620 break; 1621 case 1: // memory_order_consume 1622 case 2: // memory_order_acquire 1623 Builder.CreateFence(llvm::AtomicOrdering::Acquire, Scope); 1624 break; 1625 case 3: // memory_order_release 1626 Builder.CreateFence(llvm::AtomicOrdering::Release, Scope); 1627 break; 1628 case 4: // memory_order_acq_rel 1629 Builder.CreateFence(llvm::AtomicOrdering::AcquireRelease, Scope); 1630 break; 1631 case 5: // memory_order_seq_cst 1632 Builder.CreateFence(llvm::AtomicOrdering::SequentiallyConsistent, 1633 Scope); 1634 break; 1635 } 1636 return RValue::get(nullptr); 1637 } 1638 1639 llvm::BasicBlock *AcquireBB, *ReleaseBB, *AcqRelBB, *SeqCstBB; 1640 AcquireBB = createBasicBlock("acquire", CurFn); 1641 ReleaseBB = createBasicBlock("release", CurFn); 1642 AcqRelBB = createBasicBlock("acqrel", CurFn); 1643 SeqCstBB = createBasicBlock("seqcst", CurFn); 1644 llvm::BasicBlock *ContBB = createBasicBlock("atomic.continue", CurFn); 1645 1646 Order = Builder.CreateIntCast(Order, Builder.getInt32Ty(), false); 1647 llvm::SwitchInst *SI = Builder.CreateSwitch(Order, ContBB); 1648 1649 Builder.SetInsertPoint(AcquireBB); 1650 Builder.CreateFence(llvm::AtomicOrdering::Acquire, Scope); 1651 Builder.CreateBr(ContBB); 1652 SI->addCase(Builder.getInt32(1), AcquireBB); 1653 SI->addCase(Builder.getInt32(2), AcquireBB); 1654 1655 Builder.SetInsertPoint(ReleaseBB); 1656 Builder.CreateFence(llvm::AtomicOrdering::Release, Scope); 1657 Builder.CreateBr(ContBB); 1658 SI->addCase(Builder.getInt32(3), ReleaseBB); 1659 1660 Builder.SetInsertPoint(AcqRelBB); 1661 Builder.CreateFence(llvm::AtomicOrdering::AcquireRelease, Scope); 1662 Builder.CreateBr(ContBB); 1663 SI->addCase(Builder.getInt32(4), AcqRelBB); 1664 1665 Builder.SetInsertPoint(SeqCstBB); 1666 Builder.CreateFence(llvm::AtomicOrdering::SequentiallyConsistent, Scope); 1667 Builder.CreateBr(ContBB); 1668 SI->addCase(Builder.getInt32(5), SeqCstBB); 1669 1670 Builder.SetInsertPoint(ContBB); 1671 return RValue::get(nullptr); 1672 } 1673 1674 // Library functions with special handling. 1675 case Builtin::BIsqrt: 1676 case Builtin::BIsqrtf: 1677 case Builtin::BIsqrtl: { 1678 // Transform a call to sqrt* into a @llvm.sqrt.* intrinsic call, but only 1679 // in finite- or unsafe-math mode (the intrinsic has different semantics 1680 // for handling negative numbers compared to the library function, so 1681 // -fmath-errno=0 is not enough). 1682 if (!FD->hasAttr<ConstAttr>()) 1683 break; 1684 if (!(CGM.getCodeGenOpts().UnsafeFPMath || 1685 CGM.getCodeGenOpts().NoNaNsFPMath)) 1686 break; 1687 Value *Arg0 = EmitScalarExpr(E->getArg(0)); 1688 llvm::Type *ArgType = Arg0->getType(); 1689 Value *F = CGM.getIntrinsic(Intrinsic::sqrt, ArgType); 1690 return RValue::get(Builder.CreateCall(F, Arg0)); 1691 } 1692 1693 case Builtin::BI__builtin_pow: 1694 case Builtin::BI__builtin_powf: 1695 case Builtin::BI__builtin_powl: 1696 case Builtin::BIpow: 1697 case Builtin::BIpowf: 1698 case Builtin::BIpowl: { 1699 // Transform a call to pow* into a @llvm.pow.* intrinsic call. 1700 if (!FD->hasAttr<ConstAttr>()) 1701 break; 1702 Value *Base = EmitScalarExpr(E->getArg(0)); 1703 Value *Exponent = EmitScalarExpr(E->getArg(1)); 1704 llvm::Type *ArgType = Base->getType(); 1705 Value *F = CGM.getIntrinsic(Intrinsic::pow, ArgType); 1706 return RValue::get(Builder.CreateCall(F, {Base, Exponent})); 1707 } 1708 1709 case Builtin::BIfma: 1710 case Builtin::BIfmaf: 1711 case Builtin::BIfmal: 1712 case Builtin::BI__builtin_fma: 1713 case Builtin::BI__builtin_fmaf: 1714 case Builtin::BI__builtin_fmal: { 1715 // Rewrite fma to intrinsic. 1716 Value *FirstArg = EmitScalarExpr(E->getArg(0)); 1717 llvm::Type *ArgType = FirstArg->getType(); 1718 Value *F = CGM.getIntrinsic(Intrinsic::fma, ArgType); 1719 return RValue::get( 1720 Builder.CreateCall(F, {FirstArg, EmitScalarExpr(E->getArg(1)), 1721 EmitScalarExpr(E->getArg(2))})); 1722 } 1723 1724 case Builtin::BI__builtin_signbit: 1725 case Builtin::BI__builtin_signbitf: 1726 case Builtin::BI__builtin_signbitl: { 1727 return RValue::get( 1728 Builder.CreateZExt(EmitSignBit(*this, EmitScalarExpr(E->getArg(0))), 1729 ConvertType(E->getType()))); 1730 } 1731 case Builtin::BI__builtin_annotation: { 1732 llvm::Value *AnnVal = EmitScalarExpr(E->getArg(0)); 1733 llvm::Value *F = CGM.getIntrinsic(llvm::Intrinsic::annotation, 1734 AnnVal->getType()); 1735 1736 // Get the annotation string, go through casts. Sema requires this to be a 1737 // non-wide string literal, potentially casted, so the cast<> is safe. 1738 const Expr *AnnotationStrExpr = E->getArg(1)->IgnoreParenCasts(); 1739 StringRef Str = cast<StringLiteral>(AnnotationStrExpr)->getString(); 1740 return RValue::get(EmitAnnotationCall(F, AnnVal, Str, E->getExprLoc())); 1741 } 1742 case Builtin::BI__builtin_addcb: 1743 case Builtin::BI__builtin_addcs: 1744 case Builtin::BI__builtin_addc: 1745 case Builtin::BI__builtin_addcl: 1746 case Builtin::BI__builtin_addcll: 1747 case Builtin::BI__builtin_subcb: 1748 case Builtin::BI__builtin_subcs: 1749 case Builtin::BI__builtin_subc: 1750 case Builtin::BI__builtin_subcl: 1751 case Builtin::BI__builtin_subcll: { 1752 1753 // We translate all of these builtins from expressions of the form: 1754 // int x = ..., y = ..., carryin = ..., carryout, result; 1755 // result = __builtin_addc(x, y, carryin, &carryout); 1756 // 1757 // to LLVM IR of the form: 1758 // 1759 // %tmp1 = call {i32, i1} @llvm.uadd.with.overflow.i32(i32 %x, i32 %y) 1760 // %tmpsum1 = extractvalue {i32, i1} %tmp1, 0 1761 // %carry1 = extractvalue {i32, i1} %tmp1, 1 1762 // %tmp2 = call {i32, i1} @llvm.uadd.with.overflow.i32(i32 %tmpsum1, 1763 // i32 %carryin) 1764 // %result = extractvalue {i32, i1} %tmp2, 0 1765 // %carry2 = extractvalue {i32, i1} %tmp2, 1 1766 // %tmp3 = or i1 %carry1, %carry2 1767 // %tmp4 = zext i1 %tmp3 to i32 1768 // store i32 %tmp4, i32* %carryout 1769 1770 // Scalarize our inputs. 1771 llvm::Value *X = EmitScalarExpr(E->getArg(0)); 1772 llvm::Value *Y = EmitScalarExpr(E->getArg(1)); 1773 llvm::Value *Carryin = EmitScalarExpr(E->getArg(2)); 1774 Address CarryOutPtr = EmitPointerWithAlignment(E->getArg(3)); 1775 1776 // Decide if we are lowering to a uadd.with.overflow or usub.with.overflow. 1777 llvm::Intrinsic::ID IntrinsicId; 1778 switch (BuiltinID) { 1779 default: llvm_unreachable("Unknown multiprecision builtin id."); 1780 case Builtin::BI__builtin_addcb: 1781 case Builtin::BI__builtin_addcs: 1782 case Builtin::BI__builtin_addc: 1783 case Builtin::BI__builtin_addcl: 1784 case Builtin::BI__builtin_addcll: 1785 IntrinsicId = llvm::Intrinsic::uadd_with_overflow; 1786 break; 1787 case Builtin::BI__builtin_subcb: 1788 case Builtin::BI__builtin_subcs: 1789 case Builtin::BI__builtin_subc: 1790 case Builtin::BI__builtin_subcl: 1791 case Builtin::BI__builtin_subcll: 1792 IntrinsicId = llvm::Intrinsic::usub_with_overflow; 1793 break; 1794 } 1795 1796 // Construct our resulting LLVM IR expression. 1797 llvm::Value *Carry1; 1798 llvm::Value *Sum1 = EmitOverflowIntrinsic(*this, IntrinsicId, 1799 X, Y, Carry1); 1800 llvm::Value *Carry2; 1801 llvm::Value *Sum2 = EmitOverflowIntrinsic(*this, IntrinsicId, 1802 Sum1, Carryin, Carry2); 1803 llvm::Value *CarryOut = Builder.CreateZExt(Builder.CreateOr(Carry1, Carry2), 1804 X->getType()); 1805 Builder.CreateStore(CarryOut, CarryOutPtr); 1806 return RValue::get(Sum2); 1807 } 1808 1809 case Builtin::BI__builtin_add_overflow: 1810 case Builtin::BI__builtin_sub_overflow: 1811 case Builtin::BI__builtin_mul_overflow: { 1812 const clang::Expr *LeftArg = E->getArg(0); 1813 const clang::Expr *RightArg = E->getArg(1); 1814 const clang::Expr *ResultArg = E->getArg(2); 1815 1816 clang::QualType ResultQTy = 1817 ResultArg->getType()->castAs<PointerType>()->getPointeeType(); 1818 1819 WidthAndSignedness LeftInfo = 1820 getIntegerWidthAndSignedness(CGM.getContext(), LeftArg->getType()); 1821 WidthAndSignedness RightInfo = 1822 getIntegerWidthAndSignedness(CGM.getContext(), RightArg->getType()); 1823 WidthAndSignedness ResultInfo = 1824 getIntegerWidthAndSignedness(CGM.getContext(), ResultQTy); 1825 WidthAndSignedness EncompassingInfo = 1826 EncompassingIntegerType({LeftInfo, RightInfo, ResultInfo}); 1827 1828 llvm::Type *EncompassingLLVMTy = 1829 llvm::IntegerType::get(CGM.getLLVMContext(), EncompassingInfo.Width); 1830 1831 llvm::Type *ResultLLVMTy = CGM.getTypes().ConvertType(ResultQTy); 1832 1833 llvm::Intrinsic::ID IntrinsicId; 1834 switch (BuiltinID) { 1835 default: 1836 llvm_unreachable("Unknown overflow builtin id."); 1837 case Builtin::BI__builtin_add_overflow: 1838 IntrinsicId = EncompassingInfo.Signed 1839 ? llvm::Intrinsic::sadd_with_overflow 1840 : llvm::Intrinsic::uadd_with_overflow; 1841 break; 1842 case Builtin::BI__builtin_sub_overflow: 1843 IntrinsicId = EncompassingInfo.Signed 1844 ? llvm::Intrinsic::ssub_with_overflow 1845 : llvm::Intrinsic::usub_with_overflow; 1846 break; 1847 case Builtin::BI__builtin_mul_overflow: 1848 IntrinsicId = EncompassingInfo.Signed 1849 ? llvm::Intrinsic::smul_with_overflow 1850 : llvm::Intrinsic::umul_with_overflow; 1851 break; 1852 } 1853 1854 llvm::Value *Left = EmitScalarExpr(LeftArg); 1855 llvm::Value *Right = EmitScalarExpr(RightArg); 1856 Address ResultPtr = EmitPointerWithAlignment(ResultArg); 1857 1858 // Extend each operand to the encompassing type. 1859 Left = Builder.CreateIntCast(Left, EncompassingLLVMTy, LeftInfo.Signed); 1860 Right = Builder.CreateIntCast(Right, EncompassingLLVMTy, RightInfo.Signed); 1861 1862 // Perform the operation on the extended values. 1863 llvm::Value *Overflow, *Result; 1864 Result = EmitOverflowIntrinsic(*this, IntrinsicId, Left, Right, Overflow); 1865 1866 if (EncompassingInfo.Width > ResultInfo.Width) { 1867 // The encompassing type is wider than the result type, so we need to 1868 // truncate it. 1869 llvm::Value *ResultTrunc = Builder.CreateTrunc(Result, ResultLLVMTy); 1870 1871 // To see if the truncation caused an overflow, we will extend 1872 // the result and then compare it to the original result. 1873 llvm::Value *ResultTruncExt = Builder.CreateIntCast( 1874 ResultTrunc, EncompassingLLVMTy, ResultInfo.Signed); 1875 llvm::Value *TruncationOverflow = 1876 Builder.CreateICmpNE(Result, ResultTruncExt); 1877 1878 Overflow = Builder.CreateOr(Overflow, TruncationOverflow); 1879 Result = ResultTrunc; 1880 } 1881 1882 // Finally, store the result using the pointer. 1883 bool isVolatile = 1884 ResultArg->getType()->getPointeeType().isVolatileQualified(); 1885 Builder.CreateStore(EmitToMemory(Result, ResultQTy), ResultPtr, isVolatile); 1886 1887 return RValue::get(Overflow); 1888 } 1889 1890 case Builtin::BI__builtin_uadd_overflow: 1891 case Builtin::BI__builtin_uaddl_overflow: 1892 case Builtin::BI__builtin_uaddll_overflow: 1893 case Builtin::BI__builtin_usub_overflow: 1894 case Builtin::BI__builtin_usubl_overflow: 1895 case Builtin::BI__builtin_usubll_overflow: 1896 case Builtin::BI__builtin_umul_overflow: 1897 case Builtin::BI__builtin_umull_overflow: 1898 case Builtin::BI__builtin_umulll_overflow: 1899 case Builtin::BI__builtin_sadd_overflow: 1900 case Builtin::BI__builtin_saddl_overflow: 1901 case Builtin::BI__builtin_saddll_overflow: 1902 case Builtin::BI__builtin_ssub_overflow: 1903 case Builtin::BI__builtin_ssubl_overflow: 1904 case Builtin::BI__builtin_ssubll_overflow: 1905 case Builtin::BI__builtin_smul_overflow: 1906 case Builtin::BI__builtin_smull_overflow: 1907 case Builtin::BI__builtin_smulll_overflow: { 1908 1909 // We translate all of these builtins directly to the relevant llvm IR node. 1910 1911 // Scalarize our inputs. 1912 llvm::Value *X = EmitScalarExpr(E->getArg(0)); 1913 llvm::Value *Y = EmitScalarExpr(E->getArg(1)); 1914 Address SumOutPtr = EmitPointerWithAlignment(E->getArg(2)); 1915 1916 // Decide which of the overflow intrinsics we are lowering to: 1917 llvm::Intrinsic::ID IntrinsicId; 1918 switch (BuiltinID) { 1919 default: llvm_unreachable("Unknown overflow builtin id."); 1920 case Builtin::BI__builtin_uadd_overflow: 1921 case Builtin::BI__builtin_uaddl_overflow: 1922 case Builtin::BI__builtin_uaddll_overflow: 1923 IntrinsicId = llvm::Intrinsic::uadd_with_overflow; 1924 break; 1925 case Builtin::BI__builtin_usub_overflow: 1926 case Builtin::BI__builtin_usubl_overflow: 1927 case Builtin::BI__builtin_usubll_overflow: 1928 IntrinsicId = llvm::Intrinsic::usub_with_overflow; 1929 break; 1930 case Builtin::BI__builtin_umul_overflow: 1931 case Builtin::BI__builtin_umull_overflow: 1932 case Builtin::BI__builtin_umulll_overflow: 1933 IntrinsicId = llvm::Intrinsic::umul_with_overflow; 1934 break; 1935 case Builtin::BI__builtin_sadd_overflow: 1936 case Builtin::BI__builtin_saddl_overflow: 1937 case Builtin::BI__builtin_saddll_overflow: 1938 IntrinsicId = llvm::Intrinsic::sadd_with_overflow; 1939 break; 1940 case Builtin::BI__builtin_ssub_overflow: 1941 case Builtin::BI__builtin_ssubl_overflow: 1942 case Builtin::BI__builtin_ssubll_overflow: 1943 IntrinsicId = llvm::Intrinsic::ssub_with_overflow; 1944 break; 1945 case Builtin::BI__builtin_smul_overflow: 1946 case Builtin::BI__builtin_smull_overflow: 1947 case Builtin::BI__builtin_smulll_overflow: 1948 IntrinsicId = llvm::Intrinsic::smul_with_overflow; 1949 break; 1950 } 1951 1952 1953 llvm::Value *Carry; 1954 llvm::Value *Sum = EmitOverflowIntrinsic(*this, IntrinsicId, X, Y, Carry); 1955 Builder.CreateStore(Sum, SumOutPtr); 1956 1957 return RValue::get(Carry); 1958 } 1959 case Builtin::BI__builtin_addressof: 1960 return RValue::get(EmitLValue(E->getArg(0)).getPointer()); 1961 case Builtin::BI__builtin_operator_new: 1962 return EmitBuiltinNewDeleteCall(FD->getType()->castAs<FunctionProtoType>(), 1963 E->getArg(0), false); 1964 case Builtin::BI__builtin_operator_delete: 1965 return EmitBuiltinNewDeleteCall(FD->getType()->castAs<FunctionProtoType>(), 1966 E->getArg(0), true); 1967 case Builtin::BI__noop: 1968 // __noop always evaluates to an integer literal zero. 1969 return RValue::get(ConstantInt::get(IntTy, 0)); 1970 case Builtin::BI__builtin_call_with_static_chain: { 1971 const CallExpr *Call = cast<CallExpr>(E->getArg(0)); 1972 const Expr *Chain = E->getArg(1); 1973 return EmitCall(Call->getCallee()->getType(), 1974 EmitScalarExpr(Call->getCallee()), Call, ReturnValue, 1975 Call->getCalleeDecl(), EmitScalarExpr(Chain)); 1976 } 1977 case Builtin::BI_InterlockedExchange8: 1978 case Builtin::BI_InterlockedExchange16: 1979 case Builtin::BI_InterlockedExchange: 1980 case Builtin::BI_InterlockedExchangePointer: 1981 return EmitBinaryAtomic(*this, llvm::AtomicRMWInst::Xchg, E); 1982 case Builtin::BI_InterlockedCompareExchangePointer: { 1983 llvm::Type *RTy; 1984 llvm::IntegerType *IntType = 1985 IntegerType::get(getLLVMContext(), 1986 getContext().getTypeSize(E->getType())); 1987 llvm::Type *IntPtrType = IntType->getPointerTo(); 1988 1989 llvm::Value *Destination = 1990 Builder.CreateBitCast(EmitScalarExpr(E->getArg(0)), IntPtrType); 1991 1992 llvm::Value *Exchange = EmitScalarExpr(E->getArg(1)); 1993 RTy = Exchange->getType(); 1994 Exchange = Builder.CreatePtrToInt(Exchange, IntType); 1995 1996 llvm::Value *Comparand = 1997 Builder.CreatePtrToInt(EmitScalarExpr(E->getArg(2)), IntType); 1998 1999 auto Result = 2000 Builder.CreateAtomicCmpXchg(Destination, Comparand, Exchange, 2001 AtomicOrdering::SequentiallyConsistent, 2002 AtomicOrdering::SequentiallyConsistent); 2003 Result->setVolatile(true); 2004 2005 return RValue::get(Builder.CreateIntToPtr(Builder.CreateExtractValue(Result, 2006 0), 2007 RTy)); 2008 } 2009 case Builtin::BI_InterlockedCompareExchange8: 2010 case Builtin::BI_InterlockedCompareExchange16: 2011 case Builtin::BI_InterlockedCompareExchange: 2012 case Builtin::BI_InterlockedCompareExchange64: { 2013 AtomicCmpXchgInst *CXI = Builder.CreateAtomicCmpXchg( 2014 EmitScalarExpr(E->getArg(0)), 2015 EmitScalarExpr(E->getArg(2)), 2016 EmitScalarExpr(E->getArg(1)), 2017 AtomicOrdering::SequentiallyConsistent, 2018 AtomicOrdering::SequentiallyConsistent); 2019 CXI->setVolatile(true); 2020 return RValue::get(Builder.CreateExtractValue(CXI, 0)); 2021 } 2022 case Builtin::BI_InterlockedIncrement16: 2023 case Builtin::BI_InterlockedIncrement: { 2024 llvm::Type *IntTy = ConvertType(E->getType()); 2025 AtomicRMWInst *RMWI = Builder.CreateAtomicRMW( 2026 AtomicRMWInst::Add, 2027 EmitScalarExpr(E->getArg(0)), 2028 ConstantInt::get(IntTy, 1), 2029 llvm::AtomicOrdering::SequentiallyConsistent); 2030 return RValue::get(Builder.CreateAdd(RMWI, ConstantInt::get(IntTy, 1))); 2031 } 2032 case Builtin::BI_InterlockedDecrement16: 2033 case Builtin::BI_InterlockedDecrement: { 2034 llvm::Type *IntTy = ConvertType(E->getType()); 2035 AtomicRMWInst *RMWI = Builder.CreateAtomicRMW( 2036 AtomicRMWInst::Sub, 2037 EmitScalarExpr(E->getArg(0)), 2038 ConstantInt::get(IntTy, 1), 2039 llvm::AtomicOrdering::SequentiallyConsistent); 2040 return RValue::get(Builder.CreateSub(RMWI, ConstantInt::get(IntTy, 1))); 2041 } 2042 case Builtin::BI_InterlockedAnd8: 2043 case Builtin::BI_InterlockedAnd16: 2044 case Builtin::BI_InterlockedAnd: 2045 return EmitBinaryAtomic(*this, AtomicRMWInst::And, E); 2046 case Builtin::BI_InterlockedExchangeAdd8: 2047 case Builtin::BI_InterlockedExchangeAdd16: 2048 case Builtin::BI_InterlockedExchangeAdd: 2049 return EmitBinaryAtomic(*this, AtomicRMWInst::Add, E); 2050 case Builtin::BI_InterlockedExchangeSub8: 2051 case Builtin::BI_InterlockedExchangeSub16: 2052 case Builtin::BI_InterlockedExchangeSub: 2053 return EmitBinaryAtomic(*this, AtomicRMWInst::Sub, E); 2054 case Builtin::BI_InterlockedOr8: 2055 case Builtin::BI_InterlockedOr16: 2056 case Builtin::BI_InterlockedOr: 2057 return EmitBinaryAtomic(*this, AtomicRMWInst::Or, E); 2058 case Builtin::BI_InterlockedXor8: 2059 case Builtin::BI_InterlockedXor16: 2060 case Builtin::BI_InterlockedXor: 2061 return EmitBinaryAtomic(*this, AtomicRMWInst::Xor, E); 2062 case Builtin::BI__readfsdword: { 2063 llvm::Type *IntTy = ConvertType(E->getType()); 2064 Value *IntToPtr = 2065 Builder.CreateIntToPtr(EmitScalarExpr(E->getArg(0)), 2066 llvm::PointerType::get(IntTy, 257)); 2067 LoadInst *Load = 2068 Builder.CreateDefaultAlignedLoad(IntToPtr, /*isVolatile=*/true); 2069 return RValue::get(Load); 2070 } 2071 2072 case Builtin::BI__exception_code: 2073 case Builtin::BI_exception_code: 2074 return RValue::get(EmitSEHExceptionCode()); 2075 case Builtin::BI__exception_info: 2076 case Builtin::BI_exception_info: 2077 return RValue::get(EmitSEHExceptionInfo()); 2078 case Builtin::BI__abnormal_termination: 2079 case Builtin::BI_abnormal_termination: 2080 return RValue::get(EmitSEHAbnormalTermination()); 2081 case Builtin::BI_setjmpex: { 2082 if (getTarget().getTriple().isOSMSVCRT()) { 2083 llvm::Type *ArgTypes[] = {Int8PtrTy, Int8PtrTy}; 2084 llvm::AttributeSet ReturnsTwiceAttr = 2085 AttributeSet::get(getLLVMContext(), llvm::AttributeSet::FunctionIndex, 2086 llvm::Attribute::ReturnsTwice); 2087 llvm::Constant *SetJmpEx = CGM.CreateRuntimeFunction( 2088 llvm::FunctionType::get(IntTy, ArgTypes, /*isVarArg=*/false), 2089 "_setjmpex", ReturnsTwiceAttr); 2090 llvm::Value *Buf = Builder.CreateBitOrPointerCast( 2091 EmitScalarExpr(E->getArg(0)), Int8PtrTy); 2092 llvm::Value *FrameAddr = 2093 Builder.CreateCall(CGM.getIntrinsic(Intrinsic::frameaddress), 2094 ConstantInt::get(Int32Ty, 0)); 2095 llvm::Value *Args[] = {Buf, FrameAddr}; 2096 llvm::CallSite CS = EmitRuntimeCallOrInvoke(SetJmpEx, Args); 2097 CS.setAttributes(ReturnsTwiceAttr); 2098 return RValue::get(CS.getInstruction()); 2099 } 2100 break; 2101 } 2102 case Builtin::BI_setjmp: { 2103 if (getTarget().getTriple().isOSMSVCRT()) { 2104 llvm::AttributeSet ReturnsTwiceAttr = 2105 AttributeSet::get(getLLVMContext(), llvm::AttributeSet::FunctionIndex, 2106 llvm::Attribute::ReturnsTwice); 2107 llvm::Value *Buf = Builder.CreateBitOrPointerCast( 2108 EmitScalarExpr(E->getArg(0)), Int8PtrTy); 2109 llvm::CallSite CS; 2110 if (getTarget().getTriple().getArch() == llvm::Triple::x86) { 2111 llvm::Type *ArgTypes[] = {Int8PtrTy, IntTy}; 2112 llvm::Constant *SetJmp3 = CGM.CreateRuntimeFunction( 2113 llvm::FunctionType::get(IntTy, ArgTypes, /*isVarArg=*/true), 2114 "_setjmp3", ReturnsTwiceAttr); 2115 llvm::Value *Count = ConstantInt::get(IntTy, 0); 2116 llvm::Value *Args[] = {Buf, Count}; 2117 CS = EmitRuntimeCallOrInvoke(SetJmp3, Args); 2118 } else { 2119 llvm::Type *ArgTypes[] = {Int8PtrTy, Int8PtrTy}; 2120 llvm::Constant *SetJmp = CGM.CreateRuntimeFunction( 2121 llvm::FunctionType::get(IntTy, ArgTypes, /*isVarArg=*/false), 2122 "_setjmp", ReturnsTwiceAttr); 2123 llvm::Value *FrameAddr = 2124 Builder.CreateCall(CGM.getIntrinsic(Intrinsic::frameaddress), 2125 ConstantInt::get(Int32Ty, 0)); 2126 llvm::Value *Args[] = {Buf, FrameAddr}; 2127 CS = EmitRuntimeCallOrInvoke(SetJmp, Args); 2128 } 2129 CS.setAttributes(ReturnsTwiceAttr); 2130 return RValue::get(CS.getInstruction()); 2131 } 2132 break; 2133 } 2134 2135 case Builtin::BI__GetExceptionInfo: { 2136 if (llvm::GlobalVariable *GV = 2137 CGM.getCXXABI().getThrowInfo(FD->getParamDecl(0)->getType())) 2138 return RValue::get(llvm::ConstantExpr::getBitCast(GV, CGM.Int8PtrTy)); 2139 break; 2140 } 2141 2142 case Builtin::BI__builtin_coro_size: { 2143 auto & Context = getContext(); 2144 auto SizeTy = Context.getSizeType(); 2145 auto T = Builder.getIntNTy(Context.getTypeSize(SizeTy)); 2146 Value *F = CGM.getIntrinsic(Intrinsic::coro_size, T); 2147 return RValue::get(Builder.CreateCall(F)); 2148 } 2149 2150 case Builtin::BI__builtin_coro_id: 2151 return EmitCoroutineIntrinsic(E, Intrinsic::coro_id); 2152 case Builtin::BI__builtin_coro_promise: 2153 return EmitCoroutineIntrinsic(E, Intrinsic::coro_promise); 2154 case Builtin::BI__builtin_coro_resume: 2155 return EmitCoroutineIntrinsic(E, Intrinsic::coro_resume); 2156 case Builtin::BI__builtin_coro_frame: 2157 return EmitCoroutineIntrinsic(E, Intrinsic::coro_frame); 2158 case Builtin::BI__builtin_coro_free: 2159 return EmitCoroutineIntrinsic(E, Intrinsic::coro_free); 2160 case Builtin::BI__builtin_coro_destroy: 2161 return EmitCoroutineIntrinsic(E, Intrinsic::coro_destroy); 2162 case Builtin::BI__builtin_coro_done: 2163 return EmitCoroutineIntrinsic(E, Intrinsic::coro_done); 2164 case Builtin::BI__builtin_coro_alloc: 2165 return EmitCoroutineIntrinsic(E, Intrinsic::coro_alloc); 2166 case Builtin::BI__builtin_coro_begin: 2167 return EmitCoroutineIntrinsic(E, Intrinsic::coro_begin); 2168 case Builtin::BI__builtin_coro_end: 2169 return EmitCoroutineIntrinsic(E, Intrinsic::coro_end); 2170 case Builtin::BI__builtin_coro_suspend: 2171 return EmitCoroutineIntrinsic(E, Intrinsic::coro_suspend); 2172 case Builtin::BI__builtin_coro_param: 2173 return EmitCoroutineIntrinsic(E, Intrinsic::coro_param); 2174 2175 // OpenCL v2.0 s6.13.16.2, Built-in pipe read and write functions 2176 case Builtin::BIread_pipe: 2177 case Builtin::BIwrite_pipe: { 2178 Value *Arg0 = EmitScalarExpr(E->getArg(0)), 2179 *Arg1 = EmitScalarExpr(E->getArg(1)); 2180 CGOpenCLRuntime OpenCLRT(CGM); 2181 Value *PacketSize = OpenCLRT.getPipeElemSize(E->getArg(0)); 2182 Value *PacketAlign = OpenCLRT.getPipeElemAlign(E->getArg(0)); 2183 2184 // Type of the generic packet parameter. 2185 unsigned GenericAS = 2186 getContext().getTargetAddressSpace(LangAS::opencl_generic); 2187 llvm::Type *I8PTy = llvm::PointerType::get( 2188 llvm::Type::getInt8Ty(getLLVMContext()), GenericAS); 2189 2190 // Testing which overloaded version we should generate the call for. 2191 if (2U == E->getNumArgs()) { 2192 const char *Name = (BuiltinID == Builtin::BIread_pipe) ? "__read_pipe_2" 2193 : "__write_pipe_2"; 2194 // Creating a generic function type to be able to call with any builtin or 2195 // user defined type. 2196 llvm::Type *ArgTys[] = {Arg0->getType(), I8PTy, Int32Ty, Int32Ty}; 2197 llvm::FunctionType *FTy = llvm::FunctionType::get( 2198 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys), false); 2199 Value *BCast = Builder.CreatePointerCast(Arg1, I8PTy); 2200 return RValue::get( 2201 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2202 {Arg0, BCast, PacketSize, PacketAlign})); 2203 } else { 2204 assert(4 == E->getNumArgs() && 2205 "Illegal number of parameters to pipe function"); 2206 const char *Name = (BuiltinID == Builtin::BIread_pipe) ? "__read_pipe_4" 2207 : "__write_pipe_4"; 2208 2209 llvm::Type *ArgTys[] = {Arg0->getType(), Arg1->getType(), Int32Ty, I8PTy, 2210 Int32Ty, Int32Ty}; 2211 Value *Arg2 = EmitScalarExpr(E->getArg(2)), 2212 *Arg3 = EmitScalarExpr(E->getArg(3)); 2213 llvm::FunctionType *FTy = llvm::FunctionType::get( 2214 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys), false); 2215 Value *BCast = Builder.CreatePointerCast(Arg3, I8PTy); 2216 // We know the third argument is an integer type, but we may need to cast 2217 // it to i32. 2218 if (Arg2->getType() != Int32Ty) 2219 Arg2 = Builder.CreateZExtOrTrunc(Arg2, Int32Ty); 2220 return RValue::get(Builder.CreateCall( 2221 CGM.CreateRuntimeFunction(FTy, Name), 2222 {Arg0, Arg1, Arg2, BCast, PacketSize, PacketAlign})); 2223 } 2224 } 2225 // OpenCL v2.0 s6.13.16 ,s9.17.3.5 - Built-in pipe reserve read and write 2226 // functions 2227 case Builtin::BIreserve_read_pipe: 2228 case Builtin::BIreserve_write_pipe: 2229 case Builtin::BIwork_group_reserve_read_pipe: 2230 case Builtin::BIwork_group_reserve_write_pipe: 2231 case Builtin::BIsub_group_reserve_read_pipe: 2232 case Builtin::BIsub_group_reserve_write_pipe: { 2233 // Composing the mangled name for the function. 2234 const char *Name; 2235 if (BuiltinID == Builtin::BIreserve_read_pipe) 2236 Name = "__reserve_read_pipe"; 2237 else if (BuiltinID == Builtin::BIreserve_write_pipe) 2238 Name = "__reserve_write_pipe"; 2239 else if (BuiltinID == Builtin::BIwork_group_reserve_read_pipe) 2240 Name = "__work_group_reserve_read_pipe"; 2241 else if (BuiltinID == Builtin::BIwork_group_reserve_write_pipe) 2242 Name = "__work_group_reserve_write_pipe"; 2243 else if (BuiltinID == Builtin::BIsub_group_reserve_read_pipe) 2244 Name = "__sub_group_reserve_read_pipe"; 2245 else 2246 Name = "__sub_group_reserve_write_pipe"; 2247 2248 Value *Arg0 = EmitScalarExpr(E->getArg(0)), 2249 *Arg1 = EmitScalarExpr(E->getArg(1)); 2250 llvm::Type *ReservedIDTy = ConvertType(getContext().OCLReserveIDTy); 2251 CGOpenCLRuntime OpenCLRT(CGM); 2252 Value *PacketSize = OpenCLRT.getPipeElemSize(E->getArg(0)); 2253 Value *PacketAlign = OpenCLRT.getPipeElemAlign(E->getArg(0)); 2254 2255 // Building the generic function prototype. 2256 llvm::Type *ArgTys[] = {Arg0->getType(), Int32Ty, Int32Ty, Int32Ty}; 2257 llvm::FunctionType *FTy = llvm::FunctionType::get( 2258 ReservedIDTy, llvm::ArrayRef<llvm::Type *>(ArgTys), false); 2259 // We know the second argument is an integer type, but we may need to cast 2260 // it to i32. 2261 if (Arg1->getType() != Int32Ty) 2262 Arg1 = Builder.CreateZExtOrTrunc(Arg1, Int32Ty); 2263 return RValue::get( 2264 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2265 {Arg0, Arg1, PacketSize, PacketAlign})); 2266 } 2267 // OpenCL v2.0 s6.13.16, s9.17.3.5 - Built-in pipe commit read and write 2268 // functions 2269 case Builtin::BIcommit_read_pipe: 2270 case Builtin::BIcommit_write_pipe: 2271 case Builtin::BIwork_group_commit_read_pipe: 2272 case Builtin::BIwork_group_commit_write_pipe: 2273 case Builtin::BIsub_group_commit_read_pipe: 2274 case Builtin::BIsub_group_commit_write_pipe: { 2275 const char *Name; 2276 if (BuiltinID == Builtin::BIcommit_read_pipe) 2277 Name = "__commit_read_pipe"; 2278 else if (BuiltinID == Builtin::BIcommit_write_pipe) 2279 Name = "__commit_write_pipe"; 2280 else if (BuiltinID == Builtin::BIwork_group_commit_read_pipe) 2281 Name = "__work_group_commit_read_pipe"; 2282 else if (BuiltinID == Builtin::BIwork_group_commit_write_pipe) 2283 Name = "__work_group_commit_write_pipe"; 2284 else if (BuiltinID == Builtin::BIsub_group_commit_read_pipe) 2285 Name = "__sub_group_commit_read_pipe"; 2286 else 2287 Name = "__sub_group_commit_write_pipe"; 2288 2289 Value *Arg0 = EmitScalarExpr(E->getArg(0)), 2290 *Arg1 = EmitScalarExpr(E->getArg(1)); 2291 CGOpenCLRuntime OpenCLRT(CGM); 2292 Value *PacketSize = OpenCLRT.getPipeElemSize(E->getArg(0)); 2293 Value *PacketAlign = OpenCLRT.getPipeElemAlign(E->getArg(0)); 2294 2295 // Building the generic function prototype. 2296 llvm::Type *ArgTys[] = {Arg0->getType(), Arg1->getType(), Int32Ty, Int32Ty}; 2297 llvm::FunctionType *FTy = 2298 llvm::FunctionType::get(llvm::Type::getVoidTy(getLLVMContext()), 2299 llvm::ArrayRef<llvm::Type *>(ArgTys), false); 2300 2301 return RValue::get( 2302 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2303 {Arg0, Arg1, PacketSize, PacketAlign})); 2304 } 2305 // OpenCL v2.0 s6.13.16.4 Built-in pipe query functions 2306 case Builtin::BIget_pipe_num_packets: 2307 case Builtin::BIget_pipe_max_packets: { 2308 const char *Name; 2309 if (BuiltinID == Builtin::BIget_pipe_num_packets) 2310 Name = "__get_pipe_num_packets"; 2311 else 2312 Name = "__get_pipe_max_packets"; 2313 2314 // Building the generic function prototype. 2315 Value *Arg0 = EmitScalarExpr(E->getArg(0)); 2316 CGOpenCLRuntime OpenCLRT(CGM); 2317 Value *PacketSize = OpenCLRT.getPipeElemSize(E->getArg(0)); 2318 Value *PacketAlign = OpenCLRT.getPipeElemAlign(E->getArg(0)); 2319 llvm::Type *ArgTys[] = {Arg0->getType(), Int32Ty, Int32Ty}; 2320 llvm::FunctionType *FTy = llvm::FunctionType::get( 2321 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys), false); 2322 2323 return RValue::get(Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2324 {Arg0, PacketSize, PacketAlign})); 2325 } 2326 2327 // OpenCL v2.0 s6.13.9 - Address space qualifier functions. 2328 case Builtin::BIto_global: 2329 case Builtin::BIto_local: 2330 case Builtin::BIto_private: { 2331 auto Arg0 = EmitScalarExpr(E->getArg(0)); 2332 auto NewArgT = llvm::PointerType::get(Int8Ty, 2333 CGM.getContext().getTargetAddressSpace(LangAS::opencl_generic)); 2334 auto NewRetT = llvm::PointerType::get(Int8Ty, 2335 CGM.getContext().getTargetAddressSpace( 2336 E->getType()->getPointeeType().getAddressSpace())); 2337 auto FTy = llvm::FunctionType::get(NewRetT, {NewArgT}, false); 2338 llvm::Value *NewArg; 2339 if (Arg0->getType()->getPointerAddressSpace() != 2340 NewArgT->getPointerAddressSpace()) 2341 NewArg = Builder.CreateAddrSpaceCast(Arg0, NewArgT); 2342 else 2343 NewArg = Builder.CreateBitOrPointerCast(Arg0, NewArgT); 2344 auto NewName = std::string("__") + E->getDirectCallee()->getName().str(); 2345 auto NewCall = 2346 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, NewName), {NewArg}); 2347 return RValue::get(Builder.CreateBitOrPointerCast(NewCall, 2348 ConvertType(E->getType()))); 2349 } 2350 2351 // OpenCL v2.0, s6.13.17 - Enqueue kernel function. 2352 // It contains four different overload formats specified in Table 6.13.17.1. 2353 case Builtin::BIenqueue_kernel: { 2354 StringRef Name; // Generated function call name 2355 unsigned NumArgs = E->getNumArgs(); 2356 2357 llvm::Type *QueueTy = ConvertType(getContext().OCLQueueTy); 2358 llvm::Type *RangeTy = ConvertType(getContext().OCLNDRangeTy); 2359 2360 llvm::Value *Queue = EmitScalarExpr(E->getArg(0)); 2361 llvm::Value *Flags = EmitScalarExpr(E->getArg(1)); 2362 llvm::Value *Range = EmitScalarExpr(E->getArg(2)); 2363 2364 if (NumArgs == 4) { 2365 // The most basic form of the call with parameters: 2366 // queue_t, kernel_enqueue_flags_t, ndrange_t, block(void) 2367 Name = "__enqueue_kernel_basic"; 2368 llvm::Type *ArgTys[] = {QueueTy, Int32Ty, RangeTy, Int8PtrTy}; 2369 llvm::FunctionType *FTy = llvm::FunctionType::get( 2370 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys, 4), false); 2371 2372 llvm::Value *Block = 2373 Builder.CreateBitCast(EmitScalarExpr(E->getArg(3)), Int8PtrTy); 2374 2375 return RValue::get(Builder.CreateCall( 2376 CGM.CreateRuntimeFunction(FTy, Name), {Queue, Flags, Range, Block})); 2377 } 2378 assert(NumArgs >= 5 && "Invalid enqueue_kernel signature"); 2379 2380 // Could have events and/or vaargs. 2381 if (E->getArg(3)->getType()->isBlockPointerType()) { 2382 // No events passed, but has variadic arguments. 2383 Name = "__enqueue_kernel_vaargs"; 2384 llvm::Value *Block = 2385 Builder.CreateBitCast(EmitScalarExpr(E->getArg(3)), Int8PtrTy); 2386 // Create a vector of the arguments, as well as a constant value to 2387 // express to the runtime the number of variadic arguments. 2388 std::vector<llvm::Value *> Args = {Queue, Flags, Range, Block, 2389 ConstantInt::get(IntTy, NumArgs - 4)}; 2390 std::vector<llvm::Type *> ArgTys = {QueueTy, IntTy, RangeTy, Int8PtrTy, 2391 IntTy}; 2392 2393 // Add the variadics. 2394 for (unsigned I = 4; I < NumArgs; ++I) { 2395 llvm::Value *ArgSize = EmitScalarExpr(E->getArg(I)); 2396 unsigned TypeSizeInBytes = 2397 getContext() 2398 .getTypeSizeInChars(E->getArg(I)->getType()) 2399 .getQuantity(); 2400 Args.push_back(TypeSizeInBytes < 4 2401 ? Builder.CreateZExt(ArgSize, Int32Ty) 2402 : ArgSize); 2403 } 2404 2405 llvm::FunctionType *FTy = llvm::FunctionType::get( 2406 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys), true); 2407 return RValue::get( 2408 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2409 llvm::ArrayRef<llvm::Value *>(Args))); 2410 } 2411 // Any calls now have event arguments passed. 2412 if (NumArgs >= 7) { 2413 llvm::Type *EventTy = ConvertType(getContext().OCLClkEventTy); 2414 unsigned AS4 = 2415 E->getArg(4)->getType()->isArrayType() 2416 ? E->getArg(4)->getType().getAddressSpace() 2417 : E->getArg(4)->getType()->getPointeeType().getAddressSpace(); 2418 llvm::Type *EventPtrAS4Ty = 2419 EventTy->getPointerTo(CGM.getContext().getTargetAddressSpace(AS4)); 2420 unsigned AS5 = 2421 E->getArg(5)->getType()->getPointeeType().getAddressSpace(); 2422 llvm::Type *EventPtrAS5Ty = 2423 EventTy->getPointerTo(CGM.getContext().getTargetAddressSpace(AS5)); 2424 2425 llvm::Value *NumEvents = EmitScalarExpr(E->getArg(3)); 2426 llvm::Value *EventList = 2427 E->getArg(4)->getType()->isArrayType() 2428 ? EmitArrayToPointerDecay(E->getArg(4)).getPointer() 2429 : EmitScalarExpr(E->getArg(4)); 2430 llvm::Value *ClkEvent = EmitScalarExpr(E->getArg(5)); 2431 llvm::Value *Block = 2432 Builder.CreateBitCast(EmitScalarExpr(E->getArg(6)), Int8PtrTy); 2433 2434 std::vector<llvm::Type *> ArgTys = { 2435 QueueTy, Int32Ty, RangeTy, Int32Ty, 2436 EventPtrAS4Ty, EventPtrAS5Ty, Int8PtrTy}; 2437 std::vector<llvm::Value *> Args = {Queue, Flags, Range, NumEvents, 2438 EventList, ClkEvent, Block}; 2439 2440 if (NumArgs == 7) { 2441 // Has events but no variadics. 2442 Name = "__enqueue_kernel_basic_events"; 2443 llvm::FunctionType *FTy = llvm::FunctionType::get( 2444 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys), false); 2445 return RValue::get( 2446 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2447 llvm::ArrayRef<llvm::Value *>(Args))); 2448 } 2449 // Has event info and variadics 2450 // Pass the number of variadics to the runtime function too. 2451 Args.push_back(ConstantInt::get(Int32Ty, NumArgs - 7)); 2452 ArgTys.push_back(Int32Ty); 2453 Name = "__enqueue_kernel_events_vaargs"; 2454 2455 // Add the variadics. 2456 for (unsigned I = 7; I < NumArgs; ++I) { 2457 llvm::Value *ArgSize = EmitScalarExpr(E->getArg(I)); 2458 unsigned TypeSizeInBytes = 2459 getContext() 2460 .getTypeSizeInChars(E->getArg(I)->getType()) 2461 .getQuantity(); 2462 Args.push_back(TypeSizeInBytes < 4 2463 ? Builder.CreateZExt(ArgSize, Int32Ty) 2464 : ArgSize); 2465 } 2466 llvm::FunctionType *FTy = llvm::FunctionType::get( 2467 Int32Ty, llvm::ArrayRef<llvm::Type *>(ArgTys), true); 2468 return RValue::get( 2469 Builder.CreateCall(CGM.CreateRuntimeFunction(FTy, Name), 2470 llvm::ArrayRef<llvm::Value *>(Args))); 2471 } 2472 } 2473 // OpenCL v2.0 s6.13.17.6 - Kernel query functions need bitcast of block 2474 // parameter. 2475 case Builtin::BIget_kernel_work_group_size: { 2476 Value *Arg = EmitScalarExpr(E->getArg(0)); 2477 Arg = Builder.CreateBitCast(Arg, Int8PtrTy); 2478 return RValue::get( 2479 Builder.CreateCall(CGM.CreateRuntimeFunction( 2480 llvm::FunctionType::get(IntTy, Int8PtrTy, false), 2481 "__get_kernel_work_group_size_impl"), 2482 Arg)); 2483 } 2484 case Builtin::BIget_kernel_preferred_work_group_size_multiple: { 2485 Value *Arg = EmitScalarExpr(E->getArg(0)); 2486 Arg = Builder.CreateBitCast(Arg, Int8PtrTy); 2487 return RValue::get(Builder.CreateCall( 2488 CGM.CreateRuntimeFunction( 2489 llvm::FunctionType::get(IntTy, Int8PtrTy, false), 2490 "__get_kernel_preferred_work_group_multiple_impl"), 2491 Arg)); 2492 } 2493 case Builtin::BIprintf: 2494 if (getLangOpts().CUDA && getLangOpts().CUDAIsDevice) 2495 return EmitCUDADevicePrintfCallExpr(E, ReturnValue); 2496 break; 2497 case Builtin::BI__builtin_canonicalize: 2498 case Builtin::BI__builtin_canonicalizef: 2499 case Builtin::BI__builtin_canonicalizel: 2500 return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::canonicalize)); 2501 2502 case Builtin::BI__builtin_thread_pointer: { 2503 if (!getContext().getTargetInfo().isTLSSupported()) 2504 CGM.ErrorUnsupported(E, "__builtin_thread_pointer"); 2505 // Fall through - it's already mapped to the intrinsic by GCCBuiltin. 2506 break; 2507 } 2508 } 2509 2510 // If this is an alias for a lib function (e.g. __builtin_sin), emit 2511 // the call using the normal call path, but using the unmangled 2512 // version of the function name. 2513 if (getContext().BuiltinInfo.isLibFunction(BuiltinID)) 2514 return emitLibraryCall(*this, FD, E, 2515 CGM.getBuiltinLibFunction(FD, BuiltinID)); 2516 2517 // If this is a predefined lib function (e.g. malloc), emit the call 2518 // using exactly the normal call path. 2519 if (getContext().BuiltinInfo.isPredefinedLibFunction(BuiltinID)) 2520 return emitLibraryCall(*this, FD, E, EmitScalarExpr(E->getCallee())); 2521 2522 // Check that a call to a target specific builtin has the correct target 2523 // features. 2524 // This is down here to avoid non-target specific builtins, however, if 2525 // generic builtins start to require generic target features then we 2526 // can move this up to the beginning of the function. 2527 checkTargetFeatures(E, FD); 2528 2529 // See if we have a target specific intrinsic. 2530 const char *Name = getContext().BuiltinInfo.getName(BuiltinID); 2531 Intrinsic::ID IntrinsicID = Intrinsic::not_intrinsic; 2532 StringRef Prefix = 2533 llvm::Triple::getArchTypePrefix(getTarget().getTriple().getArch()); 2534 if (!Prefix.empty()) { 2535 IntrinsicID = Intrinsic::getIntrinsicForGCCBuiltin(Prefix.data(), Name); 2536 // NOTE we dont need to perform a compatibility flag check here since the 2537 // intrinsics are declared in Builtins*.def via LANGBUILTIN which filter the 2538 // MS builtins via ALL_MS_LANGUAGES and are filtered earlier. 2539 if (IntrinsicID == Intrinsic::not_intrinsic) 2540 IntrinsicID = Intrinsic::getIntrinsicForMSBuiltin(Prefix.data(), Name); 2541 } 2542 2543 if (IntrinsicID != Intrinsic::not_intrinsic) { 2544 SmallVector<Value*, 16> Args; 2545 2546 // Find out if any arguments are required to be integer constant 2547 // expressions. 2548 unsigned ICEArguments = 0; 2549 ASTContext::GetBuiltinTypeError Error; 2550 getContext().GetBuiltinType(BuiltinID, Error, &ICEArguments); 2551 assert(Error == ASTContext::GE_None && "Should not codegen an error"); 2552 2553 Function *F = CGM.getIntrinsic(IntrinsicID); 2554 llvm::FunctionType *FTy = F->getFunctionType(); 2555 2556 for (unsigned i = 0, e = E->getNumArgs(); i != e; ++i) { 2557 Value *ArgValue; 2558 // If this is a normal argument, just emit it as a scalar. 2559 if ((ICEArguments & (1 << i)) == 0) { 2560 ArgValue = EmitScalarExpr(E->getArg(i)); 2561 } else { 2562 // If this is required to be a constant, constant fold it so that we 2563 // know that the generated intrinsic gets a ConstantInt. 2564 llvm::APSInt Result; 2565 bool IsConst = E->getArg(i)->isIntegerConstantExpr(Result,getContext()); 2566 assert(IsConst && "Constant arg isn't actually constant?"); 2567 (void)IsConst; 2568 ArgValue = llvm::ConstantInt::get(getLLVMContext(), Result); 2569 } 2570 2571 // If the intrinsic arg type is different from the builtin arg type 2572 // we need to do a bit cast. 2573 llvm::Type *PTy = FTy->getParamType(i); 2574 if (PTy != ArgValue->getType()) { 2575 assert(PTy->canLosslesslyBitCastTo(FTy->getParamType(i)) && 2576 "Must be able to losslessly bit cast to param"); 2577 ArgValue = Builder.CreateBitCast(ArgValue, PTy); 2578 } 2579 2580 Args.push_back(ArgValue); 2581 } 2582 2583 Value *V = Builder.CreateCall(F, Args); 2584 QualType BuiltinRetType = E->getType(); 2585 2586 llvm::Type *RetTy = VoidTy; 2587 if (!BuiltinRetType->isVoidType()) 2588 RetTy = ConvertType(BuiltinRetType); 2589 2590 if (RetTy != V->getType()) { 2591 assert(V->getType()->canLosslesslyBitCastTo(RetTy) && 2592 "Must be able to losslessly bit cast result type"); 2593 V = Builder.CreateBitCast(V, RetTy); 2594 } 2595 2596 return RValue::get(V); 2597 } 2598 2599 // See if we have a target specific builtin that needs to be lowered. 2600 if (Value *V = EmitTargetBuiltinExpr(BuiltinID, E)) 2601 return RValue::get(V); 2602 2603 ErrorUnsupported(E, "builtin function"); 2604 2605 // Unknown builtin, for now just dump it out and return undef. 2606 return GetUndefRValue(E->getType()); 2607 } 2608 2609 static Value *EmitTargetArchBuiltinExpr(CodeGenFunction *CGF, 2610 unsigned BuiltinID, const CallExpr *E, 2611 llvm::Triple::ArchType Arch) { 2612 switch (Arch) { 2613 case llvm::Triple::arm: 2614 case llvm::Triple::armeb: 2615 case llvm::Triple::thumb: 2616 case llvm::Triple::thumbeb: 2617 return CGF->EmitARMBuiltinExpr(BuiltinID, E); 2618 case llvm::Triple::aarch64: 2619 case llvm::Triple::aarch64_be: 2620 return CGF->EmitAArch64BuiltinExpr(BuiltinID, E); 2621 case llvm::Triple::x86: 2622 case llvm::Triple::x86_64: 2623 return CGF->EmitX86BuiltinExpr(BuiltinID, E); 2624 case llvm::Triple::ppc: 2625 case llvm::Triple::ppc64: 2626 case llvm::Triple::ppc64le: 2627 return CGF->EmitPPCBuiltinExpr(BuiltinID, E); 2628 case llvm::Triple::r600: 2629 case llvm::Triple::amdgcn: 2630 return CGF->EmitAMDGPUBuiltinExpr(BuiltinID, E); 2631 case llvm::Triple::systemz: 2632 return CGF->EmitSystemZBuiltinExpr(BuiltinID, E); 2633 case llvm::Triple::nvptx: 2634 case llvm::Triple::nvptx64: 2635 return CGF->EmitNVPTXBuiltinExpr(BuiltinID, E); 2636 case llvm::Triple::wasm32: 2637 case llvm::Triple::wasm64: 2638 return CGF->EmitWebAssemblyBuiltinExpr(BuiltinID, E); 2639 default: 2640 return nullptr; 2641 } 2642 } 2643 2644 // Many of MSVC builtins are on both x64 and ARM; to avoid repeating code, we 2645 // handle them here. 2646 enum class CodeGenFunction::MSVCIntrin { 2647 _BitScanForward, 2648 _BitScanReverse 2649 }; 2650 2651 Value *CodeGenFunction::EmitMSVCBuiltinExpr(MSVCIntrin BuiltinID, 2652 const CallExpr *E) { 2653 switch (BuiltinID) { 2654 case MSVCIntrin::_BitScanForward: 2655 case MSVCIntrin::_BitScanReverse: { 2656 Value *ArgValue = EmitScalarExpr(E->getArg(1)); 2657 2658 llvm::Type *ArgType = ArgValue->getType(); 2659 llvm::Type *IndexType = 2660 EmitScalarExpr(E->getArg(0))->getType()->getPointerElementType(); 2661 llvm::Type *ResultType = ConvertType(E->getType()); 2662 2663 Value *ArgZero = llvm::Constant::getNullValue(ArgType); 2664 Value *ResZero = llvm::Constant::getNullValue(ResultType); 2665 Value *ResOne = llvm::ConstantInt::get(ResultType, 1); 2666 2667 BasicBlock *Begin = Builder.GetInsertBlock(); 2668 BasicBlock *End = createBasicBlock("bitscan_end", this->CurFn); 2669 Builder.SetInsertPoint(End); 2670 PHINode *Result = Builder.CreatePHI(ResultType, 2, "bitscan_result"); 2671 2672 Builder.SetInsertPoint(Begin); 2673 Value *IsZero = Builder.CreateICmpEQ(ArgValue, ArgZero); 2674 BasicBlock *NotZero = createBasicBlock("bitscan_not_zero", this->CurFn); 2675 Builder.CreateCondBr(IsZero, End, NotZero); 2676 Result->addIncoming(ResZero, Begin); 2677 2678 Builder.SetInsertPoint(NotZero); 2679 Address IndexAddress = EmitPointerWithAlignment(E->getArg(0)); 2680 2681 if (BuiltinID == MSVCIntrin::_BitScanForward) { 2682 Value *F = CGM.getIntrinsic(Intrinsic::cttz, ArgType); 2683 Value *ZeroCount = Builder.CreateCall(F, {ArgValue, Builder.getTrue()}); 2684 ZeroCount = Builder.CreateIntCast(ZeroCount, IndexType, false); 2685 Builder.CreateStore(ZeroCount, IndexAddress, false); 2686 } else { 2687 unsigned ArgWidth = cast<llvm::IntegerType>(ArgType)->getBitWidth(); 2688 Value *ArgTypeLastIndex = llvm::ConstantInt::get(IndexType, ArgWidth - 1); 2689 2690 Value *F = CGM.getIntrinsic(Intrinsic::ctlz, ArgType); 2691 Value *ZeroCount = Builder.CreateCall(F, {ArgValue, Builder.getTrue()}); 2692 ZeroCount = Builder.CreateIntCast(ZeroCount, IndexType, false); 2693 Value *Index = Builder.CreateNSWSub(ArgTypeLastIndex, ZeroCount); 2694 Builder.CreateStore(Index, IndexAddress, false); 2695 } 2696 Builder.CreateBr(End); 2697 Result->addIncoming(ResOne, NotZero); 2698 2699 Builder.SetInsertPoint(End); 2700 return Result; 2701 } 2702 } 2703 llvm_unreachable("Incorrect MSVC intrinsic!"); 2704 } 2705 2706 Value *CodeGenFunction::EmitTargetBuiltinExpr(unsigned BuiltinID, 2707 const CallExpr *E) { 2708 if (getContext().BuiltinInfo.isAuxBuiltinID(BuiltinID)) { 2709 assert(getContext().getAuxTargetInfo() && "Missing aux target info"); 2710 return EmitTargetArchBuiltinExpr( 2711 this, getContext().BuiltinInfo.getAuxBuiltinID(BuiltinID), E, 2712 getContext().getAuxTargetInfo()->getTriple().getArch()); 2713 } 2714 2715 return EmitTargetArchBuiltinExpr(this, BuiltinID, E, 2716 getTarget().getTriple().getArch()); 2717 } 2718 2719 static llvm::VectorType *GetNeonType(CodeGenFunction *CGF, 2720 NeonTypeFlags TypeFlags, 2721 bool V1Ty=false) { 2722 int IsQuad = TypeFlags.isQuad(); 2723 switch (TypeFlags.getEltType()) { 2724 case NeonTypeFlags::Int8: 2725 case NeonTypeFlags::Poly8: 2726 return llvm::VectorType::get(CGF->Int8Ty, V1Ty ? 1 : (8 << IsQuad)); 2727 case NeonTypeFlags::Int16: 2728 case NeonTypeFlags::Poly16: 2729 case NeonTypeFlags::Float16: 2730 return llvm::VectorType::get(CGF->Int16Ty, V1Ty ? 1 : (4 << IsQuad)); 2731 case NeonTypeFlags::Int32: 2732 return llvm::VectorType::get(CGF->Int32Ty, V1Ty ? 1 : (2 << IsQuad)); 2733 case NeonTypeFlags::Int64: 2734 case NeonTypeFlags::Poly64: 2735 return llvm::VectorType::get(CGF->Int64Ty, V1Ty ? 1 : (1 << IsQuad)); 2736 case NeonTypeFlags::Poly128: 2737 // FIXME: i128 and f128 doesn't get fully support in Clang and llvm. 2738 // There is a lot of i128 and f128 API missing. 2739 // so we use v16i8 to represent poly128 and get pattern matched. 2740 return llvm::VectorType::get(CGF->Int8Ty, 16); 2741 case NeonTypeFlags::Float32: 2742 return llvm::VectorType::get(CGF->FloatTy, V1Ty ? 1 : (2 << IsQuad)); 2743 case NeonTypeFlags::Float64: 2744 return llvm::VectorType::get(CGF->DoubleTy, V1Ty ? 1 : (1 << IsQuad)); 2745 } 2746 llvm_unreachable("Unknown vector element type!"); 2747 } 2748 2749 static llvm::VectorType *GetFloatNeonType(CodeGenFunction *CGF, 2750 NeonTypeFlags IntTypeFlags) { 2751 int IsQuad = IntTypeFlags.isQuad(); 2752 switch (IntTypeFlags.getEltType()) { 2753 case NeonTypeFlags::Int32: 2754 return llvm::VectorType::get(CGF->FloatTy, (2 << IsQuad)); 2755 case NeonTypeFlags::Int64: 2756 return llvm::VectorType::get(CGF->DoubleTy, (1 << IsQuad)); 2757 default: 2758 llvm_unreachable("Type can't be converted to floating-point!"); 2759 } 2760 } 2761 2762 Value *CodeGenFunction::EmitNeonSplat(Value *V, Constant *C) { 2763 unsigned nElts = V->getType()->getVectorNumElements(); 2764 Value* SV = llvm::ConstantVector::getSplat(nElts, C); 2765 return Builder.CreateShuffleVector(V, V, SV, "lane"); 2766 } 2767 2768 Value *CodeGenFunction::EmitNeonCall(Function *F, SmallVectorImpl<Value*> &Ops, 2769 const char *name, 2770 unsigned shift, bool rightshift) { 2771 unsigned j = 0; 2772 for (Function::const_arg_iterator ai = F->arg_begin(), ae = F->arg_end(); 2773 ai != ae; ++ai, ++j) 2774 if (shift > 0 && shift == j) 2775 Ops[j] = EmitNeonShiftVector(Ops[j], ai->getType(), rightshift); 2776 else 2777 Ops[j] = Builder.CreateBitCast(Ops[j], ai->getType(), name); 2778 2779 return Builder.CreateCall(F, Ops, name); 2780 } 2781 2782 Value *CodeGenFunction::EmitNeonShiftVector(Value *V, llvm::Type *Ty, 2783 bool neg) { 2784 int SV = cast<ConstantInt>(V)->getSExtValue(); 2785 return ConstantInt::get(Ty, neg ? -SV : SV); 2786 } 2787 2788 // \brief Right-shift a vector by a constant. 2789 Value *CodeGenFunction::EmitNeonRShiftImm(Value *Vec, Value *Shift, 2790 llvm::Type *Ty, bool usgn, 2791 const char *name) { 2792 llvm::VectorType *VTy = cast<llvm::VectorType>(Ty); 2793 2794 int ShiftAmt = cast<ConstantInt>(Shift)->getSExtValue(); 2795 int EltSize = VTy->getScalarSizeInBits(); 2796 2797 Vec = Builder.CreateBitCast(Vec, Ty); 2798 2799 // lshr/ashr are undefined when the shift amount is equal to the vector 2800 // element size. 2801 if (ShiftAmt == EltSize) { 2802 if (usgn) { 2803 // Right-shifting an unsigned value by its size yields 0. 2804 return llvm::ConstantAggregateZero::get(VTy); 2805 } else { 2806 // Right-shifting a signed value by its size is equivalent 2807 // to a shift of size-1. 2808 --ShiftAmt; 2809 Shift = ConstantInt::get(VTy->getElementType(), ShiftAmt); 2810 } 2811 } 2812 2813 Shift = EmitNeonShiftVector(Shift, Ty, false); 2814 if (usgn) 2815 return Builder.CreateLShr(Vec, Shift, name); 2816 else 2817 return Builder.CreateAShr(Vec, Shift, name); 2818 } 2819 2820 enum { 2821 AddRetType = (1 << 0), 2822 Add1ArgType = (1 << 1), 2823 Add2ArgTypes = (1 << 2), 2824 2825 VectorizeRetType = (1 << 3), 2826 VectorizeArgTypes = (1 << 4), 2827 2828 InventFloatType = (1 << 5), 2829 UnsignedAlts = (1 << 6), 2830 2831 Use64BitVectors = (1 << 7), 2832 Use128BitVectors = (1 << 8), 2833 2834 Vectorize1ArgType = Add1ArgType | VectorizeArgTypes, 2835 VectorRet = AddRetType | VectorizeRetType, 2836 VectorRetGetArgs01 = 2837 AddRetType | Add2ArgTypes | VectorizeRetType | VectorizeArgTypes, 2838 FpCmpzModifiers = 2839 AddRetType | VectorizeRetType | Add1ArgType | InventFloatType 2840 }; 2841 2842 namespace { 2843 struct NeonIntrinsicInfo { 2844 const char *NameHint; 2845 unsigned BuiltinID; 2846 unsigned LLVMIntrinsic; 2847 unsigned AltLLVMIntrinsic; 2848 unsigned TypeModifier; 2849 2850 bool operator<(unsigned RHSBuiltinID) const { 2851 return BuiltinID < RHSBuiltinID; 2852 } 2853 bool operator<(const NeonIntrinsicInfo &TE) const { 2854 return BuiltinID < TE.BuiltinID; 2855 } 2856 }; 2857 } // end anonymous namespace 2858 2859 #define NEONMAP0(NameBase) \ 2860 { #NameBase, NEON::BI__builtin_neon_ ## NameBase, 0, 0, 0 } 2861 2862 #define NEONMAP1(NameBase, LLVMIntrinsic, TypeModifier) \ 2863 { #NameBase, NEON:: BI__builtin_neon_ ## NameBase, \ 2864 Intrinsic::LLVMIntrinsic, 0, TypeModifier } 2865 2866 #define NEONMAP2(NameBase, LLVMIntrinsic, AltLLVMIntrinsic, TypeModifier) \ 2867 { #NameBase, NEON:: BI__builtin_neon_ ## NameBase, \ 2868 Intrinsic::LLVMIntrinsic, Intrinsic::AltLLVMIntrinsic, \ 2869 TypeModifier } 2870 2871 static const NeonIntrinsicInfo ARMSIMDIntrinsicMap [] = { 2872 NEONMAP2(vabd_v, arm_neon_vabdu, arm_neon_vabds, Add1ArgType | UnsignedAlts), 2873 NEONMAP2(vabdq_v, arm_neon_vabdu, arm_neon_vabds, Add1ArgType | UnsignedAlts), 2874 NEONMAP1(vabs_v, arm_neon_vabs, 0), 2875 NEONMAP1(vabsq_v, arm_neon_vabs, 0), 2876 NEONMAP0(vaddhn_v), 2877 NEONMAP1(vaesdq_v, arm_neon_aesd, 0), 2878 NEONMAP1(vaeseq_v, arm_neon_aese, 0), 2879 NEONMAP1(vaesimcq_v, arm_neon_aesimc, 0), 2880 NEONMAP1(vaesmcq_v, arm_neon_aesmc, 0), 2881 NEONMAP1(vbsl_v, arm_neon_vbsl, AddRetType), 2882 NEONMAP1(vbslq_v, arm_neon_vbsl, AddRetType), 2883 NEONMAP1(vcage_v, arm_neon_vacge, 0), 2884 NEONMAP1(vcageq_v, arm_neon_vacge, 0), 2885 NEONMAP1(vcagt_v, arm_neon_vacgt, 0), 2886 NEONMAP1(vcagtq_v, arm_neon_vacgt, 0), 2887 NEONMAP1(vcale_v, arm_neon_vacge, 0), 2888 NEONMAP1(vcaleq_v, arm_neon_vacge, 0), 2889 NEONMAP1(vcalt_v, arm_neon_vacgt, 0), 2890 NEONMAP1(vcaltq_v, arm_neon_vacgt, 0), 2891 NEONMAP1(vcls_v, arm_neon_vcls, Add1ArgType), 2892 NEONMAP1(vclsq_v, arm_neon_vcls, Add1ArgType), 2893 NEONMAP1(vclz_v, ctlz, Add1ArgType), 2894 NEONMAP1(vclzq_v, ctlz, Add1ArgType), 2895 NEONMAP1(vcnt_v, ctpop, Add1ArgType), 2896 NEONMAP1(vcntq_v, ctpop, Add1ArgType), 2897 NEONMAP1(vcvt_f16_f32, arm_neon_vcvtfp2hf, 0), 2898 NEONMAP1(vcvt_f32_f16, arm_neon_vcvthf2fp, 0), 2899 NEONMAP0(vcvt_f32_v), 2900 NEONMAP2(vcvt_n_f32_v, arm_neon_vcvtfxu2fp, arm_neon_vcvtfxs2fp, 0), 2901 NEONMAP1(vcvt_n_s32_v, arm_neon_vcvtfp2fxs, 0), 2902 NEONMAP1(vcvt_n_s64_v, arm_neon_vcvtfp2fxs, 0), 2903 NEONMAP1(vcvt_n_u32_v, arm_neon_vcvtfp2fxu, 0), 2904 NEONMAP1(vcvt_n_u64_v, arm_neon_vcvtfp2fxu, 0), 2905 NEONMAP0(vcvt_s32_v), 2906 NEONMAP0(vcvt_s64_v), 2907 NEONMAP0(vcvt_u32_v), 2908 NEONMAP0(vcvt_u64_v), 2909 NEONMAP1(vcvta_s32_v, arm_neon_vcvtas, 0), 2910 NEONMAP1(vcvta_s64_v, arm_neon_vcvtas, 0), 2911 NEONMAP1(vcvta_u32_v, arm_neon_vcvtau, 0), 2912 NEONMAP1(vcvta_u64_v, arm_neon_vcvtau, 0), 2913 NEONMAP1(vcvtaq_s32_v, arm_neon_vcvtas, 0), 2914 NEONMAP1(vcvtaq_s64_v, arm_neon_vcvtas, 0), 2915 NEONMAP1(vcvtaq_u32_v, arm_neon_vcvtau, 0), 2916 NEONMAP1(vcvtaq_u64_v, arm_neon_vcvtau, 0), 2917 NEONMAP1(vcvtm_s32_v, arm_neon_vcvtms, 0), 2918 NEONMAP1(vcvtm_s64_v, arm_neon_vcvtms, 0), 2919 NEONMAP1(vcvtm_u32_v, arm_neon_vcvtmu, 0), 2920 NEONMAP1(vcvtm_u64_v, arm_neon_vcvtmu, 0), 2921 NEONMAP1(vcvtmq_s32_v, arm_neon_vcvtms, 0), 2922 NEONMAP1(vcvtmq_s64_v, arm_neon_vcvtms, 0), 2923 NEONMAP1(vcvtmq_u32_v, arm_neon_vcvtmu, 0), 2924 NEONMAP1(vcvtmq_u64_v, arm_neon_vcvtmu, 0), 2925 NEONMAP1(vcvtn_s32_v, arm_neon_vcvtns, 0), 2926 NEONMAP1(vcvtn_s64_v, arm_neon_vcvtns, 0), 2927 NEONMAP1(vcvtn_u32_v, arm_neon_vcvtnu, 0), 2928 NEONMAP1(vcvtn_u64_v, arm_neon_vcvtnu, 0), 2929 NEONMAP1(vcvtnq_s32_v, arm_neon_vcvtns, 0), 2930 NEONMAP1(vcvtnq_s64_v, arm_neon_vcvtns, 0), 2931 NEONMAP1(vcvtnq_u32_v, arm_neon_vcvtnu, 0), 2932 NEONMAP1(vcvtnq_u64_v, arm_neon_vcvtnu, 0), 2933 NEONMAP1(vcvtp_s32_v, arm_neon_vcvtps, 0), 2934 NEONMAP1(vcvtp_s64_v, arm_neon_vcvtps, 0), 2935 NEONMAP1(vcvtp_u32_v, arm_neon_vcvtpu, 0), 2936 NEONMAP1(vcvtp_u64_v, arm_neon_vcvtpu, 0), 2937 NEONMAP1(vcvtpq_s32_v, arm_neon_vcvtps, 0), 2938 NEONMAP1(vcvtpq_s64_v, arm_neon_vcvtps, 0), 2939 NEONMAP1(vcvtpq_u32_v, arm_neon_vcvtpu, 0), 2940 NEONMAP1(vcvtpq_u64_v, arm_neon_vcvtpu, 0), 2941 NEONMAP0(vcvtq_f32_v), 2942 NEONMAP2(vcvtq_n_f32_v, arm_neon_vcvtfxu2fp, arm_neon_vcvtfxs2fp, 0), 2943 NEONMAP1(vcvtq_n_s32_v, arm_neon_vcvtfp2fxs, 0), 2944 NEONMAP1(vcvtq_n_s64_v, arm_neon_vcvtfp2fxs, 0), 2945 NEONMAP1(vcvtq_n_u32_v, arm_neon_vcvtfp2fxu, 0), 2946 NEONMAP1(vcvtq_n_u64_v, arm_neon_vcvtfp2fxu, 0), 2947 NEONMAP0(vcvtq_s32_v), 2948 NEONMAP0(vcvtq_s64_v), 2949 NEONMAP0(vcvtq_u32_v), 2950 NEONMAP0(vcvtq_u64_v), 2951 NEONMAP0(vext_v), 2952 NEONMAP0(vextq_v), 2953 NEONMAP0(vfma_v), 2954 NEONMAP0(vfmaq_v), 2955 NEONMAP2(vhadd_v, arm_neon_vhaddu, arm_neon_vhadds, Add1ArgType | UnsignedAlts), 2956 NEONMAP2(vhaddq_v, arm_neon_vhaddu, arm_neon_vhadds, Add1ArgType | UnsignedAlts), 2957 NEONMAP2(vhsub_v, arm_neon_vhsubu, arm_neon_vhsubs, Add1ArgType | UnsignedAlts), 2958 NEONMAP2(vhsubq_v, arm_neon_vhsubu, arm_neon_vhsubs, Add1ArgType | UnsignedAlts), 2959 NEONMAP0(vld1_dup_v), 2960 NEONMAP1(vld1_v, arm_neon_vld1, 0), 2961 NEONMAP0(vld1q_dup_v), 2962 NEONMAP1(vld1q_v, arm_neon_vld1, 0), 2963 NEONMAP1(vld2_lane_v, arm_neon_vld2lane, 0), 2964 NEONMAP1(vld2_v, arm_neon_vld2, 0), 2965 NEONMAP1(vld2q_lane_v, arm_neon_vld2lane, 0), 2966 NEONMAP1(vld2q_v, arm_neon_vld2, 0), 2967 NEONMAP1(vld3_lane_v, arm_neon_vld3lane, 0), 2968 NEONMAP1(vld3_v, arm_neon_vld3, 0), 2969 NEONMAP1(vld3q_lane_v, arm_neon_vld3lane, 0), 2970 NEONMAP1(vld3q_v, arm_neon_vld3, 0), 2971 NEONMAP1(vld4_lane_v, arm_neon_vld4lane, 0), 2972 NEONMAP1(vld4_v, arm_neon_vld4, 0), 2973 NEONMAP1(vld4q_lane_v, arm_neon_vld4lane, 0), 2974 NEONMAP1(vld4q_v, arm_neon_vld4, 0), 2975 NEONMAP2(vmax_v, arm_neon_vmaxu, arm_neon_vmaxs, Add1ArgType | UnsignedAlts), 2976 NEONMAP1(vmaxnm_v, arm_neon_vmaxnm, Add1ArgType), 2977 NEONMAP1(vmaxnmq_v, arm_neon_vmaxnm, Add1ArgType), 2978 NEONMAP2(vmaxq_v, arm_neon_vmaxu, arm_neon_vmaxs, Add1ArgType | UnsignedAlts), 2979 NEONMAP2(vmin_v, arm_neon_vminu, arm_neon_vmins, Add1ArgType | UnsignedAlts), 2980 NEONMAP1(vminnm_v, arm_neon_vminnm, Add1ArgType), 2981 NEONMAP1(vminnmq_v, arm_neon_vminnm, Add1ArgType), 2982 NEONMAP2(vminq_v, arm_neon_vminu, arm_neon_vmins, Add1ArgType | UnsignedAlts), 2983 NEONMAP0(vmovl_v), 2984 NEONMAP0(vmovn_v), 2985 NEONMAP1(vmul_v, arm_neon_vmulp, Add1ArgType), 2986 NEONMAP0(vmull_v), 2987 NEONMAP1(vmulq_v, arm_neon_vmulp, Add1ArgType), 2988 NEONMAP2(vpadal_v, arm_neon_vpadalu, arm_neon_vpadals, UnsignedAlts), 2989 NEONMAP2(vpadalq_v, arm_neon_vpadalu, arm_neon_vpadals, UnsignedAlts), 2990 NEONMAP1(vpadd_v, arm_neon_vpadd, Add1ArgType), 2991 NEONMAP2(vpaddl_v, arm_neon_vpaddlu, arm_neon_vpaddls, UnsignedAlts), 2992 NEONMAP2(vpaddlq_v, arm_neon_vpaddlu, arm_neon_vpaddls, UnsignedAlts), 2993 NEONMAP1(vpaddq_v, arm_neon_vpadd, Add1ArgType), 2994 NEONMAP2(vpmax_v, arm_neon_vpmaxu, arm_neon_vpmaxs, Add1ArgType | UnsignedAlts), 2995 NEONMAP2(vpmin_v, arm_neon_vpminu, arm_neon_vpmins, Add1ArgType | UnsignedAlts), 2996 NEONMAP1(vqabs_v, arm_neon_vqabs, Add1ArgType), 2997 NEONMAP1(vqabsq_v, arm_neon_vqabs, Add1ArgType), 2998 NEONMAP2(vqadd_v, arm_neon_vqaddu, arm_neon_vqadds, Add1ArgType | UnsignedAlts), 2999 NEONMAP2(vqaddq_v, arm_neon_vqaddu, arm_neon_vqadds, Add1ArgType | UnsignedAlts), 3000 NEONMAP2(vqdmlal_v, arm_neon_vqdmull, arm_neon_vqadds, 0), 3001 NEONMAP2(vqdmlsl_v, arm_neon_vqdmull, arm_neon_vqsubs, 0), 3002 NEONMAP1(vqdmulh_v, arm_neon_vqdmulh, Add1ArgType), 3003 NEONMAP1(vqdmulhq_v, arm_neon_vqdmulh, Add1ArgType), 3004 NEONMAP1(vqdmull_v, arm_neon_vqdmull, Add1ArgType), 3005 NEONMAP2(vqmovn_v, arm_neon_vqmovnu, arm_neon_vqmovns, Add1ArgType | UnsignedAlts), 3006 NEONMAP1(vqmovun_v, arm_neon_vqmovnsu, Add1ArgType), 3007 NEONMAP1(vqneg_v, arm_neon_vqneg, Add1ArgType), 3008 NEONMAP1(vqnegq_v, arm_neon_vqneg, Add1ArgType), 3009 NEONMAP1(vqrdmulh_v, arm_neon_vqrdmulh, Add1ArgType), 3010 NEONMAP1(vqrdmulhq_v, arm_neon_vqrdmulh, Add1ArgType), 3011 NEONMAP2(vqrshl_v, arm_neon_vqrshiftu, arm_neon_vqrshifts, Add1ArgType | UnsignedAlts), 3012 NEONMAP2(vqrshlq_v, arm_neon_vqrshiftu, arm_neon_vqrshifts, Add1ArgType | UnsignedAlts), 3013 NEONMAP2(vqshl_n_v, arm_neon_vqshiftu, arm_neon_vqshifts, UnsignedAlts), 3014 NEONMAP2(vqshl_v, arm_neon_vqshiftu, arm_neon_vqshifts, Add1ArgType | UnsignedAlts), 3015 NEONMAP2(vqshlq_n_v, arm_neon_vqshiftu, arm_neon_vqshifts, UnsignedAlts), 3016 NEONMAP2(vqshlq_v, arm_neon_vqshiftu, arm_neon_vqshifts, Add1ArgType | UnsignedAlts), 3017 NEONMAP1(vqshlu_n_v, arm_neon_vqshiftsu, 0), 3018 NEONMAP1(vqshluq_n_v, arm_neon_vqshiftsu, 0), 3019 NEONMAP2(vqsub_v, arm_neon_vqsubu, arm_neon_vqsubs, Add1ArgType | UnsignedAlts), 3020 NEONMAP2(vqsubq_v, arm_neon_vqsubu, arm_neon_vqsubs, Add1ArgType | UnsignedAlts), 3021 NEONMAP1(vraddhn_v, arm_neon_vraddhn, Add1ArgType), 3022 NEONMAP2(vrecpe_v, arm_neon_vrecpe, arm_neon_vrecpe, 0), 3023 NEONMAP2(vrecpeq_v, arm_neon_vrecpe, arm_neon_vrecpe, 0), 3024 NEONMAP1(vrecps_v, arm_neon_vrecps, Add1ArgType), 3025 NEONMAP1(vrecpsq_v, arm_neon_vrecps, Add1ArgType), 3026 NEONMAP2(vrhadd_v, arm_neon_vrhaddu, arm_neon_vrhadds, Add1ArgType | UnsignedAlts), 3027 NEONMAP2(vrhaddq_v, arm_neon_vrhaddu, arm_neon_vrhadds, Add1ArgType | UnsignedAlts), 3028 NEONMAP1(vrnd_v, arm_neon_vrintz, Add1ArgType), 3029 NEONMAP1(vrnda_v, arm_neon_vrinta, Add1ArgType), 3030 NEONMAP1(vrndaq_v, arm_neon_vrinta, Add1ArgType), 3031 NEONMAP1(vrndm_v, arm_neon_vrintm, Add1ArgType), 3032 NEONMAP1(vrndmq_v, arm_neon_vrintm, Add1ArgType), 3033 NEONMAP1(vrndn_v, arm_neon_vrintn, Add1ArgType), 3034 NEONMAP1(vrndnq_v, arm_neon_vrintn, Add1ArgType), 3035 NEONMAP1(vrndp_v, arm_neon_vrintp, Add1ArgType), 3036 NEONMAP1(vrndpq_v, arm_neon_vrintp, Add1ArgType), 3037 NEONMAP1(vrndq_v, arm_neon_vrintz, Add1ArgType), 3038 NEONMAP1(vrndx_v, arm_neon_vrintx, Add1ArgType), 3039 NEONMAP1(vrndxq_v, arm_neon_vrintx, Add1ArgType), 3040 NEONMAP2(vrshl_v, arm_neon_vrshiftu, arm_neon_vrshifts, Add1ArgType | UnsignedAlts), 3041 NEONMAP2(vrshlq_v, arm_neon_vrshiftu, arm_neon_vrshifts, Add1ArgType | UnsignedAlts), 3042 NEONMAP2(vrshr_n_v, arm_neon_vrshiftu, arm_neon_vrshifts, UnsignedAlts), 3043 NEONMAP2(vrshrq_n_v, arm_neon_vrshiftu, arm_neon_vrshifts, UnsignedAlts), 3044 NEONMAP2(vrsqrte_v, arm_neon_vrsqrte, arm_neon_vrsqrte, 0), 3045 NEONMAP2(vrsqrteq_v, arm_neon_vrsqrte, arm_neon_vrsqrte, 0), 3046 NEONMAP1(vrsqrts_v, arm_neon_vrsqrts, Add1ArgType), 3047 NEONMAP1(vrsqrtsq_v, arm_neon_vrsqrts, Add1ArgType), 3048 NEONMAP1(vrsubhn_v, arm_neon_vrsubhn, Add1ArgType), 3049 NEONMAP1(vsha1su0q_v, arm_neon_sha1su0, 0), 3050 NEONMAP1(vsha1su1q_v, arm_neon_sha1su1, 0), 3051 NEONMAP1(vsha256h2q_v, arm_neon_sha256h2, 0), 3052 NEONMAP1(vsha256hq_v, arm_neon_sha256h, 0), 3053 NEONMAP1(vsha256su0q_v, arm_neon_sha256su0, 0), 3054 NEONMAP1(vsha256su1q_v, arm_neon_sha256su1, 0), 3055 NEONMAP0(vshl_n_v), 3056 NEONMAP2(vshl_v, arm_neon_vshiftu, arm_neon_vshifts, Add1ArgType | UnsignedAlts), 3057 NEONMAP0(vshll_n_v), 3058 NEONMAP0(vshlq_n_v), 3059 NEONMAP2(vshlq_v, arm_neon_vshiftu, arm_neon_vshifts, Add1ArgType | UnsignedAlts), 3060 NEONMAP0(vshr_n_v), 3061 NEONMAP0(vshrn_n_v), 3062 NEONMAP0(vshrq_n_v), 3063 NEONMAP1(vst1_v, arm_neon_vst1, 0), 3064 NEONMAP1(vst1q_v, arm_neon_vst1, 0), 3065 NEONMAP1(vst2_lane_v, arm_neon_vst2lane, 0), 3066 NEONMAP1(vst2_v, arm_neon_vst2, 0), 3067 NEONMAP1(vst2q_lane_v, arm_neon_vst2lane, 0), 3068 NEONMAP1(vst2q_v, arm_neon_vst2, 0), 3069 NEONMAP1(vst3_lane_v, arm_neon_vst3lane, 0), 3070 NEONMAP1(vst3_v, arm_neon_vst3, 0), 3071 NEONMAP1(vst3q_lane_v, arm_neon_vst3lane, 0), 3072 NEONMAP1(vst3q_v, arm_neon_vst3, 0), 3073 NEONMAP1(vst4_lane_v, arm_neon_vst4lane, 0), 3074 NEONMAP1(vst4_v, arm_neon_vst4, 0), 3075 NEONMAP1(vst4q_lane_v, arm_neon_vst4lane, 0), 3076 NEONMAP1(vst4q_v, arm_neon_vst4, 0), 3077 NEONMAP0(vsubhn_v), 3078 NEONMAP0(vtrn_v), 3079 NEONMAP0(vtrnq_v), 3080 NEONMAP0(vtst_v), 3081 NEONMAP0(vtstq_v), 3082 NEONMAP0(vuzp_v), 3083 NEONMAP0(vuzpq_v), 3084 NEONMAP0(vzip_v), 3085 NEONMAP0(vzipq_v) 3086 }; 3087 3088 static const NeonIntrinsicInfo AArch64SIMDIntrinsicMap[] = { 3089 NEONMAP1(vabs_v, aarch64_neon_abs, 0), 3090 NEONMAP1(vabsq_v, aarch64_neon_abs, 0), 3091 NEONMAP0(vaddhn_v), 3092 NEONMAP1(vaesdq_v, aarch64_crypto_aesd, 0), 3093 NEONMAP1(vaeseq_v, aarch64_crypto_aese, 0), 3094 NEONMAP1(vaesimcq_v, aarch64_crypto_aesimc, 0), 3095 NEONMAP1(vaesmcq_v, aarch64_crypto_aesmc, 0), 3096 NEONMAP1(vcage_v, aarch64_neon_facge, 0), 3097 NEONMAP1(vcageq_v, aarch64_neon_facge, 0), 3098 NEONMAP1(vcagt_v, aarch64_neon_facgt, 0), 3099 NEONMAP1(vcagtq_v, aarch64_neon_facgt, 0), 3100 NEONMAP1(vcale_v, aarch64_neon_facge, 0), 3101 NEONMAP1(vcaleq_v, aarch64_neon_facge, 0), 3102 NEONMAP1(vcalt_v, aarch64_neon_facgt, 0), 3103 NEONMAP1(vcaltq_v, aarch64_neon_facgt, 0), 3104 NEONMAP1(vcls_v, aarch64_neon_cls, Add1ArgType), 3105 NEONMAP1(vclsq_v, aarch64_neon_cls, Add1ArgType), 3106 NEONMAP1(vclz_v, ctlz, Add1ArgType), 3107 NEONMAP1(vclzq_v, ctlz, Add1ArgType), 3108 NEONMAP1(vcnt_v, ctpop, Add1ArgType), 3109 NEONMAP1(vcntq_v, ctpop, Add1ArgType), 3110 NEONMAP1(vcvt_f16_f32, aarch64_neon_vcvtfp2hf, 0), 3111 NEONMAP1(vcvt_f32_f16, aarch64_neon_vcvthf2fp, 0), 3112 NEONMAP0(vcvt_f32_v), 3113 NEONMAP2(vcvt_n_f32_v, aarch64_neon_vcvtfxu2fp, aarch64_neon_vcvtfxs2fp, 0), 3114 NEONMAP2(vcvt_n_f64_v, aarch64_neon_vcvtfxu2fp, aarch64_neon_vcvtfxs2fp, 0), 3115 NEONMAP1(vcvt_n_s32_v, aarch64_neon_vcvtfp2fxs, 0), 3116 NEONMAP1(vcvt_n_s64_v, aarch64_neon_vcvtfp2fxs, 0), 3117 NEONMAP1(vcvt_n_u32_v, aarch64_neon_vcvtfp2fxu, 0), 3118 NEONMAP1(vcvt_n_u64_v, aarch64_neon_vcvtfp2fxu, 0), 3119 NEONMAP0(vcvtq_f32_v), 3120 NEONMAP2(vcvtq_n_f32_v, aarch64_neon_vcvtfxu2fp, aarch64_neon_vcvtfxs2fp, 0), 3121 NEONMAP2(vcvtq_n_f64_v, aarch64_neon_vcvtfxu2fp, aarch64_neon_vcvtfxs2fp, 0), 3122 NEONMAP1(vcvtq_n_s32_v, aarch64_neon_vcvtfp2fxs, 0), 3123 NEONMAP1(vcvtq_n_s64_v, aarch64_neon_vcvtfp2fxs, 0), 3124 NEONMAP1(vcvtq_n_u32_v, aarch64_neon_vcvtfp2fxu, 0), 3125 NEONMAP1(vcvtq_n_u64_v, aarch64_neon_vcvtfp2fxu, 0), 3126 NEONMAP1(vcvtx_f32_v, aarch64_neon_fcvtxn, AddRetType | Add1ArgType), 3127 NEONMAP0(vext_v), 3128 NEONMAP0(vextq_v), 3129 NEONMAP0(vfma_v), 3130 NEONMAP0(vfmaq_v), 3131 NEONMAP2(vhadd_v, aarch64_neon_uhadd, aarch64_neon_shadd, Add1ArgType | UnsignedAlts), 3132 NEONMAP2(vhaddq_v, aarch64_neon_uhadd, aarch64_neon_shadd, Add1ArgType | UnsignedAlts), 3133 NEONMAP2(vhsub_v, aarch64_neon_uhsub, aarch64_neon_shsub, Add1ArgType | UnsignedAlts), 3134 NEONMAP2(vhsubq_v, aarch64_neon_uhsub, aarch64_neon_shsub, Add1ArgType | UnsignedAlts), 3135 NEONMAP0(vmovl_v), 3136 NEONMAP0(vmovn_v), 3137 NEONMAP1(vmul_v, aarch64_neon_pmul, Add1ArgType), 3138 NEONMAP1(vmulq_v, aarch64_neon_pmul, Add1ArgType), 3139 NEONMAP1(vpadd_v, aarch64_neon_addp, Add1ArgType), 3140 NEONMAP2(vpaddl_v, aarch64_neon_uaddlp, aarch64_neon_saddlp, UnsignedAlts), 3141 NEONMAP2(vpaddlq_v, aarch64_neon_uaddlp, aarch64_neon_saddlp, UnsignedAlts), 3142 NEONMAP1(vpaddq_v, aarch64_neon_addp, Add1ArgType), 3143 NEONMAP1(vqabs_v, aarch64_neon_sqabs, Add1ArgType), 3144 NEONMAP1(vqabsq_v, aarch64_neon_sqabs, Add1ArgType), 3145 NEONMAP2(vqadd_v, aarch64_neon_uqadd, aarch64_neon_sqadd, Add1ArgType | UnsignedAlts), 3146 NEONMAP2(vqaddq_v, aarch64_neon_uqadd, aarch64_neon_sqadd, Add1ArgType | UnsignedAlts), 3147 NEONMAP2(vqdmlal_v, aarch64_neon_sqdmull, aarch64_neon_sqadd, 0), 3148 NEONMAP2(vqdmlsl_v, aarch64_neon_sqdmull, aarch64_neon_sqsub, 0), 3149 NEONMAP1(vqdmulh_v, aarch64_neon_sqdmulh, Add1ArgType), 3150 NEONMAP1(vqdmulhq_v, aarch64_neon_sqdmulh, Add1ArgType), 3151 NEONMAP1(vqdmull_v, aarch64_neon_sqdmull, Add1ArgType), 3152 NEONMAP2(vqmovn_v, aarch64_neon_uqxtn, aarch64_neon_sqxtn, Add1ArgType | UnsignedAlts), 3153 NEONMAP1(vqmovun_v, aarch64_neon_sqxtun, Add1ArgType), 3154 NEONMAP1(vqneg_v, aarch64_neon_sqneg, Add1ArgType), 3155 NEONMAP1(vqnegq_v, aarch64_neon_sqneg, Add1ArgType), 3156 NEONMAP1(vqrdmulh_v, aarch64_neon_sqrdmulh, Add1ArgType), 3157 NEONMAP1(vqrdmulhq_v, aarch64_neon_sqrdmulh, Add1ArgType), 3158 NEONMAP2(vqrshl_v, aarch64_neon_uqrshl, aarch64_neon_sqrshl, Add1ArgType | UnsignedAlts), 3159 NEONMAP2(vqrshlq_v, aarch64_neon_uqrshl, aarch64_neon_sqrshl, Add1ArgType | UnsignedAlts), 3160 NEONMAP2(vqshl_n_v, aarch64_neon_uqshl, aarch64_neon_sqshl, UnsignedAlts), 3161 NEONMAP2(vqshl_v, aarch64_neon_uqshl, aarch64_neon_sqshl, Add1ArgType | UnsignedAlts), 3162 NEONMAP2(vqshlq_n_v, aarch64_neon_uqshl, aarch64_neon_sqshl,UnsignedAlts), 3163 NEONMAP2(vqshlq_v, aarch64_neon_uqshl, aarch64_neon_sqshl, Add1ArgType | UnsignedAlts), 3164 NEONMAP1(vqshlu_n_v, aarch64_neon_sqshlu, 0), 3165 NEONMAP1(vqshluq_n_v, aarch64_neon_sqshlu, 0), 3166 NEONMAP2(vqsub_v, aarch64_neon_uqsub, aarch64_neon_sqsub, Add1ArgType | UnsignedAlts), 3167 NEONMAP2(vqsubq_v, aarch64_neon_uqsub, aarch64_neon_sqsub, Add1ArgType | UnsignedAlts), 3168 NEONMAP1(vraddhn_v, aarch64_neon_raddhn, Add1ArgType), 3169 NEONMAP2(vrecpe_v, aarch64_neon_frecpe, aarch64_neon_urecpe, 0), 3170 NEONMAP2(vrecpeq_v, aarch64_neon_frecpe, aarch64_neon_urecpe, 0), 3171 NEONMAP1(vrecps_v, aarch64_neon_frecps, Add1ArgType), 3172 NEONMAP1(vrecpsq_v, aarch64_neon_frecps, Add1ArgType), 3173 NEONMAP2(vrhadd_v, aarch64_neon_urhadd, aarch64_neon_srhadd, Add1ArgType | UnsignedAlts), 3174 NEONMAP2(vrhaddq_v, aarch64_neon_urhadd, aarch64_neon_srhadd, Add1ArgType | UnsignedAlts), 3175 NEONMAP2(vrshl_v, aarch64_neon_urshl, aarch64_neon_srshl, Add1ArgType | UnsignedAlts), 3176 NEONMAP2(vrshlq_v, aarch64_neon_urshl, aarch64_neon_srshl, Add1ArgType | UnsignedAlts), 3177 NEONMAP2(vrshr_n_v, aarch64_neon_urshl, aarch64_neon_srshl, UnsignedAlts), 3178 NEONMAP2(vrshrq_n_v, aarch64_neon_urshl, aarch64_neon_srshl, UnsignedAlts), 3179 NEONMAP2(vrsqrte_v, aarch64_neon_frsqrte, aarch64_neon_ursqrte, 0), 3180 NEONMAP2(vrsqrteq_v, aarch64_neon_frsqrte, aarch64_neon_ursqrte, 0), 3181 NEONMAP1(vrsqrts_v, aarch64_neon_frsqrts, Add1ArgType), 3182 NEONMAP1(vrsqrtsq_v, aarch64_neon_frsqrts, Add1ArgType), 3183 NEONMAP1(vrsubhn_v, aarch64_neon_rsubhn, Add1ArgType), 3184 NEONMAP1(vsha1su0q_v, aarch64_crypto_sha1su0, 0), 3185 NEONMAP1(vsha1su1q_v, aarch64_crypto_sha1su1, 0), 3186 NEONMAP1(vsha256h2q_v, aarch64_crypto_sha256h2, 0), 3187 NEONMAP1(vsha256hq_v, aarch64_crypto_sha256h, 0), 3188 NEONMAP1(vsha256su0q_v, aarch64_crypto_sha256su0, 0), 3189 NEONMAP1(vsha256su1q_v, aarch64_crypto_sha256su1, 0), 3190 NEONMAP0(vshl_n_v), 3191 NEONMAP2(vshl_v, aarch64_neon_ushl, aarch64_neon_sshl, Add1ArgType | UnsignedAlts), 3192 NEONMAP0(vshll_n_v), 3193 NEONMAP0(vshlq_n_v), 3194 NEONMAP2(vshlq_v, aarch64_neon_ushl, aarch64_neon_sshl, Add1ArgType | UnsignedAlts), 3195 NEONMAP0(vshr_n_v), 3196 NEONMAP0(vshrn_n_v), 3197 NEONMAP0(vshrq_n_v), 3198 NEONMAP0(vsubhn_v), 3199 NEONMAP0(vtst_v), 3200 NEONMAP0(vtstq_v), 3201 }; 3202 3203 static const NeonIntrinsicInfo AArch64SISDIntrinsicMap[] = { 3204 NEONMAP1(vabdd_f64, aarch64_sisd_fabd, Add1ArgType), 3205 NEONMAP1(vabds_f32, aarch64_sisd_fabd, Add1ArgType), 3206 NEONMAP1(vabsd_s64, aarch64_neon_abs, Add1ArgType), 3207 NEONMAP1(vaddlv_s32, aarch64_neon_saddlv, AddRetType | Add1ArgType), 3208 NEONMAP1(vaddlv_u32, aarch64_neon_uaddlv, AddRetType | Add1ArgType), 3209 NEONMAP1(vaddlvq_s32, aarch64_neon_saddlv, AddRetType | Add1ArgType), 3210 NEONMAP1(vaddlvq_u32, aarch64_neon_uaddlv, AddRetType | Add1ArgType), 3211 NEONMAP1(vaddv_f32, aarch64_neon_faddv, AddRetType | Add1ArgType), 3212 NEONMAP1(vaddv_s32, aarch64_neon_saddv, AddRetType | Add1ArgType), 3213 NEONMAP1(vaddv_u32, aarch64_neon_uaddv, AddRetType | Add1ArgType), 3214 NEONMAP1(vaddvq_f32, aarch64_neon_faddv, AddRetType | Add1ArgType), 3215 NEONMAP1(vaddvq_f64, aarch64_neon_faddv, AddRetType | Add1ArgType), 3216 NEONMAP1(vaddvq_s32, aarch64_neon_saddv, AddRetType | Add1ArgType), 3217 NEONMAP1(vaddvq_s64, aarch64_neon_saddv, AddRetType | Add1ArgType), 3218 NEONMAP1(vaddvq_u32, aarch64_neon_uaddv, AddRetType | Add1ArgType), 3219 NEONMAP1(vaddvq_u64, aarch64_neon_uaddv, AddRetType | Add1ArgType), 3220 NEONMAP1(vcaged_f64, aarch64_neon_facge, AddRetType | Add1ArgType), 3221 NEONMAP1(vcages_f32, aarch64_neon_facge, AddRetType | Add1ArgType), 3222 NEONMAP1(vcagtd_f64, aarch64_neon_facgt, AddRetType | Add1ArgType), 3223 NEONMAP1(vcagts_f32, aarch64_neon_facgt, AddRetType | Add1ArgType), 3224 NEONMAP1(vcaled_f64, aarch64_neon_facge, AddRetType | Add1ArgType), 3225 NEONMAP1(vcales_f32, aarch64_neon_facge, AddRetType | Add1ArgType), 3226 NEONMAP1(vcaltd_f64, aarch64_neon_facgt, AddRetType | Add1ArgType), 3227 NEONMAP1(vcalts_f32, aarch64_neon_facgt, AddRetType | Add1ArgType), 3228 NEONMAP1(vcvtad_s64_f64, aarch64_neon_fcvtas, AddRetType | Add1ArgType), 3229 NEONMAP1(vcvtad_u64_f64, aarch64_neon_fcvtau, AddRetType | Add1ArgType), 3230 NEONMAP1(vcvtas_s32_f32, aarch64_neon_fcvtas, AddRetType | Add1ArgType), 3231 NEONMAP1(vcvtas_u32_f32, aarch64_neon_fcvtau, AddRetType | Add1ArgType), 3232 NEONMAP1(vcvtd_n_f64_s64, aarch64_neon_vcvtfxs2fp, AddRetType | Add1ArgType), 3233 NEONMAP1(vcvtd_n_f64_u64, aarch64_neon_vcvtfxu2fp, AddRetType | Add1ArgType), 3234 NEONMAP1(vcvtd_n_s64_f64, aarch64_neon_vcvtfp2fxs, AddRetType | Add1ArgType), 3235 NEONMAP1(vcvtd_n_u64_f64, aarch64_neon_vcvtfp2fxu, AddRetType | Add1ArgType), 3236 NEONMAP1(vcvtmd_s64_f64, aarch64_neon_fcvtms, AddRetType | Add1ArgType), 3237 NEONMAP1(vcvtmd_u64_f64, aarch64_neon_fcvtmu, AddRetType | Add1ArgType), 3238 NEONMAP1(vcvtms_s32_f32, aarch64_neon_fcvtms, AddRetType | Add1ArgType), 3239 NEONMAP1(vcvtms_u32_f32, aarch64_neon_fcvtmu, AddRetType | Add1ArgType), 3240 NEONMAP1(vcvtnd_s64_f64, aarch64_neon_fcvtns, AddRetType | Add1ArgType), 3241 NEONMAP1(vcvtnd_u64_f64, aarch64_neon_fcvtnu, AddRetType | Add1ArgType), 3242 NEONMAP1(vcvtns_s32_f32, aarch64_neon_fcvtns, AddRetType | Add1ArgType), 3243 NEONMAP1(vcvtns_u32_f32, aarch64_neon_fcvtnu, AddRetType | Add1ArgType), 3244 NEONMAP1(vcvtpd_s64_f64, aarch64_neon_fcvtps, AddRetType | Add1ArgType), 3245 NEONMAP1(vcvtpd_u64_f64, aarch64_neon_fcvtpu, AddRetType | Add1ArgType), 3246 NEONMAP1(vcvtps_s32_f32, aarch64_neon_fcvtps, AddRetType | Add1ArgType), 3247 NEONMAP1(vcvtps_u32_f32, aarch64_neon_fcvtpu, AddRetType | Add1ArgType), 3248 NEONMAP1(vcvts_n_f32_s32, aarch64_neon_vcvtfxs2fp, AddRetType | Add1ArgType), 3249 NEONMAP1(vcvts_n_f32_u32, aarch64_neon_vcvtfxu2fp, AddRetType | Add1ArgType), 3250 NEONMAP1(vcvts_n_s32_f32, aarch64_neon_vcvtfp2fxs, AddRetType | Add1ArgType), 3251 NEONMAP1(vcvts_n_u32_f32, aarch64_neon_vcvtfp2fxu, AddRetType | Add1ArgType), 3252 NEONMAP1(vcvtxd_f32_f64, aarch64_sisd_fcvtxn, 0), 3253 NEONMAP1(vmaxnmv_f32, aarch64_neon_fmaxnmv, AddRetType | Add1ArgType), 3254 NEONMAP1(vmaxnmvq_f32, aarch64_neon_fmaxnmv, AddRetType | Add1ArgType), 3255 NEONMAP1(vmaxnmvq_f64, aarch64_neon_fmaxnmv, AddRetType | Add1ArgType), 3256 NEONMAP1(vmaxv_f32, aarch64_neon_fmaxv, AddRetType | Add1ArgType), 3257 NEONMAP1(vmaxv_s32, aarch64_neon_smaxv, AddRetType | Add1ArgType), 3258 NEONMAP1(vmaxv_u32, aarch64_neon_umaxv, AddRetType | Add1ArgType), 3259 NEONMAP1(vmaxvq_f32, aarch64_neon_fmaxv, AddRetType | Add1ArgType), 3260 NEONMAP1(vmaxvq_f64, aarch64_neon_fmaxv, AddRetType | Add1ArgType), 3261 NEONMAP1(vmaxvq_s32, aarch64_neon_smaxv, AddRetType | Add1ArgType), 3262 NEONMAP1(vmaxvq_u32, aarch64_neon_umaxv, AddRetType | Add1ArgType), 3263 NEONMAP1(vminnmv_f32, aarch64_neon_fminnmv, AddRetType | Add1ArgType), 3264 NEONMAP1(vminnmvq_f32, aarch64_neon_fminnmv, AddRetType | Add1ArgType), 3265 NEONMAP1(vminnmvq_f64, aarch64_neon_fminnmv, AddRetType | Add1ArgType), 3266 NEONMAP1(vminv_f32, aarch64_neon_fminv, AddRetType | Add1ArgType), 3267 NEONMAP1(vminv_s32, aarch64_neon_sminv, AddRetType | Add1ArgType), 3268 NEONMAP1(vminv_u32, aarch64_neon_uminv, AddRetType | Add1ArgType), 3269 NEONMAP1(vminvq_f32, aarch64_neon_fminv, AddRetType | Add1ArgType), 3270 NEONMAP1(vminvq_f64, aarch64_neon_fminv, AddRetType | Add1ArgType), 3271 NEONMAP1(vminvq_s32, aarch64_neon_sminv, AddRetType | Add1ArgType), 3272 NEONMAP1(vminvq_u32, aarch64_neon_uminv, AddRetType | Add1ArgType), 3273 NEONMAP1(vmull_p64, aarch64_neon_pmull64, 0), 3274 NEONMAP1(vmulxd_f64, aarch64_neon_fmulx, Add1ArgType), 3275 NEONMAP1(vmulxs_f32, aarch64_neon_fmulx, Add1ArgType), 3276 NEONMAP1(vpaddd_s64, aarch64_neon_uaddv, AddRetType | Add1ArgType), 3277 NEONMAP1(vpaddd_u64, aarch64_neon_uaddv, AddRetType | Add1ArgType), 3278 NEONMAP1(vpmaxnmqd_f64, aarch64_neon_fmaxnmv, AddRetType | Add1ArgType), 3279 NEONMAP1(vpmaxnms_f32, aarch64_neon_fmaxnmv, AddRetType | Add1ArgType), 3280 NEONMAP1(vpmaxqd_f64, aarch64_neon_fmaxv, AddRetType | Add1ArgType), 3281 NEONMAP1(vpmaxs_f32, aarch64_neon_fmaxv, AddRetType | Add1ArgType), 3282 NEONMAP1(vpminnmqd_f64, aarch64_neon_fminnmv, AddRetType | Add1ArgType), 3283 NEONMAP1(vpminnms_f32, aarch64_neon_fminnmv, AddRetType | Add1ArgType), 3284 NEONMAP1(vpminqd_f64, aarch64_neon_fminv, AddRetType | Add1ArgType), 3285 NEONMAP1(vpmins_f32, aarch64_neon_fminv, AddRetType | Add1ArgType), 3286 NEONMAP1(vqabsb_s8, aarch64_neon_sqabs, Vectorize1ArgType | Use64BitVectors), 3287 NEONMAP1(vqabsd_s64, aarch64_neon_sqabs, Add1ArgType), 3288 NEONMAP1(vqabsh_s16, aarch64_neon_sqabs, Vectorize1ArgType | Use64BitVectors), 3289 NEONMAP1(vqabss_s32, aarch64_neon_sqabs, Add1ArgType), 3290 NEONMAP1(vqaddb_s8, aarch64_neon_sqadd, Vectorize1ArgType | Use64BitVectors), 3291 NEONMAP1(vqaddb_u8, aarch64_neon_uqadd, Vectorize1ArgType | Use64BitVectors), 3292 NEONMAP1(vqaddd_s64, aarch64_neon_sqadd, Add1ArgType), 3293 NEONMAP1(vqaddd_u64, aarch64_neon_uqadd, Add1ArgType), 3294 NEONMAP1(vqaddh_s16, aarch64_neon_sqadd, Vectorize1ArgType | Use64BitVectors), 3295 NEONMAP1(vqaddh_u16, aarch64_neon_uqadd, Vectorize1ArgType | Use64BitVectors), 3296 NEONMAP1(vqadds_s32, aarch64_neon_sqadd, Add1ArgType), 3297 NEONMAP1(vqadds_u32, aarch64_neon_uqadd, Add1ArgType), 3298 NEONMAP1(vqdmulhh_s16, aarch64_neon_sqdmulh, Vectorize1ArgType | Use64BitVectors), 3299 NEONMAP1(vqdmulhs_s32, aarch64_neon_sqdmulh, Add1ArgType), 3300 NEONMAP1(vqdmullh_s16, aarch64_neon_sqdmull, VectorRet | Use128BitVectors), 3301 NEONMAP1(vqdmulls_s32, aarch64_neon_sqdmulls_scalar, 0), 3302 NEONMAP1(vqmovnd_s64, aarch64_neon_scalar_sqxtn, AddRetType | Add1ArgType), 3303 NEONMAP1(vqmovnd_u64, aarch64_neon_scalar_uqxtn, AddRetType | Add1ArgType), 3304 NEONMAP1(vqmovnh_s16, aarch64_neon_sqxtn, VectorRet | Use64BitVectors), 3305 NEONMAP1(vqmovnh_u16, aarch64_neon_uqxtn, VectorRet | Use64BitVectors), 3306 NEONMAP1(vqmovns_s32, aarch64_neon_sqxtn, VectorRet | Use64BitVectors), 3307 NEONMAP1(vqmovns_u32, aarch64_neon_uqxtn, VectorRet | Use64BitVectors), 3308 NEONMAP1(vqmovund_s64, aarch64_neon_scalar_sqxtun, AddRetType | Add1ArgType), 3309 NEONMAP1(vqmovunh_s16, aarch64_neon_sqxtun, VectorRet | Use64BitVectors), 3310 NEONMAP1(vqmovuns_s32, aarch64_neon_sqxtun, VectorRet | Use64BitVectors), 3311 NEONMAP1(vqnegb_s8, aarch64_neon_sqneg, Vectorize1ArgType | Use64BitVectors), 3312 NEONMAP1(vqnegd_s64, aarch64_neon_sqneg, Add1ArgType), 3313 NEONMAP1(vqnegh_s16, aarch64_neon_sqneg, Vectorize1ArgType | Use64BitVectors), 3314 NEONMAP1(vqnegs_s32, aarch64_neon_sqneg, Add1ArgType), 3315 NEONMAP1(vqrdmulhh_s16, aarch64_neon_sqrdmulh, Vectorize1ArgType | Use64BitVectors), 3316 NEONMAP1(vqrdmulhs_s32, aarch64_neon_sqrdmulh, Add1ArgType), 3317 NEONMAP1(vqrshlb_s8, aarch64_neon_sqrshl, Vectorize1ArgType | Use64BitVectors), 3318 NEONMAP1(vqrshlb_u8, aarch64_neon_uqrshl, Vectorize1ArgType | Use64BitVectors), 3319 NEONMAP1(vqrshld_s64, aarch64_neon_sqrshl, Add1ArgType), 3320 NEONMAP1(vqrshld_u64, aarch64_neon_uqrshl, Add1ArgType), 3321 NEONMAP1(vqrshlh_s16, aarch64_neon_sqrshl, Vectorize1ArgType | Use64BitVectors), 3322 NEONMAP1(vqrshlh_u16, aarch64_neon_uqrshl, Vectorize1ArgType | Use64BitVectors), 3323 NEONMAP1(vqrshls_s32, aarch64_neon_sqrshl, Add1ArgType), 3324 NEONMAP1(vqrshls_u32, aarch64_neon_uqrshl, Add1ArgType), 3325 NEONMAP1(vqrshrnd_n_s64, aarch64_neon_sqrshrn, AddRetType), 3326 NEONMAP1(vqrshrnd_n_u64, aarch64_neon_uqrshrn, AddRetType), 3327 NEONMAP1(vqrshrnh_n_s16, aarch64_neon_sqrshrn, VectorRet | Use64BitVectors), 3328 NEONMAP1(vqrshrnh_n_u16, aarch64_neon_uqrshrn, VectorRet | Use64BitVectors), 3329 NEONMAP1(vqrshrns_n_s32, aarch64_neon_sqrshrn, VectorRet | Use64BitVectors), 3330 NEONMAP1(vqrshrns_n_u32, aarch64_neon_uqrshrn, VectorRet | Use64BitVectors), 3331 NEONMAP1(vqrshrund_n_s64, aarch64_neon_sqrshrun, AddRetType), 3332 NEONMAP1(vqrshrunh_n_s16, aarch64_neon_sqrshrun, VectorRet | Use64BitVectors), 3333 NEONMAP1(vqrshruns_n_s32, aarch64_neon_sqrshrun, VectorRet | Use64BitVectors), 3334 NEONMAP1(vqshlb_n_s8, aarch64_neon_sqshl, Vectorize1ArgType | Use64BitVectors), 3335 NEONMAP1(vqshlb_n_u8, aarch64_neon_uqshl, Vectorize1ArgType | Use64BitVectors), 3336 NEONMAP1(vqshlb_s8, aarch64_neon_sqshl, Vectorize1ArgType | Use64BitVectors), 3337 NEONMAP1(vqshlb_u8, aarch64_neon_uqshl, Vectorize1ArgType | Use64BitVectors), 3338 NEONMAP1(vqshld_s64, aarch64_neon_sqshl, Add1ArgType), 3339 NEONMAP1(vqshld_u64, aarch64_neon_uqshl, Add1ArgType), 3340 NEONMAP1(vqshlh_n_s16, aarch64_neon_sqshl, Vectorize1ArgType | Use64BitVectors), 3341 NEONMAP1(vqshlh_n_u16, aarch64_neon_uqshl, Vectorize1ArgType | Use64BitVectors), 3342 NEONMAP1(vqshlh_s16, aarch64_neon_sqshl, Vectorize1ArgType | Use64BitVectors), 3343 NEONMAP1(vqshlh_u16, aarch64_neon_uqshl, Vectorize1ArgType | Use64BitVectors), 3344 NEONMAP1(vqshls_n_s32, aarch64_neon_sqshl, Add1ArgType), 3345 NEONMAP1(vqshls_n_u32, aarch64_neon_uqshl, Add1ArgType), 3346 NEONMAP1(vqshls_s32, aarch64_neon_sqshl, Add1ArgType), 3347 NEONMAP1(vqshls_u32, aarch64_neon_uqshl, Add1ArgType), 3348 NEONMAP1(vqshlub_n_s8, aarch64_neon_sqshlu, Vectorize1ArgType | Use64BitVectors), 3349 NEONMAP1(vqshluh_n_s16, aarch64_neon_sqshlu, Vectorize1ArgType | Use64BitVectors), 3350 NEONMAP1(vqshlus_n_s32, aarch64_neon_sqshlu, Add1ArgType), 3351 NEONMAP1(vqshrnd_n_s64, aarch64_neon_sqshrn, AddRetType), 3352 NEONMAP1(vqshrnd_n_u64, aarch64_neon_uqshrn, AddRetType), 3353 NEONMAP1(vqshrnh_n_s16, aarch64_neon_sqshrn, VectorRet | Use64BitVectors), 3354 NEONMAP1(vqshrnh_n_u16, aarch64_neon_uqshrn, VectorRet | Use64BitVectors), 3355 NEONMAP1(vqshrns_n_s32, aarch64_neon_sqshrn, VectorRet | Use64BitVectors), 3356 NEONMAP1(vqshrns_n_u32, aarch64_neon_uqshrn, VectorRet | Use64BitVectors), 3357 NEONMAP1(vqshrund_n_s64, aarch64_neon_sqshrun, AddRetType), 3358 NEONMAP1(vqshrunh_n_s16, aarch64_neon_sqshrun, VectorRet | Use64BitVectors), 3359 NEONMAP1(vqshruns_n_s32, aarch64_neon_sqshrun, VectorRet | Use64BitVectors), 3360 NEONMAP1(vqsubb_s8, aarch64_neon_sqsub, Vectorize1ArgType | Use64BitVectors), 3361 NEONMAP1(vqsubb_u8, aarch64_neon_uqsub, Vectorize1ArgType | Use64BitVectors), 3362 NEONMAP1(vqsubd_s64, aarch64_neon_sqsub, Add1ArgType), 3363 NEONMAP1(vqsubd_u64, aarch64_neon_uqsub, Add1ArgType), 3364 NEONMAP1(vqsubh_s16, aarch64_neon_sqsub, Vectorize1ArgType | Use64BitVectors), 3365 NEONMAP1(vqsubh_u16, aarch64_neon_uqsub, Vectorize1ArgType | Use64BitVectors), 3366 NEONMAP1(vqsubs_s32, aarch64_neon_sqsub, Add1ArgType), 3367 NEONMAP1(vqsubs_u32, aarch64_neon_uqsub, Add1ArgType), 3368 NEONMAP1(vrecped_f64, aarch64_neon_frecpe, Add1ArgType), 3369 NEONMAP1(vrecpes_f32, aarch64_neon_frecpe, Add1ArgType), 3370 NEONMAP1(vrecpxd_f64, aarch64_neon_frecpx, Add1ArgType), 3371 NEONMAP1(vrecpxs_f32, aarch64_neon_frecpx, Add1ArgType), 3372 NEONMAP1(vrshld_s64, aarch64_neon_srshl, Add1ArgType), 3373 NEONMAP1(vrshld_u64, aarch64_neon_urshl, Add1ArgType), 3374 NEONMAP1(vrsqrted_f64, aarch64_neon_frsqrte, Add1ArgType), 3375 NEONMAP1(vrsqrtes_f32, aarch64_neon_frsqrte, Add1ArgType), 3376 NEONMAP1(vrsqrtsd_f64, aarch64_neon_frsqrts, Add1ArgType), 3377 NEONMAP1(vrsqrtss_f32, aarch64_neon_frsqrts, Add1ArgType), 3378 NEONMAP1(vsha1cq_u32, aarch64_crypto_sha1c, 0), 3379 NEONMAP1(vsha1h_u32, aarch64_crypto_sha1h, 0), 3380 NEONMAP1(vsha1mq_u32, aarch64_crypto_sha1m, 0), 3381 NEONMAP1(vsha1pq_u32, aarch64_crypto_sha1p, 0), 3382 NEONMAP1(vshld_s64, aarch64_neon_sshl, Add1ArgType), 3383 NEONMAP1(vshld_u64, aarch64_neon_ushl, Add1ArgType), 3384 NEONMAP1(vslid_n_s64, aarch64_neon_vsli, Vectorize1ArgType), 3385 NEONMAP1(vslid_n_u64, aarch64_neon_vsli, Vectorize1ArgType), 3386 NEONMAP1(vsqaddb_u8, aarch64_neon_usqadd, Vectorize1ArgType | Use64BitVectors), 3387 NEONMAP1(vsqaddd_u64, aarch64_neon_usqadd, Add1ArgType), 3388 NEONMAP1(vsqaddh_u16, aarch64_neon_usqadd, Vectorize1ArgType | Use64BitVectors), 3389 NEONMAP1(vsqadds_u32, aarch64_neon_usqadd, Add1ArgType), 3390 NEONMAP1(vsrid_n_s64, aarch64_neon_vsri, Vectorize1ArgType), 3391 NEONMAP1(vsrid_n_u64, aarch64_neon_vsri, Vectorize1ArgType), 3392 NEONMAP1(vuqaddb_s8, aarch64_neon_suqadd, Vectorize1ArgType | Use64BitVectors), 3393 NEONMAP1(vuqaddd_s64, aarch64_neon_suqadd, Add1ArgType), 3394 NEONMAP1(vuqaddh_s16, aarch64_neon_suqadd, Vectorize1ArgType | Use64BitVectors), 3395 NEONMAP1(vuqadds_s32, aarch64_neon_suqadd, Add1ArgType), 3396 }; 3397 3398 #undef NEONMAP0 3399 #undef NEONMAP1 3400 #undef NEONMAP2 3401 3402 static bool NEONSIMDIntrinsicsProvenSorted = false; 3403 3404 static bool AArch64SIMDIntrinsicsProvenSorted = false; 3405 static bool AArch64SISDIntrinsicsProvenSorted = false; 3406 3407 3408 static const NeonIntrinsicInfo * 3409 findNeonIntrinsicInMap(ArrayRef<NeonIntrinsicInfo> IntrinsicMap, 3410 unsigned BuiltinID, bool &MapProvenSorted) { 3411 3412 #ifndef NDEBUG 3413 if (!MapProvenSorted) { 3414 assert(std::is_sorted(std::begin(IntrinsicMap), std::end(IntrinsicMap))); 3415 MapProvenSorted = true; 3416 } 3417 #endif 3418 3419 const NeonIntrinsicInfo *Builtin = 3420 std::lower_bound(IntrinsicMap.begin(), IntrinsicMap.end(), BuiltinID); 3421 3422 if (Builtin != IntrinsicMap.end() && Builtin->BuiltinID == BuiltinID) 3423 return Builtin; 3424 3425 return nullptr; 3426 } 3427 3428 Function *CodeGenFunction::LookupNeonLLVMIntrinsic(unsigned IntrinsicID, 3429 unsigned Modifier, 3430 llvm::Type *ArgType, 3431 const CallExpr *E) { 3432 int VectorSize = 0; 3433 if (Modifier & Use64BitVectors) 3434 VectorSize = 64; 3435 else if (Modifier & Use128BitVectors) 3436 VectorSize = 128; 3437 3438 // Return type. 3439 SmallVector<llvm::Type *, 3> Tys; 3440 if (Modifier & AddRetType) { 3441 llvm::Type *Ty = ConvertType(E->getCallReturnType(getContext())); 3442 if (Modifier & VectorizeRetType) 3443 Ty = llvm::VectorType::get( 3444 Ty, VectorSize ? VectorSize / Ty->getPrimitiveSizeInBits() : 1); 3445 3446 Tys.push_back(Ty); 3447 } 3448 3449 // Arguments. 3450 if (Modifier & VectorizeArgTypes) { 3451 int Elts = VectorSize ? VectorSize / ArgType->getPrimitiveSizeInBits() : 1; 3452 ArgType = llvm::VectorType::get(ArgType, Elts); 3453 } 3454 3455 if (Modifier & (Add1ArgType | Add2ArgTypes)) 3456 Tys.push_back(ArgType); 3457 3458 if (Modifier & Add2ArgTypes) 3459 Tys.push_back(ArgType); 3460 3461 if (Modifier & InventFloatType) 3462 Tys.push_back(FloatTy); 3463 3464 return CGM.getIntrinsic(IntrinsicID, Tys); 3465 } 3466 3467 static Value *EmitCommonNeonSISDBuiltinExpr(CodeGenFunction &CGF, 3468 const NeonIntrinsicInfo &SISDInfo, 3469 SmallVectorImpl<Value *> &Ops, 3470 const CallExpr *E) { 3471 unsigned BuiltinID = SISDInfo.BuiltinID; 3472 unsigned int Int = SISDInfo.LLVMIntrinsic; 3473 unsigned Modifier = SISDInfo.TypeModifier; 3474 const char *s = SISDInfo.NameHint; 3475 3476 switch (BuiltinID) { 3477 case NEON::BI__builtin_neon_vcled_s64: 3478 case NEON::BI__builtin_neon_vcled_u64: 3479 case NEON::BI__builtin_neon_vcles_f32: 3480 case NEON::BI__builtin_neon_vcled_f64: 3481 case NEON::BI__builtin_neon_vcltd_s64: 3482 case NEON::BI__builtin_neon_vcltd_u64: 3483 case NEON::BI__builtin_neon_vclts_f32: 3484 case NEON::BI__builtin_neon_vcltd_f64: 3485 case NEON::BI__builtin_neon_vcales_f32: 3486 case NEON::BI__builtin_neon_vcaled_f64: 3487 case NEON::BI__builtin_neon_vcalts_f32: 3488 case NEON::BI__builtin_neon_vcaltd_f64: 3489 // Only one direction of comparisons actually exist, cmle is actually a cmge 3490 // with swapped operands. The table gives us the right intrinsic but we 3491 // still need to do the swap. 3492 std::swap(Ops[0], Ops[1]); 3493 break; 3494 } 3495 3496 assert(Int && "Generic code assumes a valid intrinsic"); 3497 3498 // Determine the type(s) of this overloaded AArch64 intrinsic. 3499 const Expr *Arg = E->getArg(0); 3500 llvm::Type *ArgTy = CGF.ConvertType(Arg->getType()); 3501 Function *F = CGF.LookupNeonLLVMIntrinsic(Int, Modifier, ArgTy, E); 3502 3503 int j = 0; 3504 ConstantInt *C0 = ConstantInt::get(CGF.SizeTy, 0); 3505 for (Function::const_arg_iterator ai = F->arg_begin(), ae = F->arg_end(); 3506 ai != ae; ++ai, ++j) { 3507 llvm::Type *ArgTy = ai->getType(); 3508 if (Ops[j]->getType()->getPrimitiveSizeInBits() == 3509 ArgTy->getPrimitiveSizeInBits()) 3510 continue; 3511 3512 assert(ArgTy->isVectorTy() && !Ops[j]->getType()->isVectorTy()); 3513 // The constant argument to an _n_ intrinsic always has Int32Ty, so truncate 3514 // it before inserting. 3515 Ops[j] = 3516 CGF.Builder.CreateTruncOrBitCast(Ops[j], ArgTy->getVectorElementType()); 3517 Ops[j] = 3518 CGF.Builder.CreateInsertElement(UndefValue::get(ArgTy), Ops[j], C0); 3519 } 3520 3521 Value *Result = CGF.EmitNeonCall(F, Ops, s); 3522 llvm::Type *ResultType = CGF.ConvertType(E->getType()); 3523 if (ResultType->getPrimitiveSizeInBits() < 3524 Result->getType()->getPrimitiveSizeInBits()) 3525 return CGF.Builder.CreateExtractElement(Result, C0); 3526 3527 return CGF.Builder.CreateBitCast(Result, ResultType, s); 3528 } 3529 3530 Value *CodeGenFunction::EmitCommonNeonBuiltinExpr( 3531 unsigned BuiltinID, unsigned LLVMIntrinsic, unsigned AltLLVMIntrinsic, 3532 const char *NameHint, unsigned Modifier, const CallExpr *E, 3533 SmallVectorImpl<llvm::Value *> &Ops, Address PtrOp0, Address PtrOp1) { 3534 // Get the last argument, which specifies the vector type. 3535 llvm::APSInt NeonTypeConst; 3536 const Expr *Arg = E->getArg(E->getNumArgs() - 1); 3537 if (!Arg->isIntegerConstantExpr(NeonTypeConst, getContext())) 3538 return nullptr; 3539 3540 // Determine the type of this overloaded NEON intrinsic. 3541 NeonTypeFlags Type(NeonTypeConst.getZExtValue()); 3542 bool Usgn = Type.isUnsigned(); 3543 bool Quad = Type.isQuad(); 3544 3545 llvm::VectorType *VTy = GetNeonType(this, Type); 3546 llvm::Type *Ty = VTy; 3547 if (!Ty) 3548 return nullptr; 3549 3550 auto getAlignmentValue32 = [&](Address addr) -> Value* { 3551 return Builder.getInt32(addr.getAlignment().getQuantity()); 3552 }; 3553 3554 unsigned Int = LLVMIntrinsic; 3555 if ((Modifier & UnsignedAlts) && !Usgn) 3556 Int = AltLLVMIntrinsic; 3557 3558 switch (BuiltinID) { 3559 default: break; 3560 case NEON::BI__builtin_neon_vabs_v: 3561 case NEON::BI__builtin_neon_vabsq_v: 3562 if (VTy->getElementType()->isFloatingPointTy()) 3563 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::fabs, Ty), Ops, "vabs"); 3564 return EmitNeonCall(CGM.getIntrinsic(LLVMIntrinsic, Ty), Ops, "vabs"); 3565 case NEON::BI__builtin_neon_vaddhn_v: { 3566 llvm::VectorType *SrcTy = 3567 llvm::VectorType::getExtendedElementVectorType(VTy); 3568 3569 // %sum = add <4 x i32> %lhs, %rhs 3570 Ops[0] = Builder.CreateBitCast(Ops[0], SrcTy); 3571 Ops[1] = Builder.CreateBitCast(Ops[1], SrcTy); 3572 Ops[0] = Builder.CreateAdd(Ops[0], Ops[1], "vaddhn"); 3573 3574 // %high = lshr <4 x i32> %sum, <i32 16, i32 16, i32 16, i32 16> 3575 Constant *ShiftAmt = 3576 ConstantInt::get(SrcTy, SrcTy->getScalarSizeInBits() / 2); 3577 Ops[0] = Builder.CreateLShr(Ops[0], ShiftAmt, "vaddhn"); 3578 3579 // %res = trunc <4 x i32> %high to <4 x i16> 3580 return Builder.CreateTrunc(Ops[0], VTy, "vaddhn"); 3581 } 3582 case NEON::BI__builtin_neon_vcale_v: 3583 case NEON::BI__builtin_neon_vcaleq_v: 3584 case NEON::BI__builtin_neon_vcalt_v: 3585 case NEON::BI__builtin_neon_vcaltq_v: 3586 std::swap(Ops[0], Ops[1]); 3587 case NEON::BI__builtin_neon_vcage_v: 3588 case NEON::BI__builtin_neon_vcageq_v: 3589 case NEON::BI__builtin_neon_vcagt_v: 3590 case NEON::BI__builtin_neon_vcagtq_v: { 3591 llvm::Type *VecFlt = llvm::VectorType::get( 3592 VTy->getScalarSizeInBits() == 32 ? FloatTy : DoubleTy, 3593 VTy->getNumElements()); 3594 llvm::Type *Tys[] = { VTy, VecFlt }; 3595 Function *F = CGM.getIntrinsic(LLVMIntrinsic, Tys); 3596 return EmitNeonCall(F, Ops, NameHint); 3597 } 3598 case NEON::BI__builtin_neon_vclz_v: 3599 case NEON::BI__builtin_neon_vclzq_v: 3600 // We generate target-independent intrinsic, which needs a second argument 3601 // for whether or not clz of zero is undefined; on ARM it isn't. 3602 Ops.push_back(Builder.getInt1(getTarget().isCLZForZeroUndef())); 3603 break; 3604 case NEON::BI__builtin_neon_vcvt_f32_v: 3605 case NEON::BI__builtin_neon_vcvtq_f32_v: 3606 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 3607 Ty = GetNeonType(this, NeonTypeFlags(NeonTypeFlags::Float32, false, Quad)); 3608 return Usgn ? Builder.CreateUIToFP(Ops[0], Ty, "vcvt") 3609 : Builder.CreateSIToFP(Ops[0], Ty, "vcvt"); 3610 case NEON::BI__builtin_neon_vcvt_n_f32_v: 3611 case NEON::BI__builtin_neon_vcvt_n_f64_v: 3612 case NEON::BI__builtin_neon_vcvtq_n_f32_v: 3613 case NEON::BI__builtin_neon_vcvtq_n_f64_v: { 3614 llvm::Type *Tys[2] = { GetFloatNeonType(this, Type), Ty }; 3615 Int = Usgn ? LLVMIntrinsic : AltLLVMIntrinsic; 3616 Function *F = CGM.getIntrinsic(Int, Tys); 3617 return EmitNeonCall(F, Ops, "vcvt_n"); 3618 } 3619 case NEON::BI__builtin_neon_vcvt_n_s32_v: 3620 case NEON::BI__builtin_neon_vcvt_n_u32_v: 3621 case NEON::BI__builtin_neon_vcvt_n_s64_v: 3622 case NEON::BI__builtin_neon_vcvt_n_u64_v: 3623 case NEON::BI__builtin_neon_vcvtq_n_s32_v: 3624 case NEON::BI__builtin_neon_vcvtq_n_u32_v: 3625 case NEON::BI__builtin_neon_vcvtq_n_s64_v: 3626 case NEON::BI__builtin_neon_vcvtq_n_u64_v: { 3627 llvm::Type *Tys[2] = { Ty, GetFloatNeonType(this, Type) }; 3628 Function *F = CGM.getIntrinsic(LLVMIntrinsic, Tys); 3629 return EmitNeonCall(F, Ops, "vcvt_n"); 3630 } 3631 case NEON::BI__builtin_neon_vcvt_s32_v: 3632 case NEON::BI__builtin_neon_vcvt_u32_v: 3633 case NEON::BI__builtin_neon_vcvt_s64_v: 3634 case NEON::BI__builtin_neon_vcvt_u64_v: 3635 case NEON::BI__builtin_neon_vcvtq_s32_v: 3636 case NEON::BI__builtin_neon_vcvtq_u32_v: 3637 case NEON::BI__builtin_neon_vcvtq_s64_v: 3638 case NEON::BI__builtin_neon_vcvtq_u64_v: { 3639 Ops[0] = Builder.CreateBitCast(Ops[0], GetFloatNeonType(this, Type)); 3640 return Usgn ? Builder.CreateFPToUI(Ops[0], Ty, "vcvt") 3641 : Builder.CreateFPToSI(Ops[0], Ty, "vcvt"); 3642 } 3643 case NEON::BI__builtin_neon_vcvta_s32_v: 3644 case NEON::BI__builtin_neon_vcvta_s64_v: 3645 case NEON::BI__builtin_neon_vcvta_u32_v: 3646 case NEON::BI__builtin_neon_vcvta_u64_v: 3647 case NEON::BI__builtin_neon_vcvtaq_s32_v: 3648 case NEON::BI__builtin_neon_vcvtaq_s64_v: 3649 case NEON::BI__builtin_neon_vcvtaq_u32_v: 3650 case NEON::BI__builtin_neon_vcvtaq_u64_v: 3651 case NEON::BI__builtin_neon_vcvtn_s32_v: 3652 case NEON::BI__builtin_neon_vcvtn_s64_v: 3653 case NEON::BI__builtin_neon_vcvtn_u32_v: 3654 case NEON::BI__builtin_neon_vcvtn_u64_v: 3655 case NEON::BI__builtin_neon_vcvtnq_s32_v: 3656 case NEON::BI__builtin_neon_vcvtnq_s64_v: 3657 case NEON::BI__builtin_neon_vcvtnq_u32_v: 3658 case NEON::BI__builtin_neon_vcvtnq_u64_v: 3659 case NEON::BI__builtin_neon_vcvtp_s32_v: 3660 case NEON::BI__builtin_neon_vcvtp_s64_v: 3661 case NEON::BI__builtin_neon_vcvtp_u32_v: 3662 case NEON::BI__builtin_neon_vcvtp_u64_v: 3663 case NEON::BI__builtin_neon_vcvtpq_s32_v: 3664 case NEON::BI__builtin_neon_vcvtpq_s64_v: 3665 case NEON::BI__builtin_neon_vcvtpq_u32_v: 3666 case NEON::BI__builtin_neon_vcvtpq_u64_v: 3667 case NEON::BI__builtin_neon_vcvtm_s32_v: 3668 case NEON::BI__builtin_neon_vcvtm_s64_v: 3669 case NEON::BI__builtin_neon_vcvtm_u32_v: 3670 case NEON::BI__builtin_neon_vcvtm_u64_v: 3671 case NEON::BI__builtin_neon_vcvtmq_s32_v: 3672 case NEON::BI__builtin_neon_vcvtmq_s64_v: 3673 case NEON::BI__builtin_neon_vcvtmq_u32_v: 3674 case NEON::BI__builtin_neon_vcvtmq_u64_v: { 3675 llvm::Type *Tys[2] = { Ty, GetFloatNeonType(this, Type) }; 3676 return EmitNeonCall(CGM.getIntrinsic(LLVMIntrinsic, Tys), Ops, NameHint); 3677 } 3678 case NEON::BI__builtin_neon_vext_v: 3679 case NEON::BI__builtin_neon_vextq_v: { 3680 int CV = cast<ConstantInt>(Ops[2])->getSExtValue(); 3681 SmallVector<uint32_t, 16> Indices; 3682 for (unsigned i = 0, e = VTy->getNumElements(); i != e; ++i) 3683 Indices.push_back(i+CV); 3684 3685 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 3686 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 3687 return Builder.CreateShuffleVector(Ops[0], Ops[1], Indices, "vext"); 3688 } 3689 case NEON::BI__builtin_neon_vfma_v: 3690 case NEON::BI__builtin_neon_vfmaq_v: { 3691 Value *F = CGM.getIntrinsic(Intrinsic::fma, Ty); 3692 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 3693 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 3694 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 3695 3696 // NEON intrinsic puts accumulator first, unlike the LLVM fma. 3697 return Builder.CreateCall(F, {Ops[1], Ops[2], Ops[0]}); 3698 } 3699 case NEON::BI__builtin_neon_vld1_v: 3700 case NEON::BI__builtin_neon_vld1q_v: { 3701 llvm::Type *Tys[] = {Ty, Int8PtrTy}; 3702 Ops.push_back(getAlignmentValue32(PtrOp0)); 3703 return EmitNeonCall(CGM.getIntrinsic(LLVMIntrinsic, Tys), Ops, "vld1"); 3704 } 3705 case NEON::BI__builtin_neon_vld2_v: 3706 case NEON::BI__builtin_neon_vld2q_v: 3707 case NEON::BI__builtin_neon_vld3_v: 3708 case NEON::BI__builtin_neon_vld3q_v: 3709 case NEON::BI__builtin_neon_vld4_v: 3710 case NEON::BI__builtin_neon_vld4q_v: { 3711 llvm::Type *Tys[] = {Ty, Int8PtrTy}; 3712 Function *F = CGM.getIntrinsic(LLVMIntrinsic, Tys); 3713 Value *Align = getAlignmentValue32(PtrOp1); 3714 Ops[1] = Builder.CreateCall(F, {Ops[1], Align}, NameHint); 3715 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 3716 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 3717 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 3718 } 3719 case NEON::BI__builtin_neon_vld1_dup_v: 3720 case NEON::BI__builtin_neon_vld1q_dup_v: { 3721 Value *V = UndefValue::get(Ty); 3722 Ty = llvm::PointerType::getUnqual(VTy->getElementType()); 3723 PtrOp0 = Builder.CreateBitCast(PtrOp0, Ty); 3724 LoadInst *Ld = Builder.CreateLoad(PtrOp0); 3725 llvm::Constant *CI = ConstantInt::get(SizeTy, 0); 3726 Ops[0] = Builder.CreateInsertElement(V, Ld, CI); 3727 return EmitNeonSplat(Ops[0], CI); 3728 } 3729 case NEON::BI__builtin_neon_vld2_lane_v: 3730 case NEON::BI__builtin_neon_vld2q_lane_v: 3731 case NEON::BI__builtin_neon_vld3_lane_v: 3732 case NEON::BI__builtin_neon_vld3q_lane_v: 3733 case NEON::BI__builtin_neon_vld4_lane_v: 3734 case NEON::BI__builtin_neon_vld4q_lane_v: { 3735 llvm::Type *Tys[] = {Ty, Int8PtrTy}; 3736 Function *F = CGM.getIntrinsic(LLVMIntrinsic, Tys); 3737 for (unsigned I = 2; I < Ops.size() - 1; ++I) 3738 Ops[I] = Builder.CreateBitCast(Ops[I], Ty); 3739 Ops.push_back(getAlignmentValue32(PtrOp1)); 3740 Ops[1] = Builder.CreateCall(F, makeArrayRef(Ops).slice(1), NameHint); 3741 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 3742 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 3743 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 3744 } 3745 case NEON::BI__builtin_neon_vmovl_v: { 3746 llvm::Type *DTy =llvm::VectorType::getTruncatedElementVectorType(VTy); 3747 Ops[0] = Builder.CreateBitCast(Ops[0], DTy); 3748 if (Usgn) 3749 return Builder.CreateZExt(Ops[0], Ty, "vmovl"); 3750 return Builder.CreateSExt(Ops[0], Ty, "vmovl"); 3751 } 3752 case NEON::BI__builtin_neon_vmovn_v: { 3753 llvm::Type *QTy = llvm::VectorType::getExtendedElementVectorType(VTy); 3754 Ops[0] = Builder.CreateBitCast(Ops[0], QTy); 3755 return Builder.CreateTrunc(Ops[0], Ty, "vmovn"); 3756 } 3757 case NEON::BI__builtin_neon_vmull_v: 3758 // FIXME: the integer vmull operations could be emitted in terms of pure 3759 // LLVM IR (2 exts followed by a mul). Unfortunately LLVM has a habit of 3760 // hoisting the exts outside loops. Until global ISel comes along that can 3761 // see through such movement this leads to bad CodeGen. So we need an 3762 // intrinsic for now. 3763 Int = Usgn ? Intrinsic::arm_neon_vmullu : Intrinsic::arm_neon_vmulls; 3764 Int = Type.isPoly() ? (unsigned)Intrinsic::arm_neon_vmullp : Int; 3765 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vmull"); 3766 case NEON::BI__builtin_neon_vpadal_v: 3767 case NEON::BI__builtin_neon_vpadalq_v: { 3768 // The source operand type has twice as many elements of half the size. 3769 unsigned EltBits = VTy->getElementType()->getPrimitiveSizeInBits(); 3770 llvm::Type *EltTy = 3771 llvm::IntegerType::get(getLLVMContext(), EltBits / 2); 3772 llvm::Type *NarrowTy = 3773 llvm::VectorType::get(EltTy, VTy->getNumElements() * 2); 3774 llvm::Type *Tys[2] = { Ty, NarrowTy }; 3775 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, NameHint); 3776 } 3777 case NEON::BI__builtin_neon_vpaddl_v: 3778 case NEON::BI__builtin_neon_vpaddlq_v: { 3779 // The source operand type has twice as many elements of half the size. 3780 unsigned EltBits = VTy->getElementType()->getPrimitiveSizeInBits(); 3781 llvm::Type *EltTy = llvm::IntegerType::get(getLLVMContext(), EltBits / 2); 3782 llvm::Type *NarrowTy = 3783 llvm::VectorType::get(EltTy, VTy->getNumElements() * 2); 3784 llvm::Type *Tys[2] = { Ty, NarrowTy }; 3785 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vpaddl"); 3786 } 3787 case NEON::BI__builtin_neon_vqdmlal_v: 3788 case NEON::BI__builtin_neon_vqdmlsl_v: { 3789 SmallVector<Value *, 2> MulOps(Ops.begin() + 1, Ops.end()); 3790 Ops[1] = 3791 EmitNeonCall(CGM.getIntrinsic(LLVMIntrinsic, Ty), MulOps, "vqdmlal"); 3792 Ops.resize(2); 3793 return EmitNeonCall(CGM.getIntrinsic(AltLLVMIntrinsic, Ty), Ops, NameHint); 3794 } 3795 case NEON::BI__builtin_neon_vqshl_n_v: 3796 case NEON::BI__builtin_neon_vqshlq_n_v: 3797 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqshl_n", 3798 1, false); 3799 case NEON::BI__builtin_neon_vqshlu_n_v: 3800 case NEON::BI__builtin_neon_vqshluq_n_v: 3801 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqshlu_n", 3802 1, false); 3803 case NEON::BI__builtin_neon_vrecpe_v: 3804 case NEON::BI__builtin_neon_vrecpeq_v: 3805 case NEON::BI__builtin_neon_vrsqrte_v: 3806 case NEON::BI__builtin_neon_vrsqrteq_v: 3807 Int = Ty->isFPOrFPVectorTy() ? LLVMIntrinsic : AltLLVMIntrinsic; 3808 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, NameHint); 3809 3810 case NEON::BI__builtin_neon_vrshr_n_v: 3811 case NEON::BI__builtin_neon_vrshrq_n_v: 3812 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrshr_n", 3813 1, true); 3814 case NEON::BI__builtin_neon_vshl_n_v: 3815 case NEON::BI__builtin_neon_vshlq_n_v: 3816 Ops[1] = EmitNeonShiftVector(Ops[1], Ty, false); 3817 return Builder.CreateShl(Builder.CreateBitCast(Ops[0],Ty), Ops[1], 3818 "vshl_n"); 3819 case NEON::BI__builtin_neon_vshll_n_v: { 3820 llvm::Type *SrcTy = llvm::VectorType::getTruncatedElementVectorType(VTy); 3821 Ops[0] = Builder.CreateBitCast(Ops[0], SrcTy); 3822 if (Usgn) 3823 Ops[0] = Builder.CreateZExt(Ops[0], VTy); 3824 else 3825 Ops[0] = Builder.CreateSExt(Ops[0], VTy); 3826 Ops[1] = EmitNeonShiftVector(Ops[1], VTy, false); 3827 return Builder.CreateShl(Ops[0], Ops[1], "vshll_n"); 3828 } 3829 case NEON::BI__builtin_neon_vshrn_n_v: { 3830 llvm::Type *SrcTy = llvm::VectorType::getExtendedElementVectorType(VTy); 3831 Ops[0] = Builder.CreateBitCast(Ops[0], SrcTy); 3832 Ops[1] = EmitNeonShiftVector(Ops[1], SrcTy, false); 3833 if (Usgn) 3834 Ops[0] = Builder.CreateLShr(Ops[0], Ops[1]); 3835 else 3836 Ops[0] = Builder.CreateAShr(Ops[0], Ops[1]); 3837 return Builder.CreateTrunc(Ops[0], Ty, "vshrn_n"); 3838 } 3839 case NEON::BI__builtin_neon_vshr_n_v: 3840 case NEON::BI__builtin_neon_vshrq_n_v: 3841 return EmitNeonRShiftImm(Ops[0], Ops[1], Ty, Usgn, "vshr_n"); 3842 case NEON::BI__builtin_neon_vst1_v: 3843 case NEON::BI__builtin_neon_vst1q_v: 3844 case NEON::BI__builtin_neon_vst2_v: 3845 case NEON::BI__builtin_neon_vst2q_v: 3846 case NEON::BI__builtin_neon_vst3_v: 3847 case NEON::BI__builtin_neon_vst3q_v: 3848 case NEON::BI__builtin_neon_vst4_v: 3849 case NEON::BI__builtin_neon_vst4q_v: 3850 case NEON::BI__builtin_neon_vst2_lane_v: 3851 case NEON::BI__builtin_neon_vst2q_lane_v: 3852 case NEON::BI__builtin_neon_vst3_lane_v: 3853 case NEON::BI__builtin_neon_vst3q_lane_v: 3854 case NEON::BI__builtin_neon_vst4_lane_v: 3855 case NEON::BI__builtin_neon_vst4q_lane_v: { 3856 llvm::Type *Tys[] = {Int8PtrTy, Ty}; 3857 Ops.push_back(getAlignmentValue32(PtrOp0)); 3858 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, ""); 3859 } 3860 case NEON::BI__builtin_neon_vsubhn_v: { 3861 llvm::VectorType *SrcTy = 3862 llvm::VectorType::getExtendedElementVectorType(VTy); 3863 3864 // %sum = add <4 x i32> %lhs, %rhs 3865 Ops[0] = Builder.CreateBitCast(Ops[0], SrcTy); 3866 Ops[1] = Builder.CreateBitCast(Ops[1], SrcTy); 3867 Ops[0] = Builder.CreateSub(Ops[0], Ops[1], "vsubhn"); 3868 3869 // %high = lshr <4 x i32> %sum, <i32 16, i32 16, i32 16, i32 16> 3870 Constant *ShiftAmt = 3871 ConstantInt::get(SrcTy, SrcTy->getScalarSizeInBits() / 2); 3872 Ops[0] = Builder.CreateLShr(Ops[0], ShiftAmt, "vsubhn"); 3873 3874 // %res = trunc <4 x i32> %high to <4 x i16> 3875 return Builder.CreateTrunc(Ops[0], VTy, "vsubhn"); 3876 } 3877 case NEON::BI__builtin_neon_vtrn_v: 3878 case NEON::BI__builtin_neon_vtrnq_v: { 3879 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(Ty)); 3880 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 3881 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 3882 Value *SV = nullptr; 3883 3884 for (unsigned vi = 0; vi != 2; ++vi) { 3885 SmallVector<uint32_t, 16> Indices; 3886 for (unsigned i = 0, e = VTy->getNumElements(); i != e; i += 2) { 3887 Indices.push_back(i+vi); 3888 Indices.push_back(i+e+vi); 3889 } 3890 Value *Addr = Builder.CreateConstInBoundsGEP1_32(Ty, Ops[0], vi); 3891 SV = Builder.CreateShuffleVector(Ops[1], Ops[2], Indices, "vtrn"); 3892 SV = Builder.CreateDefaultAlignedStore(SV, Addr); 3893 } 3894 return SV; 3895 } 3896 case NEON::BI__builtin_neon_vtst_v: 3897 case NEON::BI__builtin_neon_vtstq_v: { 3898 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 3899 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 3900 Ops[0] = Builder.CreateAnd(Ops[0], Ops[1]); 3901 Ops[0] = Builder.CreateICmp(ICmpInst::ICMP_NE, Ops[0], 3902 ConstantAggregateZero::get(Ty)); 3903 return Builder.CreateSExt(Ops[0], Ty, "vtst"); 3904 } 3905 case NEON::BI__builtin_neon_vuzp_v: 3906 case NEON::BI__builtin_neon_vuzpq_v: { 3907 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(Ty)); 3908 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 3909 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 3910 Value *SV = nullptr; 3911 3912 for (unsigned vi = 0; vi != 2; ++vi) { 3913 SmallVector<uint32_t, 16> Indices; 3914 for (unsigned i = 0, e = VTy->getNumElements(); i != e; ++i) 3915 Indices.push_back(2*i+vi); 3916 3917 Value *Addr = Builder.CreateConstInBoundsGEP1_32(Ty, Ops[0], vi); 3918 SV = Builder.CreateShuffleVector(Ops[1], Ops[2], Indices, "vuzp"); 3919 SV = Builder.CreateDefaultAlignedStore(SV, Addr); 3920 } 3921 return SV; 3922 } 3923 case NEON::BI__builtin_neon_vzip_v: 3924 case NEON::BI__builtin_neon_vzipq_v: { 3925 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(Ty)); 3926 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 3927 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 3928 Value *SV = nullptr; 3929 3930 for (unsigned vi = 0; vi != 2; ++vi) { 3931 SmallVector<uint32_t, 16> Indices; 3932 for (unsigned i = 0, e = VTy->getNumElements(); i != e; i += 2) { 3933 Indices.push_back((i + vi*e) >> 1); 3934 Indices.push_back(((i + vi*e) >> 1)+e); 3935 } 3936 Value *Addr = Builder.CreateConstInBoundsGEP1_32(Ty, Ops[0], vi); 3937 SV = Builder.CreateShuffleVector(Ops[1], Ops[2], Indices, "vzip"); 3938 SV = Builder.CreateDefaultAlignedStore(SV, Addr); 3939 } 3940 return SV; 3941 } 3942 } 3943 3944 assert(Int && "Expected valid intrinsic number"); 3945 3946 // Determine the type(s) of this overloaded AArch64 intrinsic. 3947 Function *F = LookupNeonLLVMIntrinsic(Int, Modifier, Ty, E); 3948 3949 Value *Result = EmitNeonCall(F, Ops, NameHint); 3950 llvm::Type *ResultType = ConvertType(E->getType()); 3951 // AArch64 intrinsic one-element vector type cast to 3952 // scalar type expected by the builtin 3953 return Builder.CreateBitCast(Result, ResultType, NameHint); 3954 } 3955 3956 Value *CodeGenFunction::EmitAArch64CompareBuiltinExpr( 3957 Value *Op, llvm::Type *Ty, const CmpInst::Predicate Fp, 3958 const CmpInst::Predicate Ip, const Twine &Name) { 3959 llvm::Type *OTy = Op->getType(); 3960 3961 // FIXME: this is utterly horrific. We should not be looking at previous 3962 // codegen context to find out what needs doing. Unfortunately TableGen 3963 // currently gives us exactly the same calls for vceqz_f32 and vceqz_s32 3964 // (etc). 3965 if (BitCastInst *BI = dyn_cast<BitCastInst>(Op)) 3966 OTy = BI->getOperand(0)->getType(); 3967 3968 Op = Builder.CreateBitCast(Op, OTy); 3969 if (OTy->getScalarType()->isFloatingPointTy()) { 3970 Op = Builder.CreateFCmp(Fp, Op, Constant::getNullValue(OTy)); 3971 } else { 3972 Op = Builder.CreateICmp(Ip, Op, Constant::getNullValue(OTy)); 3973 } 3974 return Builder.CreateSExt(Op, Ty, Name); 3975 } 3976 3977 static Value *packTBLDVectorList(CodeGenFunction &CGF, ArrayRef<Value *> Ops, 3978 Value *ExtOp, Value *IndexOp, 3979 llvm::Type *ResTy, unsigned IntID, 3980 const char *Name) { 3981 SmallVector<Value *, 2> TblOps; 3982 if (ExtOp) 3983 TblOps.push_back(ExtOp); 3984 3985 // Build a vector containing sequential number like (0, 1, 2, ..., 15) 3986 SmallVector<uint32_t, 16> Indices; 3987 llvm::VectorType *TblTy = cast<llvm::VectorType>(Ops[0]->getType()); 3988 for (unsigned i = 0, e = TblTy->getNumElements(); i != e; ++i) { 3989 Indices.push_back(2*i); 3990 Indices.push_back(2*i+1); 3991 } 3992 3993 int PairPos = 0, End = Ops.size() - 1; 3994 while (PairPos < End) { 3995 TblOps.push_back(CGF.Builder.CreateShuffleVector(Ops[PairPos], 3996 Ops[PairPos+1], Indices, 3997 Name)); 3998 PairPos += 2; 3999 } 4000 4001 // If there's an odd number of 64-bit lookup table, fill the high 64-bit 4002 // of the 128-bit lookup table with zero. 4003 if (PairPos == End) { 4004 Value *ZeroTbl = ConstantAggregateZero::get(TblTy); 4005 TblOps.push_back(CGF.Builder.CreateShuffleVector(Ops[PairPos], 4006 ZeroTbl, Indices, Name)); 4007 } 4008 4009 Function *TblF; 4010 TblOps.push_back(IndexOp); 4011 TblF = CGF.CGM.getIntrinsic(IntID, ResTy); 4012 4013 return CGF.EmitNeonCall(TblF, TblOps, Name); 4014 } 4015 4016 Value *CodeGenFunction::GetValueForARMHint(unsigned BuiltinID) { 4017 unsigned Value; 4018 switch (BuiltinID) { 4019 default: 4020 return nullptr; 4021 case ARM::BI__builtin_arm_nop: 4022 Value = 0; 4023 break; 4024 case ARM::BI__builtin_arm_yield: 4025 case ARM::BI__yield: 4026 Value = 1; 4027 break; 4028 case ARM::BI__builtin_arm_wfe: 4029 case ARM::BI__wfe: 4030 Value = 2; 4031 break; 4032 case ARM::BI__builtin_arm_wfi: 4033 case ARM::BI__wfi: 4034 Value = 3; 4035 break; 4036 case ARM::BI__builtin_arm_sev: 4037 case ARM::BI__sev: 4038 Value = 4; 4039 break; 4040 case ARM::BI__builtin_arm_sevl: 4041 case ARM::BI__sevl: 4042 Value = 5; 4043 break; 4044 } 4045 4046 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::arm_hint), 4047 llvm::ConstantInt::get(Int32Ty, Value)); 4048 } 4049 4050 // Generates the IR for the read/write special register builtin, 4051 // ValueType is the type of the value that is to be written or read, 4052 // RegisterType is the type of the register being written to or read from. 4053 static Value *EmitSpecialRegisterBuiltin(CodeGenFunction &CGF, 4054 const CallExpr *E, 4055 llvm::Type *RegisterType, 4056 llvm::Type *ValueType, 4057 bool IsRead, 4058 StringRef SysReg = "") { 4059 // write and register intrinsics only support 32 and 64 bit operations. 4060 assert((RegisterType->isIntegerTy(32) || RegisterType->isIntegerTy(64)) 4061 && "Unsupported size for register."); 4062 4063 CodeGen::CGBuilderTy &Builder = CGF.Builder; 4064 CodeGen::CodeGenModule &CGM = CGF.CGM; 4065 LLVMContext &Context = CGM.getLLVMContext(); 4066 4067 if (SysReg.empty()) { 4068 const Expr *SysRegStrExpr = E->getArg(0)->IgnoreParenCasts(); 4069 SysReg = cast<StringLiteral>(SysRegStrExpr)->getString(); 4070 } 4071 4072 llvm::Metadata *Ops[] = { llvm::MDString::get(Context, SysReg) }; 4073 llvm::MDNode *RegName = llvm::MDNode::get(Context, Ops); 4074 llvm::Value *Metadata = llvm::MetadataAsValue::get(Context, RegName); 4075 4076 llvm::Type *Types[] = { RegisterType }; 4077 4078 bool MixedTypes = RegisterType->isIntegerTy(64) && ValueType->isIntegerTy(32); 4079 assert(!(RegisterType->isIntegerTy(32) && ValueType->isIntegerTy(64)) 4080 && "Can't fit 64-bit value in 32-bit register"); 4081 4082 if (IsRead) { 4083 llvm::Value *F = CGM.getIntrinsic(llvm::Intrinsic::read_register, Types); 4084 llvm::Value *Call = Builder.CreateCall(F, Metadata); 4085 4086 if (MixedTypes) 4087 // Read into 64 bit register and then truncate result to 32 bit. 4088 return Builder.CreateTrunc(Call, ValueType); 4089 4090 if (ValueType->isPointerTy()) 4091 // Have i32/i64 result (Call) but want to return a VoidPtrTy (i8*). 4092 return Builder.CreateIntToPtr(Call, ValueType); 4093 4094 return Call; 4095 } 4096 4097 llvm::Value *F = CGM.getIntrinsic(llvm::Intrinsic::write_register, Types); 4098 llvm::Value *ArgValue = CGF.EmitScalarExpr(E->getArg(1)); 4099 if (MixedTypes) { 4100 // Extend 32 bit write value to 64 bit to pass to write. 4101 ArgValue = Builder.CreateZExt(ArgValue, RegisterType); 4102 return Builder.CreateCall(F, { Metadata, ArgValue }); 4103 } 4104 4105 if (ValueType->isPointerTy()) { 4106 // Have VoidPtrTy ArgValue but want to return an i32/i64. 4107 ArgValue = Builder.CreatePtrToInt(ArgValue, RegisterType); 4108 return Builder.CreateCall(F, { Metadata, ArgValue }); 4109 } 4110 4111 return Builder.CreateCall(F, { Metadata, ArgValue }); 4112 } 4113 4114 /// Return true if BuiltinID is an overloaded Neon intrinsic with an extra 4115 /// argument that specifies the vector type. 4116 static bool HasExtraNeonArgument(unsigned BuiltinID) { 4117 switch (BuiltinID) { 4118 default: break; 4119 case NEON::BI__builtin_neon_vget_lane_i8: 4120 case NEON::BI__builtin_neon_vget_lane_i16: 4121 case NEON::BI__builtin_neon_vget_lane_i32: 4122 case NEON::BI__builtin_neon_vget_lane_i64: 4123 case NEON::BI__builtin_neon_vget_lane_f32: 4124 case NEON::BI__builtin_neon_vgetq_lane_i8: 4125 case NEON::BI__builtin_neon_vgetq_lane_i16: 4126 case NEON::BI__builtin_neon_vgetq_lane_i32: 4127 case NEON::BI__builtin_neon_vgetq_lane_i64: 4128 case NEON::BI__builtin_neon_vgetq_lane_f32: 4129 case NEON::BI__builtin_neon_vset_lane_i8: 4130 case NEON::BI__builtin_neon_vset_lane_i16: 4131 case NEON::BI__builtin_neon_vset_lane_i32: 4132 case NEON::BI__builtin_neon_vset_lane_i64: 4133 case NEON::BI__builtin_neon_vset_lane_f32: 4134 case NEON::BI__builtin_neon_vsetq_lane_i8: 4135 case NEON::BI__builtin_neon_vsetq_lane_i16: 4136 case NEON::BI__builtin_neon_vsetq_lane_i32: 4137 case NEON::BI__builtin_neon_vsetq_lane_i64: 4138 case NEON::BI__builtin_neon_vsetq_lane_f32: 4139 case NEON::BI__builtin_neon_vsha1h_u32: 4140 case NEON::BI__builtin_neon_vsha1cq_u32: 4141 case NEON::BI__builtin_neon_vsha1pq_u32: 4142 case NEON::BI__builtin_neon_vsha1mq_u32: 4143 case ARM::BI_MoveToCoprocessor: 4144 case ARM::BI_MoveToCoprocessor2: 4145 return false; 4146 } 4147 return true; 4148 } 4149 4150 Value *CodeGenFunction::EmitARMBuiltinExpr(unsigned BuiltinID, 4151 const CallExpr *E) { 4152 if (auto Hint = GetValueForARMHint(BuiltinID)) 4153 return Hint; 4154 4155 if (BuiltinID == ARM::BI__emit) { 4156 bool IsThumb = getTarget().getTriple().getArch() == llvm::Triple::thumb; 4157 llvm::FunctionType *FTy = 4158 llvm::FunctionType::get(VoidTy, /*Variadic=*/false); 4159 4160 APSInt Value; 4161 if (!E->getArg(0)->EvaluateAsInt(Value, CGM.getContext())) 4162 llvm_unreachable("Sema will ensure that the parameter is constant"); 4163 4164 uint64_t ZExtValue = Value.zextOrTrunc(IsThumb ? 16 : 32).getZExtValue(); 4165 4166 llvm::InlineAsm *Emit = 4167 IsThumb ? InlineAsm::get(FTy, ".inst.n 0x" + utohexstr(ZExtValue), "", 4168 /*SideEffects=*/true) 4169 : InlineAsm::get(FTy, ".inst 0x" + utohexstr(ZExtValue), "", 4170 /*SideEffects=*/true); 4171 4172 return Builder.CreateCall(Emit); 4173 } 4174 4175 if (BuiltinID == ARM::BI__builtin_arm_dbg) { 4176 Value *Option = EmitScalarExpr(E->getArg(0)); 4177 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::arm_dbg), Option); 4178 } 4179 4180 if (BuiltinID == ARM::BI__builtin_arm_prefetch) { 4181 Value *Address = EmitScalarExpr(E->getArg(0)); 4182 Value *RW = EmitScalarExpr(E->getArg(1)); 4183 Value *IsData = EmitScalarExpr(E->getArg(2)); 4184 4185 // Locality is not supported on ARM target 4186 Value *Locality = llvm::ConstantInt::get(Int32Ty, 3); 4187 4188 Value *F = CGM.getIntrinsic(Intrinsic::prefetch); 4189 return Builder.CreateCall(F, {Address, RW, Locality, IsData}); 4190 } 4191 4192 if (BuiltinID == ARM::BI__builtin_arm_rbit) { 4193 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::arm_rbit), 4194 EmitScalarExpr(E->getArg(0)), 4195 "rbit"); 4196 } 4197 4198 if (BuiltinID == ARM::BI__clear_cache) { 4199 assert(E->getNumArgs() == 2 && "__clear_cache takes 2 arguments"); 4200 const FunctionDecl *FD = E->getDirectCallee(); 4201 Value *Ops[2]; 4202 for (unsigned i = 0; i < 2; i++) 4203 Ops[i] = EmitScalarExpr(E->getArg(i)); 4204 llvm::Type *Ty = CGM.getTypes().ConvertType(FD->getType()); 4205 llvm::FunctionType *FTy = cast<llvm::FunctionType>(Ty); 4206 StringRef Name = FD->getName(); 4207 return EmitNounwindRuntimeCall(CGM.CreateRuntimeFunction(FTy, Name), Ops); 4208 } 4209 4210 if (BuiltinID == ARM::BI__builtin_arm_mcrr || 4211 BuiltinID == ARM::BI__builtin_arm_mcrr2) { 4212 Function *F; 4213 4214 switch (BuiltinID) { 4215 default: llvm_unreachable("unexpected builtin"); 4216 case ARM::BI__builtin_arm_mcrr: 4217 F = CGM.getIntrinsic(Intrinsic::arm_mcrr); 4218 break; 4219 case ARM::BI__builtin_arm_mcrr2: 4220 F = CGM.getIntrinsic(Intrinsic::arm_mcrr2); 4221 break; 4222 } 4223 4224 // MCRR{2} instruction has 5 operands but 4225 // the intrinsic has 4 because Rt and Rt2 4226 // are represented as a single unsigned 64 4227 // bit integer in the intrinsic definition 4228 // but internally it's represented as 2 32 4229 // bit integers. 4230 4231 Value *Coproc = EmitScalarExpr(E->getArg(0)); 4232 Value *Opc1 = EmitScalarExpr(E->getArg(1)); 4233 Value *RtAndRt2 = EmitScalarExpr(E->getArg(2)); 4234 Value *CRm = EmitScalarExpr(E->getArg(3)); 4235 4236 Value *C1 = llvm::ConstantInt::get(Int64Ty, 32); 4237 Value *Rt = Builder.CreateTruncOrBitCast(RtAndRt2, Int32Ty); 4238 Value *Rt2 = Builder.CreateLShr(RtAndRt2, C1); 4239 Rt2 = Builder.CreateTruncOrBitCast(Rt2, Int32Ty); 4240 4241 return Builder.CreateCall(F, {Coproc, Opc1, Rt, Rt2, CRm}); 4242 } 4243 4244 if (BuiltinID == ARM::BI__builtin_arm_mrrc || 4245 BuiltinID == ARM::BI__builtin_arm_mrrc2) { 4246 Function *F; 4247 4248 switch (BuiltinID) { 4249 default: llvm_unreachable("unexpected builtin"); 4250 case ARM::BI__builtin_arm_mrrc: 4251 F = CGM.getIntrinsic(Intrinsic::arm_mrrc); 4252 break; 4253 case ARM::BI__builtin_arm_mrrc2: 4254 F = CGM.getIntrinsic(Intrinsic::arm_mrrc2); 4255 break; 4256 } 4257 4258 Value *Coproc = EmitScalarExpr(E->getArg(0)); 4259 Value *Opc1 = EmitScalarExpr(E->getArg(1)); 4260 Value *CRm = EmitScalarExpr(E->getArg(2)); 4261 Value *RtAndRt2 = Builder.CreateCall(F, {Coproc, Opc1, CRm}); 4262 4263 // Returns an unsigned 64 bit integer, represented 4264 // as two 32 bit integers. 4265 4266 Value *Rt = Builder.CreateExtractValue(RtAndRt2, 1); 4267 Value *Rt1 = Builder.CreateExtractValue(RtAndRt2, 0); 4268 Rt = Builder.CreateZExt(Rt, Int64Ty); 4269 Rt1 = Builder.CreateZExt(Rt1, Int64Ty); 4270 4271 Value *ShiftCast = llvm::ConstantInt::get(Int64Ty, 32); 4272 RtAndRt2 = Builder.CreateShl(Rt, ShiftCast, "shl", true); 4273 RtAndRt2 = Builder.CreateOr(RtAndRt2, Rt1); 4274 4275 return Builder.CreateBitCast(RtAndRt2, ConvertType(E->getType())); 4276 } 4277 4278 if (BuiltinID == ARM::BI__builtin_arm_ldrexd || 4279 ((BuiltinID == ARM::BI__builtin_arm_ldrex || 4280 BuiltinID == ARM::BI__builtin_arm_ldaex) && 4281 getContext().getTypeSize(E->getType()) == 64) || 4282 BuiltinID == ARM::BI__ldrexd) { 4283 Function *F; 4284 4285 switch (BuiltinID) { 4286 default: llvm_unreachable("unexpected builtin"); 4287 case ARM::BI__builtin_arm_ldaex: 4288 F = CGM.getIntrinsic(Intrinsic::arm_ldaexd); 4289 break; 4290 case ARM::BI__builtin_arm_ldrexd: 4291 case ARM::BI__builtin_arm_ldrex: 4292 case ARM::BI__ldrexd: 4293 F = CGM.getIntrinsic(Intrinsic::arm_ldrexd); 4294 break; 4295 } 4296 4297 Value *LdPtr = EmitScalarExpr(E->getArg(0)); 4298 Value *Val = Builder.CreateCall(F, Builder.CreateBitCast(LdPtr, Int8PtrTy), 4299 "ldrexd"); 4300 4301 Value *Val0 = Builder.CreateExtractValue(Val, 1); 4302 Value *Val1 = Builder.CreateExtractValue(Val, 0); 4303 Val0 = Builder.CreateZExt(Val0, Int64Ty); 4304 Val1 = Builder.CreateZExt(Val1, Int64Ty); 4305 4306 Value *ShiftCst = llvm::ConstantInt::get(Int64Ty, 32); 4307 Val = Builder.CreateShl(Val0, ShiftCst, "shl", true /* nuw */); 4308 Val = Builder.CreateOr(Val, Val1); 4309 return Builder.CreateBitCast(Val, ConvertType(E->getType())); 4310 } 4311 4312 if (BuiltinID == ARM::BI__builtin_arm_ldrex || 4313 BuiltinID == ARM::BI__builtin_arm_ldaex) { 4314 Value *LoadAddr = EmitScalarExpr(E->getArg(0)); 4315 4316 QualType Ty = E->getType(); 4317 llvm::Type *RealResTy = ConvertType(Ty); 4318 llvm::Type *IntResTy = llvm::IntegerType::get(getLLVMContext(), 4319 getContext().getTypeSize(Ty)); 4320 LoadAddr = Builder.CreateBitCast(LoadAddr, IntResTy->getPointerTo()); 4321 4322 Function *F = CGM.getIntrinsic(BuiltinID == ARM::BI__builtin_arm_ldaex 4323 ? Intrinsic::arm_ldaex 4324 : Intrinsic::arm_ldrex, 4325 LoadAddr->getType()); 4326 Value *Val = Builder.CreateCall(F, LoadAddr, "ldrex"); 4327 4328 if (RealResTy->isPointerTy()) 4329 return Builder.CreateIntToPtr(Val, RealResTy); 4330 else { 4331 Val = Builder.CreateTruncOrBitCast(Val, IntResTy); 4332 return Builder.CreateBitCast(Val, RealResTy); 4333 } 4334 } 4335 4336 if (BuiltinID == ARM::BI__builtin_arm_strexd || 4337 ((BuiltinID == ARM::BI__builtin_arm_stlex || 4338 BuiltinID == ARM::BI__builtin_arm_strex) && 4339 getContext().getTypeSize(E->getArg(0)->getType()) == 64)) { 4340 Function *F = CGM.getIntrinsic(BuiltinID == ARM::BI__builtin_arm_stlex 4341 ? Intrinsic::arm_stlexd 4342 : Intrinsic::arm_strexd); 4343 llvm::Type *STy = llvm::StructType::get(Int32Ty, Int32Ty, nullptr); 4344 4345 Address Tmp = CreateMemTemp(E->getArg(0)->getType()); 4346 Value *Val = EmitScalarExpr(E->getArg(0)); 4347 Builder.CreateStore(Val, Tmp); 4348 4349 Address LdPtr = Builder.CreateBitCast(Tmp,llvm::PointerType::getUnqual(STy)); 4350 Val = Builder.CreateLoad(LdPtr); 4351 4352 Value *Arg0 = Builder.CreateExtractValue(Val, 0); 4353 Value *Arg1 = Builder.CreateExtractValue(Val, 1); 4354 Value *StPtr = Builder.CreateBitCast(EmitScalarExpr(E->getArg(1)), Int8PtrTy); 4355 return Builder.CreateCall(F, {Arg0, Arg1, StPtr}, "strexd"); 4356 } 4357 4358 if (BuiltinID == ARM::BI__builtin_arm_strex || 4359 BuiltinID == ARM::BI__builtin_arm_stlex) { 4360 Value *StoreVal = EmitScalarExpr(E->getArg(0)); 4361 Value *StoreAddr = EmitScalarExpr(E->getArg(1)); 4362 4363 QualType Ty = E->getArg(0)->getType(); 4364 llvm::Type *StoreTy = llvm::IntegerType::get(getLLVMContext(), 4365 getContext().getTypeSize(Ty)); 4366 StoreAddr = Builder.CreateBitCast(StoreAddr, StoreTy->getPointerTo()); 4367 4368 if (StoreVal->getType()->isPointerTy()) 4369 StoreVal = Builder.CreatePtrToInt(StoreVal, Int32Ty); 4370 else { 4371 StoreVal = Builder.CreateBitCast(StoreVal, StoreTy); 4372 StoreVal = Builder.CreateZExtOrBitCast(StoreVal, Int32Ty); 4373 } 4374 4375 Function *F = CGM.getIntrinsic(BuiltinID == ARM::BI__builtin_arm_stlex 4376 ? Intrinsic::arm_stlex 4377 : Intrinsic::arm_strex, 4378 StoreAddr->getType()); 4379 return Builder.CreateCall(F, {StoreVal, StoreAddr}, "strex"); 4380 } 4381 4382 switch (BuiltinID) { 4383 case ARM::BI__iso_volatile_load8: 4384 case ARM::BI__iso_volatile_load16: 4385 case ARM::BI__iso_volatile_load32: 4386 case ARM::BI__iso_volatile_load64: { 4387 Value *Ptr = EmitScalarExpr(E->getArg(0)); 4388 QualType ElTy = E->getArg(0)->getType()->getPointeeType(); 4389 CharUnits LoadSize = getContext().getTypeSizeInChars(ElTy); 4390 llvm::Type *ITy = llvm::IntegerType::get(getLLVMContext(), 4391 LoadSize.getQuantity() * 8); 4392 Ptr = Builder.CreateBitCast(Ptr, ITy->getPointerTo()); 4393 llvm::LoadInst *Load = 4394 Builder.CreateAlignedLoad(Ptr, LoadSize); 4395 Load->setVolatile(true); 4396 return Load; 4397 } 4398 case ARM::BI__iso_volatile_store8: 4399 case ARM::BI__iso_volatile_store16: 4400 case ARM::BI__iso_volatile_store32: 4401 case ARM::BI__iso_volatile_store64: { 4402 Value *Ptr = EmitScalarExpr(E->getArg(0)); 4403 Value *Value = EmitScalarExpr(E->getArg(1)); 4404 QualType ElTy = E->getArg(0)->getType()->getPointeeType(); 4405 CharUnits StoreSize = getContext().getTypeSizeInChars(ElTy); 4406 llvm::Type *ITy = llvm::IntegerType::get(getLLVMContext(), 4407 StoreSize.getQuantity() * 8); 4408 Ptr = Builder.CreateBitCast(Ptr, ITy->getPointerTo()); 4409 llvm::StoreInst *Store = 4410 Builder.CreateAlignedStore(Value, Ptr, 4411 StoreSize); 4412 Store->setVolatile(true); 4413 return Store; 4414 } 4415 } 4416 4417 if (BuiltinID == ARM::BI__builtin_arm_clrex) { 4418 Function *F = CGM.getIntrinsic(Intrinsic::arm_clrex); 4419 return Builder.CreateCall(F); 4420 } 4421 4422 // CRC32 4423 Intrinsic::ID CRCIntrinsicID = Intrinsic::not_intrinsic; 4424 switch (BuiltinID) { 4425 case ARM::BI__builtin_arm_crc32b: 4426 CRCIntrinsicID = Intrinsic::arm_crc32b; break; 4427 case ARM::BI__builtin_arm_crc32cb: 4428 CRCIntrinsicID = Intrinsic::arm_crc32cb; break; 4429 case ARM::BI__builtin_arm_crc32h: 4430 CRCIntrinsicID = Intrinsic::arm_crc32h; break; 4431 case ARM::BI__builtin_arm_crc32ch: 4432 CRCIntrinsicID = Intrinsic::arm_crc32ch; break; 4433 case ARM::BI__builtin_arm_crc32w: 4434 case ARM::BI__builtin_arm_crc32d: 4435 CRCIntrinsicID = Intrinsic::arm_crc32w; break; 4436 case ARM::BI__builtin_arm_crc32cw: 4437 case ARM::BI__builtin_arm_crc32cd: 4438 CRCIntrinsicID = Intrinsic::arm_crc32cw; break; 4439 } 4440 4441 if (CRCIntrinsicID != Intrinsic::not_intrinsic) { 4442 Value *Arg0 = EmitScalarExpr(E->getArg(0)); 4443 Value *Arg1 = EmitScalarExpr(E->getArg(1)); 4444 4445 // crc32{c,}d intrinsics are implemnted as two calls to crc32{c,}w 4446 // intrinsics, hence we need different codegen for these cases. 4447 if (BuiltinID == ARM::BI__builtin_arm_crc32d || 4448 BuiltinID == ARM::BI__builtin_arm_crc32cd) { 4449 Value *C1 = llvm::ConstantInt::get(Int64Ty, 32); 4450 Value *Arg1a = Builder.CreateTruncOrBitCast(Arg1, Int32Ty); 4451 Value *Arg1b = Builder.CreateLShr(Arg1, C1); 4452 Arg1b = Builder.CreateTruncOrBitCast(Arg1b, Int32Ty); 4453 4454 Function *F = CGM.getIntrinsic(CRCIntrinsicID); 4455 Value *Res = Builder.CreateCall(F, {Arg0, Arg1a}); 4456 return Builder.CreateCall(F, {Res, Arg1b}); 4457 } else { 4458 Arg1 = Builder.CreateZExtOrBitCast(Arg1, Int32Ty); 4459 4460 Function *F = CGM.getIntrinsic(CRCIntrinsicID); 4461 return Builder.CreateCall(F, {Arg0, Arg1}); 4462 } 4463 } 4464 4465 if (BuiltinID == ARM::BI__builtin_arm_rsr || 4466 BuiltinID == ARM::BI__builtin_arm_rsr64 || 4467 BuiltinID == ARM::BI__builtin_arm_rsrp || 4468 BuiltinID == ARM::BI__builtin_arm_wsr || 4469 BuiltinID == ARM::BI__builtin_arm_wsr64 || 4470 BuiltinID == ARM::BI__builtin_arm_wsrp) { 4471 4472 bool IsRead = BuiltinID == ARM::BI__builtin_arm_rsr || 4473 BuiltinID == ARM::BI__builtin_arm_rsr64 || 4474 BuiltinID == ARM::BI__builtin_arm_rsrp; 4475 4476 bool IsPointerBuiltin = BuiltinID == ARM::BI__builtin_arm_rsrp || 4477 BuiltinID == ARM::BI__builtin_arm_wsrp; 4478 4479 bool Is64Bit = BuiltinID == ARM::BI__builtin_arm_rsr64 || 4480 BuiltinID == ARM::BI__builtin_arm_wsr64; 4481 4482 llvm::Type *ValueType; 4483 llvm::Type *RegisterType; 4484 if (IsPointerBuiltin) { 4485 ValueType = VoidPtrTy; 4486 RegisterType = Int32Ty; 4487 } else if (Is64Bit) { 4488 ValueType = RegisterType = Int64Ty; 4489 } else { 4490 ValueType = RegisterType = Int32Ty; 4491 } 4492 4493 return EmitSpecialRegisterBuiltin(*this, E, RegisterType, ValueType, IsRead); 4494 } 4495 4496 // Find out if any arguments are required to be integer constant 4497 // expressions. 4498 unsigned ICEArguments = 0; 4499 ASTContext::GetBuiltinTypeError Error; 4500 getContext().GetBuiltinType(BuiltinID, Error, &ICEArguments); 4501 assert(Error == ASTContext::GE_None && "Should not codegen an error"); 4502 4503 auto getAlignmentValue32 = [&](Address addr) -> Value* { 4504 return Builder.getInt32(addr.getAlignment().getQuantity()); 4505 }; 4506 4507 Address PtrOp0 = Address::invalid(); 4508 Address PtrOp1 = Address::invalid(); 4509 SmallVector<Value*, 4> Ops; 4510 bool HasExtraArg = HasExtraNeonArgument(BuiltinID); 4511 unsigned NumArgs = E->getNumArgs() - (HasExtraArg ? 1 : 0); 4512 for (unsigned i = 0, e = NumArgs; i != e; i++) { 4513 if (i == 0) { 4514 switch (BuiltinID) { 4515 case NEON::BI__builtin_neon_vld1_v: 4516 case NEON::BI__builtin_neon_vld1q_v: 4517 case NEON::BI__builtin_neon_vld1q_lane_v: 4518 case NEON::BI__builtin_neon_vld1_lane_v: 4519 case NEON::BI__builtin_neon_vld1_dup_v: 4520 case NEON::BI__builtin_neon_vld1q_dup_v: 4521 case NEON::BI__builtin_neon_vst1_v: 4522 case NEON::BI__builtin_neon_vst1q_v: 4523 case NEON::BI__builtin_neon_vst1q_lane_v: 4524 case NEON::BI__builtin_neon_vst1_lane_v: 4525 case NEON::BI__builtin_neon_vst2_v: 4526 case NEON::BI__builtin_neon_vst2q_v: 4527 case NEON::BI__builtin_neon_vst2_lane_v: 4528 case NEON::BI__builtin_neon_vst2q_lane_v: 4529 case NEON::BI__builtin_neon_vst3_v: 4530 case NEON::BI__builtin_neon_vst3q_v: 4531 case NEON::BI__builtin_neon_vst3_lane_v: 4532 case NEON::BI__builtin_neon_vst3q_lane_v: 4533 case NEON::BI__builtin_neon_vst4_v: 4534 case NEON::BI__builtin_neon_vst4q_v: 4535 case NEON::BI__builtin_neon_vst4_lane_v: 4536 case NEON::BI__builtin_neon_vst4q_lane_v: 4537 // Get the alignment for the argument in addition to the value; 4538 // we'll use it later. 4539 PtrOp0 = EmitPointerWithAlignment(E->getArg(0)); 4540 Ops.push_back(PtrOp0.getPointer()); 4541 continue; 4542 } 4543 } 4544 if (i == 1) { 4545 switch (BuiltinID) { 4546 case NEON::BI__builtin_neon_vld2_v: 4547 case NEON::BI__builtin_neon_vld2q_v: 4548 case NEON::BI__builtin_neon_vld3_v: 4549 case NEON::BI__builtin_neon_vld3q_v: 4550 case NEON::BI__builtin_neon_vld4_v: 4551 case NEON::BI__builtin_neon_vld4q_v: 4552 case NEON::BI__builtin_neon_vld2_lane_v: 4553 case NEON::BI__builtin_neon_vld2q_lane_v: 4554 case NEON::BI__builtin_neon_vld3_lane_v: 4555 case NEON::BI__builtin_neon_vld3q_lane_v: 4556 case NEON::BI__builtin_neon_vld4_lane_v: 4557 case NEON::BI__builtin_neon_vld4q_lane_v: 4558 case NEON::BI__builtin_neon_vld2_dup_v: 4559 case NEON::BI__builtin_neon_vld3_dup_v: 4560 case NEON::BI__builtin_neon_vld4_dup_v: 4561 // Get the alignment for the argument in addition to the value; 4562 // we'll use it later. 4563 PtrOp1 = EmitPointerWithAlignment(E->getArg(1)); 4564 Ops.push_back(PtrOp1.getPointer()); 4565 continue; 4566 } 4567 } 4568 4569 if ((ICEArguments & (1 << i)) == 0) { 4570 Ops.push_back(EmitScalarExpr(E->getArg(i))); 4571 } else { 4572 // If this is required to be a constant, constant fold it so that we know 4573 // that the generated intrinsic gets a ConstantInt. 4574 llvm::APSInt Result; 4575 bool IsConst = E->getArg(i)->isIntegerConstantExpr(Result, getContext()); 4576 assert(IsConst && "Constant arg isn't actually constant?"); (void)IsConst; 4577 Ops.push_back(llvm::ConstantInt::get(getLLVMContext(), Result)); 4578 } 4579 } 4580 4581 switch (BuiltinID) { 4582 default: break; 4583 4584 case NEON::BI__builtin_neon_vget_lane_i8: 4585 case NEON::BI__builtin_neon_vget_lane_i16: 4586 case NEON::BI__builtin_neon_vget_lane_i32: 4587 case NEON::BI__builtin_neon_vget_lane_i64: 4588 case NEON::BI__builtin_neon_vget_lane_f32: 4589 case NEON::BI__builtin_neon_vgetq_lane_i8: 4590 case NEON::BI__builtin_neon_vgetq_lane_i16: 4591 case NEON::BI__builtin_neon_vgetq_lane_i32: 4592 case NEON::BI__builtin_neon_vgetq_lane_i64: 4593 case NEON::BI__builtin_neon_vgetq_lane_f32: 4594 return Builder.CreateExtractElement(Ops[0], Ops[1], "vget_lane"); 4595 4596 case NEON::BI__builtin_neon_vset_lane_i8: 4597 case NEON::BI__builtin_neon_vset_lane_i16: 4598 case NEON::BI__builtin_neon_vset_lane_i32: 4599 case NEON::BI__builtin_neon_vset_lane_i64: 4600 case NEON::BI__builtin_neon_vset_lane_f32: 4601 case NEON::BI__builtin_neon_vsetq_lane_i8: 4602 case NEON::BI__builtin_neon_vsetq_lane_i16: 4603 case NEON::BI__builtin_neon_vsetq_lane_i32: 4604 case NEON::BI__builtin_neon_vsetq_lane_i64: 4605 case NEON::BI__builtin_neon_vsetq_lane_f32: 4606 return Builder.CreateInsertElement(Ops[1], Ops[0], Ops[2], "vset_lane"); 4607 4608 case NEON::BI__builtin_neon_vsha1h_u32: 4609 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_sha1h), Ops, 4610 "vsha1h"); 4611 case NEON::BI__builtin_neon_vsha1cq_u32: 4612 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_sha1c), Ops, 4613 "vsha1h"); 4614 case NEON::BI__builtin_neon_vsha1pq_u32: 4615 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_sha1p), Ops, 4616 "vsha1h"); 4617 case NEON::BI__builtin_neon_vsha1mq_u32: 4618 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_sha1m), Ops, 4619 "vsha1h"); 4620 4621 // The ARM _MoveToCoprocessor builtins put the input register value as 4622 // the first argument, but the LLVM intrinsic expects it as the third one. 4623 case ARM::BI_MoveToCoprocessor: 4624 case ARM::BI_MoveToCoprocessor2: { 4625 Function *F = CGM.getIntrinsic(BuiltinID == ARM::BI_MoveToCoprocessor ? 4626 Intrinsic::arm_mcr : Intrinsic::arm_mcr2); 4627 return Builder.CreateCall(F, {Ops[1], Ops[2], Ops[0], 4628 Ops[3], Ops[4], Ops[5]}); 4629 } 4630 case ARM::BI_BitScanForward: 4631 case ARM::BI_BitScanForward64: 4632 return EmitMSVCBuiltinExpr(MSVCIntrin::_BitScanForward, E); 4633 case ARM::BI_BitScanReverse: 4634 case ARM::BI_BitScanReverse64: 4635 return EmitMSVCBuiltinExpr(MSVCIntrin::_BitScanReverse, E); 4636 } 4637 4638 // Get the last argument, which specifies the vector type. 4639 assert(HasExtraArg); 4640 llvm::APSInt Result; 4641 const Expr *Arg = E->getArg(E->getNumArgs()-1); 4642 if (!Arg->isIntegerConstantExpr(Result, getContext())) 4643 return nullptr; 4644 4645 if (BuiltinID == ARM::BI__builtin_arm_vcvtr_f || 4646 BuiltinID == ARM::BI__builtin_arm_vcvtr_d) { 4647 // Determine the overloaded type of this builtin. 4648 llvm::Type *Ty; 4649 if (BuiltinID == ARM::BI__builtin_arm_vcvtr_f) 4650 Ty = FloatTy; 4651 else 4652 Ty = DoubleTy; 4653 4654 // Determine whether this is an unsigned conversion or not. 4655 bool usgn = Result.getZExtValue() == 1; 4656 unsigned Int = usgn ? Intrinsic::arm_vcvtru : Intrinsic::arm_vcvtr; 4657 4658 // Call the appropriate intrinsic. 4659 Function *F = CGM.getIntrinsic(Int, Ty); 4660 return Builder.CreateCall(F, Ops, "vcvtr"); 4661 } 4662 4663 // Determine the type of this overloaded NEON intrinsic. 4664 NeonTypeFlags Type(Result.getZExtValue()); 4665 bool usgn = Type.isUnsigned(); 4666 bool rightShift = false; 4667 4668 llvm::VectorType *VTy = GetNeonType(this, Type); 4669 llvm::Type *Ty = VTy; 4670 if (!Ty) 4671 return nullptr; 4672 4673 // Many NEON builtins have identical semantics and uses in ARM and 4674 // AArch64. Emit these in a single function. 4675 auto IntrinsicMap = makeArrayRef(ARMSIMDIntrinsicMap); 4676 const NeonIntrinsicInfo *Builtin = findNeonIntrinsicInMap( 4677 IntrinsicMap, BuiltinID, NEONSIMDIntrinsicsProvenSorted); 4678 if (Builtin) 4679 return EmitCommonNeonBuiltinExpr( 4680 Builtin->BuiltinID, Builtin->LLVMIntrinsic, Builtin->AltLLVMIntrinsic, 4681 Builtin->NameHint, Builtin->TypeModifier, E, Ops, PtrOp0, PtrOp1); 4682 4683 unsigned Int; 4684 switch (BuiltinID) { 4685 default: return nullptr; 4686 case NEON::BI__builtin_neon_vld1q_lane_v: 4687 // Handle 64-bit integer elements as a special case. Use shuffles of 4688 // one-element vectors to avoid poor code for i64 in the backend. 4689 if (VTy->getElementType()->isIntegerTy(64)) { 4690 // Extract the other lane. 4691 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 4692 uint32_t Lane = cast<ConstantInt>(Ops[2])->getZExtValue(); 4693 Value *SV = llvm::ConstantVector::get(ConstantInt::get(Int32Ty, 1-Lane)); 4694 Ops[1] = Builder.CreateShuffleVector(Ops[1], Ops[1], SV); 4695 // Load the value as a one-element vector. 4696 Ty = llvm::VectorType::get(VTy->getElementType(), 1); 4697 llvm::Type *Tys[] = {Ty, Int8PtrTy}; 4698 Function *F = CGM.getIntrinsic(Intrinsic::arm_neon_vld1, Tys); 4699 Value *Align = getAlignmentValue32(PtrOp0); 4700 Value *Ld = Builder.CreateCall(F, {Ops[0], Align}); 4701 // Combine them. 4702 uint32_t Indices[] = {1 - Lane, Lane}; 4703 SV = llvm::ConstantDataVector::get(getLLVMContext(), Indices); 4704 return Builder.CreateShuffleVector(Ops[1], Ld, SV, "vld1q_lane"); 4705 } 4706 // fall through 4707 case NEON::BI__builtin_neon_vld1_lane_v: { 4708 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 4709 PtrOp0 = Builder.CreateElementBitCast(PtrOp0, VTy->getElementType()); 4710 Value *Ld = Builder.CreateLoad(PtrOp0); 4711 return Builder.CreateInsertElement(Ops[1], Ld, Ops[2], "vld1_lane"); 4712 } 4713 case NEON::BI__builtin_neon_vld2_dup_v: 4714 case NEON::BI__builtin_neon_vld3_dup_v: 4715 case NEON::BI__builtin_neon_vld4_dup_v: { 4716 // Handle 64-bit elements as a special-case. There is no "dup" needed. 4717 if (VTy->getElementType()->getPrimitiveSizeInBits() == 64) { 4718 switch (BuiltinID) { 4719 case NEON::BI__builtin_neon_vld2_dup_v: 4720 Int = Intrinsic::arm_neon_vld2; 4721 break; 4722 case NEON::BI__builtin_neon_vld3_dup_v: 4723 Int = Intrinsic::arm_neon_vld3; 4724 break; 4725 case NEON::BI__builtin_neon_vld4_dup_v: 4726 Int = Intrinsic::arm_neon_vld4; 4727 break; 4728 default: llvm_unreachable("unknown vld_dup intrinsic?"); 4729 } 4730 llvm::Type *Tys[] = {Ty, Int8PtrTy}; 4731 Function *F = CGM.getIntrinsic(Int, Tys); 4732 llvm::Value *Align = getAlignmentValue32(PtrOp1); 4733 Ops[1] = Builder.CreateCall(F, {Ops[1], Align}, "vld_dup"); 4734 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 4735 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 4736 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 4737 } 4738 switch (BuiltinID) { 4739 case NEON::BI__builtin_neon_vld2_dup_v: 4740 Int = Intrinsic::arm_neon_vld2lane; 4741 break; 4742 case NEON::BI__builtin_neon_vld3_dup_v: 4743 Int = Intrinsic::arm_neon_vld3lane; 4744 break; 4745 case NEON::BI__builtin_neon_vld4_dup_v: 4746 Int = Intrinsic::arm_neon_vld4lane; 4747 break; 4748 default: llvm_unreachable("unknown vld_dup intrinsic?"); 4749 } 4750 llvm::Type *Tys[] = {Ty, Int8PtrTy}; 4751 Function *F = CGM.getIntrinsic(Int, Tys); 4752 llvm::StructType *STy = cast<llvm::StructType>(F->getReturnType()); 4753 4754 SmallVector<Value*, 6> Args; 4755 Args.push_back(Ops[1]); 4756 Args.append(STy->getNumElements(), UndefValue::get(Ty)); 4757 4758 llvm::Constant *CI = ConstantInt::get(Int32Ty, 0); 4759 Args.push_back(CI); 4760 Args.push_back(getAlignmentValue32(PtrOp1)); 4761 4762 Ops[1] = Builder.CreateCall(F, Args, "vld_dup"); 4763 // splat lane 0 to all elts in each vector of the result. 4764 for (unsigned i = 0, e = STy->getNumElements(); i != e; ++i) { 4765 Value *Val = Builder.CreateExtractValue(Ops[1], i); 4766 Value *Elt = Builder.CreateBitCast(Val, Ty); 4767 Elt = EmitNeonSplat(Elt, CI); 4768 Elt = Builder.CreateBitCast(Elt, Val->getType()); 4769 Ops[1] = Builder.CreateInsertValue(Ops[1], Elt, i); 4770 } 4771 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 4772 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 4773 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 4774 } 4775 case NEON::BI__builtin_neon_vqrshrn_n_v: 4776 Int = 4777 usgn ? Intrinsic::arm_neon_vqrshiftnu : Intrinsic::arm_neon_vqrshiftns; 4778 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqrshrn_n", 4779 1, true); 4780 case NEON::BI__builtin_neon_vqrshrun_n_v: 4781 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vqrshiftnsu, Ty), 4782 Ops, "vqrshrun_n", 1, true); 4783 case NEON::BI__builtin_neon_vqshrn_n_v: 4784 Int = usgn ? Intrinsic::arm_neon_vqshiftnu : Intrinsic::arm_neon_vqshiftns; 4785 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqshrn_n", 4786 1, true); 4787 case NEON::BI__builtin_neon_vqshrun_n_v: 4788 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vqshiftnsu, Ty), 4789 Ops, "vqshrun_n", 1, true); 4790 case NEON::BI__builtin_neon_vrecpe_v: 4791 case NEON::BI__builtin_neon_vrecpeq_v: 4792 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vrecpe, Ty), 4793 Ops, "vrecpe"); 4794 case NEON::BI__builtin_neon_vrshrn_n_v: 4795 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vrshiftn, Ty), 4796 Ops, "vrshrn_n", 1, true); 4797 case NEON::BI__builtin_neon_vrsra_n_v: 4798 case NEON::BI__builtin_neon_vrsraq_n_v: 4799 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 4800 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 4801 Ops[2] = EmitNeonShiftVector(Ops[2], Ty, true); 4802 Int = usgn ? Intrinsic::arm_neon_vrshiftu : Intrinsic::arm_neon_vrshifts; 4803 Ops[1] = Builder.CreateCall(CGM.getIntrinsic(Int, Ty), {Ops[1], Ops[2]}); 4804 return Builder.CreateAdd(Ops[0], Ops[1], "vrsra_n"); 4805 case NEON::BI__builtin_neon_vsri_n_v: 4806 case NEON::BI__builtin_neon_vsriq_n_v: 4807 rightShift = true; 4808 case NEON::BI__builtin_neon_vsli_n_v: 4809 case NEON::BI__builtin_neon_vsliq_n_v: 4810 Ops[2] = EmitNeonShiftVector(Ops[2], Ty, rightShift); 4811 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vshiftins, Ty), 4812 Ops, "vsli_n"); 4813 case NEON::BI__builtin_neon_vsra_n_v: 4814 case NEON::BI__builtin_neon_vsraq_n_v: 4815 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 4816 Ops[1] = EmitNeonRShiftImm(Ops[1], Ops[2], Ty, usgn, "vsra_n"); 4817 return Builder.CreateAdd(Ops[0], Ops[1]); 4818 case NEON::BI__builtin_neon_vst1q_lane_v: 4819 // Handle 64-bit integer elements as a special case. Use a shuffle to get 4820 // a one-element vector and avoid poor code for i64 in the backend. 4821 if (VTy->getElementType()->isIntegerTy(64)) { 4822 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 4823 Value *SV = llvm::ConstantVector::get(cast<llvm::Constant>(Ops[2])); 4824 Ops[1] = Builder.CreateShuffleVector(Ops[1], Ops[1], SV); 4825 Ops[2] = getAlignmentValue32(PtrOp0); 4826 llvm::Type *Tys[] = {Int8PtrTy, Ops[1]->getType()}; 4827 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::arm_neon_vst1, 4828 Tys), Ops); 4829 } 4830 // fall through 4831 case NEON::BI__builtin_neon_vst1_lane_v: { 4832 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 4833 Ops[1] = Builder.CreateExtractElement(Ops[1], Ops[2]); 4834 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 4835 auto St = Builder.CreateStore(Ops[1], Builder.CreateBitCast(PtrOp0, Ty)); 4836 return St; 4837 } 4838 case NEON::BI__builtin_neon_vtbl1_v: 4839 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbl1), 4840 Ops, "vtbl1"); 4841 case NEON::BI__builtin_neon_vtbl2_v: 4842 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbl2), 4843 Ops, "vtbl2"); 4844 case NEON::BI__builtin_neon_vtbl3_v: 4845 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbl3), 4846 Ops, "vtbl3"); 4847 case NEON::BI__builtin_neon_vtbl4_v: 4848 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbl4), 4849 Ops, "vtbl4"); 4850 case NEON::BI__builtin_neon_vtbx1_v: 4851 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbx1), 4852 Ops, "vtbx1"); 4853 case NEON::BI__builtin_neon_vtbx2_v: 4854 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbx2), 4855 Ops, "vtbx2"); 4856 case NEON::BI__builtin_neon_vtbx3_v: 4857 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbx3), 4858 Ops, "vtbx3"); 4859 case NEON::BI__builtin_neon_vtbx4_v: 4860 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::arm_neon_vtbx4), 4861 Ops, "vtbx4"); 4862 } 4863 } 4864 4865 static Value *EmitAArch64TblBuiltinExpr(CodeGenFunction &CGF, unsigned BuiltinID, 4866 const CallExpr *E, 4867 SmallVectorImpl<Value *> &Ops) { 4868 unsigned int Int = 0; 4869 const char *s = nullptr; 4870 4871 switch (BuiltinID) { 4872 default: 4873 return nullptr; 4874 case NEON::BI__builtin_neon_vtbl1_v: 4875 case NEON::BI__builtin_neon_vqtbl1_v: 4876 case NEON::BI__builtin_neon_vqtbl1q_v: 4877 case NEON::BI__builtin_neon_vtbl2_v: 4878 case NEON::BI__builtin_neon_vqtbl2_v: 4879 case NEON::BI__builtin_neon_vqtbl2q_v: 4880 case NEON::BI__builtin_neon_vtbl3_v: 4881 case NEON::BI__builtin_neon_vqtbl3_v: 4882 case NEON::BI__builtin_neon_vqtbl3q_v: 4883 case NEON::BI__builtin_neon_vtbl4_v: 4884 case NEON::BI__builtin_neon_vqtbl4_v: 4885 case NEON::BI__builtin_neon_vqtbl4q_v: 4886 break; 4887 case NEON::BI__builtin_neon_vtbx1_v: 4888 case NEON::BI__builtin_neon_vqtbx1_v: 4889 case NEON::BI__builtin_neon_vqtbx1q_v: 4890 case NEON::BI__builtin_neon_vtbx2_v: 4891 case NEON::BI__builtin_neon_vqtbx2_v: 4892 case NEON::BI__builtin_neon_vqtbx2q_v: 4893 case NEON::BI__builtin_neon_vtbx3_v: 4894 case NEON::BI__builtin_neon_vqtbx3_v: 4895 case NEON::BI__builtin_neon_vqtbx3q_v: 4896 case NEON::BI__builtin_neon_vtbx4_v: 4897 case NEON::BI__builtin_neon_vqtbx4_v: 4898 case NEON::BI__builtin_neon_vqtbx4q_v: 4899 break; 4900 } 4901 4902 assert(E->getNumArgs() >= 3); 4903 4904 // Get the last argument, which specifies the vector type. 4905 llvm::APSInt Result; 4906 const Expr *Arg = E->getArg(E->getNumArgs() - 1); 4907 if (!Arg->isIntegerConstantExpr(Result, CGF.getContext())) 4908 return nullptr; 4909 4910 // Determine the type of this overloaded NEON intrinsic. 4911 NeonTypeFlags Type(Result.getZExtValue()); 4912 llvm::VectorType *Ty = GetNeonType(&CGF, Type); 4913 if (!Ty) 4914 return nullptr; 4915 4916 CodeGen::CGBuilderTy &Builder = CGF.Builder; 4917 4918 // AArch64 scalar builtins are not overloaded, they do not have an extra 4919 // argument that specifies the vector type, need to handle each case. 4920 switch (BuiltinID) { 4921 case NEON::BI__builtin_neon_vtbl1_v: { 4922 return packTBLDVectorList(CGF, makeArrayRef(Ops).slice(0, 1), nullptr, 4923 Ops[1], Ty, Intrinsic::aarch64_neon_tbl1, 4924 "vtbl1"); 4925 } 4926 case NEON::BI__builtin_neon_vtbl2_v: { 4927 return packTBLDVectorList(CGF, makeArrayRef(Ops).slice(0, 2), nullptr, 4928 Ops[2], Ty, Intrinsic::aarch64_neon_tbl1, 4929 "vtbl1"); 4930 } 4931 case NEON::BI__builtin_neon_vtbl3_v: { 4932 return packTBLDVectorList(CGF, makeArrayRef(Ops).slice(0, 3), nullptr, 4933 Ops[3], Ty, Intrinsic::aarch64_neon_tbl2, 4934 "vtbl2"); 4935 } 4936 case NEON::BI__builtin_neon_vtbl4_v: { 4937 return packTBLDVectorList(CGF, makeArrayRef(Ops).slice(0, 4), nullptr, 4938 Ops[4], Ty, Intrinsic::aarch64_neon_tbl2, 4939 "vtbl2"); 4940 } 4941 case NEON::BI__builtin_neon_vtbx1_v: { 4942 Value *TblRes = 4943 packTBLDVectorList(CGF, makeArrayRef(Ops).slice(1, 1), nullptr, Ops[2], 4944 Ty, Intrinsic::aarch64_neon_tbl1, "vtbl1"); 4945 4946 llvm::Constant *EightV = ConstantInt::get(Ty, 8); 4947 Value *CmpRes = Builder.CreateICmp(ICmpInst::ICMP_UGE, Ops[2], EightV); 4948 CmpRes = Builder.CreateSExt(CmpRes, Ty); 4949 4950 Value *EltsFromInput = Builder.CreateAnd(CmpRes, Ops[0]); 4951 Value *EltsFromTbl = Builder.CreateAnd(Builder.CreateNot(CmpRes), TblRes); 4952 return Builder.CreateOr(EltsFromInput, EltsFromTbl, "vtbx"); 4953 } 4954 case NEON::BI__builtin_neon_vtbx2_v: { 4955 return packTBLDVectorList(CGF, makeArrayRef(Ops).slice(1, 2), Ops[0], 4956 Ops[3], Ty, Intrinsic::aarch64_neon_tbx1, 4957 "vtbx1"); 4958 } 4959 case NEON::BI__builtin_neon_vtbx3_v: { 4960 Value *TblRes = 4961 packTBLDVectorList(CGF, makeArrayRef(Ops).slice(1, 3), nullptr, Ops[4], 4962 Ty, Intrinsic::aarch64_neon_tbl2, "vtbl2"); 4963 4964 llvm::Constant *TwentyFourV = ConstantInt::get(Ty, 24); 4965 Value *CmpRes = Builder.CreateICmp(ICmpInst::ICMP_UGE, Ops[4], 4966 TwentyFourV); 4967 CmpRes = Builder.CreateSExt(CmpRes, Ty); 4968 4969 Value *EltsFromInput = Builder.CreateAnd(CmpRes, Ops[0]); 4970 Value *EltsFromTbl = Builder.CreateAnd(Builder.CreateNot(CmpRes), TblRes); 4971 return Builder.CreateOr(EltsFromInput, EltsFromTbl, "vtbx"); 4972 } 4973 case NEON::BI__builtin_neon_vtbx4_v: { 4974 return packTBLDVectorList(CGF, makeArrayRef(Ops).slice(1, 4), Ops[0], 4975 Ops[5], Ty, Intrinsic::aarch64_neon_tbx2, 4976 "vtbx2"); 4977 } 4978 case NEON::BI__builtin_neon_vqtbl1_v: 4979 case NEON::BI__builtin_neon_vqtbl1q_v: 4980 Int = Intrinsic::aarch64_neon_tbl1; s = "vtbl1"; break; 4981 case NEON::BI__builtin_neon_vqtbl2_v: 4982 case NEON::BI__builtin_neon_vqtbl2q_v: { 4983 Int = Intrinsic::aarch64_neon_tbl2; s = "vtbl2"; break; 4984 case NEON::BI__builtin_neon_vqtbl3_v: 4985 case NEON::BI__builtin_neon_vqtbl3q_v: 4986 Int = Intrinsic::aarch64_neon_tbl3; s = "vtbl3"; break; 4987 case NEON::BI__builtin_neon_vqtbl4_v: 4988 case NEON::BI__builtin_neon_vqtbl4q_v: 4989 Int = Intrinsic::aarch64_neon_tbl4; s = "vtbl4"; break; 4990 case NEON::BI__builtin_neon_vqtbx1_v: 4991 case NEON::BI__builtin_neon_vqtbx1q_v: 4992 Int = Intrinsic::aarch64_neon_tbx1; s = "vtbx1"; break; 4993 case NEON::BI__builtin_neon_vqtbx2_v: 4994 case NEON::BI__builtin_neon_vqtbx2q_v: 4995 Int = Intrinsic::aarch64_neon_tbx2; s = "vtbx2"; break; 4996 case NEON::BI__builtin_neon_vqtbx3_v: 4997 case NEON::BI__builtin_neon_vqtbx3q_v: 4998 Int = Intrinsic::aarch64_neon_tbx3; s = "vtbx3"; break; 4999 case NEON::BI__builtin_neon_vqtbx4_v: 5000 case NEON::BI__builtin_neon_vqtbx4q_v: 5001 Int = Intrinsic::aarch64_neon_tbx4; s = "vtbx4"; break; 5002 } 5003 } 5004 5005 if (!Int) 5006 return nullptr; 5007 5008 Function *F = CGF.CGM.getIntrinsic(Int, Ty); 5009 return CGF.EmitNeonCall(F, Ops, s); 5010 } 5011 5012 Value *CodeGenFunction::vectorWrapScalar16(Value *Op) { 5013 llvm::Type *VTy = llvm::VectorType::get(Int16Ty, 4); 5014 Op = Builder.CreateBitCast(Op, Int16Ty); 5015 Value *V = UndefValue::get(VTy); 5016 llvm::Constant *CI = ConstantInt::get(SizeTy, 0); 5017 Op = Builder.CreateInsertElement(V, Op, CI); 5018 return Op; 5019 } 5020 5021 Value *CodeGenFunction::EmitAArch64BuiltinExpr(unsigned BuiltinID, 5022 const CallExpr *E) { 5023 unsigned HintID = static_cast<unsigned>(-1); 5024 switch (BuiltinID) { 5025 default: break; 5026 case AArch64::BI__builtin_arm_nop: 5027 HintID = 0; 5028 break; 5029 case AArch64::BI__builtin_arm_yield: 5030 HintID = 1; 5031 break; 5032 case AArch64::BI__builtin_arm_wfe: 5033 HintID = 2; 5034 break; 5035 case AArch64::BI__builtin_arm_wfi: 5036 HintID = 3; 5037 break; 5038 case AArch64::BI__builtin_arm_sev: 5039 HintID = 4; 5040 break; 5041 case AArch64::BI__builtin_arm_sevl: 5042 HintID = 5; 5043 break; 5044 } 5045 5046 if (HintID != static_cast<unsigned>(-1)) { 5047 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_hint); 5048 return Builder.CreateCall(F, llvm::ConstantInt::get(Int32Ty, HintID)); 5049 } 5050 5051 if (BuiltinID == AArch64::BI__builtin_arm_prefetch) { 5052 Value *Address = EmitScalarExpr(E->getArg(0)); 5053 Value *RW = EmitScalarExpr(E->getArg(1)); 5054 Value *CacheLevel = EmitScalarExpr(E->getArg(2)); 5055 Value *RetentionPolicy = EmitScalarExpr(E->getArg(3)); 5056 Value *IsData = EmitScalarExpr(E->getArg(4)); 5057 5058 Value *Locality = nullptr; 5059 if (cast<llvm::ConstantInt>(RetentionPolicy)->isZero()) { 5060 // Temporal fetch, needs to convert cache level to locality. 5061 Locality = llvm::ConstantInt::get(Int32Ty, 5062 -cast<llvm::ConstantInt>(CacheLevel)->getValue() + 3); 5063 } else { 5064 // Streaming fetch. 5065 Locality = llvm::ConstantInt::get(Int32Ty, 0); 5066 } 5067 5068 // FIXME: We need AArch64 specific LLVM intrinsic if we want to specify 5069 // PLDL3STRM or PLDL2STRM. 5070 Value *F = CGM.getIntrinsic(Intrinsic::prefetch); 5071 return Builder.CreateCall(F, {Address, RW, Locality, IsData}); 5072 } 5073 5074 if (BuiltinID == AArch64::BI__builtin_arm_rbit) { 5075 assert((getContext().getTypeSize(E->getType()) == 32) && 5076 "rbit of unusual size!"); 5077 llvm::Value *Arg = EmitScalarExpr(E->getArg(0)); 5078 return Builder.CreateCall( 5079 CGM.getIntrinsic(Intrinsic::aarch64_rbit, Arg->getType()), Arg, "rbit"); 5080 } 5081 if (BuiltinID == AArch64::BI__builtin_arm_rbit64) { 5082 assert((getContext().getTypeSize(E->getType()) == 64) && 5083 "rbit of unusual size!"); 5084 llvm::Value *Arg = EmitScalarExpr(E->getArg(0)); 5085 return Builder.CreateCall( 5086 CGM.getIntrinsic(Intrinsic::aarch64_rbit, Arg->getType()), Arg, "rbit"); 5087 } 5088 5089 if (BuiltinID == AArch64::BI__clear_cache) { 5090 assert(E->getNumArgs() == 2 && "__clear_cache takes 2 arguments"); 5091 const FunctionDecl *FD = E->getDirectCallee(); 5092 Value *Ops[2]; 5093 for (unsigned i = 0; i < 2; i++) 5094 Ops[i] = EmitScalarExpr(E->getArg(i)); 5095 llvm::Type *Ty = CGM.getTypes().ConvertType(FD->getType()); 5096 llvm::FunctionType *FTy = cast<llvm::FunctionType>(Ty); 5097 StringRef Name = FD->getName(); 5098 return EmitNounwindRuntimeCall(CGM.CreateRuntimeFunction(FTy, Name), Ops); 5099 } 5100 5101 if ((BuiltinID == AArch64::BI__builtin_arm_ldrex || 5102 BuiltinID == AArch64::BI__builtin_arm_ldaex) && 5103 getContext().getTypeSize(E->getType()) == 128) { 5104 Function *F = CGM.getIntrinsic(BuiltinID == AArch64::BI__builtin_arm_ldaex 5105 ? Intrinsic::aarch64_ldaxp 5106 : Intrinsic::aarch64_ldxp); 5107 5108 Value *LdPtr = EmitScalarExpr(E->getArg(0)); 5109 Value *Val = Builder.CreateCall(F, Builder.CreateBitCast(LdPtr, Int8PtrTy), 5110 "ldxp"); 5111 5112 Value *Val0 = Builder.CreateExtractValue(Val, 1); 5113 Value *Val1 = Builder.CreateExtractValue(Val, 0); 5114 llvm::Type *Int128Ty = llvm::IntegerType::get(getLLVMContext(), 128); 5115 Val0 = Builder.CreateZExt(Val0, Int128Ty); 5116 Val1 = Builder.CreateZExt(Val1, Int128Ty); 5117 5118 Value *ShiftCst = llvm::ConstantInt::get(Int128Ty, 64); 5119 Val = Builder.CreateShl(Val0, ShiftCst, "shl", true /* nuw */); 5120 Val = Builder.CreateOr(Val, Val1); 5121 return Builder.CreateBitCast(Val, ConvertType(E->getType())); 5122 } else if (BuiltinID == AArch64::BI__builtin_arm_ldrex || 5123 BuiltinID == AArch64::BI__builtin_arm_ldaex) { 5124 Value *LoadAddr = EmitScalarExpr(E->getArg(0)); 5125 5126 QualType Ty = E->getType(); 5127 llvm::Type *RealResTy = ConvertType(Ty); 5128 llvm::Type *IntResTy = llvm::IntegerType::get(getLLVMContext(), 5129 getContext().getTypeSize(Ty)); 5130 LoadAddr = Builder.CreateBitCast(LoadAddr, IntResTy->getPointerTo()); 5131 5132 Function *F = CGM.getIntrinsic(BuiltinID == AArch64::BI__builtin_arm_ldaex 5133 ? Intrinsic::aarch64_ldaxr 5134 : Intrinsic::aarch64_ldxr, 5135 LoadAddr->getType()); 5136 Value *Val = Builder.CreateCall(F, LoadAddr, "ldxr"); 5137 5138 if (RealResTy->isPointerTy()) 5139 return Builder.CreateIntToPtr(Val, RealResTy); 5140 5141 Val = Builder.CreateTruncOrBitCast(Val, IntResTy); 5142 return Builder.CreateBitCast(Val, RealResTy); 5143 } 5144 5145 if ((BuiltinID == AArch64::BI__builtin_arm_strex || 5146 BuiltinID == AArch64::BI__builtin_arm_stlex) && 5147 getContext().getTypeSize(E->getArg(0)->getType()) == 128) { 5148 Function *F = CGM.getIntrinsic(BuiltinID == AArch64::BI__builtin_arm_stlex 5149 ? Intrinsic::aarch64_stlxp 5150 : Intrinsic::aarch64_stxp); 5151 llvm::Type *STy = llvm::StructType::get(Int64Ty, Int64Ty, nullptr); 5152 5153 Address Tmp = CreateMemTemp(E->getArg(0)->getType()); 5154 EmitAnyExprToMem(E->getArg(0), Tmp, Qualifiers(), /*init*/ true); 5155 5156 Tmp = Builder.CreateBitCast(Tmp, llvm::PointerType::getUnqual(STy)); 5157 llvm::Value *Val = Builder.CreateLoad(Tmp); 5158 5159 Value *Arg0 = Builder.CreateExtractValue(Val, 0); 5160 Value *Arg1 = Builder.CreateExtractValue(Val, 1); 5161 Value *StPtr = Builder.CreateBitCast(EmitScalarExpr(E->getArg(1)), 5162 Int8PtrTy); 5163 return Builder.CreateCall(F, {Arg0, Arg1, StPtr}, "stxp"); 5164 } 5165 5166 if (BuiltinID == AArch64::BI__builtin_arm_strex || 5167 BuiltinID == AArch64::BI__builtin_arm_stlex) { 5168 Value *StoreVal = EmitScalarExpr(E->getArg(0)); 5169 Value *StoreAddr = EmitScalarExpr(E->getArg(1)); 5170 5171 QualType Ty = E->getArg(0)->getType(); 5172 llvm::Type *StoreTy = llvm::IntegerType::get(getLLVMContext(), 5173 getContext().getTypeSize(Ty)); 5174 StoreAddr = Builder.CreateBitCast(StoreAddr, StoreTy->getPointerTo()); 5175 5176 if (StoreVal->getType()->isPointerTy()) 5177 StoreVal = Builder.CreatePtrToInt(StoreVal, Int64Ty); 5178 else { 5179 StoreVal = Builder.CreateBitCast(StoreVal, StoreTy); 5180 StoreVal = Builder.CreateZExtOrBitCast(StoreVal, Int64Ty); 5181 } 5182 5183 Function *F = CGM.getIntrinsic(BuiltinID == AArch64::BI__builtin_arm_stlex 5184 ? Intrinsic::aarch64_stlxr 5185 : Intrinsic::aarch64_stxr, 5186 StoreAddr->getType()); 5187 return Builder.CreateCall(F, {StoreVal, StoreAddr}, "stxr"); 5188 } 5189 5190 if (BuiltinID == AArch64::BI__builtin_arm_clrex) { 5191 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_clrex); 5192 return Builder.CreateCall(F); 5193 } 5194 5195 // CRC32 5196 Intrinsic::ID CRCIntrinsicID = Intrinsic::not_intrinsic; 5197 switch (BuiltinID) { 5198 case AArch64::BI__builtin_arm_crc32b: 5199 CRCIntrinsicID = Intrinsic::aarch64_crc32b; break; 5200 case AArch64::BI__builtin_arm_crc32cb: 5201 CRCIntrinsicID = Intrinsic::aarch64_crc32cb; break; 5202 case AArch64::BI__builtin_arm_crc32h: 5203 CRCIntrinsicID = Intrinsic::aarch64_crc32h; break; 5204 case AArch64::BI__builtin_arm_crc32ch: 5205 CRCIntrinsicID = Intrinsic::aarch64_crc32ch; break; 5206 case AArch64::BI__builtin_arm_crc32w: 5207 CRCIntrinsicID = Intrinsic::aarch64_crc32w; break; 5208 case AArch64::BI__builtin_arm_crc32cw: 5209 CRCIntrinsicID = Intrinsic::aarch64_crc32cw; break; 5210 case AArch64::BI__builtin_arm_crc32d: 5211 CRCIntrinsicID = Intrinsic::aarch64_crc32x; break; 5212 case AArch64::BI__builtin_arm_crc32cd: 5213 CRCIntrinsicID = Intrinsic::aarch64_crc32cx; break; 5214 } 5215 5216 if (CRCIntrinsicID != Intrinsic::not_intrinsic) { 5217 Value *Arg0 = EmitScalarExpr(E->getArg(0)); 5218 Value *Arg1 = EmitScalarExpr(E->getArg(1)); 5219 Function *F = CGM.getIntrinsic(CRCIntrinsicID); 5220 5221 llvm::Type *DataTy = F->getFunctionType()->getParamType(1); 5222 Arg1 = Builder.CreateZExtOrBitCast(Arg1, DataTy); 5223 5224 return Builder.CreateCall(F, {Arg0, Arg1}); 5225 } 5226 5227 if (BuiltinID == AArch64::BI__builtin_arm_rsr || 5228 BuiltinID == AArch64::BI__builtin_arm_rsr64 || 5229 BuiltinID == AArch64::BI__builtin_arm_rsrp || 5230 BuiltinID == AArch64::BI__builtin_arm_wsr || 5231 BuiltinID == AArch64::BI__builtin_arm_wsr64 || 5232 BuiltinID == AArch64::BI__builtin_arm_wsrp) { 5233 5234 bool IsRead = BuiltinID == AArch64::BI__builtin_arm_rsr || 5235 BuiltinID == AArch64::BI__builtin_arm_rsr64 || 5236 BuiltinID == AArch64::BI__builtin_arm_rsrp; 5237 5238 bool IsPointerBuiltin = BuiltinID == AArch64::BI__builtin_arm_rsrp || 5239 BuiltinID == AArch64::BI__builtin_arm_wsrp; 5240 5241 bool Is64Bit = BuiltinID != AArch64::BI__builtin_arm_rsr && 5242 BuiltinID != AArch64::BI__builtin_arm_wsr; 5243 5244 llvm::Type *ValueType; 5245 llvm::Type *RegisterType = Int64Ty; 5246 if (IsPointerBuiltin) { 5247 ValueType = VoidPtrTy; 5248 } else if (Is64Bit) { 5249 ValueType = Int64Ty; 5250 } else { 5251 ValueType = Int32Ty; 5252 } 5253 5254 return EmitSpecialRegisterBuiltin(*this, E, RegisterType, ValueType, IsRead); 5255 } 5256 5257 // Find out if any arguments are required to be integer constant 5258 // expressions. 5259 unsigned ICEArguments = 0; 5260 ASTContext::GetBuiltinTypeError Error; 5261 getContext().GetBuiltinType(BuiltinID, Error, &ICEArguments); 5262 assert(Error == ASTContext::GE_None && "Should not codegen an error"); 5263 5264 llvm::SmallVector<Value*, 4> Ops; 5265 for (unsigned i = 0, e = E->getNumArgs() - 1; i != e; i++) { 5266 if ((ICEArguments & (1 << i)) == 0) { 5267 Ops.push_back(EmitScalarExpr(E->getArg(i))); 5268 } else { 5269 // If this is required to be a constant, constant fold it so that we know 5270 // that the generated intrinsic gets a ConstantInt. 5271 llvm::APSInt Result; 5272 bool IsConst = E->getArg(i)->isIntegerConstantExpr(Result, getContext()); 5273 assert(IsConst && "Constant arg isn't actually constant?"); 5274 (void)IsConst; 5275 Ops.push_back(llvm::ConstantInt::get(getLLVMContext(), Result)); 5276 } 5277 } 5278 5279 auto SISDMap = makeArrayRef(AArch64SISDIntrinsicMap); 5280 const NeonIntrinsicInfo *Builtin = findNeonIntrinsicInMap( 5281 SISDMap, BuiltinID, AArch64SISDIntrinsicsProvenSorted); 5282 5283 if (Builtin) { 5284 Ops.push_back(EmitScalarExpr(E->getArg(E->getNumArgs() - 1))); 5285 Value *Result = EmitCommonNeonSISDBuiltinExpr(*this, *Builtin, Ops, E); 5286 assert(Result && "SISD intrinsic should have been handled"); 5287 return Result; 5288 } 5289 5290 llvm::APSInt Result; 5291 const Expr *Arg = E->getArg(E->getNumArgs()-1); 5292 NeonTypeFlags Type(0); 5293 if (Arg->isIntegerConstantExpr(Result, getContext())) 5294 // Determine the type of this overloaded NEON intrinsic. 5295 Type = NeonTypeFlags(Result.getZExtValue()); 5296 5297 bool usgn = Type.isUnsigned(); 5298 bool quad = Type.isQuad(); 5299 5300 // Handle non-overloaded intrinsics first. 5301 switch (BuiltinID) { 5302 default: break; 5303 case NEON::BI__builtin_neon_vldrq_p128: { 5304 llvm::Type *Int128PTy = llvm::Type::getIntNPtrTy(getLLVMContext(), 128); 5305 Value *Ptr = Builder.CreateBitCast(EmitScalarExpr(E->getArg(0)), Int128PTy); 5306 return Builder.CreateDefaultAlignedLoad(Ptr); 5307 } 5308 case NEON::BI__builtin_neon_vstrq_p128: { 5309 llvm::Type *Int128PTy = llvm::Type::getIntNPtrTy(getLLVMContext(), 128); 5310 Value *Ptr = Builder.CreateBitCast(Ops[0], Int128PTy); 5311 return Builder.CreateDefaultAlignedStore(EmitScalarExpr(E->getArg(1)), Ptr); 5312 } 5313 case NEON::BI__builtin_neon_vcvts_u32_f32: 5314 case NEON::BI__builtin_neon_vcvtd_u64_f64: 5315 usgn = true; 5316 // FALL THROUGH 5317 case NEON::BI__builtin_neon_vcvts_s32_f32: 5318 case NEON::BI__builtin_neon_vcvtd_s64_f64: { 5319 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5320 bool Is64 = Ops[0]->getType()->getPrimitiveSizeInBits() == 64; 5321 llvm::Type *InTy = Is64 ? Int64Ty : Int32Ty; 5322 llvm::Type *FTy = Is64 ? DoubleTy : FloatTy; 5323 Ops[0] = Builder.CreateBitCast(Ops[0], FTy); 5324 if (usgn) 5325 return Builder.CreateFPToUI(Ops[0], InTy); 5326 return Builder.CreateFPToSI(Ops[0], InTy); 5327 } 5328 case NEON::BI__builtin_neon_vcvts_f32_u32: 5329 case NEON::BI__builtin_neon_vcvtd_f64_u64: 5330 usgn = true; 5331 // FALL THROUGH 5332 case NEON::BI__builtin_neon_vcvts_f32_s32: 5333 case NEON::BI__builtin_neon_vcvtd_f64_s64: { 5334 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5335 bool Is64 = Ops[0]->getType()->getPrimitiveSizeInBits() == 64; 5336 llvm::Type *InTy = Is64 ? Int64Ty : Int32Ty; 5337 llvm::Type *FTy = Is64 ? DoubleTy : FloatTy; 5338 Ops[0] = Builder.CreateBitCast(Ops[0], InTy); 5339 if (usgn) 5340 return Builder.CreateUIToFP(Ops[0], FTy); 5341 return Builder.CreateSIToFP(Ops[0], FTy); 5342 } 5343 case NEON::BI__builtin_neon_vpaddd_s64: { 5344 llvm::Type *Ty = llvm::VectorType::get(Int64Ty, 2); 5345 Value *Vec = EmitScalarExpr(E->getArg(0)); 5346 // The vector is v2f64, so make sure it's bitcast to that. 5347 Vec = Builder.CreateBitCast(Vec, Ty, "v2i64"); 5348 llvm::Value *Idx0 = llvm::ConstantInt::get(SizeTy, 0); 5349 llvm::Value *Idx1 = llvm::ConstantInt::get(SizeTy, 1); 5350 Value *Op0 = Builder.CreateExtractElement(Vec, Idx0, "lane0"); 5351 Value *Op1 = Builder.CreateExtractElement(Vec, Idx1, "lane1"); 5352 // Pairwise addition of a v2f64 into a scalar f64. 5353 return Builder.CreateAdd(Op0, Op1, "vpaddd"); 5354 } 5355 case NEON::BI__builtin_neon_vpaddd_f64: { 5356 llvm::Type *Ty = 5357 llvm::VectorType::get(DoubleTy, 2); 5358 Value *Vec = EmitScalarExpr(E->getArg(0)); 5359 // The vector is v2f64, so make sure it's bitcast to that. 5360 Vec = Builder.CreateBitCast(Vec, Ty, "v2f64"); 5361 llvm::Value *Idx0 = llvm::ConstantInt::get(SizeTy, 0); 5362 llvm::Value *Idx1 = llvm::ConstantInt::get(SizeTy, 1); 5363 Value *Op0 = Builder.CreateExtractElement(Vec, Idx0, "lane0"); 5364 Value *Op1 = Builder.CreateExtractElement(Vec, Idx1, "lane1"); 5365 // Pairwise addition of a v2f64 into a scalar f64. 5366 return Builder.CreateFAdd(Op0, Op1, "vpaddd"); 5367 } 5368 case NEON::BI__builtin_neon_vpadds_f32: { 5369 llvm::Type *Ty = 5370 llvm::VectorType::get(FloatTy, 2); 5371 Value *Vec = EmitScalarExpr(E->getArg(0)); 5372 // The vector is v2f32, so make sure it's bitcast to that. 5373 Vec = Builder.CreateBitCast(Vec, Ty, "v2f32"); 5374 llvm::Value *Idx0 = llvm::ConstantInt::get(SizeTy, 0); 5375 llvm::Value *Idx1 = llvm::ConstantInt::get(SizeTy, 1); 5376 Value *Op0 = Builder.CreateExtractElement(Vec, Idx0, "lane0"); 5377 Value *Op1 = Builder.CreateExtractElement(Vec, Idx1, "lane1"); 5378 // Pairwise addition of a v2f32 into a scalar f32. 5379 return Builder.CreateFAdd(Op0, Op1, "vpaddd"); 5380 } 5381 case NEON::BI__builtin_neon_vceqzd_s64: 5382 case NEON::BI__builtin_neon_vceqzd_f64: 5383 case NEON::BI__builtin_neon_vceqzs_f32: 5384 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5385 return EmitAArch64CompareBuiltinExpr( 5386 Ops[0], ConvertType(E->getCallReturnType(getContext())), 5387 ICmpInst::FCMP_OEQ, ICmpInst::ICMP_EQ, "vceqz"); 5388 case NEON::BI__builtin_neon_vcgezd_s64: 5389 case NEON::BI__builtin_neon_vcgezd_f64: 5390 case NEON::BI__builtin_neon_vcgezs_f32: 5391 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5392 return EmitAArch64CompareBuiltinExpr( 5393 Ops[0], ConvertType(E->getCallReturnType(getContext())), 5394 ICmpInst::FCMP_OGE, ICmpInst::ICMP_SGE, "vcgez"); 5395 case NEON::BI__builtin_neon_vclezd_s64: 5396 case NEON::BI__builtin_neon_vclezd_f64: 5397 case NEON::BI__builtin_neon_vclezs_f32: 5398 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5399 return EmitAArch64CompareBuiltinExpr( 5400 Ops[0], ConvertType(E->getCallReturnType(getContext())), 5401 ICmpInst::FCMP_OLE, ICmpInst::ICMP_SLE, "vclez"); 5402 case NEON::BI__builtin_neon_vcgtzd_s64: 5403 case NEON::BI__builtin_neon_vcgtzd_f64: 5404 case NEON::BI__builtin_neon_vcgtzs_f32: 5405 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5406 return EmitAArch64CompareBuiltinExpr( 5407 Ops[0], ConvertType(E->getCallReturnType(getContext())), 5408 ICmpInst::FCMP_OGT, ICmpInst::ICMP_SGT, "vcgtz"); 5409 case NEON::BI__builtin_neon_vcltzd_s64: 5410 case NEON::BI__builtin_neon_vcltzd_f64: 5411 case NEON::BI__builtin_neon_vcltzs_f32: 5412 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5413 return EmitAArch64CompareBuiltinExpr( 5414 Ops[0], ConvertType(E->getCallReturnType(getContext())), 5415 ICmpInst::FCMP_OLT, ICmpInst::ICMP_SLT, "vcltz"); 5416 5417 case NEON::BI__builtin_neon_vceqzd_u64: { 5418 Ops.push_back(EmitScalarExpr(E->getArg(0))); 5419 Ops[0] = Builder.CreateBitCast(Ops[0], Int64Ty); 5420 Ops[0] = 5421 Builder.CreateICmpEQ(Ops[0], llvm::Constant::getNullValue(Int64Ty)); 5422 return Builder.CreateSExt(Ops[0], Int64Ty, "vceqzd"); 5423 } 5424 case NEON::BI__builtin_neon_vceqd_f64: 5425 case NEON::BI__builtin_neon_vcled_f64: 5426 case NEON::BI__builtin_neon_vcltd_f64: 5427 case NEON::BI__builtin_neon_vcged_f64: 5428 case NEON::BI__builtin_neon_vcgtd_f64: { 5429 llvm::CmpInst::Predicate P; 5430 switch (BuiltinID) { 5431 default: llvm_unreachable("missing builtin ID in switch!"); 5432 case NEON::BI__builtin_neon_vceqd_f64: P = llvm::FCmpInst::FCMP_OEQ; break; 5433 case NEON::BI__builtin_neon_vcled_f64: P = llvm::FCmpInst::FCMP_OLE; break; 5434 case NEON::BI__builtin_neon_vcltd_f64: P = llvm::FCmpInst::FCMP_OLT; break; 5435 case NEON::BI__builtin_neon_vcged_f64: P = llvm::FCmpInst::FCMP_OGE; break; 5436 case NEON::BI__builtin_neon_vcgtd_f64: P = llvm::FCmpInst::FCMP_OGT; break; 5437 } 5438 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5439 Ops[0] = Builder.CreateBitCast(Ops[0], DoubleTy); 5440 Ops[1] = Builder.CreateBitCast(Ops[1], DoubleTy); 5441 Ops[0] = Builder.CreateFCmp(P, Ops[0], Ops[1]); 5442 return Builder.CreateSExt(Ops[0], Int64Ty, "vcmpd"); 5443 } 5444 case NEON::BI__builtin_neon_vceqs_f32: 5445 case NEON::BI__builtin_neon_vcles_f32: 5446 case NEON::BI__builtin_neon_vclts_f32: 5447 case NEON::BI__builtin_neon_vcges_f32: 5448 case NEON::BI__builtin_neon_vcgts_f32: { 5449 llvm::CmpInst::Predicate P; 5450 switch (BuiltinID) { 5451 default: llvm_unreachable("missing builtin ID in switch!"); 5452 case NEON::BI__builtin_neon_vceqs_f32: P = llvm::FCmpInst::FCMP_OEQ; break; 5453 case NEON::BI__builtin_neon_vcles_f32: P = llvm::FCmpInst::FCMP_OLE; break; 5454 case NEON::BI__builtin_neon_vclts_f32: P = llvm::FCmpInst::FCMP_OLT; break; 5455 case NEON::BI__builtin_neon_vcges_f32: P = llvm::FCmpInst::FCMP_OGE; break; 5456 case NEON::BI__builtin_neon_vcgts_f32: P = llvm::FCmpInst::FCMP_OGT; break; 5457 } 5458 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5459 Ops[0] = Builder.CreateBitCast(Ops[0], FloatTy); 5460 Ops[1] = Builder.CreateBitCast(Ops[1], FloatTy); 5461 Ops[0] = Builder.CreateFCmp(P, Ops[0], Ops[1]); 5462 return Builder.CreateSExt(Ops[0], Int32Ty, "vcmpd"); 5463 } 5464 case NEON::BI__builtin_neon_vceqd_s64: 5465 case NEON::BI__builtin_neon_vceqd_u64: 5466 case NEON::BI__builtin_neon_vcgtd_s64: 5467 case NEON::BI__builtin_neon_vcgtd_u64: 5468 case NEON::BI__builtin_neon_vcltd_s64: 5469 case NEON::BI__builtin_neon_vcltd_u64: 5470 case NEON::BI__builtin_neon_vcged_u64: 5471 case NEON::BI__builtin_neon_vcged_s64: 5472 case NEON::BI__builtin_neon_vcled_u64: 5473 case NEON::BI__builtin_neon_vcled_s64: { 5474 llvm::CmpInst::Predicate P; 5475 switch (BuiltinID) { 5476 default: llvm_unreachable("missing builtin ID in switch!"); 5477 case NEON::BI__builtin_neon_vceqd_s64: 5478 case NEON::BI__builtin_neon_vceqd_u64:P = llvm::ICmpInst::ICMP_EQ;break; 5479 case NEON::BI__builtin_neon_vcgtd_s64:P = llvm::ICmpInst::ICMP_SGT;break; 5480 case NEON::BI__builtin_neon_vcgtd_u64:P = llvm::ICmpInst::ICMP_UGT;break; 5481 case NEON::BI__builtin_neon_vcltd_s64:P = llvm::ICmpInst::ICMP_SLT;break; 5482 case NEON::BI__builtin_neon_vcltd_u64:P = llvm::ICmpInst::ICMP_ULT;break; 5483 case NEON::BI__builtin_neon_vcged_u64:P = llvm::ICmpInst::ICMP_UGE;break; 5484 case NEON::BI__builtin_neon_vcged_s64:P = llvm::ICmpInst::ICMP_SGE;break; 5485 case NEON::BI__builtin_neon_vcled_u64:P = llvm::ICmpInst::ICMP_ULE;break; 5486 case NEON::BI__builtin_neon_vcled_s64:P = llvm::ICmpInst::ICMP_SLE;break; 5487 } 5488 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5489 Ops[0] = Builder.CreateBitCast(Ops[0], Int64Ty); 5490 Ops[1] = Builder.CreateBitCast(Ops[1], Int64Ty); 5491 Ops[0] = Builder.CreateICmp(P, Ops[0], Ops[1]); 5492 return Builder.CreateSExt(Ops[0], Int64Ty, "vceqd"); 5493 } 5494 case NEON::BI__builtin_neon_vtstd_s64: 5495 case NEON::BI__builtin_neon_vtstd_u64: { 5496 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5497 Ops[0] = Builder.CreateBitCast(Ops[0], Int64Ty); 5498 Ops[1] = Builder.CreateBitCast(Ops[1], Int64Ty); 5499 Ops[0] = Builder.CreateAnd(Ops[0], Ops[1]); 5500 Ops[0] = Builder.CreateICmp(ICmpInst::ICMP_NE, Ops[0], 5501 llvm::Constant::getNullValue(Int64Ty)); 5502 return Builder.CreateSExt(Ops[0], Int64Ty, "vtstd"); 5503 } 5504 case NEON::BI__builtin_neon_vset_lane_i8: 5505 case NEON::BI__builtin_neon_vset_lane_i16: 5506 case NEON::BI__builtin_neon_vset_lane_i32: 5507 case NEON::BI__builtin_neon_vset_lane_i64: 5508 case NEON::BI__builtin_neon_vset_lane_f32: 5509 case NEON::BI__builtin_neon_vsetq_lane_i8: 5510 case NEON::BI__builtin_neon_vsetq_lane_i16: 5511 case NEON::BI__builtin_neon_vsetq_lane_i32: 5512 case NEON::BI__builtin_neon_vsetq_lane_i64: 5513 case NEON::BI__builtin_neon_vsetq_lane_f32: 5514 Ops.push_back(EmitScalarExpr(E->getArg(2))); 5515 return Builder.CreateInsertElement(Ops[1], Ops[0], Ops[2], "vset_lane"); 5516 case NEON::BI__builtin_neon_vset_lane_f64: 5517 // The vector type needs a cast for the v1f64 variant. 5518 Ops[1] = Builder.CreateBitCast(Ops[1], 5519 llvm::VectorType::get(DoubleTy, 1)); 5520 Ops.push_back(EmitScalarExpr(E->getArg(2))); 5521 return Builder.CreateInsertElement(Ops[1], Ops[0], Ops[2], "vset_lane"); 5522 case NEON::BI__builtin_neon_vsetq_lane_f64: 5523 // The vector type needs a cast for the v2f64 variant. 5524 Ops[1] = Builder.CreateBitCast(Ops[1], 5525 llvm::VectorType::get(DoubleTy, 2)); 5526 Ops.push_back(EmitScalarExpr(E->getArg(2))); 5527 return Builder.CreateInsertElement(Ops[1], Ops[0], Ops[2], "vset_lane"); 5528 5529 case NEON::BI__builtin_neon_vget_lane_i8: 5530 case NEON::BI__builtin_neon_vdupb_lane_i8: 5531 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int8Ty, 8)); 5532 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5533 "vget_lane"); 5534 case NEON::BI__builtin_neon_vgetq_lane_i8: 5535 case NEON::BI__builtin_neon_vdupb_laneq_i8: 5536 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int8Ty, 16)); 5537 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5538 "vgetq_lane"); 5539 case NEON::BI__builtin_neon_vget_lane_i16: 5540 case NEON::BI__builtin_neon_vduph_lane_i16: 5541 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int16Ty, 4)); 5542 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5543 "vget_lane"); 5544 case NEON::BI__builtin_neon_vgetq_lane_i16: 5545 case NEON::BI__builtin_neon_vduph_laneq_i16: 5546 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int16Ty, 8)); 5547 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5548 "vgetq_lane"); 5549 case NEON::BI__builtin_neon_vget_lane_i32: 5550 case NEON::BI__builtin_neon_vdups_lane_i32: 5551 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int32Ty, 2)); 5552 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5553 "vget_lane"); 5554 case NEON::BI__builtin_neon_vdups_lane_f32: 5555 Ops[0] = Builder.CreateBitCast(Ops[0], 5556 llvm::VectorType::get(FloatTy, 2)); 5557 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5558 "vdups_lane"); 5559 case NEON::BI__builtin_neon_vgetq_lane_i32: 5560 case NEON::BI__builtin_neon_vdups_laneq_i32: 5561 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int32Ty, 4)); 5562 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5563 "vgetq_lane"); 5564 case NEON::BI__builtin_neon_vget_lane_i64: 5565 case NEON::BI__builtin_neon_vdupd_lane_i64: 5566 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int64Ty, 1)); 5567 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5568 "vget_lane"); 5569 case NEON::BI__builtin_neon_vdupd_lane_f64: 5570 Ops[0] = Builder.CreateBitCast(Ops[0], 5571 llvm::VectorType::get(DoubleTy, 1)); 5572 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5573 "vdupd_lane"); 5574 case NEON::BI__builtin_neon_vgetq_lane_i64: 5575 case NEON::BI__builtin_neon_vdupd_laneq_i64: 5576 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::VectorType::get(Int64Ty, 2)); 5577 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5578 "vgetq_lane"); 5579 case NEON::BI__builtin_neon_vget_lane_f32: 5580 Ops[0] = Builder.CreateBitCast(Ops[0], 5581 llvm::VectorType::get(FloatTy, 2)); 5582 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5583 "vget_lane"); 5584 case NEON::BI__builtin_neon_vget_lane_f64: 5585 Ops[0] = Builder.CreateBitCast(Ops[0], 5586 llvm::VectorType::get(DoubleTy, 1)); 5587 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5588 "vget_lane"); 5589 case NEON::BI__builtin_neon_vgetq_lane_f32: 5590 case NEON::BI__builtin_neon_vdups_laneq_f32: 5591 Ops[0] = Builder.CreateBitCast(Ops[0], 5592 llvm::VectorType::get(FloatTy, 4)); 5593 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5594 "vgetq_lane"); 5595 case NEON::BI__builtin_neon_vgetq_lane_f64: 5596 case NEON::BI__builtin_neon_vdupd_laneq_f64: 5597 Ops[0] = Builder.CreateBitCast(Ops[0], 5598 llvm::VectorType::get(DoubleTy, 2)); 5599 return Builder.CreateExtractElement(Ops[0], EmitScalarExpr(E->getArg(1)), 5600 "vgetq_lane"); 5601 case NEON::BI__builtin_neon_vaddd_s64: 5602 case NEON::BI__builtin_neon_vaddd_u64: 5603 return Builder.CreateAdd(Ops[0], EmitScalarExpr(E->getArg(1)), "vaddd"); 5604 case NEON::BI__builtin_neon_vsubd_s64: 5605 case NEON::BI__builtin_neon_vsubd_u64: 5606 return Builder.CreateSub(Ops[0], EmitScalarExpr(E->getArg(1)), "vsubd"); 5607 case NEON::BI__builtin_neon_vqdmlalh_s16: 5608 case NEON::BI__builtin_neon_vqdmlslh_s16: { 5609 SmallVector<Value *, 2> ProductOps; 5610 ProductOps.push_back(vectorWrapScalar16(Ops[1])); 5611 ProductOps.push_back(vectorWrapScalar16(EmitScalarExpr(E->getArg(2)))); 5612 llvm::Type *VTy = llvm::VectorType::get(Int32Ty, 4); 5613 Ops[1] = EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_sqdmull, VTy), 5614 ProductOps, "vqdmlXl"); 5615 Constant *CI = ConstantInt::get(SizeTy, 0); 5616 Ops[1] = Builder.CreateExtractElement(Ops[1], CI, "lane0"); 5617 5618 unsigned AccumInt = BuiltinID == NEON::BI__builtin_neon_vqdmlalh_s16 5619 ? Intrinsic::aarch64_neon_sqadd 5620 : Intrinsic::aarch64_neon_sqsub; 5621 return EmitNeonCall(CGM.getIntrinsic(AccumInt, Int32Ty), Ops, "vqdmlXl"); 5622 } 5623 case NEON::BI__builtin_neon_vqshlud_n_s64: { 5624 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5625 Ops[1] = Builder.CreateZExt(Ops[1], Int64Ty); 5626 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_sqshlu, Int64Ty), 5627 Ops, "vqshlu_n"); 5628 } 5629 case NEON::BI__builtin_neon_vqshld_n_u64: 5630 case NEON::BI__builtin_neon_vqshld_n_s64: { 5631 unsigned Int = BuiltinID == NEON::BI__builtin_neon_vqshld_n_u64 5632 ? Intrinsic::aarch64_neon_uqshl 5633 : Intrinsic::aarch64_neon_sqshl; 5634 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5635 Ops[1] = Builder.CreateZExt(Ops[1], Int64Ty); 5636 return EmitNeonCall(CGM.getIntrinsic(Int, Int64Ty), Ops, "vqshl_n"); 5637 } 5638 case NEON::BI__builtin_neon_vrshrd_n_u64: 5639 case NEON::BI__builtin_neon_vrshrd_n_s64: { 5640 unsigned Int = BuiltinID == NEON::BI__builtin_neon_vrshrd_n_u64 5641 ? Intrinsic::aarch64_neon_urshl 5642 : Intrinsic::aarch64_neon_srshl; 5643 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5644 int SV = cast<ConstantInt>(Ops[1])->getSExtValue(); 5645 Ops[1] = ConstantInt::get(Int64Ty, -SV); 5646 return EmitNeonCall(CGM.getIntrinsic(Int, Int64Ty), Ops, "vrshr_n"); 5647 } 5648 case NEON::BI__builtin_neon_vrsrad_n_u64: 5649 case NEON::BI__builtin_neon_vrsrad_n_s64: { 5650 unsigned Int = BuiltinID == NEON::BI__builtin_neon_vrsrad_n_u64 5651 ? Intrinsic::aarch64_neon_urshl 5652 : Intrinsic::aarch64_neon_srshl; 5653 Ops[1] = Builder.CreateBitCast(Ops[1], Int64Ty); 5654 Ops.push_back(Builder.CreateNeg(EmitScalarExpr(E->getArg(2)))); 5655 Ops[1] = Builder.CreateCall(CGM.getIntrinsic(Int, Int64Ty), 5656 {Ops[1], Builder.CreateSExt(Ops[2], Int64Ty)}); 5657 return Builder.CreateAdd(Ops[0], Builder.CreateBitCast(Ops[1], Int64Ty)); 5658 } 5659 case NEON::BI__builtin_neon_vshld_n_s64: 5660 case NEON::BI__builtin_neon_vshld_n_u64: { 5661 llvm::ConstantInt *Amt = cast<ConstantInt>(EmitScalarExpr(E->getArg(1))); 5662 return Builder.CreateShl( 5663 Ops[0], ConstantInt::get(Int64Ty, Amt->getZExtValue()), "shld_n"); 5664 } 5665 case NEON::BI__builtin_neon_vshrd_n_s64: { 5666 llvm::ConstantInt *Amt = cast<ConstantInt>(EmitScalarExpr(E->getArg(1))); 5667 return Builder.CreateAShr( 5668 Ops[0], ConstantInt::get(Int64Ty, std::min(static_cast<uint64_t>(63), 5669 Amt->getZExtValue())), 5670 "shrd_n"); 5671 } 5672 case NEON::BI__builtin_neon_vshrd_n_u64: { 5673 llvm::ConstantInt *Amt = cast<ConstantInt>(EmitScalarExpr(E->getArg(1))); 5674 uint64_t ShiftAmt = Amt->getZExtValue(); 5675 // Right-shifting an unsigned value by its size yields 0. 5676 if (ShiftAmt == 64) 5677 return ConstantInt::get(Int64Ty, 0); 5678 return Builder.CreateLShr(Ops[0], ConstantInt::get(Int64Ty, ShiftAmt), 5679 "shrd_n"); 5680 } 5681 case NEON::BI__builtin_neon_vsrad_n_s64: { 5682 llvm::ConstantInt *Amt = cast<ConstantInt>(EmitScalarExpr(E->getArg(2))); 5683 Ops[1] = Builder.CreateAShr( 5684 Ops[1], ConstantInt::get(Int64Ty, std::min(static_cast<uint64_t>(63), 5685 Amt->getZExtValue())), 5686 "shrd_n"); 5687 return Builder.CreateAdd(Ops[0], Ops[1]); 5688 } 5689 case NEON::BI__builtin_neon_vsrad_n_u64: { 5690 llvm::ConstantInt *Amt = cast<ConstantInt>(EmitScalarExpr(E->getArg(2))); 5691 uint64_t ShiftAmt = Amt->getZExtValue(); 5692 // Right-shifting an unsigned value by its size yields 0. 5693 // As Op + 0 = Op, return Ops[0] directly. 5694 if (ShiftAmt == 64) 5695 return Ops[0]; 5696 Ops[1] = Builder.CreateLShr(Ops[1], ConstantInt::get(Int64Ty, ShiftAmt), 5697 "shrd_n"); 5698 return Builder.CreateAdd(Ops[0], Ops[1]); 5699 } 5700 case NEON::BI__builtin_neon_vqdmlalh_lane_s16: 5701 case NEON::BI__builtin_neon_vqdmlalh_laneq_s16: 5702 case NEON::BI__builtin_neon_vqdmlslh_lane_s16: 5703 case NEON::BI__builtin_neon_vqdmlslh_laneq_s16: { 5704 Ops[2] = Builder.CreateExtractElement(Ops[2], EmitScalarExpr(E->getArg(3)), 5705 "lane"); 5706 SmallVector<Value *, 2> ProductOps; 5707 ProductOps.push_back(vectorWrapScalar16(Ops[1])); 5708 ProductOps.push_back(vectorWrapScalar16(Ops[2])); 5709 llvm::Type *VTy = llvm::VectorType::get(Int32Ty, 4); 5710 Ops[1] = EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_sqdmull, VTy), 5711 ProductOps, "vqdmlXl"); 5712 Constant *CI = ConstantInt::get(SizeTy, 0); 5713 Ops[1] = Builder.CreateExtractElement(Ops[1], CI, "lane0"); 5714 Ops.pop_back(); 5715 5716 unsigned AccInt = (BuiltinID == NEON::BI__builtin_neon_vqdmlalh_lane_s16 || 5717 BuiltinID == NEON::BI__builtin_neon_vqdmlalh_laneq_s16) 5718 ? Intrinsic::aarch64_neon_sqadd 5719 : Intrinsic::aarch64_neon_sqsub; 5720 return EmitNeonCall(CGM.getIntrinsic(AccInt, Int32Ty), Ops, "vqdmlXl"); 5721 } 5722 case NEON::BI__builtin_neon_vqdmlals_s32: 5723 case NEON::BI__builtin_neon_vqdmlsls_s32: { 5724 SmallVector<Value *, 2> ProductOps; 5725 ProductOps.push_back(Ops[1]); 5726 ProductOps.push_back(EmitScalarExpr(E->getArg(2))); 5727 Ops[1] = 5728 EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_sqdmulls_scalar), 5729 ProductOps, "vqdmlXl"); 5730 5731 unsigned AccumInt = BuiltinID == NEON::BI__builtin_neon_vqdmlals_s32 5732 ? Intrinsic::aarch64_neon_sqadd 5733 : Intrinsic::aarch64_neon_sqsub; 5734 return EmitNeonCall(CGM.getIntrinsic(AccumInt, Int64Ty), Ops, "vqdmlXl"); 5735 } 5736 case NEON::BI__builtin_neon_vqdmlals_lane_s32: 5737 case NEON::BI__builtin_neon_vqdmlals_laneq_s32: 5738 case NEON::BI__builtin_neon_vqdmlsls_lane_s32: 5739 case NEON::BI__builtin_neon_vqdmlsls_laneq_s32: { 5740 Ops[2] = Builder.CreateExtractElement(Ops[2], EmitScalarExpr(E->getArg(3)), 5741 "lane"); 5742 SmallVector<Value *, 2> ProductOps; 5743 ProductOps.push_back(Ops[1]); 5744 ProductOps.push_back(Ops[2]); 5745 Ops[1] = 5746 EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_sqdmulls_scalar), 5747 ProductOps, "vqdmlXl"); 5748 Ops.pop_back(); 5749 5750 unsigned AccInt = (BuiltinID == NEON::BI__builtin_neon_vqdmlals_lane_s32 || 5751 BuiltinID == NEON::BI__builtin_neon_vqdmlals_laneq_s32) 5752 ? Intrinsic::aarch64_neon_sqadd 5753 : Intrinsic::aarch64_neon_sqsub; 5754 return EmitNeonCall(CGM.getIntrinsic(AccInt, Int64Ty), Ops, "vqdmlXl"); 5755 } 5756 } 5757 5758 llvm::VectorType *VTy = GetNeonType(this, Type); 5759 llvm::Type *Ty = VTy; 5760 if (!Ty) 5761 return nullptr; 5762 5763 // Not all intrinsics handled by the common case work for AArch64 yet, so only 5764 // defer to common code if it's been added to our special map. 5765 Builtin = findNeonIntrinsicInMap(AArch64SIMDIntrinsicMap, BuiltinID, 5766 AArch64SIMDIntrinsicsProvenSorted); 5767 5768 if (Builtin) 5769 return EmitCommonNeonBuiltinExpr( 5770 Builtin->BuiltinID, Builtin->LLVMIntrinsic, Builtin->AltLLVMIntrinsic, 5771 Builtin->NameHint, Builtin->TypeModifier, E, Ops, 5772 /*never use addresses*/ Address::invalid(), Address::invalid()); 5773 5774 if (Value *V = EmitAArch64TblBuiltinExpr(*this, BuiltinID, E, Ops)) 5775 return V; 5776 5777 unsigned Int; 5778 switch (BuiltinID) { 5779 default: return nullptr; 5780 case NEON::BI__builtin_neon_vbsl_v: 5781 case NEON::BI__builtin_neon_vbslq_v: { 5782 llvm::Type *BitTy = llvm::VectorType::getInteger(VTy); 5783 Ops[0] = Builder.CreateBitCast(Ops[0], BitTy, "vbsl"); 5784 Ops[1] = Builder.CreateBitCast(Ops[1], BitTy, "vbsl"); 5785 Ops[2] = Builder.CreateBitCast(Ops[2], BitTy, "vbsl"); 5786 5787 Ops[1] = Builder.CreateAnd(Ops[0], Ops[1], "vbsl"); 5788 Ops[2] = Builder.CreateAnd(Builder.CreateNot(Ops[0]), Ops[2], "vbsl"); 5789 Ops[0] = Builder.CreateOr(Ops[1], Ops[2], "vbsl"); 5790 return Builder.CreateBitCast(Ops[0], Ty); 5791 } 5792 case NEON::BI__builtin_neon_vfma_lane_v: 5793 case NEON::BI__builtin_neon_vfmaq_lane_v: { // Only used for FP types 5794 // The ARM builtins (and instructions) have the addend as the first 5795 // operand, but the 'fma' intrinsics have it last. Swap it around here. 5796 Value *Addend = Ops[0]; 5797 Value *Multiplicand = Ops[1]; 5798 Value *LaneSource = Ops[2]; 5799 Ops[0] = Multiplicand; 5800 Ops[1] = LaneSource; 5801 Ops[2] = Addend; 5802 5803 // Now adjust things to handle the lane access. 5804 llvm::Type *SourceTy = BuiltinID == NEON::BI__builtin_neon_vfmaq_lane_v ? 5805 llvm::VectorType::get(VTy->getElementType(), VTy->getNumElements() / 2) : 5806 VTy; 5807 llvm::Constant *cst = cast<Constant>(Ops[3]); 5808 Value *SV = llvm::ConstantVector::getSplat(VTy->getNumElements(), cst); 5809 Ops[1] = Builder.CreateBitCast(Ops[1], SourceTy); 5810 Ops[1] = Builder.CreateShuffleVector(Ops[1], Ops[1], SV, "lane"); 5811 5812 Ops.pop_back(); 5813 Int = Intrinsic::fma; 5814 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "fmla"); 5815 } 5816 case NEON::BI__builtin_neon_vfma_laneq_v: { 5817 llvm::VectorType *VTy = cast<llvm::VectorType>(Ty); 5818 // v1f64 fma should be mapped to Neon scalar f64 fma 5819 if (VTy && VTy->getElementType() == DoubleTy) { 5820 Ops[0] = Builder.CreateBitCast(Ops[0], DoubleTy); 5821 Ops[1] = Builder.CreateBitCast(Ops[1], DoubleTy); 5822 llvm::Type *VTy = GetNeonType(this, 5823 NeonTypeFlags(NeonTypeFlags::Float64, false, true)); 5824 Ops[2] = Builder.CreateBitCast(Ops[2], VTy); 5825 Ops[2] = Builder.CreateExtractElement(Ops[2], Ops[3], "extract"); 5826 Value *F = CGM.getIntrinsic(Intrinsic::fma, DoubleTy); 5827 Value *Result = Builder.CreateCall(F, {Ops[1], Ops[2], Ops[0]}); 5828 return Builder.CreateBitCast(Result, Ty); 5829 } 5830 Value *F = CGM.getIntrinsic(Intrinsic::fma, Ty); 5831 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 5832 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 5833 5834 llvm::Type *STy = llvm::VectorType::get(VTy->getElementType(), 5835 VTy->getNumElements() * 2); 5836 Ops[2] = Builder.CreateBitCast(Ops[2], STy); 5837 Value* SV = llvm::ConstantVector::getSplat(VTy->getNumElements(), 5838 cast<ConstantInt>(Ops[3])); 5839 Ops[2] = Builder.CreateShuffleVector(Ops[2], Ops[2], SV, "lane"); 5840 5841 return Builder.CreateCall(F, {Ops[2], Ops[1], Ops[0]}); 5842 } 5843 case NEON::BI__builtin_neon_vfmaq_laneq_v: { 5844 Value *F = CGM.getIntrinsic(Intrinsic::fma, Ty); 5845 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 5846 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 5847 5848 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 5849 Ops[2] = EmitNeonSplat(Ops[2], cast<ConstantInt>(Ops[3])); 5850 return Builder.CreateCall(F, {Ops[2], Ops[1], Ops[0]}); 5851 } 5852 case NEON::BI__builtin_neon_vfmas_lane_f32: 5853 case NEON::BI__builtin_neon_vfmas_laneq_f32: 5854 case NEON::BI__builtin_neon_vfmad_lane_f64: 5855 case NEON::BI__builtin_neon_vfmad_laneq_f64: { 5856 Ops.push_back(EmitScalarExpr(E->getArg(3))); 5857 llvm::Type *Ty = ConvertType(E->getCallReturnType(getContext())); 5858 Value *F = CGM.getIntrinsic(Intrinsic::fma, Ty); 5859 Ops[2] = Builder.CreateExtractElement(Ops[2], Ops[3], "extract"); 5860 return Builder.CreateCall(F, {Ops[1], Ops[2], Ops[0]}); 5861 } 5862 case NEON::BI__builtin_neon_vmull_v: 5863 // FIXME: improve sharing scheme to cope with 3 alternative LLVM intrinsics. 5864 Int = usgn ? Intrinsic::aarch64_neon_umull : Intrinsic::aarch64_neon_smull; 5865 if (Type.isPoly()) Int = Intrinsic::aarch64_neon_pmull; 5866 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vmull"); 5867 case NEON::BI__builtin_neon_vmax_v: 5868 case NEON::BI__builtin_neon_vmaxq_v: 5869 // FIXME: improve sharing scheme to cope with 3 alternative LLVM intrinsics. 5870 Int = usgn ? Intrinsic::aarch64_neon_umax : Intrinsic::aarch64_neon_smax; 5871 if (Ty->isFPOrFPVectorTy()) Int = Intrinsic::aarch64_neon_fmax; 5872 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vmax"); 5873 case NEON::BI__builtin_neon_vmin_v: 5874 case NEON::BI__builtin_neon_vminq_v: 5875 // FIXME: improve sharing scheme to cope with 3 alternative LLVM intrinsics. 5876 Int = usgn ? Intrinsic::aarch64_neon_umin : Intrinsic::aarch64_neon_smin; 5877 if (Ty->isFPOrFPVectorTy()) Int = Intrinsic::aarch64_neon_fmin; 5878 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vmin"); 5879 case NEON::BI__builtin_neon_vabd_v: 5880 case NEON::BI__builtin_neon_vabdq_v: 5881 // FIXME: improve sharing scheme to cope with 3 alternative LLVM intrinsics. 5882 Int = usgn ? Intrinsic::aarch64_neon_uabd : Intrinsic::aarch64_neon_sabd; 5883 if (Ty->isFPOrFPVectorTy()) Int = Intrinsic::aarch64_neon_fabd; 5884 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vabd"); 5885 case NEON::BI__builtin_neon_vpadal_v: 5886 case NEON::BI__builtin_neon_vpadalq_v: { 5887 unsigned ArgElts = VTy->getNumElements(); 5888 llvm::IntegerType *EltTy = cast<IntegerType>(VTy->getElementType()); 5889 unsigned BitWidth = EltTy->getBitWidth(); 5890 llvm::Type *ArgTy = llvm::VectorType::get( 5891 llvm::IntegerType::get(getLLVMContext(), BitWidth/2), 2*ArgElts); 5892 llvm::Type* Tys[2] = { VTy, ArgTy }; 5893 Int = usgn ? Intrinsic::aarch64_neon_uaddlp : Intrinsic::aarch64_neon_saddlp; 5894 SmallVector<llvm::Value*, 1> TmpOps; 5895 TmpOps.push_back(Ops[1]); 5896 Function *F = CGM.getIntrinsic(Int, Tys); 5897 llvm::Value *tmp = EmitNeonCall(F, TmpOps, "vpadal"); 5898 llvm::Value *addend = Builder.CreateBitCast(Ops[0], tmp->getType()); 5899 return Builder.CreateAdd(tmp, addend); 5900 } 5901 case NEON::BI__builtin_neon_vpmin_v: 5902 case NEON::BI__builtin_neon_vpminq_v: 5903 // FIXME: improve sharing scheme to cope with 3 alternative LLVM intrinsics. 5904 Int = usgn ? Intrinsic::aarch64_neon_uminp : Intrinsic::aarch64_neon_sminp; 5905 if (Ty->isFPOrFPVectorTy()) Int = Intrinsic::aarch64_neon_fminp; 5906 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vpmin"); 5907 case NEON::BI__builtin_neon_vpmax_v: 5908 case NEON::BI__builtin_neon_vpmaxq_v: 5909 // FIXME: improve sharing scheme to cope with 3 alternative LLVM intrinsics. 5910 Int = usgn ? Intrinsic::aarch64_neon_umaxp : Intrinsic::aarch64_neon_smaxp; 5911 if (Ty->isFPOrFPVectorTy()) Int = Intrinsic::aarch64_neon_fmaxp; 5912 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vpmax"); 5913 case NEON::BI__builtin_neon_vminnm_v: 5914 case NEON::BI__builtin_neon_vminnmq_v: 5915 Int = Intrinsic::aarch64_neon_fminnm; 5916 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vminnm"); 5917 case NEON::BI__builtin_neon_vmaxnm_v: 5918 case NEON::BI__builtin_neon_vmaxnmq_v: 5919 Int = Intrinsic::aarch64_neon_fmaxnm; 5920 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vmaxnm"); 5921 case NEON::BI__builtin_neon_vrecpss_f32: { 5922 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5923 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_frecps, FloatTy), 5924 Ops, "vrecps"); 5925 } 5926 case NEON::BI__builtin_neon_vrecpsd_f64: { 5927 Ops.push_back(EmitScalarExpr(E->getArg(1))); 5928 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_frecps, DoubleTy), 5929 Ops, "vrecps"); 5930 } 5931 case NEON::BI__builtin_neon_vqshrun_n_v: 5932 Int = Intrinsic::aarch64_neon_sqshrun; 5933 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqshrun_n"); 5934 case NEON::BI__builtin_neon_vqrshrun_n_v: 5935 Int = Intrinsic::aarch64_neon_sqrshrun; 5936 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqrshrun_n"); 5937 case NEON::BI__builtin_neon_vqshrn_n_v: 5938 Int = usgn ? Intrinsic::aarch64_neon_uqshrn : Intrinsic::aarch64_neon_sqshrn; 5939 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqshrn_n"); 5940 case NEON::BI__builtin_neon_vrshrn_n_v: 5941 Int = Intrinsic::aarch64_neon_rshrn; 5942 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrshrn_n"); 5943 case NEON::BI__builtin_neon_vqrshrn_n_v: 5944 Int = usgn ? Intrinsic::aarch64_neon_uqrshrn : Intrinsic::aarch64_neon_sqrshrn; 5945 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vqrshrn_n"); 5946 case NEON::BI__builtin_neon_vrnda_v: 5947 case NEON::BI__builtin_neon_vrndaq_v: { 5948 Int = Intrinsic::round; 5949 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrnda"); 5950 } 5951 case NEON::BI__builtin_neon_vrndi_v: 5952 case NEON::BI__builtin_neon_vrndiq_v: { 5953 Int = Intrinsic::nearbyint; 5954 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrndi"); 5955 } 5956 case NEON::BI__builtin_neon_vrndm_v: 5957 case NEON::BI__builtin_neon_vrndmq_v: { 5958 Int = Intrinsic::floor; 5959 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrndm"); 5960 } 5961 case NEON::BI__builtin_neon_vrndn_v: 5962 case NEON::BI__builtin_neon_vrndnq_v: { 5963 Int = Intrinsic::aarch64_neon_frintn; 5964 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrndn"); 5965 } 5966 case NEON::BI__builtin_neon_vrndp_v: 5967 case NEON::BI__builtin_neon_vrndpq_v: { 5968 Int = Intrinsic::ceil; 5969 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrndp"); 5970 } 5971 case NEON::BI__builtin_neon_vrndx_v: 5972 case NEON::BI__builtin_neon_vrndxq_v: { 5973 Int = Intrinsic::rint; 5974 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrndx"); 5975 } 5976 case NEON::BI__builtin_neon_vrnd_v: 5977 case NEON::BI__builtin_neon_vrndq_v: { 5978 Int = Intrinsic::trunc; 5979 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrndz"); 5980 } 5981 case NEON::BI__builtin_neon_vceqz_v: 5982 case NEON::BI__builtin_neon_vceqzq_v: 5983 return EmitAArch64CompareBuiltinExpr(Ops[0], Ty, ICmpInst::FCMP_OEQ, 5984 ICmpInst::ICMP_EQ, "vceqz"); 5985 case NEON::BI__builtin_neon_vcgez_v: 5986 case NEON::BI__builtin_neon_vcgezq_v: 5987 return EmitAArch64CompareBuiltinExpr(Ops[0], Ty, ICmpInst::FCMP_OGE, 5988 ICmpInst::ICMP_SGE, "vcgez"); 5989 case NEON::BI__builtin_neon_vclez_v: 5990 case NEON::BI__builtin_neon_vclezq_v: 5991 return EmitAArch64CompareBuiltinExpr(Ops[0], Ty, ICmpInst::FCMP_OLE, 5992 ICmpInst::ICMP_SLE, "vclez"); 5993 case NEON::BI__builtin_neon_vcgtz_v: 5994 case NEON::BI__builtin_neon_vcgtzq_v: 5995 return EmitAArch64CompareBuiltinExpr(Ops[0], Ty, ICmpInst::FCMP_OGT, 5996 ICmpInst::ICMP_SGT, "vcgtz"); 5997 case NEON::BI__builtin_neon_vcltz_v: 5998 case NEON::BI__builtin_neon_vcltzq_v: 5999 return EmitAArch64CompareBuiltinExpr(Ops[0], Ty, ICmpInst::FCMP_OLT, 6000 ICmpInst::ICMP_SLT, "vcltz"); 6001 case NEON::BI__builtin_neon_vcvt_f64_v: 6002 case NEON::BI__builtin_neon_vcvtq_f64_v: 6003 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6004 Ty = GetNeonType(this, NeonTypeFlags(NeonTypeFlags::Float64, false, quad)); 6005 return usgn ? Builder.CreateUIToFP(Ops[0], Ty, "vcvt") 6006 : Builder.CreateSIToFP(Ops[0], Ty, "vcvt"); 6007 case NEON::BI__builtin_neon_vcvt_f64_f32: { 6008 assert(Type.getEltType() == NeonTypeFlags::Float64 && quad && 6009 "unexpected vcvt_f64_f32 builtin"); 6010 NeonTypeFlags SrcFlag = NeonTypeFlags(NeonTypeFlags::Float32, false, false); 6011 Ops[0] = Builder.CreateBitCast(Ops[0], GetNeonType(this, SrcFlag)); 6012 6013 return Builder.CreateFPExt(Ops[0], Ty, "vcvt"); 6014 } 6015 case NEON::BI__builtin_neon_vcvt_f32_f64: { 6016 assert(Type.getEltType() == NeonTypeFlags::Float32 && 6017 "unexpected vcvt_f32_f64 builtin"); 6018 NeonTypeFlags SrcFlag = NeonTypeFlags(NeonTypeFlags::Float64, false, true); 6019 Ops[0] = Builder.CreateBitCast(Ops[0], GetNeonType(this, SrcFlag)); 6020 6021 return Builder.CreateFPTrunc(Ops[0], Ty, "vcvt"); 6022 } 6023 case NEON::BI__builtin_neon_vcvt_s32_v: 6024 case NEON::BI__builtin_neon_vcvt_u32_v: 6025 case NEON::BI__builtin_neon_vcvt_s64_v: 6026 case NEON::BI__builtin_neon_vcvt_u64_v: 6027 case NEON::BI__builtin_neon_vcvtq_s32_v: 6028 case NEON::BI__builtin_neon_vcvtq_u32_v: 6029 case NEON::BI__builtin_neon_vcvtq_s64_v: 6030 case NEON::BI__builtin_neon_vcvtq_u64_v: { 6031 Ops[0] = Builder.CreateBitCast(Ops[0], GetFloatNeonType(this, Type)); 6032 if (usgn) 6033 return Builder.CreateFPToUI(Ops[0], Ty); 6034 return Builder.CreateFPToSI(Ops[0], Ty); 6035 } 6036 case NEON::BI__builtin_neon_vcvta_s32_v: 6037 case NEON::BI__builtin_neon_vcvtaq_s32_v: 6038 case NEON::BI__builtin_neon_vcvta_u32_v: 6039 case NEON::BI__builtin_neon_vcvtaq_u32_v: 6040 case NEON::BI__builtin_neon_vcvta_s64_v: 6041 case NEON::BI__builtin_neon_vcvtaq_s64_v: 6042 case NEON::BI__builtin_neon_vcvta_u64_v: 6043 case NEON::BI__builtin_neon_vcvtaq_u64_v: { 6044 Int = usgn ? Intrinsic::aarch64_neon_fcvtau : Intrinsic::aarch64_neon_fcvtas; 6045 llvm::Type *Tys[2] = { Ty, GetFloatNeonType(this, Type) }; 6046 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vcvta"); 6047 } 6048 case NEON::BI__builtin_neon_vcvtm_s32_v: 6049 case NEON::BI__builtin_neon_vcvtmq_s32_v: 6050 case NEON::BI__builtin_neon_vcvtm_u32_v: 6051 case NEON::BI__builtin_neon_vcvtmq_u32_v: 6052 case NEON::BI__builtin_neon_vcvtm_s64_v: 6053 case NEON::BI__builtin_neon_vcvtmq_s64_v: 6054 case NEON::BI__builtin_neon_vcvtm_u64_v: 6055 case NEON::BI__builtin_neon_vcvtmq_u64_v: { 6056 Int = usgn ? Intrinsic::aarch64_neon_fcvtmu : Intrinsic::aarch64_neon_fcvtms; 6057 llvm::Type *Tys[2] = { Ty, GetFloatNeonType(this, Type) }; 6058 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vcvtm"); 6059 } 6060 case NEON::BI__builtin_neon_vcvtn_s32_v: 6061 case NEON::BI__builtin_neon_vcvtnq_s32_v: 6062 case NEON::BI__builtin_neon_vcvtn_u32_v: 6063 case NEON::BI__builtin_neon_vcvtnq_u32_v: 6064 case NEON::BI__builtin_neon_vcvtn_s64_v: 6065 case NEON::BI__builtin_neon_vcvtnq_s64_v: 6066 case NEON::BI__builtin_neon_vcvtn_u64_v: 6067 case NEON::BI__builtin_neon_vcvtnq_u64_v: { 6068 Int = usgn ? Intrinsic::aarch64_neon_fcvtnu : Intrinsic::aarch64_neon_fcvtns; 6069 llvm::Type *Tys[2] = { Ty, GetFloatNeonType(this, Type) }; 6070 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vcvtn"); 6071 } 6072 case NEON::BI__builtin_neon_vcvtp_s32_v: 6073 case NEON::BI__builtin_neon_vcvtpq_s32_v: 6074 case NEON::BI__builtin_neon_vcvtp_u32_v: 6075 case NEON::BI__builtin_neon_vcvtpq_u32_v: 6076 case NEON::BI__builtin_neon_vcvtp_s64_v: 6077 case NEON::BI__builtin_neon_vcvtpq_s64_v: 6078 case NEON::BI__builtin_neon_vcvtp_u64_v: 6079 case NEON::BI__builtin_neon_vcvtpq_u64_v: { 6080 Int = usgn ? Intrinsic::aarch64_neon_fcvtpu : Intrinsic::aarch64_neon_fcvtps; 6081 llvm::Type *Tys[2] = { Ty, GetFloatNeonType(this, Type) }; 6082 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vcvtp"); 6083 } 6084 case NEON::BI__builtin_neon_vmulx_v: 6085 case NEON::BI__builtin_neon_vmulxq_v: { 6086 Int = Intrinsic::aarch64_neon_fmulx; 6087 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vmulx"); 6088 } 6089 case NEON::BI__builtin_neon_vmul_lane_v: 6090 case NEON::BI__builtin_neon_vmul_laneq_v: { 6091 // v1f64 vmul_lane should be mapped to Neon scalar mul lane 6092 bool Quad = false; 6093 if (BuiltinID == NEON::BI__builtin_neon_vmul_laneq_v) 6094 Quad = true; 6095 Ops[0] = Builder.CreateBitCast(Ops[0], DoubleTy); 6096 llvm::Type *VTy = GetNeonType(this, 6097 NeonTypeFlags(NeonTypeFlags::Float64, false, Quad)); 6098 Ops[1] = Builder.CreateBitCast(Ops[1], VTy); 6099 Ops[1] = Builder.CreateExtractElement(Ops[1], Ops[2], "extract"); 6100 Value *Result = Builder.CreateFMul(Ops[0], Ops[1]); 6101 return Builder.CreateBitCast(Result, Ty); 6102 } 6103 case NEON::BI__builtin_neon_vnegd_s64: 6104 return Builder.CreateNeg(EmitScalarExpr(E->getArg(0)), "vnegd"); 6105 case NEON::BI__builtin_neon_vpmaxnm_v: 6106 case NEON::BI__builtin_neon_vpmaxnmq_v: { 6107 Int = Intrinsic::aarch64_neon_fmaxnmp; 6108 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vpmaxnm"); 6109 } 6110 case NEON::BI__builtin_neon_vpminnm_v: 6111 case NEON::BI__builtin_neon_vpminnmq_v: { 6112 Int = Intrinsic::aarch64_neon_fminnmp; 6113 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vpminnm"); 6114 } 6115 case NEON::BI__builtin_neon_vsqrt_v: 6116 case NEON::BI__builtin_neon_vsqrtq_v: { 6117 Int = Intrinsic::sqrt; 6118 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6119 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vsqrt"); 6120 } 6121 case NEON::BI__builtin_neon_vrbit_v: 6122 case NEON::BI__builtin_neon_vrbitq_v: { 6123 Int = Intrinsic::aarch64_neon_rbit; 6124 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vrbit"); 6125 } 6126 case NEON::BI__builtin_neon_vaddv_u8: 6127 // FIXME: These are handled by the AArch64 scalar code. 6128 usgn = true; 6129 // FALLTHROUGH 6130 case NEON::BI__builtin_neon_vaddv_s8: { 6131 Int = usgn ? Intrinsic::aarch64_neon_uaddv : Intrinsic::aarch64_neon_saddv; 6132 Ty = Int32Ty; 6133 VTy = llvm::VectorType::get(Int8Ty, 8); 6134 llvm::Type *Tys[2] = { Ty, VTy }; 6135 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6136 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddv"); 6137 return Builder.CreateTrunc(Ops[0], Int8Ty); 6138 } 6139 case NEON::BI__builtin_neon_vaddv_u16: 6140 usgn = true; 6141 // FALLTHROUGH 6142 case NEON::BI__builtin_neon_vaddv_s16: { 6143 Int = usgn ? Intrinsic::aarch64_neon_uaddv : Intrinsic::aarch64_neon_saddv; 6144 Ty = Int32Ty; 6145 VTy = llvm::VectorType::get(Int16Ty, 4); 6146 llvm::Type *Tys[2] = { Ty, VTy }; 6147 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6148 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddv"); 6149 return Builder.CreateTrunc(Ops[0], Int16Ty); 6150 } 6151 case NEON::BI__builtin_neon_vaddvq_u8: 6152 usgn = true; 6153 // FALLTHROUGH 6154 case NEON::BI__builtin_neon_vaddvq_s8: { 6155 Int = usgn ? Intrinsic::aarch64_neon_uaddv : Intrinsic::aarch64_neon_saddv; 6156 Ty = Int32Ty; 6157 VTy = llvm::VectorType::get(Int8Ty, 16); 6158 llvm::Type *Tys[2] = { Ty, VTy }; 6159 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6160 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddv"); 6161 return Builder.CreateTrunc(Ops[0], Int8Ty); 6162 } 6163 case NEON::BI__builtin_neon_vaddvq_u16: 6164 usgn = true; 6165 // FALLTHROUGH 6166 case NEON::BI__builtin_neon_vaddvq_s16: { 6167 Int = usgn ? Intrinsic::aarch64_neon_uaddv : Intrinsic::aarch64_neon_saddv; 6168 Ty = Int32Ty; 6169 VTy = llvm::VectorType::get(Int16Ty, 8); 6170 llvm::Type *Tys[2] = { Ty, VTy }; 6171 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6172 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddv"); 6173 return Builder.CreateTrunc(Ops[0], Int16Ty); 6174 } 6175 case NEON::BI__builtin_neon_vmaxv_u8: { 6176 Int = Intrinsic::aarch64_neon_umaxv; 6177 Ty = Int32Ty; 6178 VTy = llvm::VectorType::get(Int8Ty, 8); 6179 llvm::Type *Tys[2] = { Ty, VTy }; 6180 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6181 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6182 return Builder.CreateTrunc(Ops[0], Int8Ty); 6183 } 6184 case NEON::BI__builtin_neon_vmaxv_u16: { 6185 Int = Intrinsic::aarch64_neon_umaxv; 6186 Ty = Int32Ty; 6187 VTy = llvm::VectorType::get(Int16Ty, 4); 6188 llvm::Type *Tys[2] = { Ty, VTy }; 6189 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6190 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6191 return Builder.CreateTrunc(Ops[0], Int16Ty); 6192 } 6193 case NEON::BI__builtin_neon_vmaxvq_u8: { 6194 Int = Intrinsic::aarch64_neon_umaxv; 6195 Ty = Int32Ty; 6196 VTy = llvm::VectorType::get(Int8Ty, 16); 6197 llvm::Type *Tys[2] = { Ty, VTy }; 6198 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6199 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6200 return Builder.CreateTrunc(Ops[0], Int8Ty); 6201 } 6202 case NEON::BI__builtin_neon_vmaxvq_u16: { 6203 Int = Intrinsic::aarch64_neon_umaxv; 6204 Ty = Int32Ty; 6205 VTy = llvm::VectorType::get(Int16Ty, 8); 6206 llvm::Type *Tys[2] = { Ty, VTy }; 6207 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6208 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6209 return Builder.CreateTrunc(Ops[0], Int16Ty); 6210 } 6211 case NEON::BI__builtin_neon_vmaxv_s8: { 6212 Int = Intrinsic::aarch64_neon_smaxv; 6213 Ty = Int32Ty; 6214 VTy = llvm::VectorType::get(Int8Ty, 8); 6215 llvm::Type *Tys[2] = { Ty, VTy }; 6216 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6217 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6218 return Builder.CreateTrunc(Ops[0], Int8Ty); 6219 } 6220 case NEON::BI__builtin_neon_vmaxv_s16: { 6221 Int = Intrinsic::aarch64_neon_smaxv; 6222 Ty = Int32Ty; 6223 VTy = llvm::VectorType::get(Int16Ty, 4); 6224 llvm::Type *Tys[2] = { Ty, VTy }; 6225 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6226 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6227 return Builder.CreateTrunc(Ops[0], Int16Ty); 6228 } 6229 case NEON::BI__builtin_neon_vmaxvq_s8: { 6230 Int = Intrinsic::aarch64_neon_smaxv; 6231 Ty = Int32Ty; 6232 VTy = llvm::VectorType::get(Int8Ty, 16); 6233 llvm::Type *Tys[2] = { Ty, VTy }; 6234 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6235 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6236 return Builder.CreateTrunc(Ops[0], Int8Ty); 6237 } 6238 case NEON::BI__builtin_neon_vmaxvq_s16: { 6239 Int = Intrinsic::aarch64_neon_smaxv; 6240 Ty = Int32Ty; 6241 VTy = llvm::VectorType::get(Int16Ty, 8); 6242 llvm::Type *Tys[2] = { Ty, VTy }; 6243 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6244 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vmaxv"); 6245 return Builder.CreateTrunc(Ops[0], Int16Ty); 6246 } 6247 case NEON::BI__builtin_neon_vminv_u8: { 6248 Int = Intrinsic::aarch64_neon_uminv; 6249 Ty = Int32Ty; 6250 VTy = llvm::VectorType::get(Int8Ty, 8); 6251 llvm::Type *Tys[2] = { Ty, VTy }; 6252 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6253 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6254 return Builder.CreateTrunc(Ops[0], Int8Ty); 6255 } 6256 case NEON::BI__builtin_neon_vminv_u16: { 6257 Int = Intrinsic::aarch64_neon_uminv; 6258 Ty = Int32Ty; 6259 VTy = llvm::VectorType::get(Int16Ty, 4); 6260 llvm::Type *Tys[2] = { Ty, VTy }; 6261 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6262 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6263 return Builder.CreateTrunc(Ops[0], Int16Ty); 6264 } 6265 case NEON::BI__builtin_neon_vminvq_u8: { 6266 Int = Intrinsic::aarch64_neon_uminv; 6267 Ty = Int32Ty; 6268 VTy = llvm::VectorType::get(Int8Ty, 16); 6269 llvm::Type *Tys[2] = { Ty, VTy }; 6270 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6271 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6272 return Builder.CreateTrunc(Ops[0], Int8Ty); 6273 } 6274 case NEON::BI__builtin_neon_vminvq_u16: { 6275 Int = Intrinsic::aarch64_neon_uminv; 6276 Ty = Int32Ty; 6277 VTy = llvm::VectorType::get(Int16Ty, 8); 6278 llvm::Type *Tys[2] = { Ty, VTy }; 6279 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6280 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6281 return Builder.CreateTrunc(Ops[0], Int16Ty); 6282 } 6283 case NEON::BI__builtin_neon_vminv_s8: { 6284 Int = Intrinsic::aarch64_neon_sminv; 6285 Ty = Int32Ty; 6286 VTy = llvm::VectorType::get(Int8Ty, 8); 6287 llvm::Type *Tys[2] = { Ty, VTy }; 6288 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6289 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6290 return Builder.CreateTrunc(Ops[0], Int8Ty); 6291 } 6292 case NEON::BI__builtin_neon_vminv_s16: { 6293 Int = Intrinsic::aarch64_neon_sminv; 6294 Ty = Int32Ty; 6295 VTy = llvm::VectorType::get(Int16Ty, 4); 6296 llvm::Type *Tys[2] = { Ty, VTy }; 6297 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6298 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6299 return Builder.CreateTrunc(Ops[0], Int16Ty); 6300 } 6301 case NEON::BI__builtin_neon_vminvq_s8: { 6302 Int = Intrinsic::aarch64_neon_sminv; 6303 Ty = Int32Ty; 6304 VTy = llvm::VectorType::get(Int8Ty, 16); 6305 llvm::Type *Tys[2] = { Ty, VTy }; 6306 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6307 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6308 return Builder.CreateTrunc(Ops[0], Int8Ty); 6309 } 6310 case NEON::BI__builtin_neon_vminvq_s16: { 6311 Int = Intrinsic::aarch64_neon_sminv; 6312 Ty = Int32Ty; 6313 VTy = llvm::VectorType::get(Int16Ty, 8); 6314 llvm::Type *Tys[2] = { Ty, VTy }; 6315 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6316 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vminv"); 6317 return Builder.CreateTrunc(Ops[0], Int16Ty); 6318 } 6319 case NEON::BI__builtin_neon_vmul_n_f64: { 6320 Ops[0] = Builder.CreateBitCast(Ops[0], DoubleTy); 6321 Value *RHS = Builder.CreateBitCast(EmitScalarExpr(E->getArg(1)), DoubleTy); 6322 return Builder.CreateFMul(Ops[0], RHS); 6323 } 6324 case NEON::BI__builtin_neon_vaddlv_u8: { 6325 Int = Intrinsic::aarch64_neon_uaddlv; 6326 Ty = Int32Ty; 6327 VTy = llvm::VectorType::get(Int8Ty, 8); 6328 llvm::Type *Tys[2] = { Ty, VTy }; 6329 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6330 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6331 return Builder.CreateTrunc(Ops[0], Int16Ty); 6332 } 6333 case NEON::BI__builtin_neon_vaddlv_u16: { 6334 Int = Intrinsic::aarch64_neon_uaddlv; 6335 Ty = Int32Ty; 6336 VTy = llvm::VectorType::get(Int16Ty, 4); 6337 llvm::Type *Tys[2] = { Ty, VTy }; 6338 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6339 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6340 } 6341 case NEON::BI__builtin_neon_vaddlvq_u8: { 6342 Int = Intrinsic::aarch64_neon_uaddlv; 6343 Ty = Int32Ty; 6344 VTy = llvm::VectorType::get(Int8Ty, 16); 6345 llvm::Type *Tys[2] = { Ty, VTy }; 6346 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6347 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6348 return Builder.CreateTrunc(Ops[0], Int16Ty); 6349 } 6350 case NEON::BI__builtin_neon_vaddlvq_u16: { 6351 Int = Intrinsic::aarch64_neon_uaddlv; 6352 Ty = Int32Ty; 6353 VTy = llvm::VectorType::get(Int16Ty, 8); 6354 llvm::Type *Tys[2] = { Ty, VTy }; 6355 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6356 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6357 } 6358 case NEON::BI__builtin_neon_vaddlv_s8: { 6359 Int = Intrinsic::aarch64_neon_saddlv; 6360 Ty = Int32Ty; 6361 VTy = llvm::VectorType::get(Int8Ty, 8); 6362 llvm::Type *Tys[2] = { Ty, VTy }; 6363 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6364 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6365 return Builder.CreateTrunc(Ops[0], Int16Ty); 6366 } 6367 case NEON::BI__builtin_neon_vaddlv_s16: { 6368 Int = Intrinsic::aarch64_neon_saddlv; 6369 Ty = Int32Ty; 6370 VTy = llvm::VectorType::get(Int16Ty, 4); 6371 llvm::Type *Tys[2] = { Ty, VTy }; 6372 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6373 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6374 } 6375 case NEON::BI__builtin_neon_vaddlvq_s8: { 6376 Int = Intrinsic::aarch64_neon_saddlv; 6377 Ty = Int32Ty; 6378 VTy = llvm::VectorType::get(Int8Ty, 16); 6379 llvm::Type *Tys[2] = { Ty, VTy }; 6380 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6381 Ops[0] = EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6382 return Builder.CreateTrunc(Ops[0], Int16Ty); 6383 } 6384 case NEON::BI__builtin_neon_vaddlvq_s16: { 6385 Int = Intrinsic::aarch64_neon_saddlv; 6386 Ty = Int32Ty; 6387 VTy = llvm::VectorType::get(Int16Ty, 8); 6388 llvm::Type *Tys[2] = { Ty, VTy }; 6389 Ops.push_back(EmitScalarExpr(E->getArg(0))); 6390 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, "vaddlv"); 6391 } 6392 case NEON::BI__builtin_neon_vsri_n_v: 6393 case NEON::BI__builtin_neon_vsriq_n_v: { 6394 Int = Intrinsic::aarch64_neon_vsri; 6395 llvm::Function *Intrin = CGM.getIntrinsic(Int, Ty); 6396 return EmitNeonCall(Intrin, Ops, "vsri_n"); 6397 } 6398 case NEON::BI__builtin_neon_vsli_n_v: 6399 case NEON::BI__builtin_neon_vsliq_n_v: { 6400 Int = Intrinsic::aarch64_neon_vsli; 6401 llvm::Function *Intrin = CGM.getIntrinsic(Int, Ty); 6402 return EmitNeonCall(Intrin, Ops, "vsli_n"); 6403 } 6404 case NEON::BI__builtin_neon_vsra_n_v: 6405 case NEON::BI__builtin_neon_vsraq_n_v: 6406 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6407 Ops[1] = EmitNeonRShiftImm(Ops[1], Ops[2], Ty, usgn, "vsra_n"); 6408 return Builder.CreateAdd(Ops[0], Ops[1]); 6409 case NEON::BI__builtin_neon_vrsra_n_v: 6410 case NEON::BI__builtin_neon_vrsraq_n_v: { 6411 Int = usgn ? Intrinsic::aarch64_neon_urshl : Intrinsic::aarch64_neon_srshl; 6412 SmallVector<llvm::Value*,2> TmpOps; 6413 TmpOps.push_back(Ops[1]); 6414 TmpOps.push_back(Ops[2]); 6415 Function* F = CGM.getIntrinsic(Int, Ty); 6416 llvm::Value *tmp = EmitNeonCall(F, TmpOps, "vrshr_n", 1, true); 6417 Ops[0] = Builder.CreateBitCast(Ops[0], VTy); 6418 return Builder.CreateAdd(Ops[0], tmp); 6419 } 6420 // FIXME: Sharing loads & stores with 32-bit is complicated by the absence 6421 // of an Align parameter here. 6422 case NEON::BI__builtin_neon_vld1_x2_v: 6423 case NEON::BI__builtin_neon_vld1q_x2_v: 6424 case NEON::BI__builtin_neon_vld1_x3_v: 6425 case NEON::BI__builtin_neon_vld1q_x3_v: 6426 case NEON::BI__builtin_neon_vld1_x4_v: 6427 case NEON::BI__builtin_neon_vld1q_x4_v: { 6428 llvm::Type *PTy = llvm::PointerType::getUnqual(VTy->getVectorElementType()); 6429 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6430 llvm::Type *Tys[2] = { VTy, PTy }; 6431 unsigned Int; 6432 switch (BuiltinID) { 6433 case NEON::BI__builtin_neon_vld1_x2_v: 6434 case NEON::BI__builtin_neon_vld1q_x2_v: 6435 Int = Intrinsic::aarch64_neon_ld1x2; 6436 break; 6437 case NEON::BI__builtin_neon_vld1_x3_v: 6438 case NEON::BI__builtin_neon_vld1q_x3_v: 6439 Int = Intrinsic::aarch64_neon_ld1x3; 6440 break; 6441 case NEON::BI__builtin_neon_vld1_x4_v: 6442 case NEON::BI__builtin_neon_vld1q_x4_v: 6443 Int = Intrinsic::aarch64_neon_ld1x4; 6444 break; 6445 } 6446 Function *F = CGM.getIntrinsic(Int, Tys); 6447 Ops[1] = Builder.CreateCall(F, Ops[1], "vld1xN"); 6448 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 6449 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6450 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6451 } 6452 case NEON::BI__builtin_neon_vst1_x2_v: 6453 case NEON::BI__builtin_neon_vst1q_x2_v: 6454 case NEON::BI__builtin_neon_vst1_x3_v: 6455 case NEON::BI__builtin_neon_vst1q_x3_v: 6456 case NEON::BI__builtin_neon_vst1_x4_v: 6457 case NEON::BI__builtin_neon_vst1q_x4_v: { 6458 llvm::Type *PTy = llvm::PointerType::getUnqual(VTy->getVectorElementType()); 6459 llvm::Type *Tys[2] = { VTy, PTy }; 6460 unsigned Int; 6461 switch (BuiltinID) { 6462 case NEON::BI__builtin_neon_vst1_x2_v: 6463 case NEON::BI__builtin_neon_vst1q_x2_v: 6464 Int = Intrinsic::aarch64_neon_st1x2; 6465 break; 6466 case NEON::BI__builtin_neon_vst1_x3_v: 6467 case NEON::BI__builtin_neon_vst1q_x3_v: 6468 Int = Intrinsic::aarch64_neon_st1x3; 6469 break; 6470 case NEON::BI__builtin_neon_vst1_x4_v: 6471 case NEON::BI__builtin_neon_vst1q_x4_v: 6472 Int = Intrinsic::aarch64_neon_st1x4; 6473 break; 6474 } 6475 std::rotate(Ops.begin(), Ops.begin() + 1, Ops.end()); 6476 return EmitNeonCall(CGM.getIntrinsic(Int, Tys), Ops, ""); 6477 } 6478 case NEON::BI__builtin_neon_vld1_v: 6479 case NEON::BI__builtin_neon_vld1q_v: 6480 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(VTy)); 6481 return Builder.CreateDefaultAlignedLoad(Ops[0]); 6482 case NEON::BI__builtin_neon_vst1_v: 6483 case NEON::BI__builtin_neon_vst1q_v: 6484 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(VTy)); 6485 Ops[1] = Builder.CreateBitCast(Ops[1], VTy); 6486 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6487 case NEON::BI__builtin_neon_vld1_lane_v: 6488 case NEON::BI__builtin_neon_vld1q_lane_v: 6489 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6490 Ty = llvm::PointerType::getUnqual(VTy->getElementType()); 6491 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6492 Ops[0] = Builder.CreateDefaultAlignedLoad(Ops[0]); 6493 return Builder.CreateInsertElement(Ops[1], Ops[0], Ops[2], "vld1_lane"); 6494 case NEON::BI__builtin_neon_vld1_dup_v: 6495 case NEON::BI__builtin_neon_vld1q_dup_v: { 6496 Value *V = UndefValue::get(Ty); 6497 Ty = llvm::PointerType::getUnqual(VTy->getElementType()); 6498 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6499 Ops[0] = Builder.CreateDefaultAlignedLoad(Ops[0]); 6500 llvm::Constant *CI = ConstantInt::get(Int32Ty, 0); 6501 Ops[0] = Builder.CreateInsertElement(V, Ops[0], CI); 6502 return EmitNeonSplat(Ops[0], CI); 6503 } 6504 case NEON::BI__builtin_neon_vst1_lane_v: 6505 case NEON::BI__builtin_neon_vst1q_lane_v: 6506 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6507 Ops[1] = Builder.CreateExtractElement(Ops[1], Ops[2]); 6508 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 6509 return Builder.CreateDefaultAlignedStore(Ops[1], 6510 Builder.CreateBitCast(Ops[0], Ty)); 6511 case NEON::BI__builtin_neon_vld2_v: 6512 case NEON::BI__builtin_neon_vld2q_v: { 6513 llvm::Type *PTy = llvm::PointerType::getUnqual(VTy); 6514 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6515 llvm::Type *Tys[2] = { VTy, PTy }; 6516 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld2, Tys); 6517 Ops[1] = Builder.CreateCall(F, Ops[1], "vld2"); 6518 Ops[0] = Builder.CreateBitCast(Ops[0], 6519 llvm::PointerType::getUnqual(Ops[1]->getType())); 6520 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6521 } 6522 case NEON::BI__builtin_neon_vld3_v: 6523 case NEON::BI__builtin_neon_vld3q_v: { 6524 llvm::Type *PTy = llvm::PointerType::getUnqual(VTy); 6525 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6526 llvm::Type *Tys[2] = { VTy, PTy }; 6527 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld3, Tys); 6528 Ops[1] = Builder.CreateCall(F, Ops[1], "vld3"); 6529 Ops[0] = Builder.CreateBitCast(Ops[0], 6530 llvm::PointerType::getUnqual(Ops[1]->getType())); 6531 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6532 } 6533 case NEON::BI__builtin_neon_vld4_v: 6534 case NEON::BI__builtin_neon_vld4q_v: { 6535 llvm::Type *PTy = llvm::PointerType::getUnqual(VTy); 6536 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6537 llvm::Type *Tys[2] = { VTy, PTy }; 6538 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld4, Tys); 6539 Ops[1] = Builder.CreateCall(F, Ops[1], "vld4"); 6540 Ops[0] = Builder.CreateBitCast(Ops[0], 6541 llvm::PointerType::getUnqual(Ops[1]->getType())); 6542 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6543 } 6544 case NEON::BI__builtin_neon_vld2_dup_v: 6545 case NEON::BI__builtin_neon_vld2q_dup_v: { 6546 llvm::Type *PTy = 6547 llvm::PointerType::getUnqual(VTy->getElementType()); 6548 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6549 llvm::Type *Tys[2] = { VTy, PTy }; 6550 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld2r, Tys); 6551 Ops[1] = Builder.CreateCall(F, Ops[1], "vld2"); 6552 Ops[0] = Builder.CreateBitCast(Ops[0], 6553 llvm::PointerType::getUnqual(Ops[1]->getType())); 6554 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6555 } 6556 case NEON::BI__builtin_neon_vld3_dup_v: 6557 case NEON::BI__builtin_neon_vld3q_dup_v: { 6558 llvm::Type *PTy = 6559 llvm::PointerType::getUnqual(VTy->getElementType()); 6560 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6561 llvm::Type *Tys[2] = { VTy, PTy }; 6562 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld3r, Tys); 6563 Ops[1] = Builder.CreateCall(F, Ops[1], "vld3"); 6564 Ops[0] = Builder.CreateBitCast(Ops[0], 6565 llvm::PointerType::getUnqual(Ops[1]->getType())); 6566 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6567 } 6568 case NEON::BI__builtin_neon_vld4_dup_v: 6569 case NEON::BI__builtin_neon_vld4q_dup_v: { 6570 llvm::Type *PTy = 6571 llvm::PointerType::getUnqual(VTy->getElementType()); 6572 Ops[1] = Builder.CreateBitCast(Ops[1], PTy); 6573 llvm::Type *Tys[2] = { VTy, PTy }; 6574 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld4r, Tys); 6575 Ops[1] = Builder.CreateCall(F, Ops[1], "vld4"); 6576 Ops[0] = Builder.CreateBitCast(Ops[0], 6577 llvm::PointerType::getUnqual(Ops[1]->getType())); 6578 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6579 } 6580 case NEON::BI__builtin_neon_vld2_lane_v: 6581 case NEON::BI__builtin_neon_vld2q_lane_v: { 6582 llvm::Type *Tys[2] = { VTy, Ops[1]->getType() }; 6583 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld2lane, Tys); 6584 Ops.push_back(Ops[1]); 6585 Ops.erase(Ops.begin()+1); 6586 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6587 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 6588 Ops[3] = Builder.CreateZExt(Ops[3], Int64Ty); 6589 Ops[1] = Builder.CreateCall(F, makeArrayRef(Ops).slice(1), "vld2_lane"); 6590 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 6591 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6592 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6593 } 6594 case NEON::BI__builtin_neon_vld3_lane_v: 6595 case NEON::BI__builtin_neon_vld3q_lane_v: { 6596 llvm::Type *Tys[2] = { VTy, Ops[1]->getType() }; 6597 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld3lane, Tys); 6598 Ops.push_back(Ops[1]); 6599 Ops.erase(Ops.begin()+1); 6600 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6601 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 6602 Ops[3] = Builder.CreateBitCast(Ops[3], Ty); 6603 Ops[4] = Builder.CreateZExt(Ops[4], Int64Ty); 6604 Ops[1] = Builder.CreateCall(F, makeArrayRef(Ops).slice(1), "vld3_lane"); 6605 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 6606 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6607 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6608 } 6609 case NEON::BI__builtin_neon_vld4_lane_v: 6610 case NEON::BI__builtin_neon_vld4q_lane_v: { 6611 llvm::Type *Tys[2] = { VTy, Ops[1]->getType() }; 6612 Function *F = CGM.getIntrinsic(Intrinsic::aarch64_neon_ld4lane, Tys); 6613 Ops.push_back(Ops[1]); 6614 Ops.erase(Ops.begin()+1); 6615 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6616 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 6617 Ops[3] = Builder.CreateBitCast(Ops[3], Ty); 6618 Ops[4] = Builder.CreateBitCast(Ops[4], Ty); 6619 Ops[5] = Builder.CreateZExt(Ops[5], Int64Ty); 6620 Ops[1] = Builder.CreateCall(F, makeArrayRef(Ops).slice(1), "vld4_lane"); 6621 Ty = llvm::PointerType::getUnqual(Ops[1]->getType()); 6622 Ops[0] = Builder.CreateBitCast(Ops[0], Ty); 6623 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 6624 } 6625 case NEON::BI__builtin_neon_vst2_v: 6626 case NEON::BI__builtin_neon_vst2q_v: { 6627 Ops.push_back(Ops[0]); 6628 Ops.erase(Ops.begin()); 6629 llvm::Type *Tys[2] = { VTy, Ops[2]->getType() }; 6630 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_st2, Tys), 6631 Ops, ""); 6632 } 6633 case NEON::BI__builtin_neon_vst2_lane_v: 6634 case NEON::BI__builtin_neon_vst2q_lane_v: { 6635 Ops.push_back(Ops[0]); 6636 Ops.erase(Ops.begin()); 6637 Ops[2] = Builder.CreateZExt(Ops[2], Int64Ty); 6638 llvm::Type *Tys[2] = { VTy, Ops[3]->getType() }; 6639 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_st2lane, Tys), 6640 Ops, ""); 6641 } 6642 case NEON::BI__builtin_neon_vst3_v: 6643 case NEON::BI__builtin_neon_vst3q_v: { 6644 Ops.push_back(Ops[0]); 6645 Ops.erase(Ops.begin()); 6646 llvm::Type *Tys[2] = { VTy, Ops[3]->getType() }; 6647 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_st3, Tys), 6648 Ops, ""); 6649 } 6650 case NEON::BI__builtin_neon_vst3_lane_v: 6651 case NEON::BI__builtin_neon_vst3q_lane_v: { 6652 Ops.push_back(Ops[0]); 6653 Ops.erase(Ops.begin()); 6654 Ops[3] = Builder.CreateZExt(Ops[3], Int64Ty); 6655 llvm::Type *Tys[2] = { VTy, Ops[4]->getType() }; 6656 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_st3lane, Tys), 6657 Ops, ""); 6658 } 6659 case NEON::BI__builtin_neon_vst4_v: 6660 case NEON::BI__builtin_neon_vst4q_v: { 6661 Ops.push_back(Ops[0]); 6662 Ops.erase(Ops.begin()); 6663 llvm::Type *Tys[2] = { VTy, Ops[4]->getType() }; 6664 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_st4, Tys), 6665 Ops, ""); 6666 } 6667 case NEON::BI__builtin_neon_vst4_lane_v: 6668 case NEON::BI__builtin_neon_vst4q_lane_v: { 6669 Ops.push_back(Ops[0]); 6670 Ops.erase(Ops.begin()); 6671 Ops[4] = Builder.CreateZExt(Ops[4], Int64Ty); 6672 llvm::Type *Tys[2] = { VTy, Ops[5]->getType() }; 6673 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_st4lane, Tys), 6674 Ops, ""); 6675 } 6676 case NEON::BI__builtin_neon_vtrn_v: 6677 case NEON::BI__builtin_neon_vtrnq_v: { 6678 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(Ty)); 6679 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6680 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 6681 Value *SV = nullptr; 6682 6683 for (unsigned vi = 0; vi != 2; ++vi) { 6684 SmallVector<uint32_t, 16> Indices; 6685 for (unsigned i = 0, e = VTy->getNumElements(); i != e; i += 2) { 6686 Indices.push_back(i+vi); 6687 Indices.push_back(i+e+vi); 6688 } 6689 Value *Addr = Builder.CreateConstInBoundsGEP1_32(Ty, Ops[0], vi); 6690 SV = Builder.CreateShuffleVector(Ops[1], Ops[2], Indices, "vtrn"); 6691 SV = Builder.CreateDefaultAlignedStore(SV, Addr); 6692 } 6693 return SV; 6694 } 6695 case NEON::BI__builtin_neon_vuzp_v: 6696 case NEON::BI__builtin_neon_vuzpq_v: { 6697 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(Ty)); 6698 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6699 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 6700 Value *SV = nullptr; 6701 6702 for (unsigned vi = 0; vi != 2; ++vi) { 6703 SmallVector<uint32_t, 16> Indices; 6704 for (unsigned i = 0, e = VTy->getNumElements(); i != e; ++i) 6705 Indices.push_back(2*i+vi); 6706 6707 Value *Addr = Builder.CreateConstInBoundsGEP1_32(Ty, Ops[0], vi); 6708 SV = Builder.CreateShuffleVector(Ops[1], Ops[2], Indices, "vuzp"); 6709 SV = Builder.CreateDefaultAlignedStore(SV, Addr); 6710 } 6711 return SV; 6712 } 6713 case NEON::BI__builtin_neon_vzip_v: 6714 case NEON::BI__builtin_neon_vzipq_v: { 6715 Ops[0] = Builder.CreateBitCast(Ops[0], llvm::PointerType::getUnqual(Ty)); 6716 Ops[1] = Builder.CreateBitCast(Ops[1], Ty); 6717 Ops[2] = Builder.CreateBitCast(Ops[2], Ty); 6718 Value *SV = nullptr; 6719 6720 for (unsigned vi = 0; vi != 2; ++vi) { 6721 SmallVector<uint32_t, 16> Indices; 6722 for (unsigned i = 0, e = VTy->getNumElements(); i != e; i += 2) { 6723 Indices.push_back((i + vi*e) >> 1); 6724 Indices.push_back(((i + vi*e) >> 1)+e); 6725 } 6726 Value *Addr = Builder.CreateConstInBoundsGEP1_32(Ty, Ops[0], vi); 6727 SV = Builder.CreateShuffleVector(Ops[1], Ops[2], Indices, "vzip"); 6728 SV = Builder.CreateDefaultAlignedStore(SV, Addr); 6729 } 6730 return SV; 6731 } 6732 case NEON::BI__builtin_neon_vqtbl1q_v: { 6733 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbl1, Ty), 6734 Ops, "vtbl1"); 6735 } 6736 case NEON::BI__builtin_neon_vqtbl2q_v: { 6737 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbl2, Ty), 6738 Ops, "vtbl2"); 6739 } 6740 case NEON::BI__builtin_neon_vqtbl3q_v: { 6741 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbl3, Ty), 6742 Ops, "vtbl3"); 6743 } 6744 case NEON::BI__builtin_neon_vqtbl4q_v: { 6745 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbl4, Ty), 6746 Ops, "vtbl4"); 6747 } 6748 case NEON::BI__builtin_neon_vqtbx1q_v: { 6749 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbx1, Ty), 6750 Ops, "vtbx1"); 6751 } 6752 case NEON::BI__builtin_neon_vqtbx2q_v: { 6753 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbx2, Ty), 6754 Ops, "vtbx2"); 6755 } 6756 case NEON::BI__builtin_neon_vqtbx3q_v: { 6757 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbx3, Ty), 6758 Ops, "vtbx3"); 6759 } 6760 case NEON::BI__builtin_neon_vqtbx4q_v: { 6761 return EmitNeonCall(CGM.getIntrinsic(Intrinsic::aarch64_neon_tbx4, Ty), 6762 Ops, "vtbx4"); 6763 } 6764 case NEON::BI__builtin_neon_vsqadd_v: 6765 case NEON::BI__builtin_neon_vsqaddq_v: { 6766 Int = Intrinsic::aarch64_neon_usqadd; 6767 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vsqadd"); 6768 } 6769 case NEON::BI__builtin_neon_vuqadd_v: 6770 case NEON::BI__builtin_neon_vuqaddq_v: { 6771 Int = Intrinsic::aarch64_neon_suqadd; 6772 return EmitNeonCall(CGM.getIntrinsic(Int, Ty), Ops, "vuqadd"); 6773 } 6774 } 6775 } 6776 6777 llvm::Value *CodeGenFunction:: 6778 BuildVector(ArrayRef<llvm::Value*> Ops) { 6779 assert((Ops.size() & (Ops.size() - 1)) == 0 && 6780 "Not a power-of-two sized vector!"); 6781 bool AllConstants = true; 6782 for (unsigned i = 0, e = Ops.size(); i != e && AllConstants; ++i) 6783 AllConstants &= isa<Constant>(Ops[i]); 6784 6785 // If this is a constant vector, create a ConstantVector. 6786 if (AllConstants) { 6787 SmallVector<llvm::Constant*, 16> CstOps; 6788 for (unsigned i = 0, e = Ops.size(); i != e; ++i) 6789 CstOps.push_back(cast<Constant>(Ops[i])); 6790 return llvm::ConstantVector::get(CstOps); 6791 } 6792 6793 // Otherwise, insertelement the values to build the vector. 6794 Value *Result = 6795 llvm::UndefValue::get(llvm::VectorType::get(Ops[0]->getType(), Ops.size())); 6796 6797 for (unsigned i = 0, e = Ops.size(); i != e; ++i) 6798 Result = Builder.CreateInsertElement(Result, Ops[i], Builder.getInt32(i)); 6799 6800 return Result; 6801 } 6802 6803 // Convert the mask from an integer type to a vector of i1. 6804 static Value *getMaskVecValue(CodeGenFunction &CGF, Value *Mask, 6805 unsigned NumElts) { 6806 6807 llvm::VectorType *MaskTy = llvm::VectorType::get(CGF.Builder.getInt1Ty(), 6808 cast<IntegerType>(Mask->getType())->getBitWidth()); 6809 Value *MaskVec = CGF.Builder.CreateBitCast(Mask, MaskTy); 6810 6811 // If we have less than 8 elements, then the starting mask was an i8 and 6812 // we need to extract down to the right number of elements. 6813 if (NumElts < 8) { 6814 uint32_t Indices[4]; 6815 for (unsigned i = 0; i != NumElts; ++i) 6816 Indices[i] = i; 6817 MaskVec = CGF.Builder.CreateShuffleVector(MaskVec, MaskVec, 6818 makeArrayRef(Indices, NumElts), 6819 "extract"); 6820 } 6821 return MaskVec; 6822 } 6823 6824 static Value *EmitX86MaskedStore(CodeGenFunction &CGF, 6825 SmallVectorImpl<Value *> &Ops, 6826 unsigned Align) { 6827 // Cast the pointer to right type. 6828 Ops[0] = CGF.Builder.CreateBitCast(Ops[0], 6829 llvm::PointerType::getUnqual(Ops[1]->getType())); 6830 6831 // If the mask is all ones just emit a regular store. 6832 if (const auto *C = dyn_cast<Constant>(Ops[2])) 6833 if (C->isAllOnesValue()) 6834 return CGF.Builder.CreateAlignedStore(Ops[1], Ops[0], Align); 6835 6836 Value *MaskVec = getMaskVecValue(CGF, Ops[2], 6837 Ops[1]->getType()->getVectorNumElements()); 6838 6839 return CGF.Builder.CreateMaskedStore(Ops[1], Ops[0], Align, MaskVec); 6840 } 6841 6842 static Value *EmitX86MaskedLoad(CodeGenFunction &CGF, 6843 SmallVectorImpl<Value *> &Ops, unsigned Align) { 6844 // Cast the pointer to right type. 6845 Ops[0] = CGF.Builder.CreateBitCast(Ops[0], 6846 llvm::PointerType::getUnqual(Ops[1]->getType())); 6847 6848 // If the mask is all ones just emit a regular store. 6849 if (const auto *C = dyn_cast<Constant>(Ops[2])) 6850 if (C->isAllOnesValue()) 6851 return CGF.Builder.CreateAlignedLoad(Ops[0], Align); 6852 6853 Value *MaskVec = getMaskVecValue(CGF, Ops[2], 6854 Ops[1]->getType()->getVectorNumElements()); 6855 6856 return CGF.Builder.CreateMaskedLoad(Ops[0], Align, MaskVec, Ops[1]); 6857 } 6858 6859 static Value *EmitX86SubVectorBroadcast(CodeGenFunction &CGF, 6860 SmallVectorImpl<Value *> &Ops, 6861 llvm::Type *DstTy, 6862 unsigned SrcSizeInBits, 6863 unsigned Align) { 6864 // Load the subvector. 6865 Ops[0] = CGF.Builder.CreateAlignedLoad(Ops[0], Align); 6866 6867 // Create broadcast mask. 6868 unsigned NumDstElts = DstTy->getVectorNumElements(); 6869 unsigned NumSrcElts = SrcSizeInBits / DstTy->getScalarSizeInBits(); 6870 6871 SmallVector<uint32_t, 8> Mask; 6872 for (unsigned i = 0; i != NumDstElts; i += NumSrcElts) 6873 for (unsigned j = 0; j != NumSrcElts; ++j) 6874 Mask.push_back(j); 6875 6876 return CGF.Builder.CreateShuffleVector(Ops[0], Ops[0], Mask, "subvecbcst"); 6877 } 6878 6879 static Value *EmitX86Select(CodeGenFunction &CGF, 6880 Value *Mask, Value *Op0, Value *Op1) { 6881 6882 // If the mask is all ones just return first argument. 6883 if (const auto *C = dyn_cast<Constant>(Mask)) 6884 if (C->isAllOnesValue()) 6885 return Op0; 6886 6887 Mask = getMaskVecValue(CGF, Mask, Op0->getType()->getVectorNumElements()); 6888 6889 return CGF.Builder.CreateSelect(Mask, Op0, Op1); 6890 } 6891 6892 static Value *EmitX86MaskedCompare(CodeGenFunction &CGF, unsigned CC, 6893 bool Signed, SmallVectorImpl<Value *> &Ops) { 6894 unsigned NumElts = Ops[0]->getType()->getVectorNumElements(); 6895 Value *Cmp; 6896 6897 if (CC == 3) { 6898 Cmp = Constant::getNullValue( 6899 llvm::VectorType::get(CGF.Builder.getInt1Ty(), NumElts)); 6900 } else if (CC == 7) { 6901 Cmp = Constant::getAllOnesValue( 6902 llvm::VectorType::get(CGF.Builder.getInt1Ty(), NumElts)); 6903 } else { 6904 ICmpInst::Predicate Pred; 6905 switch (CC) { 6906 default: llvm_unreachable("Unknown condition code"); 6907 case 0: Pred = ICmpInst::ICMP_EQ; break; 6908 case 1: Pred = Signed ? ICmpInst::ICMP_SLT : ICmpInst::ICMP_ULT; break; 6909 case 2: Pred = Signed ? ICmpInst::ICMP_SLE : ICmpInst::ICMP_ULE; break; 6910 case 4: Pred = ICmpInst::ICMP_NE; break; 6911 case 5: Pred = Signed ? ICmpInst::ICMP_SGE : ICmpInst::ICMP_UGE; break; 6912 case 6: Pred = Signed ? ICmpInst::ICMP_SGT : ICmpInst::ICMP_UGT; break; 6913 } 6914 Cmp = CGF.Builder.CreateICmp(Pred, Ops[0], Ops[1]); 6915 } 6916 6917 const auto *C = dyn_cast<Constant>(Ops.back()); 6918 if (!C || !C->isAllOnesValue()) 6919 Cmp = CGF.Builder.CreateAnd(Cmp, getMaskVecValue(CGF, Ops.back(), NumElts)); 6920 6921 if (NumElts < 8) { 6922 uint32_t Indices[8]; 6923 for (unsigned i = 0; i != NumElts; ++i) 6924 Indices[i] = i; 6925 for (unsigned i = NumElts; i != 8; ++i) 6926 Indices[i] = i % NumElts + NumElts; 6927 Cmp = CGF.Builder.CreateShuffleVector( 6928 Cmp, llvm::Constant::getNullValue(Cmp->getType()), Indices); 6929 } 6930 return CGF.Builder.CreateBitCast(Cmp, 6931 IntegerType::get(CGF.getLLVMContext(), 6932 std::max(NumElts, 8U))); 6933 } 6934 6935 Value *CodeGenFunction::EmitX86BuiltinExpr(unsigned BuiltinID, 6936 const CallExpr *E) { 6937 if (BuiltinID == X86::BI__builtin_ms_va_start || 6938 BuiltinID == X86::BI__builtin_ms_va_end) 6939 return EmitVAStartEnd(EmitMSVAListRef(E->getArg(0)).getPointer(), 6940 BuiltinID == X86::BI__builtin_ms_va_start); 6941 if (BuiltinID == X86::BI__builtin_ms_va_copy) { 6942 // Lower this manually. We can't reliably determine whether or not any 6943 // given va_copy() is for a Win64 va_list from the calling convention 6944 // alone, because it's legal to do this from a System V ABI function. 6945 // With opaque pointer types, we won't have enough information in LLVM 6946 // IR to determine this from the argument types, either. Best to do it 6947 // now, while we have enough information. 6948 Address DestAddr = EmitMSVAListRef(E->getArg(0)); 6949 Address SrcAddr = EmitMSVAListRef(E->getArg(1)); 6950 6951 llvm::Type *BPP = Int8PtrPtrTy; 6952 6953 DestAddr = Address(Builder.CreateBitCast(DestAddr.getPointer(), BPP, "cp"), 6954 DestAddr.getAlignment()); 6955 SrcAddr = Address(Builder.CreateBitCast(SrcAddr.getPointer(), BPP, "ap"), 6956 SrcAddr.getAlignment()); 6957 6958 Value *ArgPtr = Builder.CreateLoad(SrcAddr, "ap.val"); 6959 return Builder.CreateStore(ArgPtr, DestAddr); 6960 } 6961 6962 SmallVector<Value*, 4> Ops; 6963 6964 // Find out if any arguments are required to be integer constant expressions. 6965 unsigned ICEArguments = 0; 6966 ASTContext::GetBuiltinTypeError Error; 6967 getContext().GetBuiltinType(BuiltinID, Error, &ICEArguments); 6968 assert(Error == ASTContext::GE_None && "Should not codegen an error"); 6969 6970 for (unsigned i = 0, e = E->getNumArgs(); i != e; i++) { 6971 // If this is a normal argument, just emit it as a scalar. 6972 if ((ICEArguments & (1 << i)) == 0) { 6973 Ops.push_back(EmitScalarExpr(E->getArg(i))); 6974 continue; 6975 } 6976 6977 // If this is required to be a constant, constant fold it so that we know 6978 // that the generated intrinsic gets a ConstantInt. 6979 llvm::APSInt Result; 6980 bool IsConst = E->getArg(i)->isIntegerConstantExpr(Result, getContext()); 6981 assert(IsConst && "Constant arg isn't actually constant?"); (void)IsConst; 6982 Ops.push_back(llvm::ConstantInt::get(getLLVMContext(), Result)); 6983 } 6984 6985 // These exist so that the builtin that takes an immediate can be bounds 6986 // checked by clang to avoid passing bad immediates to the backend. Since 6987 // AVX has a larger immediate than SSE we would need separate builtins to 6988 // do the different bounds checking. Rather than create a clang specific 6989 // SSE only builtin, this implements eight separate builtins to match gcc 6990 // implementation. 6991 auto getCmpIntrinsicCall = [this, &Ops](Intrinsic::ID ID, unsigned Imm) { 6992 Ops.push_back(llvm::ConstantInt::get(Int8Ty, Imm)); 6993 llvm::Function *F = CGM.getIntrinsic(ID); 6994 return Builder.CreateCall(F, Ops); 6995 }; 6996 6997 // For the vector forms of FP comparisons, translate the builtins directly to 6998 // IR. 6999 // TODO: The builtins could be removed if the SSE header files used vector 7000 // extension comparisons directly (vector ordered/unordered may need 7001 // additional support via __builtin_isnan()). 7002 auto getVectorFCmpIR = [this, &Ops](CmpInst::Predicate Pred) { 7003 Value *Cmp = Builder.CreateFCmp(Pred, Ops[0], Ops[1]); 7004 llvm::VectorType *FPVecTy = cast<llvm::VectorType>(Ops[0]->getType()); 7005 llvm::VectorType *IntVecTy = llvm::VectorType::getInteger(FPVecTy); 7006 Value *Sext = Builder.CreateSExt(Cmp, IntVecTy); 7007 return Builder.CreateBitCast(Sext, FPVecTy); 7008 }; 7009 7010 switch (BuiltinID) { 7011 default: return nullptr; 7012 case X86::BI__builtin_cpu_supports: { 7013 const Expr *FeatureExpr = E->getArg(0)->IgnoreParenCasts(); 7014 StringRef FeatureStr = cast<StringLiteral>(FeatureExpr)->getString(); 7015 7016 // TODO: When/if this becomes more than x86 specific then use a TargetInfo 7017 // based mapping. 7018 // Processor features and mapping to processor feature value. 7019 enum X86Features { 7020 CMOV = 0, 7021 MMX, 7022 POPCNT, 7023 SSE, 7024 SSE2, 7025 SSE3, 7026 SSSE3, 7027 SSE4_1, 7028 SSE4_2, 7029 AVX, 7030 AVX2, 7031 SSE4_A, 7032 FMA4, 7033 XOP, 7034 FMA, 7035 AVX512F, 7036 BMI, 7037 BMI2, 7038 AES, 7039 PCLMUL, 7040 AVX512VL, 7041 AVX512BW, 7042 AVX512DQ, 7043 AVX512CD, 7044 AVX512ER, 7045 AVX512PF, 7046 AVX512VBMI, 7047 AVX512IFMA, 7048 MAX 7049 }; 7050 7051 X86Features Feature = StringSwitch<X86Features>(FeatureStr) 7052 .Case("cmov", X86Features::CMOV) 7053 .Case("mmx", X86Features::MMX) 7054 .Case("popcnt", X86Features::POPCNT) 7055 .Case("sse", X86Features::SSE) 7056 .Case("sse2", X86Features::SSE2) 7057 .Case("sse3", X86Features::SSE3) 7058 .Case("ssse3", X86Features::SSSE3) 7059 .Case("sse4.1", X86Features::SSE4_1) 7060 .Case("sse4.2", X86Features::SSE4_2) 7061 .Case("avx", X86Features::AVX) 7062 .Case("avx2", X86Features::AVX2) 7063 .Case("sse4a", X86Features::SSE4_A) 7064 .Case("fma4", X86Features::FMA4) 7065 .Case("xop", X86Features::XOP) 7066 .Case("fma", X86Features::FMA) 7067 .Case("avx512f", X86Features::AVX512F) 7068 .Case("bmi", X86Features::BMI) 7069 .Case("bmi2", X86Features::BMI2) 7070 .Case("aes", X86Features::AES) 7071 .Case("pclmul", X86Features::PCLMUL) 7072 .Case("avx512vl", X86Features::AVX512VL) 7073 .Case("avx512bw", X86Features::AVX512BW) 7074 .Case("avx512dq", X86Features::AVX512DQ) 7075 .Case("avx512cd", X86Features::AVX512CD) 7076 .Case("avx512er", X86Features::AVX512ER) 7077 .Case("avx512pf", X86Features::AVX512PF) 7078 .Case("avx512vbmi", X86Features::AVX512VBMI) 7079 .Case("avx512ifma", X86Features::AVX512IFMA) 7080 .Default(X86Features::MAX); 7081 assert(Feature != X86Features::MAX && "Invalid feature!"); 7082 7083 // Matching the struct layout from the compiler-rt/libgcc structure that is 7084 // filled in: 7085 // unsigned int __cpu_vendor; 7086 // unsigned int __cpu_type; 7087 // unsigned int __cpu_subtype; 7088 // unsigned int __cpu_features[1]; 7089 llvm::Type *STy = llvm::StructType::get( 7090 Int32Ty, Int32Ty, Int32Ty, llvm::ArrayType::get(Int32Ty, 1), nullptr); 7091 7092 // Grab the global __cpu_model. 7093 llvm::Constant *CpuModel = CGM.CreateRuntimeVariable(STy, "__cpu_model"); 7094 7095 // Grab the first (0th) element from the field __cpu_features off of the 7096 // global in the struct STy. 7097 Value *Idxs[] = { 7098 ConstantInt::get(Int32Ty, 0), 7099 ConstantInt::get(Int32Ty, 3), 7100 ConstantInt::get(Int32Ty, 0) 7101 }; 7102 Value *CpuFeatures = Builder.CreateGEP(STy, CpuModel, Idxs); 7103 Value *Features = Builder.CreateAlignedLoad(CpuFeatures, 7104 CharUnits::fromQuantity(4)); 7105 7106 // Check the value of the bit corresponding to the feature requested. 7107 Value *Bitset = Builder.CreateAnd( 7108 Features, llvm::ConstantInt::get(Int32Ty, 1ULL << Feature)); 7109 return Builder.CreateICmpNE(Bitset, llvm::ConstantInt::get(Int32Ty, 0)); 7110 } 7111 case X86::BI_mm_prefetch: { 7112 Value *Address = Ops[0]; 7113 Value *RW = ConstantInt::get(Int32Ty, 0); 7114 Value *Locality = Ops[1]; 7115 Value *Data = ConstantInt::get(Int32Ty, 1); 7116 Value *F = CGM.getIntrinsic(Intrinsic::prefetch); 7117 return Builder.CreateCall(F, {Address, RW, Locality, Data}); 7118 } 7119 case X86::BI_mm_clflush: { 7120 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse2_clflush), 7121 Ops[0]); 7122 } 7123 case X86::BI_mm_lfence: { 7124 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse2_lfence)); 7125 } 7126 case X86::BI_mm_mfence: { 7127 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse2_mfence)); 7128 } 7129 case X86::BI_mm_sfence: { 7130 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse_sfence)); 7131 } 7132 case X86::BI_mm_pause: { 7133 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse2_pause)); 7134 } 7135 case X86::BI__rdtsc: { 7136 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_rdtsc)); 7137 } 7138 case X86::BI__builtin_ia32_undef128: 7139 case X86::BI__builtin_ia32_undef256: 7140 case X86::BI__builtin_ia32_undef512: 7141 return UndefValue::get(ConvertType(E->getType())); 7142 case X86::BI__builtin_ia32_vec_init_v8qi: 7143 case X86::BI__builtin_ia32_vec_init_v4hi: 7144 case X86::BI__builtin_ia32_vec_init_v2si: 7145 return Builder.CreateBitCast(BuildVector(Ops), 7146 llvm::Type::getX86_MMXTy(getLLVMContext())); 7147 case X86::BI__builtin_ia32_vec_ext_v2si: 7148 return Builder.CreateExtractElement(Ops[0], 7149 llvm::ConstantInt::get(Ops[1]->getType(), 0)); 7150 case X86::BI_mm_setcsr: 7151 case X86::BI__builtin_ia32_ldmxcsr: { 7152 Address Tmp = CreateMemTemp(E->getArg(0)->getType()); 7153 Builder.CreateStore(Ops[0], Tmp); 7154 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse_ldmxcsr), 7155 Builder.CreateBitCast(Tmp.getPointer(), Int8PtrTy)); 7156 } 7157 case X86::BI_mm_getcsr: 7158 case X86::BI__builtin_ia32_stmxcsr: { 7159 Address Tmp = CreateMemTemp(E->getType()); 7160 Builder.CreateCall(CGM.getIntrinsic(Intrinsic::x86_sse_stmxcsr), 7161 Builder.CreateBitCast(Tmp.getPointer(), Int8PtrTy)); 7162 return Builder.CreateLoad(Tmp, "stmxcsr"); 7163 } 7164 case X86::BI__builtin_ia32_xsave: 7165 case X86::BI__builtin_ia32_xsave64: 7166 case X86::BI__builtin_ia32_xrstor: 7167 case X86::BI__builtin_ia32_xrstor64: 7168 case X86::BI__builtin_ia32_xsaveopt: 7169 case X86::BI__builtin_ia32_xsaveopt64: 7170 case X86::BI__builtin_ia32_xrstors: 7171 case X86::BI__builtin_ia32_xrstors64: 7172 case X86::BI__builtin_ia32_xsavec: 7173 case X86::BI__builtin_ia32_xsavec64: 7174 case X86::BI__builtin_ia32_xsaves: 7175 case X86::BI__builtin_ia32_xsaves64: { 7176 Intrinsic::ID ID; 7177 #define INTRINSIC_X86_XSAVE_ID(NAME) \ 7178 case X86::BI__builtin_ia32_##NAME: \ 7179 ID = Intrinsic::x86_##NAME; \ 7180 break 7181 switch (BuiltinID) { 7182 default: llvm_unreachable("Unsupported intrinsic!"); 7183 INTRINSIC_X86_XSAVE_ID(xsave); 7184 INTRINSIC_X86_XSAVE_ID(xsave64); 7185 INTRINSIC_X86_XSAVE_ID(xrstor); 7186 INTRINSIC_X86_XSAVE_ID(xrstor64); 7187 INTRINSIC_X86_XSAVE_ID(xsaveopt); 7188 INTRINSIC_X86_XSAVE_ID(xsaveopt64); 7189 INTRINSIC_X86_XSAVE_ID(xrstors); 7190 INTRINSIC_X86_XSAVE_ID(xrstors64); 7191 INTRINSIC_X86_XSAVE_ID(xsavec); 7192 INTRINSIC_X86_XSAVE_ID(xsavec64); 7193 INTRINSIC_X86_XSAVE_ID(xsaves); 7194 INTRINSIC_X86_XSAVE_ID(xsaves64); 7195 } 7196 #undef INTRINSIC_X86_XSAVE_ID 7197 Value *Mhi = Builder.CreateTrunc( 7198 Builder.CreateLShr(Ops[1], ConstantInt::get(Int64Ty, 32)), Int32Ty); 7199 Value *Mlo = Builder.CreateTrunc(Ops[1], Int32Ty); 7200 Ops[1] = Mhi; 7201 Ops.push_back(Mlo); 7202 return Builder.CreateCall(CGM.getIntrinsic(ID), Ops); 7203 } 7204 case X86::BI__builtin_ia32_storedqudi128_mask: 7205 case X86::BI__builtin_ia32_storedqusi128_mask: 7206 case X86::BI__builtin_ia32_storedquhi128_mask: 7207 case X86::BI__builtin_ia32_storedquqi128_mask: 7208 case X86::BI__builtin_ia32_storeupd128_mask: 7209 case X86::BI__builtin_ia32_storeups128_mask: 7210 case X86::BI__builtin_ia32_storedqudi256_mask: 7211 case X86::BI__builtin_ia32_storedqusi256_mask: 7212 case X86::BI__builtin_ia32_storedquhi256_mask: 7213 case X86::BI__builtin_ia32_storedquqi256_mask: 7214 case X86::BI__builtin_ia32_storeupd256_mask: 7215 case X86::BI__builtin_ia32_storeups256_mask: 7216 case X86::BI__builtin_ia32_storedqudi512_mask: 7217 case X86::BI__builtin_ia32_storedqusi512_mask: 7218 case X86::BI__builtin_ia32_storedquhi512_mask: 7219 case X86::BI__builtin_ia32_storedquqi512_mask: 7220 case X86::BI__builtin_ia32_storeupd512_mask: 7221 case X86::BI__builtin_ia32_storeups512_mask: 7222 return EmitX86MaskedStore(*this, Ops, 1); 7223 7224 case X86::BI__builtin_ia32_movdqa32store128_mask: 7225 case X86::BI__builtin_ia32_movdqa64store128_mask: 7226 case X86::BI__builtin_ia32_storeaps128_mask: 7227 case X86::BI__builtin_ia32_storeapd128_mask: 7228 case X86::BI__builtin_ia32_movdqa32store256_mask: 7229 case X86::BI__builtin_ia32_movdqa64store256_mask: 7230 case X86::BI__builtin_ia32_storeaps256_mask: 7231 case X86::BI__builtin_ia32_storeapd256_mask: 7232 case X86::BI__builtin_ia32_movdqa32store512_mask: 7233 case X86::BI__builtin_ia32_movdqa64store512_mask: 7234 case X86::BI__builtin_ia32_storeaps512_mask: 7235 case X86::BI__builtin_ia32_storeapd512_mask: { 7236 unsigned Align = 7237 getContext().getTypeAlignInChars(E->getArg(1)->getType()).getQuantity(); 7238 return EmitX86MaskedStore(*this, Ops, Align); 7239 } 7240 case X86::BI__builtin_ia32_loadups128_mask: 7241 case X86::BI__builtin_ia32_loadups256_mask: 7242 case X86::BI__builtin_ia32_loadups512_mask: 7243 case X86::BI__builtin_ia32_loadupd128_mask: 7244 case X86::BI__builtin_ia32_loadupd256_mask: 7245 case X86::BI__builtin_ia32_loadupd512_mask: 7246 case X86::BI__builtin_ia32_loaddquqi128_mask: 7247 case X86::BI__builtin_ia32_loaddquqi256_mask: 7248 case X86::BI__builtin_ia32_loaddquqi512_mask: 7249 case X86::BI__builtin_ia32_loaddquhi128_mask: 7250 case X86::BI__builtin_ia32_loaddquhi256_mask: 7251 case X86::BI__builtin_ia32_loaddquhi512_mask: 7252 case X86::BI__builtin_ia32_loaddqusi128_mask: 7253 case X86::BI__builtin_ia32_loaddqusi256_mask: 7254 case X86::BI__builtin_ia32_loaddqusi512_mask: 7255 case X86::BI__builtin_ia32_loaddqudi128_mask: 7256 case X86::BI__builtin_ia32_loaddqudi256_mask: 7257 case X86::BI__builtin_ia32_loaddqudi512_mask: 7258 return EmitX86MaskedLoad(*this, Ops, 1); 7259 7260 case X86::BI__builtin_ia32_loadaps128_mask: 7261 case X86::BI__builtin_ia32_loadaps256_mask: 7262 case X86::BI__builtin_ia32_loadaps512_mask: 7263 case X86::BI__builtin_ia32_loadapd128_mask: 7264 case X86::BI__builtin_ia32_loadapd256_mask: 7265 case X86::BI__builtin_ia32_loadapd512_mask: 7266 case X86::BI__builtin_ia32_movdqa32load128_mask: 7267 case X86::BI__builtin_ia32_movdqa32load256_mask: 7268 case X86::BI__builtin_ia32_movdqa32load512_mask: 7269 case X86::BI__builtin_ia32_movdqa64load128_mask: 7270 case X86::BI__builtin_ia32_movdqa64load256_mask: 7271 case X86::BI__builtin_ia32_movdqa64load512_mask: { 7272 unsigned Align = 7273 getContext().getTypeAlignInChars(E->getArg(1)->getType()).getQuantity(); 7274 return EmitX86MaskedLoad(*this, Ops, Align); 7275 } 7276 7277 case X86::BI__builtin_ia32_vbroadcastf128_pd256: 7278 case X86::BI__builtin_ia32_vbroadcastf128_ps256: { 7279 llvm::Type *DstTy = ConvertType(E->getType()); 7280 return EmitX86SubVectorBroadcast(*this, Ops, DstTy, 128, 1); 7281 } 7282 7283 case X86::BI__builtin_ia32_storehps: 7284 case X86::BI__builtin_ia32_storelps: { 7285 llvm::Type *PtrTy = llvm::PointerType::getUnqual(Int64Ty); 7286 llvm::Type *VecTy = llvm::VectorType::get(Int64Ty, 2); 7287 7288 // cast val v2i64 7289 Ops[1] = Builder.CreateBitCast(Ops[1], VecTy, "cast"); 7290 7291 // extract (0, 1) 7292 unsigned Index = BuiltinID == X86::BI__builtin_ia32_storelps ? 0 : 1; 7293 llvm::Value *Idx = llvm::ConstantInt::get(SizeTy, Index); 7294 Ops[1] = Builder.CreateExtractElement(Ops[1], Idx, "extract"); 7295 7296 // cast pointer to i64 & store 7297 Ops[0] = Builder.CreateBitCast(Ops[0], PtrTy); 7298 return Builder.CreateDefaultAlignedStore(Ops[1], Ops[0]); 7299 } 7300 case X86::BI__builtin_ia32_palignr128: 7301 case X86::BI__builtin_ia32_palignr256: 7302 case X86::BI__builtin_ia32_palignr128_mask: 7303 case X86::BI__builtin_ia32_palignr256_mask: 7304 case X86::BI__builtin_ia32_palignr512_mask: { 7305 unsigned ShiftVal = cast<llvm::ConstantInt>(Ops[2])->getZExtValue(); 7306 7307 unsigned NumElts = Ops[0]->getType()->getVectorNumElements(); 7308 assert(NumElts % 16 == 0); 7309 7310 // If palignr is shifting the pair of vectors more than the size of two 7311 // lanes, emit zero. 7312 if (ShiftVal >= 32) 7313 return llvm::Constant::getNullValue(ConvertType(E->getType())); 7314 7315 // If palignr is shifting the pair of input vectors more than one lane, 7316 // but less than two lanes, convert to shifting in zeroes. 7317 if (ShiftVal > 16) { 7318 ShiftVal -= 16; 7319 Ops[1] = Ops[0]; 7320 Ops[0] = llvm::Constant::getNullValue(Ops[0]->getType()); 7321 } 7322 7323 uint32_t Indices[64]; 7324 // 256-bit palignr operates on 128-bit lanes so we need to handle that 7325 for (unsigned l = 0; l != NumElts; l += 16) { 7326 for (unsigned i = 0; i != 16; ++i) { 7327 unsigned Idx = ShiftVal + i; 7328 if (Idx >= 16) 7329 Idx += NumElts - 16; // End of lane, switch operand. 7330 Indices[l + i] = Idx + l; 7331 } 7332 } 7333 7334 Value *Align = Builder.CreateShuffleVector(Ops[1], Ops[0], 7335 makeArrayRef(Indices, NumElts), 7336 "palignr"); 7337 7338 // If this isn't a masked builtin, just return the align operation. 7339 if (Ops.size() == 3) 7340 return Align; 7341 7342 return EmitX86Select(*this, Ops[4], Align, Ops[3]); 7343 } 7344 7345 case X86::BI__builtin_ia32_movnti: 7346 case X86::BI__builtin_ia32_movnti64: { 7347 llvm::MDNode *Node = llvm::MDNode::get( 7348 getLLVMContext(), llvm::ConstantAsMetadata::get(Builder.getInt32(1))); 7349 7350 // Convert the type of the pointer to a pointer to the stored type. 7351 Value *BC = Builder.CreateBitCast(Ops[0], 7352 llvm::PointerType::getUnqual(Ops[1]->getType()), 7353 "cast"); 7354 StoreInst *SI = Builder.CreateDefaultAlignedStore(Ops[1], BC); 7355 SI->setMetadata(CGM.getModule().getMDKindID("nontemporal"), Node); 7356 7357 // No alignment for scalar intrinsic store. 7358 SI->setAlignment(1); 7359 return SI; 7360 } 7361 case X86::BI__builtin_ia32_movntsd: 7362 case X86::BI__builtin_ia32_movntss: { 7363 llvm::MDNode *Node = llvm::MDNode::get( 7364 getLLVMContext(), llvm::ConstantAsMetadata::get(Builder.getInt32(1))); 7365 7366 // Extract the 0'th element of the source vector. 7367 Value *Scl = Builder.CreateExtractElement(Ops[1], (uint64_t)0, "extract"); 7368 7369 // Convert the type of the pointer to a pointer to the stored type. 7370 Value *BC = Builder.CreateBitCast(Ops[0], 7371 llvm::PointerType::getUnqual(Scl->getType()), 7372 "cast"); 7373 7374 // Unaligned nontemporal store of the scalar value. 7375 StoreInst *SI = Builder.CreateDefaultAlignedStore(Scl, BC); 7376 SI->setMetadata(CGM.getModule().getMDKindID("nontemporal"), Node); 7377 SI->setAlignment(1); 7378 return SI; 7379 } 7380 7381 case X86::BI__builtin_ia32_selectb_128: 7382 case X86::BI__builtin_ia32_selectb_256: 7383 case X86::BI__builtin_ia32_selectb_512: 7384 case X86::BI__builtin_ia32_selectw_128: 7385 case X86::BI__builtin_ia32_selectw_256: 7386 case X86::BI__builtin_ia32_selectw_512: 7387 case X86::BI__builtin_ia32_selectd_128: 7388 case X86::BI__builtin_ia32_selectd_256: 7389 case X86::BI__builtin_ia32_selectd_512: 7390 case X86::BI__builtin_ia32_selectq_128: 7391 case X86::BI__builtin_ia32_selectq_256: 7392 case X86::BI__builtin_ia32_selectq_512: 7393 case X86::BI__builtin_ia32_selectps_128: 7394 case X86::BI__builtin_ia32_selectps_256: 7395 case X86::BI__builtin_ia32_selectps_512: 7396 case X86::BI__builtin_ia32_selectpd_128: 7397 case X86::BI__builtin_ia32_selectpd_256: 7398 case X86::BI__builtin_ia32_selectpd_512: 7399 return EmitX86Select(*this, Ops[0], Ops[1], Ops[2]); 7400 case X86::BI__builtin_ia32_pcmpeqb128_mask: 7401 case X86::BI__builtin_ia32_pcmpeqb256_mask: 7402 case X86::BI__builtin_ia32_pcmpeqb512_mask: 7403 case X86::BI__builtin_ia32_pcmpeqw128_mask: 7404 case X86::BI__builtin_ia32_pcmpeqw256_mask: 7405 case X86::BI__builtin_ia32_pcmpeqw512_mask: 7406 case X86::BI__builtin_ia32_pcmpeqd128_mask: 7407 case X86::BI__builtin_ia32_pcmpeqd256_mask: 7408 case X86::BI__builtin_ia32_pcmpeqd512_mask: 7409 case X86::BI__builtin_ia32_pcmpeqq128_mask: 7410 case X86::BI__builtin_ia32_pcmpeqq256_mask: 7411 case X86::BI__builtin_ia32_pcmpeqq512_mask: 7412 return EmitX86MaskedCompare(*this, 0, false, Ops); 7413 case X86::BI__builtin_ia32_pcmpgtb128_mask: 7414 case X86::BI__builtin_ia32_pcmpgtb256_mask: 7415 case X86::BI__builtin_ia32_pcmpgtb512_mask: 7416 case X86::BI__builtin_ia32_pcmpgtw128_mask: 7417 case X86::BI__builtin_ia32_pcmpgtw256_mask: 7418 case X86::BI__builtin_ia32_pcmpgtw512_mask: 7419 case X86::BI__builtin_ia32_pcmpgtd128_mask: 7420 case X86::BI__builtin_ia32_pcmpgtd256_mask: 7421 case X86::BI__builtin_ia32_pcmpgtd512_mask: 7422 case X86::BI__builtin_ia32_pcmpgtq128_mask: 7423 case X86::BI__builtin_ia32_pcmpgtq256_mask: 7424 case X86::BI__builtin_ia32_pcmpgtq512_mask: 7425 return EmitX86MaskedCompare(*this, 6, true, Ops); 7426 case X86::BI__builtin_ia32_cmpb128_mask: 7427 case X86::BI__builtin_ia32_cmpb256_mask: 7428 case X86::BI__builtin_ia32_cmpb512_mask: 7429 case X86::BI__builtin_ia32_cmpw128_mask: 7430 case X86::BI__builtin_ia32_cmpw256_mask: 7431 case X86::BI__builtin_ia32_cmpw512_mask: 7432 case X86::BI__builtin_ia32_cmpd128_mask: 7433 case X86::BI__builtin_ia32_cmpd256_mask: 7434 case X86::BI__builtin_ia32_cmpd512_mask: 7435 case X86::BI__builtin_ia32_cmpq128_mask: 7436 case X86::BI__builtin_ia32_cmpq256_mask: 7437 case X86::BI__builtin_ia32_cmpq512_mask: { 7438 unsigned CC = cast<llvm::ConstantInt>(Ops[2])->getZExtValue() & 0x7; 7439 return EmitX86MaskedCompare(*this, CC, true, Ops); 7440 } 7441 case X86::BI__builtin_ia32_ucmpb128_mask: 7442 case X86::BI__builtin_ia32_ucmpb256_mask: 7443 case X86::BI__builtin_ia32_ucmpb512_mask: 7444 case X86::BI__builtin_ia32_ucmpw128_mask: 7445 case X86::BI__builtin_ia32_ucmpw256_mask: 7446 case X86::BI__builtin_ia32_ucmpw512_mask: 7447 case X86::BI__builtin_ia32_ucmpd128_mask: 7448 case X86::BI__builtin_ia32_ucmpd256_mask: 7449 case X86::BI__builtin_ia32_ucmpd512_mask: 7450 case X86::BI__builtin_ia32_ucmpq128_mask: 7451 case X86::BI__builtin_ia32_ucmpq256_mask: 7452 case X86::BI__builtin_ia32_ucmpq512_mask: { 7453 unsigned CC = cast<llvm::ConstantInt>(Ops[2])->getZExtValue() & 0x7; 7454 return EmitX86MaskedCompare(*this, CC, false, Ops); 7455 } 7456 7457 case X86::BI__builtin_ia32_vplzcntd_128_mask: 7458 case X86::BI__builtin_ia32_vplzcntd_256_mask: 7459 case X86::BI__builtin_ia32_vplzcntd_512_mask: 7460 case X86::BI__builtin_ia32_vplzcntq_128_mask: 7461 case X86::BI__builtin_ia32_vplzcntq_256_mask: 7462 case X86::BI__builtin_ia32_vplzcntq_512_mask: { 7463 Function *F = CGM.getIntrinsic(Intrinsic::ctlz, Ops[0]->getType()); 7464 return EmitX86Select(*this, Ops[2], 7465 Builder.CreateCall(F, {Ops[0],Builder.getInt1(false)}), 7466 Ops[1]); 7467 } 7468 7469 // TODO: Handle 64/512-bit vector widths of min/max. 7470 case X86::BI__builtin_ia32_pmaxsb128: 7471 case X86::BI__builtin_ia32_pmaxsw128: 7472 case X86::BI__builtin_ia32_pmaxsd128: 7473 case X86::BI__builtin_ia32_pmaxsb256: 7474 case X86::BI__builtin_ia32_pmaxsw256: 7475 case X86::BI__builtin_ia32_pmaxsd256: { 7476 Value *Cmp = Builder.CreateICmp(ICmpInst::ICMP_SGT, Ops[0], Ops[1]); 7477 return Builder.CreateSelect(Cmp, Ops[0], Ops[1]); 7478 } 7479 case X86::BI__builtin_ia32_pmaxub128: 7480 case X86::BI__builtin_ia32_pmaxuw128: 7481 case X86::BI__builtin_ia32_pmaxud128: 7482 case X86::BI__builtin_ia32_pmaxub256: 7483 case X86::BI__builtin_ia32_pmaxuw256: 7484 case X86::BI__builtin_ia32_pmaxud256: { 7485 Value *Cmp = Builder.CreateICmp(ICmpInst::ICMP_UGT, Ops[0], Ops[1]); 7486 return Builder.CreateSelect(Cmp, Ops[0], Ops[1]); 7487 } 7488 case X86::BI__builtin_ia32_pminsb128: 7489 case X86::BI__builtin_ia32_pminsw128: 7490 case X86::BI__builtin_ia32_pminsd128: 7491 case X86::BI__builtin_ia32_pminsb256: 7492 case X86::BI__builtin_ia32_pminsw256: 7493 case X86::BI__builtin_ia32_pminsd256: { 7494 Value *Cmp = Builder.CreateICmp(ICmpInst::ICMP_SLT, Ops[0], Ops[1]); 7495 return Builder.CreateSelect(Cmp, Ops[0], Ops[1]); 7496 } 7497 case X86::BI__builtin_ia32_pminub128: 7498 case X86::BI__builtin_ia32_pminuw128: 7499 case X86::BI__builtin_ia32_pminud128: 7500 case X86::BI__builtin_ia32_pminub256: 7501 case X86::BI__builtin_ia32_pminuw256: 7502 case X86::BI__builtin_ia32_pminud256: { 7503 Value *Cmp = Builder.CreateICmp(ICmpInst::ICMP_ULT, Ops[0], Ops[1]); 7504 return Builder.CreateSelect(Cmp, Ops[0], Ops[1]); 7505 } 7506 7507 // 3DNow! 7508 case X86::BI__builtin_ia32_pswapdsf: 7509 case X86::BI__builtin_ia32_pswapdsi: { 7510 llvm::Type *MMXTy = llvm::Type::getX86_MMXTy(getLLVMContext()); 7511 Ops[0] = Builder.CreateBitCast(Ops[0], MMXTy, "cast"); 7512 llvm::Function *F = CGM.getIntrinsic(Intrinsic::x86_3dnowa_pswapd); 7513 return Builder.CreateCall(F, Ops, "pswapd"); 7514 } 7515 case X86::BI__builtin_ia32_rdrand16_step: 7516 case X86::BI__builtin_ia32_rdrand32_step: 7517 case X86::BI__builtin_ia32_rdrand64_step: 7518 case X86::BI__builtin_ia32_rdseed16_step: 7519 case X86::BI__builtin_ia32_rdseed32_step: 7520 case X86::BI__builtin_ia32_rdseed64_step: { 7521 Intrinsic::ID ID; 7522 switch (BuiltinID) { 7523 default: llvm_unreachable("Unsupported intrinsic!"); 7524 case X86::BI__builtin_ia32_rdrand16_step: 7525 ID = Intrinsic::x86_rdrand_16; 7526 break; 7527 case X86::BI__builtin_ia32_rdrand32_step: 7528 ID = Intrinsic::x86_rdrand_32; 7529 break; 7530 case X86::BI__builtin_ia32_rdrand64_step: 7531 ID = Intrinsic::x86_rdrand_64; 7532 break; 7533 case X86::BI__builtin_ia32_rdseed16_step: 7534 ID = Intrinsic::x86_rdseed_16; 7535 break; 7536 case X86::BI__builtin_ia32_rdseed32_step: 7537 ID = Intrinsic::x86_rdseed_32; 7538 break; 7539 case X86::BI__builtin_ia32_rdseed64_step: 7540 ID = Intrinsic::x86_rdseed_64; 7541 break; 7542 } 7543 7544 Value *Call = Builder.CreateCall(CGM.getIntrinsic(ID)); 7545 Builder.CreateDefaultAlignedStore(Builder.CreateExtractValue(Call, 0), 7546 Ops[0]); 7547 return Builder.CreateExtractValue(Call, 1); 7548 } 7549 7550 // SSE packed comparison intrinsics 7551 case X86::BI__builtin_ia32_cmpeqps: 7552 case X86::BI__builtin_ia32_cmpeqpd: 7553 return getVectorFCmpIR(CmpInst::FCMP_OEQ); 7554 case X86::BI__builtin_ia32_cmpltps: 7555 case X86::BI__builtin_ia32_cmpltpd: 7556 return getVectorFCmpIR(CmpInst::FCMP_OLT); 7557 case X86::BI__builtin_ia32_cmpleps: 7558 case X86::BI__builtin_ia32_cmplepd: 7559 return getVectorFCmpIR(CmpInst::FCMP_OLE); 7560 case X86::BI__builtin_ia32_cmpunordps: 7561 case X86::BI__builtin_ia32_cmpunordpd: 7562 return getVectorFCmpIR(CmpInst::FCMP_UNO); 7563 case X86::BI__builtin_ia32_cmpneqps: 7564 case X86::BI__builtin_ia32_cmpneqpd: 7565 return getVectorFCmpIR(CmpInst::FCMP_UNE); 7566 case X86::BI__builtin_ia32_cmpnltps: 7567 case X86::BI__builtin_ia32_cmpnltpd: 7568 return getVectorFCmpIR(CmpInst::FCMP_UGE); 7569 case X86::BI__builtin_ia32_cmpnleps: 7570 case X86::BI__builtin_ia32_cmpnlepd: 7571 return getVectorFCmpIR(CmpInst::FCMP_UGT); 7572 case X86::BI__builtin_ia32_cmpordps: 7573 case X86::BI__builtin_ia32_cmpordpd: 7574 return getVectorFCmpIR(CmpInst::FCMP_ORD); 7575 case X86::BI__builtin_ia32_cmpps: 7576 case X86::BI__builtin_ia32_cmpps256: 7577 case X86::BI__builtin_ia32_cmppd: 7578 case X86::BI__builtin_ia32_cmppd256: { 7579 unsigned CC = cast<llvm::ConstantInt>(Ops[2])->getZExtValue(); 7580 // If this one of the SSE immediates, we can use native IR. 7581 if (CC < 8) { 7582 FCmpInst::Predicate Pred; 7583 switch (CC) { 7584 case 0: Pred = FCmpInst::FCMP_OEQ; break; 7585 case 1: Pred = FCmpInst::FCMP_OLT; break; 7586 case 2: Pred = FCmpInst::FCMP_OLE; break; 7587 case 3: Pred = FCmpInst::FCMP_UNO; break; 7588 case 4: Pred = FCmpInst::FCMP_UNE; break; 7589 case 5: Pred = FCmpInst::FCMP_UGE; break; 7590 case 6: Pred = FCmpInst::FCMP_UGT; break; 7591 case 7: Pred = FCmpInst::FCMP_ORD; break; 7592 } 7593 return getVectorFCmpIR(Pred); 7594 } 7595 7596 // We can't handle 8-31 immediates with native IR, use the intrinsic. 7597 Intrinsic::ID ID; 7598 switch (BuiltinID) { 7599 default: llvm_unreachable("Unsupported intrinsic!"); 7600 case X86::BI__builtin_ia32_cmpps: 7601 ID = Intrinsic::x86_sse_cmp_ps; 7602 break; 7603 case X86::BI__builtin_ia32_cmpps256: 7604 ID = Intrinsic::x86_avx_cmp_ps_256; 7605 break; 7606 case X86::BI__builtin_ia32_cmppd: 7607 ID = Intrinsic::x86_sse2_cmp_pd; 7608 break; 7609 case X86::BI__builtin_ia32_cmppd256: 7610 ID = Intrinsic::x86_avx_cmp_pd_256; 7611 break; 7612 } 7613 7614 return Builder.CreateCall(CGM.getIntrinsic(ID), Ops); 7615 } 7616 7617 // SSE scalar comparison intrinsics 7618 case X86::BI__builtin_ia32_cmpeqss: 7619 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 0); 7620 case X86::BI__builtin_ia32_cmpltss: 7621 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 1); 7622 case X86::BI__builtin_ia32_cmpless: 7623 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 2); 7624 case X86::BI__builtin_ia32_cmpunordss: 7625 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 3); 7626 case X86::BI__builtin_ia32_cmpneqss: 7627 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 4); 7628 case X86::BI__builtin_ia32_cmpnltss: 7629 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 5); 7630 case X86::BI__builtin_ia32_cmpnless: 7631 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 6); 7632 case X86::BI__builtin_ia32_cmpordss: 7633 return getCmpIntrinsicCall(Intrinsic::x86_sse_cmp_ss, 7); 7634 case X86::BI__builtin_ia32_cmpeqsd: 7635 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 0); 7636 case X86::BI__builtin_ia32_cmpltsd: 7637 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 1); 7638 case X86::BI__builtin_ia32_cmplesd: 7639 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 2); 7640 case X86::BI__builtin_ia32_cmpunordsd: 7641 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 3); 7642 case X86::BI__builtin_ia32_cmpneqsd: 7643 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 4); 7644 case X86::BI__builtin_ia32_cmpnltsd: 7645 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 5); 7646 case X86::BI__builtin_ia32_cmpnlesd: 7647 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 6); 7648 case X86::BI__builtin_ia32_cmpordsd: 7649 return getCmpIntrinsicCall(Intrinsic::x86_sse2_cmp_sd, 7); 7650 7651 case X86::BI__emul: 7652 case X86::BI__emulu: { 7653 llvm::Type *Int64Ty = llvm::IntegerType::get(getLLVMContext(), 64); 7654 bool isSigned = (BuiltinID == X86::BI__emul); 7655 Value *LHS = Builder.CreateIntCast(Ops[0], Int64Ty, isSigned); 7656 Value *RHS = Builder.CreateIntCast(Ops[1], Int64Ty, isSigned); 7657 return Builder.CreateMul(LHS, RHS, "", !isSigned, isSigned); 7658 } 7659 case X86::BI__mulh: 7660 case X86::BI__umulh: 7661 case X86::BI_mul128: 7662 case X86::BI_umul128: { 7663 llvm::Type *ResType = ConvertType(E->getType()); 7664 llvm::Type *Int128Ty = llvm::IntegerType::get(getLLVMContext(), 128); 7665 7666 bool IsSigned = (BuiltinID == X86::BI__mulh || BuiltinID == X86::BI_mul128); 7667 Value *LHS = Builder.CreateIntCast(Ops[0], Int128Ty, IsSigned); 7668 Value *RHS = Builder.CreateIntCast(Ops[1], Int128Ty, IsSigned); 7669 7670 Value *MulResult, *HigherBits; 7671 if (IsSigned) { 7672 MulResult = Builder.CreateNSWMul(LHS, RHS); 7673 HigherBits = Builder.CreateAShr(MulResult, 64); 7674 } else { 7675 MulResult = Builder.CreateNUWMul(LHS, RHS); 7676 HigherBits = Builder.CreateLShr(MulResult, 64); 7677 } 7678 HigherBits = Builder.CreateIntCast(HigherBits, ResType, IsSigned); 7679 7680 if (BuiltinID == X86::BI__mulh || BuiltinID == X86::BI__umulh) 7681 return HigherBits; 7682 7683 Address HighBitsAddress = EmitPointerWithAlignment(E->getArg(2)); 7684 Builder.CreateStore(HigherBits, HighBitsAddress); 7685 return Builder.CreateIntCast(MulResult, ResType, IsSigned); 7686 } 7687 7688 case X86::BI__faststorefence: { 7689 return Builder.CreateFence(llvm::AtomicOrdering::SequentiallyConsistent, 7690 llvm::CrossThread); 7691 } 7692 case X86::BI_ReadWriteBarrier: 7693 case X86::BI_ReadBarrier: 7694 case X86::BI_WriteBarrier: { 7695 return Builder.CreateFence(llvm::AtomicOrdering::SequentiallyConsistent, 7696 llvm::SingleThread); 7697 } 7698 case X86::BI_BitScanForward: 7699 case X86::BI_BitScanForward64: 7700 return EmitMSVCBuiltinExpr(MSVCIntrin::_BitScanForward, E); 7701 case X86::BI_BitScanReverse: 7702 case X86::BI_BitScanReverse64: 7703 return EmitMSVCBuiltinExpr(MSVCIntrin::_BitScanReverse, E); 7704 case X86::BI_AddressOfReturnAddress: { 7705 Value *F = CGM.getIntrinsic(Intrinsic::addressofreturnaddress); 7706 return Builder.CreateCall(F); 7707 } 7708 } 7709 } 7710 7711 7712 Value *CodeGenFunction::EmitPPCBuiltinExpr(unsigned BuiltinID, 7713 const CallExpr *E) { 7714 SmallVector<Value*, 4> Ops; 7715 7716 for (unsigned i = 0, e = E->getNumArgs(); i != e; i++) 7717 Ops.push_back(EmitScalarExpr(E->getArg(i))); 7718 7719 Intrinsic::ID ID = Intrinsic::not_intrinsic; 7720 7721 switch (BuiltinID) { 7722 default: return nullptr; 7723 7724 // __builtin_ppc_get_timebase is GCC 4.8+'s PowerPC-specific name for what we 7725 // call __builtin_readcyclecounter. 7726 case PPC::BI__builtin_ppc_get_timebase: 7727 return Builder.CreateCall(CGM.getIntrinsic(Intrinsic::readcyclecounter)); 7728 7729 // vec_ld, vec_lvsl, vec_lvsr 7730 case PPC::BI__builtin_altivec_lvx: 7731 case PPC::BI__builtin_altivec_lvxl: 7732 case PPC::BI__builtin_altivec_lvebx: 7733 case PPC::BI__builtin_altivec_lvehx: 7734 case PPC::BI__builtin_altivec_lvewx: 7735 case PPC::BI__builtin_altivec_lvsl: 7736 case PPC::BI__builtin_altivec_lvsr: 7737 case PPC::BI__builtin_vsx_lxvd2x: 7738 case PPC::BI__builtin_vsx_lxvw4x: 7739 { 7740 Ops[1] = Builder.CreateBitCast(Ops[1], Int8PtrTy); 7741 7742 Ops[0] = Builder.CreateGEP(Ops[1], Ops[0]); 7743 Ops.pop_back(); 7744 7745 switch (BuiltinID) { 7746 default: llvm_unreachable("Unsupported ld/lvsl/lvsr intrinsic!"); 7747 case PPC::BI__builtin_altivec_lvx: 7748 ID = Intrinsic::ppc_altivec_lvx; 7749 break; 7750 case PPC::BI__builtin_altivec_lvxl: 7751 ID = Intrinsic::ppc_altivec_lvxl; 7752 break; 7753 case PPC::BI__builtin_altivec_lvebx: 7754 ID = Intrinsic::ppc_altivec_lvebx; 7755 break; 7756 case PPC::BI__builtin_altivec_lvehx: 7757 ID = Intrinsic::ppc_altivec_lvehx; 7758 break; 7759 case PPC::BI__builtin_altivec_lvewx: 7760 ID = Intrinsic::ppc_altivec_lvewx; 7761 break; 7762 case PPC::BI__builtin_altivec_lvsl: 7763 ID = Intrinsic::ppc_altivec_lvsl; 7764 break; 7765 case PPC::BI__builtin_altivec_lvsr: 7766 ID = Intrinsic::ppc_altivec_lvsr; 7767 break; 7768 case PPC::BI__builtin_vsx_lxvd2x: 7769 ID = Intrinsic::ppc_vsx_lxvd2x; 7770 break; 7771 case PPC::BI__builtin_vsx_lxvw4x: 7772 ID = Intrinsic::ppc_vsx_lxvw4x; 7773 break; 7774 } 7775 llvm::Function *F = CGM.getIntrinsic(ID); 7776 return Builder.CreateCall(F, Ops, ""); 7777 } 7778 7779 // vec_st 7780 case PPC::BI__builtin_altivec_stvx: 7781 case PPC::BI__builtin_altivec_stvxl: 7782 case PPC::BI__builtin_altivec_stvebx: 7783 case PPC::BI__builtin_altivec_stvehx: 7784 case PPC::BI__builtin_altivec_stvewx: 7785 case PPC::BI__builtin_vsx_stxvd2x: 7786 case PPC::BI__builtin_vsx_stxvw4x: 7787 { 7788 Ops[2] = Builder.CreateBitCast(Ops[2], Int8PtrTy); 7789 Ops[1] = Builder.CreateGEP(Ops[2], Ops[1]); 7790 Ops.pop_back(); 7791 7792 switch (BuiltinID) { 7793 default: llvm_unreachable("Unsupported st intrinsic!"); 7794 case PPC::BI__builtin_altivec_stvx: 7795 ID = Intrinsic::ppc_altivec_stvx; 7796 break; 7797 case PPC::BI__builtin_altivec_stvxl: 7798 ID = Intrinsic::ppc_altivec_stvxl; 7799 break; 7800 case PPC::BI__builtin_altivec_stvebx: 7801 ID = Intrinsic::ppc_altivec_stvebx; 7802 break; 7803 case PPC::BI__builtin_altivec_stvehx: 7804 ID = Intrinsic::ppc_altivec_stvehx; 7805 break; 7806 case PPC::BI__builtin_altivec_stvewx: 7807 ID = Intrinsic::ppc_altivec_stvewx; 7808 break; 7809 case PPC::BI__builtin_vsx_stxvd2x: 7810 ID = Intrinsic::ppc_vsx_stxvd2x; 7811 break; 7812 case PPC::BI__builtin_vsx_stxvw4x: 7813 ID = Intrinsic::ppc_vsx_stxvw4x; 7814 break; 7815 } 7816 llvm::Function *F = CGM.getIntrinsic(ID); 7817 return Builder.CreateCall(F, Ops, ""); 7818 } 7819 // Square root 7820 case PPC::BI__builtin_vsx_xvsqrtsp: 7821 case PPC::BI__builtin_vsx_xvsqrtdp: { 7822 llvm::Type *ResultType = ConvertType(E->getType()); 7823 Value *X = EmitScalarExpr(E->getArg(0)); 7824 ID = Intrinsic::sqrt; 7825 llvm::Function *F = CGM.getIntrinsic(ID, ResultType); 7826 return Builder.CreateCall(F, X); 7827 } 7828 // Count leading zeros 7829 case PPC::BI__builtin_altivec_vclzb: 7830 case PPC::BI__builtin_altivec_vclzh: 7831 case PPC::BI__builtin_altivec_vclzw: 7832 case PPC::BI__builtin_altivec_vclzd: { 7833 llvm::Type *ResultType = ConvertType(E->getType()); 7834 Value *X = EmitScalarExpr(E->getArg(0)); 7835 Value *Undef = ConstantInt::get(Builder.getInt1Ty(), false); 7836 Function *F = CGM.getIntrinsic(Intrinsic::ctlz, ResultType); 7837 return Builder.CreateCall(F, {X, Undef}); 7838 } 7839 case PPC::BI__builtin_altivec_vctzb: 7840 case PPC::BI__builtin_altivec_vctzh: 7841 case PPC::BI__builtin_altivec_vctzw: 7842 case PPC::BI__builtin_altivec_vctzd: { 7843 llvm::Type *ResultType = ConvertType(E->getType()); 7844 Value *X = EmitScalarExpr(E->getArg(0)); 7845 Value *Undef = ConstantInt::get(Builder.getInt1Ty(), false); 7846 Function *F = CGM.getIntrinsic(Intrinsic::cttz, ResultType); 7847 return Builder.CreateCall(F, {X, Undef}); 7848 } 7849 case PPC::BI__builtin_altivec_vpopcntb: 7850 case PPC::BI__builtin_altivec_vpopcnth: 7851 case PPC::BI__builtin_altivec_vpopcntw: 7852 case PPC::BI__builtin_altivec_vpopcntd: { 7853 llvm::Type *ResultType = ConvertType(E->getType()); 7854 Value *X = EmitScalarExpr(E->getArg(0)); 7855 llvm::Function *F = CGM.getIntrinsic(Intrinsic::ctpop, ResultType); 7856 return Builder.CreateCall(F, X); 7857 } 7858 // Copy sign 7859 case PPC::BI__builtin_vsx_xvcpsgnsp: 7860 case PPC::BI__builtin_vsx_xvcpsgndp: { 7861 llvm::Type *ResultType = ConvertType(E->getType()); 7862 Value *X = EmitScalarExpr(E->getArg(0)); 7863 Value *Y = EmitScalarExpr(E->getArg(1)); 7864 ID = Intrinsic::copysign; 7865 llvm::Function *F = CGM.getIntrinsic(ID, ResultType); 7866 return Builder.CreateCall(F, {X, Y}); 7867 } 7868 // Rounding/truncation 7869 case PPC::BI__builtin_vsx_xvrspip: 7870 case PPC::BI__builtin_vsx_xvrdpip: 7871 case PPC::BI__builtin_vsx_xvrdpim: 7872 case PPC::BI__builtin_vsx_xvrspim: 7873 case PPC::BI__builtin_vsx_xvrdpi: 7874 case PPC::BI__builtin_vsx_xvrspi: 7875 case PPC::BI__builtin_vsx_xvrdpic: 7876 case PPC::BI__builtin_vsx_xvrspic: 7877 case PPC::BI__builtin_vsx_xvrdpiz: 7878 case PPC::BI__builtin_vsx_xvrspiz: { 7879 llvm::Type *ResultType = ConvertType(E->getType()); 7880 Value *X = EmitScalarExpr(E->getArg(0)); 7881 if (BuiltinID == PPC::BI__builtin_vsx_xvrdpim || 7882 BuiltinID == PPC::BI__builtin_vsx_xvrspim) 7883 ID = Intrinsic::floor; 7884 else if (BuiltinID == PPC::BI__builtin_vsx_xvrdpi || 7885 BuiltinID == PPC::BI__builtin_vsx_xvrspi) 7886 ID = Intrinsic::round; 7887 else if (BuiltinID == PPC::BI__builtin_vsx_xvrdpic || 7888 BuiltinID == PPC::BI__builtin_vsx_xvrspic) 7889 ID = Intrinsic::nearbyint; 7890 else if (BuiltinID == PPC::BI__builtin_vsx_xvrdpip || 7891 BuiltinID == PPC::BI__builtin_vsx_xvrspip) 7892 ID = Intrinsic::ceil; 7893 else if (BuiltinID == PPC::BI__builtin_vsx_xvrdpiz || 7894 BuiltinID == PPC::BI__builtin_vsx_xvrspiz) 7895 ID = Intrinsic::trunc; 7896 llvm::Function *F = CGM.getIntrinsic(ID, ResultType); 7897 return Builder.CreateCall(F, X); 7898 } 7899 7900 // Absolute value 7901 case PPC::BI__builtin_vsx_xvabsdp: 7902 case PPC::BI__builtin_vsx_xvabssp: { 7903 llvm::Type *ResultType = ConvertType(E->getType()); 7904 Value *X = EmitScalarExpr(E->getArg(0)); 7905 llvm::Function *F = CGM.getIntrinsic(Intrinsic::fabs, ResultType); 7906 return Builder.CreateCall(F, X); 7907 } 7908 7909 // FMA variations 7910 case PPC::BI__builtin_vsx_xvmaddadp: 7911 case PPC::BI__builtin_vsx_xvmaddasp: 7912 case PPC::BI__builtin_vsx_xvnmaddadp: 7913 case PPC::BI__builtin_vsx_xvnmaddasp: 7914 case PPC::BI__builtin_vsx_xvmsubadp: 7915 case PPC::BI__builtin_vsx_xvmsubasp: 7916 case PPC::BI__builtin_vsx_xvnmsubadp: 7917 case PPC::BI__builtin_vsx_xvnmsubasp: { 7918 llvm::Type *ResultType = ConvertType(E->getType()); 7919 Value *X = EmitScalarExpr(E->getArg(0)); 7920 Value *Y = EmitScalarExpr(E->getArg(1)); 7921 Value *Z = EmitScalarExpr(E->getArg(2)); 7922 Value *Zero = llvm::ConstantFP::getZeroValueForNegation(ResultType); 7923 llvm::Function *F = CGM.getIntrinsic(Intrinsic::fma, ResultType); 7924 switch (BuiltinID) { 7925 case PPC::BI__builtin_vsx_xvmaddadp: 7926 case PPC::BI__builtin_vsx_xvmaddasp: 7927 return Builder.CreateCall(F, {X, Y, Z}); 7928 case PPC::BI__builtin_vsx_xvnmaddadp: 7929 case PPC::BI__builtin_vsx_xvnmaddasp: 7930 return Builder.CreateFSub(Zero, 7931 Builder.CreateCall(F, {X, Y, Z}), "sub"); 7932 case PPC::BI__builtin_vsx_xvmsubadp: 7933 case PPC::BI__builtin_vsx_xvmsubasp: 7934 return Builder.CreateCall(F, 7935 {X, Y, Builder.CreateFSub(Zero, Z, "sub")}); 7936 case PPC::BI__builtin_vsx_xvnmsubadp: 7937 case PPC::BI__builtin_vsx_xvnmsubasp: 7938 Value *FsubRes = 7939 Builder.CreateCall(F, {X, Y, Builder.CreateFSub(Zero, Z, "sub")}); 7940 return Builder.CreateFSub(Zero, FsubRes, "sub"); 7941 } 7942 llvm_unreachable("Unknown FMA operation"); 7943 return nullptr; // Suppress no-return warning 7944 } 7945 } 7946 } 7947 7948 Value *CodeGenFunction::EmitAMDGPUBuiltinExpr(unsigned BuiltinID, 7949 const CallExpr *E) { 7950 switch (BuiltinID) { 7951 case AMDGPU::BI__builtin_amdgcn_div_scale: 7952 case AMDGPU::BI__builtin_amdgcn_div_scalef: { 7953 // Translate from the intrinsics's struct return to the builtin's out 7954 // argument. 7955 7956 Address FlagOutPtr = EmitPointerWithAlignment(E->getArg(3)); 7957 7958 llvm::Value *X = EmitScalarExpr(E->getArg(0)); 7959 llvm::Value *Y = EmitScalarExpr(E->getArg(1)); 7960 llvm::Value *Z = EmitScalarExpr(E->getArg(2)); 7961 7962 llvm::Value *Callee = CGM.getIntrinsic(Intrinsic::amdgcn_div_scale, 7963 X->getType()); 7964 7965 llvm::Value *Tmp = Builder.CreateCall(Callee, {X, Y, Z}); 7966 7967 llvm::Value *Result = Builder.CreateExtractValue(Tmp, 0); 7968 llvm::Value *Flag = Builder.CreateExtractValue(Tmp, 1); 7969 7970 llvm::Type *RealFlagType 7971 = FlagOutPtr.getPointer()->getType()->getPointerElementType(); 7972 7973 llvm::Value *FlagExt = Builder.CreateZExt(Flag, RealFlagType); 7974 Builder.CreateStore(FlagExt, FlagOutPtr); 7975 return Result; 7976 } 7977 case AMDGPU::BI__builtin_amdgcn_div_fmas: 7978 case AMDGPU::BI__builtin_amdgcn_div_fmasf: { 7979 llvm::Value *Src0 = EmitScalarExpr(E->getArg(0)); 7980 llvm::Value *Src1 = EmitScalarExpr(E->getArg(1)); 7981 llvm::Value *Src2 = EmitScalarExpr(E->getArg(2)); 7982 llvm::Value *Src3 = EmitScalarExpr(E->getArg(3)); 7983 7984 llvm::Value *F = CGM.getIntrinsic(Intrinsic::amdgcn_div_fmas, 7985 Src0->getType()); 7986 llvm::Value *Src3ToBool = Builder.CreateIsNotNull(Src3); 7987 return Builder.CreateCall(F, {Src0, Src1, Src2, Src3ToBool}); 7988 } 7989 7990 case AMDGPU::BI__builtin_amdgcn_ds_swizzle: 7991 return emitBinaryBuiltin(*this, E, Intrinsic::amdgcn_ds_swizzle); 7992 case AMDGPU::BI__builtin_amdgcn_div_fixup: 7993 case AMDGPU::BI__builtin_amdgcn_div_fixupf: 7994 return emitTernaryBuiltin(*this, E, Intrinsic::amdgcn_div_fixup); 7995 case AMDGPU::BI__builtin_amdgcn_trig_preop: 7996 case AMDGPU::BI__builtin_amdgcn_trig_preopf: 7997 return emitFPIntBuiltin(*this, E, Intrinsic::amdgcn_trig_preop); 7998 case AMDGPU::BI__builtin_amdgcn_rcp: 7999 case AMDGPU::BI__builtin_amdgcn_rcpf: 8000 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_rcp); 8001 case AMDGPU::BI__builtin_amdgcn_rsq: 8002 case AMDGPU::BI__builtin_amdgcn_rsqf: 8003 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_rsq); 8004 case AMDGPU::BI__builtin_amdgcn_rsq_clamp: 8005 case AMDGPU::BI__builtin_amdgcn_rsq_clampf: 8006 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_rsq_clamp); 8007 case AMDGPU::BI__builtin_amdgcn_sinf: 8008 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_sin); 8009 case AMDGPU::BI__builtin_amdgcn_cosf: 8010 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_cos); 8011 case AMDGPU::BI__builtin_amdgcn_log_clampf: 8012 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_log_clamp); 8013 case AMDGPU::BI__builtin_amdgcn_ldexp: 8014 case AMDGPU::BI__builtin_amdgcn_ldexpf: 8015 return emitFPIntBuiltin(*this, E, Intrinsic::amdgcn_ldexp); 8016 case AMDGPU::BI__builtin_amdgcn_frexp_mant: 8017 case AMDGPU::BI__builtin_amdgcn_frexp_mantf: { 8018 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_frexp_mant); 8019 } 8020 case AMDGPU::BI__builtin_amdgcn_frexp_exp: 8021 case AMDGPU::BI__builtin_amdgcn_frexp_expf: { 8022 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_frexp_exp); 8023 } 8024 case AMDGPU::BI__builtin_amdgcn_fract: 8025 case AMDGPU::BI__builtin_amdgcn_fractf: 8026 return emitUnaryBuiltin(*this, E, Intrinsic::amdgcn_fract); 8027 case AMDGPU::BI__builtin_amdgcn_lerp: 8028 return emitTernaryBuiltin(*this, E, Intrinsic::amdgcn_lerp); 8029 case AMDGPU::BI__builtin_amdgcn_uicmp: 8030 case AMDGPU::BI__builtin_amdgcn_uicmpl: 8031 case AMDGPU::BI__builtin_amdgcn_sicmp: 8032 case AMDGPU::BI__builtin_amdgcn_sicmpl: 8033 return emitTernaryBuiltin(*this, E, Intrinsic::amdgcn_icmp); 8034 case AMDGPU::BI__builtin_amdgcn_fcmp: 8035 case AMDGPU::BI__builtin_amdgcn_fcmpf: 8036 return emitTernaryBuiltin(*this, E, Intrinsic::amdgcn_fcmp); 8037 case AMDGPU::BI__builtin_amdgcn_class: 8038 case AMDGPU::BI__builtin_amdgcn_classf: 8039 return emitFPIntBuiltin(*this, E, Intrinsic::amdgcn_class); 8040 8041 case AMDGPU::BI__builtin_amdgcn_read_exec: { 8042 CallInst *CI = cast<CallInst>( 8043 EmitSpecialRegisterBuiltin(*this, E, Int64Ty, Int64Ty, true, "exec")); 8044 CI->setConvergent(); 8045 return CI; 8046 } 8047 8048 // amdgcn workitem 8049 case AMDGPU::BI__builtin_amdgcn_workitem_id_x: 8050 return emitRangedBuiltin(*this, Intrinsic::amdgcn_workitem_id_x, 0, 1024); 8051 case AMDGPU::BI__builtin_amdgcn_workitem_id_y: 8052 return emitRangedBuiltin(*this, Intrinsic::amdgcn_workitem_id_y, 0, 1024); 8053 case AMDGPU::BI__builtin_amdgcn_workitem_id_z: 8054 return emitRangedBuiltin(*this, Intrinsic::amdgcn_workitem_id_z, 0, 1024); 8055 8056 // r600 intrinsics 8057 case AMDGPU::BI__builtin_r600_recipsqrt_ieee: 8058 case AMDGPU::BI__builtin_r600_recipsqrt_ieeef: 8059 return emitUnaryBuiltin(*this, E, Intrinsic::r600_recipsqrt_ieee); 8060 case AMDGPU::BI__builtin_r600_read_tidig_x: 8061 return emitRangedBuiltin(*this, Intrinsic::r600_read_tidig_x, 0, 1024); 8062 case AMDGPU::BI__builtin_r600_read_tidig_y: 8063 return emitRangedBuiltin(*this, Intrinsic::r600_read_tidig_y, 0, 1024); 8064 case AMDGPU::BI__builtin_r600_read_tidig_z: 8065 return emitRangedBuiltin(*this, Intrinsic::r600_read_tidig_z, 0, 1024); 8066 default: 8067 return nullptr; 8068 } 8069 } 8070 8071 /// Handle a SystemZ function in which the final argument is a pointer 8072 /// to an int that receives the post-instruction CC value. At the LLVM level 8073 /// this is represented as a function that returns a {result, cc} pair. 8074 static Value *EmitSystemZIntrinsicWithCC(CodeGenFunction &CGF, 8075 unsigned IntrinsicID, 8076 const CallExpr *E) { 8077 unsigned NumArgs = E->getNumArgs() - 1; 8078 SmallVector<Value *, 8> Args(NumArgs); 8079 for (unsigned I = 0; I < NumArgs; ++I) 8080 Args[I] = CGF.EmitScalarExpr(E->getArg(I)); 8081 Address CCPtr = CGF.EmitPointerWithAlignment(E->getArg(NumArgs)); 8082 Value *F = CGF.CGM.getIntrinsic(IntrinsicID); 8083 Value *Call = CGF.Builder.CreateCall(F, Args); 8084 Value *CC = CGF.Builder.CreateExtractValue(Call, 1); 8085 CGF.Builder.CreateStore(CC, CCPtr); 8086 return CGF.Builder.CreateExtractValue(Call, 0); 8087 } 8088 8089 Value *CodeGenFunction::EmitSystemZBuiltinExpr(unsigned BuiltinID, 8090 const CallExpr *E) { 8091 switch (BuiltinID) { 8092 case SystemZ::BI__builtin_tbegin: { 8093 Value *TDB = EmitScalarExpr(E->getArg(0)); 8094 Value *Control = llvm::ConstantInt::get(Int32Ty, 0xff0c); 8095 Value *F = CGM.getIntrinsic(Intrinsic::s390_tbegin); 8096 return Builder.CreateCall(F, {TDB, Control}); 8097 } 8098 case SystemZ::BI__builtin_tbegin_nofloat: { 8099 Value *TDB = EmitScalarExpr(E->getArg(0)); 8100 Value *Control = llvm::ConstantInt::get(Int32Ty, 0xff0c); 8101 Value *F = CGM.getIntrinsic(Intrinsic::s390_tbegin_nofloat); 8102 return Builder.CreateCall(F, {TDB, Control}); 8103 } 8104 case SystemZ::BI__builtin_tbeginc: { 8105 Value *TDB = llvm::ConstantPointerNull::get(Int8PtrTy); 8106 Value *Control = llvm::ConstantInt::get(Int32Ty, 0xff08); 8107 Value *F = CGM.getIntrinsic(Intrinsic::s390_tbeginc); 8108 return Builder.CreateCall(F, {TDB, Control}); 8109 } 8110 case SystemZ::BI__builtin_tabort: { 8111 Value *Data = EmitScalarExpr(E->getArg(0)); 8112 Value *F = CGM.getIntrinsic(Intrinsic::s390_tabort); 8113 return Builder.CreateCall(F, Builder.CreateSExt(Data, Int64Ty, "tabort")); 8114 } 8115 case SystemZ::BI__builtin_non_tx_store: { 8116 Value *Address = EmitScalarExpr(E->getArg(0)); 8117 Value *Data = EmitScalarExpr(E->getArg(1)); 8118 Value *F = CGM.getIntrinsic(Intrinsic::s390_ntstg); 8119 return Builder.CreateCall(F, {Data, Address}); 8120 } 8121 8122 // Vector builtins. Note that most vector builtins are mapped automatically 8123 // to target-specific LLVM intrinsics. The ones handled specially here can 8124 // be represented via standard LLVM IR, which is preferable to enable common 8125 // LLVM optimizations. 8126 8127 case SystemZ::BI__builtin_s390_vpopctb: 8128 case SystemZ::BI__builtin_s390_vpopcth: 8129 case SystemZ::BI__builtin_s390_vpopctf: 8130 case SystemZ::BI__builtin_s390_vpopctg: { 8131 llvm::Type *ResultType = ConvertType(E->getType()); 8132 Value *X = EmitScalarExpr(E->getArg(0)); 8133 Function *F = CGM.getIntrinsic(Intrinsic::ctpop, ResultType); 8134 return Builder.CreateCall(F, X); 8135 } 8136 8137 case SystemZ::BI__builtin_s390_vclzb: 8138 case SystemZ::BI__builtin_s390_vclzh: 8139 case SystemZ::BI__builtin_s390_vclzf: 8140 case SystemZ::BI__builtin_s390_vclzg: { 8141 llvm::Type *ResultType = ConvertType(E->getType()); 8142 Value *X = EmitScalarExpr(E->getArg(0)); 8143 Value *Undef = ConstantInt::get(Builder.getInt1Ty(), false); 8144 Function *F = CGM.getIntrinsic(Intrinsic::ctlz, ResultType); 8145 return Builder.CreateCall(F, {X, Undef}); 8146 } 8147 8148 case SystemZ::BI__builtin_s390_vctzb: 8149 case SystemZ::BI__builtin_s390_vctzh: 8150 case SystemZ::BI__builtin_s390_vctzf: 8151 case SystemZ::BI__builtin_s390_vctzg: { 8152 llvm::Type *ResultType = ConvertType(E->getType()); 8153 Value *X = EmitScalarExpr(E->getArg(0)); 8154 Value *Undef = ConstantInt::get(Builder.getInt1Ty(), false); 8155 Function *F = CGM.getIntrinsic(Intrinsic::cttz, ResultType); 8156 return Builder.CreateCall(F, {X, Undef}); 8157 } 8158 8159 case SystemZ::BI__builtin_s390_vfsqdb: { 8160 llvm::Type *ResultType = ConvertType(E->getType()); 8161 Value *X = EmitScalarExpr(E->getArg(0)); 8162 Function *F = CGM.getIntrinsic(Intrinsic::sqrt, ResultType); 8163 return Builder.CreateCall(F, X); 8164 } 8165 case SystemZ::BI__builtin_s390_vfmadb: { 8166 llvm::Type *ResultType = ConvertType(E->getType()); 8167 Value *X = EmitScalarExpr(E->getArg(0)); 8168 Value *Y = EmitScalarExpr(E->getArg(1)); 8169 Value *Z = EmitScalarExpr(E->getArg(2)); 8170 Function *F = CGM.getIntrinsic(Intrinsic::fma, ResultType); 8171 return Builder.CreateCall(F, {X, Y, Z}); 8172 } 8173 case SystemZ::BI__builtin_s390_vfmsdb: { 8174 llvm::Type *ResultType = ConvertType(E->getType()); 8175 Value *X = EmitScalarExpr(E->getArg(0)); 8176 Value *Y = EmitScalarExpr(E->getArg(1)); 8177 Value *Z = EmitScalarExpr(E->getArg(2)); 8178 Value *Zero = llvm::ConstantFP::getZeroValueForNegation(ResultType); 8179 Function *F = CGM.getIntrinsic(Intrinsic::fma, ResultType); 8180 return Builder.CreateCall(F, {X, Y, Builder.CreateFSub(Zero, Z, "sub")}); 8181 } 8182 case SystemZ::BI__builtin_s390_vflpdb: { 8183 llvm::Type *ResultType = ConvertType(E->getType()); 8184 Value *X = EmitScalarExpr(E->getArg(0)); 8185 Function *F = CGM.getIntrinsic(Intrinsic::fabs, ResultType); 8186 return Builder.CreateCall(F, X); 8187 } 8188 case SystemZ::BI__builtin_s390_vflndb: { 8189 llvm::Type *ResultType = ConvertType(E->getType()); 8190 Value *X = EmitScalarExpr(E->getArg(0)); 8191 Value *Zero = llvm::ConstantFP::getZeroValueForNegation(ResultType); 8192 Function *F = CGM.getIntrinsic(Intrinsic::fabs, ResultType); 8193 return Builder.CreateFSub(Zero, Builder.CreateCall(F, X), "sub"); 8194 } 8195 case SystemZ::BI__builtin_s390_vfidb: { 8196 llvm::Type *ResultType = ConvertType(E->getType()); 8197 Value *X = EmitScalarExpr(E->getArg(0)); 8198 // Constant-fold the M4 and M5 mask arguments. 8199 llvm::APSInt M4, M5; 8200 bool IsConstM4 = E->getArg(1)->isIntegerConstantExpr(M4, getContext()); 8201 bool IsConstM5 = E->getArg(2)->isIntegerConstantExpr(M5, getContext()); 8202 assert(IsConstM4 && IsConstM5 && "Constant arg isn't actually constant?"); 8203 (void)IsConstM4; (void)IsConstM5; 8204 // Check whether this instance of vfidb can be represented via a LLVM 8205 // standard intrinsic. We only support some combinations of M4 and M5. 8206 Intrinsic::ID ID = Intrinsic::not_intrinsic; 8207 switch (M4.getZExtValue()) { 8208 default: break; 8209 case 0: // IEEE-inexact exception allowed 8210 switch (M5.getZExtValue()) { 8211 default: break; 8212 case 0: ID = Intrinsic::rint; break; 8213 } 8214 break; 8215 case 4: // IEEE-inexact exception suppressed 8216 switch (M5.getZExtValue()) { 8217 default: break; 8218 case 0: ID = Intrinsic::nearbyint; break; 8219 case 1: ID = Intrinsic::round; break; 8220 case 5: ID = Intrinsic::trunc; break; 8221 case 6: ID = Intrinsic::ceil; break; 8222 case 7: ID = Intrinsic::floor; break; 8223 } 8224 break; 8225 } 8226 if (ID != Intrinsic::not_intrinsic) { 8227 Function *F = CGM.getIntrinsic(ID, ResultType); 8228 return Builder.CreateCall(F, X); 8229 } 8230 Function *F = CGM.getIntrinsic(Intrinsic::s390_vfidb); 8231 Value *M4Value = llvm::ConstantInt::get(getLLVMContext(), M4); 8232 Value *M5Value = llvm::ConstantInt::get(getLLVMContext(), M5); 8233 return Builder.CreateCall(F, {X, M4Value, M5Value}); 8234 } 8235 8236 // Vector intrisincs that output the post-instruction CC value. 8237 8238 #define INTRINSIC_WITH_CC(NAME) \ 8239 case SystemZ::BI__builtin_##NAME: \ 8240 return EmitSystemZIntrinsicWithCC(*this, Intrinsic::NAME, E) 8241 8242 INTRINSIC_WITH_CC(s390_vpkshs); 8243 INTRINSIC_WITH_CC(s390_vpksfs); 8244 INTRINSIC_WITH_CC(s390_vpksgs); 8245 8246 INTRINSIC_WITH_CC(s390_vpklshs); 8247 INTRINSIC_WITH_CC(s390_vpklsfs); 8248 INTRINSIC_WITH_CC(s390_vpklsgs); 8249 8250 INTRINSIC_WITH_CC(s390_vceqbs); 8251 INTRINSIC_WITH_CC(s390_vceqhs); 8252 INTRINSIC_WITH_CC(s390_vceqfs); 8253 INTRINSIC_WITH_CC(s390_vceqgs); 8254 8255 INTRINSIC_WITH_CC(s390_vchbs); 8256 INTRINSIC_WITH_CC(s390_vchhs); 8257 INTRINSIC_WITH_CC(s390_vchfs); 8258 INTRINSIC_WITH_CC(s390_vchgs); 8259 8260 INTRINSIC_WITH_CC(s390_vchlbs); 8261 INTRINSIC_WITH_CC(s390_vchlhs); 8262 INTRINSIC_WITH_CC(s390_vchlfs); 8263 INTRINSIC_WITH_CC(s390_vchlgs); 8264 8265 INTRINSIC_WITH_CC(s390_vfaebs); 8266 INTRINSIC_WITH_CC(s390_vfaehs); 8267 INTRINSIC_WITH_CC(s390_vfaefs); 8268 8269 INTRINSIC_WITH_CC(s390_vfaezbs); 8270 INTRINSIC_WITH_CC(s390_vfaezhs); 8271 INTRINSIC_WITH_CC(s390_vfaezfs); 8272 8273 INTRINSIC_WITH_CC(s390_vfeebs); 8274 INTRINSIC_WITH_CC(s390_vfeehs); 8275 INTRINSIC_WITH_CC(s390_vfeefs); 8276 8277 INTRINSIC_WITH_CC(s390_vfeezbs); 8278 INTRINSIC_WITH_CC(s390_vfeezhs); 8279 INTRINSIC_WITH_CC(s390_vfeezfs); 8280 8281 INTRINSIC_WITH_CC(s390_vfenebs); 8282 INTRINSIC_WITH_CC(s390_vfenehs); 8283 INTRINSIC_WITH_CC(s390_vfenefs); 8284 8285 INTRINSIC_WITH_CC(s390_vfenezbs); 8286 INTRINSIC_WITH_CC(s390_vfenezhs); 8287 INTRINSIC_WITH_CC(s390_vfenezfs); 8288 8289 INTRINSIC_WITH_CC(s390_vistrbs); 8290 INTRINSIC_WITH_CC(s390_vistrhs); 8291 INTRINSIC_WITH_CC(s390_vistrfs); 8292 8293 INTRINSIC_WITH_CC(s390_vstrcbs); 8294 INTRINSIC_WITH_CC(s390_vstrchs); 8295 INTRINSIC_WITH_CC(s390_vstrcfs); 8296 8297 INTRINSIC_WITH_CC(s390_vstrczbs); 8298 INTRINSIC_WITH_CC(s390_vstrczhs); 8299 INTRINSIC_WITH_CC(s390_vstrczfs); 8300 8301 INTRINSIC_WITH_CC(s390_vfcedbs); 8302 INTRINSIC_WITH_CC(s390_vfchdbs); 8303 INTRINSIC_WITH_CC(s390_vfchedbs); 8304 8305 INTRINSIC_WITH_CC(s390_vftcidb); 8306 8307 #undef INTRINSIC_WITH_CC 8308 8309 default: 8310 return nullptr; 8311 } 8312 } 8313 8314 Value *CodeGenFunction::EmitNVPTXBuiltinExpr(unsigned BuiltinID, 8315 const CallExpr *E) { 8316 auto MakeLdg = [&](unsigned IntrinsicID) { 8317 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8318 AlignmentSource AlignSource; 8319 clang::CharUnits Align = 8320 getNaturalPointeeTypeAlignment(E->getArg(0)->getType(), &AlignSource); 8321 return Builder.CreateCall( 8322 CGM.getIntrinsic(IntrinsicID, {Ptr->getType()->getPointerElementType(), 8323 Ptr->getType()}), 8324 {Ptr, ConstantInt::get(Builder.getInt32Ty(), Align.getQuantity())}); 8325 }; 8326 auto MakeScopedAtomic = [&](unsigned IntrinsicID) { 8327 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8328 return Builder.CreateCall( 8329 CGM.getIntrinsic(IntrinsicID, {Ptr->getType()->getPointerElementType(), 8330 Ptr->getType()}), 8331 {Ptr, EmitScalarExpr(E->getArg(1))}); 8332 }; 8333 switch (BuiltinID) { 8334 case NVPTX::BI__nvvm_atom_add_gen_i: 8335 case NVPTX::BI__nvvm_atom_add_gen_l: 8336 case NVPTX::BI__nvvm_atom_add_gen_ll: 8337 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Add, E); 8338 8339 case NVPTX::BI__nvvm_atom_sub_gen_i: 8340 case NVPTX::BI__nvvm_atom_sub_gen_l: 8341 case NVPTX::BI__nvvm_atom_sub_gen_ll: 8342 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Sub, E); 8343 8344 case NVPTX::BI__nvvm_atom_and_gen_i: 8345 case NVPTX::BI__nvvm_atom_and_gen_l: 8346 case NVPTX::BI__nvvm_atom_and_gen_ll: 8347 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::And, E); 8348 8349 case NVPTX::BI__nvvm_atom_or_gen_i: 8350 case NVPTX::BI__nvvm_atom_or_gen_l: 8351 case NVPTX::BI__nvvm_atom_or_gen_ll: 8352 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Or, E); 8353 8354 case NVPTX::BI__nvvm_atom_xor_gen_i: 8355 case NVPTX::BI__nvvm_atom_xor_gen_l: 8356 case NVPTX::BI__nvvm_atom_xor_gen_ll: 8357 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Xor, E); 8358 8359 case NVPTX::BI__nvvm_atom_xchg_gen_i: 8360 case NVPTX::BI__nvvm_atom_xchg_gen_l: 8361 case NVPTX::BI__nvvm_atom_xchg_gen_ll: 8362 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Xchg, E); 8363 8364 case NVPTX::BI__nvvm_atom_max_gen_i: 8365 case NVPTX::BI__nvvm_atom_max_gen_l: 8366 case NVPTX::BI__nvvm_atom_max_gen_ll: 8367 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Max, E); 8368 8369 case NVPTX::BI__nvvm_atom_max_gen_ui: 8370 case NVPTX::BI__nvvm_atom_max_gen_ul: 8371 case NVPTX::BI__nvvm_atom_max_gen_ull: 8372 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::UMax, E); 8373 8374 case NVPTX::BI__nvvm_atom_min_gen_i: 8375 case NVPTX::BI__nvvm_atom_min_gen_l: 8376 case NVPTX::BI__nvvm_atom_min_gen_ll: 8377 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::Min, E); 8378 8379 case NVPTX::BI__nvvm_atom_min_gen_ui: 8380 case NVPTX::BI__nvvm_atom_min_gen_ul: 8381 case NVPTX::BI__nvvm_atom_min_gen_ull: 8382 return MakeBinaryAtomicValue(*this, llvm::AtomicRMWInst::UMin, E); 8383 8384 case NVPTX::BI__nvvm_atom_cas_gen_i: 8385 case NVPTX::BI__nvvm_atom_cas_gen_l: 8386 case NVPTX::BI__nvvm_atom_cas_gen_ll: 8387 // __nvvm_atom_cas_gen_* should return the old value rather than the 8388 // success flag. 8389 return MakeAtomicCmpXchgValue(*this, E, /*ReturnBool=*/false); 8390 8391 case NVPTX::BI__nvvm_atom_add_gen_f: { 8392 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8393 Value *Val = EmitScalarExpr(E->getArg(1)); 8394 // atomicrmw only deals with integer arguments so we need to use 8395 // LLVM's nvvm_atomic_load_add_f32 intrinsic for that. 8396 Value *FnALAF32 = 8397 CGM.getIntrinsic(Intrinsic::nvvm_atomic_load_add_f32, Ptr->getType()); 8398 return Builder.CreateCall(FnALAF32, {Ptr, Val}); 8399 } 8400 8401 case NVPTX::BI__nvvm_atom_inc_gen_ui: { 8402 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8403 Value *Val = EmitScalarExpr(E->getArg(1)); 8404 Value *FnALI32 = 8405 CGM.getIntrinsic(Intrinsic::nvvm_atomic_load_inc_32, Ptr->getType()); 8406 return Builder.CreateCall(FnALI32, {Ptr, Val}); 8407 } 8408 8409 case NVPTX::BI__nvvm_atom_dec_gen_ui: { 8410 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8411 Value *Val = EmitScalarExpr(E->getArg(1)); 8412 Value *FnALD32 = 8413 CGM.getIntrinsic(Intrinsic::nvvm_atomic_load_dec_32, Ptr->getType()); 8414 return Builder.CreateCall(FnALD32, {Ptr, Val}); 8415 } 8416 8417 case NVPTX::BI__nvvm_ldg_c: 8418 case NVPTX::BI__nvvm_ldg_c2: 8419 case NVPTX::BI__nvvm_ldg_c4: 8420 case NVPTX::BI__nvvm_ldg_s: 8421 case NVPTX::BI__nvvm_ldg_s2: 8422 case NVPTX::BI__nvvm_ldg_s4: 8423 case NVPTX::BI__nvvm_ldg_i: 8424 case NVPTX::BI__nvvm_ldg_i2: 8425 case NVPTX::BI__nvvm_ldg_i4: 8426 case NVPTX::BI__nvvm_ldg_l: 8427 case NVPTX::BI__nvvm_ldg_ll: 8428 case NVPTX::BI__nvvm_ldg_ll2: 8429 case NVPTX::BI__nvvm_ldg_uc: 8430 case NVPTX::BI__nvvm_ldg_uc2: 8431 case NVPTX::BI__nvvm_ldg_uc4: 8432 case NVPTX::BI__nvvm_ldg_us: 8433 case NVPTX::BI__nvvm_ldg_us2: 8434 case NVPTX::BI__nvvm_ldg_us4: 8435 case NVPTX::BI__nvvm_ldg_ui: 8436 case NVPTX::BI__nvvm_ldg_ui2: 8437 case NVPTX::BI__nvvm_ldg_ui4: 8438 case NVPTX::BI__nvvm_ldg_ul: 8439 case NVPTX::BI__nvvm_ldg_ull: 8440 case NVPTX::BI__nvvm_ldg_ull2: 8441 // PTX Interoperability section 2.2: "For a vector with an even number of 8442 // elements, its alignment is set to number of elements times the alignment 8443 // of its member: n*alignof(t)." 8444 return MakeLdg(Intrinsic::nvvm_ldg_global_i); 8445 case NVPTX::BI__nvvm_ldg_f: 8446 case NVPTX::BI__nvvm_ldg_f2: 8447 case NVPTX::BI__nvvm_ldg_f4: 8448 case NVPTX::BI__nvvm_ldg_d: 8449 case NVPTX::BI__nvvm_ldg_d2: 8450 return MakeLdg(Intrinsic::nvvm_ldg_global_f); 8451 8452 case NVPTX::BI__nvvm_atom_cta_add_gen_i: 8453 case NVPTX::BI__nvvm_atom_cta_add_gen_l: 8454 case NVPTX::BI__nvvm_atom_cta_add_gen_ll: 8455 return MakeScopedAtomic(Intrinsic::nvvm_atomic_add_gen_i_cta); 8456 case NVPTX::BI__nvvm_atom_sys_add_gen_i: 8457 case NVPTX::BI__nvvm_atom_sys_add_gen_l: 8458 case NVPTX::BI__nvvm_atom_sys_add_gen_ll: 8459 return MakeScopedAtomic(Intrinsic::nvvm_atomic_add_gen_i_sys); 8460 case NVPTX::BI__nvvm_atom_cta_add_gen_f: 8461 case NVPTX::BI__nvvm_atom_cta_add_gen_d: 8462 return MakeScopedAtomic(Intrinsic::nvvm_atomic_add_gen_f_cta); 8463 case NVPTX::BI__nvvm_atom_sys_add_gen_f: 8464 case NVPTX::BI__nvvm_atom_sys_add_gen_d: 8465 return MakeScopedAtomic(Intrinsic::nvvm_atomic_add_gen_f_sys); 8466 case NVPTX::BI__nvvm_atom_cta_xchg_gen_i: 8467 case NVPTX::BI__nvvm_atom_cta_xchg_gen_l: 8468 case NVPTX::BI__nvvm_atom_cta_xchg_gen_ll: 8469 return MakeScopedAtomic(Intrinsic::nvvm_atomic_exch_gen_i_cta); 8470 case NVPTX::BI__nvvm_atom_sys_xchg_gen_i: 8471 case NVPTX::BI__nvvm_atom_sys_xchg_gen_l: 8472 case NVPTX::BI__nvvm_atom_sys_xchg_gen_ll: 8473 return MakeScopedAtomic(Intrinsic::nvvm_atomic_exch_gen_i_sys); 8474 case NVPTX::BI__nvvm_atom_cta_max_gen_i: 8475 case NVPTX::BI__nvvm_atom_cta_max_gen_ui: 8476 case NVPTX::BI__nvvm_atom_cta_max_gen_l: 8477 case NVPTX::BI__nvvm_atom_cta_max_gen_ul: 8478 case NVPTX::BI__nvvm_atom_cta_max_gen_ll: 8479 case NVPTX::BI__nvvm_atom_cta_max_gen_ull: 8480 return MakeScopedAtomic(Intrinsic::nvvm_atomic_max_gen_i_cta); 8481 case NVPTX::BI__nvvm_atom_sys_max_gen_i: 8482 case NVPTX::BI__nvvm_atom_sys_max_gen_ui: 8483 case NVPTX::BI__nvvm_atom_sys_max_gen_l: 8484 case NVPTX::BI__nvvm_atom_sys_max_gen_ul: 8485 case NVPTX::BI__nvvm_atom_sys_max_gen_ll: 8486 case NVPTX::BI__nvvm_atom_sys_max_gen_ull: 8487 return MakeScopedAtomic(Intrinsic::nvvm_atomic_max_gen_i_sys); 8488 case NVPTX::BI__nvvm_atom_cta_min_gen_i: 8489 case NVPTX::BI__nvvm_atom_cta_min_gen_ui: 8490 case NVPTX::BI__nvvm_atom_cta_min_gen_l: 8491 case NVPTX::BI__nvvm_atom_cta_min_gen_ul: 8492 case NVPTX::BI__nvvm_atom_cta_min_gen_ll: 8493 case NVPTX::BI__nvvm_atom_cta_min_gen_ull: 8494 return MakeScopedAtomic(Intrinsic::nvvm_atomic_min_gen_i_cta); 8495 case NVPTX::BI__nvvm_atom_sys_min_gen_i: 8496 case NVPTX::BI__nvvm_atom_sys_min_gen_ui: 8497 case NVPTX::BI__nvvm_atom_sys_min_gen_l: 8498 case NVPTX::BI__nvvm_atom_sys_min_gen_ul: 8499 case NVPTX::BI__nvvm_atom_sys_min_gen_ll: 8500 case NVPTX::BI__nvvm_atom_sys_min_gen_ull: 8501 return MakeScopedAtomic(Intrinsic::nvvm_atomic_min_gen_i_sys); 8502 case NVPTX::BI__nvvm_atom_cta_inc_gen_ui: 8503 return MakeScopedAtomic(Intrinsic::nvvm_atomic_inc_gen_i_cta); 8504 case NVPTX::BI__nvvm_atom_cta_dec_gen_ui: 8505 return MakeScopedAtomic(Intrinsic::nvvm_atomic_dec_gen_i_cta); 8506 case NVPTX::BI__nvvm_atom_sys_inc_gen_ui: 8507 return MakeScopedAtomic(Intrinsic::nvvm_atomic_inc_gen_i_sys); 8508 case NVPTX::BI__nvvm_atom_sys_dec_gen_ui: 8509 return MakeScopedAtomic(Intrinsic::nvvm_atomic_dec_gen_i_sys); 8510 case NVPTX::BI__nvvm_atom_cta_and_gen_i: 8511 case NVPTX::BI__nvvm_atom_cta_and_gen_l: 8512 case NVPTX::BI__nvvm_atom_cta_and_gen_ll: 8513 return MakeScopedAtomic(Intrinsic::nvvm_atomic_and_gen_i_cta); 8514 case NVPTX::BI__nvvm_atom_sys_and_gen_i: 8515 case NVPTX::BI__nvvm_atom_sys_and_gen_l: 8516 case NVPTX::BI__nvvm_atom_sys_and_gen_ll: 8517 return MakeScopedAtomic(Intrinsic::nvvm_atomic_and_gen_i_sys); 8518 case NVPTX::BI__nvvm_atom_cta_or_gen_i: 8519 case NVPTX::BI__nvvm_atom_cta_or_gen_l: 8520 case NVPTX::BI__nvvm_atom_cta_or_gen_ll: 8521 return MakeScopedAtomic(Intrinsic::nvvm_atomic_or_gen_i_cta); 8522 case NVPTX::BI__nvvm_atom_sys_or_gen_i: 8523 case NVPTX::BI__nvvm_atom_sys_or_gen_l: 8524 case NVPTX::BI__nvvm_atom_sys_or_gen_ll: 8525 return MakeScopedAtomic(Intrinsic::nvvm_atomic_or_gen_i_sys); 8526 case NVPTX::BI__nvvm_atom_cta_xor_gen_i: 8527 case NVPTX::BI__nvvm_atom_cta_xor_gen_l: 8528 case NVPTX::BI__nvvm_atom_cta_xor_gen_ll: 8529 return MakeScopedAtomic(Intrinsic::nvvm_atomic_xor_gen_i_cta); 8530 case NVPTX::BI__nvvm_atom_sys_xor_gen_i: 8531 case NVPTX::BI__nvvm_atom_sys_xor_gen_l: 8532 case NVPTX::BI__nvvm_atom_sys_xor_gen_ll: 8533 return MakeScopedAtomic(Intrinsic::nvvm_atomic_xor_gen_i_sys); 8534 case NVPTX::BI__nvvm_atom_cta_cas_gen_i: 8535 case NVPTX::BI__nvvm_atom_cta_cas_gen_l: 8536 case NVPTX::BI__nvvm_atom_cta_cas_gen_ll: { 8537 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8538 return Builder.CreateCall( 8539 CGM.getIntrinsic( 8540 Intrinsic::nvvm_atomic_cas_gen_i_cta, 8541 {Ptr->getType()->getPointerElementType(), Ptr->getType()}), 8542 {Ptr, EmitScalarExpr(E->getArg(1)), EmitScalarExpr(E->getArg(2))}); 8543 } 8544 case NVPTX::BI__nvvm_atom_sys_cas_gen_i: 8545 case NVPTX::BI__nvvm_atom_sys_cas_gen_l: 8546 case NVPTX::BI__nvvm_atom_sys_cas_gen_ll: { 8547 Value *Ptr = EmitScalarExpr(E->getArg(0)); 8548 return Builder.CreateCall( 8549 CGM.getIntrinsic( 8550 Intrinsic::nvvm_atomic_cas_gen_i_sys, 8551 {Ptr->getType()->getPointerElementType(), Ptr->getType()}), 8552 {Ptr, EmitScalarExpr(E->getArg(1)), EmitScalarExpr(E->getArg(2))}); 8553 } 8554 default: 8555 return nullptr; 8556 } 8557 } 8558 8559 Value *CodeGenFunction::EmitWebAssemblyBuiltinExpr(unsigned BuiltinID, 8560 const CallExpr *E) { 8561 switch (BuiltinID) { 8562 case WebAssembly::BI__builtin_wasm_current_memory: { 8563 llvm::Type *ResultType = ConvertType(E->getType()); 8564 Value *Callee = CGM.getIntrinsic(Intrinsic::wasm_current_memory, ResultType); 8565 return Builder.CreateCall(Callee); 8566 } 8567 case WebAssembly::BI__builtin_wasm_grow_memory: { 8568 Value *X = EmitScalarExpr(E->getArg(0)); 8569 Value *Callee = CGM.getIntrinsic(Intrinsic::wasm_grow_memory, X->getType()); 8570 return Builder.CreateCall(Callee, X); 8571 } 8572 8573 default: 8574 return nullptr; 8575 } 8576 } 8577