6lowpan: uncompress of addresses fix
Subsystems (3)
v2 cover 6lowpan: uncompress of addresses fix
The current implementation to uncompress addresses in a 6lowpan header is completely broken.
This patch series fixes the parsing of addresses in a 6lowpan header. It contains a major rewrite of the uncompress address function to parse the address in a correct way.
Changes since v2:
- Add tags for net-next
- Change commit msg in Patch 1/6 that this patch depends for the following patches
Alexander Aring (5):
6lowpan: init ipv6hdr buffer to zero 6lowpan: introduce lowpan_fetch_skb function 6lowpan: add function to uncompress multicast addr 6lowpan: lowpan_uncompress_addr with address_mode 6lowpan: handle context based source address
David Hauweele (1):
6lowpan: Fix fragmentation with link-local compressed addresses
net/ieee802154/6lowpan.c | 284 +++++++++++++++++++++++++++++++---------------- net/ieee802154/6lowpan.h | 20 +++- 2 files changed, 203 insertions(+), 101 deletions(-)
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
A message that is not in the archive (sent off-list or not yet received): 1376478108-3539-1-git-send-email-alex.aring-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org
PATCH v2 1/6 6lowpan: init ipv6hdr buffer to zero
This patch simplify the handling to set fields inside of struct ipv6hdr to zero. Instead of setting some memory regions with memset to zero we initialize the whole ipv6hdr to zero.
This is a simplification for parsing the 6lowpan header for the upcomming patches.
--- net/ieee802154/6lowpan.c | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-)
net/ieee802154/6lowpan.c +1 -11
@@ -223,10 +223,6 @@ lowpan_uncompress_addr(struct sk_buff *skb, struct in6_addr *ipaddr,if (prefcount >0 )memcpy (ipaddr, prefix, prefcount); -if (prefcount + postcount <16 ) -memset (&ipaddr->s6_addr[prefcount],0 , -16 - (prefcount + postcount)); -if (postcount >0 ) {memcpy (&ipaddr->s6_addr[16 - postcount], skb->data, postcount);skb_pull (skb, postcount);
@@ -723,7 +719,7 @@ frame_err:static int lowpan_process_data (struct sk_buff *skb) { -struct ipv6hdr hdr; +struct ipv6hdr hdr = {};u8 tmp, iphc0, iphc1, num_context =0 ;u8 *_saddr, *_daddr;int err;
@@ -868,8 +864,6 @@ lowpan_process_data(struct sk_buff *skb) hdr.priority = ((tmp >>2 ) &0x0f ); hdr.flow_lbl[0 ] = ((tmp <<6 ) &0xC0 ) | ((tmp >>2 ) &0x30 ); - hdr.flow_lbl[1 ] =0 ; - hdr.flow_lbl[2 ] =0 ;break ;/* * Flow Label carried in-line
@@ -885,10 +879,6 @@ lowpan_process_data(struct sk_buff *skb)break ;/* Traffic Class and Flow Label are elided */ case 3 :/* 11b */ - hdr.priority =0 ; - hdr.flow_lbl[0 ] =0 ; - hdr.flow_lbl[1 ] =0 ; - hdr.flow_lbl[2 ] =0 ;break ;default :break ;
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
A message that is not in the archive (sent off-list or not yet received): 1376478108-3539-2-git-send-email-alex.aring-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org
Re: [PATCH 1/6] 6lowpan: init ipv6hdr buffer to zero
Hi,
I forgot a "net-next" in the subject, sry.
So this patch is for "net-next"
Regards
Alex
------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes.
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
PATCH v2 2/6 6lowpan: Fix fragmentation with link-local compressed addresses
In reply to a message not in the archiveFrom: David Hauweele <[email protected]>
When a new 6lowpan fragment is received, a skbuff is allocated for the reassembled packet. However when a 6lowpan packet compresses link-local addresses based on link-layer addresses, the processing function relies on the skb mac control block to find the related link-layer address.
This patch copies the control block from the first fragment into the newly allocated skb to keep a trace of the link-layer addresses in case of a link-local compressed address.
Edit: small changes on comment issue
--- net/ieee802154/6lowpan.c | 6 ++++++ 1 file changed, 6 insertions(+)
net/ieee802154/6lowpan.c +6 -0
@@ -698,6 +698,12 @@ lowpan_alloc_new_frame(struct sk_buff *skb, u16 len, u16 tag)skb_reserve (frame->skb,sizeof (struct ipv6hdr ));skb_put (frame->skb, frame->length); +/* copy the first control block to keep a +* trace of the link-layer addresses in case +* of a link-local compressed address +*/ +memcpy (frame->skb->cb, skb->cb,sizeof (skb->cb)); +init_timer (&frame->timer);/* time out is the same as for ipv6 - 60 sec */ frame->timer.expires = jiffies +LOWPAN_FRAG_TIMEOUT ;
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
PATCH v2 3/6 6lowpan: introduce lowpan_fetch_skb function
In reply to a message not in the archiveThis patch adds a helper function to parse the ipv6 header to a 6lowpan header in stream.
This function checks first if we can pull data with a specific length from a skb. If this seems to be okay, we copy skb data to a destination pointer and run skb_pull.
--- net/ieee802154/6lowpan.h | 12 ++++++++++++ 1 file changed, 12 insertions(+)
net/ieee802154/6lowpan.h +12 -0
@@ -233,4 +233,16 @@dest = 16 bit inline */ #define LOWPAN_NHC_UDP_CS_P_11 0xF3/* source & dest = 0xF0B + 4bit inline */ +static inline bool lowpan_fetch_skb (struct sk_buff *skb, +void *data,const unsigned int len) +{ +if (unlikely (!pskb_may_pull (skb, len))) +return true; + +skb_copy_from_linear_data (skb, data, len); +skb_pull (skb, len); + +return false; +} +#endif /* __6LOWPAN_H__ */
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
Re: [PATCH net-next 3/6] 6lowpan: introduce lowpan_fetch_skb function
Quoted 22 lines · Alexander Aring
This patch adds a helper function to parse the ipv6 header to a 6lowpan header in stream.
This function checks first if we can pull data with a specific length from a skb. If this seems to be okay, we copy skb data to a destination pointer and run
skb_pull.Signed-off-by Alexander Aring <[email protected]>Reviewed-by Werner Almesberger <[email protected]>--- net/ieee802154/6lowpan.h | 12 ++++++++++++ 1 file changed, 12 insertions(+)net/ieee802154/6lowpan.h +1
-0@@ -233,4 +233,16 @@dest = 16 bit inline */ #define LOWPAN_NHC_UDP_CS_P_11 0xF3/* source & dest = 0xF0B + 4bit inline */ +static inline bool lowpan_fetch_skb(struct sk_buff *skb,
net/ieee802154/6lowpan.h line 246
Quoted 10 lines
net/ieee802154/6lowpan.h +10
-0+ void *data, const unsigned int len) +{ +if (unlikely (!pskb_may_pull (skb, len))) +return true; + +skb_copy_from_linear_data (skb, data, len); +skb_pull (skb, len); + +return false; +}
Isn't the return value inverted here?
Greetings,
Hannes
Re: [PATCH net-next 3/6] 6lowpan: introduce lowpan_fetch_skb function
Quoted 22 lines · Hannes Frederic Sowa
Quoted 21 lines · Alexander Aring
This patch adds a helper function to parse the ipv6 header to a 6lowpan header in stream.
This function checks first if we can pull data with a specific length from a skb. If this seems to be okay, we copy skb data to a destination pointer and run
skb_pull.Signed-off-by Alexander Aring <[email protected]>Reviewed-by Werner Almesberger <[email protected]>--- net/ieee802154/6lowpan.h | 12 ++++++++++++ 1 file changed, 12 insertions(+)net/ieee802154/6lowpan.h +0
-0@@ -233,4 +233,16 @@dest = 16 bit inline */ #define LOWPAN_NHC_UDP_CS_P_11 0xF3/* source & dest = 0xF0B + 4bit inline */
Quoted 13 lines
net/ieee802154/6lowpan.h line 246
Quoted 11 lines
net/ieee802154/6lowpan.h +11
-0+static inline bool lowpan_fetch_skb (struct sk_buff *skb, +void *data,const unsigned int len) +{ +if (unlikely (!pskb_may_pull (skb, len))) +return true; + +skb_copy_from_linear_data (skb, data, len); +skb_pull (skb, len); + +return false; +}Isn't the return value inverted here?
Nope, everything is right here, but I spent several minutes to get it... Probably using of standard intergers will be better here: return -EINVAL and return 0;
Quoted 5 lines
Greetings,
Hannes
Re: [PATCH net-next 3/6] 6lowpan: introduce lowpan_fetch_skb function
Quoted 38 lines · Alexander Smirnov
Quoted 23 lines · Hannes Frederic Sowa
Quoted 22 lines · Alexander Aring
This patch adds a helper function to parse the ipv6 header to a 6lowpan header in stream.
This function checks first if we can pull data with a specific length from a skb. If this seems to be okay, we copy skb data to a destination pointer and run
skb_pull.Signed-off-by Alexander Aring <[email protected]>Reviewed-by Werner Almesberger <[email protected]>--- net/ieee802154/6lowpan.h | 12 ++++++++++++ 1 file changed, 12 insertions(+)net/ieee802154/6lowpan.h +0
-0@@ -233,4 +233,16 @@dest = 16 bit inline */ #define LOWPAN_NHC_UDP_CS_P_11 0xF3/* source & dest = 0xF0B + 4bit inline */ Quoted 13 lines
net/ieee802154/6lowpan.h line 246
Quoted 11 lines
net/ieee802154/6lowpan.h +11
-0+static inline bool lowpan_fetch_skb (struct sk_buff *skb, +void *data,const unsigned int len) +{ +if (unlikely (!pskb_may_pull (skb, len))) +return true; + +skb_copy_from_linear_data (skb, data, len); +skb_pull (skb, len); + +return false; +}Isn't the return value inverted here?
Quoted 3 lines
Nope, everything is right here, but I spent several minutes to get it... Probably using of standard intergers will be better here: return
-EINVALand return 0;
Ah, yes, I saw it in your next patch. You could also use false for failure and true for success. Either way, this seemd a bit unnatural for me.
Thanks,
Hannes
Alexander Aring
maintainerRe: [PATCH net-next 3/6] 6lowpan: introduce lowpan_fetch_skb function
In reply to Alexander SmirnovHi Alex,
Quoted 37 lines · Alexander Smirnov
Quoted 22 lines · Hannes Frederic Sowa
Quoted 21 lines · Alexander Aring
This patch adds a helper function to parse the ipv6 header to a 6lowpan header in stream.
This function checks first if we can pull data with a specific length from a skb. If this seems to be okay, we copy skb data to a destination pointer and run
skb_pull.Signed-off-by Alexander Aring <[email protected]>Reviewed-by Werner Almesberger <[email protected]>--- net/ieee802154/6lowpan.h | 12 ++++++++++++ 1 file changed, 12 insertions(+)net/ieee802154/6lowpan.h +0
-0@@ -233,4 +233,16 @@dest = 16 bit inline */ #define LOWPAN_NHC_UDP_CS_P_11 0xF3/* source & dest = 0xF0B + 4bit inline */ Quoted 13 lines
net/ieee802154/6lowpan.h line 246
Quoted 11 lines
net/ieee802154/6lowpan.h +11
-0+static inline bool lowpan_fetch_skb (struct sk_buff *skb, +void *data,const unsigned int len) +{ +if (unlikely (!pskb_may_pull (skb, len))) +return true; + +skb_copy_from_linear_data (skb, data, len); +skb_pull (skb, len); + +return false; +}Isn't the return value inverted here?
Quoted 4 lines
Nope, everything is right here, but I spent several minutes to get it... Probably using of standard intergers will be better here: return
-EINVALand return 0;
This was the old behaviour, we decide it to make it like this:
fail = ...
fail |= ....
if (fail)
...
We discussed that already at the linux-zigbee-devel mailinglist. I don't know what I should do now, on linux-zigbee-devel we decide it to this way, now we decide it in a other way...
Regards
Alex
Re: [PATCH net-next 3/6] 6lowpan: introduce lowpan_fetch_skb function
Quoted 11 lines · Alexander Aring
This was the old behaviour, we decide it to make it like this:
fail = ...
fail |= ....if (fail)
...We discussed that already at the linux-zigbee-devel mailinglist. I don't know what I should do now, on linux-zigbee-devel we decide it to this way, now we decide it in a other way...
Oh, I didn't know. Please just take my mail as a suggestion. If there already was a discussion and you had a consensus about that please just ignore my mails. :)
Thanks,
Hannes
Alexander Aring
maintainerRe: [PATCH net-next 3/6] 6lowpan: introduce lowpan_fetch_skb function
Hi Hannes,
Quoted 9 lines · Hannes Frederic Sowa
Quoted 8 lines · Alexander Aring
This was the old behaviour, we decide it to make it like this:
fail = ...
fail |= ....if (fail)
...
Quoted 8 lines
Quoted 3 lines
We discussed that already at the linux-zigbee-devel mailinglist. I don't know what I should do now, on linux-zigbee-devel we decide it to this way, now we decide it in a other way...
Oh, I didn't know. Please just take my mail as a suggestion. If there already was a discussion and you had a consensus about that please just ignore my mails. :)
This discussion was only with two persons.
So I am happy to hear some other opinions. :-)
Regards
Alex
PATCH v2 4/6 6lowpan: add function to uncompress multicast addr
In reply to a message not in the archiveAdd function to uncompress multicast address.
This function split the uncompress function for a multicast address in a seperate function.
To uncompress a multicast address is different than a other non-multicasts addresses according to rfc6282.
--- net/ieee802154/6lowpan.c | 78 ++++++++++++++++++++++++++++++++++++------------ 1 file changed, 59 insertions(+), 19 deletions(-)
net/ieee802154/6lowpan.c +59 -19
@@ -88,15 +88,6 @@ static const u8 lowpan_unc_llconf[] = {0x0f, 0x28, 0x22, 0x20};*/ static const u8 lowpan_unc_ctxconf[] = {0x00 ,0x88 ,0x82 ,0x80 }; -/* -* Uncompression of ctx-base -* 0 -> 0 bits from packet -* 1 -> 2 bytes from prefix - bunch of zeroes 5 from packet -* 2 -> 2 bytes from prefix - zeroes + 3 from packet -* 3 -> 2 bytes from prefix - infer 1 bytes from lladdr -*/ -static const u8 lowpan_unc_mxconf[] = {0x0f ,0x25 ,0x23 ,0x21 }; -/* Link local prefix */ static const u8 lowpan_llprefix[] = {0xfe ,0x80 };
@@ -240,6 +231,63 @@ lowpan_uncompress_addr(struct sk_buff *skb, struct in6_addr *ipaddr,return 0 ; } +/* Uncompress function for multicast destination address, +* when M bit is set. +*/ +static int +lowpan_uncompress_multicast_daddr (struct sk_buff *skb, +struct in6_addr *ipaddr, +const u8 dam) +{ +bool fail; + +switch (dam) { +case LOWPAN_IPHC_DAM_00 : +/* 00: 128 bits. The full address +* is carried in-line. +*/ + fail =lowpan_fetch_skb (skb, ipaddr->s6_addr,16 ); +break ; +case LOWPAN_IPHC_DAM_01 : +/* 01: 48 bits. The address takes +* the form ffXX::00XX:XXXX:XXXX. +*/ + ipaddr->s6_addr[0 ] =0xFF ; + fail =lowpan_fetch_skb (skb, &ipaddr->s6_addr[1 ],1 ); + fail |=lowpan_fetch_skb (skb, &ipaddr->s6_addr[11 ],5 ); +break ; +case LOWPAN_IPHC_DAM_10 : +/* 10: 32 bits. The address takes +* the form ffXX::00XX:XXXX. +*/ + ipaddr->s6_addr[0 ] =0xFF ; + fail =lowpan_fetch_skb (skb, &ipaddr->s6_addr[1 ],1 ); + fail |=lowpan_fetch_skb (skb, &ipaddr->s6_addr[13 ],3 ); +break ; +case LOWPAN_IPHC_DAM_11 : +/* 11: 8 bits. The address takes +* the form ff02::00XX. +*/ + ipaddr->s6_addr[0 ] =0xFF ; + ipaddr->s6_addr[1 ] =0x02 ; + fail =lowpan_fetch_skb (skb, &ipaddr->s6_addr[15 ],1 ); +break ; +default : +pr_debug ("DAM value has a wrong value: 0x%x\n" , dam); +return -EINVAL ; + } + +if (fail) { +pr_debug ("Failed to fetch skb data\n" ); +return -EIO ; + } + +pr_debug ("Reconstructed ipv6 multicast addr is:\n" ); +lowpan_raw_dump_inline (NULL ,NULL , ipaddr->s6_addr,16 ); + +return 0 ; +} +static void lowpan_compress_udp_header (u8 **hc06_ptr,struct sk_buff *skb) {
@@ -927,16 +975,8 @@ lowpan_process_data(struct sk_buff *skb)pr_debug ("dest: context-based mcast compression\n" );/* TODO: implement this */ }else { -u8 prefix[] = {0xff ,0x02 }; - -pr_debug ("dest: non context-based mcast compression\n" ); -if (0 < tmp && tmp <3 ) { -if (lowpan_fetch_skb_u8 (skb, &prefix[1 ])) - goto drop; - } - - err =lowpan_uncompress_addr (skb, &hdr.daddr, prefix, - lowpan_unc_mxconf[tmp],NULL ); + err =lowpan_uncompress_multicast_daddr ( + skb, &hdr.daddr, tmp);if (err) goto drop; }
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
PATCH v2 5/6 6lowpan: lowpan_uncompress_addr with address_mode
In reply to a message not in the archiveThis patch drop the pre and postcount calculation from the lowpan_uncompress_addr function.
We use instead a switch case over address_mode value, it's easier to understand what's going on there.
--- net/ieee802154/6lowpan.c | 144 +++++++++++++++++++++++++---------------------- net/ieee802154/6lowpan.h | 8 ++- 2 files changed, 82 insertions(+), 70 deletions(-)
net/ieee802154/6lowpan.c +77 -67
@@ -67,30 +67,6 @@ static const u8 lowpan_ttl_values[] = {0, 1, 64, 255};static LIST_HEAD (lowpan_devices); -/* -* Uncompression of linklocal: -* 0 -> 16 bytes from packet -* 1 -> 2 bytes from prefix - bunch of zeroes and 8 from packet -* 2 -> 2 bytes from prefix - zeroes + 2 from packet -* 3 -> 2 bytes from prefix - infer 8 bytes from lladdr -* -* NOTE: => the uncompress function does change 0xf to 0x10 -* NOTE: 0x00 => no-autoconfig => unspecified -*/ -static const u8 lowpan_unc_llconf[] = {0x0f ,0x28 ,0x22 ,0x20 }; - -/* -* Uncompression of ctx-based: -* 0 -> 0 bits from packet [unspecified / reserved] -* 1 -> 8 bytes from prefix - bunch of zeroes and 8 from packet -* 2 -> 8 bytes from prefix - zeroes + 2 from packet -* 3 -> 8 bytes from prefix - infer 8 bytes from lladdr -*/ -static const u8 lowpan_unc_ctxconf[] = {0x00 ,0x88 ,0x82 ,0x80 }; - -/* Link local prefix */ -static const u8 lowpan_llprefix[] = {0xfe ,0x80 }; -/* private device info */ struct lowpan_dev_info {struct net_device *real_dev;/* real WPAN device ptr */
@@ -182,50 +158,86 @@ lowpan_compress_addr_64(u8 **hc06_ptr, u8 shift, const struct in6_addr *ipaddr,return rol8 (val, shift); } -static void -lowpan_uip_ds6_set_addr_iid (struct in6_addr *ipaddr,unsigned char *lladdr) -{ -memcpy (&ipaddr->s6_addr[8 ], lladdr,IEEE802154_ADDR_LEN ); -/* second bit-flip (Universe/Local) is done according RFC2464 */ - ipaddr->s6_addr[8 ] ^=0x02 ; -} -/* -* Uncompress addresses based on a prefix and a postfix with zeroes in -* between. If the postfix is zero in length it will use the link address -* to configure the IP address (autoconf style). -* pref_post_count takes a byte where the first nibble specify prefix count -* and the second postfix count (NOTE: 15/0xf => 16 bytes copy). +* Uncompress address function for source and +* destination address(non-multicast). +* +* address_mode is sam value or dam value. */ static int -lowpan_uncompress_addr (struct sk_buff *skb,struct in6_addr *ipaddr, -u8 const *prefix,u8 pref_post_count,unsigned char *lladdr) +lowpan_uncompress_addr (struct sk_buff *skb, +struct in6_addr *ipaddr, +const u8 address_mode, +const struct ieee802154_addr *lladdr) { -u8 prefcount = pref_post_count >>4 ; -u8 postcount = pref_post_count &0x0f ; - -/* full nibble 15 => 16 */ - prefcount = (prefcount ==15 ?16 : prefcount); - postcount = (postcount ==15 ?16 : postcount); - -if (lladdr) -lowpan_raw_dump_inline (__func__,"linklocal address" , - lladdr,IEEE802154_ADDR_LEN ); -if (prefcount >0 ) -memcpy (ipaddr, prefix, prefcount); - -if (postcount >0 ) { -memcpy (&ipaddr->s6_addr[16 - postcount], skb->data, postcount); -skb_pull (skb, postcount); - }else if (prefcount >0 ) { -if (lladdr ==NULL ) +bool fail; + +switch (address_mode) { +case LOWPAN_IPHC_ADDR_00 : +/* for global link addresses */ + fail =lowpan_fetch_skb (skb, ipaddr->s6_addr,16 ); +break ; +case LOWPAN_IPHC_ADDR_01 : +/* fe:80::XXXX:XXXX:XXXX:XXXX */ + ipaddr->s6_addr[0 ] =0xFE ; + ipaddr->s6_addr[1 ] =0x80 ; + fail =lowpan_fetch_skb (skb, &ipaddr->s6_addr[8 ],8 ); +break ; +case LOWPAN_IPHC_ADDR_02 : +/* fe:80::ff:fe00:XXXX */ + ipaddr->s6_addr[0 ] =0xFE ; + ipaddr->s6_addr[1 ] =0x80 ; + ipaddr->s6_addr[11 ] =0xFF ; + ipaddr->s6_addr[12 ] =0xFE ; + fail =lowpan_fetch_skb (skb, &ipaddr->s6_addr[14 ],2 ); +break ; +case LOWPAN_IPHC_ADDR_03 : + fail = false; +switch (lladdr->addr_type) { +case IEEE802154_ADDR_LONG : +/* fe:80::XXXX:XXXX:XXXX:XXXX +* \_________________/ +* hwaddr +*/ + ipaddr->s6_addr[0 ] =0xFE ; + ipaddr->s6_addr[1 ] =0x80 ; +memcpy (&ipaddr->s6_addr[8 ], lladdr->hwaddr, +IEEE802154_ADDR_LEN ); +/* second bit-flip (Universe/Local) +* is done according RFC2464 +*/ + ipaddr->s6_addr[8 ] ^=0x02 ; +break ; +case IEEE802154_ADDR_SHORT : +/* fe:80::ff:fe00:XXXX +* \__/ +* short_addr +* +* Universe/Local bit is zero. +*/ + ipaddr->s6_addr[0 ] =0xFE ; + ipaddr->s6_addr[1 ] =0x80 ; + ipaddr->s6_addr[11 ] =0xFF ; + ipaddr->s6_addr[12 ] =0xFE ; +memcpy (&ipaddr->s6_addr[14 ], &lladdr->short_addr, +UIP_802154_SHORTADDR_LEN ); +break ; +default : +pr_debug ("Invalid addr_type set\n" );return -EINVAL ; + } +break ; +default : +pr_debug ("Invalid address mode value: 0x%x\n" , address_mode); +return -EINVAL ; + } -/* no IID based configuration if no prefix and no data */ -lowpan_uip_ds6_set_addr_iid (ipaddr, lladdr); +if (fail) { +pr_debug ("Failed to fetch skb data\n" ); +return -EIO ; } -pr_debug ("uncompressing %d + %d => " , prefcount, postcount); +pr_debug ("Reconstructed ipv6 addr is:\n" );lowpan_raw_dump_inline (NULL ,NULL , ipaddr->s6_addr,16 );return 0 ;
@@ -775,7 +787,7 @@ lowpan_process_data(struct sk_buff *skb) {struct ipv6hdr hdr = {};u8 tmp, iphc0, iphc1, num_context =0 ; -u8 *_saddr, *_daddr; +const struct ieee802154_addr *_saddr, *_daddr;int err; lowpan_raw_dump_table(__func__, "raw skb data dump", skb->data,
@@ -878,8 +890,8 @@ lowpan_process_data(struct sk_buff *skb)if (lowpan_fetch_skb_u8 (skb, &iphc1)) goto drop; - _saddr =mac_cb (skb)->sa.hwaddr; - _daddr =mac_cb (skb)->da.hwaddr; + _saddr = &mac_cb (skb)->sa; + _daddr = &mac_cb (skb)->da;pr_debug ("iphc0 = %02x, iphc1 = %02x\n" , iphc0, iphc1);
@@ -961,8 +973,7 @@ lowpan_process_data(struct sk_buff *skb)/* Source address uncompression */ pr_debug ("source address stateless compression\n" ); - err =lowpan_uncompress_addr (skb, &hdr.saddr, lowpan_llprefix, - lowpan_unc_llconf[tmp], skb->data); + err =lowpan_uncompress_addr (skb, &hdr.saddr, tmp, _saddr);if (err) goto drop;
@@ -982,8 +993,7 @@ lowpan_process_data(struct sk_buff *skb) } }else {pr_debug ("dest: stateless compression\n" ); - err =lowpan_uncompress_addr (skb, &hdr.daddr, lowpan_llprefix, - lowpan_unc_llconf[tmp], skb->data); + err =lowpan_uncompress_addr (skb, &hdr.daddr, tmp, _daddr);if (err) goto drop; }
net/ieee802154/6lowpan.h +5 -3
@@ -196,10 +196,12 @@/* Values of fields within the IPHC encoding second byte */ #define LOWPAN_IPHC_CID 0x80 +#define LOWPAN_IPHC_ADDR_00 0x00 +#define LOWPAN_IPHC_ADDR_01 0x01 +#define LOWPAN_IPHC_ADDR_02 0x02 +#define LOWPAN_IPHC_ADDR_03 0x03 +#define LOWPAN_IPHC_SAC 0x40 -#define LOWPAN_IPHC_SAM_00 0x00 -#define LOWPAN_IPHC_SAM_01 0x10 -#define LOWPAN_IPHC_SAM_10 0x20#define LOWPAN_IPHC_SAM 0x30#define LOWPAN_IPHC_SAM_BIT 4
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
PATCH v2 6/6 6lowpan: handle context based source address
In reply to a message not in the archiveHandle context based address when a unspecific address is specified. For other context based address we print a warning and drop the packet currently because we don't support it right now.
--- net/ieee802154/6lowpan.c | 48 +++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 45 insertions(+), 3 deletions(-)
net/ieee802154/6lowpan.c +45 -3
@@ -243,6 +243,39 @@ lowpan_uncompress_addr(struct sk_buff *skb,return 0 ; } +/* Uncompress address function for source context +* based address(non-multicast). +*/ +static int +lowpan_uncompress_context_based_src_addr (struct sk_buff *skb, +struct in6_addr *ipaddr, +const u8 sam) +{ +switch (sam) { +case LOWPAN_IPHC_ADDR_00 : +/* unspec address :: +* Do nothing, address is already :: +*/ +break ; +case LOWPAN_IPHC_ADDR_01 : +/* TODO */ +case LOWPAN_IPHC_ADDR_02 : +/* TODO */ +case LOWPAN_IPHC_ADDR_03 : +/* TODO */ +netdev_warn (skb->dev,"SAM value 0x%x not supported\n" , sam); +return -EINVAL ; +default : +pr_debug ("Invalid sam value: 0x%x\n" , sam); +return -EINVAL ; + } + +pr_debug ("Reconstructed context based ipv6 src addr is:\n" ); +lowpan_raw_dump_inline (NULL ,NULL , ipaddr->s6_addr,16 ); + +return 0 ; +} +/* Uncompress function for multicast destination address, * when M bit is set. */
@@ -971,9 +1004,18 @@ lowpan_process_data(struct sk_buff *skb)/* Extract SAM to the tmp variable */ tmp = ((iphc1 &LOWPAN_IPHC_SAM ) >>LOWPAN_IPHC_SAM_BIT ) &0x03 ; -/* Source address uncompression */ -pr_debug ("source address stateless compression\n" ); - err =lowpan_uncompress_addr (skb, &hdr.saddr, tmp, _saddr); +if (iphc1 &LOWPAN_IPHC_SAC ) { +/* Source address context based uncompression */ +pr_debug ("SAC bit is set. Handle context based source address.\n" ); + err =lowpan_uncompress_context_based_src_addr ( + skb, &hdr.saddr, tmp); + }else { +/* Source address uncompression */ +pr_debug ("source address stateless compression\n" ); + err =lowpan_uncompress_addr (skb, &hdr.saddr, tmp, _saddr); + } + +/* Check on error of previous branch */ if (err) goto drop;
Signature · 9 lines
1.8.3.3 ------------------------------------------------------------------------------ Get 100% visibility into Java/.NET code with AppDynamics Lite! It's a free troubleshooting tool designed for production. Get down to code-level detail for bottlenecks, with <2% overhead. Download for free and get started troubleshooting in minutes. http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
Quoted 7 lines · Alexander Aring
The current implementation to uncompress addresses in a 6lowpan header is completely broken.
This patch series fixes the parsing of addresses in a 6lowpan header. It contains a major rewrite of the uncompress address function to parse the address in a correct way.
Could you please describe in a few words how have you tested the changes?
Small cosmetic hint: lowpan_raw_dump_inline() already has an argument to print debug message, so there is no need to add extra pr_debug calls before it to print static text.
Alex
Quoted 19 lines
Changes since v2:
- Add tags for net-next
- Change commit msg in Patch 1/6 that this patch depends for the following patchesAlexander Aring (5):
6lowpan: init ipv6hdr buffer to zero 6lowpan: introducelowpan_fetch_skbfunction 6lowpan: add function to uncompress multicast addr 6lowpan:lowpan_uncompress_addrwithaddress_mode6lowpan: handle context based source addressDavid Hauweele (1):
6lowpan: Fix fragmentation with link-local compressed addressesnet/ieee802154/6lowpan.c | 284 +++++++++++++++++++++++++++++++---------------- net/ieee802154/6lowpan.h | 20 +++- 2 files changed, 203 insertions(+), 101 deletions(-)
Alexander Aring
maintainerHi Alex,
Quoted 11 lines · Alexander Smirnov
Quoted 7 lines · Alexander Aring
The current implementation to uncompress addresses in a 6lowpan header is completely broken.
This patch series fixes the parsing of addresses in a 6lowpan header. It contains a major rewrite of the uncompress address function to parse the address in a correct way.
Could you please describe in a few words how have you tested the changes?
I test this with a ravenusbstick and the jackdaw firmware. This is a usb stick with a contiki stack which offers a ipv6 interface under linux. It still uses the 6LoWPAN contiki stack.
On the other side I have a beaglebone device with the current net-next 6LoWPAN stack.
I add several addresses to this linux device to catch all cases (except short address) in the uncompression function.
With a ping6 $ADDRESS and wireshark on the usb stick I see the outcomming 6lowpan packets. If I get a correct reply with the used address it seems that the uncompression works.
I am thinking to implement some test cases to test all uncompression of all address-cases. This patch series was tested manually.
A wireshark on the beaglebone doesn't work at the moment. I get a nullpointer dereference in the 6LoWPAN stack. I suppose this is why the 6LoWPAN Stack copies sk_buffs and free the old one. This is a wrong behaviour because the caller of a function has the old sk_buff which is freed.
I need some time to drop the skb_clone functions.... and then I will check wireshark.
If wireshark works I don't see the 6LoWPAN Header anyway, but I can see if the ipv6 header is reconstructed correctly.
Quoted 4 lines
Small cosmetic hint:
lowpan_raw_dump_inline()already has an argument to print debug message, so there is no need to add extrapr_debugcalls before it to print static text.
ok, I will change it.
Regards
Alex