diff --git a/gck-rpc-dispatch.c b/gck-rpc-dispatch.c index 2ae87b7c12cc96a815ab826fa6a6287a4e96f92e..5cb46d44925171c406991081833316ea4243c711 100644 --- a/gck-rpc-dispatch.c +++ b/gck-rpc-dispatch.c @@ -71,9 +71,13 @@ static CK_FUNCTION_LIST_PTR pkcs11_module = NULL; #define return_val_if_fail(x, v) \ if (!(x)) { rpc_warn ("'%s' not true at %s", #x, __func__); return v; } -void gck_rpc_log(const char *line) +void gck_rpc_log(const char *msg, ...) { - printf("%s", line); + va_list ap; + + va_start(ap, msg); + vfprintf(stdout, msg, ap); + va_end(ap); } /* ------------------------------------------------------------------------------- @@ -84,7 +88,7 @@ typedef struct _CallState { GckRpcMessage *req; GckRpcMessage *resp; void *allocated; - CK_ULONG appid; + uint64_t appid; } CallState; static int call_init(CallState * cs) @@ -832,9 +836,7 @@ static CK_RV rpc_C_Finalize(CallState * cs) (pkcs11_module->C_GetSlotList) (TRUE, slots, &n_slots); for (i = 0; ret == CKR_OK && i < n_slots; ++i) { - appartment = - CK_GNOME_MAKE_APPARTMENT(slots[i], - cs->appid); + appartment = slots[i]; ret = (pkcs11_module-> C_CloseAllSessions) (appartment); @@ -880,7 +882,6 @@ static CK_RV rpc_C_GetSlotInfo(CallState * cs) BEGIN_CALL(C_GetSlotInfo); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); PROCESS_CALL((slot_id, &info)); OUT_SLOT_INFO(info); END_CALL; @@ -895,7 +896,6 @@ static CK_RV rpc_C_GetTokenInfo(CallState * cs) BEGIN_CALL(C_GetTokenInfo); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); PROCESS_CALL((slot_id, &info)); OUT_TOKEN_INFO(info); END_CALL; @@ -911,7 +911,6 @@ static CK_RV rpc_C_GetMechanismList(CallState * cs) BEGIN_CALL(C_GetMechanismList); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); IN_ULONG_BUFFER(mechanism_list, count); PROCESS_CALL((slot_id, mechanism_list, &count)); OUT_ULONG_ARRAY(mechanism_list, count); @@ -928,7 +927,6 @@ static CK_RV rpc_C_GetMechanismInfo(CallState * cs) BEGIN_CALL(C_GetMechanismInfo); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); IN_ULONG(type); PROCESS_CALL((slot_id, type, &info)); OUT_MECHANISM_INFO(info); @@ -946,7 +944,6 @@ static CK_RV rpc_C_InitToken(CallState * cs) BEGIN_CALL(C_InitToken); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); IN_BYTE_ARRAY(pin, pin_len); IN_STRING(label); PROCESS_CALL((slot_id, pin, pin_len, label)); @@ -978,7 +975,6 @@ static CK_RV rpc_C_OpenSession(CallState * cs) BEGIN_CALL(C_OpenSession); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); IN_ULONG(flags); PROCESS_CALL((slot_id, flags, NULL, NULL, &session)); OUT_ULONG(session); @@ -1003,7 +999,6 @@ static CK_RV rpc_C_CloseAllSessions(CallState * cs) BEGIN_CALL(C_CloseAllSessions); IN_ULONG(slot_id); - slot_id = CK_GNOME_MAKE_APPARTMENT(slot_id, cs->appid); PROCESS_CALL((slot_id)); END_CALL; } @@ -2062,7 +2057,11 @@ static void run_dispatch_loop(int sock) assert(sock != -1); /* The client application */ - cs.appid = 0; + if (!read_all(sock, (unsigned char *)&cs.appid, sizeof (cs.appid))) { + return ; + } + gck_rpc_log("New session %d-%d\n", (uint32_t) (cs.appid >> 32), + (uint32_t) cs.appid); /* Setup our buffers */ if (!call_init(&cs)) { @@ -2228,7 +2227,7 @@ int gck_rpc_layer_initialize(const char *prefix, CK_FUNCTION_LIST_PTR module) iResult = WSAStartup(MAKEWORD(2,2), &wsaData); if (iResult != 0) { - printf("WSAStartup failed: %d\n", iResult); + gck_rpc_warn("WSAStartup failed: %d\n", iResult); return -1; } } @@ -2334,7 +2333,7 @@ int gck_rpc_layer_initialize(const char *prefix, CK_FUNCTION_LIST_PTR module) "%s:%d", inet_ntoa(sa.sin_addr), ntohs(sa.sin_port)); } - printf("Listening on: %s\n", pkcs11_socket_path); + gck_rpc_log("Listening on: %s\n", pkcs11_socket_path); pkcs11_module = module; pkcs11_socket = sock; diff --git a/gck-rpc-module.c b/gck-rpc-module.c index c62162c1d1fed2101bd9a3ffce7f2e3871c1254d..add803e749c70b64f281c5e66b6c53eb7a686d20 100644 --- a/gck-rpc-module.c +++ b/gck-rpc-module.c @@ -62,6 +62,7 @@ static pthread_mutex_t init_mutex = PTHREAD_MUTEX_INITIALIZER; /* Whether we've been initialized, and on what process id it happened */ static int pkcs11_initialized = 0; static pid_t pkcs11_initialized_pid = 0; +static uint64_t pkcs11_app_id = 0; /* The socket to connect to */ static char pkcs11_socket_path[MAXPATHLEN] = { 0, }; @@ -84,9 +85,13 @@ static char pkcs11_socket_path[MAXPATHLEN] = { 0, }; #define return_val_if_fail(x, v) \ if (!(x)) { gck_rpc_warn ("'%s' not true at %s", #x, __func__); return v; } -void gck_rpc_log(const char *line) +void gck_rpc_log(const char *msg, ...) { - fprintf(stderr, "%s\n", line); + va_list ap; + + va_start(ap, msg); + vfprintf(stderr, msg, ap); + va_end(ap); } /* ----------------------------------------------------------------------------- @@ -218,6 +223,95 @@ static void *call_allocator(void *p, size_t sz) return res; } +static void call_disconnect(CallState * cs) +{ + assert(cs); + + if (cs->socket != -1) { + debug(("disconnected socket")); + close(cs->socket); + cs->socket = -1; + } +} + +/* Write all data to session socket. */ +static CK_RV call_write(CallState * cs, unsigned char *data, size_t len) +{ + int fd, r; + + assert(cs); + assert(data); + assert(len > 0); + + while (len > 0) { + + fd = cs->socket; + if (fd == -1) { + warning(("couldn't send data: socket has been closed")); + return CKR_DEVICE_ERROR; + } + + r = send(fd, data, len, 0); + + if (r == -1) { + if (errno == EPIPE) { + warning(("couldn't send data: daemon closed connection")); + call_disconnect(cs); + return CKR_DEVICE_ERROR; + } else if (errno != EAGAIN && errno != EINTR) { + warning(("couldn't send data: %s", + strerror(errno))); + return CKR_DEVICE_ERROR; + } + } else { + debug(("wrote %d bytes", r)); + data += r; + len -= r; + } + } + + return CKR_OK; +} + +/* Read a certain amount of data from session socket. */ +static CK_RV call_read(CallState * cs, unsigned char *data, size_t len) +{ + int fd, r; + + assert(cs); + assert(data); + assert(len > 0); + + while (len > 0) { + + fd = cs->socket; + if (fd == -1) { + warning(("couldn't receive data: session socket has been closed")); + return CKR_DEVICE_ERROR; + } + + r = recv(fd, data, len, 0); + + if (r == 0) { + warning(("couldn't receive data: daemon closed connection")); + call_disconnect(cs); + return CKR_DEVICE_ERROR; + } else if (r == -1) { + if (errno != EAGAIN && errno != EINTR) { + warning(("couldn't receive data: %s", + strerror(errno))); + return CKR_DEVICE_ERROR; + } + } else { + debug(("read %d bytes", r)); + data += r; + len -= r; + } + } + + return CKR_OK; +} + static CK_RV call_connect(CallState * cs) { struct sockaddr_un addr; @@ -304,18 +398,8 @@ static CK_RV call_connect(CallState * cs) cs->call_status = CALL_READY; debug(("connected socket")); - return CKR_OK; -} - -static void call_disconnect(CallState * cs) -{ - assert(cs); - - if (cs->socket != -1) { - debug(("disconnected socket")); - close(cs->socket); - cs->socket = -1; - } + return call_write(cs, (unsigned char*)&pkcs11_app_id, + sizeof(pkcs11_app_id)); } static void call_destroy(void *value) @@ -404,84 +488,6 @@ static CK_RV call_prepare(CallState * cs, int call_id) return CKR_OK; } -/* Write all data to session socket. */ -static CK_RV call_write(CallState * cs, unsigned char *data, size_t len) -{ - int fd, r; - - assert(cs); - assert(data); - assert(len > 0); - - while (len > 0) { - - fd = cs->socket; - if (fd == -1) { - warning(("couldn't send data: socket has been closed")); - return CKR_DEVICE_ERROR; - } - - r = send(fd, data, len, 0); - - if (r == -1) { - if (errno == EPIPE) { - warning(("couldn't send data: daemon closed connection")); - call_disconnect(cs); - return CKR_DEVICE_ERROR; - } else if (errno != EAGAIN && errno != EINTR) { - warning(("couldn't send data: %s", - strerror(errno))); - return CKR_DEVICE_ERROR; - } - } else { - debug(("wrote %d bytes", r)); - data += r; - len -= r; - } - } - - return CKR_OK; -} - -/* Read a certain amount of data from session socket. */ -static CK_RV call_read(CallState * cs, unsigned char *data, size_t len) -{ - int fd, r; - - assert(cs); - assert(data); - assert(len > 0); - - while (len > 0) { - - fd = cs->socket; - if (fd == -1) { - warning(("couldn't receive data: session socket has been closed")); - return CKR_DEVICE_ERROR; - } - - r = recv(fd, data, len, 0); - - if (r == 0) { - warning(("couldn't receive data: daemon closed connection")); - call_disconnect(cs); - return CKR_DEVICE_ERROR; - } else if (r == -1) { - if (errno != EAGAIN && errno != EINTR) { - warning(("couldn't receive data: %s", - strerror(errno))); - return CKR_DEVICE_ERROR; - } - } else { - debug(("read %d bytes", r)); - data += r; - len -= r; - } - } - - return CKR_OK; -} - /* * Used by call_session_do_call() to actually send the message to the daemon. * Note how we unlock and relock the session during the call. @@ -1255,6 +1261,9 @@ static CK_RV rpc_C_Initialize(CK_VOID_PTR init_args) } } + srand(time(NULL) ^ pid); + pkcs11_app_id = (uint64_t) rand() << 32 | rand(); + /* Call through and initialize the daemon */ ret = call_lookup(&cs); if (ret == CKR_OK) { diff --git a/gck-rpc-private.h b/gck-rpc-private.h index 403e6bd83a292eec70b0e8544112cd870e624983..22f897a3260e0833acfcd841f2426051cc151b59 100644 --- a/gck-rpc-private.h +++ b/gck-rpc-private.h @@ -293,7 +293,7 @@ int gck_rpc_message_read_space_string(GckRpcMessage * msg, int gck_rpc_message_read_version(GckRpcMessage * msg, CK_VERSION * version); -void gck_rpc_log(const char *line); +void gck_rpc_log(const char *msg, ...); void gck_rpc_warn(const char *msg, ...);