mirror of
https://github.com/systemd/systemd.git
synced 2024-12-22 17:35:35 +03:00
sd-dhcp6-client: support custom DUIDs
The caller may have an existing DUID that it wants to use, and may want to use some other DUID generation scheme than systemd's default DUID-EN. [tomegun: whitespace - we never use tabs]
This commit is contained in:
parent
995a1063db
commit
66eac1201a
@ -39,6 +39,8 @@
|
||||
#define SYSTEMD_PEN 43793
|
||||
#define HASH_KEY SD_ID128_MAKE(80,11,8c,c2,fe,4a,03,ee,3e,d6,0c,6f,36,39,14,09)
|
||||
|
||||
#define MAX_DUID_LEN 32
|
||||
|
||||
struct sd_dhcp6_client {
|
||||
RefCount n_ref;
|
||||
|
||||
@ -62,12 +64,8 @@ struct sd_dhcp6_client {
|
||||
sd_event_source *timeout_resend_expire;
|
||||
sd_dhcp6_client_cb_t cb;
|
||||
void *userdata;
|
||||
|
||||
struct duid_en {
|
||||
uint16_t type; /* DHCP6_DUID_EN */
|
||||
uint32_t pen;
|
||||
uint8_t id[8];
|
||||
} _packed_ duid;
|
||||
uint8_t duid[MAX_DUID_LEN];
|
||||
size_t duid_len;
|
||||
};
|
||||
|
||||
static const uint16_t default_req_opts[] = {
|
||||
@ -147,6 +145,19 @@ int sd_dhcp6_client_set_mac(sd_dhcp6_client *client,
|
||||
return 0;
|
||||
}
|
||||
|
||||
int sd_dhcp6_client_set_duid(sd_dhcp6_client *client, uint8_t *duid,
|
||||
size_t duid_len)
|
||||
{
|
||||
assert_return(client, -EINVAL);
|
||||
assert_return(duid, -EINVAL);
|
||||
assert_return(duid_len > 0 && duid_len <= MAX_DUID_LEN, -EINVAL);
|
||||
|
||||
memcpy(&client->duid, duid, duid_len);
|
||||
client->duid_len = duid_len;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int sd_dhcp6_client_set_request_option(sd_dhcp6_client *client,
|
||||
uint16_t option) {
|
||||
size_t t;
|
||||
@ -308,7 +319,7 @@ static int client_send_message(sd_dhcp6_client *client, usec_t time_now) {
|
||||
return r;
|
||||
|
||||
r = dhcp6_option_append(&opt, &optlen, DHCP6_OPTION_CLIENTID,
|
||||
sizeof(client->duid), &client->duid);
|
||||
client->duid_len, &client->duid);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -616,7 +627,7 @@ static int client_parse_message(sd_dhcp6_client *client,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (optlen != sizeof(client->duid) ||
|
||||
if (optlen != client->duid_len ||
|
||||
memcmp(&client->duid, optval, optlen) != 0) {
|
||||
log_dhcp6_client(client, "%s DUID does not match",
|
||||
dhcp6_message_type_to_string(message->type));
|
||||
@ -1116,9 +1127,16 @@ sd_dhcp6_client *sd_dhcp6_client_unref(sd_dhcp6_client *client) {
|
||||
return client;
|
||||
}
|
||||
|
||||
struct duid_en {
|
||||
uint16_t type; /* DHCP6_DUID_EN */
|
||||
uint32_t pen;
|
||||
uint8_t id[8];
|
||||
} _packed_;
|
||||
|
||||
int sd_dhcp6_client_new(sd_dhcp6_client **ret)
|
||||
{
|
||||
_cleanup_dhcp6_client_unref_ sd_dhcp6_client *client = NULL;
|
||||
struct duid_en *duid;
|
||||
sd_id128_t machine_id;
|
||||
int r;
|
||||
size_t t;
|
||||
@ -1138,8 +1156,9 @@ int sd_dhcp6_client_new(sd_dhcp6_client **ret)
|
||||
client->fd = -1;
|
||||
|
||||
/* initialize DUID */
|
||||
client->duid.type = htobe16(DHCP6_DUID_EN);
|
||||
client->duid.pen = htobe32(SYSTEMD_PEN);
|
||||
duid = (struct duid_en *) &client->duid;
|
||||
duid->type = htobe16(DHCP6_DUID_EN);
|
||||
duid->pen = htobe32(SYSTEMD_PEN);
|
||||
|
||||
r = sd_id128_get_machine(&machine_id);
|
||||
if (r < 0)
|
||||
@ -1147,8 +1166,8 @@ int sd_dhcp6_client_new(sd_dhcp6_client **ret)
|
||||
|
||||
/* a bit of snake-oil perhaps, but no need to expose the machine-id
|
||||
directly */
|
||||
siphash24(client->duid.id, &machine_id, sizeof(machine_id),
|
||||
HASH_KEY.bytes);
|
||||
siphash24(duid->id, &machine_id, sizeof(machine_id), HASH_KEY.bytes);
|
||||
client->duid_len = sizeof (struct duid_en);
|
||||
|
||||
client->req_opts_len = ELEMENTSOF(default_req_opts);
|
||||
|
||||
|
@ -45,6 +45,8 @@ int sd_dhcp6_client_set_callback(sd_dhcp6_client *client,
|
||||
int sd_dhcp6_client_set_index(sd_dhcp6_client *client, int interface_index);
|
||||
int sd_dhcp6_client_set_mac(sd_dhcp6_client *client,
|
||||
const struct ether_addr *mac_addr);
|
||||
int sd_dhcp6_client_set_duid(sd_dhcp6_client *client, uint8_t *duid,
|
||||
size_t duid_len);
|
||||
int sd_dhcp6_client_set_request_option(sd_dhcp6_client *client,
|
||||
uint16_t option);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user