aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--conf.c1
-rw-r--r--conf.h1
-rwxr-xr-xconfigure16
-rw-r--r--protocols/nogaim.c4
-rw-r--r--protocols/oscar/conn.c4
-rw-r--r--protocols/proxy.c14
-rw-r--r--protocols/ssl_bogus.c2
-rw-r--r--protocols/ssl_client.h6
-rw-r--r--protocols/ssl_gnutls.c81
-rw-r--r--protocols/ssl_nss.c2
-rw-r--r--protocols/ssl_openssl.c2
-rw-r--r--sock.h2
-rw-r--r--storage_text.c2
13 files changed, 99 insertions, 38 deletions
diff --git a/conf.c b/conf.c
index 10c6911f..15055ca3 100644
--- a/conf.c
+++ b/conf.c
@@ -54,6 +54,7 @@ conf_t *conf_load( int argc, char *argv[] )
conf->authmode = AUTHMODE_OPEN;
conf->password = NULL;
conf->configdir = g_strdup( CONFIG );
+ conf->plugindir = g_strdup( PLUGINDIR );
conf->motdfile = g_strdup( ETCDIR "/motd.txt" );
conf->ping_interval = 180;
conf->ping_timeout = 300;
diff --git a/conf.h b/conf.h
index ea9de150..c5b2455f 100644
--- a/conf.h
+++ b/conf.h
@@ -40,6 +40,7 @@ typedef struct conf
char *password;
char *hostname;
char *configdir;
+ char *plugindir;
char *motdfile;
char *primary_storage;
char **migrate_storage;
diff --git a/configure b/configure
index e172d40d..37915a07 100755
--- a/configure
+++ b/configure
@@ -144,10 +144,14 @@ else
exit 1;
fi
-if type pkg-config > /dev/null 2>/dev/null && pkg-config glib-2.0; then
+if [ -z "$PKG_CONFIG" ]; then
+ PKG_CONFIG=pkg-config
+fi
+
+if $PKG_CONFIG --version > /dev/null 2>/dev/null && $PKG_CONFIG glib-2.0; then
cat<<EOF>>Makefile.settings
-EFLAGS+=`pkg-config --libs glib-2.0 gmodule-2.0`
-CFLAGS+=`pkg-config --cflags glib-2.0 gmodule-2.0`
+EFLAGS+=`$PKG_CONFIG --libs glib-2.0 gmodule-2.0`
+CFLAGS+=`$PKG_CONFIG --cflags glib-2.0 gmodule-2.0`
EOF
echo '#define GLIB2' >> config.h
elif type glib-config > /dev/null 2> /dev/null; then
@@ -189,10 +193,10 @@ EOF
detect_nss()
{
- if type pkg-config > /dev/null 2>/dev/null && pkg-config mozilla-nss; then
+ if $PKG_CONFIG --version > /dev/null 2>/dev/null && $PKG_CONFIG mozilla-nss; then
cat<<EOF>>Makefile.settings
-EFLAGS+=`pkg-config --libs mozilla-nss`
-CFLAGS+=`pkg-config --cflags mozilla-nss`
+EFLAGS+=`$PKG_CONFIG --libs mozilla-nss`
+CFLAGS+=`$PKG_CONFIG --cflags mozilla-nss`
EOF
ssl=nss
diff --git a/protocols/nogaim.c b/protocols/nogaim.c
index 4966a76f..29ae860a 100644
--- a/protocols/nogaim.c
+++ b/protocols/nogaim.c
@@ -81,14 +81,14 @@ void load_plugins(void)
GDir *dir;
GError *error = NULL;
- dir = g_dir_open(PLUGINDIR, 0, &error);
+ dir = g_dir_open(global.conf->plugindir, 0, &error);
if (dir) {
const gchar *entry;
char *path;
while ((entry = g_dir_read_name(dir))) {
- path = g_build_filename(PLUGINDIR, entry, NULL);
+ path = g_build_filename(global.conf->plugindir, entry, NULL);
if(!path) {
log_message(LOGLVL_WARNING, "Can't build path for %s\n", entry);
continue;
diff --git a/protocols/oscar/conn.c b/protocols/oscar/conn.c
index 0155e5bc..77ffd50f 100644
--- a/protocols/oscar/conn.c
+++ b/protocols/oscar/conn.c
@@ -626,9 +626,7 @@ int aim_conn_completeconnect(aim_session_t *sess, aim_conn_t *conn)
return -1;
}
-#ifndef _WIN32
- fcntl(conn->fd, F_SETFL, 0); /* XXX should restore original flags */
-#endif
+ sock_make_blocking(conn->fd);
conn->status &= ~AIM_CONN_STATUS_INPROGRESS;
diff --git a/protocols/proxy.c b/protocols/proxy.c
index 0546f2d7..c658a163 100644
--- a/protocols/proxy.c
+++ b/protocols/proxy.c
@@ -132,8 +132,8 @@ static void gaim_io_connected(gpointer data, gint source, GaimInputCondition con
}
return;
}
- fcntl(source, F_SETFL, 0);
#endif
+ sock_make_blocking(source);
gaim_input_remove(phb->inpa);
if( phb->proxy_func )
phb->proxy_func(phb->proxy_data, source, GAIM_INPUT_READ);
@@ -228,9 +228,7 @@ static void http_canwrite(gpointer data, gint source, GaimInputCondition cond)
g_free(phb);
return;
}
-#ifdef F_SETFL
- fcntl(source, F_SETFL, 0);
-#endif
+ sock_make_blocking(source);
g_snprintf(cmd, sizeof(cmd), "CONNECT %s:%d HTTP/1.1\r\nHost: %s:%d\r\n", phb->host, phb->port,
phb->host, phb->port);
@@ -321,9 +319,7 @@ static void s4_canwrite(gpointer data, gint source, GaimInputCondition cond)
g_free(phb);
return;
}
-#ifdef F_SETFL
- fcntl(source, F_SETFL, 0);
-#endif
+ sock_make_blocking(source);
/* XXX does socks4 not support host name lookups by the proxy? */
if (!(hp = gethostbyname(phb->host))) {
@@ -508,9 +504,7 @@ static void s5_canwrite(gpointer data, gint source, GaimInputCondition cond)
g_free(phb);
return;
}
-#ifdef F_SETFL
- fcntl(source, F_SETFL, 0);
-#endif
+ sock_make_blocking(source);
i = 0;
buf[0] = 0x05; /* SOCKS version 5 */
diff --git a/protocols/ssl_bogus.c b/protocols/ssl_bogus.c
index 226997db..1ee0df4c 100644
--- a/protocols/ssl_bogus.c
+++ b/protocols/ssl_bogus.c
@@ -25,6 +25,8 @@
#include "ssl_client.h"
+int ssl_errno;
+
void *ssl_connect( char *host, int port, SslInputFunction func, gpointer data )
{
return( NULL );
diff --git a/protocols/ssl_client.h b/protocols/ssl_client.h
index a829a7b1..719cd0c4 100644
--- a/protocols/ssl_client.h
+++ b/protocols/ssl_client.h
@@ -26,6 +26,12 @@
#include <glib.h>
#include "proxy.h"
+#define SSL_OK 0
+#define SSL_NOHANDSHAKE 1
+#define SSL_AGAIN 2
+
+extern int ssl_errno;
+
typedef void (*SslInputFunction)(gpointer, void*, GaimInputCondition);
G_MODULE_EXPORT void *ssl_connect( char *host, int port, SslInputFunction func, gpointer data );
diff --git a/protocols/ssl_gnutls.c b/protocols/ssl_gnutls.c
index 535d126e..c2eb6906 100644
--- a/protocols/ssl_gnutls.c
+++ b/protocols/ssl_gnutls.c
@@ -24,11 +24,15 @@
*/
#include <gnutls/gnutls.h>
+#include <fcntl.h>
+#include <unistd.h>
#include "proxy.h"
#include "ssl_client.h"
#include "sock.h"
#include "stdlib.h"
+int ssl_errno = 0;
+
static gboolean initialized = FALSE;
struct scd
@@ -37,6 +41,7 @@ struct scd
gpointer data;
int fd;
gboolean established;
+ int inpa;
gnutls_session session;
gnutls_certificate_credentials xcred;
@@ -45,7 +50,6 @@ struct scd
static void ssl_connected( gpointer data, gint source, GaimInputCondition cond );
-
void *ssl_connect( char *host, int port, SslInputFunction func, gpointer data )
{
struct scd *conn = g_new0( struct scd, 1 );
@@ -53,6 +57,7 @@ void *ssl_connect( char *host, int port, SslInputFunction func, gpointer data )
conn->fd = proxy_connect( host, port, ssl_connected, conn );
conn->func = func;
conn->data = data;
+ conn->inpa = -1;
if( conn->fd < 0 )
{
@@ -75,43 +80,87 @@ void *ssl_connect( char *host, int port, SslInputFunction func, gpointer data )
return( conn );
}
+static void ssl_handshake( gpointer data, gint source, GaimInputCondition cond );
+
static void ssl_connected( gpointer data, gint source, GaimInputCondition cond )
{
struct scd *conn = data;
if( source == -1 )
- goto ssl_connected_failure;
+ {
+ conn->func( conn->data, NULL, cond );
+
+ gnutls_deinit( conn->session );
+ gnutls_certificate_free_credentials( conn->xcred );
+
+ g_free( conn );
+
+ return;
+ }
+ sock_make_nonblocking( conn->fd );
gnutls_transport_set_ptr( conn->session, (gnutls_transport_ptr) conn->fd );
- if( gnutls_handshake( conn->session ) < 0 )
- goto ssl_connected_failure;
-
- conn->established = TRUE;
- conn->func( conn->data, conn, cond );
- return;
+ ssl_handshake( data, source, cond );
+}
+
+static void ssl_handshake( gpointer data, gint source, GaimInputCondition cond )
+{
+ struct scd *conn = data;
+ int st;
-ssl_connected_failure:
- conn->func( conn->data, NULL, cond );
+ if( conn->inpa != -1 )
+ gaim_input_remove( conn->inpa );
- gnutls_deinit( conn->session );
- gnutls_certificate_free_credentials( conn->xcred );
- if( source >= 0 ) closesocket( source );
- g_free( conn );
+ if( ( st = gnutls_handshake( conn->session ) ) < 0 )
+ {
+ if( st == GNUTLS_E_AGAIN || st == GNUTLS_E_INTERRUPTED )
+ {
+ conn->inpa = gaim_input_add( conn->fd,
+ gnutls_record_get_direction( conn->session ) ?
+ GAIM_INPUT_WRITE : GAIM_INPUT_READ,
+ ssl_handshake, data );
+ }
+ else
+ {
+ conn->func( conn->data, NULL, cond );
+
+ gnutls_deinit( conn->session );
+ gnutls_certificate_free_credentials( conn->xcred );
+ closesocket( conn->fd );
+
+ g_free( conn );
+ }
+ }
+ else
+ {
+ /* For now we can't handle non-blocking perfectly everywhere... */
+ sock_make_blocking( conn->fd );
+
+ conn->established = TRUE;
+ conn->func( conn->data, conn, cond );
+ }
}
int ssl_read( void *conn, char *buf, int len )
{
if( !((struct scd*)conn)->established )
- return( 0 );
+ {
+ ssl_errno = SSL_NOHANDSHAKE;
+ return( -1 );
+ }
return( gnutls_record_recv( ((struct scd*)conn)->session, buf, len ) );
+
}
int ssl_write( void *conn, const char *buf, int len )
{
if( !((struct scd*)conn)->established )
- return( 0 );
+ {
+ ssl_errno = SSL_NOHANDSHAKE;
+ return( -1 );
+ }
return( gnutls_record_send( ((struct scd*)conn)->session, buf, len ) );
}
diff --git a/protocols/ssl_nss.c b/protocols/ssl_nss.c
index 7c5f5637..d28983fc 100644
--- a/protocols/ssl_nss.c
+++ b/protocols/ssl_nss.c
@@ -38,6 +38,8 @@
#include <secerr.h>
#include <sslerr.h>
+int ssl_errno = 0;
+
static gboolean initialized = FALSE;
struct scd
diff --git a/protocols/ssl_openssl.c b/protocols/ssl_openssl.c
index d2a7e1fe..bf87ab73 100644
--- a/protocols/ssl_openssl.c
+++ b/protocols/ssl_openssl.c
@@ -34,6 +34,8 @@
#include "ssl_client.h"
#include "sock.h"
+int ssl_errno = 0;
+
static gboolean initialized = FALSE;
struct scd
diff --git a/sock.h b/sock.h
index 3878cff1..29bd6f8e 100644
--- a/sock.h
+++ b/sock.h
@@ -5,6 +5,7 @@
#include <arpa/inet.h>
#include <netdb.h>
#define sock_make_nonblocking(fd) fcntl(fd, F_SETFL, O_NONBLOCK)
+#define sock_make_blocking(fd) fcntl(fd, F_SETFL, 0)
#define sockerr_again() (errno == EINPROGRESS || errno == EINTR)
#define closesocket(a) close(a)
#else
@@ -16,6 +17,7 @@
# define read(a,b,c) recv(a,b,c,0)
# define write(a,b,c) send(a,b,c,0)
# define sock_make_nonblocking(fd) { int non_block = 1; ioctlsocket(fd, FIONBIO, &non_block); }
+# define sock_make_blocking(fd) { int non_block = 0; ioctlsocket(fd, FIONBIO, &non_block); }
# define sockerr_again() (WSAGetLastError() == WSAEINTR || WSAGetLastError() == WSAEINPROGRESS || WSAGetLastError() == WSAEWOULDBLOCK)
# define ETIMEDOUT WSAETIMEDOUT
# define sleep(a) Sleep(a*1000)
diff --git a/storage_text.c b/storage_text.c
index d3823cac..54905440 100644
--- a/storage_text.c
+++ b/storage_text.c
@@ -41,7 +41,7 @@
static struct prpl *find_protocol_by_id(int id)
{
switch (id) {
- case 1: return find_protocol("oscar");
+ case 0: case 1: case 3: return find_protocol("oscar");
case 4: return find_protocol("msn");
case 2: return find_protocol("yahoo");
case 8: return find_protocol("jabber");