/** * function invoked when a file transfer is received. **/ static void file_transfer_received(LinphoneChatMessage *message, const LinphoneContent* content, const LinphoneBuffer *buffer){ FILE* file=NULL; if (!linphone_chat_message_get_user_data(message)) { /*first chunk, creating file*/ file = fopen("receive_file.dump","wb"); linphone_chat_message_set_user_data(message,(void*)file); /*store fd for next chunks*/ } file = (FILE*)linphone_chat_message_get_user_data(message); if (linphone_buffer_is_empty(buffer)) { printf("File transfert completed\n"); linphone_chat_room_destroy(linphone_chat_message_get_chat_room(message)); linphone_chat_message_destroy(message); fclose(file); running=FALSE; } else { /* store content on a file*/ if (fwrite(linphone_buffer_get_content(buffer),linphone_buffer_get_size(buffer),1,file)==-1){ ms_warning("file_transfer_received() write failed: %s",strerror(errno)); } } }
/* * function called when the file transfer is initiated. file content should be feed into object LinphoneContent * */ static void file_transfer_send(LinphoneCore *lc, LinphoneChatMessage *message, const LinphoneContent* content, char* buff, size_t* size){ int offset=-1; if (!linphone_chat_message_get_user_data(message)) { /*first chunk*/ offset=0; } else { /*subsequent chunk*/ offset = (int)((long)(linphone_chat_message_get_user_data(message))&0x00000000FFFFFFFF); } *size = MIN(*size,sizeof(big_file)-offset); /*updating content->size with minimun between remaining data and requested size*/ if (*size==0) { /*end of file*/ return; } memcpy(buff,big_file+offset,*size); /*store offset for next chunk*/ linphone_chat_message_set_user_data(message,(void*)(offset+*size)); }
/** * function invoked when a file transfer is received. * */ void file_transfer_received(LinphoneChatMessage *message, const LinphoneContent* content, const LinphoneBuffer *buffer){ FILE* file=NULL; char receive_file[256]; LinphoneChatRoom *cr = linphone_chat_message_get_chat_room(message); LinphoneCore *lc = linphone_chat_room_get_core(cr); snprintf(receive_file,sizeof(receive_file), "%s/receive_file.dump", liblinphone_tester_writable_dir_prefix); if (!linphone_chat_message_get_user_data(message)) { /*first chunk, creating file*/ file = fopen(receive_file,"wb"); linphone_chat_message_set_user_data(message,(void*)file); /*store fd for next chunks*/ } file = (FILE*)linphone_chat_message_get_user_data(message); if (linphone_buffer_is_empty(buffer)) { /* tranfer complete */ stats* counters = get_stats(lc); counters->number_of_LinphoneMessageExtBodyReceived++; fclose(file); } else { /* store content on a file*/ if (fwrite(linphone_buffer_get_content(buffer),linphone_buffer_get_size(buffer),1,file)==-1){ ms_error("file_transfer_received(): write() failed: %s",strerror(errno)); } } }
static void file_transfer_message(void) { char* to; LinphoneChatRoom* chat_room; LinphoneChatMessage* message; LinphoneChatMessageCbs *cbs; LinphoneContent* content; FILE *file_to_send = NULL; size_t file_size; char *send_filepath = ms_strdup_printf("%s/images/nowebcamCIF.jpg", liblinphone_tester_file_prefix); char *receive_filepath = ms_strdup_printf("%s/receive_file.dump", liblinphone_tester_writable_dir_prefix); LinphoneCoreManager* marie = linphone_core_manager_new( "marie_rc"); LinphoneCoreManager* pauline = linphone_core_manager_new( "pauline_rc"); reset_counters(&marie->stat); reset_counters(&pauline->stat); file_to_send = fopen(send_filepath, "rb"); fseek(file_to_send, 0, SEEK_END); file_size = ftell(file_to_send); fseek(file_to_send, 0, SEEK_SET); /* Globally configure an http file transfer server. */ linphone_core_set_file_transfer_server(pauline->lc,"https://www.linphone.org:444/lft.php"); /* create a chatroom on pauline's side */ to = linphone_address_as_string(marie->identity); chat_room = linphone_core_create_chat_room(pauline->lc,to); ms_free(to); /* create a file transfer message */ content = linphone_core_create_content(pauline->lc); linphone_content_set_type(content,"image"); linphone_content_set_subtype(content,"jpeg"); linphone_content_set_size(content,file_size); /*total size to be transfered*/ linphone_content_set_name(content,"nowebcamCIF.jpg"); message = linphone_chat_room_create_file_transfer_message(chat_room, content); linphone_chat_message_set_user_data(message, file_to_send); cbs = linphone_chat_message_get_callbacks(message); { int dummy=0; wait_for_until(marie->lc,pauline->lc,&dummy,1,100); /*just to have time to purge message stored in the server*/ reset_counters(&marie->stat); reset_counters(&pauline->stat); } linphone_chat_message_cbs_set_msg_state_changed(cbs,liblinphone_tester_chat_message_msg_state_changed); linphone_chat_message_cbs_set_file_transfer_send(cbs, file_transfer_send); linphone_chat_room_send_chat_message(chat_room,message); CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&marie->stat.number_of_LinphoneMessageReceivedWithFile,1)); fclose(file_to_send); if (marie->stat.last_received_chat_message ) { cbs = linphone_chat_message_get_callbacks(marie->stat.last_received_chat_message); linphone_chat_message_cbs_set_msg_state_changed(cbs, liblinphone_tester_chat_message_msg_state_changed); linphone_chat_message_cbs_set_file_transfer_recv(cbs, file_transfer_received); linphone_chat_message_download_file(marie->stat.last_received_chat_message); } CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&marie->stat.number_of_LinphoneMessageExtBodyReceived,1)); CU_ASSERT_EQUAL(pauline->stat.number_of_LinphoneMessageInProgress,1); CU_ASSERT_EQUAL(pauline->stat.number_of_LinphoneMessageDelivered,1); CU_ASSERT_EQUAL(marie->stat.number_of_LinphoneMessageExtBodyReceived,1); CU_ASSERT_TRUE(compare_files(send_filepath, receive_filepath)); linphone_content_unref(content); linphone_core_manager_destroy(marie); linphone_core_manager_destroy(pauline); ms_free(send_filepath); ms_free(receive_filepath); }