comparison libpurple/protocols/qq/qq.c @ 23050:51dbe83ebbd3

patch-04-tcp-pending
author SHiNE CsyFeK <csyfek@gmail.com>
date Tue, 24 Jun 2008 12:22:40 +0000
parents 665e04562de0
children 55f986ccbb6a
comparison
equal deleted inserted replaced
23049:190bc4ecf6c3 23050:51dbe83ebbd3
53 #include "im.h" 53 #include "im.h"
54 #include "keep_alive.h" 54 #include "keep_alive.h"
55 #include "login_logout.h" 55 #include "login_logout.h"
56 #include "packet_parse.h" 56 #include "packet_parse.h"
57 #include "qq.h" 57 #include "qq.h"
58 #include "qq_proxy.h" 58 #include "qq_network.h"
59 #include "send_core.h"
60 #include "send_file.h" 59 #include "send_file.h"
61 #include "utils.h" 60 #include "utils.h"
62 #include "version.h" 61 #include "version.h"
63 62
64 #define OPENQ_AUTHOR "Puzzlebird" 63 #define OPENQ_AUTHOR "Puzzlebird"
65 #define OPENQ_WEBSITE "http://openq.sourceforge.net" 64 #define OPENQ_WEBSITE "http://openq.sourceforge.net"
66 #define QQ_TCP_QUERY_PORT "8000" 65 #define QQ_TCP_PORT 8000
67 #define QQ_UDP_PORT "8000" 66 #define QQ_UDP_PORT 8000
68 67
69 const gchar *udp_server_list[] = { 68 const gchar *udp_server_list[] = {
70 "sz.tencent.com", 69 "sz.tencent.com",
71 "sz2.tencent.com", 70 "sz2.tencent.com",
72 "sz3.tencent.com", 71 "sz3.tencent.com",
88 "tcpconn5.tencent.com", 87 "tcpconn5.tencent.com",
89 "tcpconn6.tencent.com" 88 "tcpconn6.tencent.com"
90 }; 89 };
91 const gint tcp_server_amount = (sizeof(tcp_server_list) / sizeof(tcp_server_list[0])); 90 const gint tcp_server_amount = (sizeof(tcp_server_list) / sizeof(tcp_server_list[0]));
92 91
93 static void _qq_login(PurpleAccount *account) 92 static void srv_resolved(PurpleSrvResponse *resp, int results, gpointer account)
94 { 93 {
95 const gchar *qq_server, *qq_port; 94 PurpleConnection *gc;
96 qq_data *qd; 95 qq_data *qd;
96 gchar *hostname;
97 int port;
98
99 gc = purple_account_get_connection(account);
100 g_return_if_fail(gc != NULL && gc->proto_data != NULL);
101 qd = (qq_data *) gc->proto_data;
102
103 qd->srv_query_data = NULL;
104
105 /* find the host to connect to */
106 port = purple_account_get_int(account, "port", 0);
107 if (port == 0) {
108 if (qd->use_tcp) {
109 port = QQ_TCP_PORT;
110 } else {
111 port = QQ_UDP_PORT;
112 }
113 }
114
115 if(results) {
116 hostname = g_strdup(resp->hostname);
117 if(!port)
118 port = resp->port;
119 g_free(resp);
120 } else {
121 if(!purple_account_get_bool(account, "useproxy", FALSE)) {
122 hostname = g_strdup(qd->server_name);
123 } else {
124 hostname = g_strdup(purple_account_get_string(account,
125 "proxy", qd->server_name));
126 }
127 }
128
129 /*
130 purple_debug(PURPLE_DEBUG_INFO, "QQ",
131 "using with server %s and port %d\n", hostname, port);
132 */
133 qd->real_hostname = g_strdup(hostname);
134 qd->real_port = port;
135 qq_connect(account);
136
137 g_free(hostname);
138 }
139
140 static void qq_login(PurpleAccount *account)
141 {
142 const gchar *userserver;
143 qq_data *qd;
144 gchar *host2connect;
97 PurpleConnection *gc; 145 PurpleConnection *gc;
98 PurplePresence *presence; 146 PurplePresence *presence;
99 gboolean use_tcp;
100 147
101 g_return_if_fail(account != NULL); 148 g_return_if_fail(account != NULL);
102 149
103 gc = purple_account_get_connection(account); 150 gc = purple_account_get_connection(account);
104 g_return_if_fail(gc != NULL); 151 g_return_if_fail(gc != NULL);
107 154
108 qd = g_new0(qq_data, 1); 155 qd = g_new0(qq_data, 1);
109 qd->gc = gc; 156 qd->gc = gc;
110 gc->proto_data = qd; 157 gc->proto_data = qd;
111 158
112 qq_server = purple_account_get_string(account, "server", NULL);
113 qq_port = purple_account_get_string(account, "port", NULL);
114 use_tcp = purple_account_get_bool(account, "use_tcp", FALSE);
115 presence = purple_account_get_presence(account); 159 presence = purple_account_get_presence(account);
116
117 qd->use_tcp = use_tcp;
118
119 if(purple_presence_is_status_primitive_active(presence, PURPLE_STATUS_INVISIBLE)) { 160 if(purple_presence_is_status_primitive_active(presence, PURPLE_STATUS_INVISIBLE)) {
120 qd->login_mode = QQ_LOGIN_MODE_HIDDEN; 161 qd->login_mode = QQ_LOGIN_MODE_HIDDEN;
121 } else if(purple_presence_is_status_primitive_active(presence, PURPLE_STATUS_AWAY) 162 } else if(purple_presence_is_status_primitive_active(presence, PURPLE_STATUS_AWAY)
122 || purple_presence_is_status_primitive_active(presence, PURPLE_STATUS_EXTENDED_AWAY)) { 163 || purple_presence_is_status_primitive_active(presence, PURPLE_STATUS_EXTENDED_AWAY)) {
123 qd->login_mode = QQ_LOGIN_MODE_AWAY; 164 qd->login_mode = QQ_LOGIN_MODE_AWAY;
124 } else { 165 } else {
125 qd->login_mode = QQ_LOGIN_MODE_NORMAL; 166 qd->login_mode = QQ_LOGIN_MODE_NORMAL;
126 } 167 }
127 168
128 if (qq_server == NULL || strlen(qq_server) == 0) 169 userserver = purple_account_get_string(account, "server", NULL);
129 qq_server = use_tcp ? 170 qd->use_tcp = purple_account_get_bool(account, "use_tcp", TRUE);
130 tcp_server_list[random() % tcp_server_amount] : 171
131 udp_server_list[random() % udp_server_amount]; 172 if (userserver == NULL || strlen(userserver) == 0) {
132 173 if (qd->use_tcp) {
133 if (qq_port == NULL || strtol(qq_port, NULL, 10) == 0) 174 qd->server_name = g_strdup(tcp_server_list[random() % tcp_server_amount]);
134 qq_port = use_tcp ? QQ_TCP_QUERY_PORT : QQ_UDP_PORT; 175 } else {
176 qd->server_name = g_strdup(udp_server_list[random() % udp_server_amount]);
177 }
178 } else {
179 qd->server_name = g_strdup(userserver);
180 }
135 181
136 purple_connection_update_progress(gc, _("Connecting"), 0, QQ_CONNECT_STEPS); 182 purple_connection_update_progress(gc, _("Connecting"), 0, QQ_CONNECT_STEPS);
137 183
138 if (qq_connect(account, qq_server, strtol(qq_port, NULL, 10), use_tcp, FALSE) < 0) 184 if(!purple_account_get_bool(account, "useproxy", FALSE)) {
139 purple_connection_error_reason(gc, PURPLE_CONNECTION_ERROR_NETWORK_ERROR, 185 host2connect = g_strdup(qd->server_name);
140 _("Unable to connect.")); 186 } else {
141 } 187 host2connect = g_strdup(purple_account_get_string(account, "proxy", qd->server_name));
142 188 }
143 /* directly goes for qq_disconnect */ 189
144 static void _qq_close(PurpleConnection *gc) 190 qd->srv_query_data = purple_srv_resolve("QQ",
145 { 191 qd->use_tcp ? "tcp" : "udp", host2connect, srv_resolved, account);
192 g_free(host2connect);
193 }
194
195 /* clean up the given QQ connection and free all resources */
196 static void qq_close(PurpleConnection *gc)
197 {
198 qq_data *qd;
199
146 g_return_if_fail(gc != NULL); 200 g_return_if_fail(gc != NULL);
201 qd = gc->proto_data;
202
147 qq_disconnect(gc); 203 qq_disconnect(gc);
204
205 if (qd->real_hostname) {
206 purple_debug(PURPLE_DEBUG_INFO, "QQ", "free real_hostname\n");
207 g_free(qd->real_hostname);
208 qd->real_hostname = NULL;
209 }
210 if (qd->srv_query_data != NULL)
211 purple_srv_cancel(qd->srv_query_data);
212
213 g_free(qd->server_name);
214 g_free(qd);
215
216 gc->proto_data = NULL;
148 } 217 }
149 218
150 /* returns the icon name for a buddy or protocol */ 219 /* returns the icon name for a buddy or protocol */
151 static const gchar *_qq_list_icon(PurpleAccount *a, PurpleBuddy *b) 220 static const gchar *_qq_list_icon(PurpleAccount *a, PurpleBuddy *b)
152 { 221 {
440 g_string_append_printf(info, _("<b>Current Online</b>: %d<br>\n"), qd->all_online); 509 g_string_append_printf(info, _("<b>Current Online</b>: %d<br>\n"), qd->all_online);
441 g_string_append_printf(info, _("<b>Last Refresh</b>: %s<br>\n"), ctime(&qd->last_get_online)); 510 g_string_append_printf(info, _("<b>Last Refresh</b>: %s<br>\n"), ctime(&qd->last_get_online));
442 511
443 g_string_append(info, "<hr>\n"); 512 g_string_append(info, "<hr>\n");
444 513
514 g_string_append_printf(info, _("<b>Server</b>: %s: %d<br>\n"), qd->server_name, qd->real_port);
445 g_string_append_printf(info, _("<b>Connection Mode</b>: %s<br>\n"), qd->use_tcp ? "TCP" : "UDP"); 515 g_string_append_printf(info, _("<b>Connection Mode</b>: %s<br>\n"), qd->use_tcp ? "TCP" : "UDP");
446 g_string_append_printf(info, _("<b>Server IP</b>: %s: %d<br>\n"), qd->server_ip, qd->server_port); 516 g_string_append_printf(info, _("<b>Real hostname</b>: %s: %d<br>\n"), qd->real_hostname, qd->real_port);
447 g_string_append_printf(info, _("<b>My Public IP</b>: %s<br>\n"), qd->my_ip); 517 g_string_append_printf(info, _("<b>My Public IP</b>: %s<br>\n"), qd->my_ip);
448 518
449 g_string_append(info, "<hr>\n"); 519 g_string_append(info, "<hr>\n");
450 g_string_append(info, "<i>Information below may not be accurate</i><br>\n"); 520 g_string_append(info, "<i>Information below may not be accurate</i><br>\n");
451 521
592 662
593 return m; 663 return m;
594 } 664 }
595 665
596 666
597 static void _qq_keep_alive(PurpleConnection *gc) 667 static void qq_keep_alive(PurpleConnection *gc)
598 { 668 {
599 qq_group *group; 669 qq_group *group;
600 qq_data *qd; 670 qq_data *qd;
601 GList *list; 671 GList *list;
602 672
649 _qq_tooltip_text, /* tooltip_text */ 719 _qq_tooltip_text, /* tooltip_text */
650 _qq_away_states, /* away_states */ 720 _qq_away_states, /* away_states */
651 _qq_buddy_menu, /* blist_node_menu */ 721 _qq_buddy_menu, /* blist_node_menu */
652 qq_chat_info, /* chat_info */ 722 qq_chat_info, /* chat_info */
653 qq_chat_info_defaults, /* chat_info_defaults */ 723 qq_chat_info_defaults, /* chat_info_defaults */
654 _qq_login, /* login */ 724 qq_login, /* open */
655 _qq_close, /* close */ 725 qq_close, /* close */
656 _qq_send_im, /* send_im */ 726 _qq_send_im, /* send_im */
657 NULL, /* set_info */ 727 NULL, /* set_info */
658 NULL, /* send_typing */ 728 NULL, /* send_typing */
659 _qq_get_info, /* get_info */ 729 _qq_get_info, /* get_info */
660 _qq_set_away, /* set_away */ 730 _qq_set_away, /* set_away */
674 NULL, /* get_chat_name */ 744 NULL, /* get_chat_name */
675 NULL, /* chat_invite */ 745 NULL, /* chat_invite */
676 NULL, /* chat_leave */ 746 NULL, /* chat_leave */
677 NULL, /* chat_whisper */ 747 NULL, /* chat_whisper */
678 _qq_chat_send, /* chat_send */ 748 _qq_chat_send, /* chat_send */
679 _qq_keep_alive, /* keepalive */ 749 qq_keep_alive, /* keepalive */
680 NULL, /* register_user */ 750 NULL, /* register_user */
681 _qq_get_chat_buddy_info, /* get_cb_info */ 751 _qq_get_chat_buddy_info, /* get_cb_info */
682 NULL, /* get_cb_away */ 752 NULL, /* get_cb_away */
683 NULL, /* alias_buddy */ 753 NULL, /* alias_buddy */
684 NULL, /* group_buddy */ 754 NULL, /* group_buddy */
748 818
749 static void init_plugin(PurplePlugin *plugin) 819 static void init_plugin(PurplePlugin *plugin)
750 { 820 {
751 PurpleAccountOption *option; 821 PurpleAccountOption *option;
752 822
753 option = purple_account_option_bool_new(_("Connect using TCP"), "use_tcp", FALSE);
754 prpl_info.protocol_options = g_list_append(prpl_info.protocol_options, option);
755
756 option = purple_account_option_string_new(_("Server"), "server", NULL); 823 option = purple_account_option_string_new(_("Server"), "server", NULL);
757 prpl_info.protocol_options = g_list_append(prpl_info.protocol_options, option); 824 prpl_info.protocol_options = g_list_append(prpl_info.protocol_options, option);
758 825
759 option = purple_account_option_string_new(_("Port"), "port", NULL); 826 option = purple_account_option_int_new(_("Port"), "port", 0);
827 prpl_info.protocol_options = g_list_append(prpl_info.protocol_options, option);
828
829 option = purple_account_option_bool_new(_("Connect using TCP"), "use_tcp", TRUE);
760 prpl_info.protocol_options = g_list_append(prpl_info.protocol_options, option); 830 prpl_info.protocol_options = g_list_append(prpl_info.protocol_options, option);
761 831
762 my_protocol = plugin; 832 my_protocol = plugin;
763 833
764 purple_prefs_add_none("/plugins/prpl/qq"); 834 purple_prefs_add_none("/plugins/prpl/qq");