diff options
author | Alexander Lantsev <aunsane@gmail.com> | 2015-01-03 08:12:27 +0000 |
---|---|---|
committer | Alexander Lantsev <aunsane@gmail.com> | 2015-01-03 08:12:27 +0000 |
commit | f1f8a71bd4df7f239e28a9625b82ee02428c3f3f (patch) | |
tree | 9bfbccff9826c0cb530805eec4373a1365122201 /protocols/Tox/include | |
parent | c42d4e21629ebefaf5a720c5270e77187edfc720 (diff) |
Tox: work commit
- removed *.lib and lib generator
- disabled profile encryption and import
- loading tox profile on connection
- project reordering
- http proxy support
git-svn-id: http://svn.miranda-ng.org/main/trunk@11730 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c
Diffstat (limited to 'protocols/Tox/include')
-rw-r--r-- | protocols/Tox/include/tox.h | 951 | ||||
-rw-r--r-- | protocols/Tox/include/toxav.h | 329 | ||||
-rw-r--r-- | protocols/Tox/include/toxdns.h | 96 | ||||
-rw-r--r-- | protocols/Tox/include/toxencryptsave.h | 196 |
4 files changed, 1572 insertions, 0 deletions
diff --git a/protocols/Tox/include/tox.h b/protocols/Tox/include/tox.h new file mode 100644 index 0000000000..db1b10331c --- /dev/null +++ b/protocols/Tox/include/tox.h @@ -0,0 +1,951 @@ +/* tox.h + * + * The Tox public API. + * + * Copyright (C) 2013 Tox project All Rights Reserved. + * + * This file is part of Tox. + * + * Tox is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tox is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tox. If not, see <http://www.gnu.org/licenses/>. + * + */ + +#ifndef TOX_H +#define TOX_H + +#include <stdint.h> + + +#ifdef __cplusplus +extern "C" { +#endif + +#define TOX_MAX_NAME_LENGTH 128 + +/* Maximum length of single messages after which they should be split. */ +#define TOX_MAX_MESSAGE_LENGTH 1368 +#define TOX_MAX_STATUSMESSAGE_LENGTH 1007 +#define TOX_MAX_FRIENDREQUEST_LENGTH 1016 + +#define TOX_CLIENT_ID_SIZE 32 +#define TOX_AVATAR_MAX_DATA_LENGTH 16384 +#define TOX_HASH_LENGTH /*crypto_hash_sha256_BYTES*/ 32 + +#define TOX_FRIEND_ADDRESS_SIZE (TOX_CLIENT_ID_SIZE + sizeof(uint32_t) + sizeof(uint16_t)) + +#define TOX_ENABLE_IPV6_DEFAULT 1 + +#define TOX_ENC_SAVE_MAGIC_NUMBER "toxEsave" +#define TOX_ENC_SAVE_MAGIC_LENGTH 8 + +/* Errors for m_addfriend + * FAERR - Friend Add Error + */ +enum { + TOX_FAERR_TOOLONG = -1, + TOX_FAERR_NOMESSAGE = -2, + TOX_FAERR_OWNKEY = -3, + TOX_FAERR_ALREADYSENT = -4, + TOX_FAERR_UNKNOWN = -5, + TOX_FAERR_BADCHECKSUM = -6, + TOX_FAERR_SETNEWNOSPAM = -7, + TOX_FAERR_NOMEM = -8 +}; + +/* USERSTATUS - + * Represents userstatuses someone can have. + */ +typedef enum { + TOX_USERSTATUS_NONE, + TOX_USERSTATUS_AWAY, + TOX_USERSTATUS_BUSY, + TOX_USERSTATUS_INVALID +} +TOX_USERSTATUS; + + +/* AVATAR_FORMAT - + * Data formats for user avatar images + */ +typedef enum { + TOX_AVATAR_FORMAT_NONE = 0, + TOX_AVATAR_FORMAT_PNG +} +TOX_AVATAR_FORMAT; + +#ifndef __TOX_DEFINED__ +#define __TOX_DEFINED__ +typedef struct Tox Tox; +#endif + +/* NOTE: Strings in Tox are all UTF-8, (This means that there is no terminating NULL character.) + * + * The exact buffer you send will be received at the other end without modification. + * + * Do not treat Tox strings as C strings. + */ + +/* return TOX_FRIEND_ADDRESS_SIZE byte address to give to others. + * format: [client_id (32 bytes)][nospam number (4 bytes)][checksum (2 bytes)] + */ +void tox_get_address(const Tox *tox, uint8_t *address); + +/* Add a friend. + * Set the data that will be sent along with friend request. + * address is the address of the friend (returned by getaddress of the friend you wish to add) it must be TOX_FRIEND_ADDRESS_SIZE bytes. TODO: add checksum. + * data is the data and length is the length (maximum length of data is TOX_MAX_FRIENDREQUEST_LENGTH). + * + * return the friend number if success. + * return TOX_FAERR_TOOLONG if message length is too long. + * return TOX_FAERR_NOMESSAGE if no message (message length must be >= 1 byte). + * return TOX_FAERR_OWNKEY if user's own key. + * return TOX_FAERR_ALREADYSENT if friend request already sent or already a friend. + * return TOX_FAERR_UNKNOWN for unknown error. + * return TOX_FAERR_BADCHECKSUM if bad checksum in address. + * return TOX_FAERR_SETNEWNOSPAM if the friend was already there but the nospam was different. + * (the nospam for that friend was set to the new one). + * return TOX_FAERR_NOMEM if increasing the friend list size fails. + */ +int32_t tox_add_friend(Tox *tox, const uint8_t *address, const uint8_t *data, uint16_t length); + + +/* Add a friend without sending a friendrequest. + * return the friend number if success. + * return -1 if failure. + */ +int32_t tox_add_friend_norequest(Tox *tox, const uint8_t *client_id); + +/* return the friend number associated to that client id. + return -1 if no such friend */ +int32_t tox_get_friend_number(const Tox *tox, const uint8_t *client_id); + +/* Copies the public key associated to that friend id into client_id buffer. + * Make sure that client_id is of size CLIENT_ID_SIZE. + * return 0 if success. + * return -1 if failure. + */ +int tox_get_client_id(const Tox *tox, int32_t friendnumber, uint8_t *client_id); + +/* Remove a friend. + * + * return 0 if success. + * return -1 if failure. + */ +int tox_del_friend(Tox *tox, int32_t friendnumber); + +/* Checks friend's connecting status. + * + * return 1 if friend is connected to us (Online). + * return 0 if friend is not connected to us (Offline). + * return -1 on failure. + */ +int tox_get_friend_connection_status(const Tox *tox, int32_t friendnumber); + +/* Checks if there exists a friend with given friendnumber. + * + * return 1 if friend exists. + * return 0 if friend doesn't exist. + */ +int tox_friend_exists(const Tox *tox, int32_t friendnumber); + +/* Send a text chat message to an online friend. + * + * return the message id if packet was successfully put into the send queue. + * return 0 if it was not. + * + * maximum length of messages is TOX_MAX_MESSAGE_LENGTH, your client must split larger messages + * or else sending them will not work. No the core will not split messages for you because that + * requires me to parse UTF-8. + * + * You will want to retain the return value, it will be passed to your read_receipt callback + * if one is received. + */ +uint32_t tox_send_message(Tox *tox, int32_t friendnumber, const uint8_t *message, uint32_t length); + +/* Send an action to an online friend. + * + * return the message id if packet was successfully put into the send queue. + * return 0 if it was not. + * + * maximum length of actions is TOX_MAX_MESSAGE_LENGTH, your client must split larger actions + * or else sending them will not work. No the core will not split actions for you because that + * requires me to parse UTF-8. + * + * You will want to retain the return value, it will be passed to your read_receipt callback + * if one is received. + */ +uint32_t tox_send_action(Tox *tox, int32_t friendnumber, const uint8_t *action, uint32_t length); + +/* Set our nickname. + * name must be a string of maximum MAX_NAME_LENGTH length. + * length must be at least 1 byte. + * length is the length of name. + * + * return 0 if success. + * return -1 if failure. + */ +int tox_set_name(Tox *tox, const uint8_t *name, uint16_t length); + +/* + * Get your nickname. + * m - The messenger context to use. + * name - needs to be a valid memory location with a size of at least MAX_NAME_LENGTH (128) bytes. + * + * return length of name. + * return 0 on error. + */ +uint16_t tox_get_self_name(const Tox *tox, uint8_t *name); + +/* Get name of friendnumber and put it in name. + * name needs to be a valid memory location with a size of at least MAX_NAME_LENGTH (128) bytes. + * + * return length of name if success. + * return -1 if failure. + */ +int tox_get_name(const Tox *tox, int32_t friendnumber, uint8_t *name); + +/* returns the length of name on success. + * returns -1 on failure. + */ +int tox_get_name_size(const Tox *tox, int32_t friendnumber); +int tox_get_self_name_size(const Tox *tox); + +/* Set our user status. + * + * userstatus must be one of TOX_USERSTATUS values. + * max length of the status is TOX_MAX_STATUSMESSAGE_LENGTH. + * + * returns 0 on success. + * returns -1 on failure. + */ +int tox_set_status_message(Tox *tox, const uint8_t *status, uint16_t length); +int tox_set_user_status(Tox *tox, uint8_t userstatus); + +/* returns the length of status message on success. + * returns -1 on failure. + */ +int tox_get_status_message_size(const Tox *tox, int32_t friendnumber); +int tox_get_self_status_message_size(const Tox *tox); + +/* Copy friendnumber's status message into buf, truncating if size is over maxlen. + * Get the size you need to allocate from m_get_statusmessage_size. + * The self variant will copy our own status message. + * + * returns the length of the copied data on success + * retruns -1 on failure. + */ +int tox_get_status_message(const Tox *tox, int32_t friendnumber, uint8_t *buf, uint32_t maxlen); +int tox_get_self_status_message(const Tox *tox, uint8_t *buf, uint32_t maxlen); + +/* return one of TOX_USERSTATUS values. + * Values unknown to your application should be represented as TOX_USERSTATUS_NONE. + * As above, the self variant will return our own TOX_USERSTATUS. + * If friendnumber is invalid, this shall return TOX_USERSTATUS_INVALID. + */ +uint8_t tox_get_user_status(const Tox *tox, int32_t friendnumber); +uint8_t tox_get_self_user_status(const Tox *tox); + +/* returns timestamp of last time friendnumber was seen online, or 0 if never seen. + * returns -1 on error. + */ +uint64_t tox_get_last_online(const Tox *tox, int32_t friendnumber); + +/* Set our typing status for a friend. + * You are responsible for turning it on or off. + * + * returns 0 on success. + * returns -1 on failure. + */ +int tox_set_user_is_typing(Tox *tox, int32_t friendnumber, uint8_t is_typing); + +/* Get the typing status of a friend. + * + * returns 0 if friend is not typing. + * returns 1 if friend is typing. + */ +uint8_t tox_get_is_typing(const Tox *tox, int32_t friendnumber); + +/* Return the number of friends in the instance m. + * You should use this to determine how much memory to allocate + * for copy_friendlist. */ +uint32_t tox_count_friendlist(const Tox *tox); + +/* Return the number of online friends in the instance m. */ +uint32_t tox_get_num_online_friends(const Tox *tox); + +/* Copy a list of valid friend IDs into the array out_list. + * If out_list is NULL, returns 0. + * Otherwise, returns the number of elements copied. + * If the array was too small, the contents + * of out_list will be truncated to list_size. */ +uint32_t tox_get_friendlist(const Tox *tox, int32_t *out_list, uint32_t list_size); + +/* Set the function that will be executed when a friend request is received. + * Function format is function(Tox *tox, const uint8_t * public_key, const uint8_t * data, uint16_t length, void *userdata) + */ +void tox_callback_friend_request(Tox *tox, void (*function)(Tox *tox, const uint8_t *, const uint8_t *, uint16_t, + void *), void *userdata); + +/* Set the function that will be executed when a message from a friend is received. + * Function format is: function(Tox *tox, int32_t friendnumber, const uint8_t * message, uint16_t length, void *userdata) + */ +void tox_callback_friend_message(Tox *tox, void (*function)(Tox *tox, int32_t, const uint8_t *, uint16_t, void *), + void *userdata); + +/* Set the function that will be executed when an action from a friend is received. + * Function format is: function(Tox *tox, int32_t friendnumber, const uint8_t * action, uint16_t length, void *userdata) + */ +void tox_callback_friend_action(Tox *tox, void (*function)(Tox *tox, int32_t, const uint8_t *, uint16_t, void *), + void *userdata); + +/* Set the callback for name changes. + * function(Tox *tox, int32_t friendnumber, const uint8_t *newname, uint16_t length, void *userdata) + * You are not responsible for freeing newname + */ +void tox_callback_name_change(Tox *tox, void (*function)(Tox *tox, int32_t, const uint8_t *, uint16_t, void *), + void *userdata); + +/* Set the callback for status message changes. + * function(Tox *tox, int32_t friendnumber, const uint8_t *newstatus, uint16_t length, void *userdata) + * You are not responsible for freeing newstatus. + */ +void tox_callback_status_message(Tox *tox, void (*function)(Tox *tox, int32_t, const uint8_t *, uint16_t, void *), + void *userdata); + +/* Set the callback for status type changes. + * function(Tox *tox, int32_t friendnumber, uint8_t TOX_USERSTATUS, void *userdata) + */ +void tox_callback_user_status(Tox *tox, void (*function)(Tox *tox, int32_t, uint8_t, void *), void *userdata); + +/* Set the callback for typing changes. + * function (Tox *tox, int32_t friendnumber, uint8_t is_typing, void *userdata) + */ +void tox_callback_typing_change(Tox *tox, void (*function)(Tox *tox, int32_t, uint8_t, void *), void *userdata); + +/* Set the callback for read receipts. + * function(Tox *tox, int32_t friendnumber, uint32_t receipt, void *userdata) + * + * If you are keeping a record of returns from m_sendmessage; + * receipt might be one of those values, meaning the message + * has been received on the other side. + * Since core doesn't track ids for you, receipt may not correspond to any message. + * In that case, you should discard it. + */ +void tox_callback_read_receipt(Tox *tox, void (*function)(Tox *tox, int32_t, uint32_t, void *), void *userdata); + +/* Set the callback for connection status changes. + * function(Tox *tox, int32_t friendnumber, uint8_t status, void *userdata) + * + * Status: + * 0 -- friend went offline after being previously online + * 1 -- friend went online + * + * NOTE: This callback is not called when adding friends, thus the "after + * being previously online" part. it's assumed that when adding friends, + * their connection status is offline. + */ +void tox_callback_connection_status(Tox *tox, void (*function)(Tox *tox, int32_t, uint8_t, void *), void *userdata); + + +/**********ADVANCED FUNCTIONS (If you don't know what they do you can safely ignore them.) ************/ + +/* Functions to get/set the nospam part of the id. + */ +uint32_t tox_get_nospam(const Tox *tox); +void tox_set_nospam(Tox *tox, uint32_t nospam); + +/* Copy the public and secret key from the Tox object. + public_key and secret_key must be 32 bytes big. + if the pointer is NULL, no data will be copied to it.*/ +void tox_get_keys(Tox *tox, uint8_t *public_key, uint8_t *secret_key); + +/* Maximum size of custom packets. */ +#define TOX_MAX_CUSTOM_PACKET_SIZE 1373 + +/* Set handlers for custom lossy packets. + * Set the function to be called when friend sends us a lossy packet starting with byte. + * byte must be in the 200-254 range. + * + * NOTE: lossy packets behave like UDP packets meaning they might never reach the other side + * or might arrive more than once (if someone is messing with the connection) or might arrive + * in the wrong order. + * + * Unless latency is an issue, it is recommended that you use lossless packets instead. + * + * return -1 on failure. + * return 0 on success. + */ +int tox_lossy_packet_registerhandler(Tox *tox, int32_t friendnumber, uint8_t byte, + int (*packet_handler_callback)(Tox *tox, int32_t friendnumber, const uint8_t *data, uint32_t len, void *object), + void *object); + +/* Function to send custom lossy packets. + * First byte of data must be in the range: 200-254. + * + * return -1 on failure. + * return 0 on success. + */ +int tox_send_lossy_packet(const Tox *tox, int32_t friendnumber, const uint8_t *data, uint32_t length); + +/* Set handlers for custom lossless packets. + * Set the function to be called when friend sends us a lossless packet starting with byte. + * byte must be in the 160-191 range. + * + * Lossless packets behave kind of like TCP (reliability, arrive in order.) but with packets instead of a stream. + * + * return -1 on failure. + * return 0 on success. + */ +int tox_lossless_packet_registerhandler(Tox *tox, int32_t friendnumber, uint8_t byte, + int (*packet_handler_callback)(Tox *tox, int32_t friendnumber, const uint8_t *data, uint32_t len, void *object), + void *object); + +/* Function to send custom lossless packets. + * First byte of data must be in the range: 160-191. + * + * return -1 on failure. + * return 0 on success. + */ +int tox_send_lossless_packet(const Tox *tox, int32_t friendnumber, const uint8_t *data, uint32_t length); + +/**********GROUP CHAT FUNCTIONS: WARNING Group chats will be rewritten so this might change ************/ + +/* Group chat types for tox_callback_group_invite function. + * + * TOX_GROUPCHAT_TYPE_TEXT groupchats must be accepted with the tox_join_groupchat() function. + * The function to accept TOX_GROUPCHAT_TYPE_AV is in toxav. + */ +enum { + TOX_GROUPCHAT_TYPE_TEXT, + TOX_GROUPCHAT_TYPE_AV +}; + +/* Set the callback for group invites. + * + * Function(Tox *tox, int32_t friendnumber, uint8_t type, const uint8_t *data, uint16_t length, void *userdata) + * + * data of length is what needs to be passed to join_groupchat(). + * + * for what type means see the enum right above this comment. + */ +void tox_callback_group_invite(Tox *tox, void (*function)(Tox *tox, int32_t, uint8_t, const uint8_t *, uint16_t, + void *), void *userdata); + +/* Set the callback for group messages. + * + * Function(Tox *tox, int groupnumber, int peernumber, const uint8_t * message, uint16_t length, void *userdata) + */ +void tox_callback_group_message(Tox *tox, void (*function)(Tox *tox, int, int, const uint8_t *, uint16_t, void *), + void *userdata); + +/* Set the callback for group actions. + * + * Function(Tox *tox, int groupnumber, int peernumber, const uint8_t * action, uint16_t length, void *userdata) + */ +void tox_callback_group_action(Tox *tox, void (*function)(Tox *tox, int, int, const uint8_t *, uint16_t, void *), + void *userdata); + +/* Set callback function for title changes. + * + * Function(Tox *tox, int groupnumber, int peernumber, uint8_t * title, uint8_t length, void *userdata) + * if peernumber == -1, then author is unknown (e.g. initial joining the group) + */ +void tox_callback_group_title(Tox *tox, void (*function)(Tox *tox, int, int, const uint8_t *, uint8_t, + void *), void *userdata); + +/* Set callback function for peer name list changes. + * + * It gets called every time the name list changes(new peer/name, deleted peer) + * Function(Tox *tox, int groupnumber, int peernumber, TOX_CHAT_CHANGE change, void *userdata) + */ +typedef enum { + TOX_CHAT_CHANGE_PEER_ADD, + TOX_CHAT_CHANGE_PEER_DEL, + TOX_CHAT_CHANGE_PEER_NAME, +} TOX_CHAT_CHANGE; + +void tox_callback_group_namelist_change(Tox *tox, void (*function)(Tox *tox, int, int, uint8_t, void *), + void *userdata); + +/* Creates a new groupchat and puts it in the chats array. + * + * return group number on success. + * return -1 on failure. + */ +int tox_add_groupchat(Tox *tox); + +/* Delete a groupchat from the chats array. + * + * return 0 on success. + * return -1 if failure. + */ +int tox_del_groupchat(Tox *tox, int groupnumber); + +/* Copy the name of peernumber who is in groupnumber to name. + * name must be at least TOX_MAX_NAME_LENGTH long. + * + * return length of name if success + * return -1 if failure + */ +int tox_group_peername(const Tox *tox, int groupnumber, int peernumber, uint8_t *name); + +/* Copy the public key of peernumber who is in groupnumber to pk. + * pk must be TOX_CLIENT_ID_SIZE long. + * + * returns 0 on success + * returns -1 on failure + */ +int tox_group_peer_pubkey(const Tox *tox, int groupnumber, int peernumber, uint8_t *pk); + +/* invite friendnumber to groupnumber + * return 0 on success + * return -1 on failure + */ +int tox_invite_friend(Tox *tox, int32_t friendnumber, int groupnumber); + +/* Join a group (you need to have been invited first.) using data of length obtained + * in the group invite callback. + * + * returns group number on success + * returns -1 on failure. + */ +int tox_join_groupchat(Tox *tox, int32_t friendnumber, const uint8_t *data, uint16_t length); + +/* send a group message + * return 0 on success + * return -1 on failure + */ +int tox_group_message_send(Tox *tox, int groupnumber, const uint8_t *message, uint16_t length); + +/* send a group action + * return 0 on success + * return -1 on failure + */ +int tox_group_action_send(Tox *tox, int groupnumber, const uint8_t *action, uint16_t length); + +/* set the group's title, limited to MAX_NAME_LENGTH + * return 0 on success + * return -1 on failure + */ +int tox_group_set_title(Tox *tox, int groupnumber, const uint8_t *title, uint8_t length); + +/* Get group title from groupnumber and put it in title. + * title needs to be a valid memory location with a max_length size of at least MAX_NAME_LENGTH (128) bytes. + * + * return length of copied title if success. + * return -1 if failure. + */ +int tox_group_get_title(Tox *tox, int groupnumber, uint8_t *title, uint32_t max_length); + +/* Check if the current peernumber corresponds to ours. + * + * return 1 if the peernumber corresponds to ours. + * return 0 on failure. + */ +unsigned int tox_group_peernumber_is_ours(const Tox *tox, int groupnumber, int peernumber); + +/* Return the number of peers in the group chat on success. + * return -1 on failure + */ +int tox_group_number_peers(const Tox *tox, int groupnumber); + +/* List all the peers in the group chat. + * + * Copies the names of the peers to the name[length][TOX_MAX_NAME_LENGTH] array. + * + * Copies the lengths of the names to lengths[length] + * + * returns the number of peers on success. + * + * return -1 on failure. + */ +int tox_group_get_names(const Tox *tox, int groupnumber, uint8_t names[][TOX_MAX_NAME_LENGTH], uint16_t lengths[], + uint16_t length); + +/* Return the number of chats in the instance m. + * You should use this to determine how much memory to allocate + * for copy_chatlist. */ +uint32_t tox_count_chatlist(const Tox *tox); + +/* Copy a list of valid chat IDs into the array out_list. + * If out_list is NULL, returns 0. + * Otherwise, returns the number of elements copied. + * If the array was too small, the contents + * of out_list will be truncated to list_size. */ +uint32_t tox_get_chatlist(const Tox *tox, int32_t *out_list, uint32_t list_size); + +/* return the type of groupchat (TOX_GROUPCHAT_TYPE_) that groupnumber is. + * + * return -1 on failure. + * return type on success. + */ +int tox_group_get_type(const Tox *tox, int groupnumber); + +/****************AVATAR FUNCTIONS*****************/ + +/* Set the callback function for avatar information. + * This callback will be called when avatar information are received from friends. These events + * can arrive at anytime, but are usually received uppon connection and in reply of avatar + * information requests. + * + * Function format is: + * function(Tox *tox, int32_t friendnumber, uint8_t format, uint8_t *hash, void *userdata) + * + * where 'format' is the avatar image format (see TOX_AVATAR_FORMAT) and 'hash' is the hash of + * the avatar data for caching purposes and it is exactly TOX_HASH_LENGTH long. If the image + * format is NONE, the hash is zeroed. + * + */ +void tox_callback_avatar_info(Tox *tox, void (*function)(Tox *tox, int32_t, uint8_t, uint8_t *, void *), + void *userdata); + + +/* Set the callback function for avatar data. + * This callback will be called when the complete avatar data was correctly received from a + * friend. This only happens in reply of a avatar data request (see tox_request_avatar_data); + * + * Function format is: + * function(Tox *tox, int32_t friendnumber, uint8_t format, uint8_t *hash, uint8_t *data, uint32_t datalen, void *userdata) + * + * where 'format' is the avatar image format (see TOX_AVATAR_FORMAT); 'hash' is the + * locally-calculated cryptographic hash of the avatar data and it is exactly + * TOX_HASH_LENGTH long; 'data' is the avatar image data and 'datalen' is the length + * of such data. + * + * If format is NONE, 'data' is NULL, 'datalen' is zero, and the hash is zeroed. The hash is + * always validated locally with the function tox_hash and ensured to match the image data, + * so this value can be safely used to compare with cached avatars. + * + * WARNING: users MUST treat all avatar image data received from another peer as untrusted and + * potentially malicious. The library only ensures that the data which arrived is the same the + * other user sent, and does not interpret or validate any image data. + */ +void tox_callback_avatar_data(Tox *tox, void (*function)(Tox *tox, int32_t, uint8_t, uint8_t *, uint8_t *, uint32_t, + void *), void *userdata); + +/* Set the user avatar image data. + * This should be made before connecting, so we will not announce that the user have no avatar + * before setting and announcing a new one, forcing the peers to re-download it. + * + * Notice that the library treats the image as raw data and does not interpret it by any way. + * + * Arguments: + * format - Avatar image format or NONE for user with no avatar (see TOX_AVATAR_FORMAT); + * data - pointer to the avatar data (may be NULL it the format is NONE); + * length - length of image data. Must be <= TOX_AVATAR_MAX_DATA_LENGTH. + * + * returns 0 on success + * returns -1 on failure. + */ +int tox_set_avatar(Tox *tox, uint8_t format, const uint8_t *data, uint32_t length); + +/* Unsets the user avatar. + + returns 0 on success (currently always returns 0) */ +int tox_unset_avatar(Tox *tox); + +/* Get avatar data from the current user. + * Copies the current user avatar data to the destination buffer and sets the image format + * accordingly. + * + * If the avatar format is NONE, the buffer 'buf' isleft uninitialized, 'hash' is zeroed, and + * 'length' is set to zero. + * + * If any of the pointers format, buf, length, and hash are NULL, that particular field will be ignored. + * + * Arguments: + * format - destination pointer to the avatar image format (see TOX_AVATAR_FORMAT); + * buf - destination buffer to the image data. Must have at least 'maxlen' bytes; + * length - destination pointer to the image data length; + * maxlen - length of the destination buffer 'buf'; + * hash - destination pointer to the avatar hash (it must be exactly TOX_HASH_LENGTH bytes long). + * + * returns 0 on success; + * returns -1 on failure. + * + */ +int tox_get_self_avatar(const Tox *tox, uint8_t *format, uint8_t *buf, uint32_t *length, uint32_t maxlen, + uint8_t *hash); + + +/* Generates a cryptographic hash of the given data. + * This function may be used by clients for any purpose, but is provided primarily for + * validating cached avatars. This use is highly recommended to avoid unnecessary avatar + * updates. + * This function is a wrapper to internal message-digest functions. + * + * Arguments: + * hash - destination buffer for the hash data, it must be exactly TOX_HASH_LENGTH bytes long. + * data - data to be hashed; + * datalen - length of the data; for avatars, should be TOX_AVATAR_MAX_DATA_LENGTH + * + * returns 0 on success + * returns -1 on failure. + */ +int tox_hash(uint8_t *hash, const uint8_t *data, const uint32_t datalen); + +/* Request avatar information from a friend. + * Asks a friend to provide their avatar information (image format and hash). The friend may + * or may not answer this request and, if answered, the information will be provided through + * the callback 'avatar_info'. + * + * returns 0 on success + * returns -1 on failure. + */ +int tox_request_avatar_info(const Tox *tox, const int32_t friendnumber); + + +/* Send an unrequested avatar information to a friend. + * Sends our avatar format and hash to a friend; he/she can use this information to validate + * an avatar from the cache and may (or not) reply with an avatar data request. + * + * Notice: it is NOT necessary to send these notification after changing the avatar or + * connecting. The library already does this. + * + * returns 0 on success + * returns -1 on failure. + */ +int tox_send_avatar_info(Tox *tox, const int32_t friendnumber); + + +/* Request the avatar data from a friend. + * Ask a friend to send their avatar data. The friend may or may not answer this request and, + * if answered, the information will be provided in callback 'avatar_data'. + * + * returns 0 on sucess + * returns -1 on failure. + */ +int tox_request_avatar_data(const Tox *tox, const int32_t friendnumber); + +/****************FILE SENDING FUNCTIONS*****************/ +/* NOTE: This how to will be updated. + * + * HOW TO SEND FILES CORRECTLY: + * 1. Use tox_new_file_sender(...) to create a new file sender. + * 2. Wait for the callback set with tox_callback_file_control(...) to be called with receive_send == 1 and control_type == TOX_FILECONTROL_ACCEPT + * 3. Send the data with tox_file_send_data(...) with chunk size tox_file_data_size(...) + * 4. When sending is done, send a tox_file_send_control(...) with send_receive = 0 and message_id = TOX_FILECONTROL_FINISHED + * 5. when the callback set with tox_callback_file_control(...) is called with receive_send == 1 and control_type == TOX_FILECONTROL_FINISHED + * the other person has received the file correctly. + * + * HOW TO RECEIVE FILES CORRECTLY: + * 1. wait for the callback set with tox_callback_file_send_request(...) + * 2. accept or refuse the connection with tox_file_send_control(...) with send_receive = 1 and message_id = TOX_FILECONTROL_ACCEPT or TOX_FILECONTROL_KILL + * 3. save all the data received with the callback set with tox_callback_file_data(...) to a file. + * 4. when the callback set with tox_callback_file_control(...) is called with receive_send == 0 and control_type == TOX_FILECONTROL_FINISHED + * the file is done transferring. + * 5. send a tox_file_send_control(...) with send_receive = 1 and message_id = TOX_FILECONTROL_FINISHED to confirm that we did receive the file. + * + * tox_file_data_remaining(...) can be used to know how many bytes are left to send/receive. + * + * If the connection breaks during file sending (The other person goes offline without pausing the sending and then comes back) + * the receiver must send a control packet with send_receive == 1 message_id = TOX_FILECONTROL_RESUME_BROKEN and the data being + * a uint64_t (in host byte order) containing the number of bytes received. + * + * If the sender receives this packet, he must send a control packet with send_receive == 0 and control_type == TOX_FILECONTROL_ACCEPT + * then he must start sending file data from the position (data , uint64_t in host byte order) received in the TOX_FILECONTROL_RESUME_BROKEN packet. + * + * To pause a file transfer send a control packet with control_type == TOX_FILECONTROL_PAUSE. + * To unpause a file transfer send a control packet with control_type == TOX_FILECONTROL_ACCEPT. + * + * If you receive a control packet with receive_send == 1 and control_type == TOX_FILECONTROL_PAUSE, you must stop sending filenumber until the other + * person sends a control packet with send_receive == 0 and control_type == TOX_FILECONTROL_ACCEPT with the filenumber being a paused filenumber. + * + * If you receive a control packet with receive_send == 0 and control_type == TOX_FILECONTROL_PAUSE, it means the sender of filenumber has paused the + * transfer and will resume it later with a control packet with send_receive == 1 and control_type == TOX_FILECONTROL_ACCEPT for that file number. + * + * More to come... + */ + +enum { + TOX_FILECONTROL_ACCEPT, + TOX_FILECONTROL_PAUSE, + TOX_FILECONTROL_KILL, + TOX_FILECONTROL_FINISHED, + TOX_FILECONTROL_RESUME_BROKEN +}; +/* Set the callback for file send requests. + * + * Function(Tox *tox, int32_t friendnumber, uint8_t filenumber, uint64_t filesize, const uint8_t *filename, uint16_t filename_length, void *userdata) + */ +void tox_callback_file_send_request(Tox *tox, void (*function)(Tox *m, int32_t, uint8_t, uint64_t, const uint8_t *, + uint16_t, void *), void *userdata); + +/* Set the callback for file control requests. + * + * receive_send is 1 if the message is for a slot on which we are currently sending a file and 0 if the message + * is for a slot on which we are receiving the file + * + * Function(Tox *tox, int32_t friendnumber, uint8_t receive_send, uint8_t filenumber, uint8_t control_type, const uint8_t *data, uint16_t length, void *userdata) + * + */ +void tox_callback_file_control(Tox *tox, void (*function)(Tox *m, int32_t, uint8_t, uint8_t, uint8_t, const uint8_t *, + uint16_t, void *), void *userdata); + +/* Set the callback for file data. + * + * Function(Tox *tox, int32_t friendnumber, uint8_t filenumber, const uint8_t *data, uint16_t length, void *userdata) + * + */ +void tox_callback_file_data(Tox *tox, void (*function)(Tox *m, int32_t, uint8_t, const uint8_t *, uint16_t length, + void *), void *userdata); + + +/* Send a file send request. + * Maximum filename length is 255 bytes. + * return file number on success + * return -1 on failure + */ +int tox_new_file_sender(Tox *tox, int32_t friendnumber, uint64_t filesize, const uint8_t *filename, + uint16_t filename_length); + +/* Send a file control request. + * + * send_receive is 0 if we want the control packet to target a file we are currently sending, + * 1 if it targets a file we are currently receiving. + * + * return 0 on success + * return -1 on failure + */ +int tox_file_send_control(Tox *tox, int32_t friendnumber, uint8_t send_receive, uint8_t filenumber, uint8_t message_id, + const uint8_t *data, uint16_t length); + +/* Send file data. + * + * return 0 on success + * return -1 on failure + */ +int tox_file_send_data(Tox *tox, int32_t friendnumber, uint8_t filenumber, const uint8_t *data, uint16_t length); + +/* Returns the recommended/maximum size of the filedata you send with tox_file_send_data() + * + * return size on success + * return -1 on failure (currently will never return -1) + */ +int tox_file_data_size(const Tox *tox, int32_t friendnumber); + +/* Give the number of bytes left to be sent/received. + * + * send_receive is 0 if we want the sending files, 1 if we want the receiving. + * + * return number of bytes remaining to be sent/received on success + * return 0 on failure + */ +uint64_t tox_file_data_remaining(const Tox *tox, int32_t friendnumber, uint8_t filenumber, uint8_t send_receive); + +/***************END OF FILE SENDING FUNCTIONS******************/ + +/* + * Use this function to bootstrap the client. + */ + +/* Resolves address into an IP address. If successful, sends a "get nodes" + * request to the given node with ip, port (in host byte order). + * and public_key to setup connections + * + * address can be a hostname or an IP address (IPv4 or IPv6). + * + * returns 1 if the address could be converted into an IP address + * returns 0 otherwise + */ +int tox_bootstrap_from_address(Tox *tox, const char *address, uint16_t port, const uint8_t *public_key); + +/* Like tox_bootstrap_from_address but for TCP relays only. + * + * return 0 on failure. + * return 1 on success. + */ +int tox_add_tcp_relay(Tox *tox, const char *address, uint16_t port, const uint8_t *public_key); + +/* return 0 if we are not connected to the DHT. + * return 1 if we are. + */ +int tox_isconnected(const Tox *tox); + +typedef enum { + TOX_PROXY_NONE, + TOX_PROXY_SOCKS5, + TOX_PROXY_HTTP +} TOX_PROXY_TYPE; + +typedef struct { + /* + * The type of UDP socket created depends on ipv6enabled: + * If set to 0 (zero), creates an IPv4 socket which subsequently only allows + * IPv4 communication + * If set to anything else (default), creates an IPv6 socket which allows both IPv4 AND + * IPv6 communication + */ + uint8_t ipv6enabled; + + /* Set to 1 to disable udp support. (default: 0) + This will force Tox to use TCP only which may slow things down. + Disabling udp support is necessary when using proxies or Tor.*/ + uint8_t udp_disabled; + uint8_t proxy_type; /* a value from TOX_PROXY_TYPE */ + char proxy_address[256]; /* Proxy ip or domain in NULL terminated string format. */ + uint16_t proxy_port; /* Proxy port in host byte order. */ +} Tox_Options; + +/* + * Run this function at startup. + * + * Options are some options that can be passed to the Tox instance (see above struct). + * + * If options is NULL, tox_new() will use default settings. + * + * Initializes a tox structure + * return allocated instance of tox on success. + * return NULL on failure. + */ +Tox *tox_new(Tox_Options *options); + +/* Run this before closing shop. + * Free all datastructures. */ +void tox_kill(Tox *tox); + +/* Return the time in milliseconds before tox_do() should be called again + * for optimal performance. + * + * returns time (in ms) before the next tox_do() needs to be run on success. + */ +uint32_t tox_do_interval(Tox *tox); + +/* The main loop that needs to be run in intervals of tox_do_interval() ms. */ +void tox_do(Tox *tox); + +/* SAVING AND LOADING FUNCTIONS: */ + +/* return size of messenger data (for saving). */ +uint32_t tox_size(const Tox *tox); + +/* Save the messenger in data (must be allocated memory of size Messenger_size()). */ +void tox_save(const Tox *tox, uint8_t *data); + +/* Load the messenger from data of size length. + * NOTE: The Tox save format isn't stable yet meaning this function sometimes + * returns -1 when loading older saves. This however does not mean nothing was + * loaded from the save. + * + * returns 0 on success + * returns -1 on failure + * returns +1 on finding encrypted save data + */ +int tox_load(Tox *tox, const uint8_t *data, uint32_t length); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/protocols/Tox/include/toxav.h b/protocols/Tox/include/toxav.h new file mode 100644 index 0000000000..3696f96199 --- /dev/null +++ b/protocols/Tox/include/toxav.h @@ -0,0 +1,329 @@ +/** toxav.h + * + * Copyright (C) 2013 Tox project All Rights Reserved. + * + * This file is part of Tox. + * + * Tox is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tox is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tox. If not, see <http://www.gnu.org/licenses/>. + * + */ + + +#ifndef __TOXAV +#define __TOXAV +#include <inttypes.h> + +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct _ToxAv ToxAv; + +/* vpx_image_t */ +#include <vpx/vpx_image.h> + +typedef void ( *ToxAVCallback ) ( void *agent, int32_t call_idx, void *arg ); +typedef void ( *ToxAvAudioCallback ) (void *agent, int32_t call_idx, const int16_t *PCM, uint16_t size, void *data); +typedef void ( *ToxAvVideoCallback ) (void *agent, int32_t call_idx, const vpx_image_t *img, void *data); + +#ifndef __TOX_DEFINED__ +#define __TOX_DEFINED__ +typedef struct Tox Tox; +#endif + +#define RTP_PAYLOAD_SIZE 65535 + + +/** + * Callbacks ids that handle the call states. + */ +typedef enum { + av_OnInvite, /* Incoming call */ + av_OnRinging, /* When peer is ready to accept/reject the call */ + av_OnStart, /* Call (RTP transmission) started */ + av_OnCancel, /* The side that initiated call canceled invite */ + av_OnReject, /* The side that was invited rejected the call */ + av_OnEnd, /* Call that was active ended */ + av_OnRequestTimeout, /* When the requested action didn't get response in specified time */ + av_OnPeerTimeout, /* Peer timed out; stop the call */ + av_OnPeerCSChange, /* Peer changing Csettings. Prepare for changed AV */ + av_OnSelfCSChange /* Csettings change confirmation. Once triggered peer is ready to recv changed AV */ +} ToxAvCallbackID; + + +/** + * Call type identifier. + */ +typedef enum { + av_TypeAudio = 192, + av_TypeVideo +} ToxAvCallType; + + +typedef enum { + av_CallNonExistent = -1, + av_CallInviting, /* when sending call invite */ + av_CallStarting, /* when getting call invite */ + av_CallActive, + av_CallHold, + av_CallHungUp +} ToxAvCallState; + +/** + * Error indicators. Values under -20 are reserved for toxcore. + */ +typedef enum { + av_ErrorNone = 0, + av_ErrorUnknown = -1, /* Unknown error */ + av_ErrorNoCall = -20, /* Trying to perform call action while not in a call */ + av_ErrorInvalidState = -21, /* Trying to perform call action while in invalid state*/ + av_ErrorAlreadyInCallWithPeer = -22, /* Trying to call peer when already in a call with peer */ + av_ErrorReachedCallLimit = -23, /* Cannot handle more calls */ + av_ErrorInitializingCodecs = -30, /* Failed creating CSSession */ + av_ErrorSettingVideoResolution = -31, /* Error setting resolution */ + av_ErrorSettingVideoBitrate = -32, /* Error setting bitrate */ + av_ErrorSplittingVideoPayload = -33, /* Error splitting video payload */ + av_ErrorEncodingVideo = -34, /* vpx_codec_encode failed */ + av_ErrorEncodingAudio = -35, /* opus_encode failed */ + av_ErrorSendingPayload = -40, /* Sending lossy packet failed */ + av_ErrorCreatingRtpSessions = -41, /* One of the rtp sessions failed to initialize */ + av_ErrorNoRtpSession = -50, /* Trying to perform rtp action on invalid session */ + av_ErrorInvalidCodecState = -51, /* Codec state not initialized */ + av_ErrorPacketTooLarge = -52, /* Split packet exceeds it's limit */ +} ToxAvError; + + +/** + * Locally supported capabilities. + */ +typedef enum { + av_AudioEncoding = 1 << 0, + av_AudioDecoding = 1 << 1, + av_VideoEncoding = 1 << 2, + av_VideoDecoding = 1 << 3 +} ToxAvCapabilities; + + +/** + * Encoding settings. + */ +typedef struct _ToxAvCSettings { + ToxAvCallType call_type; + + uint32_t video_bitrate; /* In kbits/s */ + uint16_t max_video_width; /* In px */ + uint16_t max_video_height; /* In px */ + + uint32_t audio_bitrate; /* In bits/s */ + uint16_t audio_frame_duration; /* In ms */ + uint32_t audio_sample_rate; /* In Hz */ + uint32_t audio_channels; +} ToxAvCSettings; + +extern const ToxAvCSettings av_DefaultSettings; + +/** + * Start new A/V session. There can only be one session at the time. + */ +ToxAv *toxav_new(Tox *messenger, int32_t max_calls); + +/** + * Remove A/V session. + */ +void toxav_kill(ToxAv *av); + +/** + * Returns the interval in milliseconds when the next toxav_do() should be called. + * If no call is active at the moment returns 200. + */ +uint32_t toxav_do_interval(ToxAv *av); + +/** + * Main loop for the session. Best called right after tox_do(); + */ +void toxav_do(ToxAv *av); + +/** + * Register callback for call state. + */ +void toxav_register_callstate_callback (ToxAv *av, ToxAVCallback cb, ToxAvCallbackID id, void *userdata); + +/** + * Register callback for audio data. + */ +void toxav_register_audio_callback (ToxAv *av, ToxAvAudioCallback cb, void *userdata); + +/** + * Register callback for video data. + */ +void toxav_register_video_callback (ToxAv *av, ToxAvVideoCallback cb, void *userdata); + +/** + * Call user. Use its friend_id. + */ +int toxav_call(ToxAv *av, + int32_t *call_index, + int friend_id, + const ToxAvCSettings *csettings, + int ringing_seconds); + +/** + * Hangup active call. + */ +int toxav_hangup(ToxAv *av, int32_t call_index); + +/** + * Answer incoming call. Pass the csettings that you will use. + */ +int toxav_answer(ToxAv *av, int32_t call_index, const ToxAvCSettings *csettings ); + +/** + * Reject incoming call. + */ +int toxav_reject(ToxAv *av, int32_t call_index, const char *reason); + +/** + * Cancel outgoing request. + */ +int toxav_cancel(ToxAv *av, int32_t call_index, int peer_id, const char *reason); + +/** + * Notify peer that we are changing codec settings. + */ +int toxav_change_settings(ToxAv *av, int32_t call_index, const ToxAvCSettings *csettings); + +/** + * Terminate transmission. Note that transmission will be + * terminated without informing remote peer. Usually called when we can't inform peer. + */ +int toxav_stop_call(ToxAv *av, int32_t call_index); + +/** + * Allocates transmission data. Must be call before calling toxav_prepare_* and toxav_send_*. + * Also, it must be called when call is started + */ +int toxav_prepare_transmission(ToxAv *av, int32_t call_index, int support_video); + +/** + * Clears transmission data. Call this at the end of the transmission. + */ +int toxav_kill_transmission(ToxAv *av, int32_t call_index); + +/** + * Encode video frame. + */ +int toxav_prepare_video_frame ( ToxAv *av, + int32_t call_index, + uint8_t *dest, + int dest_max, + vpx_image_t *input); + +/** + * Send encoded video packet. + */ +int toxav_send_video ( ToxAv *av, int32_t call_index, const uint8_t *frame, uint32_t frame_size); + +/** + * Encode audio frame. + */ +int toxav_prepare_audio_frame ( ToxAv *av, + int32_t call_index, + uint8_t *dest, + int dest_max, + const int16_t *frame, + int frame_size); + +/** + * Send encoded audio frame. + */ +int toxav_send_audio ( ToxAv *av, int32_t call_index, const uint8_t *frame, unsigned int size); + +/** + * Get codec settings from the peer. These were exchanged during call initialization + * or when peer send us new csettings. + */ +int toxav_get_peer_csettings ( ToxAv *av, int32_t call_index, int peer, ToxAvCSettings *dest ); + +/** + * Get friend id of peer participating in conversation. + */ +int toxav_get_peer_id ( ToxAv *av, int32_t call_index, int peer ); + +/** + * Get current call state. + */ +ToxAvCallState toxav_get_call_state ( ToxAv *av, int32_t call_index ); + +/** + * Is certain capability supported. Used to determine if encoding/decoding is ready. + */ +int toxav_capability_supported ( ToxAv *av, int32_t call_index, ToxAvCapabilities capability ); + +/** + * Returns tox reference. + */ +Tox *toxav_get_tox (ToxAv *av); + +/** + * Returns number of active calls or -1 on error. + */ +int toxav_get_active_count (ToxAv *av); + +/* Create a new toxav group. + * + * return group number on success. + * return -1 on failure. + * + * Audio data callback format: + * audio_callback(Tox *tox, int groupnumber, int peernumber, const int16_t *pcm, unsigned int samples, uint8_t channels, unsigned int sample_rate, void *userdata) + * + * Note that total size of pcm in bytes is equal to (samples * channels * sizeof(int16_t)). + */ +int toxav_add_av_groupchat(Tox *tox, void (*audio_callback)(Tox *, int, int, const int16_t *, unsigned int, uint8_t, + unsigned int, void *), void *userdata); + +/* Join a AV group (you need to have been invited first.) + * + * returns group number on success + * returns -1 on failure. + * + * Audio data callback format (same as the one for toxav_add_av_groupchat()): + * audio_callback(Tox *tox, int groupnumber, int peernumber, const int16_t *pcm, unsigned int samples, uint8_t channels, unsigned int sample_rate, void *userdata) + * + * Note that total size of pcm in bytes is equal to (samples * channels * sizeof(int16_t)). + */ +int toxav_join_av_groupchat(Tox *tox, int32_t friendnumber, const uint8_t *data, uint16_t length, + void (*audio_callback)(Tox *, int, int, const int16_t *, unsigned int, uint8_t, unsigned int, void *), void *userdata); + +/* Send audio to the group chat. + * + * return 0 on success. + * return -1 on failure. + * + * Note that total size of pcm in bytes is equal to (samples * channels * sizeof(int16_t)). + * + * Valid number of samples are ((sample rate) * (audio length (Valid ones are: 2.5, 5, 10, 20, 40 or 60 ms)) / 1000) + * Valid number of channels are 1 or 2. + * Valid sample rates are 8000, 12000, 16000, 24000, or 48000. + * + * Recommended values are: samples = 960, channels = 1, sample_rate = 48000 + */ +int toxav_group_send_audio(Tox *tox, int groupnumber, const int16_t *pcm, unsigned int samples, uint8_t channels, + unsigned int sample_rate); + +#ifdef __cplusplus +} +#endif + +#endif /* __TOXAV */ diff --git a/protocols/Tox/include/toxdns.h b/protocols/Tox/include/toxdns.h new file mode 100644 index 0000000000..06071b82d6 --- /dev/null +++ b/protocols/Tox/include/toxdns.h @@ -0,0 +1,96 @@ +/* toxdns.h + * + * Tox secure username DNS toxid resolving functions. + * + * Copyright (C) 2014 Tox project All Rights Reserved. + * + * This file is part of Tox. + * + * Tox is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tox is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tox. If not, see <http://www.gnu.org/licenses/>. + * + */ + +#ifndef TOXDNS_H +#define TOXDNS_H + +#ifdef __cplusplus +extern "C" { +#endif + +#include <stdint.h> + +/* Clients are encouraged to set this as the maximum length names can have. */ +#define TOXDNS_MAX_RECOMMENDED_NAME_LENGTH 32 + +/* How to use this api to make secure tox dns3 requests: + * + * 1. Get the public key of a server that supports tox dns3. + * 2. use tox_dns3_new() to create a new object to create DNS requests + * and handle responses for that server. + * 3. Use tox_generate_dns3_string() to generate a string based on the name we want to query and a request_id + * that must be stored somewhere for when we want to decrypt the response. + * 4. take the string and use it for your DNS request like this: + * _4haaaaipr1o3mz0bxweox541airydbovqlbju51mb4p0ebxq.rlqdj4kkisbep2ks3fj2nvtmk4daduqiueabmexqva1jc._tox.utox.org + * 5. The TXT in the DNS you receive should look like this: + * v=tox3;id=2vgcxuycbuctvauik3plsv3d3aadv4zfjfhi3thaizwxinelrvigchv0ah3qjcsx5qhmaksb2lv2hm5cwbtx0yp + * 6. Take the id string and use it with tox_decrypt_dns3_TXT() and the request_id corresponding to the + * request we stored earlier to get the Tox id returned by the DNS server. + */ + +/* Create a new tox_dns3 object for server with server_public_key of size TOX_CLIENT_ID_SIZE. + * + * return Null on failure. + * return pointer object on success. + */ +void *tox_dns3_new(uint8_t *server_public_key); + +/* Destroy the tox dns3 object. + */ +void tox_dns3_kill(void *dns3_object); + +/* Generate a dns3 string of string_max_len used to query the dns server referred to by to + * dns3_object for a tox id registered to user with name of name_len. + * + * the uint32_t pointed by request_id will be set to the request id which must be passed to + * tox_decrypt_dns3_TXT() to correctly decode the response. + * + * This is what the string returned looks like: + * 4haaaaipr1o3mz0bxweox541airydbovqlbju51mb4p0ebxq.rlqdj4kkisbep2ks3fj2nvtmk4daduqiueabmexqva1jc + * + * returns length of string on success. + * returns -1 on failure. + */ +int tox_generate_dns3_string(void *dns3_object, uint8_t *string, uint16_t string_max_len, uint32_t *request_id, + uint8_t *name, uint8_t name_len); + +/* Decode and decrypt the id_record returned of length id_record_len into + * tox_id (needs to be at least TOX_FRIEND_ADDRESS_SIZE). + * + * request_id is the request id given by tox_generate_dns3_string() when creating the request. + * + * the id_record passed to this function should look somewhat like this: + * 2vgcxuycbuctvauik3plsv3d3aadv4zfjfhi3thaizwxinelrvigchv0ah3qjcsx5qhmaksb2lv2hm5cwbtx0yp + * + * returns -1 on failure. + * returns 0 on success. + * + */ +int tox_decrypt_dns3_TXT(void *dns3_object, uint8_t *tox_id, uint8_t *id_record, uint32_t id_record_len, + uint32_t request_id); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/protocols/Tox/include/toxencryptsave.h b/protocols/Tox/include/toxencryptsave.h new file mode 100644 index 0000000000..169f736c0b --- /dev/null +++ b/protocols/Tox/include/toxencryptsave.h @@ -0,0 +1,196 @@ +/* toxencryptsave.h + * + * The Tox encrypted save functions. + * + * Copyright (C) 2013 Tox project All Rights Reserved. + * + * This file is part of Tox. + * + * Tox is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Tox is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Tox. If not, see <http://www.gnu.org/licenses/>. + * + */ + +#ifndef TOXENCRYPTSAVE_H +#define TOXENCRYPTSAVE_H + +#ifdef __cplusplus +extern "C" { +#endif + +#include <stdint.h> + +#ifndef __TOX_DEFINED__ +#define __TOX_DEFINED__ +typedef struct Tox Tox; +#endif + +// these functions provide access to these defines in toxencryptsave.c, which +// otherwise aren't actually available in clients... +int tox_pass_encryption_extra_length(); + +int tox_pass_key_length(); + +int tox_pass_salt_length(); + +/* return size of the messenger data (for encrypted Messenger saving). */ +uint32_t tox_encrypted_size(const Tox *tox); + +/* This "module" provides functions analogous to tox_load and tox_save in toxcore, + * as well as functions for encryption of arbitrary client data (e.g. chat logs). + * + * It is conceptually organized into two parts. The first part are the functions + * with "key" in the name. To use these functions, first derive an encryption key + * from a password with tox_derive_key_from_pass, and use the returned key to + * encrypt the data. The second part takes the password itself instead of the key, + * and then delegates to the first part to derive the key before de/encryption, + * which can simplify client code; however, key derivation is very expensive + * compared to the actual encryption, so clients that do a lot of encryption should + * favor using the first part intead of the second part. + * + * The encrypted data is prepended with a magic number, to aid validity checking + * (no guarantees are made of course). + * + * Clients should consider alerting their users that, unlike plain data, if even one bit + * becomes corrupted, the data will be entirely unrecoverable. + * Ditto if they forget their password, there is no way to recover the data. + */ + + +/******************************* BEGIN PART 2 ******************************* + * For simplicty, the second part of the module is presented first. The API for + * the first part is analgous, with some extra functions for key handling. If + * your code spends too much time using these functions, consider using the part + * 1 functions instead. + */ + +/* Encrypts the given data with the given passphrase. The output array must be + * at least data_len + tox_pass_encryption_extra_length() bytes long. This delegates + * to tox_derive_key_from_pass and tox_pass_key_encrypt. + * + * tox_encrypted_save() is a good example of how to use this function. + * + * returns 0 on success + * returns -1 on failure + */ +int tox_pass_encrypt(const uint8_t *data, uint32_t data_len, uint8_t *passphrase, uint32_t pplength, uint8_t *out); + +/* Save the messenger data encrypted with the given password. + * data must be at least tox_encrypted_size(). + * + * returns 0 on success + * returns -1 on failure + */ +int tox_encrypted_save(const Tox *tox, uint8_t *data, uint8_t *passphrase, uint32_t pplength); + +/* Decrypts the given data with the given passphrase. The output array must be + * at least data_len - tox_pass_encryption_extra_length() bytes long. This delegates + * to tox_pass_key_decrypt. + * + * tox_encrypted_load() is a good example of how to use this function. + * + * returns the length of the output data (== data_len - tox_pass_encryption_extra_length()) on success + * returns -1 on failure + */ +int tox_pass_decrypt(const uint8_t *data, uint32_t length, uint8_t *passphrase, uint32_t pplength, uint8_t *out); + +/* Load the messenger from encrypted data of size length. + * + * returns 0 on success + * returns -1 on failure + */ +int tox_encrypted_load(Tox *tox, const uint8_t *data, uint32_t length, uint8_t *passphrase, uint32_t pplength); + + +/******************************* BEGIN PART 1 ******************************* + * And now part "1", which does the actual encryption, and is rather less cpu + * intensive than part one. The first 3 functions are for key handling. + */ + +/* Generates a secret symmetric key from the given passphrase. out_key must be at least + * tox_pass_key_length() bytes long. + * Be sure to not compromise the key! Only keep it in memory, do not write to disk. + * The password is zeroed after key derivation. + * The key should only be used with the other functions in this module, as it + * includes a salt. + * Note that this function is not deterministic; to derive the same key from a + * password, you also must know the random salt that was used. See below. + * + * returns 0 on success + * returns -1 on failure + */ +int tox_derive_key_from_pass(uint8_t *passphrase, uint32_t pplength, uint8_t *out_key); + +/* Same as above, except with use the given salt for deterministic key derivation. + * The salt must be tox_salt_length() bytes in length. + */ +int tox_derive_key_with_salt(uint8_t *passphrase, uint32_t pplength, uint8_t *salt, uint8_t *out_key); + +/* This retrieves the salt used to encrypt the given data, which can then be passed to + * derive_key_with_salt to produce the same key as was previously used. Any encrpyted + * data with this module can be used as input. + * + * returns -1 if the magic number is wrong + * returns 0 otherwise (no guarantee about validity of data) + */ +int tox_get_salt(uint8_t *data, uint8_t *salt); + +/* Now come the functions that are analogous to the part 2 functions. */ + +/* Encrypt arbitrary with a key produced by tox_derive_key_. The output + * array must be at least data_len + tox_pass_encryption_extra_length() bytes long. + * key must be tox_pass_key_length() bytes. + * If you already have a symmetric key from somewhere besides this module, simply + * call encrypt_data_symmetric in toxcore/crypto_core directly. + * + * returns 0 on success + * returns -1 on failure + */ +int tox_pass_key_encrypt(const uint8_t *data, uint32_t data_len, const uint8_t *key, uint8_t *out); + +/* Save the messenger data encrypted with the given key from tox_derive_key. + * data must be at least tox_encrypted_size(). + * + * returns 0 on success + * returns -1 on failure + */ +int tox_encrypted_key_save(const Tox *tox, uint8_t *data, uint8_t *key); + +/* This is the inverse of tox_pass_key_encrypt, also using only keys produced by + * tox_derive_key_from_pass. + * + * returns the length of the output data (== data_len - tox_pass_encryption_extra_length()) on success + * returns -1 on failure + */ +int tox_pass_key_decrypt(const uint8_t *data, uint32_t length, const uint8_t *key, uint8_t *out); + +/* Load the messenger from encrypted data of size length, with key from tox_derive_key. + * + * returns 0 on success + * returns -1 on failure + */ +int tox_encrypted_key_load(Tox *tox, const uint8_t *data, uint32_t length, uint8_t *key); + +/* Determines whether or not the given data is encrypted (by checking the magic number) + * + * returns 1 if it is encrypted + * returns 0 otherwise + */ +int tox_is_data_encrypted(const uint8_t *data); +int tox_is_save_encrypted(const uint8_t *data); // poorly-named alias for backwards compat (oh irony...) + +#ifdef __cplusplus +} +#endif + +#endif |