I tried to give adding support for Unix domain sockets in pil a go, but I couldn't make functional code yet because I don't really grasp completely how the macro beast language pil32 is written in works (I wrote all the docs though).
The changes would be basically to add a function called 'sock, which will create a Unix socket at a given path, and modify 'connect and 'udp to accept a Unix socket path in the position of the port/service if the given host name is NIL. The patch should be attached to this message, if it isn't I pasted a copy here: http://2.71828.com.ar/p/c;QYLoXQ I'd thank any help to get those functions working as I intend. Cheers, José
diff -r 425552fd43a8 doc/refA.html --- a/doc/refA.html Fri Aug 03 09:10:32 2012 +0200 +++ b/doc/refA.html Sat Sep 01 16:58:35 2012 -0300 @@ -129,7 +129,8 @@ <dt><a name="accept"><code>(accept 'cnt) -> cnt | NIL</code></a> <dd>Accepts a connection on descriptor <code>cnt</code> (as received by <code><a -href="refP.html#port">port</a></code>), and returns the new socket descriptor +href="refP.html#port">port</a></code> or <code><a +href="refS.html#sock">sock</a></code>), and returns the new socket descriptor <code>cnt</code>. The global variable <code>*Adr</code> is set to the IP address of the client. See also <code><a href="refL.html#listen">listen</a></code>, <code><a href="refC.html#connect">connect</a></code> and <code><a diff -r 425552fd43a8 doc/refC.html --- a/doc/refC.html Fri Aug 03 09:10:32 2012 +0200 +++ b/doc/refC.html Sat Sep 01 16:58:35 2012 -0300 @@ -536,21 +536,25 @@ -> 2 </code></pre> -<dt><a name="connect"><code>(connect 'any1 'any2) -> cnt | NIL</code></a> +<dt><a name="connect"><code>(connect ['any1|'NIL] 'any2) -> cnt | NIL</code></a> <dd>Tries to establish a TCP/IP connection to a server listening at host <code>any1</code>, port <code>any2</code>. <code>any1</code> may be either a hostname or a standard internet address in numbers-and-dots/colons notation (IPv4/IPv6). <code>any2</code> may be either a port number or a service name. Returns a socket descriptor <code>cnt</code>, or <code>NIL</code> if the -connection cannot be established. See also <code><a -href="refL.html#listen">listen</a></code> and <code><a -href="refU.html#udp">udp</a></code>. +connection cannot be established. If the first argument +is <code>NIL</code>, then it attempts to establish the connection with +a unix domain socket located in <code>any2</code>. See +also <code><a href="refL.html#listen">listen</a></code> +and <code><a href="refU.html#udp">udp</a></code>. <pre><code> : (connect "localhost" 4444) -> 3 : (connect "some.host.org" "http") -> 4 +: (connect NIL (pil "foo.sock")) +-> 5 </code></pre> <dt><a name="cons"><code>(cons 'any ['any ..]) -> lst</code></a> diff -r 425552fd43a8 doc/refL.html --- a/doc/refL.html Fri Aug 03 09:10:32 2012 +0200 +++ b/doc/refL.html Sat Sep 01 16:58:35 2012 -0300 @@ -361,7 +361,9 @@ <dt><a name="listen"><code>(listen 'cnt1 ['cnt2]) -> cnt | NIL</code></a> <dd>Listens at a socket descriptor <code>cnt1</code> (as received by <code><a -href="refP.html#port">port</a></code>) for an incoming connection, and returns +href="refP.html#port">port</a></code> +or <code><a href="refS.html#sock">sock</a></code>) for an incoming +connection, and returns the new socket descriptor <code>cnt</code>. While waiting for a connection, a <code>select</code> system call is executed for all file descriptors and timers in the <code>VAL</code> of the global variable <code><a diff -r 425552fd43a8 doc/refS.html --- a/doc/refS.html Fri Aug 03 09:10:32 2012 +0200 +++ b/doc/refS.html Sat Sep 01 16:58:35 2012 -0300 @@ -325,7 +325,7 @@ : (? @Nr (2 . 5) # Select all items with numbers between 2 and 5 @Sup "Active" # and suppliers matching "Active" - (select (@Item) # Bind results to '@Item" + (select (@Item) # Bind results to '@Item ((nr +Item @Nr) (nm +CuSu @Sup (sup +Item))) # Generator clauses (range @Nr @Item nr) # Filter clauses (part @Sup @Item sup nm) ) ) @@ -508,6 +508,19 @@ -> "a" </code></pre> +<dt><a name="sock"><code>(sock ['T] 'any) -> cnt</code></a> +<dd>Opens a TCP Unix domain socket at the path <code>any</code> (or a +UDP socket if the first argument is <code>T</code>), and returns a +socket descriptor suitable as an argument +for <code><a href="refL.html#listen">listen</a></code> +or <code><a href="refA.html#accept">accept</a></code> +(or <code><a href="refU.html#udp">udp</a></code>, respectively). + +<pre><code> +: (sock (pil "foo.sock")) # Open a socket in ~/.pil/foo.sock +-> 4 +</code></pre> + <dt><a name="solve"><code>(solve 'lst [. prg]) -> lst</code></a> <dd>Evaluates a <a href="ref.html#pilog">Pilog</a> query and, returns the list of result sets. If <code>prg</code> is given, it is executed for each result diff -r 425552fd43a8 doc/refU.html --- a/doc/refU.html Fri Aug 03 09:10:32 2012 +0200 +++ b/doc/refU.html Sat Sep 01 16:58:35 2012 -0300 @@ -93,15 +93,18 @@ -> T </code></pre> -<dt><a name="udp"><code>(udp 'any1 'any2 'any3) -> any</code></a> +<dt><a name="udp"><code>(udp ['any1|'NIL] 'any2 'any3) -> any</code></a> <dt><code>(udp 'cnt) -> any</code> <dd>Simple unidirectional sending/receiving of UDP packets. In the first form, <code>any3</code> is sent to a UDP server listening at host <code>any1</code>, -port <code>any2</code>. In the second form, one item is received from a UDP -socket <code>cnt</code>, established with <code><a -href="refP.html#port">port</a></code>. See also <code><a -href="refL.html#listen">listen</a></code> and <code><a -href="refC.html#connect">connect</a></code>. +port <code>any2</code>. If the first parameter is <code>NIL</code>, +the data will be sent to a unix socket located +in <code>any2</code>. In the second form, one item is received from a +UDP socket <code>cnt</code>, established +with <code><a href="refP.html#port">port</a></code> +or <code><a href="refS.html#sock">sock</a></code>. See +also <code><a href="refL.html#listen">listen</a></code> +and <code><a href="refC.html#connect">connect</a></code>. <pre><code> # First session diff -r 425552fd43a8 src/net.c --- a/src/net.c Fri Aug 03 09:10:32 2012 +0200 +++ b/src/net.c Sat Sep 01 16:58:35 2012 -0300 @@ -62,6 +62,31 @@ return boxCnt(sd); } +// (sock ['T] 'any) -> cnt +any doSock(any ex) { + any x, y; + int type, sd, n; + unsigned short port; + char* nm; + struct sockaddr_un addr; + x = cdr(ex); + type = SOCK_STREAM; + if ((y = EVAL(car(x))) == T) + type = SOCK_DGRAM, x = cdr(x), y = EVAL(car(x)); + if ((sd = socket(AF_UNIX, type, 0)) < 0) + ipErr(ex, "socket"); + closeOnExec(ex, sd); + memset(&addr, 0, sizeof(addr)); + addr.sun_family = AF_UNIX; + // nm = /* A WAY TO GET THE PARAM'S SYMBOL NAME */ + strncpy(addr.sun_path, nm, sizeof(addr.sun_path)-1); + if (bind(sd, (struct sockaddr*)&addr, sizeof(addr)) < 0) + close(sd), ipErr(ex, "bind"); + if (type == SOCK_STREAM && listen(sd,5) < 0) + close(sd), ipErr(ex, "listen"); + return boxCnt(sd); +} + static any tcpAccept(int sd) { int i, f, sd2; char s[INET6_ADDRSTRLEN]; @@ -139,13 +164,13 @@ return getaddrinfo(nd, sv, &hints, &lst)? NULL : lst; } -// (connect 'any1 'any2) -> cnt | NIL +// (connect ['any1|'NIL] 'any2) -> cnt | NIL any doConnect(any ex) { struct addrinfo *lst, *p; any port; int sd; cell c1; - + /* MAKE IT SO IF FIRST PARAM IS NIL 'any2 IS SUN_PATH */ Push(c1, evSym(cdr(ex))); port = evSym(cddr(ex)); for (p = lst = server(SOCK_STREAM, Pop(c1), port); p; p = p->ai_next) { @@ -179,7 +204,7 @@ return *UdpPtr++; } -// (udp 'any1 'any2 'any3) -> any +// (udp ['any1|'NIL] 'any2 'any3) -> any // (udp 'cnt) -> any any doUdp(any ex) { any x, y; @@ -187,7 +212,7 @@ struct addrinfo *lst, *p; int sd; byte buf[UDPMAX]; - + /* ALSO MAKE IT SO IF FIRST PARAM IS NIL, 'any2 IS SUN_PATH */ x = cdr(ex), data(c1) = EVAL(car(x)); if (!isCell(x = cdr(x))) { if (recv((int)xCnt(ex, data(c1)), buf, UDPMAX, 0) < 0)