static void info_resp_handler(int err, const struct sip_msg *msg, void *arg, void *user_data) { struct sipsess_request *req = arg; if (err || sip_request_loops(&req->ls, msg->scode)) goto out; if (msg->scode < 200) { return; } else if (msg->scode < 300) { ; } else { if (req->sess->terminated) goto out; switch (msg->scode) { case 401: case 407: err = sip_auth_authenticate(req->sess->auth, msg); if (err) { err = (err == EAUTH) ? 0 : err; break; } err = info_request(req); if (err) break; return; case 408: case 481: sipsess_terminate(req->sess, 0, msg); break; } } out: if (!req->sess->terminated) { if (err == ETIMEDOUT) sipsess_terminate(req->sess, err, NULL); else req->resph(err, msg, req->arg, NULL); } mem_deref(req); }
static void bye_handler(struct sipsess_sock *sock, const struct sip_msg *msg) { struct sip *sip = sock->sip; struct sipsess *sess; sess = sipsess_find(sock, msg); if (!sess) { (void)sip_reply(sip, msg, 481, "Call Does Not Exist"); return; } if (!sip_dialog_rseq_valid(sess->dlg, msg)) { (void)sip_reply(sip, msg, 500, "Server Internal Error"); return; } (void)sip_treplyf(NULL, NULL, sip, msg, false, 200, "OK", "%s" "Content-Length: 0\r\n" "\r\n", sess->close_hdrs); sess->peerterm = true; if (sess->terminated) return; if (sess->st) { (void)sip_treply(&sess->st, sess->sip, sess->msg, 487, "Request Terminated"); } sipsess_terminate(sess, ECONNRESET, NULL); }
static void bye_handler(struct sipsess_sock *sock, const struct sip_msg *msg) { struct sip *sip = sock->sip; struct sipsess *sess; sess = sipsess_find(sock, msg); if (!sess) { (void)sip_reply(sip, msg, 481, "Call Does Not Exist"); return; } if (!sip_dialog_rseq_valid(sess->dlg, msg)) { (void)sip_reply(sip, msg, 500, "Server Internal Error"); return; } (void)sip_treply(NULL, sip, msg, 200, "OK"); sess->peerterm = true; if (sess->terminated) return; if (sess->st) { (void)sip_treply(&sess->st, sess->sip, sess->msg, 487, "Request Terminated"); } sipsess_terminate(sess, E_SIP_SESSION_CLOSED_BYE, NULL); }
static void cancel_handler(void *arg) { struct sipsess *sess = arg; (void)sip_treply(&sess->st, sess->sip, sess->msg, 487, "Request Terminated"); sess->peerterm = true; if (sess->terminated) return; sipsess_terminate(sess, ECONNRESET, NULL); }
static void tmr_handler(void *arg) { struct sipsess_reply *reply = arg; struct sipsess *sess = reply->sess; mem_deref(reply); /* wait for all pending ACKs */ if (sess->replyl.head) return; /* we want to send bye */ sess->established = true; if (!sess->terminated) sipsess_terminate(sess, ETIMEDOUT, NULL); else mem_deref(sess); }
static void ack_handler(struct sipsess_sock *sock, const struct sip_msg *msg) { struct sipsess *sess; bool awaiting_answer; int err = 0; sess = sipsess_find(sock, msg); if (!sess) return; if (sipsess_reply_ack(sess, msg, &awaiting_answer)) return; if (sess->terminated) { if (!sess->replyl.head) { sess->established = true; mem_deref(sess); } return; } if (awaiting_answer) { sess->awaiting_answer = false; err = sess->answerh(msg, sess->arg); } if (sess->modify_pending && !sess->replyl.head) (void)sipsess_reinvite(sess, true); if (sess->established) return; sess->msg = mem_deref((void *)sess->msg); sess->established = true; if (err) sipsess_terminate(sess, err, NULL); else sess->estabh(msg, sess->arg); }
static void bye_handler(struct sipsess_sock *sock, const struct sip_msg *msg) { struct sip *sip = sock->sip; struct sipsess *sess; // char tmp[256]; sess = sipsess_find(sock, msg); if (!sess) { (void)sip_reply(sip, msg, 481, "Call Does Not Exist"); return; } if (!sip_dialog_rseq_valid(sess->dlg, msg)) { (void)sip_reply(sip, msg, 500, "Server Internal Error"); return; } /* QXIP */ if (sess->xrtpstats && !sess->xrtpstats[0] == '\0') { /* Inject X-RTP-Stat header */ (void)sip_treplyf(NULL, NULL, sip, msg, false, 200, "OK", "X-RTP-Stat: %s\r\nContent-Length: 0\r\n\r\n", sess->xrtpstats); } else { /* Vanilla 200 OK */ (void)sip_treply(NULL, sip, msg, 200, "OK"); } sess->peerterm = true; if (sess->terminated) return; if (sess->st) { (void)sip_treply(&sess->st, sess->sip, sess->msg, 487, "Request Terminated"); } sipsess_terminate(sess, ECONNRESET, NULL); }
static void invite_resp_handler(int err, const struct sip_msg *msg, void *arg) { struct sipsess *sess = arg; struct mbuf *desc = NULL; if (err || sip_request_loops(&sess->ls, msg->scode)) goto out; if (msg->scode < 200) { sess->progrh(msg, sess->arg); return; } else if (msg->scode < 300) { sess->hdrs = mem_deref(sess->hdrs); err = sip_dialog_create(sess->dlg, msg); if (err) goto out; if (sess->sent_offer) err = sess->answerh(msg, sess->arg); else { sess->modify_pending = false; err = sess->offerh(&desc, msg, sess->arg); } int err2 = sipsess_ack(sess->sock, sess->dlg, msg->cseq.num, sess->auth, sess->ctype, desc); if (err2) printf("sipsess - sent first ACK for call %.*s, got err %d (%s)\n", msg->callid.l, msg->callid.p, err2, strerror(err2)); err |= err2; sess->established = true; mem_deref(desc); if (err || sess->terminated) goto out; if (sess->modify_pending) (void)sipsess_reinvite(sess, true); else sess->desc = mem_deref(sess->desc); sess->estabh(msg, sess->arg); return; } else if (msg->scode < 400) { /* Redirect to first Contact */ if (sess->terminated) goto out; err = sip_dialog_update(sess->dlg, msg); if (err) goto out; err = invite(sess); if (err) goto out; return; } else { if (sess->terminated) goto out; switch (msg->scode) { case 401: case 407: err = sip_auth_authenticate(sess->auth, msg); if (err) { err = (err == EAUTH) ? 0 : err; break; } err = invite(sess); if (err) break; return; } } out: if (!sess->terminated) sipsess_terminate(sess, err, msg); else mem_deref(sess); }