fix: don't count filetransfer as sending until accepted

This fixes high CPU load in c-toxcore due to started but not accepted
file transfers causing lots of iterations in do_all_filetransfers(...).
Additionally this skips expensive calls max_speed_reached(...).
This commit is contained in:
sudden6 2022-01-13 21:11:34 +01:00 committed by iphydf
parent 4a2cb37e4b
commit 2073d02c33
No known key found for this signature in database
GPG Key ID: 3855DBA2D74403C9

View File

@ -1148,8 +1148,6 @@ long int new_filesender(const Messenger *m, int32_t friendnumber, uint32_t file_
memcpy(ft->id, file_id, FILE_ID_LENGTH);
++m->friendlist[friendnumber].num_sending_files;
return i;
}
@ -1255,11 +1253,12 @@ int file_control(const Messenger *m, int32_t friendnumber, uint32_t filenumber,
if (send_file_control_packet(m, friendnumber, send_receive, file_number, control, nullptr, 0)) {
if (control == FILECONTROL_KILL) {
ft->status = FILESTATUS_NONE;
if (send_receive == 0) {
if (send_receive == 0 && (ft->status == FILESTATUS_TRANSFERRING || ft->status == FILESTATUS_FINISHED)) {
// We are actively sending that file, remove from list
--m->friendlist[friendnumber].num_sending_files;
}
ft->status = FILESTATUS_NONE;
} else if (control == FILECONTROL_PAUSE) {
ft->paused |= FILE_PAUSE_US;
} else if (control == FILECONTROL_ACCEPT) {
@ -1465,15 +1464,13 @@ static bool do_all_filetransfers(Messenger *m, int32_t friendnumber, void *userd
return false;
}
if (max_speed_reached(m->net_crypto, friend_connection_crypt_connection_id(
m->fr_c, friendcon->friendcon_id))) {
LOGGER_TRACE(m->log, "Maximum connection speed reached");
// connection doesn't support any more data
return false;
}
struct File_Transfers *const ft = &friendcon->file_sending[i];
if (ft->status == FILESTATUS_NONE || ft->status == FILESTATUS_NOT_ACCEPTED) {
// Filetransfers not actively sending, nothing to do
continue;
}
// If the file transfer is complete, we request a chunk of size 0.
if (ft->status == FILESTATUS_FINISHED && friend_received_packet(m, friendnumber, ft->last_packet_number) == 0) {
if (m->file_reqchunk) {
@ -1483,9 +1480,7 @@ static bool do_all_filetransfers(Messenger *m, int32_t friendnumber, void *userd
// Now it's inactive, we're no longer sending this.
ft->status = FILESTATUS_NONE;
--friendcon->num_sending_files;
}
if (ft->status == FILESTATUS_TRANSFERRING && ft->paused == FILE_PAUSE_NOT) {
} else if (ft->status == FILESTATUS_TRANSFERRING && ft->paused == FILE_PAUSE_NOT) {
if (ft->size == 0) {
/* Send 0 data to friend if file is 0 length. */
file_data(m, friendnumber, i, 0, nullptr, 0);
@ -1508,6 +1503,14 @@ static bool do_all_filetransfers(Messenger *m, int32_t friendnumber, void *userd
// The allocated slot is no longer free.
--*free_slots;
}
// Must be last to allow finishing file transfers
if (max_speed_reached(m->net_crypto, friend_connection_crypt_connection_id(
m->fr_c, friendcon->friendcon_id))) {
LOGGER_TRACE(m->log, "Maximum connection speed reached");
// connection doesn't support any more data
return false;
}
}
return true;
@ -1614,6 +1617,7 @@ static int handle_filecontrol(Messenger *m, int32_t friendnumber, uint8_t receiv
case FILECONTROL_ACCEPT: {
if (receive_send && ft->status == FILESTATUS_NOT_ACCEPTED) {
ft->status = FILESTATUS_TRANSFERRING;
++m->friendlist[friendnumber].num_sending_files;
} else {
if (ft->paused & FILE_PAUSE_OTHER) {
ft->paused ^= FILE_PAUSE_OTHER;
@ -1652,12 +1656,12 @@ static int handle_filecontrol(Messenger *m, int32_t friendnumber, uint8_t receiv
m->file_filecontrol(m, friendnumber, real_filenumber, control_type, userdata);
}
ft->status = FILESTATUS_NONE;
if (receive_send) {
if (receive_send && (ft->status == FILESTATUS_TRANSFERRING || ft->status == FILESTATUS_FINISHED)) {
--m->friendlist[friendnumber].num_sending_files;
}
ft->status = FILESTATUS_NONE;
return 0;
}