diff --git a/src/tun_if.c b/src/tun_if.c index 0cb2182..b924ce2 100644 --- a/src/tun_if.c +++ b/src/tun_if.c @@ -1,9 +1,12 @@ -// tun_if.c - TUN interface management implementation +// tun_if.c - Simplified TUN interface management implementation #define _POSIX_C_SOURCE 200809L #include "tun_if.h" +#include "config_parser.h" +#include "etcp.h" #include "../lib/debug_config.h" #include "../lib/u_async.h" -#include "etcp_connections.h" +#include "../lib/ll_queue.h" +#include "../lib/memory_pool.h" #include #include #include @@ -46,7 +49,7 @@ static int parse_ip_mask(const char *ip_addr, struct in_addr *ip, struct in_addr char ip_str[INET_ADDRSTRLEN]; char *slash = strchr(ip_addr, '/'); - if (!slash) return -1; // Require /mask + if (!slash) return -1; size_t ip_len = slash - ip_addr; if (ip_len >= sizeof(ip_str)) return -1; @@ -97,46 +100,8 @@ static int create_tun_device(char *ifname, size_t ifname_len) { return fd; } -int tun_create(struct tun_config *config) { - if (!config) { - errno = EINVAL; - return -1; - } - - // Create TUN device - int fd = create_tun_device(config->ifname, sizeof(config->ifname)); - if (fd < 0) { - return -1; - } - - config->fd = fd; - - // Configure IP if specified - if (config->ip_addr[0] != '\0') { - if (tun_set_ip(config->ifname, config->ip_addr) < 0) { - close(fd); - return -1; - } - } - - // Set MTU if specified - if (config->mtu > 0) { - if (tun_set_mtu(config->ifname, config->mtu) < 0) { - DEBUG_WARN(DEBUG_CATEGORY_TUN, "Failed to set MTU %d on %s: %s", config->mtu, config->ifname, strerror(errno)); - } - } - - // Bring interface up - if (tun_set_up(config->ifname) < 0) { - close(fd); - return -1; - } - - config->is_up = 1; - return 0; -} - -int tun_set_ip(const char *ifname, const char *ip_addr) { +// Set IP address on TUN interface +static int tun_set_ip(const char *ifname, const char *ip_addr) { if (!ifname || !ip_addr) { errno = EINVAL; return -1; @@ -167,7 +132,8 @@ int tun_set_ip(const char *ifname, const char *ip_addr) { return 0; } -int tun_set_up(const char *ifname) { +// Bring TUN interface up +static int tun_set_up(const char *ifname) { if (!ifname) { errno = EINVAL; return -1; @@ -186,7 +152,8 @@ int tun_set_up(const char *ifname) { return 0; } -int tun_set_mtu(const char *ifname, int mtu) { +// Set MTU on TUN interface +static int tun_set_mtu(const char *ifname, int mtu) { if (!ifname || mtu <= 0) { errno = EINVAL; return -1; @@ -201,119 +168,228 @@ int tun_set_mtu(const char *ifname, int mtu) { return 0; } -ssize_t tun_read(int fd, uint8_t *buffer, size_t size) { - if (fd < 0 || !buffer || size == 0) { - errno = EINVAL; - return -1; - } +// Internal read callback - called by uasync when data available on TUN +static void tun_read_callback(int fd, void* user_arg) { + struct tun_if* tun = (struct tun_if*)user_arg; + uint8_t buffer[TUN_MAX_PACKET_SIZE]; - ssize_t nread = read(fd, buffer, size); + // Read from TUN device + ssize_t nread = read(fd, buffer, sizeof(buffer)); if (nread < 0) { - perror("tun_read"); + if (errno == EINTR) return; + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to read from TUN device %s: %s", tun->ifname, strerror(errno)); + tun->read_errors++; + return; } - return nread; -} + if (nread == 0) return; -ssize_t tun_write(int fd, const uint8_t *buffer, size_t size) { - if (fd < 0 || !buffer || size == 0) { - errno = EINVAL; - return -1; + // Allocate packet data + uint8_t* packet_data = malloc(nread); + if (!packet_data) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to allocate packet data (size=%zd)", nread); + tun->read_errors++; + return; + } + memcpy(packet_data, buffer, nread); + + // Allocate ETCP_FRAGMENT from pool + struct ETCP_FRAGMENT* pkt = (struct ETCP_FRAGMENT*)queue_entry_new_from_pool(tun->pool); + if (!pkt) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to allocate ETCP_FRAGMENT from pool"); + free(packet_data); + tun->read_errors++; + return; } - ssize_t nwritten = write(fd, buffer, size); - if (nwritten < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to write to TUN device fd=%d: %s", fd, strerror(errno)); + // Initialize fragment + pkt->seq = 0; + pkt->timestamp = 0; + pkt->ll.dgram = packet_data; + pkt->ll.len = nread; + + // Add to input queue + if (queue_data_put(tun->input_queue, (struct ll_entry*)pkt, 0) != 0) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to add packet to input queue"); + free(packet_data); + memory_pool_free(tun->pool, pkt); + tun->read_errors++; + return; } - return nwritten; + // Update statistics + tun->bytes_read += nread; + tun->packets_read++; + + DEBUG_DEBUG(DEBUG_CATEGORY_TUN, "Read %zd bytes from TUN %s", nread, tun->ifname); } -void tun_close(struct tun_config *config) { - if (!config) return; +struct tun_if* tun_init(struct UASYNC* ua, struct utun_config* config) { + if (!ua || !config) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Invalid arguments: ua=%p, config=%p", ua, config); + return NULL; + } - if (config->fd >= 0) { - close(config->fd); - config->fd = -1; + // Allocate tun_if structure + struct tun_if* tun = calloc(1, sizeof(struct tun_if)); + if (!tun) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to allocate tun_if"); + return NULL; } - config->is_up = 0; -} + tun->ua = ua; + tun->fd = -1; -int tun_get_config(const char *ifname, struct tun_config *config) { - if (!ifname || !config) { - errno = EINVAL; - return -1; + // Get interface name from config (or empty for auto) + const char* ifname = config->global.tun_ifname; + if (ifname && ifname[0] != '\0') { + strncpy(tun->ifname, ifname, sizeof(tun->ifname) - 1); } - // TODO: Implement reading current interface configuration - // This would require ioctl SIOCGIFADDR, SIOCGIFNETMASK, etc. + // Create TUN device + tun->fd = create_tun_device(tun->ifname, sizeof(tun->ifname)); + if (tun->fd < 0) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to create TUN device"); + free(tun); + return NULL; + } - memset(config, 0, sizeof(*config)); - strncpy(config->ifname, ifname, sizeof(config->ifname) - 1); - config->fd = -1; + // Build IP address string from config + char ip_buffer[INET_ADDRSTRLEN]; + char tun_ip_str[64]; + + if (config->global.tun_ip.family == AF_INET) { + inet_ntop(AF_INET, &config->global.tun_ip.addr.v4, ip_buffer, sizeof(ip_buffer)); + } else { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Only IPv4 is supported for TUN"); + close(tun->fd); + free(tun); + return NULL; + } - return 0; -} +#ifdef __linux__ + snprintf(tun_ip_str, sizeof(tun_ip_str), "%s/32", ip_buffer); +#elif defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(__APPLE__) + snprintf(tun_ip_str, sizeof(tun_ip_str), "%s", ip_buffer); +#else + snprintf(tun_ip_str, sizeof(tun_ip_str), "%s/32", ip_buffer); +#endif + + // Configure IP address + if (tun_set_ip(tun->ifname, tun_ip_str) < 0) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to set TUN IP: %s", tun_ip_str); + close(tun->fd); + free(tun); + return NULL; + } + + // Set MTU to 1500 (default) + int mtu = config->global.mtu > 0 ? config->global.mtu : TUN_MTU_DEFAULT; + if (tun_set_mtu(tun->ifname, mtu) < 0) { + DEBUG_WARN(DEBUG_CATEGORY_TUN, "Failed to set MTU %d on %s: %s", mtu, tun->ifname, strerror(errno)); + } + + // Bring interface up + if (tun_set_up(tun->ifname) < 0) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to bring up TUN interface %s", tun->ifname); + close(tun->fd); + free(tun); + return NULL; + } + + // Create memory pool for ETCP_FRAGMENT + tun->pool = memory_pool_init(sizeof(struct ETCP_FRAGMENT)); + if (!tun->pool) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to create memory pool"); + close(tun->fd); + free(tun); + return NULL; + } + + // Create input queue + tun->input_queue = queue_new(ua, 0); // hash_size=0 - no ID lookup needed + if (!tun->input_queue) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to create input queue"); + memory_pool_destroy(tun->pool); + close(tun->fd); + free(tun); + return NULL; + } + + // Register TUN socket with uasync + tun->socket_id = uasync_add_socket(ua, tun->fd, tun_read_callback, NULL, NULL, tun); + if (!tun->socket_id) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to register TUN socket with uasync"); + queue_free(tun->input_queue); + memory_pool_destroy(tun->pool); + close(tun->fd); + free(tun); + return NULL; + } + + DEBUG_INFO(DEBUG_CATEGORY_TUN, "TUN interface initialized: %s (fd=%d, IP=%s, MTU=%d)", + tun->ifname, tun->fd, tun_ip_str, mtu); -// Extract destination IPv4 address from packet -static uint32_t get_dest_ip(const uint8_t *packet, size_t len) { - if (len < 20) return 0; // Minimum IPv4 header size - // Check IP version (first nibble) - uint8_t version = (packet[0] >> 4) & 0x0F; - if (version != 4) return 0; - // Destination IP is at offset 16 - uint32_t dest_ip; - memcpy(&dest_ip, packet + 16, 4); - return dest_ip; + return tun; } -// Callback for TUN device read events -void tun_read_callback(int fd, void* user_arg) { - struct UTUN_INSTANCE *instance = (struct UTUN_INSTANCE*)user_arg; - uint8_t buffer[MAX_PACKET_SIZE]; +void tun_close(struct tun_if* tun) { + if (!tun) return; - // Read from TUN device - ssize_t nread = tun_read(fd, buffer, sizeof(buffer)); - if (nread < 0) { - if (errno == EINTR) return; - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to read from TUN device %s: %s", instance->tun.ifname, strerror(errno)); - return; + DEBUG_INFO(DEBUG_CATEGORY_TUN, "Closing TUN interface: %s", tun->ifname); + + // Unregister socket from uasync + if (tun->socket_id && tun->ua) { + uasync_remove_socket(tun->ua, tun->socket_id); + tun->socket_id = NULL; + } + + // Drain and free all packets from input queue + if (tun->input_queue) { + struct ETCP_FRAGMENT* pkt; + while ((pkt = (struct ETCP_FRAGMENT*)queue_data_get(tun->input_queue)) != NULL) { + if (pkt->ll.dgram) { + free(pkt->ll.dgram); + } + memory_pool_free(tun->pool, pkt); + } + queue_free(tun->input_queue); + tun->input_queue = NULL; } - if (nread > 0) { - // Route packet based on destination IP - uint32_t dest_ip = get_dest_ip(buffer, nread); - // ... (rest of the routing logic) + // Destroy memory pool + if (tun->pool) { + memory_pool_destroy(tun->pool); + tun->pool = NULL; } + + // Close file descriptor + if (tun->fd >= 0) { + close(tun->fd); + tun->fd = -1; + } + + free(tun); } -// Register sockets with uasync -int utun_instance_register_sockets(struct UTUN_INSTANCE *instance) { - if (!instance || !instance->ua || instance->tun.fd < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Invalid instance or TUN fd"); +ssize_t tun_write(struct tun_if* tun, const uint8_t* buf, size_t len) { + if (!tun || tun->fd < 0 || !buf || len == 0) { + if (tun) tun->write_errors++; + errno = EINVAL; return -1; } - // Register TUN file descriptor - instance->tun_socket_id = uasync_add_socket(instance->ua, instance->tun.fd, - tun_read_callback, NULL, NULL, instance); - if (!instance->tun_socket_id) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to register TUN socket"); + ssize_t nwritten = write(tun->fd, buf, len); + if (nwritten < 0) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to write to TUN device %s: %s", tun->ifname, strerror(errno)); + tun->write_errors++; return -1; } - DEBUG_INFO(DEBUG_CATEGORY_TUN, "Registered TUN socket (fd=%d)", instance->tun.fd); - return 0; -} + tun->bytes_written += nwritten; + tun->packets_written++; -// Unregister sockets -void utun_instance_unregister_sockets(struct UTUN_INSTANCE *instance) { - if (!instance || !instance->ua) return; + DEBUG_DEBUG(DEBUG_CATEGORY_TUN, "Wrote %zd bytes to TUN %s", nwritten, tun->ifname); - if (instance->tun_socket_id) { - uasync_remove_socket(instance->ua, instance->tun_socket_id); - instance->tun_socket_id = NULL; - DEBUG_INFO(DEBUG_CATEGORY_TUN, "Unregistered TUN socket: %s", instance->tun.ifname); - } -} \ No newline at end of file + return nwritten; +} diff --git a/src/tun_if.h b/src/tun_if.h index bfece0f..a347849 100644 --- a/src/tun_if.h +++ b/src/tun_if.h @@ -1,102 +1,82 @@ -// tun_if.h - TUN interface management for utun +// tun_if.h - Simplified TUN interface management for utun #ifndef TUN_IF_H #define TUN_IF_H + #include #include #include // Forward declarations -struct UTUN_INSTANCE; +struct UASYNC; +struct utun_config; +struct ll_queue; +struct memory_pool; #ifdef __cplusplus extern "C" { #endif -#define MAX_PACKET_SIZE 1500 - -// TUN interface configuration -struct tun_config { - char ifname[16]; // Interface name (e.g., "tun12") - char ip_addr[64]; // IP address with mask (e.g., "10.0.0.1/24") - int mtu; // MTU size - int fd; // File descriptor - uint8_t is_up; // 1 if interface is up +#define TUN_MTU_DEFAULT 1500 +#define TUN_MAX_PACKET_SIZE 1500 + +// TUN interface handle - opaque structure +struct tun_if { + char ifname[16]; // Interface name (e.g., "tun12") + int fd; // File descriptor + struct UASYNC* ua; // uasync instance + void* socket_id; // Socket ID from uasync_add_socket + struct memory_pool* pool; // Pool for ETCP_FRAGMENT structures + struct ll_queue* input_queue; // Queue for incoming packets (ETCP_FRAGMENT) // Statistics - uint64_t bytes_read; // Bytes read from TUN - uint64_t bytes_written; // Bytes written to TUN - uint32_t packets_read; // Packets read from TUN - uint32_t packets_written; // Packets written to TUN - uint32_t read_errors; // Read errors - uint32_t write_errors; // Write errors + uint64_t bytes_read; // Bytes read from TUN + uint64_t bytes_written; // Bytes written to TUN + uint32_t packets_read; // Packets read from TUN + uint32_t packets_written; // Packets written to TUN + uint32_t read_errors; // Read errors + uint32_t write_errors; // Write errors }; /** - * @brief Create and configure TUN interface - * @param config TUN configuration (ifname can be empty for auto) - * @return 0 on success, -1 on error - */ -int tun_create(struct tun_config *config); - -/** - * @brief Configure IP address on TUN interface - * @param ifname Interface name - * @param ip_addr IP address with mask (e.g., "10.0.0.1/24") - * @return 0 on success, -1 on error + * @brief Initialize TUN interface + * Creates TUN device, sets MTU=1500, brings interface up, + * configures IP from config, registers read callback in uasync, + * creates memory pool and input queue for incoming packets. + * @param ua uasync instance for event handling + * @param config Configuration containing tun_ip and other settings + * @return Pointer to tun_if on success, NULL on error */ -int tun_set_ip(const char *ifname, const char *ip_addr); +struct tun_if* tun_init(struct UASYNC* ua, struct utun_config* config); /** - * @brief Bring TUN interface up - * @param ifname Interface name - * @return 0 on success, -1 on error + * @brief Close TUN interface and free resources + * Unregisters socket from uasync, closes fd, drains and frees + * all packets from input_queue, destroys pool and queue. + * @param tun TUN interface handle */ -int tun_set_up(const char *ifname); - -/** - * @brief Set MTU on TUN interface - * @param ifname Interface name - * @param mtu MTU value - * @return 0 on success, -1 on error - */ -int tun_set_mtu(const char *ifname, int mtu); - -/** - * @brief Read packet from TUN interface - * @param fd TUN file descriptor - * @param buffer Buffer to store packet - * @param size Buffer size - * @return Number of bytes read, -1 on error - */ -ssize_t tun_read(int fd, uint8_t *buffer, size_t size); +void tun_close(struct tun_if* tun); /** * @brief Write packet to TUN interface - * @param fd TUN file descriptor - * @param buffer Packet data - * @param size Packet size + * @param tun TUN interface handle + * @param buf Packet data + * @param len Packet size * @return Number of bytes written, -1 on error */ -ssize_t tun_write(int fd, const uint8_t *buffer, size_t size); - -/** - * @brief Close TUN interface - * @param config TUN configuration - */ -void tun_close(struct tun_config *config); +ssize_t tun_write(struct tun_if* tun, const uint8_t* buf, size_t len); /** - * @brief Get current TUN configuration - * @param ifname Interface name - * @param config Output configuration - * @return 0 on success, -1 on error + * @brief Get input queue for reading packets + * User should call queue_data_get(tun->input_queue) to retrieve packets. + * Each packet is struct ETCP_FRAGMENT with: + * - ll.dgram: malloc'd packet data (user must free) + * - ll.len: packet length + * User must free dgram and return fragment to pool via memory_pool_free(). + * @param tun TUN interface handle + * @return Pointer to input queue */ -int tun_get_config(const char *ifname, struct tun_config *config); - -int utun_instance_register_sockets(struct UTUN_INSTANCE *instance); -void utun_instance_unregister_sockets(struct UTUN_INSTANCE *instance); - -// TUN callback function -void tun_read_callback(int fd, void* user_arg); +static inline struct ll_queue* tun_get_input_queue(struct tun_if* tun) { + return tun ? tun->input_queue : NULL; +} #ifdef __cplusplus } diff --git a/src/utun.c b/src/utun.c index eccc514..a6345c2 100644 --- a/src/utun.c +++ b/src/utun.c @@ -292,12 +292,7 @@ int main(int argc, char *argv[]) { return 1; } - // Register sockets with uasync - if (utun_instance_register_sockets(instance) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_MEMORY, "Failed to register sockets"); - utun_instance_destroy(instance); - return 1; - } + // Note: TUN socket is registered in tun_init(), ETCP sockets in init_connections() // Setup signal handlers signal(SIGINT, signal_handler); @@ -324,7 +319,6 @@ int main(int argc, char *argv[]) { // Cleanup DEBUG_ERROR(DEBUG_CATEGORY_ETCP, "Shutdown"); - utun_instance_unregister_sockets(instance); utun_instance_destroy(instance); // Destroy uasync instance after instance is destroyed diff --git a/src/utun_instance.c b/src/utun_instance.c index 9a0ca65..8c16fea 100644 --- a/src/utun_instance.c +++ b/src/utun_instance.c @@ -81,70 +81,17 @@ struct UTUN_INSTANCE* utun_instance_create(struct UASYNC* ua, const char *config // Initialize TUN device only if enabled if (g_tun_init_enabled) { - // Initialize TUN device - if (tun_create(&instance->tun) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to create TUN device"); + instance->tun = tun_init(ua, instance->config); + if (!instance->tun) { + DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to initialize TUN device"); free(instance); return NULL; } - - // Configure TUN device IP (BSD: use config IP as-is, Linux/Win: IP/32) - char tun_ip_str[64]; - char ip_buffer[64]; - - // Convert struct IP to string using inet_ntop - if (instance->config->global.tun_ip.family == AF_INET) { - inet_ntop(AF_INET, &instance->config->global.tun_ip.addr.v4, ip_buffer, sizeof(ip_buffer)); - } else { - inet_ntop(AF_INET6, &instance->config->global.tun_ip.addr.v6, ip_buffer, sizeof(ip_buffer)); - } - - #ifdef __linux__ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wformat-truncation" - snprintf(tun_ip_str, sizeof(tun_ip_str), "%s/32", ip_buffer); -#pragma GCC diagnostic pop - #elif defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(__APPLE__) - // BSD systems: use config IP as-is, peer IP will be 192.0.2.1 - snprintf(tun_ip_str, sizeof(tun_ip_str), "%s", ip_buffer); - #else -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wformat-truncation" - snprintf(tun_ip_str, sizeof(tun_ip_str), "%s/32", ip_buffer); // Default to /32 -#pragma GCC diagnostic pop - #endif - - if (tun_set_ip(instance->tun.ifname, tun_ip_str) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to set TUN IP: %s", tun_ip_str); - tun_close(&instance->tun); - free(instance); - return NULL; - } - - // Set MTU (default 1500) - int mtu = instance->config->global.mtu > 0 ? instance->config->global.mtu : 1500; - if (tun_set_mtu(instance->tun.ifname, mtu) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to set TUN MTU: %d", mtu); - tun_close(&instance->tun); - free(instance); - return NULL; - } - - if (tun_set_up(instance->tun.ifname) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to bring up TUN interface"); - tun_close(&instance->tun); - free(instance); - return NULL; - } - - DEBUG_INFO(DEBUG_CATEGORY_TUN, "TUN interface initialized: %s with IP %s", - instance->tun.ifname, tun_ip_str); + DEBUG_INFO(DEBUG_CATEGORY_TUN, "TUN interface initialized: %s", instance->tun->ifname); } else { // TUN initialization disabled - skip TUN setup DEBUG_INFO(DEBUG_CATEGORY_TUN, "TUN initialization disabled - skipping TUN device setup"); - // Initialize TUN structure with safe defaults - memset(&instance->tun, 0, sizeof(instance->tun)); - instance->tun.fd = -1; // Invalid file descriptor to indicate no TUN device + instance->tun = NULL; } return instance; @@ -162,12 +109,6 @@ void utun_instance_destroy(struct UTUN_INSTANCE *instance) { // Stop running if not already instance->running = 0; - // Unregister all sockets from uasync BEFORE destroying ETCP components - DEBUG_INFO(DEBUG_CATEGORY_MEMORY, "[INSTANCE_DESTROY] Unregistering sockets from uasync"); - utun_instance_unregister_sockets(instance); - DEBUG_INFO(DEBUG_CATEGORY_MEMORY, "[INSTANCE_DESTROY] Socket unregistration complete"); - - // Cleanup ETCP sockets and connections FIRST (before destroying uasync) DEBUG_INFO(DEBUG_CATEGORY_MEMORY, "[INSTANCE_DESTROY] Cleaning up ETCP sockets and connections"); struct ETCP_SOCKET* sock = instance->etcp_sockets; @@ -194,9 +135,10 @@ void utun_instance_destroy(struct UTUN_INSTANCE *instance) { DEBUG_INFO(DEBUG_CATEGORY_MEMORY, "[INSTANCE_DESTROY] ETCP connections cleanup complete"); // Cleanup TUN - if (instance->tun.fd >= 0) { - DEBUG_INFO(DEBUG_CATEGORY_TUN, "Closing TUN interface: %s", instance->tun.ifname); - tun_close(&instance->tun); + if (instance->tun) { + DEBUG_INFO(DEBUG_CATEGORY_TUN, "Closing TUN interface: %s", instance->tun->ifname); + tun_close(instance->tun); + instance->tun = NULL; } // Cleanup config @@ -258,17 +200,7 @@ void utun_instance_stop(struct UTUN_INSTANCE *instance) { int utun_instance_init(struct UTUN_INSTANCE *instance) { if (!instance) return -1; - // Register TUN socket with uasync - if (instance->tun.fd >= 0) { - instance->tun_socket_id = uasync_add_socket(instance->ua, instance->tun.fd, - tun_read_callback, NULL, NULL, instance); - if (!instance->tun_socket_id) { - DEBUG_ERROR(DEBUG_CATEGORY_TUN, "Failed to register TUN socket with uasync"); - return -1; - } - DEBUG_INFO(DEBUG_CATEGORY_TUN, "TUN interface registered: %s (fd=%d)", - instance->tun.ifname, instance->tun.fd); - } + // Note: TUN socket is already registered in tun_init() // Initialize connections // Добавляем прямой вывод для отладки проблемы double free @@ -344,8 +276,8 @@ void utun_instance_diagnose_leaks(struct UTUN_INSTANCE *instance, const char *ph printf("\n🔧 RESOURCE STATUS:\n"); printf(" Memory Pool: %s\n", instance->pkt_pool ? "ALLOCATED" : "NULL"); - printf(" TUN Socket ID: %p\n", instance->tun_socket_id); - printf(" TUN FD: %d\n", instance->tun.fd); + printf(" TUN Interface: %s\n", instance->tun ? instance->tun->ifname : "NULL"); + printf(" TUN FD: %d\n", instance->tun ? instance->tun->fd : -1); printf(" Connections list: %p\n", instance->connections); printf(" ETCP Sockets list: %p\n", instance->etcp_sockets); @@ -353,8 +285,8 @@ void utun_instance_diagnose_leaks(struct UTUN_INSTANCE *instance, const char *ph if (instance->pkt_pool) { printf(" ❌ Memory Pool not freed\n"); } - if (instance->tun_socket_id) { - printf(" ❌ TUN socket not unregistered from uasync\n"); + if (instance->tun) { + printf(" ❌ TUN interface not closed\n"); } if (report.etcp_sockets_count > 0) { printf(" ❌ %d ETCP sockets still allocated\n", report.etcp_sockets_count); @@ -370,8 +302,8 @@ void utun_instance_diagnose_leaks(struct UTUN_INSTANCE *instance, const char *ph if (instance->pkt_pool) { printf(" → Call memory_pool_destroy() before freeing instance\n"); } - if (instance->tun_socket_id) { - printf(" → Call uasync_remove_socket() for TUN socket\n"); + if (instance->tun) { + printf(" → Call tun_close() to close TUN interface\n"); } if (report.etcp_sockets_count > 0) { printf(" → Iterate and call etcp_socket_remove() for each socket\n"); diff --git a/src/utun_instance.h b/src/utun_instance.h index 95a6b7b..b613d6e 100644 --- a/src/utun_instance.h +++ b/src/utun_instance.h @@ -6,7 +6,6 @@ #include #include "../lib/memory_pool.h" #include "secure_channel.h" -#include "tun_if.h" // Forward declarations struct utun_config; @@ -14,6 +13,7 @@ struct uasync_s; struct routing_table; struct ETCP_CONN; struct ETCP_SOCKET; +struct tun_if; // uTun instance configuration struct UTUN_INSTANCE { @@ -21,8 +21,7 @@ struct UTUN_INSTANCE { struct utun_config *config; // TUN interface - struct tun_config tun; - void *tun_socket_id; // Socket ID from uasync_add_socket + struct tun_if* tun; // Identification uint64_t node_id; diff --git a/tests/bench_timeout_heap b/tests/bench_timeout_heap deleted file mode 100755 index a0b97ef..0000000 Binary files a/tests/bench_timeout_heap and /dev/null differ diff --git a/tests/bench_uasync_timeouts b/tests/bench_uasync_timeouts deleted file mode 100755 index 4bfba10..0000000 Binary files a/tests/bench_uasync_timeouts and /dev/null differ diff --git a/tests/test_config_debug b/tests/test_config_debug deleted file mode 100755 index e2a6b18..0000000 Binary files a/tests/test_config_debug and /dev/null differ diff --git a/tests/test_crypto b/tests/test_crypto deleted file mode 100755 index 043da27..0000000 Binary files a/tests/test_crypto and /dev/null differ diff --git a/tests/test_debug_categories b/tests/test_debug_categories deleted file mode 100755 index d8f80ec..0000000 Binary files a/tests/test_debug_categories and /dev/null differ diff --git a/tests/test_ecc_encrypt b/tests/test_ecc_encrypt deleted file mode 100755 index 7b28462..0000000 Binary files a/tests/test_ecc_encrypt and /dev/null differ diff --git a/tests/test_etcp_100_packets b/tests/test_etcp_100_packets deleted file mode 100755 index 3af8c94..0000000 Binary files a/tests/test_etcp_100_packets and /dev/null differ diff --git a/tests/test_etcp_crypto b/tests/test_etcp_crypto deleted file mode 100755 index b155760..0000000 Binary files a/tests/test_etcp_crypto and /dev/null differ diff --git a/tests/test_etcp_minimal b/tests/test_etcp_minimal deleted file mode 100755 index 0dfbd77..0000000 Binary files a/tests/test_etcp_minimal and /dev/null differ diff --git a/tests/test_etcp_simple_traffic b/tests/test_etcp_simple_traffic deleted file mode 100755 index 28c0bb2..0000000 Binary files a/tests/test_etcp_simple_traffic and /dev/null differ diff --git a/tests/test_etcp_two_instances b/tests/test_etcp_two_instances deleted file mode 100755 index af50861..0000000 Binary files a/tests/test_etcp_two_instances and /dev/null differ diff --git a/tests/test_etcp_two_instances.c b/tests/test_etcp_two_instances.c index eb8e521..5f8a9e7 100644 --- a/tests/test_etcp_two_instances.c +++ b/tests/test_etcp_two_instances.c @@ -144,23 +144,11 @@ int main() { return 1; } - // Check if TUN is disabled and handle accordingly - if (server_instance->tun.fd < 0) { - DEBUG_INFO(DEBUG_CATEGORY_TUN, "Server TUN disabled - skipping TUN initialization"); - DEBUG_INFO(DEBUG_CATEGORY_ETCP, "Server instance created successfully (node_id=%llx)", (unsigned long long)server_instance->node_id); - } else { - // Normal initialization for TUN-enabled mode - if (utun_instance_init(server_instance) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_ETCP, "Failed to initialize server instance"); - utun_instance_destroy(server_instance); - return 1; - } - - if (utun_instance_register_sockets(server_instance) < 0) { - DEBUG_ERROR(DEBUG_CATEGORY_ETCP, "Failed to register server sockets"); - utun_instance_destroy(server_instance); - return 1; - } + // Initialize instance (TUN is initialized in utun_instance_create if enabled) + if (utun_instance_init(server_instance) < 0) { + DEBUG_ERROR(DEBUG_CATEGORY_ETCP, "Failed to initialize server instance"); + utun_instance_destroy(server_instance); + return 1; } DEBUG_INFO(DEBUG_CATEGORY_ETCP, "Server instance ready (node_id=%llx)", (unsigned long long)server_instance->node_id); @@ -181,25 +169,12 @@ int main() { return 1; } - // Check if TUN is disabled and handle accordingly - if (client_instance->tun.fd < 0) { - DEBUG_INFO(DEBUG_CATEGORY_ETCP, "ℹ️ Client TUN disabled - skipping TUN initialization\n"); - DEBUG_INFO(DEBUG_CATEGORY_ETCP, "✅ Client instance created successfully (node_id=%llx)\n", (unsigned long long)client_instance->node_id); - } else { - // Normal initialization for TUN-enabled mode - if (utun_instance_init(client_instance) < 0) { - DEBUG_INFO(DEBUG_CATEGORY_ETCP, "Failed to initialize client instance\n"); - utun_instance_destroy(server_instance); - utun_instance_destroy(client_instance); - return 1; - } - - if (utun_instance_register_sockets(client_instance) < 0) { - DEBUG_INFO(DEBUG_CATEGORY_ETCP, "Failed to register client sockets\n"); - utun_instance_destroy(server_instance); - utun_instance_destroy(client_instance); - return 1; - } + // Initialize instance (TUN is initialized in utun_instance_create if enabled) + if (utun_instance_init(client_instance) < 0) { + DEBUG_INFO(DEBUG_CATEGORY_ETCP, "Failed to initialize client instance\n"); + utun_instance_destroy(server_instance); + utun_instance_destroy(client_instance); + return 1; } DEBUG_INFO(DEBUG_CATEGORY_ETCP, "Client instance ready (node_id=%llx)\n\n", (unsigned long long)client_instance->node_id); @@ -278,14 +253,14 @@ int main() { if (test_completed == 1) { DEBUG_INFO(DEBUG_CATEGORY_ETCP, "\n=== TEST PASSED ===\n"); // Check if TUN was disabled and add note - if (server_instance->tun.fd < 0 || client_instance->tun.fd < 0) { + if (!server_instance->tun || !client_instance->tun) { DEBUG_INFO(DEBUG_CATEGORY_ETCP, "✅ ETCP connection test successful with TUN disabled\n"); DEBUG_INFO(DEBUG_CATEGORY_ETCP, "✅ Core ETCP protocol functionality verified\n"); } return 0; } else if (test_completed == 2) { // Check if TUN was disabled - if so, timeout is expected and acceptable - if (server_instance->tun.fd < 0 || client_instance->tun.fd < 0) { + if (!server_instance->tun || !client_instance->tun) { DEBUG_INFO(DEBUG_CATEGORY_ETCP, "\n=== TEST PASSED ===\n"); DEBUG_INFO(DEBUG_CATEGORY_ETCP, "ℹ️ Connection timeout expected with TUN disabled\n"); DEBUG_INFO(DEBUG_CATEGORY_ETCP, "✅ ETCP core infrastructure verified successfully\n"); diff --git a/tests/test_intensive_memory_pool b/tests/test_intensive_memory_pool deleted file mode 100755 index 7bb8e16..0000000 Binary files a/tests/test_intensive_memory_pool and /dev/null differ diff --git a/tests/test_ll_queue b/tests/test_ll_queue deleted file mode 100755 index 368fa1a..0000000 Binary files a/tests/test_ll_queue and /dev/null differ diff --git a/tests/test_memory_pool_and_config b/tests/test_memory_pool_and_config deleted file mode 100755 index 6e40e75..0000000 Binary files a/tests/test_memory_pool_and_config and /dev/null differ diff --git a/tests/test_packet_dump b/tests/test_packet_dump deleted file mode 100755 index 05a1820..0000000 Binary files a/tests/test_packet_dump and /dev/null differ diff --git a/tests/test_pkt_normalizer_etcp b/tests/test_pkt_normalizer_etcp deleted file mode 100755 index 1f65eaa..0000000 Binary files a/tests/test_pkt_normalizer_etcp and /dev/null differ diff --git a/tests/test_pkt_normalizer_standalone b/tests/test_pkt_normalizer_standalone deleted file mode 100755 index 6c93106..0000000 Binary files a/tests/test_pkt_normalizer_standalone and /dev/null differ diff --git a/tests/test_u_async_comprehensive b/tests/test_u_async_comprehensive deleted file mode 100755 index f84e1cf..0000000 Binary files a/tests/test_u_async_comprehensive and /dev/null differ diff --git a/tests/test_u_async_performance b/tests/test_u_async_performance deleted file mode 100755 index 4a8b2aa..0000000 Binary files a/tests/test_u_async_performance and /dev/null differ