linux/net/netfilter/xt_CONNMARK.c
<<
>>
Prefs
   1/*
   2 *      xt_CONNMARK - Netfilter module to modify the connection mark values
   3 *
   4 *      Copyright (C) 2002,2004 MARA Systems AB <http://www.marasystems.com>
   5 *      by Henrik Nordstrom <hno@marasystems.com>
   6 *      Copyright © CC Computer Consultants GmbH, 2007 - 2008
   7 *      Jan Engelhardt <jengelh@computergmbh.de>
   8 *
   9 * This program is free software; you can redistribute it and/or modify
  10 * it under the terms of the GNU General Public License as published by
  11 * the Free Software Foundation; either version 2 of the License, or
  12 * (at your option) any later version.
  13 *
  14 * This program is distributed in the hope that it will be useful,
  15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  17 * GNU General Public License for more details.
  18 *
  19 * You should have received a copy of the GNU General Public License
  20 * along with this program; if not, write to the Free Software
  21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  22 */
  23#include <linux/module.h>
  24#include <linux/skbuff.h>
  25#include <linux/ip.h>
  26#include <net/checksum.h>
  27
  28MODULE_AUTHOR("Henrik Nordstrom <hno@marasystems.com>");
  29MODULE_DESCRIPTION("Xtables: connection mark modification");
  30MODULE_LICENSE("GPL");
  31MODULE_ALIAS("ipt_CONNMARK");
  32MODULE_ALIAS("ip6t_CONNMARK");
  33
  34#include <linux/netfilter/x_tables.h>
  35#include <linux/netfilter/xt_CONNMARK.h>
  36#include <net/netfilter/nf_conntrack_ecache.h>
  37
  38static unsigned int
  39connmark_tg(struct sk_buff *skb, const struct xt_target_param *par)
  40{
  41        const struct xt_connmark_tginfo1 *info = par->targinfo;
  42        enum ip_conntrack_info ctinfo;
  43        struct nf_conn *ct;
  44        u_int32_t newmark;
  45
  46        ct = nf_ct_get(skb, &ctinfo);
  47        if (ct == NULL)
  48                return XT_CONTINUE;
  49
  50        switch (info->mode) {
  51        case XT_CONNMARK_SET:
  52                newmark = (ct->mark & ~info->ctmask) ^ info->ctmark;
  53                if (ct->mark != newmark) {
  54                        ct->mark = newmark;
  55                        nf_conntrack_event_cache(IPCT_MARK, ct);
  56                }
  57                break;
  58        case XT_CONNMARK_SAVE:
  59                newmark = (ct->mark & ~info->ctmask) ^
  60                          (skb->mark & info->nfmask);
  61                if (ct->mark != newmark) {
  62                        ct->mark = newmark;
  63                        nf_conntrack_event_cache(IPCT_MARK, ct);
  64                }
  65                break;
  66        case XT_CONNMARK_RESTORE:
  67                newmark = (skb->mark & ~info->nfmask) ^
  68                          (ct->mark & info->ctmask);
  69                skb->mark = newmark;
  70                break;
  71        }
  72
  73        return XT_CONTINUE;
  74}
  75
  76static bool connmark_tg_check(const struct xt_tgchk_param *par)
  77{
  78        if (nf_ct_l3proto_try_module_get(par->family) < 0) {
  79                printk(KERN_WARNING "cannot load conntrack support for "
  80                       "proto=%u\n", par->family);
  81                return false;
  82        }
  83        return true;
  84}
  85
  86static void connmark_tg_destroy(const struct xt_tgdtor_param *par)
  87{
  88        nf_ct_l3proto_module_put(par->family);
  89}
  90
  91static struct xt_target connmark_tg_reg __read_mostly = {
  92        .name           = "CONNMARK",
  93        .revision       = 1,
  94        .family         = NFPROTO_UNSPEC,
  95        .checkentry     = connmark_tg_check,
  96        .target         = connmark_tg,
  97        .targetsize     = sizeof(struct xt_connmark_tginfo1),
  98        .destroy        = connmark_tg_destroy,
  99        .me             = THIS_MODULE,
 100};
 101
 102static int __init connmark_tg_init(void)
 103{
 104        return xt_register_target(&connmark_tg_reg);
 105}
 106
 107static void __exit connmark_tg_exit(void)
 108{
 109        xt_unregister_target(&connmark_tg_reg);
 110}
 111
 112module_init(connmark_tg_init);
 113module_exit(connmark_tg_exit);
 114