diff --git a/gck-rpc-daemon-standalone.c b/gck-rpc-daemon-standalone.c
index 7b60ad9eb97b88bb7aa4922adc055c95691b57c6..7214bb078eb5f56d12a6d5345b2a72abdfeabcc9 100644
--- a/gck-rpc-daemon-standalone.c
+++ b/gck-rpc-daemon-standalone.c
@@ -58,7 +58,7 @@ static int is_running = 1;
 
 static int usage(void)
 {
-	fprintf(stderr, "usage: gck-rpc-daemon pkcs11-module\n");
+	fprintf(stderr, "usage: pkcs11-daemon pkcs11-module [<socket>|\"-\"]\n\tUsing \"-\" results in a single-thread inetd-type daemon\n");
 	exit(2);
 }
 
@@ -73,7 +73,7 @@ int main(int argc, char *argv[])
 	CK_RV rv;
 
 	/* The module to load is the argument */
-	if (argc != 2)
+	if (argc != 2 || argc != 3)
 		usage();
 
 	/* Load the library */
@@ -113,15 +113,20 @@ int main(int argc, char *argv[])
 	}
 
 	path = getenv("PKCS11_DAEMON_SOCKET");
-	if (!path)
-		path = SOCKET_PATH;
-
-	sock = gck_rpc_layer_initialize(path, funcs);
-	if (sock == -1)
-		exit(1);
-
-	is_running = 1;
-	while (is_running) {
+	if (!path && argc == 3)
+           path = argv[2];
+        if (!path)
+	   path = SOCKET_PATH;
+
+        if (strcmp(path,"-") == 0) {
+           gck_rpc_layer_inetd();
+        } else {
+	   sock = gck_rpc_layer_initialize(path, funcs);
+	   if (sock == -1)
+		   exit(1);
+
+	   is_running = 1;
+	   while (is_running) {
 		FD_ZERO(&read_fds);
 		FD_SET(sock, &read_fds);
 		ret = select(sock + 1, &read_fds, NULL, NULL, NULL);
@@ -135,9 +140,10 @@ int main(int argc, char *argv[])
 
 		if (FD_ISSET(sock, &read_fds))
 			gck_rpc_layer_accept();
-	}
+	   }
 
-	gck_rpc_layer_uninitialize();
+	   gck_rpc_layer_uninitialize();
+        }
 
 	rv = (funcs->C_Finalize) (NULL);
 	if (rv != CKR_OK)
diff --git a/gck-rpc-dispatch.c b/gck-rpc-dispatch.c
index e1f3bd1b64ff5ed51235eec931333d96a138228e..de6f55886e34dd2cc09a3c4dbc03fb0c5a276435 100644
--- a/gck-rpc-dispatch.c
+++ b/gck-rpc-dispatch.c
@@ -63,6 +63,8 @@ typedef struct _CallState {
 	uint64_t appid;
 	int call;
 	int sock;
+        int (*read)(int, unsigned char *,size_t);
+        int (*write)(int, unsigned char *,size_t);
 } CallState;
 
 typedef struct _DispatchState {
@@ -2097,7 +2099,7 @@ static void run_dispatch_loop(CallState *cs)
 	assert(cs->sock != -1);
 
 	/* The client application */
-	if (!read_all(cs->sock, (unsigned char *)&cs->appid, sizeof (cs->appid))) {
+	if (!cs->read(cs->sock, (unsigned char *)&cs->appid, sizeof (cs->appid))) {
 		gck_rpc_warn("Can't read appid\n");
 		return ;
 	}
@@ -2116,7 +2118,7 @@ static void run_dispatch_loop(CallState *cs)
 		call_reset(cs);
 
 		/* Read the number of bytes ... */
-		if (!read_all(cs->sock, buf, 4))
+		if (!cs->read(cs->sock, buf, 4))
 			break;
 
 		/* Calculate the number of bytes */
@@ -2135,7 +2137,7 @@ static void run_dispatch_loop(CallState *cs)
 		}
 
 		/* ... and read/parse in the actual message */
-		if (!read_all(cs->sock, cs->req->buffer.buf, len))
+		if (!cs->read(cs->sock, cs->req->buffer.buf, len))
 			break;
 
 		egg_buffer_add_empty(&cs->req->buffer, len);
@@ -2149,8 +2151,8 @@ static void run_dispatch_loop(CallState *cs)
 
 		/* .. send back response length, and then response data */
 		egg_buffer_encode_uint32(buf, cs->resp->buffer.len);
-		if (!write_all(cs->sock, buf, 4) ||
-		    !write_all(cs->sock, cs->resp->buffer.buf, cs->resp->buffer.len))
+		if (!cs->write(cs->sock, buf, 4) ||
+		    !cs->write(cs->sock, cs->resp->buffer.buf, cs->resp->buffer.len))
 			break;
 	}
 
@@ -2221,6 +2223,8 @@ void gck_rpc_layer_accept(void)
 
 	ds->socket = new_fd;
 	ds->cs.sock = new_fd;
+        ds->cs.read = &read_all;
+        ds->cs.write = &write_all;
 
 	error = pthread_create(&ds->thread, NULL,
 			       run_dispatch_thread, &(ds->cs));
@@ -2236,6 +2240,18 @@ void gck_rpc_layer_accept(void)
 	pthread_mutex_unlock(&pkcs11_dispatchers_mutex);
 }
 
+void gck_rpc_layer_inetd(void)
+{
+   CallState cs;
+
+   memset(&cs, 0, sizeof(cs));
+   cs.sock = STDIN_FILENO;
+   cs.read = &read;
+   cs.write = &write;
+
+   run_dispatch_thread(&cs);
+}
+
 int gck_rpc_layer_initialize(const char *prefix, CK_FUNCTION_LIST_PTR module)
 {
 	struct sockaddr_un addr;
diff --git a/gck-rpc-layer.h b/gck-rpc-layer.h
index 8a6318fe34b19a39de5b9ef1cf33f79ab5050aed..be6cdeb0c2e8c26692282d2b9c7e5c217971c7a0 100644
--- a/gck-rpc-layer.h
+++ b/gck-rpc-layer.h
@@ -16,4 +16,7 @@ void gck_rpc_layer_uninitialize(void);
 /* Accept a new connection. Should be called when above fd has read */
 void gck_rpc_layer_accept(void);
 
+/* Run a single connection off of STDIN - call from inetd or stunnel */
+void gck_rpc_layer_inetd(void);
+
 #endif /* GCKRPC_LAYER_H_ */