diff options
| author | Paul Donald | 2025-12-20 22:47:03 +0000 |
|---|---|---|
| committer | Álvaro Fernández Rojas | 2025-12-22 11:11:01 +0000 |
| commit | 65f9ee25e5ebb92f1165348b40bbc0d2dbf56564 (patch) | |
| tree | 8c2a0725fd6e982b1c0fed96ff9bebf31714f46a | |
| parent | 48dbd38122e4ddf361042529ec95175fab847bfc (diff) | |
| download | odhcp6c-65f9ee25e5ebb92f1165348b40bbc0d2dbf56564.tar.gz | |
dhcpv6: offload FQDN construction to init_dhcpv6
Improve performance by doing this only once at init, instead
of every time at dhcpv6_send.
We also add a length check for dn_comp which can return -1.
Signed-off-by: Paul Donald <newtwen+github@gmail.com>
Link: https://github.com/openwrt/odhcp6c/pull/143
Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
| -rw-r--r-- | src/dhcpv6.c | 41 | ||||
| -rw-r--r-- | src/odhcp6c.h | 1 |
2 files changed, 28 insertions, 14 deletions
diff --git a/src/dhcpv6.c b/src/dhcpv6.c index f3e0be1..1f21004 100644 --- a/src/dhcpv6.c +++ b/src/dhcpv6.c @@ -583,6 +583,30 @@ int init_dhcpv6(const char *ifname) if (fd_set_nonblocking(sock) < 0) goto failure; + // Build our FQDN + size_t fqdn_len; + odhcp6c_get_state(STATE_OUR_FQDN, &fqdn_len); + if(fqdn_len == 0) { + char fqdn_buf[256]; + gethostname(fqdn_buf, sizeof(fqdn_buf)); + struct { + uint16_t type; + uint16_t len; + uint8_t flags; + uint8_t data[256]; + } fqdn = {0}; + int dn_result = dn_comp(fqdn_buf, fqdn.data, + sizeof(fqdn.data), NULL, NULL); + fqdn_len = 0; + if (dn_result > 0) { + fqdn.type = htons(DHCPV6_OPT_FQDN); + fqdn.len = htons(1 + dn_result); + fqdn.flags = 0; + fqdn_len = DHCPV6_OPT_HDR_SIZE + 1 + dn_result; + } + odhcp6c_add_state(STATE_OUR_FQDN, &fqdn, fqdn_len); + } + // Create client DUID size_t client_id_len; odhcp6c_get_state(STATE_CLIENT_ID, &client_id_len); @@ -707,19 +731,8 @@ int dhcpv6_get_ia_mode(void) static void dhcpv6_send(enum dhcpv6_msg req_msg_type, uint8_t trid[3], uint32_t ecs) { // Build FQDN - char fqdn_buf[256]; - gethostname(fqdn_buf, sizeof(fqdn_buf)); - struct { - uint16_t type; - uint16_t len; - uint8_t flags; - uint8_t data[256]; - } fqdn; - size_t fqdn_len = 5 + dn_comp(fqdn_buf, fqdn.data, - sizeof(fqdn.data), NULL, NULL); - fqdn.type = htons(DHCPV6_OPT_FQDN); - fqdn.len = htons(fqdn_len - DHCPV6_OPT_HDR_SIZE); - fqdn.flags = 0; + size_t fqdn_len; + void *fqdn = odhcp6c_get_state(STATE_OUR_FQDN, &fqdn_len); // Build Client ID size_t cl_id_len; @@ -934,7 +947,7 @@ static void dhcpv6_send(enum dhcpv6_msg req_msg_type, uint8_t trid[3], uint32_t [IOV_SRV_ID] = {srv_id, srv_id_len}, [IOV_OPTS] = { opts, opts_len }, [IOV_RECONF_ACCEPT] = {&reconf_accept, sizeof(reconf_accept)}, - [IOV_FQDN] = {&fqdn, fqdn_len}, + [IOV_FQDN] = {fqdn, fqdn_len}, [IOV_HDR_IA_NA] = {&hdr_ia_na, sizeof(hdr_ia_na)}, [IOV_IA_NA] = {ia_na, ia_na_len}, [IOV_IA_PD] = {ia_pd, ia_pd_len}, diff --git a/src/odhcp6c.h b/src/odhcp6c.h index c57f885..8405439 100644 --- a/src/odhcp6c.h +++ b/src/odhcp6c.h @@ -415,6 +415,7 @@ struct dhcpv6_stats { enum odhcp6c_state { STATE_CLIENT_ID, STATE_SERVER_ID, + STATE_OUR_FQDN, STATE_SERVER_CAND, STATE_SERVER_ADDR, STATE_ORO, |