diff --git a/ChangeLog b/ChangeLog
index ab00f47ef32758fefb8f43ec4fcd391e1cda114e..b3718c0aa49d14d20cc907a516acbb7609a0e1df 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,20 @@
+2006-02-10	Benedikt Meurer <benny@xfce.org>
+
+	* thunar/thunar-text-renderer.c(thunar_text_renderer_set_widget): Use
+	  the base text direction specified by Gtk+. Also, do not interpret
+	  line separators in file names.
+	* thunar-vfs/thunar-vfs-listdir-job.c,
+	  thunar-vfs/thunar-vfs-marshal.list: Add boolean return value to the
+	  ThunarVfsListdirJob::infos-ready signal, and allow handlers to take
+	  over ownership of the infos list to avoid having to allocate a new
+	  list (which reduces both performance overhead and the negative effects
+	  on the data cache). Handlers must take care when using this feature,
+	  documentation has been updated to explain the details.
+	* thunar/thunar-folder.c: Take over ownership of the list provided by
+	  "infos-ready" and just replace the ThunarVfsInfo's with ThunarFile's
+	  for the initial load case. For the reload case, there's no real gain
+	  in taking over ownership, so we keep the existing behaviour there.
+
 2006-02-09	Benedikt Meurer <benny@xfce.org>
 
 	* thunarx/thunarx-provider-factory.c: Initialize the factory on demand.
diff --git a/thunar-vfs/thunar-vfs-listdir-job.c b/thunar-vfs/thunar-vfs-listdir-job.c
index 9657531732aad5f7cd1f722434483149fe4d2afe..f55984488d3c8ec8b632a11ea8867979ae71b98b 100644
--- a/thunar-vfs/thunar-vfs-listdir-job.c
+++ b/thunar-vfs/thunar-vfs-listdir-job.c
@@ -31,6 +31,7 @@
 
 #include <thunar-vfs/thunar-vfs-info.h>
 #include <thunar-vfs/thunar-vfs-listdir-job.h>
+#include <thunar-vfs/thunar-vfs-marshal.h>
 #include <thunar-vfs/thunar-vfs-scandir.h>
 #include <thunar-vfs/thunar-vfs-alias.h>
 
@@ -132,13 +133,30 @@ thunar_vfs_listdir_job_class_init (ThunarVfsJobClass *klass)
    * This signal is emitted whenever there's a new bunch of
    * #ThunarVfsInfo<!---->s ready. This signal is garantied
    * to be never emitted with an @infos parameter of %NULL.
+   *
+   * To allow some further optimizations on the handler-side,
+   * the handler is allowed to take over ownership of the @infos
+   * list, i.e. it can reuse the @infos list and just replace
+   * the data elements with it's own objects based on the
+   * #ThunarVfsInfo<!--->s contained within the @infos list (and
+   * of course properly unreffing the previously contained infos).
+   * If a handler takes over ownership of @infos it must return
+   * %TRUE here, and no further handlers will be run. Else, if
+   * the handler doesn't want to take over ownership of @infos,
+   * it must return %FALSE, and other handlers will be run. Use
+   * this feature with care, and only if you can be sure that
+   * you are the only handler connected to this signal for a
+   * given job!
+   *
+   * Return value: %TRUE if the handler took over ownership of
+   *               @infos, else %FALSE.
    **/
   listdir_signals[INFOS_READY] =
     g_signal_new (I_("infos-ready"),
-                  G_TYPE_FROM_CLASS (klass),
-                  G_SIGNAL_NO_HOOKS, 0, NULL, NULL,
-                  g_cclosure_marshal_VOID__POINTER,
-                  G_TYPE_NONE, 1, G_TYPE_POINTER);
+                  G_TYPE_FROM_CLASS (klass), G_SIGNAL_NO_HOOKS,
+                  0, g_signal_accumulator_true_handled, NULL,
+                  _thunar_vfs_marshal_BOOLEAN__POINTER,
+                  G_TYPE_BOOLEAN, 1, G_TYPE_POINTER);
 }
 
 
@@ -172,6 +190,7 @@ static void
 thunar_vfs_listdir_job_execute (ThunarVfsJob *job)
 {
   GThreadPool *pool;
+  gboolean     handled = FALSE;
   GError      *error = NULL;
   GList       *list = NULL;
   GList       *lp;
@@ -276,11 +295,15 @@ thunar_vfs_listdir_job_execute (ThunarVfsJob *job)
     }
   else if (G_LIKELY (list != NULL))
     {
-      thunar_vfs_job_emit (job, listdir_signals[INFOS_READY], 0, list);
+      /* emit the "infos-ready" signal with the given list */
+      thunar_vfs_job_emit (job, listdir_signals[INFOS_READY], 0, list, &handled);
+
+      /* check if one of the handlers took over ownership of the list, if
+       * not, we still own it and we are responsible to release it.
+       */
+      if (G_UNLIKELY (!handled))
+        thunar_vfs_info_list_free (list);
     }
-
-  /* cleanup */
-  thunar_vfs_info_list_free (list);
 }
 
 
diff --git a/thunar-vfs/thunar-vfs-marshal.list b/thunar-vfs/thunar-vfs-marshal.list
index e4c52859b0c73a34195d5294e5a02ff1c1c817f8..c716f5d728f806e487098862e1bfb5a0d4c00248 100644
--- a/thunar-vfs/thunar-vfs-marshal.list
+++ b/thunar-vfs/thunar-vfs-marshal.list
@@ -1 +1,2 @@
+BOOLEAN:POINTER
 FLAGS:STRING,FLAGS
diff --git a/thunar/thunar-folder.c b/thunar/thunar-folder.c
index bfbbedc07c02f5b50b080de5960a688aa591ef77..512b8b4a39e23fe804efebccf0fa2a15967c1f2b 100644
--- a/thunar/thunar-folder.c
+++ b/thunar/thunar-folder.c
@@ -44,33 +44,33 @@ enum
 
 
 
-static void thunar_folder_class_init                  (ThunarFolderClass      *klass);
-static void thunar_folder_init                        (ThunarFolder           *folder);
-static void thunar_folder_finalize                    (GObject                *object);
-static void thunar_folder_get_property                (GObject                *object,
-                                                       guint                   prop_id,
-                                                       GValue                 *value,
-                                                       GParamSpec             *pspec);
-static void thunar_folder_error                       (ThunarVfsJob           *job,
-                                                       GError                 *error,
-                                                       ThunarFolder           *folder);
-static void thunar_folder_infos_ready                 (ThunarVfsJob           *job,
-                                                       GList                  *infos,
-                                                       ThunarFolder           *folder);
-static void thunar_folder_finished                    (ThunarVfsJob           *job,
-                                                       ThunarFolder           *folder);
-static void thunar_folder_corresponding_file_destroy  (ThunarFile             *file,
-                                                       ThunarFolder           *folder);
-static void thunar_folder_corresponding_file_renamed  (ThunarFile             *file,
-                                                       ThunarFolder           *folder);
-static void thunar_folder_file_destroy                (ThunarFile             *file,
-                                                       ThunarFolder           *folder);
-static void thunar_folder_monitor                     (ThunarVfsMonitor       *monitor,
-                                                       ThunarVfsMonitorHandle *handle,
-                                                       ThunarVfsMonitorEvent   event,
-                                                       ThunarVfsPath          *handle_path,
-                                                       ThunarVfsPath          *event_path,
-                                                       gpointer                user_data);
+static void     thunar_folder_class_init                  (ThunarFolderClass      *klass);
+static void     thunar_folder_init                        (ThunarFolder           *folder);
+static void     thunar_folder_finalize                    (GObject                *object);
+static void     thunar_folder_get_property                (GObject                *object,
+                                                           guint                   prop_id,
+                                                           GValue                 *value,
+                                                           GParamSpec             *pspec);
+static void     thunar_folder_error                       (ThunarVfsJob           *job,
+                                                           GError                 *error,
+                                                           ThunarFolder           *folder);
+static gboolean thunar_folder_infos_ready                 (ThunarVfsJob           *job,
+                                                           GList                  *infos,
+                                                           ThunarFolder           *folder);
+static void     thunar_folder_finished                    (ThunarVfsJob           *job,
+                                                           ThunarFolder           *folder);
+static void     thunar_folder_corresponding_file_destroy  (ThunarFile             *file,
+                                                           ThunarFolder           *folder);
+static void     thunar_folder_corresponding_file_renamed  (ThunarFile             *file,
+                                                           ThunarFolder           *folder);
+static void     thunar_folder_file_destroy                (ThunarFile             *file,
+                                                           ThunarFolder           *folder);
+static void     thunar_folder_monitor                     (ThunarVfsMonitor       *monitor,
+                                                           ThunarVfsMonitorHandle *handle,
+                                                           ThunarVfsMonitorEvent   event,
+                                                           ThunarVfsPath          *handle_path,
+                                                           ThunarVfsPath          *event_path,
+                                                           gpointer                user_data);
 
 
 
@@ -324,24 +324,27 @@ thunar_folder_error (ThunarVfsJob *job,
 
 
 
-static void
+static gboolean
 thunar_folder_infos_ready (ThunarVfsJob *job,
                            GList        *infos,
                            ThunarFolder *folder)
 {
   ThunarFile *file;
-  GList      *nfiles = NULL;
+  GList      *nfiles;
   GList      *fp;
   GList      *lp;
 
-  g_return_if_fail (THUNAR_IS_FOLDER (folder));
-  g_return_if_fail (THUNAR_VFS_IS_JOB (job));
-  g_return_if_fail (folder->handle == NULL);
-  g_return_if_fail (folder->job == job);
+  g_return_val_if_fail (THUNAR_IS_FOLDER (folder), FALSE);
+  g_return_val_if_fail (THUNAR_VFS_IS_JOB (job), FALSE);
+  g_return_val_if_fail (folder->handle == NULL, FALSE);
+  g_return_val_if_fail (folder->job == job, FALSE);
 
   /* check if we have any previous files */
   if (G_UNLIKELY (folder->previous_files != NULL))
     {
+      /* start with a fresh list of new files */
+      nfiles = NULL;
+
       /* for every new info, check if we already have it on the previous list */
       for (lp = infos; lp != NULL; lp = lp->next)
         {
@@ -370,14 +373,20 @@ thunar_folder_infos_ready (ThunarVfsJob *job,
     }
   else
     {
+      /* take over ownership of the infos list */
+      nfiles = infos;
+
       /* add the new files to our temporary list of new files */
       for (lp = infos; lp != NULL; lp = lp->next)
         {
-          /* get the file corresponding to the info */
+          /* get the file corresponding to the info... */
           file = thunar_file_get_for_info (lp->data);
 
-          /* add the file to the temporary list of new files */
-          nfiles = g_list_prepend (nfiles, file);
+          /* ...release the info at the list position... */
+          thunar_vfs_info_unref (lp->data);
+
+          /* ...and replace it with the file */
+          lp->data = file;
 
           /* connect the "destroy" signal */
           g_signal_connect_closure_by_id (G_OBJECT (file), folder->file_destroy_id,
@@ -394,6 +403,9 @@ thunar_folder_infos_ready (ThunarVfsJob *job,
       /* tell the consumers that we have new files */
       g_signal_emit (G_OBJECT (folder), folder_signals[FILES_ADDED], 0, nfiles);
     }
+
+  /* return TRUE if we took over ownership of the infos list */
+  return (nfiles == infos);
 }
 
 
diff --git a/thunar/thunar-text-renderer.c b/thunar/thunar-text-renderer.c
index 577f50404357fa072169d54fdb8e3712516ac13a..388bb90927696b221b1ff00fa435913743bd1532 100644
--- a/thunar/thunar-text-renderer.c
+++ b/thunar/thunar-text-renderer.c
@@ -675,6 +675,12 @@ thunar_text_renderer_set_widget (ThunarTextRenderer *text_renderer,
       context = gtk_widget_get_pango_context (widget);
       text_renderer->layout = pango_layout_new (context);
 
+      /* disable automatic text direction, but use the direction specified by Gtk+ */
+      pango_layout_set_auto_dir (text_renderer->layout, FALSE);
+
+      /* we don't want to interpret line separators in file names */
+      pango_layout_set_single_paragraph_mode (text_renderer->layout, TRUE);
+
       /* calculate the average character dimensions */
       metrics = pango_context_get_metrics (context, widget->style->font_desc, pango_context_get_language (context));
       text_renderer->char_width = PANGO_PIXELS (pango_font_metrics_get_approximate_char_width (metrics));