--- libaitrpc/src/cli.c 2011/08/18 15:08:03 1.3 +++ libaitrpc/src/cli.c 2011/08/19 09:20:47 1.3.2.1 @@ -3,7 +3,7 @@ * by Michael Pounov * * $Author: misho $ -* $Id: cli.c,v 1.3 2011/08/18 15:08:03 misho Exp $ +* $Id: cli.c,v 1.3.2.1 2011/08/19 09:20:47 misho Exp $ * ************************************************************************** The ELWIX and AITNET software is distributed under the following @@ -49,17 +49,22 @@ SUCH DAMAGE. /* * rpc_cli_openBLOBClient() Connect to BLOB Server * @rpccli = RPC Client session + * @sockType = Socket type, like SOCK_STREAM, SOCK_DGRAM or SOCK_RAW * @Port = Port for bind server, if Port == 0 default port is selected * return: NULL == error or !=NULL connection to BLOB server established */ rpc_cli_t * -rpc_cli_openBLOBClient(rpc_cli_t * __restrict rpccli, u_short Port) +rpc_cli_openBLOBClient(rpc_cli_t * __restrict rpccli, int sockType, u_short Port) { rpc_cli_t *cli = NULL; - struct sockaddr_in sin; - struct sockaddr_in6 sin6; + struct sockaddr sa; + struct sockaddr_in *sin = (struct sockaddr_in*) &sa; + struct sockaddr_in6 *sin6 = (struct sockaddr_in6*) &sa; + struct sockaddr_un *sun = (struct sockaddr_un*) &sa; - if (!rpccli || (rpccli->cli_sa.sa_family != AF_INET && rpccli->cli_sa.sa_family != AF_INET6)) { + if (!rpccli || + (rpccli->cli_sa.sa_family != AF_INET && rpccli->cli_sa.sa_family != AF_INET6 && + rpccli->cli_sa.sa_family != AF_LOCAL)) { rpc_SetErr(EINVAL, "Error:: Invalid parameters can`t connect to BLOB server ...\n"); return NULL; } @@ -73,17 +78,25 @@ rpc_cli_openBLOBClient(rpc_cli_t * __restrict rpccli, } else memcpy(cli, rpccli, sizeof(rpc_cli_t)); - if (rpccli->cli_sa.sa_family == AF_INET) { - memcpy(&sin, &rpccli->cli_sa, sizeof sin); - sin.sin_port = htons(Port); - memcpy(&cli->cli_sa, &sin, sizeof(struct sockaddr)); - } else { - memcpy(&sin6, &rpccli->cli_sa, sizeof sin6); - sin6.sin6_port = htons(Port); - memcpy(&cli->cli_sa, &sin6, sizeof(struct sockaddr)); + memcpy(&sa, &rpccli->cli_sa, sizeof sa); + switch (rpccli->cli_sa.sa_family) { + case AF_INET: + sin->sin_port = htons(Port); + memcpy(&cli->cli_sa, sin, sizeof(struct sockaddr)); + break; + case AF_INET6: + sin6->sin6_port = htons(Port); + memcpy(&cli->cli_sa, sin6, sizeof(struct sockaddr)); + break; + case AF_LOCAL: + strlcat(sun->sun_path, ".blob", sizeof sun->sun_path); + memcpy(&cli->cli_sa, sun, sizeof(struct sockaddr)); + break; } - cli->cli_sock = socket(cli->cli_sa.sa_family, SOCK_STREAM, 0); + /* connect to BLOB server */ + cli->cli_type = sockType ? sockType : SOCK_STREAM; + cli->cli_sock = socket(cli->cli_sa.sa_family, cli->cli_type, 0); if (cli->cli_sock == -1) { LOGERR; free(cli); @@ -124,49 +137,55 @@ rpc_cli_closeBLOBClient(rpc_cli_t * __restrict cli) * rpc_cli_openClient() Connect to RPC Server * @ProgID = ProgramID for RPC session request * @ProcID = ProcessID for RPC session request + * @sockType = Socket type, like SOCK_STREAM, SOCK_DGRAM or SOCK_RAW * @family = Family socket type, AF_INET or AF_INET6 * @csHost = Host name or IP address for bind server * @Port = Port for bind server, if Port == 0 default port is selected * return: NULL == error or !=NULL connection to RPC server established */ rpc_cli_t * -rpc_cli_openClient(u_int ProgID, u_int ProcID, u_short family, const char *csHost, u_short Port) +rpc_cli_openClient(u_int ProgID, u_int ProcID, int sockType, u_short family, const char *csHost, u_short Port) { rpc_cli_t *cli = NULL; struct hostent *host = NULL; - struct sockaddr_in sin; - struct sockaddr_in6 sin6; + struct sockaddr sa; + struct sockaddr_in *sin = (struct sockaddr_in*) &sa; + struct sockaddr_in6 *sin6 = (struct sockaddr_in6*) &sa; + struct sockaddr_un *sun = (struct sockaddr_un*) &sa; - if (!csHost || (family != AF_INET && family != AF_INET6)) { + if (!csHost || (family != AF_INET && family != AF_INET6 && family != AF_LOCAL)) { rpc_SetErr(EINVAL, "Error:: Invalid parameters can`t connect to RPC server ...\n"); return NULL; } if (!Port) Port = RPC_DEFPORT; - if (csHost) { + if (csHost && family != AF_LOCAL) { host = gethostbyname2(csHost, family); if (!host) { rpc_SetErr(h_errno, "Error:: %s\n", hstrerror(h_errno)); return NULL; } } + memset(&sa, 0, sizeof sa); + sa.sa_family = family; switch (family) { case AF_INET: - memset(&sin, 0, sizeof sin); - sin.sin_len = sizeof sin; - sin.sin_family = family; - sin.sin_port = htons(Port); + sin->sin_len = sizeof(struct sockaddr_in); + sin->sin_port = htons(Port); if (csHost) - memcpy(&sin.sin_addr, host->h_addr, host->h_length); + memcpy(&sin->sin_addr, host->h_addr, host->h_length); break; case AF_INET6: - memset(&sin6, 0, sizeof sin6); - sin6.sin6_len = sizeof sin6; - sin6.sin6_family = family; - sin6.sin6_port = htons(Port); + sin6->sin6_len = sizeof(struct sockaddr_in6); + sin6->sin6_port = htons(Port); if (csHost) - memcpy(&sin6.sin6_addr, host->h_addr, host->h_length); + memcpy(&sin6->sin6_addr, host->h_addr, host->h_length); break; + case AF_LOCAL: + sun->sun_len = sizeof(struct sockaddr_un); + if (csHost) + strlcpy(sun->sun_path, csHost, sizeof sun->sun_path); + break; default: rpc_SetErr(EINVAL, "Error:: Invalid parameters can`t connect to RPC server ...\n"); return NULL; @@ -189,11 +208,21 @@ rpc_cli_openClient(u_int ProgID, u_int ProcID, u_short ((rpc_sess_t*) cli->cli_parent)->sess_process = ProcID; } - if (family == AF_INET) - memcpy(&cli->cli_sa, &sin, sizeof cli->cli_sa); - else - memcpy(&cli->cli_sa, &sin6, sizeof cli->cli_sa); - cli->cli_sock = socket(family, SOCK_STREAM, 0); + switch (family) { + case AF_INET: + memcpy(&cli->cli_sa, sin, sizeof cli->cli_sa); + break; + case AF_INET6: + memcpy(&cli->cli_sa, sin6, sizeof cli->cli_sa); + break; + case AF_LOCAL: + memcpy(&cli->cli_sa, sun, sizeof cli->cli_sa); + break; + } + + /* connect to RPC server */ + cli->cli_type = sockType ? sockType : SOCK_STREAM; + cli->cli_sock = socket(family, cli->cli_type, 0); if (cli->cli_sock == -1) { LOGERR; free(cli->cli_parent);