libgnomevfs2-mythtv/modules/mythtv-method.c
author rosfran
Tue Feb 13 23:15:54 2007 +0000 (2007-02-13)
branchtrunk
changeset 357 194c44ef8da4
parent 355 f7b40eb795c2
child 361 7140b2c2e63c
permissions -rwxr-xr-x
[svn r359] Now it is running; removed some GStaticMutex race conditions.
melunko@38
     1
/*
melunko@38
     2
 * @author Hallyson Melo <hallyson.melo@indt.org.br>
melunko@38
     3
 *
melunko@38
     4
 * This program is free software; you can redistribute it and/or modify
melunko@38
     5
 * it under the terms of the GNU Lesser General Public License as published by
melunko@38
     6
 * the Free Software Foundation; either version 2 of the License, or
melunko@38
     7
 * (at your option) any later version.
melunko@38
     8
 *
melunko@38
     9
 * This program is distributed in the hope that it will be useful,
melunko@38
    10
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
melunko@38
    11
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
melunko@38
    12
 * GNU General Public License for more details.
melunko@38
    13
 *
melunko@38
    14
 * You should have received a copy of the GNU Lesser General Public License
melunko@38
    15
 * along with this program; if not, write to the Free Software
melunko@38
    16
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
melunko@38
    17
 */
melunko@38
    18
melunko@38
    19
#ifdef HAVE_CONFIG_H
melunko@38
    20
#include <config.h>
melunko@38
    21
#endif
melunko@38
    22
melunko@38
    23
#include <string.h>
melunko@38
    24
#include <glib.h>
melunko@38
    25
#include <math.h>
melunko@38
    26
melunko@38
    27
#include <libgnomevfs/gnome-vfs-module.h>
melunko@38
    28
#include <libgnomevfs/gnome-vfs-utils.h>
melunko@38
    29
rosfran@277
    30
#include <gmyth/gmyth_file_transfer.h>
rosfran@277
    31
#include <gmyth/gmyth_livetv.h>
rosfran@277
    32
#include <gmyth/gmyth_uri.h>
rosfran@277
    33
#include <gmyth/gmyth_recorder.h>
rosfran@277
    34
#include <gmyth/gmyth_backendinfo.h>
rosfran@277
    35
#include <gmyth/gmyth_util.h>
rosfran@332
    36
#include <gmyth/gmyth_remote_util.h>
rosfran@332
    37
#include <gmyth/gmyth_tvchain.h>
rosfran@357
    38
#include <gmyth/gmyth_programinfo.h>
melunko@38
    39
melunko@38
    40
#define GST_MYTHTV_ID_NUM               1
melunko@38
    41
#define MYTHTV_VERSION_DEFAULT          30
rosfran@277
    42
#define MYTHTV_TRANSFER_MAX_WAITS       100
melunko@38
    43
rosfran@357
    44
#define MYTHTV_BUFFER_SIZE							1024*140
rosfran@354
    45
#define MYTHTV_MAX_VFS_BUFFER_SIZE			4096
rosfran@354
    46
#define MYTHTV_MAX_REQUEST_SIZE					1024*64
melunko@111
    47
melunko@38
    48
static GnomeVFSResult do_read (GnomeVFSMethod *method,
melunko@38
    49
                               GnomeVFSMethodHandle *method_handle,
melunko@38
    50
                               gpointer buffer,
melunko@38
    51
                               GnomeVFSFileSize num_bytes,
melunko@38
    52
                               GnomeVFSFileSize *bytes_read,
melunko@38
    53
                               GnomeVFSContext *context);
melunko@38
    54
melunko@38
    55
typedef struct {
melunko@48
    56
    GMythFileTransfer *file_transfer;
rosfran@277
    57
    GMythLiveTV 			*livetv;
rosfran@327
    58
    gchar 						*channel_name;
melunko@38
    59
    
melunko@38
    60
    gint mythtv_version;
rosfran@297
    61
    gint64 content_size;
melunko@38
    62
    guint64 bytes_read;
melunko@111
    63
rosfran@116
    64
    GByteArray *buffer;
melunko@111
    65
    gsize buffer_remain;
rosfran@338
    66
    gboolean	is_livetv;
rosfran@338
    67
    
rosfran@357
    68
    gboolean configured;
rosfran@357
    69
    
melunko@38
    70
} MythtvHandle;
melunko@38
    71
rosfran@357
    72
//static MythtvHandle *myth_handle = NULL;
rosfran@357
    73
melunko@38
    74
static GnomeVFSResult
melunko@38
    75
do_open (GnomeVFSMethod *method,
melunko@38
    76
         GnomeVFSMethodHandle **method_handle,
melunko@38
    77
         GnomeVFSURI *uri,
melunko@38
    78
         GnomeVFSOpenMode mode,
melunko@38
    79
         GnomeVFSContext *context)
rosfran@357
    80
{ 
rosfran@357
    81
		MythtvHandle *myth_handle = NULL;   
rosfran@357
    82
    GMythBackendInfo *backend_info = NULL;
rosfran@277
    83
    GMythURI *gmyth_uri = NULL;
rosfran@277
    84
    gboolean ret = TRUE;
melunko@38
    85
melunko@38
    86
    _GNOME_VFS_METHOD_PARAM_CHECK (method_handle != NULL);
melunko@38
    87
    _GNOME_VFS_METHOD_PARAM_CHECK (uri != NULL);
melunko@38
    88
melunko@38
    89
    if (mode & GNOME_VFS_OPEN_WRITE) {
melunko@38
    90
        return GNOME_VFS_ERROR_NOT_PERMITTED;
melunko@38
    91
    }
melunko@38
    92
renatofilho@149
    93
    if (gnome_vfs_uri_get_host_name (uri) == NULL) {
renatofilho@149
    94
    	return GNOME_VFS_ERROR_INVALID_HOST_NAME;
melunko@38
    95
    }
rosfran@357
    96
    
rosfran@357
    97
    /*
rosfran@357
    98
    if ( method_handle != NULL && *method_handle != NULL )
rosfran@357
    99
    {
rosfran@357
   100
    	myth_handle = (MythtvHandle*)*method_handle;
rosfran@357
   101
    	//if ( !myth_handle->configured )    	
rosfran@357
   102
    }
rosfran@357
   103
    */
rosfran@357
   104
    
rosfran@357
   105
    if ( ( NULL == myth_handle ) || !myth_handle->configured ) {
rosfran@357
   106
    	myth_handle = g_new0 (MythtvHandle, 1);
rosfran@357
   107
    	
rosfran@357
   108
    	myth_handle->configured = FALSE;
rosfran@357
   109
	    
rosfran@357
   110
	    myth_handle->is_livetv = FALSE;
rosfran@357
   111
	    
rosfran@357
   112
	    /* Initialize mythtv handler*/
rosfran@357
   113
	    myth_handle->file_transfer = NULL;
rosfran@357
   114
	    myth_handle->livetv = NULL;
rosfran@357
   115
	    myth_handle->mythtv_version = MYTHTV_VERSION_DEFAULT;
rosfran@357
   116
	    myth_handle->bytes_read = 0;
rosfran@357
   117
	    myth_handle->content_size = (GnomeVFSFileSize) - 1;
rosfran@357
   118
	
rosfran@357
   119
	    /* Creates and fills out the backend info structure */    
rosfran@357
   120
		  backend_info = gmyth_backend_info_new_with_uri ( 
rosfran@357
   121
		  			gnome_vfs_unescape_string( gnome_vfs_uri_to_string( uri, GNOME_VFS_URI_HIDE_NONE ), "" ) );
rosfran@357
   122
		  
rosfran@357
   123
		  /* creates an instance of  */  
rosfran@357
   124
		  gmyth_uri = gmyth_uri_new_with_value( 
rosfran@357
   125
		  		gnome_vfs_unescape_string( gnome_vfs_uri_to_string( uri, GNOME_VFS_URI_HIDE_NONE ), "" ) );
rosfran@357
   126
	
rosfran@357
   127
		  myth_handle->is_livetv = gmyth_uri_is_livetv( gmyth_uri );
rosfran@357
   128
	
rosfran@357
   129
		  /* Connect to the backend */	  
rosfran@357
   130
		  if ( gmyth_uri != NULL && myth_handle->is_livetv == TRUE ) {
rosfran@357
   131
		  	
rosfran@357
   132
		  	if ( NULL == myth_handle->livetv )
rosfran@357
   133
		  	{
rosfran@357
   134
		    	myth_handle->livetv = gmyth_livetv_new ();
rosfran@357
   135
		    
rosfran@357
   136
			    myth_handle->channel_name = gmyth_uri_get_channel_name( gmyth_uri );
rosfran@357
   137
			    
rosfran@357
   138
			    g_debug( "[%s] Channel name = %s\n", __FUNCTION__, myth_handle->channel_name );
rosfran@357
   139
			
rosfran@357
   140
			    if ( myth_handle->channel_name != NULL ) {
rosfran@357
   141
			      if (gmyth_livetv_channel_name_setup (myth_handle->livetv, myth_handle->channel_name,
rosfran@357
   142
			              backend_info) == FALSE) {
rosfran@357
   143
			        g_object_unref( gmyth_uri );
rosfran@357
   144
			        ret = FALSE;
rosfran@357
   145
			      }
rosfran@357
   146
			    } else {
rosfran@357
   147
			      if ( gmyth_livetv_setup (myth_handle->livetv, backend_info) == FALSE ) {
rosfran@357
   148
			      	g_object_unref( gmyth_uri );
rosfran@357
   149
			        ret = FALSE;
rosfran@357
   150
			      }
rosfran@357
   151
			    }
rosfran@357
   152
		  	}
rosfran@357
   153
		  	
rosfran@357
   154
		  	if ( NULL == myth_handle->file_transfer )	{
rosfran@357
   155
		    	myth_handle->file_transfer = gmyth_livetv_create_file_transfer (myth_handle->livetv);
rosfran@357
   156
		
rosfran@357
   157
			    if (NULL == myth_handle->file_transfer) {
rosfran@357
   158
			      ret = FALSE;
rosfran@357
   159
				    g_debug ("MythTV FileTransfer is NULL!\n");
rosfran@357
   160
				    return GNOME_VFS_ERROR_NOT_OPEN;
rosfran@357
   161
			    }
rosfran@357
   162
			    
rosfran@357
   163
		  		if ( !gmyth_file_transfer_open( myth_handle->file_transfer, myth_handle->livetv->uri != NULL ? 
rosfran@357
   164
										gmyth_uri_get_path(myth_handle->livetv->uri) : 
rosfran@357
   165
										myth_handle->livetv->proginfo->pathname->str ) )
rosfran@357
   166
					{
rosfran@357
   167
						g_debug ("Couldn't open MythTV FileTransfer is NULL!\n");
rosfran@357
   168
						g_object_unref( myth_handle->file_transfer );
rosfran@357
   169
						myth_handle->file_transfer = NULL;
rosfran@357
   170
						ret = FALSE;
rosfran@357
   171
					}
rosfran@357
   172
		  	} /* if - FileTransfer is NULL, or not */
rosfran@357
   173
		    
rosfran@357
   174
		  } else {
rosfran@357
   175
		  	
rosfran@357
   176
		  	if (NULL == myth_handle->file_transfer ) {
rosfran@357
   177
		
rosfran@357
   178
			    myth_handle->file_transfer = gmyth_file_transfer_new (backend_info);
rosfran@357
   179
			    
rosfran@357
   180
			    /* Verifies if the file exists */
rosfran@357
   181
			    if (!gmyth_util_file_exists (backend_info, gmyth_uri_get_path (gmyth_uri))) {
rosfran@357
   182
			        g_object_unref (backend_info);
rosfran@357
   183
							ret = FALSE;
rosfran@357
   184
			    }
rosfran@357
   185
			    
rosfran@357
   186
			    /* sets the Playback monitor connection */
rosfran@357
   187
			    ret = gmyth_file_transfer_open ( myth_handle->file_transfer, 
rosfran@357
   188
			    		gmyth_uri_get_path (gmyth_uri) );
rosfran@357
   189
			    		
rosfran@357
   190
		  	}
rosfran@357
   191
			
rosfran@357
   192
		  } /* if - LiveTV or not? */
rosfran@357
   193
		  
rosfran@357
   194
	    if (ret == FALSE) {
rosfran@357
   195
		    g_debug ("MythTV FileTransfer open error.\n");
rosfran@357
   196
		    return GNOME_VFS_ERROR_NOT_OPEN;
rosfran@357
   197
		  }
rosfran@357
   198
		  
rosfran@357
   199
		  myth_handle->configured = TRUE;
rosfran@357
   200
	
rosfran@357
   201
	    g_object_unref (backend_info);
rosfran@357
   202
	    
rosfran@357
   203
		  if ( gmyth_uri != NULL )
rosfran@357
   204
		  	g_object_unref( gmyth_uri );
rosfran@357
   205
		  
rosfran@357
   206
	    myth_handle->buffer = g_byte_array_sized_new (MYTHTV_BUFFER_SIZE);
rosfran@357
   207
	    myth_handle->buffer_remain = 0;
rosfran@357
   208
	    
rosfran@357
   209
		  g_return_val_if_fail (myth_handle->file_transfer != NULL, GNOME_VFS_ERROR_NOT_OPEN);
rosfran@357
   210
		  
rosfran@357
   211
		  if ( /*myth_handle->file_transfer->filesize <= 0 && */myth_handle->is_livetv ) {
rosfran@357
   212
		  	myth_handle->content_size = gmyth_recorder_get_file_position(myth_handle->livetv->recorder);
rosfran@357
   213
		  } else {
rosfran@357
   214
	    	myth_handle->content_size = myth_handle->file_transfer->filesize;
rosfran@357
   215
		  }
rosfran@357
   216
		  
rosfran@357
   217
    } /* if - configured or not? */
rosfran@277
   218
	  
melunko@38
   219
    *method_handle = (GnomeVFSMethodHandle *) myth_handle;
melunko@38
   220
melunko@38
   221
    return GNOME_VFS_OK;
melunko@38
   222
}
melunko@38
   223
melunko@38
   224
static GnomeVFSResult
melunko@38
   225
do_read (GnomeVFSMethod *method,
melunko@38
   226
         GnomeVFSMethodHandle *method_handle,
melunko@38
   227
         gpointer buffer,
melunko@38
   228
         GnomeVFSFileSize num_bytes,
melunko@38
   229
         GnomeVFSFileSize *bytes_read,
melunko@38
   230
         GnomeVFSContext *context)
melunko@38
   231
{
rosfran@327
   232
  MythtvHandle *myth_handle = (MythtvHandle *) method_handle;
rosfran@357
   233
  GnomeVFSFileSize bytes_to_read = num_bytes;
rosfran@357
   234
  gint64 size_stream = *bytes_read;
melunko@38
   235
rosfran@357
   236
  //*bytes_read = 0;
rosfran@354
   237
  
rosfran@357
   238
  g_debug ("XXXXXXXXXX Requested %llu bytes (remains %d bytes on buffer...) file_size = %lld\n", 
rosfran@357
   239
  		(guint64)num_bytes, myth_handle->buffer->len, *bytes_read );
melunko@38
   240
rosfran@340
   241
  if ( !myth_handle->is_livetv && ( myth_handle->bytes_read >= myth_handle->content_size ) )
rosfran@327
   242
      return GNOME_VFS_ERROR_EOF;
melunko@38
   243
rosfran@327
   244
  // fixme: change this to min math function
rosfran@357
   245
  if (( myth_handle->content_size > 0 ) ) 
rosfran@357
   246
  {
rosfran@357
   247
  	if ( !myth_handle->is_livetv && 
rosfran@341
   248
  				( num_bytes > ( myth_handle->content_size - myth_handle->bytes_read ) ) )
rosfran@357
   249
  	{
rosfran@357
   250
    	bytes_to_read = myth_handle->content_size - myth_handle->bytes_read;
rosfran@357
   251
  	} else {
rosfran@357
   252
    	size_stream = gmyth_recorder_get_file_position(myth_handle->livetv->recorder);
rosfran@357
   253
    	if ( size_stream > myth_handle->content_size ) {
rosfran@357
   254
    		g_debug( "New file size %lld, old size = %lld.", size_stream, myth_handle->content_size );    		
rosfran@357
   255
    		myth_handle->content_size = size_stream;
rosfran@357
   256
    		num_bytes = ( myth_handle->content_size - myth_handle->bytes_read );
rosfran@357
   257
    	} else if ( num_bytes > ( myth_handle->content_size - myth_handle->bytes_read ) )
rosfran@357
   258
    		num_bytes = MYTHTV_MAX_VFS_BUFFER_SIZE;
rosfran@357
   259
    }
rosfran@357
   260
  }
melunko@38
   261
rosfran@327
   262
  /* Loop sending the Myth File Transfer request:
rosfran@355
   263
   * Retry whilst authentication fails and we supply it. */
rosfran@355
   264
  /* if (myth_handle->buffer_remain  < MYTHTV_BUFFER_SIZE) { */
rosfran@357
   265
  if ( ( myth_handle->buffer_remain = myth_handle->buffer->len ) < bytes_to_read ) 
rosfran@355
   266
  {
rosfran@355
   267
  	gint buffer_size;
rosfran@354
   268
  	
rosfran@357
   269
  	//while ( MYTHTV_BUFFER_SIZE != myth_handle->buffer_remain ) {
rosfran@355
   270
  		
rosfran@355
   271
	  	/* resize buffer length request to no more than MYTHTV_MAX_REQUEST_SIZE */
rosfran@355
   272
	  	if ( ( MYTHTV_BUFFER_SIZE - myth_handle->buffer_remain ) <= MYTHTV_MAX_REQUEST_SIZE )
rosfran@355
   273
	  		buffer_size = MYTHTV_BUFFER_SIZE - myth_handle->buffer_remain;
rosfran@355
   274
	  	else
rosfran@355
   275
	  		buffer_size = MYTHTV_MAX_REQUEST_SIZE;
rosfran@355
   276
	
rosfran@355
   277
	  	GByteArray *tmp_buffer = g_byte_array_new();
rosfran@355
   278
	
rosfran@355
   279
			g_debug ("XXXXXXXXXX Asking %d bytes (there is %d bytes in the buffer)\n", 
rosfran@355
   280
					buffer_size, myth_handle->buffer_remain);
rosfran@355
   281
	
rosfran@355
   282
	    gint len = gmyth_file_transfer_read (myth_handle->file_transfer,
rosfran@355
   283
	          tmp_buffer, buffer_size, TRUE);
rosfran@355
   284
	
rosfran@355
   285
			if (!myth_handle->is_livetv && len < 0) {
rosfran@327
   286
		    g_byte_array_free (tmp_buffer, TRUE);
rosfran@355
   287
		    g_debug ("Fail to read bytes");
rosfran@355
   288
		    return GNOME_VFS_ERROR_IO;
rosfran@355
   289
		  } /*else if (len == 0) {
rosfran@355
   290
			    g_byte_array_free (tmp_buffer, TRUE);
rosfran@355
   291
			    g_warning ("End of file probably achieved");
rosfran@355
   292
			    return GNOME_VFS_ERROR_EOF;
rosfran@355
   293
			}*/
rosfran@327
   294
	
rosfran@357
   295
	    myth_handle->buffer = g_byte_array_append ( myth_handle->buffer,
rosfran@357
   296
	    		tmp_buffer->data, len );
rosfran@327
   297
	
rosfran@327
   298
			myth_handle->buffer_remain += len;
melunko@111
   299
rosfran@354
   300
			if ( tmp_buffer != NULL )
rosfran@354
   301
			{
rosfran@357
   302
	      g_byte_array_free ( tmp_buffer, TRUE );
rosfran@354
   303
	    	tmp_buffer = NULL;
rosfran@354
   304
			}
rosfran@357
   305
  	//} /* while - iterates until fills the internal buffer */
rosfran@355
   306
  	
rosfran@355
   307
  } /* if - got from the network, or not */
rosfran@355
   308
  
rosfran@357
   309
  bytes_to_read = ( bytes_to_read > myth_handle->buffer_remain ) ? myth_handle->buffer_remain : bytes_to_read;
rosfran@355
   310
  /* gets the first buffer_size bytes from the byte array buffer variable */ 
rosfran@116
   311
rosfran@355
   312
  g_memmove (buffer, myth_handle->buffer->data, bytes_to_read);
rosfran@116
   313
rosfran@355
   314
  myth_handle->bytes_read += bytes_to_read;
rosfran@355
   315
  myth_handle->buffer_remain -= bytes_to_read;
rosfran@116
   316
rosfran@355
   317
	/* flushs the newly buffer got from byte array */
rosfran@355
   318
	myth_handle->buffer = g_byte_array_remove_range (myth_handle->buffer, 0, bytes_to_read);
rosfran@355
   319
	g_debug ("Got from %llu bytes from internal buffer. (there are %d bytes in the buffer, from a total of %llu dispatched.)\n", 
rosfran@355
   320
				bytes_to_read, myth_handle->buffer_remain, myth_handle->bytes_read );
rosfran@357
   321
	
rosfran@357
   322
 	*bytes_read = bytes_to_read;
rosfran@355
   323
rosfran@355
   324
  return GNOME_VFS_OK;
melunko@38
   325
}
melunko@38
   326
melunko@38
   327
static GnomeVFSResult
melunko@38
   328
do_close (GnomeVFSMethod *method,
melunko@38
   329
          GnomeVFSMethodHandle *method_handle,
melunko@38
   330
          GnomeVFSContext *context)
melunko@38
   331
{
melunko@111
   332
rosfran@357
   333
  MythtvHandle *myth_handle = (MythtvHandle *) method_handle;
rosfran@357
   334
  
rosfran@357
   335
  //if ( NULL == myth_handle || myth_handle->configured ) {
rosfran@357
   336
	
rosfran@357
   337
	  if (myth_handle->file_transfer != NULL) {
rosfran@357
   338
	    g_object_unref (myth_handle->file_transfer);
rosfran@357
   339
	  	myth_handle->file_transfer = NULL;
rosfran@357
   340
	  }
rosfran@357
   341
	  
rosfran@357
   342
	  if (myth_handle->is_livetv && myth_handle->livetv != NULL) {
rosfran@357
   343
	    g_object_unref (myth_handle->livetv);
rosfran@357
   344
	  	myth_handle->livetv = NULL;
rosfran@357
   345
	  }
rosfran@357
   346
	  
rosfran@357
   347
	  if (myth_handle->buffer) {
rosfran@357
   348
			g_byte_array_free (myth_handle->buffer, TRUE);
rosfran@357
   349
			myth_handle->buffer = NULL;
rosfran@357
   350
	  }
rosfran@357
   351
	
rosfran@357
   352
	  myth_handle->configured = FALSE;
rosfran@357
   353
	
rosfran@357
   354
	  g_free (myth_handle);
rosfran@357
   355
	  
rosfran@357
   356
	  myth_handle = NULL;	    
rosfran@357
   357
	  
rosfran@357
   358
 // }
rosfran@127
   359
    
rosfran@357
   360
  return GNOME_VFS_OK;
melunko@38
   361
}
melunko@38
   362
melunko@38
   363
static GnomeVFSResult
melunko@38
   364
do_get_file_info (GnomeVFSMethod *method,
melunko@38
   365
                  GnomeVFSURI *uri,
melunko@38
   366
                  GnomeVFSFileInfo *file_info,
melunko@38
   367
                  GnomeVFSFileInfoOptions options,
melunko@38
   368
                  GnomeVFSContext *context)
melunko@38
   369
{
renatofilho@188
   370
    GMythFileTransfer *file_transfer = NULL;
rosfran@340
   371
    GMythRecorder			*recorder 		 = NULL;
rosfran@346
   372
    GMythTVChain			*tvchain	 		 = NULL;
rosfran@297
   373
    GMythBackendInfo  *backend_info  = NULL;
rosfran@297
   374
    GMythURI					*gmyth_uri		 = NULL;
rosfran@340
   375
		GMythSocket 			*socket 			 = NULL;		 
rosfran@297
   376
    gboolean 					is_livetv 		 = FALSE;
rosfran@301
   377
    gboolean					ret						 = TRUE;
rosfran@346
   378
    gboolean 					res 					 = TRUE;
rosfran@297
   379
    
rosfran@297
   380
    /* Creates and fills out the backend info structure */    
rosfran@297
   381
	  backend_info = gmyth_backend_info_new_with_uri ( 
rosfran@297
   382
	  			gnome_vfs_unescape_string( gnome_vfs_uri_to_string( uri, GNOME_VFS_URI_HIDE_NONE ), "" ) );
rosfran@297
   383
	  
rosfran@297
   384
	  /* creates an instance of */  
rosfran@297
   385
	  gmyth_uri = gmyth_uri_new_with_value( 
rosfran@297
   386
	  		gnome_vfs_unescape_string( gnome_vfs_uri_to_string( uri, GNOME_VFS_URI_HIDE_NONE ), "" ) );
renatofilho@188
   387
rosfran@297
   388
	  is_livetv = gmyth_uri_is_livetv( gmyth_uri );
rosfran@297
   389
melunko@38
   390
    file_info->valid_fields = file_info->valid_fields
melunko@38
   391
        | GNOME_VFS_FILE_INFO_FIELDS_TYPE
melunko@38
   392
        | GNOME_VFS_FILE_INFO_FIELDS_MIME_TYPE
melunko@38
   393
        | GNOME_VFS_FILE_INFO_FIELDS_PERMISSIONS;
melunko@38
   394
    file_info->type = GNOME_VFS_FILE_TYPE_REGULAR;
rosfran@297
   395
    /* fixme: get from file extension? */
melunko@111
   396
    file_info->mime_type = g_strdup ("video/x-nuv");
melunko@38
   397
    file_info->permissions =
melunko@38
   398
        GNOME_VFS_PERM_USER_READ |
melunko@38
   399
        GNOME_VFS_PERM_OTHER_READ |
melunko@38
   400
        GNOME_VFS_PERM_GROUP_READ;
rosfran@331
   401
        
rosfran@332
   402
    g_print( "gnome_vfs_uri == %s | gmyth_uri == %s.\n",
rosfran@331
   403
    				gnome_vfs_uri_get_path (uri),
rosfran@331
   404
    				gmyth_uri_get_path (gmyth_uri) );
melunko@38
   405
rosfran@301
   406
	  /* Connect to the backend */
rosfran@297
   407
	  if ( gmyth_uri != NULL && is_livetv == TRUE ) {
rosfran@332
   408
	  	
rosfran@338
   409
	  	/* start to get file info from LiveTV remote encoder */	  	
rosfran@332
   410
			socket = gmyth_socket_new ();
rosfran@332
   411
			
rosfran@332
   412
			/* FIME: Implement this at gmyth_socket */
rosfran@332
   413
			res = gmyth_socket_connect_to_backend (socket, backend_info->hostname,
rosfran@332
   414
					backend_info->port, TRUE);
rosfran@332
   415
			if (!res) {
rosfran@333
   416
				g_print ("[%s] LiveTV can not connect to backend", __FUNCTION__);	
rosfran@332
   417
				res = FALSE;
rosfran@332
   418
				goto error;
rosfran@332
   419
			}
rosfran@332
   420
rosfran@332
   421
			if ( gmyth_remote_util_get_free_recorder_count (socket) <= 0 ) {
rosfran@333
   422
				g_print ("No free remote encoder available.");
rosfran@332
   423
				res = FALSE;
rosfran@332
   424
				goto error;
rosfran@332
   425
			}
rosfran@332
   426
		
rosfran@332
   427
			/* Gets the recorder num */
rosfran@332
   428
			recorder = remote_request_next_free_recorder (socket, -1);
rosfran@335
   429
			
rosfran@346
   430
			//if ( socket != NULL )
rosfran@346
   431
			//	g_object_unref (socket);
rosfran@332
   432
		
rosfran@332
   433
			if ( recorder == NULL ) {
rosfran@333
   434
				g_print ("[%s] None remote encoder available", __FUNCTION__);
rosfran@332
   435
				res = FALSE;
rosfran@332
   436
				goto error;
rosfran@332
   437
			}
rosfran@332
   438
			
rosfran@332
   439
			/* Init remote encoder. Opens its control socket. */
rosfran@332
   440
			res = gmyth_recorder_setup(recorder);
rosfran@332
   441
			if ( !res ) {
rosfran@333
   442
				g_print ("[%s] Fail while setting remote encoder\n", __FUNCTION__);
rosfran@332
   443
				res = FALSE;
rosfran@332
   444
				goto error;
rosfran@346
   445
			}
rosfran@346
   446
			
rosfran@346
   447
			/* Creates livetv chain handler */
rosfran@346
   448
			tvchain = gmyth_tvchain_new();
rosfran@346
   449
			gmyth_tvchain_initialize ( tvchain, backend_info );
rosfran@346
   450
		
rosfran@346
   451
			if ( tvchain == NULL || tvchain->tvchain_id == NULL ) {
rosfran@346
   452
				res = FALSE;
rosfran@346
   453
				goto error;
rosfran@346
   454
			}
rosfran@346
   455
			
rosfran@346
   456
			// Spawn live tv. Uses the socket to send mythprotocol data to start livetv in the backend (remotelly)
rosfran@346
   457
			res = gmyth_recorder_spawntv ( recorder,
rosfran@346
   458
					gmyth_tvchain_get_id(tvchain) );
rosfran@346
   459
			if (!res) {
rosfran@346
   460
				g_warning ("[%s] Fail while spawn tv\n", __FUNCTION__);
rosfran@346
   461
				res = FALSE;
rosfran@346
   462
				goto error;
rosfran@355
   463
			}	
rosfran@332
   464
			
rosfran@357
   465
		  //gchar* channel_name = gmyth_uri_get_channel_name( gmyth_uri );		  
rosfran@338
   466
	
rosfran@338
   467
		  /* DEBUG message */
rosfran@332
   468
			GMythProgramInfo* prog_info = gmyth_recorder_get_current_program_info( recorder );
rosfran@332
   469
			
rosfran@332
   470
			if ( prog_info != NULL )
rosfran@332
   471
			{
rosfran@357
   472
				//gmyth_program_info_print( prog_info );
rosfran@357
   473
				g_debug( "Program Info: %s\n", gmyth_program_info_to_string( prog_info ) ); 
rosfran@332
   474
  
rosfran@332
   475
		    g_print( "path = %s",  prog_info->pathname->str );
rosfran@332
   476
		    
rosfran@332
   477
		    file_info->name = g_strdup ( g_strrstr( prog_info->pathname->str, "/" ) );
rosfran@332
   478
		    
rosfran@332
   479
			} else {
rosfran@341
   480
				file_info->name = g_strdup ( "LiveTV.nuv" );
rosfran@332
   481
				file_info->size = gmyth_recorder_get_file_position( recorder );
rosfran@332
   482
			}
rosfran@333
   483
			
rosfran@332
   484
	    if ( recorder != NULL )
rosfran@338
   485
	    	g_object_unref (recorder);
rosfran@333
   486
	    
rosfran@333
   487
	    if ( prog_info != NULL )
rosfran@333
   488
	    	g_object_unref( prog_info );
rosfran@346
   489
rosfran@346
   490
	    if ( tvchain != NULL )
rosfran@346
   491
	    	g_object_unref (tvchain);
rosfran@338
   492
	    
rosfran@340
   493
	    file_info->size = (GnomeVFSFileSize) - 1;
rosfran@331
   494
rosfran@297
   495
	  } else {
rosfran@332
   496
	  	
rosfran@332
   497
	  	/* start to get file info from remote file encoder */	
rosfran@297
   498
	    file_transfer = gmyth_file_transfer_new (backend_info);
rosfran@297
   499
	    
rosfran@297
   500
	    /* Verifies if the file exists */
rosfran@297
   501
	    if (!gmyth_util_file_exists (backend_info, gmyth_uri_get_path (gmyth_uri))) {
rosfran@297
   502
	        g_object_unref (backend_info);
rosfran@297
   503
					return GNOME_VFS_ERROR_NOT_FOUND;
rosfran@297
   504
	    }
rosfran@297
   505
	    
rosfran@297
   506
	    /* sets the Playback monitor connection */
rosfran@297
   507
	    ret = gmyth_file_transfer_open ( file_transfer, gmyth_uri_get_path (gmyth_uri) );
rosfran@331
   508
	    
rosfran@338
   509
	    file_info->name = g_strdup ( gnome_vfs_uri_get_path (uri) );
rosfran@297
   510
		
rosfran@335
   511
	  } /* if - LiveTV or not? */	  
rosfran@297
   512
	  
rosfran@297
   513
    if (ret == FALSE) {
rosfran@335
   514
	    g_debug ("MythTV FileTransfer open error\n");
rosfran@297
   515
	    return GNOME_VFS_ERROR_NOT_OPEN;
rosfran@297
   516
	  }
rosfran@335
   517
	  
rosfran@332
   518
		if ( ret == TRUE  && file_transfer != NULL ) {
rosfran@323
   519
    	file_info->size = gmyth_file_transfer_get_filesize (file_transfer);
rosfran@331
   520
	    if ( file_transfer )
rosfran@338
   521
	    	g_object_unref (file_transfer);
rosfran@331
   522
   	}
rosfran@338
   523
rosfran@331
   524
    file_info->block_count = GNOME_VFS_FILE_INFO_FIELDS_BLOCK_COUNT;
rosfran@331
   525
	  file_info->io_block_size = GNOME_VFS_FILE_INFO_FIELDS_IO_BLOCK_SIZE;
rosfran@332
   526
	  
rosfran@340
   527
error:
rosfran@331
   528
    if (backend_info)
rosfran@331
   529
   		g_object_unref (backend_info);
rosfran@346
   530
   		
rosfran@346
   531
   	if (!res)
rosfran@346
   532
   		return GNOME_VFS_ERROR_IO;
rosfran@301
   533
melunko@38
   534
    return GNOME_VFS_OK;
melunko@38
   535
}
melunko@38
   536
melunko@38
   537
static gboolean
melunko@38
   538
do_is_local (GnomeVFSMethod *method,
melunko@38
   539
             const GnomeVFSURI *uri)
melunko@38
   540
{
melunko@38
   541
	return FALSE;
melunko@38
   542
}
melunko@38
   543
melunko@38
   544
static GnomeVFSMethod method = {
melunko@38
   545
	sizeof (GnomeVFSMethod),
melunko@38
   546
	do_open,
melunko@38
   547
	NULL,
melunko@38
   548
	do_close,
melunko@38
   549
	do_read,
melunko@38
   550
	NULL,
melunko@38
   551
	NULL,
melunko@38
   552
	NULL,
melunko@38
   553
	NULL,
melunko@38
   554
	NULL,
melunko@38
   555
	NULL,
melunko@38
   556
	NULL,
melunko@38
   557
	do_get_file_info,
melunko@38
   558
	NULL,
melunko@38
   559
	do_is_local,
melunko@38
   560
	NULL,
melunko@38
   561
	NULL,
melunko@38
   562
	NULL,
melunko@38
   563
	NULL,
melunko@38
   564
	NULL,
melunko@38
   565
	NULL,
melunko@38
   566
	NULL,
melunko@38
   567
	NULL,
melunko@38
   568
	NULL,
melunko@38
   569
	NULL,
melunko@38
   570
	NULL,
melunko@38
   571
	NULL,
melunko@38
   572
};
melunko@38
   573
melunko@38
   574
melunko@38
   575
GnomeVFSMethod *
melunko@38
   576
vfs_module_init (const char *method_name, const char *args)
melunko@38
   577
{
melunko@38
   578
	return &method;
melunko@38
   579
}
melunko@38
   580
melunko@38
   581
void
melunko@38
   582
vfs_module_shutdown (GnomeVFSMethod *method)
melunko@38
   583
{
melunko@38
   584
}