00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #include "copyright.h"
00012 #include "system.h"
00013
00014 extern "C" {
00015 int bcopy(char *, char *, int);
00016 };
00017
00018
00019 static void NetworkReadPoll(int arg)
00020 { Network *net = (Network *)arg; net->CheckPktAvail(); }
00021 static void NetworkSendDone(int arg)
00022 { Network *net = (Network *)arg; net->SendDone(); }
00023
00024
00025
00026
00027
00028 Network::Network(NetworkAddress addr, double reliability,
00029 VoidFunctionPtr readAvail, VoidFunctionPtr writeDone, int callArg)
00030 {
00031 ident = addr;
00032 if (reliability < 0) chanceToWork = 0;
00033 else if (reliability > 1) chanceToWork = 1;
00034 else chanceToWork = reliability;
00035
00036
00037 writeHandler = writeDone;
00038 readHandler = readAvail;
00039 handlerArg = callArg;
00040 sendBusy = FALSE;
00041 inHdr.length = 0;
00042
00043 sock = OpenSocket();
00044 sprintf(sockName, "SOCKET_%d", (int)addr);
00045 AssignNameToSocket(sockName, sock);
00046
00047
00048
00049 interrupt->Schedule(NetworkReadPoll, (int)this, NetworkTime, NetworkRecvInt);
00050 }
00051
00052 Network::~Network()
00053 {
00054 CloseSocket(sock);
00055 DeAssignNameToSocket(sockName);
00056 }
00057
00058
00059
00060
00061 void
00062 Network::CheckPktAvail()
00063 {
00064
00065 interrupt->Schedule(NetworkReadPoll, (int)this, NetworkTime, NetworkRecvInt);
00066
00067 if (inHdr.length != 0)
00068 return;
00069 if (!PollSocket(sock))
00070 return;
00071
00072
00073 char *buffer = new char[MaxWireSize];
00074 ReadFromSocket(sock, buffer, MaxWireSize);
00075
00076
00077 inHdr = *(PacketHeader *)buffer;
00078 ASSERT((inHdr.to == ident) && (inHdr.length <= MaxPacketSize));
00079 bcopy(buffer + sizeof(PacketHeader), inbox, inHdr.length);
00080 delete []buffer ;
00081
00082 DEBUG('n', "Network received packet from %d, length %d...\n",
00083 (int) inHdr.from, inHdr.length);
00084 stats->numPacketsRecvd++;
00085
00086
00087 (*readHandler)(handlerArg);
00088 }
00089
00090
00091 void
00092 Network::SendDone()
00093 {
00094 sendBusy = FALSE;
00095 stats->numPacketsSent++;
00096 (*writeHandler)(handlerArg);
00097 }
00098
00099
00100
00101
00102
00103
00104 void
00105 Network::Send(PacketHeader hdr, char* data)
00106 {
00107 char toName[32];
00108
00109 sprintf(toName, "SOCKET_%d", (int)hdr.to);
00110
00111 ASSERT((sendBusy == FALSE) && (hdr.length > 0)
00112 && (hdr.length <= MaxPacketSize) && (hdr.from == ident));
00113 DEBUG('n', "Sending to addr %d, %d bytes... ", hdr.to, hdr.length);
00114
00115 interrupt->Schedule(NetworkSendDone, (int)this, NetworkTime, NetworkSendInt);
00116
00117 if (Random() % 100 >= chanceToWork * 100) {
00118 DEBUG('n', "oops, lost it!\n");
00119 return;
00120 }
00121
00122
00123 char *buffer = new char[MaxWireSize];
00124 *(PacketHeader *)buffer = hdr;
00125 bcopy(data, buffer + sizeof(PacketHeader), hdr.length);
00126 SendToSocket(sock, buffer, MaxWireSize, toName);
00127 delete []buffer;
00128 }
00129
00130
00131 PacketHeader
00132 Network::Receive(char* data)
00133 {
00134 PacketHeader hdr = inHdr;
00135
00136 inHdr.length = 0;
00137 if (hdr.length != 0)
00138 bcopy(inbox, data, hdr.length);
00139 return hdr;
00140 }
The University of Southern California does not screen or control the content on this website and thus does not guarantee the accuracy, integrity, or quality of such content. All content on this website is provided by and is the sole responsibility of the person from which such content originated, and such content does not necessarily reflect the opinions of the University administration or the Board of Trustees