From 43a050ca3d325320871f96f69e186007ab978815 Mon Sep 17 00:00:00 2001 From: Christian Spielberger Date: Fri, 22 Oct 2021 13:09:10 +0200 Subject: [PATCH] sipsess: add a function pointer for the content description This allows the application to postpone the encoding of the content description (e.g. the SDP) until the source address of the SIP transport is known. sipsess_connect() uses this for the INVITE. Other SIP session types do not set the new function pointer. --- include/re_sipsess.h | 5 +++- src/sipevent/notify.c | 4 ++- src/sipevent/subscribe.c | 4 ++- src/sipreg/reg.c | 4 ++- src/sipsess/accept.c | 2 +- src/sipsess/ack.c | 4 ++- src/sipsess/connect.c | 63 ++++++++++++++++++++++++++++++---------- src/sipsess/modify.c | 4 ++- src/sipsess/sess.c | 2 ++ src/sipsess/sipsess.h | 2 ++ 10 files changed, 71 insertions(+), 23 deletions(-) diff --git a/include/re_sipsess.h b/include/re_sipsess.h index c4be7ef02..36ac502ef 100644 --- a/include/re_sipsess.h +++ b/include/re_sipsess.h @@ -9,6 +9,8 @@ struct sipsess; typedef void (sipsess_conn_h)(const struct sip_msg *msg, void *arg); +typedef int (sipsess_desc_h)(struct mbuf **descp, const struct sa *src, + const struct sa *dst, void *arg); typedef int (sipsess_offer_h)(struct mbuf **descp, const struct sip_msg *msg, void *arg); typedef int (sipsess_answer_h)(const struct sip_msg *msg, void *arg); @@ -30,9 +32,10 @@ int sipsess_connect(struct sipsess **sessp, struct sipsess_sock *sock, const char *to_uri, const char *from_name, const char *from_uri, const char *cuser, const char *routev[], uint32_t routec, - const char *ctype, struct mbuf *desc, + const char *ctype, sip_auth_h *authh, void *aarg, bool aref, const char *callid, + sipsess_desc_h *desch, sipsess_offer_h *offerh, sipsess_answer_h *answerh, sipsess_progr_h *progrh, sipsess_estab_h *estabh, sipsess_info_h *infoh, sipsess_refer_h *referh, diff --git a/src/sipevent/notify.c b/src/sipevent/notify.c index 7a7a87d25..a9646afff 100644 --- a/src/sipevent/notify.c +++ b/src/sipevent/notify.c @@ -175,11 +175,13 @@ static void response_handler(int err, const struct sip_msg *msg, void *arg) static int send_handler(enum sip_transp tp, const struct sa *src, - const struct sa *dst, struct mbuf *mb, void *arg) + const struct sa *dst, struct mbuf *mb, + struct mbuf **contp, void *arg) { struct sip_contact contact; struct sipnot *not = arg; (void)dst; + (void)contp; sip_contact_set(&contact, not->cuser, src, tp); diff --git a/src/sipevent/subscribe.c b/src/sipevent/subscribe.c index fe6ba5628..c2be64e91 100644 --- a/src/sipevent/subscribe.c +++ b/src/sipevent/subscribe.c @@ -296,11 +296,13 @@ static void response_handler(int err, const struct sip_msg *msg, void *arg) static int send_handler(enum sip_transp tp, const struct sa *src, - const struct sa *dst, struct mbuf *mb, void *arg) + const struct sa *dst, struct mbuf *mb, + struct mbuf **contp, void *arg) { struct sip_contact contact; struct sipsub *sub = arg; (void)dst; + (void)contp; sip_contact_set(&contact, sub->cuser, src, tp); diff --git a/src/sipreg/reg.c b/src/sipreg/reg.c index e9a08f565..2bd56f8c7 100644 --- a/src/sipreg/reg.c +++ b/src/sipreg/reg.c @@ -265,12 +265,14 @@ static void response_handler(int err, const struct sip_msg *msg, void *arg) static int send_handler(enum sip_transp tp, const struct sa *src, - const struct sa *dst, struct mbuf *mb, void *arg) + const struct sa *dst, struct mbuf *mb, + struct mbuf **contp, void *arg) { struct sipreg *reg = arg; int err; (void)dst; + (void)contp; reg->laddr = *src; reg->tp = tp; diff --git a/src/sipsess/accept.c b/src/sipsess/accept.c index b8d02f849..1c79e610c 100644 --- a/src/sipsess/accept.c +++ b/src/sipsess/accept.c @@ -78,7 +78,7 @@ int sipsess_accept(struct sipsess **sessp, struct sipsess_sock *sock, return EINVAL; err = sipsess_alloc(&sess, sock, cuser, ctype, NULL, authh, aarg, aref, - offerh, answerh, NULL, estabh, infoh, referh, + NULL, offerh, answerh, NULL, estabh, infoh, referh, closeh, arg); if (err) return err; diff --git a/src/sipsess/ack.c b/src/sipsess/ack.c index 4a9be682a..adfc805d1 100644 --- a/src/sipsess/ack.c +++ b/src/sipsess/ack.c @@ -51,10 +51,12 @@ static void tmr_handler(void *arg) static int send_handler(enum sip_transp tp, const struct sa *src, - const struct sa *dst, struct mbuf *mb, void *arg) + const struct sa *dst, struct mbuf *mb, + struct mbuf **contp, void *arg) { struct sipsess_ack *ack = arg; (void)src; + (void)contp; mem_deref(ack->mb); ack->mb = mem_ref(mb); diff --git a/src/sipsess/connect.c b/src/sipsess/connect.c index 346a7d32b..265108008 100644 --- a/src/sipsess/connect.c +++ b/src/sipsess/connect.c @@ -23,15 +23,53 @@ static int invite(struct sipsess *sess); static int send_handler(enum sip_transp tp, const struct sa *src, - const struct sa *dst, struct mbuf *mb, void *arg) + const struct sa *dst, struct mbuf *mb, + struct mbuf **contp, void *arg) { struct sip_contact contact; struct sipsess *sess = arg; - (void)dst; + struct mbuf *desc = NULL; + struct mbuf *cont = NULL; + int err; + + if (sess->desch) { + err = sess->desch(&desc, src, dst, sess->arg); + if (err) + return err; + } sip_contact_set(&contact, sess->cuser, src, tp); + err = mbuf_printf(mb, "%H", sip_contact_print, &contact); + if (err) + goto out; - return mbuf_printf(mb, "%H", sip_contact_print, &contact); + cont = mbuf_alloc(1024); + if (!cont) { + err = ENOMEM; + goto out; + } + + err |= mbuf_printf(cont, + "%s%s%s" + "Content-Length: %zu\r\n" + "\r\n" + "%b", + desc ? "Content-Type: " : "", + desc ? sess->ctype : "", + desc ? "\r\n" : "", + mbuf_get_left(desc), + mbuf_buf(desc), + mbuf_get_left(desc)); + cont->pos = 0; + + if (err) + mem_deref(cont); + else + *contp = cont; + +out: + mem_deref(desc); + return err; } @@ -138,19 +176,10 @@ static int invite(struct sipsess *sess) return sip_drequestf(&sess->req, sess->sip, true, "INVITE", sess->dlg, 0, sess->auth, send_handler, invite_resp_handler, sess, - "%b" - "%s%s%s" - "Content-Length: %zu\r\n" - "\r\n" "%b", sess->hdrs ? mbuf_buf(sess->hdrs) : NULL, - sess->hdrs ? mbuf_get_left(sess->hdrs) :(size_t)0, - sess->desc ? "Content-Type: " : "", - sess->desc ? sess->ctype : "", - sess->desc ? "\r\n" : "", - sess->desc ? mbuf_get_left(sess->desc) :(size_t)0, - sess->desc ? mbuf_buf(sess->desc) : NULL, - sess->desc ? mbuf_get_left(sess->desc):(size_t)0); + sess->hdrs ? mbuf_get_left(sess->hdrs) :(size_t)0 + ); } @@ -186,9 +215,10 @@ int sipsess_connect(struct sipsess **sessp, struct sipsess_sock *sock, const char *to_uri, const char *from_name, const char *from_uri, const char *cuser, const char *routev[], uint32_t routec, - const char *ctype, struct mbuf *desc, + const char *ctype, sip_auth_h *authh, void *aarg, bool aref, const char *callid, + sipsess_desc_h *desch, sipsess_offer_h *offerh, sipsess_answer_h *answerh, sipsess_progr_h *progrh, sipsess_estab_h *estabh, sipsess_info_h *infoh, sipsess_refer_h *referh, @@ -200,7 +230,8 @@ int sipsess_connect(struct sipsess **sessp, struct sipsess_sock *sock, if (!sessp || !sock || !to_uri || !from_uri || !cuser || !ctype) return EINVAL; - err = sipsess_alloc(&sess, sock, cuser, ctype, desc, authh, aarg, aref, + err = sipsess_alloc(&sess, sock, cuser, ctype, NULL, authh, aarg, aref, + desch, offerh, answerh, progrh, estabh, infoh, referh, closeh, arg); if (err) diff --git a/src/sipsess/modify.c b/src/sipsess/modify.c index 452115fd5..9a88bdf26 100644 --- a/src/sipsess/modify.c +++ b/src/sipsess/modify.c @@ -107,11 +107,13 @@ static void reinvite_resp_handler(int err, const struct sip_msg *msg, static int send_handler(enum sip_transp tp, const struct sa *src, - const struct sa *dst, struct mbuf *mb, void *arg) + const struct sa *dst, struct mbuf *mb, + struct mbuf **contp, void *arg) { struct sip_contact contact; struct sipsess *sess = arg; (void)dst; + (void)contp; sip_contact_set(&contact, sess->cuser, src, tp); diff --git a/src/sipsess/sess.c b/src/sipsess/sess.c index f80017f48..b72f72e85 100644 --- a/src/sipsess/sess.c +++ b/src/sipsess/sess.c @@ -157,6 +157,7 @@ static void destructor(void *arg) int sipsess_alloc(struct sipsess **sessp, struct sipsess_sock *sock, const char *cuser, const char *ctype, struct mbuf *desc, sip_auth_h *authh, void *aarg, bool aref, + sipsess_desc_h *desch, sipsess_offer_h *offerh, sipsess_answer_h *answerh, sipsess_progr_h *progrh, sipsess_estab_h *estabh, sipsess_info_h *infoh, sipsess_refer_h *referh, @@ -184,6 +185,7 @@ int sipsess_alloc(struct sipsess **sessp, struct sipsess_sock *sock, sess->sock = mem_ref(sock); sess->desc = mem_ref(desc); sess->sip = mem_ref(sock->sip); + sess->desch = desch; sess->offerh = offerh ? offerh : internal_offer_handler; sess->answerh = answerh ? answerh : internal_answer_handler; sess->progrh = progrh ? progrh : internal_progress_handler; diff --git a/src/sipsess/sipsess.h b/src/sipsess/sipsess.h index a8f387b64..87b65cd8f 100644 --- a/src/sipsess/sipsess.h +++ b/src/sipsess/sipsess.h @@ -23,6 +23,7 @@ struct sipsess { char *close_hdrs; struct mbuf *hdrs; struct mbuf *desc; + sipsess_desc_h *desch; sipsess_offer_h *offerh; sipsess_answer_h *answerh; sipsess_progr_h *progrh; @@ -68,6 +69,7 @@ struct sipsess_request { int sipsess_alloc(struct sipsess **sessp, struct sipsess_sock *sock, const char *cuser, const char *ctype, struct mbuf *desc, sip_auth_h *authh, void *aarg, bool aref, + sipsess_desc_h *desch, sipsess_offer_h *offerh, sipsess_answer_h *answerh, sipsess_progr_h *progrh, sipsess_estab_h *estabh, sipsess_info_h *infoh, sipsess_refer_h *referh,