[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
(usagi-users 00052) Sugesstion for Setting the IPv6 Traffic Class
- To: usagi-users@xxxxxxxxxxxxxx
- Subject: (usagi-users 00052) Sugesstion for Setting the IPv6 Traffic Class
- From: Sampo Saaristo <sambo@xxxxxxxxx>
- Date: Thu, 07 Dec 2000 12:05:28 +0200
- Cc: sambo@xxxxxxxxx
- Reply-to: usagi-users@xxxxxxxxxxxxxx
- Sender: sambo@xxxxxxxxx
Greetings from Finland.
This is a suggestion for setting the TC-octet on socket level. All comments
would appreciated.
The patch below introduces a new socket option IPV6_TCLASS for SOL_IPV6.
The option causes the traffic -- sent from the socket it was applied to -- to
be stamped with given 8-bit Traffic Class -value. I tested it with TCP and UDP
sockets and according to tcpdump(8) the TC-field in the IPv6-header got the
intended value. The patch is against the current USAGI/kernel linux24-release
from CVS.
--
Sampo Saaristo
TUT/Telecom lab
--__--__--__--__--__--__--__--__--__--__--__--__--__--__--__--__
Index: include/linux/in6.h
===================================================================
RCS file: /cvsroot/usagi/kernel/linux24/include/linux/in6.h,v
retrieving revision 1.10
diff -u -r1.10 in6.h
--- include/linux/in6.h 2000/12/02 08:30:46 1.10
+++ include/linux/in6.h 2000/12/07 09:57:38
@@ -138,6 +138,7 @@
#define IPV6_NEXTHOP 9
#define IPV6_AUTHHDR 10
#define IPV6_FLOWINFO 11
+#define IPV6_TCLASS 12
#define IPV6_UNICAST_HOPS 16
#define IPV6_MULTICAST_IF 17
Index: include/net/sock.h
===================================================================
RCS file: /cvsroot/usagi/kernel/linux24/include/net/sock.h,v
retrieving revision 1.7
diff -u -r1.7 sock.h
--- include/net/sock.h 2000/11/21 08:25:59 1.7
+++ include/net/sock.h 2000/12/07 09:57:38
@@ -146,6 +146,7 @@
struct in6_addr *daddr_cache;
__u32 flow_label;
+ __u8 tclass;
__u32 frag_size;
int hop_limit;
int mcast_hops;
Index: net/ipv6/ip6_output.c
===================================================================
RCS file: /cvsroot/usagi/kernel/linux24/net/ipv6/ip6_output.c,v
retrieving revision 1.4
diff -u -r1.4 ip6_output.c
--- net/ipv6/ip6_output.c 2000/11/23 10:40:00 1.4
+++ net/ipv6/ip6_output.c 2000/12/07 09:57:38
@@ -24,6 +24,7 @@
* etc.
*
* H. von Brand : Added missing #include <linux/string.h>
+ * S. Saaristo : Support for setting of traffic class.
*/
#include <linux/config.h>
@@ -228,8 +229,11 @@
*(u32*)hdr = __constant_htonl(0x60000000) | fl->fl6_flowlabel;
hlimit = -1;
- if (np)
- hlimit = np->hop_limit;
+ if (np){
+ hlimit = np->hop_limit;
+ hdr->tclass1 = np->tclass>>4;
+ hdr->tclass2_flow[0] |= np->tclass << 4;
+ }
if (hlimit < 0)
hlimit = ((struct rt6_info*)dst)->rt6i_hoplimit;
@@ -282,15 +286,15 @@
hdr->payload_len = htons(len);
hdr->nexthdr = proto;
hdr->hop_limit = np->hop_limit;
-
ipv6_addr_copy(&hdr->saddr, saddr);
ipv6_addr_copy(&hdr->daddr, daddr);
return 0;
}
-static struct ipv6hdr * ip6_bld_1(struct sock *sk, struct sk_buff *skb,
struct flowi *fl,
- int hlimit, unsigned pktlength)
+static struct ipv6hdr * ip6_bld_1(struct sock *sk, struct sk_buff *skb,
+ struct flowi *fl, int hlimit, u8 tclass,
+ unsigned pktlength)
{
struct ipv6hdr *hdr;
@@ -301,6 +305,8 @@
hdr->payload_len = htons(pktlength - sizeof(struct ipv6hdr));
hdr->hop_limit = hlimit;
+ hdr->tclass1 = tclass>>4;
+ hdr->tclass2_flow[0] |= tclass << 4;
hdr->nexthdr = fl->proto;
ipv6_addr_copy(&hdr->saddr, fl->nl_u.ip6_u.saddr);
@@ -328,7 +334,8 @@
const void *data, struct dst_entry *dst,
struct flowi *fl, struct ipv6_txoptions *opt,
struct in6_addr *final_dst,
- int hlimit, int flags, unsigned length, int mtu)
+ int hlimit, u8 tclass,
+ int flags, unsigned length, int mtu)
{
struct ipv6hdr *hdr;
struct sk_buff *last_skb;
@@ -435,7 +442,7 @@
skb_reserve(last_skb, (dst->dev->hard_header_len + 15) & ~15);
- hdr = ip6_bld_1(sk, last_skb, fl, hlimit, frag_len+unfrag_len);
+ hdr = ip6_bld_1(sk, last_skb, fl, hlimit, tclass, frag_len+unfrag_len);
prev_hdr = &hdr->nexthdr;
if (opt && opt->opt_nflen)
@@ -533,6 +540,7 @@
int err = 0;
unsigned int pktlength, jumbolen, mtu;
struct in6_addr saddr;
+ u8 tclass;
if (opt && opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) opt->srcrt;
@@ -672,9 +680,12 @@
hdr = (struct ipv6hdr *) skb->tail;
skb->nh.ipv6h = hdr;
-
+
+ if(np)
+ tclass = np->tclass;
+
if (!sk->protinfo.af_inet.hdrincl) {
- ip6_bld_1(sk, skb, fl, hlimit,
+ ip6_bld_1(sk, skb, fl, hlimit, tclass,
jumbolen ? sizeof(struct ipv6hdr) : pktlength);
if (opt || jumbolen) {
@@ -705,8 +716,8 @@
goto out;
}
- err = ip6_frag_xmit(sk, getfrag, data, dst, fl, opt, final_dst, hlimit,
- flags, length, mtu);
+ err = ip6_frag_xmit(sk, getfrag, data, dst, fl, opt, final_dst,
+ hlimit, tclass, flags, length, mtu);
}
/*
Index: net/ipv6/ipv6_sockglue.c
===================================================================
RCS file: /cvsroot/usagi/kernel/linux24/net/ipv6/ipv6_sockglue.c,v
retrieving revision 1.17
diff -u -r1.17 ipv6_sockglue.c
--- net/ipv6/ipv6_sockglue.c 2000/11/14 03:27:41 1.17
+++ net/ipv6/ipv6_sockglue.c 2000/12/07 09:57:38
@@ -257,6 +257,12 @@
np->rxopt.bits.rxflow = valbool;
retv = 0;
break;
+ case IPV6_TCLASS:
+ if (optlen != sizeof(int))
+ goto e_inval;
+ np->tclass = (__u8 *)val;
+ retv = 0;
+ break;
case IPV6_PKTOPTIONS:
{