diff --git a/src/librustc_codegen_llvm/base.rs b/src/librustc_codegen_llvm/base.rs index 31884e0748bfcbb1aab998e023c2f8eaaf2ae475..f8b9c794086261bc44028f63ac2c805fe28587d1 100644 --- a/src/librustc_codegen_llvm/base.rs +++ b/src/librustc_codegen_llvm/base.rs @@ -75,7 +75,7 @@ use rustc_data_structures::sync::Lrc; use rustc_data_structures::indexed_vec::Idx; -use traits::{IntPredicate, BuilderMethods}; +use traits::{IntPredicate, RealPredicate, BuilderMethods}; use llvm::BasicBlock; use std::any::Any; @@ -143,14 +143,14 @@ pub fn bin_op_to_icmp_predicate(op: hir::BinOpKind, } } -pub fn bin_op_to_fcmp_predicate(op: hir::BinOpKind) -> llvm::RealPredicate { +pub fn bin_op_to_fcmp_predicate(op: hir::BinOpKind) -> RealPredicate { match op { - hir::BinOpKind::Eq => llvm::RealOEQ, - hir::BinOpKind::Ne => llvm::RealUNE, - hir::BinOpKind::Lt => llvm::RealOLT, - hir::BinOpKind::Le => llvm::RealOLE, - hir::BinOpKind::Gt => llvm::RealOGT, - hir::BinOpKind::Ge => llvm::RealOGE, + hir::BinOpKind::Eq => RealPredicate::RealOEQ, + hir::BinOpKind::Ne => RealPredicate::RealUNE, + hir::BinOpKind::Lt => RealPredicate::RealOLT, + hir::BinOpKind::Le => RealPredicate::RealOLE, + hir::BinOpKind::Gt => RealPredicate::RealOGT, + hir::BinOpKind::Ge => RealPredicate::RealOGE, op => { bug!("comparison_op_to_fcmp_predicate: expected comparison operator, \ found {:?}", diff --git a/src/librustc_codegen_llvm/builder.rs b/src/librustc_codegen_llvm/builder.rs index 640067fd6a38b98704ecfdbe748b272cb1f06d6b..488b1a2ff4e322a180ca1d7aa7f5dcf8cd12fb66 100644 --- a/src/librustc_codegen_llvm/builder.rs +++ b/src/librustc_codegen_llvm/builder.rs @@ -9,7 +9,7 @@ // except according to those terms. use llvm::{AtomicRmwBinOp, AtomicOrdering, SynchronizationScope, AsmDialect}; -use llvm::{RealPredicate, False, OperandBundleDef}; +use llvm::{False, OperandBundleDef}; use llvm::{self, BasicBlock}; use common::*; use type_::Type; @@ -697,7 +697,7 @@ fn icmp(&self, op: traits::IntPredicate, lhs: &'ll Value, rhs: &'ll Value) -> &' } } - fn fcmp(&self, op: RealPredicate, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value { + fn fcmp(&self, op: traits::RealPredicate, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value { self.count_insn("fcmp"); unsafe { llvm::LLVMBuildFCmp(self.llbuilder, op as c_uint, lhs, rhs, noname()) diff --git a/src/librustc_codegen_llvm/llvm/ffi.rs b/src/librustc_codegen_llvm/llvm/ffi.rs index 9c0ffd2b7acbfb5158754c20d2ad1751cd29f20e..37fa2e46b28bf235ff5becc5b602458ff8dc7614 100644 --- a/src/librustc_codegen_llvm/llvm/ffi.rs +++ b/src/librustc_codegen_llvm/llvm/ffi.rs @@ -181,6 +181,29 @@ pub enum RealPredicate { RealPredicateTrue = 15, } +impl traits::RealPredicateMethods for RealPredicate { + fn convert_to_backend_specific(realpred: traits::RealPredicate) -> Self { + match realpred { + traits::RealPredicate::RealPredicateFalse => RealPredicate::RealPredicateFalse, + traits::RealPredicate::RealOEQ => RealPredicate::RealOEQ, + traits::RealPredicate::RealOGT => RealPredicate::RealOGT, + traits::RealPredicate::RealOGE => RealPredicate::RealOGE, + traits::RealPredicate::RealOLT => RealPredicate::RealOLT, + traits::RealPredicate::RealOLE => RealPredicate::RealOLE, + traits::RealPredicate::RealONE => RealPredicate::RealONE, + traits::RealPredicate::RealORD => RealPredicate::RealORD, + traits::RealPredicate::RealUNO => RealPredicate::RealUNO, + traits::RealPredicate::RealUEQ => RealPredicate::RealUEQ, + traits::RealPredicate::RealUGT => RealPredicate::RealUGT, + traits::RealPredicate::RealUGE => RealPredicate::RealUGE, + traits::RealPredicate::RealULT => RealPredicate::RealULT, + traits::RealPredicate::RealULE => RealPredicate::RealULE, + traits::RealPredicate::RealUNE => RealPredicate::RealUNE, + traits::RealPredicate::RealPredicateTrue => RealPredicate::RealPredicateTrue + } + } +} + /// LLVMTypeKind #[derive(Copy, Clone, PartialEq, Debug)] #[repr(C)] diff --git a/src/librustc_codegen_llvm/mir/rvalue.rs b/src/librustc_codegen_llvm/mir/rvalue.rs index 35e0fd396eee6ad6db13a858582afb9c82cfd6f5..05c775522318c13539560521bdf7d9a5fd3e21d5 100644 --- a/src/librustc_codegen_llvm/mir/rvalue.rs +++ b/src/librustc_codegen_llvm/mir/rvalue.rs @@ -8,7 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use llvm; use rustc::ty::{self, Ty}; use rustc::ty::cast::{CastTy, IntTy}; use rustc::ty::layout::{self, LayoutOf}; @@ -28,7 +27,7 @@ use type_of::LayoutLlvmExt; use value::Value; -use traits::{IntPredicate,BuilderMethods}; +use traits::{IntPredicate, RealPredicate, BuilderMethods}; use super::{FunctionCx, LocalRef}; use super::operand::{OperandRef, OperandValue}; @@ -962,8 +961,8 @@ fn int_min(signed: bool, int_ty: &Type) -> i128 { // negation, and the negation can be merged into the select. Therefore, it not necessarily any // more expensive than a ordered ("normal") comparison. Whether these optimizations will be // performed is ultimately up to the backend, but at least x86 does perform them. - let less_or_nan = bx.fcmp(llvm::RealULT, x, f_min); - let greater = bx.fcmp(llvm::RealOGT, x, f_max); + let less_or_nan = bx.fcmp(RealPredicate::RealULT, x, f_min); + let greater = bx.fcmp(RealPredicate::RealOGT, x, f_max); let int_max = C_uint_big(int_ty, int_max(signed, int_ty)); let int_min = C_uint_big(int_ty, int_min(signed, int_ty) as u128); let s0 = bx.select(less_or_nan, int_min, fptosui_result); @@ -974,7 +973,7 @@ fn int_min(signed: bool, int_ty: &Type) -> i128 { // Therefore we only need to execute this step for signed integer types. if signed { // LLVM has no isNaN predicate, so we use (x == x) instead - bx.select(bx.fcmp(llvm::RealOEQ, x, x), s1, C_uint(int_ty, 0)) + bx.select(bx.fcmp(RealPredicate::RealOEQ, x, x), s1, C_uint(int_ty, 0)) } else { s1 } diff --git a/src/librustc_codegen_llvm/traits.rs b/src/librustc_codegen_llvm/traits.rs index e35669dc383b591b9639ad79faa74b3eb15d6201..0c53d0eaf90423f2fc288327d1ba834a4f162035 100644 --- a/src/librustc_codegen_llvm/traits.rs +++ b/src/librustc_codegen_llvm/traits.rs @@ -9,7 +9,7 @@ // except according to those terms. use llvm::{AtomicRmwBinOp, AtomicOrdering, SynchronizationScope, AsmDialect}; -use llvm::{RealPredicate, OperandBundleDef}; +use llvm::OperandBundleDef; use common::*; use type_::Type; use libc::c_char; @@ -38,6 +38,30 @@ pub trait IntPredicateMethods { fn convert_to_backend_specific(intpre : IntPredicate) -> Self; } +#[allow(dead_code)] +pub enum RealPredicate { + RealPredicateFalse, + RealOEQ, + RealOGT, + RealOGE, + RealOLT, + RealOLE, + RealONE, + RealORD, + RealUNO, + RealUEQ, + RealUGT, + RealUGE, + RealULT, + RealULE, + RealUNE, + RealPredicateTrue, +} + +pub trait RealPredicateMethods { + fn convert_to_backend_specific(realpred : RealPredicate) -> Self; +} + pub trait BuilderMethods<'a, 'll :'a, 'tcx: 'll, Value : ?Sized,