| ... | ... | @@ -539,19 +539,82 @@ export fn stage2_progress_update_node(node: *std.Progress.Node, done_count: usiz |
| 539 | 539 | node.context.maybeRefresh(); |
| 540 | 540 | } |
| 541 | 541 | |
| 542 | fn cpuFeaturesFromLLVM( |
| 543 | arch: Target.Arch, |
| 544 | llvm_cpu_name_z: ?[*:0]const u8, |
| 545 | llvm_cpu_features_opt: ?[*:0]const u8, |
| 546 | ) !Target.CpuFeatures { |
| 547 | if (llvm_cpu_name_z) |cpu_name_z| { |
| 548 | const llvm_cpu_name = mem.toSliceConst(u8, cpu_name_z); |
| 549 | |
| 550 | for (arch.allCpus()) |cpu| { |
| 551 | const this_llvm_name = cpu.llvm_name orelse continue; |
| 552 | if (mem.eql(u8, this_llvm_name, llvm_cpu_name)) { |
| 553 | return Target.CpuFeatures{ .cpu = cpu }; |
| 554 | } |
| 555 | } |
| 556 | } |
| 557 | |
| 558 | var set = arch.baselineFeatures(); |
| 559 | const llvm_cpu_features = llvm_cpu_features_opt orelse return Target.CpuFeatures{ |
| 560 | .features = set, |
| 561 | }; |
| 562 | |
| 563 | var it = mem.tokenize(mem.toSliceConst(u8, llvm_cpu_features), ","); |
| 564 | while (it.next()) |decorated_llvm_feat| { |
| 565 | var op: enum { |
| 566 | add, |
| 567 | sub, |
| 568 | } = undefined; |
| 569 | var llvm_feat: []const u8 = undefined; |
| 570 | if (mem.startsWith(u8, decorated_llvm_feat, "+")) { |
| 571 | op = .add; |
| 572 | llvm_feat = decorated_llvm_feat[1..]; |
| 573 | } else if (mem.startsWith(u8, decorated_llvm_feat, "-")) { |
| 574 | op = .sub; |
| 575 | llvm_feat = decorated_llvm_feat[1..]; |
| 576 | } else { |
| 577 | return error.InvalidLlvmCpuFeaturesFormat; |
| 578 | } |
| 579 | for (arch.allFeaturesList()) |feature, index| { |
| 580 | const this_llvm_name = feature.llvm_name orelse continue; |
| 581 | if (mem.eql(u8, llvm_feat, this_llvm_name)) { |
| 582 | switch (op) { |
| 583 | .add => set.addFeature(@intCast(u8, index)), |
| 584 | .sub => set.removeFeature(@intCast(u8, index)), |
| 585 | } |
| 586 | break; |
| 587 | } |
| 588 | } |
| 589 | } |
| 590 | return Target.CpuFeatures{ .features = set }; |
| 591 | } |
| 592 | |
| 542 | 593 | // ABI warning |
| 543 | | export fn stage2_cmd_targets() c_int { |
| 544 | | @import("print_targets.zig").cmdTargets( |
| 545 | | std.heap.c_allocator, |
| 546 | | &[0][]u8{}, |
| 547 | | &std.io.getStdOut().outStream().stream, |
| 548 | | ) catch |err| { |
| 594 | export fn stage2_cmd_targets(zig_triple: [*:0]const u8) c_int { |
| 595 | cmdTargets(zig_triple) catch |err| { |
| 549 | 596 | std.debug.warn("unable to list targets: {}\n", .{@errorName(err)}); |
| 550 | 597 | return -1; |
| 551 | 598 | }; |
| 552 | 599 | return 0; |
| 553 | 600 | } |
| 554 | 601 | |
| 602 | fn cmdTargets(zig_triple: [*:0]const u8) !void { |
| 603 | var target = try Target.parse(mem.toSliceConst(u8, zig_triple)); |
| 604 | target.Cross.cpu_features = blk: { |
| 605 | const llvm = @import("llvm.zig"); |
| 606 | const llvm_cpu_name = llvm.GetHostCPUName(); |
| 607 | const llvm_cpu_features = llvm.GetNativeFeatures(); |
| 608 | break :blk try cpuFeaturesFromLLVM(target.Cross.arch, llvm_cpu_name, llvm_cpu_features); |
| 609 | }; |
| 610 | return @import("print_targets.zig").cmdTargets( |
| 611 | std.heap.c_allocator, |
| 612 | &[0][]u8{}, |
| 613 | &std.io.getStdOut().outStream().stream, |
| 614 | target, |
| 615 | ); |
| 616 | } |
| 617 | |
| 555 | 618 | const Stage2CpuFeatures = struct { |
| 556 | 619 | allocator: *mem.Allocator, |
| 557 | 620 | cpu_features: Target.CpuFeatures, |
| ... | ... | @@ -588,49 +651,17 @@ const Stage2CpuFeatures = struct { |
| 588 | 651 | fn createFromLLVM( |
| 589 | 652 | allocator: *mem.Allocator, |
| 590 | 653 | zig_triple: [*:0]const u8, |
| 591 | | llvm_cpu_name_z: [*:0]const u8, |
| 592 | | llvm_cpu_features: [*:0]const u8, |
| 654 | llvm_cpu_name_z: ?[*:0]const u8, |
| 655 | llvm_cpu_features: ?[*:0]const u8, |
| 593 | 656 | ) !*Self { |
| 594 | 657 | const target = try Target.parse(mem.toSliceConst(u8, zig_triple)); |
| 595 | 658 | const arch = target.Cross.arch; |
| 596 | | const llvm_cpu_name = mem.toSliceConst(u8, llvm_cpu_name_z); |
| 597 | | |
| 598 | | for (arch.allCpus()) |cpu| { |
| 599 | | const this_llvm_name = cpu.llvm_name orelse continue; |
| 600 | | if (mem.eql(u8, this_llvm_name, llvm_cpu_name)) { |
| 601 | | return createFromCpu(allocator, arch, cpu); |
| 602 | | } |
| 603 | | } |
| 604 | | |
| 605 | | var set = arch.baselineFeatures(); |
| 606 | | var it = mem.tokenize(mem.toSliceConst(u8, llvm_cpu_features), ","); |
| 607 | | while (it.next()) |decorated_llvm_feat| { |
| 608 | | var op: enum { |
| 609 | | add, |
| 610 | | sub, |
| 611 | | } = undefined; |
| 612 | | var llvm_feat: []const u8 = undefined; |
| 613 | | if (mem.startsWith(u8, decorated_llvm_feat, "+")) { |
| 614 | | op = .add; |
| 615 | | llvm_feat = decorated_llvm_feat[1..]; |
| 616 | | } else if (mem.startsWith(u8, decorated_llvm_feat, "-")) { |
| 617 | | op = .sub; |
| 618 | | llvm_feat = decorated_llvm_feat[1..]; |
| 619 | | } else { |
| 620 | | return error.InvalidLlvmCpuFeaturesFormat; |
| 621 | | } |
| 622 | | for (arch.allFeaturesList()) |feature, index| { |
| 623 | | const this_llvm_name = feature.llvm_name orelse continue; |
| 624 | | if (mem.eql(u8, llvm_feat, this_llvm_name)) { |
| 625 | | switch (op) { |
| 626 | | .add => set.addFeature(@intCast(u8, index)), |
| 627 | | .sub => set.removeFeature(@intCast(u8, index)), |
| 628 | | } |
| 629 | | break; |
| 630 | | } |
| 631 | | } |
| 659 | const cpu_features = try cpuFeaturesFromLLVM(arch, llvm_cpu_name_z, llvm_cpu_features); |
| 660 | switch (cpu_features) { |
| 661 | .baseline => return createBaseline(allocator), |
| 662 | .cpu => |cpu| return createFromCpu(allocator, arch, cpu), |
| 663 | .features => |features| return createFromCpuFeatures(allocator, arch, features), |
| 632 | 664 | } |
| 633 | | return createFromCpuFeatures(allocator, arch, set); |
| 634 | 665 | } |
| 635 | 666 | |
| 636 | 667 | fn createFromCpu(allocator: *mem.Allocator, arch: Target.Arch, cpu: *const Target.Cpu) !*Self { |
| ... | ... | @@ -823,8 +854,8 @@ export fn stage2_cpu_features_baseline(result: **Stage2CpuFeatures) Error { |
| 823 | 854 | export fn stage2_cpu_features_llvm( |
| 824 | 855 | result: **Stage2CpuFeatures, |
| 825 | 856 | zig_triple: [*:0]const u8, |
| 826 | | llvm_cpu_name: [*:0]const u8, |
| 827 | | llvm_cpu_features: [*:0]const u8, |
| 857 | llvm_cpu_name: ?[*:0]const u8, |
| 858 | llvm_cpu_features: ?[*:0]const u8, |
| 828 | 859 | ) Error { |
| 829 | 860 | result.* = Stage2CpuFeatures.createFromLLVM( |
| 830 | 861 | std.heap.c_allocator, |