mirror of
git://git.code.sf.net/p/xtables-addons/xtables-addons
synced 2025-09-20 19:44:56 +02:00
ACCOUNT/userspace: simple reformat, use tabs instead of spaces
This commit is contained in:
@@ -25,197 +25,197 @@
|
|||||||
char exit_now = 0;
|
char exit_now = 0;
|
||||||
static void sig_term(int signr)
|
static void sig_term(int signr)
|
||||||
{
|
{
|
||||||
signal(SIGINT, SIG_IGN);
|
signal(SIGINT, SIG_IGN);
|
||||||
signal(SIGQUIT, SIG_IGN);
|
signal(SIGQUIT, SIG_IGN);
|
||||||
signal(SIGTERM, SIG_IGN);
|
signal(SIGTERM, SIG_IGN);
|
||||||
|
|
||||||
exit_now=1;
|
exit_now = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
char *addr_to_dotted(unsigned int);
|
char *addr_to_dotted(unsigned int);
|
||||||
char *addr_to_dotted(unsigned int addr)
|
char *addr_to_dotted(unsigned int addr)
|
||||||
{
|
{
|
||||||
static char buf[17];
|
static char buf[17];
|
||||||
const unsigned char *bytep;
|
const unsigned char *bytep;
|
||||||
|
|
||||||
bytep = (const unsigned char *) &addr;
|
bytep = (const unsigned char *)&addr;
|
||||||
snprintf(buf, 16, "%u.%u.%u.%u", bytep[0], bytep[1], bytep[2], bytep[3]);
|
snprintf(buf, 16, "%u.%u.%u.%u", bytep[0], bytep[1], bytep[2], bytep[3]);
|
||||||
buf[16] = 0;
|
buf[16] = 0;
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void show_usage(void)
|
static void show_usage(void)
|
||||||
{
|
{
|
||||||
printf ("Unknown command line option. Try: [-u] [-h] [-a] [-f] [-c] [-s] [-l name]\n");
|
printf("Unknown command line option. Try: [-u] [-h] [-a] [-f] [-c] [-s] [-l name]\n");
|
||||||
printf("[-u] show kernel handle usage\n");
|
printf("[-u] show kernel handle usage\n");
|
||||||
printf("[-h] free all kernel handles (experts only!)\n\n");
|
printf("[-h] free all kernel handles (experts only!)\n\n");
|
||||||
printf("[-a] list all table names\n");
|
printf("[-a] list all table names\n");
|
||||||
printf("[-l name] show data in table <name>\n");
|
printf("[-l name] show data in table <name>\n");
|
||||||
printf("[-f] flush data after showing\n");
|
printf("[-f] flush data after showing\n");
|
||||||
printf("[-c] loop every second (abort with CTRL+C)\n");
|
printf("[-c] loop every second (abort with CTRL+C)\n");
|
||||||
printf("[-s] CSV output (for spreadsheet import)\n");
|
printf("[-s] CSV output (for spreadsheet import)\n");
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
struct ipt_ACCOUNT_context ctx;
|
struct ipt_ACCOUNT_context ctx;
|
||||||
struct ipt_acc_handle_ip *entry;
|
struct ipt_acc_handle_ip *entry;
|
||||||
int i;
|
int i;
|
||||||
char optchar, doHandleUsage=0, doHandleFree=0, doTableNames=0,
|
char optchar, doHandleUsage = 0, doHandleFree = 0, doTableNames = 0;
|
||||||
doFlush=0, doContinue=0, doCSV=0;
|
char doFlush = 0, doContinue = 0, doCSV = 0;
|
||||||
|
|
||||||
char *table_name = NULL;
|
char *table_name = NULL;
|
||||||
const char *name;
|
const char *name;
|
||||||
|
|
||||||
printf("\nlibxt_ACCOUNT_cl userspace accounting tool v%s\n\n",
|
printf("\nlibxt_ACCOUNT_cl userspace accounting tool v%s\n\n",
|
||||||
LIBXT_ACCOUNT_VERSION);
|
LIBXT_ACCOUNT_VERSION);
|
||||||
|
|
||||||
if (argc == 1)
|
if (argc == 1)
|
||||||
{
|
{
|
||||||
show_usage();
|
show_usage();
|
||||||
exit(0);
|
exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
while ((optchar = getopt (argc, argv, "uhacfsl:")) != -1)
|
while ((optchar = getopt(argc, argv, "uhacfsl:")) != -1)
|
||||||
{
|
{
|
||||||
switch (optchar)
|
switch (optchar)
|
||||||
{
|
{
|
||||||
case 'u':
|
case 'u':
|
||||||
doHandleUsage=1;
|
doHandleUsage = 1;
|
||||||
break;
|
break;
|
||||||
case 'h':
|
case 'h':
|
||||||
doHandleFree=1;
|
doHandleFree = 1;
|
||||||
break;
|
break;
|
||||||
case 'a':
|
case 'a':
|
||||||
doTableNames=1;
|
doTableNames = 1;
|
||||||
break;
|
break;
|
||||||
case 'f':
|
case 'f':
|
||||||
doFlush=1;
|
doFlush = 1;
|
||||||
break;
|
break;
|
||||||
case 'c':
|
case 'c':
|
||||||
doContinue=1;
|
doContinue = 1;
|
||||||
break;
|
break;
|
||||||
case 's':
|
case 's':
|
||||||
doCSV=1;
|
doCSV = 1;
|
||||||
break;
|
break;
|
||||||
case 'l':
|
case 'l':
|
||||||
table_name = (char *)strdup(optarg);
|
table_name = (char *)strdup(optarg);
|
||||||
break;
|
break;
|
||||||
case '?':
|
case '?':
|
||||||
default:
|
default:
|
||||||
show_usage();
|
show_usage();
|
||||||
exit (0);
|
exit(0);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// install exit handler
|
// install exit handler
|
||||||
if (signal(SIGTERM, sig_term) == SIG_ERR)
|
if (signal(SIGTERM, sig_term) == SIG_ERR)
|
||||||
{
|
{
|
||||||
printf("can't install signal handler for SIGTERM\n");
|
printf("can't install signal handler for SIGTERM\n");
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
if (signal(SIGINT, sig_term) == SIG_ERR)
|
if (signal(SIGINT, sig_term) == SIG_ERR)
|
||||||
{
|
{
|
||||||
printf("can't install signal handler for SIGINT\n");
|
printf("can't install signal handler for SIGINT\n");
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
if (signal(SIGQUIT, sig_term) == SIG_ERR)
|
if (signal(SIGQUIT, sig_term) == SIG_ERR)
|
||||||
{
|
{
|
||||||
printf("can't install signal handler for SIGQUIT\n");
|
printf("can't install signal handler for SIGQUIT\n");
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ipt_ACCOUNT_init(&ctx))
|
if (ipt_ACCOUNT_init(&ctx))
|
||||||
{
|
{
|
||||||
printf("Init failed: %s\n", ctx.error_str);
|
printf("Init failed: %s\n", ctx.error_str);
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get handle usage?
|
// Get handle usage?
|
||||||
if (doHandleUsage)
|
if (doHandleUsage)
|
||||||
{
|
{
|
||||||
int rtn = ipt_ACCOUNT_get_handle_usage(&ctx);
|
int rtn = ipt_ACCOUNT_get_handle_usage(&ctx);
|
||||||
if (rtn < 0)
|
if (rtn < 0)
|
||||||
{
|
{
|
||||||
printf("get_handle_usage failed: %s\n", ctx.error_str);
|
printf("get_handle_usage failed: %s\n", ctx.error_str);
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("Current kernel handle usage: %d\n", ctx.handle.itemcount);
|
printf("Current kernel handle usage: %d\n", ctx.handle.itemcount);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (doHandleFree)
|
if (doHandleFree)
|
||||||
{
|
{
|
||||||
int rtn = ipt_ACCOUNT_free_all_handles(&ctx);
|
int rtn = ipt_ACCOUNT_free_all_handles(&ctx);
|
||||||
if (rtn < 0)
|
if (rtn < 0)
|
||||||
{
|
{
|
||||||
printf("handle_free_all failed: %s\n", ctx.error_str);
|
printf("handle_free_all failed: %s\n", ctx.error_str);
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("Freed all handles in kernel space\n");
|
printf("Freed all handles in kernel space\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (doTableNames)
|
if (doTableNames)
|
||||||
{
|
{
|
||||||
int rtn = ipt_ACCOUNT_get_table_names(&ctx);
|
int rtn = ipt_ACCOUNT_get_table_names(&ctx);
|
||||||
if (rtn < 0)
|
if (rtn < 0)
|
||||||
{
|
{
|
||||||
printf("get_table_names failed: %s\n", ctx.error_str);
|
printf("get_table_names failed: %s\n", ctx.error_str);
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
while ((name = ipt_ACCOUNT_get_next_name(&ctx)) != 0)
|
while ((name = ipt_ACCOUNT_get_next_name(&ctx)) != 0)
|
||||||
printf("Found table: %s\n", name);
|
printf("Found table: %s\n", name);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (table_name)
|
if (table_name)
|
||||||
{
|
{
|
||||||
// Read out data
|
// Read out data
|
||||||
if (doCSV)
|
if (doCSV)
|
||||||
printf("IP;SRC packets;SRC bytes;DST packets;DST bytes\n");
|
printf("IP;SRC packets;SRC bytes;DST packets;DST bytes\n");
|
||||||
else
|
else
|
||||||
printf("Showing table: %s\n", table_name);
|
printf("Showing table: %s\n", table_name);
|
||||||
|
|
||||||
i = 0;
|
i = 0;
|
||||||
while (!exit_now)
|
while (!exit_now)
|
||||||
{
|
{
|
||||||
// Get entries from table test
|
// Get entries from table test
|
||||||
if (ipt_ACCOUNT_read_entries(&ctx, table_name, !doFlush))
|
if (ipt_ACCOUNT_read_entries(&ctx, table_name, !doFlush))
|
||||||
{
|
{
|
||||||
printf("Read failed: %s\n", ctx.error_str);
|
printf("Read failed: %s\n", ctx.error_str);
|
||||||
ipt_ACCOUNT_deinit(&ctx);
|
ipt_ACCOUNT_deinit(&ctx);
|
||||||
exit (-1);
|
exit(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!doCSV)
|
if (!doCSV)
|
||||||
printf("Run #%d - %u %s found\n", i, ctx.handle.itemcount,
|
printf("Run #%d - %u %s found\n", i, ctx.handle.itemcount,
|
||||||
ctx.handle.itemcount == 1 ? "item" : "items");
|
ctx.handle.itemcount == 1 ? "item" : "items");
|
||||||
|
|
||||||
// Output and free entries
|
// Output and free entries
|
||||||
while ((entry = ipt_ACCOUNT_get_next_entry(&ctx)) != NULL)
|
while ((entry = ipt_ACCOUNT_get_next_entry(&ctx)) != NULL)
|
||||||
{
|
{
|
||||||
if (doCSV)
|
if (doCSV)
|
||||||
printf("%s;%u;%u;%u;%u\n",
|
printf("%s;%u;%u;%u;%u\n",
|
||||||
addr_to_dotted(entry->ip), entry->src_packets, entry->src_bytes,
|
addr_to_dotted(entry->ip), entry->src_packets, entry->src_bytes,
|
||||||
entry->dst_packets, entry->dst_bytes);
|
entry->dst_packets, entry->dst_bytes);
|
||||||
else
|
else
|
||||||
printf("IP: %s SRC packets: %u bytes: %u DST packets: %u bytes: %u\n",
|
printf("IP: %s SRC packets: %u bytes: %u DST packets: %u bytes: %u\n",
|
||||||
addr_to_dotted(entry->ip), entry->src_packets, entry->src_bytes,
|
addr_to_dotted(entry->ip), entry->src_packets, entry->src_bytes,
|
||||||
entry->dst_packets, entry->dst_bytes);
|
entry->dst_packets, entry->dst_bytes);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (doContinue)
|
if (doContinue)
|
||||||
{
|
{
|
||||||
sleep(1);
|
sleep(1);
|
||||||
i++;
|
i++;
|
||||||
} else
|
} else
|
||||||
exit_now = 1;
|
exit_now = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("Finished.\n");
|
printf("Finished.\n");
|
||||||
ipt_ACCOUNT_deinit(&ctx);
|
ipt_ACCOUNT_deinit(&ctx);
|
||||||
exit (0);
|
exit(0);
|
||||||
}
|
}
|
||||||
|
@@ -21,179 +21,179 @@
|
|||||||
|
|
||||||
int ipt_ACCOUNT_init(struct ipt_ACCOUNT_context *ctx)
|
int ipt_ACCOUNT_init(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
memset (ctx, 0, sizeof(struct ipt_ACCOUNT_context));
|
memset(ctx, 0, sizeof(struct ipt_ACCOUNT_context));
|
||||||
ctx->handle.handle_nr = -1;
|
ctx->handle.handle_nr = -1;
|
||||||
|
|
||||||
ctx->sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);
|
ctx->sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);
|
||||||
if (ctx->sockfd < 0) {
|
if (ctx->sockfd < 0) {
|
||||||
ctx->sockfd = -1;
|
ctx->sockfd = -1;
|
||||||
ctx->error_str = "Can't open socket to kernel. "
|
ctx->error_str = "Can't open socket to kernel. "
|
||||||
"Permission denied or ipt_ACCOUNT module not loaded";
|
"Permission denied or ipt_ACCOUNT module not loaded";
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 4096 bytes default buffer should save us from reallocations
|
// 4096 bytes default buffer should save us from reallocations
|
||||||
// as it fits 200 concurrent active clients
|
// as it fits 200 concurrent active clients
|
||||||
if((ctx->data = (void *)malloc(IPT_ACCOUNT_MIN_BUFSIZE)) == NULL) {
|
if ((ctx->data = (void *)malloc(IPT_ACCOUNT_MIN_BUFSIZE)) == NULL) {
|
||||||
close (ctx->sockfd);
|
close(ctx->sockfd);
|
||||||
ctx->sockfd = -1;
|
ctx->sockfd = -1;
|
||||||
ctx->error_str = "Out of memory for data buffer";
|
ctx->error_str = "Out of memory for data buffer";
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
ctx->data_size = IPT_ACCOUNT_MIN_BUFSIZE;
|
ctx->data_size = IPT_ACCOUNT_MIN_BUFSIZE;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ipt_ACCOUNT_free_entries(struct ipt_ACCOUNT_context *ctx)
|
void ipt_ACCOUNT_free_entries(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
if (ctx->handle.handle_nr != -1) {
|
if (ctx->handle.handle_nr != -1) {
|
||||||
setsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_SET_ACCOUNT_HANDLE_FREE,
|
setsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_SET_ACCOUNT_HANDLE_FREE,
|
||||||
&ctx->handle, sizeof (struct ipt_acc_handle_sockopt));
|
&ctx->handle, sizeof(struct ipt_acc_handle_sockopt));
|
||||||
ctx->handle.handle_nr = -1;
|
ctx->handle.handle_nr = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx->handle.itemcount = 0;
|
ctx->handle.itemcount = 0;
|
||||||
ctx->pos = 0;
|
ctx->pos = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ipt_ACCOUNT_deinit(struct ipt_ACCOUNT_context *ctx)
|
void ipt_ACCOUNT_deinit(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
free(ctx->data);
|
free(ctx->data);
|
||||||
ctx->data = NULL;
|
ctx->data = NULL;
|
||||||
|
|
||||||
ipt_ACCOUNT_free_entries(ctx);
|
ipt_ACCOUNT_free_entries(ctx);
|
||||||
|
|
||||||
close(ctx->sockfd);
|
close(ctx->sockfd);
|
||||||
ctx->sockfd =-1;
|
ctx->sockfd = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ipt_ACCOUNT_read_entries(struct ipt_ACCOUNT_context *ctx,
|
int ipt_ACCOUNT_read_entries(struct ipt_ACCOUNT_context *ctx,
|
||||||
const char *table, char dont_flush)
|
const char *table, char dont_flush)
|
||||||
{
|
{
|
||||||
unsigned int s = sizeof (struct ipt_acc_handle_sockopt);
|
unsigned int s = sizeof(struct ipt_acc_handle_sockopt);
|
||||||
unsigned int new_size;
|
unsigned int new_size;
|
||||||
int rtn;
|
int rtn;
|
||||||
|
|
||||||
strncpy(ctx->handle.name, table, ACCOUNT_TABLE_NAME_LEN-1);
|
strncpy(ctx->handle.name, table, ACCOUNT_TABLE_NAME_LEN-1);
|
||||||
|
|
||||||
// Get table information
|
// Get table information
|
||||||
if (!dont_flush)
|
if (!dont_flush)
|
||||||
rtn = getsockopt(ctx->sockfd, IPPROTO_IP,
|
rtn = getsockopt(ctx->sockfd, IPPROTO_IP,
|
||||||
IPT_SO_GET_ACCOUNT_PREPARE_READ_FLUSH, &ctx->handle, &s);
|
IPT_SO_GET_ACCOUNT_PREPARE_READ_FLUSH, &ctx->handle, &s);
|
||||||
else
|
else
|
||||||
rtn = getsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_GET_ACCOUNT_PREPARE_READ,
|
rtn = getsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_GET_ACCOUNT_PREPARE_READ,
|
||||||
&ctx->handle, &s);
|
&ctx->handle, &s);
|
||||||
|
|
||||||
if (rtn < 0) {
|
if (rtn < 0) {
|
||||||
ctx->error_str = "Can't get table information from kernel. "
|
ctx->error_str = "Can't get table information from kernel. "
|
||||||
"Does it exist?";
|
"Does it exist?";
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check data buffer size
|
// Check data buffer size
|
||||||
ctx->pos = 0;
|
ctx->pos = 0;
|
||||||
new_size = ctx->handle.itemcount * sizeof(struct ipt_acc_handle_ip);
|
new_size = ctx->handle.itemcount * sizeof(struct ipt_acc_handle_ip);
|
||||||
// We want to prevent reallocations all the time
|
// We want to prevent reallocations all the time
|
||||||
if (new_size < IPT_ACCOUNT_MIN_BUFSIZE)
|
if (new_size < IPT_ACCOUNT_MIN_BUFSIZE)
|
||||||
new_size = IPT_ACCOUNT_MIN_BUFSIZE;
|
new_size = IPT_ACCOUNT_MIN_BUFSIZE;
|
||||||
|
|
||||||
// Reallocate if it's too small or twice as big
|
// Reallocate if it's too small or twice as big
|
||||||
if (ctx->data_size < new_size || ctx->data_size > new_size*2) {
|
if (ctx->data_size < new_size || ctx->data_size > new_size * 2) {
|
||||||
// Free old buffer
|
// Free old buffer
|
||||||
free (ctx->data);
|
free(ctx->data);
|
||||||
ctx->data_size = 0;
|
ctx->data_size = 0;
|
||||||
|
|
||||||
if ((ctx->data = (void*)malloc(new_size)) == NULL) {
|
if ((ctx->data = (void*)malloc(new_size)) == NULL) {
|
||||||
ctx->error_str = "Out of memory for data buffer";
|
ctx->error_str = "Out of memory for data buffer";
|
||||||
ipt_ACCOUNT_free_entries(ctx);
|
ipt_ACCOUNT_free_entries(ctx);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx->data_size = new_size;
|
ctx->data_size = new_size;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Copy data from kernel
|
// Copy data from kernel
|
||||||
memcpy(ctx->data, &ctx->handle, sizeof(struct ipt_acc_handle_sockopt));
|
memcpy(ctx->data, &ctx->handle, sizeof(struct ipt_acc_handle_sockopt));
|
||||||
rtn = getsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_GET_ACCOUNT_GET_DATA,
|
rtn = getsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_GET_ACCOUNT_GET_DATA,
|
||||||
ctx->data, &ctx->data_size);
|
ctx->data, &ctx->data_size);
|
||||||
if (rtn < 0) {
|
if (rtn < 0) {
|
||||||
ctx->error_str = "Can't get data from kernel. "
|
ctx->error_str = "Can't get data from kernel. "
|
||||||
"Check /var/log/messages for details.";
|
"Check /var/log/messages for details.";
|
||||||
ipt_ACCOUNT_free_entries(ctx);
|
ipt_ACCOUNT_free_entries(ctx);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Free kernel handle but don't reset pos/itemcount
|
// Free kernel handle but don't reset pos/itemcount
|
||||||
setsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_SET_ACCOUNT_HANDLE_FREE,
|
setsockopt(ctx->sockfd, IPPROTO_IP, IPT_SO_SET_ACCOUNT_HANDLE_FREE,
|
||||||
&ctx->handle, sizeof (struct ipt_acc_handle_sockopt));
|
&ctx->handle, sizeof(struct ipt_acc_handle_sockopt));
|
||||||
ctx->handle.handle_nr = -1;
|
ctx->handle.handle_nr = -1;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct ipt_acc_handle_ip *ipt_ACCOUNT_get_next_entry(struct ipt_ACCOUNT_context *ctx)
|
struct ipt_acc_handle_ip *ipt_ACCOUNT_get_next_entry(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
struct ipt_acc_handle_ip *rtn;
|
struct ipt_acc_handle_ip *rtn;
|
||||||
|
|
||||||
// Empty or no more items left to return?
|
// Empty or no more items left to return?
|
||||||
if (!ctx->handle.itemcount || ctx->pos >= ctx->handle.itemcount)
|
if (!ctx->handle.itemcount || ctx->pos >= ctx->handle.itemcount)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
// Get next entry
|
// Get next entry
|
||||||
rtn = (struct ipt_acc_handle_ip *)(ctx->data + ctx->pos
|
rtn = (struct ipt_acc_handle_ip *)(ctx->data + ctx->pos
|
||||||
* sizeof(struct ipt_acc_handle_ip));
|
* sizeof(struct ipt_acc_handle_ip));
|
||||||
ctx->pos++;
|
ctx->pos++;
|
||||||
|
|
||||||
return rtn;
|
return rtn;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ipt_ACCOUNT_get_handle_usage(struct ipt_ACCOUNT_context *ctx)
|
int ipt_ACCOUNT_get_handle_usage(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
unsigned int s = sizeof (struct ipt_acc_handle_sockopt);
|
unsigned int s = sizeof(struct ipt_acc_handle_sockopt);
|
||||||
if (getsockopt(ctx->sockfd, IPPROTO_IP,
|
if (getsockopt(ctx->sockfd, IPPROTO_IP,
|
||||||
IPT_SO_GET_ACCOUNT_GET_HANDLE_USAGE, &ctx->handle, &s) < 0) {
|
IPT_SO_GET_ACCOUNT_GET_HANDLE_USAGE, &ctx->handle, &s) < 0) {
|
||||||
ctx->error_str = "Can't get handle usage information from kernel";
|
ctx->error_str = "Can't get handle usage information from kernel";
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
ctx->handle.handle_nr = -1;
|
ctx->handle.handle_nr = -1;
|
||||||
|
|
||||||
return ctx->handle.itemcount;
|
return ctx->handle.itemcount;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ipt_ACCOUNT_free_all_handles(struct ipt_ACCOUNT_context *ctx)
|
int ipt_ACCOUNT_free_all_handles(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
if (setsockopt(ctx->sockfd, IPPROTO_IP,
|
if (setsockopt(ctx->sockfd, IPPROTO_IP,
|
||||||
IPT_SO_SET_ACCOUNT_HANDLE_FREE_ALL, NULL, 0) < 0) {
|
IPT_SO_SET_ACCOUNT_HANDLE_FREE_ALL, NULL, 0) < 0) {
|
||||||
ctx->error_str = "Can't free all kernel handles";
|
ctx->error_str = "Can't free all kernel handles";
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ipt_ACCOUNT_get_table_names(struct ipt_ACCOUNT_context *ctx)
|
int ipt_ACCOUNT_get_table_names(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
int rtn = getsockopt(ctx->sockfd, IPPROTO_IP,
|
int rtn = getsockopt(ctx->sockfd, IPPROTO_IP,
|
||||||
IPT_SO_GET_ACCOUNT_GET_TABLE_NAMES,
|
IPT_SO_GET_ACCOUNT_GET_TABLE_NAMES,
|
||||||
ctx->data, &ctx->data_size);
|
ctx->data, &ctx->data_size);
|
||||||
if (rtn < 0) {
|
if (rtn < 0) {
|
||||||
ctx->error_str = "Can't get table names from kernel. Out of memory, "
|
ctx->error_str = "Can't get table names from kernel. Out of memory, "
|
||||||
"MINBUFISZE too small?";
|
"MINBUFISZE too small?";
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
ctx->pos = 0;
|
ctx->pos = 0;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
const char *ipt_ACCOUNT_get_next_name(struct ipt_ACCOUNT_context *ctx)
|
const char *ipt_ACCOUNT_get_next_name(struct ipt_ACCOUNT_context *ctx)
|
||||||
{
|
{
|
||||||
const char *rtn;
|
const char *rtn;
|
||||||
if (((char *)ctx->data)[ctx->pos] == 0)
|
if (((char *)ctx->data)[ctx->pos] == 0)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
rtn = ctx->data + ctx->pos;
|
rtn = ctx->data + ctx->pos;
|
||||||
ctx->pos += strlen(ctx->data+ctx->pos) + 1;
|
ctx->pos += strlen(ctx->data + ctx->pos) + 1;
|
||||||
|
|
||||||
return rtn;
|
return rtn;
|
||||||
}
|
}
|
||||||
|
@@ -20,37 +20,37 @@
|
|||||||
|
|
||||||
struct ipt_ACCOUNT_context
|
struct ipt_ACCOUNT_context
|
||||||
{
|
{
|
||||||
int sockfd;
|
int sockfd;
|
||||||
struct ipt_acc_handle_sockopt handle;
|
struct ipt_acc_handle_sockopt handle;
|
||||||
|
|
||||||
unsigned int data_size;
|
unsigned int data_size;
|
||||||
void *data;
|
void *data;
|
||||||
unsigned int pos;
|
unsigned int pos;
|
||||||
|
|
||||||
char *error_str;
|
char *error_str;
|
||||||
};
|
};
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
int ipt_ACCOUNT_init(struct ipt_ACCOUNT_context *ctx);
|
int ipt_ACCOUNT_init(struct ipt_ACCOUNT_context *ctx);
|
||||||
void ipt_ACCOUNT_deinit(struct ipt_ACCOUNT_context *ctx);
|
void ipt_ACCOUNT_deinit(struct ipt_ACCOUNT_context *ctx);
|
||||||
|
|
||||||
void ipt_ACCOUNT_free_entries(struct ipt_ACCOUNT_context *ctx);
|
void ipt_ACCOUNT_free_entries(struct ipt_ACCOUNT_context *ctx);
|
||||||
int ipt_ACCOUNT_read_entries(struct ipt_ACCOUNT_context *ctx,
|
int ipt_ACCOUNT_read_entries(struct ipt_ACCOUNT_context *ctx,
|
||||||
const char *table, char dont_flush);
|
const char *table, char dont_flush);
|
||||||
struct ipt_acc_handle_ip *ipt_ACCOUNT_get_next_entry(
|
struct ipt_acc_handle_ip *ipt_ACCOUNT_get_next_entry(
|
||||||
struct ipt_ACCOUNT_context *ctx);
|
struct ipt_ACCOUNT_context *ctx);
|
||||||
|
|
||||||
/* ipt_ACCOUNT_free_entries is for internal use only function as this library
|
/* ipt_ACCOUNT_free_entries is for internal use only function as this library
|
||||||
is constructed to be used in a loop -> Don't allocate memory all the time.
|
is constructed to be used in a loop -> Don't allocate memory all the time.
|
||||||
The data buffer is freed on deinit() */
|
The data buffer is freed on deinit() */
|
||||||
|
|
||||||
int ipt_ACCOUNT_get_handle_usage(struct ipt_ACCOUNT_context *ctx);
|
int ipt_ACCOUNT_get_handle_usage(struct ipt_ACCOUNT_context *ctx);
|
||||||
int ipt_ACCOUNT_free_all_handles(struct ipt_ACCOUNT_context *ctx);
|
int ipt_ACCOUNT_free_all_handles(struct ipt_ACCOUNT_context *ctx);
|
||||||
int ipt_ACCOUNT_get_table_names(struct ipt_ACCOUNT_context *ctx);
|
int ipt_ACCOUNT_get_table_names(struct ipt_ACCOUNT_context *ctx);
|
||||||
const char *ipt_ACCOUNT_get_next_name(struct ipt_ACCOUNT_context *ctx);
|
const char *ipt_ACCOUNT_get_next_name(struct ipt_ACCOUNT_context *ctx);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user