changeset 253:5b28ef2b550e

[gaim-migrate @ 263] A few things happened in this update: - Commented out the libfaim deny/permit list stuff because it's seriously buggy - Added Socks v4 support - improved proxy support for things like getting users' info - i think that's it committer: Tailor Script <tailor@pidgin.im>
author Eric Warmenhoven <eric@warmenhoven.org>
date Tue, 23 May 2000 05:26:30 +0000
parents 4a41f8323022
children fa67d29b53d5
files ChangeLog libfaim/CHANGES.gaim libfaim/README.gaim src/aim.c src/dialogs.c src/gaim.h src/html.c src/oscar.c src/prefs.c src/proxy.c src/rvous.c src/server.c
diffstat 12 files changed, 190 insertions(+), 137 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Mon May 22 23:58:03 2000 +0000
+++ b/ChangeLog	Tue May 23 05:26:30 2000 +0000
@@ -10,7 +10,9 @@
 	  (AOL does not back up machines that contain TOC-based buddy
 	  lists, unfortunately).  (Thanks Syd)
 	* Font selection dialog 
-	* Small changes to the Oscar/libfaim stuff (it works now, sort of)
+	* Small changes to the Oscar/libfaim stuff (see libfaim/README.gaim)
+	* SOCKS v4 Proxy support
+	* Better proxy support overall (you can get people's info now! :) )
 
 version 0.9.15: (05/06/2000)
 	* Plugin support enabled by default (oops)
--- a/libfaim/CHANGES.gaim	Mon May 22 23:58:03 2000 +0000
+++ b/libfaim/CHANGES.gaim	Tue May 23 05:26:30 2000 +0000
@@ -1,3 +1,12 @@
+
+Tue May 23 03:32:26 UTC 2000 EWarmenhoven
+	- I commented out the code to tell the server who's on your permit or
+	  deny lists. I coded that part seriously wrong.
+	- un-#ifndef'd rvous.c, so theoretically, once libfaim supports file
+	  transfer (et al.) it should be relatively easy to add the code for
+	  it.
+	- Placed FIXME's throughout the code to try to signal problems
+	- Other touch-ups (not worth mentioning)
 
 Mon May 22 19:02:19 UTC 2000 EWarmenhoven
 	- Able to be invited to join a chat room
--- a/libfaim/README.gaim	Mon May 22 23:58:03 2000 +0000
+++ b/libfaim/README.gaim	Tue May 23 05:26:30 2000 +0000
@@ -33,7 +33,6 @@
 Getting users' away messages (PLEASE do not use oscar/libfaim just because of
 	this, gaim with libfaim is still really buggy, none of you will listen
 	to me anyway)
-Telling the server who's on your permit/deny lists (buggy)
 Chat:
  - joining rooms
  - leaving rooms
@@ -50,6 +49,7 @@
 Getting/setting dir info
 Changing your password
 File transfer/IM images/voice chat/etc.
+Telling the server who's on your permit/deny lists (buggy)
 
 KNOWN ISSUES
 ============
@@ -57,79 +57,27 @@
 You can receive more messages in less time with TOC than with libfaim. It's not
 completely libfaim's fault though.
 
-- Signing on every once in a while acts really bizarrely for me. Maybe it's just
-me. I think it has something to do with the horrible lack of error checking and
-recovery on gaim's part.
+- It's possible that if the server negotiations don't happen fast enough, it'll
+look like you're trying to sign in twice (and in fact you will be). It doesn't
+seem to negatively affect anything, but it will when people start using it. (I
+think this may actually be related to the auto_recon plugin.) (FIXME for this is
+marked in aim.c)
 
 - Adding or removing people to your permit/deny lists causes the server to tell
 you everyone on your buddy list signed off and then immediately signed in again.
 While you won't ever see that it happens (other than everyone will suddenly have
 the guy-in-the-door icon), you'll hear it. Be warned. (This also happens at
-sign-on, because the list gets built, even if you don't have a list.)
+sign-on, because the list gets built, even if you don't have a list.) I've
+commented it out because it was causing too many problems. (FIXME for this is
+marked in server.c)
 
-- It doesn't set the current_user in .gaimrc correctly, so the users listed in
-there will get really warped. Don't worry, it's just a problem with the .gaimrc,
-but it's an annoying one.
+- There are a lot of problems with panel support (funny that I'm supporting the
+panel code, and the oscar code I wrote doesn't work well with it).
 
 - Oh, yeah, by the way, it'll eat up all your CPU. (Someone please fix this,
 there's a nice FIXME near the top of oscar.c that says what the problem is.)
 
-HOW TO HELP
-===========
-So here's what you can do in order to help gaim use libfaim. There are basically
-3 steps:
-
-1) In server.c, find an #ifndef USE_OSCAR tag that doesn't have a corresponding
-#else. Find it in a good fun function that you want to implement. Basically
-copy the code from the TOC side for the Oscar side. For example:
-
-void serv_send_im(char *name, char *message, int away)
-{
-	char buf[MSG_LEN - 7];
-
-#ifndef USE_OSCAR
-	g_snprintf(buf, MSG_LEN - 8, "toc_send_im %s \"%s\"%s", normalize(name),		   message, ((away) ? " auto" : ""));
-	sflap_send(buf, strlen(buf), TYPE_DATA);
-#endif
-	if (!away)
-		serv_touch_idle();
-}
-
-becomes:
-
-void serv_send_im(char *name, char *message, int away)
-{
-        char buf[MSG_LEN - 7];
-
-#ifndef USE_OSCAR
-        g_snprintf(buf, MSG_LEN - 8, "toc_send_im %s \"%s\"%s", normalize(name),
-	           message, ((away) ? " auto" : ""));
-	sflap_send(buf, strlen(buf), TYPE_DATA);
-#else
-	oscar_send_im(name, message, away);
-#endif
-	if (!away)
-		serv_touch_idle();
-}
-
-2) Edit gaim.h to add the new function (you'll see a list of them in there)
-
-3) Edit oscar.c to implement the new function
-
-Most of the functions you're going to need to call use a session and connection
-structure. These are kept (globally) in oscar.c as gaim_sess and gaim_conn. For
-example, from above:
-
-void oscar_send_im(char *name, char *msg, int away) {
-	if (away)
-		aim_send_im(gaim_sess, gaim_conn, name, AIM_IMFLAGS_AWAY, msg);
-	else
-		aim_send_im(gaim_sess, gaim_conn, name, 0, msg);
-}
-
-That should be all that's needed.
-
-There are also FIXME's scattered about oscar.c. Grep around for those, figure
+- There are also FIXME's scattered about oscar.c. Grep around for those, figure
 out what needs to be fixed, do that sort of thing. :) (Fixing the things listed
 in KNOWN ISSUES above, or any other bugs you happen to find, is a very good use
 of your time.) (You didn't hear that from me.)
--- a/src/aim.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/aim.c	Tue May 23 05:26:30 2000 +0000
@@ -157,6 +157,8 @@
 	if (running) return;
 	running = TRUE;
 
+	/* libfaim FIXME : serv_login only starts the process. it's not over
+	 * after serv_login gets called */
         if (serv_login(username, password) < 0) {
 		running = FALSE;
                 return;
--- a/src/dialogs.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/dialogs.c	Tue May 23 05:26:30 2000 +0000
@@ -162,8 +162,7 @@
 {
 	static char email_data[2000];
 	int sock;
-	struct hostent *host;
-	struct sockaddr_in site;
+	struct in_addr *host;
 /*	char data[3]; */
 	FILE *sockfile;
 	char uname_output;
@@ -189,25 +188,14 @@
 		system(buf);
 	}
 	
-	host = gethostbyname(REG_SRVR);
+	host = (struct in_addr *)get_address(REG_SRVR);
 	if (!host) 
 	{
 		printf("Error Resolving Mail Server.\n");
 		return -1;
 	}
 
-	site.sin_family = AF_INET;
-	site.sin_addr.s_addr = *(long *)(host->h_addr);
-	site.sin_port = htons(REG_PORT);
-
-	sock = socket(AF_INET, SOCK_STREAM, 0);
-	if (sock < 0)
-	{
-		printf("Socket Error.\n");
-		return -1;
-	}
-	
-	if (connect(sock, (struct sockaddr *)&site, sizeof(site)))
+	if ((sock = connect_address(host->s_addr, REG_PORT)) < 0)
 	{
 		printf("Error Connecting to Socket.\n");
 		return -1;
--- a/src/gaim.h	Mon May 22 23:58:03 2000 +0000
+++ b/src/gaim.h	Tue May 23 05:26:30 2000 +0000
@@ -105,6 +105,8 @@
         GtkWidget *login_port_entry;
         GtkWidget *http_proxy_host_entry;
         GtkWidget *http_proxy_port_entry;
+        GtkWidget *socks_proxy_host_entry;
+        GtkWidget *socks_proxy_port_entry;
 
 };
 
@@ -337,7 +339,7 @@
 #define TYPE_SIGNOFF   4
 #define TYPE_KEEPALIVE 5
 
-#define REVISION "gaim:$Revision: 259 $"
+#define REVISION "gaim:$Revision: 263 $"
 #define FLAPON "FLAPON\r\n\r\n"
 
 #define ROAST "Tic/Toc"
--- a/src/html.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/html.c	Tue May 23 05:26:30 2000 +0000
@@ -102,8 +102,7 @@
         int sock;
         int len;
 	int datalen = 0;
-	struct hostent *host;
-	struct sockaddr_in site;
+	struct in_addr *host;
 	char buf[256];
 	char data;
         FILE *sockfile;
@@ -112,17 +111,16 @@
 
         website = parse_url(url);
 
+	/*
 	host = gethostbyname(website.address);
 	if (!host) { return g_strdup("g001: Error resolving host\n"); }
 
-	site.sin_family = AF_INET;
-	site.sin_addr.s_addr = *(long *)(host->h_addr);
-	site.sin_port = htons(website.port);
-
-	sock = socket(AF_INET, SOCK_STREAM, 0);
-	if (sock < 0) { return g_strdup("g002: Socket Error\n"); }
-
-	if (connect(sock, (struct sockaddr *)&site, sizeof(site)))
+	if ((sock = connect_address(inet_addr(host->h_addr), website.port)) <= -1)
+		return g_strdup("g003: Error opening connection.\n");
+	*/
+	host = (struct in_addr *)get_address(website.address);
+	if (!host) { return g_strdup("g001: Error resolving host\n"); }
+	if ((sock = connect_address(host->s_addr, website.port)) < 0)
 		return g_strdup("g003: Error opening connection.\n");
 
 	sockfile = fdopen(sock, "r+");
--- a/src/oscar.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/oscar.c	Tue May 23 05:26:30 2000 +0000
@@ -106,6 +106,7 @@
 	struct aim_session_t *sess;
 	struct aim_conn_t *conn;
 	struct client_info_s info = {"Gaim/Faim", 3, 5, 1670, "us", "en"};
+	struct aim_user *u;
 	char buf[256];
 
 	sess = g_new0(struct aim_session_t, 1);
@@ -155,12 +156,14 @@
 				GDK_INPUT_READ | GDK_INPUT_EXCEPTION,
 				oscar_callback, sess);
 
-	if (!current_user) {
-		current_user = g_new0(struct aim_user, 1);
-		g_snprintf(current_user->username, sizeof(current_user->username),
-				DEFAULT_INFO);
-		aim_users = g_list_append(aim_users, current_user);
+	u = find_user(username);
+
+	if (!u) {
+		u = g_new0(struct aim_user, 1);
+		g_snprintf(u->username, sizeof(u->username), DEFAULT_INFO);
+		aim_users = g_list_append(aim_users, u);
 	}
+	current_user = u;
 	g_snprintf(current_user->username, sizeof(current_user->username),
 				"%s", username);
 	g_snprintf(current_user->password, sizeof(current_user->password),
@@ -412,9 +415,9 @@
 
 	if (info->class & AIM_CLASS_TRIAL)
 		type |= UC_UNCONFIRMED;
-	if (info->class & AIM_CLASS_AOL)
+	else if (info->class & AIM_CLASS_AOL)
 		type |= UC_AOL;
-	if (info->class & AIM_CLASS_FREE)
+	else if (info->class & AIM_CLASS_FREE)
 		type |= UC_NORMAL;
 	if (info->class & AIM_CLASS_AWAY)
 		type |= UC_UNAVAILABLE;
@@ -490,6 +493,7 @@
 		} else if (rendtype == 1) {
 			/* FIXME : voice chat */
 		}
+		/* libfaim doesn't do file transfer yet, from what i can tell */
 	}
 
 	return 1;
--- a/src/prefs.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/prefs.c	Tue May 23 05:26:30 2000 +0000
@@ -213,8 +213,13 @@
 {
 	g_snprintf(aim_host, sizeof(aim_host), "%s", gtk_entry_get_text(GTK_ENTRY(pd->aim_host_entry)));
 	sscanf(gtk_entry_get_text(GTK_ENTRY(pd->aim_port_entry)), "%d", &aim_port);
-	g_snprintf(proxy_host, sizeof(proxy_host), "%s", gtk_entry_get_text(GTK_ENTRY(pd->http_proxy_host_entry)));
-	sscanf(gtk_entry_get_text(GTK_ENTRY(pd->http_proxy_port_entry)), "%d", &proxy_port);
+	if (proxy_type == PROXY_HTTP) {
+		g_snprintf(proxy_host, sizeof(proxy_host), "%s", gtk_entry_get_text(GTK_ENTRY(pd->http_proxy_host_entry)));
+		sscanf(gtk_entry_get_text(GTK_ENTRY(pd->http_proxy_port_entry)), "%d", &proxy_port);
+	} else if (proxy_type == PROXY_SOCKS) {
+		g_snprintf(proxy_host, sizeof(proxy_host), "%s", gtk_entry_get_text(GTK_ENTRY(pd->socks_proxy_host_entry)));
+		sscanf(gtk_entry_get_text(GTK_ENTRY(pd->socks_proxy_port_entry)), "%d", &proxy_port);
+	}
 
 	g_snprintf(login_host, sizeof(login_host), "%s", gtk_entry_get_text(GTK_ENTRY(pd->login_host_entry)));
 	sscanf(gtk_entry_get_text(GTK_ENTRY(pd->login_port_entry)), "%d", &login_port);	
@@ -256,13 +261,28 @@
                         gtk_widget_set_sensitive(pd->http_proxy_host_entry, TRUE);
 		if (pd->http_proxy_port_entry)
 			gtk_widget_set_sensitive(pd->http_proxy_port_entry, TRUE);
-
+		if (pd->socks_proxy_host_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_host_entry, FALSE);
+		if (pd->socks_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_port_entry, FALSE);
+	} else if (proxy_type == PROXY_SOCKS) {
+		if (pd->socks_proxy_host_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_host_entry, TRUE);
+		if (pd->socks_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_port_entry, TRUE);
+                if (pd->http_proxy_host_entry)
+                        gtk_widget_set_sensitive(pd->http_proxy_host_entry, FALSE);
+		if (pd->http_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->http_proxy_port_entry, FALSE);
 	} else {
                 if (pd->http_proxy_host_entry)
                         gtk_widget_set_sensitive(pd->http_proxy_host_entry, FALSE);
 		if (pd->http_proxy_port_entry)
 			gtk_widget_set_sensitive(pd->http_proxy_port_entry, FALSE);
-
+		if (pd->socks_proxy_host_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_host_entry, FALSE);
+		if (pd->socks_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_port_entry, FALSE);
 	}
         
         save_prefs();
@@ -509,6 +529,36 @@
 	g_snprintf(buffer, sizeof(buffer), "%d", proxy_port);
 	gtk_entry_set_text(GTK_ENTRY(pd->http_proxy_port_entry), buffer);
 
+        connectopt = gtk_radio_button_new_with_label(gtk_radio_button_group(GTK_RADIO_BUTTON(connectopt)), "SOCKS v4 Proxy");
+        gtk_box_pack_start(GTK_BOX(connection_page), connectopt, FALSE, FALSE, 0);
+        gtk_signal_connect(GTK_OBJECT(connectopt), "clicked", GTK_SIGNAL_FUNC(set_connect), (void *)PROXY_SOCKS);
+	gtk_widget_show(connectopt);
+	if (proxy_type == PROXY_SOCKS)
+                gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(connectopt), TRUE);
+
+
+	hbox = gtk_hbox_new(FALSE, 0);
+	label = gtk_label_new("Proxy Host:");
+	gtk_widget_show(label);
+	gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 5);
+        pd->socks_proxy_host_entry = gtk_entry_new();
+        gtk_widget_show(pd->socks_proxy_host_entry);
+	gtk_box_pack_start(GTK_BOX(hbox), pd->socks_proxy_host_entry, FALSE, FALSE, 0);
+
+	label = gtk_label_new("Port:");
+	gtk_widget_show(label);
+	gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 5);
+        pd->socks_proxy_port_entry = gtk_entry_new();
+        gtk_widget_show(pd->socks_proxy_port_entry);
+	gtk_box_pack_start(GTK_BOX(hbox), pd->socks_proxy_port_entry, FALSE, FALSE, 0);
+	gtk_widget_show(hbox);
+	
+	gtk_box_pack_start(GTK_BOX(connection_page), hbox, FALSE, FALSE, 0);
+	gtk_entry_set_text(GTK_ENTRY(pd->socks_proxy_host_entry), proxy_host);
+
+	g_snprintf(buffer, sizeof(buffer), "%d", proxy_port);
+	gtk_entry_set_text(GTK_ENTRY(pd->socks_proxy_port_entry), buffer);
+
 
 	gtk_widget_show(connection_page);
 
@@ -518,13 +568,28 @@
                         gtk_widget_set_sensitive(pd->http_proxy_host_entry, TRUE);
 		if (pd->http_proxy_port_entry)
 			gtk_widget_set_sensitive(pd->http_proxy_port_entry, TRUE);
-
+		if (pd->socks_proxy_host_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_host_entry, FALSE);
+		if (pd->socks_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_port_entry, FALSE);
+	} else if (proxy_type == PROXY_SOCKS) {
+		if (pd->socks_proxy_host_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_host_entry, TRUE);
+		if (pd->socks_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_port_entry, TRUE);
+                if (pd->http_proxy_host_entry)
+                        gtk_widget_set_sensitive(pd->http_proxy_host_entry, FALSE);
+		if (pd->http_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->http_proxy_port_entry, FALSE);
 	} else {
                 if (pd->http_proxy_host_entry)
                         gtk_widget_set_sensitive(pd->http_proxy_host_entry, FALSE);
 		if (pd->http_proxy_port_entry)
 			gtk_widget_set_sensitive(pd->http_proxy_port_entry, FALSE);
-
+		if (pd->socks_proxy_host_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_host_entry, FALSE);
+		if (pd->socks_proxy_port_entry)
+			gtk_widget_set_sensitive(pd->socks_proxy_port_entry, FALSE);
 	}
 
 	
@@ -533,8 +598,10 @@
         gtk_signal_connect(GTK_OBJECT(pd->aim_port_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
 	gtk_signal_connect(GTK_OBJECT(pd->login_host_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
 	gtk_signal_connect(GTK_OBJECT(pd->login_port_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
-	gtk_signal_connect(GTK_OBJECT(pd->http_proxy_host_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
-        gtk_signal_connect(GTK_OBJECT(pd->http_proxy_port_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
+	gtk_signal_connect(GTK_OBJECT(pd->socks_proxy_host_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
+        gtk_signal_connect(GTK_OBJECT(pd->socks_proxy_port_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
+	gtk_signal_connect(GTK_OBJECT(pd->socks_proxy_host_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
+        gtk_signal_connect(GTK_OBJECT(pd->socks_proxy_port_entry), "focus_out_event", GTK_SIGNAL_FUNC(connection_key_pressed), NULL);
 
 	
 	/* Away */
--- a/src/proxy.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/proxy.c	Tue May 23 05:26:30 2000 +0000
@@ -177,7 +177,6 @@
         case PROXY_SOCKS: /* Socks v4 proxy (? I'm not a proxy hacker) */
 		/* this is going to be a cross between the HTTP proxy code
 		 * above and the TiK proxy code, translated from tcl->C */
-		/*
 		{
 			struct hostent *hostinfo;
 			unsigned short shortport = proxy_port;
@@ -196,24 +195,38 @@
 		debug_print(debug_buff);
 		if ((ret = connect(sockfd,(struct sockaddr *)&name,sizeof(name)))<0)
 			return(ret);
-*/
+
 		/* here's where it's no longer http proxy and is now tik */
-/*		{
+		{
 			char cmd[80];
 			char *inputline;
+                        unsigned short realport=((struct sockaddr_in *)serv_addr)->sin_port;
+                        unsigned long realhost=((struct sockaddr_in *)serv_addr)->sin_addr.s_addr;
 
-			snprintf(cmd, 80, "\0x4\0x1%d%d%d%d%d", toc_port,
-					toc_server_1,
-					toc_server_2, /* the second part of the
-							 ip address: 1.this.1.1
-						      *//*
-					toc_server_3,
-					toc_server_4);
-                        if (send(sockfd,cmd,strlen(cmd),0)<0)
+			cmd[0] = 4; cmd[0] = 1;
+			memcpy(cmd + 2, &realport, 2);
+			memcpy(cmd + 4, &realhost, 4);
+			cmd[8] = 0;
+                        if (send(sockfd,cmd,8,0)<0)
                                 return(-1);
                         if (proxy_recv_line(sockfd,&inputline) < 0) {
                                 return(-1);
-                        }*/
+                        }
+			if (inputline[1] != 90) {
+				sprintf(debug_buff, "request failed: %d\n",
+						inputline[1]);
+				debug_print(debug_buff);
+				if (inputline[1] == 91)
+					do_error_dialog("The SOCKS proxy denied"
+							"your request.",
+							"Gaim - Proxy Error");
+				else
+					do_error_dialog("Unknown SOCKS error.",
+							"Gaim - Proxy Error");
+				return -1;
+			}
+		}
+		return ret;
                 break;
         default:
                 fprintf(stderr,"Unknown proxy type : %d.\n",proxy_type);
--- a/src/rvous.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/rvous.c	Tue May 23 05:26:30 2000 +0000
@@ -19,8 +19,6 @@
  *
  */
 
-#ifndef USE_OSCAR
-
 #include <string.h>
 #include <stdio.h>
 #include <stdlib.h>
@@ -76,9 +74,13 @@
 		return;
 	}
 	
+#ifndef USE_OSCAR
 	g_snprintf(send, 255, "toc_rvous_cancel %s %s %s", normalize(ft->user),
 			ft->cookie, ft->UID);
 	sflap_send(send, strlen(send), TYPE_DATA);
+#else
+	/* FIXME : can we really do this? */
+#endif
 	g_free(send);
 	free_ft(ft);
 }
@@ -235,9 +237,13 @@
 	
 	gtk_widget_destroy(ft->window);
 	ft->window = NULL;
+#ifndef USE_OSCAR
 	g_snprintf(send, 255, "toc_rvous_accept %s %s %s", normalize(ft->user),
 			ft->cookie, ft->UID);
 	sflap_send(send, strlen(send), TYPE_DATA);
+#else
+	/* FIXME (?) */
+#endif
 	g_free(send);
 
 	
@@ -340,8 +346,12 @@
 
 	if (!cont) {
 		char *tmp = frombase64(ft->cookie);
+#ifndef USE_OSCAR
 		sprintf(buf, "toc_rvous_cancel %s %s %s", ft->user, tmp, ft->UID);
 		sflap_send(buf, strlen(buf), TYPE_DATA);
+#else
+		/* FIXME (?) */
+#endif
 		close(ft->fd);
 		free_ft(ft);
 		g_free(header);
@@ -395,9 +405,13 @@
 
 	gtk_widget_destroy(ft->window);
 	ft->window = NULL;
+#ifndef USE_OSCAR
 	g_snprintf(send, 255, "toc_rvous_accept %s %s %s", normalize(ft->user),
 			ft->cookie, ft->UID);
 	sflap_send(send, strlen(send), TYPE_DATA);
+#else
+	/* FIXME */
+#endif
 	g_free(send);
 
 
@@ -608,8 +622,12 @@
 
 	if (!cont) {
 		char *tmp = frombase64(ft->cookie);
+#ifndef USE_OSCAR
 		sprintf(buf, "toc_rvous_cancel %s %s %s", ft->user, tmp, ft->UID);
 		sflap_send(buf, strlen(buf), TYPE_DATA);
+#else
+		/* FIXME */
+#endif
 		g_free(buf);
 		close(ft->fd);
 		free_ft(ft);
@@ -701,5 +719,3 @@
 		*/
 	}
 }
-
-#endif /* USE_OSCAR */
--- a/src/server.c	Mon May 22 23:58:03 2000 +0000
+++ b/src/server.c	Tue May 23 05:26:30 2000 +0000
@@ -377,23 +377,27 @@
 	sflap_send(buf, -1, TYPE_DATA);
 #else
 	/* oscar requires us to do everyone at once (?) */
-/* FIXME : there's nothing wrong with this code, but it causes the entire buddy
+/* FIXME : there's something wrong with this code, it causes the entire buddy
  * list to update, and can cause other people's buddy lists to improperly update
-	list = permit; at = 0;
-	while (list) {
-		at += g_snprintf(&buf[at], sizeof(buf) - at, "%s&", list->data);
-		list = list->next;
+	if (!(permdeny == 1 || permdeny == 3)) {
+		list = permit; at = 0;
+		while (list) {
+			at += g_snprintf(&buf[at], sizeof(buf) - at, "%s&", list->data);
+			list = list->next;
+		}
+		aim_bos_changevisibility(gaim_sess, gaim_conn,
+				AIM_VISIBILITYCHANGE_PERMITADD, buf);
+	} else {
+		list = deny; at = 0;
+		if (list == NULL) return;
+		while (list) {
+			at += g_snprintf(&buf[at], sizeof(buf) - at, "%s&", list->data);
+			list = list->next;
+		}
+		aim_bos_changevisibility(gaim_sess, gaim_conn,
+				AIM_VISIBILITYCHANGE_DENYADD, buf);
 	}
-	aim_bos_changevisibility(gaim_sess, gaim_conn,
-			AIM_VISIBILITYCHANGE_PERMITADD, buf);
-	list = deny; at = 0;
-	while (list) {
-		at += g_snprintf(&buf[at], sizeof(buf) - at, "%s&", list->data);
-		list = list->next;
-	}
-	aim_bos_changevisibility(gaim_sess, gaim_conn,
-			AIM_VISIBILITYCHANGE_DENYADD, buf);
-*/
+ */
 #endif
 }