static void invite_response(struct sip_ctrans *ct, const struct sip_msg *msg) { switch (ct->state) { case CALLING: tmr_cancel(&ct->tmr); tmr_cancel(&ct->tmre); /*@fallthrough@*/ case PROCEEDING: if (msg->scode < 200) { ct->state = PROCEEDING; ct->resph(0, msg, ct->arg); } else if (msg->scode < 300) { ct->resph(0, msg, ct->arg); mem_deref(ct); } else { ct->state = COMPLETED; (void)request_copy(&ct->mb_ack, ct, "ACK", msg); (void)sip_send(ct->sip, NULL, ct->tp, &ct->dst, ct->mb_ack); ct->resph(0, msg, ct->arg); if (sip_transp_reliable(ct->tp)) { mem_deref(ct); break; } tmr_start(&ct->tmr, COMPLETE_WAIT, tmr_handler, ct); } break; case COMPLETED: if (msg->scode < 300) break; (void)sip_send(ct->sip, NULL, ct->tp, &ct->dst, ct->mb_ack); break; default: break; } }
static void retransmit_handler(void *arg) { struct sipsess_reply *reply = arg; (void)sip_send(reply->sess->sip, reply->msg->sock, reply->msg->tp, &reply->msg->src, reply->mb); reply->txc++; tmr_start(&reply->tmrg, MIN(SIP_T1<<reply->txc, SIP_T2), retransmit_handler, reply); }
pj_status_t InstantMessaging::send_sip_message (pjsip_inv_session *session, std::string& id, const std::string& message) { /* Check the length of the message */ if (message.length() < getMessageMaximumSize()) { /* No problem here */ sip_send (session, id, message); } else { /* It exceeds the size limit of a SIP MESSAGE (1300 bytes), o plit it and send multiple messages */ std::vector<std::string> multiple_messages = split_message (message); /* Send multiple messages */ // int size = multiple_messages.size(); int i = 0; // Maximum is above 1500 character // TODO: Send every messages sip_send (session, id, multiple_messages[i]); } return PJ_SUCCESS; }
static int request(struct sip_request *req, enum sip_transp tp, const struct sa *dst) { struct mbuf *mb = NULL; char *branch = NULL; int err = ENOMEM; struct sa laddr; req->provrecv = false; branch = mem_alloc(24, NULL); mb = mbuf_alloc(1024); if (!branch || !mb) goto out; (void)re_snprintf(branch, 24, "z9hG4bK%016llx", rand_u64()); err = sip_transp_laddr(req->sip, &laddr, tp, dst); if (err) goto out; err = mbuf_printf(mb, "%s %s SIP/2.0\r\n", req->met, req->uri); err |= mbuf_printf(mb, "Via: SIP/2.0/%s %J;branch=%s;rport\r\n", sip_transp_name(tp), &laddr, branch); err |= req->sendh ? req->sendh(tp, &laddr, dst, mb, req->arg) : 0; err |= mbuf_write_mem(mb, mbuf_buf(req->mb), mbuf_get_left(req->mb)); if (err) goto out; mb->pos = 0; if (!req->stateful) err = sip_send(req->sip, NULL, tp, dst, mb); else err = sip_ctrans_request(&req->ct, req->sip, tp, dst, req->met, branch, mb, response_handler, req); if (err) goto out; out: mem_deref(branch); mem_deref(mb); return err; }