diff options
Diffstat (limited to 'toxcore/Messenger.c')
-rw-r--r-- | toxcore/Messenger.c | 125 |
1 files changed, 122 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 | { |