Add ip rule flush capabilty and fix all the prototype changes
because of that code rewrites the nlmsghdr.
(Logical change 1.106)
diff --git a/ChangeLog b/ChangeLog
index 5d5476b..c9c6f1f 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,12 @@
+2004-12-07 Stephen Hemminger <shemminger@osdl.org>
+
+ * Cleanup warning generated because ip_rule_flush needs to modify
+ the netlink message
+
+2004-12-07 Sven Anders <anders@anduras.de>
+
+ * Add ip rule flush
+
2004-10-19 Harald Welte <laforge@gnumonks.org>
* Replace rtstat (and ctstat) with new lnstat
diff --git a/include/libnetlink.h b/include/libnetlink.h
index 3390d8b..08be752 100644
--- a/include/libnetlink.h
+++ b/include/libnetlink.h
@@ -20,7 +20,8 @@
extern int rtnl_wilddump_request(struct rtnl_handle *rth, int fam, int type);
extern int rtnl_dump_request(struct rtnl_handle *rth, int type, void *req, int len);
-typedef int (*rtnl_filter_t)(const struct sockaddr_nl *, const struct nlmsghdr *n, void *);
+typedef int (*rtnl_filter_t)(const struct sockaddr_nl *,
+ struct nlmsghdr *n, void *);
extern int rtnl_dump_filter(struct rtnl_handle *rth, rtnl_filter_t filter,
void *arg1,
rtnl_filter_t junk,
diff --git a/include/ll_map.h b/include/ll_map.h
index 238a728..3bff5e9 100644
--- a/include/ll_map.h
+++ b/include/ll_map.h
@@ -1,8 +1,8 @@
#ifndef __LL_MAP_H__
#define __LL_MAP_H__ 1
-extern int ll_remember_index(const struct sockaddr_nl *who, const struct nlmsghdr *n,
- void *arg);
+extern int ll_remember_index(const struct sockaddr_nl *who,
+ struct nlmsghdr *n, void *arg);
extern int ll_init_map(struct rtnl_handle *rth);
extern int ll_name_to_index(const char *name);
extern const char *ll_index_to_name(int idx);
diff --git a/ip/ip_common.h b/ip/ip_common.h
index c359911..93ac3f9 100644
--- a/ip/ip_common.h
+++ b/ip/ip_common.h
@@ -1,11 +1,11 @@
extern int print_linkinfo(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg);
extern int print_addrinfo(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg);
extern int print_neigh(const struct sockaddr_nl *who,
- const struct nlmsghdr *n, void *arg);
+ struct nlmsghdr *n, void *arg);
extern int ipaddr_list(int argc, char **argv);
extern int ipaddr_list_link(int argc, char **argv);
extern int iproute_monitor(int argc, char **argv);
@@ -14,7 +14,7 @@
extern void ipaddr_reset_filter(int);
extern void ipneigh_reset_filter(void);
extern int print_route(const struct sockaddr_nl *who,
- const struct nlmsghdr *n, void *arg);
+ struct nlmsghdr *n, void *arg);
extern int do_ipaddr(int argc, char **argv);
extern int do_iproute(int argc, char **argv);
extern int do_iprule(int argc, char **argv);
diff --git a/ip/ipaddress.c b/ip/ipaddress.c
index 24c9322..ae6f8c1 100644
--- a/ip/ipaddress.c
+++ b/ip/ipaddress.c
@@ -126,7 +126,8 @@
printf("qlen %d", ifr.ifr_qlen);
}
-int print_linkinfo(const struct sockaddr_nl *who, const struct nlmsghdr *n, void *arg)
+int print_linkinfo(const struct sockaddr_nl *who,
+ struct nlmsghdr *n, void *arg)
{
FILE *fp = (FILE*)arg;
struct ifinfomsg *ifi = NLMSG_DATA(n);
@@ -275,7 +276,7 @@
return 0;
}
-int print_addrinfo(const struct sockaddr_nl *who, const struct nlmsghdr *n,
+int print_addrinfo(const struct sockaddr_nl *who, struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;
@@ -466,7 +467,7 @@
}
-static int store_nlmsg(const struct sockaddr_nl *who, const struct nlmsghdr *n,
+static int store_nlmsg(const struct sockaddr_nl *who, struct nlmsghdr *n,
void *arg)
{
struct nlmsg_list **linfo = (struct nlmsg_list**)arg;
diff --git a/ip/ipmonitor.c b/ip/ipmonitor.c
index 46373e7..7f5041a 100644
--- a/ip/ipmonitor.c
+++ b/ip/ipmonitor.c
@@ -34,7 +34,7 @@
int accept_msg(const struct sockaddr_nl *who,
- const struct nlmsghdr *n, void *arg)
+ struct nlmsghdr *n, void *arg)
{
FILE *fp = (FILE*)arg;
diff --git a/ip/ipneigh.c b/ip/ipneigh.c
index c3105ef..33e90ad 100644
--- a/ip/ipneigh.c
+++ b/ip/ipneigh.c
@@ -217,7 +217,7 @@
}
-int print_neigh(const struct sockaddr_nl *who, const struct nlmsghdr *n, void *arg)
+int print_neigh(const struct sockaddr_nl *who, struct nlmsghdr *n, void *arg)
{
FILE *fp = (FILE*)arg;
struct ndmsg *r = NLMSG_DATA(n);
diff --git a/ip/iproute.c b/ip/iproute.c
index c91075c..ccea83b 100644
--- a/ip/iproute.c
+++ b/ip/iproute.c
@@ -103,7 +103,7 @@
return 0;
}
-int print_route(const struct sockaddr_nl *who, const struct nlmsghdr *n, void *arg)
+int print_route(const struct sockaddr_nl *who, struct nlmsghdr *n, void *arg)
{
FILE *fp = (FILE*)arg;
struct rtmsg *r = NLMSG_DATA(n);
diff --git a/ip/iprule.c b/ip/iprule.c
index ced6785..8c1fc27 100644
--- a/ip/iprule.c
+++ b/ip/iprule.c
@@ -32,7 +32,7 @@
static void usage(void)
{
- fprintf(stderr, "Usage: ip rule [ list | add | del ] SELECTOR ACTION\n");
+ fprintf(stderr, "Usage: ip rule [ list | add | del | flush ] SELECTOR ACTION\n");
fprintf(stderr, "SELECTOR := [ from PREFIX ] [ to PREFIX ] [ tos TOS ] [ fwmark FWMARK ]\n");
fprintf(stderr, " [ dev STRING ] [ pref NUMBER ]\n");
fprintf(stderr, "ACTION := [ table TABLE_ID ] [ nat ADDRESS ]\n");
@@ -42,7 +42,7 @@
exit(-1);
}
-static int print_rule(const struct sockaddr_nl *who, const struct nlmsghdr *n,
+static int print_rule(const struct sockaddr_nl *who, struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;
@@ -160,7 +160,7 @@
return 0;
}
-int iprule_list(int argc, char **argv)
+static int iprule_list(int argc, char **argv)
{
struct rtnl_handle rth;
int af = preferred_family;
@@ -190,7 +190,7 @@
}
-int iprule_modify(int cmd, int argc, char **argv)
+static int iprule_modify(int cmd, int argc, char **argv)
{
int table_ok = 0;
struct rtnl_handle rth;
@@ -303,6 +303,64 @@
return 0;
}
+
+static int flush_rule(const struct sockaddr_nl *who, struct nlmsghdr *n, void *arg)
+{
+ struct rtnl_handle rth;
+ struct rtmsg *r = NLMSG_DATA(n);
+ int len = n->nlmsg_len;
+ struct rtattr * tb[RTA_MAX+1];
+
+ len -= NLMSG_LENGTH(sizeof(*r));
+ if (len < 0)
+ return -1;
+
+ memset(tb, 0, sizeof(tb));
+ parse_rtattr(tb, RTA_MAX, RTM_RTA(r), len);
+
+ if (tb[RTA_PRIORITY]) {
+ n->nlmsg_type = RTM_DELRULE;
+ n->nlmsg_flags = NLM_F_REQUEST;
+
+ if (rtnl_open(&rth, 0) < 0)
+ return -1;
+
+ if (rtnl_talk(&rth, n, 0, 0, NULL, NULL, NULL) < 0)
+ return -2;
+ }
+
+ return 0;
+}
+
+static int iprule_flush(int argc, char **argv)
+{
+ struct rtnl_handle rth;
+ int af = preferred_family;
+
+ if (af == AF_UNSPEC)
+ af = AF_INET;
+
+ if (argc > 0) {
+ fprintf(stderr, "\"ip rule flush\" need not any arguments.\n");
+ return -1;
+ }
+
+ if (rtnl_open(&rth, 0) < 0)
+ return 1;
+
+ if (rtnl_wilddump_request(&rth, af, RTM_GETRULE) < 0) {
+ perror("Cannot send dump request");
+ return 1;
+ }
+
+ if (rtnl_dump_filter(&rth, flush_rule, NULL, NULL, NULL) < 0) {
+ fprintf(stderr, "Flush terminated\n");
+ return 1;
+ }
+
+ return 0;
+}
+
int do_iprule(int argc, char **argv)
{
if (argc < 1) {
@@ -315,6 +373,8 @@
return iprule_modify(RTM_NEWRULE, argc-1, argv+1);
} else if (matches(argv[0], "delete") == 0) {
return iprule_modify(RTM_DELRULE, argc-1, argv+1);
+ } else if (matches(argv[0], "flush") == 0) {
+ return iprule_flush(argc-1, argv+1);
} else if (matches(argv[0], "help") == 0)
usage();
diff --git a/ip/rtmon.c b/ip/rtmon.c
index 76ef8b9..5ce7731 100644
--- a/ip/rtmon.c
+++ b/ip/rtmon.c
@@ -46,7 +46,7 @@
fwrite((void*)n1, 1, NLMSG_ALIGN(n1->nlmsg_len), fp);
}
-static int dump_msg(const struct sockaddr_nl *who, const struct nlmsghdr *n,
+static int dump_msg(const struct sockaddr_nl *who, struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;
diff --git a/ip/xfrm_policy.c b/ip/xfrm_policy.c
index fc17a64..95ee01d 100644
--- a/ip/xfrm_policy.c
+++ b/ip/xfrm_policy.c
@@ -336,7 +336,7 @@
}
static int xfrm_policy_print(const struct sockaddr_nl *who,
- const struct nlmsghdr *n, void *arg)
+ struct nlmsghdr *n, void *arg)
{
FILE *fp = (FILE*)arg;
struct xfrm_userpolicy_info *xpinfo = NLMSG_DATA(n);
@@ -521,7 +521,7 @@
* and store it to buffer.
*/
static int xfrm_policy_keep(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg)
{
struct xfrm_buffer *xb = (struct xfrm_buffer *)arg;
diff --git a/ip/xfrm_state.c b/ip/xfrm_state.c
index 54750f4..65f027f 100644
--- a/ip/xfrm_state.c
+++ b/ip/xfrm_state.c
@@ -375,7 +375,7 @@
}
static int xfrm_state_print(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;
@@ -517,7 +517,7 @@
* and store it to buffer.
*/
static int xfrm_state_keep(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg)
{
struct xfrm_buffer *xb = (struct xfrm_buffer *)arg;
diff --git a/lib/ll_map.c b/lib/ll_map.c
index e5798d3..89c0d20 100644
--- a/lib/ll_map.c
+++ b/lib/ll_map.c
@@ -35,7 +35,8 @@
static struct idxmap *idxmap[16];
-int ll_remember_index(const struct sockaddr_nl *who, const struct nlmsghdr *n, void *arg)
+int ll_remember_index(const struct sockaddr_nl *who,
+ struct nlmsghdr *n, void *arg)
{
int h;
struct ifinfomsg *ifi = NLMSG_DATA(n);
diff --git a/misc/ifstat.c b/misc/ifstat.c
index b6f1b87..19b1ff5 100644
--- a/misc/ifstat.c
+++ b/misc/ifstat.c
@@ -63,7 +63,7 @@
struct ifstat_ent *kern_db;
struct ifstat_ent *hist_db;
-int match(char *id)
+static int match(const char *id)
{
int i;
@@ -77,7 +77,8 @@
return 0;
}
-int get_nlmsg(const struct sockaddr_nl *who, const struct nlmsghdr *m, void *arg)
+static int get_nlmsg(const struct sockaddr_nl *who,
+ struct nlmsghdr *m, void *arg)
{
struct ifinfomsg *ifi = NLMSG_DATA(m);
struct rtattr * tb[IFLA_MAX+1];
diff --git a/tc/m_action.c b/tc/m_action.c
index f6edc0d..dc30306 100644
--- a/tc/m_action.c
+++ b/tc/m_action.c
@@ -303,7 +303,7 @@
}
static int do_print_action(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;
diff --git a/tc/tc_class.c b/tc/tc_class.c
index 0352fd6..b4aae95 100644
--- a/tc/tc_class.c
+++ b/tc/tc_class.c
@@ -152,7 +152,7 @@
__u32 filter_qdisc;
static int print_class(const struct sockaddr_nl *who,
- const struct nlmsghdr *n, void *arg)
+ struct nlmsghdr *n, void *arg)
{
FILE *fp = (FILE*)arg;
struct tcmsg *t = NLMSG_DATA(n);
diff --git a/tc/tc_filter.c b/tc/tc_filter.c
index 74e9969..af663dd 100644
--- a/tc/tc_filter.c
+++ b/tc/tc_filter.c
@@ -186,7 +186,7 @@
static __u32 filter_protocol;
static int print_filter(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;
diff --git a/tc/tc_qdisc.c b/tc/tc_qdisc.c
index 6cf08d8..fe7e354 100644
--- a/tc/tc_qdisc.c
+++ b/tc/tc_qdisc.c
@@ -203,7 +203,7 @@
static int filter_ifindex;
static int print_qdisc(const struct sockaddr_nl *who,
- const struct nlmsghdr *n,
+ struct nlmsghdr *n,
void *arg)
{
FILE *fp = (FILE*)arg;