@@ -354,6 +354,10 @@ pub fn scanRelocs(self: Atom, elf_file: *Elf, code: ?[]const u8, undefs: anytype
354
354
error .RelocFailure = > has_reloc_errors = true ,
355
355
else = > | e | return e ,
356
356
},
357
+ .loongarch64 , .loongarch32 = > loongarch .scanReloc (self , elf_file , rel , symbol , code , & it ) catch | err | switch (err ) {
358
+ error .RelocFailure = > has_reloc_errors = true ,
359
+ else = > | e | return e ,
360
+ },
357
361
else = > return error .UnsupportedCpuArch ,
358
362
}
359
363
}
@@ -688,6 +692,12 @@ pub fn resolveRelocsAlloc(self: Atom, elf_file: *Elf, code: []u8) RelocError!voi
688
692
= > has_reloc_errors = true ,
689
693
else = > | e | return e ,
690
694
},
695
+ .loongarch64 , .loongarch32 = > loongarch .resolveRelocAlloc (self , elf_file , rel , target , args , & it , code , & stream ) catch | err | switch (err ) {
696
+ error .RelocFailure ,
697
+ error .RelaxFailure ,
698
+ = > has_reloc_errors = true ,
699
+ else = > | e | return e ,
700
+ },
691
701
else = > return error .UnsupportedCpuArch ,
692
702
}
693
703
}
@@ -878,6 +888,10 @@ pub fn resolveRelocsNonAlloc(self: Atom, elf_file: *Elf, code: []u8, undefs: any
878
888
error .RelocFailure = > has_reloc_errors = true ,
879
889
else = > | e | return e ,
880
890
},
891
+ .loongarch64 , .loongarch32 = > loongarch .resolveRelocNonAlloc (self , elf_file , rel , target , args , & it , code , & stream ) catch | err | switch (err ) {
892
+ error .RelocFailure = > has_reloc_errors = true ,
893
+ else = > | e | return e ,
894
+ },
881
895
else = > return error .UnsupportedCpuArch ,
882
896
}
883
897
}
@@ -2084,6 +2098,169 @@ const riscv = struct {
2084
2098
const riscv_util = @import ("../riscv.zig" );
2085
2099
};
2086
2100
2101
+ const loongarch = struct {
2102
+ fn scanReloc (
2103
+ atom : Atom ,
2104
+ elf_file : * Elf ,
2105
+ rel : elf.Elf64_Rela ,
2106
+ symbol : * Symbol ,
2107
+ code : ? []const u8 ,
2108
+ it : * RelocsIterator ,
2109
+ ) ! void {
2110
+ _ = code ;
2111
+ _ = it ;
2112
+
2113
+ const r_type : elf.R_LARCH = @enumFromInt (rel .r_type ());
2114
+ const is_dyn_lib = elf_file .isEffectivelyDynLib ();
2115
+
2116
+ switch (r_type ) {
2117
+ .@"32" = > try atom .scanReloc (symbol , rel , absRelocAction (symbol , elf_file ), elf_file ),
2118
+ .@"64" = > try atom .scanReloc (symbol , rel , dynAbsRelocAction (symbol , elf_file ), elf_file ),
2119
+ .@"32_PCREL" = > try atom .scanReloc (symbol , rel , pcRelocAction (symbol , elf_file ), elf_file ),
2120
+ .@"64_PCREL" = > try atom .scanReloc (symbol , rel , pcRelocAction (symbol , elf_file ), elf_file ),
2121
+
2122
+ .B26 , .PCALA_HI20 , .CALL36 = > if (symbol .flags .import ) {
2123
+ symbol .flags .needs_plt = true ;
2124
+ },
2125
+ .GOT_HI20 , .GOT_PC_HI20 = > symbol .flags .needs_got = true ,
2126
+ .TLS_IE_HI20 , .TLS_IE_PC_HI20 = > symbol .flags .needs_gottp = true ,
2127
+ .TLS_GD_PC_HI20 , .TLS_LD_PC_HI20 , .TLS_GD_HI20 , .TLS_LD_HI20 = > symbol .flags .needs_tlsgd = true ,
2128
+ .TLS_DESC_CALL = > symbol .flags .needs_tlsdesc = true ,
2129
+
2130
+ .TLS_LE_HI20 ,
2131
+ .TLS_LE_LO12 ,
2132
+ .TLS_LE64_LO20 ,
2133
+ .TLS_LE64_HI12 ,
2134
+ .TLS_LE_HI20_R ,
2135
+ .TLS_LE_LO12_R ,
2136
+ = > if (is_dyn_lib ) try atom .reportPicError (symbol , rel , elf_file ),
2137
+
2138
+ .B16 ,
2139
+ .B21 ,
2140
+ .ABS_HI20 ,
2141
+ .ABS_LO12 ,
2142
+ .ABS64_LO20 ,
2143
+ .ABS64_HI12 ,
2144
+ .PCALA_LO12 ,
2145
+ .PCALA64_LO20 ,
2146
+ .PCALA64_HI12 ,
2147
+ .GOT_PC_LO12 ,
2148
+ .GOT64_PC_LO20 ,
2149
+ .GOT64_PC_HI12 ,
2150
+ .GOT_LO12 ,
2151
+ .GOT64_LO20 ,
2152
+ .GOT64_HI12 ,
2153
+ .TLS_IE_PC_LO12 ,
2154
+ .TLS_IE64_PC_LO20 ,
2155
+ .TLS_IE64_PC_HI12 ,
2156
+ .TLS_IE_LO12 ,
2157
+ .TLS_IE64_LO20 ,
2158
+ .TLS_IE64_HI12 ,
2159
+ .ADD6 ,
2160
+ .SUB6 ,
2161
+ .ADD8 ,
2162
+ .SUB8 ,
2163
+ .ADD16 ,
2164
+ .SUB16 ,
2165
+ .ADD32 ,
2166
+ .SUB32 ,
2167
+ .ADD64 ,
2168
+ .SUB64 ,
2169
+ .ADD_ULEB128 ,
2170
+ .SUB_ULEB128 ,
2171
+ .TLS_DESC_PC_HI20 ,
2172
+ .TLS_DESC_PC_LO12 ,
2173
+ .TLS_DESC_LD ,
2174
+ .TLS_LE_ADD_R ,
2175
+ = > {},
2176
+
2177
+ else = > try atom .reportUnhandledRelocError (rel , elf_file ),
2178
+ }
2179
+ }
2180
+
2181
+ fn resolveRelocAlloc (
2182
+ atom : Atom ,
2183
+ elf_file : * Elf ,
2184
+ rel : elf.Elf64_Rela ,
2185
+ target : * const Symbol ,
2186
+ args : ResolveArgs ,
2187
+ it : * RelocsIterator ,
2188
+ code : []u8 ,
2189
+ stream : anytype ,
2190
+ ) ! void {
2191
+ const diags = & elf_file .base .comp .link_diags ;
2192
+ const r_type : elf.R_LARCH = @enumFromInt (rel .r_type ());
2193
+ const r_offset = std .math .cast (usize , rel .r_offset ) orelse return error .Overflow ;
2194
+ const cwriter = stream .writer ();
2195
+
2196
+ const P , const A , const S , const GOT , const G , const TP , const DTP = args ;
2197
+ _ = TP ;
2198
+ _ = DTP ;
2199
+ _ = P ;
2200
+ _ = GOT ;
2201
+ _ = G ;
2202
+ _ = r_offset ;
2203
+ _ = diags ;
2204
+ _ = it ;
2205
+ _ = code ;
2206
+
2207
+ switch (r_type ) {
2208
+ .NONE = > unreachable ,
2209
+
2210
+ .@"32" = > try cwriter .writeInt (u32 , @as (u32 , @truncate (@as (u64 , @intCast (S + A )))), .little ),
2211
+
2212
+ .@"64" = > {
2213
+ try atom .resolveDynAbsReloc (
2214
+ target ,
2215
+ rel ,
2216
+ dynAbsRelocAction (target , elf_file ),
2217
+ elf_file ,
2218
+ cwriter ,
2219
+ );
2220
+ },
2221
+
2222
+ else = > try atom .reportUnhandledRelocError (rel , elf_file ),
2223
+ }
2224
+ }
2225
+
2226
+ fn resolveRelocNonAlloc (
2227
+ atom : Atom ,
2228
+ elf_file : * Elf ,
2229
+ rel : elf.Elf64_Rela ,
2230
+ target : * const Symbol ,
2231
+ args : ResolveArgs ,
2232
+ it : * RelocsIterator ,
2233
+ code : []u8 ,
2234
+ stream : anytype ,
2235
+ ) ! void {
2236
+ _ = it ;
2237
+
2238
+ const r_type : elf.R_LARCH = @enumFromInt (rel .r_type ());
2239
+ const r_offset = std .math .cast (usize , rel .r_offset ) orelse return error .Overflow ;
2240
+ const cwriter = stream .writer ();
2241
+
2242
+ _ , const A , const S , const GOT , _ , _ , const DTP = args ;
2243
+ _ = GOT ;
2244
+ _ = DTP ;
2245
+ _ = r_offset ;
2246
+ _ = code ;
2247
+
2248
+ switch (r_type ) {
2249
+ .NONE = > unreachable ,
2250
+
2251
+ .@"32" = > try cwriter .writeInt (i32 , @as (i32 , @intCast (S + A )), .little ),
2252
+ .@"64" = > if (atom .debugTombstoneValue (target .* , elf_file )) | value |
2253
+ try cwriter .writeInt (u64 , value , .little )
2254
+ else
2255
+ try cwriter .writeInt (i64 , S + A , .little ),
2256
+
2257
+ else = > try atom .reportUnhandledRelocError (rel , elf_file ),
2258
+ }
2259
+ }
2260
+
2261
+ const la_util = @import ("../loongarch.zig" );
2262
+ };
2263
+
2087
2264
const ResolveArgs = struct { i64 , i64 , i64 , i64 , i64 , i64 , i64 };
2088
2265
2089
2266
const RelocError = error {
0 commit comments