首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 网络技术 > 网络协议 >

怎么针对信道两端速率悬殊的情况改进滑动窗口协议

2013-01-08 
如何针对信道两端速率悬殊的情况改进滑动窗口协议?请教各位一个关于滑动窗口协议的问题。如果信道两端的传

如何针对信道两端速率悬殊的情况改进滑动窗口协议?
请教各位一个关于滑动窗口协议的问题。如果信道两端的传输速率悬殊,可能会出现这种情况:A端发送的包,B端接收到了,但是在A段超时前没有来得及发送应答。针对这种情况,如何通过改进回退N步协议,来提高信道的吞吐量?
这里有一段GoBackN的代码,有没有哪位达人能帮忙修改一下实现上述功能?或者给些提示和建议?
小女十分感谢!


public class Stopwait
    extends datalink.Protocol
{
    datalink.Packet buffer;      // copy of last packet sent
    int frameToSend;    // sequence number to use
                        // for next frame transmitted
    int frameExpected;  // sequence number expected
    double timer;       // time out value

    boolean waiting;    // a packet is waiting to be sent

    public Stopwait( int windowsize, double timer)
    {
super( windowsize, timer);
frameToSend = 0;  // initialise sequence numbers
frameExpected = 0;
waiting = false;
this.timer = timer;
    }

    public void FrameArrival( Object frame)
    {   // Object frame must be cast to DLL_Frame
DLL_Frame f = (DLL_Frame) frame;

// check that it is the one that is expected
if (f.sequence == frameExpected)
    {
sendPacket(f.info); // valid frame is passed
                    // to network layer
frameExpected = 1 - frameExpected; // flip bit
    }

if( f.acknowledgment == frameToSend)
    {   // acknowledgment has arrived
                buffer = null;
stopTimer(0);           // cancel timer
enableNetworkLayer();   // allow new packets
frameToSend = 1-frameToSend;
    }
    }

    public void PacketArrival( datalink.Packet p)
    {
DLL_Frame f;
buffer = p;
if ( isChannelIdle() )
    {
f = new DLL_Frame( frameToSend,
   1-frameExpected,
   buffer);
sendFrame( f);        // transmit it
startTimer(0, timer); // start timer
waiting = false;
    }
else
    waiting = true;
disableNetworkLayer();
    }

    public void TimeOut( int code)
    {
DLL_Frame f;
if ( isChannelIdle())
    {
// a frame has not been ACKed in time,


// so re-send the outstanding frame
f = new DLL_Frame( frameToSend,
   1-frameExpected,
   buffer);
sendFrame( f);
startTimer(0, timer);
    }
else
    waiting = true;
    }

    public void CheckSumError()
    {  // ignore check sum errors and allow frames to time out
    }

    public void ChannelIdle()
    {
DLL_Frame f;
if ( waiting )
    {
f = new DLL_Frame( frameToSend,
   1-frameExpected,
   buffer);
sendFrame( f);
startTimer(0, timer);
waiting = false;
    }
    }
   public int displayWindowWidth()
   {
      return 12;
   }

   public String displayWindow()
    {
  StringBuffer sb = new StringBuffer();
sb.append(" Receive Window: " + frameExpected + "\n\n");

sb.append(" Transmit Window\n Seq  Packet\n");

if ( buffer != null )
        sb.append("   " + frameToSend + "   " + buffer.getId() + "\n");
else sb.append("   " + frameToSend + "  null\n");

return sb.toString();
    }

}

class DLL_Frame {
    public datalink.Packet info;
    int sequence;
    int acknowledgment;

    DLL_Frame ( int s, int a, datalink.Packet p)
    {
info = p;
sequence = s;
acknowledgment = a;
    }
}


[解决办法]
不知道你的窗口怎么控制的,看代码好像是1v1的应答方式,这种方式传输效率很低。

因为每次S端发送一个包后,要等待R端ack确认了才发送下一个包。

在延迟高的情况下,传输效率太低了,大部分时间在等待ack 消息。

修改下协议。 ack部分为
uint32_t lastack;
uint32_t ackBits;

lastack为最后收到的seq.
ackbits为seq到seq-32 那些包是否收到。

现在S端可以一次多发送几个包,等待R端确认。网络利用率提高了


R端收到包后,可以延迟一点时间做ack回应,这样一个ack可以回应好几个包的seq

S端可以根据回应情况,计算出大约的丢包率,来控制发送速度。

ackbit根据你的需要,也许8位就可以满足你的需求了

热点排行