Exemplo n.º 1
0
static void request_change_memo(PurpleConnection *gc, guint32 bd_uid, gchar **segments)
{
	gint bytes;
	/* Attention, length of each segment must be guint8(0~255),
	 * so length of memo string is limited.
	 * convert it to guint8 first before putting data */
	guint seg_len;
	gint index;
	guint8 raw_data[MAX_PACKET_SIZE - 16] = {0};

	purple_debug_info( "QQ", "request_change_memo\n" );
	g_return_if_fail(NULL != gc && NULL != segments);

	bytes = 0;
	bytes += qq_put8(raw_data+bytes, QQ_BUDDY_MEMO_MODIFY);
	bytes += qq_put8(raw_data+bytes, 0x00);
	bytes += qq_put32(raw_data+bytes, (guint32)bd_uid);
	bytes += qq_put8(raw_data+bytes, 0x00);
	for (index = 0; index < QQ_MEMO_SIZE; index++) {
		seg_len = strlen(segments[index]);
		seg_len = seg_len & 0xff;
		bytes += qq_put8(raw_data+bytes, (guint8)seg_len);
		bytes += qq_putdata(raw_data+bytes, (const guint8 *)segments[index], (guint8)seg_len);
	}

	/* debug */
	/*
	   qq_show_packet("MEMO MODIFY", raw_data, bytes);
	   */

	qq_send_cmd(gc, QQ_CMD_BUDDY_MEMO, raw_data, bytes);
}
Exemplo n.º 2
0
/* this buddy needs authentication, text conversion is done at lowest level */
static void request_add_buddy_auth(PurpleConnection *gc, guint32 uid, const gchar response, const gchar *text)
{
	guint8 raw_data[MAX_PACKET_SIZE - 16];
	gint bytes;
	gchar *msg, uid_str[11];
	guint8 bar;

	g_return_if_fail(uid != 0);

	g_snprintf(uid_str, sizeof(uid_str), "%u", uid);
	bar = 0x1f;

	bytes = 0;
	bytes += qq_putdata(raw_data + bytes, (guint8 *) uid_str, strlen(uid_str));
	bytes += qq_put8(raw_data + bytes, bar);
	bytes += qq_put8(raw_data + bytes, response);

	if (text != NULL) {
		msg = utf8_to_qq(text, QQ_CHARSET_DEFAULT);
		bytes += qq_put8(raw_data + bytes, bar);
		bytes += qq_putdata(raw_data + bytes, (guint8 *) msg, strlen(msg));
		g_free(msg);
	}

	qq_send_cmd(gc, QQ_CMD_ADD_BUDDY_AUTH, raw_data, bytes);
}
Exemplo n.º 3
0
static void request_add_buddy_auth_ex(PurpleConnection *gc, guint32 uid,
	const gchar *text, guint8 *auth, guint8 auth_len)
{
	guint8 raw_data[MAX_PACKET_SIZE - 16];
	gint bytes = 0;

	g_return_if_fail(uid != 0);

	bytes = 0;
	bytes += qq_put8(raw_data + bytes, 0x02);
	bytes += qq_put32(raw_data + bytes, uid);
	bytes += qq_put16(raw_data + bytes, 0);

	bytes += qq_put8(raw_data + bytes, 0);
	if (auth == NULL || auth_len <= 0) {
		bytes += qq_put8(raw_data + bytes, 0);
	} else {
		bytes += qq_put8(raw_data + bytes, auth_len);
		bytes += qq_putdata(raw_data + bytes, auth, auth_len);
	}
	bytes += qq_put8(raw_data + bytes, 1);	/* ALLOW ADD ME FLAG */
	bytes += qq_put8(raw_data + bytes, 0);	/* group number? */
	bytes += qq_put_vstr(raw_data + bytes, text, QQ_CHARSET_DEFAULT);
	qq_send_cmd(gc, QQ_CMD_ADD_BUDDY_AUTH_EX, raw_data, bytes);
}
Exemplo n.º 4
0
/* send an IM to uid_to */
static void request_send_im(PurpleConnection *gc, guint32 uid_to, gint type,
	qq_im_format *fmt, gchar *msg, guint8 id, guint8 frag_count, guint8 frag_index)
{
	qq_data *qd;
	guint8 raw_data[MAX_PACKET_SIZE - 16];
	guint16 im_type;
	gint bytes;
	time_t now;

	qd = (qq_data *) gc->proto_data;
	im_type = QQ_NORMAL_IM_TEXT;

	/* purple_debug_info("QQ", "Send IM %d-%d\n", frag_count, frag_index); */
	bytes = 0;
	/* 000-003: receiver uid */
	bytes += qq_put32(raw_data + bytes, qd->uid);
	/* 004-007: sender uid */
	bytes += qq_put32(raw_data + bytes, uid_to);
	/* 008-009: sender client version */
	bytes += qq_put16(raw_data + bytes, qd->client_tag);
	/* 010-013: receiver uid */
	bytes += qq_put32(raw_data + bytes, qd->uid);
	/* 014-017: sender uid */
	bytes += qq_put32(raw_data + bytes, uid_to);
	/* 018-033: md5 of (uid+session_key) */
	bytes += qq_putdata(raw_data + bytes, qd->session_md5, 16);
	/* 034-035: message type */
	bytes += qq_put16(raw_data + bytes, QQ_NORMAL_IM_TEXT);
	/* 036-037: sequence number */
	bytes += qq_put16(raw_data + bytes, qd->send_seq);
	/* 038-041: send time */
	now = time(NULL);
	bytes += qq_put32(raw_data + bytes, (guint32) now);
	/* 042-043: sender icon */
	bytes += qq_put16(raw_data + bytes, qd->my_icon);
	/* 044-046: always 0x00 */
	bytes += qq_put16(raw_data + bytes, 0x0000);
	bytes += qq_put8(raw_data + bytes, 0x00);
	/* 047-047: always use font attr */
	bytes += qq_put8(raw_data + bytes, 0x01);
	/* 048-051: always 0x00 */
	/* Fixme: frag_count, frag_index not working now */
	bytes += qq_put8(raw_data + bytes, frag_count);
	bytes += qq_put8(raw_data + bytes, frag_index);
	bytes += qq_put8(raw_data + bytes, id);
	bytes += qq_put8(raw_data + bytes, 0);
	/* 052-052: text message type (normal/auto-reply) */
	bytes += qq_put8(raw_data + bytes, type);
	/* 053-   : msg ends with 0x00 */
	bytes += qq_putdata(raw_data + bytes, (guint8 *)msg, strlen(msg));
	if (frag_count == frag_index + 1) {
		bytes += qq_put8(raw_data + bytes, 0x20);	/* add extra SPACE */
	}
	bytes += qq_put_im_tail(raw_data + bytes, fmt);

	/* qq_show_packet("QQ_CMD_SEND_IM", raw_data, bytes); */
	qq_send_cmd(gc, QQ_CMD_SEND_IM, raw_data, bytes);
}
Exemplo n.º 5
0
void qq_request_get_level_2007(PurpleConnection *gc, guint32 uid)
{
	guint8 buf[16] = {0};
	gint bytes = 0;

	bytes += qq_put8(buf + bytes, 0x08);
	bytes += qq_put32(buf + bytes, uid);
	bytes += qq_put8(buf + bytes, 0x00);
	qq_send_cmd(gc, QQ_CMD_GET_LEVEL, buf, bytes);
}
Exemplo n.º 6
0
/* send logout packets to QQ server */
void qq_send_packet_logout(PurpleConnection *gc)
{
	gint i;
	qq_data *qd;

	qd = (qq_data *) gc->proto_data;
	for (i = 0; i < 4; i++)
		qq_send_cmd(gc, QQ_CMD_LOGOUT, FALSE, 0xffff, FALSE, qd->pwkey, QQ_KEY_LENGTH);

	qd->logged_in = FALSE;	/* update login status AFTER sending logout packets */
}
Exemplo n.º 7
0
void qq_request_get_level(PurpleConnection *gc, guint32 uid)
{
	qq_data *qd = (qq_data *) gc->proto_data;
	guint8 buf[16] = {0};
	gint bytes = 0;

	if (qd->client_version >= 2007) {
		bytes += qq_put8(buf + bytes, 0x02);
	} else {
		bytes += qq_put8(buf + bytes, 0x00);
	}
	bytes += qq_put32(buf + bytes, uid);
	qq_send_cmd(gc, QQ_CMD_GET_LEVEL, buf, bytes);
}
Exemplo n.º 8
0
/* send keep-alive packet to QQ server (it is a heart-beat) */
void qq_send_packet_keep_alive(GaimConnection *gc)
{
	qq_data *qd;
	guint8 *raw_data, *cursor;

	qd = (qq_data *) gc->proto_data;
	raw_data = g_newa(guint8, 4);
	cursor = raw_data;

	/* In fact, we can send whatever we like to server
	 * with this command, server return the same result including
	 * the amount of online QQ users, my ip and port */
	create_packet_dw(raw_data, &cursor, qd->uid);

	qq_send_cmd(gc, QQ_CMD_KEEP_ALIVE, TRUE, 0, TRUE, raw_data, 4);
}
Exemplo n.º 9
0
/* get all list, buddies & Quns with groupsid support */
void qq_send_packet_get_all_list_with_group(GaimConnection *gc, guint32 position)
{
	guint8 *raw_data, *cursor;
	gint data_len;

	data_len = 10;
	raw_data = g_newa(guint8, data_len);
	cursor = raw_data;
	/* 0x01 download, 0x02, upload */
	create_packet_b(raw_data, &cursor, 0x01);
	/* unknown 0x02 */
	create_packet_b(raw_data, &cursor, 0x02);
	/* unknown 00 00 00 00 */
	create_packet_dw(raw_data, &cursor, 0x00000000);
	create_packet_dw(raw_data, &cursor, position);

	qq_send_cmd(gc, QQ_CMD_GET_ALL_LIST_WITH_GROUP, TRUE, 0, TRUE, raw_data, data_len);
}
Exemplo n.º 10
0
/* position starts with 0x0000, 
 * server may return a position tag if list is too long for one packet */
void qq_send_packet_get_buddies_list(GaimConnection *gc, guint16 position)
{
	guint8 *raw_data, *cursor;
	gint data_len;

	data_len = 3;
	raw_data = g_newa(guint8, data_len);
	cursor = raw_data;
	/* 000-001 starting position, can manually specify */
	create_packet_w(raw_data, &cursor, position);
	/* before Mar 18, 2004, any value can work, and we sent 00
	 * I do not know what data QQ server is expecting, as QQ2003iii 0304 itself
	 * even can sending packets 00 and get no response.
	 * Now I tested that 00,00,00,00,00,01 work perfectly
	 * March 22, found the 00,00,00 starts to work as well */
	create_packet_b(raw_data, &cursor, 0x00);

	qq_send_cmd(gc, QQ_CMD_GET_FRIENDS_LIST, TRUE, 0, TRUE, raw_data, data_len);
}
Exemplo n.º 11
0
static void request_buddy_check_code(PurpleConnection *gc,
		gchar *from, guint8 *code, gint code_len)
{
	guint8 *raw_data;
	gint bytes;
	guint32 uid;

	g_return_if_fail(code != NULL && code_len > 0 && from != NULL);

	uid = strtoul(from, NULL, 10);
	raw_data = g_newa(guint8, code_len + 16);
	bytes = 0;
	bytes += qq_put8(raw_data + bytes, 0x03);
	bytes += qq_put8(raw_data + bytes, 0x01);
	bytes += qq_put32(raw_data + bytes, uid);
	bytes += qq_put16(raw_data + bytes, code_len);
	bytes += qq_putdata(raw_data + bytes, code, code_len);

	qq_send_cmd(gc, QQ_CMD_BUDDY_CHECK_CODE, raw_data, bytes);
}
Exemplo n.º 12
0
static void request_add_buddy_by_question(PurpleConnection *gc, guint32 uid,
	guint8 *code, guint16 code_len)
{
	guint8 raw_data[MAX_PACKET_SIZE - 16];
	gint bytes = 0;

	g_return_if_fail(uid != 0 && code_len > 0);

	bytes = 0;
	bytes += qq_put8(raw_data + bytes, 0x10);
	bytes += qq_put32(raw_data + bytes, uid);
	bytes += qq_put16(raw_data + bytes, 0);

	bytes += qq_put8(raw_data + bytes, 0);
	bytes += qq_put8(raw_data + bytes, 0);	/* no auth code */

	bytes += qq_put16(raw_data + bytes, code_len);
	bytes += qq_putdata(raw_data + bytes, code, code_len);

	bytes += qq_put8(raw_data + bytes, 1);	/* ALLOW ADD ME FLAG */
	bytes += qq_put8(raw_data + bytes, 0);	/* group number? */
	qq_send_cmd(gc, QQ_CMD_ADD_BUDDY_AUTH_EX, raw_data, bytes);
}
Exemplo n.º 13
0
/* send packet to modify personal information */
static void request_change_info(PurpleConnection *gc, gchar **segments)
{
	gint bytes = 0;
	guint8 raw_data[MAX_PACKET_SIZE - 128] = {0};
	guint8 bar;
	gchar *join;

	g_return_if_fail(segments != NULL);

	bar = 0x1f;

	bytes += qq_put8(raw_data + bytes, bar);
	bytes += qq_put8(raw_data + bytes, bar);

	/* important! skip the first uid entry */
	join = g_strjoinv("\x1f", segments + 1);
	bytes += qq_putdata(raw_data + bytes, (guint8 *)join, strlen(join));
	g_free(join);

	bytes += qq_put8(raw_data + bytes, bar);

	/* qq_show_packet("request_modify_info", raw_data, bytes); */
	qq_send_cmd(gc, QQ_CMD_UPDATE_INFO, raw_data, bytes);
}
Exemplo n.º 14
0
/* get a list of online_buddies */
void qq_send_packet_get_buddies_online(GaimConnection *gc, guint8 position)
{
	qq_data *qd;
	guint8 *raw_data, *cursor;

	qd = (qq_data *) gc->proto_data;
	raw_data = g_newa(guint8, 5);
	cursor = raw_data;

	/* 000-000 get online friends cmd
	 * only 0x02 and 0x03 returns info from server, other valuse all return 0xff
	 * I can also only send the first byte (0x02, or 0x03)
	 * and the result is the same */
	create_packet_b(raw_data, &cursor, QQ_GET_ONLINE_BUDDY_02);
	/* 001-001 seems it supports 255 online buddies at most */
	create_packet_b(raw_data, &cursor, position);
	/* 002-002 */
	create_packet_b(raw_data, &cursor, 0x00);
	/* 003-004 */
	create_packet_w(raw_data, &cursor, 0x0000);

	qq_send_cmd(gc, QQ_CMD_GET_FRIENDS_ONLINE, TRUE, 0, TRUE, raw_data, 5);
	qd->last_get_online = time(NULL);
}