资源简介
自己编的程序,利用所学数据链路层原理,自己设计一个滑动窗口协议并在仿真环境下编程实现有噪音信道环境下两站点之间无差错双工通信。信道模型为8000bps 全双工卫星信道,信道传播时延270 毫秒,信道误码率为10-5,信道提供字节流传输服务,网络层分组长度在240~256字节范围。通过该实验,进一步巩固和深刻理解数据链路层的误码检测的CRC 校验技术,以及滑动窗口的工作机理。滑动窗口机制的两个主要目标:(1) 实现有噪音信道环境下的无差错传输;(2)充分利用传输信道的带宽。在程序能够稳定运行并成功实现第一个目标之后,运行程序并检查在信道没有误码和存在误码两种情况下的信道利用率。
代码片段和文件信息
#include
#include
#include “protocol.h“
#define MAX_SEQ 15
#define NR_BUFS ((MAX_SEQ+1)/2)
#define DATA_TIMER 3000 //帧超时时间间隔
#define ACK_TIMER 240 //ack的超时间隔
struct frame {
unsigned char kind;
unsigned char ack;
unsigned char seq;
unsigned char data[PKT_LEN];
unsigned int padding;
};
int no_nak=1; //标志是否已经发送过nak
static int phl_ready = 0;
unsigned char oldest_frame=MAX_SEQ+1;
static int between(unsigned char aunsigned char bunsigned char c)
//窗口函数,判断帧号(ack号)是否在窗口内
{
if(((a<=b)&&(b return 1;
else
return 0;
}
static void put_frame(unsigned char *frame int len)//加入校验和crc
{
*(unsigned int *)(frame + len) = crc32(frame len);
send_frame(frame len + 4);
phl_ready = 0;
}
static void send_data_frame(unsigned char fkunsigned char frame_nrunsigned char frame_expectedunsigned char buffer[NR_BUFS][PKT_LEN])
{//发送数据帧,或ack,或nak
struct frame s;
s.kind = fk;
s.seq = frame_nr;
s.ack = (frame_expected + MAX_SEQ) % (MAX_SEQ + 1);
if(fk==frame_DATA)
{
memcpy(s.data buffer[frame_nr % NR_BUFS] PKT_LEN);//复制分组到帧内
dbg_frame(“Send DATA %d %d ID %d\n“ s.seq s.ack *(short *)s.data);
put_frame((unsigned char *)&s 3 + PKT_LEN); //加入校验和
start_timer(frame_nr%NR_BUFS DATA_TIMER); //启动定时器
}
else if(fk == frame_NAK)
{
no_nak=0; //下一次不再发送nak
put_frame((unsigned char *)&s 3);
}
else if(fk == frame_ACK)
{
dbg_frame(“Send ACK %d\n“ s.ack);
put_frame((unsigned char *)&s 3);
}
phl_ready = 0;
stop_ack_timer(); //没有必要启动ack定时器
}
void main(int argc char **argv)
{
int event arg;
struct frame f;
int len = 0;
int i;
static unsigned char ack_expected=0 next_frame_to_send=0;
static unsigned char frame_expected=0 too_far=NR_BUFS;
static unsigned char nbuffered;
int arrived[NR_BUFS];
static unsigned char out_buf[NR_BUFS][PKT_LEN] in_buf[NR_BUFS][PKT_LEN];
protocol_init(argc argv);
lprintf(“Designed by 成贺睿&魏娜 build: “ __DATE__“ “__TIME__“\n“);
for(i = 0; i < NR_BUFS; i++) //标记接收方的缓冲区是满还是空
arrived[i]=0;
enable_network_layer();
while(1)
{
event = wait_for_event(&arg);
switch (event)
{
case NETWORK_layer_READY:
nbuffered++; //发送却未被确认的帧数目++
get_packet(out_buf[next_frame_to_send % NR_BUFS]);//得到分组存入缓冲区内
send_data_frame(frame_DATAnext_frame_to_sendframe_expectedout_buf);
next_frame_to_send=(next_frame_to_send + 1) % ( MAX_SEQ + 1);
break;
case PHYSICAL_layer_READY:
phl_ready = 1;
break;
case frame_RECEIVED:
len = recv_frame((unsigned char *)&f sizeof f);
if (len < 5 || crc32((unsigned char *)&f len) != 0)
{ //校验和出错,就发送nak请求重传
if(no_nak=
属性 大小 日期 时间 名称
----------- --------- ---------- ----- ----
文件 3969 2009-11-28 22:25 Selective\datali
文件 3942 2009-11-28 22:25 Selective\datali
文件 5282 2009-11-28 18:23 Selective\datali
文件 3476 2009-10-19 16:46 Selective\datali
文件 524 2009-10-16 10:23 Selective\datali
文件 176222 2009-11-28 19:00 Selective\datali
文件 518 2009-10-16 12:34 Selective\datali
文件 189268 2009-11-28 19:00 Selective\datali
文件 50176 2009-11-28 19:29 Selective\datali
文件 48640 2009-11-28 19:29 Selective\datali
文件 427008 2009-11-28 19:00 Selective\datali
文件 250 2009-11-28 19:00 Selective\datali
文件 11396 2009-11-28 19:00 Selective\Debug\datali
文件 184028 2009-11-28 19:00 Selective\Debug\datali
文件 41984 2009-11-28 19:00 Selective\Debug\vc60.idb
文件 53248 2009-11-28 19:00 Selective\Debug\vc60.pdb
文件 283 2007-12-02 10:47 Selective\jiangTime.swf
文件 94208 2009-10-19 22:57 Selective\Protocol.dll
文件 1894 2009-11-24 07:15 Selective\protocol.h
文件 5932 2009-10-19 22:57 Selective\Protocol.lib
..A.SH. 5120 2009-11-23 23:52 Selective\Thumbs.db
目录 0 2009-11-28 19:00 Selective\Debug
目录 0 2009-11-28 19:29 Selective
----------- --------- ---------- ----- ----
1307368 23
评论
共有 条评论