struct rtpp_command * get_command(struct cfg *cf, int controlfd, int *rval, double dtime, struct rtpp_command_stats *csp, int umode, struct rtpp_cmd_rcache_obj *rcache_obj) { char **ap; char *cp; int len, i; struct rtpp_command *cmd; cmd = malloc(sizeof(struct rtpp_command)); if (cmd == NULL) { *rval = ENOMEM; return (NULL); } memset(cmd, 0, sizeof(struct rtpp_command)); cmd->controlfd = controlfd; cmd->dtime = dtime; cmd->csp = csp; cmd->umode = umode; if (umode == 0) { for (;;) { len = read(controlfd, cmd->buf, sizeof(cmd->buf) - 1); if (len != -1 || (errno != EAGAIN && errno != EINTR)) break; } } else { cmd->rlen = sizeof(cmd->raddr); len = recvfrom(controlfd, cmd->buf, sizeof(cmd->buf) - 1, 0, sstosa(&cmd->raddr), &cmd->rlen); } if (len == -1) { if (errno != EAGAIN && errno != EINTR) rtpp_log_ewrite(RTPP_LOG_ERR, cf->stable->glog, "can't read from control socket"); free(cmd); *rval = -1; return (NULL); } cmd->buf[len] = '\0'; rtpp_log_write(RTPP_LOG_DBUG, cf->stable->glog, "received command \"%s\"", cmd->buf); csp->ncmds_rcvd.cnt++; cp = cmd->buf; for (ap = cmd->argv; (*ap = rtpp_strsep(&cp, "\r\n\t ")) != NULL;) { if (**ap != '\0') { cmd->argc++; if (++ap >= &cmd->argv[RTPC_MAX_ARGC]) break; } } if (cmd->argc < 1 || (umode != 0 && cmd->argc < 2)) { rtpp_log_write(RTPP_LOG_ERR, cf->stable->glog, "command syntax error"); reply_error(cf, cmd, ECODE_PARSE_1); *rval = 0; free(cmd); return (NULL); } /* Stream communication mode doesn't use cookie */ if (umode != 0) { cmd->cookie = cmd->argv[0]; if (CALL_METHOD(rcache_obj, lookup, cmd->cookie, cmd->buf_r, sizeof(cmd->buf_r)) == 1) { len = strlen(cmd->buf_r); rtpp_anetio_sendto(cf->stable->rtpp_netio_cf, cmd->controlfd, cmd->buf_r, len, 0, sstosa(&cmd->raddr), cmd->rlen); csp->ncmds_rcvd.cnt--; csp->ncmds_rcvd_ndups.cnt++; *rval = 0; free(cmd); return (NULL); } cmd->rcache_obj = rcache_obj; for (i = 1; i < cmd->argc; i++) cmd->argv[i - 1] = cmd->argv[i]; cmd->argc--; cmd->argv[cmd->argc] = NULL; } /* Step I: parse parameters that are common to all ops */ if (rtpp_command_pre_parse(cf, cmd) != 0) { /* Error reply is handled by the rtpp_command_pre_parse() */ *rval = 0; free(cmd); return (NULL); } return (cmd); }
struct rtpp_command * rtpp_command_stream_get(struct cfg *cf, struct rtpp_cmd_connection *rcs, int *rval, double dtime, struct rtpp_command_stats *csp) { char **ap; char *cp, *cp1; int len; struct rtpp_command *cmd; if (rcs->inbuf_epos == rcs->inbuf_ppos) { *rval = EAGAIN; return (NULL); } cp = &(rcs->inbuf[rcs->inbuf_ppos]); len = rcs->inbuf_epos - rcs->inbuf_ppos; cp1 = memchr(cp, '\n', len); if (cp1 == NULL) { *rval = EAGAIN; return (NULL); } cmd = rtpp_zmalloc(sizeof(struct rtpp_command)); if (cmd == NULL) { *rval = ENOMEM; return (NULL); } cmd->controlfd = rcs->controlfd_out; cmd->dtime = dtime; cmd->csp = csp; cmd->umode = 0; if (rcs->rlen > 0) { cmd->rlen = rcs->rlen; memcpy(&cmd->raddr, &rcs->raddr, rcs->rlen); } len = cp1 - cp; memcpy(cmd->buf, cp, len); cmd->buf[len] = '\0'; rcs->inbuf_ppos += len + 1; rtpp_log_write(RTPP_LOG_DBUG, cf->stable->glog, "received command \"%s\"", cmd->buf); csp->ncmds_rcvd.cnt++; cp = cmd->buf; for (ap = cmd->argv; (*ap = rtpp_strsep(&cp, "\r\n\t ")) != NULL;) { if (**ap != '\0') { cmd->argc++; if (++ap >= &cmd->argv[RTPC_MAX_ARGC]) break; } } if (cmd->argc < 1) { rtpp_log_write(RTPP_LOG_ERR, cf->stable->glog, "command syntax error"); reply_error(cf, cmd, ECODE_PARSE_1); *rval = EINVAL; free(cmd); return (NULL); } /* Step I: parse parameters that are common to all ops */ if (rtpp_command_pre_parse(cf, cmd) != 0) { /* Error reply is handled by the rtpp_command_pre_parse() */ *rval = 0; free(cmd); return (NULL); } return (cmd); }