diff options
-rw-r--r-- | toxcore/Messenger.c | 125 | ||||
-rw-r--r-- | toxcore/Messenger.h | 25 | ||||
-rw-r--r-- | toxcore/network.h | 6 |
3 files changed, 153 insertions, 3 deletions
diff --git a/toxcore/Messenger.c b/toxcore/Messenger.c index fef2e9e5..cf3a60bf 100644 --- a/toxcore/Messenger.c +++ b/toxcore/Messenger.c | |||
@@ -43,6 +43,71 @@ static uint8_t friend_not_valid(Messenger *m, int friendnumber) | |||
43 | return (unsigned int)friendnumber >= m->numfriends; | 43 | return (unsigned int)friendnumber >= m->numfriends; |
44 | } | 44 | } |
45 | 45 | ||
46 | static int add_online_friend(Messenger *m, int friendnumber) | ||
47 | { | ||
48 | if (friend_not_valid(m, friendnumber)) | ||
49 | return -1; | ||
50 | |||
51 | IP_Port temp_ip_port = get_friend_ipport(m, friendnumber); | ||
52 | |||
53 | if (temp_ip_port.port == 0) | ||
54 | return -1; | ||
55 | |||
56 | uint32_t i; | ||
57 | |||
58 | for (i = 0; i < m->numonline_friends; ++i) { | ||
59 | if (m->online_friendlist[i].friend_num == (uint32_t)friendnumber) | ||
60 | return 0; | ||
61 | } | ||
62 | |||
63 | Online_Friend *temp; | ||
64 | temp = realloc(m->online_friendlist, sizeof(Online_Friend) * (m->numonline_friends + 1)); | ||
65 | |||
66 | if (temp == NULL) | ||
67 | return -1; | ||
68 | |||
69 | m->online_friendlist = temp; | ||
70 | m->online_friendlist[m->numonline_friends].friend_num = friendnumber; | ||
71 | m->online_friendlist[m->numonline_friends].ip_port = temp_ip_port; | ||
72 | ++m->numonline_friends; | ||
73 | return 0; | ||
74 | } | ||
75 | |||
76 | |||
77 | static int remove_online_friend(Messenger *m, int friendnumber) | ||
78 | { | ||
79 | uint32_t i; | ||
80 | Online_Friend *temp; | ||
81 | |||
82 | for (i = 0; i < m->numonline_friends; ++i) { | ||
83 | /* Equal */ | ||
84 | if (m->online_friendlist[i].friend_num == (uint32_t)friendnumber) { | ||
85 | --m->numonline_friends; | ||
86 | |||
87 | if (m->numonline_friends != i) { | ||
88 | memcpy( &m->online_friendlist[i], | ||
89 | &m->online_friendlist[m->numonline_friends], | ||
90 | sizeof(Online_Friend) ); | ||
91 | } | ||
92 | |||
93 | if (m->numonline_friends == 0) { | ||
94 | free(m->online_friendlist); | ||
95 | m->online_friendlist = NULL; | ||
96 | return 0; | ||
97 | } | ||
98 | |||
99 | temp = realloc(m->online_friendlist, sizeof(Online_Friend) * (m->numonline_friends)); | ||
100 | |||
101 | if (temp == NULL) | ||
102 | return -1; | ||
103 | |||
104 | m->online_friendlist = temp; | ||
105 | return 0; | ||
106 | } | ||
107 | } | ||
108 | |||
109 | return -1; | ||
110 | } | ||
46 | /* Set the size of the friend list to numfriends. | 111 | /* Set the size of the friend list to numfriends. |
47 | * | 112 | * |
48 | * return -1 if realloc fails. | 113 | * return -1 if realloc fails. |
@@ -274,7 +339,7 @@ int m_delfriend(Messenger *m, int friendnumber) | |||
274 | return -1; | 339 | return -1; |
275 | 340 | ||
276 | if (m->friendlist[friendnumber].status == FRIEND_ONLINE) | 341 | if (m->friendlist[friendnumber].status == FRIEND_ONLINE) |
277 | --m->numonline_friends; | 342 | remove_online_friend(m, friendnumber); |
278 | 343 | ||
279 | onion_delfriend(m->onion_c, m->friendlist[friendnumber].onion_friendnum); | 344 | onion_delfriend(m->onion_c, m->friendlist[friendnumber].onion_friendnum); |
280 | crypto_kill(m->net_crypto, m->friendlist[friendnumber].crypt_connection_id); | 345 | crypto_kill(m->net_crypto, m->friendlist[friendnumber].crypt_connection_id); |
@@ -670,9 +735,9 @@ static void check_friend_connectionstatus(Messenger *m, int friendnumber, uint8_ | |||
670 | if (is_online != was_online) { | 735 | if (is_online != was_online) { |
671 | if (was_online) { | 736 | if (was_online) { |
672 | break_files(m, friendnumber); | 737 | break_files(m, friendnumber); |
673 | --m->numonline_friends; | 738 | remove_online_friend(m, friendnumber); |
674 | } else { | 739 | } else { |
675 | ++m->numonline_friends; | 740 | add_online_friend(m, friendnumber); |
676 | } | 741 | } |
677 | 742 | ||
678 | m->friend_connectionstatuschange(m, friendnumber, is_online, m->friend_connectionstatuschange_userdata); | 743 | m->friend_connectionstatuschange(m, friendnumber, is_online, m->friend_connectionstatuschange_userdata); |
@@ -1500,6 +1565,60 @@ int m_msi_packet(Messenger *m, int friendnumber, uint8_t *data, uint16_t length) | |||
1500 | return write_cryptpacket_id(m, friendnumber, PACKET_ID_MSI, data, length); | 1565 | return write_cryptpacket_id(m, friendnumber, PACKET_ID_MSI, data, length); |
1501 | } | 1566 | } |
1502 | 1567 | ||
1568 | static int friendnum_from_ip_port(Messenger *m, IP_Port ip_port) | ||
1569 | { | ||
1570 | uint32_t i; | ||
1571 | |||
1572 | for (i = 0; i < m->numonline_friends; ++i) { | ||
1573 | if (ipport_equal(&m->online_friendlist[i].ip_port, &ip_port)) | ||
1574 | return m->online_friendlist[i].friend_num; | ||
1575 | } | ||
1576 | |||
1577 | return -1; | ||
1578 | } | ||
1579 | |||
1580 | static int handle_custom_user_packet(void *object, IP_Port source, uint8_t *packet, uint32_t length) | ||
1581 | { | ||
1582 | Messenger *m = object; | ||
1583 | int friend_num = friendnum_from_ip_port(m, source); | ||
1584 | |||
1585 | if (friend_num == -1) | ||
1586 | return 1; | ||
1587 | |||
1588 | if (m->friendlist[friend_num].packethandlers[packet[0] % TOTAL_USERPACKETS].function) | ||
1589 | return m->friendlist[friend_num].packethandlers[packet[0] % TOTAL_USERPACKETS].function( | ||
1590 | m->friendlist[friend_num].packethandlers[packet[0] % TOTAL_USERPACKETS].object, source, packet, length); | ||
1591 | |||
1592 | return 1; | ||
1593 | } | ||
1594 | |||
1595 | |||
1596 | int custom_user_packet_registerhandler(Messenger *m, int friendnumber, uint8_t byte, packet_handler_callback cb, | ||
1597 | void *object) | ||
1598 | { | ||
1599 | if (friend_not_valid(m, friendnumber)) | ||
1600 | return -1; | ||
1601 | |||
1602 | if (byte < NET_PACKET_CUSTOM_RANGE_START || byte >= NET_PACKET_CUSTOM_RANGE_END) | ||
1603 | return -1; | ||
1604 | |||
1605 | m->friendlist[friendnumber].packethandlers[byte % TOTAL_USERPACKETS].function = cb; | ||
1606 | m->friendlist[friendnumber].packethandlers[byte % TOTAL_USERPACKETS].object = object; | ||
1607 | networking_registerhandler(m->net, byte, handle_custom_user_packet, m); | ||
1608 | return 0; | ||
1609 | } | ||
1610 | |||
1611 | int send_custom_user_packet(Messenger *m, int friendnumber, uint8_t *data, uint32_t length) | ||
1612 | { | ||
1613 | IP_Port ip_port = get_friend_ipport(m, friendnumber); | ||
1614 | |||
1615 | if (ip_port.port == 0) | ||
1616 | return -1; | ||
1617 | |||
1618 | return sendpacket(m->net, ip_port, data, length); | ||
1619 | } | ||
1620 | |||
1621 | |||
1503 | /* Function to filter out some friend requests*/ | 1622 | /* Function to filter out some friend requests*/ |
1504 | static int friend_already_added(uint8_t *client_id, void *data) | 1623 | static int friend_already_added(uint8_t *client_id, void *data) |
1505 | { | 1624 | { |
diff --git a/toxcore/Messenger.h b/toxcore/Messenger.h index 40e857d1..375e2025 100644 --- a/toxcore/Messenger.h +++ b/toxcore/Messenger.h | |||
@@ -155,8 +155,15 @@ typedef struct { | |||
155 | struct File_Transfers file_receiving[MAX_CONCURRENT_FILE_PIPES]; | 155 | struct File_Transfers file_receiving[MAX_CONCURRENT_FILE_PIPES]; |
156 | int invited_groups[MAX_INVITED_GROUPS]; | 156 | int invited_groups[MAX_INVITED_GROUPS]; |
157 | uint16_t invited_groups_num; | 157 | uint16_t invited_groups_num; |
158 | |||
159 | Packet_Handles packethandlers[TOTAL_USERPACKETS]; | ||
158 | } Friend; | 160 | } Friend; |
159 | 161 | ||
162 | typedef struct { | ||
163 | uint32_t friend_num; | ||
164 | IP_Port ip_port; | ||
165 | } Online_Friend; | ||
166 | |||
160 | typedef struct Messenger { | 167 | typedef struct Messenger { |
161 | 168 | ||
162 | Networking_Core *net; | 169 | Networking_Core *net; |
@@ -178,6 +185,8 @@ typedef struct Messenger { | |||
178 | 185 | ||
179 | Friend *friendlist; | 186 | Friend *friendlist; |
180 | uint32_t numfriends; | 187 | uint32_t numfriends; |
188 | |||
189 | Online_Friend *online_friendlist; | ||
181 | uint32_t numonline_friends; | 190 | uint32_t numonline_friends; |
182 | 191 | ||
183 | Group_Chat **chats; | 192 | Group_Chat **chats; |
@@ -628,6 +637,22 @@ int m_msi_packet(Messenger *m, int friendnumber, uint8_t *data, uint16_t length) | |||
628 | 637 | ||
629 | /**********************************************/ | 638 | /**********************************************/ |
630 | 639 | ||
640 | /* Set handlers for custom user packets (RTP packets for example.) | ||
641 | * | ||
642 | * return -1 on failure. | ||
643 | * return 0 on success. | ||
644 | */ | ||
645 | int custom_user_packet_registerhandler(Messenger *m, int friendnumber, uint8_t byte, packet_handler_callback cb, | ||
646 | void *object); | ||
647 | |||
648 | /* High level function to send custom user packets. | ||
649 | * | ||
650 | * return -1 on failure. | ||
651 | * return number of bytes sent on success. | ||
652 | */ | ||
653 | int send_custom_user_packet(Messenger *m, int friendnumber, uint8_t *data, uint32_t length); | ||
654 | |||
655 | /**********************************************/ | ||
631 | /* Run this at startup. | 656 | /* Run this at startup. |
632 | * return allocated instance of Messenger on success. | 657 | * return allocated instance of Messenger on success. |
633 | * return 0 if there are problems. | 658 | * return 0 if there are problems. |
diff --git a/toxcore/network.h b/toxcore/network.h index 19c9ca63..aaf89f19 100644 --- a/toxcore/network.h +++ b/toxcore/network.h | |||
@@ -129,6 +129,12 @@ typedef int sock_t; | |||
129 | #define NET_PACKET_LAN_DISCOVERY 33 /* LAN discovery packet ID. */ | 129 | #define NET_PACKET_LAN_DISCOVERY 33 /* LAN discovery packet ID. */ |
130 | #define NET_PACKET_GROUP_CHATS 48 /* Group chats packet ID. */ | 130 | #define NET_PACKET_GROUP_CHATS 48 /* Group chats packet ID. */ |
131 | 131 | ||
132 | /* Range of ids that custom user packets can use. */ | ||
133 | #define NET_PACKET_CUSTOM_RANGE_START 64 | ||
134 | #define NET_PACKET_CUSTOM_RANGE_END 96 | ||
135 | |||
136 | #define TOTAL_USERPACKETS (NET_PACKET_CUSTOM_RANGE_END - NET_PACKET_CUSTOM_RANGE_START) | ||
137 | |||
132 | /* See: docs/Prevent_Tracking.txt and onion.{c, h} */ | 138 | /* See: docs/Prevent_Tracking.txt and onion.{c, h} */ |
133 | #define NET_PACKET_ONION_SEND_INITIAL 128 | 139 | #define NET_PACKET_ONION_SEND_INITIAL 128 |
134 | #define NET_PACKET_ONION_SEND_1 129 | 140 | #define NET_PACKET_ONION_SEND_1 129 |