diff --git a/cc2520.h b/cc2520.h index 01a0b5b..4c2ac02 100644 --- a/cc2520.h +++ b/cc2520.h @@ -108,6 +108,7 @@ struct cc2520_gpio_state { unsigned int sfd_irq; }; +// DEPRECATED struct cc2520_state { // Hardware struct cc2520_gpio_state gpios; @@ -220,8 +221,6 @@ typedef union cc2520_fifopctrl { } f; } cc2520_fifopctrl_t; - - typedef union cc2520_frmfilt0 { u8 value; struct { @@ -261,8 +260,6 @@ typedef union cc2520_rxctrl { u8 value; } cc2520_rxctrl_t; - - typedef union cc2520_fsctrl { u8 value; } cc2520_fsctrl_t; diff --git a/interface.c b/interface.c index 78204cd..4cc92b3 100644 --- a/interface.c +++ b/interface.c @@ -12,6 +12,7 @@ #include "cc2520.h" #include "interface.h" #include "radio.h" +#include "sack.h" struct cc2520_interface *interface_bottom; @@ -44,6 +45,7 @@ static void cc2520_interface_rx_done(u8 *buf, u8 len); static void interface_ioctl_set_channel(struct cc2520_set_channel_data *data); static void interface_ioctl_set_address(struct cc2520_set_address_data *data); static void interface_ioctl_set_txpower(struct cc2520_set_txpower_data *data); +static void interface_ioctl_set_ack(struct cc2520_set_ack_data *data); static long interface_ioctl(struct file *file, unsigned int ioctl_num, @@ -156,6 +158,9 @@ static long interface_ioctl(struct file *file, case CC2520_IO_RADIO_SET_TXPOWER: interface_ioctl_set_txpower((struct cc2520_set_txpower_data *) ioctl_param); break; + case CC2520_IO_RADIO_SET_ACK: + interface_ioctl_set_ack((struct cc2520_set_ack_data*) ioctl_param); + break; } return 0; @@ -220,6 +225,21 @@ static void interface_ioctl_set_txpower(struct cc2520_set_txpower_data *data) cc2520_radio_set_txpower(ldata.txpower); } +static void interface_ioctl_set_ack(struct cc2520_set_ack_data *data) +{ + int result; + struct cc2520_set_ack_data ldata; + result = copy_from_user(&ldata, data, sizeof(struct cc2520_set_ack_data)); + + if (result) { + printk(KERN_INFO "[cc2520] - an error occurred setting soft ack\n"); + return; + } + + printk(KERN_INFO "[cc2520] - setting softack timeout\n"); + cc2520_sack_set_timeout(ldata.timeout); +} + ///////////////// // init/free /////////////////// diff --git a/ioctl.h b/ioctl.h index 9511da3..4c37474 100644 --- a/ioctl.h +++ b/ioctl.h @@ -6,6 +6,7 @@ #include typedef uint8_t u8; typedef uint16_t u16; +typedef uint32_t u32; typedef uint64_t u64; #endif @@ -19,6 +20,10 @@ struct cc2520_set_address_data { u16 pan_id; }; +struct cc2520_set_ack_data { + u32 timeout; +}; + // Possible TX Powers: #define CC2520_TXPOWER_5DBM 0xF7 #define CC2520_TXPOWER_3DBM 0xF2 @@ -39,4 +44,5 @@ struct cc2520_set_txpower_data { #define CC2520_IO_RADIO_OFF _IO(BASE, 2) #define CC2520_IO_RADIO_SET_CHANNEL _IOW(BASE, 3, struct cc2520_set_channel_data) #define CC2520_IO_RADIO_SET_ADDRESS _IOW(BASE, 4, struct cc2520_set_address_data) -#define CC2520_IO_RADIO_SET_TXPOWER _IOW(BASE, 5, struct cc2520_set_txpower_data) \ No newline at end of file +#define CC2520_IO_RADIO_SET_TXPOWER _IOW(BASE, 5, struct cc2520_set_txpower_data) +#define CC2520_IO_RADIO_SET_ACK _IOW(BASE, 6, struct cc2520_set_ack_data) \ No newline at end of file diff --git a/sack.c b/sack.c index 9fd79d1..514d652 100644 --- a/sack.c +++ b/sack.c @@ -14,6 +14,7 @@ static int cc2520_sack_tx(u8 * buf, u8 len); static void cc2520_sack_tx_done(u8 status); static void cc2520_sack_rx_done(u8 *buf, u8 len); static enum hrtimer_restart cc2520_sack_timer_cb(struct hrtimer *timer); +static void cc2520_sack_start_timer(void); // Two pieces to software acknowledgements: // 1 - Taking packets we're transmitting, setting an ACK flag @@ -33,7 +34,7 @@ static enum hrtimer_restart cc2520_sack_timer_cb(struct hrtimer *timer); static u8 *ack_buf; static u8 *cur_tx_buf; static struct hrtimer timeout_timer; - +static int ack_timeout; //in microseconds enum cc2520_sack_state_enum { CC2520_SACK_IDLE, @@ -47,8 +48,6 @@ static spinlock_t sack_sl; int cc2520_sack_init() { - ktime_t kt; - sack_top->tx = cc2520_sack_tx; sack_bottom->tx_done = cc2520_sack_tx_done; sack_bottom->rx_done = cc2520_sack_rx_done; @@ -63,13 +62,9 @@ int cc2520_sack_init() goto error; } - // Create a 100uS time period. - kt=ktime_set(10,100000); - hrtimer_init(&timeout_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); timeout_timer.function = &cc2520_sack_timer_cb; // callback - //hrtimer_start(&timeout_timer, kt, HRTIMER_MODE_REL); - + spin_lock_init(&sack_sl); sack_state = CC2520_SACK_IDLE; @@ -102,6 +97,19 @@ void cc2520_sack_free() hrtimer_cancel(&timeout_timer); } +void cc2520_sack_set_timeout(int timeout) +{ + ack_timeout = timeout; +} + +static void cc2520_sack_start_timer() +{ + // Create a 100uS time period. + ktime_t kt; + kt=ktime_set(10,100000); + hrtimer_start(&timeout_timer, kt, HRTIMER_MODE_REL); +} + static int cc2520_sack_tx(u8 * buf, u8 len) { spin_lock(&sack_sl); @@ -116,7 +124,7 @@ static int cc2520_sack_tx(u8 * buf, u8 len) spin_unlock(&sack_sl); memcpy(cur_tx_buf, buf, len); - + return sack_bottom->tx(cur_tx_buf, len); } @@ -127,14 +135,16 @@ static void cc2520_sack_tx_done(u8 status) if (cc2520_packet_requires_ack_wait(cur_tx_buf)) { printk(KERN_INFO "[cc2520] - Entering TX wait state.\n"); sack_state = CC2520_SACK_TX_WAIT; - //spin_unlock(&sack_sl); + spin_unlock(&sack_sl); + + + // Start hr timer. } - //else { - // do we need to wait for an ACK + else { sack_state = CC2520_SACK_IDLE; spin_unlock(&sack_sl); sack_top->tx_done(status); - //} + } } else if (sack_state == CC2520_SACK_TX_ACK) { sack_state = CC2520_SACK_IDLE; diff --git a/sack.h b/sack.h index 1d98ee9..b91ced0 100644 --- a/sack.h +++ b/sack.h @@ -8,5 +8,6 @@ extern struct cc2520_interface *sack_bottom; int cc2520_sack_init(void); void cc2520_sack_free(void); +void cc2520_sack_set_timeout(int timeout); #endif \ No newline at end of file