163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*
263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim * m_xt.c	xtables based targets
363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim * 		utilities mostly ripped from iptables <duh, its the linux way>
463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim *
563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim *		This program is free software; you can distribute it and/or
663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim *		modify it under the terms of the GNU General Public License
763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim *		as published by the Free Software Foundation; either version
863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim *		2 of the License, or (at your option) any later version.
963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim *
1063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim * Authors:  J Hadi Salim (hadi@cyberus.ca)
1163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim */
1263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
1363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: in the future (xtables 1.4.3?) get rid of everything tagged
1463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim * as TC_CONFIG_XT_H */
1563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
1663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <syslog.h>
1763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <sys/socket.h>
1863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <netinet/in.h>
1963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <arpa/inet.h>
2063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <net/if.h>
2163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <linux/netfilter.h>
2263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <linux/netfilter_ipv4/ip_tables.h>
2363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <xtables.h>
2463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include "utils.h"
2563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include "tc_util.h"
2663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <linux/tc_act/tc_ipt.h>
2763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <stdio.h>
2863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <getopt.h>
2963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <errno.h>
3063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <string.h>
3163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <netdb.h>
3263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <stdlib.h>
3363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <ctype.h>
3463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <stdarg.h>
3563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <limits.h>
3663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <unistd.h>
3763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <fcntl.h>
3863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include <sys/wait.h>
3963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#ifdef TC_CONFIG_XT_H
4063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#include "xt-internal.h"
4163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#endif
4263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
43edaaa11e5a3cf2c9c1a395e95926174718cba198Stephen Hemminger#ifndef ALIGN
44edaaa11e5a3cf2c9c1a395e95926174718cba198Stephen Hemminger#define ALIGN(x,a)		__ALIGN_MASK(x,(typeof(x))(a)-1)
45edaaa11e5a3cf2c9c1a395e95926174718cba198Stephen Hemminger#define __ALIGN_MASK(x,mask)	(((x)+(mask))&~(mask))
46edaaa11e5a3cf2c9c1a395e95926174718cba198Stephen Hemminger#endif
47edaaa11e5a3cf2c9c1a395e95926174718cba198Stephen Hemminger
4863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic const char *pname = "tc-ipt";
4963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic const char *tname = "mangle";
5063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic const char *pversion = "0.2";
5163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
5263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic const char *ipthooks[] = {
5363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	"NF_IP_PRE_ROUTING",
5463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	"NF_IP_LOCAL_IN",
5563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	"NF_IP_FORWARD",
5663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	"NF_IP_LOCAL_OUT",
5763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	"NF_IP_POST_ROUTING",
5863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim};
5963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
6063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic struct option original_opts[] = {
6163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	{"jump", 1, 0, 'j'},
6263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	{0, 0, 0, 0}
6363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim};
6463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
6563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic struct option *opts = original_opts;
6663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic unsigned int global_option_offset = 0;
6763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimchar *lib_dir;
6863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimconst char *program_version = XTABLES_VERSION;
6963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimconst char *program_name = "tc-ipt";
7063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstruct afinfo afinfo = {
7163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	.family         = AF_INET,
7263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	.libprefix      = "libxt_",
7363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	.ipproto        = IPPROTO_IP,
7463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	.kmod           = "ip_tables",
7563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	.so_rev_target  = IPT_SO_GET_REVISION_TARGET,
7663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim};
7763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
7863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
7963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#define OPTION_OFFSET 256
8063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
8163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: TC_CONFIG_XT_H */
8263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic void free_opts(struct option *local_opts)
8363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
8463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (local_opts != original_opts) {
8563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		free(local_opts);
8663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		opts = original_opts;
8763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		global_option_offset = 0;
8863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
8963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
9063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
9163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: TC_CONFIG_XT_H */
9263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic struct option *
9363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimmerge_options(struct option *oldopts, const struct option *newopts,
9463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	      unsigned int *option_offset)
9563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
9663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	struct option *merge;
9763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	unsigned int num_old, num_new, i;
9863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
9963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	for (num_old = 0; oldopts[num_old].name; num_old++) ;
10063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	for (num_new = 0; newopts[num_new].name; num_new++) ;
10163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
10263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	*option_offset = global_option_offset + OPTION_OFFSET;
10363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
10463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	merge = malloc(sizeof (struct option) * (num_new + num_old + 1));
10563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	memcpy(merge, oldopts, num_old * sizeof (struct option));
10663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	for (i = 0; i < num_new; i++) {
10763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		merge[num_old + i] = newopts[i];
10863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		merge[num_old + i].val += *option_offset;
10963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
11063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	memset(merge + num_old + num_new, 0, sizeof (struct option));
11163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
11263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	return merge;
11363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
11463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
11563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
11663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: TC_CONFIG_XT_H */
11763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#ifndef TRUE
11863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#define TRUE 1
11963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#endif
12063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#ifndef FALSE
12163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#define FALSE 0
12263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim#endif
12363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
12463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: TC_CONFIG_XT_H */
12563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimint
12663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimcheck_inverse(const char option[], int *invert, int *my_optind, int argc)
12763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
12863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        if (option && strcmp(option, "!") == 0) {
12963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                if (*invert)
13063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                        exit_error(PARAMETER_PROBLEM,
13163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                                   "Multiple `!' flags not allowed");
13263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                *invert = TRUE;
13363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                if (my_optind != NULL) {
13463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                        ++*my_optind;
13563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                        if (argc && *my_optind > argc)
13663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                                exit_error(PARAMETER_PROBLEM,
13763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                                           "no argument following `!'");
13863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                }
13963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
14063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim                return TRUE;
14163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        }
14263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        return FALSE;
14363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
14463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
14563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: TC_CONFIG_XT_H */
14663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimvoid exit_error(enum exittype status, const char *msg, ...)
14763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
14863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        va_list args;
14963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
15063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        va_start(args, msg);
15163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        fprintf(stderr, "%s v%s: ", pname, pversion);
15263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        vfprintf(stderr, msg, args);
15363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        va_end(args);
15463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        fprintf(stderr, "\n");
15563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        /* On error paths, make sure that we don't leak memory */
15663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        exit(status);
15763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
15863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
15963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*XXX: TC_CONFIG_XT_H */
16063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic void set_revision(char *name, u_int8_t revision)
16163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
16263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	/* Old kernel sources don't have ".revision" field,
16363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	*  but we stole a byte from name. */
16463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	name[IPT_FUNCTION_MAXNAMELEN - 2] = '\0';
16563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	name[IPT_FUNCTION_MAXNAMELEN - 1] = revision;
16663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
16763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
16863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim/*
16963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim * we may need to check for version mismatch
17063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim*/
17163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimint
17263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimbuild_st(struct xtables_target *target, struct xt_entry_target *t)
17363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
17463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
17563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	size_t size =
17663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		    XT_ALIGN(sizeof (struct xt_entry_target)) + target->size;
17763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
17863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (NULL == t) {
17963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		target->t = fw_calloc(1, size);
18063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		target->t->u.target_size = size;
18163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		strcpy(target->t->u.user.name, target->name);
18263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		set_revision(target->t->u.user.name, target->revision);
18363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
18463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (target->init != NULL)
18563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			target->init(target->t);
18663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	} else {
18763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		target->t = t;
18863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
18963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	return 0;
19063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
19163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
19263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
19363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Saliminline void set_lib_dir(void)
19463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
19563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
19663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	lib_dir = getenv("XTABLES_LIBDIR");
19763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (!lib_dir) {
19863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		lib_dir = getenv("IPTABLES_LIB_DIR");
19963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (lib_dir)
20063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			fprintf(stderr, "using deprecated IPTABLES_LIB_DIR \n");
20163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
20263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (lib_dir == NULL)
20363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		lib_dir = XT_LIB_DIR;
20463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
20563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
20663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
20763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic int parse_ipt(struct action_util *a,int *argc_p,
20863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		     char ***argv_p, int tca_id, struct nlmsghdr *n)
20963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
21063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	struct xtables_target *m = NULL;
21163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	struct ipt_entry fw;
21263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	struct rtattr *tail;
21363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	int c;
21463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	int rargc = *argc_p;
21563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	char **argv = *argv_p;
21663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	int argc = 0, iargc = 0;
21763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	char k[16];
21863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	int size = 0;
21963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	int iok = 0, ok = 0;
22063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	__u32 hook = 0, index = 0;
22163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
22263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	set_lib_dir();
22363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
22463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	{
22563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		int i;
22663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		for (i = 0; i < rargc; i++) {
22763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			if (NULL == argv[i] || 0 == strcmp(argv[i], "action")) {
22863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				break;
22963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			}
23063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
23163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		iargc = argc = i;
23263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
23363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
23463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (argc <= 2) {
23563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(stderr,"bad arguements to ipt %d vs %d \n", argc, rargc);
23663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		return -1;
23763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
23863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
23963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	while (1) {
24063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		c = getopt_long(argc, argv, "j:", opts, NULL);
24163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (c == -1)
24263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			break;
24363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		switch (c) {
24463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		case 'j':
24563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			m = find_target(optarg, TRY_LOAD);
24663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			if (NULL != m) {
24763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
24863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				if (0 > build_st(m, NULL)) {
24963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim					printf(" %s error \n", m->name);
25063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim					return -1;
25163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				}
25263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				opts =
25363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				    merge_options(opts, m->extra_opts,
25463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim						  &m->option_offset);
25563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			} else {
25663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				fprintf(stderr," failed to find target %s\n\n", optarg);
25763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				return -1;
25863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			}
25963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			ok++;
26063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			break;
26163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
26263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		default:
26363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			memset(&fw, 0, sizeof (fw));
26463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			if (m) {
26563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				m->parse(c - m->option_offset, argv, 0,
26663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim					 &m->tflags, NULL, &m->t);
26763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			} else {
26863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				fprintf(stderr," failed to find target %s\n\n", optarg);
26963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				return -1;
27063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
27163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			}
27263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			ok++;
27363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			break;
27463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
27563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
27663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
27763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
27863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (iargc > optind) {
27963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (matches(argv[optind], "index") == 0) {
28063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			if (get_u32(&index, argv[optind + 1], 10)) {
28163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				fprintf(stderr, "Illegal \"index\"\n");
28263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				free_opts(opts);
28363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				return -1;
28463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			}
28563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			iok++;
28663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
28763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			optind += 2;
28863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
28963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
29063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
29163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (!ok && !iok) {
29263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(stderr," ipt Parser BAD!! (%s)\n", *argv);
29363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		return -1;
29463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
29563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
29663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	/* check that we passed the correct parameters to the target */
29763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (m)
29863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		m->final_check(m->tflags);
29963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
30063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	{
30163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		struct tcmsg *t = NLMSG_DATA(n);
30263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (t->tcm_parent != TC_H_ROOT
30363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		    && t->tcm_parent == TC_H_MAJ(TC_H_INGRESS)) {
30463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			hook = NF_IP_PRE_ROUTING;
30563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		} else {
30663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			hook = NF_IP_POST_ROUTING;
30763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
30863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
30963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
31063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	tail = NLMSG_TAIL(n);
31163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	addattr_l(n, MAX_MSG, tca_id, NULL, 0);
31263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	fprintf(stdout, "tablename: %s hook: %s\n ", tname, ipthooks[hook]);
31363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	fprintf(stdout, "\ttarget: ");
31463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
31563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (m)
31663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		m->print(NULL, m->t, 0);
31763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	fprintf(stdout, " index %d\n", index);
31863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
31963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (strlen(tname) > 16) {
32063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		size = 16;
32163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		k[15] = 0;
32263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	} else {
32363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		size = 1 + strlen(tname);
32463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
32563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	strncpy(k, tname, size);
32663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
32763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	addattr_l(n, MAX_MSG, TCA_IPT_TABLE, k, size);
32863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	addattr_l(n, MAX_MSG, TCA_IPT_HOOK, &hook, 4);
32963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	addattr_l(n, MAX_MSG, TCA_IPT_INDEX, &index, 4);
33063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (m)
33163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		addattr_l(n, MAX_MSG, TCA_IPT_TARG, m->t, m->t->u.target_size);
33263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	tail->rta_len = (void *) NLMSG_TAIL(n) - (void *) tail;
33363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
33463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	argc -= optind;
33563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	argv += optind;
33663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	*argc_p = rargc - iargc;
33763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	*argv_p = argv;
33863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
33963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	optind = 0;
34063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	free_opts(opts);
34163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	/* Clear flags if target will be used again */
34263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        m->tflags=0;
34363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        m->used=0;
34463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	/* Free allocated memory */
34563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        if (m->t)
34663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim            free(m->t);
34763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
34863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
34963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	return 0;
35063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
35163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
35263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
35363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstatic int
35463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimprint_ipt(struct action_util *au,FILE * f, struct rtattr *arg)
35563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim{
35663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	struct rtattr *tb[TCA_IPT_MAX + 1];
35763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	struct xt_entry_target *t = NULL;
35863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
35963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (arg == NULL)
36063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		return -1;
36163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
36263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	set_lib_dir();
36363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
36463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	parse_rtattr_nested(tb, TCA_IPT_MAX, arg);
36563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
36663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (tb[TCA_IPT_TABLE] == NULL) {
36763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, "[NULL ipt table name ] assuming mangle ");
36863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	} else {
36963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, "tablename: %s ",
370ff24746cca1ef0c92d46614158e6672acd6b63d3Stephen Hemminger			rta_getattr_str(tb[TCA_IPT_TABLE]));
37163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
37263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
37363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (tb[TCA_IPT_HOOK] == NULL) {
37463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, "[NULL ipt hook name ]\n ");
37563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		return -1;
37663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	} else {
37763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		__u32 hook;
378ff24746cca1ef0c92d46614158e6672acd6b63d3Stephen Hemminger		hook = rta_getattr_u32(tb[TCA_IPT_HOOK]);
37963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, " hook: %s \n", ipthooks[hook]);
38063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
38163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
38263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	if (tb[TCA_IPT_TARG] == NULL) {
38363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, "\t[NULL ipt target parameters ] \n");
38463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		return -1;
38563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	} else {
38663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		struct xtables_target *m = NULL;
38763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		t = RTA_DATA(tb[TCA_IPT_TARG]);
38863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		m = find_target(t->u.user.name, TRY_LOAD);
38963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (NULL != m) {
39063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			if (0 > build_st(m, t)) {
39163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				fprintf(stderr, " %s error \n", m->name);
39263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				return -1;
39363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			}
39463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
39563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			opts =
39663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			    merge_options(opts, m->extra_opts,
39763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim					  &m->option_offset);
39863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		} else {
39963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			fprintf(stderr, " failed to find target %s\n\n",
40063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				t->u.user.name);
40163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			return -1;
40263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
40363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, "\ttarget ");
40463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		m->print(NULL, m->t, 0);
40563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (tb[TCA_IPT_INDEX] == NULL) {
40663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			fprintf(f, " [NULL ipt target index ]\n");
40763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		} else {
40863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			__u32 index;
409ff24746cca1ef0c92d46614158e6672acd6b63d3Stephen Hemminger			index = rta_getattr_u32(tb[TCA_IPT_INDEX]);
41063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			fprintf(f, " \n\tindex %d", index);
41163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
41263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
41363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (tb[TCA_IPT_CNT]) {
41463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			struct tc_cnt *c  = RTA_DATA(tb[TCA_IPT_CNT]);;
41563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			fprintf(f, " ref %d bind %d", c->refcnt, c->bindcnt);
41663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
41763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		if (show_stats) {
41863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			if (tb[TCA_IPT_TM]) {
41963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				struct tcf_t *tm = RTA_DATA(tb[TCA_IPT_TM]);
42063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim				print_tm(f,tm);
42163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim			}
42263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		}
42363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim		fprintf(f, " \n");
42463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
42563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	}
42663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	free_opts(opts);
42763c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
42863c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim	return 0;
42963c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim}
43063c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
43163c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salimstruct action_util ipt_action_util = {
43263c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        .id = "ipt",
43363c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        .parse_aopt = parse_ipt,
43463c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim        .print_aopt = print_ipt,
43563c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim};
43663c7d26f941df1c7aa4a18bac5b3a777bc66216aJamal Hadi Salim
437