| author | |
| committer | |
| log | 11bb8ab9b3cf832a5e391ac8c73cbc33221db19d |
| tree | b7b1dbe0280a1843a515678f63955de1bc4c996e |
| parent | b3747dd707eeaf06e0bacbde259bf71ef525a961 |
| parent | 84a100b3e06afec33d4077052a50f8126396021f |
Reviewed-on: https://codeberg.org/ziglang/zig/pulls/354639 files changed, 260 insertions(+), 3 deletions(-)
lib/std/Thread.zig+10| ... | @@ -1411,6 +1411,16 @@ const LinuxThreadImpl = struct { | ... | @@ -1411,6 +1411,16 @@ const LinuxThreadImpl = struct { |
| 1411 | : [ptr] "{r4}" (@intFromPtr(self.mapped.ptr)), | 1411 | : [ptr] "{r4}" (@intFromPtr(self.mapped.ptr)), |
| 1412 | [len] "{r5}" (self.mapped.len), | 1412 | [len] "{r5}" (self.mapped.len), |
| 1413 | : .{ .memory = true }), | 1413 | : .{ .memory = true }), |
| 1414 | .xtensa, .xtensaeb => asm volatile ( | ||
| 1415 | \\ movi a2, 81 // SYS_munmap | ||
| 1416 | \\ syscall | ||
| 1417 | \\ movi a6, 0 | ||
| 1418 | \\ movi a2, 118 // SYS_exit | ||
| 1419 | \\ syscall | ||
| 1420 | : | ||
| 1421 | : [ptr] "{a6}" (@intFromPtr(self.mapped.ptr)), | ||
| 1422 | [len] "{a3}" (self.mapped.len), | ||
| 1423 | : .{ .memory = true }), | ||
| 1414 | else => |cpu_arch| @compileError("Unsupported linux arch: " ++ @tagName(cpu_arch)), | 1424 | else => |cpu_arch| @compileError("Unsupported linux arch: " ++ @tagName(cpu_arch)), |
| 1415 | } | 1425 | } |
| 1416 | unreachable; | 1426 | unreachable; |
lib/std/debug.zig+2| ... | @@ -994,6 +994,8 @@ const StackIterator = union(enum) { | ... | @@ -994,6 +994,8 @@ const StackIterator = union(enum) { |
| 994 | .sh, | 994 | .sh, |
| 995 | .sheb, | 995 | .sheb, |
| 996 | .xcore, | 996 | .xcore, |
| 997 | .xtensa, | ||
| 998 | .xtensaeb, | ||
| 997 | => .useless, | 999 | => .useless, |
| 998 | .hexagon, | 1000 | .hexagon, |
| 999 | // The PowerPC ABIs don't actually strictly require a backchain pointer; they allow omitting | 1001 | // The PowerPC ABIs don't actually strictly require a backchain pointer; they allow omitting |
lib/std/elf.zig+3| ... | @@ -224,6 +224,9 @@ pub const DT_PPC64_NUM = 4; | ... | @@ -224,6 +224,9 @@ pub const DT_PPC64_NUM = 4; |
| 224 | pub const DT_IA_64_PLT_RESERVE = (DT_LOPROC + 0); | 224 | pub const DT_IA_64_PLT_RESERVE = (DT_LOPROC + 0); |
| 225 | pub const DT_IA_64_NUM = 1; | 225 | pub const DT_IA_64_NUM = 1; |
| 226 | 226 | ||
| 227 | pub const DT_XTENSA_GOT_LOC_OFF = 0x70000000; | ||
| 228 | pub const DT_XTENSA_GOT_LOC_SZ = 0x70000001; | ||
| 229 | |||
| 227 | pub const DT_NIOS2_GP = 0x70000002; | 230 | pub const DT_NIOS2_GP = 0x70000002; |
| 228 | 231 | ||
| 229 | pub const DF_ORIGIN = 0x00000001; | 232 | pub const DF_ORIGIN = 0x00000001; |
lib/std/os.zig-3| ... | @@ -28,9 +28,6 @@ pub fn targetRequiresLibC(target: *const std.Target) bool { | ... | @@ -28,9 +28,6 @@ pub fn targetRequiresLibC(target: *const std.Target) bool { |
| 28 | .sheb, | 28 | .sheb, |
| 29 | // https://codeberg.org/ziglang/zig/issues/30945 | 29 | // https://codeberg.org/ziglang/zig/issues/30945 |
| 30 | .sparc, | 30 | .sparc, |
| 31 | // https://codeberg.org/ziglang/zig/issues/30947 | ||
| 32 | .xtensa, | ||
| 33 | .xtensaeb, | ||
| 34 | => true, | 31 | => true, |
| 35 | else => false, | 32 | else => false, |
| 36 | }, | 33 | }, |
lib/std/os/linux.zig+32| ... | @@ -56,6 +56,7 @@ const arch_bits = switch (native_arch) { | ... | @@ -56,6 +56,7 @@ const arch_bits = switch (native_arch) { |
| 56 | .gnux32, .muslx32 => @import("linux/x32.zig"), | 56 | .gnux32, .muslx32 => @import("linux/x32.zig"), |
| 57 | else => @import("linux/x86_64.zig"), | 57 | else => @import("linux/x86_64.zig"), |
| 58 | }, | 58 | }, |
| 59 | .xtensa, .xtensaeb => @import("linux/xtensa.zig"), | ||
| 59 | else => struct {}, | 60 | else => struct {}, |
| 60 | }; | 61 | }; |
| 61 | 62 | ||
| ... | @@ -338,6 +339,29 @@ pub const MAP = switch (native_arch) { | ... | @@ -338,6 +339,29 @@ pub const MAP = switch (native_arch) { |
| 338 | _20: u1 = 0, | 339 | _20: u1 = 0, |
| 339 | _: u5 = 0, | 340 | _: u5 = 0, |
| 340 | }, | 341 | }, |
| 342 | .xtensa, .xtensaeb => packed struct(u32) { | ||
| 343 | TYPE: MAP_TYPE, | ||
| 344 | FIXED: bool = false, | ||
| 345 | _RENAME: bool = false, | ||
| 346 | _AUTOGROW: bool = false, | ||
| 347 | _LOCAL: bool = false, | ||
| 348 | _AUTORSRV: bool = false, | ||
| 349 | _1: u1 = 0, | ||
| 350 | NORESERVE: bool = false, | ||
| 351 | ANONYMOUS: bool = false, | ||
| 352 | GROWSDOWN: bool = false, | ||
| 353 | DENYWRITE: bool = false, | ||
| 354 | EXECUTABLE: bool = false, | ||
| 355 | LOCKED: bool = false, | ||
| 356 | POPULATE: bool = false, | ||
| 357 | NONBLOCK: bool = false, | ||
| 358 | STACK: bool = false, | ||
| 359 | HUGETLB: bool = false, | ||
| 360 | FIXED_NOREPLACE: bool = false, | ||
| 361 | _2: u5 = 0, | ||
| 362 | UNINITIALIZED: bool = false, | ||
| 363 | _3: u5 = 0, | ||
| 364 | }, | ||
| 341 | else => @compileError("missing std.os.linux.MAP constants for this architecture"), | 365 | else => @compileError("missing std.os.linux.MAP constants for this architecture"), |
| 342 | }; | 366 | }; |
| 343 | 367 | ||
| ... | @@ -497,6 +521,8 @@ pub const O = switch (native_arch) { | ... | @@ -497,6 +521,8 @@ pub const O = switch (native_arch) { |
| 497 | .hexagon, | 521 | .hexagon, |
| 498 | .or1k, | 522 | .or1k, |
| 499 | .s390x, | 523 | .s390x, |
| 524 | .xtensa, | ||
| 525 | .xtensaeb, | ||
| 500 | => packed struct(u32) { | 526 | => packed struct(u32) { |
| 501 | ACCMODE: ACCMODE = .RDONLY, | 527 | ACCMODE: ACCMODE = .RDONLY, |
| 502 | _2: u4 = 0, | 528 | _2: u4 = 0, |
| ... | @@ -6617,6 +6643,12 @@ pub const k_sigaction = switch (native_arch) { | ... | @@ -6617,6 +6643,12 @@ pub const k_sigaction = switch (native_arch) { |
| 6617 | mask: sigset_t, | 6643 | mask: sigset_t, |
| 6618 | flags: c_int, | 6644 | flags: c_int, |
| 6619 | }, | 6645 | }, |
| 6646 | .xtensa, .xtensaeb => extern struct { | ||
| 6647 | handler: k_sigaction_funcs.handler, | ||
| 6648 | mask: sigset_t, | ||
| 6649 | flags: c_ulong, | ||
| 6650 | restorer: k_sigaction_funcs.restorer, | ||
| 6651 | }, | ||
| 6620 | else => extern struct { | 6652 | else => extern struct { |
| 6621 | handler: k_sigaction_funcs.handler, | 6653 | handler: k_sigaction_funcs.handler, |
| 6622 | flags: c_ulong, | 6654 | flags: c_ulong, |
lib/std/os/linux/tls.zig+11| ... | @@ -78,6 +78,8 @@ const current_variant: Variant = switch (native_arch) { | ... | @@ -78,6 +78,8 @@ const current_variant: Variant = switch (native_arch) { |
| 78 | .sheb, | 78 | .sheb, |
| 79 | .thumb, | 79 | .thumb, |
| 80 | .thumbeb, | 80 | .thumbeb, |
| 81 | .xtensa, | ||
| 82 | .xtensaeb, | ||
| 81 | => .I_original, | 83 | => .I_original, |
| 82 | .loongarch32, | 84 | .loongarch32, |
| 83 | .loongarch64, | 85 | .loongarch64, |
| ... | @@ -152,6 +154,8 @@ const AbiTcb = switch (current_variant) { | ... | @@ -152,6 +154,8 @@ const AbiTcb = switch (current_variant) { |
| 152 | .sheb, | 154 | .sheb, |
| 153 | .thumb, | 155 | .thumb, |
| 154 | .thumbeb, | 156 | .thumbeb, |
| 157 | .xtensa, | ||
| 158 | .xtensaeb, | ||
| 155 | => extern struct { | 159 | => extern struct { |
| 156 | /// This is offset by `current_dtv_offset`. | 160 | /// This is offset by `current_dtv_offset`. |
| 157 | dtv: usize, | 161 | dtv: usize, |
| ... | @@ -364,6 +368,13 @@ pub fn setThreadPointer(addr: usize) void { | ... | @@ -364,6 +368,13 @@ pub fn setThreadPointer(addr: usize) void { |
| 364 | : [addr] "r" (addr), | 368 | : [addr] "r" (addr), |
| 365 | ); | 369 | ); |
| 366 | }, | 370 | }, |
| 371 | .xtensa, .xtensaeb => { | ||
| 372 | asm volatile ( | ||
| 373 | \\ wur %[addr], threadptr | ||
| 374 | : | ||
| 375 | : [addr] "a" (addr), | ||
| 376 | ); | ||
| 377 | }, | ||
| 367 | else => @compileError("Unsupported architecture"), | 378 | else => @compileError("Unsupported architecture"), |
| 368 | } | 379 | } |
| 369 | } | 380 | } |
lib/std/os/linux/xtensa.zig created+171| ... | @@ -0,0 +1,171 @@ | ||
| 1 | const builtin = @import("builtin"); | ||
| 2 | const std = @import("../../std.zig"); | ||
| 3 | const SYS = std.os.linux.SYS; | ||
| 4 | |||
| 5 | pub const syscall_arg_t = u32; | ||
| 6 | |||
| 7 | pub fn syscall0( | ||
| 8 | number: SYS, | ||
| 9 | ) u32 { | ||
| 10 | return asm volatile ("syscall" | ||
| 11 | : [ret] "={a2}" (-> u32), | ||
| 12 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 13 | : .{ .memory = true }); | ||
| 14 | } | ||
| 15 | |||
| 16 | pub fn syscall1( | ||
| 17 | number: SYS, | ||
| 18 | arg1: syscall_arg_t, | ||
| 19 | ) u32 { | ||
| 20 | return asm volatile ("syscall" | ||
| 21 | : [ret] "={a2}" (-> u32), | ||
| 22 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 23 | [arg1] "{a6}" (arg1), | ||
| 24 | : .{ .memory = true }); | ||
| 25 | } | ||
| 26 | |||
| 27 | pub fn syscall2( | ||
| 28 | number: SYS, | ||
| 29 | arg1: syscall_arg_t, | ||
| 30 | arg2: syscall_arg_t, | ||
| 31 | ) u32 { | ||
| 32 | return asm volatile ("syscall" | ||
| 33 | : [ret] "={a2}" (-> u32), | ||
| 34 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 35 | [arg1] "{a6}" (arg1), | ||
| 36 | [arg2] "{a3}" (arg2), | ||
| 37 | : .{ .memory = true }); | ||
| 38 | } | ||
| 39 | |||
| 40 | pub fn syscall3( | ||
| 41 | number: SYS, | ||
| 42 | arg1: syscall_arg_t, | ||
| 43 | arg2: syscall_arg_t, | ||
| 44 | arg3: syscall_arg_t, | ||
| 45 | ) u32 { | ||
| 46 | return asm volatile ("syscall" | ||
| 47 | : [ret] "={a2}" (-> u32), | ||
| 48 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 49 | [arg1] "{a6}" (arg1), | ||
| 50 | [arg2] "{a3}" (arg2), | ||
| 51 | [arg3] "{a4}" (arg3), | ||
| 52 | : .{ .memory = true }); | ||
| 53 | } | ||
| 54 | |||
| 55 | pub fn syscall4( | ||
| 56 | number: SYS, | ||
| 57 | arg1: syscall_arg_t, | ||
| 58 | arg2: syscall_arg_t, | ||
| 59 | arg3: syscall_arg_t, | ||
| 60 | arg4: syscall_arg_t, | ||
| 61 | ) u32 { | ||
| 62 | return asm volatile ("syscall" | ||
| 63 | : [ret] "={a2}" (-> u32), | ||
| 64 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 65 | [arg1] "{a6}" (arg1), | ||
| 66 | [arg2] "{a3}" (arg2), | ||
| 67 | [arg3] "{a4}" (arg3), | ||
| 68 | [arg4] "{a5}" (arg4), | ||
| 69 | : .{ .memory = true }); | ||
| 70 | } | ||
| 71 | |||
| 72 | pub fn syscall5( | ||
| 73 | number: SYS, | ||
| 74 | arg1: syscall_arg_t, | ||
| 75 | arg2: syscall_arg_t, | ||
| 76 | arg3: syscall_arg_t, | ||
| 77 | arg4: syscall_arg_t, | ||
| 78 | arg5: syscall_arg_t, | ||
| 79 | ) u32 { | ||
| 80 | return asm volatile ("syscall" | ||
| 81 | : [ret] "={a2}" (-> u32), | ||
| 82 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 83 | [arg1] "{a6}" (arg1), | ||
| 84 | [arg2] "{a3}" (arg2), | ||
| 85 | [arg3] "{a4}" (arg3), | ||
| 86 | [arg4] "{a5}" (arg4), | ||
| 87 | [arg5] "{a8}" (arg5), | ||
| 88 | : .{ .memory = true }); | ||
| 89 | } | ||
| 90 | |||
| 91 | pub fn syscall6( | ||
| 92 | number: SYS, | ||
| 93 | arg1: syscall_arg_t, | ||
| 94 | arg2: syscall_arg_t, | ||
| 95 | arg3: syscall_arg_t, | ||
| 96 | arg4: syscall_arg_t, | ||
| 97 | arg5: syscall_arg_t, | ||
| 98 | arg6: syscall_arg_t, | ||
| 99 | ) u32 { | ||
| 100 | return asm volatile ("syscall" | ||
| 101 | : [ret] "={a2}" (-> u32), | ||
| 102 | : [number] "{a2}" (@intFromEnum(number)), | ||
| 103 | [arg1] "{a6}" (arg1), | ||
| 104 | [arg2] "{a3}" (arg2), | ||
| 105 | [arg3] "{a4}" (arg3), | ||
| 106 | [arg4] "{a5}" (arg4), | ||
| 107 | [arg5] "{a8}" (arg5), | ||
| 108 | [arg6] "{a9}" (arg6), | ||
| 109 | : .{ .memory = true }); | ||
| 110 | } | ||
| 111 | |||
| 112 | pub fn clone() callconv(.naked) u32 { | ||
| 113 | // __clone(func, stack, flags, arg, ptid, tls, ctid) | ||
| 114 | // a2, a3, a4, a5, a6, a7, +16 | ||
| 115 | // | ||
| 116 | // syscall(SYS_clone, flags, stack, ptid, tls, ctid) | ||
| 117 | // a2 a6, a3, a4, a5, a8 | ||
| 118 | asm volatile ( | ||
| 119 | \\ entry sp, 16 | ||
| 120 | \\ | ||
| 121 | \\ movi a8, -16 | ||
| 122 | \\ and a3, a3, a8 | ||
| 123 | \\ | ||
| 124 | \\ mov a9, a2 | ||
| 125 | \\ mov a10, a5 | ||
| 126 | \\ | ||
| 127 | \\ mov a5, a7 | ||
| 128 | \\ mov a8, a6 | ||
| 129 | \\ mov a6, a4 | ||
| 130 | \\ mov a4, a8 | ||
| 131 | \\ l32i a8, sp, 16 | ||
| 132 | \\ movi a2, 116 // SYS_clone | ||
| 133 | \\ syscall | ||
| 134 | \\ | ||
| 135 | \\ beqz a2, 1f | ||
| 136 | \\ // parent | ||
| 137 | \\ retw | ||
| 138 | \\ | ||
| 139 | \\ // child | ||
| 140 | \\1: | ||
| 141 | \\ movi a7, 0 | ||
| 142 | \\ movi a0, 0 | ||
| 143 | \\ | ||
| 144 | \\ mov a2, a10 | ||
| 145 | \\ callx0 a9 | ||
| 146 | \\ movi a2, 118 // SYS_exit | ||
| 147 | \\ syscall | ||
| 148 | ); | ||
| 149 | } | ||
| 150 | |||
| 151 | pub const restore = restore_rt; | ||
| 152 | |||
| 153 | pub fn restore_rt() callconv(.naked) noreturn { | ||
| 154 | switch (builtin.zig_backend) { | ||
| 155 | .stage2_c => asm volatile ( | ||
| 156 | \\ movi a2, %[number] | ||
| 157 | \\ syscall | ||
| 158 | : | ||
| 159 | : [number] "I" (@intFromEnum(SYS.rt_sigreturn)), | ||
| 160 | ), | ||
| 161 | else => asm volatile ( | ||
| 162 | \\ syscall | ||
| 163 | : | ||
| 164 | : [number] "{a2}" (@intFromEnum(SYS.rt_sigreturn)), | ||
| 165 | ), | ||
| 166 | } | ||
| 167 | } | ||
| 168 | |||
| 169 | pub const VDSO = void; | ||
| 170 | |||
| 171 | pub const time_t = i32; | ||
lib/std/pie.zig+21| ... | @@ -22,6 +22,7 @@ const R_RISCV_RELATIVE = 3; | ... | @@ -22,6 +22,7 @@ const R_RISCV_RELATIVE = 3; |
| 22 | const R_390_RELATIVE = 12; | 22 | const R_390_RELATIVE = 12; |
| 23 | const R_SH_RELATIVE = 165; | 23 | const R_SH_RELATIVE = 165; |
| 24 | const R_SPARC_RELATIVE = 22; | 24 | const R_SPARC_RELATIVE = 22; |
| 25 | const R_XTENSA_RELATIVE = 5; | ||
| 25 | 26 | ||
| 26 | const R_RELATIVE = switch (builtin.cpu.arch) { | 27 | const R_RELATIVE = switch (builtin.cpu.arch) { |
| 27 | .x86 => R_386_RELATIVE, | 28 | .x86 => R_386_RELATIVE, |
| ... | @@ -43,6 +44,7 @@ const R_RELATIVE = switch (builtin.cpu.arch) { | ... | @@ -43,6 +44,7 @@ const R_RELATIVE = switch (builtin.cpu.arch) { |
| 43 | .s390x => R_390_RELATIVE, | 44 | .s390x => R_390_RELATIVE, |
| 44 | .sh, .sheb => R_SH_RELATIVE, | 45 | .sh, .sheb => R_SH_RELATIVE, |
| 45 | .sparc, .sparc64 => R_SPARC_RELATIVE, | 46 | .sparc, .sparc64 => R_SPARC_RELATIVE, |
| 47 | .xtensa, .xtensaeb => R_XTENSA_RELATIVE, | ||
| 46 | else => @compileError("Missing R_RELATIVE definition for this target"), | 48 | else => @compileError("Missing R_RELATIVE definition for this target"), |
| 47 | }; | 49 | }; |
| 48 | 50 | ||
| ... | @@ -261,6 +263,25 @@ inline fn getDynamicSymbol() [*]const elf.Dyn { | ... | @@ -261,6 +263,25 @@ inline fn getDynamicSymbol() [*]const elf.Dyn { |
| 261 | : [ret] "=r" (-> [*]const elf.Dyn), | 263 | : [ret] "=r" (-> [*]const elf.Dyn), |
| 262 | : | 264 | : |
| 263 | : .{ .l7 = true }), | 265 | : .{ .l7 = true }), |
| 266 | .xtensa, .xtensaeb => asm volatile ( | ||
| 267 | \\ .weak _DYNAMIC | ||
| 268 | \\ .hidden _DYNAMIC | ||
| 269 | // Set things up such that after the `call0`, `a0` will point 1 byte before the | ||
| 270 | // embedded constant. Note that `call0` is a 3-byte instruction, so we need both | ||
| 271 | // `.balign` directives to be safe. | ||
| 272 | \\ .balign 4 | ||
| 273 | \\ .begin no-transform | ||
| 274 | \\ call0 1f | ||
| 275 | \\ .end no-transform | ||
| 276 | \\ .balign 4 | ||
| 277 | \\ .word _DYNAMIC - . | ||
| 278 | \\1: | ||
| 279 | \\ add a0, a0, 1 | ||
| 280 | \\ l32i a8, a0, 0 | ||
| 281 | \\ add %[ret], a0, a8 | ||
| 282 | : [ret] "=a" (-> [*]const elf.Dyn), | ||
| 283 | : | ||
| 284 | : .{ .a0 = true, .a8 = true }), | ||
| 264 | else => { | 285 | else => { |
| 265 | @compileError("PIE startup is not yet supported for this target!"); | 286 | @compileError("PIE startup is not yet supported for this target!"); |
| 266 | }, | 287 | }, |
lib/std/start.zig+10| ... | @@ -183,6 +183,7 @@ fn _start() callconv(.naked) noreturn { | ... | @@ -183,6 +183,7 @@ fn _start() callconv(.naked) noreturn { |
| 183 | .sparc, .sparc64 => ".cfi_undefined %%i7", | 183 | .sparc, .sparc64 => ".cfi_undefined %%i7", |
| 184 | .x86 => ".cfi_undefined %%eip", | 184 | .x86 => ".cfi_undefined %%eip", |
| 185 | .x86_64 => ".cfi_undefined %%rip", | 185 | .x86_64 => ".cfi_undefined %%rip", |
| 186 | .xtensa, .xtensaeb => "", // No CFI support. | ||
| 186 | else => @compileError("unsupported arch"), | 187 | else => @compileError("unsupported arch"), |
| 187 | }); | 188 | }); |
| 188 | 189 | ||
| ... | @@ -486,6 +487,15 @@ fn _start() callconv(.naked) noreturn { | ... | @@ -486,6 +487,15 @@ fn _start() callconv(.naked) noreturn { |
| 486 | \\ sub %%sp, 2047, %%sp | 487 | \\ sub %%sp, 2047, %%sp |
| 487 | \\ ba,a %[posixCallMainAndExit] | 488 | \\ ba,a %[posixCallMainAndExit] |
| 488 | , | 489 | , |
| 490 | .xtensa, .xtensaeb => | ||
| 491 | // a0 = LR, a7 = FP, a1 = SP | ||
| 492 | \\ movi a0, 0 | ||
| 493 | \\ movi a7, 0 | ||
| 494 | \\ mov a2, sp | ||
| 495 | \\ movi a8, -16 | ||
| 496 | \\ and sp, sp, a8 | ||
| 497 | \\ callx0 %[posixCallMainAndExit] | ||
| 498 | , | ||
| 489 | else => @compileError("unsupported arch"), | 499 | else => @compileError("unsupported arch"), |
| 490 | } | 500 | } |
| 491 | : | 501 | : |