Agrego múltiples gateways y la información de DNS en los eventos DHCP
parent
0ff00a8b9c
commit
dfc2abecd1
|
@ -49,11 +49,12 @@ struct _NIInterfacePrivate {
|
|||
gboolean dhcp_type_first_time;
|
||||
int dhcp_type, dhcp_status;
|
||||
uint32_t dhcp_lease_time;
|
||||
gboolean has_dhcp_broadcast, has_dhcp_gw, has_dhcp_server;
|
||||
struct_addr dhcp_addr, dhcp_broadcast, dhcp_gateway, dhcp_server;
|
||||
gboolean has_dhcp_broadcast, has_dhcp_server;
|
||||
int dhcp_gw_c, dhcp_dns_c;
|
||||
struct_addr dhcp_addr, dhcp_broadcast, dhcp_gateways[7], dhcp_server, dhcp_dns[7];
|
||||
guint dhcp_prefix;
|
||||
|
||||
/* TODO: Falta procesar la información del DNS */
|
||||
char dhcp_domain_name[256];
|
||||
};
|
||||
|
||||
enum {
|
||||
|
@ -575,7 +576,7 @@ static void ni_interface_process_ip_removed (NIInterface *ni_interface, gpointer
|
|||
|
||||
static void ni_interface_process_dhcp_status (NIInterface *ni_interface, gpointer data, guint size) {
|
||||
unsigned char *buffer = (unsigned char *) data;
|
||||
gint family_size = 0;
|
||||
gint family_size = 0, c, g;
|
||||
guint bits, pos;
|
||||
int old_type;
|
||||
|
||||
|
@ -591,33 +592,28 @@ static void ni_interface_process_dhcp_status (NIInterface *ni_interface, gpointe
|
|||
ni_interface->priv->dhcp_status = buffer[8];
|
||||
ni_interface->priv->dhcp_prefix = buffer[9];
|
||||
|
||||
ni_interface->priv->has_dhcp_gw = FALSE;
|
||||
if (buffer[10] & 0x01) {
|
||||
/* Hay un DHCP gateway */
|
||||
ni_interface->priv->has_dhcp_gw = TRUE;
|
||||
}
|
||||
|
||||
ni_interface->priv->has_dhcp_broadcast = FALSE;
|
||||
if (buffer[10] & 0x02) {
|
||||
if (buffer[10] & 0x01) {
|
||||
/* Hay una IP broadcast de DHCP */
|
||||
ni_interface->priv->has_dhcp_broadcast = TRUE;
|
||||
}
|
||||
|
||||
ni_interface->priv->has_dhcp_server = FALSE;
|
||||
if (buffer[10] & 0x04) {
|
||||
if (buffer[10] & 0x02) {
|
||||
/* Hay un servidor DHCP */
|
||||
ni_interface->priv->has_dhcp_server = TRUE;
|
||||
}
|
||||
|
||||
/* TODO: Procesar aquí la información de DNS */
|
||||
ni_interface->priv->dhcp_gw_c = (buffer[10] & 0x1C) >> 2;
|
||||
ni_interface->priv->dhcp_dns_c = (buffer[10] & 0xE0) >> 5;
|
||||
|
||||
memcpy (&ni_interface->priv->dhcp_lease_time, &buffer[12], 4);
|
||||
|
||||
memcpy (&ni_interface->priv->dhcp_addr, &buffer[16], family_size);
|
||||
pos = 16 + family_size;
|
||||
|
||||
if (ni_interface->priv->has_dhcp_gw) {
|
||||
memcpy (&ni_interface->priv->dhcp_gateway, &buffer[pos], family_size);
|
||||
for (g = 0; g < ni_interface->priv->dhcp_gw_c; g++) {
|
||||
memcpy (&ni_interface->priv->dhcp_gateways[g], &buffer[pos], family_size);
|
||||
pos += family_size;
|
||||
}
|
||||
|
||||
|
@ -631,7 +627,18 @@ static void ni_interface_process_dhcp_status (NIInterface *ni_interface, gpointe
|
|||
pos += family_size;
|
||||
}
|
||||
|
||||
/* TODO: Procesar la información de los DNS */
|
||||
for (g = 0; g < ni_interface->priv->dhcp_dns_c; g++) {
|
||||
memcpy (&ni_interface->priv->dhcp_dns[g], &buffer[pos], family_size);
|
||||
pos += family_size;
|
||||
}
|
||||
|
||||
/* Copiar el domain name */
|
||||
ni_interface->priv->dhcp_domain_name[0] = 0;
|
||||
if (buffer[11] > 0) {
|
||||
memcpy (ni_interface->priv->dhcp_domain_name, &buffer[pos], buffer[11]);
|
||||
pos += buffer[11];
|
||||
}
|
||||
|
||||
if (old_type != ni_interface->priv->dhcp_type || ni_interface->priv->dhcp_type_first_time) {
|
||||
/* Es una actualizacion de tipo */
|
||||
g_signal_emit (ni_interface, signals[DHCP_TYPE_CHANGED], 0, old_type, ni_interface->priv->dhcp_type);
|
||||
|
@ -869,10 +876,10 @@ gboolean ni_interface_has_dhcp_brd_addr (NIInterface *ni_interface) {
|
|||
return ni_interface->priv->has_dhcp_broadcast;
|
||||
}
|
||||
|
||||
gboolean ni_interface_has_dhcp_gw_addr (NIInterface *ni_interface) {
|
||||
g_return_val_if_fail (NI_IS_INTERFACE (ni_interface), FALSE);
|
||||
gint ni_interface_get_dhcp_gw_count (NIInterface *ni_interface) {
|
||||
g_return_val_if_fail (NI_IS_INTERFACE (ni_interface), 0);
|
||||
|
||||
return ni_interface->priv->has_dhcp_gw;
|
||||
return ni_interface->priv->dhcp_gw_c;
|
||||
}
|
||||
|
||||
gboolean ni_interface_has_dhcp_server_addr (NIInterface *ni_interface) {
|
||||
|
@ -881,6 +888,12 @@ gboolean ni_interface_has_dhcp_server_addr (NIInterface *ni_interface) {
|
|||
return ni_interface->priv->has_dhcp_server;
|
||||
}
|
||||
|
||||
gint ni_interface_get_dhcp_dns_count (NIInterface *ni_interface) {
|
||||
g_return_val_if_fail (NI_IS_INTERFACE (ni_interface), 0);
|
||||
|
||||
return ni_interface->priv->dhcp_dns_c;
|
||||
}
|
||||
|
||||
const struct_addr * ni_interface_get_dhcp_brd_addr (NIInterface *ni_interface) {
|
||||
g_return_val_if_fail (NI_IS_INTERFACE (ni_interface), NULL);
|
||||
|
||||
|
@ -890,7 +903,7 @@ const struct_addr * ni_interface_get_dhcp_brd_addr (NIInterface *ni_interface) {
|
|||
const struct_addr * ni_interface_get_dhcp_gw_addr (NIInterface *ni_interface) {
|
||||
g_return_val_if_fail (NI_IS_INTERFACE (ni_interface), NULL);
|
||||
|
||||
return &ni_interface->priv->dhcp_gateway;
|
||||
return ni_interface->priv->dhcp_gateways;
|
||||
}
|
||||
|
||||
const struct_addr * ni_interface_get_dhcp_server_addr (NIInterface *ni_interface) {
|
||||
|
@ -899,6 +912,20 @@ const struct_addr * ni_interface_get_dhcp_server_addr (NIInterface *ni_interface
|
|||
return &ni_interface->priv->dhcp_server;
|
||||
}
|
||||
|
||||
const struct_addr * ni_interface_get_dhcp_dns_addr (NIInterface *ni_interface) {
|
||||
g_return_val_if_fail (NI_IS_INTERFACE (ni_interface), NULL);
|
||||
|
||||
return ni_interface->priv->dhcp_dns;
|
||||
}
|
||||
|
||||
const char *ni_interface_get_dhcp_domain_name (NIInterface *ni_interface) {
|
||||
|
||||
if (ni_interface->priv->dhcp_domain_name[0] == 0) {
|
||||
return NULL;
|
||||
}
|
||||
return ni_interface->priv->dhcp_domain_name;
|
||||
}
|
||||
|
||||
static void ni_interface_init (NIInterface *ni_interface) {
|
||||
NIInterfacePrivate *priv = ni_interface_get_instance_private (ni_interface);
|
||||
ni_interface->priv = priv;
|
||||
|
@ -920,12 +947,12 @@ static void ni_interface_init (NIInterface *ni_interface) {
|
|||
priv->dhcp_status = 0;
|
||||
priv->dhcp_lease_time = 0;
|
||||
priv->has_dhcp_broadcast = FALSE;
|
||||
priv->has_dhcp_gw = FALSE;
|
||||
priv->dhcp_gw_c = 0;
|
||||
priv->dhcp_dns_c = 0;
|
||||
priv->has_dhcp_server = FALSE;
|
||||
|
||||
memset (&priv->dhcp_addr, 0, sizeof (priv->dhcp_addr));
|
||||
memset (&priv->dhcp_broadcast, 0, sizeof (priv->dhcp_broadcast));
|
||||
memset (&priv->dhcp_gateway, 0, sizeof (priv->dhcp_gateway));
|
||||
memset (&priv->dhcp_server, 0, sizeof (priv->dhcp_server));
|
||||
priv->dhcp_prefix = 0;
|
||||
}
|
||||
|
|
|
@ -88,11 +88,14 @@ guint ni_interface_get_dhcp_lease_time (NIInterface *ni_interface);
|
|||
guint ni_interface_get_dhcp_prefix (NIInterface *ni_interface);
|
||||
const struct_addr * ni_interface_get_dhcp_addr (NIInterface *ni_interface);
|
||||
gboolean ni_interface_has_dhcp_brd_addr (NIInterface *ni_interface);
|
||||
gboolean ni_interface_has_dhcp_gw_addr (NIInterface *ni_interface);
|
||||
gint ni_interface_get_dhcp_gw_count (NIInterface *ni_interface);
|
||||
gboolean ni_interface_has_dhcp_server_addr (NIInterface *ni_interface);
|
||||
gint ni_interface_get_dhcp_dns_count (NIInterface *ni_interface);
|
||||
const struct_addr * ni_interface_get_dhcp_brd_addr (NIInterface *ni_interface);
|
||||
const struct_addr * ni_interface_get_dhcp_gw_addr (NIInterface *ni_interface);
|
||||
const struct_addr * ni_interface_get_dhcp_server_addr (NIInterface *ni_interface);
|
||||
const struct_addr * ni_interface_get_dhcp_dns_addr (NIInterface *ni_interface);
|
||||
const char *ni_interface_get_dhcp_domain_name (NIInterface *ni_interface);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
|
|
@ -579,10 +579,11 @@ static void ni_window_interface_changed_master_cb (GObject *object, GParamSpec *
|
|||
|
||||
static void ni_window_interface_update_dhcp_status (NIWindowInterface *window_iface, NIInterface *ni_interface) {
|
||||
guint type, status, prefix, lease_time;
|
||||
char buffer[1024];
|
||||
char buffer[2048];
|
||||
char buffer_ip[256];
|
||||
const struct_addr *addr;
|
||||
gint pos = 0;
|
||||
gint pos = 0, c, g;
|
||||
const char *domain_name;
|
||||
|
||||
type = ni_interface_get_dhcp_type (ni_interface);
|
||||
|
||||
|
@ -601,11 +602,19 @@ static void ni_window_interface_update_dhcp_status (NIWindowInterface *window_if
|
|||
inet_ntop (AF_INET, addr, buffer_ip, sizeof (buffer_ip));
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "Dirección IP: %s/%i\n", buffer_ip, prefix);
|
||||
|
||||
if (ni_interface_has_dhcp_gw_addr (ni_interface)) {
|
||||
addr = ni_interface_get_dhcp_gw_addr (ni_interface);
|
||||
inet_ntop (AF_INET, addr, buffer_ip, sizeof (buffer_ip));
|
||||
c = ni_interface_get_dhcp_gw_count (ni_interface);
|
||||
addr = ni_interface_get_dhcp_gw_addr (ni_interface);
|
||||
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "Gateway: %s\n", buffer_ip);
|
||||
if (c > 0) {
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "Gateway: ");
|
||||
}
|
||||
for (g = 0; g < c; g++) {
|
||||
inet_ntop (AF_INET, &addr[g], buffer_ip, sizeof (buffer_ip));
|
||||
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "%s,", buffer_ip);
|
||||
}
|
||||
if (c > 0) {
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "\n");
|
||||
}
|
||||
|
||||
if (ni_interface_has_dhcp_brd_addr (ni_interface)) {
|
||||
|
@ -615,6 +624,21 @@ static void ni_window_interface_update_dhcp_status (NIWindowInterface *window_if
|
|||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "Broadcast: %s\n", buffer_ip);
|
||||
}
|
||||
|
||||
c = ni_interface_get_dhcp_dns_count (ni_interface);
|
||||
addr = ni_interface_get_dhcp_dns_addr (ni_interface);
|
||||
|
||||
if (c > 0) {
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "DNS: ");
|
||||
}
|
||||
for (g = 0; g < c; g++) {
|
||||
inet_ntop (AF_INET, &addr[g], buffer_ip, sizeof (buffer_ip));
|
||||
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "%s,", buffer_ip);
|
||||
}
|
||||
if (c > 0) {
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "\n");
|
||||
}
|
||||
|
||||
if (ni_interface_has_dhcp_server_addr (ni_interface)) {
|
||||
addr = ni_interface_get_dhcp_server_addr (ni_interface);
|
||||
inet_ntop (AF_INET, addr, buffer_ip, sizeof (buffer_ip));
|
||||
|
@ -628,6 +652,11 @@ static void ni_window_interface_update_dhcp_status (NIWindowInterface *window_if
|
|||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "Tiempo de concesión: %i seg(s)\n", lease_time);
|
||||
}
|
||||
|
||||
domain_name = ni_interface_get_dhcp_domain_name (ni_interface);
|
||||
if (domain_name != NULL) {
|
||||
pos += g_snprintf (&buffer[pos], sizeof (buffer) - pos, "Nombre de dominio: %s\n", domain_name);
|
||||
}
|
||||
|
||||
gtk_label_set_text (GTK_LABEL (window_iface->priv->dhcpv4_info), buffer);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -150,7 +150,10 @@ typedef struct _InterfaceDHCPClientInfo {
|
|||
guint process_watch;
|
||||
|
||||
/* La información obtenida desde el cliente */
|
||||
struct_addr ip, gateway, broadcast;
|
||||
struct_addr ip, broadcast;
|
||||
struct_addr gateways[7], dns[7];
|
||||
char domain_name[256];
|
||||
int gw_c, dns_c;
|
||||
int prefix;
|
||||
|
||||
struct_addr dhcp_server_ip;
|
||||
|
|
|
@ -24,6 +24,8 @@
|
|||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <time.h>
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
|
@ -135,13 +137,14 @@ void interfaces_dhcp_client_killed_cb (GPid pid, gint status, gpointer data) {
|
|||
|
||||
static void interfaces_dhcp_clear_info (InterfaceDHCPClientInfo *dhcpc) {
|
||||
memset (&dhcpc->ip, 0, sizeof (dhcpc->ip));
|
||||
memset (&dhcpc->gateway, 0, sizeof (dhcpc->gateway));
|
||||
dhcpc->gw_c = 0;
|
||||
dhcpc->dns_c = 0;
|
||||
memset (&dhcpc->broadcast, 0, sizeof (dhcpc->broadcast));
|
||||
memset (&dhcpc->dhcp_server_ip, 0, sizeof (dhcpc->dhcp_server_ip));
|
||||
dhcpc->lease_time = 0;
|
||||
dhcpc->prefix = 0;
|
||||
|
||||
/* TODO: Borrar la información de DNS */
|
||||
dhcpc->domain_name[0] = 0;
|
||||
}
|
||||
|
||||
int interfaces_dhcp_client_run (NetworkInadorHandle *handle, int index, int type, uint32_t flags) {
|
||||
|
@ -250,9 +253,10 @@ int interfaces_dhcp_client_stop (NetworkInadorHandle *handle, int index) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
void interfaces_dhcp_client_internal_feed_from_client (NetworkInadorHandle *handle, int index, int status, struct_addr *ip, int prefix, struct_addr *gateway, struct_addr *broadcast, struct_addr *dhcp_server, uint32_t lease_time, struct_addr *dns_list, int dns_count, char *domain_name) {
|
||||
void interfaces_dhcp_client_internal_feed_from_client (NetworkInadorHandle *handle, int index, int status, struct_addr *ip, int prefix, struct_addr *gateways, int gw_c, struct_addr *broadcast, struct_addr *dhcp_server, uint32_t lease_time, struct_addr *dns_list, int dns_count, char *domain_name) {
|
||||
Interface *iface;
|
||||
struct in_addr empty_v4;
|
||||
int g;
|
||||
|
||||
iface = _interfaces_locate_by_index (handle->interfaces, index);
|
||||
|
||||
|
@ -300,18 +304,40 @@ void interfaces_dhcp_client_internal_feed_from_client (NetworkInadorHandle *hand
|
|||
memcpy (&iface->dhcpc.ip, ip, sizeof (iface->dhcpc.ip));
|
||||
iface->dhcpc.prefix = prefix;
|
||||
|
||||
memcpy (&iface->dhcpc.gateway, gateway, sizeof (iface->dhcpc.gateway));
|
||||
iface->dhcpc.gw_c = gw_c;
|
||||
for (g = 0; g < gw_c && g < 7; g++) {
|
||||
memcpy (&iface->dhcpc.gateways[g], &gateways[g], 4);
|
||||
}
|
||||
|
||||
memcpy (&iface->dhcpc.broadcast, broadcast, sizeof (iface->dhcpc.broadcast));
|
||||
memcpy (&iface->dhcpc.dhcp_server_ip, dhcp_server, sizeof (iface->dhcpc.dhcp_server_ip));
|
||||
iface->dhcpc.lease_time = lease_time;
|
||||
|
||||
iface->dhcpc.dns_c = dns_count;
|
||||
for (g = 0; g < dns_count && g < 7; g++) {
|
||||
memcpy (&iface->dhcpc.dns[g], &dns_list[g], 4);
|
||||
}
|
||||
|
||||
strncpy (iface->dhcpc.domain_name, domain_name, sizeof (iface->dhcpc.domain_name));
|
||||
|
||||
char buf_a[256], buf_b[256], buf_c[256], buf_d[256];
|
||||
|
||||
inet_ntop (AF_INET, &iface->dhcpc.ip, buf_a, sizeof (buf_a));
|
||||
inet_ntop (AF_INET, &iface->dhcpc.gateway, buf_b, sizeof (buf_b));
|
||||
inet_ntop (AF_INET, &iface->dhcpc.broadcast, buf_c, sizeof (buf_c));
|
||||
inet_ntop (AF_INET, &iface->dhcpc.dhcp_server_ip, buf_d, sizeof (buf_d));
|
||||
printf ("----> DHCP Server (%s), IP obtenida: %s/%i, GW: %s y bcast: %s, lease: %i\n", buf_d, buf_a, prefix, buf_b, buf_c, lease_time);
|
||||
printf ("----> (%i) DHCP Server (%s), IP obtenida: %s/%i, GW: ", (unsigned int) time (NULL), buf_d, buf_a, prefix);
|
||||
|
||||
for (g = 0; g < gw_c; g++) {
|
||||
inet_ntop (AF_INET, &iface->dhcpc.gateways[g], buf_b, sizeof (buf_b));
|
||||
printf ("%s, ", buf_b);
|
||||
}
|
||||
printf ("bcast: %s, lease: %i, DNS: ", buf_c, lease_time);
|
||||
for (g = 0; g < dns_count; g++) {
|
||||
inet_ntop (AF_INET, &iface->dhcpc.dns[g], buf_b, sizeof (buf_b));
|
||||
printf ("%s, ", buf_b);
|
||||
}
|
||||
|
||||
printf (" y domain name <%s>\n", domain_name);
|
||||
}
|
||||
|
||||
manager_send_event_dhcp_change (handle, &iface->dhcpc);
|
||||
|
|
|
@ -27,7 +27,7 @@
|
|||
|
||||
int interfaces_dhcp_client_run (NetworkInadorHandle *handle, int index, int type, uint32_t flags);
|
||||
int interfaces_dhcp_client_stop (NetworkInadorHandle *handle, int index);
|
||||
void interfaces_dhcp_client_internal_feed_from_client (NetworkInadorHandle *handle, int index, int status, struct_addr *ip, int prefix, struct_addr *gateway, struct_addr *broadcast, struct_addr *dhcp_server, uint32_t lease_time, struct_addr *dns_list, int dns_count, char *domain_name);
|
||||
void interfaces_dhcp_client_internal_feed_from_client (NetworkInadorHandle *handle, int index, int status, struct_addr *ip, int prefix, struct_addr *gateways, int gw_c, struct_addr *broadcast, struct_addr *dhcp_server, uint32_t lease_time, struct_addr *dns_list, int dns_count, char *domain_name);
|
||||
|
||||
#endif /* __DHCP_CLIENT_H__ */
|
||||
|
||||
|
|
|
@ -677,8 +677,9 @@ static void _manager_execute_dhcp_client_feed (ManagerClientInfo *manager_client
|
|||
int family;
|
||||
int pos, prefix, g;
|
||||
uint32_t lease_time;
|
||||
struct_addr ip, gateway, broadcast, dhcp_server;
|
||||
struct_addr dns[8];
|
||||
struct_addr ip, broadcast, dhcp_server;
|
||||
struct_addr dns[8], gateways[8];
|
||||
int gw_c, dns_c;
|
||||
|
||||
if (buffer_len < 16) {
|
||||
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_DHCP_CLIENT_FEED);
|
||||
|
@ -695,7 +696,7 @@ static void _manager_execute_dhcp_client_feed (ManagerClientInfo *manager_client
|
|||
}
|
||||
|
||||
/* Revisar el estado */
|
||||
if (buffer[3] < DHCP_CLIENT_SELECTING || buffer[3] > DHCP_CLIENT_EXPIRED) {
|
||||
if (buffer[3] < DHCP_CLIENT_SELECTING || buffer[3] > DHCP_CLIENT_FAILED) {
|
||||
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_VALUE, NET_INADOR_COMMAND_DHCP_CLIENT_FEED);
|
||||
return;
|
||||
}
|
||||
|
@ -708,10 +709,15 @@ static void _manager_execute_dhcp_client_feed (ManagerClientInfo *manager_client
|
|||
}
|
||||
|
||||
_MANAGER_CHECK_BYTE_OR_OUT(family, buffer, 5); // Dirección IP
|
||||
_MANAGER_CHECK_BYTE_OR_OUT(family, buffer, 7); // Ruta por defecto
|
||||
_MANAGER_CHECK_BYTE_OR_OUT(family, buffer, 8); // Dirección Broadcast
|
||||
_MANAGER_CHECK_BYTE_OR_OUT(family, buffer, 9); // Dirección del servidor
|
||||
|
||||
/* Revisar la posible ruta de gateways */
|
||||
if (family == AF_INET && buffer[7] % 4 != 0) {
|
||||
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_VALUE, NET_INADOR_COMMAND_DHCP_CLIENT_FEED);
|
||||
return;
|
||||
}
|
||||
|
||||
/* La lista de servidores DNS */
|
||||
if (family == AF_INET && buffer[10] % 4 != 0) {
|
||||
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_VALUE, NET_INADOR_COMMAND_DHCP_CLIENT_FEED);
|
||||
|
@ -753,11 +759,11 @@ static void _manager_execute_dhcp_client_feed (ManagerClientInfo *manager_client
|
|||
}
|
||||
|
||||
/* Recuperar la ruta por defecto */
|
||||
if (buffer[7] != 0) {
|
||||
pos = 16 + name_len + buffer[5];
|
||||
memcpy (&gateway, &buffer[pos], buffer[7]);
|
||||
} else {
|
||||
memset (&gateway, 0, sizeof (gateway));
|
||||
gw_c = buffer[7] / 4;
|
||||
pos = 16 + name_len + buffer[5];
|
||||
for (g = 0; g < gw_c && g < 8; g++) {
|
||||
memcpy (&gateways[g].v4, &buffer[pos], 4);
|
||||
pos += 4;
|
||||
}
|
||||
|
||||
/* Recuperar el broadcast */
|
||||
|
@ -777,11 +783,11 @@ static void _manager_execute_dhcp_client_feed (ManagerClientInfo *manager_client
|
|||
}
|
||||
|
||||
/* Recuperar todos los servidores DNS */
|
||||
g = 0;
|
||||
while (g < 8 && g < (buffer[10] / 4)) {
|
||||
dns_c = buffer[10] / 4;
|
||||
pos = 16 + name_len + buffer[5] + buffer[7] + buffer[8] + buffer[9];
|
||||
for (g = 0; g < 8 && g < dns_c; g++) {
|
||||
memcpy (&dns[g].v4, &buffer[pos], 4);
|
||||
pos += 4;
|
||||
g++;
|
||||
}
|
||||
|
||||
/* Recuperar el domain name */
|
||||
|
@ -803,7 +809,7 @@ static void _manager_execute_dhcp_client_feed (ManagerClientInfo *manager_client
|
|||
return;
|
||||
}
|
||||
}
|
||||
interfaces_dhcp_client_internal_feed_from_client (manager_client->manager->handle, iface->index, buffer[3], &ip, buffer[6], &gateway, &broadcast, &dhcp_server, lease_time, dns, (buffer[10] / 4), domain_name);
|
||||
interfaces_dhcp_client_internal_feed_from_client (manager_client->manager->handle, iface->index, buffer[3], &ip, buffer[6], gateways, gw_c, &broadcast, &dhcp_server, lease_time, dns, dns_c, domain_name);
|
||||
|
||||
/* OK */
|
||||
_manager_send_executed (manager_client);
|
||||
|
@ -920,6 +926,7 @@ void _manager_send_dhcp_status (ManagerClientInfo *manager_client, InterfaceDHCP
|
|||
int pos;
|
||||
int family = AF_INET;
|
||||
struct in_addr empty;
|
||||
int g;
|
||||
|
||||
memset (&empty, 0, sizeof (empty));
|
||||
|
||||
|
@ -948,26 +955,31 @@ void _manager_send_dhcp_status (ManagerClientInfo *manager_client, InterfaceDHCP
|
|||
|
||||
/* Los campos de bits */
|
||||
buffer[10] = 0;
|
||||
if (memcmp (&dhcpc->gateway, &empty, 4) != 0) {
|
||||
if (memcmp (&dhcpc->broadcast, &empty, 4) != 0) {
|
||||
buffer[10] |= 0x01;
|
||||
}
|
||||
if (memcmp (&dhcpc->broadcast, &empty, 4) != 0) {
|
||||
if (memcmp (&dhcpc->dhcp_server_ip, &empty, 4) != 0) {
|
||||
buffer[10] |= 0x02;
|
||||
}
|
||||
if (memcmp (&dhcpc->dhcp_server_ip, &empty, 4) != 0) {
|
||||
buffer[10] |= 0x04;
|
||||
}
|
||||
|
||||
/* TODO: Falta enviar la información de cantidad de servidores DNS */
|
||||
buffer[11] = 0;
|
||||
/* Cantidad de GWs */
|
||||
g = dhcpc->gw_c & 0x07;
|
||||
buffer[10] |= (g << 2);
|
||||
|
||||
/* Cantidad de DNS */
|
||||
g = dhcpc->dns_c & 0x07;
|
||||
buffer[10] |= (g << 5);
|
||||
|
||||
buffer[11] = strlen (dhcpc->domain_name);
|
||||
|
||||
memcpy (&buffer[12], &dhcpc->lease_time, 4);
|
||||
|
||||
/* La dirección principal */
|
||||
memcpy (&buffer[16], &dhcpc->ip, family_size);
|
||||
pos = 16 + family_size;
|
||||
if (memcmp (&dhcpc->gateway, &empty, 4) != 0) {
|
||||
memcpy (&buffer[pos], &dhcpc->gateway, family_size);
|
||||
|
||||
for (g = 0; g < dhcpc->gw_c; g++) {
|
||||
memcpy (&buffer[pos], &dhcpc->gateways[g], family_size);
|
||||
pos += family_size;
|
||||
}
|
||||
|
||||
|
@ -981,7 +993,13 @@ void _manager_send_dhcp_status (ManagerClientInfo *manager_client, InterfaceDHCP
|
|||
pos += family_size;
|
||||
}
|
||||
|
||||
/* TODO: Falta aquí enviar la lista de servidores DNS y el domain name */
|
||||
for (g = 0; g < dhcpc->dns_c; g++) {
|
||||
memcpy (&buffer[pos], &dhcpc->dns[g], family_size);
|
||||
pos += family_size;
|
||||
}
|
||||
|
||||
memcpy (&buffer[pos], dhcpc->domain_name, buffer[11]);
|
||||
pos += buffer[11];
|
||||
|
||||
send (manager_client->fd, buffer, pos, 0);
|
||||
}
|
||||
|
|
|
@ -79,6 +79,17 @@ int debug (int argc, char *argv[]) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
enum {
|
||||
DHCP_CLIENT_SELECTING,
|
||||
DHCP_CLIENT_BOUND,
|
||||
DHCP_CLIENT_RENEWED,
|
||||
|
||||
DHCP_CLIENT_EXPIRED,
|
||||
DHCP_CLIENT_FAILED,
|
||||
|
||||
DHCP_CLIENT_KILLED,
|
||||
};
|
||||
|
||||
uint32_t utils_ip4_netmask_to_prefix (uint32_t netmask) {
|
||||
uint32_t prefix;
|
||||
uint8_t v;
|
||||
|
@ -151,14 +162,20 @@ int wait_for_ack_or_error (int s) {
|
|||
return -1;
|
||||
}
|
||||
|
||||
void send_preinit (int s, char *interface) {
|
||||
void send_basic (int s, char *interface, int tipo) {
|
||||
unsigned char buffer[128];
|
||||
|
||||
buffer[0] = NET_INADOR_TYPE_COMMAND;
|
||||
buffer[1] = NET_INADOR_COMMAND_DHCP_CLIENT_FEED;
|
||||
|
||||
buffer[2] = AF_INET;
|
||||
buffer[3] = NET_INADOR_DHCP_STATUS_SELECTING;
|
||||
if (tipo == DHCP_CLIENT_SELECTING) {
|
||||
buffer[3] = NET_INADOR_DHCP_STATUS_SELECTING;
|
||||
} else if (tipo == DHCP_CLIENT_EXPIRED) {
|
||||
buffer[3] = NET_INADOR_DHCP_STATUS_EXPIRED;
|
||||
} else if (tipo == DHCP_CLIENT_FAILED) {
|
||||
buffer[3] = NET_INADOR_DHCP_STATUS_FAILED;
|
||||
}
|
||||
buffer[4] = strlen (interface);
|
||||
memset (&buffer[5], 0, 11);
|
||||
|
||||
|
@ -171,10 +188,10 @@ void send_preinit (int s, char *interface) {
|
|||
}
|
||||
}
|
||||
|
||||
void send_bound_renew (int s, int is_bound, char *interface, struct in_addr *ip, int prefix, struct in_addr *gateway, struct in_addr *broadcast, struct in_addr *dhcp_server, uint32_t lease_time) {
|
||||
void send_bound_renew (int s, int is_bound, char *interface, struct in_addr *ip, int prefix, struct in_addr *gateways, int gw_c, struct in_addr *broadcast, struct in_addr *dhcp_server, uint32_t lease_time, struct in_addr *dns, int dns_c, char *domain_name) {
|
||||
unsigned char buffer[128];
|
||||
struct in_addr empty;
|
||||
int pos;
|
||||
int pos, g;
|
||||
|
||||
memset (&empty, 0, sizeof (empty));
|
||||
|
||||
|
@ -192,6 +209,10 @@ void send_bound_renew (int s, int is_bound, char *interface, struct in_addr *ip,
|
|||
|
||||
buffer[6] = prefix;
|
||||
|
||||
if (lease_time != 0) {
|
||||
memcpy (&buffer[12], &lease_time, 4);
|
||||
}
|
||||
|
||||
pos = 16;
|
||||
|
||||
/* Copiar el nombre de la interfaz */
|
||||
|
@ -205,10 +226,10 @@ void send_bound_renew (int s, int is_bound, char *interface, struct in_addr *ip,
|
|||
pos += 4;
|
||||
}
|
||||
|
||||
if (memcmp (&empty, gateway, sizeof (empty)) != 0) {
|
||||
/* Tenemos una ruta */
|
||||
buffer[7] = 4;
|
||||
memcpy (&buffer[pos], gateway, 4);
|
||||
/* Procesar las múltiples rutas posibles */
|
||||
buffer[7] = 4 * gw_c;
|
||||
for (g = 0; g < gw_c; g++) {
|
||||
memcpy (&buffer[pos], &gateways[g], 4);
|
||||
pos += 4;
|
||||
}
|
||||
|
||||
|
@ -226,11 +247,19 @@ void send_bound_renew (int s, int is_bound, char *interface, struct in_addr *ip,
|
|||
pos += 4;
|
||||
}
|
||||
|
||||
if (lease_time != 0) {
|
||||
memcpy (&buffer[12], &lease_time, 4);
|
||||
/* Procesar los múltiples dns */
|
||||
buffer[10] = 4 * dns_c;
|
||||
for (g = 0; g < dns_c; g++) {
|
||||
memcpy (&buffer[pos], &dns[g], 4);
|
||||
pos += 4;
|
||||
}
|
||||
|
||||
/* TODO: Faltan los DNS */
|
||||
/* Procesar el nombre de dominio */
|
||||
if (domain_name != NULL && domain_name[0] != 0) {
|
||||
buffer[11] = strlen (domain_name);
|
||||
memcpy (&buffer[pos], domain_name, buffer[11]);
|
||||
pos += buffer[11];
|
||||
}
|
||||
send (s, buffer, pos, 0);
|
||||
|
||||
if (wait_for_ack_or_error (s) < 0) {
|
||||
|
@ -256,6 +285,51 @@ int parse_ip (char *var, struct in_addr *addr) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
int parse_multiple_ip (char *var, struct in_addr *addr, int max) {
|
||||
int res;
|
||||
char buffer[512];
|
||||
char *inicio, *bus;
|
||||
int c = 0;
|
||||
size_t offset;
|
||||
|
||||
if (var == NULL) return 0;
|
||||
|
||||
inicio = var;
|
||||
while (inicio[0] != 0) {
|
||||
bus = strchr (inicio, ' ');
|
||||
|
||||
if (bus == NULL) break;
|
||||
|
||||
/* Desboardamiento */
|
||||
offset = bus - inicio;
|
||||
|
||||
if (offset + 1 > sizeof (buffer)) {
|
||||
return 0;
|
||||
}
|
||||
strncpy (buffer, inicio, offset);
|
||||
buffer[offset] = 0;
|
||||
inicio = &var[offset + 1];
|
||||
|
||||
res = parse_ip (buffer, &addr[c]);
|
||||
if (res < 0) continue;
|
||||
|
||||
c++;
|
||||
if (c == max) return c;
|
||||
}
|
||||
|
||||
/* Parsear lo último, si es que queda algo */
|
||||
if (inicio[0] != 0) {
|
||||
res = parse_ip (inicio, &addr[c]);
|
||||
if (res < 0) {
|
||||
return c;
|
||||
}
|
||||
|
||||
c++;
|
||||
}
|
||||
|
||||
return c;
|
||||
}
|
||||
|
||||
int parse_int (char *var, int *entero) {
|
||||
int res;
|
||||
|
||||
|
@ -306,11 +380,14 @@ int main (int argc, char *argv[]) {
|
|||
char *reason, *interface;
|
||||
int s, ret, tipo;
|
||||
struct sockaddr_un path_dest;
|
||||
struct in_addr ip, netmask, gateway, broadcast, dhcp_server;
|
||||
struct in_addr ip, netmask, broadcast, dhcp_server;
|
||||
struct in_addr gateways[7];
|
||||
struct in_addr dns[7];
|
||||
int gw_c, dns_c;
|
||||
|
||||
int prefix, lease_time;
|
||||
|
||||
debug (argc, argv);
|
||||
|
||||
tipo = 0;
|
||||
|
||||
/* Tratar de determinar si estamos siendo corridos por un el DHCP del ISC o por el udhcpc busybox */
|
||||
|
@ -371,9 +448,9 @@ int main (int argc, char *argv[]) {
|
|||
if (strcmp (reason, "PREINIT") == 0 || // ISC DHCP
|
||||
strcmp (reason, "deconfig") == 0 // Busybox udhcpc
|
||||
) {
|
||||
send_preinit (s, interface);
|
||||
send_basic (s, interface, DHCP_CLIENT_SELECTING);
|
||||
} if (strcmp (reason, "FAIL") == 0) {
|
||||
|
||||
send_basic (s, interface, DHCP_CLIENT_FAILED);
|
||||
} else if (strcmp (reason, "BOUND") == 0 || strcmp (reason, "REBOOT") == 0 ||
|
||||
strcmp (reason, "RENEW") == 0 || strcmp (reason, "REBIND") == 0 || // 4 de ISC DHCP
|
||||
strcmp (reason, "bound") == 0 || strcmp (reason, "renew") == 0 // 2 de Busybox udhcpc
|
||||
|
@ -390,7 +467,7 @@ int main (int argc, char *argv[]) {
|
|||
* new_dhcp_lease_time -> Tiempo en segundos
|
||||
*/
|
||||
/* Parsear y revisar las direcciones IP recibidas */
|
||||
char *s_ip, *s_mask, *s_gateway, *s_broadcast, *s_lease_time, *s_dhcp_server;
|
||||
char *s_ip, *s_mask, *s_gateway, *s_broadcast, *s_lease_time, *s_dhcp_server, *s_dns, *s_domain_name;
|
||||
if (tipo == IFACE_ISC_DHCLIENT) {
|
||||
s_ip = getenv ("new_ip_address");
|
||||
s_mask = getenv ("new_subnet_mask");
|
||||
|
@ -398,6 +475,8 @@ int main (int argc, char *argv[]) {
|
|||
s_broadcast = getenv ("new_broadcast_address");
|
||||
s_lease_time = getenv ("new_dhcp_lease_time");
|
||||
s_dhcp_server = getenv ("new_dhcp_server_identifier");
|
||||
s_dns = getenv ("new_domain_name_servers");
|
||||
s_domain_name = getenv ("new_domain_name");
|
||||
} else if (tipo == IFACE_BUSYBOX_UDHCPC) {
|
||||
s_ip = getenv ("ip");
|
||||
s_mask = getenv ("subnet");
|
||||
|
@ -405,6 +484,8 @@ int main (int argc, char *argv[]) {
|
|||
s_broadcast = getenv ("broadcast");
|
||||
s_lease_time = getenv ("lease");
|
||||
s_dhcp_server = getenv ("serverid");
|
||||
s_dns = getenv ("dns");
|
||||
s_domain_name = getenv ("domain");
|
||||
}
|
||||
/* TODO: Faltan los DNS */
|
||||
|
||||
|
@ -419,9 +500,7 @@ int main (int argc, char *argv[]) {
|
|||
}
|
||||
|
||||
prefix = utils_ip4_netmask_to_prefix (netmask.s_addr);
|
||||
if (parse_ip (s_gateway, &gateway) < 0) {
|
||||
memset (&gateway, 0, sizeof (gateway));
|
||||
}
|
||||
gw_c = parse_multiple_ip (s_gateway, gateways, 7);
|
||||
|
||||
if (parse_ip (s_broadcast, &broadcast) < 0) {
|
||||
memset (&broadcast, 0, sizeof (broadcast));
|
||||
|
@ -435,18 +514,22 @@ int main (int argc, char *argv[]) {
|
|||
lease_time = 0;
|
||||
}
|
||||
|
||||
dns_c = parse_multiple_ip (s_dns, dns, 7);
|
||||
int is_bound = 0;
|
||||
if (strcmp (reason, "BOUND") == 0 || strcmp (reason, "REBOOT") == 0 || // Del ISC dhcp
|
||||
strcmp (reason, "bound") == 0 // del busybox
|
||||
) {
|
||||
is_bound = 1;
|
||||
}
|
||||
send_bound_renew (s, is_bound, interface, &ip, prefix, &gateway, &broadcast, &dhcp_server, lease_time);
|
||||
send_bound_renew (s, is_bound, interface, &ip, prefix, gateways, gw_c, &broadcast, &dhcp_server, lease_time, dns, dns_c, s_domain_name);
|
||||
} else if (strcmp (reason, "EXPIRE") == 0 || strcmp (reason, "STOP") == 0 || strcmp (reason, "RELEASE") == 0) {
|
||||
/* Los mismos valores, pero con old_ */
|
||||
send_basic (s, interface, DHCP_CLIENT_EXPIRED);
|
||||
} else {
|
||||
send_basic (s, interface, DHCP_CLIENT_FAILED);
|
||||
close (s);
|
||||
|
||||
|
||||
return -1;
|
||||
}
|
||||
close (s);
|
||||
|
||||
|
|
Loading…
Reference in New Issue