summaryrefslogtreecommitdiff
path: root/test/transport.zig
blob: 3d43ddbbbebc61ddf4f9b10362afa05bd6c426d7 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
const std = @import("std");
const c9 = @import("cloud9");
const t = c9.transport;
const testing = std.testing;

test "standard readers and writers preserve frame boundaries" {
    var bytes: [128]u8 = undefined;
    const frame = try c9.encode(.{ .tversion = .{ .msize = 4096, .version = "9P2000" } }, c9.notag, &bytes);
    var source: testing.Reader = .init(&.{}, &.{.{ .buffer = frame }});
    source.artificial_limit = .limited(1);
    var target: [128]u8 = undefined;
    const got = try t.readFrame(&source.interface, &target, 4096);
    try testing.expectEqualSlices(u8, frame, got);
    var output: [128]u8 = undefined;
    var writer: std.Io.Writer = .fixed(&output);
    try t.writeFrame(&writer, got, 4096);
    try testing.expectEqualSlices(u8, frame, writer.buffered());
}

test "POSIX TCP and Unix streams handle retry and EOF" {
    var dir = testing.tmpDir(.{});
    defer dir.cleanup();
    const io = testing.io;
    var path_buffer: [std.fs.max_path_bytes]u8 = undefined;
    const parent_len = try dir.dir.realPath(io, &path_buffer);
    const parent = path_buffer[0..parent_len];
    var unix_buffer: [t.sun_path_len]u8 = undefined;
    const unix = try std.fmt.bufPrintSentinel(&unix_buffer, "{s}/9p", .{parent}, 0);
    for ([_]t.Address{ .{ .tcp = .{ .ip4 = .loopback(0) } }, .{ .unix = unix } }) |address| {
        const listener = try t.listenFd(address, 4);
        defer t.close(listener);
        var destination = address;
        if (address == .tcp) {
            var actual: std.c.sockaddr.in = undefined;
            var len: std.c.socklen_t = @sizeOf(@TypeOf(actual));
            try testing.expectEqual(@as(c_int, 0), std.c.getsockname(listener, @ptrCast(&actual), &len));
            destination.tcp.setPort(std.mem.bigToNative(u16, actual.port));
        }
        const client = try t.connectFd(destination, t.nowMs() + 1000);
        defer t.close(client);
        const server = (try t.acceptFd(listener, address == .tcp)) orelse return error.NoConnection;
        var buffer: [32]u8 = undefined;
        try testing.expectEqual(@as(?usize, null), try t.read(server, &buffer));
        try testing.expectEqual(@as(?usize, 3), try t.write(client, "abc"));
        try t.wait(server, @intCast(std.c.POLL.IN), t.nowMs() + 1000);
        try testing.expectEqual(@as(?usize, 3), try t.read(server, &buffer));
        try testing.expectEqualStrings("abc", buffer[0..3]);
        t.close(server);
        try t.wait(client, @intCast(std.c.POLL.IN), t.nowMs() + 1000);
        try testing.expectEqual(@as(?usize, 0), try t.read(client, &buffer));
    }
}

test "std.Io TCP and Unix listener and client adapters" {
    var dir = testing.tmpDir(.{});
    defer dir.cleanup();
    const io = testing.io;
    var path_buffer: [std.fs.max_path_bytes]u8 = undefined;
    const parent_len = try dir.dir.realPath(io, &path_buffer);
    const parent = path_buffer[0..parent_len];
    var unix_buffer: [t.sun_path_len]u8 = undefined;
    const unix = try std.fmt.bufPrintSentinel(&unix_buffer, "{s}/9p", .{parent}, 0);
    for ([_]t.Address{ .{ .tcp = .{ .ip4 = .loopback(0) } }, .{ .unix = unix } }) |address| {
        var listener = try t.listen(io, address, 4);
        defer listener.deinit(io);
        const destination: t.Address = if (address == .tcp) .{ .tcp = listener.socket.address } else address;
        const client = try t.connect(io, destination);
        defer client.close(io);
        const server = try listener.accept(io);
        defer server.close(io);
        var output: [128]u8 = undefined;
        var writer = client.writer(io, &output);
        var bytes: [128]u8 = undefined;
        const frame = try c9.encode(.rflush, 1, &bytes);
        try t.writeFrame(&writer.interface, frame, 4096);
        try writer.interface.flush();
        var input: [128]u8 = undefined;
        var reader = server.reader(io, &input);
        var target: [128]u8 = undefined;
        try testing.expectEqualSlices(u8, frame, try t.readFrame(&reader.interface, &target, 4096));
    }
}