From owner-svn-src-head@freebsd.org Thu Mar 7 19:33:41 2019 Return-Path: Delivered-To: svn-src-head@mailman.ysv.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mailman.ysv.freebsd.org (Postfix) with ESMTP id 144641522990; Thu, 7 Mar 2019 19:33:41 +0000 (UTC) (envelope-from dim@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) server-signature RSA-PSS (4096 bits) client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "Let's Encrypt Authority X3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id AD7766F783; Thu, 7 Mar 2019 19:33:40 +0000 (UTC) (envelope-from dim@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 9AE9520458; Thu, 7 Mar 2019 19:33:40 +0000 (UTC) (envelope-from dim@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id x27JXe98023273; Thu, 7 Mar 2019 19:33:40 GMT (envelope-from dim@FreeBSD.org) Received: (from dim@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id x27JXdMW023266; Thu, 7 Mar 2019 19:33:39 GMT (envelope-from dim@FreeBSD.org) Message-Id: <201903071933.x27JXdMW023266@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: dim set sender to dim@FreeBSD.org using -f From: Dimitry Andric Date: Thu, 7 Mar 2019 19:33:39 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r344896 - in head/contrib/llvm/tools/clang: include/clang/AST include/clang/Basic lib/AST lib/CodeGen lib/Sema X-SVN-Group: head X-SVN-Commit-Author: dim X-SVN-Commit-Paths: in head/contrib/llvm/tools/clang: include/clang/AST include/clang/Basic lib/AST lib/CodeGen lib/Sema X-SVN-Commit-Revision: 344896 X-SVN-Commit-Repository: base MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-Rspamd-Queue-Id: AD7766F783 X-Spamd-Bar: -- Authentication-Results: mx1.freebsd.org X-Spamd-Result: default: False [-2.96 / 15.00]; local_wl_from(0.00)[FreeBSD.org]; NEURAL_HAM_MEDIUM(-1.00)[-1.000,0]; NEURAL_HAM_LONG(-1.00)[-1.000,0]; NEURAL_HAM_SHORT(-0.97)[-0.965,0]; ASN(0.00)[asn:11403, ipnet:2610:1c1:1::/48, country:US] X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 07 Mar 2019 19:33:41 -0000 Author: dim Date: Thu Mar 7 19:33:39 2019 New Revision: 344896 URL: https://svnweb.freebsd.org/changeset/base/344896 Log: Pull in r354937 from upstream clang trunk (by Jörg Sonnenberger): Fix inline assembler constraint validation The current constraint logic is both too lax and too strict. It fails for input outside the [INT_MIN..INT_MAX] range, but it also implicitly accepts 0 as value when it should not. Adjust logic to handle both correctly. Differential Revision: https://reviews.llvm.org/D58649 Pull in r355491 from upstream clang trunk (by Hans Wennborg): Inline asm constraints: allow ICE-like pointers for the "n" constraint (PR40890) Apparently GCC allows this, and there's code relying on it (see bug). The idea is to allow expression that would have been allowed if they were cast to int. So I based the code on how such a cast would be done (the CK_PointerToIntegral case in IntExprEvaluator::VisitCastExpr()). Differential Revision: https://reviews.llvm.org/D58821 These should fix assertions and errors when using the inline assembly "n" constraint in certain ways. In case of devel/valgrind, a pointer was used as the input for the constraint, which lead to "Assertion failed: (isInt() && "Invalid accessor"), function getInt". In case of math/secp256k1, a very large integer value was used as input for the constraint, which lead to "error: value '4624529908474429119' out of range for constraint 'n'". PR: 236216, 236194 MFC after: 1 month X-MFC-With: r344779 Modified: head/contrib/llvm/tools/clang/include/clang/AST/APValue.h head/contrib/llvm/tools/clang/include/clang/Basic/TargetInfo.h head/contrib/llvm/tools/clang/lib/AST/APValue.cpp head/contrib/llvm/tools/clang/lib/AST/ExprConstant.cpp head/contrib/llvm/tools/clang/lib/CodeGen/CGStmt.cpp head/contrib/llvm/tools/clang/lib/Sema/SemaStmtAsm.cpp Modified: head/contrib/llvm/tools/clang/include/clang/AST/APValue.h ============================================================================== --- head/contrib/llvm/tools/clang/include/clang/AST/APValue.h Thu Mar 7 19:32:01 2019 (r344895) +++ head/contrib/llvm/tools/clang/include/clang/AST/APValue.h Thu Mar 7 19:33:39 2019 (r344896) @@ -257,6 +257,12 @@ class APValue { (public) return const_cast(this)->getInt(); } + /// Try to convert this value to an integral constant. This works if it's an + /// integer, null pointer, or offset from a null pointer. Returns true on + /// success. + bool toIntegralConstant(APSInt &Result, QualType SrcTy, + const ASTContext &Ctx) const; + APFloat &getFloat() { assert(isFloat() && "Invalid accessor"); return *(APFloat*)(char*)Data.buffer; Modified: head/contrib/llvm/tools/clang/include/clang/Basic/TargetInfo.h ============================================================================== --- head/contrib/llvm/tools/clang/include/clang/Basic/TargetInfo.h Thu Mar 7 19:32:01 2019 (r344895) +++ head/contrib/llvm/tools/clang/include/clang/Basic/TargetInfo.h Thu Mar 7 19:33:39 2019 (r344896) @@ -807,6 +807,7 @@ class TargetInfo : public RefCountedBase { struct { int Min; int Max; + bool isConstrained; } ImmRange; llvm::SmallSet ImmSet; @@ -817,6 +818,7 @@ class TargetInfo : public RefCountedBase { : Flags(0), TiedOperand(-1), ConstraintStr(ConstraintStr.str()), Name(Name.str()) { ImmRange.Min = ImmRange.Max = 0; + ImmRange.isConstrained = false; } const std::string &getConstraintStr() const { return ConstraintStr; } @@ -845,8 +847,9 @@ class TargetInfo : public RefCountedBase { return (Flags & CI_ImmediateConstant) != 0; } bool isValidAsmImmediate(const llvm::APInt &Value) const { - return (Value.sge(ImmRange.Min) && Value.sle(ImmRange.Max)) || - ImmSet.count(Value.getZExtValue()) != 0; + if (!ImmSet.empty()) + return ImmSet.count(Value.getZExtValue()) != 0; + return !ImmRange.isConstrained || (Value.sge(ImmRange.Min) && Value.sle(ImmRange.Max)); } void setIsReadWrite() { Flags |= CI_ReadWrite; } @@ -858,6 +861,7 @@ class TargetInfo : public RefCountedBase { Flags |= CI_ImmediateConstant; ImmRange.Min = Min; ImmRange.Max = Max; + ImmRange.isConstrained = true; } void setRequiresImmediate(llvm::ArrayRef Exacts) { Flags |= CI_ImmediateConstant; @@ -870,8 +874,6 @@ class TargetInfo : public RefCountedBase { } void setRequiresImmediate() { Flags |= CI_ImmediateConstant; - ImmRange.Min = INT_MIN; - ImmRange.Max = INT_MAX; } /// Indicate that this is an input operand that is tied to Modified: head/contrib/llvm/tools/clang/lib/AST/APValue.cpp ============================================================================== --- head/contrib/llvm/tools/clang/lib/AST/APValue.cpp Thu Mar 7 19:32:01 2019 (r344895) +++ head/contrib/llvm/tools/clang/lib/AST/APValue.cpp Thu Mar 7 19:33:39 2019 (r344896) @@ -600,6 +600,26 @@ std::string APValue::getAsString(ASTContext &Ctx, Qual return Result; } +bool APValue::toIntegralConstant(APSInt &Result, QualType SrcTy, + const ASTContext &Ctx) const { + if (isInt()) { + Result = getInt(); + return true; + } + + if (isLValue() && isNullPointer()) { + Result = Ctx.MakeIntValue(Ctx.getTargetNullPointerValue(SrcTy), SrcTy); + return true; + } + + if (isLValue() && !getLValueBase()) { + Result = Ctx.MakeIntValue(getLValueOffset().getQuantity(), SrcTy); + return true; + } + + return false; +} + const APValue::LValueBase APValue::getLValueBase() const { assert(isLValue() && "Invalid accessor"); return ((const LV*)(const void*)Data.buffer)->Base; Modified: head/contrib/llvm/tools/clang/lib/AST/ExprConstant.cpp ============================================================================== --- head/contrib/llvm/tools/clang/lib/AST/ExprConstant.cpp Thu Mar 7 19:32:01 2019 (r344895) +++ head/contrib/llvm/tools/clang/lib/AST/ExprConstant.cpp Thu Mar 7 19:33:39 2019 (r344896) @@ -9821,13 +9821,12 @@ bool IntExprEvaluator::VisitCastExpr(const CastExpr *E return true; } - uint64_t V; - if (LV.isNullPointer()) - V = Info.Ctx.getTargetNullPointerValue(SrcType); - else - V = LV.getLValueOffset().getQuantity(); + APSInt AsInt; + APValue V; + LV.moveInto(V); + if (!V.toIntegralConstant(AsInt, SrcType, Info.Ctx)) + llvm_unreachable("Can't cast this!"); - APSInt AsInt = Info.Ctx.MakeIntValue(V, SrcType); return Success(HandleIntToIntCast(Info, E, DestType, SrcType, AsInt), E); } Modified: head/contrib/llvm/tools/clang/lib/CodeGen/CGStmt.cpp ============================================================================== --- head/contrib/llvm/tools/clang/lib/CodeGen/CGStmt.cpp Thu Mar 7 19:32:01 2019 (r344895) +++ head/contrib/llvm/tools/clang/lib/CodeGen/CGStmt.cpp Thu Mar 7 19:33:39 2019 (r344896) @@ -1821,8 +1821,15 @@ llvm::Value* CodeGenFunction::EmitAsmInput( // (immediate or symbolic), try to emit it as such. if (!Info.allowsRegister() && !Info.allowsMemory()) { if (Info.requiresImmediateConstant()) { - llvm::APSInt AsmConst = InputExpr->EvaluateKnownConstInt(getContext()); - return llvm::ConstantInt::get(getLLVMContext(), AsmConst); + Expr::EvalResult EVResult; + InputExpr->EvaluateAsRValue(EVResult, getContext(), true); + + llvm::APSInt IntResult; + if (!EVResult.Val.toIntegralConstant(IntResult, InputExpr->getType(), + getContext())) + llvm_unreachable("Invalid immediate constant!"); + + return llvm::ConstantInt::get(getLLVMContext(), IntResult); } Expr::EvalResult Result; Modified: head/contrib/llvm/tools/clang/lib/Sema/SemaStmtAsm.cpp ============================================================================== --- head/contrib/llvm/tools/clang/lib/Sema/SemaStmtAsm.cpp Thu Mar 7 19:32:01 2019 (r344895) +++ head/contrib/llvm/tools/clang/lib/Sema/SemaStmtAsm.cpp Thu Mar 7 19:33:39 2019 (r344896) @@ -383,11 +383,20 @@ StmtResult Sema::ActOnGCCAsmStmt(SourceLocation AsmLoc return StmtError( Diag(InputExpr->getBeginLoc(), diag::err_asm_immediate_expected) << Info.getConstraintStr() << InputExpr->getSourceRange()); - llvm::APSInt Result = EVResult.Val.getInt(); - if (!Info.isValidAsmImmediate(Result)) + + // For compatibility with GCC, we also allow pointers that would be + // integral constant expressions if they were cast to int. + llvm::APSInt IntResult; + if (!EVResult.Val.toIntegralConstant(IntResult, InputExpr->getType(), + Context)) + return StmtError( + Diag(InputExpr->getBeginLoc(), diag::err_asm_immediate_expected) + << Info.getConstraintStr() << InputExpr->getSourceRange()); + + if (!Info.isValidAsmImmediate(IntResult)) return StmtError(Diag(InputExpr->getBeginLoc(), diag::err_invalid_asm_value_for_constraint) - << Result.toString(10) << Info.getConstraintStr() + << IntResult.toString(10) << Info.getConstraintStr() << InputExpr->getSourceRange()); }