Agrego manager para enviar eventos.

master
Félix Arreola Rodríguez 2021-09-04 23:28:38 -05:00
parent 9dac3ca7ed
commit 715dfeddf7
3 changed files with 826 additions and 0 deletions

725
src/manager.c 100644
View File

@ -0,0 +1,725 @@
/*
* manager.c
* This file is part of Network-inador
*
* Copyright (C) 2011 - Félix Arreola Rodríguez
*
* Network-inador is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* Network-inador is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with Network-inador; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor,
* Boston, MA 02110-1301 USA
*/
#include <glib.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <linux/if_addr.h>
#include <sys/stat.h>
#include "common.h"
#include "interfaces.h"
#include "ip-address.h"
#include "network-inador-manager.h"
#define COMMAND_SOCKET_PATH "/tmp/network-inador.socket"
static void _manager_send_error (ManagerClientInfo *manager_client, int error, int orig_cmd) {
unsigned char buffer[8];
buffer[0] = NET_INADOR_TYPE_RESPONSE_ERROR;
buffer[1] = orig_cmd;
buffer[2] = error;
send (manager_client->fd, buffer, 3, 0);
}
static void _manager_send_executed (ManagerClientInfo *manager_client) {
unsigned char buffer[8];
buffer[0] = NET_INADOR_TYPE_RESPONSE;
buffer[1] = NET_INADOR_RESPONSE_EXECUTED;
send (manager_client->fd, buffer, 2, 0);
}
static void _manager_send_end_command (ManagerClientInfo *manager_client, int orig_cmd) {
unsigned char buffer[8];
buffer[0] = NET_INADOR_TYPE_RESPONSE_LISTING_END;
buffer[1] = orig_cmd;
send (manager_client->fd, buffer, 2, 0);
}
static Interface * _manager_fetch_interface (ManagerClientInfo *manager_client, unsigned char *buffer, int orig_cmd) {
Interface *iface;
uint32_t index;
memcpy (&index, buffer, 4);
/* TODO: Revisar el ntohl */
iface = _interfaces_locate_by_index (manager_client->manager->handle->interfaces, index);
if (iface == NULL) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_IFACE_INDEX, orig_cmd);
return NULL;
}
return iface;
}
void _manager_send_interface (ManagerClientInfo *manager_client, Interface *iface, gboolean is_event) {
unsigned char buffer[32 + IFNAMSIZ + IFNAMSIZ];
int name_len = strlen (iface->name);
if (is_event) {
buffer[0] = NET_INADOR_TYPE_EVENT;
buffer[1] = NET_INADOR_EVENT_IFACE_ADDED;
} else {
buffer[0] = NET_INADOR_TYPE_RESPONSE;
buffer[1] = NET_INADOR_RESPONSE_IFACE;
}
memcpy (&buffer[2], &iface->index, 4);
memcpy (&buffer[6], &iface->link_type, 4);
memcpy (&buffer[10], &iface->master_index, 4);
memcpy (&buffer[14], &iface->mtu, 4);
memcpy (&buffer[18], &iface->flags, 2);
buffer[20] = iface->is_wireless;
buffer[21] = name_len;
memcpy (&buffer[22], iface->name, name_len);
send (manager_client->fd, buffer, 22 + name_len, 0);
}
void _manager_send_interface_del (ManagerClientInfo *manager_client, uint32_t index) {
unsigned char buffer[8];
buffer[0] = NET_INADOR_TYPE_EVENT;
buffer[1] = NET_INADOR_EVENT_IFACE_REMOVED;
memcpy (&buffer[2], &index, 4);
send (manager_client->fd, buffer, 6, 0);
}
void _manager_send_ip (ManagerClientInfo *manager_client, IPAddr *ip_addr, gboolean is_event) {
unsigned char buffer[80];
int family_size = 0;
int pos;
if (is_event) {
buffer[0] = NET_INADOR_TYPE_EVENT;
buffer[1] = NET_INADOR_EVENT_IPADDR_ADDED;
} else {
buffer[0] = NET_INADOR_TYPE_RESPONSE;
buffer[1] = NET_INADOR_RESPONSE_IPADDR;
}
if (ip_addr->family == AF_INET) {
family_size = sizeof (struct in_addr);
} else if (ip_addr->family == AF_INET6) {
family_size = sizeof (struct in6_addr);
}
memcpy (&buffer[2], &ip_addr->iface->index, 4);
buffer[6] = ip_addr->family;
buffer[7] = ip_addr->prefix;
buffer[8] = 0;
if (ip_addr->has_local) {
buffer[8] |= 0x01;
}
if (ip_addr->has_brd) {
buffer[8] |= 0x02;
}
buffer[9] = ip_addr->scope;
memcpy (&buffer[10], &ip_addr->flags, 4);
memcpy (&buffer[14], &ip_addr->addr, family_size);
pos = 14 + family_size;
if (ip_addr->has_local) {
memcpy (&buffer[pos], &ip_addr->local_addr, family_size);
pos += family_size;
}
if (ip_addr->has_brd) {
memcpy (&buffer[pos], &ip_addr->brd_addr, family_size);
pos += family_size;
}
send (manager_client->fd, buffer, pos, 0);
}
void _manager_send_ip_del (ManagerClientInfo *manager_client, IPAddr *ip_addr) {
unsigned char buffer[80];
int family_size = 0;
int pos;
buffer[0] = NET_INADOR_TYPE_EVENT;
buffer[1] = NET_INADOR_EVENT_IPADDR_REMOVED;
if (ip_addr->family == AF_INET) {
family_size = sizeof (struct in_addr);
} else if (ip_addr->family == AF_INET6) {
family_size = sizeof (struct in6_addr);
}
memcpy (&buffer[2], &ip_addr->iface->index, 4);
buffer[6] = ip_addr->family;
buffer[7] = ip_addr->prefix;
buffer[8] = 0;
if (ip_addr->has_local) {
buffer[8] |= 0x01;
}
buffer[9] = 0;
memcpy (&buffer[10], &ip_addr->addr, family_size);
pos = 10 + family_size;
if (ip_addr->has_local) {
memcpy (&buffer[pos], &ip_addr->local_addr, family_size);
pos += family_size;
}
send (manager_client->fd, buffer, pos, 0);
}
void _manager_send_list_interfaces (ManagerClientInfo *manager_client) {
GList *g;
Interface *iface;
g = manager_client->manager->handle->interfaces;
while (g != NULL) {
iface = (Interface *) g->data;
_manager_send_interface (manager_client, iface, FALSE);
g = g->next;
}
_manager_send_end_command (manager_client, NET_INADOR_COMMAND_LIST_IFACES);
}
void _manager_send_iface (ManagerClientInfo *manager_client, unsigned char *buffer, int buffer_len) {
Interface *iface;
if (buffer_len < 6) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_GET_IFACE);
return;
}
iface = _manager_fetch_interface (manager_client, &buffer[2], NET_INADOR_COMMAND_GET_IFACE);
if (iface == NULL) return;
_manager_send_interface (manager_client, iface, FALSE);
}
void _manager_send_list_ips (ManagerClientInfo *manager_client, unsigned char *buffer, int buffer_len) {
int family;
GList *g;
IPAddr *ip_addr;
Interface *iface;
if (buffer_len < 7) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_LIST_IP);
return;
}
family = buffer[6];
if (family != AF_UNSPEC && family != AF_INET && family != AF_INET6) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_FAMILY, NET_INADOR_COMMAND_LIST_IP);
return;
}
iface = _manager_fetch_interface (manager_client, &buffer[2], NET_INADOR_COMMAND_LIST_IP);
if (iface == NULL) return;
for (g = iface->address; g != NULL; g = g->next) {
ip_addr = (IPAddr *) g->data;
if (family != AF_UNSPEC && family != ip_addr->family) continue;
_manager_send_ip (manager_client, ip_addr, FALSE);
}
_manager_send_end_command (manager_client, NET_INADOR_COMMAND_LIST_IP);
}
void _manager_execute_iface_down_up (ManagerClientInfo *manager_client, int is_up, unsigned char *buffer, int buffer_len) {
Interface *iface;
int ret;
if (buffer_len < 6) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, (is_up ? NET_INADOR_COMMAND_IFACE_UP : NET_INADOR_COMMAND_IFACE_DOWN));
return;
}
iface = _manager_fetch_interface (manager_client, &buffer[2], (is_up ? NET_INADOR_COMMAND_IFACE_UP : NET_INADOR_COMMAND_IFACE_DOWN));
if (iface == NULL) return;
if (is_up) {
ret = interfaces_change_set_up (manager_client->manager->handle, iface->index);
} else {
ret = interfaces_change_set_down (manager_client->manager->handle, iface->index);
}
if (ret == 0) {
/* OK */
_manager_send_executed (manager_client);
} else {
_manager_send_error (manager_client, NET_INADOR_ERROR_NOT_EXECUTED, (is_up ? NET_INADOR_COMMAND_IFACE_UP : NET_INADOR_COMMAND_IFACE_DOWN));
}
}
void _manager_execute_iface_change_name (ManagerClientInfo *manager_client, unsigned char *buffer, int buffer_len) {
Interface *iface;
int ret;
int name_len;
unsigned char name[IFNAMSIZ];
if (buffer_len < 7) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_IFACE_CHANGE_NAME);
return;
}
iface = _manager_fetch_interface (manager_client, &buffer[2], NET_INADOR_COMMAND_IFACE_CHANGE_NAME);
if (iface == NULL) return;
name_len = buffer[6];
if (name_len == 0 || name_len >= IFNAMSIZ) {
_manager_send_error (manager_client, NET_INADOR_ERROR_BAD_STRING, NET_INADOR_COMMAND_IFACE_CHANGE_NAME);
return;
}
if (name_len + 7 < buffer_len) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_IFACE_CHANGE_NAME);
return;
}
memcpy (name, &buffer[7], name_len);
if (name[0] == 0) {
_manager_send_error (manager_client, NET_INADOR_ERROR_BAD_STRING, NET_INADOR_COMMAND_IFACE_CHANGE_NAME);
return;
}
ret = interfaces_change_name (manager_client->manager->handle, iface->index, name);
if (ret == 0) {
/* OK */
_manager_send_executed (manager_client);
} else {
_manager_send_error (manager_client, NET_INADOR_ERROR_NOT_EXECUTED, NET_INADOR_COMMAND_IFACE_CHANGE_NAME);
}
}
void _manager_execute_clear_ips (ManagerClientInfo *manager_client, unsigned char *buffer, int buffer_len) {
int family;
Interface *iface;
IPAddr *ip_addr;
GList *g;
int ret;
if (buffer_len < 7) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_CLEAR_IP);
return;
}
family = buffer[6];
if (family != AF_UNSPEC && family != AF_INET && family != AF_INET6) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_FAMILY, NET_INADOR_COMMAND_CLEAR_IP);
return;
}
iface = _manager_fetch_interface (manager_client, &buffer[2], NET_INADOR_COMMAND_CLEAR_IP);
if (iface == NULL) return;
ret = 0;
for (g = iface->address; g != NULL; g = g->next) {
ip_addr = (IPAddr *) g->data;
if (family != AF_UNSPEC && family != ip_addr->family) continue;
ret |= ip_address_del_ip (manager_client->manager->handle, iface->index, ip_addr);
}
if (ret == 0) {
/* OK */
_manager_send_executed (manager_client);
} else {
_manager_send_error (manager_client, NET_INADOR_ERROR_NOT_EXECUTED, NET_INADOR_COMMAND_CLEAR_IP);
}
}
void _manager_execute_add_ip (ManagerClientInfo *manager_client, unsigned char *buffer, int buffer_len) {
Interface *iface;
IPAddr ip_addr;
GList *g;
int ret;
int family_size, wanted_size, family;
int has_local, has_brd;
if (buffer_len < 14) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_ADD_IP);
return;
}
family = ip_addr.family = buffer[6];
if (family != AF_INET && family != AF_INET6) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_FAMILY, NET_INADOR_COMMAND_ADD_IP);
return;
}
iface = _manager_fetch_interface (manager_client, &buffer[2], NET_INADOR_COMMAND_ADD_IP);
if (iface == NULL) return;
ip_addr.prefix = buffer[7];
if (ip_addr.family == AF_INET && (ip_addr.prefix > 32 || ip_addr.prefix < 1)) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_VALUE, NET_INADOR_COMMAND_ADD_IP);
return;
} else if (ip_addr.family == AF_INET6 && (ip_addr.prefix > 128 || ip_addr.prefix < 1)) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INVALID_VALUE, NET_INADOR_COMMAND_ADD_IP);
return;
}
has_local = buffer[8] & 0x01;
has_brd = (buffer[8] & 0x02) >> 1;
if (ip_addr.family == AF_INET) {
family_size = sizeof (struct in_addr);
} else if (ip_addr.family == AF_INET6) {
family_size = sizeof (struct in6_addr);
}
/* Ya puedo revisar el resto de la longitud */
wanted_size = 14 + family_size + (family_size * has_local) + (family_size * has_brd);
if (buffer_len < wanted_size) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_ADD_IP);
return;
}
ip_addr.scope = buffer[9];
memcpy (&ip_addr.flags, &buffer[10], 4);
memcpy (&ip_addr.addr, &buffer[14], family_size);
wanted_size = 14 + family_size;
if (has_local) {
memcpy (&ip_addr.local_addr, &buffer[wanted_size], family_size);
wanted_size += family_size;
}
if (has_brd) {
memcpy (&ip_addr.brd_addr, &buffer[wanted_size], family_size);
wanted_size += family_size;
}
ret = ip_address_add_ip (manager_client->manager->handle, iface->index, &ip_addr);
if (ret == 0) {
/* OK */
_manager_send_executed (manager_client);
} else {
_manager_send_error (manager_client, NET_INADOR_ERROR_NOT_EXECUTED, NET_INADOR_COMMAND_ADD_IP);
}
}
static void _manager_handle_set_event_mask (ManagerClientInfo *manager_client, unsigned char *buffer, int buffer_len) {
uint32_t events;
if (buffer_len < 6) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, NET_INADOR_COMMAND_SET_EVENT_MASK);
return;
}
memcpy (&events, &buffer[2], 4);
printf ("___ MANAGER __ Set events de un cliente (%i), eventos: %u\n", manager_client->fd, events);
manager_client->wanted_events = events;
}
static gboolean _manager_client_data (GIOChannel *source, GIOCondition condition, gpointer data) {
ManagerClientInfo *manager_client = (ManagerClientInfo *) data;
NetworkInadorManager *manager = manager_client->manager;
int type, command;
Interface *iface;
int g;
unsigned char buffer[8192];
int bytes;
bytes = recv (manager_client->fd, buffer, sizeof (buffer), 0);
if (bytes <= 0) {
printf ("___ MANAGER ___ Conexión cerrada manager (%i)\n", manager_client->fd);
/* Error de lectura o cierre */
close (manager_client->fd);
manager->connected_client_list = g_list_remove (manager->connected_client_list, manager_client);
free (manager_client);
return FALSE;
}
printf ("___ MANAGER ___ Data arrival (%i):\n", manager_client->fd);
for (g = 0; g < bytes; g++) {
printf ("%02hhx ", buffer[g]);
}
printf ("\n");
/* Comando incompleto */
if (bytes < 2) {
_manager_send_error (manager_client, NET_INADOR_ERROR_INCOMPLETE_REQUEST, 0);
return TRUE;
}
/* Procesar los datos del cliente */
type = buffer[0];
if (type != NET_INADOR_TYPE_COMMAND) {
_manager_send_error (manager_client, NET_INADOR_ERROR_WRONG_COMMAND, 0);
return TRUE;
}
command = buffer[1];
switch (command) {
case NET_INADOR_COMMAND_LIST_IFACES:
_manager_send_list_interfaces (manager_client);
break;
case NET_INADOR_COMMAND_GET_IFACE:
_manager_send_iface (manager_client, buffer, bytes);
break;
case NET_INADOR_COMMAND_IFACE_UP:
case NET_INADOR_COMMAND_IFACE_DOWN:
_manager_execute_iface_down_up (manager_client, (command == NET_INADOR_COMMAND_IFACE_UP), buffer, bytes);
break;
case NET_INADOR_COMMAND_IFACE_CHANGE_NAME:
_manager_execute_iface_change_name (manager_client, buffer, bytes);
break;
case NET_INADOR_COMMAND_LIST_IP:
_manager_send_list_ips (manager_client, buffer, bytes);
break;
case NET_INADOR_COMMAND_CLEAR_IP:
_manager_execute_clear_ips (manager_client, buffer, bytes);
break;
case NET_INADOR_COMMAND_ADD_IP:
_manager_execute_add_ip (manager_client, buffer, bytes);
break;
/*case NET_INADOR_COMMAND_REMOVE_IP:
break;*/
case NET_INADOR_COMMAND_SET_EVENT_MASK:
_manager_handle_set_event_mask (manager_client, buffer, bytes);
break;
default:
_manager_send_error (manager_client, NET_INADOR_ERROR_WRONG_COMMAND, command);
}
return TRUE;
}
static gboolean _manager_client_connect (GIOChannel *source, GIOCondition condition, gpointer data) {
NetworkInadorManager *manager = (NetworkInadorManager *) data;
ManagerClientInfo *manager_client;
int fd;
GIOChannel *channel;
fd = accept (manager->socket, NULL, NULL);
printf ("___ MANAGER ___ Nueva conexión (%i)\n", fd);
manager_client = malloc (sizeof (ManagerClientInfo));
if (manager_client == NULL) {
close (fd);
return TRUE;
}
memset (manager_client, 0, sizeof (*manager_client));
manager_client->fd = fd;
/* Generar el vigilador */
channel = g_io_channel_unix_new (fd);
manager_client->source = g_io_add_watch (channel, G_IO_IN | G_IO_PRI | G_IO_ERR | G_IO_HUP, _manager_client_data, manager_client);
g_io_channel_unref (channel);
manager_client->manager = manager;
manager->connected_client_list = g_list_prepend (manager->connected_client_list, manager_client);
return TRUE;
}
void manager_send_event_interface_add (NetworkInadorHandle *handle, Interface *iface) {
printf ("___ MANAGER ___ Informando interfaz agregada: %s (%i)\n", iface->name, iface->index);
GList *g;
ManagerClientInfo *manager_client;
if (handle->manager == NULL) return;
for (g = handle->manager->connected_client_list; g != NULL; g = g->next) {
manager_client = (ManagerClientInfo *) g->data;
if (manager_client->wanted_events & NET_INADOR_EVENT_MASK_INTERFACES) {
printf ("___ MANAGER ___ Informando a la conexión (%i)\n", manager_client->fd);
_manager_send_interface (manager_client, iface, TRUE);
}
}
}
void manager_send_event_interface_del (NetworkInadorHandle *handle, uint32_t index) {
printf ("___ MANAGER ___ Informando interfaz eliminada: %i\n", index);
GList *g;
ManagerClientInfo *manager_client;
if (handle->manager == NULL) return;
for (g = handle->manager->connected_client_list; g != NULL; g = g->next) {
manager_client = (ManagerClientInfo *) g->data;
if (manager_client->wanted_events & NET_INADOR_EVENT_MASK_INTERFACES) {
printf ("___ MANAGER ___ Informando a la conexión (%i)\n", manager_client->fd);
_manager_send_interface_del (manager_client, index);
}
}
}
void manager_send_event_interface_update (NetworkInadorHandle *handle, Interface *iface) {
printf ("___ MANAGER ___ Informando interfaz actualizada: %s (%i)\n", iface->name, iface->index);
GList *g;
ManagerClientInfo *manager_client;
if (handle->manager == NULL) return;
for (g = handle->manager->connected_client_list; g != NULL; g = g->next) {
manager_client = (ManagerClientInfo *) g->data;
if (manager_client->wanted_events & NET_INADOR_EVENT_MASK_INTERFACES) {
printf ("___ MANAGER ___ Informando a la conexión (%i)\n", manager_client->fd);
_manager_send_interface (manager_client, iface, TRUE);
}
}
}
void manager_send_event_ip_add (NetworkInadorHandle *handle, IPAddr *ip_addr) {
printf ("___ MANAGER ___ Informando ip agregada: %s (%i)\n", ip_addr->iface->name, ip_addr->iface->index);
GList *g;
ManagerClientInfo *manager_client;
if (handle->manager == NULL) return;
for (g = handle->manager->connected_client_list; g != NULL; g = g->next) {
manager_client = (ManagerClientInfo *) g->data;
if (manager_client->wanted_events & NET_INADOR_EVENT_MASK_IP) {
printf ("___ MANAGER ___ Informando a la conexión (%i)\n", manager_client->fd);
_manager_send_ip (manager_client, ip_addr, TRUE);
}
}
}
void manager_send_event_ip_del (NetworkInadorHandle *handle, IPAddr *ip_addr) {
printf ("___ MANAGER ___ Informando ip eliminada: %s (%i)\n", ip_addr->iface->name, ip_addr->iface->index);
GList *g;
ManagerClientInfo *manager_client;
if (handle->manager == NULL) return;
for (g = handle->manager->connected_client_list; g != NULL; g = g->next) {
manager_client = (ManagerClientInfo *) g->data;
if (manager_client->wanted_events & NET_INADOR_EVENT_MASK_IP) {
printf ("___ MANAGER ___ Informando a la conexión (%i)\n", manager_client->fd);
_manager_send_ip_del (manager_client, ip_addr);
}
}
}
int manager_init (NetworkInadorHandle *handle) {
NetworkInadorManager *manager;
struct sockaddr_un socket_name;
GIOChannel *channel;
manager = malloc (sizeof (NetworkInadorManager));
if (manager == NULL) {
return -1;
}
memset (manager, 0, sizeof (*manager));
manager->socket = socket (AF_UNIX, SOCK_SEQPACKET | SOCK_CLOEXEC, 0);
if (manager->socket < 0) {
perror ("Failed to create AF_UNIX socket");
free (manager);
return -1;
}
memset (&socket_name, 0, sizeof (struct sockaddr_un));
socket_name.sun_family = AF_UNIX;
strncpy (socket_name.sun_path, COMMAND_SOCKET_PATH, sizeof (socket_name.sun_path) - 1);
unlink (COMMAND_SOCKET_PATH);
if (bind (manager->socket, (struct sockaddr *) &socket_name, sizeof (struct sockaddr_un)) < 0) {
perror ("bind");
close (manager->socket);
manager->socket = -1;
free (manager);
return -1;
}
if (listen (manager->socket, 10) < 0) {
perror ("listen");
close (manager->socket);
manager->socket = -1;
free (manager);
return -1;
}
/* TODO: Aplicar permisos aquí */
chmod (COMMAND_SOCKET_PATH, 0666);
channel = g_io_channel_unix_new (manager->socket);
manager->source = g_io_add_watch (channel, G_IO_IN | G_IO_PRI | G_IO_ERR | G_IO_HUP, _manager_client_connect, manager);
g_io_channel_unref (channel);
manager->handle = handle;
handle->manager = manager;
return 0;
}

38
src/manager.h 100644
View File

@ -0,0 +1,38 @@
/*
* manager.h
* This file is part of Network Inador
*
* Copyright (C) 2021 - Gatuno
*
* Network Inador is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* Network Inador is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with Network Inador; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor,
* Boston, MA 02110-1301 USA
*/
#ifndef __MANAGER_H__
#define __MANAGER_H__
#include <stdint.h>
#include "common.h"
int manager_init (NetworkInadorHandle *handle);
void manager_send_event_interface_add (NetworkInadorHandle *handle, Interface *iface);
void manager_send_event_interface_del (NetworkInadorHandle *handle, uint32_t index);
void manager_send_event_interface_update (NetworkInadorHandle *handle, Interface *iface);
void manager_send_event_ip_add (NetworkInadorHandle *handle, IPAddr *ip_addr);
void manager_send_event_ip_del (NetworkInadorHandle *handle, IPAddr *ip_addr);
#endif /* __MANAGER_H__ */

View File

@ -0,0 +1,63 @@
#ifndef __NETWOR_INADOR_MANAGER_H__
#define __NETWOR_INADOR_MANAGER_H__
enum {
NET_INADOR_TYPE_COMMAND = 1,
NET_INADOR_TYPE_RESPONSE = 2,
NET_INADOR_TYPE_RESPONSE_ERROR = 3,
NET_INADOR_TYPE_RESPONSE_LISTING_END = 4,
NET_INADOR_TYPE_EVENT = 16
};
/* Lista de eventos */
#define NET_INADOR_EVENT_MASK_INTERFACES 0x01
#define NET_INADOR_EVENT_MASK_IP 0x02
enum {
NET_INADOR_COMMAND_LIST_IFACES = 1,
NET_INADOR_COMMAND_GET_IFACE,
NET_INADOR_COMMAND_IFACE_UP,
NET_INADOR_COMMAND_IFACE_DOWN,
NET_INADOR_COMMAND_IFACE_CHANGE_NAME,
NET_INADOR_COMMAND_LIST_IP = 32,
NET_INADOR_COMMAND_CLEAR_IP,
NET_INADOR_COMMAND_ADD_IP,
NET_INADOR_COMMAND_REMOVE_IP,
NET_INADOR_COMMAND_SET_EVENT_MASK = 192,
};
enum {
NET_INADOR_ERROR_UNKNOWN = 0,
NET_INADOR_ERROR_WRONG_COMMAND,
NET_INADOR_ERROR_INCOMPLETE_REQUEST,
NET_INADOR_ERROR_INVALID_IFACE_INDEX,
NET_INADOR_ERROR_INVALID_FAMILY,
NET_INADOR_ERROR_INVALID_VALUE,
NET_INADOR_ERROR_NOT_EXECUTED,
NET_INADOR_ERROR_BAD_STRING,
};
enum {
NET_INADOR_EVENT_IFACE_ADDED = 2,
NET_INADOR_EVENT_IPADDR_ADDED,
NET_INADOR_EVENT_IFACE_REMOVED,
NET_INADOR_EVENT_IPADDR_REMOVED
};
enum {
NET_INADOR_RESPONSE_EXECUTED = 1,
NET_INADOR_RESPONSE_IFACE = 2,
NET_INADOR_RESPONSE_IPADDR,
};
#endif /* __NETWOR_INADOR_MANAGER_H__ */