// Copyright (c) 2002 FireBrick (Andrews & Arnold Ltd / Watchfront Ltd) - GPL licenced
// vim: sw=8 ts=8
-char const *cvs_id_l2tpns = "$Id: l2tpns.c,v 1.21 2004/08/02 06:06:28 fred_nerk Exp $";
+char const *cvs_id_l2tpns = "$Id: l2tpns.c,v 1.22 2004/08/13 00:02:50 fred_nerk Exp $";
#include <arpa/inet.h>
#include <assert.h>
if (CLI_HELP_REQUESTED)
return CLI_HELP_NO_ARGS;
- cli_print(cli, "%7s %s", "Sess#", "IP Address");
+ cli_print(cli, "%7s %s", "Sess#", "IP Address");
for (i = 0; i < 256; ++i) {
if (!d[i]) continue;
if (!session[s].tunnel)
return 0; // No-one home.
- if (!*session[s].user)
- return 0; // User not logged in
+ if (!*session[s].user)
+ return 0; // User not logged in
if (throttle) {
if (session[s].tbf_in || session[s].tbf_out) {
// TBA
break;
case 12: // ICCN
+ if ( amagic == 0) amagic = time_now;
session[s].magic = amagic; // set magic number
session[s].l2tp_flags = aflags; // set flags received
log(3, ntohl(addr->sin_addr.s_addr), s, t, "Magic %X Flags %X\n", amagic, aflags);
}
void dump_acct_info()
+
{
- char filename[1024];
- char timestr[64];
- time_t t = time(NULL);
- int i;
- FILE *f = NULL;
+ char filename[1024];
+ char timestr[64];
+ time_t t = time(NULL);
+ int i;
+ FILE *f = NULL;
- CSTAT(call_dump_acct_info);
+ CSTAT(call_dump_acct_info);
- strftime(timestr, 64, "%Y%m%d%H%M%S", localtime(&t));
- snprintf(filename, 1024, "%s/%s", config->accounting_dir, timestr);
+ strftime(timestr, 64, "%Y%m%d%H%M%S", localtime(&t));
+ snprintf(filename, 1024, "%s/%s", config->accounting_dir, timestr);
- for (i = 0; i < MAXSESSION; i++)
- {
- if (!session[i].opened || !session[i].ip || !session[i].cin || !session[i].cout || !*session[i].user || session[i].walled_garden)
- continue;
- if (!f)
+ for (i = 0; i < MAXSESSION; i++)
{
- time_t now = time(NULL);
- if (!(f = fopen(filename, "w")))
- {
- log(0, 0, 0, 0, "Can't write accounting info to %s: %s\n", filename, strerror(errno));
- return;
- }
- log(3, 0, 0, 0, "Dumping accounting information to %s\n", filename);
- fprintf(f, "# dslwatch.pl dump file V1.01\n"
- "# host: %s\n"
- "# time: %ld\n"
- "# uptime: %ld\n"
- "# format: username ip qos uptxoctets downrxoctets\n",
- hostname,
- now,
- now - basetime);
- }
-
- log(4, 0, 0, 0, "Dumping accounting information for %s\n", session[i].user);
- fprintf(f, "%s %s %d %u %u\n",
- session[i].user, // username
- inet_toa(htonl(session[i].ip)), // ip
- (session[i].throttle) ? 2 : 1, // qos
- (u32)session[i].cin, // uptxoctets
- (u32)session[i].cout); // downrxoctets
-
- session[i].pin = session[i].cin = 0;
- session[i].pout = session[i].cout = 0;
- }
-
- if (f) fclose(f);
+ if (!session[i].opened || !session[i].ip || !session[i].cin || !session[i].cout || !*session[i].user || session[i].walled_garden)
+ continue;
+ if (!f)
+ {
+ time_t now = time(NULL);
+ if (!(f = fopen(filename, "w")))
+ {
+ log(0, 0, 0, 0, "Can't write accounting info to %s: %s\n", filename, strerror(errno));
+ return ;
+ }
+ log(3, 0, 0, 0, "Dumping accounting information to %s\n", filename);
+ fprintf(f, "# dslwatch.pl dump file V1.01\n"
+ "# host: %s\n"
+ "# time: %ld\n"
+ "# uptime: %ld\n"
+ "# format: username ip qos uptxoctets downrxoctets\n",
+ hostname,
+ now,
+ now - basetime);
+ }
+
+ log(4, 0, 0, 0, "Dumping accounting information for %s\n", session[i].user);
+ fprintf(f, "%s %s %d %u %u\n",
+ session[i].user, // username
+ inet_toa(htonl(session[i].ip)), // ip
+ (session[i].throttle) ? 2 : 1, // qos
+ (u32)session[i].cin, // uptxoctets
+ (u32)session[i].cout); // downrxoctets
+
+ session[i].pin = session[i].cin = 0;
+ session[i].pout = session[i].cout = 0;
+ }
+
+ if (f)
+ fclose(f);
}
// Main program
signal(SIGPIPE, SIG_IGN);
bgp_setup(config->as_number);
bgp_add_route(config->bind_address, 0xffffffff);
- if (*config->bgp_peer[0])
+ if (*config->bgp_peer[0])
bgp_start(&bgp_peers[0], config->bgp_peer[0],
config->bgp_peer_as[0], 0); /* 0 = routing disabled */
- if (*config->bgp_peer[1])
+ if (*config->bgp_peer[1])
bgp_start(&bgp_peers[1], config->bgp_peer[1],
config->bgp_peer_as[1], 0);
#endif /* BGP */
void read_state()
{
- struct stat sb;
- int i;
- ippoolt itmp;
- FILE *f;
- char magic[sizeof(DUMP_MAGIC)-1];
- u32 buf[2];
+ struct stat sb;
+ int i;
+ ippoolt itmp;
+ FILE *f;
+ char magic[sizeof(DUMP_MAGIC) - 1];
+ u32 buf[2];
- if (!config->save_state)
- {
- unlink(STATEFILE);
- return;
- }
+ if (!config->save_state)
+ {
+ unlink(STATEFILE);
+ return ;
+ }
- if (stat(STATEFILE, &sb) < 0)
- {
- unlink(STATEFILE);
- return;
- }
+ if (stat(STATEFILE, &sb) < 0)
+ {
+ unlink(STATEFILE);
+ return ;
+ }
+
+ if (sb.st_mtime < (time(NULL) - 60))
+ {
+ log(0, 0, 0, 0, "State file is too old to read, ignoring\n");
+ unlink(STATEFILE);
+ return ;
+ }
- if (sb.st_mtime < (time(NULL) - 60))
- {
- log(0, 0, 0, 0, "State file is too old to read, ignoring\n");
+ f = fopen(STATEFILE, "r");
unlink(STATEFILE);
- return;
- }
-
- f = fopen(STATEFILE, "r");
- unlink(STATEFILE);
-
- if (!f)
- {
- log(0, 0, 0, 0, "Can't read state file: %s\n", strerror(errno));
- exit(1);
- }
-
- if (fread(magic, sizeof(magic), 1, f) != 1 || strncmp(magic, DUMP_MAGIC, sizeof(magic)))
- {
- log(0, 0, 0, 0, "Bad state file magic\n");
- exit(1);
- }
-
- log(1, 0, 0, 0, "Reading state information\n");
- if (fread(buf, sizeof(buf), 1, f) != 1 || buf[0] > MAXIPPOOL || buf[1] != sizeof(ippoolt))
- {
- log(0, 0, 0, 0, "Error/mismatch reading ip pool header from state file\n");
- exit(1);
- }
-
- if (buf[0] > ip_pool_size)
- {
- log(0, 0, 0, 0, "ip pool has shrunk! state = %d, current = %d\n", buf[0], ip_pool_size);
- exit(1);
- }
-
- log(2, 0, 0, 0, "Loading %u ip addresses\n", buf[0]);
- for (i = 0; i < buf[0]; i++)
- {
- if (fread(&itmp, sizeof(itmp), 1, f) != 1)
- {
- log(0, 0, 0, 0, "Error reading ip %d from state file: %s\n", i, strerror(errno));
- exit(1);
- }
-
- if (itmp.address != ip_address_pool[i].address)
- {
- log(0, 0, 0, 0, "Mismatched ip %d from state file: pool may only be extended\n", i);
- exit(1);
- }
-
- memcpy(&ip_address_pool[i], &itmp, sizeof(itmp));
- }
-
- if (fread(buf, sizeof(buf), 1, f) != 1 || buf[0] != MAXTUNNEL || buf[1] != sizeof(tunnelt))
- {
- log(0, 0, 0, 0, "Error/mismatch reading tunnel header from state file\n");
- exit(1);
- }
-
- log(2, 0, 0, 0, "Loading %u tunnels\n", MAXTUNNEL);
- if (fread(tunnel, sizeof(tunnelt), MAXTUNNEL, f) != MAXTUNNEL)
- {
- log(0, 0, 0, 0, "Error reading tunnel data from state file\n");
- exit(1);
- }
-
- for (i = 0; i < MAXTUNNEL; i++)
- {
- tunnel[i].controlc = 0;
- tunnel[i].controls = NULL;
- tunnel[i].controle = NULL;
- if (*tunnel[i].hostname)
- log(3, 0, 0, 0, "Created tunnel for %s\n", tunnel[i].hostname);
- }
-
- if (fread(buf, sizeof(buf), 1, f) != 1 || buf[0] != MAXSESSION || buf[1] != sizeof(sessiont))
- {
- log(0, 0, 0, 0, "Error/mismatch reading session header from state file\n");
- exit(1);
- }
-
- log(2, 0, 0, 0, "Loading %u sessions\n", MAXSESSION);
- if (fread(session, sizeof(sessiont), MAXSESSION, f) != MAXSESSION)
- {
- log(0, 0, 0, 0, "Error reading session data from state file\n");
- exit(1);
- }
-
- for (i = 0; i < MAXSESSION; i++)
- {
- session[i].tbf_in = 0;
- session[i].tbf_out = 0;
- if (session[i].opened)
- {
- log(2, 0, i, 0, "Loaded active session for user %s\n", session[i].user);
- if (session[i].ip)
- sessionsetup(session[i].tunnel, i);
- }
- }
-
- fclose(f);
- log(0, 0, 0, 0, "Loaded saved state information\n");
+
+ if (!f)
+ {
+ log(0, 0, 0, 0, "Can't read state file: %s\n", strerror(errno));
+ exit(1);
+ }
+
+ if (fread(magic, sizeof(magic), 1, f) != 1 || strncmp(magic, DUMP_MAGIC, sizeof(magic)))
+ {
+ log(0, 0, 0, 0, "Bad state file magic\n");
+ exit(1);
+ }
+
+ log(1, 0, 0, 0, "Reading state information\n");
+ if (fread(buf, sizeof(buf), 1, f) != 1 || buf[0] > MAXIPPOOL || buf[1] != sizeof(ippoolt))
+ {
+ log(0, 0, 0, 0, "Error/mismatch reading ip pool header from state file\n");
+ exit(1);
+ }
+
+ if (buf[0] > ip_pool_size)
+ {
+ log(0, 0, 0, 0, "ip pool has shrunk! state = %d, current = %d\n", buf[0], ip_pool_size);
+ exit(1);
+ }
+
+ log(2, 0, 0, 0, "Loading %u ip addresses\n", buf[0]);
+ for (i = 0; i < buf[0]; i++)
+ {
+ if (fread(&itmp, sizeof(itmp), 1, f) != 1)
+ {
+ log(0, 0, 0, 0, "Error reading ip %d from state file: %s\n", i, strerror(errno));
+ exit(1);
+ }
+
+ if (itmp.address != ip_address_pool[i].address)
+ {
+ log(0, 0, 0, 0, "Mismatched ip %d from state file: pool may only be extended\n", i);
+ exit(1);
+ }
+
+ memcpy(&ip_address_pool[i], &itmp, sizeof(itmp));
+ }
+
+ if (fread(buf, sizeof(buf), 1, f) != 1 || buf[0] != MAXTUNNEL || buf[1] != sizeof(tunnelt))
+ {
+ log(0, 0, 0, 0, "Error/mismatch reading tunnel header from state file\n");
+ exit(1);
+ }
+
+ log(2, 0, 0, 0, "Loading %u tunnels\n", MAXTUNNEL);
+ if (fread(tunnel, sizeof(tunnelt), MAXTUNNEL, f) != MAXTUNNEL)
+ {
+ log(0, 0, 0, 0, "Error reading tunnel data from state file\n");
+ exit(1);
+ }
+
+ for (i = 0; i < MAXTUNNEL; i++)
+ {
+ tunnel[i].controlc = 0;
+ tunnel[i].controls = NULL;
+ tunnel[i].controle = NULL;
+ if (*tunnel[i].hostname)
+ log(3, 0, 0, 0, "Created tunnel for %s\n", tunnel[i].hostname);
+ }
+
+ if (fread(buf, sizeof(buf), 1, f) != 1 || buf[0] != MAXSESSION || buf[1] != sizeof(sessiont))
+ {
+ log(0, 0, 0, 0, "Error/mismatch reading session header from state file\n");
+ exit(1);
+ }
+
+ log(2, 0, 0, 0, "Loading %u sessions\n", MAXSESSION);
+ if (fread(session, sizeof(sessiont), MAXSESSION, f) != MAXSESSION)
+ {
+ log(0, 0, 0, 0, "Error reading session data from state file\n");
+ exit(1);
+ }
+
+ for (i = 0; i < MAXSESSION; i++)
+ {
+ session[i].tbf_in = 0;
+ session[i].tbf_out = 0;
+ if (session[i].opened)
+ {
+ log(2, 0, i, 0, "Loaded active session for user %s\n", session[i].user);
+ if (session[i].ip)
+ sessionsetup(session[i].tunnel, i);
+ }
+ }
+
+ fclose(f);
+ log(0, 0, 0, 0, "Loaded saved state information\n");
}
void dump_state()
{
- FILE *f;
- u32 buf[2];
+ FILE *f;
+ u32 buf[2];
- if (!config->save_state)
- return;
+ if (!config->save_state)
+ return;
- do {
- if (!(f = fopen(STATEFILE, "w")))
- break;
+ do
+ {
+ if (!(f = fopen(STATEFILE, "w")))
+ break;
- log(1, 0, 0, 0, "Dumping state information\n");
+ log(1, 0, 0, 0, "Dumping state information\n");
- if (fwrite(DUMP_MAGIC, sizeof(DUMP_MAGIC)-1, 1, f) != 1) break;
+ if (fwrite(DUMP_MAGIC, sizeof(DUMP_MAGIC) - 1, 1, f) != 1)
+ break;
- log(2, 0, 0, 0, "Dumping %u ip addresses\n", ip_pool_size);
- buf[0] = ip_pool_size;
- buf[1] = sizeof(ippoolt);
- if (fwrite(buf, sizeof(buf), 1, f) != 1) break;
- if (fwrite(ip_address_pool, sizeof(ippoolt), ip_pool_size, f) != ip_pool_size) break;
+ log(2, 0, 0, 0, "Dumping %u ip addresses\n", ip_pool_size);
+ buf[0] = ip_pool_size;
+ buf[1] = sizeof(ippoolt);
+ if (fwrite(buf, sizeof(buf), 1, f) != 1)
+ break;
+ if (fwrite(ip_address_pool, sizeof(ippoolt), ip_pool_size, f) != ip_pool_size)
+ break;
- log(2, 0, 0, 0, "Dumping %u tunnels\n", MAXTUNNEL);
- buf[0] = MAXTUNNEL;
- buf[1] = sizeof(tunnelt);
- if (fwrite(buf, sizeof(buf), 1, f) != 1) break;
- if (fwrite(tunnel, sizeof(tunnelt), MAXTUNNEL, f) != MAXTUNNEL) break;
+ log(2, 0, 0, 0, "Dumping %u tunnels\n", MAXTUNNEL);
+ buf[0] = MAXTUNNEL;
+ buf[1] = sizeof(tunnelt);
+ if (fwrite(buf, sizeof(buf), 1, f) != 1)
+ break;
+ if (fwrite(tunnel, sizeof(tunnelt), MAXTUNNEL, f) != MAXTUNNEL)
+ break;
- log(2, 0, 0, 0, "Dumping %u sessions\n", MAXSESSION);
- buf[0] = MAXSESSION;
- buf[1] = sizeof(sessiont);
- if (fwrite(buf, sizeof(buf), 1, f) != 1) break;
- if (fwrite(session, sizeof(sessiont), MAXSESSION, f) != MAXSESSION) break;
+ log(2, 0, 0, 0, "Dumping %u sessions\n", MAXSESSION);
+ buf[0] = MAXSESSION;
+ buf[1] = sizeof(sessiont);
+ if (fwrite(buf, sizeof(buf), 1, f) != 1)
+ break;
+ if (fwrite(session, sizeof(sessiont), MAXSESSION, f) != MAXSESSION)
+ break;
- if (fclose(f) == 0) return; // OK
- } while (0);
+ if (fclose(f) == 0)
+ return ; // OK
+ }
+ while (0);
- log(0, 0, 0, 0, "Can't write state information: %s\n", strerror(errno));
- unlink(STATEFILE);
+ log(0, 0, 0, 0, "Can't write state information: %s\n", strerror(errno));
+ unlink(STATEFILE);
}
void build_chap_response(char *challenge, u8 id, u16 challenge_length, char **challenge_response)
static int facility_value(char *name)
{
- int i;
- for (i = 0; facilitynames[i].c_name; i++)
- {
- if (strcmp(facilitynames[i].c_name, name) == 0)
- return facilitynames[i].c_val;
- }
- return 0;
+ int i;
+ for (i = 0; facilitynames[i].c_name; i++)
+ {
+ if (strcmp(facilitynames[i].c_name, name) == 0)
+ return facilitynames[i].c_val;
+ }
+ return 0;
}
void update_config()