Skip to content

Commit 5d0930c

Browse files
committed
Remove Op type.
First, move the `lang_item_for_op` call from the top of `lookup_op_method`'s body to its callsites. It makes those callsites a little more verbose, but also means `lookup_op_method` no longer cares whether it's handling a binop or unop. This lets us remove `Op` and split `lang_item_for_op` into `lang_item_for_{bin,un}op`, which is a little simpler. This change is a prerequisite for adding the `ast::AssignOpKind` type in a subsequent commit.
1 parent f9e0239 commit 5d0930c

File tree

1 file changed

+46
-40
lines changed
  • compiler/rustc_hir_typeck/src

1 file changed

+46
-40
lines changed

compiler/rustc_hir_typeck/src/op.rs

Lines changed: 46 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -4,15 +4,15 @@ use rustc_data_structures::packed::Pu128;
44
use rustc_errors::codes::*;
55
use rustc_errors::{Applicability, Diag, struct_span_code_err};
66
use rustc_infer::traits::ObligationCauseCode;
7+
use rustc_middle::bug;
78
use rustc_middle::ty::adjustment::{
89
Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability,
910
};
1011
use rustc_middle::ty::print::with_no_trimmed_paths;
1112
use rustc_middle::ty::{self, IsSuggestable, Ty, TyCtxt, TypeVisitableExt};
12-
use rustc_middle::{bug, span_bug};
1313
use rustc_session::errors::ExprParenthesesNeeded;
1414
use rustc_span::source_map::Spanned;
15-
use rustc_span::{Ident, Span, sym};
15+
use rustc_span::{Ident, Span, Symbol, sym};
1616
use rustc_trait_selection::infer::InferCtxtExt;
1717
use rustc_trait_selection::traits::{FulfillmentError, Obligation, ObligationCtxt};
1818
use rustc_type_ir::TyKind::*;
@@ -50,7 +50,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
5050
.lookup_op_method(
5151
(lhs, lhs_deref_ty),
5252
Some((rhs, rhs_ty)),
53-
Op::Binary(op, IsAssign::Yes),
53+
lang_item_for_binop(self.tcx, op, IsAssign::Yes),
54+
op.span,
5455
expected,
5556
)
5657
.is_ok()
@@ -61,7 +62,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
6162
.lookup_op_method(
6263
(lhs, lhs_ty),
6364
Some((rhs, rhs_ty)),
64-
Op::Binary(op, IsAssign::Yes),
65+
lang_item_for_binop(self.tcx, op, IsAssign::Yes),
66+
op.span,
6567
expected,
6668
)
6769
.is_err()
@@ -243,7 +245,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
243245
let result = self.lookup_op_method(
244246
(lhs_expr, lhs_ty),
245247
Some((rhs_expr, rhs_ty_var)),
246-
Op::Binary(op, is_assign),
248+
lang_item_for_binop(self.tcx, op, is_assign),
249+
op.span,
247250
expected,
248251
);
249252

@@ -302,8 +305,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
302305
Ty::new_misc_error(self.tcx)
303306
}
304307
Err(errors) => {
305-
let (_, trait_def_id) =
306-
lang_item_for_op(self.tcx, Op::Binary(op, is_assign), op.span);
308+
let (_, trait_def_id) = lang_item_for_binop(self.tcx, op, is_assign);
307309
let missing_trait = trait_def_id
308310
.map(|def_id| with_no_trimmed_paths!(self.tcx.def_path_str(def_id)));
309311
let mut path = None;
@@ -410,7 +412,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
410412
.lookup_op_method(
411413
(lhs_expr, lhs_deref_ty),
412414
Some((rhs_expr, rhs_ty)),
413-
Op::Binary(op, is_assign),
415+
lang_item_for_binop(self.tcx, op, is_assign),
416+
op.span,
414417
expected,
415418
)
416419
.is_ok()
@@ -443,7 +446,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
443446
.lookup_op_method(
444447
(lhs_expr, lhs_adjusted_ty),
445448
Some((rhs_expr, rhs_adjusted_ty)),
446-
Op::Binary(op, is_assign),
449+
lang_item_for_binop(self.tcx, op, is_assign),
450+
op.span,
447451
expected,
448452
)
449453
.is_ok()
@@ -500,7 +504,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
500504
self.lookup_op_method(
501505
(lhs_expr, lhs_ty),
502506
Some((rhs_expr, rhs_ty)),
503-
Op::Binary(op, is_assign),
507+
lang_item_for_binop(self.tcx, op, is_assign),
508+
op.span,
504509
expected,
505510
)
506511
.is_ok()
@@ -593,7 +598,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
593598
.lookup_op_method(
594599
(lhs_expr, lhs_ty),
595600
Some((rhs_expr, rhs_ty)),
596-
Op::Binary(op, is_assign),
601+
lang_item_for_binop(self.tcx, op, is_assign),
602+
op.span,
597603
expected,
598604
)
599605
.unwrap_err();
@@ -800,7 +806,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
800806
expected: Expectation<'tcx>,
801807
) -> Ty<'tcx> {
802808
assert!(op.is_by_value());
803-
match self.lookup_op_method((ex, operand_ty), None, Op::Unary(op, ex.span), expected) {
809+
match self.lookup_op_method(
810+
(ex, operand_ty),
811+
None,
812+
lang_item_for_unop(self.tcx, op),
813+
ex.span,
814+
expected,
815+
) {
804816
Ok(method) => {
805817
self.write_method_call_and_enforce_effects(ex.hir_id, ex.span, method);
806818
method.sig.output()
@@ -899,21 +911,18 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
899911
&self,
900912
(lhs_expr, lhs_ty): (&'tcx hir::Expr<'tcx>, Ty<'tcx>),
901913
opt_rhs: Option<(&'tcx hir::Expr<'tcx>, Ty<'tcx>)>,
902-
op: Op,
914+
(opname, trait_did): (Symbol, Option<hir::def_id::DefId>),
915+
span: Span,
903916
expected: Expectation<'tcx>,
904917
) -> Result<MethodCallee<'tcx>, Vec<FulfillmentError<'tcx>>> {
905-
let span = match op {
906-
Op::Binary(op, _) => op.span,
907-
Op::Unary(_, span) => span,
908-
};
909-
let (opname, Some(trait_did)) = lang_item_for_op(self.tcx, op, span) else {
918+
let Some(trait_did) = trait_did else {
910919
// Bail if the operator trait is not defined.
911920
return Err(vec![]);
912921
};
913922

914923
debug!(
915-
"lookup_op_method(lhs_ty={:?}, op={:?}, opname={:?}, trait_did={:?})",
916-
lhs_ty, op, opname, trait_did
924+
"lookup_op_method(lhs_ty={:?}, opname={:?}, trait_did={:?})",
925+
lhs_ty, opname, trait_did
917926
);
918927

919928
let opname = Ident::with_dummy_span(opname);
@@ -981,13 +990,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
981990
}
982991
}
983992

984-
fn lang_item_for_op(
993+
fn lang_item_for_binop(
985994
tcx: TyCtxt<'_>,
986-
op: Op,
987-
span: Span,
988-
) -> (rustc_span::Symbol, Option<hir::def_id::DefId>) {
995+
op: hir::BinOp,
996+
is_assign: IsAssign,
997+
) -> (Symbol, Option<hir::def_id::DefId>) {
989998
let lang = tcx.lang_items();
990-
if let Op::Binary(op, IsAssign::Yes) = op {
999+
if is_assign == IsAssign::Yes {
9911000
match op.node {
9921001
hir::BinOpKind::Add => (sym::add_assign, lang.add_assign_trait()),
9931002
hir::BinOpKind::Sub => (sym::sub_assign, lang.sub_assign_trait()),
@@ -1007,10 +1016,10 @@ fn lang_item_for_op(
10071016
| hir::BinOpKind::Ne
10081017
| hir::BinOpKind::And
10091018
| hir::BinOpKind::Or => {
1010-
span_bug!(span, "impossible assignment operation: {}=", op.node.as_str())
1019+
bug!("impossible assignment operation: {}=", op.node.as_str())
10111020
}
10121021
}
1013-
} else if let Op::Binary(op, IsAssign::No) = op {
1022+
} else {
10141023
match op.node {
10151024
hir::BinOpKind::Add => (sym::add, lang.add_trait()),
10161025
hir::BinOpKind::Sub => (sym::sub, lang.sub_trait()),
@@ -1029,15 +1038,18 @@ fn lang_item_for_op(
10291038
hir::BinOpKind::Eq => (sym::eq, lang.eq_trait()),
10301039
hir::BinOpKind::Ne => (sym::ne, lang.eq_trait()),
10311040
hir::BinOpKind::And | hir::BinOpKind::Or => {
1032-
span_bug!(span, "&& and || are not overloadable")
1041+
bug!("&& and || are not overloadable")
10331042
}
10341043
}
1035-
} else if let Op::Unary(hir::UnOp::Not, _) = op {
1036-
(sym::not, lang.not_trait())
1037-
} else if let Op::Unary(hir::UnOp::Neg, _) = op {
1038-
(sym::neg, lang.neg_trait())
1039-
} else {
1040-
bug!("lookup_op_method: op not supported: {:?}", op)
1044+
}
1045+
}
1046+
1047+
fn lang_item_for_unop(tcx: TyCtxt<'_>, op: hir::UnOp) -> (Symbol, Option<hir::def_id::DefId>) {
1048+
let lang = tcx.lang_items();
1049+
match op {
1050+
hir::UnOp::Not => (sym::not, lang.not_trait()),
1051+
hir::UnOp::Neg => (sym::neg, lang.neg_trait()),
1052+
hir::UnOp::Deref => bug!("Deref is not overloadable"),
10411053
}
10421054
}
10431055

@@ -1098,12 +1110,6 @@ enum IsAssign {
10981110
Yes,
10991111
}
11001112

1101-
#[derive(Clone, Copy, Debug)]
1102-
enum Op {
1103-
Binary(hir::BinOp, IsAssign),
1104-
Unary(hir::UnOp, Span),
1105-
}
1106-
11071113
/// Dereferences a single level of immutable referencing.
11081114
fn deref_ty_if_possible(ty: Ty<'_>) -> Ty<'_> {
11091115
match ty.kind() {

0 commit comments

Comments
 (0)