xt_iface: reorder code for upcoming address checking

From now on, info->flags lists the flags to test, not just the flags
to test positively for.
This commit is contained in:
Jan Engelhardt
2010-10-24 18:13:28 +02:00
parent f757049112
commit 6733265358
2 changed files with 26 additions and 20 deletions

View File

@@ -44,9 +44,7 @@ static void iface_print_opt(const struct xt_iface_mtinfo *info,
const unsigned int option, const char *command) const unsigned int option, const char *command)
{ {
if (info->flags & option) if (info->flags & option)
printf(" %s", command); printf(" %s%s", (info->invflags & option) ? "! " : "", command);
if (info->invflags & option)
printf(" ! %s", command);
} }
static void iface_setflag(struct xt_iface_mtinfo *info, static void iface_setflag(struct xt_iface_mtinfo *info,
@@ -55,10 +53,9 @@ static void iface_setflag(struct xt_iface_mtinfo *info,
if (*flags & flag) if (*flags & flag)
xtables_error(PARAMETER_PROBLEM, xtables_error(PARAMETER_PROBLEM,
"iface: \"--%s\" flag already specified", command); "iface: \"--%s\" flag already specified", command);
info->flags |= flag;
if (invert) if (invert)
info->invflags |= flag; info->invflags |= flag;
else
info->flags |= flag;
*flags |= flag; *flags |= flag;
} }

View File

@@ -40,29 +40,38 @@ static const struct xt_iface_flag_pairs xt_iface_lookup[] =
{.iface_flag = XT_IFACE_DORMANT, .iff_flag = IFF_DORMANT}, {.iface_flag = XT_IFACE_DORMANT, .iff_flag = IFF_DORMANT},
}; };
static struct net_device *iface_get(const char *name)
{
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 24)
return dev_get_by_name(&init_net, name);
#else
return dev_get_by_name(name);
#endif
}
static bool iface_flagtest(unsigned int devflags, unsigned int flags,
unsigned int invflags)
{
unsigned int i;
for (i = 0; i < ARRAY_SIZE(xt_iface_lookup); ++i)
if ((flags & xt_iface_lookup[i].iface_flag) &&
!!(devflags & xt_iface_lookup[i].iff_flag) ^
!(invflags & xt_iface_lookup[i].iface_flag))
return false;
return true;
}
static bool xt_iface_mt(const struct sk_buff *skb, static bool xt_iface_mt(const struct sk_buff *skb,
struct xt_action_param *par) struct xt_action_param *par)
{ {
const struct xt_iface_mtinfo *info = par->matchinfo; const struct xt_iface_mtinfo *info = par->matchinfo;
struct net_device *dev; struct net_device *dev = iface_get(info->ifname);
bool retval; bool retval;
int i;
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 24)
dev = dev_get_by_name(&init_net, info->ifname);
#else
dev = dev_get_by_name(info->ifname);
#endif
if (dev == NULL) if (dev == NULL)
return false; return false;
retval = iface_flagtest(dev->flags, info->flags, info->invflags);
retval = true;
for (i = 0; i < ARRAY_SIZE(xt_iface_lookup) && retval; ++i) {
if (info->flags & xt_iface_lookup[i].iface_flag)
retval &= dev->flags & xt_iface_lookup[i].iff_flag;
if (info->invflags & xt_iface_lookup[i].iface_flag)
retval &= !(dev->flags & xt_iface_lookup[i].iff_flag);
}
dev_put(dev); dev_put(dev);
return retval; return retval;
} }