| author | |
| committer | |
| log | 9dcddc2249217c8c99c9d07bb0187904847d2ae2 |
| tree | 1edf9eddb4d9353a5778c86c69366de963ea7eeb |
| parent | 92e781baa147a7d07af4cb3c1f08c08bed8613e4 |
| signature |
closes #275926 files changed, 259 insertions(+), 281 deletions(-)
build.zig+1-1| ... | ... | @@ -134,7 +134,7 @@ pub fn build(b: *Builder) !void { |
| 134 | 134 | test_step.dependOn(tests.addPkgTests(b, test_filter, "std/special/compiler_rt.zig", "compiler-rt", "Run the compiler_rt tests", modes, skip_non_native)); |
| 135 | 135 | |
| 136 | 136 | test_step.dependOn(tests.addCompareOutputTests(b, test_filter, modes)); |
| 137 | test_step.dependOn(tests.addBuildExampleTests(b, test_filter, modes)); | |
| 137 | test_step.dependOn(tests.addStandaloneTests(b, test_filter, modes)); | |
| 138 | 138 | test_step.dependOn(tests.addCliTests(b, test_filter, modes)); |
| 139 | 139 | test_step.dependOn(tests.addCompileErrorTests(b, test_filter, modes)); |
| 140 | 140 | test_step.dependOn(tests.addAssembleAndLinkTests(b, test_filter, modes)); |
example/README.md deleted-14| ... | ... | @@ -1,14 +0,0 @@ |
| 1 | # Zig Examples | |
| 2 | ||
| 3 | * **Tetris** - A simple Tetris clone written in Zig. See | |
| 4 | [andrewrk/tetris](https://github.com/andrewrk/tetris). | |
| 5 | * **hello_world** - demonstration of a printing a single line to stdout. | |
| 6 | One version depends on libc; one does not. | |
| 7 | * **guess_number** - simple console game where you guess the number the | |
| 8 | computer is thinking of and it says higher or lower. No dependency on | |
| 9 | libc. | |
| 10 | * **cat** - implementation of the `cat` UNIX utility in Zig, with no dependency | |
| 11 | on libc. | |
| 12 | * **shared_library** - demonstration of building a shared library and generating | |
| 13 | a header file for interop with C code. | |
| 14 | * **mix_o_files** - how to mix .zig and .c files together as object files |
example/cat/main.zig deleted-70| ... | ... | @@ -1,70 +0,0 @@ |
| 1 | const std = @import("std"); | |
| 2 | const io = std.io; | |
| 3 | const process = std.process; | |
| 4 | const File = std.fs.File; | |
| 5 | const mem = std.mem; | |
| 6 | const warn = std.debug.warn; | |
| 7 | const allocator = std.debug.global_allocator; | |
| 8 | ||
| 9 | pub fn main() !void { | |
| 10 | var args_it = process.args(); | |
| 11 | const exe = try unwrapArg(args_it.next(allocator).?); | |
| 12 | var catted_anything = false; | |
| 13 | var stdout_file = try io.getStdOut(); | |
| 14 | ||
| 15 | while (args_it.next(allocator)) |arg_or_err| { | |
| 16 | const arg = try unwrapArg(arg_or_err); | |
| 17 | if (mem.eql(u8, arg, "-")) { | |
| 18 | catted_anything = true; | |
| 19 | var stdin_file = try io.getStdIn(); | |
| 20 | try cat_file(&stdout_file, &stdin_file); | |
| 21 | } else if (arg[0] == '-') { | |
| 22 | return usage(exe); | |
| 23 | } else { | |
| 24 | var file = File.openRead(arg) catch |err| { | |
| 25 | warn("Unable to open file: {}\n", @errorName(err)); | |
| 26 | return err; | |
| 27 | }; | |
| 28 | defer file.close(); | |
| 29 | ||
| 30 | catted_anything = true; | |
| 31 | try cat_file(&stdout_file, &file); | |
| 32 | } | |
| 33 | } | |
| 34 | if (!catted_anything) { | |
| 35 | var stdin_file = try io.getStdIn(); | |
| 36 | try cat_file(&stdout_file, &stdin_file); | |
| 37 | } | |
| 38 | } | |
| 39 | ||
| 40 | fn usage(exe: []const u8) !void { | |
| 41 | warn("Usage: {} [FILE]...\n", exe); | |
| 42 | return error.Invalid; | |
| 43 | } | |
| 44 | ||
| 45 | fn cat_file(stdout: *File, file: *File) !void { | |
| 46 | var buf: [1024 * 4]u8 = undefined; | |
| 47 | ||
| 48 | while (true) { | |
| 49 | const bytes_read = file.read(buf[0..]) catch |err| { | |
| 50 | warn("Unable to read from stream: {}\n", @errorName(err)); | |
| 51 | return err; | |
| 52 | }; | |
| 53 | ||
| 54 | if (bytes_read == 0) { | |
| 55 | break; | |
| 56 | } | |
| 57 | ||
| 58 | stdout.write(buf[0..bytes_read]) catch |err| { | |
| 59 | warn("Unable to write to stdout: {}\n", @errorName(err)); | |
| 60 | return err; | |
| 61 | }; | |
| 62 | } | |
| 63 | } | |
| 64 | ||
| 65 | fn unwrapArg(arg: anyerror![]u8) ![]u8 { | |
| 66 | return arg catch |err| { | |
| 67 | warn("Unable to parse command line: {}\n", err); | |
| 68 | return err; | |
| 69 | }; | |
| 70 | } |
example/guess_number/main.zig deleted-47| ... | ... | @@ -1,47 +0,0 @@ |
| 1 | const builtin = @import("builtin"); | |
| 2 | const std = @import("std"); | |
| 3 | const io = std.io; | |
| 4 | const fmt = std.fmt; | |
| 5 | ||
| 6 | pub fn main() !void { | |
| 7 | var stdout_file = try io.getStdOut(); | |
| 8 | const stdout = &stdout_file.outStream().stream; | |
| 9 | ||
| 10 | try stdout.print("Welcome to the Guess Number Game in Zig.\n"); | |
| 11 | ||
| 12 | var seed_bytes: [@sizeOf(u64)]u8 = undefined; | |
| 13 | std.crypto.randomBytes(seed_bytes[0..]) catch |err| { | |
| 14 | std.debug.warn("unable to seed random number generator: {}", err); | |
| 15 | return err; | |
| 16 | }; | |
| 17 | const seed = std.mem.readIntNative(u64, &seed_bytes); | |
| 18 | var prng = std.rand.DefaultPrng.init(seed); | |
| 19 | ||
| 20 | const answer = prng.random.range(u8, 0, 100) + 1; | |
| 21 | ||
| 22 | while (true) { | |
| 23 | try stdout.print("\nGuess a number between 1 and 100: "); | |
| 24 | var line_buf: [20]u8 = undefined; | |
| 25 | ||
| 26 | const line = io.readLineSlice(line_buf[0..]) catch |err| switch (err) { | |
| 27 | error.OutOfMemory => { | |
| 28 | try stdout.print("Input too long.\n"); | |
| 29 | continue; | |
| 30 | }, | |
| 31 | else => return err, | |
| 32 | }; | |
| 33 | ||
| 34 | const guess = fmt.parseUnsigned(u8, line, 10) catch { | |
| 35 | try stdout.print("Invalid number.\n"); | |
| 36 | continue; | |
| 37 | }; | |
| 38 | if (guess > answer) { | |
| 39 | try stdout.print("Guess lower.\n"); | |
| 40 | } else if (guess < answer) { | |
| 41 | try stdout.print("Guess higher.\n"); | |
| 42 | } else { | |
| 43 | try stdout.print("You win!\n"); | |
| 44 | return; | |
| 45 | } | |
| 46 | } | |
| 47 | } |
example/hello_world/hello.zig deleted-9| ... | ... | @@ -1,9 +0,0 @@ |
| 1 | const std = @import("std"); | |
| 2 | ||
| 3 | pub fn main() !void { | |
| 4 | // If this program is run without stdout attached, exit with an error. | |
| 5 | const stdout_file = try std.io.getStdOut(); | |
| 6 | // If this program encounters pipe failure when printing to stdout, exit | |
| 7 | // with an error. | |
| 8 | try stdout_file.write("Hello, world!\n"); | |
| 9 | } |
example/hello_world/hello_libc.zig deleted-13| ... | ... | @@ -1,13 +0,0 @@ |
| 1 | const c = @cImport({ | |
| 2 | // See https://github.com/ziglang/zig/issues/515 | |
| 3 | @cDefine("_NO_CRT_STDIO_INLINE", "1"); | |
| 4 | @cInclude("stdio.h"); | |
| 5 | @cInclude("string.h"); | |
| 6 | }); | |
| 7 | ||
| 8 | const msg = c"Hello, world!\n"; | |
| 9 | ||
| 10 | export fn main(argc: c_int, argv: **u8) c_int { | |
| 11 | if (c.printf(msg) != @intCast(c_int, c.strlen(msg))) return -1; | |
| 12 | return 0; | |
| 13 | } |
example/hello_world/hello_windows.zig deleted-8| ... | ... | @@ -1,8 +0,0 @@ |
| 1 | use @import("std").os.windows; | |
| 2 | ||
| 3 | extern "user32" stdcallcc fn MessageBoxA(hWnd: ?HANDLE, lpText: ?LPCTSTR, lpCaption: ?LPCTSTR, uType: UINT) c_int; | |
| 4 | ||
| 5 | export fn WinMain(hInstance: HINSTANCE, hPrevInstance: HINSTANCE, lpCmdLine: PWSTR, nCmdShow: INT) INT { | |
| 6 | _ = MessageBoxA(null, c"hello", c"title", 0); | |
| 7 | return 0; | |
| 8 | } |
example/mix_o_files/base64.zig deleted-13| ... | ... | @@ -1,13 +0,0 @@ |
| 1 | const base64 = @import("std").base64; | |
| 2 | ||
| 3 | export fn decode_base_64(dest_ptr: [*]u8, dest_len: usize, source_ptr: [*]const u8, source_len: usize) usize { | |
| 4 | const src = source_ptr[0..source_len]; | |
| 5 | const dest = dest_ptr[0..dest_len]; | |
| 6 | const base64_decoder = base64.standard_decoder_unsafe; | |
| 7 | const decoded_size = base64_decoder.calcSize(src); | |
| 8 | base64_decoder.decode(dest[0..decoded_size], src); | |
| 9 | return decoded_size; | |
| 10 | } | |
| 11 | ||
| 12 | var x: c_int = 1234; | |
| 13 | export var x_ptr = &x; |
example/mix_o_files/build.zig deleted-17| ... | ... | @@ -1,17 +0,0 @@ |
| 1 | const Builder = @import("std").build.Builder; | |
| 2 | ||
| 3 | pub fn build(b: *Builder) void { | |
| 4 | const obj = b.addObject("base64", "base64.zig"); | |
| 5 | ||
| 6 | const exe = b.addExecutable("test", null); | |
| 7 | exe.addCSourceFile("test.c", [_][]const u8{"-std=c99"}); | |
| 8 | exe.addObject(obj); | |
| 9 | exe.linkSystemLibrary("c"); | |
| 10 | ||
| 11 | b.default_step.dependOn(&exe.step); | |
| 12 | ||
| 13 | const run_cmd = exe.run(); | |
| 14 | ||
| 15 | const test_step = b.step("test", "Test the program"); | |
| 16 | test_step.dependOn(&run_cmd.step); | |
| 17 | } |
example/mix_o_files/test.c deleted-20| ... | ... | @@ -1,20 +0,0 @@ |
| 1 | // This header is generated by zig from base64.zig | |
| 2 | #include "base64.h" | |
| 3 | ||
| 4 | #include <assert.h> | |
| 5 | #include <string.h> | |
| 6 | ||
| 7 | extern int *x_ptr; | |
| 8 | ||
| 9 | int main(int argc, char **argv) { | |
| 10 | const char *encoded = "YWxsIHlvdXIgYmFzZSBhcmUgYmVsb25nIHRvIHVz"; | |
| 11 | char buf[200]; | |
| 12 | ||
| 13 | size_t len = decode_base_64((uint8_t *)buf, 200, (uint8_t *)encoded, strlen(encoded)); | |
| 14 | buf[len] = 0; | |
| 15 | assert(strcmp(buf, "all your base are belong to us") == 0); | |
| 16 | ||
| 17 | assert(*x_ptr == 1234); | |
| 18 | ||
| 19 | return 0; | |
| 20 | } |
example/shared_library/build.zig deleted-17| ... | ... | @@ -1,17 +0,0 @@ |
| 1 | const Builder = @import("std").build.Builder; | |
| 2 | ||
| 3 | pub fn build(b: *Builder) void { | |
| 4 | const lib = b.addSharedLibrary("mathtest", "mathtest.zig", b.version(1, 0, 0)); | |
| 5 | ||
| 6 | const exe = b.addExecutable("test", null); | |
| 7 | exe.addCSourceFile("test.c", [_][]const u8{"-std=c99"}); | |
| 8 | exe.linkLibrary(lib); | |
| 9 | exe.linkSystemLibrary("c"); | |
| 10 | ||
| 11 | b.default_step.dependOn(&exe.step); | |
| 12 | ||
| 13 | const run_cmd = exe.run(); | |
| 14 | ||
| 15 | const test_step = b.step("test", "Test the program"); | |
| 16 | test_step.dependOn(&run_cmd.step); | |
| 17 | } |
example/shared_library/mathtest.zig deleted-3| ... | ... | @@ -1,3 +0,0 @@ |
| 1 | export fn add(a: i32, b: i32) i32 { | |
| 2 | return a + b; | |
| 3 | } |
example/shared_library/test.c deleted-7| ... | ... | @@ -1,7 +0,0 @@ |
| 1 | #include "mathtest.h" | |
| 2 | #include <assert.h> | |
| 3 | ||
| 4 | int main(int argc, char **argv) { | |
| 5 | assert(add(42, 1337) == 1379); | |
| 6 | return 0; | |
| 7 | } |
test/build_examples.zig deleted-31| ... | ... | @@ -1,31 +0,0 @@ |
| 1 | const tests = @import("tests.zig"); | |
| 2 | const builtin = @import("builtin"); | |
| 3 | const is_windows = builtin.os == builtin.Os.windows; | |
| 4 | ||
| 5 | pub fn addCases(cases: *tests.BuildExamplesContext) void { | |
| 6 | cases.add("example/hello_world/hello.zig"); | |
| 7 | cases.addC("example/hello_world/hello_libc.zig"); | |
| 8 | cases.add("example/cat/main.zig"); | |
| 9 | cases.add("example/guess_number/main.zig"); | |
| 10 | cases.add("test/standalone/main_return_error/error_u8.zig"); | |
| 11 | cases.add("test/standalone/main_return_error/error_u8_non_zero.zig"); | |
| 12 | cases.addBuildFile("test/standalone/main_pkg_path/build.zig"); | |
| 13 | cases.addBuildFile("example/shared_library/build.zig"); | |
| 14 | cases.addBuildFile("example/mix_o_files/build.zig"); | |
| 15 | cases.addBuildFile("test/standalone/static_c_lib/build.zig"); | |
| 16 | cases.addBuildFile("test/standalone/issue_339/build.zig"); | |
| 17 | cases.addBuildFile("test/standalone/issue_794/build.zig"); | |
| 18 | cases.addBuildFile("test/standalone/pkg_import/build.zig"); | |
| 19 | cases.addBuildFile("test/standalone/use_alias/build.zig"); | |
| 20 | cases.addBuildFile("test/standalone/brace_expansion/build.zig"); | |
| 21 | cases.addBuildFile("test/standalone/empty_env/build.zig"); | |
| 22 | if (builtin.os == builtin.Os.linux) { | |
| 23 | // TODO hook up the DynLib API for windows using LoadLibraryA | |
| 24 | // TODO figure out how to make this work on darwin - probably libSystem has dlopen/dlsym in it | |
| 25 | cases.addBuildFile("test/standalone/load_dynamic_library/build.zig"); | |
| 26 | } | |
| 27 | ||
| 28 | if (builtin.arch == builtin.Arch.x86_64) { // TODO add C ABI support for other architectures | |
| 29 | cases.addBuildFile("test/stage1/c_abi/build.zig"); | |
| 30 | } | |
| 31 | } |
test/standalone.zig created+31| ... | ... | @@ -0,0 +1,31 @@ |
| 1 | const tests = @import("tests.zig"); | |
| 2 | const builtin = @import("builtin"); | |
| 3 | const is_windows = builtin.os == builtin.Os.windows; | |
| 4 | ||
| 5 | pub fn addCases(cases: *tests.StandaloneContext) void { | |
| 6 | cases.add("test/standalone/hello_world/hello.zig"); | |
| 7 | cases.addC("test/standalone/hello_world/hello_libc.zig"); | |
| 8 | cases.add("test/standalone/cat/main.zig"); | |
| 9 | cases.add("test/standalone/guess_number/main.zig"); | |
| 10 | cases.add("test/standalone/main_return_error/error_u8.zig"); | |
| 11 | cases.add("test/standalone/main_return_error/error_u8_non_zero.zig"); | |
| 12 | cases.addBuildFile("test/standalone/main_pkg_path/build.zig"); | |
| 13 | cases.addBuildFile("test/standalone/shared_library/build.zig"); | |
| 14 | cases.addBuildFile("test/standalone/mix_o_files/build.zig"); | |
| 15 | cases.addBuildFile("test/standalone/static_c_lib/build.zig"); | |
| 16 | cases.addBuildFile("test/standalone/issue_339/build.zig"); | |
| 17 | cases.addBuildFile("test/standalone/issue_794/build.zig"); | |
| 18 | cases.addBuildFile("test/standalone/pkg_import/build.zig"); | |
| 19 | cases.addBuildFile("test/standalone/use_alias/build.zig"); | |
| 20 | cases.addBuildFile("test/standalone/brace_expansion/build.zig"); | |
| 21 | cases.addBuildFile("test/standalone/empty_env/build.zig"); | |
| 22 | if (builtin.os == builtin.Os.linux) { | |
| 23 | // TODO hook up the DynLib API for windows using LoadLibraryA | |
| 24 | // TODO figure out how to make this work on darwin - probably libSystem has dlopen/dlsym in it | |
| 25 | cases.addBuildFile("test/standalone/load_dynamic_library/build.zig"); | |
| 26 | } | |
| 27 | ||
| 28 | if (builtin.arch == builtin.Arch.x86_64) { // TODO add C ABI support for other architectures | |
| 29 | cases.addBuildFile("test/stage1/c_abi/build.zig"); | |
| 30 | } | |
| 31 | } |
test/standalone/cat/main.zig created+70| ... | ... | @@ -0,0 +1,70 @@ |
| 1 | const std = @import("std"); | |
| 2 | const io = std.io; | |
| 3 | const process = std.process; | |
| 4 | const File = std.fs.File; | |
| 5 | const mem = std.mem; | |
| 6 | const warn = std.debug.warn; | |
| 7 | const allocator = std.debug.global_allocator; | |
| 8 | ||
| 9 | pub fn main() !void { | |
| 10 | var args_it = process.args(); | |
| 11 | const exe = try unwrapArg(args_it.next(allocator).?); | |
| 12 | var catted_anything = false; | |
| 13 | var stdout_file = try io.getStdOut(); | |
| 14 | ||
| 15 | while (args_it.next(allocator)) |arg_or_err| { | |
| 16 | const arg = try unwrapArg(arg_or_err); | |
| 17 | if (mem.eql(u8, arg, "-")) { | |
| 18 | catted_anything = true; | |
| 19 | var stdin_file = try io.getStdIn(); | |
| 20 | try cat_file(&stdout_file, &stdin_file); | |
| 21 | } else if (arg[0] == '-') { | |
| 22 | return usage(exe); | |
| 23 | } else { | |
| 24 | var file = File.openRead(arg) catch |err| { | |
| 25 | warn("Unable to open file: {}\n", @errorName(err)); | |
| 26 | return err; | |
| 27 | }; | |
| 28 | defer file.close(); | |
| 29 | ||
| 30 | catted_anything = true; | |
| 31 | try cat_file(&stdout_file, &file); | |
| 32 | } | |
| 33 | } | |
| 34 | if (!catted_anything) { | |
| 35 | var stdin_file = try io.getStdIn(); | |
| 36 | try cat_file(&stdout_file, &stdin_file); | |
| 37 | } | |
| 38 | } | |
| 39 | ||
| 40 | fn usage(exe: []const u8) !void { | |
| 41 | warn("Usage: {} [FILE]...\n", exe); | |
| 42 | return error.Invalid; | |
| 43 | } | |
| 44 | ||
| 45 | fn cat_file(stdout: *File, file: *File) !void { | |
| 46 | var buf: [1024 * 4]u8 = undefined; | |
| 47 | ||
| 48 | while (true) { | |
| 49 | const bytes_read = file.read(buf[0..]) catch |err| { | |
| 50 | warn("Unable to read from stream: {}\n", @errorName(err)); | |
| 51 | return err; | |
| 52 | }; | |
| 53 | ||
| 54 | if (bytes_read == 0) { | |
| 55 | break; | |
| 56 | } | |
| 57 | ||
| 58 | stdout.write(buf[0..bytes_read]) catch |err| { | |
| 59 | warn("Unable to write to stdout: {}\n", @errorName(err)); | |
| 60 | return err; | |
| 61 | }; | |
| 62 | } | |
| 63 | } | |
| 64 | ||
| 65 | fn unwrapArg(arg: anyerror![]u8) ![]u8 { | |
| 66 | return arg catch |err| { | |
| 67 | warn("Unable to parse command line: {}\n", err); | |
| 68 | return err; | |
| 69 | }; | |
| 70 | } |
test/standalone/guess_number/main.zig created+47| ... | ... | @@ -0,0 +1,47 @@ |
| 1 | const builtin = @import("builtin"); | |
| 2 | const std = @import("std"); | |
| 3 | const io = std.io; | |
| 4 | const fmt = std.fmt; | |
| 5 | ||
| 6 | pub fn main() !void { | |
| 7 | var stdout_file = try io.getStdOut(); | |
| 8 | const stdout = &stdout_file.outStream().stream; | |
| 9 | ||
| 10 | try stdout.print("Welcome to the Guess Number Game in Zig.\n"); | |
| 11 | ||
| 12 | var seed_bytes: [@sizeOf(u64)]u8 = undefined; | |
| 13 | std.crypto.randomBytes(seed_bytes[0..]) catch |err| { | |
| 14 | std.debug.warn("unable to seed random number generator: {}", err); | |
| 15 | return err; | |
| 16 | }; | |
| 17 | const seed = std.mem.readIntNative(u64, &seed_bytes); | |
| 18 | var prng = std.rand.DefaultPrng.init(seed); | |
| 19 | ||
| 20 | const answer = prng.random.range(u8, 0, 100) + 1; | |
| 21 | ||
| 22 | while (true) { | |
| 23 | try stdout.print("\nGuess a number between 1 and 100: "); | |
| 24 | var line_buf: [20]u8 = undefined; | |
| 25 | ||
| 26 | const line = io.readLineSlice(line_buf[0..]) catch |err| switch (err) { | |
| 27 | error.OutOfMemory => { | |
| 28 | try stdout.print("Input too long.\n"); | |
| 29 | continue; | |
| 30 | }, | |
| 31 | else => return err, | |
| 32 | }; | |
| 33 | ||
| 34 | const guess = fmt.parseUnsigned(u8, line, 10) catch { | |
| 35 | try stdout.print("Invalid number.\n"); | |
| 36 | continue; | |
| 37 | }; | |
| 38 | if (guess > answer) { | |
| 39 | try stdout.print("Guess lower.\n"); | |
| 40 | } else if (guess < answer) { | |
| 41 | try stdout.print("Guess higher.\n"); | |
| 42 | } else { | |
| 43 | try stdout.print("You win!\n"); | |
| 44 | return; | |
| 45 | } | |
| 46 | } | |
| 47 | } |
test/standalone/hello_world/hello.zig created+9| ... | ... | @@ -0,0 +1,9 @@ |
| 1 | const std = @import("std"); | |
| 2 | ||
| 3 | pub fn main() !void { | |
| 4 | // If this program is run without stdout attached, exit with an error. | |
| 5 | const stdout_file = try std.io.getStdOut(); | |
| 6 | // If this program encounters pipe failure when printing to stdout, exit | |
| 7 | // with an error. | |
| 8 | try stdout_file.write("Hello, world!\n"); | |
| 9 | } |
test/standalone/hello_world/hello_libc.zig created+13| ... | ... | @@ -0,0 +1,13 @@ |
| 1 | const c = @cImport({ | |
| 2 | // See https://github.com/ziglang/zig/issues/515 | |
| 3 | @cDefine("_NO_CRT_STDIO_INLINE", "1"); | |
| 4 | @cInclude("stdio.h"); | |
| 5 | @cInclude("string.h"); | |
| 6 | }); | |
| 7 | ||
| 8 | const msg = c"Hello, world!\n"; | |
| 9 | ||
| 10 | export fn main(argc: c_int, argv: **u8) c_int { | |
| 11 | if (c.printf(msg) != @intCast(c_int, c.strlen(msg))) return -1; | |
| 12 | return 0; | |
| 13 | } |
test/standalone/mix_o_files/base64.zig created+13| ... | ... | @@ -0,0 +1,13 @@ |
| 1 | const base64 = @import("std").base64; | |
| 2 | ||
| 3 | export fn decode_base_64(dest_ptr: [*]u8, dest_len: usize, source_ptr: [*]const u8, source_len: usize) usize { | |
| 4 | const src = source_ptr[0..source_len]; | |
| 5 | const dest = dest_ptr[0..dest_len]; | |
| 6 | const base64_decoder = base64.standard_decoder_unsafe; | |
| 7 | const decoded_size = base64_decoder.calcSize(src); | |
| 8 | base64_decoder.decode(dest[0..decoded_size], src); | |
| 9 | return decoded_size; | |
| 10 | } | |
| 11 | ||
| 12 | var x: c_int = 1234; | |
| 13 | export var x_ptr = &x; |
test/standalone/mix_o_files/build.zig created+17| ... | ... | @@ -0,0 +1,17 @@ |
| 1 | const Builder = @import("std").build.Builder; | |
| 2 | ||
| 3 | pub fn build(b: *Builder) void { | |
| 4 | const obj = b.addObject("base64", "base64.zig"); | |
| 5 | ||
| 6 | const exe = b.addExecutable("test", null); | |
| 7 | exe.addCSourceFile("test.c", [_][]const u8{"-std=c99"}); | |
| 8 | exe.addObject(obj); | |
| 9 | exe.linkSystemLibrary("c"); | |
| 10 | ||
| 11 | b.default_step.dependOn(&exe.step); | |
| 12 | ||
| 13 | const run_cmd = exe.run(); | |
| 14 | ||
| 15 | const test_step = b.step("test", "Test the program"); | |
| 16 | test_step.dependOn(&run_cmd.step); | |
| 17 | } |
test/standalone/mix_o_files/test.c created+20| ... | ... | @@ -0,0 +1,20 @@ |
| 1 | // This header is generated by zig from base64.zig | |
| 2 | #include "base64.h" | |
| 3 | ||
| 4 | #include <assert.h> | |
| 5 | #include <string.h> | |
| 6 | ||
| 7 | extern int *x_ptr; | |
| 8 | ||
| 9 | int main(int argc, char **argv) { | |
| 10 | const char *encoded = "YWxsIHlvdXIgYmFzZSBhcmUgYmVsb25nIHRvIHVz"; | |
| 11 | char buf[200]; | |
| 12 | ||
| 13 | size_t len = decode_base_64((uint8_t *)buf, 200, (uint8_t *)encoded, strlen(encoded)); | |
| 14 | buf[len] = 0; | |
| 15 | assert(strcmp(buf, "all your base are belong to us") == 0); | |
| 16 | ||
| 17 | assert(*x_ptr == 1234); | |
| 18 | ||
| 19 | return 0; | |
| 20 | } |
test/standalone/shared_library/build.zig created+17| ... | ... | @@ -0,0 +1,17 @@ |
| 1 | const Builder = @import("std").build.Builder; | |
| 2 | ||
| 3 | pub fn build(b: *Builder) void { | |
| 4 | const lib = b.addSharedLibrary("mathtest", "mathtest.zig", b.version(1, 0, 0)); | |
| 5 | ||
| 6 | const exe = b.addExecutable("test", null); | |
| 7 | exe.addCSourceFile("test.c", [_][]const u8{"-std=c99"}); | |
| 8 | exe.linkLibrary(lib); | |
| 9 | exe.linkSystemLibrary("c"); | |
| 10 | ||
| 11 | b.default_step.dependOn(&exe.step); | |
| 12 | ||
| 13 | const run_cmd = exe.run(); | |
| 14 | ||
| 15 | const test_step = b.step("test", "Test the program"); | |
| 16 | test_step.dependOn(&run_cmd.step); | |
| 17 | } |
test/standalone/shared_library/mathtest.zig created+3| ... | ... | @@ -0,0 +1,3 @@ |
| 1 | export fn add(a: i32, b: i32) i32 { | |
| 2 | return a + b; | |
| 3 | } |
test/standalone/shared_library/test.c created+7| ... | ... | @@ -0,0 +1,7 @@ |
| 1 | #include "mathtest.h" | |
| 2 | #include <assert.h> | |
| 3 | ||
| 4 | int main(int argc, char **argv) { | |
| 5 | assert(add(42, 1337) == 1379); | |
| 6 | return 0; | |
| 7 | } |
test/tests.zig+11-11| ... | ... | @@ -13,7 +13,7 @@ const Mode = builtin.Mode; |
| 13 | 13 | const LibExeObjStep = build.LibExeObjStep; |
| 14 | 14 | |
| 15 | 15 | const compare_output = @import("compare_output.zig"); |
| 16 | const build_examples = @import("build_examples.zig"); | |
| 16 | const standalone = @import("standalone.zig"); | |
| 17 | 17 | const compile_errors = @import("compile_errors.zig"); |
| 18 | 18 | const assemble_and_link = @import("assemble_and_link.zig"); |
| 19 | 19 | const runtime_safety = @import("runtime_safety.zig"); |
| ... | ... | @@ -91,17 +91,17 @@ pub fn addCompileErrorTests(b: *build.Builder, test_filter: ?[]const u8, modes: |
| 91 | 91 | return cases.step; |
| 92 | 92 | } |
| 93 | 93 | |
| 94 | pub fn addBuildExampleTests(b: *build.Builder, test_filter: ?[]const u8, modes: []const Mode) *build.Step { | |
| 95 | const cases = b.allocator.create(BuildExamplesContext) catch unreachable; | |
| 96 | cases.* = BuildExamplesContext{ | |
| 94 | pub fn addStandaloneTests(b: *build.Builder, test_filter: ?[]const u8, modes: []const Mode) *build.Step { | |
| 95 | const cases = b.allocator.create(StandaloneContext) catch unreachable; | |
| 96 | cases.* = StandaloneContext{ | |
| 97 | 97 | .b = b, |
| 98 | .step = b.step("test-build-examples", "Build the examples"), | |
| 98 | .step = b.step("test-standalone", "Run the standalone tests"), | |
| 99 | 99 | .test_index = 0, |
| 100 | 100 | .test_filter = test_filter, |
| 101 | 101 | .modes = modes, |
| 102 | 102 | }; |
| 103 | 103 | |
| 104 | build_examples.addCases(cases); | |
| 104 | standalone.addCases(cases); | |
| 105 | 105 | |
| 106 | 106 | return cases.step; |
| 107 | 107 | } |
| ... | ... | @@ -830,22 +830,22 @@ pub const CompileErrorContext = struct { |
| 830 | 830 | } |
| 831 | 831 | }; |
| 832 | 832 | |
| 833 | pub const BuildExamplesContext = struct { | |
| 833 | pub const StandaloneContext = struct { | |
| 834 | 834 | b: *build.Builder, |
| 835 | 835 | step: *build.Step, |
| 836 | 836 | test_index: usize, |
| 837 | 837 | test_filter: ?[]const u8, |
| 838 | 838 | modes: []const Mode, |
| 839 | 839 | |
| 840 | pub fn addC(self: *BuildExamplesContext, root_src: []const u8) void { | |
| 840 | pub fn addC(self: *StandaloneContext, root_src: []const u8) void { | |
| 841 | 841 | self.addAllArgs(root_src, true); |
| 842 | 842 | } |
| 843 | 843 | |
| 844 | pub fn add(self: *BuildExamplesContext, root_src: []const u8) void { | |
| 844 | pub fn add(self: *StandaloneContext, root_src: []const u8) void { | |
| 845 | 845 | self.addAllArgs(root_src, false); |
| 846 | 846 | } |
| 847 | 847 | |
| 848 | pub fn addBuildFile(self: *BuildExamplesContext, build_file: []const u8) void { | |
| 848 | pub fn addBuildFile(self: *StandaloneContext, build_file: []const u8) void { | |
| 849 | 849 | const b = self.b; |
| 850 | 850 | |
| 851 | 851 | const annotated_case_name = b.fmt("build {} (Debug)", build_file); |
| ... | ... | @@ -875,7 +875,7 @@ pub const BuildExamplesContext = struct { |
| 875 | 875 | self.step.dependOn(&log_step.step); |
| 876 | 876 | } |
| 877 | 877 | |
| 878 | pub fn addAllArgs(self: *BuildExamplesContext, root_src: []const u8, link_libc: bool) void { | |
| 878 | pub fn addAllArgs(self: *StandaloneContext, root_src: []const u8, link_libc: bool) void { | |
| 879 | 879 | const b = self.b; |
| 880 | 880 | |
| 881 | 881 | for (self.modes) |mode| { |