self-hosted libc detection

* libc_installation.cpp is deleted.
   src-self-hosted/libc_installation.zig is now used for both stage1 and
   stage2 compilers.
 * (breaking) move `std.fs.File.access` to `std.fs.Dir.access`. The API
   now encourages use with an open directory handle.
 * Add `std.os.faccessat` and related functions.
 * Deprecate the "C" suffix naming convention for null-terminated
   parameters. "C" should be used when it is related to libc. However
   null-terminated parameters often have to do with the native system
   ABI rather than libc. "Z" suffix is the new convention. For example,
   `std.os.openC` is deprecated in favor of `std.os.openZ`.
 * Add `std.mem.dupeZ` for using an allocator to copy memory and add a
   null terminator.
 * Remove dead struct field `std.ChildProcess.llnode`.
 * Introduce `std.event.Batch`. This API allows expressing concurrency
   without forcing code to be async. It requires no Allocator and does
   not introduce any failure conditions. However it is not thread-safe.
 * There is now an ongoing experiment to transition away from
   `std.event.Group` in favor of `std.event.Batch`.
 * `std.os.execvpeC` calls `getenvZ` rather than `getenv`. This is
   slightly more efficient on most systems, and works around a
   limitation of `getenv` lack of integration with libc.
 * (breaking) `std.os.AccessError` gains `FileBusy`, `SymLinkLoop`, and
   `ReadOnlyFileSystem`. Previously these error codes were all reported
   as `PermissionDenied`.
 * Add `std.Target.isDragonFlyBSD`.
 * stage2: access to the windows_sdk functions is done with a manually
   maintained .zig binding file instead of `@cImport`.
 * Update src-self-hosted/libc_installation.zig with all the
   improvements that stage1 has seen to src/libc_installation.cpp until
   now. In addition, it now takes advantage of Batch so that evented I/O
   mode takes advantage of concurrency, but it still works in blocking
   I/O mode, which is how it is used in stage1.
This commit is contained in:
Andrew Kelley
2020-02-16 13:25:30 -05:00
parent 5e37fc0746
commit 4b02a39aa9
31 changed files with 930 additions and 1018 deletions

View File

@@ -8982,17 +8982,20 @@ static void detect_dynamic_linker(CodeGen *g) {
#if defined(ZIG_OS_LINUX)
{
Error err;
Buf *result = buf_alloc();
for (size_t i = 0; possible_ld_names[i] != NULL; i += 1) {
const char *lib_name = possible_ld_names[i];
if ((err = zig_libc_cc_print_file_name(lib_name, result, false, true))) {
char *result_ptr;
size_t result_len;
if ((err = stage2_libc_cc_print_file_name(&result_ptr, &result_len, lib_name, false))) {
if (err != ErrorCCompilerCannotFindFile && err != ErrorNoCCompilerInstalled) {
fprintf(stderr, "Unable to detect native dynamic linker: %s\n", err_str(err));
exit(1);
}
continue;
}
g->dynamic_linker_path = result;
g->dynamic_linker_path = buf_create_from_mem(result_ptr, result_len);
// Skips heap::c_allocator because the memory is allocated by stage2 library.
free(result_ptr);
return;
}
}
@@ -9028,16 +9031,16 @@ static void detect_libc(CodeGen *g) {
buf_ptr(g->zig_lib_dir), target_os_name(g->zig_target->os));
g->libc_include_dir_len = 4;
g->libc_include_dir_list = heap::c_allocator.allocate<Buf*>(g->libc_include_dir_len);
g->libc_include_dir_list[0] = arch_include_dir;
g->libc_include_dir_list[1] = generic_include_dir;
g->libc_include_dir_list[2] = arch_os_include_dir;
g->libc_include_dir_list[3] = generic_os_include_dir;
g->libc_include_dir_list = heap::c_allocator.allocate<const char*>(g->libc_include_dir_len);
g->libc_include_dir_list[0] = buf_ptr(arch_include_dir);
g->libc_include_dir_list[1] = buf_ptr(generic_include_dir);
g->libc_include_dir_list[2] = buf_ptr(arch_os_include_dir);
g->libc_include_dir_list[3] = buf_ptr(generic_os_include_dir);
return;
}
if (g->zig_target->is_native) {
g->libc = heap::c_allocator.create<ZigLibCInstallation>();
g->libc = heap::c_allocator.create<Stage2LibCInstallation>();
// search for native_libc.txt in following dirs:
// - LOCAL_CACHE_DIR
@@ -9082,8 +9085,8 @@ static void detect_libc(CodeGen *g) {
if (libc_txt == nullptr)
libc_txt = &global_libc_txt;
if ((err = zig_libc_parse(g->libc, libc_txt, g->zig_target, false))) {
if ((err = zig_libc_find_native(g->libc, true))) {
if ((err = stage2_libc_parse(g->libc, buf_ptr(libc_txt)))) {
if ((err = stage2_libc_find_native(g->libc))) {
fprintf(stderr,
"Unable to link against libc: Unable to find libc installation: %s\n"
"See `zig libc --help` for more details.\n", err_str(err));
@@ -9103,7 +9106,7 @@ static void detect_libc(CodeGen *g) {
fprintf(stderr, "Unable to open %s: %s\n", buf_ptr(native_libc_tmp), strerror(errno));
exit(1);
}
zig_libc_render(g->libc, file);
stage2_libc_render(g->libc, file);
if (fclose(file) != 0) {
fprintf(stderr, "Unable to save %s: %s\n", buf_ptr(native_libc_tmp), strerror(errno));
exit(1);
@@ -9113,27 +9116,28 @@ static void detect_libc(CodeGen *g) {
exit(1);
}
}
bool want_sys_dir = !buf_eql_buf(&g->libc->include_dir, &g->libc->sys_include_dir);
bool want_sys_dir = !mem_eql_mem(g->libc->include_dir, g->libc->include_dir_len,
g->libc->sys_include_dir, g->libc->sys_include_dir_len);
size_t want_um_and_shared_dirs = (g->zig_target->os == OsWindows) ? 2 : 0;
size_t dir_count = 1 + want_sys_dir + want_um_and_shared_dirs;
g->libc_include_dir_len = 0;
g->libc_include_dir_list = heap::c_allocator.allocate<Buf*>(dir_count);
g->libc_include_dir_list = heap::c_allocator.allocate<const char *>(dir_count);
g->libc_include_dir_list[g->libc_include_dir_len] = &g->libc->include_dir;
g->libc_include_dir_list[g->libc_include_dir_len] = g->libc->include_dir;
g->libc_include_dir_len += 1;
if (want_sys_dir) {
g->libc_include_dir_list[g->libc_include_dir_len] = &g->libc->sys_include_dir;
g->libc_include_dir_list[g->libc_include_dir_len] = g->libc->sys_include_dir;
g->libc_include_dir_len += 1;
}
if (want_um_and_shared_dirs != 0) {
g->libc_include_dir_list[g->libc_include_dir_len] = buf_sprintf("%s" OS_SEP ".." OS_SEP "um",
buf_ptr(&g->libc->include_dir));
g->libc_include_dir_list[g->libc_include_dir_len] = buf_ptr(buf_sprintf(
"%s" OS_SEP ".." OS_SEP "um", g->libc->include_dir));
g->libc_include_dir_len += 1;
g->libc_include_dir_list[g->libc_include_dir_len] = buf_sprintf("%s" OS_SEP ".." OS_SEP "shared",
buf_ptr(&g->libc->include_dir));
g->libc_include_dir_list[g->libc_include_dir_len] = buf_ptr(buf_sprintf(
"%s" OS_SEP ".." OS_SEP "shared", g->libc->include_dir));
g->libc_include_dir_len += 1;
}
assert(g->libc_include_dir_len == dir_count);
@@ -9208,9 +9212,9 @@ void add_cc_args(CodeGen *g, ZigList<const char *> &args, const char *out_dep_pa
args.append(buf_ptr(g->zig_c_headers_dir));
for (size_t i = 0; i < g->libc_include_dir_len; i += 1) {
Buf *include_dir = g->libc_include_dir_list[i];
const char *include_dir = g->libc_include_dir_list[i];
args.append("-isystem");
args.append(buf_ptr(include_dir));
args.append(include_dir);
}
if (g->zig_target->is_native) {
@@ -9666,7 +9670,7 @@ Error create_c_object_cache(CodeGen *g, CacheHash **out_cache_hash, bool verbose
cache_buf(cache_hash, compiler_id);
cache_int(cache_hash, g->err_color);
cache_buf(cache_hash, g->zig_c_headers_dir);
cache_list_of_buf(cache_hash, g->libc_include_dir_list, g->libc_include_dir_len);
cache_list_of_str(cache_hash, g->libc_include_dir_list, g->libc_include_dir_len);
cache_int(cache_hash, g->zig_target->is_native);
cache_int(cache_hash, g->zig_target->arch);
cache_int(cache_hash, g->zig_target->sub_arch);
@@ -10482,11 +10486,11 @@ static Error check_cache(CodeGen *g, Buf *manifest_dir, Buf *digest) {
cache_list_of_str(ch, g->lib_dirs.items, g->lib_dirs.length);
cache_list_of_str(ch, g->framework_dirs.items, g->framework_dirs.length);
if (g->libc) {
cache_buf(ch, &g->libc->include_dir);
cache_buf(ch, &g->libc->sys_include_dir);
cache_buf(ch, &g->libc->crt_dir);
cache_buf(ch, &g->libc->msvc_lib_dir);
cache_buf(ch, &g->libc->kernel32_lib_dir);
cache_str(ch, g->libc->include_dir);
cache_str(ch, g->libc->sys_include_dir);
cache_str(ch, g->libc->crt_dir);
cache_str(ch, g->libc->msvc_lib_dir);
cache_str(ch, g->libc->kernel32_lib_dir);
}
cache_buf_opt(ch, g->dynamic_linker_path);
cache_buf_opt(ch, g->version_script_path);
@@ -10765,7 +10769,7 @@ ZigPackage *codegen_create_package(CodeGen *g, const char *root_src_dir, const c
}
CodeGen *create_child_codegen(CodeGen *parent_gen, Buf *root_src_path, OutType out_type,
ZigLibCInstallation *libc, const char *name, Stage2ProgressNode *parent_progress_node)
Stage2LibCInstallation *libc, const char *name, Stage2ProgressNode *parent_progress_node)
{
Stage2ProgressNode *child_progress_node = stage2_progress_start(
parent_progress_node ? parent_progress_node : parent_gen->sub_progress_node,
@@ -10804,7 +10808,7 @@ CodeGen *create_child_codegen(CodeGen *parent_gen, Buf *root_src_path, OutType o
CodeGen *codegen_create(Buf *main_pkg_path, Buf *root_src_path, const ZigTarget *target,
OutType out_type, BuildMode build_mode, Buf *override_lib_dir,
ZigLibCInstallation *libc, Buf *cache_dir, bool is_test_build, Stage2ProgressNode *progress_node)
Stage2LibCInstallation *libc, Buf *cache_dir, bool is_test_build, Stage2ProgressNode *progress_node)
{
CodeGen *g = heap::c_allocator.create<CodeGen>();
g->pass1_arena = heap::ArenaAllocator::construct(&heap::c_allocator, &heap::c_allocator, "pass1");