--- libaitrpc/src/srv.c 2011/07/14 00:38:50 1.2.2.1 +++ libaitrpc/src/srv.c 2011/07/14 01:37:02 1.2.2.3 @@ -3,7 +3,7 @@ * by Michael Pounov * * $Author: misho $ -* $Id: srv.c,v 1.2.2.1 2011/07/14 00:38:50 misho Exp $ +* $Id: srv.c,v 1.2.2.3 2011/07/14 01:37:02 misho Exp $ * ************************************************************************** The ELWIX and AITNET software is distributed under the following @@ -54,7 +54,7 @@ rpc_srv_dispatchCall(void *arg) rpc_val_t *vals = NULL, *v = NULL; rpc_func_t *f; struct tagRPCCall *rpc; - struct tagRPCRet rrpc; + struct tagRPCRet *rrpc; fd_set fds; u_char buf[BUFSIZ], *data; int ret, argc = 0, Limit = 0; @@ -74,7 +74,6 @@ rpc_srv_dispatchCall(void *arg) if (ret == -1) { ret = -2; } - memset(&rrpc, 0, sizeof rrpc); memset(buf, 0, BUFSIZ); if ((ret = recv(c->cli_sock, buf, BUFSIZ, 0)) == -1) { LOGERR; @@ -158,27 +157,39 @@ rpc_srv_dispatchCall(void *arg) argc = rpc_srv_getValsCall(f, &vals); makeReply: - memcpy(&rrpc.ret_session, &rpc->call_session, sizeof rrpc.ret_session); - rrpc.ret_tag = rpc->call_tag; - rrpc.ret_hash = rpc->call_hash; - rrpc.ret_errno = rpc_Errno; - rrpc.ret_retcode = ret; - rrpc.ret_argc = argc; - memset(buf, 0, BUFSIZ); - memcpy(buf, &rrpc, (Limit = sizeof rrpc)); + rrpc = (struct tagRPCRet*) buf; + Limit = sizeof(struct tagRPCRet); + + memcpy(&rrpc->ret_session, &rpc->call_session, sizeof rrpc->ret_session); + rrpc->ret_tag = rpc->call_tag; + rrpc->ret_hash = rpc->call_hash; + rrpc->ret_errno = rpc_Errno; + rrpc->ret_retcode = ret; + rrpc->ret_argc = argc; + if (argc && vals) { - v = (rpc_val_t*) (buf + sizeof rrpc); + v = (rpc_val_t*) (buf + Limit); + if (argc * sizeof(rpc_val_t) > BUFSIZ - Limit) { + for (i = 0; i < argc; i++) + RPC_FREE_VAL(&vals[i]); + free(vals); + vals = NULL; + argc = 0; + ret = -7; + rpc_SetErr(EMSGSIZE, "Error:: in prepare RPC packet values (-7) ...\n"); + goto makeReply; + } else + Limit += argc * sizeof(rpc_val_t); memcpy(v, vals, argc * sizeof(rpc_val_t)); - Limit += argc * sizeof(rpc_val_t); data = (u_char*) v + argc * sizeof(rpc_val_t); for (ret = i = 0; i < argc; i++) { switch (vals[i].val_type) { case buffer: if (ret || Limit + vals[i].val_len > BUFSIZ) { rpc_SetErr(EMSGSIZE, "Error:: in prepare RPC packet (-7) ...\n"); - rrpc.ret_retcode = ret = -7; - rrpc.ret_argc = 0; + rrpc->ret_retcode = ret = -7; + rrpc->ret_argc = 0; break; } @@ -187,22 +198,22 @@ makeReply: Limit += vals[i].val_len; break; case string: - if (ret || Limit + vals[i].val_len + 1 > BUFSIZ) { + if (ret || Limit + vals[i].val_len > BUFSIZ) { rpc_SetErr(EMSGSIZE, "Error:: in prepare RPC packet (-7) ...\n"); - rrpc.ret_retcode = ret = -7; - rrpc.ret_argc = 0; + rrpc->ret_retcode = ret = -7; + rrpc->ret_argc = 0; break; } - memcpy(data, vals[i].val.string, vals[i].val_len + 1); - data += vals[i].val_len + 1; - Limit += vals[i].val_len + 1; + memcpy(data, vals[i].val.string, vals[i].val_len); + data += vals[i].val_len; + Limit += vals[i].val_len; break; case blob: if (s->srv_blob.state == disable) { rpc_SetErr(ENOTSUP, "Error:: BLOB server is disabled\n"); - rrpc.ret_retcode = ret = -5; - rrpc.ret_argc = 0; + rrpc->ret_retcode = ret = -5; + rrpc->ret_argc = 0; break; } default: @@ -211,6 +222,8 @@ makeReply: RPC_FREE_VAL(&vals[i]); } + free(vals); + vals = NULL; } if ((ret = send(c->cli_sock, buf, Limit, 0)) == -1) {