libgnomevfs2-mythtv/modules/mythtv-method.c
author rosfran
Thu Mar 08 23:42:25 2007 +0000 (2007-03-08)
branchtrunk
changeset 406 131040a49e9f
parent 372 36b50b1902c5
child 408 7d529c58a88f
permissions -rwxr-xr-x
[svn r411] Fixes the bug that makes a recorded MythTV movie REQUEST_BLOCK message to recurse indefinitely.
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@361
    44
/* internal GnomeVFS plug-in buffer size ( 120 Kbytes ) */
rosfran@363
    45
#define MYTHTV_BUFFER_SIZE							1024*80
rosfran@361
    46
/* internally sized GnomeVFS plug-in buffer ( 4 Kbytes ) */
rosfran@354
    47
#define MYTHTV_MAX_VFS_BUFFER_SIZE			4096
rosfran@361
    48
/* maximum number of bytes to be requested to the MythTV backend ( 64 Kbytes ) */
rosfran@354
    49
#define MYTHTV_MAX_REQUEST_SIZE					1024*64
melunko@111
    50
renatofilho@367
    51
static GnomeVFSResult do_read (GnomeVFSMethod * method,
renatofilho@367
    52
			       GnomeVFSMethodHandle * method_handle,
renatofilho@367
    53
			       gpointer buffer,
renatofilho@367
    54
			       GnomeVFSFileSize num_bytes,
renatofilho@367
    55
			       GnomeVFSFileSize * bytes_read,
renatofilho@367
    56
			       GnomeVFSContext * context);
melunko@38
    57
melunko@38
    58
typedef struct {
renatofilho@367
    59
	GMythFileTransfer *file_transfer;
renatofilho@367
    60
	GMythLiveTV *livetv;
renatofilho@367
    61
	gchar *channel_name;
melunko@111
    62
renatofilho@367
    63
	gint mythtv_version;
renatofilho@367
    64
	gint64 content_size;
renatofilho@367
    65
	guint64 bytes_read;
renatofilho@367
    66
renatofilho@367
    67
	GByteArray *buffer;
renatofilho@367
    68
	gsize buffer_remain;
renatofilho@367
    69
	gboolean is_livetv;
renatofilho@367
    70
renatofilho@367
    71
	gboolean configured;
renatofilho@367
    72
melunko@38
    73
} MythtvHandle;
melunko@38
    74
rosfran@357
    75
//static MythtvHandle *myth_handle = NULL;
rosfran@357
    76
melunko@38
    77
static GnomeVFSResult
renatofilho@367
    78
do_open (GnomeVFSMethod * method,
renatofilho@367
    79
	 GnomeVFSMethodHandle ** method_handle,
renatofilho@367
    80
	 GnomeVFSURI * uri,
renatofilho@367
    81
	 GnomeVFSOpenMode mode, GnomeVFSContext * context)
renatofilho@367
    82
{
renatofilho@367
    83
	MythtvHandle *myth_handle = NULL;
renatofilho@367
    84
	GMythBackendInfo *backend_info = NULL;
renatofilho@367
    85
	GMythURI *gmyth_uri = NULL;
renatofilho@367
    86
	gboolean ret = TRUE;
melunko@38
    87
renatofilho@367
    88
	_GNOME_VFS_METHOD_PARAM_CHECK (method_handle != NULL);
renatofilho@367
    89
	_GNOME_VFS_METHOD_PARAM_CHECK (uri != NULL);
melunko@38
    90
renatofilho@367
    91
	if (mode & GNOME_VFS_OPEN_WRITE) {
renatofilho@367
    92
		return GNOME_VFS_ERROR_NOT_PERMITTED;
renatofilho@367
    93
	}
melunko@38
    94
renatofilho@367
    95
	if (gnome_vfs_uri_get_host_name (uri) == NULL) {
renatofilho@367
    96
		return GNOME_VFS_ERROR_INVALID_HOST_NAME;
renatofilho@367
    97
	}
renatofilho@367
    98
renatofilho@367
    99
	if ((NULL == myth_handle) || !myth_handle->configured) {
renatofilho@367
   100
		myth_handle = g_new0 (MythtvHandle, 1);
renatofilho@367
   101
renatofilho@367
   102
		myth_handle->configured = FALSE;
renatofilho@367
   103
renatofilho@367
   104
		myth_handle->is_livetv = FALSE;
renatofilho@367
   105
renatofilho@367
   106
		/* Initialize mythtv handler */
renatofilho@367
   107
		myth_handle->file_transfer = NULL;
renatofilho@367
   108
		myth_handle->livetv = NULL;
renatofilho@367
   109
		myth_handle->mythtv_version = MYTHTV_VERSION_DEFAULT;
renatofilho@367
   110
		myth_handle->bytes_read = 0;
renatofilho@367
   111
		myth_handle->content_size = (GnomeVFSFileSize) - 1;
renatofilho@367
   112
renatofilho@367
   113
		/* Creates and fills out the backend info structure */
renatofilho@367
   114
		backend_info =
renatofilho@367
   115
		    gmyth_backend_info_new_with_uri
renatofilho@367
   116
		    (gnome_vfs_unescape_string
renatofilho@367
   117
		     (gnome_vfs_uri_to_string
renatofilho@367
   118
		      (uri, GNOME_VFS_URI_HIDE_NONE), ""));
renatofilho@367
   119
renatofilho@367
   120
		/* creates an instance of  */
renatofilho@367
   121
		gmyth_uri =
renatofilho@367
   122
		    gmyth_uri_new_with_value (gnome_vfs_unescape_string
renatofilho@367
   123
					      (gnome_vfs_uri_to_string
renatofilho@367
   124
					       (uri,
renatofilho@367
   125
						GNOME_VFS_URI_HIDE_NONE),
renatofilho@367
   126
					       ""));
renatofilho@367
   127
renatofilho@367
   128
		myth_handle->is_livetv = gmyth_uri_is_livetv (gmyth_uri);
renatofilho@367
   129
renatofilho@367
   130
		/* Connect to the backend */
renatofilho@367
   131
		if (gmyth_uri != NULL && myth_handle->is_livetv == TRUE) {
renatofilho@367
   132
renatofilho@367
   133
			if (NULL == myth_handle->livetv) {
renatofilho@367
   134
				myth_handle->livetv = gmyth_livetv_new ();
renatofilho@367
   135
renatofilho@367
   136
				myth_handle->channel_name =
renatofilho@367
   137
				    gmyth_uri_get_channel_name (gmyth_uri);
renatofilho@367
   138
renatofilho@367
   139
				g_debug ("[%s] Channel name = %s\n",
renatofilho@367
   140
					 __FUNCTION__,
renatofilho@367
   141
					 myth_handle->channel_name);
renatofilho@367
   142
renatofilho@367
   143
				if (myth_handle->channel_name != NULL) {
renatofilho@367
   144
					if (gmyth_livetv_channel_name_setup
renatofilho@367
   145
					    (myth_handle->livetv,
renatofilho@367
   146
					     myth_handle->channel_name,
renatofilho@367
   147
					     backend_info) == FALSE) {
renatofilho@367
   148
						g_object_unref (gmyth_uri);
rosfran@357
   149
						ret = FALSE;
rosfran@357
   150
					}
renatofilho@367
   151
				} else {
renatofilho@367
   152
					if (gmyth_livetv_setup
renatofilho@367
   153
					    (myth_handle->livetv,
renatofilho@367
   154
					     backend_info) == FALSE) {
renatofilho@367
   155
						g_object_unref (gmyth_uri);
renatofilho@367
   156
						ret = FALSE;
renatofilho@367
   157
					}
renatofilho@367
   158
				}
renatofilho@367
   159
			}
melunko@38
   160
renatofilho@367
   161
			if (NULL == myth_handle->file_transfer) {
renatofilho@367
   162
				myth_handle->file_transfer =
renatofilho@367
   163
				    gmyth_livetv_create_file_transfer
renatofilho@367
   164
				    (myth_handle->livetv);
renatofilho@367
   165
renatofilho@367
   166
				if (NULL == myth_handle->file_transfer) {
renatofilho@367
   167
					ret = FALSE;
renatofilho@367
   168
					g_debug
renatofilho@367
   169
					    ("MythTV FileTransfer is NULL!\n");
renatofilho@367
   170
					return GNOME_VFS_ERROR_NOT_OPEN;
renatofilho@367
   171
				}
renatofilho@367
   172
renatofilho@367
   173
				if (!gmyth_file_transfer_open
renatofilho@367
   174
				    (myth_handle->file_transfer,
renatofilho@367
   175
				     myth_handle->livetv->uri !=
renatofilho@367
   176
				     NULL ?
renatofilho@367
   177
				     gmyth_uri_get_path (myth_handle->
renatofilho@367
   178
							 livetv->
renatofilho@367
   179
							 uri) :
renatofilho@367
   180
				     myth_handle->livetv->proginfo->
renatofilho@367
   181
				     pathname->str)) {
renatofilho@367
   182
					g_debug
renatofilho@367
   183
					    ("Couldn't open MythTV FileTransfer is NULL!\n");
renatofilho@367
   184
					g_object_unref (myth_handle->
renatofilho@367
   185
							file_transfer);
renatofilho@367
   186
					myth_handle->file_transfer = NULL;
renatofilho@367
   187
					ret = FALSE;
renatofilho@367
   188
				}
renatofilho@367
   189
			}
renatofilho@367
   190
			/* if - FileTransfer is NULL, or not */
renatofilho@367
   191
		} else {
renatofilho@367
   192
renatofilho@367
   193
			if (NULL == myth_handle->file_transfer) {
renatofilho@367
   194
renatofilho@367
   195
				myth_handle->file_transfer =
renatofilho@367
   196
				    gmyth_file_transfer_new (backend_info);
renatofilho@367
   197
renatofilho@367
   198
				/* Verifies if the file exists */
renatofilho@367
   199
				if (!gmyth_util_file_exists
renatofilho@367
   200
				    (backend_info,
renatofilho@367
   201
				     gmyth_uri_get_path (gmyth_uri))) {
renatofilho@367
   202
					g_object_unref (backend_info);
renatofilho@367
   203
					ret = FALSE;
renatofilho@367
   204
				}
renatofilho@367
   205
renatofilho@367
   206
				/* sets the Playback monitor connection */
renatofilho@367
   207
				ret =
renatofilho@367
   208
				    gmyth_file_transfer_open (myth_handle->
renatofilho@367
   209
							      file_transfer,
renatofilho@367
   210
							      gmyth_uri_get_path
renatofilho@367
   211
							      (gmyth_uri));
renatofilho@367
   212
renatofilho@367
   213
			}
renatofilho@367
   214
renatofilho@367
   215
		}		/* if - LiveTV or not? */
renatofilho@367
   216
renatofilho@367
   217
		if (ret == FALSE) {
renatofilho@367
   218
			g_debug ("MythTV FileTransfer open error.\n");
renatofilho@367
   219
			return GNOME_VFS_ERROR_NOT_OPEN;
renatofilho@367
   220
		}
renatofilho@367
   221
renatofilho@367
   222
		myth_handle->configured = TRUE;
renatofilho@367
   223
renatofilho@367
   224
		g_object_unref (backend_info);
renatofilho@367
   225
renatofilho@367
   226
		if (gmyth_uri != NULL)
renatofilho@367
   227
			g_object_unref (gmyth_uri);
renatofilho@367
   228
renatofilho@367
   229
		myth_handle->buffer =
renatofilho@367
   230
		    g_byte_array_sized_new (MYTHTV_BUFFER_SIZE);
renatofilho@367
   231
		myth_handle->buffer_remain = 0;
renatofilho@367
   232
renatofilho@367
   233
		g_return_val_if_fail (myth_handle->file_transfer != NULL,
renatofilho@367
   234
				      GNOME_VFS_ERROR_NOT_OPEN);
renatofilho@367
   235
renatofilho@367
   236
		if ( /*myth_handle->file_transfer->filesize <= 0 && */
renatofilho@367
   237
		    myth_handle->is_livetv) {
renatofilho@367
   238
			myth_handle->content_size =
renatofilho@367
   239
			    gmyth_recorder_get_file_position (myth_handle->
renatofilho@367
   240
							      livetv->
renatofilho@367
   241
							      recorder);
renatofilho@367
   242
		} else {
renatofilho@367
   243
			myth_handle->content_size =
renatofilho@367
   244
			    myth_handle->file_transfer->filesize;
renatofilho@367
   245
		}
renatofilho@367
   246
renatofilho@367
   247
	}
renatofilho@367
   248
	/* if - configured or not? */
renatofilho@367
   249
	*method_handle = (GnomeVFSMethodHandle *) myth_handle;
renatofilho@367
   250
renatofilho@367
   251
	return GNOME_VFS_OK;
melunko@38
   252
}
melunko@38
   253
melunko@38
   254
static GnomeVFSResult
renatofilho@367
   255
do_read (GnomeVFSMethod * method,
renatofilho@367
   256
	 GnomeVFSMethodHandle * method_handle,
renatofilho@367
   257
	 gpointer buffer,
renatofilho@367
   258
	 GnomeVFSFileSize num_bytes,
renatofilho@367
   259
	 GnomeVFSFileSize * bytes_read, GnomeVFSContext * context)
melunko@38
   260
{
renatofilho@367
   261
	MythtvHandle *myth_handle = (MythtvHandle *) method_handle;
renatofilho@367
   262
	GnomeVFSFileSize bytes_to_read = num_bytes;
melunko@38
   263
renatofilho@367
   264
	if (!myth_handle->is_livetv
renatofilho@367
   265
	    && (myth_handle->bytes_read >= myth_handle->content_size))
renatofilho@367
   266
		return GNOME_VFS_ERROR_EOF;
melunko@38
   267
renatofilho@367
   268
	/* fixme: change this to min math function */
renatofilho@367
   269
	if ((myth_handle->content_size > 0)) {
renatofilho@367
   270
		if (!myth_handle->is_livetv &&
renatofilho@367
   271
		    (num_bytes >
renatofilho@367
   272
		     (myth_handle->content_size -
renatofilho@367
   273
		      myth_handle->bytes_read))) {
renatofilho@367
   274
			bytes_to_read =
renatofilho@367
   275
			    myth_handle->content_size -
renatofilho@367
   276
			    myth_handle->bytes_read;
renatofilho@367
   277
		}
renatofilho@367
   278
	}
melunko@38
   279
renatofilho@367
   280
	/* Loop sending the Myth File Transfer request:
renatofilho@367
   281
	 * Retry whilst authentication fails and we supply it. */
renatofilho@367
   282
	if ((myth_handle->buffer_remain =
renatofilho@367
   283
	     myth_handle->buffer->len) < bytes_to_read) {
renatofilho@367
   284
		gint buffer_size;
renatofilho@367
   285
renatofilho@367
   286
		while (MYTHTV_BUFFER_SIZE != myth_handle->buffer_remain) {
renatofilho@367
   287
renatofilho@367
   288
			/* resize buffer length request to no more than MYTHTV_MAX_REQUEST_SIZE */
renatofilho@367
   289
			if ((MYTHTV_BUFFER_SIZE -
renatofilho@367
   290
			     myth_handle->buffer_remain) <=
renatofilho@367
   291
			    MYTHTV_MAX_REQUEST_SIZE)
renatofilho@367
   292
				buffer_size =
renatofilho@367
   293
				    MYTHTV_BUFFER_SIZE -
renatofilho@367
   294
				    myth_handle->buffer_remain;
renatofilho@367
   295
			else
renatofilho@367
   296
				buffer_size = MYTHTV_MAX_REQUEST_SIZE;
renatofilho@367
   297
renatofilho@367
   298
			GByteArray *tmp_buffer = g_byte_array_new ();
renatofilho@367
   299
renatofilho@367
   300
			g_debug
rosfran@368
   301
			    ("Asking %d bytes (there is %d bytes in the buffer)\n",
renatofilho@367
   302
			     buffer_size, myth_handle->buffer_remain);
renatofilho@367
   303
renatofilho@367
   304
			gint len =
renatofilho@367
   305
			    gmyth_file_transfer_read (myth_handle->
renatofilho@367
   306
						      file_transfer,
renatofilho@367
   307
						      tmp_buffer,
renatofilho@367
   308
						      buffer_size, TRUE);
renatofilho@367
   309
rosfran@405
   310
			if (!myth_handle->is_livetv && len <= 0) {
renatofilho@367
   311
				g_byte_array_free (tmp_buffer, TRUE);
renatofilho@367
   312
				g_debug ("Fail to read bytes");
renatofilho@367
   313
				return GNOME_VFS_ERROR_IO;
renatofilho@367
   314
			}
renatofilho@367
   315
			/*else if (len == 0) {
renatofilho@367
   316
			   g_byte_array_free (tmp_buffer, TRUE);
renatofilho@367
   317
			   g_warning ("End of file probably achieved");
renatofilho@367
   318
			   return GNOME_VFS_ERROR_EOF;
renatofilho@367
   319
			   } */
renatofilho@367
   320
			myth_handle->buffer =
renatofilho@367
   321
			    g_byte_array_append (myth_handle->buffer,
renatofilho@367
   322
						 tmp_buffer->data, len);
renatofilho@367
   323
rosfran@327
   324
			myth_handle->buffer_remain += len;
melunko@111
   325
renatofilho@367
   326
			if (tmp_buffer != NULL) {
renatofilho@367
   327
				g_byte_array_free (tmp_buffer, TRUE);
renatofilho@367
   328
				tmp_buffer = NULL;
rosfran@354
   329
			}
renatofilho@367
   330
		}		/* while - iterates until fills the internal buffer */
rosfran@116
   331
renatofilho@367
   332
	}
renatofilho@367
   333
	/* if - got from the network, or not */
renatofilho@367
   334
	bytes_to_read =
renatofilho@367
   335
	    (bytes_to_read >
renatofilho@367
   336
	     myth_handle->buffer_remain) ? myth_handle->
renatofilho@367
   337
	    buffer_remain : bytes_to_read;
renatofilho@367
   338
	/* gets the first buffer_size bytes from the byte array buffer variable */
rosfran@116
   339
renatofilho@367
   340
	g_memmove (buffer, myth_handle->buffer->data, bytes_to_read);
renatofilho@367
   341
renatofilho@367
   342
	myth_handle->bytes_read += bytes_to_read;
renatofilho@367
   343
	myth_handle->buffer_remain -= bytes_to_read;
rosfran@116
   344
rosfran@355
   345
	/* flushs the newly buffer got from byte array */
renatofilho@367
   346
	myth_handle->buffer =
renatofilho@367
   347
	    g_byte_array_remove_range (myth_handle->buffer, 0,
renatofilho@367
   348
				       bytes_to_read);
renatofilho@367
   349
	g_debug
renatofilho@367
   350
	    ("Got from %llu bytes from internal buffer. (there are %d bytes in the buffer, from a total of %llu dispatched.)\n",
renatofilho@367
   351
	     bytes_to_read, myth_handle->buffer_remain,
renatofilho@367
   352
	     myth_handle->bytes_read);
rosfran@355
   353
renatofilho@367
   354
	*bytes_read = bytes_to_read;
renatofilho@367
   355
renatofilho@367
   356
	return GNOME_VFS_OK;
melunko@38
   357
}
melunko@38
   358
melunko@38
   359
static GnomeVFSResult
renatofilho@367
   360
do_close (GnomeVFSMethod * method,
renatofilho@367
   361
	  GnomeVFSMethodHandle * method_handle, GnomeVFSContext * context)
melunko@38
   362
{
melunko@111
   363
renatofilho@367
   364
	MythtvHandle *myth_handle = (MythtvHandle *) method_handle;
renatofilho@367
   365
renatofilho@367
   366
	//if ( NULL == myth_handle || myth_handle->configured ) {
renatofilho@367
   367
renatofilho@367
   368
	if (myth_handle->file_transfer != NULL) {
renatofilho@367
   369
		g_object_unref (myth_handle->file_transfer);
renatofilho@367
   370
		myth_handle->file_transfer = NULL;
renatofilho@367
   371
	}
renatofilho@367
   372
renatofilho@367
   373
	if (myth_handle->is_livetv && myth_handle->livetv != NULL) {
renatofilho@367
   374
		g_object_unref (myth_handle->livetv);
renatofilho@367
   375
		myth_handle->livetv = NULL;
renatofilho@367
   376
	}
renatofilho@367
   377
renatofilho@367
   378
	if (myth_handle->buffer) {
renatofilho@367
   379
		g_byte_array_free (myth_handle->buffer, TRUE);
renatofilho@367
   380
		myth_handle->buffer = NULL;
renatofilho@367
   381
	}
renatofilho@367
   382
renatofilho@367
   383
	myth_handle->configured = FALSE;
renatofilho@367
   384
renatofilho@367
   385
	g_free (myth_handle);
renatofilho@367
   386
renatofilho@367
   387
	myth_handle = NULL;
renatofilho@367
   388
renatofilho@367
   389
	// }
renatofilho@367
   390
renatofilho@367
   391
	return GNOME_VFS_OK;
melunko@38
   392
}
melunko@38
   393
melunko@38
   394
static GnomeVFSResult
renatofilho@367
   395
do_get_file_info (GnomeVFSMethod * method,
renatofilho@367
   396
		  GnomeVFSURI * uri,
renatofilho@367
   397
		  GnomeVFSFileInfo * file_info,
renatofilho@367
   398
		  GnomeVFSFileInfoOptions options,
renatofilho@367
   399
		  GnomeVFSContext * context)
melunko@38
   400
{
renatofilho@367
   401
	GMythFileTransfer *file_transfer = NULL;
renatofilho@367
   402
	GMythRecorder *recorder = NULL;
renatofilho@367
   403
	GMythTVChain *tvchain = NULL;
renatofilho@367
   404
	GMythBackendInfo *backend_info = NULL;
renatofilho@367
   405
	GMythURI *gmyth_uri = NULL;
renatofilho@367
   406
	GMythSocket *socket = NULL;
renatofilho@367
   407
	gboolean is_livetv = FALSE;
renatofilho@367
   408
	gboolean ret = TRUE;
renatofilho@367
   409
	gboolean res = TRUE;
renatofilho@188
   410
renatofilho@367
   411
	/* Creates and fills out the backend info structure */
renatofilho@367
   412
	backend_info =
renatofilho@367
   413
	    gmyth_backend_info_new_with_uri (gnome_vfs_unescape_string
renatofilho@367
   414
					     (gnome_vfs_uri_to_string
renatofilho@367
   415
					      (uri,
renatofilho@367
   416
					       GNOME_VFS_URI_HIDE_NONE),
renatofilho@367
   417
					      ""));
rosfran@297
   418
renatofilho@367
   419
	/* creates an instance of */
renatofilho@367
   420
	gmyth_uri =
renatofilho@367
   421
	    gmyth_uri_new_with_value (gnome_vfs_unescape_string
renatofilho@367
   422
				      (gnome_vfs_uri_to_string
renatofilho@367
   423
				       (uri, GNOME_VFS_URI_HIDE_NONE),
renatofilho@367
   424
				       ""));
melunko@38
   425
renatofilho@367
   426
	is_livetv = gmyth_uri_is_livetv (gmyth_uri);
rosfran@332
   427
renatofilho@367
   428
	file_info->valid_fields = file_info->valid_fields
renatofilho@367
   429
	    | GNOME_VFS_FILE_INFO_FIELDS_TYPE
renatofilho@367
   430
	    | GNOME_VFS_FILE_INFO_FIELDS_MIME_TYPE
renatofilho@367
   431
	    | GNOME_VFS_FILE_INFO_FIELDS_PERMISSIONS;
renatofilho@367
   432
	file_info->type = GNOME_VFS_FILE_TYPE_REGULAR;
renatofilho@367
   433
	/* fixme: get from file extension? */
renatofilho@367
   434
	file_info->mime_type = g_strdup ("video/x-nuv");
renatofilho@367
   435
	file_info->permissions =
renatofilho@367
   436
	    GNOME_VFS_PERM_USER_READ |
renatofilho@367
   437
	    GNOME_VFS_PERM_OTHER_READ | GNOME_VFS_PERM_GROUP_READ;
rosfran@346
   438
rosfran@368
   439
	g_debug ("gnome_vfs_uri == %s | gmyth_uri == %s.\n",
renatofilho@367
   440
		 gnome_vfs_uri_get_path (uri),
renatofilho@367
   441
		 gmyth_uri_get_path (gmyth_uri));
rosfran@331
   442
renatofilho@367
   443
	/* Connect to the backend */
renatofilho@367
   444
	if (gmyth_uri != NULL && is_livetv == TRUE) {
rosfran@338
   445
renatofilho@367
   446
		/* start to get file info from LiveTV remote encoder */
renatofilho@367
   447
		socket = gmyth_socket_new ();
rosfran@301
   448
renatofilho@367
   449
		/* FIME: Implement this at gmyth_socket */
renatofilho@367
   450
		res =
renatofilho@367
   451
		    gmyth_socket_connect_to_backend (socket,
renatofilho@367
   452
						     backend_info->
renatofilho@367
   453
						     hostname,
renatofilho@367
   454
						     backend_info->port,
renatofilho@367
   455
						     TRUE);
renatofilho@367
   456
		if (!res) {
rosfran@368
   457
			g_debug ("[%s] LiveTV can not connect to backend",
renatofilho@367
   458
				 __FUNCTION__);
renatofilho@367
   459
			res = FALSE;
renatofilho@367
   460
			goto error;
renatofilho@367
   461
		}
renatofilho@367
   462
renatofilho@367
   463
		if (gmyth_remote_util_get_free_recorder_count (socket) <=
renatofilho@367
   464
		    0) {
rosfran@368
   465
			g_debug ("No free remote encoder available.");
renatofilho@367
   466
			res = FALSE;
renatofilho@367
   467
			goto error;
renatofilho@367
   468
		}
renatofilho@367
   469
renatofilho@367
   470
		/* Gets the recorder num */
renatofilho@367
   471
		recorder = remote_request_next_free_recorder (socket, -1);
renatofilho@367
   472
rosfran@368
   473
		if ( socket != NULL )
rosfran@368
   474
			g_object_unref (socket);
renatofilho@367
   475
renatofilho@367
   476
		if (recorder == NULL) {
rosfran@368
   477
			g_debug ("[%s] None remote encoder available",
renatofilho@367
   478
				 __FUNCTION__);
renatofilho@367
   479
			res = FALSE;
renatofilho@367
   480
			goto error;
renatofilho@367
   481
		}
renatofilho@367
   482
renatofilho@367
   483
		/* Init remote encoder. Opens its control socket. */
renatofilho@367
   484
		res = gmyth_recorder_setup (recorder);
renatofilho@367
   485
		if (!res) {
rosfran@368
   486
			g_debug
renatofilho@367
   487
			    ("[%s] Fail while setting remote encoder\n",
renatofilho@367
   488
			     __FUNCTION__);
renatofilho@367
   489
			res = FALSE;
renatofilho@367
   490
			goto error;
renatofilho@367
   491
		}
renatofilho@367
   492
renatofilho@367
   493
		/* Creates livetv chain handler */
renatofilho@367
   494
		tvchain = gmyth_tvchain_new ();
renatofilho@367
   495
		gmyth_tvchain_initialize (tvchain, backend_info);
renatofilho@367
   496
renatofilho@367
   497
		if (tvchain == NULL || tvchain->tvchain_id == NULL) {
renatofilho@367
   498
			res = FALSE;
renatofilho@367
   499
			goto error;
renatofilho@367
   500
		}
rosfran@368
   501
		/* Spawn live tv. Uses the socket to send mythprotocol data to start livetv in the backend (remotelly) */
renatofilho@367
   502
		res = gmyth_recorder_spawntv (recorder,
renatofilho@367
   503
					      gmyth_tvchain_get_id
renatofilho@367
   504
					      (tvchain));
renatofilho@367
   505
		if (!res) {
renatofilho@367
   506
			g_warning ("[%s] Fail while spawn tv\n",
renatofilho@367
   507
				   __FUNCTION__);
renatofilho@367
   508
			res = FALSE;
renatofilho@367
   509
			goto error;
renatofilho@367
   510
		}
rosfran@372
   511
		
rosfran@372
   512
		sleep(1);
renatofilho@367
   513
renatofilho@367
   514
		/* DEBUG message */
renatofilho@367
   515
		GMythProgramInfo *prog_info =
renatofilho@367
   516
		    gmyth_recorder_get_current_program_info (recorder);
renatofilho@367
   517
renatofilho@367
   518
		if (prog_info != NULL) {
renatofilho@367
   519
rosfran@368
   520
			g_debug ("path = %s", prog_info->pathname->str);
renatofilho@367
   521
renatofilho@367
   522
			file_info->name =
renatofilho@367
   523
			    g_strdup (g_strrstr
renatofilho@367
   524
				      (prog_info->pathname->str, "/"));
renatofilho@367
   525
renatofilho@367
   526
		} else {
renatofilho@367
   527
			file_info->name = g_strdup ("LiveTV.nuv");
renatofilho@367
   528
			file_info->size =
renatofilho@367
   529
			    gmyth_recorder_get_file_position (recorder);
renatofilho@367
   530
		}
renatofilho@367
   531
renatofilho@367
   532
		if (recorder != NULL)
renatofilho@367
   533
			g_object_unref (recorder);
renatofilho@367
   534
renatofilho@367
   535
		if (prog_info != NULL)
renatofilho@367
   536
			g_object_unref (prog_info);
renatofilho@367
   537
renatofilho@367
   538
		if (tvchain != NULL)
renatofilho@367
   539
			g_object_unref (tvchain);
renatofilho@367
   540
renatofilho@367
   541
		file_info->size = (GnomeVFSFileSize) - 1;
renatofilho@367
   542
renatofilho@367
   543
	} else {
renatofilho@367
   544
renatofilho@367
   545
		/* start to get file info from remote file encoder */
renatofilho@367
   546
		file_transfer = gmyth_file_transfer_new (backend_info);
renatofilho@367
   547
renatofilho@367
   548
		/* Verifies if the file exists */
renatofilho@367
   549
		if (!gmyth_util_file_exists
renatofilho@367
   550
		    (backend_info, gmyth_uri_get_path (gmyth_uri))) {
renatofilho@367
   551
			g_object_unref (backend_info);
renatofilho@367
   552
			return GNOME_VFS_ERROR_NOT_FOUND;
renatofilho@367
   553
		}
renatofilho@367
   554
renatofilho@367
   555
		/* sets the Playback monitor connection */
renatofilho@367
   556
		ret =
renatofilho@367
   557
		    gmyth_file_transfer_open (file_transfer,
renatofilho@367
   558
					      gmyth_uri_get_path
renatofilho@367
   559
					      (gmyth_uri));
renatofilho@367
   560
renatofilho@367
   561
		file_info->name = g_strdup (gnome_vfs_uri_get_path (uri));
renatofilho@367
   562
renatofilho@367
   563
	}			/* if - LiveTV or not? */
renatofilho@367
   564
renatofilho@367
   565
	if (ret == FALSE) {
renatofilho@367
   566
		g_debug ("MythTV FileTransfer open error\n");
renatofilho@367
   567
		return GNOME_VFS_ERROR_NOT_OPEN;
renatofilho@367
   568
	}
renatofilho@367
   569
renatofilho@367
   570
	if (ret == TRUE && file_transfer != NULL) {
renatofilho@367
   571
		file_info->size =
renatofilho@367
   572
		    gmyth_file_transfer_get_filesize (file_transfer);
renatofilho@367
   573
		if (file_transfer)
renatofilho@367
   574
			g_object_unref (file_transfer);
renatofilho@367
   575
	}
renatofilho@367
   576
renatofilho@367
   577
	file_info->block_count = GNOME_VFS_FILE_INFO_FIELDS_BLOCK_COUNT;
renatofilho@367
   578
	file_info->io_block_size =
renatofilho@367
   579
	    GNOME_VFS_FILE_INFO_FIELDS_IO_BLOCK_SIZE;
renatofilho@367
   580
renatofilho@367
   581
      error:
renatofilho@367
   582
	if (backend_info)
renatofilho@367
   583
		g_object_unref (backend_info);
renatofilho@367
   584
renatofilho@367
   585
	if (!res)
renatofilho@367
   586
		return GNOME_VFS_ERROR_IO;
renatofilho@367
   587
renatofilho@367
   588
	return GNOME_VFS_OK;
melunko@38
   589
}
melunko@38
   590
melunko@38
   591
static gboolean
renatofilho@367
   592
do_is_local (GnomeVFSMethod * method, const GnomeVFSURI * uri)
melunko@38
   593
{
melunko@38
   594
	return FALSE;
melunko@38
   595
}
melunko@38
   596
melunko@38
   597
static GnomeVFSMethod method = {
melunko@38
   598
	sizeof (GnomeVFSMethod),
melunko@38
   599
	do_open,
melunko@38
   600
	NULL,
melunko@38
   601
	do_close,
melunko@38
   602
	do_read,
melunko@38
   603
	NULL,
melunko@38
   604
	NULL,
melunko@38
   605
	NULL,
melunko@38
   606
	NULL,
melunko@38
   607
	NULL,
melunko@38
   608
	NULL,
melunko@38
   609
	NULL,
melunko@38
   610
	do_get_file_info,
melunko@38
   611
	NULL,
melunko@38
   612
	do_is_local,
melunko@38
   613
	NULL,
melunko@38
   614
	NULL,
melunko@38
   615
	NULL,
melunko@38
   616
	NULL,
melunko@38
   617
	NULL,
melunko@38
   618
	NULL,
melunko@38
   619
	NULL,
melunko@38
   620
	NULL,
melunko@38
   621
	NULL,
melunko@38
   622
	NULL,
melunko@38
   623
	NULL,
melunko@38
   624
	NULL,
melunko@38
   625
};
melunko@38
   626
melunko@38
   627
melunko@38
   628
GnomeVFSMethod *
melunko@38
   629
vfs_module_init (const char *method_name, const char *args)
melunko@38
   630
{
melunko@38
   631
	return &method;
melunko@38
   632
}
melunko@38
   633
melunko@38
   634
void
renatofilho@367
   635
vfs_module_shutdown (GnomeVFSMethod * method)
melunko@38
   636
{
melunko@38
   637
}