44 lines
1.6 KiB
Zig
44 lines
1.6 KiB
Zig
|
const std = @import("std");
|
||
|
const net = std.net;
|
||
|
const posix = std.posix;
|
||
|
|
||
|
pub fn main() !void {
|
||
|
const address = try std.net.Address.parseIp("127.0.0.1", 5882);
|
||
|
|
||
|
const tpe: u32 = posix.SOCK.STREAM;
|
||
|
const protocol = posix.IPPROTO.TCP;
|
||
|
const listener = try posix.socket(address.any.family, tpe, protocol);
|
||
|
defer posix.close(listener);
|
||
|
|
||
|
try posix.setsockopt(listener, posix.SOL.SOCKET, posix.SO.REUSEADDR, &std.mem.toBytes(@as(c_int, 1)));
|
||
|
try posix.bind(listener, &address.any, address.getOsSockLen());
|
||
|
try posix.listen(listener, 128);
|
||
|
|
||
|
var buf: [128]u8 = undefined;
|
||
|
while (true) {
|
||
|
var client_address: net.Address = undefined;
|
||
|
var client_address_len: posix.socklen_t = @sizeOf(net.Address);
|
||
|
const socket = posix.accept(listener, &client_address.any, &client_address_len, 0) catch |err| {
|
||
|
// Rare that this happens, but in later parts we'll
|
||
|
// see examples where it does.
|
||
|
std.debug.print("error accept: {}\n", .{err});
|
||
|
continue;
|
||
|
};
|
||
|
defer posix.close(socket);
|
||
|
|
||
|
std.debug.print("{} connected\n", .{client_address});
|
||
|
|
||
|
const timeout = posix.timeval{.tv_sec = 2, .tv_usec = 500_000};
|
||
|
try posix.setsockopt(socket, posix.SOL.SOCKET, posix.SO.RCVTIMEO, &std.mem.toBytes(timeout));
|
||
|
try posix.setsockopt(socket, posix.SOL.SOCKET, posix.SO.SNDTIMEO, &std.mem.toBytes(timeout));
|
||
|
|
||
|
// we've changed everything from this point on
|
||
|
const stream = std.net.Stream{.handle = socket};
|
||
|
|
||
|
const read = try stream.read(&buf);
|
||
|
if (read == 0) {
|
||
|
continue;
|
||
|
}
|
||
|
try stream.writeAll(buf[0..read]);
|
||
|
}
|
||
|
}
|