82 Commits

Author SHA1 Message Date
Andrew Kelley
f60c24c73c
Merge pull request #19155 from ianic/tar_max_file_size
std.tar: error on insufficient buffers provided to iterator
2024-03-11 17:03:44 -07:00
Igor Anić
f8f43ca3e1 package: remove git fetch zlib lookahead fix
My first zlib implementation broke git fetch because it introduce
[lookahead](https://github.com/ziglang/zig/issues/18967). That resulted
in workarounds [1](80f3ef6e14)
[2](d00faa2407)

After [fixing](https://github.com/ziglang/zig/pull/19163) lookahead in
zlib decompressor this fixes are no longer necessary.
2024-03-11 16:49:21 -07:00
Tristan Ross
9d70d614ae
std.builtin: make link mode fields lowercase 2024-03-11 07:09:10 -07:00
Igor Anić
0cca7e732e std.tar: fix broken public interface 2024-03-11 12:25:51 +01:00
mlugg
38331b1cab
Package.Module: actually set File.path_digest for builtin modules 2024-03-07 06:26:25 +00:00
mlugg
b41a0b4768
Package.Module: deduplicate identical builtin modules
Previously, when multiple modules had builtin modules with identical
sources, two distinct `Module`s and `File`s were created pointing at the
same file path. This led to a bug later in the frontend. These modules
are now deduplicated with a simple hashmap on the builtin source.
2024-03-06 21:26:39 +00:00
Andrew Kelley
d661f0f35b compiler: JIT zig fmt
See #19063
2024-02-26 22:26:19 -07:00
Andrew Kelley
08e886b8fe package management: fix regression of printing expected hash
Regressed in ed4ccea7bae99c1baa634716941f308d9f922985. The early exit
path was only supposed to happen in case of --system mode.
2024-02-25 09:27:39 -08:00
Andrew Kelley
c44a902836 fix zstd compilation errors from previous commit 2024-02-23 02:37:11 -07:00
dweiller
ac1b957e79 std.compress.zstd: remove allocation from DecompressStream 2024-02-23 02:37:11 -07:00
Andrew Kelley
99a5de9dbb git fetching: fix redirect handling
I mistakenly thought this was dead code in an earlier commit in this
branch. This commit restores the proper behavior.
2024-02-23 02:37:11 -07:00
Andrew Kelley
4d401e6159 std.http: remove Headers API
I originally removed these in 402f967ed5339fa3d828b7fe1d57cdb5bf38dbf2.
I allowed them to be added back in #15299 because they were smuggled in
alongside a bug fix, however, I wasn't kidding when I said that I wanted
to take the design of std.http in a different direction than using this
data structure.

Instead, some headers are provided via explicit field names populated
while parsing the HTTP request/response, and some are provided via
new fields that support passing extra, arbitrary headers.

This resulted in simplification of logic in many places, as well as
elimination of the possibility of failure in many places. There is
less deinitialization code happening now.

Furthermore, it made it no longer necessary to clone the headers data
structure in order to handle redirects.

http_proxy and https_proxy fields are now pointers since it is common
for them to be unpopulated.

loadDefaultProxies is changed into initDefaultProxies to communicate
that it does not actually load anything from disk or from the network.
The function now is leaky; the API user must pass an already
instantiated arena allocator. Removes the need to deinitialize proxies.

Before, proxies stored arbitrary sets of headers. Now they only store
the authorization value.

Removed the duplicated code between https_proxy and http_proxy. Finally,
parsing failures of the environment variables result in errors being
emitted rather than silently ignoring the proxy.

error.CompressionNotSupported is renamed to
error.CompressionUnsupported, matching the naming convention from all
the other errors in the same set.

Removed documentation comments that were redundant with field and type
names.

Disabling zstd decompression in the server for now; see #18937.

I found some apparently dead code in src/Package/Fetch/git.zig. I want
to check with Ian about this.

I discovered that test/standalone/http.zig is dead code, it is only
being compiled but not being run. Furthermore it hangs at the end if you
run it manually. The previous commits in this branch were written under
the assumption that this test was being run with
`zig build test-standalone`.
2024-02-23 02:37:11 -07:00
Andrew Kelley
90bd4f226e std.http: remove the ability to heap-allocate headers
The buffer for HTTP headers is now always provided via a static buffer.
As a consequence, OutOfMemory is no longer a member of the read() error
set, and the API and implementation of Client and Server are simplified.

error.HttpHeadersExceededSizeLimit is renamed to
error.HttpHeadersOversize.
2024-02-23 02:37:10 -07:00
Igor Anić
a5326c5ef8 return few previous fixes
Review: https://github.com/ziglang/zig/pull/19032#pullrequestreview-1896251841
2024-02-22 17:20:41 +01:00
Igor Anić
d00faa2407 use BufferedTee in Fetch/git.zig 2024-02-22 15:18:03 +01:00
Ian Johnson
80f3ef6e14 Package.Fetch: fix Git package fetching
This commit works around #18967 by adding an `AccumulatingReader`, which
accumulates data read from the underlying packfile, and by keeping track
of the position in the packfile and hash/checksum information separately
rather than using reader composition. That is, the packfile position and
hashes/checksums are updated with the accumulated read history data only
after we can determine what data has actually been used by the
decompressor rather than merely being buffered.

The only addition to the standard library APIs to support this change is
the `unreadBytes` function in `std.compress.flate.Inflate`, which allows
the user to determine how many bytes have been read only for buffering
and not used as part of compressed data.

These changes can be reverted if #18967 is resolved with a decompressor
that reads precisely only the number of bytes needed for decompression.
2024-02-19 13:43:32 -08:00
Igor Anić
d645114f7e add deflate implemented from first principles
Zig deflate compression/decompression implementation. It supports compression and decompression of gzip, zlib and raw deflate format.

Fixes #18062.

This PR replaces current compress/gzip and compress/zlib packages. Deflate package is renamed to flate. Flate is common name for deflate/inflate where deflate is compression and inflate decompression.

There are breaking change. Methods signatures are changed because of removal of the allocator, and I also unified API for all three namespaces (flate, gzip, zlib).

Currently I put old packages under v1 namespace they are still available as compress/v1/gzip, compress/v1/zlib, compress/v1/deflate. Idea is to give users of the current API little time to postpone analyzing what they had to change. Although that rises question when it is safe to remove that v1 namespace.

Here is current API in the compress package:

```Zig
// deflate
    fn compressor(allocator, writer, options) !Compressor(@TypeOf(writer))
    fn Compressor(comptime WriterType) type

    fn decompressor(allocator, reader, null) !Decompressor(@TypeOf(reader))
    fn Decompressor(comptime ReaderType: type) type

// gzip
    fn compress(allocator, writer, options) !Compress(@TypeOf(writer))
    fn Compress(comptime WriterType: type) type

    fn decompress(allocator, reader) !Decompress(@TypeOf(reader))
    fn Decompress(comptime ReaderType: type) type

// zlib
    fn compressStream(allocator, writer, options) !CompressStream(@TypeOf(writer))
    fn CompressStream(comptime WriterType: type) type

    fn decompressStream(allocator, reader) !DecompressStream(@TypeOf(reader))
    fn DecompressStream(comptime ReaderType: type) type

// xz
   fn decompress(allocator: Allocator, reader: anytype) !Decompress(@TypeOf(reader))
   fn Decompress(comptime ReaderType: type) type

// lzma
    fn decompress(allocator, reader) !Decompress(@TypeOf(reader))
    fn Decompress(comptime ReaderType: type) type

// lzma2
    fn decompress(allocator, reader, writer !void

// zstandard:
    fn DecompressStream(ReaderType, options) type
    fn decompressStream(allocator, reader) DecompressStream(@TypeOf(reader), .{})
    struct decompress
```

The proposed naming convention:
 - Compressor/Decompressor for functions which return type, like Reader/Writer/GeneralPurposeAllocator
 - compressor/compressor for functions which are initializers for that type, like reader/writer/allocator
 - compress/decompress for one shot operations, accepts reader/writer pair, like read/write/alloc

```Zig
/// Compress from reader and write compressed data to the writer.
fn compress(reader: anytype, writer: anytype, options: Options) !void

/// Create Compressor which outputs the writer.
fn compressor(writer: anytype, options: Options) !Compressor(@TypeOf(writer))

/// Compressor type
fn Compressor(comptime WriterType: type) type

/// Decompress from reader and write plain data to the writer.
fn decompress(reader: anytype, writer: anytype) !void

/// Create Decompressor which reads from reader.
fn decompressor(reader: anytype) Decompressor(@TypeOf(reader)

/// Decompressor type
fn Decompressor(comptime ReaderType: type) type

```

Comparing this implementation with the one we currently have in Zig's standard library (std).
Std is roughly 1.2-1.4 times slower in decompression, and 1.1-1.2 times slower in compression. Compressed sizes are pretty much same in both cases.
More resutls in [this](https://github.com/ianic/flate) repo.

This library uses static allocations for all structures, doesn't require allocator. That makes sense especially for deflate where all structures, internal buffers are allocated to the full size. Little less for inflate where we std version uses less memory by not preallocating to theoretical max size array which are usually not fully used.

For deflate this library allocates 395K while std 779K.
For inflate this library allocates 74.5K while std around 36K.

Inflate difference is because we here use 64K history instead of 32K in std.

If merged existing usage of compress gzip/zlib/deflate need some changes. Here is example with necessary changes in comments:

```Zig

const std = @import("std");

// To get this file:
// wget -nc -O war_and_peace.txt https://www.gutenberg.org/ebooks/2600.txt.utf-8
const data = @embedFile("war_and_peace.txt");

pub fn main() !void {
    var gpa = std.heap.GeneralPurposeAllocator(.{}){};
    defer std.debug.assert(gpa.deinit() == .ok);
    const allocator = gpa.allocator();

    try oldDeflate(allocator);
    try new(std.compress.flate, allocator);

    try oldZlib(allocator);
    try new(std.compress.zlib, allocator);

    try oldGzip(allocator);
    try new(std.compress.gzip, allocator);
}

pub fn new(comptime pkg: type, allocator: std.mem.Allocator) !void {
    var buf = std.ArrayList(u8).init(allocator);
    defer buf.deinit();

    // Compressor
    var cmp = try pkg.compressor(buf.writer(), .{});
    _ = try cmp.write(data);
    try cmp.finish();

    var fbs = std.io.fixedBufferStream(buf.items);
    // Decompressor
    var dcp = pkg.decompressor(fbs.reader());

    const plain = try dcp.reader().readAllAlloc(allocator, std.math.maxInt(usize));
    defer allocator.free(plain);
    try std.testing.expectEqualSlices(u8, data, plain);
}

pub fn oldDeflate(allocator: std.mem.Allocator) !void {
    const deflate = std.compress.v1.deflate;

    // Compressor
    var buf = std.ArrayList(u8).init(allocator);
    defer buf.deinit();
    // Remove allocator
    // Rename deflate -> flate
    var cmp = try deflate.compressor(allocator, buf.writer(), .{});
    _ = try cmp.write(data);
    try cmp.close(); // Rename to finish
    cmp.deinit(); // Remove

    // Decompressor
    var fbs = std.io.fixedBufferStream(buf.items);
    // Remove allocator and last param
    // Rename deflate -> flate
    // Remove try
    var dcp = try deflate.decompressor(allocator, fbs.reader(), null);
    defer dcp.deinit(); // Remove

    const plain = try dcp.reader().readAllAlloc(allocator, std.math.maxInt(usize));
    defer allocator.free(plain);
    try std.testing.expectEqualSlices(u8, data, plain);
}

pub fn oldZlib(allocator: std.mem.Allocator) !void {
    const zlib = std.compress.v1.zlib;

    var buf = std.ArrayList(u8).init(allocator);
    defer buf.deinit();

    // Compressor
    // Rename compressStream => compressor
    // Remove allocator
    var cmp = try zlib.compressStream(allocator, buf.writer(), .{});
    _ = try cmp.write(data);
    try cmp.finish();
    cmp.deinit(); // Remove

    var fbs = std.io.fixedBufferStream(buf.items);
    // Decompressor
    // decompressStream => decompressor
    // Remove allocator
    // Remove try
    var dcp = try zlib.decompressStream(allocator, fbs.reader());
    defer dcp.deinit(); // Remove

    const plain = try dcp.reader().readAllAlloc(allocator, std.math.maxInt(usize));
    defer allocator.free(plain);
    try std.testing.expectEqualSlices(u8, data, plain);
}

pub fn oldGzip(allocator: std.mem.Allocator) !void {
    const gzip = std.compress.v1.gzip;

    var buf = std.ArrayList(u8).init(allocator);
    defer buf.deinit();

    // Compressor
    // Rename compress => compressor
    // Remove allocator
    var cmp = try gzip.compress(allocator, buf.writer(), .{});
    _ = try cmp.write(data);
    try cmp.close(); // Rename to finisho
    cmp.deinit(); // Remove

    var fbs = std.io.fixedBufferStream(buf.items);
    // Decompressor
    // Rename decompress => decompressor
    // Remove allocator
    // Remove try
    var dcp = try gzip.decompress(allocator, fbs.reader());
    defer dcp.deinit(); // Remove

    const plain = try dcp.reader().readAllAlloc(allocator, std.math.maxInt(usize));
    defer allocator.free(plain);
    try std.testing.expectEqualSlices(u8, data, plain);
}

```
2024-02-14 18:28:20 +01:00
Andrew Kelley
54bbc73f85
Merge pull request #18712 from Vexu/std.options
std: make options a struct instance instead of a namespace
2024-02-09 13:38:42 -08:00
Andrew Kelley
d753c3a121 CLI: implement 'zig build' lazy dependency fetching
This makes `zig build` notice when lazy dependencies were missing, fetch
them, and then rebuild the build runner and run it again.
2024-02-02 20:43:01 -07:00
Andrew Kelley
252f4ab2a5 build system: implement lazy dependencies, part 1
Build manifest files support `lazy: true` for dependency sections.
This causes the auto-generated dependencies.zig to have 2 more
possibilities:
1. It communicates whether a dependency is lazy or not.
2. The dependency might be acknowledged, but missing due to being lazy
   and not fetched.

Lazy dependencies are not fetched by default, but if they are already
fetched then they are provided to the build script.

The build runner reports the set of missing lazy dependenices that are
required to the parent process via stdout and indicates the situation
with exit code 3.

std.Build now has a `lazyDependency` function. I'll let the doc comments
speak for themselves:

When this function is called, it means that the current build does, in
fact, require this dependency. If the dependency is already fetched, it
proceeds in the same manner as `dependency`. However if the dependency
was not fetched, then when the build script is finished running, the
build will not proceed to the make phase. Instead, the parent process
will additionally fetch all the lazy dependencies that were actually
required by running the build script, rebuild the build script, and then
run it again.
In other words, if this function returns `null` it means that the only
purpose of completing the configure phase is to find out all the other
lazy dependencies that are also required.
It is allowed to use this function for non-lazy dependencies, in which
case it will never return `null`. This allows toggling laziness via
build.zig.zon without changing build.zig logic.

The CLI for `zig build` detects this situation, but the logic for then
redoing the build process with these extra dependencies fetched is not
yet implemented.
2024-02-02 20:43:01 -07:00
Andrew Kelley
ed4ccea7ba build system: implement --system [dir]
This prevents package fetching and enables system_package_mode in the
build system which flips the defaults for system integrations.
2024-02-02 20:43:01 -07:00
Veikka Tuominen
a4f27e8987 remove std.io.Mode 2024-02-01 15:22:36 +02:00
Krzysztof Wolicki
14efbbfd89
std.Uri: change specifier for printing with scheme to semicolon ;
Fetch: print scheme when suggesting adding a ref to git URIs
2024-01-18 09:13:04 +02:00
cipharius
2e77956629 Accepts generic application/x-compressed in package fetch 2024-01-15 18:26:12 +02:00
Joel Gustafson
dbdee2d53c
ignore charset and boundary directives in content-type headers when fetching dependencies 2024-01-09 20:16:59 +00:00
Andrew Kelley
196ddf010c frontend: fix populateTestFunctions accessing the wrong module
The test runner reads the list of test function pointers from its own
builtin module, which is the root_mod, not main_mod.
2024-01-01 19:49:08 -07:00
Andrew Kelley
edccd68adf Package.Module: fix typo in default red-zone setting
oops, this was supposed to return true, not false.
2024-01-01 17:51:21 -07:00
Andrew Kelley
f256431838 fix compilation errors when enabling llvm 2024-01-01 17:51:20 -07:00
Andrew Kelley
0be97b5ae3 fix population of builtin.zig not making the parent dir 2024-01-01 17:51:20 -07:00
Andrew Kelley
a1236b32f9 libcxx: update to new Compilation API 2024-01-01 17:51:19 -07:00
Andrew Kelley
2596f5d925 update bin_file.options references in Sema
mainly pertaining to error return tracing
2024-01-01 17:51:19 -07:00
Andrew Kelley
f54471b54c compiler: miscellaneous branch progress
implement builtin.zig file population for all modules rather than
assuming there is only one global builtin.zig module.

move some fields from link.File to Compilation
move some fields from Module to Compilation

compute debug_format in global Compilation config resolution

wire up C compilation to the concept of owner modules

make whole cache mode call link.File.createEmpty() instead of
link.File.open()
2024-01-01 17:51:19 -07:00
Andrew Kelley
33cdf33b95 compiler: update many references to bin_file.options 2024-01-01 17:51:19 -07:00
Andrew Kelley
43720be04a frontend: fix stack protector option logic
Commit 97e23896a9168132b6d36ca22ae1af10dd53d80d regressed this behavior
because it made target_util.supportsStackProtector *correctly*
notice which zig backend is being used to generate code, while the
logic calling that function *incorrectly assumed* that .zig code is being
compiled, when in reality it might be only C code being compiled.

This commit adjusts the option resolution logic for stack protector so
that it takes into account the zig backend only if there is a zig
compilation unit. A separate piece of logic checks whether clang
supports stack protector for a given target.

closes #18009
closes #18114
closes #18254
2024-01-01 17:51:19 -07:00
Andrew Kelley
12de7e3472 WIP: move many global settings to become per-Module
Much of the logic from Compilation.create() is extracted into
Compilation.Config.resolve() which accepts many optional settings and
produces concrete settings. This separate step is needed by API users of
Compilation so that they can pass the resolved global settings to the
Module creation function, which itself needs to resolve per-Module
settings.

Since the target and other things are no longer global settings, I did
not want them stored in link.File (in the `options` field). That options
field was already a kludge; those options should be resolved into
concrete settings. This commit also starts to work on that, deleting
link.Options, moving the fields into Compilation and
ObjectFormat-specific structs instead. Some fields were ephemeral and
should not have been stored at all, such as symbol_size_hint.

The link.File object of Compilation is now a `?*link.File` and `null`
when -fno-emit-bin is passed. It is now arena-allocated along with
Compilation itself, avoiding some messy cleanup code that was there
before.

On the command line, it is now possible to configure the standard
library itself by using `--mod std` just like any other module. This
meant that the CLI needed to create the standard library module rather
than having Compilation create it.

There are a lot of changes in this commit and it's still not done. I
didn't realize how quickly this changeset was going to balloon out of
control, and there are still many lines that need to be changed before
it even compiles successfully.

* introduce std.Build.Cache.HashHelper.oneShot
* add error_tracing to std.Build.Module
* extract build.zig file generation into src/Builtin.zig
* each CSourceFile and RcSourceFile now has a Module owner, which
  determines some of the C compiler flags.
2024-01-01 17:51:18 -07:00
Jacob Young
3f2a65594e Compilation: cleanup hashmap usage 2024-01-01 13:38:30 -08:00
Andrew Kelley
2a32264533 package fetching: catch relative paths that resolve into cache dir
The logic here already caught the case when a dependency path tried to
escape out of the zig cache directory using up directories. However, it
did not catch the case when the relative path tried to reach into a
different path within the zig-cache. For example, if it asked for
"../../../blah" then it would be caught, but if it asked for "../blah"
then it would try to resolve as "zig-cache/p/blah" and probably result
in file-not-found, or perhaps resolve to a different package if someone
inadvertently used a valid package hash instead of "blah".

Now it correctly gives a "dependency path outside project" error,
however, still allows relative paths with up-dirs that were not fetched
via URL.
2023-11-28 04:14:41 -05:00
Andrew Kelley
a0c8d54823 add Package.Manifest.copyErrorsIntoBundle 2023-11-26 19:41:00 -07:00
Andrew Kelley
e357550610 update for the std.fs.Dir changes 2023-11-22 15:24:57 -07:00
mlugg
b355893438
compiler: correct unnecessary uses of 'var' 2023-11-19 11:11:49 +00:00
Ian Johnson
7048e93665 Package.Fetch.git: handle optional pkt-line LF
Addresses a comment in #17779 pointing out the inability to fetch the
upstream BoringSSL sources over Git. The reason for this is because the
Git server used in this case did not include the optional (but
recommended) LF terminator for textual pkt-line data. This commit
adjusts handling of textual pkt-line data so that it works both with and
without the optional trailing LF.
2023-11-12 05:11:23 -05:00
Andrew Kelley
3fc6fc6812 std.builtin.Endian: make the tags lower case
Let's take this breaking change opportunity to fix the style of this
enum.
2023-10-31 21:37:35 -04:00
Jacob Young
d890e81761 mem: fix ub in writeInt
Use inline to vastly simplify the exposed API.  This allows a
comptime-known endian parameter to be propogated, making extra functions
for a specific endianness completely unnecessary.
2023-10-31 21:37:35 -04:00
Tobias Simetsreiter
d1230842ac add Fetch support for short compressed tar ext
these short extensions are common in a lot of
places, and should be treated like their double
versions
2023-10-24 13:49:28 -04:00
Nameless
363d0ee5e1
std.http: rename start->send and request->open to be more inline with operation 2023-10-21 20:52:59 -05:00
Andrew Kelley
777af14b57 Package.Manifest: fix bitrotted unit tests 2023-10-18 18:59:13 -07:00
DraagrenKirneh
1882ff95e7 Package.Manifest: add minimum_zig_version field 2023-10-18 18:58:58 -07:00
dweiller
f58811a58a package fetching: support .tar.zst archives 2023-10-17 19:02:00 -04:00
Andrew Kelley
ba656e5c9f zig fetch: add --debug-hash argument
This argument causes zig to print verbose hashing information to stdout,
which can be used to diff two different fetches and find out why the
hashes do not equal each other.
2023-10-16 18:15:47 -07:00
Andrew Kelley
b171a6f25d Package.Fetch: normalize path separators in symlinks
closes #17549
2023-10-16 16:47:47 -07:00