/* $Id$
- * CORBA/ORBit server side of Directory object of sandbox_parent()
+ * CORBA/ORBit client side of Directory object of sandbox_parent()
* Copyright (C) 2003 Jan Kratochvil <project-captive@jankratochvil.net>
*
* This program is free software; you can redistribute it and/or modify
#include "config.h"
-#include "captive/parent-Directory.h" /* self */
+#include "parent-Directory.h" /* self */
#include <glib/gmessages.h>
#include "split.h"
#include "sandbox.h"
#include "../client/directory.h"
#include "../client/vfs.h"
#include "FileInfo.h"
+#include "captive/macros.h"
+#include "../client/vfs-parent.h"
+#include "captive/client-file-info.h"
GnomeVFSResult captive_sandbox_parent_directory_new_open
- (CaptiveDirectoryObject *captive_directory_object,const gchar *pathname)
+ (CaptiveDirectoryParentObject *captive_directory_parent_object)
{
- g_return_val_if_fail(captive_directory_object!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(pathname!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(captive_directory_object->dir_Handle==NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+xmlNode *xml_action=NULL;
+CaptiveVfsParentObject *captive_vfs_parent_object;
+GnomeVFSResult r;
+Captive_Directory corba_Directory_object;
+
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
+ g_return_val_if_fail(captive_directory_parent_object->pathname!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+
+ captive_vfs_parent_object=CAPTIVE_VFS_PARENT_OBJECT(CAPTIVE_DIRECTORY_OBJECT(captive_directory_parent_object)->vfs);
- captive_directory_object->corba_Directory_object=Captive_Vfs_directory_new_open(
- captive_directory_object->vfs->corba_Vfs_object,pathname,&captive_corba_ev);
+ if (captive_vfs_parent_object->corba_bug_action) {
+ xml_action=xmlNewTextChild(captive_vfs_parent_object->corba_bug_action,NULL,BAD_CAST "directory_new_open",NULL);
+ xmlNewProp(xml_action,BAD_CAST "object",BAD_CAST captive_printf_alloca("%p",captive_directory_parent_object));
+ xmlNewProp(xml_action,BAD_CAST "pathname",BAD_CAST captive_directory_parent_object->pathname);
+ }
- return captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev);
+ corba_Directory_object=Captive_Vfs_directory_new_open(
+ captive_vfs_parent_object->corba_Vfs_object,captive_directory_parent_object->pathname,&captive_corba_ev);
+ if (xml_action)
+ xmlNewProp(xml_action,BAD_CAST "result",BAD_CAST (captive_corba_ev._major==CORBA_NO_EXCEPTION ? "1" : "0"));
+ /* If 'r' means failure 'corba_Directory_object' may not be 'CORBA_OBJECT_NIL'
+ * although it is not valid 'CORBA_Object' to be passed to CORBA_Object_release().
+ */
+ if (GNOME_VFS_OK!=(r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev,captive_vfs_parent_object)))
+ return r;
+
+ captive_directory_parent_object->corba_Directory_object=corba_Directory_object;
+ return GNOME_VFS_OK;
}
GnomeVFSResult captive_sandbox_parent_directory_new_make
- (CaptiveDirectoryObject *captive_directory_object,const gchar *pathname,guint perm)
+ (CaptiveDirectoryParentObject *captive_directory_parent_object,guint perm)
{
- g_return_val_if_fail(captive_directory_object!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(pathname!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(captive_directory_object->dir_Handle==NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+xmlNode *xml_action=NULL;
+CaptiveVfsParentObject *captive_vfs_parent_object;
+GnomeVFSResult r;
+Captive_Directory corba_Directory_object;
+
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
+ g_return_val_if_fail(captive_directory_parent_object->pathname!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+
+ captive_vfs_parent_object=CAPTIVE_VFS_PARENT_OBJECT(CAPTIVE_DIRECTORY_OBJECT(captive_directory_parent_object)->vfs);
- captive_directory_object->corba_Directory_object=Captive_Vfs_directory_new_make(
- captive_directory_object->vfs->corba_Vfs_object,pathname,perm,&captive_corba_ev);
+ if (captive_vfs_parent_object->corba_bug_action) {
+ xml_action=xmlNewTextChild(captive_vfs_parent_object->corba_bug_action,NULL,BAD_CAST "directory_new_make",NULL);
+ xmlNewProp(xml_action,BAD_CAST "object",BAD_CAST captive_printf_alloca("%p",captive_directory_parent_object));
+ xmlNewProp(xml_action,BAD_CAST "pathname",BAD_CAST captive_directory_parent_object->pathname);
+ xmlNewProp(xml_action,BAD_CAST "perm",BAD_CAST captive_printf_alloca("%u",(unsigned)perm));
+ }
- return captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev);
+ corba_Directory_object=Captive_Vfs_directory_new_make(
+ captive_vfs_parent_object->corba_Vfs_object,captive_directory_parent_object->pathname,perm,&captive_corba_ev);
+ if (xml_action)
+ xmlNewProp(xml_action,BAD_CAST "result",BAD_CAST (captive_corba_ev._major==CORBA_NO_EXCEPTION ? "1" : "0"));
+ /* If 'r' means failure 'corba_Directory_object' may not be 'CORBA_OBJECT_NIL'
+ * although it is not valid 'CORBA_Object' to be passed to CORBA_Object_release().
+ */
+ if (GNOME_VFS_OK!=(r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev,captive_vfs_parent_object)))
+ return r;
+
+ captive_directory_parent_object->corba_Directory_object=corba_Directory_object;
+ return GNOME_VFS_OK;
}
-GnomeVFSResult captive_sandbox_parent_directory_close(CaptiveDirectoryObject *captive_directory_object)
+GnomeVFSResult captive_sandbox_parent_directory_close(CaptiveDirectoryParentObject *captive_directory_parent_object)
{
- g_return_val_if_fail(captive_directory_object!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(captive_directory_object->dir_Handle==NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+GnomeVFSResult r;
+xmlNode *xml_action=NULL;
+CaptiveVfsParentObject *captive_vfs_parent_object;
- CORBA_Object_release((CORBA_Object)captive_directory_object->corba_Directory_object,&captive_corba_ev);
- captive_directory_object->corba_Directory_object=CORBA_OBJECT_NIL;
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
- return captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev);
-}
+ captive_vfs_parent_object=CAPTIVE_VFS_PARENT_OBJECT(CAPTIVE_DIRECTORY_OBJECT(captive_directory_parent_object)->vfs);
+ if (captive_vfs_parent_object->corba_bug_action) {
+ xml_action=xmlNewTextChild(captive_vfs_parent_object->corba_bug_action,NULL,BAD_CAST "directory_close",NULL);
+ xmlNewProp(xml_action,BAD_CAST "object",BAD_CAST captive_printf_alloca("%p",captive_directory_parent_object));
+ }
-GnomeVFSResult captive_sandbox_parent_directory_read
- (CaptiveDirectoryObject *captive_directory_object,GnomeVFSFileInfo *file_info_captive)
+ Captive_Directory_shutdown(captive_directory_parent_object->corba_Directory_object,&captive_corba_ev);
+ r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev,captive_vfs_parent_object);
+ if (xml_action)
+ xmlNewProp(xml_action,BAD_CAST "result",BAD_CAST gnome_vfs_result_to_string(r));
+
+ /* Always clear 'corba_Directory_object' even if 'r' means failure. */
+ CORBA_Object_release((CORBA_Object)captive_directory_parent_object->corba_Directory_object,&captive_corba_ev);
+ captive_directory_parent_object->corba_Directory_object=CORBA_OBJECT_NIL;
+
+ if (captive_directory_parent_object->corba_Directory_file_info_list) {
+GList *file_info_last_l=g_list_last(captive_directory_parent_object->corba_Directory_file_info_list);
+
+ /* Prevent gnome_vfs_file_info_list_free() and its gnome_vfs_file_info_unref()
+ * on the last 'file_info_list' items as it is EOF with NULL '->data'.
+ */
+ /* Do not: g_assert(file_info_last_l->data==NULL); * directory EOF *
+ * as the crashed client may not produced the trailing NULL.
+ */
+ if (!file_info_last_l->data)
+ captive_directory_parent_object->corba_Directory_file_info_list=g_list_delete_link(
+ captive_directory_parent_object->corba_Directory_file_info_list,file_info_last_l);
+ gnome_vfs_file_info_list_free(captive_directory_parent_object->corba_Directory_file_info_list);
+ captive_directory_parent_object->corba_Directory_file_info_list=NULL;
+ }
+
+ return r;
+}
+
+static GnomeVFSResult captive_sandbox_parent_directory_read_get1
+ (CaptiveDirectoryParentObject *captive_directory_parent_object,CaptiveFileInfoObject **file_info_captive_return)
{
-Captive_GnomeVFSFileInfo *file_info_corba;
+xmlNode *xml_action=NULL;
+Captive_CaptiveFileInfoObject *file_info_corba;
GnomeVFSResult r;
+CaptiveVfsParentObject *captive_vfs_parent_object;
+CaptiveFileInfoObject *file_info_captive;
+
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
+ g_return_val_if_fail(file_info_captive_return!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+
+ captive_vfs_parent_object=CAPTIVE_VFS_PARENT_OBJECT(CAPTIVE_DIRECTORY_OBJECT(captive_directory_parent_object)->vfs);
- g_return_val_if_fail(captive_directory_object!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(file_info_captive!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(captive_directory_object->dir_Handle==NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+ if (captive_vfs_parent_object->corba_bug_action) {
+ xml_action=xmlNewTextChild(captive_vfs_parent_object->corba_bug_action,NULL,BAD_CAST "directory_read",NULL);
+ xmlNewProp(xml_action,BAD_CAST "object",BAD_CAST captive_printf_alloca("%p",captive_directory_parent_object));
+ }
- Captive_Directory_read(captive_directory_object->corba_Directory_object,&file_info_corba,&captive_corba_ev);
- if (GNOME_VFS_OK!=(r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev)))
+ Captive_Directory_read(captive_directory_parent_object->corba_Directory_object,&file_info_corba,&captive_corba_ev);
+ r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev,captive_vfs_parent_object);
+ if (xml_action)
+ xmlNewProp(xml_action,BAD_CAST "result",BAD_CAST gnome_vfs_result_to_string(r));
+ if (r!=GNOME_VFS_OK)
return r;
- if (GNOME_VFS_OK!=(r=captive_sandbox_file_info_corba_to_captive(file_info_captive,file_info_corba)))
+ r=captive_file_info_object_new(&file_info_captive);
+ if (xml_action)
+ xmlSetProp(xml_action,BAD_CAST "result",BAD_CAST gnome_vfs_result_to_string(r));
+ if (r!=GNOME_VFS_OK)
return r; /* 'file_info_corba' leak */
- Captive_GnomeVFSFileInfo__freekids(file_info_corba,NULL/* 'd'; meaning? */);
+ r=captive_sandbox_file_info_corba_to_captive(file_info_captive,file_info_corba);
+ if (xml_action)
+ xmlSetProp(xml_action,BAD_CAST "result",BAD_CAST gnome_vfs_result_to_string(r));
+ if (r!=GNOME_VFS_OK) {
+ g_object_unref(file_info_captive);
+ return r; /* 'file_info_corba' leak */
+ }
+
+ Captive_CaptiveFileInfoObject__freekids(file_info_corba,NULL/* 'd'; meaning? */);
CORBA_free(file_info_corba);
+ *file_info_captive_return=file_info_captive;
return GNOME_VFS_OK;
}
+static GnomeVFSResult captive_sandbox_parent_directory_read_filldir(CaptiveDirectoryParentObject *captive_directory_parent_object)
+{
+CaptiveFileInfoObject *file_info_captive;
+GnomeVFSResult r;
+
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
+ g_return_val_if_fail(captive_directory_parent_object->corba_Directory_file_info_list==NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+
+ for (;;) {
+ r=captive_sandbox_parent_directory_read_get1(captive_directory_parent_object,&file_info_captive);
+ if (r==GNOME_VFS_ERROR_EOF)
+ break;
+ if (r!=GNOME_VFS_OK) {
+ gnome_vfs_file_info_list_free(captive_directory_parent_object->corba_Directory_file_info_list);
+ captive_directory_parent_object->corba_Directory_file_info_list=NULL;
+ return r;
+ }
+ captive_directory_parent_object->corba_Directory_file_info_list=g_list_prepend(
+ captive_directory_parent_object->corba_Directory_file_info_list,file_info_captive);
+ }
-GnomeVFSResult captive_sandbox_parent_directory_remove(CaptiveDirectoryObject *captive_directory_object)
+ captive_directory_parent_object->corba_Directory_file_info_list=g_list_prepend(
+ captive_directory_parent_object->corba_Directory_file_info_list,NULL); /* EOF */
+ captive_directory_parent_object->corba_Directory_file_info_list=g_list_reverse(
+ captive_directory_parent_object->corba_Directory_file_info_list);
+
+ return GNOME_VFS_OK;
+}
+
+/* We have to read the whole directory atomically
+ * as during valid child restart we would loose our reading position.
+ * Returned 'CaptiveFileInfoObject' has 1 reference for yourself, you must g_object_unref() it.
+ */
+GnomeVFSResult captive_sandbox_parent_directory_read
+ (CaptiveDirectoryParentObject *captive_directory_parent_object,CaptiveFileInfoObject **file_info_captive_return)
{
GnomeVFSResult r;
- g_return_val_if_fail(captive_directory_object!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
- g_return_val_if_fail(captive_directory_object->dir_Handle==NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
+ g_return_val_if_fail(file_info_captive_return!=NULL,GNOME_VFS_ERROR_BAD_PARAMETERS);
+
+ if (!captive_directory_parent_object->corba_Directory_file_info_list)
+ if (GNOME_VFS_OK!=(r=captive_sandbox_parent_directory_read_filldir(captive_directory_parent_object)))
+ return r;
+
+ if (!captive_directory_parent_object->corba_Directory_file_info_list->data) {
+ g_assert(captive_directory_parent_object->corba_Directory_file_info_list->next==NULL);
+ /* Do not clear the list to leave us stuck at EOF - GnomeVFS behaves that way. */
+ r=GNOME_VFS_ERROR_EOF;
+ }
+ else {
+ /* Cut first list item. */
+ *file_info_captive_return=captive_directory_parent_object->corba_Directory_file_info_list->data;
+ captive_directory_parent_object->corba_Directory_file_info_list=g_list_delete_link(
+ captive_directory_parent_object->corba_Directory_file_info_list,
+ captive_directory_parent_object->corba_Directory_file_info_list);
+ r=GNOME_VFS_OK;
+ }
+
+ return r;
+}
+
+
+GnomeVFSResult captive_sandbox_parent_directory_remove(CaptiveDirectoryParentObject *captive_directory_parent_object)
+{
+GnomeVFSResult r;
+xmlNode *xml_action=NULL;
+CaptiveVfsParentObject *captive_vfs_parent_object;
+
+ g_return_val_if_fail(CAPTIVE_DIRECTORY_PARENT_IS_OBJECT(captive_directory_parent_object),GNOME_VFS_ERROR_BAD_PARAMETERS);
+
+ captive_vfs_parent_object=CAPTIVE_VFS_PARENT_OBJECT(CAPTIVE_DIRECTORY_OBJECT(captive_directory_parent_object)->vfs);
+
+ if (captive_vfs_parent_object->corba_bug_action) {
+ xml_action=xmlNewTextChild(captive_vfs_parent_object->corba_bug_action,NULL,BAD_CAST "directory_remove",NULL);
+ xmlNewProp(xml_action,BAD_CAST "object",BAD_CAST captive_printf_alloca("%p",captive_directory_parent_object));
+ }
- Captive_Directory_remove(captive_directory_object->corba_Directory_object,&captive_corba_ev);
- if (GNOME_VFS_OK!=(r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev)))
+ Captive_Directory_remove(captive_directory_parent_object->corba_Directory_object,&captive_corba_ev);
+ r=captive_sandbox_parent_return_from_CORBA_Environment(&captive_corba_ev,captive_vfs_parent_object);
+ if (xml_action)
+ xmlNewProp(xml_action,BAD_CAST "result",BAD_CAST gnome_vfs_result_to_string(r));
+ if (r!=GNOME_VFS_OK)
return r;
return GNOME_VFS_OK;