@@ -1056,6 +1056,11 @@ impl<'tcx, 'pat> Candidate<'pat, 'tcx> {
10561056 }
10571057 }
10581058
1059+ /// Returns whether the first match pair of this candidate is an or-pattern.
1060+ fn starts_with_or_pattern ( & self ) -> bool {
1061+ matches ! ( & * self . match_pairs, [ MatchPair { test_case: TestCase :: Or { .. } , .. } , ..] )
1062+ }
1063+
10591064 /// Visit the leaf candidates (those with no subcandidates) contained in
10601065 /// this candidate.
10611066 fn visit_leaves < ' a > ( & ' a mut self , mut visit_leaf : impl FnMut ( & ' a mut Self ) ) {
@@ -1372,39 +1377,20 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
13721377 otherwise_block : BasicBlock ,
13731378 candidates : & mut [ & mut Candidate < ' _ , ' tcx > ] ,
13741379 ) {
1375- // If any candidate starts with an or-pattern, we have to expand the or-pattern before we
1376- // can proceed further.
1377- let expand_ors = candidates. iter ( ) . any ( |candidate| {
1378- matches ! (
1379- & * candidate. match_pairs,
1380- [ MatchPair { test_case: TestCase :: Or { .. } , .. } , ..]
1381- )
1382- } ) ;
13831380 ensure_sufficient_stack ( || {
1384- if !expand_ors {
1385- // No candidates start with an or-pattern, we can continue.
1386- self . match_expanded_candidates (
1387- span,
1388- scrutinee_span,
1389- start_block,
1390- otherwise_block,
1391- candidates,
1392- ) ;
1393- } else {
1394- self . expand_and_match_or_candidates (
1395- span,
1396- scrutinee_span,
1397- start_block,
1398- otherwise_block,
1399- candidates,
1400- ) ;
1401- }
1381+ self . match_candidates_with_enough_stack (
1382+ span,
1383+ scrutinee_span,
1384+ start_block,
1385+ otherwise_block,
1386+ candidates,
1387+ )
14021388 } ) ;
14031389 }
14041390
1405- /// Construct the decision tree for `candidates`. Caller must ensure that no candidate in
1406- /// `candidates` starts with an or-pattern .
1407- fn match_expanded_candidates (
1391+ /// Construct the decision tree for `candidates`. Don't call this, call `match_candidates`
1392+ /// instead to reserve sufficient stack space .
1393+ fn match_candidates_with_enough_stack (
14081394 & mut self ,
14091395 span : Span ,
14101396 scrutinee_span : Span ,
@@ -1429,12 +1415,17 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
14291415 // The first candidate has satisfied all its match pairs; we link it up and continue
14301416 // with the remaining candidates.
14311417 start_block = self . select_matched_candidate ( first, start_block) ;
1432- self . match_expanded_candidates (
1418+ self . match_candidates ( span, scrutinee_span, start_block, otherwise_block, remaining)
1419+ }
1420+ candidates if candidates. iter ( ) . any ( |candidate| candidate. starts_with_or_pattern ( ) ) => {
1421+ // If any candidate starts with an or-pattern, we have to expand the or-pattern before we
1422+ // can proceed further.
1423+ self . expand_and_match_or_candidates (
14331424 span,
14341425 scrutinee_span,
14351426 start_block,
14361427 otherwise_block,
1437- remaining ,
1428+ candidates ,
14381429 )
14391430 }
14401431 candidates => {
@@ -1528,9 +1519,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
15281519 let mut expand_until = 0 ;
15291520 for ( i, candidate) in candidates. iter ( ) . enumerate ( ) {
15301521 expand_until = i + 1 ;
1531- if candidate. match_pairs . len ( ) > 1
1532- && matches ! ( & candidate. match_pairs[ 0 ] . test_case, TestCase :: Or { .. } )
1533- {
1522+ if candidate. match_pairs . len ( ) > 1 && candidate. starts_with_or_pattern ( ) {
15341523 // The candidate has an or-pattern as well as more match pairs: we must
15351524 // split the candidates list here.
15361525 break ;
@@ -1541,8 +1530,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
15411530 // Expand one level of or-patterns for each candidate in `candidates_to_expand`.
15421531 let mut expanded_candidates = Vec :: new ( ) ;
15431532 for candidate in candidates_to_expand. iter_mut ( ) {
1544- if let [ MatchPair { test_case : TestCase :: Or { .. } , .. } , ..] = & * candidate. match_pairs
1545- {
1533+ if candidate. starts_with_or_pattern ( ) {
15461534 let or_match_pair = candidate. match_pairs . remove ( 0 ) ;
15471535 // Expand the or-pattern into subcandidates.
15481536 self . create_or_subcandidates ( candidate, or_match_pair) ;
0 commit comments