authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2020-01-21 03:01:20-05:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2020-01-21 03:01:20-05:00
log1f7babbc80211e12c9a38ff2196d6ff8c5a19302
tree1768b836888481ba8f82afa11ec6e1c6262bf429
parent0abaee79af462f4264717f88af052fb00eefde7c
signature Commit is signed but in an unrecognized format.

properly forward baseline target cpu features to llvm


5 files changed, 59 insertions(+), 34 deletions(-)

src-self-hosted/stage1.zig+53-31
...@@ -627,7 +627,7 @@ const Stage2CpuFeatures = struct {...@@ -627,7 +627,7 @@ const Stage2CpuFeatures = struct {
627627
628 const Self = @This();628 const Self = @This();
629629
630 fn createBaseline(allocator: *mem.Allocator) !*Self {630 fn createBaseline(allocator: *mem.Allocator, arch: Target.Arch) !*Self {
631 const self = try allocator.create(Self);631 const self = try allocator.create(Self);
632 errdefer allocator.destroy(self);632 errdefer allocator.destroy(self);
633633
...@@ -641,10 +641,11 @@ const Stage2CpuFeatures = struct {...@@ -641,10 +641,11 @@ const Stage2CpuFeatures = struct {
641 .allocator = allocator,641 .allocator = allocator,
642 .cpu_features = .baseline,642 .cpu_features = .baseline,
643 .llvm_cpu_name = null,643 .llvm_cpu_name = null,
644 .llvm_features_str = null,644 .llvm_features_str = try initLLVMFeatures(allocator, arch, arch.baselineFeatures()),
645 .builtin_str = builtin_str,645 .builtin_str = builtin_str,
646 .cache_hash = cache_hash,646 .cache_hash = cache_hash,
647 };647 };
648
648 return self;649 return self;
649 }650 }
650651
...@@ -658,7 +659,7 @@ const Stage2CpuFeatures = struct {...@@ -658,7 +659,7 @@ const Stage2CpuFeatures = struct {
658 const arch = target.Cross.arch;659 const arch = target.Cross.arch;
659 const cpu_features = try cpuFeaturesFromLLVM(arch, llvm_cpu_name_z, llvm_cpu_features);660 const cpu_features = try cpuFeaturesFromLLVM(arch, llvm_cpu_name_z, llvm_cpu_features);
660 switch (cpu_features) {661 switch (cpu_features) {
661 .baseline => return createBaseline(allocator),662 .baseline => return createBaseline(allocator, arch),
662 .cpu => |cpu| return createFromCpu(allocator, arch, cpu),663 .cpu => |cpu| return createFromCpu(allocator, arch, cpu),
663 .features => |features| return createFromCpuFeatures(allocator, arch, features),664 .features => |features| return createFromCpuFeatures(allocator, arch, features),
664 }665 }
...@@ -688,31 +689,13 @@ const Stage2CpuFeatures = struct {...@@ -688,31 +689,13 @@ const Stage2CpuFeatures = struct {
688 return self;689 return self;
689 }690 }
690691
691 fn createFromCpuFeatures(692 fn initLLVMFeatures(
692 allocator: *mem.Allocator,693 allocator: *mem.Allocator,
693 arch: Target.Arch,694 arch: Target.Arch,
694 feature_set: Target.Cpu.Feature.Set,695 feature_set: Target.Cpu.Feature.Set,
695 ) !*Self {696 ) ![*:0]const u8 {
696 const self = try allocator.create(Self);
697 errdefer allocator.destroy(self);
698
699 const cache_hash = try std.fmt.allocPrint0(allocator, "\n{x}", .{feature_set});
700 errdefer allocator.free(cache_hash);
701
702 const generic_arch_name = arch.genericName();
703 var builtin_str_buffer = try std.Buffer.allocPrint(
704 allocator,
705 \\CpuFeatures{{
706 \\ .features = Target.{}.featureSet(&[_]Target.{}.Feature{{
707 \\
708 ,
709 .{ generic_arch_name, generic_arch_name },
710 );
711 defer builtin_str_buffer.deinit();
712
713 var llvm_features_buffer = try std.Buffer.initSize(allocator, 0);697 var llvm_features_buffer = try std.Buffer.initSize(allocator, 0);
714 defer llvm_features_buffer.deinit();698 defer llvm_features_buffer.deinit();
715
716 // First, disable all features.699 // First, disable all features.
717 // This way, we only get the ones the user requests.700 // This way, we only get the ones the user requests.
718 const all_features = arch.allFeaturesList();701 const all_features = arch.allFeaturesList();
...@@ -723,7 +706,6 @@ const Stage2CpuFeatures = struct {...@@ -723,7 +706,6 @@ const Stage2CpuFeatures = struct {
723 try llvm_features_buffer.append(",");706 try llvm_features_buffer.append(",");
724 }707 }
725 }708 }
726
727 for (all_features) |feature, index| {709 for (all_features) |feature, index| {
728 if (!feature_set.isEnabled(@intCast(u8, index))) continue;710 if (!feature_set.isEnabled(@intCast(u8, index))) continue;
729711
...@@ -732,15 +714,43 @@ const Stage2CpuFeatures = struct {...@@ -732,15 +714,43 @@ const Stage2CpuFeatures = struct {
732 try llvm_features_buffer.append(llvm_name);714 try llvm_features_buffer.append(llvm_name);
733 try llvm_features_buffer.append(",");715 try llvm_features_buffer.append(",");
734 }716 }
735
736 try builtin_str_buffer.append(" .");
737 try builtin_str_buffer.append(feature.name);
738 try builtin_str_buffer.append(",\n");
739 }717 }
740718
741 if (mem.endsWith(u8, llvm_features_buffer.toSliceConst(), ",")) {719 if (mem.endsWith(u8, llvm_features_buffer.toSliceConst(), ",")) {
742 llvm_features_buffer.shrink(llvm_features_buffer.len() - 1);720 llvm_features_buffer.shrink(llvm_features_buffer.len() - 1);
743 }721 }
722 return llvm_features_buffer.toOwnedSlice().ptr;
723 }
724
725 fn createFromCpuFeatures(
726 allocator: *mem.Allocator,
727 arch: Target.Arch,
728 feature_set: Target.Cpu.Feature.Set,
729 ) !*Self {
730 const self = try allocator.create(Self);
731 errdefer allocator.destroy(self);
732
733 const cache_hash = try std.fmt.allocPrint0(allocator, "\n{x}", .{feature_set});
734 errdefer allocator.free(cache_hash);
735
736 const generic_arch_name = arch.genericName();
737 var builtin_str_buffer = try std.Buffer.allocPrint(
738 allocator,
739 \\CpuFeatures{{
740 \\ .features = Target.{}.featureSet(&[_]Target.{}.Feature{{
741 \\
742 ,
743 .{ generic_arch_name, generic_arch_name },
744 );
745 defer builtin_str_buffer.deinit();
746
747 for (arch.allFeaturesList()) |feature, index| {
748 if (!feature_set.isEnabled(@intCast(u8, index))) continue;
749
750 try builtin_str_buffer.append(" .");
751 try builtin_str_buffer.append(feature.name);
752 try builtin_str_buffer.append(",\n");
753 }
744754
745 try builtin_str_buffer.append(755 try builtin_str_buffer.append(
746 \\ }),756 \\ }),
...@@ -752,7 +762,7 @@ const Stage2CpuFeatures = struct {...@@ -752,7 +762,7 @@ const Stage2CpuFeatures = struct {
752 .allocator = allocator,762 .allocator = allocator,
753 .cpu_features = .{ .features = feature_set },763 .cpu_features = .{ .features = feature_set },
754 .llvm_cpu_name = null,764 .llvm_cpu_name = null,
755 .llvm_features_str = llvm_features_buffer.toOwnedSlice().ptr,765 .llvm_features_str = try initLLVMFeatures(allocator, arch, feature_set),
756 .builtin_str = builtin_str_buffer.toOwnedSlice(),766 .builtin_str = builtin_str_buffer.toOwnedSlice(),
757 .cache_hash = cache_hash,767 .cache_hash = cache_hash,
758 };768 };
...@@ -843,13 +853,25 @@ fn parseFeatures(zig_triple: [*:0]const u8, features_text: [*:0]const u8) !*Stag...@@ -843,13 +853,25 @@ fn parseFeatures(zig_triple: [*:0]const u8, features_text: [*:0]const u8) !*Stag
843}853}
844854
845// ABI warning855// ABI warning
846export fn stage2_cpu_features_baseline(result: **Stage2CpuFeatures) Error {856export fn stage2_cpu_features_baseline(result: **Stage2CpuFeatures, zig_triple: [*:0]const u8) Error {
847 result.* = Stage2CpuFeatures.createBaseline(std.heap.c_allocator) catch |err| switch (err) {857 result.* = cpuFeaturesBaseline(zig_triple) catch |err| switch (err) {
848 error.OutOfMemory => return .OutOfMemory,858 error.OutOfMemory => return .OutOfMemory,
859 error.UnknownArchitecture => return .UnknownArchitecture,
860 error.UnknownSubArchitecture => return .UnknownSubArchitecture,
861 error.UnknownOperatingSystem => return .UnknownOperatingSystem,
862 error.UnknownApplicationBinaryInterface => return .UnknownApplicationBinaryInterface,
863 error.MissingOperatingSystem => return .MissingOperatingSystem,
864 error.MissingArchitecture => return .MissingArchitecture,
849 };865 };
850 return .None;866 return .None;
851}867}
852868
869fn cpuFeaturesBaseline(zig_triple: [*:0]const u8) !*Stage2CpuFeatures {
870 const target = try Target.parse(mem.toSliceConst(u8, zig_triple));
871 const arch = target.Cross.arch;
872 return Stage2CpuFeatures.createBaseline(std.heap.c_allocator, arch);
873}
874
853// ABI warning875// ABI warning
854export fn stage2_cpu_features_llvm(876export fn stage2_cpu_features_llvm(
855 result: **Stage2CpuFeatures,877 result: **Stage2CpuFeatures,
src/codegen.cpp+2
...@@ -8802,6 +8802,8 @@ static void init(CodeGen *g) {...@@ -8802,6 +8802,8 @@ static void init(CodeGen *g) {
8802 target_specific_cpu_args = stage2_cpu_features_get_llvm_cpu(g->zig_target->cpu_features);8802 target_specific_cpu_args = stage2_cpu_features_get_llvm_cpu(g->zig_target->cpu_features);
8803 target_specific_features = stage2_cpu_features_get_llvm_features(g->zig_target->cpu_features);8803 target_specific_features = stage2_cpu_features_get_llvm_features(g->zig_target->cpu_features);
8804 }8804 }
8805 //fprintf(stderr, "name=%s target_specific_cpu_args=%s\n", buf_ptr(g->root_out_name), target_specific_cpu_args);
8806 //fprintf(stderr, "name=%s target_specific_features=%s\n", buf_ptr(g->root_out_name), target_specific_features);
8805 8807
8806 g->target_machine = ZigLLVMCreateTargetMachine(target_ref, buf_ptr(&g->llvm_triple_str),8808 g->target_machine = ZigLLVMCreateTargetMachine(target_ref, buf_ptr(&g->llvm_triple_str),
8807 target_specific_cpu_args, target_specific_features, opt_level, reloc_mode,8809 target_specific_cpu_args, target_specific_features, opt_level, reloc_mode,
src/main.cpp+1-1
...@@ -1005,7 +1005,7 @@ int main(int argc, char **argv) {...@@ -1005,7 +1005,7 @@ int main(int argc, char **argv) {
1005 return main_exit(root_progress_node, EXIT_FAILURE);1005 return main_exit(root_progress_node, EXIT_FAILURE);
1006 }1006 }
1007 } else {1007 } else {
1008 if ((err = stage2_cpu_features_baseline(&target.cpu_features))) {1008 if ((err = stage2_cpu_features_baseline(&target.cpu_features, buf_ptr(&zig_triple_buf)))) {
1009 fprintf(stderr, "unable to determine baseline CPU features: %s\n", err_str(err));1009 fprintf(stderr, "unable to determine baseline CPU features: %s\n", err_str(err));
1010 return main_exit(root_progress_node, EXIT_FAILURE);1010 return main_exit(root_progress_node, EXIT_FAILURE);
1011 }1011 }
src/userland.cpp+1-1
...@@ -104,7 +104,7 @@ Error stage2_cpu_features_parse_features(Stage2CpuFeatures **out, const char *zi...@@ -104,7 +104,7 @@ Error stage2_cpu_features_parse_features(Stage2CpuFeatures **out, const char *zi
104 const char *msg = "stage0 called stage2_cpu_features_parse_features";104 const char *msg = "stage0 called stage2_cpu_features_parse_features";
105 stage2_panic(msg, strlen(msg));105 stage2_panic(msg, strlen(msg));
106}106}
107Error stage2_cpu_features_baseline(Stage2CpuFeatures **out) {107Error stage2_cpu_features_baseline(Stage2CpuFeatures **out, const char *zig_triple) {
108 Stage2CpuFeatures *result = allocate<Stage2CpuFeatures>(1, "Stage2CpuFeatures");108 Stage2CpuFeatures *result = allocate<Stage2CpuFeatures>(1, "Stage2CpuFeatures");
109 result->builtin_str = ".baseline;\n";109 result->builtin_str = ".baseline;\n";
110 result->cache_hash = "\n\n";110 result->cache_hash = "\n\n";
src/userland.h+2-1
...@@ -192,7 +192,8 @@ ZIG_EXTERN_C Error stage2_cpu_features_parse_features(struct Stage2CpuFeatures *...@@ -192,7 +192,8 @@ ZIG_EXTERN_C Error stage2_cpu_features_parse_features(struct Stage2CpuFeatures *
192 const char *zig_triple, const char *features);192 const char *zig_triple, const char *features);
193193
194// ABI warning194// ABI warning
195ZIG_EXTERN_C Error stage2_cpu_features_baseline(struct Stage2CpuFeatures **result);195ZIG_EXTERN_C Error stage2_cpu_features_baseline(struct Stage2CpuFeatures **result,
196 const char *zig_triple);
196197
197// ABI warning198// ABI warning
198ZIG_EXTERN_C Error stage2_cpu_features_llvm(struct Stage2CpuFeatures **result,199ZIG_EXTERN_C Error stage2_cpu_features_llvm(struct Stage2CpuFeatures **result,