From f08c1747255bada9b1636dea346dca389a932c68 Mon Sep 17 00:00:00 2001 From: "Nicholas J. Kain" Date: Sun, 3 Jul 2011 05:36:47 -0400 Subject: [PATCH] Add clientid-mac option for sending a MAC address as a client identifier other than our own. --- ndhc/config.h | 3 ++- ndhc/dhcp.c | 21 +++++++++++++-------- ndhc/ndhc.c | 35 +++++++++++++++++++++++++++++++++-- 3 files changed, 48 insertions(+), 11 deletions(-) diff --git a/ndhc/config.h b/ndhc/config.h index 7419d4f..2a60edd 100644 --- a/ndhc/config.h +++ b/ndhc/config.h @@ -1,5 +1,5 @@ /* config.h - internal configuration and state for ndhc - * Time-stamp: <2011-03-31 01:38:03 nk> + * Time-stamp: <2011-07-03 05:10:18 njk> * * (c) 2004-2011 Nicholas J. Kain * @@ -44,6 +44,7 @@ struct client_config_t { char quit_after_lease; // Quit after obtaining lease char abort_if_no_lease; // Abort if no lease char background_if_no_lease; // Fork to background if no lease + char clientid_mac; // If true, then the clientid is a MAC addr char *interface; // The name of the interface to use char clientid[64]; // Optional client id to use char hostname[64]; // Optional hostname to use diff --git a/ndhc/dhcp.c b/ndhc/dhcp.c index 89bbd20..a97d4c4 100644 --- a/ndhc/dhcp.c +++ b/ndhc/dhcp.c @@ -1,5 +1,5 @@ /* packet.c - send and react to DHCP message packets - * Time-stamp: <2011-06-11 11:15:09 njk> + * Time-stamp: <2011-07-03 05:31:57 njk> * * (c) 2004-2011 Nicholas J. Kain * @@ -545,15 +545,20 @@ static void add_option_vendor(struct dhcpmsg *packet) static void add_option_clientid(struct dhcpmsg *packet) { char buf[sizeof client_config.clientid + 1]; + size_t len = 6; buf[0] = 1; // Ethernet MAC - size_t len = strlen(client_config.clientid); - if (len) { + if (!client_config.clientid_mac) { + size_t slen = strlen(client_config.clientid); + if (!slen) { + memcpy(buf+1, client_config.arp, len); + } else { + buf[0] = 0; // Not a hardware address + len = slen; + memcpy(buf+1, client_config.clientid, slen); + } + } else memcpy(buf+1, client_config.clientid, len); - } else { - len = 6; - memcpy(buf+1, client_config.arp, len); - } - add_option_string(packet, DHCP_CLIENT_ID, buf, len + 1); + add_option_string(packet, DHCP_CLIENT_ID, buf, len+1); } static void add_option_hostname(struct dhcpmsg *packet) diff --git a/ndhc/ndhc.c b/ndhc/ndhc.c index 990620d..d1e2752 100644 --- a/ndhc/ndhc.c +++ b/ndhc/ndhc.c @@ -1,5 +1,5 @@ /* ndhc.c - DHCP client - * Time-stamp: <2011-06-11 11:13:32 njk> + * Time-stamp: <2011-07-03 05:33:42 njk> * * (c) 2004-2011 Nicholas J. Kain * @@ -28,6 +28,7 @@ #include #include #include +#include #include #include #include @@ -126,6 +127,29 @@ static void signal_dispatch() } } +static int get_clientid_mac_string(char *str, size_t slen) +{ + if (slen != 17) + return 0; + if (str[2] == ':' && str[5] == ':' && str[8] == ':' && str[11] == ':' && + str[14] == ':' && + isxdigit(str[0]) && isxdigit(str[1]) && isxdigit(str[3]) && + isxdigit(str[4]) && isxdigit(str[6]) && isxdigit(str[7]) && + isxdigit(str[9]) && isxdigit(str[10]) && isxdigit(str[12]) && + isxdigit(str[13]) && isxdigit(str[15]) && isxdigit(str[16])) + { + client_config.clientid[0] = strtol(str, NULL, 16); + client_config.clientid[1] = strtol(str+3, NULL, 16); + client_config.clientid[2] = strtol(str+6, NULL, 16); + client_config.clientid[3] = strtol(str+9, NULL, 16); + client_config.clientid[4] = strtol(str+12, NULL, 16); + client_config.clientid[5] = strtol(str+15, NULL, 16); + client_config.clientid[6] = '\0'; + return 1; + } + return 0; +} + static void do_work(void) { struct epoll_event events[3]; @@ -181,6 +205,7 @@ int main(int argc, char **argv) gid_t gid = 0; static struct option arg_options[] = { {"clientid", required_argument, 0, 'c'}, + {"mac-clientid",required_argument, 0, 'm'}, {"foreground", no_argument, 0, 'f'}, {"background", no_argument, 0, 'b'}, {"pidfile", required_argument, 0, 'p'}, @@ -201,7 +226,7 @@ int main(int argc, char **argv) while (1) { int option_index = 0; - c = getopt_long(argc, argv, "c:fbp:H:h:i:np:l:qr:u:C:vV:", arg_options, + c = getopt_long(argc, argv, "c:m:fbp:H:h:i:np:l:qr:u:C:vV:", arg_options, &option_index); if (c == -1) break; @@ -210,6 +235,12 @@ int main(int argc, char **argv) strlcpy(client_config.clientid, optarg, sizeof client_config.clientid); break; + case 'm': + if (!get_clientid_mac_string(optarg, strlen(optarg))) + suicide("clientid %s is not a valid ethernet MAC", optarg); + else + client_config.clientid_mac = 1; + break; case 'f': client_config.foreground = 1; gflags_detach = 0;