void friend_history_clear(FRIEND *f) { uint8_t path[UTOX_FILE_NAME_LENGTH], *p; message_clear(&messages_friend, &f->msg); { /* We get the file path of the log file */ p = path + datapath(path); if(countof(path) - (p - path) < TOX_PUBLIC_KEY_SIZE * 2 + sizeof(LOGFILE_EXT)) { /* We ensure that we have enough space in the buffer, if not we fail */ debug("error/history_clear: path too long\n"); return; } cid_to_string(p, f->cid); p += TOX_PUBLIC_KEY_SIZE * 2; memcpy((char*)p, LOGFILE_EXT, sizeof(LOGFILE_EXT)); } remove((const char *)path); }
/* Writes log filename for fid to dest. returns length written */ static int log_file_name(uint8_t *dest, size_t size_dest, Tox *tox, int fid) { if (size_dest < TOX_CLIENT_ID_SIZE * 2 + sizeof(".txt")) return -1; uint8_t client_id[TOX_CLIENT_ID_SIZE]; tox_get_client_id(tox, fid, client_id); cid_to_string(dest, client_id); dest += TOX_CLIENT_ID_SIZE * 2; memcpy((char*)dest, ".txt", sizeof(".txt")); return TOX_CLIENT_ID_SIZE * 2 + sizeof(".txt"); }
void log_write(Tox *tox, int fid, const uint8_t *message, uint16_t length, _Bool self) { if(!logging_enabled) { return; } uint8_t path[512], *p; uint8_t name[TOX_MAX_NAME_LENGTH]; int namelen; uint8_t client_id[TOX_CLIENT_ID_SIZE]; FILE *file; p = path + datapath(path); tox_get_client_id(tox, fid, client_id); cid_to_string(p, client_id); p += TOX_CLIENT_ID_SIZE * 2; strcpy((char*)p, ".txt"); file = fopen((char*)path, "ab"); if(file) { time_t rawtime; time(&rawtime); if(self) { namelen = tox_get_self_name(tox, name); } else if((namelen = tox_get_name(tox, fid, name)) == -1) { //error reading name namelen = 0; } struct { uint64_t time; uint16_t namelen, length; uint8_t flags, zeroes[3]; } header = { .time = rawtime, .namelen = namelen, .length = length, .flags = self, }; fwrite(&header, sizeof(header), 1, file); fwrite(name, namelen, 1, file); fwrite(message, length, 1, file); fclose(file); } }
// Checks if a user is in the Messaging Menu _Bool is_in_mm(uint8_t *f_id) { if(f_id == NULL) { strcpy((char*)f_id_data, (char*)f_id_data_on_minimize); } else { cid_to_string(f_id_data, f_id); f_id_data[TOX_PUBLIC_KEY_SIZE * 2] = '\0'; } if(f_id_data[0] != '\0') { if(messaging_menu_app_has_source(mmapp, (gchar*)f_id_data)) { return 1; } } return 0; }
void utox_friend_init(Tox *tox, uint32_t friend_number){ int size; // get friend pointer FRIEND *f = &friend[friend_number]; uint8_t name[TOX_MAX_NAME_LENGTH]; // Set scroll position to bottom of window. f->msg.scroll = 1.0; // Get and set the public key for this friend number and set it. tox_friend_get_public_key(tox, friend_number, f->cid, 0); // Set the friend number we got from toxcore f->number = friend_number; // Get and set friend name and length size = tox_friend_get_name_size(tox, friend_number, 0); tox_friend_get_name(tox, friend_number, name, 0); // Set the name for utox as well friend_setname(f, name, size); // Get and set the status message size = tox_friend_get_status_message_size(tox, friend_number, 0); f->status_message = malloc(size); tox_friend_get_status_message(tox, friend_number, f->status_message, 0); f->status_length = size; // Get the hex version of this friends ID char_t cid[TOX_PUBLIC_KEY_SIZE * 2]; cid_to_string(cid, f->cid); init_avatar(&f->avatar, cid, NULL, NULL); // Get the chat backlog log_read(tox, friend_number); // Load the meta data, if it exists. friend_meta_data_read(tox, friend_number); }
void log_read(Tox *tox, int fid) { uint8_t path[512], *p, *pp, *end; uint8_t client_id[TOX_CLIENT_ID_SIZE]; uint32_t size, i; p = path + datapath(path); tox_get_client_id(tox, fid, client_id); cid_to_string(p, client_id); p += TOX_CLIENT_ID_SIZE * 2; strcpy((char*)p, ".txt"); p = pp = file_raw((char*)path, &size); if(!p) { return; } end = p + size; /* todo: some checks to avoid crashes with corrupted log files */ /* first find the last 128 messages in the log */ i = 0; while(p < end) { uint16_t namelen, length; memcpy(&namelen, p + 8, 2); memcpy(&length, p + 10, 2); p += 16 + namelen + length;; if(++i > 128) { memcpy(&namelen, pp + 8, 2); memcpy(&length, pp + 10, 2); pp += 16 + namelen + length; } } if(i > 128) { i = 128; } MSG_DATA *m = &friend[fid].msg; m->data = malloc(sizeof(void*) * i); m->n = i; i = 0; /* add the messages */ p = pp; while(p < end) { uint64_t time; uint16_t namelen, length; uint8_t flags; memcpy(&time, p, 8); memcpy(&namelen, p + 8, 2); memcpy(&length, p + 10, 2); flags = p[12]; p += 16; MESSAGE *msg = malloc(sizeof(MESSAGE) + length); msg->flags = flags; msg->length = length; memcpy(msg->msg, p + namelen, length); struct tm *ti; time_t rawtime = time; ti = localtime(&rawtime); msg->time = ti->tm_hour * 60 + ti->tm_min; m->data[i++] = msg; debug("loaded backlog: %.*s: %.*s\n", namelen, p, length, p + namelen); p += namelen + length; } }