📄 mn_config.c
字号:
/* $Id: mn_config.c,v 1.42 2001/09/01 14:52:18 jm Exp $ * Mobile Node configuration file handling * * Dynamic hierarchial IP tunnel * Copyright (C) 1998-2001, Dynamics group * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. See README and COPYING for * more details. */#ifdef HAVE_CONFIG_H#include <config.h>#endif#include <stdlib.h>#include <stdio.h>#include <string.h>#include <assert.h>#include "fileio.h"#include "debug.h"#include "auth.h"#include "mn.h"#define DEBUG_FLAG 'M'struct load_mn_data { struct mn_config *cfg; int process_fa_spi_list; int process_ignore_iflist; int process_dev_prio_list;};static int check_config_data(struct mn_config *cfg) { int ret = TRUE; if (!auth_supported_auth_alg(cfg->auth_alg)) { fprintf(stderr, "Unsupported authentication algorithm %i\n", cfg->auth_alg); ret = FALSE; } if (cfg->replay_meth < 0 || cfg->replay_meth > 2) { fprintf(stderr, "Unsupported authentication algorithm %i\n", cfg->auth_alg); ret = FALSE; } if (cfg->tunneling_mode != TUNMODE_AUTO_REVERSE && cfg->tunneling_mode != TUNMODE_AUTO_TRIANGLE && cfg->tunneling_mode != TUNMODE_REVERSE && cfg->tunneling_mode != TUNMODE_TRIANGLE) { fprintf(stderr, "Unknown TunnelingMode: %i\n", cfg->tunneling_mode); ret = FALSE; } if (cfg->mndecaps_route_handling != MNDECAPS_ROUTE_DEFAULT && cfg->mndecaps_route_handling != MNDECAPS_ROUTE_HOME_NET && cfg->mndecaps_route_handling != MNDECAPS_ROUTE_NONE) { fprintf(stderr, "Unknown MNDecapsRouteHandling: %i\n", cfg->mndecaps_route_handling); ret = FALSE; } if (cfg->mndecaps_route_handling == MNDECAPS_ROUTE_HOME_NET && cfg->home_net_addr_plen == -1) { fprintf(stderr, "MNDecapsRouteHandling: home net, but home net" " address not properly configured.\n"); ret = FALSE; } return ret;}static int process_load_ignore_iflist(struct load_mn_data *mn, char *key, char *data){ struct mn_config *cfg; struct ignore_iflist_entry *ifs; int len; if (strcmp(key, "IGNORE_INTERFACES_END") == 0) { ASSERT(mn->process_ignore_iflist == TRUE); mn->process_ignore_iflist = FALSE; return 0; } cfg = mn->cfg; ifs = malloc(sizeof(struct ignore_iflist_entry)); if (ifs == NULL) { fprintf(stderr, "process_load_ignore_iflist: not enough memory for " "struct ignore_iflist_entry"); return -1; } list_init_node(&ifs->node); len = strlen(key); if (len > IFNAMSIZ - 1) { fprintf(stderr, "process_load_ignore_iflist: name too long (%d/%d)\n", len, IFNAMSIZ); free(ifs); return -1; } if (sscanf(key, "%s", ifs->ifname) != 1) { fprintf(stderr, "process_load_ignore_iflist: couldn't read interface " "name\n"); free(ifs); return -1; } ASSERT(ifs->ifname != NULL); list_add_tail(&cfg->ignore_iflist, &ifs->node); return 0;}static int process_load_fa_spi_list(struct load_mn_data *mn, char *key, char *data){ struct mn_config *cfg; struct fa_spi_entry *spi; char *pos; int res; if (strcmp(key, "FA_SECURITY_END") == 0) { ASSERT(mn->process_fa_spi_list == TRUE); mn->process_fa_spi_list = FALSE; return 0; } cfg = mn->cfg; spi = malloc(sizeof(struct fa_spi_entry)); if (spi == NULL) { fprintf(stderr, "process_load_fa_spi_list: not enough memory for " "struct spi_entry\n"); return -1; } memset(spi, 0, sizeof(struct fa_spi_entry)); list_init_node(&spi->node); if (key[0] == '0' && key[1] == 'x') res = sscanf(key, "%x", &spi->spi); else res = sscanf(key, "%d", &spi->spi); if (res != 1) { fprintf(stderr, "process_load_fa_spi_list: invalid SPI number\n"); free(spi); return -1; } pos = data; while (*pos == ' ' || *pos == '\t') pos++; if (load_ip_address(pos, &spi->addr) != TRUE) { fprintf(stderr, "process_load_fa_authorized_list: invalid " "IP address\n"); free(spi); return -1; } while (*pos != ' ' && *pos != '\t' && *pos != '\0') pos++; while (*pos == ' ' || *pos == '\t') pos++; if (*pos == '\0' || sscanf(pos, "%d", &spi->alg) != 1) { fprintf(stderr, "process_load_fa_spi_list: invalid algorithm " "number\n"); free(spi); return -1; } if (!auth_supported_auth_alg(spi->alg)) { fprintf(stderr, "process_load_fa_spi_list: unsupported " "algorithm %i\n", spi->alg); free(spi); return -1; } while (*pos != ' ' && *pos != '\t' && *pos != '\0') pos++; while (*pos == ' ' || *pos == '\t') pos++; if (*pos == '\0' || load_hex_table(pos, spi->shared_secret, MAXSHAREDSECRETLEN, &spi->shared_secret_len) == FALSE) { fprintf(stderr, "process_load_fa_spi_list: invalid shared secret\n"); free(spi); return -1; } spi->created = 0; /* static security association */ ASSERT(spi->shared_secret_len >= 0); ASSERT(spi->shared_secret_len <= MAXSHAREDSECRETLEN); list_add_tail(&cfg->fa_spi_list, &spi->node); return 0;}/* Process loading of the mn_data * Return values: -2: consistency error, -1: error, 0: ok, 1: end */static int process_load_mn(void *voidptr, char *key, char *data){ struct load_mn_data *mn; struct mn_config *cfg; mn = voidptr; cfg = mn->cfg; if (mn->process_fa_spi_list == TRUE) { return process_load_fa_spi_list(mn, key, data); } if (mn->process_ignore_iflist == TRUE) { return process_load_ignore_iflist(mn, key, data); } if (strcmp(key, "FA_SECURITY_BEGIN") == 0) { if (mn->process_fa_spi_list) { fprintf(stderr, "List processing error while handling " "FA_SECURITY_BEGIN\n"); return -1; } mn->process_fa_spi_list = TRUE; return 0; } if (strcmp(key, "IGNORE_INTERFACES_BEGIN") == 0) { if (mn->process_ignore_iflist) { fprintf(stderr, "List processing error while handling " "IGNORE_INTERFACES_BEGIN\n"); return -1; } mn->process_ignore_iflist = TRUE; return 0; } if (strcmp(key, "MNHomeIPAddress") == 0) { if (load_ip_address(data, &cfg->mn_home_ip_addr) == TRUE) return 0; return -1; } if (strcmp(key, "HAIPAddress") == 0) { if (load_ip_address(data, &cfg->ha_ip_addr) == TRUE) return 0; return -1; } if (strcmp(key, "AlternativeHAIPAddress") == 0) { struct in_addr tmpaddr; if (load_ip_address(data, &tmpaddr) == TRUE) { struct alt_ha_entry *alt; alt = (struct alt_ha_entry *) malloc(sizeof(*alt)); if (alt == NULL) return -1; list_init_node(&alt->node); alt->addr.s_addr = tmpaddr.s_addr; list_add_tail(&cfg->alt_ha_ip_addrs, &alt->node); return 0; } return -1; } if (strcmp(key, "AllowHomeAddrFromForeignNet") == 0) { if (load_bool(data, &cfg->allow_home_addr_from_foreign_net) == TRUE) return 0; return -1; } /* obsolete, remove sometime */ if (strcmp(key, "HomeNetAddr") == 0) { fprintf(stderr, "Please use HomeNetPrefix instead of " "HomeNetAddr/HomeNetAddrPrefixLen\n"); if (load_ip_address(data, &cfg->home_net_addr) == TRUE) return 0; return -1; } /* obsolete, remove sometime */ if (strcmp(key, "HomeNetAddrPrefixLen") == 0) { if (load_int(data, &cfg->home_net_addr_plen) == TRUE) return 0; return -1; } /* makes HomeNetAddr/HomeNetAddrPrefixLen obsolete */ if (strcmp(key, "HomeNetPrefix") == 0) { if (load_ip_prefix(data, &cfg->home_net_addr, &cfg->home_net_addr_plen) == TRUE) return 0; return -1; } if (strcmp(key, "HomeNetGateway") == 0) { if (load_ip_address(data, &cfg->home_net_gateway) == TRUE) return 0; return -1; } if (strcmp(key, "MNDecapsRouteHandling") == 0) { if (load_int(data, &cfg->mndecaps_route_handling) == TRUE) return 0; return -1; } if (strcmp(key, "SharedSecret") == 0) { if (load_hex_table(data, cfg->shared_secret, MAXSHAREDSECRETLEN, &cfg->shared_secret_len) == TRUE) { assert(cfg->shared_secret_len >= 0); assert(cfg->shared_secret_len <= MAXSHAREDSECRETLEN); return 0; } return -1; } if (strcmp(key, "SPI") == 0) { if (load_int(data, &cfg->spi) == TRUE) return 0; return -1; } if (strcmp(key, "UDPPort") == 0) { if (load_int(data, &cfg->udp_port) == TRUE) { return 0; } return -1; } if (strcmp(key, "AuthenticationAlgorithm") == 0) { if (load_int(data, &cfg->auth_alg) == TRUE) { return 0; } return -1; } if (strcmp(key, "ReplayMethod") == 0) { if (load_int(data, &cfg->replay_meth) == TRUE) { return 0; } return -1; } if (strcmp(key, "UseAAA") == 0) { if (load_bool(data, &cfg->use_aaa) == TRUE) return 0; return -1; } if (strcmp(key, "MN-AAA-SharedSecret") == 0) { if (load_hex_table(data, cfg->mn_aaa_shared_secret, MAXSHAREDSECRETLEN, &cfg->mn_aaa_shared_secret_len) == TRUE) { assert(cfg->mn_aaa_shared_secret_len >= 0); assert(cfg->mn_aaa_shared_secret_len <= MAXSHAREDSECRETLEN); return 0; } return -1; } if (strcmp(key, "MN-AAA-SPI") == 0) { if (load_int(data, &cfg->mn_aaa_spi) == TRUE) return 0; return -1; } if (strcmp(key, "MN-AAA-AuthenticationAlgorithm") == 0) { if (load_int(data, &cfg->mn_aaa_auth_alg) == TRUE) { return 0; } return -1; } if (strcmp(key, "MN-AAA-KeyGenerationAlgorithm") == 0) { if (load_int(data, &cfg->mn_aaa_keygen_alg) == TRUE) return 0; return -1; } if (strcmp(key, "EnableFADecapsulation") == 0) { if (load_bool(data, &cfg->enable_fa_decapsulation) == TRUE) { return 0; } return -1; } if (strcmp(key, "TunnelingMode") == 0) { if (load_int(data, &cfg->tunneling_mode) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNDefaultTunnelLifetime") == 0) { if (load_int(data, (int*)&cfg->mn_default_tunnel_lifetime) == TRUE) { return 0; } return -1; } if (strcmp(key, "SyslogFacility") == 0) { if (load_syslog_facility(data, &cfg->syslog_facility) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIReadSocketPath") == 0) { if (load_char_table(data, cfg->mn_api_read_socket_path, MAXFILENAMELEN) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIReadSocketGroup") == 0) { if (load_char_table(data, cfg->mn_api_read_socket_group, MAXGROUPNAMELEN) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIReadSocketOwner") == 0) { if (load_char_table(data, cfg->mn_api_read_socket_owner, MAXOWNERNAMELEN) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIReadSocketPermissions") == 0) { if (load_int(data, &cfg->mn_api_read_socket_permissions) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIAdminSocketPath") == 0) { if (load_char_table(data, cfg->mn_api_admin_socket_path, MAXFILENAMELEN) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIAdminSocketGroup") == 0) { if (load_char_table(data, cfg->mn_api_admin_socket_group, MAXGROUPNAMELEN) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIAdminSocketOwner") == 0) { if (load_char_table(data, cfg->mn_api_admin_socket_owner, MAXOWNERNAMELEN) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNAPIAdminSocketPermissions") == 0) { if (load_int(data, &cfg->mn_api_admin_socket_permissions) == TRUE) { return 0; } return -1; } if (strcmp(key, "SocketPriority") == 0) { if (load_int(data, &cfg->socket_priority) == TRUE) { return 0; } return -1; } if (strcmp(key, "EnforceRoutes") == 0) { if (load_bool(data, &cfg->enforce_routes) == TRUE) { return 0; } return -1; } if (strcmp(key, "APPollingInterval") == 0) { if (load_int(data, &cfg->wlan_ap_poll_interval) == TRUE) { return 0; } return -1; } if (strcmp(key, "SolicitationInterval") == 0) { if (load_int(data, &cfg->solicitation_interval) == TRUE) { return 0; } return -1; } if (strcmp(key, "PrivateHAIPAddress") == 0) { if (load_ip_address(data, &cfg->priv_ha_ip_addr) == TRUE) return 0; return -1; } if (strcmp(key, "PrivateHAIdentifier") == 0) { if (load_int(data, (int *) &cfg->priv_ha) == TRUE) { return 0; } return -1; } if (strcmp(key, "MNNetworkAccessIdentifier") == 0) { if (load_nai(data, cfg->mn_nai, &cfg->mn_nai_len) == TRUE) return 0; return -1; } if (strcmp(key, "HANetworkAccessIdentifier") == 0) { if (load_nai(data, cfg->ha_nai, &cfg->ha_nai_len) == TRUE) return 0; return -1; }#ifdef BIND_UDP_SOCKET if (strcmp(key, "BindAddress") == 0) { if (load_ip_address(data, &cfg->bind_addr) == TRUE) return 0; return -1; } if (strcmp(key, "BindPort") == 0) { int port; if (load_int(data, &port) == TRUE) { cfg->bind_port = htons((unsigned short) port); return 0; } return -1; }#endif#ifdef INCLUDE_IPAY if (strcmp(key, "IpayMNAddress") == 0) { if (load_ip_address(data, &cfg->ipay_mn_addr) == TRUE) return 0; return -1; } if (strcmp(key, "IpayMNPort") == 0) { if (load_int(data, &cfg->ipay_mn_port) == TRUE) { return 0; } return -1; } if (strcmp(key, "IpayBuyerAddress") == 0) { if (load_ip_address(data, &cfg->ipay_buyer_addr) == TRUE) return 0; return -1; } if (strcmp(key, "IpayBuyerPort") == 0) { if (load_int(data, &cfg->ipay_buyer_port) == TRUE) { return 0; } return -1; } if (strcmp(key, "IpayFAPort") == 0) { if (load_int(data, &cfg->ipay_fa_port) == TRUE) { return 0; } return -1; }#endif if (strcmp(key, "END") == 0) return 1; return -1;}int load_mn(struct mn_config *cfg, char *program_name, char *config_file) { FILE *file; struct load_mn_data mn; int i; mn.cfg = cfg; memset(cfg, '\0', sizeof(struct mn_config)); cfg->mn_default_tunnel_lifetime = MN_DEFAULT_TUNNEL_LIFETIME; cfg->syslog_facility = MN_DEFAULT_SYSLOG_FACILITY; cfg->shared_secret_len = -1; cfg->auth_alg = 1; cfg->replay_meth = 1; cfg->udp_port = 434; cfg->socket_priority = -1; cfg->home_net_addr_plen = -1; cfg->mndecaps_route_handling = MNDECAPS_ROUTE_DEFAULT; cfg->tunneling_mode = TUNMODE_AUTO_REVERSE; cfg->wlan_ap_poll_interval = -1; cfg->solicitation_interval = -1; mn.process_fa_spi_list = FALSE; mn.process_ignore_iflist = FALSE; list_init(&cfg->fa_spi_list); list_init(&cfg->ignore_iflist); list_init(&cfg->alt_ha_ip_addrs);#ifdef BIND_UDP_SOCKET cfg->bind_addr.s_addr = INADDR_ANY; cfg->bind_port = htons(cfg->udp_port);#endif file = fopen(config_file, "r"); if (file == NULL) { fprintf(stderr, "%s: Could not open configuration file '%s'.\n", program_name, config_file); return FALSE; } if (load_data(&mn, file, process_load_mn) == FALSE) { fprintf(stderr, "load_mn: Error while interpreting file '%s'!\n", config_file); fclose(file); return FALSE; } fclose(file); if (cfg->home_net_addr_plen > -1) { /* determine home net's subnet-direct broadcast address */ __u32 ones = 0; for (i = cfg->home_net_addr_plen; i < 32; i++) { ones |= 1 << (31 - i); } cfg->home_net_subnet_bc.s_addr = cfg->home_net_addr.s_addr | htonl(ones); } if (cfg->ha_ip_addr.s_addr == 0) cfg->use_hadisc = TRUE; cfg->ha_ip_addr_orig.s_addr = cfg->ha_ip_addr.s_addr; cfg->mn_home_ip_addr_orig.s_addr = cfg->mn_home_ip_addr.s_addr; return check_config_data(cfg);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -