⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 family_feedbag.c

📁 Linux下的多协议即时通讯程序源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
 * * @param od The oscar odion. * @param oldgn The old group name. * @param newgn The new group name. * @return Return 0 if no errors, otherwise return the error number. */int aim_ssi_rename_group(OscarData *od, const char *oldgn, const char *newgn){	struct aim_ssi_item *group;	if (!od || !oldgn || !newgn)		return -EINVAL;	if (!(group = aim_ssi_itemlist_finditem(od->ssi.local, oldgn, NULL, AIM_SSI_TYPE_GROUP)))		return -EINVAL;	g_free(group->name);	group->name = (char *)g_malloc((strlen(newgn)+1)*sizeof(char));	strcpy(group->name, newgn);	/* Sync our local list with the server list */	return aim_ssi_sync(od);}/** * Stores your permit/deny setting on the server, and starts using it. * * @param od The oscar odion. * @param permdeny Your permit/deny setting.  Can be one of the following: *        1 - Allow all users *        2 - Block all users *        3 - Allow only the users below *        4 - Block only the users below *        5 - Allow only users on my buddy list * @param vismask A bitmask of the class of users to whom you want to be *        visible.  See the AIM_FLAG_BLEH #defines in oscar.h * @return Return 0 if no errors, otherwise return the error number. */int aim_ssi_setpermdeny(OscarData *od, guint8 permdeny, guint32 vismask){	struct aim_ssi_item *tmp;	if (!od || !od->ssi.received_data)		return -EINVAL;	/* Find the PDINFO item, or add it if it does not exist */	if (!(tmp = aim_ssi_itemlist_finditem(od->ssi.local, NULL, NULL, AIM_SSI_TYPE_PDINFO))) {		/* Make sure the master group exists */		if (aim_ssi_itemlist_find(od->ssi.local, 0x0000, 0x0000) == NULL)			aim_ssi_itemlist_add(&od->ssi.local, NULL, 0x0000, 0x0000, AIM_SSI_TYPE_GROUP, NULL);		tmp = aim_ssi_itemlist_add(&od->ssi.local, NULL, 0x0000, 0xFFFF, AIM_SSI_TYPE_PDINFO, NULL);	}	/* Need to add the 0x00ca TLV to the TLV chain */	aim_tlvlist_replace_8(&tmp->data, 0x00ca, permdeny);	/* Need to add the 0x00cb TLV to the TLV chain */	aim_tlvlist_replace_32(&tmp->data, 0x00cb, vismask);	/* Sync our local list with the server list */	return aim_ssi_sync(od);}/** * Set buddy icon information * * @param od The oscar odion. * @param iconcsum The MD5 checksum of the icon you are using. * @param iconcsumlen Length of the MD5 checksum given above.  Should be 0x10 bytes. * @return Return 0 if no errors, otherwise return the error number. */int aim_ssi_seticon(OscarData *od, const guint8 *iconsum, guint8 iconsumlen){	struct aim_ssi_item *tmp;	guint8 *csumdata;	if (!od || !iconsum || !iconsumlen || !od->ssi.received_data)		return -EINVAL;	/* Find the ICONINFO item, or add it if it does not exist */	if (!(tmp = aim_ssi_itemlist_finditem(od->ssi.local, NULL, "1", AIM_SSI_TYPE_ICONINFO))) {		/* Make sure the master group exists */		if (aim_ssi_itemlist_find(od->ssi.local, 0x0000, 0x0000) == NULL)			aim_ssi_itemlist_add(&od->ssi.local, NULL, 0x0000, 0x0000, AIM_SSI_TYPE_GROUP, NULL);		tmp = aim_ssi_itemlist_add(&od->ssi.local, "1", 0x0000, 0xFFFF, AIM_SSI_TYPE_ICONINFO, NULL);	}	/* Need to add the 0x00d5 TLV to the TLV chain */	csumdata = (guint8 *)g_malloc((iconsumlen+2)*sizeof(guint8));	aimutil_put8(&csumdata[0], 0x00);	aimutil_put8(&csumdata[1], iconsumlen);	memcpy(&csumdata[2], iconsum, iconsumlen);	aim_tlvlist_replace_raw(&tmp->data, 0x00d5, (iconsumlen+2) * sizeof(guint8), csumdata);	g_free(csumdata);	/* Need to add the 0x0131 TLV to the TLV chain, used to cache the icon */	aim_tlvlist_replace_noval(&tmp->data, 0x0131);	/* Sync our local list with the server list */	aim_ssi_sync(od);	return 0;}/** * Remove a reference to a server stored buddy icon.  This will make your * icon stop showing up to other people. * * Really this function just sets the icon to a dummy value.  It's weird... * but I think the dummy value basically means "I don't have an icon!" * * @param od The oscar session. * @return Return 0 if no errors, otherwise return the error number. */int aim_ssi_delicon(OscarData *od){	const guint8 csumdata[] = {0x02, 0x01, 0xd2, 0x04, 0x72};	return aim_ssi_seticon(od, csumdata, 5);}/** * Stores your setting for various SSI settings.  Whether you * should show up as idle or not, etc. * * @param od The oscar odion. * @param presence I think it's a bitmask, but I only know what one of the bits is: *        0x00000002 - Hide wireless? *        0x00000400 - Allow others to see your idle time * @return Return 0 if no errors, otherwise return the error number. */int aim_ssi_setpresence(OscarData *od, guint32 presence) {	struct aim_ssi_item *tmp;	if (!od || !od->ssi.received_data)		return -EINVAL;	/* Find the PRESENCEPREFS item, or add it if it does not exist */	if (!(tmp = aim_ssi_itemlist_finditem(od->ssi.local, NULL, NULL, AIM_SSI_TYPE_PRESENCEPREFS))) {		/* Make sure the master group exists */		if (aim_ssi_itemlist_find(od->ssi.local, 0x0000, 0x0000) == NULL)			aim_ssi_itemlist_add(&od->ssi.local, NULL, 0x0000, 0x0000, AIM_SSI_TYPE_GROUP, NULL);		tmp = aim_ssi_itemlist_add(&od->ssi.local, NULL, 0x0000, 0xFFFF, AIM_SSI_TYPE_PRESENCEPREFS, NULL);	}	/* Need to add the x00c9 TLV to the TLV chain */	aim_tlvlist_replace_32(&tmp->data, 0x00c9, presence);	/* Sync our local list with the server list */	return aim_ssi_sync(od);}/* * Subtype 0x0002 - Request SSI Rights. */int aim_ssi_reqrights(OscarData *od){	FlapConnection *conn;	if (!od || !(conn = flap_connection_findbygroup(od, SNAC_FAMILY_FEEDBAG)))		return -EINVAL;	aim_genericreq_n_snacid(od, conn, SNAC_FAMILY_FEEDBAG, SNAC_SUBTYPE_FEEDBAG_REQRIGHTS);	return 0;}/* * Subtype 0x0003 - SSI Rights Information. */static int parserights(OscarData *od, FlapConnection *conn, aim_module_t *mod, FlapFrame *frame, aim_modsnac_t *snac, ByteStream *bs){	int ret = 0, i;	aim_rxcallback_t userfunc;	GSList *tlvlist;	aim_tlv_t *tlv;	ByteStream bstream;	guint16 *maxitems;	/* This SNAC is made up of a bunch of TLVs */	tlvlist = aim_tlvlist_read(bs);	/* TLV 0x0004 contains the maximum number of each item */	if (!(tlv = aim_tlv_gettlv(tlvlist, 0x0004, 1))) {		aim_tlvlist_free(tlvlist);		return 0;	}	byte_stream_init(&bstream, tlv->value, tlv->length);	maxitems = (guint16 *)g_malloc((tlv->length/2)*sizeof(guint16));	for (i=0; i<(tlv->length/2); i++)		maxitems[i] = byte_stream_get16(&bstream);	if ((userfunc = aim_callhandler(od, snac->family, snac->subtype)))		ret = userfunc(od, conn, frame, tlv->length/2, maxitems);	aim_tlvlist_free(tlvlist);	g_free(maxitems);	return ret;}/* * Subtype 0x0004 - Request SSI Data when you don't have a timestamp and * revision number. * */int aim_ssi_reqdata(OscarData *od){	FlapConnection *conn;	if (!od || !(conn = flap_connection_findbygroup(od, SNAC_FAMILY_FEEDBAG)))		return -EINVAL;	/* Free any current data, just in case */	aim_ssi_freelist(od);	aim_genericreq_n_snacid(od, conn, SNAC_FAMILY_FEEDBAG, SNAC_SUBTYPE_FEEDBAG_REQDATA);	return 0;}/* * Subtype 0x0005 - Request SSI Data when you have a timestamp and revision * number. * * The data will only be sent if it is newer than the posted local * timestamp and revision. * * Note that the client should never increment the revision, only the server. * */int aim_ssi_reqifchanged(OscarData *od, time_t timestamp, guint16 numitems){	FlapConnection *conn;	FlapFrame *frame;	aim_snacid_t snacid;	if (!od || !(conn = flap_connection_findbygroup(od, SNAC_FAMILY_FEEDBAG)))		return -EINVAL;	frame = flap_frame_new(od, 0x02, 10+4+2);	snacid = aim_cachesnac(od, SNAC_FAMILY_FEEDBAG, SNAC_SUBTYPE_FEEDBAG_REQIFCHANGED, 0x0000, NULL, 0);	aim_putsnac(&frame->data, SNAC_FAMILY_FEEDBAG, SNAC_SUBTYPE_FEEDBAG_REQIFCHANGED, 0x0000, snacid);	byte_stream_put32(&frame->data, timestamp);	byte_stream_put16(&frame->data, numitems);	flap_connection_send(conn, frame);	/* Free any current data, just in case */	aim_ssi_freelist(od);	return 0;}/* * Subtype 0x0006 - SSI Data. */static int parsedata(OscarData *od, FlapConnection *conn, aim_module_t *mod, FlapFrame *frame, aim_modsnac_t *snac, ByteStream *bs){	int ret = 0;	aim_rxcallback_t userfunc;	guint8 fmtver; /* guess */	guint16 namelen, gid, bid, type;	char *name;	GSList *data;	fmtver = byte_stream_get8(bs); /* Version of ssi data.  Should be 0x00 */	od->ssi.numitems += byte_stream_get16(bs); /* # of items in this SSI SNAC */	/* Read in the list */	while (byte_stream_empty(bs) > 4) { /* last four bytes are timestamp */		if ((namelen = byte_stream_get16(bs)))			name = byte_stream_getstr(bs, namelen);		else			name = NULL;		gid = byte_stream_get16(bs);		bid = byte_stream_get16(bs);		type = byte_stream_get16(bs);		data = aim_tlvlist_readlen(bs, byte_stream_get16(bs));		aim_ssi_itemlist_add(&od->ssi.official, name, gid, bid, type, data);		g_free(name);		aim_tlvlist_free(data);	}	/* Read in the timestamp */	od->ssi.timestamp = byte_stream_get32(bs);	if (!(snac->flags & 0x0001)) {		/* Make a copy of the list */		struct aim_ssi_item *cur;		for (cur=od->ssi.official; cur; cur=cur->next)			aim_ssi_itemlist_add(&od->ssi.local, cur->name, cur->gid, cur->bid, cur->type, cur->data);		od->ssi.received_data = TRUE;		if ((userfunc = aim_callhandler(od, snac->family, snac->subtype)))			ret = userfunc(od, conn, frame, fmtver, od->ssi.numitems, od->ssi.timestamp);	}	return ret;}/* * Subtype 0x0007 - SSI Activate Data. * * Should be sent after receiving 13/6 or 13/f to tell the server you * are ready to begin using the list.  It will promptly give you the * presence information for everyone in your list and put your permit/deny * settings into effect. * */int aim_ssi_enable(OscarData *od){	FlapConnection *conn;	if (!od || !(conn = flap_connection_findbygroup(od, SNAC_FAMILY_FEEDBAG)))		return -EINVAL;	aim_genericreq_n(od, conn, SNAC_FAMILY_FEEDBAG, 0x0007);	return 0;}/* * Subtype 0x0008/0x0009/0x000a - SSI Add/Mod/Del Item(s). * * Sends the SNAC to add, modify, or delete items from the server-stored * information.  These 3 SNACs all have an identical structure.  The only * difference is the subtype that is set for the SNAC. * */static int aim_ssi_addmoddel(OscarData *od){	FlapConnection *conn;	FlapFrame *frame;	aim_snacid_t snacid;	int snaclen;	struct aim_ssi_tmp *cur;	if (!od || !(conn = flap_connection_findbygroup(od, SNAC_FAMILY_FEEDBAG)) || !od->ssi.pending || !od->ssi.pending->item)		return -EINVAL;	/* Calculate total SNAC size */	snaclen = 10; /* For family, subtype, flags, and SNAC ID */	for (cur=od->ssi.pending; cur; cur=cur->next) {		snaclen += 10; /* For length, GID, BID, type, and length */		if (cur->item->name)			snaclen += strlen(cur->item->name);		if (cur->item->data)			snaclen += aim_tlvlist_size(cur->item->data);	}	frame = flap_frame_new(od, 0x02, snaclen);	snacid = aim_cachesnac(od, SNAC_FAMILY_FEEDBAG, od->ssi.pending->action, 0x0000, NULL, 0);	aim_putsnac(&frame->data, SNAC_FAMILY_FEEDBAG, od->ssi.pending->action, 0x0000, snacid);	for (cur=od->ssi.pending; cur; cur=cur->next) {		byte_stream_put16(&frame->data, cur->item->name ? strlen(cur->item->name) : 0);		if (cur->item->name)			byte_stream_putstr(&frame->data, cur->item->name);		byte_stream_put16(&frame->data, cur->item->gid);		byte_stream_put16(&frame->data, cur->item->bid);		byte_stream_put16(&frame->data, cur->item->type);		byte_stream_put16(&frame->data, cur->item->data ? aim_tlvlist_size(cur->item->data) : 0);		if (cur->item->data)			aim_tlvlist_write(&frame->data, &cur->item->data);	}	flap_connection_send(conn, frame);	return 0;}/* * Subtype 0x0008 - Incoming SSI add. * * Sent by the server, for example, when someone is added to * your "Recent Buddies" group. */static int parseadd(OscarData *od, FlapConnection *conn, aim_module_t *mod, FlapFrame *frame, aim_modsnac_t *snac, ByteStream *bs){	int ret = 0;	aim_rxcallback_t userfunc;	char *name;	guint16 len, gid, bid, type;	GSList *data;	while (byte_stream_empty(bs)) {		if ((len = byte_stream_get16(bs)))			name = byte_stream_getstr(bs, len);		else			name = NULL;		gid = byte_stream_get16(bs);		bid = byte_stream_get16(bs);		type = byte_stream_get16(bs);		if ((len = byte_stream_get16(bs)))			data = aim_tlvlist_readlen(bs, len);		else			data = NULL;		aim_ssi_itemlist_add(&od->ssi.local, name, gid, bid, type, data);		aim_ssi_itemlist_add(&od->ssi.official, name, gid, bid, type, data);		aim_tlvlist_free(data);		if ((userfunc = aim_callhandler(od, snac->family, snac->subtype)))			ret = userfunc(od, conn, frame, type, name);		g_free(name);	}	return ret;}/* * Subtype 0x0009 - Incoming SSI mod. * * XXX - It would probably be good for the client to actually do something when it gets this. */static int parsemod(OscarData *od, FlapConnection *conn, aim_module_t *mod, FlapFrame *frame, aim_modsnac_t *snac, ByteStream *bs){	int ret = 0;	aim_rxcallback_t userfunc;	char *name;	guint16 len, gid, bid, type;	GSList *data;	struct aim_ssi_item *item;	while (byte_stream_empty(bs)) {		if ((len = byte_stream_get16(bs)))			name = byte_stream_getstr(bs, len);		else			name = NULL;		gid = byte_stream_get16(bs);		bid = byte_stream_get16(bs);		type = byte_stream_get16(bs);		if ((len = byte_stream_get16(bs)))			data = aim_tlvlist_readlen(bs, len);		else			data = NULL;		/* Replace the 2 local items with the given one */		if ((item = aim_ssi_itemlist_find(od->ssi.local, gid, bid))) {			item->type = type;			g_free(item->name);			if (name) {				item->name = (char *)g_malloc((strlen(name)+1)*sizeof(char));				strcpy(item->name, name);			} else				item->name = NULL;			aim_tlvlist_free(item->data);			item->data = aim_tlvlist_copy(data);		}		if ((item = aim_ssi_itemlist_find(od->ssi.official, gid, bid))) {			item->type = type;			g_free(item->name);			if (name) {				item->name = (char *)g_malloc((strlen(name)+1)*sizeof(char));				strcpy(item->name, name);			} else				item->name = NULL;			aim_tlvlist_free(item->data);			item->data = aim_tlvlist_copy(data);		}		if ((userfunc = aim_callhandler(od, snac->family, snac->subtype)))			ret = userfunc(od, conn, frame);		g_free(name);		aim_tlvlist_free(data);	}	return ret;}/* * Subtype 0x000a - Incoming SSI del. * * XXX - It would probably be good for the client to actually do something when it gets this. */static int parsedel(OscarData *od, FlapConnection *conn, aim_module_t *mod, FlapFrame *frame, aim_modsnac_t *snac, ByteStream *bs){	int ret = 0;	aim_rxcallback_t userfunc;	guint16 gid, bid;	struct aim_ssi_item *del;	while (byte_stream_empty(bs)) {		byte_stream_advance(bs, byte_stream_get16(bs));		gid = byte_stream_get16(bs);		bid = byte_stream_get16(bs);		byte_stream_get16(bs);		byte_stream_advance(bs, byte_stream_get16(bs));

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -