- Ngôn ngữ Zig đang chuyển hướng sang triển khai trực tiếp các chức năng của libc bằng thư viện chuẩn Zig, đồng thời dần loại bỏ mã nguồn C hiện có
- Đến nay đã xóa khoảng 250 tệp mã nguồn C, và còn lại 2032 tệp
- Việc chuyển đổi này mang lại các hiệu quả như tăng tốc độ biên dịch, giảm kích thước cài đặt, và thu nhỏ kích thước binary khi liên kết tĩnh
- Với cải tiến gần đây, zig libc được tối ưu cùng với mã khác bên trong Zig Compilation Unit (ZCU) thay vì là một static archive riêng, nhờ đó có thể loại bỏ mã trùng lặp và tối ưu ở mức tương đương LTO
- Khi Zig chuyển sang vai trò nhà cung cấp static libc riêng, nếu phát sinh vấn đề liên quan thì cần gửi bug report trực tiếp cho dự án Zig
Tổng quan dự án Zig libc
- Nhiều cộng tác viên đang tham gia tiểu dự án zig libc để thay thế triển khai libc dựa trên C hiện có bằng các wrapper của thư viện chuẩn Zig
- Mục tiêu là loại bỏ mã C trùng lặp và cung cấp các hàm như
memcpy, atan2 dưới dạng ánh xạ đơn giản hoặc bọc các hàm phổ biến như strnlen
- Ví dụ, hàm
strnlen được triển khai bằng std.mem.findScalar của Zig
- Đến nay đã xóa khoảng 250 tệp mã nguồn C, còn lại 2032 tệp
Cải thiện về hiệu năng và kiến trúc
- Càng nhiều hàm được chuyển sang Zig thì sự phụ thuộc vào các dự án bên ngoài và ngôn ngữ C càng giảm
- Từ đó mang lại tốc độ biên dịch tốt hơn, đơn giản hóa và giảm kích thước cài đặt, đồng thời giảm kích thước binary của ứng dụng người dùng được liên kết tĩnh
- Thay đổi gần đây cho phép zig libc được biên dịch cùng mã Zig khác trong Zig Compilation Unit (ZCU)
- Không còn liên kết dưới dạng static archive riêng, mà tận dụng kiến trúc tích hợp giữa compiler và linker
- Nhờ đó có thể loại bỏ mã trùng lặp và tối ưu giữa các hàm
- Điều này tương tự link-time optimization (LTO), nhưng được thực hiện ở frontend thay vì giai đoạn linker
Khả năng mở rộng trong tương lai
- Khi kết hợp với các thay đổi gần đây của std.Io, có khả năng người dùng sẽ kiểm soát được hành vi I/O của libc
- Ví dụ: tích hợp các lệnh gọi
read, write vào vòng lặp sự kiện io_uring
- Có thể áp dụng chức năng phát hiện rò rỉ tài nguyên cả với mã C của bên thứ ba
- Tuy nhiên hiện tại đây mới chỉ là ý tưởng chưa được thử nghiệm
Kiểm thử và đảm bảo chất lượng
- Dự án libc-test của Szabolcs Nagy đã hỗ trợ rất nhiều trong việc ngăn hồi quy ở các hàm toán học
- Bộ kiểm thử này được dùng để xác minh độ chính xác của Zig libc
Hướng dẫn cho người dùng
- Zig đang chuyển sang giai đoạn tự cung cấp các chức năng của musl, mingw-w64, wasi-libc
- Nếu phát sinh vấn đề liên quan thì cần gửi bug report trực tiếp cho dự án Zig
- Điều này nhằm tránh việc các issue bị gửi nhầm cho maintainer của các dự án libc độc lập trước đây
Kết
- Câu cuối của bài viết kết thúc bằng “Abolish ICE” (không có giải thích bổ sung)
1 bình luận
Ý kiến Hacker News
250 tệp C đã bị xóa, và giờ còn lại 2032 tệp
Việc theo dõi quá trình Zig thay thế libc từ bên trong thực sự là một dự án khá phấn khích về lâu dài
Nhiều ngôn ngữ tuyên bố thay thế C, nhưng Zig gần như là ngôn ngữ duy nhất tích hợp tự nhiên C ABI và hệ thống build trong thực tế
Tính năng translate-c cũng hoạt động tốt đến mức đáng kinh ngạc
Thay vì cố giữ tương thích 99% như C++, tôi nghĩ lựa chọn giữ lại sự đơn giản của C trong khi tránh các cạm bẫy của ngôn ngữ là khôn ngoan hơn
Tôi tự hỏi liệu về lâu dài điều này có nghĩa là Zig sẽ không chạy được trên OpenBSD hay không
Vì OpenBSD chặn syscall trực tiếp và buộc chỉ được gọi thông qua libc
Có thể tham khảo chuỗi thảo luận này
Nếu dùng tùy chọn
-dynamic -lcthì các hàm libc của hệ thống đích sẽ được cung cấpCũng có những hệ thống như macOS chỉ hỗ trợ libc động, và theo tôi biết OpenBSD cũng hỗ trợ cả libc tĩnh
Đây là một thay đổi rất thú vị trong cách dự án Zig liên kết thư viện C
Nhưng tôi thắc mắc khi cross-compile chương trình C cho Windows dùng MinGW bằng Zig, liệu vẫn có thể liên kết tĩnh libc của MinGW hay không
Nếu chỉ định
-target x86_64-windows-gnu -lcthì một số hàm libc do Zig cung cấp, còn một số do vendored mingw-w64 cung cấpZig cung cấp mọi thứ mà không cần cài mingw-w64 riêng
Nếu muốn, bạn cũng có thể chỉ định trực tiếp libc bên ngoài bằng
--libc libc.txtĐây là một ý tưởng hay, nhưng tôi lo rằng có phải sẽ phải tiếp tục theo dõi các lỗ hổng CVE của glibc hay musl đối với phần mã đã được port hay không
Ở các đường mã dùng chung như toán học, thậm chí còn có thể giảm bớt lỗi tiềm ẩn
Có đoạn mô tả rằng “nó giống như bật LTO vượt qua ranh giới libc, nhưng được thực hiện đúng cách ở frontend thay vì linker”
Tôi tò mò vì sao đến giai đoạn linker lại là quá muộn, và liệu Zig có thể tối ưu nhiều hơn linker ở mức LLVM IR hay không
Vì với thư viện tĩnh đã được tối ưu sẵn thì các tối ưu kiểu này rất khó làm ở thời điểm liên kết
Khi kết hợp với thay đổi std.Io gần đây, thật thú vị khi người dùng có thể tự kiểm soát hành vi I/O của libc
Ví dụ như cho mọi lệnh gọi read/write tham gia vào vòng lặp sự kiện io_uring
Cá nhân tôi quan tâm đến phía kqueue hơn, nhưng có vẻ đoạn trích này cũng áp dụng được cho hướng đó
libc có nhiều phần đáng sợ, nhưng đây thực sự là một dự án rất thú vị
Ví dụ như "memfrob" hay "strfry", dù nói đùa thôi nhưng mấy thứ này chỉ có trong glibc :)
Tôi tự hỏi Rust có thứ gì như thế này không
Không phải để tranh luận Zig vs Rust, chỉ là tôi cũng muốn tạo một môi trường độc lập hơn trong các dự án Rust
Tôi tự hỏi có ai biết khi nào Zig sẽ đạt tới phiên bản 1.0 không
Tôi rất quan tâm đến ngôn ngữ này, nhưng vì nó vẫn còn thay đổi nhiều nên vẫn ngần ngại dùng cho dự án quan trọng
Dù vậy, các dự án production quy mô lớn như Bun, Ghostty, Tigerbeetle vẫn đang theo kịp khá tốt
Vì ngữ nghĩa của Zig đơn giản, nên khi nâng phiên bản thường chỉ cần cập nhật compiler và thực hiện vài chỉnh sửa mang tính cơ học
Thứ cản trở tôi chỉ là mức độ sẵn sàng chấp nhận của đồng nghiệp, nên trước mắt tôi đang làm những dự án mà một mình tôi có thể xây dựng
Tham khảo thêm thì video này có thể sẽ thú vị