@@ -3533,6 +3533,40 @@ impl Parse for TypeHandle {
3533
3533
return Ok ( ( handle, tail) ) ;
3534
3534
}
3535
3535
3536
+ // ::= <qualified-type>
3537
+ // We don't have a separate type for the <qualified-type> production.
3538
+ // Process these all up front, so that any ambiguity that might exist
3539
+ // with later productions is handled correctly.
3540
+
3541
+ // ::= <extended-qualifier>
3542
+ if let Ok ( tail) = consume ( b"U" , input) {
3543
+ let ( name, tail) = SourceName :: parse ( ctx, subs, tail) ?;
3544
+ let ( args, tail) = if let Ok ( ( args, tail) ) = TemplateArgs :: parse ( ctx, subs, tail) {
3545
+ ( Some ( args) , tail)
3546
+ } else {
3547
+ ( None , tail)
3548
+ } ;
3549
+ let ( ty, tail) = TypeHandle :: parse ( ctx, subs, tail) ?;
3550
+ let ty = Type :: VendorExtension ( name, args, ty) ;
3551
+ return insert_and_return_handle ( ty, subs, tail) ;
3552
+ }
3553
+
3554
+ // ::= <CV-qualifiers>
3555
+ if let Ok ( ( qualifiers, tail) ) = CvQualifiers :: parse ( ctx, subs, input) {
3556
+ // CvQualifiers can parse successfully without consuming any input,
3557
+ // but we don't want to recurse unless we know we did consume some
3558
+ // input, lest we go into an infinite loop and blow the stack.
3559
+ if tail. len ( ) < input. len ( ) {
3560
+ // If the following production is a <function-type>, we want to let
3561
+ // it pick up these <CV-qualifiers>.
3562
+ if !FunctionType :: starts_with ( & tail) {
3563
+ let ( ty, tail) = TypeHandle :: parse ( ctx, subs, tail) ?;
3564
+ let ty = Type :: Qualified ( qualifiers, ty) ;
3565
+ return insert_and_return_handle ( ty, subs, tail) ;
3566
+ }
3567
+ }
3568
+ }
3569
+
3536
3570
if let Ok ( ( ty, tail) ) = ClassEnumType :: parse ( ctx, subs, input) {
3537
3571
let ty = Type :: ClassEnum ( ty) ;
3538
3572
return insert_and_return_handle ( ty, subs, tail) ;
@@ -3625,17 +3659,6 @@ impl Parse for TypeHandle {
3625
3659
return insert_and_return_handle ( ty, subs, tail) ;
3626
3660
}
3627
3661
3628
- if let Ok ( ( qualifiers, tail) ) = CvQualifiers :: parse ( ctx, subs, input) {
3629
- // CvQualifiers can parse successfully without consuming any input,
3630
- // but we don't want to recurse unless we know we did consume some
3631
- // input, lest we go into an infinite loop and blow the stack.
3632
- if tail. len ( ) < input. len ( ) {
3633
- let ( ty, tail) = TypeHandle :: parse ( ctx, subs, tail) ?;
3634
- let ty = Type :: Qualified ( qualifiers, ty) ;
3635
- return insert_and_return_handle ( ty, subs, tail) ;
3636
- }
3637
- }
3638
-
3639
3662
if let Ok ( tail) = consume ( b"P" , input) {
3640
3663
let ( ty, tail) = TypeHandle :: parse ( ctx, subs, tail) ?;
3641
3664
let ty = Type :: PointerTo ( ty) ;
@@ -3666,18 +3689,6 @@ impl Parse for TypeHandle {
3666
3689
return insert_and_return_handle ( ty, subs, tail) ;
3667
3690
}
3668
3691
3669
- if let Ok ( tail) = consume ( b"U" , input) {
3670
- let ( name, tail) = SourceName :: parse ( ctx, subs, tail) ?;
3671
- let ( args, tail) = if let Ok ( ( args, tail) ) = TemplateArgs :: parse ( ctx, subs, tail) {
3672
- ( Some ( args) , tail)
3673
- } else {
3674
- ( None , tail)
3675
- } ;
3676
- let ( ty, tail) = TypeHandle :: parse ( ctx, subs, tail) ?;
3677
- let ty = Type :: VendorExtension ( name, args, ty) ;
3678
- return insert_and_return_handle ( ty, subs, tail) ;
3679
- }
3680
-
3681
3692
let tail = consume ( b"Dp" , input) ?;
3682
3693
let ( ty, tail) = TypeHandle :: parse ( ctx, subs, tail) ?;
3683
3694
let ty = Type :: PackExpansion ( ty) ;
@@ -4330,6 +4341,18 @@ where
4330
4341
}
4331
4342
}
4332
4343
4344
+ impl FunctionType {
4345
+ #[ inline]
4346
+ fn starts_with ( input : & IndexStr ) -> bool {
4347
+ input. peek ( ) == Some ( b'F' )
4348
+ || ( input. peek ( ) == Some ( b'D' )
4349
+ && ( matches ! (
4350
+ input. peek_second( ) ,
4351
+ Some ( b'o' ) | Some ( b'O' ) | Some ( b'x' ) | Some ( b'w' )
4352
+ ) ) )
4353
+ }
4354
+ }
4355
+
4333
4356
/// The `<bare-function-type>` production.
4334
4357
///
4335
4358
/// ```text
@@ -8953,6 +8976,7 @@ mod tests {
8953
8976
b"Dp" => Error :: UnexpectedEnd ,
8954
8977
b"D" => Error :: UnexpectedEnd ,
8955
8978
b"P" => Error :: UnexpectedEnd ,
8979
+ b"UlvE_" => Error :: UnexpectedText ,
8956
8980
b"" => Error :: UnexpectedEnd ,
8957
8981
}
8958
8982
}
0 commit comments