authorgravatar for alex@alexrp.comAlex Rønne Petersen <alex@alexrp.com> 2026-08-29 19:54:12+02:00
committergravatar for alex@alexrp.comAlex Rønne Petersen <alex@alexrp.com> 2026-08-29 19:54:12+02:00
logbb7af4df66b7d627472f219b274fcbbc7b1b65ec
treecc8469e4baadfedc170a612da87ddd9ea6430a02
parent85781eb71daf957a25e2f007335a557b25f0c1b4
parenta1e5c0d25a8b4009b225b57c8469866631b0eb01
signaturebadge-check Signed by SSH key SHA256:7B/LJ7bpR1eX8aCXSr4mtd5M45VMPKcx9zY8e95b5QM

Merge branch 'riscv-hwprobe'


4 files changed, 327 insertions(+), 22 deletions(-)

lib/std/os/linux.zig+162
...@@ -3258,6 +3258,44 @@ pub fn sysinfo(info: *Sysinfo) usize {...@@ -3258,6 +3258,44 @@ pub fn sysinfo(info: *Sysinfo) usize {
3258 return syscall1(.sysinfo, @intFromPtr(info));3258 return syscall1(.sysinfo, @intFromPtr(info));
3259}3259}
32603260
3261const VdsoSysRiscvHwprobe = *align(1) const fn (
3262 pairs: [*]riscv_hwprobe,
3263 pair_count: usize,
3264 cpusetsize: usize,
3265 cpus: ?[*]cpu_set_t,
3266 flags: u32,
3267) callconv(.c) usize;
3268var vdso_sys_riscv_hwprobe: ?VdsoSysRiscvHwprobe = &init_vdso_sys_riscv_hwprobe;
3269
3270fn init_vdso_sys_riscv_hwprobe(
3271 pairs: [*]riscv_hwprobe,
3272 pair_count: usize,
3273 cpusetsize: usize,
3274 cpus: ?[*]cpu_set_t,
3275 flags: u32,
3276) callconv(.c) usize {
3277 const ptr: ?VdsoSysRiscvHwprobe = @ptrFromInt(vdso.lookup(VDSO.HWPROBE_VER, VDSO.HWPROBE_SYM));
3278 @atomicStore(?VdsoSysRiscvHwprobe, &vdso_sys_riscv_hwprobe, ptr, .monotonic);
3279 if (ptr) |f| return f(pairs, pair_count, cpusetsize, cpus, flags);
3280 return @bitCast(-@as(isize, @backingInt(E.NOSYS)));
3281}
3282
3283pub fn sys_riscv_hwprobe(
3284 pairs: [*]riscv_hwprobe,
3285 pair_count: usize,
3286 cpusetsize: usize,
3287 cpus: ?[*]cpu_set_t,
3288 flags: u32,
3289) usize {
3290 if (VDSO != void) {
3291 const ptr = @atomicLoad(?VdsoSysRiscvHwprobe, &vdso_sys_riscv_hwprobe, .unordered);
3292 if (ptr) |f| {
3293 if (f(pairs, pair_count, cpusetsize, cpus, flags) == 0) return 0;
3294 }
3295 }
3296 return syscall5(.riscv_hwprobe, @intFromPtr(pairs), pair_count, cpusetsize, @intFromPtr(cpus), flags);
3297}
3298
3261pub const E = switch (native_arch) {3299pub const E = switch (native_arch) {
3262 .mips, .mipsel, .mips64, .mips64el => enum(u16) {3300 .mips, .mipsel, .mips64, .mips64el => enum(u16) {
3263 /// No error occurred.3301 /// No error occurred.
...@@ -10920,3 +10958,127 @@ pub const cmsghdr = extern struct {...@@ -10920,3 +10958,127 @@ pub const cmsghdr = extern struct {
10920 level: i32,10958 level: i32,
10921 type: i32,10959 type: i32,
10922};10960};
10961
10962pub const riscv_hwprobe = extern struct {
10963 key: i64,
10964 value: u64,
10965};
10966
10967pub const RISCV_HWPROBE = struct {
10968 pub const KEY = struct {
10969 pub const MVENDORID = 0;
10970 pub const MARCHID = 1;
10971 pub const MIMPID = 2;
10972 pub const BASE_BEHAVIOR = 3;
10973 pub const IMA_EXT_0 = 4;
10974 pub const CPUPERF_0 = 5;
10975 pub const ZICBOZ_BLOCK_SIZE = 6;
10976 pub const HIGHEST_VIRT_ADDRESS = 7;
10977 pub const TIME_CSR_FREQ = 8;
10978 pub const MISALIGNED_SCALAR_PERF = 9;
10979 pub const MISALIGNED_VECTOR_PERF = 10;
10980 pub const VENDOR_EXT_THEAD_0 = 11;
10981 pub const ZICBOM_BLOCK_SIZE = 12;
10982 pub const VENDOR_EXT_SIFIVE_0 = 13;
10983 pub const VENDOR_EXT_MIPS_0 = 14;
10984 pub const ZICBOP_BLOCK_SIZE = 15;
10985 pub const IMA_EXT_1 = 16;
10986 };
10987
10988 pub const FLAGS_WHICH_CPUS = 1 << 0;
10989
10990 pub const BASE_BEHAVIOR_IMA = 1 << 0;
10991
10992 pub const IMA_EXT_0 = struct {
10993 pub const IMA_FD = 1 << 0;
10994 pub const IMA_C = 1 << 1;
10995 pub const IMA_V = 1 << 2;
10996 pub const EXT_ZBA = 1 << 3;
10997 pub const EXT_ZBB = 1 << 4;
10998 pub const EXT_ZBS = 1 << 5;
10999 pub const EXT_ZICBOZ = 1 << 6;
11000 pub const EXT_ZBC = 1 << 7;
11001 pub const EXT_ZBKB = 1 << 8;
11002 pub const EXT_ZBKC = 1 << 9;
11003 pub const EXT_ZBKX = 1 << 10;
11004 pub const EXT_ZKND = 1 << 11;
11005 pub const EXT_ZKNE = 1 << 12;
11006 pub const EXT_ZKNH = 1 << 13;
11007 pub const EXT_ZKSED = 1 << 14;
11008 pub const EXT_ZKSH = 1 << 15;
11009 pub const EXT_ZKT = 1 << 16;
11010 pub const EXT_ZVBB = 1 << 17;
11011 pub const EXT_ZVBC = 1 << 18;
11012 pub const EXT_ZVKB = 1 << 19;
11013 pub const EXT_ZVKG = 1 << 20;
11014 pub const EXT_ZVKNED = 1 << 21;
11015 pub const EXT_ZVKNHA = 1 << 22;
11016 pub const EXT_ZVKNHB = 1 << 23;
11017 pub const EXT_ZVKSED = 1 << 24;
11018 pub const EXT_ZVKSH = 1 << 25;
11019 pub const EXT_ZVKT = 1 << 26;
11020 pub const EXT_ZFH = 1 << 27;
11021 pub const EXT_ZFHMIN = 1 << 28;
11022 pub const EXT_ZIHINTNTL = 1 << 29;
11023 pub const EXT_ZVFH = 1 << 30;
11024 pub const EXT_ZVFHMIN = 1 << 31;
11025 pub const EXT_ZFA = 1 << 32;
11026 pub const EXT_ZTSO = 1 << 33;
11027 pub const EXT_ZACAS = 1 << 34;
11028 pub const EXT_ZICOND = 1 << 35;
11029 pub const EXT_ZIHINTPAUSE = 1 << 36;
11030 pub const EXT_ZVE32X = 1 << 37;
11031 pub const EXT_ZVE32F = 1 << 38;
11032 pub const EXT_ZVE64X = 1 << 39;
11033 pub const EXT_ZVE64F = 1 << 40;
11034 pub const EXT_ZVE64D = 1 << 41;
11035 pub const EXT_ZIMOP = 1 << 42;
11036 pub const EXT_ZCA = 1 << 43;
11037 pub const EXT_ZCB = 1 << 44;
11038 pub const EXT_ZCD = 1 << 45;
11039 pub const EXT_ZCF = 1 << 46;
11040 pub const EXT_ZCMOP = 1 << 47;
11041 pub const EXT_ZAWRS = 1 << 48;
11042 pub const EXT_SUPM = 1 << 49;
11043 pub const EXT_ZICNTR = 1 << 50;
11044 pub const EXT_ZIHPM = 1 << 51;
11045 pub const EXT_ZFBFMIN = 1 << 52;
11046 pub const EXT_ZVFBFMIN = 1 << 53;
11047 pub const EXT_ZVFBFWMA = 1 << 54;
11048 pub const EXT_ZICBOM = 1 << 55;
11049 pub const EXT_ZAAMO = 1 << 56;
11050 pub const EXT_ZALRSC = 1 << 57;
11051 pub const EXT_ZABHA = 1 << 58;
11052 pub const EXT_ZALASR = 1 << 59;
11053 pub const EXT_ZICBOP = 1 << 60;
11054 pub const EXT_ZILSD = 1 << 61;
11055 pub const EXT_ZCLSD = 1 << 62;
11056 pub const EXT_ZICFILP = 1 << 63;
11057 };
11058
11059 pub const IMA_EXT_1_EXT_ZICFISS = 1 << 0;
11060
11061 pub const MISALIGNED_SCALAR = struct {
11062 pub const UNKNOWN = 0;
11063 pub const EMULATED = 1;
11064 pub const SLOW = 2;
11065 pub const FAST = 3;
11066 pub const UNSUPPORTED = 4;
11067 };
11068
11069 pub const MISALIGNED_VECTOR = struct {
11070 pub const UNKNOWN = 0;
11071 pub const SLOW = 2;
11072 pub const FAST = 3;
11073 pub const UNSUPPORTED = 4;
11074 };
11075
11076 pub const MIPS_VENDOR_EXT_XMIPSEXECTL = 1 << 0;
11077
11078 pub const SIFIVE_VENDOR_EXT = struct {
11079 pub const XSFVQMACCDOD = 1 << 0;
11080 pub const XSFVQMACCQOQ = 1 << 1;
11081 pub const XSFVFNRCLIPXFQF = 1 << 2;
11082 pub const XSFVFWMACCQQQ = 1 << 3;
11083 };
11084};
lib/std/os/linux/riscv32.zig+3
...@@ -159,4 +159,7 @@ pub const time_t = i64;...@@ -159,4 +159,7 @@ pub const time_t = i64;
159pub const VDSO = struct {159pub const VDSO = struct {
160 pub const CGT_SYM = "__vdso_clock_gettime";160 pub const CGT_SYM = "__vdso_clock_gettime";
161 pub const CGT_VER = "LINUX_4.15";161 pub const CGT_VER = "LINUX_4.15";
162
163 pub const HWPROBE_SYM = "__vdso_riscv_hwprobe";
164 pub const HWPROBE_VER = "LINUX_4.15";
162};165};
lib/std/os/linux/riscv64.zig+3
...@@ -159,4 +159,7 @@ pub const time_t = i64;...@@ -159,4 +159,7 @@ pub const time_t = i64;
159pub const VDSO = struct {159pub const VDSO = struct {
160 pub const CGT_SYM = "__vdso_clock_gettime";160 pub const CGT_SYM = "__vdso_clock_gettime";
161 pub const CGT_VER = "LINUX_4.15";161 pub const CGT_VER = "LINUX_4.15";
162
163 pub const HWPROBE_SYM = "__vdso_riscv_hwprobe";
164 pub const HWPROBE_VER = "LINUX_4.15";
162};165};
lib/std/zig/system/linux.zig+159-22
...@@ -447,6 +447,142 @@ inline fn getAArch64CpuFeature(comptime feat_reg: []const u8) u64 {...@@ -447,6 +447,142 @@ inline fn getAArch64CpuFeature(comptime feat_reg: []const u8) u64 {
447 );447 );
448}448}
449449
450const riscv = struct {
451 const linux = std.os.linux;
452 const RISCV_HWPROBE = linux.RISCV_HWPROBE;
453
454 fn setFeature(cpu: *Target.Cpu, feature: Target.riscv.Feature, enabled: bool) void {
455 const idx = @as(Target.Cpu.Feature.Set.Index, @backingInt(feature));
456
457 if (enabled) cpu.features.addFeature(idx) else cpu.features.removeFeature(idx);
458 }
459
460 inline fn set(value: u64, mask: u64) bool {
461 return (value & mask) == mask;
462 }
463
464 pub fn detectCpuFeatures(cpu: *Target.Cpu) void {
465 var probes = [_]linux.riscv_hwprobe{
466 .{ .key = RISCV_HWPROBE.KEY.BASE_BEHAVIOR, .value = 0 },
467 .{ .key = RISCV_HWPROBE.KEY.IMA_EXT_0, .value = 0 },
468 .{ .key = RISCV_HWPROBE.KEY.MISALIGNED_SCALAR_PERF, .value = 0 },
469 .{ .key = RISCV_HWPROBE.KEY.MISALIGNED_VECTOR_PERF, .value = 0 },
470 .{ .key = RISCV_HWPROBE.KEY.VENDOR_EXT_MIPS_0, .value = 0 },
471 .{ .key = RISCV_HWPROBE.KEY.VENDOR_EXT_SIFIVE_0, .value = 0 },
472 .{ .key = RISCV_HWPROBE.KEY.IMA_EXT_1, .value = 0 },
473 };
474
475 const rc = linux.sys_riscv_hwprobe(&probes, probes.len, 0, null, 0);
476 if (linux.errno(rc) == .NOSYS)
477 return;
478
479 var ima_support = false;
480 for (probes) |probe| {
481 const value = probe.value;
482
483 switch (probe.key) {
484 -1 => continue, // The running kernel doesn't know this key.
485 RISCV_HWPROBE.KEY.BASE_BEHAVIOR => {
486 ima_support = set(value, RISCV_HWPROBE.BASE_BEHAVIOR_IMA);
487 setFeature(cpu, Target.riscv.Feature.i, ima_support);
488 setFeature(cpu, Target.riscv.Feature.m, ima_support);
489 setFeature(cpu, Target.riscv.Feature.a, ima_support);
490 },
491 RISCV_HWPROBE.KEY.IMA_EXT_0 => {
492 // https://bugzilla.kernel.org/show_bug.cgi?id=221874
493 const fd_support = set(value, RISCV_HWPROBE.IMA_EXT_0.IMA_FD);
494 setFeature(cpu, .f, ima_support and fd_support);
495 setFeature(cpu, .d, ima_support and fd_support);
496 setFeature(cpu, .c, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.IMA_C));
497 setFeature(cpu, .v, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.IMA_V));
498 setFeature(cpu, .zba, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBA));
499 setFeature(cpu, .zbb, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBB));
500 setFeature(cpu, .zbs, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBS));
501 setFeature(cpu, .zicboz, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICBOZ));
502 setFeature(cpu, .zbc, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBC));
503 setFeature(cpu, .zbkb, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBKB));
504 setFeature(cpu, .zbkc, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBKC));
505 setFeature(cpu, .zbkx, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZBKX));
506 setFeature(cpu, .zknd, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZKND));
507 setFeature(cpu, .zkne, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZKNE));
508 setFeature(cpu, .zknh, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZKNH));
509 setFeature(cpu, .zksed, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZKSED));
510 setFeature(cpu, .zksh, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZKSH));
511 setFeature(cpu, .zkt, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZKT));
512 setFeature(cpu, .zvbb, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVBB));
513 setFeature(cpu, .zvbc, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVBC));
514 setFeature(cpu, .zvkb, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKB));
515 setFeature(cpu, .zvkg, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKG));
516 setFeature(cpu, .zvkned, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKNED));
517 setFeature(cpu, .zvknha, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKNHA));
518 setFeature(cpu, .zvknhb, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKNHB));
519 setFeature(cpu, .zvksed, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKSED));
520 setFeature(cpu, .zvksh, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKSH));
521 setFeature(cpu, .zvkt, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVKT));
522 setFeature(cpu, .zfh, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZFH));
523 setFeature(cpu, .zfhmin, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZFHMIN));
524 setFeature(cpu, .zihintntl, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZIHINTNTL));
525 setFeature(cpu, .zvfh, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVFH));
526 setFeature(cpu, .zvfhmin, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVFHMIN));
527 setFeature(cpu, .zfa, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZFA));
528 setFeature(cpu, .ztso, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZTSO));
529 setFeature(cpu, .zacas, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZACAS));
530 setFeature(cpu, .zicntr, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICNTR));
531 setFeature(cpu, .zicond, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICOND));
532 setFeature(cpu, .zihintpause, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZIHINTPAUSE));
533 setFeature(cpu, .zihpm, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZIHPM));
534 setFeature(cpu, .zve32x, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVE32X));
535 setFeature(cpu, .zve32f, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVE32F));
536 setFeature(cpu, .zve64x, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVE64X));
537 setFeature(cpu, .zve64f, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVE64F));
538 setFeature(cpu, .zve64d, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVE64D));
539 setFeature(cpu, .zimop, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZIMOP));
540 setFeature(cpu, .zca, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZCA));
541 setFeature(cpu, .zcb, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZCB));
542 setFeature(cpu, .zcd, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZCD));
543 setFeature(cpu, .zcf, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZCF));
544 setFeature(cpu, .zcmop, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZCMOP));
545 setFeature(cpu, .zawrs, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZAWRS));
546 setFeature(cpu, .supm, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_SUPM));
547 setFeature(cpu, .zicntr, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICNTR));
548 setFeature(cpu, .zihpm, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZIHPM));
549 setFeature(cpu, .zfbfmin, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZFBFMIN));
550 setFeature(cpu, .zvfbfmin, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVFBFMIN));
551 setFeature(cpu, .zvfbfwma, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZVFBFWMA));
552 setFeature(cpu, .zicbom, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICBOM));
553 setFeature(cpu, .zaamo, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZAAMO));
554 setFeature(cpu, .zalrsc, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZALRSC));
555 setFeature(cpu, .zabha, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZABHA));
556 setFeature(cpu, .zalasr, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZALASR));
557 setFeature(cpu, .zicbop, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICBOP));
558 setFeature(cpu, .zilsd, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZILSD));
559 setFeature(cpu, .zclsd, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZCLSD));
560 setFeature(cpu, .experimental_zicfilp, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_0.EXT_ZICFILP));
561 },
562 RISCV_HWPROBE.KEY.MISALIGNED_SCALAR_PERF => {
563 setFeature(cpu, .unaligned_scalar_mem, value == RISCV_HWPROBE.MISALIGNED_SCALAR.FAST);
564 },
565 RISCV_HWPROBE.KEY.MISALIGNED_VECTOR_PERF => {
566 setFeature(cpu, .unaligned_vector_mem, value == RISCV_HWPROBE.MISALIGNED_VECTOR.FAST);
567 },
568 RISCV_HWPROBE.KEY.VENDOR_EXT_MIPS_0 => {
569 setFeature(cpu, .xmipsexectl, ima_support and set(value, RISCV_HWPROBE.MIPS_VENDOR_EXT_XMIPSEXECTL));
570 },
571 RISCV_HWPROBE.KEY.VENDOR_EXT_SIFIVE_0 => {
572 setFeature(cpu, .xsfvqmaccdod, ima_support and set(value, RISCV_HWPROBE.SIFIVE_VENDOR_EXT.XSFVQMACCDOD));
573 setFeature(cpu, .xsfvqmaccqoq, ima_support and set(value, RISCV_HWPROBE.SIFIVE_VENDOR_EXT.XSFVQMACCQOQ));
574 setFeature(cpu, .xsfvfnrclipxfqf, ima_support and set(value, RISCV_HWPROBE.SIFIVE_VENDOR_EXT.XSFVFNRCLIPXFQF));
575 setFeature(cpu, .xsfvfwmaccqqq, ima_support and set(value, RISCV_HWPROBE.SIFIVE_VENDOR_EXT.XSFVFWMACCQQQ));
576 },
577 RISCV_HWPROBE.KEY.IMA_EXT_1 => {
578 setFeature(cpu, .experimental_zicfiss, ima_support and set(value, RISCV_HWPROBE.IMA_EXT_1_EXT_ZICFISS));
579 },
580 else => unreachable,
581 }
582 }
583 }
584};
585
450pub fn detectNativeCpuAndFeatures(io: Io) ?Target.Cpu {586pub fn detectNativeCpuAndFeatures(io: Io) ?Target.Cpu {
451 var file = Io.Dir.openFileAbsolute(io, "/proc/cpuinfo", .{}) catch |err| switch (err) {587 var file = Io.Dir.openFileAbsolute(io, "/proc/cpuinfo", .{}) catch |err| switch (err) {
452 else => return null,588 else => return null,
...@@ -457,11 +593,8 @@ pub fn detectNativeCpuAndFeatures(io: Io) ?Target.Cpu {...@@ -457,11 +593,8 @@ pub fn detectNativeCpuAndFeatures(io: Io) ?Target.Cpu {
457 var file_reader = file.reader(io, &buffer);593 var file_reader = file.reader(io, &buffer);
458594
459 const current_arch = builtin.cpu.arch;595 const current_arch = builtin.cpu.arch;
460 switch (current_arch) {596 return switch (current_arch) {
461 .arm, .armeb, .thumb, .thumbeb => {597 .aarch64, .aarch64_be => b: {
462 return ArmCpuinfoParser.parse(current_arch, &file_reader.interface) catch null;
463 },
464 .aarch64, .aarch64_be => {
465 const registers = [12]u64{598 const registers = [12]u64{
466 getAArch64CpuFeature("MIDR_EL1"),599 getAArch64CpuFeature("MIDR_EL1"),
467 getAArch64CpuFeature("ID_AA64PFR0_EL1"),600 getAArch64CpuFeature("ID_AA64PFR0_EL1"),
...@@ -477,23 +610,27 @@ pub fn detectNativeCpuAndFeatures(io: Io) ?Target.Cpu {...@@ -477,23 +610,27 @@ pub fn detectNativeCpuAndFeatures(io: Io) ?Target.Cpu {
477 getAArch64CpuFeature("ID_AA64MMFR2_EL1"),610 getAArch64CpuFeature("ID_AA64MMFR2_EL1"),
478 };611 };
479612
480 const core = @import("arm.zig").aarch64.detectNativeCpuAndFeatures(current_arch, registers);613 break :b @import("arm.zig").aarch64.detectNativeCpuAndFeatures(current_arch, registers);
481 return core;
482 },
483 .sparc, .sparc64 => {
484 return SparcCpuinfoParser.parse(current_arch, &file_reader.interface) catch null;
485 },
486 .powerpc, .powerpcle, .powerpc64, .powerpc64le => {
487 return PowerpcCpuinfoParser.parse(current_arch, &file_reader.interface) catch null;
488 },
489 .riscv64, .riscv32 => {
490 return RiscvCpuinfoParser.parse(current_arch, &file_reader.interface) catch null;
491 },
492 .s390x => {
493 return S390xCpuinfoParser.parse(current_arch, &file_reader.interface) catch null;
494 },614 },
495 else => {},615 .arm, .armeb, .thumb, .thumbeb => ArmCpuinfoParser.parse(current_arch, &file_reader.interface) catch null,
496 }616 .powerpc, .powerpcle, .powerpc64, .powerpc64le => PowerpcCpuinfoParser.parse(current_arch, &file_reader.interface) catch null,
617 .riscv64, .riscv32 => b: {
618 var cpu = (RiscvCpuinfoParser.parse(current_arch, &file_reader.interface) catch null) orelse cpu: {
619 const model = Target.Cpu.Model.generic(current_arch);
620 break :cpu Target.Cpu{
621 .arch = current_arch,
622 .model = model,
623 .features = model.features,
624 };
625 };
626
627 riscv.detectCpuFeatures(&cpu);
628 cpu.features.populateDependencies(cpu.arch.allFeaturesList());
497629
498 return null;630 break :b cpu;
631 },
632 .s390x => S390xCpuinfoParser.parse(current_arch, &file_reader.interface) catch null,
633 .sparc, .sparc64 => SparcCpuinfoParser.parse(current_arch, &file_reader.interface) catch null,
634 else => null,
635 };
499}636}