Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members | Related Pages

# Platform/Aperios1.3.2/UDPHandler.cpp

Go to the documentation of this file.

    00001 /**
    00002 * @file  Platform/Aperios1.3.2/UDPHandler.cpp
    00003 *
    00004 * Class for using NetSender/NetReceivers over UDP
    00005 * @author <A href=mailto:robocup@m-wachter.de>Michael Wachter</A>
    00006 *
    00007 */
    00008
    00009 #include "UDPHandler.h"
    00010 #include <Tools/Debugging/Debugging.h>
    00011 #include "Tools/Debugging/Watchdog.h"
    00012
    00013 #include <stdio.h>
    00014 #include <iostream.h>
    00015
    00016 UDPHandlerEndpoint::UDPHandlerEndpoint() : UDPEndpoint(2048,2048)
    00017 {
    00018       lastReceivedSerial=0;
    00019     sendSerial=0;
    00020 }
    00021
    00022 UDPHandlerEndpoint::~UDPHandlerEndpoint()
    00023 {
    00024
    00025 };
    00026
    00027 void UDPHandlerEndpoint::sendPackage(int senderNumber, void* packet, int size)
    00028 {
    00029   // cout << "Sender " << senderNumber << " wants to send :" ;
    00030
    00031    if ((ddpHandler->activeTeamMembers()) && (size<1400))
    00032
    00033   {
    00034     // cout << " sending to " << ddpHandler.list[senderNumber].ip << " \n " << flush;
    00035       char* ende = static_cast<char*>(packet);
    00036
    00037       ende += size;
    00038       sendSerial++;
    00039       memcpy(ende,&sendSerial,4);
    00040 /**   send((char*)(packet),size+4,ddpHandler->list[sender->senderNumber].ip,
    00041        TEAMPORTBASE + (int)getPlayer().getPlayerNumber());*/
    00042
    00043           send((char*)(packet),size+4,IP_ADDR_BROADCAST,
    00044                    TEAMPORTBASE + (int)getPlayer().getPlayerNumber());
    00045
    00046   }
    00047   else
    00048   {
    00049      // cout << " no target ";
    00050       sender->sendDone();
    00051   }
    00052   udpHandler->doRegularStuff();
    00053   // cout << "\n" << flush;
    00054 }
    00055
    00056 void UDPHandlerEndpoint::onSendingDone()
    00057  {
    00058    sender->sendDone();
    00059  }
    00060
    00061 void UDPHandlerEndpoint::onReceive(void *data, int size)
    00062 {
    00063     watchdog.enter(1001);
    00064   //cout << "UDPHandlerEndpoint::onReceive() ";
    00065   //cout << size << " " << sender->senderNumber << " ";   // 13
    00066   //char pN = ((char*)data)[17] ;
    00067   //cout << ((int)pN) << " ";
    00068   //cout << "listip: " << ddpHandler->list[sender->senderNumber].ip << " ip: " << ipOfLastPackage ;
    00069   //cout << "\n";
    00070
    00071
    00072
    00073      if (ddpHandler->list[sender->senderNumber].ip == ipOfLastPackage)
    00074      {
    00075         // cout << " handler " << i ;
    00076         int packetSize = *(int*)data;
    00077
    00078     // Scheiss alignment-kack !!!
    00079         char* ende = static_cast<char*>(data);
    00080         ende += packetSize;
    00081         ende += 4;
    00082         int serial;
    00083         memcpy(&serial,ende,4);
    00084
    00085     if (serial != lastReceivedSerial + 1) // Package can be an old or a missing one.
    00086     {
    00087
    00088       // Test if the package is already missing
    00089       bool isMissingPackage = false;
    00090       static RingBuffer<int,10> missingSerials;
    00091
    00092       for(int i=0; i< missingSerials.getNumberOfEntries(); i++)
    00093       {
    00094         if (missingSerials[i]==serial)
    00095         {
    00096           isMissingPackage= true;
    00097           INFO(sendTimeOffsets,idText,text,
    00098             "Package jitter from " << ipOfLastPackage << " detected. Package is " <<
    00099             lastReceivedSerial - missingSerials[i]
    00100             << " packages too late");
    00101             missingSerials[i] = 0;
    00102         }
    00103       }
    00104
    00105       if (isMissingPackage) // Order of the packages changed.
    00106       {
    00107
    00108
    00109       }
    00110       else
    00111       {
    00112         missingSerials.add(serial-1);
    00113       }
    00114
    00115       // Check if there are serials older than 10 packages
    00116
    00117       for(int i=0; i< missingSerials.getNumberOfEntries(); i++)
    00118       {
    00119         if ((missingSerials[i]<serial-10) && (missingSerials[i]!=0))
    00120         {
    00121           INFO(sendTimeOffsets,idText,text,
    00122             "Packet-Loss from " << ipOfLastPackage << " detected. (Serial " << missingSerials[i] << ")");
    00123           missingSerials[i] = 0;
    00124         }
    00125       }
    00126         }
    00127
    00128         lastReceivedSerial = serial;
    00129
    00130         receiver->getPackage(packetSize);
    00131         memcpy(receiver->package, (char*)data + 4, packetSize);
    00132         receiver->onReceive();
    00133      }
    00134    else
    00135    {
    00136     // cout << "ip <-> DDP-ip mismatch \n";
    00137     // cout << ddpHandler->list[sender->senderNumber].ip << " =! " << ipOfLastPackage << endl << flush;
    00138    }
    00139   watchdog.leave(1001);
    00140 }
    00141
    00142
    00143 UDPHandler::UDPHandler()
    00144 {
    00145    numberOfEndpoints = 0;
    00146 }
    00147
    00148 void UDPHandler::addSenderAndReceiver(NetSenderBase& sender, NetReceiverBase& receiver)
    00149 {
    00150     endPoints[numberOfEndpoints].sender = &sender;
    00151   endPoints[numberOfEndpoints].receiver = &receiver;
    00152   endPoints[numberOfEndpoints].sender->setHandler(&endPoints[numberOfEndpoints]);
    00153     endPoints[numberOfEndpoints].sender->getPackage(2048);
    00154   endPoints[numberOfEndpoints].sender->senderNumber = numberOfEndpoints;
    00155     endPoints[numberOfEndpoints].receiver->getPackage(2048);
    00156   endPoints[numberOfEndpoints].ddpHandler = &ddpHandler;
    00157   endPoints[numberOfEndpoints].udpHandler = this;
    00158   numberOfEndpoints++;
    00159
    00160 }
    00161 void UDPHandler::start()
    00162 {
    00163     ddpHandler.initDDPHandler();
    00164   int i;
    00165   int j = 0;
    00166   for (i=0; i< Player::numOfPlayerNumbers; i++)
    00167     {
    00168       if ((int)getPlayer().getPlayerNumber() != i)
    00169     {
    00170            endPoints[j].bind(TEAMPORTBASE+i);
    00171            j++;
    00172     }
    00173     }
    00174 }
    00175
    00176 void UDPHandler::doRegularStuff()
    00177 {
    00178     ddpHandler.sendDDPPackage();
    00179 }
    00180
    00181
    00182
    00183
    00184
    00185
    00186
    00187   // cout << "\n";
    00188