@@ -2471,12 +2471,23 @@ pub const SrcLoc = struct {
2471
2471
}
2472
2472
} else unreachable ;
2473
2473
},
2474
- .node_offset_switch_prong_capture = > | node_off | {
2474
+ .node_offset_switch_prong_capture ,
2475
+ .node_offset_switch_prong_tag_capture ,
2476
+ = > | node_off | {
2475
2477
const tree = try src_loc .file_scope .getTree (gpa );
2476
2478
const case_node = src_loc .declRelativeToNodeIndex (node_off );
2477
2479
const case = tree .fullSwitchCase (case_node ).? ;
2478
- const start_tok = case .payload_token .? ;
2479
2480
const token_tags = tree .tokens .items (.tag );
2481
+ const start_tok = switch (src_loc .lazy ) {
2482
+ .node_offset_switch_prong_capture = > case .payload_token .? ,
2483
+ .node_offset_switch_prong_tag_capture = > blk : {
2484
+ var tok = case .payload_token .? ;
2485
+ if (token_tags [tok ] == .asterisk ) tok += 1 ;
2486
+ tok += 2 ; // skip over comma
2487
+ break :blk tok ;
2488
+ },
2489
+ else = > unreachable ,
2490
+ };
2480
2491
const end_tok = switch (token_tags [start_tok ]) {
2481
2492
.asterisk = > start_tok + 1 ,
2482
2493
else = > start_tok ,
@@ -2957,6 +2968,9 @@ pub const LazySrcLoc = union(enum) {
2957
2968
/// The source location points to the capture of a switch_prong.
2958
2969
/// The Decl is determined contextually.
2959
2970
node_offset_switch_prong_capture : i32 ,
2971
+ /// The source location points to the tag capture of a switch_prong.
2972
+ /// The Decl is determined contextually.
2973
+ node_offset_switch_prong_tag_capture : i32 ,
2960
2974
/// The source location points to the align expr of a function type
2961
2975
/// expression, found by taking this AST node index offset from the containing
2962
2976
/// Decl AST node, which points to a function type AST node. Next, navigate to
@@ -3130,6 +3144,7 @@ pub const LazySrcLoc = union(enum) {
3130
3144
.node_offset_switch_special_prong ,
3131
3145
.node_offset_switch_range ,
3132
3146
.node_offset_switch_prong_capture ,
3147
+ .node_offset_switch_prong_tag_capture ,
3133
3148
.node_offset_fn_type_align ,
3134
3149
.node_offset_fn_type_addrspace ,
3135
3150
.node_offset_fn_type_section ,
@@ -5867,11 +5882,26 @@ fn lockAndClearFileCompileError(mod: *Module, file: *File) void {
5867
5882
}
5868
5883
5869
5884
pub const SwitchProngSrc = union (enum ) {
5885
+ /// The item for a scalar prong.
5870
5886
scalar : u32 ,
5887
+ /// A given single item for a multi prong.
5871
5888
multi : Multi ,
5889
+ /// A given range item for a multi prong.
5872
5890
range : Multi ,
5873
- multi_capture : u32 ,
5891
+ /// The item for the special prong.
5874
5892
special ,
5893
+ /// The main capture for a scalar prong.
5894
+ scalar_capture : u32 ,
5895
+ /// The main capture for a multi prong.
5896
+ multi_capture : u32 ,
5897
+ /// The main capture for the special prong.
5898
+ special_capture ,
5899
+ /// The tag capture for a scalar prong.
5900
+ scalar_tag_capture : u32 ,
5901
+ /// The tag capture for a multi prong.
5902
+ multi_tag_capture : u32 ,
5903
+ /// The tag capture for the special prong.
5904
+ special_tag_capture ,
5875
5905
5876
5906
pub const Multi = struct {
5877
5907
prong : u32 ,
@@ -5887,6 +5917,7 @@ pub const SwitchProngSrc = union(enum) {
5887
5917
mod : * Module ,
5888
5918
decl : * Decl ,
5889
5919
switch_node_offset : i32 ,
5920
+ /// Ignored if `prong_src` is not `.range`
5890
5921
range_expand : RangeExpand ,
5891
5922
) LazySrcLoc {
5892
5923
@setCold (true );
@@ -5907,7 +5938,7 @@ pub const SwitchProngSrc = union(enum) {
5907
5938
5908
5939
var multi_i : u32 = 0 ;
5909
5940
var scalar_i : u32 = 0 ;
5910
- for (case_nodes ) | case_node | {
5941
+ const case_node = for (case_nodes ) | case_node | {
5911
5942
const case = tree .fullSwitchCase (case_node ).? ;
5912
5943
5913
5944
const is_special = special : {
@@ -5919,60 +5950,85 @@ pub const SwitchProngSrc = union(enum) {
5919
5950
};
5920
5951
5921
5952
if (is_special ) {
5922
- if (prong_src != .special ) continue ;
5923
- return LazySrcLoc . nodeOffset (
5924
- decl . nodeIndexToRelative ( case . ast . values [ 0 ]) ,
5925
- );
5953
+ switch (prong_src ) {
5954
+ .special , .special_capture , .special_tag_capture = > break case_node ,
5955
+ else = > continue ,
5956
+ }
5926
5957
}
5927
5958
5928
5959
const is_multi = case .ast .values .len != 1 or
5929
5960
node_tags [case .ast .values [0 ]] == .switch_range ;
5930
5961
5931
5962
switch (prong_src ) {
5932
- .scalar = > | i | if (! is_multi and i == scalar_i ) return LazySrcLoc .nodeOffset (
5933
- decl .nodeIndexToRelative (case .ast .values [0 ]),
5934
- ),
5935
- .multi_capture = > | i | if (is_multi and i == multi_i ) {
5936
- return LazySrcLoc { .node_offset_switch_prong_capture = decl .nodeIndexToRelative (case_node ) };
5937
- },
5938
- .multi = > | s | if (is_multi and s .prong == multi_i ) {
5939
- var item_i : u32 = 0 ;
5940
- for (case .ast .values ) | item_node | {
5941
- if (node_tags [item_node ] == .switch_range ) continue ;
5942
-
5943
- if (item_i == s .item ) return LazySrcLoc .nodeOffset (
5944
- decl .nodeIndexToRelative (item_node ),
5945
- );
5946
- item_i += 1 ;
5947
- } else unreachable ;
5948
- },
5949
- .range = > | s | if (is_multi and s .prong == multi_i ) {
5950
- var range_i : u32 = 0 ;
5951
- for (case .ast .values ) | range | {
5952
- if (node_tags [range ] != .switch_range ) continue ;
5953
-
5954
- if (range_i == s .item ) switch (range_expand ) {
5955
- .none = > return LazySrcLoc .nodeOffset (
5956
- decl .nodeIndexToRelative (range ),
5957
- ),
5958
- .first = > return LazySrcLoc .nodeOffset (
5959
- decl .nodeIndexToRelative (node_datas [range ].lhs ),
5960
- ),
5961
- .last = > return LazySrcLoc .nodeOffset (
5962
- decl .nodeIndexToRelative (node_datas [range ].rhs ),
5963
- ),
5964
- };
5965
- range_i += 1 ;
5966
- } else unreachable ;
5967
- },
5968
- .special = > {},
5963
+ .scalar ,
5964
+ .scalar_capture ,
5965
+ .scalar_tag_capture ,
5966
+ = > | i | if (! is_multi and i == scalar_i ) break case_node ,
5967
+
5968
+ .multi_capture ,
5969
+ .multi_tag_capture ,
5970
+ = > | i | if (is_multi and i == multi_i ) break case_node ,
5971
+
5972
+ .multi ,
5973
+ .range ,
5974
+ = > | m | if (is_multi and m .prong == multi_i ) break case_node ,
5975
+
5976
+ .special ,
5977
+ .special_capture ,
5978
+ .special_tag_capture ,
5979
+ = > {},
5969
5980
}
5981
+
5970
5982
if (is_multi ) {
5971
5983
multi_i += 1 ;
5972
5984
} else {
5973
5985
scalar_i += 1 ;
5974
5986
}
5975
5987
} else unreachable ;
5988
+
5989
+ const case = tree .fullSwitchCase (case_node ).? ;
5990
+
5991
+ switch (prong_src ) {
5992
+ .scalar , .special = > return LazySrcLoc .nodeOffset (
5993
+ decl .nodeIndexToRelative (case .ast .values [0 ]),
5994
+ ),
5995
+ .multi = > | m | {
5996
+ var item_i : u32 = 0 ;
5997
+ for (case .ast .values ) | item_node | {
5998
+ if (node_tags [item_node ] == .switch_range ) continue ;
5999
+ if (item_i == m .item ) return LazySrcLoc .nodeOffset (
6000
+ decl .nodeIndexToRelative (item_node ),
6001
+ );
6002
+ item_i += 1 ;
6003
+ }
6004
+ unreachable ;
6005
+ },
6006
+ .range = > | m | {
6007
+ var range_i : u32 = 0 ;
6008
+ for (case .ast .values ) | range | {
6009
+ if (node_tags [range ] != .switch_range ) continue ;
6010
+ if (range_i == m .item ) switch (range_expand ) {
6011
+ .none = > return LazySrcLoc .nodeOffset (
6012
+ decl .nodeIndexToRelative (range ),
6013
+ ),
6014
+ .first = > return LazySrcLoc .nodeOffset (
6015
+ decl .nodeIndexToRelative (node_datas [range ].lhs ),
6016
+ ),
6017
+ .last = > return LazySrcLoc .nodeOffset (
6018
+ decl .nodeIndexToRelative (node_datas [range ].rhs ),
6019
+ ),
6020
+ };
6021
+ range_i += 1 ;
6022
+ }
6023
+ unreachable ;
6024
+ },
6025
+ .scalar_capture , .multi_capture , .special_capture = > {
6026
+ return .{ .node_offset_switch_prong_capture = decl .nodeIndexToRelative (case_node ) };
6027
+ },
6028
+ .scalar_tag_capture , .multi_tag_capture , .special_tag_capture = > {
6029
+ return .{ .node_offset_switch_prong_tag_capture = decl .nodeIndexToRelative (case_node ) };
6030
+ },
6031
+ }
5976
6032
}
5977
6033
};
5978
6034
0 commit comments