[svn r113] A lot of changes at gmyth_socket.c and gmyth_filetransfer. From now on, file transfer dont handle the monitor socket, and the QUERY_RECORDER messages - dont call spawn livetv, dont call get_file_position, is_recording, etc. These are gmyth_livetv responsibility. File transfer now has the _new, _open, _seek, and _close methods, just like gnomevfs does. trunk
authormelunko
Fri Nov 24 21:43:04 2006 +0000 (2006-11-24)
branchtrunk
changeset 112a99f881ed02f
parent 111 dfa72795bd32
child 113 7dcc53d63f37
[svn r113] A lot of changes at gmyth_socket.c and gmyth_filetransfer. From now on, file transfer dont handle the monitor socket, and the QUERY_RECORDER messages - dont call spawn livetv, dont call get_file_position, is_recording, etc. These are gmyth_livetv responsibility. File transfer now has the _new, _open, _seek, and _close methods, just like gnomevfs does.
gmyth/src/gmyth_file_transfer.c
gmyth/src/gmyth_file_transfer.h
gmyth/src/gmyth_socket.c
gmyth/src/gmyth_socket.h
     1.1 --- a/gmyth/src/gmyth_file_transfer.c	Fri Nov 24 21:19:49 2006 +0000
     1.2 +++ b/gmyth/src/gmyth_file_transfer.c	Fri Nov 24 21:43:04 2006 +0000
     1.3 @@ -50,8 +50,7 @@
     1.4  #include <errno.h>
     1.5  #include <stdlib.h>
     1.6  
     1.7 -#define GMYTHTV_QUERY_HEADER 			"QUERY_FILETRANSFER"
     1.8 -#define GMYTHTV_RECORDER_HEADER 	"QUERY_RECORDER"
     1.9 +#define GMYTHTV_QUERY_HEADER		"QUERY_FILETRANSFER "
    1.10  
    1.11  /* default values to the file transfer parameters */
    1.12  #define GMYTHTV_USER_READ_AHEAD			TRUE
    1.13 @@ -75,8 +74,6 @@
    1.14  #define GMYTHTV_ENABLE_DEBUG				1
    1.15  #endif
    1.16  
    1.17 -static guint wait_to_transfer = 0;
    1.18 -
    1.19  static gboolean has_io_access = TRUE;
    1.20  
    1.21  enum myth_sock_types {
    1.22 @@ -100,7 +97,7 @@
    1.23  static void gmyth_file_transfer_dispose  (GObject *object);
    1.24  static void gmyth_file_transfer_finalize (GObject *object);
    1.25  
    1.26 -static GMythSocket *gmyth_connect_to_transfer_backend( GMythFileTransfer **transfer, guint sock_type );
    1.27 +static gboolean gmyth_connect_to_backend (GMythFileTransfer *transfer);
    1.28  static gboolean myth_init_io_watchers( GMythFileTransfer *transfer );
    1.29  
    1.30  void gmyth_file_transfer_close( GMythFileTransfer *transfer );
    1.31 @@ -111,29 +108,6 @@
    1.32  
    1.33  G_DEFINE_TYPE(GMythFileTransfer, gmyth_file_transfer, G_TYPE_OBJECT)
    1.34  
    1.35 -#if 0
    1.36 -static guint64
    1.37 -mmyth_util_decode_long_long( GMythStringList *strlist, guint offset  )
    1.38 -{
    1.39 -
    1.40 -  guint64 ret_value = 0LL;
    1.41 -
    1.42 -  g_return_val_if_fail( strlist != NULL, ret_value );
    1.43 -
    1.44 -  if ( offset < gmyth_string_list_length( strlist ))
    1.45 -    g_printerr( "[%s] Offset is lower than the GMythStringList (offset = %d)!\n", __FUNCTION__, offset );
    1.46 -  g_return_val_if_fail( offset < gmyth_string_list_length( strlist ), ret_value );
    1.47 -
    1.48 -  gint l1 = gmyth_string_list_get_int( strlist, offset );
    1.49 -  gint l2 = gmyth_string_list_get_int( strlist, offset + 1 );
    1.50 -
    1.51 -  ret_value = ((guint64)(l2) & 0xffffffffLL) | ((guint64)(l1) << 32);
    1.52 -
    1.53 -  return ret_value;
    1.54 -
    1.55 -}
    1.56 -#endif
    1.57 -
    1.58  static void
    1.59  gmyth_file_transfer_class_init (GMythFileTransferClass *klass)
    1.60  {
    1.61 @@ -145,11 +119,24 @@
    1.62    gobject_class->finalize = gmyth_file_transfer_finalize;
    1.63  }
    1.64  
    1.65 -  static void
    1.66 -gmyth_file_transfer_init (GMythFileTransfer *gmyth_file_transfer)
    1.67 +static void
    1.68 +gmyth_file_transfer_init (GMythFileTransfer *transfer)
    1.69  { 
    1.70 -  g_return_if_fail( gmyth_file_transfer != NULL );
    1.71 -  gmyth_file_transfer->mythtv_version = GMYTHTV_VERSION;
    1.72 +  g_return_if_fail( transfer != NULL );
    1.73 +
    1.74 +  //transfer->card_id = num;
    1.75 +  //transfer->rec_id = -1;
    1.76 +  //transfer->recordernum = num;
    1.77 +
    1.78 +  transfer->readposition = 0;
    1.79 +  transfer->filesize = GMYTHTV_FILE_SIZE;
    1.80 +  //transfer->timeoutisfast = FALSE;
    1.81 +
    1.82 +  //transfer->userreadahead = GMYTHTV_USER_READ_AHEAD;
    1.83 +  //transfer->retries = GMYTHTV_RETRIES;  
    1.84 +
    1.85 +  transfer->control_sock = NULL;
    1.86 +  transfer->sock = NULL;
    1.87    
    1.88    /* it is used for signalizing the event socket consumer thread */
    1.89    io_watcher_cond = g_cond_new();
    1.90 @@ -163,8 +150,6 @@
    1.91  {
    1.92    GMythFileTransfer *gmyth_file_transfer = GMYTH_FILE_TRANSFER(object);
    1.93  
    1.94 -  gmyth_file_transfer_close( gmyth_file_transfer );
    1.95 -
    1.96    G_OBJECT_CLASS (gmyth_file_transfer_parent_class)->dispose (object);
    1.97  }
    1.98  
    1.99 @@ -176,80 +161,34 @@
   1.100    G_OBJECT_CLASS (gmyth_file_transfer_parent_class)->finalize (object);
   1.101  }
   1.102  
   1.103 -  GMythFileTransfer*
   1.104 -gmyth_file_transfer_new (gint num, GString *uri_str, gshort port, gint mythtv_version)
   1.105 +// fixme: do we need the card_id????
   1.106 +GMythFileTransfer*
   1.107 +gmyth_file_transfer_new ()
   1.108  {
   1.109    GMythFileTransfer *transfer = GMYTH_FILE_TRANSFER ( g_object_new (
   1.110  	GMYTH_FILE_TRANSFER_TYPE, FALSE ));
   1.111  
   1.112 -  transfer->mythtv_version = MYTHTV_CANNOT_NEGOTIATE_VERSION;
   1.113 -
   1.114 -  transfer->card_id = num;
   1.115 -
   1.116 -  transfer->rec_id = -1;
   1.117 -
   1.118 -  transfer->recordernum = num;
   1.119 -  transfer->uri = gmyth_uri_new ( uri_str->str );
   1.120 -
   1.121 -  transfer->hostname = g_string_new( gmyth_uri_gethost(transfer->uri) );
   1.122 -  g_print( "\t--> transfer->hostname = %s\n", transfer->hostname->str );
   1.123 -
   1.124 -  if ( port >= 0 )
   1.125 -    transfer->port = port;
   1.126 -  else
   1.127 -    transfer->port = gmyth_uri_getport( transfer->uri );
   1.128 -
   1.129 -  g_print( "\t--> transfer->port = %d\n", transfer->port );
   1.130 -
   1.131 -  transfer->readposition = 0;
   1.132 -  transfer->filesize = GMYTHTV_FILE_SIZE;
   1.133 -  transfer->timeoutisfast = FALSE;
   1.134 -
   1.135 -  transfer->userreadahead = GMYTHTV_USER_READ_AHEAD;
   1.136 -  transfer->retries = GMYTHTV_RETRIES;  
   1.137 -
   1.138 -  transfer->live_tv = FALSE;
   1.139 -  
   1.140 -  transfer->backend_msgs = g_hash_table_new( g_int_hash, g_int_equal );
   1.141 -
   1.142 -  transfer->query = g_string_new( GMYTHTV_QUERY_HEADER );
   1.143 -  g_string_append_printf ( transfer->query, " %d", transfer->recordernum );
   1.144 -  g_print( "\t--> transfer->query = %s\n", transfer->query->str );
   1.145 -
   1.146 -  transfer->control_sock = NULL;
   1.147 -  transfer->event_sock = NULL;
   1.148 -  transfer->sock = NULL;
   1.149 -
   1.150    return transfer;
   1.151  }
   1.152  
   1.153  gboolean
   1.154 -gmyth_file_transfer_livetv_setup( GMythFileTransfer **transfer, GMythSocket *live_socket )
   1.155 +gmyth_file_transfer_open (GMythFileTransfer *transfer, GString *uri_str)
   1.156  {
   1.157 -	(*transfer)->sock = live_socket;
   1.158 -	g_object_ref( live_socket );
   1.159 -
   1.160 -	return TRUE;
   1.161 -}
   1.162 -
   1.163 -gboolean
   1.164 -gmyth_file_transfer_playback_setup( GMythFileTransfer **transfer, gboolean live_tv )
   1.165 -{
   1.166 -
   1.167    gboolean ret = TRUE;
   1.168  
   1.169 -  (*transfer)->live_tv = live_tv;
   1.170 +  transfer->uri = gmyth_uri_new ( uri_str->str );
   1.171 +  transfer->hostname = g_string_new( gmyth_uri_gethost(transfer->uri) );
   1.172 +  transfer->port = gmyth_uri_getport( transfer->uri );
   1.173  
   1.174 -  printf("[%s] Running config to the %s...\n", __FUNCTION__, live_tv ? "LiveTV" : "FileTransfer" );
   1.175 -
   1.176 +  g_debug ("[%s] URI: %s\n", __FUNCTION__, uri_str->str);
   1.177 +  g_debug ("hostname: %s, port %d\n", transfer->hostname->str, transfer->port);
   1.178 +  
   1.179    /* configure the control socket */
   1.180 -  if ((*transfer)->control_sock == NULL) { 
   1.181 -
   1.182 -    if ( gmyth_connect_to_transfer_backend ( transfer, GMYTH_PLAYBACK_TYPE ) == NULL ) {
   1.183 +  if (transfer->control_sock == NULL) { 
   1.184 +    if ( !gmyth_connect_to_backend (transfer)) {
   1.185        g_printerr( "Connection to backend failed (Control Socket).\n" );
   1.186        ret = FALSE;
   1.187      }
   1.188 -
   1.189    } else {
   1.190      g_warning("Remote transfer control socket already created.\n");
   1.191    }
   1.192 @@ -258,38 +197,45 @@
   1.193  
   1.194  }
   1.195  
   1.196 -gboolean
   1.197 -gmyth_file_transfer_setup( GMythFileTransfer **transfer, gboolean live_tv )
   1.198 +static gboolean
   1.199 +gmyth_connect_to_backend (GMythFileTransfer *transfer)
   1.200  {
   1.201 -  GMythStringList *strlist = NULL;
   1.202 +  GString *base_str = g_string_new( "" );
   1.203 +  GString *hostname = NULL;
   1.204 +  GMythStringList *strlist;
   1.205  
   1.206 -  gboolean ret = TRUE;
   1.207 +  g_return_val_if_fail (transfer != NULL, FALSE );
   1.208 +  g_return_val_if_fail (transfer->uri != NULL, FALSE );
   1.209 +  g_return_val_if_fail (transfer->hostname != NULL, FALSE);
   1.210 +  g_return_val_if_fail (transfer->port > 0, FALSE);
   1.211  
   1.212 -  (*transfer)->live_tv = live_tv;
   1.213 +  gchar *path_dir = gmyth_uri_getpath (transfer->uri);
   1.214  
   1.215 -  printf("[%s] Running config to the %s...\n", __FUNCTION__, live_tv ? "LiveTV" : "FileTransfer" );
   1.216 +  /* Creates the control socket */
   1.217 +  transfer->control_sock = gmyth_socket_new();
   1.218  
   1.219 -  /* configure the control socket */
   1.220 -  if ((*transfer)->event_sock == NULL) { 
   1.221 +  // Connects the socket, send Mythtv ANN command and verify Mythtv protocol version 
   1.222 +  if (!gmyth_socket_connect_to_backend (transfer->control_sock,
   1.223 +          transfer->hostname->str, transfer->port, TRUE)) {
   1.224  
   1.225 -    if ( gmyth_connect_to_transfer_backend ( transfer, GMYTH_MONITOR_TYPE ) == NULL ) {
   1.226 -      g_printerr( "Connection to backend failed (Event Socket).\n" );
   1.227 -      ret = FALSE;
   1.228 -    }
   1.229 +    g_object_unref (transfer->control_sock);
   1.230 +    transfer->control_sock = NULL;
   1.231 +    return FALSE;
   1.232 +  }
   1.233 +    
   1.234 +  /* Creates the data socket */
   1.235 +  transfer->sock = gmyth_socket_new ();
   1.236 +  gmyth_socket_connect (transfer->sock, transfer->hostname->str, transfer->port);
   1.237  
   1.238 -  } else {
   1.239 -    g_warning("Remote transfer control socket already created.\n");
   1.240 -  }
   1.241 +  strlist = gmyth_string_list_new();
   1.242 +  hostname = gmyth_socket_get_local_hostname();
   1.243 +  g_string_printf( base_str, "ANN FileTransfer %s 1 -1", hostname->str);
   1.244  
   1.245 -  /* configure the socket */
   1.246 -  if ( (*transfer)->sock == NULL ) { 
   1.247 +  gmyth_string_list_append_string (strlist, base_str );
   1.248 +  gmyth_string_list_append_char_array (strlist, path_dir );
   1.249  
   1.250 -    //if ( live_tv == FALSE ) {
   1.251 -
   1.252 -    if ( gmyth_connect_to_transfer_backend ( transfer, GMYTH_FILETRANSFER_TYPE ) == NULL ) {
   1.253 -      g_printerr ("Connection to backend failed (Raw Transfer Socket).\n");
   1.254 -      ret = FALSE;
   1.255 -    }
   1.256 +  gmyth_socket_write_stringlist (transfer->sock, strlist );
   1.257 +  gmyth_socket_read_stringlist (transfer->sock, strlist );
   1.258      
   1.259      GIOChannel* io_channel = (*transfer)->sock->sd_io_ch, 
   1.260      			*io_channel_control = (*transfer)->control_sock->sd_io_ch;
   1.261 @@ -337,337 +283,108 @@
   1.262  		  }	
   1.263  	  }
   1.264  
   1.265 -    if ( /*!(*transfer)->live_tv && */ (*transfer)->control_sock != NULL ) {
   1.266 -      strlist = gmyth_string_list_new();
   1.267 -      g_string_printf ( (*transfer)->query, "%s %d", GMYTHTV_QUERY_HEADER, (*transfer)->recordernum );
   1.268 +  /* file identification used in future file transfer requests to backend */
   1.269 +  transfer->file_id = gmyth_string_list_get_int( strlist, 1 );
   1.270  
   1.271 -      gmyth_string_list_append_string( strlist, (*transfer)->query );
   1.272 -      gmyth_string_list_append_char_array( strlist, "IS_OPEN" );
   1.273 +  /* Myth URI stream file size - decoded using two 8-bytes sequences (64 bits/long long types) */
   1.274 +  transfer->filesize = gmyth_util_decode_long_long( strlist, 2 );
   1.275  
   1.276 -      gmyth_socket_write_stringlist( (*transfer)->control_sock, strlist );
   1.277 -      gmyth_socket_read_stringlist( (*transfer)->control_sock, strlist );
   1.278 +  g_debug ( "[%s] ***** Received: recordernum = %d, filesize = %" G_GUINT64_FORMAT "\n", __FUNCTION__,
   1.279 +          transfer->file_id, transfer->filesize );
   1.280  
   1.281 -      if ( strlist!=NULL && gmyth_string_list_get_int( strlist, 0 ) == 1 ) {
   1.282 -	g_print( "[%s] Remote Myth FileTransfer socket is open!\n", __FUNCTION__ );
   1.283 -      } else {
   1.284 -	g_print( "[%s] Remote Myth FileTransfer socket is CLOSED! See the MythTV Server Backend for configuration details...\n", __FUNCTION__ );
   1.285 -	ret = FALSE;
   1.286 -      }
   1.287 -    }
   1.288 -
   1.289 -  } else {
   1.290 -    g_warning("Remote transfer (raw) socket already created.\n");
   1.291 +  if (transfer->filesize < 0 ) {
   1.292 +      g_print( "[%s] Got filesize equals to %llu is lesser than 0 [invalid stream file]\n", __FUNCTION__, transfer->filesize );
   1.293 +      g_object_unref(transfer->sock);
   1.294 +      transfer->sock = NULL;
   1.295 +      return FALSE;
   1.296    }
   1.297 -
   1.298 -  return ret;
   1.299 -}
   1.300 -
   1.301 -static GMythSocket *
   1.302 -gmyth_connect_to_transfer_backend( GMythFileTransfer **transfer, guint sock_type )
   1.303 -{
   1.304 -  GMythSocket *sock = NULL;
   1.305 -
   1.306 -  g_return_val_if_fail( transfer != NULL && *transfer != NULL, NULL );
   1.307 -  g_return_val_if_fail( (*transfer)->uri != NULL, NULL );
   1.308 -
   1.309 -  //myth_control_acquire_context (TRUE);
   1.310 -
   1.311 -  gchar *path_dir = gmyth_uri_getpath( (*transfer)->uri );
   1.312 -
   1.313 -  gchar *stype = g_strdup( "" );
   1.314 -
   1.315 -  sock = gmyth_socket_new();
   1.316 -
   1.317 -  gmyth_socket_connect( &sock, (*transfer)->hostname->str, (*transfer)->port );
   1.318 -
   1.319 -#ifdef GMYTHTV_ENABLE_DEBUG
   1.320 -
   1.321 -  g_print( "[%s] --> Creating socket... (%s, %d)\n", __FUNCTION__, (*transfer)->hostname->str, (*transfer)->port );
   1.322 -#endif
   1.323 -
   1.324 -  GMythStringList *strlist = NULL;
   1.325 -
   1.326 -  GString *hostname = g_string_new( gmyth_uri_gethost( (*transfer)->uri ) );
   1.327 -  GString *base_str = g_string_new( "" );
   1.328 -
   1.329 -  if ( (*transfer)->mythtv_version != MYTHTV_CANNOT_NEGOTIATE_VERSION || 
   1.330 -  			( (*transfer)->mythtv_version = gmyth_socket_check_protocol_version_number (sock, 
   1.331 -  					MYTHTV_VERSION_DEFAULT ) ) != MYTHTV_CANNOT_NEGOTIATE_VERSION ) {
   1.332 -
   1.333 -    if (sock == NULL) {
   1.334 -      stype = (sock_type==GMYTH_PLAYBACK_TYPE) ? "control socket" : "file data socket";
   1.335 -      g_printerr( "FileTransfer, open_socket(%s): \n"
   1.336 -	  "\t\t\tCould not connect to server \"%s\" @ port %d\n", stype, 
   1.337 -	  (*transfer)->hostname->str, (*transfer)->port );
   1.338 -      g_object_unref(sock);
   1.339 -      //myth_control_release_context( );
   1.340 -      return NULL;
   1.341 -    }
   1.342 -
   1.343 -    hostname = gmyth_socket_get_local_hostname();
   1.344 -
   1.345 -    g_print( "[%s] local hostname = %s\n", __FUNCTION__, hostname->str  );
   1.346 -
   1.347 -    if ( sock_type == GMYTH_PLAYBACK_TYPE )
   1.348 -    {
   1.349 -      (*transfer)->control_sock = sock;
   1.350 -      
   1.351 -     	g_string_printf( base_str, "ANN Playback %s %d", hostname->str, FALSE );
   1.352 -
   1.353 -      gmyth_socket_send_command( (*transfer)->control_sock, base_str );
   1.354 -      GString *resp = gmyth_socket_receive_response( (*transfer)->control_sock );
   1.355 -      g_print( "[%s] Got Playback response from %s: %s\n", __FUNCTION__, base_str->str, resp->str );
   1.356 -      //myth_init_io_watchers ( (*transfer) );
   1.357 -    }
   1.358 -    else if ( sock_type == GMYTH_MONITOR_TYPE )
   1.359 -    {
   1.360 -      (*transfer)->event_sock = sock;
   1.361 -      g_string_printf( base_str, "ANN Monitor %s %d", hostname->str, TRUE );
   1.362 -
   1.363 -      gmyth_socket_send_command( (*transfer)->event_sock, base_str );
   1.364 -      GString *resp = gmyth_socket_receive_response( (*transfer)->event_sock );
   1.365 -      g_print( "[%s] Got Monitor response from %s: %s\n", __FUNCTION__, base_str->str, resp->str );
   1.366 -      //g_thread_create( myth_init_io_watchers, (void*)(*transfer), FALSE, NULL );
   1.367 -      //g_thread_create( myth_init_io_watchers, (*transfer), FALSE, NULL );
   1.368 -
   1.369 -      g_printerr( "[%s] Watch listener function to the IO control channel on thread %p.\n", 
   1.370 -      			__FUNCTION__, g_thread_self() );
   1.371 -
   1.372 -    }
   1.373 -    else if ( sock_type == GMYTH_FILETRANSFER_TYPE )
   1.374 -    {
   1.375 -      (*transfer)->sock = sock;
   1.376 -      strlist = gmyth_string_list_new();
   1.377 -      
   1.378 -      if ( (*transfer)->mythtv_version > 26 )      
   1.379 -      	g_string_printf( base_str, "ANN FileTransfer %s %d %d", hostname->str,
   1.380 -        		(*transfer)->userreadahead, (*transfer)->retries );
   1.381 -      else
   1.382 -      	g_string_printf( base_str, "ANN FileTransfer %s", hostname->str );
   1.383 -
   1.384 -      gmyth_string_list_append_string( strlist, base_str );
   1.385 -      gmyth_string_list_append_char_array( strlist, path_dir );
   1.386 -
   1.387 -      gmyth_socket_write_stringlist( (*transfer)->sock, strlist );
   1.388 -      gmyth_socket_read_stringlist( (*transfer)->sock, strlist );
   1.389 -
   1.390 -      /* socket number, where all the stream data comes from - got from the MythTV remote backend */
   1.391 -      (*transfer)->recordernum = gmyth_string_list_get_int( strlist, 1 );
   1.392 -
   1.393 -      /* Myth URI stream file size - decoded using two 8-bytes sequences (64 bits/long long types) */
   1.394 -      (*transfer)->filesize = gmyth_util_decode_long_long( strlist, 2 );
   1.395 -
   1.396 -      printf( "[%s] ***** Received: recordernum = %d, filesize = %" G_GUINT64_FORMAT "\n", __FUNCTION__,
   1.397 -	  (*transfer)->recordernum, (*transfer)->filesize );
   1.398 -
   1.399 -      if ( (*transfer)->filesize <= 0 ) {
   1.400 -	g_print( "[%s] Got filesize equals to %llu is lesser than 0 [invalid stream file]\n", __FUNCTION__, (*transfer)->filesize );
   1.401 -	g_object_unref(sock);
   1.402 -	sock = NULL; 
   1.403 -      }
   1.404 -    }
   1.405 -    else if ( sock_type == GMYTH_RINGBUFFER_TYPE )
   1.406 -    {
   1.407 -      (*transfer)->sock = sock;
   1.408 -      //gmyth_file_transfer_spawntv( (*transfer), NULL );      
   1.409 -
   1.410 -      strlist = gmyth_string_list_new();
   1.411 -      g_string_printf( base_str, "ANN RingBuffer %s %d", hostname->str, (*transfer)->card_id );
   1.412 -
   1.413 -      gmyth_socket_send_command( (*transfer)->sock, base_str );
   1.414 -      GString *resp = gmyth_socket_receive_response( (*transfer)->sock );
   1.415 -      g_print( "[%s] Got RingBuffer response from %s: %s\n", __FUNCTION__, base_str->str, resp->str );
   1.416 -
   1.417 -    }
   1.418 -
   1.419 -  }
   1.420 -
   1.421 -  printf("[%s] ANN %s sent: %s\n", (sock_type==GMYTH_PLAYBACK_TYPE) ? "Playback" : (sock_type==GMYTH_FILETRANSFER_TYPE) ? "FileTransfer" : "Monitor", __FUNCTION__, base_str->str);
   1.422 +  
   1.423  
   1.424    if ( strlist != NULL )
   1.425      g_object_unref( strlist );
   1.426  
   1.427 -  //myth_control_release_context( );
   1.428 +  g_string_free (base_str, TRUE);
   1.429 +  g_string_free (hostname, TRUE);
   1.430  
   1.431 -  return sock;
   1.432 +  return TRUE;
   1.433  }    
   1.434  
   1.435 -void
   1.436 -gmyth_file_transfer_spawntv ( GMythFileTransfer *file_transfer, 
   1.437 -    GString *tvchain_id )
   1.438 +gboolean
   1.439 +gmyth_file_transfer_is_open (GMythFileTransfer *transfer)
   1.440  {
   1.441 -  GMythStringList *str_list;
   1.442 +    GMythStringList *strlist;
   1.443 +    GString *query;
   1.444  
   1.445 -  g_debug ("gmyth_file_transfer_spawntv.\n");
   1.446 +    g_return_val_if_fail (transfer->control_sock != NULL, FALSE);
   1.447 +    g_return_val_if_fail (transfer->sock != NULL, FALSE);
   1.448  
   1.449 -  str_list = gmyth_string_list_new ();
   1.450 +    strlist = gmyth_string_list_new();
   1.451 +    query = g_string_new (GMYTHTV_QUERY_HEADER);
   1.452 +    g_string_append_printf (query, "%d", transfer->file_id );
   1.453  
   1.454 -  g_string_printf( file_transfer->query, "%s %d", GMYTHTV_RECORDER_HEADER, 
   1.455 -      file_transfer->card_id );
   1.456 -  gmyth_string_list_append_string (str_list, file_transfer->query);
   1.457 -  gmyth_string_list_append_string (str_list, g_string_new ("SPAWN_LIVETV"));
   1.458 -  if (tvchain_id!=NULL) {
   1.459 -    gmyth_string_list_append_string (str_list, tvchain_id);
   1.460 -    gmyth_string_list_append_int (str_list, FALSE); // PIP = FALSE (0)
   1.461 -  }
   1.462 +    gmyth_string_list_append_string (strlist, query );
   1.463 +    gmyth_string_list_append_char_array( strlist, "IS_OPEN" );
   1.464  
   1.465 -  gmyth_socket_sendreceive_stringlist ( file_transfer->sock, str_list );
   1.466 +    gmyth_socket_write_stringlist( transfer->control_sock, strlist );
   1.467 +    gmyth_socket_read_stringlist( transfer->control_sock, strlist );
   1.468  
   1.469 -  //GString *str = NULL;
   1.470 +    g_string_free (query, TRUE);
   1.471 +    g_object_unref (strlist);
   1.472  
   1.473 -  //if (str_list!=NULL && (str = gmyth_string_list_get_string( str_list, 0 )) != NULL && strcasecmp( str->str, "ok" ) != 0 ) {
   1.474 -  //  g_print( "[%s]\t\tSpawnLiveTV is OK!\n", __FUNCTION__ );
   1.475 -  //}
   1.476 -  if (str_list!=NULL)
   1.477 -    g_object_unref (str_list);
   1.478 -
   1.479 +    return ( strlist != NULL && gmyth_string_list_get_int( strlist, 0 ) == 1 );
   1.480  }
   1.481  
   1.482 -gint64
   1.483 -gmyth_file_transfer_get_file_position ( GMythFileTransfer *file_transfer )
   1.484 -{
   1.485 -  gint64 pos = 0;
   1.486 -
   1.487 -  GMythStringList *str_list = gmyth_string_list_new ();
   1.488 -
   1.489 -  g_debug ( "[%s]\n", __FUNCTION__ );
   1.490 -  myth_control_acquire_context (TRUE);
   1.491 -
   1.492 -  g_string_printf( file_transfer->query, "%s %d", GMYTHTV_RECORDER_HEADER, 
   1.493 -      file_transfer->rec_id >= 0 ? file_transfer->rec_id : file_transfer->card_id );
   1.494 -
   1.495 -  gmyth_string_list_append_string (str_list, file_transfer->query);
   1.496 -  gmyth_string_list_append_string (str_list, g_string_new ("GET_FILE_POSITION"));
   1.497 -
   1.498 -  gmyth_socket_sendreceive_stringlist ( file_transfer->control_sock, str_list );
   1.499 -
   1.500 -  if ( str_list != NULL && gmyth_string_list_length(str_list) > 0 ) 
   1.501 -  {
   1.502 -    GString *str = NULL;
   1.503 -    if ( ( str = gmyth_string_list_get_string( str_list, 0 ) ) != NULL && strstr ( str->str, "bad" ) == NULL )
   1.504 -      pos = gmyth_util_decode_long_long( str_list, 0 );
   1.505 -  } 
   1.506 -  myth_control_release_context( );
   1.507 -
   1.508 -#ifndef GMYTHTV_ENABLE_DEBUG
   1.509 -
   1.510 -  g_print( "[%s] Got file position = %lld\n", __FUNCTION__, pos );
   1.511 -#endif
   1.512 -  if (str_list!=NULL)
   1.513 -    g_object_unref (str_list);
   1.514 -
   1.515 -  return pos;
   1.516 -
   1.517 -}
   1.518 -
   1.519 -  glong
   1.520 -gmyth_file_transfer_get_recordernum( GMythFileTransfer *transfer )
   1.521 -{
   1.522 -  return transfer->recordernum;
   1.523 -}
   1.524 -
   1.525 -  glong
   1.526 -gmyth_file_transfer_get_filesize( GMythFileTransfer *transfer )
   1.527 -{
   1.528 -  return transfer->filesize;
   1.529 -}
   1.530 -
   1.531 -  gboolean
   1.532 -gmyth_file_transfer_isopen( GMythFileTransfer *transfer )
   1.533 -{
   1.534 -  return (transfer->sock != NULL && transfer->control_sock != NULL);
   1.535 -}
   1.536 -
   1.537 -  void
   1.538 +void
   1.539  gmyth_file_transfer_close( GMythFileTransfer *transfer )
   1.540  {
   1.541    GMythStringList *strlist;
   1.542 +  GString *query;
   1.543  
   1.544 -  if (transfer->control_sock == NULL)
   1.545 -    return;
   1.546 +  g_return_if_fail (transfer->control_sock != NULL);
   1.547  
   1.548    strlist = gmyth_string_list_new( );
   1.549 +  query = g_string_new (GMYTHTV_QUERY_HEADER);
   1.550 +  g_string_append_printf( query, "%d", transfer->file_id);
   1.551  
   1.552 -  g_string_printf( transfer->query, "%s %d", GMYTHTV_QUERY_HEADER, 
   1.553 -      transfer->recordernum );
   1.554 -  gmyth_string_list_append_string( strlist, transfer->query );
   1.555 +  gmyth_string_list_append_string( strlist, query );
   1.556    gmyth_string_list_append_char_array( strlist, "DONE" );
   1.557  
   1.558 -
   1.559 -  if ( gmyth_socket_sendreceive_stringlist(transfer->control_sock, strlist) <= 0 )
   1.560 -  {
   1.561 +  if ( gmyth_socket_sendreceive_stringlist(transfer->control_sock, strlist) <= 0 ) {
   1.562 +    // fixme: time out???
   1.563      g_printerr( "Remote file timeout.\n" );
   1.564    }
   1.565  
   1.566 -  if (transfer->sock)
   1.567 -  {
   1.568 +  g_string_free (query, TRUE);
   1.569 +  g_object_unref (strlist);
   1.570 +
   1.571 +  if (transfer->sock) {
   1.572      g_object_unref( transfer->sock );
   1.573      transfer->sock = NULL;
   1.574    }
   1.575  
   1.576 -  if (transfer->control_sock)
   1.577 -  {
   1.578 +  if (transfer->control_sock) {
   1.579      g_object_unref( transfer->control_sock );
   1.580      transfer->control_sock = NULL;
   1.581    } 
   1.582  
   1.583  }
   1.584  
   1.585 -  void
   1.586 -gmyth_file_transfer_reset_controlsock( GMythFileTransfer *transfer )
   1.587 -{
   1.588 -  if (transfer->control_sock == NULL)
   1.589 -  {
   1.590 -    g_printerr( "gmyth_file_transfer_reset_controlsock(): Called with no control socket" );
   1.591 -    return;
   1.592 -  }
   1.593 -
   1.594 -  GString *str = gmyth_socket_receive_response( transfer->control_sock );
   1.595 -
   1.596 -  g_string_free( str, TRUE );
   1.597 -}
   1.598 -
   1.599 -void
   1.600 -gmyth_file_transfer_reset_sock( GMythFileTransfer *transfer )
   1.601 -{
   1.602 -  if ( transfer->sock == NULL )
   1.603 -  {
   1.604 -    g_printerr( "gmyth_file_transfer_reset_sock(): Called with no raw socket" );
   1.605 -    return;
   1.606 -  }
   1.607 -
   1.608 -  GString *str = gmyth_socket_receive_response( transfer->sock );
   1.609 -
   1.610 -  g_string_free( str, TRUE );
   1.611 -}
   1.612 -
   1.613 -void
   1.614 -gmyth_file_transfer_reset( GMythFileTransfer *transfer )
   1.615 -{
   1.616 -  gmyth_file_transfer_reset_controlsock( transfer );
   1.617 -  gmyth_file_transfer_reset_sock( transfer );
   1.618 -}
   1.619 -
   1.620  gint64
   1.621  gmyth_file_transfer_seek(GMythFileTransfer *transfer, guint64 pos, gint whence)
   1.622  {
   1.623 -  if (transfer->sock == NULL)
   1.624 -  {
   1.625 -    g_printerr( "[%s] gmyth_file_transfer_seek(): Called with no socket", __FUNCTION__ );
   1.626 -    return 0;
   1.627 -  }
   1.628 +  GMythStringList *strlist = gmyth_string_list_new();
   1.629 +  GString *query;
   1.630  
   1.631 -  if (transfer->control_sock == NULL)
   1.632 -    return 0;
   1.633 +  g_return_val_if_fail (transfer->sock != NULL, -1);
   1.634 +  g_return_val_if_fail (transfer->control_sock != NULL, -1);
   1.635  
   1.636 -  // if (!controlSock->isOpen() || controlSock->error())
   1.637 -  //   return 0;
   1.638 +  strlist = gmyth_string_list_new();
   1.639 +  query = g_string_new (GMYTHTV_QUERY_HEADER);
   1.640 +  g_string_append_printf (query, "%d", transfer->file_id);
   1.641    
   1.642    myth_control_acquire_context( TRUE );
   1.643  
   1.644 -  GMythStringList *strlist = gmyth_string_list_new();
   1.645 -  g_string_printf (transfer->query, "%s %d", GMYTHTV_QUERY_HEADER, transfer->recordernum);
   1.646 -  gmyth_string_list_append_string( strlist, transfer->query );
   1.647 +  gmyth_string_list_append_string( strlist, query );
   1.648    gmyth_string_list_append_char_array( strlist, "SEEK" );
   1.649    gmyth_string_list_append_uint64( strlist, pos );
   1.650    
   1.651 @@ -740,122 +457,15 @@
   1.652    
   1.653  }
   1.654  
   1.655 -static gboolean
   1.656 -myth_control_sock_listener( GIOChannel *io_channel, GIOCondition condition, gpointer data )
   1.657 -{
   1.658 -
   1.659 -  GIOStatus io_status;
   1.660 -  GError *error = NULL;
   1.661 -  GIOCondition io_cond;
   1.662 -  gchar *trash = g_new0( gchar, GMYTHTV_BUFFER_SIZE*10 );
   1.663 -  guint recv = 0;
   1.664 -  
   1.665 -  myth_control_acquire_context (TRUE);
   1.666 -  
   1.667 -  gsize len = 0;
   1.668 -  if (condition & G_IO_HUP)
   1.669 -    g_print ("Read end of pipe died!\n");
   1.670 -    
   1.671 -  if ( ( condition & G_IO_IN ) != 0 ) {
   1.672 -  	io_status = g_io_channel_set_encoding( io_channel, NULL, &error );
   1.673 -    do 
   1.674 -    {
   1.675 -      //trash = g_new0( gchar, GMYTHTV_BUFFER_SIZE );
   1.676 -
   1.677 -      io_status = g_io_channel_read_chars( io_channel, trash + recv, 
   1.678 -      		GMYTHTV_BUFFER_SIZE, &len, &error);
   1.679 -
   1.680 -      g_print( "[%s] Received data buffer from IO binary channel... %d bytes gone!\n", 
   1.681 -      		__FUNCTION__, len );
   1.682 -      		
   1.683 -      recv += len;
   1.684 -      
   1.685 -      //msg = g_strconcat( msg, g_strdup(trash), NULL );
   1.686 -      
   1.687 -      //if ( trash != NULL )
   1.688 -      //	g_free( trash );
   1.689 -      	
   1.690 -      io_cond = g_io_channel_get_buffer_condition( io_channel );
   1.691 -
   1.692 -    } while ( ( io_cond & G_IO_IN ) != 0 && ( io_status != G_IO_STATUS_ERROR ) );
   1.693 -  }
   1.694 -  //ret = g_io_channel_read_chars ( source, &msg, &len, NULL, &err);
   1.695 -  if ( io_status == G_IO_STATUS_ERROR )
   1.696 -    g_print ("[%s] Error reading: %s\n", __FUNCTION__, error != NULL ? error->message : "" );
   1.697 -  g_print ("\n[%s]\tEVENT: Read %d bytes: %s\n\n", __FUNCTION__, len, trash != NULL ? trash : "[no event data]" );
   1.698 -  
   1.699 -  myth_control_release_context( );
   1.700 -  
   1.701 -  return TRUE;
   1.702 -
   1.703 -}
   1.704 -
   1.705 -static gboolean
   1.706 -myth_init_io_watchers( GMythFileTransfer *transfer )
   1.707 -{
   1.708 -  io_watcher_context = g_main_context_default();
   1.709 -  //GMainLoop *loop = g_main_loop_new( io_watcher_context, FALSE );
   1.710 -
   1.711 -  GSource *source;
   1.712 -
   1.713 -  if ( transfer->event_sock->sd_io_ch != NULL )
   1.714 -    source = g_io_create_watch( transfer->event_sock->sd_io_ch, G_IO_IN | G_IO_HUP );
   1.715 -  else
   1.716 -  	goto cleanup;
   1.717 -
   1.718 -  g_source_set_callback ( source, (GSourceFunc)myth_control_sock_listener, NULL, NULL );
   1.719 -
   1.720 -  g_source_attach( source, io_watcher_context );
   1.721 -
   1.722 -  if (source==NULL) {
   1.723 -    g_printerr( "[%s] Error adding watch listener function to the IO control channel!\n", __FUNCTION__ );
   1.724 -    goto cleanup;
   1.725 -  }
   1.726 -  
   1.727 -  g_print( "[%s]\tOK! Starting listener on the MONITOR event socket...\n", __FUNCTION__ );
   1.728 -  
   1.729 -  //g_main_loop_run( loop );
   1.730 -
   1.731 -cleanup:
   1.732 -  if ( source != NULL )
   1.733 -    g_source_unref( source );
   1.734 -
   1.735 -  return TRUE;
   1.736 -}	
   1.737 -
   1.738 -static gboolean
   1.739 -gmyth_file_transfer_is_backend_message( GMythFileTransfer *transfer, 
   1.740 -			GMythStringList* strlist )
   1.741 -{	
   1.742 -	gboolean found_backend_msg = FALSE;	
   1.743 -	GString *back_msg = NULL;
   1.744 -	
   1.745 -	back_msg = gmyth_string_list_get_string( strlist, 0 );
   1.746 -	if ( back_msg != NULL && back_msg->str != NULL && 
   1.747 -					strstr( back_msg->str, "BACKEND" ) != NULL )
   1.748 -	{
   1.749 -		found_backend_msg = TRUE;
   1.750 -		if ( transfer->backend_msgs != NULL ) {
   1.751 -			
   1.752 -			g_hash_table_insert ( transfer->backend_msgs, 
   1.753 -						&(transfer->readposition), back_msg );  
   1.754 -			
   1.755 -		}
   1.756 -	}
   1.757 -	
   1.758 -	return found_backend_msg;
   1.759 -	
   1.760 -}
   1.761 -
   1.762  gint 
   1.763  gmyth_file_transfer_read(GMythFileTransfer *transfer, GByteArray *data, gint size, gboolean read_unlimited)
   1.764  {
   1.765 -  gint recv = 0;
   1.766 +  gsize bytes_sent = 0;
   1.767    gsize bytes_read = 0;
   1.768 -  gint sent = 0;
   1.769 -  guint remaining = 0;  
   1.770 -  gboolean response = FALSE;
   1.771 -
   1.772 +  gsize total_read = 0;
   1.773 +  
   1.774 +  GError *error = NULL;
   1.775 +  
   1.776    GIOChannel *io_channel;
   1.777    GIOChannel *io_channel_control;
   1.778  
   1.779 @@ -864,20 +474,10 @@
   1.780    GIOStatus io_status = G_IO_STATUS_NORMAL, io_status_control = G_IO_STATUS_NORMAL;   
   1.781  
   1.782    GMythStringList *strlist = NULL;
   1.783 -  GError *error = NULL;
   1.784 -  
   1.785 -  gchar *data_buffer = NULL;
   1.786 -
   1.787 -  gchar *trash = g_strdup("");
   1.788 +  GString *query;
   1.789  
   1.790    g_return_val_if_fail ( data != NULL, -2 );
   1.791  
   1.792 -  myth_control_acquire_context (FALSE);
   1.793 -  
   1.794 -  /* gets the size of the entire file, if the size requested is lesser than 0 */
   1.795 -  if ( size <= 0 )
   1.796 -    size = transfer->filesize;
   1.797 -
   1.798    io_channel = transfer->sock->sd_io_ch;
   1.799    io_channel_control = transfer->control_sock->sd_io_ch;
   1.800  
   1.801 @@ -888,201 +488,91 @@
   1.802    io_cond = g_io_channel_get_buffer_condition( io_channel );  
   1.803  
   1.804    io_cond_control = g_io_channel_get_buffer_condition( io_channel );
   1.805 -
   1.806 -  if ( transfer->sock == NULL || ( io_status == G_IO_STATUS_ERROR ) )
   1.807 -  {
   1.808 +  if ( transfer->sock == NULL || ( io_status == G_IO_STATUS_ERROR ) ) {
   1.809      g_printerr( "gmyth_file_transfer_read(): Called with no raw socket.\n" );
   1.810 -    recv = -1;
   1.811 -    goto cleanup;
   1.812 +    exit(0); // fixme remove this
   1.813 +    return -1;
   1.814    }
   1.815  
   1.816 -  if ( transfer->control_sock == NULL || ( io_status_control == G_IO_STATUS_ERROR ) )
   1.817 -  {
   1.818 +  if ( transfer->control_sock == NULL || ( io_status_control == G_IO_STATUS_ERROR ) ) {
   1.819      g_printerr( "gmyth_file_transfer_read(): Called with no control socket.\n" );
   1.820 -    recv = -1;
   1.821 -    goto cleanup;
   1.822 +    exit(0); // fixme remove this
   1.823 +    return -1;
   1.824    }
   1.825  
   1.826 -  wait_to_transfer = 0;
   1.827 -
   1.828 -  g_string_printf ( transfer->query, "%s %d", GMYTHTV_QUERY_HEADER, 
   1.829 -      transfer->recordernum ); // transfer->recordernum
   1.830 -  g_print( "\t[%s] Transfer_query = %s\n", __FUNCTION__, transfer->query->str );
   1.831 +  query = g_string_new (GMYTHTV_QUERY_HEADER);
   1.832 +  g_string_append_printf ( query, "%d", transfer->file_id );
   1.833 +  g_debug ("[%s] Transfer_query = %s\n", __FUNCTION__, query->str );
   1.834    
   1.835 -  sent = size;
   1.836 -  remaining = size - recv;  
   1.837 -
   1.838 -  while ( recv < size  && !response )
   1.839 -  {
   1.840 +  while (total_read == 0) {
   1.841  
   1.842      strlist = gmyth_string_list_new();
   1.843 -    gmyth_string_list_append_char_array( strlist, transfer->query->str );
   1.844 +
   1.845 +    gmyth_string_list_append_char_array( strlist, query->str );
   1.846      gmyth_string_list_append_char_array( strlist, "REQUEST_BLOCK" );
   1.847 -    gmyth_string_list_append_int( strlist, remaining );
   1.848 -		gmyth_socket_write_stringlist( transfer->control_sock, strlist );
   1.849 -				
   1.850 -		/* see the number of bytes transferred by the MythTV backend */
   1.851 +    gmyth_string_list_append_int( strlist, size );
   1.852 +
   1.853 +    // Request the block to the backend
   1.854 +    gmyth_socket_write_stringlist( transfer->control_sock, strlist );
   1.855 +
   1.856 +    // Receives the backand answer    
   1.857      gmyth_socket_read_stringlist( transfer->control_sock, strlist );
   1.858 -    if ( strlist != NULL && gmyth_string_list_length( strlist ) > 0 ) 
   1.859 -    { 
   1.860 -    	sent = gmyth_string_list_get_int( strlist,  0 ); // -1 on backend error
   1.861 -    	g_print( "[%s] got SENT buffer message = %d\n", __FUNCTION__, sent );
   1.862 -    	if ( sent != 0 )
   1.863 -    	{
   1.864 -    		g_print( "[%s]\t received = %d bytes, backend says %d bytes sent, "\
   1.865 -    				"io_cond %s prepared for reading! (G_IO_IN) !!!\n\n", __FUNCTION__, 
   1.866 -  					recv, sent, ( ( io_cond & G_IO_IN ) != 0 ) ? "IS" : "IS NOT" );
   1.867  
   1.868 -	  		if ( sent == remaining )
   1.869 -	  		{
   1.870 -	  			g_print( "[%s]\t\tsent %d, which is equals to requested size = %d\n\n", 
   1.871 -	  						__FUNCTION__, sent, remaining );	  			
   1.872 -	  		}
   1.873 -	  		else
   1.874 -	  		{
   1.875 -	  			g_print( "[%s]\t\tsent %d, which is NOT equals to requested size = %d\n\n", 
   1.876 -	  						__FUNCTION__, sent, remaining );
   1.877 -	  			size = remaining = sent;
   1.878 -	  			if ( sent < 0 ) {
   1.879 -	  				goto cleanup;
   1.880 -	  			} 
   1.881 -	  		}
   1.882 -    	} else {
   1.883 -    			//continue;
   1.884 -  				goto cleanup;	      		
   1.885 -    	} // if
   1.886 -  	}
   1.887 +    if ( strlist != NULL && gmyth_string_list_length( strlist ) > 0 ) { 
   1.888 +	bytes_sent = gmyth_string_list_get_int( strlist,  0 ); // -1 on backend error
   1.889  
   1.890 -    guint count_bytes = 0;
   1.891 -      
   1.892 -    bytes_read = 0;
   1.893 -    
   1.894 -    data_buffer = g_new0( gchar, remaining );    
   1.895 +	g_print( "[%s] got SENT buffer message = %d\n", __FUNCTION__, bytes_sent );
   1.896 +      	if ( bytes_sent != 0 ) {
   1.897 +     	    while (total_read != bytes_sent) { 
   1.898  
   1.899 -    io_status = g_io_channel_read_chars( io_channel, data_buffer, 
   1.900 -  		remaining, &bytes_read, &error );
   1.901 +                io_status = g_io_channel_read_chars( io_channel, data + total_read, 
   1.902 +	  		(gsize) bytes_sent, // buffer_len
   1.903 +		       	&bytes_read, &error );
   1.904  
   1.905 -    if ( bytes_read > 0 )
   1.906 -    {
   1.907 -		  recv += bytes_read;
   1.908 -		  count_bytes += bytes_read;
   1.909 -		  remaining -= bytes_read;
   1.910 -		  
   1.911 -		  /* append new data to the increasing byte array */
   1.912 -		  data = g_byte_array_append ( data, g_memdup( data_buffer, bytes_read ), bytes_read );
   1.913 -		  
   1.914 -		  g_print( "[%s] Reading buffer (bytes read = %d, remaining = %d)\n", __FUNCTION__, bytes_read, remaining );
   1.915 -		  if ( remaining == 0 ) {
   1.916 -		  	response = TRUE;
   1.917 -		  	break;
   1.918 -		  }
   1.919 +	        total_read += bytes_read;
   1.920 +		printf ("Total file transfer data read: %d\n", total_read);
   1.921 +	    }
   1.922 +	}
   1.923 +    }
   1.924 +  }
   1.925  
   1.926 -    } else {
   1.927 -	    if ( io_status == G_IO_STATUS_EOF ) {
   1.928 -				g_print( "[%s] got EOS!", __FUNCTION__ );
   1.929 -	    } else if ( io_status == G_IO_STATUS_ERROR ) {
   1.930 -				g_print( "[%s] gmyth_file_transfer_read(): socket error.\n", __FUNCTION__ );
   1.931 -	    }
   1.932 -    	break;
   1.933 +    g_object_unref( strlist );
   1.934 +    g_string_free (query, TRUE);
   1.935 +
   1.936 +
   1.937 +    if ( error != NULL ) {
   1.938 +        g_printerr( "Cleaning-up ERROR: %s [msg = %s, code = %d]\n", __FUNCTION__, error->message, 
   1.939 +			error->code );
   1.940 +        g_error_free( error );
   1.941      }
   1.942 +  
   1.943 +  transfer->readposition += total_read;
   1.944  
   1.945 -    g_print( "[%s]\t io_cond %s prepared for reading! (G_IO_IN) !!!\n\n", __FUNCTION__, 
   1.946 -    		( ( io_cond & G_IO_IN ) != 0 ) ? "IS" : "IS NOT" );
   1.947 -	  
   1.948 -		if ( ( io_cond_control & G_IO_IN ) != 0 ) {
   1.949 -	  	g_print( "[%s] Finishind reading function: cleaning all data on the I/O control socket...\n", __FUNCTION__ );  
   1.950 -		  while ( gmyth_socket_read_stringlist( transfer->control_sock, strlist ) > 0 )
   1.951 -		  {
   1.952 -		    if ( strlist != NULL && gmyth_string_list_length(strlist) > 0 ) 
   1.953 -		    {
   1.954 -					gint backend_code = gmyth_string_list_get_int( strlist, 0 ); // -1 on backend error
   1.955 -					g_print( "[%s]\t backend code = %d -\t"\
   1.956 -					 		"[%s prepared for reading]! (G_IO_IN) !!!\n\n", __FUNCTION__, 
   1.957 -		    			backend_code, ( ( io_cond & G_IO_IN ) != 0 ) ? "IS" : "IS NOT" );
   1.958 -		    }
   1.959 -		  }
   1.960 -	  }
   1.961 -	  g_io_channel_flush( io_channel_control, NULL );
   1.962 -    
   1.963 -  } // while
   1.964 -
   1.965 -cleanup:
   1.966 -  myth_control_release_context (mutex);
   1.967 -  
   1.968 -	if ( data_buffer != NULL )
   1.969 -		g_free( data_buffer );
   1.970 -  
   1.971 -  if ( trash != NULL )
   1.972 -    g_free( trash );
   1.973 -
   1.974 -  if ( strlist != NULL )
   1.975 -    g_object_unref( strlist );
   1.976 -
   1.977 -  g_print( "gmyth_file_transfer_read(): reqd=%d, rcvd=%d, rept=%d, "\
   1.978 -      "(rcvd and rept MUST be the same!)\n", size, 
   1.979 -      recv, sent );
   1.980 -
   1.981 -  if ( error != NULL ) {
   1.982 -    g_printerr( "Cleaning-up ERROR: %s [msg = %s, code = %d]\n", __FUNCTION__, error->message, 
   1.983 -			error->code );
   1.984 -		g_error_free( error );
   1.985 -  }
   1.986 -  
   1.987 -  if ( !response ) {
   1.988 -  	recv = GMYTHTV_FILE_TRANSFER_READ_ERROR;
   1.989 -  } else {
   1.990 -  	transfer->readposition += recv;
   1.991 -  }  
   1.992 -
   1.993 -  return recv;
   1.994 +  return total_read;
   1.995  }
   1.996  
   1.997 -void 
   1.998 +gboolean 
   1.999  gmyth_file_transfer_settimeout( GMythFileTransfer *transfer, gboolean fast )
  1.1000  {
  1.1001  
  1.1002    GMythStringList *strlist = NULL;
  1.1003  
  1.1004 -  if ( transfer->timeoutisfast == fast )
  1.1005 -    return;
  1.1006 +  g_return_val_if_fail (transfer->sock != NULL, FALSE);
  1.1007 +  g_return_val_if_fail (transfer->control_sock != NULL, FALSE);
  1.1008  
  1.1009 -  if ( transfer->sock == NULL )
  1.1010 -  {
  1.1011 -    g_printerr( "gmyth_file_transfer_settimeout(): Called with no socket" );
  1.1012 -    return;
  1.1013 -  }
  1.1014 -
  1.1015 -  if ( transfer->control_sock == NULL )
  1.1016 -    return;
  1.1017 +//  if ( transfer->timeoutisfast == fast )
  1.1018 +//    return;
  1.1019  
  1.1020    strlist = gmyth_string_list_new(); 
  1.1021 -  gmyth_string_list_append_string( strlist, transfer->query );
  1.1022 +  gmyth_string_list_append_char_array( strlist, GMYTHTV_QUERY_HEADER );
  1.1023    gmyth_string_list_append_char_array( strlist, "SET_TIMEOUT" );
  1.1024    gmyth_string_list_append_int( strlist, fast ); 
  1.1025  
  1.1026    gmyth_socket_write_stringlist( transfer->control_sock, strlist );
  1.1027    gmyth_socket_read_stringlist( transfer->control_sock, strlist );
  1.1028  
  1.1029 -  transfer->timeoutisfast = fast;
  1.1030 +//  transfer->timeoutisfast = fast;
  1.1031  
  1.1032 +  return TRUE;
  1.1033  }
  1.1034  
  1.1035 -#ifdef DO_TESTING
  1.1036 -
  1.1037 -  int
  1.1038 -main( int argc, char *argv[] )
  1.1039 -{
  1.1040 -  g_type_init();
  1.1041 -
  1.1042 -  GMythFileTransfer *file_transfer = gmyth_file_transfer_new( 1, 
  1.1043 -      g_string_new("myth://192.168.1.109:6543/jshks.nuv"), -1, GMYTHTV_VERSION );
  1.1044 -  gmyth_file_transfer_setup( &file_transfer );
  1.1045 -  gchar *data = g_strdup("");
  1.1046 -
  1.1047 -  gint num = gmyth_file_transfer_read( file_transfer, data, -1 );
  1.1048 -
  1.1049 -  return 0;
  1.1050 -
  1.1051 -}
  1.1052 -
  1.1053 -#endif
     2.1 --- a/gmyth/src/gmyth_file_transfer.h	Fri Nov 24 21:19:49 2006 +0000
     2.2 +++ b/gmyth/src/gmyth_file_transfer.h	Fri Nov 24 21:43:04 2006 +0000
     2.3 @@ -78,47 +78,45 @@
     2.4  
     2.5  	/* socket descriptors */
     2.6  	GMythSocket *control_sock;
     2.7 -	GMythSocket *event_sock;
     2.8  	GMythSocket *sock;
     2.9  
    2.10  	gint64 readposition;
    2.11  	guint64 filesize;
    2.12 -	gboolean timeoutisfast;
    2.13 -	gboolean userreadahead;
    2.14 -	gboolean live_tv;
    2.15 -	gint retries;
    2.16 +	//gboolean timeoutisfast;
    2.17 +	//gboolean userreadahead;
    2.18 +	//gint retries;
    2.19  
    2.20 -	GString *query;
    2.21 -
    2.22 -	gint rec_id;
    2.23 -	gint recordernum;
    2.24 -	gint card_id;
    2.25 +	gint file_id;
    2.26 +	//gint rec_id;
    2.27 +	//gint recordernum;
    2.28 +	//gint card_id;
    2.29  	GString *hostname;
    2.30  	gint port;
    2.31  	
    2.32  	/* stores the messages coming from the backend */
    2.33 -	GHashTable *backend_msgs;
    2.34 +	//GHashTable *backend_msgs;
    2.35  };
    2.36  
    2.37  GType          gmyth_file_transfer_get_type        (void);
    2.38  
    2.39 -GMythFileTransfer* gmyth_file_transfer_new (gint num, GString *hostname, gshort port, gint mythtv_version );
    2.40 +//GMythFileTransfer* gmyth_file_transfer_new (gint num, GString *hostname, gshort port, gint mythtv_version );
    2.41 +GMythFileTransfer* gmyth_file_transfer_new ( );
    2.42  
    2.43 -gint gmyth_file_transfer_read(GMythFileTransfer *transfer, GByteArray *data, gint size, gboolean read_unlimited);
    2.44 +gboolean gmyth_file_transfer_open (GMythFileTransfer *transfer, GString *uri_str);
    2.45 +void gmyth_file_transfer_close (GMythFileTransfer *transfer);
    2.46  
    2.47 +gboolean gmyth_file_transfer_is_open (GMythFileTransfer *transfer);
    2.48 +gint gmyth_file_transfer_read(GMythFileTransfer *transfer, void *data, gint size, gboolean read_unlimited);
    2.49  gint64 gmyth_file_transfer_seek(GMythFileTransfer *transfer, guint64 pos, gint whence);
    2.50 +gboolean gmyth_file_transfer_settimeout( GMythFileTransfer *transfer, gboolean fast);
    2.51  
    2.52 -gboolean gmyth_file_transfer_playback_setup( GMythFileTransfer **transfer, gboolean live_tv );
    2.53  
    2.54 -gboolean gmyth_file_transfer_setup( GMythFileTransfer **transfer, gboolean live_tv );
    2.55 -
    2.56 -gboolean gmyth_file_transfer_livetv_setup( GMythFileTransfer **transfer, GMythSocket *live_sock );
    2.57 -
    2.58 -void gmyth_file_transfer_spawntv ( GMythFileTransfer *file_transfer, GString *tvchain_id );
    2.59 -
    2.60 -gboolean gmyth_file_transfer_is_recording( GMythFileTransfer *file_transfer );
    2.61 -
    2.62 -gint64  gmyth_file_transfer_get_file_position( GMythFileTransfer *file_transfer );
    2.63 +//gboolean gmyth_file_transfer_playback_setup( GMythFileTransfer **transfer, gboolean live_tv );
    2.64 +//gboolean gmyth_file_transfer_setup( GMythFileTransfer **transfer, gboolean live_tv );
    2.65 +//gboolean gmyth_file_transfer_livetv_setup( GMythFileTransfer **transfer, GMythSocket *live_sock );
    2.66 +//void gmyth_file_transfer_spawntv ( GMythFileTransfer *file_transfer, GString *tvchain_id );
    2.67 +//gboolean gmyth_file_transfer_is_recording( GMythFileTransfer *file_transfer );
    2.68 +//gint64  gmyth_file_transfer_get_file_position( GMythFileTransfer *file_transfer );
    2.69  
    2.70  #define G_END_DECLS
    2.71  
     3.1 --- a/gmyth/src/gmyth_socket.c	Fri Nov 24 21:19:49 2006 +0000
     3.2 +++ b/gmyth/src/gmyth_socket.c	Fri Nov 24 21:43:04 2006 +0000
     3.3 @@ -474,7 +474,7 @@
     3.4   * @return TRUE if success, FALSE if error.
     3.5   */
     3.6  gboolean
     3.7 -gmyth_socket_connect (GMythSocket **gmyth_socket,
     3.8 +gmyth_socket_connect (GMythSocket *gmyth_socket,
     3.9  	gchar *hostname, gint port)
    3.10  {
    3.11      struct addrinfo *addr_info_data = NULL, *addr_info0 = NULL;
    3.12 @@ -490,22 +490,22 @@
    3.13      g_return_val_if_fail( addr_info_data != NULL, FALSE );
    3.14  
    3.15      /* store hostname and port number */
    3.16 -    (*gmyth_socket)->hostname = g_strdup( hostname );
    3.17 -    (*gmyth_socket)->port = port;
    3.18 +    gmyth_socket->hostname = g_strdup( hostname );
    3.19 +    gmyth_socket->port = port;
    3.20  
    3.21      for ( addr_info0 = addr_info_data; addr_info0; addr_info0 = addr_info_data->ai_next ) {
    3.22  
    3.23  	struct sockaddr_in *sa = (struct sockaddr_in*)addr_info0->ai_addr;
    3.24  	/* init socket descriptor */
    3.25 -	(*gmyth_socket)->sd = socket( addr_info0->ai_family, addr_info0->ai_socktype,
    3.26 +	gmyth_socket->sd = socket( addr_info0->ai_family, addr_info0->ai_socktype,
    3.27  				     addr_info0->ai_protocol );
    3.28  
    3.29 -	if ( (*gmyth_socket)->sd < 0 )
    3.30 +	if ( gmyth_socket->sd < 0 )
    3.31  	    continue;
    3.32  
    3.33  	g_debug( "[%s] hostname = %s, sock_fd = %d, addr = %s, addr_len = %d, \
    3.34  		ai_family = %d, ai_protocol = %d\n",
    3.35 -		__FUNCTION__, hostname, (*gmyth_socket)->sd, inet_ntoa( sa->sin_addr ),
    3.36 +		__FUNCTION__, hostname, gmyth_socket->sd, inet_ntoa( sa->sin_addr ),
    3.37  		addr_info0->ai_addrlen, addr_info0->ai_family, addr_info0->ai_protocol );
    3.38  		
    3.39  	struct timeval *timeout = g_new0( struct timeval, 1 );
    3.40 @@ -514,7 +514,7 @@
    3.41  	timeout->tv_sec = 40;
    3.42  	timeout->tv_usec = 0;
    3.43  		
    3.44 -	if ( gmyth_socket_try_connect( (*gmyth_socket)->sd, (struct sockaddr *)addr_info0->ai_addr,
    3.45 +	if ( gmyth_socket_try_connect( gmyth_socket->sd, (struct sockaddr *)addr_info0->ai_addr,
    3.46  			addr_info0->ai_addrlen, timeout, &ret_code ) < 0 )
    3.47  	{
    3.48  	    g_printerr( "[%s] Error connecting to backend!\n", __FUNCTION__ );
    3.49 @@ -530,7 +530,7 @@
    3.50  
    3.51      }
    3.52  
    3.53 -    (*gmyth_socket)->sd_io_ch = g_io_channel_unix_new( (*gmyth_socket)->sd );
    3.54 +    gmyth_socket->sd_io_ch = g_io_channel_unix_new( gmyth_socket->sd );
    3.55  
    3.56      ret = ( ret_code == 0 ) ? TRUE : FALSE ;
    3.57  
    3.58 @@ -687,7 +687,7 @@
    3.59  gmyth_socket_connect_to_backend (GMythSocket *gmyth_socket, 
    3.60  	gchar *hostname_backend, int port, gboolean blocking_client)
    3.61  {
    3.62 -    if (!gmyth_socket_connect (&gmyth_socket, hostname_backend, port)) {
    3.63 +    if (!gmyth_socket_connect (gmyth_socket, hostname_backend, port)) {
    3.64  		g_warning ("[%s] Could not open socket to backend machine", __FUNCTION__);
    3.65  		return FALSE;
    3.66      }
    3.67 @@ -719,10 +719,9 @@
    3.68  
    3.69  	return TRUE;
    3.70      } else {
    3.71 -		g_warning ("[%s] GMythSocket could not connect to the backend", __FUNCTION__);	
    3.72 -		return FALSE;
    3.73 -	}
    3.74 -
    3.75 +	g_warning ("[%s] GMythSocket could not connect to the backend", __FUNCTION__);	
    3.76 +	return FALSE;
    3.77 +    }
    3.78  }
    3.79  
    3.80  /** Closes the socket connection to the backend.
    3.81 @@ -780,7 +779,7 @@
    3.82  		    g_print( "[%s] got MythTV version = %s.\n", __FUNCTION__, new_version );
    3.83  		    mythtv_version = (gint)g_ascii_strtoull( g_strdup( new_version ), NULL, 10 );
    3.84  		    /* do reconnection to the socket (socket is closed if the MythTV version was wrong) */
    3.85 -		    gmyth_socket_connect( &gmyth_socket, gmyth_socket->hostname, gmyth_socket->port );
    3.86 +		    gmyth_socket_connect( gmyth_socket, gmyth_socket->hostname, gmyth_socket->port );
    3.87  		    /* g_free( new_version ); */
    3.88  		    if ( --max_iterations > 0 ) 
    3.89  		    	goto try_new_version;
     4.1 --- a/gmyth/src/gmyth_socket.h	Fri Nov 24 21:19:49 2006 +0000
     4.2 +++ b/gmyth/src/gmyth_socket.h	Fri Nov 24 21:43:04 2006 +0000
     4.3 @@ -92,10 +92,10 @@
     4.4  gboolean        gmyth_socket_send_command (GMythSocket *gmyth_socket, 
     4.5                                             GString *command);
     4.6  GString *       gmyth_socket_receive_response (GMythSocket *gmyth_socket);
     4.7 -int             gmyth_socket_sendreceive_stringlist (GMythSocket * gmyth_socket, 
     4.8 +int             gmyth_socket_sendreceive_stringlist (GMythSocket *gmyth_socket, 
     4.9                                                       GMythStringList *str_list);
    4.10  
    4.11 -gboolean        gmyth_socket_connect (GMythSocket **gmyth_socket,
    4.12 +gboolean        gmyth_socket_connect (GMythSocket *gmyth_socket,
    4.13                                        gchar *hostname, gint port);
    4.14  gboolean        gmyth_socket_connect_to_backend (GMythSocket *gmyth_socket, 
    4.15                                                   gchar *hostname_backend, int port,