@@ -2867,6 +2867,79 @@ enum AsmLabelKind {
28672867 Binary ,
28682868}
28692869
2870+ /// Checks if a potential label is actually a Hexagon register span notation.
2871+ ///
2872+ /// Hexagon assembly uses register span notation like `r1:0`, `V5:4.w`, `p1:0` etc.
2873+ /// These follow the pattern: `[letter][digit(s)]:[digit(s)][optional_suffix]`
2874+ ///
2875+ /// Returns `true` if the string matches a valid Hexagon register span pattern.
2876+ fn is_hexagon_register_span ( possible_label : & str ) -> bool {
2877+ if possible_label. len ( ) < 3 {
2878+ return false ;
2879+ }
2880+
2881+ let mut chars = possible_label. chars ( ) ;
2882+ let start = chars. next ( ) . unwrap ( ) ;
2883+
2884+ // Must start with a letter (r, V, p, etc.)
2885+ if !start. is_ascii_alphabetic ( ) {
2886+ return false ;
2887+ }
2888+
2889+ let rest = & possible_label[ 1 ..] ;
2890+ let Some ( colon_idx) = rest. find ( ':' ) else {
2891+ return false ;
2892+ } ;
2893+
2894+ let ( before_colon, after_colon_with_colon) = rest. split_at ( colon_idx) ;
2895+ let after_colon = & after_colon_with_colon[ 1 ..] ; // Skip the ':'
2896+
2897+ // Check if before colon is all digits and non-empty
2898+ if before_colon. is_empty ( ) || !before_colon. chars ( ) . all ( |c| c. is_ascii_digit ( ) ) {
2899+ return false ;
2900+ }
2901+
2902+ // Check if after colon starts with digits (may have suffix like .w, .h)
2903+ let digits_after = after_colon. chars ( )
2904+ . take_while ( |c| c. is_ascii_digit ( ) )
2905+ . collect :: < String > ( ) ;
2906+
2907+ !digits_after. is_empty ( )
2908+ }
2909+
2910+ #[ cfg( test) ]
2911+ mod tests {
2912+ use super :: is_hexagon_register_span;
2913+
2914+ #[ test]
2915+ fn test_hexagon_register_span_patterns ( ) {
2916+ // Valid Hexagon register span patterns
2917+ assert ! ( is_hexagon_register_span( "r1:0" ) ) ;
2918+ assert ! ( is_hexagon_register_span( "r15:14" ) ) ;
2919+ assert ! ( is_hexagon_register_span( "V5:4" ) ) ;
2920+ assert ! ( is_hexagon_register_span( "V3:2" ) ) ;
2921+ assert ! ( is_hexagon_register_span( "V5:4.w" ) ) ;
2922+ assert ! ( is_hexagon_register_span( "V3:2.h" ) ) ;
2923+ assert ! ( is_hexagon_register_span( "p1:0" ) ) ;
2924+ assert ! ( is_hexagon_register_span( "p3:2" ) ) ;
2925+ assert ! ( is_hexagon_register_span( "r99:98" ) ) ;
2926+ assert ! ( is_hexagon_register_span( "V123:122.whatever" ) ) ;
2927+
2928+ // Invalid patterns - these should be treated as potential labels
2929+ assert ! ( !is_hexagon_register_span( "label1" ) ) ;
2930+ assert ! ( !is_hexagon_register_span( "foo:" ) ) ;
2931+ assert ! ( !is_hexagon_register_span( ":0" ) ) ;
2932+ assert ! ( !is_hexagon_register_span( "r:0" ) ) ; // missing digits before colon
2933+ assert ! ( !is_hexagon_register_span( "r1:" ) ) ; // missing digits after colon
2934+ assert ! ( !is_hexagon_register_span( "r1:a" ) ) ; // non-digit after colon
2935+ assert ! ( !is_hexagon_register_span( "1:0" ) ) ; // starts with digit, not letter
2936+ assert ! ( !is_hexagon_register_span( "r1" ) ) ; // no colon
2937+ assert ! ( !is_hexagon_register_span( "r" ) ) ; // too short
2938+ assert ! ( !is_hexagon_register_span( "" ) ) ; // empty
2939+ assert ! ( !is_hexagon_register_span( "ra:0" ) ) ; // letter in first digit group
2940+ }
2941+ }
2942+
28702943impl < ' tcx > LateLintPass < ' tcx > for AsmLabels {
28712944 fn check_expr ( & mut self , cx : & LateContext < ' tcx > , expr : & ' tcx hir:: Expr < ' tcx > ) {
28722945 if let hir:: Expr {
@@ -2940,6 +3013,13 @@ impl<'tcx> LateLintPass<'tcx> for AsmLabels {
29403013 break ' label_loop;
29413014 }
29423015
3016+ // Check for Hexagon register span notation (e.g., "r1:0", "V5:4", "V3:2.w")
3017+ // This is valid Hexagon assembly syntax, not a label
3018+ if matches ! ( cx. tcx. sess. asm_arch, Some ( InlineAsmArch :: Hexagon ) )
3019+ && is_hexagon_register_span ( possible_label) {
3020+ break ' label_loop;
3021+ }
3022+
29433023 for c in chars {
29443024 // Inside a template format arg, any character is permitted for the
29453025 // puproses of label detection because we assume that it can be
0 commit comments