diff options
Diffstat (limited to 'doc/api/libstd/networking.txt')
-rw-r--r-- | doc/api/libstd/networking.txt | 181 |
1 files changed, 181 insertions, 0 deletions
diff --git a/doc/api/libstd/networking.txt b/doc/api/libstd/networking.txt new file mode 100644 index 0000000..0229573 --- /dev/null +++ b/doc/api/libstd/networking.txt @@ -0,0 +1,181 @@ +{ + title: Networking + description: libstd: Networking +} +Networking +---------- + + pkg std = + type netaddr = union + `Ipv4 byte[4] + `Ipv6 byte[16] + ;; + + + /* network connections */ + const dial : (dialstr : byte[:] -> result(fd, byte[:])) + const announce : (ds : byte[:] -> result(fd, byte[:])) + const listen : (sock : fd -> result(fd, byte[:])) + const accept : (lfd : fd -> result(fd, byte[:])) + + /* ip parsing */ + const ipparse : (ip : byte[:] -> option(netaddr)) + const ip4parse : (ip : byte[:] -> option(netaddr)) + const ip6parse : (ip : byte[:] -> option(netaddr)) + + generic hosttonet : (v : @a -> @a) + generic nettohost : (v : @a -> @a) + ;; + +Summary +------- + +This group of functions contains the basic, portable networking functionality +provided by libstd. There are other packages shipped which provide access +to the underlying functionality used to implement this code, and which may +provide more control. + +The bulk of the functionality is fairly low level. Most of the client side +networking should be done using nothing more than `dial` and `announce` + +Dial describes the endpoint to connect to in the form `proto!host!service`. +`proto` can be any supported protocol. The host specified can be an IP +address, hostname, or path to a local socket. The service ismay be either a +named service, or a protocol specific port. If the port is not a component of +the address (eg, Unix domain sockets) then it should be ommitted. + +On plan 9, the full dial(2) dial string syntax is suported. + +Data Types +---------- + +This contains the infomation that we extract by resolving a host. + + type ipaddr = union + `Ipv4 byte[4] + `Ipv6 byte[16] + ;; + +This contains an IP address. Either V4 or V6 is supported. + +Connections +---------- + + const dial : (dialstr : byte[:] -> result(fd, byte[:])) + +Dial connects to a dial string as described in the summary, returning either a +file descriptor on success, or an error description on failure. The FD +returned is a connection to the server. + + const announce : (ds : byte[:] -> result(fd, byte[:])) + +Announce sets up a file descriptor which is ready to listen for connections, +and binds it to an address. Wildcards can be specified with '*' within the +dial string. + + const listen : (sock : fd -> result(fd, byte[:])) + +Listen specifies that the socket created with `announce` is willing to accept +connections. + + const accept : (lfd : fd -> result(fd, byte[:])) + +Accept takes the returned file descriptor from listen, and returns a file +descriptor that is prepared for reading and writing. + +IP Parsing +---------- + + const ipparse : (ip : byte[:] -> option(netaddr)) + +Ipparse will parse an IP address. This will recognize either V4 or V6 +addresses, and `\`Some \`Ipv4 bits or `\`Some \`Ipv6 bits` as appropriate, or +`\`None` if the address can't be parsed. + + const ip4parse : (ip : byte[:] -> option(netaddr)) + +Parses an Ipv4 address from the string `ip`. The syntax expected is dotted +quad notation. Returns `\` Some \`Ipv4 bits` if the address parses successfully, or +`\`None` if parsing fails. + + const ip6parse : (ip : byte[:] -> option(netaddr)) + +Parses an Ipv6 address from the string `ip`. Returns `\` Some \`Ipv4 bits` if +the address parses successfully, or `\`None` if parsing fails. Zones are +currently not supported. This is a bug. + + +Endian flipping +-------------- + + generic hosttonet : (v : @a -> @a) + generic nettohost : (v : @a -> @a) + + +Flips the bits in an integer to match the expected. These functions should be +avoided in favor of explicit packing functions. + +Examples +-------- + +Some simple examples of how to use the Myrddin networking API + +#### Echo Server + + use std + + const Dialstr = "tcp!*!1234" + const main = { + var lfd, afd + var buf : byte[1024] + + match std.announce(Dialstr) + | `std.Ok f: lfd = f + | `std.Fail e: std.fatal("unable to announce on {}: {}\n", Dialstr, e) + ;; + + match std.listen(lfd) + | `std.Ok f: afd = f + | `std.Fail e: std.fatal("unable to listen on {}: {}\n", Dialstr, e) + ;; + + while true + match std.accept(afd) + | `std.Ok fd: + match std.read(fd, buf[:]) + | `std.Ok n: + std.writeall(fd, buf[:n]) + | `std.Fail e: + std.put("lost conection while reading: {}\n", e) + ;; + std.close(fd) + | `std.Fail e: + std.fatal("unable to accept connection on {}: {}\n", Dialstr, e) + ;; + ;; + } + + +#### Echo Client + + use std + + const Dialstr = "tcp!localhost!1234" + const main = {args : byte[:][:] + var req, resp + + match std.dial(Dialstr) + | `std.Ok fd: + req = std.strjoin(args[1:], " ") + std.writeall(fd, req) + resp = std.try(std.fslurp(fd)) + std.put("{}\n", resp) + | `std.Fail e: + std.fatal("unable to dial {}: {}\n", Dialstr, e) + ;; + } + +Bugs +---- +The errors returned are strings, when they should be unions with default +formatting functions. |