Skip to content

Commit ea2dfa4

Browse files
sip/transp: add client certificate to all TLS transports (#1173)
Currently, when a client certificate is added to a SIP transport, it is only added to the first matching transport in the transport list. Then, if multiple SIP transports exist (e.g if there are multiple network interfaces), the certificate might not be present in the transport when it is needed. Now, the certificate is added to all matching transports.
1 parent fe0c201 commit ea2dfa4

File tree

1 file changed

+64
-23
lines changed

1 file changed

+64
-23
lines changed

src/sip/transp.c

+64-23
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,12 @@ struct sip_ccert {
4747
};
4848

4949

50+
struct sip_ccert_data {
51+
uint32_t hsup;
52+
struct sip_ccert *ccert;
53+
};
54+
55+
5056
struct sip_transport {
5157
struct le le;
5258
struct sa laddr;
@@ -191,6 +197,31 @@ static const struct sip_transport *transp_find(struct sip *sip,
191197
}
192198

193199

200+
static struct le *transp_apply_all(struct sip *sip, enum sip_transp tp, int af,
201+
list_apply_h ah, void *arg)
202+
{
203+
if (!ah)
204+
return NULL;
205+
206+
for (struct le *le = sip->transpl.head; le; le = le->next) {
207+
208+
const struct sip_transport *transp = le->data;
209+
const struct sa *laddr = &transp->laddr;
210+
211+
if (transp->tp != tp)
212+
continue;
213+
214+
if (af != AF_UNSPEC && sa_af(laddr) != af)
215+
continue;
216+
217+
if (ah(le, arg))
218+
return le;
219+
}
220+
221+
return NULL;
222+
}
223+
224+
194225
static struct sip_conn *conn_find(struct sip *sip, const struct sa *paddr,
195226
bool secure)
196227
{
@@ -1401,6 +1432,27 @@ int sip_transp_add_websock(struct sip *sip, enum sip_transp tp,
14011432
}
14021433

14031434

1435+
static bool add_ccert_handler(struct le *le, void *arg)
1436+
{
1437+
const struct sip_transport *transp = le->data;
1438+
struct sip_ccert_data *cc = arg;
1439+
1440+
if (!cc->ccert->he.list)
1441+
hash_append(transp->ht_ccert, cc->hsup, &cc->ccert->he,
1442+
cc->ccert);
1443+
else {
1444+
struct sip_ccert *ccert = mem_zalloc(sizeof(*ccert), NULL);
1445+
if (!ccert)
1446+
return false;
1447+
1448+
ccert->file = cc->ccert->file;
1449+
hash_append(transp->ht_ccert, cc->hsup, &ccert->he, ccert);
1450+
}
1451+
1452+
return false;
1453+
}
1454+
1455+
14041456
/**
14051457
* Add a client certificate to the TLS transport object
14061458
* Client certificates are saved as hash-table.
@@ -1416,10 +1468,9 @@ int sip_transp_add_ccert(struct sip *sip, const struct uri *uri,
14161468
const char *cert)
14171469
{
14181470
int err = 0;
1419-
const struct sip_transport *transp = NULL;
14201471
struct sip_ccert *ccert = NULL;
1472+
struct sip_ccert_data cc_data;
14211473
struct mbuf *sup = NULL;
1422-
uint32_t hsup = 0;
14231474

14241475
if (!sip || !uri || !cert)
14251476
return EINVAL;
@@ -1435,30 +1486,20 @@ int sip_transp_add_ccert(struct sip *sip, const struct uri *uri,
14351486

14361487
mbuf_set_pos(sup, 0);
14371488

1438-
hsup = hash_joaat(mbuf_buf(sup), mbuf_get_left(sup));
1439-
transp = transp_find(sip, SIP_TRANSP_TLS, AF_INET, NULL);
1440-
if (transp) {
1441-
ccert = mem_zalloc(sizeof(*ccert), NULL);
1442-
if (!ccert) {
1443-
err = ENOMEM;
1444-
goto out;
1445-
}
1446-
1447-
pl_set_str(&ccert->file, cert);
1448-
hash_append(transp->ht_ccert, hsup, &ccert->he, ccert);
1489+
ccert = mem_zalloc(sizeof(*ccert), NULL);
1490+
if (!ccert) {
1491+
err = ENOMEM;
1492+
goto out;
14491493
}
1494+
pl_set_str(&ccert->file, cert);
14501495

1451-
transp = transp_find(sip, SIP_TRANSP_TLS, AF_INET6, NULL);
1452-
if (transp) {
1453-
ccert = mem_zalloc(sizeof(*ccert), NULL);
1454-
if (!ccert) {
1455-
err = ENOMEM;
1456-
goto out;
1457-
}
1496+
cc_data.hsup = hash_joaat(mbuf_buf(sup), mbuf_get_left(sup));
1497+
cc_data.ccert = ccert;
14581498

1459-
pl_set_str(&ccert->file, cert);
1460-
hash_append(transp->ht_ccert, hsup, &ccert->he, ccert);
1461-
}
1499+
(void)transp_apply_all(sip, SIP_TRANSP_TLS, AF_INET, add_ccert_handler,
1500+
&cc_data);
1501+
(void)transp_apply_all(sip, SIP_TRANSP_TLS, AF_INET6,
1502+
add_ccert_handler, &cc_data);
14621503

14631504
out:
14641505
mem_deref(sup);

0 commit comments

Comments
 (0)