Beispiel #1
0
int main(int argc, char **argv) {
	packet test_pack;
	STAT_packet *data = (STAT_packet*) malloc( sizeof(STAT_packet) );
	data->mount = 1234;
	strcpy(data->filereq, "test.txt");

	test_pack.request = eSTAT;
	test_pack.data = data;
	printPacket(&test_pack);

	char *serialized = serializePacket( &test_pack );
	packet *dsPack;
	dsPack = deserializePacket( serialized );
	printPacket(dsPack);

	return 0;
}
Beispiel #2
0
void deserializeIpPacket(void *msg, struct ip_packet *pkt) {
    if (msg == NULL) {
        fprintf(stderr, "Deserialize: invalid message\n");
        return;
    }
    if (pkt == NULL) {
        fprintf(stderr, "Deserialize: invalid packet\n");
        return;
    }

    struct ip_packet *p = (struct ip_packet *)msg;
    pkt->priority = p->priority;
    pkt->src  = ntohl(p->src);
	pkt->srcPort  = ntohs(p->srcPort);
	pkt->dest  = ntohl(p->dest);
	pkt->destPort  = ntohs(p->destPort);
    pkt->length  = ntohl(p->length);
	deserializePacket(p->payload, (struct packet *)pkt->payload);
}
Beispiel #3
0
void
DebugNet::networkThread()
{
#ifdef PLATFORM_WINDOWS
   SOCKET sock = (SOCKET)mSocket;
   std::vector<uint8_t> buffer;

   while (true) {
      buffer.resize(sizeof(DebugNetHeader));
      int recvd = recv(sock, (char*)&buffer[0], sizeof(DebugNetHeader), 0);
      if (recvd <= 0) {
         // Disconnected
         handleDisconnect();
         break;
      }
      assert(recvd == sizeof(DebugNetHeader));

      DebugNetHeader *header = (DebugNetHeader*)buffer.data();
      if (header->size > (uint32_t)buffer.size()) {
         buffer.resize(header->size);

         recvd = recv(sock,
            (char*)&buffer[sizeof(DebugNetHeader)],
            (int)buffer.size() - sizeof(DebugNetHeader),
            0);
         if (recvd <= 0) {
            handleDisconnect();
            break;
         }
         assert(recvd == buffer.size() - sizeof(DebugNetHeader));
      }

      DebugPacket *packet = nullptr;
      deserializePacket(buffer, packet);
      handlePacket(packet);
   }
#endif
}
Beispiel #4
0
int main(int argc, char **argv) {
    // ------------------------------------------------------------------------
    // Handle commandline arguments
    if (argc != 11) {
        printf("usage: requester -p <port> -f <f_hostname> -h <f_port> ");
        printf("-o <file option> -w <window>\n");
        exit(1);
    }
    char *portStr    = NULL;
    char *fileOption = NULL;
    char *emuHost    = NULL;
    char *emuPortStr = NULL;
    char *windowStr  = NULL;

    int cmd;
    while ((cmd = getopt(argc, argv, "p:o:f:h:w:")) != -1) {
        switch(cmd) {
        case 'p':
            portStr    = optarg;
            break;
        case 'o':
            fileOption = optarg;
            break;
        case 'f':
            emuHost    = optarg;
            break;
        case 'h':
            emuPortStr = optarg;
            break;
        case 'w':
            windowStr  = optarg;
            break;
        case '?':
            if (optopt == 'p' || optopt == 'o' || optopt == 'f'
                    || optopt == 'h' || optopt == 'w')
                fprintf(stderr, "Option -%c requires an argument.\n", optopt);
            else if (isprint(optopt))
                fprintf(stderr, "Unknown option -%c.\n", optopt);
            else
                fprintf(stderr, "Unknown option character '\\x%x'.\n", optopt);
            exit(EXIT_FAILURE);
            break;
        default:
            printf("Unhandled argument: %d\n", cmd);
            exit(EXIT_FAILURE);
        }
    }

    // DEBUG
    printf("Port: %s\n", portStr);
    printf("File: %s\n", fileOption);
    printf("Emu Name: %s\n", emuHost);
    printf("Emu Port: %s\n", emuPortStr);
    printf("Window: %s\n", windowStr);

    // Convert program args to values
    int requesterPort = atoi(portStr);
    int windowSize    = atoi(windowStr);
    // TODO: uncomment these once they are used
    //int emuPort       = atoi(emuPortStr);

    // Validate the argument values
    if (requesterPort <= 1024 || requesterPort >= 65536)
        ferrorExit("Invalid requester port");
    if (windowSize <= 0 || windowSize >= 65536) // upper bound is arbitrary
        ferrorExit("Invalid window size");
    puts("");

    // ------------------------------------------------------------------------

    // Parse the tracker file for parts corresponding to the specified file
    struct file_info *fileParts = parseTracker(fileOption);
    assert(fileParts != NULL && "Invalid file_info struct");

    // ------------------------------------------------------------------------
    // Setup requester address info
    struct addrinfo rhints;
    bzero(&rhints, sizeof(struct addrinfo));
    rhints.ai_family   = AF_INET;
    rhints.ai_socktype = SOCK_DGRAM;
    rhints.ai_flags    = AI_PASSIVE;

    // Get the requester's address info
    struct addrinfo *requesterinfo;
    int errcode = getaddrinfo(NULL, portStr, &rhints, &requesterinfo);
    if (errcode != 0) {
        fprintf(stderr, "requester getaddrinfo: %s\n", gai_strerror(errcode));
        exit(EXIT_FAILURE);
    }

    // Loop through all the results of getaddrinfo and try to create a socket for requester
    int sockfd;
    struct addrinfo *rp;
    for(rp = requesterinfo; rp != NULL; rp = rp->ai_next) {
        // Try to create a new socket
        sockfd = socket(rp->ai_family, rp->ai_socktype, rp->ai_protocol);
        if (sockfd == -1) {
            perror("Socket error");
            continue;
        }

        // Try to bind the socket
        if (bind(sockfd, rp->ai_addr, rp->ai_addrlen) == -1) {
            perror("Bind error");
            close(sockfd);
            continue;
        }

        break;
    }
    if (rp == NULL) perrorExit("Request socket creation failed");
    else            {
        printf("Requester socket: ");
        printNameInfo(rp);
    }
    // ------------------------------------------------------------------------
    // Emulator hints
    struct addrinfo ehints;
    bzero(&ehints, sizeof(struct addrinfo));
    ehints.ai_family   = AF_INET;
    ehints.ai_socktype = SOCK_DGRAM;
    ehints.ai_flags    = 0;

    FILE *file = fopen("recvd.txt", "at");
    if (file == NULL) perrorExit("File open error");
    struct file_part *part = fileParts->parts;
    //while (part != NULL) {
    // Convert the sender's port # to a string
    /*
    char senderPortStr[6] = "\0\0\0\0\0\0";
    sprintf(senderPortStr, "%d", part->sender_port);
    */

    // Setup emulator address info
    struct addrinfo *emuinfo;
    errcode = getaddrinfo(emuHost, emuPortStr, &ehints, &emuinfo);
    if (errcode != 0) {
        fprintf(stderr, "emulator getaddrinfo: %s\n", gai_strerror(errcode));
        exit(EXIT_FAILURE);
    }

    // Loop through all the results of getaddrinfo and try to create a socket for emulator
    // NOTE: this is done so that we can find which of the getaddrinfo results is the emulator
    int emusockfd;
    struct addrinfo *ep;
    for(ep = emuinfo; ep != NULL; ep = ep->ai_next) {
        emusockfd = socket(ep->ai_family, ep->ai_socktype, ep->ai_protocol);
        if (emusockfd == -1) {
            perror("Socket error");
            continue;
        }

        break;
    }
    if (ep == NULL) perrorExit("Emulator socket creation failed");
    else            close(emusockfd);

    // ------------------------------------------------------------------------

    struct addrinfo shints;
    bzero(&shints, sizeof(struct addrinfo));
    shints.ai_family   = AF_INET;
    shints.ai_socktype = SOCK_DGRAM;
    shints.ai_flags    = 0;

    int sendersockfd = 0;

    // Setup variables for statistics
    unsigned long numPacketsRecvd = 0;
    unsigned long numBytesRecvd = 0;
    time_t startTime = time(NULL);

    char str[6];
    sprintf(str, "%d", part->sender_port);
    struct addrinfo *senderinfo;
    errcode = getaddrinfo(part->sender_hostname, str, &shints, &senderinfo);
    if (errcode != 0) {
        fprintf(stderr, "emulator getaddrinfo %s\n", gai_strerror(errcode));
        exit(EXIT_FAILURE);
    }

    struct addrinfo *sp;
    for(sp = senderinfo; sp != NULL; sp = ep->ai_next) {
        sendersockfd = socket(sp->ai_family, sp->ai_socktype, sp->ai_protocol);
        if (sendersockfd == -1) {
            perror("Socket error");
            continue;
        }

        break;
    }
    if (sp == NULL) perrorExit("Sender socket creation failed");
    else		close(sendersockfd);
    // ------------------------------------------------------------------------
    // Construct a REQUEST packet and send it to the emulator
    struct new_packet *pkt = NULL;
    pkt = malloc(sizeof(struct new_packet));
    bzero(pkt, sizeof(struct new_packet));
    pkt->priority = 1;
    pkt->src_ip   = ((struct sockaddr_in*)rp)->sin_addr.s_addr; // TODO
    pkt->src_port = requesterPort; // TODO
    pkt->dst_ip   = ((struct sockaddr_in*)sp)->sin_addr.s_addr; // TODO
    pkt->dst_port = part->sender_port; // TODO
    pkt->len      = sizeof(struct packet) - MAX_PAYLOAD + strlen(fileOption) + 1;
    // encapsulated packet
    pkt->pkt.type = 'R';
    pkt->pkt.seq  = 0;
    pkt->pkt.len  = windowSize;
    strcpy(pkt->pkt.payload, fileOption);


    sendPacketTo(sockfd, pkt, (struct sockaddr *)ep->ai_addr);
    free(pkt);


    // ------------------------------------------------------------------------
    // Connect to emulator to receive all parts of requested file

    // Start a recv loop here to get all packets for the given part
    //

    struct new_packet *buffer = malloc(windowSize * sizeof(struct new_packet));
    unsigned int *acked = malloc(windowSize * sizeof(unsigned int));
    int l;
    for( l = 0; l < windowSize; ++l) {
        acked[l] = 0;
    }
    for (;;) {
        // Receive a message
        struct new_packet msg;
        bzero(&msg, sizeof(struct new_packet));
        size_t bytesRecvd = recvfrom(sockfd, &msg, sizeof(struct new_packet), 0,
                                     (struct sockaddr *)ep->ai_addr, &ep->ai_addrlen);
        if (bytesRecvd == -1) perrorExit("Receive error");

        // Deserialize the message into a packet
        struct new_packet p;
        bzero(&p, sizeof(struct new_packet));
        deserializePacket(&msg, &p);

        // Handle DATA packet
        if (p.pkt.type == 'D') {
            // Update statistics
            ++numPacketsRecvd;
            numBytesRecvd += p.len;

            /* FOR DEBUG
            printf("[Packet Details]\n------------------\n");
            printf("type : %c\n", p.type);
            printf("seq  : %lu\n", p.seq);
            printf("len  : %lu\n", p.len);
            printf("payload: %s\n\n", p.payload);
            */

            // Print details about the received packet
            //printf("<- [Received DATA packet] ");
            //printPacketInfo(&p, (struct sockaddr_storage *)ep->ai_addr);

            // See if this packet has already been received
            int i;
            int found = 0;
            for(i = 0; i < windowSize; ++i) {
                if(buffer[i].pkt.seq == p.pkt.seq) {
                    found = 1;
                }
            }
            if(found == 0) {
                buffer[(p.pkt.seq - 1) % windowSize] = p;
            }
            // Save the data so the file can be reassembled later
            //size_t bytesWritten = fprintf(file, "%s", p.pkt.payload);
            //fflush(file);
            //if (bytesWritten == -1) {
            //    fprintf(stderr,
            //        "Incomplete file write: %d bytes written, %lu p len",
            //        (int)bytesWritten, p.pkt.len);
            //}

            // Requester now ACK's this packet
            struct new_packet *ack = NULL;
            ack = malloc(sizeof(struct new_packet));
            bzero(ack, sizeof(struct new_packet));
            ack->priority = 1;
            ack->src_ip   = ((struct sockaddr_in*)rp)->sin_addr.s_addr; // TODO
            ack->src_port = requesterPort; // TODO
            ack->dst_ip   = ((struct sockaddr_in*)sp)->sin_addr.s_addr; // TODO
            ack->dst_port = part->sender_port; // TODO
            ack->len      = sizeof(struct packet) - MAX_PAYLOAD + strlen(fileOption) + 1;
            // encapsulated packet
            ack->pkt.type = 'A';
            ack->pkt.seq  = p.pkt.seq;
            ack->pkt.len  = windowSize;
            strcpy(ack->pkt.payload, fileOption);


            sendPacketTo(sockfd, ack, (struct sockaddr *)ep->ai_addr);
            acked[(p.pkt.seq - 1) % windowSize] = 1;
            free(ack);
        }
        int j;
        int doneAcking = 1;
        for(j = 0; j < windowSize; ++j) {
            if(acked[j] == 0) {
                doneAcking = 0;
            }
        }
        if(doneAcking) {
            // write out to file in order
            int k;
            for(k = 0; k < windowSize; ++k) {
                acked[k] = 0;

                size_t bytesWritten = fprintf(file, "%s", buffer[k].pkt.payload);
                fflush(file);
                if (bytesWritten == -1) {
                    fprintf(stderr,
                            "Incomplete file write: %d bytes written, %lu p len",
                            (int)bytesWritten, buffer[k].pkt.len);
                }
            }
        }


        // Handle END packet
        if (p.pkt.type == 'E') {
            printf("<- *** [Received END packet] ***");
            double dt = difftime(time(NULL), startTime);
            if (dt <= 1) dt = 1;

            // Print statistics
            printf("\n---------------------------------------\n");
            printf("Total packets recvd: %lu\n", numPacketsRecvd);
            printf("Total payload bytes recvd: %lu\n", numBytesRecvd);
            printf("Average packets/second: %d\n", (int)(numPacketsRecvd / dt));
            printf("Duration of test: %f sec\n\n", dt);

            break;
        }
    }
    part = part->next_part;

    freeaddrinfo(emuinfo);


    // TODO: this crashes the program... figure out why
    //fclose(file);

    // Got what we came for, shut it down
    if (close(sockfd) == -1) perrorExit("Close error");
    else                     puts("Connection closed.\n");

    // Cleanup address and file info data
    freeaddrinfo(requesterinfo);
    freeFileInfo(fileParts);

    // All done!
    exit(EXIT_SUCCESS);
}
Beispiel #5
0
int main(int argc, char **argv) {
    // ------------------------------------------------------------------------
    // Handle commandline arguments
    if (argc != 5) {
        printf("usage: emulator -p <port> -f <filename>\n");
        exit(1);
    }

    char *portStr     = NULL;
    char *filename    = NULL;

    int cmd;
    while ((cmd = getopt(argc, argv, "p:f:")) != -1) {
        switch(cmd) {
          case 'p': portStr      = optarg; break;
          case 'f': filename     = optarg; break;
          case '?':
                    if (optopt == 'p' || optopt == 'f')
                        fprintf(stderr, "Option -%c requires an argument.\n", optopt);
                    else if (isprint(optopt))
                        fprintf(stderr, "Unknown option -%c.\n", optopt);
                    else
                        fprintf(stderr, "Unknown option character '\\x%x'.\n", optopt);
                    exit(EXIT_FAILURE);
                    break;
          default: 
                    printf("Unhandled argument: %d\n", cmd);
                    exit(EXIT_FAILURE); 
        }
    }

    printf("Port           : %s\n", portStr);
    printf("Filename       : %s\n", filename);

    // Convert program args to values
    int port         = atoi(portStr);

    // Validate the argument values
    if (port < 1 || port > 65536)
        ferrorExit("Invalid port");
    puts("");


    // Read network topology
    struct entry **topology = readtopology(filename);
    printTopology(topology);

    // Create network routes from topology
    createRoutes(topology);


    // TODO: this is temporary, need to get sender address info from fwd table
    // Setup sender address info 
    struct addrinfo ehints;
    bzero(&ehints, sizeof(struct addrinfo));
    ehints.ai_family   = AF_INET;
    ehints.ai_socktype = SOCK_DGRAM;
    ehints.ai_flags    = 0;

    // Setup emu sending socket
    struct sockaddr_in emuaddr;

    int sockfd;

    if( (sockfd = socket(AF_INET, SOCK_DGRAM | SOCK_NONBLOCK, 0)) == -1){
        perrorExit("Socket error");
    }

    emuaddr.sin_family = AF_INET;
    emuaddr.sin_port = htons(port);
    emuaddr.sin_addr.s_addr = INADDR_ANY;
    bzero(&(emuaddr.sin_zero), 8);


    if (bind(sockfd, (struct sockaddr*)&emuaddr, sizeof(emuaddr)) == -1) {
        close(sockfd);
        perrorExit("Bind error");
    }

    printf("Emulator socket created on port:%d\n", port );

    //-------------------------------------------------------------------------
    // BEGIN NETWORK EMULATION LOOP
    puts("Emulator waiting for packets...\n");

    struct sockaddr_in recvAddr;

    socklen_t recvLen = sizeof(recvAddr);
    //socklen_t sendLen = sizeof(sendAddr);
    // HACK: Don't like hard coding this, but don't know any other way
    size_t MAX_HOST_LEN = 256;
    char name[MAX_HOST_LEN];
    gethostname(name, MAX_HOST_LEN);
    //Need to just get lowest level dns name i.e. mumble-30

    while (1) {
        void *msg = malloc(sizeof(struct packet));
        bzero(msg, sizeof(struct packet));
        size_t bytesRecvd;
        bytesRecvd = recvfrom(sockfd, msg, sizeof(struct packet), 0,
                              (struct sockaddr *)&recvAddr, &recvLen);
        if (bytesRecvd != -1) {
            //printf("Received %d bytes\n", (int)bytesRecvd);
            // Deserialize the message into a packet 
            struct packet *pkt = malloc(sizeof(struct packet));
            bzero(pkt, sizeof(struct packet));
            deserializePacket(msg, pkt);

            struct addrinfo entryHints;
            bzero(&entryHints, sizeof(struct addrinfo));
            entryHints.ai_family   = AF_INET;
            entryHints.ai_socktype = SOCK_DGRAM;
            entryHints.ai_flags    = 0;

        }	
    }
    if (close(sockfd) == -1) perrorExit("Close error");
    else                     puts("Connection closed.\n");

    // All done!
    exit(EXIT_SUCCESS);


}