Add torrent hash to model.

Implement lookup, remove, start, and stop messages.
This commit is contained in:
Josh Elsasser 2007-05-24 09:18:03 +00:00
parent 80c7f8c922
commit 4657345141
6 changed files with 216 additions and 48 deletions

198
gtk/ipc.c
View File

@ -46,6 +46,8 @@
#include "tr_torrent.h"
#include "util.h"
/* XXX error handling throught this file is pretty bogus */
enum contype { CON_SERV, CON_CLIENT };
struct constate_serv
@ -110,11 +112,17 @@ static int
addinfo( TrTorrent * tor, enum ipc_msg msgid, int torid, int types,
benc_val_t * val );
static void
smsg_look( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg );
static void
smsg_tor( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg );
static void
all_default( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg );
static gboolean
simpleresp( struct constate * con, enum ipc_msg id, int64_t tag );
simpleresp( struct constate * con, int64_t tag, enum ipc_msg id );
static TrTorrent *
findtor( TrCore * core, int id );
findtorid( TrCore * core, int id, GtkTreeIter * iter );
static TrTorrent *
findtorhash( TrCore * core, const char * hash, int * id );
/* this is only used on the server */
static char *gl_sockpath = NULL;
@ -136,6 +144,10 @@ ipc_socket_setup( GtkWindow * parent, TrCore * core )
0 > ipc_addmsg( con->msgs, IPC_MSG_GETINFOALL, smsg_infoall ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_GETSTAT, smsg_info ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_GETSTATALL, smsg_infoall ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_LOOKUP, smsg_look ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_REMOVE, smsg_tor ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_START, smsg_tor ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_STOP, smsg_tor ) ||
0 > ipc_addmsg( con->msgs, IPC_MSG_QUIT, smsg_quit ) )
{
errmsg( con->u.serv.wind, _("Failed to set up IPC:\n%s"),
@ -335,14 +347,20 @@ static unsigned int
srv_io_received( GSource * source SHUTUP, char * data, unsigned int len,
void * vdata)
{
struct constate * con = vdata;
ssize_t res;
struct constate * con = vdata;
struct constate_serv * srv = &con->u.serv;
ssize_t res;
if( IPC_MIN_MSG_LEN > len )
{
return 0;
}
if( NULL == srv->core )
{
destroycon( con );
}
res = ipc_parse( &con->ipc, data, len, con );
if( 0 > res )
@ -504,11 +522,6 @@ smsg_add( enum ipc_msg id SHUTUP, benc_val_t * val, int64_t tag, void * arg )
benc_val_t * path;
int ii;
if( NULL == srv->core )
{
return;
}
if( NULL == val || TYPE_LIST != val->type )
{
simpleresp( con, tag, IPC_MSG_NOTSUP );
@ -529,7 +542,7 @@ smsg_add( enum ipc_msg id SHUTUP, benc_val_t * val, int64_t tag, void * arg )
tr_core_torrents_added( TR_CORE( srv->core ) );
/* XXX should send info response back with torrent ids */
simpleresp( con, IPC_MSG_OK, tag );
simpleresp( con, tag, IPC_MSG_OK );
}
static void
@ -554,11 +567,6 @@ smsg_info( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg )
uint8_t * buf;
size_t size;
if( NULL == srv->core )
{
return;
}
if( NULL == val || TYPE_DICT != val->type )
{
simpleresp( con, tag, IPC_MSG_NOTSUP );
@ -586,7 +594,7 @@ smsg_info( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg )
{
idval = &ids->val.l.vals[ii];
if( TYPE_INT != idval->type || !TORRENT_ID_VALID( idval->val.i ) ||
NULL == ( tor = findtor( srv->core, idval->val.i ) ) )
NULL == ( tor = findtorid( srv->core, idval->val.i, NULL ) ) )
{
continue;
}
@ -625,11 +633,6 @@ smsg_infoall( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg )
uint8_t * buf;
size_t size;
if( NULL == srv->core )
{
return;
}
if( NULL == val || TYPE_LIST != val->type )
{
simpleresp( con, tag, IPC_MSG_NOTSUP );
@ -695,6 +698,110 @@ addinfo( TrTorrent * tor, enum ipc_msg msgid, int torid, int types,
}
}
static void
smsg_look( enum ipc_msg id SHUTUP, benc_val_t * val, int64_t tag,
void * arg )
{
struct constate * con = arg;
struct constate_serv * srv = &con->u.serv;
benc_val_t packet, * pkval, * hash;
int ii, torid;
TrTorrent * tor;
tr_info_t * inf;
uint8_t * buf;
size_t size;
if( NULL == val || TYPE_LIST != val->type )
{
simpleresp( con, tag, IPC_MSG_NOTSUP );
return;
}
pkval = ipc_initval( &con->ipc, IPC_MSG_INFO, tag, &packet, TYPE_LIST );
if( NULL == pkval )
{
simpleresp( con, tag, IPC_MSG_FAIL );
return;
}
for( ii = 0; val->val.l.count > ii; ii++ )
{
hash = &val->val.l.vals[ii];
if( NULL == hash || TYPE_STR != hash->type ||
SHA_DIGEST_LENGTH * 2 != hash->val.s.i ||
NULL == ( tor = findtorhash( srv->core, hash->val.s.s, &torid ) ) )
{
continue;
}
inf = tr_torrent_info( tor );
if( 0 > ipc_addinfo( pkval, torid, inf, IPC_INF_HASH ) )
{
tr_bencFree( &packet );
simpleresp( con, tag, IPC_MSG_FAIL );
return;
}
}
buf = ipc_mkval( &packet, &size );
tr_bencFree( &packet );
if( NULL == buf )
{
simpleresp( con, tag, IPC_MSG_FAIL );
}
else
{
io_send_keepdata( con->source, buf, size );
}
}
static void
smsg_tor( enum ipc_msg id, benc_val_t * val, int64_t tag, void * arg )
{
struct constate * con = arg;
struct constate_serv * srv = &con->u.serv;
benc_val_t * idval;
TrTorrent * tor;
GtkTreeIter iter;
int ii;
if( NULL == val || TYPE_LIST != val->type )
{
simpleresp( con, tag, IPC_MSG_NOTSUP );
return;
}
for( ii = 0; val->val.l.count > ii; ii++ )
{
idval = &val->val.l.vals[ii];
if( TYPE_INT != idval->type || !TORRENT_ID_VALID( idval->val.i ) ||
NULL == ( tor = findtorid( srv->core, idval->val.i, &iter ) ) )
{
continue;
}
switch( id )
{
case IPC_MSG_REMOVE:
tr_core_delete_torrent( srv->core, &iter );
break;
case IPC_MSG_START:
tr_torrent_start( tor );
break;
case IPC_MSG_STOP:
tr_torrent_stop( tor );
break;
default:
g_assert_not_reached();
break;
}
}
tr_core_update( srv->core );
tr_core_save( srv->core );
/* XXX this is a lie */
simpleresp( con, tag, IPC_MSG_OK );
}
static void
all_default( enum ipc_msg id, benc_val_t * val SHUTUP, int64_t tag, void * arg )
{
@ -705,16 +812,16 @@ all_default( enum ipc_msg id, benc_val_t * val SHUTUP, int64_t tag, void * arg )
case IPC_MSG_OK:
break;
case IPC_MSG_NOOP:
simpleresp( arg, IPC_MSG_OK, tag );
simpleresp( arg, tag, IPC_MSG_OK );
break;
default:
simpleresp( arg, IPC_MSG_NOTSUP, tag );
simpleresp( arg, tag, IPC_MSG_NOTSUP );
break;
}
}
static gboolean
simpleresp( struct constate * con, enum ipc_msg id, int64_t tag )
simpleresp( struct constate * con, int64_t tag, enum ipc_msg id )
{
uint8_t * buf;
size_t size;
@ -731,11 +838,43 @@ simpleresp( struct constate * con, enum ipc_msg id, int64_t tag )
}
static TrTorrent *
findtor( TrCore * core, int id )
findtorid( TrCore * core, int id, GtkTreeIter * iter )
{
GtkTreeModel * model;
GtkTreeIter myiter;
int rowid;
TrTorrent * tor;
if( NULL == iter )
{
iter = &myiter;
}
model = tr_core_model( core );
if( gtk_tree_model_get_iter_first( model, iter ) )
{
do
{
gtk_tree_model_get( model, iter, MC_ID, &rowid, -1 );
if( rowid == id )
{
gtk_tree_model_get( model, iter, MC_TORRENT, &tor, -1 );
g_object_unref( tor );
return tor;
}
}
while( gtk_tree_model_iter_next( model, iter ) );
}
return NULL;
}
static TrTorrent *
findtorhash( TrCore * core, const char * hash, int * torid )
{
GtkTreeModel * model;
GtkTreeIter iter;
int rowid;
char * rowhash;
TrTorrent * tor;
model = tr_core_model( core );
@ -743,10 +882,11 @@ findtor( TrCore * core, int id )
{
do
{
gtk_tree_model_get( model, &iter, MC_ID, &rowid, -1 );
if( rowid == id )
gtk_tree_model_get( model, &iter, MC_HASH, &rowhash, -1 );
if( 0 == strcmp( hash, rowhash ) )
{
gtk_tree_model_get( model, &iter, MC_TORRENT, &tor, -1 );
gtk_tree_model_get( model, &iter, MC_ID, torid,
MC_TORRENT, &tor, -1 );
g_object_unref( tor );
return tor;
}

View File

@ -986,11 +986,11 @@ handleaction( struct cbdata * data, int act )
switch( act )
{
case ACT_START:
tr_torrentStart( tr_torrent_handle( tor ) );
tr_torrent_start( tor );
changed = TRUE;
break;
case ACT_STOP:
tr_torrentStop( tr_torrent_handle( tor ) );
tr_torrent_stop( tor );
changed = TRUE;
break;
case ACT_DELETE:

View File

@ -178,16 +178,16 @@ tr_core_init( GTypeInstance * instance, gpointer g_class SHUTUP )
/* keep this in sync with the enum near the bottom of tr_core.h */
GType types[] =
{
/* info->name, info->totalSize, status, error, errorString, */
G_TYPE_STRING, G_TYPE_UINT64, G_TYPE_INT, G_TYPE_INT, G_TYPE_STRING,
/* progress, rateDownload, rateUpload, eta, peersTotal, */
G_TYPE_FLOAT, G_TYPE_FLOAT, G_TYPE_FLOAT, G_TYPE_INT, G_TYPE_INT,
/* peersUploading, peersDownloading, seeders, leechers */
G_TYPE_INT, G_TYPE_INT, G_TYPE_INT, G_TYPE_INT,
/* completedFromTracker, downloaded, uploaded left */
G_TYPE_INT, G_TYPE_UINT64, G_TYPE_UINT64, G_TYPE_UINT64,
/* tracker, the TrTorrent object, the ID for IPC */
TR_TRACKER_BOXED_TYPE, TR_TORRENT_TYPE, G_TYPE_INT,
/* info->name, info->totalSize, info->hashString, status, */
G_TYPE_STRING, G_TYPE_UINT64, G_TYPE_STRING, G_TYPE_INT,
/* error, errorString, progress, rateDownload, rateUpload, */
G_TYPE_INT, G_TYPE_STRING, G_TYPE_FLOAT, G_TYPE_FLOAT, G_TYPE_FLOAT,
/* eta, peersTotal, peersUploading, peersDownloading, seeders, */
G_TYPE_INT, G_TYPE_INT, G_TYPE_INT, G_TYPE_INT, G_TYPE_INT,
/* leechers, completedFromTracker, downloaded, uploaded */
G_TYPE_INT, G_TYPE_INT, G_TYPE_UINT64, G_TYPE_UINT64,
/* left, tracker, TrTorrent object, ID for IPC */
G_TYPE_UINT64, TR_TRACKER_BOXED_TYPE, TR_TORRENT_TYPE, G_TYPE_INT,
};
#ifdef REFDBG
@ -298,7 +298,6 @@ tr_core_shutdown( TrCore * self )
{
GtkTreeIter iter;
TrTorrent * tor;
tr_stat_t * st;
TR_IS_CORE( self );
@ -316,11 +315,7 @@ tr_core_shutdown( TrCore * self )
do
{
gtk_tree_model_get( self->model, &iter, MC_TORRENT, &tor, -1 );
st = tr_torrent_stat( tor );
if( TR_STATUS_ACTIVE & st->status )
{
tr_torrentStop( tr_torrent_handle( tor ) );
}
tr_torrent_stop( tor );
g_object_unref( tor );
}
while( gtk_tree_model_iter_next( self->model, &iter ) );
@ -638,6 +633,7 @@ tr_core_insert( TrCore * self, TrTorrent * tor )
gtk_list_store_set( GTK_LIST_STORE( self->model ), &iter,
MC_NAME, inf->name,
MC_SIZE, inf->totalSize,
MC_HASH, inf->hashString,
MC_TORRENT, tor,
MC_ID, self->nextid,
-1);

View File

@ -157,7 +157,7 @@ tr_core_quit( TrCore * self );
/* column names for the model used to store torrent information */
/* keep this in sync with the type array in tr_core_init() in tr_core.c */
enum {
MC_NAME, MC_SIZE, MC_STAT, MC_ERR, MC_TERR,
MC_NAME, MC_SIZE, MC_HASH, MC_STAT, MC_ERR, MC_TERR,
MC_PROG, MC_DRATE, MC_URATE, MC_ETA, MC_PEERS,
MC_UPEERS, MC_DPEERS, MC_SEED, MC_LEECH, MC_DONE,
MC_DOWN, MC_UP, MC_LEFT, MC_TRACKER, MC_TORRENT, MC_ID,

View File

@ -290,6 +290,32 @@ tr_torrent_info(TrTorrent *tor) {
return tr_torrentInfo(tor->handle);
}
void
tr_torrent_start( TrTorrent * self )
{
TR_IS_TORRENT( self );
if( self->severed || !tr_torrent_paused( self ) )
{
return;
}
tr_torrentStart( self->handle );
}
void
tr_torrent_stop( TrTorrent * self )
{
TR_IS_TORRENT( self );
if( self->severed || tr_torrent_paused( self ) )
{
return;
}
tr_torrentStop( self->handle );
}
static TrTorrent *
maketorrent( tr_torrent_t * handle, const char * dir, gboolean paused )
{

View File

@ -78,6 +78,12 @@ tr_torrent_stat(TrTorrent *tor);
tr_info_t *
tr_torrent_info(TrTorrent *tor);
void
tr_torrent_start( TrTorrent * tor );
void
tr_torrent_stop( TrTorrent * tor );
#ifdef TR_WANT_TORRENT_PRIVATE
TrTorrent *