11da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 21da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * ebt_mark 31da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 41da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Authors: 51da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Bart De Schuymer <bdschuym@pandora.be> 61da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 71da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * July, 2002 81da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 91da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* The mark target can be used in any chain, 121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * I believe adding a mangle table just for marking is total overkill. 131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Marking a frame doesn't really change anything in the frame anyway. 141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1618219d3f7d6a5bc43825a41e0763158efbdb80d3Jan Engelhardt#include <linux/module.h> 1718219d3f7d6a5bc43825a41e0763158efbdb80d3Jan Engelhardt#include <linux/netfilter/x_tables.h> 181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/netfilter_bridge/ebtables.h> 191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/netfilter_bridge/ebt_mark_t.h> 201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 212d06d4a5cc107046508d860a0b47dbc43b829b79Jan Engelhardtstatic unsigned int 224b560b447df83368df44bd3712c0c39b1d79ba04Jan Engelhardtebt_mark_tg(struct sk_buff *skb, const struct xt_action_param *par) 231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 247eb3558655aaa87a3e71a0c065dfaddda521fa6dJan Engelhardt const struct ebt_mark_t_info *info = par->targinfo; 25b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer int action = info->target & -16; 261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 27b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer if (action == MARK_SET_VALUE) 283db05fea51cdb162cfa8f69e9cfb9e228919d2a9Herbert Xu skb->mark = info->mark; 29b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer else if (action == MARK_OR_VALUE) 303db05fea51cdb162cfa8f69e9cfb9e228919d2a9Herbert Xu skb->mark |= info->mark; 31b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer else if (action == MARK_AND_VALUE) 323db05fea51cdb162cfa8f69e9cfb9e228919d2a9Herbert Xu skb->mark &= info->mark; 33b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer else 343db05fea51cdb162cfa8f69e9cfb9e228919d2a9Herbert Xu skb->mark ^= info->mark; 356869c4d8e066e21623c812c448a05f1ed931c9c6Harald Welte 36d12cdc3ccf140bd2febef1c1be92284571da983fBart De Schuymer return info->target | ~EBT_VERDICT_BITS; 371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 39135367b8f6a18507af6b9a6910a14b5699415309Jan Engelhardtstatic int ebt_mark_tg_check(const struct xt_tgchk_param *par) 401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 41af5d6dc200eb0fcc6fbd3df1ab4d8969004cb37fJan Engelhardt const struct ebt_mark_t_info *info = par->targinfo; 42b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer int tmp; 431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 44d12cdc3ccf140bd2febef1c1be92284571da983fBart De Schuymer tmp = info->target | ~EBT_VERDICT_BITS; 45b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer if (BASE_CHAIN && tmp == EBT_RETURN) 46d6b00a5345ce4e86e8b00a88bb84a2c0c1f69ddcJan Engelhardt return -EINVAL; 47b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer if (tmp < -NUM_STANDARD_TARGETS || tmp >= 0) 48d6b00a5345ce4e86e8b00a88bb84a2c0c1f69ddcJan Engelhardt return -EINVAL; 49d12cdc3ccf140bd2febef1c1be92284571da983fBart De Schuymer tmp = info->target & ~EBT_VERDICT_BITS; 50b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer if (tmp != MARK_SET_VALUE && tmp != MARK_OR_VALUE && 51b18dfa90c008850e0f3bfd63638dd8fbe8e08701Bart De Schuymer tmp != MARK_AND_VALUE && tmp != MARK_XOR_VALUE) 52d6b00a5345ce4e86e8b00a88bb84a2c0c1f69ddcJan Engelhardt return -EINVAL; 53d6b00a5345ce4e86e8b00a88bb84a2c0c1f69ddcJan Engelhardt return 0; 541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 556e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal#ifdef CONFIG_COMPAT 566e705f56a181118f6fbd35e6b443eab33df07290Florian Westphalstruct compat_ebt_mark_t_info { 576e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal compat_ulong_t mark; 586e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal compat_uint_t target; 596e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal}; 606e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal 616e705f56a181118f6fbd35e6b443eab33df07290Florian Westphalstatic void mark_tg_compat_from_user(void *dst, const void *src) 626e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal{ 636e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal const struct compat_ebt_mark_t_info *user = src; 646e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal struct ebt_mark_t_info *kern = dst; 656e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal 666e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal kern->mark = user->mark; 676e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal kern->target = user->target; 686e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal} 696e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal 706e705f56a181118f6fbd35e6b443eab33df07290Florian Westphalstatic int mark_tg_compat_to_user(void __user *dst, const void *src) 716e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal{ 726e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal struct compat_ebt_mark_t_info __user *user = dst; 736e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal const struct ebt_mark_t_info *kern = src; 746e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal 756e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal if (put_user(kern->mark, &user->mark) || 766e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal put_user(kern->target, &user->target)) 776e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal return -EFAULT; 786e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal return 0; 796e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal} 806e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal#endif 811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 82043ef46c7690bfdbd5b012e15812a14a19ca5604Jan Engelhardtstatic struct xt_target ebt_mark_tg_reg __read_mostly = { 83043ef46c7690bfdbd5b012e15812a14a19ca5604Jan Engelhardt .name = "mark", 84001a18d369f4813ed792629ff4a9a6ade2a4a031Jan Engelhardt .revision = 0, 85001a18d369f4813ed792629ff4a9a6ade2a4a031Jan Engelhardt .family = NFPROTO_BRIDGE, 862d06d4a5cc107046508d860a0b47dbc43b829b79Jan Engelhardt .target = ebt_mark_tg, 872d06d4a5cc107046508d860a0b47dbc43b829b79Jan Engelhardt .checkentry = ebt_mark_tg_check, 88fc0e3df4f00a5f62c2f2fce84bf496136b58c474Florian Westphal .targetsize = sizeof(struct ebt_mark_t_info), 896e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal#ifdef CONFIG_COMPAT 906e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal .compatsize = sizeof(struct compat_ebt_mark_t_info), 916e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal .compat_from_user = mark_tg_compat_from_user, 926e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal .compat_to_user = mark_tg_compat_to_user, 936e705f56a181118f6fbd35e6b443eab33df07290Florian Westphal#endif 941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds .me = THIS_MODULE, 951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds}; 961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 9765b4b4e81a5094d52cbe372b887b1779abe53f9bAndrew Mortonstatic int __init ebt_mark_init(void) 981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 99043ef46c7690bfdbd5b012e15812a14a19ca5604Jan Engelhardt return xt_register_target(&ebt_mark_tg_reg); 1001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 1011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 10265b4b4e81a5094d52cbe372b887b1779abe53f9bAndrew Mortonstatic void __exit ebt_mark_fini(void) 1031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 104043ef46c7690bfdbd5b012e15812a14a19ca5604Jan Engelhardt xt_unregister_target(&ebt_mark_tg_reg); 1051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 1061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 10765b4b4e81a5094d52cbe372b887b1779abe53f9bAndrew Mortonmodule_init(ebt_mark_init); 10865b4b4e81a5094d52cbe372b887b1779abe53f9bAndrew Mortonmodule_exit(ebt_mark_fini); 109f776c4cda449bab463f5388eb07bd63dc52e2b13Jan EngelhardtMODULE_DESCRIPTION("Ebtables: Packet mark modification"); 1101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsMODULE_LICENSE("GPL"); 111