1
0
mirror of https://github.com/RIOT-OS/RIOT.git synced 2024-12-29 04:50:03 +01:00
RIOT/sys/net/ieee802154/ieee802154_frame.c
Milan Babel db1fc96ffe added driver for cc2420
also added cc2420 to transceiver and added cc2420 shell commands
2013-06-06 08:35:17 +02:00

226 lines
6.8 KiB
C

#include "ieee802154_frame.h"
//uint8_t mac_buf[IEEE_802154_HDR_LEN + IEEE_802154_PAYLOAD_LEN];
uint8_t ieee802154_hdr_ptr;
uint8_t ieee802154_payload_ptr;
uint16_t ieee802154_payload_len;
uint8_t init_802154_frame(ieee802154_frame_t *frame, uint8_t *buf){
/* Frame Control Field - 802.15.4 - 2006 - 7.2.1.1 */
uint8_t index = 0;
buf[index] = ((frame->fcf.dest_addr_m << 2) |
(frame->fcf.frame_ver << 4) |
(frame->fcf.src_addr_m << 6));
index++;
buf[index] = ((frame->fcf.frame_type) |
(frame->fcf.sec_enb << 3) |
(frame->fcf.frame_pend << 4) |
(frame->fcf.ack_req << 5) |
(frame->fcf.panid_comp << 6));
index++;
/* Sequence Number - 802.15.4 - 2006 - 7.2.1.2 */
buf[index] = frame->seq_nr;
index++;
/* Destination PAN Identifier - 802.15.4 - 2006 - 7.2.1.3 */
if(frame->fcf.dest_addr_m == 0x02 || frame->fcf.dest_addr_m == 0x03){
buf[index] = ((frame->dest_pan_id >> 8) & 0xff);
buf[index+1] = (frame->dest_pan_id & 0xff);
}
index += 2;
/* Destination Address - 802.15.4 - 2006 - 7.2.1.4 */
if(frame->fcf.dest_addr_m == 0x02){
buf[index] = frame->dest_addr[0];
buf[index+1] = frame->dest_addr[1];
index += 2;
} else if(frame->fcf.dest_addr_m == 0x03){
buf[index] = frame->dest_addr[0];
buf[index+1] = frame->dest_addr[1];
buf[index+2] = frame->dest_addr[2];
buf[index+3] = frame->dest_addr[3];
buf[index+4] = frame->dest_addr[4];
buf[index+5] = frame->dest_addr[5];
buf[index+6] = frame->dest_addr[6];
buf[index+7] = frame->dest_addr[7];
index += 8;
}
/* Source PAN Identifier - 802.15.4 - 2006 - 7.2.1.5 */
if(!(frame->fcf.panid_comp & 0x01)){
if(frame->fcf.src_addr_m == 0x02 || frame->fcf.src_addr_m == 0x03){
buf[index] = ((frame->src_pan_id >> 8) & 0xff);
buf[index+1] = (frame->src_pan_id & 0xff);
index += 2;
}
}
/* Source Address field - 802.15.4 - 2006 - 7.2.1.6 */
if(frame->fcf.src_addr_m == 0x02){
buf[index] = frame->src_addr[0];
buf[index+1] = frame->src_addr[1];
index += 2;
} else if(frame->fcf.src_addr_m == 0x03){
buf[index] = frame->src_addr[0];
buf[index+1] = frame->src_addr[1];
buf[index+2] = frame->src_addr[2];
buf[index+3] = frame->src_addr[3];
buf[index+4] = frame->src_addr[4];
buf[index+5] = frame->src_addr[5];
buf[index+6] = frame->src_addr[6];
buf[index+7] = frame->src_addr[7];
index += 8;
}
return index;
}
/** 2 1 2 VAR 2 VAR
* -------------------------------------------
* | FCF | DSN | DPID | DAD | SPID | SAD |
* -------------------------------------------
*/
uint8_t get_802154_hdr_len(ieee802154_frame_t *frame){
uint8_t len = 0;
if(frame->fcf.dest_addr_m == 0x02){
len += 2;
} else if(frame->fcf.dest_addr_m == 0x03){
len += 8;
}
if(frame->fcf.src_addr_m == 0x02){
len += 2;
} else if(frame->fcf.src_addr_m == 0x03){
len += 8;
}
if((frame->fcf.dest_addr_m == 0x02) || (frame->fcf.dest_addr_m == 0x03)){
len += 2;
}
if((frame->fcf.src_addr_m == 0x02) || (frame->fcf.src_addr_m == 0x03)){
len += 2;
}
/* if src pan id == dest pan id set compression bit */
if(frame->src_pan_id == frame->dest_pan_id){
frame->fcf.panid_comp = 1;
len -= 2;
}
/* (DPID + DAD + SPID + SAD) + (FCF + DSN) */
return (len + 3);
}
uint8_t read_802154_frame(uint8_t *buf, ieee802154_frame_t *frame, uint8_t len){
uint8_t index = 0;
uint8_t hdrlen;
frame->fcf.dest_addr_m = (buf[index] >> 2) & 0x03;
frame->fcf.frame_ver = (buf[index] >> 4) & 0x03;
frame->fcf.src_addr_m = (buf[index] >> 6) & 0x03;
index++;
frame->fcf.frame_type = (buf[index]) & 0x07;
frame->fcf.sec_enb = (buf[index] >> 3) & 0x01;
frame->fcf.frame_pend = (buf[index] >> 4) & 0x01;
frame->fcf.ack_req = (buf[index] >> 5) & 0x01;
frame->fcf.panid_comp = (buf[index] >> 6) & 0x01;
//print_802154_fcf_frame(frame);
index++;
frame->seq_nr = buf[index];
index++;
frame->dest_pan_id = (((uint16_t)buf[index]) << 8) | buf[index+1];
index += 2;
switch(frame->fcf.dest_addr_m){
case(0):{
printf("fcf.dest_addr_m: pan identifier/address fields empty\n");
break;
}
case(2):{
frame->dest_addr[0] = buf[index];
frame->dest_addr[1] = buf[index+1];
index += 2;
break;
}
case(3):{
frame->dest_addr[0] = buf[index];
frame->dest_addr[1] = buf[index+1];
frame->dest_addr[2] = buf[index+2];
frame->dest_addr[3] = buf[index+3];
frame->dest_addr[4] = buf[index+4];
frame->dest_addr[5] = buf[index+5];
frame->dest_addr[6] = buf[index+6];
frame->dest_addr[7] = buf[index+7];
index += 8;
break;
}
}
if(!(frame->fcf.panid_comp == 1)){
frame->src_pan_id = (((uint16_t)buf[index]) << 8) | buf[index+1];
index += 2;
}
switch(frame->fcf.src_addr_m){
case(0):{
printf("fcf.src_addr_m: pan identifier/address fields empty\n");
break;
}
case(2):{
frame->src_addr[0] = buf[index];
frame->src_addr[1] = buf[index+1];
index += 2;
break;
}
case(3):{
frame->src_addr[0] = buf[index];
frame->src_addr[1] = buf[index+1];
frame->src_addr[2] = buf[index+2];
frame->src_addr[3] = buf[index+3];
frame->src_addr[4] = buf[index+4];
frame->src_addr[5] = buf[index+5];
frame->src_addr[6] = buf[index+6];
frame->src_addr[7] = buf[index+7];
index += 8;
break;
}
}
frame->payload = (buf + index);
hdrlen = index;
frame->payload_len = (len - hdrlen);
return hdrlen;
}
void print_802154_fcf_frame(ieee802154_frame_t *frame){
printf("frame type: %02x\n"
"security enabled: %02x\n"
"frame pending: %02x\n"
"ack requested: %02x\n"
"pan id compression: %02x\n"
"destination address mode: %02x\n"
"frame version: %02x\n"
"source address mode: %02x\n",
frame->fcf.frame_type,
frame->fcf.sec_enb,
frame->fcf.frame_pend,
frame->fcf.ack_req,
frame->fcf.panid_comp,
frame->fcf.dest_addr_m,
frame->fcf.frame_ver,
frame->fcf.src_addr_m);
}