|
From: Mats F. <ma...@us...> - 2001-05-18 07:05:04
|
The following file was modified in linux/drivers/char/bluetooth:
Name Old version New version Comment
---- ----------- ----------- -------
bcsp_sequence.c 1.3 1.4=20=20=20=20=20=20=20=20=20=20=20=20=20
The accompanying log:
Rewrote the resend procedures
The diff of the modified file(s):
--- bcsp_sequence.c 2001/05/17 15:55:00 1.3
+++ bcsp_sequence.c 2001/05/18 07:05:03 1.4
@@ -47,6 +47,7 @@
#include <linux/bluetooth/bcsp.h>
#include <linux/interrupt.h>
#include <linux/bluetooth/sysdep-2.1.h>
+#include <linux/bluetooth/bcsp_debug.h>
=20
/****************** CONSTANT AND MACRO SECTION ***************************=
***/
=20
@@ -56,6 +57,9 @@
#define D(fmt...)
#endif
=20
+#define WINSIZE 7
+#define SEQUENCE_TIMEOUT HZ
+
/****************** TYPE DEFINITION SECTION ******************************=
***/
=20
typedef struct resend_buf {
@@ -68,20 +72,31 @@
/****************** LOCAL FUNCTION DECLARATION SECTION *******************=
***/
=20
static void sequence_resend(void);
+static void send_ack(void);
=20
+static void start_resend_timer(void);
+static void release_resend_timer(void);
+
/****************** GLOBAL VARIABLE DECLARATION SECTION ******************=
***/
=20
/****************** LOCAL VARIABLE DECLARATION SECTION *******************=
***/
=20
static struct tq_struct resend_data_task;
+static struct tq_struct send_ack_task;
=20
-static u8 seq_nbr =3D 0;
-static u8 ack_nbr =3D 0;
+static u8 txseq =3D 0;
+static u8 txack =3D 0;
+static u8 rxack =3D 0;
+static u8 expected_rxseq =3D 0;
=20
-static u8 remote_ack_nbr =3D 0;
+static u8 winspace =3D WINSIZE;
=20
static u32 got_packet =3D FALSE;
=20
+static struct timer_list resend_timer;
+
+static u8 resend_timer_active =3D FALSE;
+
static struct resend_buf resend_buffer[8];
=20
/****************** FUNCTION DEFINITION SECTION **************************=
***/
@@ -90,6 +105,9 @@
{
resend_data_task.routine =3D (void*)sequence_resend;
resend_data_task.data =3D NULL;
+
+ send_ack_task.routine =3D (void*)send_ack;
+ send_ack_task.data =3D NULL;
}
=20
s32
@@ -100,12 +118,28 @@
bcsp_syncronized();
}
=20=09
- ack_nbr =3D BCSP_GET_SEQ(bcsp) + 1;
- /* Do we realy need to do this ? */
- //remote_ack_nbr =3D BCSP_GET_ACK(bcsp);
- send_txack(ack_nbr);
+ if (expected_rxseq =3D=3D BCSP_GET_SEQ(bcsp)) {
=20
+ cli();
+ txack =3D (BCSP_GET_SEQ(bcsp) + 1) % 8;
+ expected_rxseq =3D (expected_rxseq + 1) % 8;
+ sti();
+
bcsp_receive_top(bcsp->payload, bcsp->payload_length, bcsp->identifier);
+=09=09
+ }
+
+/* FIXME: Do we need a task_queue for sending the ack packets ? */
+#if 0
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
+ queue_task(&send_ack_task, &tq_immediate);
+#else
+ queue_task(&send_ack_task, &tq_immediate);
+ mark_bh(IMMEDIATE_BH);
+#endif
+#endif=09=09
+ send_ack();
+=09
return 0;
}
=20
@@ -115,73 +149,128 @@
{
struct bcsp bcsp;
=20=09
+ if (winspace > 0) {
init_bcsp_packet(&bcsp);
=20=09
bcsp.identifier =3D chn;
=20
BCSP_SET_PROTOCOL_TYPE(&bcsp, BCSP_RELIABLE);
=20=09
- BCSP_SET_SEQ(&bcsp, seq_nbr);
+ BCSP_SET_SEQ(&bcsp, txseq);
=20
- BCSP_SET_ACK(&bcsp, ack_nbr);
+ BCSP_SET_ACK(&bcsp, txack);
=20=09
bcsp.payload =3D data;
bcsp.payload_length =3D len;
=20
- memcpy(resend_buffer[seq_nbr].data, data, len);
- resend_buffer[seq_nbr].len =3D len;
- resend_buffer[seq_nbr].chn =3D chn;
+ memcpy(resend_buffer[txseq].data, data, len);
+ resend_buffer[txseq].len =3D len;
+ resend_buffer[txseq].chn =3D chn;
=20
- seq_nbr =3D (seq_nbr + 1) % 8;
+ txseq =3D (txseq + 1) % 8;
+ winspace--;
+
+ D(__FUNCTION__": winspace:%d, txreq:%d\n", winspace, txseq);
+=09=09
+ if (resend_timer_active) {
+ release_resend_timer();
+ }
+ start_resend_timer();
+ } else {
+ printk(__FUNCTION__": winspace =3D 0\n");
+ return 0;
+ }
=20=09=09
return mux_send(&bcsp);
}
=20
void
-signal_rxack(u8 ack)
+signal_rxack(u8 new_ack)
{
- static u8 last_ack =3D 0;
=20
- remote_ack_nbr =3D ack;
+ D(__FUNCTION__": Got rxack:%d\n", new_ack);
=20=09
- if (last_ack =3D=3D ack) {
- printk(__FUNCTION__ ": Got incorrect ack:%d, seq_nbr:%d\n", ack, seq_nbr=
);
+ if ((rxack =3D=3D new_ack) && !(rxack =3D=3D txseq)) {
+ printk(__FUNCTION__": Got incorrect new_ack:%d, seq_nbr:%d\n", new_ack,=
txseq);
+=09=09
#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
queue_task(&resend_data_task, &tq_scheduler);
#else
queue_task(&resend_data_task, &tq_immediate);
mark_bh(IMMEDIATE_BH);
#endif
+ } else if (rxack < new_ack) {
+ D(__FUNCTION__": winspace before:%d\n", winspace);
+ winspace +=3D new_ack - rxack;
+ D(__FUNCTION__": winspace after:%d\n", winspace);
} else {
- D(__FUNCTION__ ": Got rx ack:%d\n", ack);
+ D(__FUNCTION__": winspace before:%d\n", winspace);
+ winspace +=3D (WINSIZE - rxack) + new_ack + 1;
+ D(__FUNCTION__": winspace after:%d\n", winspace);
}
- last_ack =3D ack;
+
+=09
+ rxack =3D new_ack;
+
+ if (winspace =3D=3D WINSIZE) {
+ release_resend_timer();
}
+}
=20
-void sequence_resend(void)
+void
+sequence_resend(void)
{
struct bcsp bcsp;
+ u8 resend_cnt =3D rxack;
=20
- while (remote_ack_nbr !=3D seq_nbr) {
+ while (resend_cnt !=3D txseq) {
=20=09
- printk(__FUNCTION__ ": Resending seq_nbr:%d, last sent was %d\n", remote=
_ack_nbr, seq_nbr);
+ printk(__FUNCTION__": Resending with seq_nbr:%d, last ack was %d, cur se=
q_nbr:%d\n", resend_cnt, rxack, txseq);
=20=09=09
init_bcsp_packet(&bcsp);
=20=09=09
- bcsp.identifier =3D resend_buffer[remote_ack_nbr].chn;
+ bcsp.identifier =3D resend_buffer[resend_cnt].chn;
=20=09=09
BCSP_SET_PROTOCOL_TYPE(&bcsp, BCSP_RELIABLE);
=20=09=09
- BCSP_SET_SEQ(&bcsp, remote_ack_nbr);
+ BCSP_SET_SEQ(&bcsp, resend_cnt);
=20=09=09
- BCSP_SET_ACK(&bcsp, ack_nbr);
+ BCSP_SET_ACK(&bcsp, txack);
=20=09=09
- bcsp.payload =3D resend_buffer[remote_ack_nbr].data;
- bcsp.payload_length =3D resend_buffer[remote_ack_nbr].len;
+ bcsp.payload =3D resend_buffer[resend_cnt].data;
+ bcsp.payload_length =3D resend_buffer[resend_cnt].len;
=20=09=09
mux_send(&bcsp);
- remote_ack_nbr =3D (remote_ack_nbr + 1) % 8;
+ resend_cnt =3D (resend_cnt + 1) % 8;
+ }
+
+ start_resend_timer();
+}
+
+void
+send_ack(void)
+{
+ send_txack(txack);
+}
+
+void
+start_resend_timer(void)
+{
+ init_timer(&resend_timer);
+ resend_timer.function =3D (void*)sequence_resend;
+ resend_timer.data =3D 0;
+ resend_timer.expires =3D jiffies + SEQUENCE_TIMEOUT;
+
+ resend_timer_active =3D TRUE;
+=09
+ add_timer(&resend_timer);
}
+
+void
+release_resend_timer(void)
+{
+ resend_timer_active =3D FALSE;
+ del_timer(&resend_timer);
}
=20
/****************** END OF FILE sequence.c *******************************=
***/
|