void dcc_send_connection::packet_arrived(dcc_stream& aStream, const dcc_packet& aPacket) { if (iSendType == Download) { if (!iFile.valid() || fwrite(static_cast<const char*>(aPacket.data()), 1, aPacket.length(), iFile) != aPacket.length()) { close(); return; } iBytesTransferred += aPacket.length(); unsigned long ack = htonl(iBytesTransferred); stream().send_packet(dcc_packet(reinterpret_cast<void*>(&ack), sizeof(ack))); neolib::observable<dcc_send_connection_observer>::notify_observers(dcc_send_connection_observer::NotifyTransferProgress); } else if (iSendType == Upload) { char* ack = reinterpret_cast<char*>(&iAck); const char* data = static_cast<const char*>(aPacket.data()); for (std::size_t i = 0; i < aPacket.length(); ++i, iAckReceived = (iAckReceived + 1) % 4) { *(ack + iAckReceived) = *(data + i); } if (iAckReceived == 0 && ntohl(iAck) == iBytesTransferred) send_next_packet(); } }
int fast_retrans(int sock, struct sockaddr_in out, fd_set socks, struct timeval t, struct sockaddr_in in, socklen_t in_len ) { for (int i = 0; i < RETRANS_WIND; i++ ) { send_next_packet(sock, out); if (select(sock + 1, &socks, NULL, NULL, &t)) { unsigned char buf[DATA_SIZE + sizeof(header)]; int buf_length = sizeof(buf); int recvd; if ((recvd = recvfrom(sock, &buf, buf_length, 0, (struct sockaddr *) &in, (socklen_t *) &in_len)) < 0) { perror("Recvfrom"); exit(1); } header *myheader = get_header(buf); if ((myheader->magic == MAGIC) && (myheader->ack == 1)) { mylog("[Recv ack] %d\n", myheader->sequence); rec_sequence = myheader->sequence; } else { mylog("[Recv Corrupted ack] %x %d > %d - %d - %d\n", MAGIC, myheader->sequence, sent_sequence, myheader->ack, myheader->eof); } } else { mylog("[Error] A Timeout Occurred\n"); sent_sequence = rec_sequence + 1; return 1; } } return 0; }
void dcc_send_connection::send_file(const std::string& aFilePath) { iFile.close(); if (has_resume_data()) { iBytesTransferred = resume_data()->iResumeFileSize; iLastBytesTransferred = iBytesTransferred; } iFilePath = aFilePath; iFileSize = static_cast<unsigned long>(neolib::large_file_size(aFilePath)); neolib::observable<dcc_send_connection_observer>::notify_observers(dcc_send_connection_observer::NotifyTransferStarted); if (!open_file()) return; send_next_packet(); }
int send_next_window(int sock, struct sockaddr_in out, unsigned int* pkts_sent) { //determines unacknowledged packets in circulation *pkts_sent = 0; for(int i = 0; i < WIND_SIZE; i++) { if (!send_next_packet(sock,out)) { break; } (*pkts_sent)++; sent_sequence++; } sent_sequence--; return *pkts_sent; }
void dcc_send_connection::packet_sent(dcc_stream& aStream, const dcc_packet& aPacket) { if (iSendType == Upload && iConnectionManager.dcc_fast_send()) send_next_packet(); }