From e0fe0f7f1e26c7cc0266b3f0168363135ec75ff4 Mon Sep 17 00:00:00 2001 From: Michael Dusan Date: Wed, 11 Mar 2020 19:33:10 -0400 Subject: [PATCH 1/3] parse CPU features when --target is null - fixes case where features are not parsed when `-target` is null - `zig builtin -mcpu native+bogus` should return error/list of valid features --- src-self-hosted/stage2.zig | 74 +++++++++++++++++++------------------- 1 file changed, 36 insertions(+), 38 deletions(-) diff --git a/src-self-hosted/stage2.zig b/src-self-hosted/stage2.zig index 8f2656de44..bdd68925ee 100644 --- a/src-self-hosted/stage2.zig +++ b/src-self-hosted/stage2.zig @@ -679,44 +679,42 @@ fn stage2TargetParse( mcpu_oz: ?[*:0]const u8, dynamic_linker_oz: ?[*:0]const u8, ) !void { - const target: CrossTarget = if (zig_triple_oz) |zig_triple_z| blk: { - const zig_triple = mem.toSliceConst(u8, zig_triple_z); - const mcpu = if (mcpu_oz) |mcpu_z| mem.toSliceConst(u8, mcpu_z) else null; - const dynamic_linker = if (dynamic_linker_oz) |dl_z| mem.toSliceConst(u8, dl_z) else null; - var diags: CrossTarget.ParseOptions.Diagnostics = .{}; - break :blk CrossTarget.parse(.{ - .arch_os_abi = zig_triple, - .cpu_features = mcpu, - .dynamic_linker = dynamic_linker, - .diagnostics = &diags, - }) catch |err| switch (err) { - error.UnknownCpuModel => { - std.debug.warn("Unknown CPU: '{}'\nAvailable CPUs for architecture '{}':\n", .{ - diags.cpu_name.?, - @tagName(diags.arch.?), - }); - for (diags.arch.?.allCpuModels()) |cpu| { - std.debug.warn(" {}\n", .{cpu.name}); - } - process.exit(1); - }, - error.UnknownCpuFeature => { - std.debug.warn( - \\Unknown CPU feature: '{}' - \\Available CPU features for architecture '{}': - \\ - , .{ - diags.unknown_feature_name, - @tagName(diags.arch.?), - }); - for (diags.arch.?.allFeaturesList()) |feature| { - std.debug.warn(" {}: {}\n", .{ feature.name, feature.description }); - } - process.exit(1); - }, - else => |e| return e, - }; - } else .{}; + const zig_triple = if (zig_triple_oz) |zig_triple_z| mem.toSliceConst(u8, zig_triple_z) else "native"; + const mcpu = if (mcpu_oz) |mcpu_z| mem.toSliceConst(u8, mcpu_z) else null; + const dynamic_linker = if (dynamic_linker_oz) |dl_z| mem.toSliceConst(u8, dl_z) else null; + var diags: CrossTarget.ParseOptions.Diagnostics = .{}; + const target: CrossTarget = CrossTarget.parse(.{ + .arch_os_abi = zig_triple, + .cpu_features = mcpu, + .dynamic_linker = dynamic_linker, + .diagnostics = &diags, + }) catch |err| switch (err) { + error.UnknownCpuModel => { + std.debug.warn("Unknown CPU: '{}'\nAvailable CPUs for architecture '{}':\n", .{ + diags.cpu_name.?, + @tagName(diags.arch.?), + }); + for (diags.arch.?.allCpuModels()) |cpu| { + std.debug.warn(" {}\n", .{cpu.name}); + } + process.exit(1); + }, + error.UnknownCpuFeature => { + std.debug.warn( + \\Unknown CPU feature: '{}' + \\Available CPU features for architecture '{}': + \\ + , .{ + diags.unknown_feature_name, + @tagName(diags.arch.?), + }); + for (diags.arch.?.allFeaturesList()) |feature| { + std.debug.warn(" {}: {}\n", .{ feature.name, feature.description }); + } + process.exit(1); + }, + else => |e| return e, + }; try stage1_target.fromTarget(target); } From c988167377c92359fed42f12ad32b5f349f9ffb8 Mon Sep 17 00:00:00 2001 From: Michael Dusan Date: Wed, 11 Mar 2020 19:33:11 -0400 Subject: [PATCH 2/3] update/apply CPU features when -mcpu native - fix: features were not applied if cpu is specified as native --- lib/std/zig/system.zig | 21 ++++++--------------- 1 file changed, 6 insertions(+), 15 deletions(-) diff --git a/lib/std/zig/system.zig b/lib/std/zig/system.zig index 558b50b5b3..88b3022bb2 100644 --- a/lib/std/zig/system.zig +++ b/lib/std/zig/system.zig @@ -325,22 +325,19 @@ pub const NativeTargetInfo = struct { // native CPU architecture as being different than the current target), we use this: const cpu_arch = cross_target.getCpuArch(); - const cpu = switch (cross_target.cpu_model) { + var cpu = switch (cross_target.cpu_model) { .native => detectNativeCpuAndFeatures(cpu_arch, os, cross_target), - .baseline => baselineCpuAndFeatures(cpu_arch, cross_target), + .baseline => Target.Cpu.baseline(cpu_arch), .determined_by_cpu_arch => if (cross_target.cpu_arch == null) detectNativeCpuAndFeatures(cpu_arch, os, cross_target) else - baselineCpuAndFeatures(cpu_arch, cross_target), - .explicit => |model| blk: { - var adjusted_model = model.toCpu(cpu_arch); - cross_target.updateCpuFeatures(&adjusted_model.features); - break :blk adjusted_model; - }, + Target.Cpu.baseline(cpu_arch), + .explicit => |model| model.toCpu(cpu_arch), } orelse backup_cpu_detection: { cpu_detection_unimplemented = true; - break :backup_cpu_detection baselineCpuAndFeatures(cpu_arch, cross_target); + break :backup_cpu_detection Target.Cpu.baseline(cpu_arch); }; + cross_target.updateCpuFeatures(&cpu.features); var target = try detectAbiAndDynamicLinker(allocator, cpu, os, cross_target); target.cpu_detection_unimplemented = cpu_detection_unimplemented; @@ -884,10 +881,4 @@ pub const NativeTargetInfo = struct { }, } } - - fn baselineCpuAndFeatures(cpu_arch: Target.Cpu.Arch, cross_target: CrossTarget) Target.Cpu { - var adjusted_baseline = Target.Cpu.baseline(cpu_arch); - cross_target.updateCpuFeatures(&adjusted_baseline.features); - return adjusted_baseline; - } }; From bfebc11d0633e3f4a3fe86d1a9d6f90ffdb1fbb6 Mon Sep 17 00:00:00 2001 From: Michael Dusan Date: Wed, 11 Mar 2020 19:33:12 -0400 Subject: [PATCH 3/3] fix zig-cache to treat cpu-features as raw-bytes - add Stage2Target.cache_hash_len - add cache_mem(ch, ptr, len) - update call sites to use { ptr, len } --- src-self-hosted/stage2.zig | 5 ++++- src/cache_hash.cpp | 8 ++++++-- src/cache_hash.hpp | 1 + src/codegen.cpp | 4 ++-- src/stage2.cpp | 3 +++ src/stage2.h | 1 + 6 files changed, 17 insertions(+), 5 deletions(-) diff --git a/src-self-hosted/stage2.zig b/src-self-hosted/stage2.zig index bdd68925ee..83a70c29e0 100644 --- a/src-self-hosted/stage2.zig +++ b/src-self-hosted/stage2.zig @@ -900,6 +900,7 @@ const Stage2Target = extern struct { llvm_cpu_features: ?[*:0]const u8, cpu_builtin_str: ?[*:0]const u8, cache_hash: ?[*:0]const u8, + cache_hash_len: usize, os_builtin_str: ?[*:0]const u8, dynamic_linker: ?[*:0]const u8, @@ -1129,6 +1130,7 @@ const Stage2Target = extern struct { } }; + const cache_hash_slice = cache_hash.toOwnedSlice(); self.* = .{ .arch = @enumToInt(target.cpu.arch) + 1, // skip over ZigLLVM_UnknownArch .vendor = 0, @@ -1138,7 +1140,8 @@ const Stage2Target = extern struct { .llvm_cpu_features = llvm_features_buffer.toOwnedSlice().ptr, .cpu_builtin_str = cpu_builtin_str_buffer.toOwnedSlice().ptr, .os_builtin_str = os_builtin_str_buffer.toOwnedSlice().ptr, - .cache_hash = cache_hash.toOwnedSlice().ptr, + .cache_hash = cache_hash_slice.ptr, + .cache_hash_len = cache_hash_slice.len, .is_native = cross_target.isNative(), .glibc_or_darwin_version = glibc_or_darwin_version, .dynamic_linker = dynamic_linker, diff --git a/src/cache_hash.cpp b/src/cache_hash.cpp index 35b05a1ddf..3cff34ea5c 100644 --- a/src/cache_hash.cpp +++ b/src/cache_hash.cpp @@ -24,11 +24,15 @@ void cache_init(CacheHash *ch, Buf *manifest_dir) { ch->b64_digest = BUF_INIT; } -void cache_str(CacheHash *ch, const char *ptr) { +void cache_mem(CacheHash *ch, const char *ptr, size_t len) { assert(ch->manifest_file_path == nullptr); assert(ptr != nullptr); // + 1 to include the null byte - blake2b_update(&ch->blake, ptr, strlen(ptr) + 1); + blake2b_update(&ch->blake, ptr, len); +} + +void cache_str(CacheHash *ch, const char *ptr) { + cache_mem(ch, ptr, strlen(ptr) + 1); } void cache_int(CacheHash *ch, int x) { diff --git a/src/cache_hash.hpp b/src/cache_hash.hpp index e2a10270f3..9e4c41b1e0 100644 --- a/src/cache_hash.hpp +++ b/src/cache_hash.hpp @@ -35,6 +35,7 @@ struct CacheHash { void cache_init(CacheHash *ch, Buf *manifest_dir); // Next, use the hash population functions to add the initial parameters. +void cache_mem(CacheHash *ch, const char *ptr, size_t len); void cache_str(CacheHash *ch, const char *ptr); void cache_int(CacheHash *ch, int x); void cache_bool(CacheHash *ch, bool x); diff --git a/src/codegen.cpp b/src/codegen.cpp index d659e27d86..e692c7b805 100644 --- a/src/codegen.cpp +++ b/src/codegen.cpp @@ -8664,7 +8664,7 @@ static Error define_builtin_compile_vars(CodeGen *g) { cache_int(&cache_hash, g->zig_target->os); cache_int(&cache_hash, g->zig_target->abi); if (g->zig_target->cache_hash != nullptr) { - cache_str(&cache_hash, g->zig_target->cache_hash); + cache_mem(&cache_hash, g->zig_target->cache_hash, g->zig_target->cache_hash_len); } if (g->zig_target->glibc_or_darwin_version != nullptr) { cache_int(&cache_hash, g->zig_target->glibc_or_darwin_version->major); @@ -10309,7 +10309,7 @@ static Error check_cache(CodeGen *g, Buf *manifest_dir, Buf *digest) { cache_int(ch, g->zig_target->os); cache_int(ch, g->zig_target->abi); if (g->zig_target->cache_hash != nullptr) { - cache_str(ch, g->zig_target->cache_hash); + cache_mem(ch, g->zig_target->cache_hash, g->zig_target->cache_hash_len); } if (g->zig_target->glibc_or_darwin_version != nullptr) { cache_int(ch, g->zig_target->glibc_or_darwin_version->major); diff --git a/src/stage2.cpp b/src/stage2.cpp index 1f6cb2d6aa..afb7ebb548 100644 --- a/src/stage2.cpp +++ b/src/stage2.cpp @@ -251,9 +251,12 @@ Error stage2_target_parse(struct ZigTarget *target, const char *zig_triple, cons target->cache_hash = "\n\n"; } + target->cache_hash_len = strlen(target->cache_hash); + if (dynamic_linker != nullptr) { target->dynamic_linker = dynamic_linker; } + return ErrorNone; } diff --git a/src/stage2.h b/src/stage2.h index b73269f4e8..1ff0b5e826 100644 --- a/src/stage2.h +++ b/src/stage2.h @@ -293,6 +293,7 @@ struct ZigTarget { const char *llvm_cpu_features; const char *cpu_builtin_str; const char *cache_hash; + size_t cache_hash_len; const char *os_builtin_str; const char *dynamic_linker; };