diff --git a/feeds/packages/utils/pcsc-lite/patches/support-network-sockets.patch b/feeds/packages/utils/pcsc-lite/patches/support-network-sockets.patch new file mode 100644 index 0000000..d4fff6f --- /dev/null +++ b/feeds/packages/utils/pcsc-lite/patches/support-network-sockets.patch @@ -0,0 +1,298 @@ +diff --git a/src/winscard_clnt.c b/src/winscard_clnt.c +index 7cd85ff..8ec452a 100644 +--- a/src/winscard_clnt.c ++++ b/src/winscard_clnt.c +@@ -3513,6 +3513,7 @@ static LONG SCardGetContextAndChannelFromHandleTH(SCARDHANDLE hCard, + */ + LONG SCardCheckDaemonAvailability(void) + { ++#if 0 + LONG rv; + struct stat statBuffer; + char *socketName; +@@ -3526,6 +3527,7 @@ LONG SCardCheckDaemonAvailability(void) + socketName, strerror(errno)); + return SCARD_E_NO_SERVICE; + } ++#endif + + return SCARD_S_SUCCESS; + } +diff --git a/src/winscard_msg.c b/src/winscard_msg.c +index bd165d0..844c310 100644 +--- a/src/winscard_msg.c ++++ b/src/winscard_msg.c +@@ -49,6 +49,8 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + #include + #include + #include ++#include ++#include + #include + #include + #include +@@ -81,6 +83,7 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + #define member_size(type, member) sizeof(((type *)0)->member) + ++#if 0 + char *getSocketName(void) + { + static char socketName[member_size(struct sockaddr_un, sun_path)]; +@@ -102,6 +105,7 @@ char *getSocketName(void) + + return socketName; + } ++#endif + + /** + * @brief Prepares a communication channel for the client to talk to the server. +@@ -118,28 +122,86 @@ char *getSocketName(void) + */ + INTERNAL int ClientSetupSession(uint32_t *pdwClientID) + { +- struct sockaddr_un svc_addr; + int ret; +- char *socketName; + +- ret = socket(PF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0); +- if (ret < 0) ++ union + { +- Log2(PCSC_LOG_CRITICAL, "Error: create on client socket: %s", +- strerror(errno)); ++ struct sockaddr sa; ++ struct sockaddr_un un; ++ struct sockaddr_in in; ++ } sa; ++ ++ const char *socket_name = getenv("PCSCLITE_CSOCK_NAME"); ++ size_t sa_len = 0; ++ ++ if (!socket_name) ++ socket_name = PCSCLITE_CSOCK_NAME; ++ ++ if (socket_name[0] == '/') { ++ /* ++ * Create the common shared connection socket ++ */ ++ if ((*pdwClientID = socket(PF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0)) < 0) ++ { ++ Log2(PCSC_LOG_CRITICAL, "Unable to create socket: %s", ++ strerror(errno)); ++ return -1; ++ } ++ ++ memset(&sa, 0, sizeof sa); ++ sa.un.sun_family = AF_UNIX; ++ strncpy(sa.un.sun_path, socket_name, sizeof sa.un.sun_path); ++ ++ sa_len = sizeof(sa.un); ++ } else if (!strncmp(socket_name, "tcp:", 4)) { ++ char address[128]; ++ char *port; ++ struct sockaddr_in local; ++ ++ ++ if ((*pdwClientID = socket(PF_INET, SOCK_STREAM | SOCK_CLOEXEC, 0)) < 0) ++ { ++ Log2(PCSC_LOG_CRITICAL, "Unable to create socket: %s", ++ strerror(errno)); ++ return -1; ++ } ++ ++ strncpy(address, socket_name + 4, sizeof(address)); ++ address[sizeof(address) - 1] = 0; ++ ++ port = rindex(address, ':'); ++ if (port) ++ *(port++) = 0; ++ else ++ port = "3213"; ++ ++ ++ memset(&local, 0, sizeof(local)); ++ local.sin_family = AF_INET; ++ local.sin_port = 0; ++ local.sin_addr.s_addr = INADDR_ANY; ++ ++ if (bind(*pdwClientID, (struct sockaddr *) &local, sizeof(local))) { ++ Log2(PCSC_LOG_CRITICAL, "Unable to bind socket: %s", ++ strerror(errno)); ++ return -1; ++ } ++ ++ memset(&sa, 0, sizeof sa); ++ sa.in.sin_family = AF_INET; ++ sa.in.sin_port = htons(atoi(port)); ++ inet_aton(address, &sa.in.sin_addr); ++ ++ sa_len = sizeof(sa.in); ++ } else { ++ Log2(PCSC_LOG_CRITICAL, "unknown socket type: %s", socket_name); + return -1; + } +- *pdwClientID = ret; +- +- socketName = getSocketName(); +- svc_addr.sun_family = AF_UNIX; +- strncpy(svc_addr.sun_path, socketName, sizeof(svc_addr.sun_path)); + +- if (connect(*pdwClientID, (struct sockaddr *) &svc_addr, +- sizeof(svc_addr.sun_family) + strlen(svc_addr.sun_path) + 1) < 0) ++ if (connect(*pdwClientID, &sa.sa, sa_len) < 0) + { +- Log3(PCSC_LOG_CRITICAL, "Error: connect to client socket %s: %s", +- socketName, strerror(errno)); ++ Log3(PCSC_LOG_CRITICAL, "Error: connect %s: %s", ++ socket_name, strerror(errno)); + (void)close(*pdwClientID); + return -1; + } +@@ -148,7 +211,7 @@ INTERNAL int ClientSetupSession(uint32_t *pdwClientID) + if (ret < 0) + { + Log3(PCSC_LOG_CRITICAL, "Error: cannot retrieve socket %s flags: %s", +- socketName, strerror(errno)); ++ socket_name, strerror(errno)); + (void)close(*pdwClientID); + return -1; + } +@@ -156,7 +219,7 @@ INTERNAL int ClientSetupSession(uint32_t *pdwClientID) + if (fcntl(*pdwClientID, F_SETFL, ret | O_NONBLOCK) < 0) + { + Log3(PCSC_LOG_CRITICAL, "Error: cannot set socket %s nonblocking: %s", +- socketName, strerror(errno)); ++ socket_name, strerror(errno)); + (void)close(*pdwClientID); + return -1; + } +diff --git a/src/winscard_msg.h b/src/winscard_msg.h +index ad06042..3abfd9c 100644 +--- a/src/winscard_msg.h ++++ b/src/winscard_msg.h +@@ -276,7 +276,7 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + int32_t ListenExistingSocket(int fd); + int32_t ProcessEventsServer(/*@out@*/ uint32_t *); + #else +- char *getSocketName(void); ++// char *getSocketName(void); + int32_t ClientSetupSession(uint32_t *); + void ClientCloseSession(uint32_t); + LONG MessageReceiveTimeout(uint32_t command, /*@out@*/ void *buffer, +diff --git a/src/winscard_msg_srv.c b/src/winscard_msg_srv.c +index 7287279..5a5383f 100644 +--- a/src/winscard_msg_srv.c ++++ b/src/winscard_msg_srv.c +@@ -49,9 +49,12 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + #include + #include + #include ++#include ++#include + #include + #include + #include ++#include + #include + #include + #ifdef HAVE_SYS_FILIO_H +@@ -125,24 +128,76 @@ INTERNAL int32_t InitializeSocket(void) + { + struct sockaddr sa; + struct sockaddr_un un; ++ struct sockaddr_in in; + } sa; + +- /* +- * Create the common shared connection socket +- */ +- if ((commonSocket = socket(PF_UNIX, SOCK_STREAM, 0)) < 0) +- { +- Log2(PCSC_LOG_CRITICAL, "Unable to create common socket: %s", +- strerror(errno)); ++ const char *socket_name = getenv("PCSCLITE_CSOCK_NAME"); ++ size_t sa_len = 0; ++ ++ if (!socket_name) ++ socket_name = PCSCLITE_CSOCK_NAME; ++ ++ if (socket_name[0] == '/') { ++ /* ++ * Create the common shared connection socket ++ */ ++ if ((commonSocket = socket(PF_UNIX, SOCK_STREAM, 0)) < 0) ++ { ++ Log2(PCSC_LOG_CRITICAL, "Unable to create common socket: %s", ++ strerror(errno)); ++ return -1; ++ } ++ ++ memset(&sa, 0, sizeof sa); ++ sa.un.sun_family = AF_UNIX; ++ strncpy(sa.un.sun_path, socket_name, sizeof sa.un.sun_path); ++ (void)remove(socket_name); ++ ++ sa_len = sizeof(sa.un); ++ } else if (!strncmp(socket_name, "tcp:", 4)) { ++ char address[128]; ++ char *port; ++ int one = 1; ++ ++ if ((commonSocket = socket(PF_INET, SOCK_STREAM, 0)) < 0) ++ { ++ Log2(PCSC_LOG_CRITICAL, "Unable to create common socket: %s", ++ strerror(errno)); ++ return -1; ++ } ++ ++ if (setsockopt(commonSocket, SOL_SOCKET, SO_REUSEADDR, &one, sizeof(one)) < 0) { ++ Log2(PCSC_LOG_CRITICAL, "setsockopt(SO_REUSEADDR): %s", ++ strerror(errno)); ++ return -1; ++ } ++ ++ strncpy(address, socket_name + 4, sizeof(address)); ++ address[sizeof(address) - 1] = 0; ++ ++ port = rindex(address, ':'); ++ if (port) ++ *(port++) = 0; ++ else ++ port = "3213"; ++ ++ ++ fprintf(stderr,"port = %s\n",port); ++ ++ ++ memset(&sa, 0, sizeof sa); ++ sa.in.sin_family = AF_INET; ++ sa.in.sin_port = htons(atoi(port)); ++ inet_aton(address, &sa.in.sin_addr); ++ ++ sa_len = sizeof(sa.in); ++ } else { ++ Log2(PCSC_LOG_CRITICAL, "unknown socket type: %s", socket_name); + return -1; + } + +- memset(&sa, 0, sizeof sa); +- sa.un.sun_family = AF_UNIX; +- strncpy(sa.un.sun_path, PCSCLITE_CSOCK_NAME, sizeof sa.un.sun_path); +- (void)remove(PCSCLITE_CSOCK_NAME); + +- if (bind(commonSocket, &sa.sa, sizeof sa) < 0) ++ if (bind(commonSocket, &sa.sa, sa_len) < 0) + { + Log2(PCSC_LOG_CRITICAL, "Unable to bind common socket: %s", + strerror(errno)); +@@ -159,7 +214,8 @@ INTERNAL int32_t InitializeSocket(void) + /* + * Chmod the public entry channel + */ +- (void)chmod(PCSCLITE_CSOCK_NAME, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH); ++ if (socket_name[0] == '/') ++ (void)chmod(socket_name, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH); + + return 0; + }