Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
911e72b5
Commit
911e72b5
authored
Jul 17, 2003
by
Bart De Schuymer
Committed by
David S. Miller
Jul 17, 2003
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
[BRIDGE/EBTABLES]: Add stp packet matching.
parent
a99a78fb
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
247 additions
and
0 deletions
+247
-0
include/linux/netfilter_bridge/ebt_stp.h
include/linux/netfilter_bridge/ebt_stp.h
+46
-0
net/bridge/netfilter/Kconfig
net/bridge/netfilter/Kconfig
+10
-0
net/bridge/netfilter/Makefile
net/bridge/netfilter/Makefile
+1
-0
net/bridge/netfilter/ebt_stp.c
net/bridge/netfilter/ebt_stp.c
+190
-0
No files found.
include/linux/netfilter_bridge/ebt_stp.h
0 → 100644
View file @
911e72b5
#ifndef __LINUX_BRIDGE_EBT_STP_H
#define __LINUX_BRIDGE_EBT_STP_H
#define EBT_STP_TYPE 0x0001
#define EBT_STP_FLAGS 0x0002
#define EBT_STP_ROOTPRIO 0x0004
#define EBT_STP_ROOTADDR 0x0008
#define EBT_STP_ROOTCOST 0x0010
#define EBT_STP_SENDERPRIO 0x0020
#define EBT_STP_SENDERADDR 0x0040
#define EBT_STP_PORT 0x0080
#define EBT_STP_MSGAGE 0x0100
#define EBT_STP_MAXAGE 0x0200
#define EBT_STP_HELLOTIME 0x0400
#define EBT_STP_FWDD 0x0800
#define EBT_STP_MASK 0x0fff
#define EBT_STP_CONFIG_MASK 0x0ffe
#define EBT_STP_MATCH "stp"
struct
ebt_stp_config_info
{
uint8_t
flags
;
uint16_t
root_priol
,
root_priou
;
char
root_addr
[
6
],
root_addrmsk
[
6
];
uint32_t
root_costl
,
root_costu
;
uint16_t
sender_priol
,
sender_priou
;
char
sender_addr
[
6
],
sender_addrmsk
[
6
];
uint16_t
portl
,
portu
;
uint16_t
msg_agel
,
msg_ageu
;
uint16_t
max_agel
,
max_ageu
;
uint16_t
hello_timel
,
hello_timeu
;
uint16_t
forward_delayl
,
forward_delayu
;
};
struct
ebt_stp_info
{
uint8_t
type
;
struct
ebt_stp_config_info
config
;
uint16_t
bitmask
;
uint16_t
invflags
;
};
#endif
net/bridge/netfilter/Kconfig
View file @
911e72b5
...
...
@@ -103,6 +103,16 @@ config BRIDGE_EBT_PKTTYPE
If you want to compile it as a module, say M here and read
<file:Documentation/modules.txt>. If unsure, say `N'.
config BRIDGE_EBT_STP
tristate "ebt: STP filter support"
depends on BRIDGE_NF_EBTABLES
help
This option adds the Spanning Tree Protocol match, which
allows STP header field filtering.
If you want to compile it as a module, say M here and read
<file:Documentation/modules.txt>. If unsure, say `N'.
config BRIDGE_EBT_SNAT
tristate "ebt: snat target support"
depends on BRIDGE_NF_EBTABLES
...
...
net/bridge/netfilter/Makefile
View file @
911e72b5
...
...
@@ -11,6 +11,7 @@ obj-$(CONFIG_BRIDGE_EBT_ARP) += ebt_arp.o
obj-$(CONFIG_BRIDGE_EBT_VLAN)
+=
ebt_vlan.o
obj-$(CONFIG_BRIDGE_EBT_MARK)
+=
ebt_mark_m.o
obj-$(CONFIG_BRIDGE_EBT_PKTTYPE)
+=
ebt_pkttype.o
obj-$(CONFIG_BRIDGE_EBT_STP)
+=
ebt_stp.o
obj-$(CONFIG_BRIDGE_EBT_LOG)
+=
ebt_log.o
obj-$(CONFIG_BRIDGE_EBT_SNAT)
+=
ebt_snat.o
obj-$(CONFIG_BRIDGE_EBT_DNAT)
+=
ebt_dnat.o
...
...
net/bridge/netfilter/ebt_stp.c
0 → 100644
View file @
911e72b5
/*
* ebt_stp
*
* Authors:
* Bart De Schuymer <bdschuym@pandora.be>
* Stephen Hemminger <shemminger@osdl.org>
*
* July, 2003
*/
#include <linux/netfilter_bridge/ebtables.h>
#include <linux/netfilter_bridge/ebt_stp.h>
#include <linux/module.h>
#define BPDU_TYPE_CONFIG 0
#define BPDU_TYPE_TCN 0x80
struct
stp_header
{
uint8_t
dsap
;
uint8_t
ssap
;
uint8_t
ctrl
;
uint8_t
pid
;
uint8_t
vers
;
uint8_t
type
;
};
struct
stp_config_pdu
{
uint8_t
flags
;
uint8_t
root
[
8
];
uint8_t
root_cost
[
4
];
uint8_t
sender
[
8
];
uint8_t
port
[
2
];
uint8_t
msg_age
[
2
];
uint8_t
max_age
[
2
];
uint8_t
hello_time
[
2
];
uint8_t
forward_delay
[
2
];
};
#define NR16(p) (p[0] << 8 | p[1])
#define NR32(p) ((p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3])
static
int
ebt_filter_config
(
struct
ebt_stp_info
*
info
,
struct
stp_config_pdu
*
stpc
)
{
struct
ebt_stp_config_info
*
c
;
uint16_t
v16
;
uint32_t
v32
;
int
verdict
,
i
;
c
=
&
info
->
config
;
if
((
info
->
bitmask
&
EBT_STP_FLAGS
)
&&
FWINV
(
c
->
flags
!=
stpc
->
flags
,
EBT_STP_FLAGS
))
return
EBT_NOMATCH
;
if
(
info
->
bitmask
&
EBT_STP_ROOTPRIO
)
{
v16
=
NR16
(
stpc
->
root
);
if
(
FWINV
(
v16
<
c
->
root_priol
||
v16
>
c
->
root_priou
,
EBT_STP_ROOTPRIO
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_ROOTADDR
)
{
verdict
=
0
;
for
(
i
=
0
;
i
<
6
;
i
++
)
verdict
|=
(
stpc
->
root
[
2
+
i
]
^
c
->
root_addr
[
i
])
&
c
->
root_addrmsk
[
i
];
if
(
FWINV
(
verdict
!=
0
,
EBT_STP_ROOTADDR
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_ROOTCOST
)
{
v32
=
NR32
(
stpc
->
root_cost
);
if
(
FWINV
(
v32
<
c
->
root_costl
||
v32
>
c
->
root_costu
,
EBT_STP_ROOTCOST
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_SENDERPRIO
)
{
v16
=
NR16
(
stpc
->
sender
);
if
(
FWINV
(
v16
<
c
->
sender_priol
||
v16
>
c
->
sender_priou
,
EBT_STP_SENDERPRIO
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_SENDERADDR
)
{
verdict
=
0
;
for
(
i
=
0
;
i
<
6
;
i
++
)
verdict
|=
(
stpc
->
sender
[
2
+
i
]
^
c
->
sender_addr
[
i
])
&
c
->
sender_addrmsk
[
i
];
if
(
FWINV
(
verdict
!=
0
,
EBT_STP_SENDERADDR
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_PORT
)
{
v16
=
NR16
(
stpc
->
port
);
if
(
FWINV
(
v16
<
c
->
portl
||
v16
>
c
->
portu
,
EBT_STP_PORT
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_MSGAGE
)
{
v16
=
NR16
(
stpc
->
msg_age
);
if
(
FWINV
(
v16
<
c
->
msg_agel
||
v16
>
c
->
msg_ageu
,
EBT_STP_MSGAGE
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_MAXAGE
)
{
v16
=
NR16
(
stpc
->
max_age
);
if
(
FWINV
(
v16
<
c
->
max_agel
||
v16
>
c
->
max_ageu
,
EBT_STP_MAXAGE
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_HELLOTIME
)
{
v16
=
NR16
(
stpc
->
hello_time
);
if
(
FWINV
(
v16
<
c
->
hello_timel
||
v16
>
c
->
hello_timeu
,
EBT_STP_HELLOTIME
))
return
EBT_NOMATCH
;
}
if
(
info
->
bitmask
&
EBT_STP_FWDD
)
{
v16
=
NR16
(
stpc
->
forward_delay
);
if
(
FWINV
(
v16
<
c
->
forward_delayl
||
v16
>
c
->
forward_delayu
,
EBT_STP_FWDD
))
return
EBT_NOMATCH
;
}
return
EBT_MATCH
;
}
static
int
ebt_filter_stp
(
const
struct
sk_buff
*
skb
,
const
struct
net_device
*
in
,
const
struct
net_device
*
out
,
const
void
*
data
,
unsigned
int
datalen
)
{
struct
ebt_stp_info
*
info
=
(
struct
ebt_stp_info
*
)
data
;
struct
stp_header
stph
;
uint8_t
header
[
6
]
=
{
0x42
,
0x42
,
0x03
,
0x00
,
0x00
,
0x00
};
if
(
skb_copy_bits
(
skb
,
0
,
&
stph
,
sizeof
(
stph
)))
return
EBT_NOMATCH
;
/* The stp code only considers these */
if
(
memcmp
(
&
stph
,
header
,
sizeof
(
header
)))
return
EBT_NOMATCH
;
if
(
info
->
bitmask
&
EBT_STP_TYPE
&&
FWINV
(
info
->
type
!=
stph
.
type
,
EBT_STP_TYPE
))
return
EBT_NOMATCH
;
if
(
stph
.
type
==
BPDU_TYPE_CONFIG
&&
info
->
bitmask
&
EBT_STP_CONFIG_MASK
)
{
struct
stp_config_pdu
stpc
;
if
(
skb_copy_bits
(
skb
,
sizeof
(
stph
),
&
stpc
,
sizeof
(
stpc
)))
return
EBT_NOMATCH
;
return
ebt_filter_config
(
info
,
&
stpc
);
}
return
EBT_MATCH
;
}
static
int
ebt_stp_check
(
const
char
*
tablename
,
unsigned
int
hookmask
,
const
struct
ebt_entry
*
e
,
void
*
data
,
unsigned
int
datalen
)
{
struct
ebt_stp_info
*
info
=
(
struct
ebt_stp_info
*
)
data
;
int
len
=
sizeof
(
struct
ebt_stp_info
);
uint8_t
bridge_ula
[
6
]
=
{
0x01
,
0x80
,
0xc2
,
0x00
,
0x00
,
0x00
};
uint8_t
msk
[
6
]
=
{
0xff
,
0xff
,
0xff
,
0xff
,
0xff
,
0xff
};
if
(
info
->
bitmask
&
~
EBT_STP_MASK
||
info
->
invflags
&
~
EBT_STP_MASK
||
!
(
info
->
bitmask
&
EBT_STP_MASK
))
return
-
EINVAL
;
if
(
datalen
!=
len
)
return
-
EINVAL
;
/* Make sure the match only receives stp frames */
if
(
memcmp
(
e
->
destmac
,
bridge_ula
,
ETH_ALEN
)
||
memcmp
(
e
->
destmsk
,
msk
,
ETH_ALEN
)
||
!
(
e
->
bitmask
&
EBT_DESTMAC
))
return
-
EINVAL
;
return
0
;
}
static
struct
ebt_match
filter_stp
=
{
.
name
=
EBT_STP_MATCH
,
.
match
=
ebt_filter_stp
,
.
check
=
ebt_stp_check
,
.
me
=
THIS_MODULE
,
};
static
int
__init
init
(
void
)
{
return
ebt_register_match
(
&
filter_stp
);
}
static
void
__exit
fini
(
void
)
{
ebt_unregister_match
(
&
filter_stp
);
}
module_init
(
init
);
module_exit
(
fini
);
MODULE_LICENSE
(
"GPL"
);
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment