diff --git a/pressure-vessel/wrap.c b/pressure-vessel/wrap.c
index 21c5f6876fcf374488a94b4e571dd6f30c490074..0f6be0e66cf791af963ea8f62d0353cda1edd498 100644
--- a/pressure-vessel/wrap.c
+++ b/pressure-vessel/wrap.c
@@ -412,10 +412,63 @@ static const char * const steam_api_subdirs[] =
 
 static gboolean expose_steam (FlatpakExports *exports,
                               FlatpakFilesystemMode mode,
+                              gboolean is_home_shared,
                               const char *real_home,
                               const char *fake_home,
                               GError **error);
 
+static gboolean
+use_tmpfs_home (FlatpakExports *exports,
+                FlatpakBwrap *bwrap,
+                PvEnviron *container_env,
+                GError **error)
+{
+  const gchar *home = g_get_home_dir ();
+  g_autofree char *real_home = realpath (home, NULL);
+  g_autofree gchar *cache = g_build_filename (real_home, ".cache", NULL);
+  g_autofree gchar *cache2 = g_build_filename (real_home, "cache", NULL);
+  g_autofree gchar *tmp = g_build_filename (cache, "tmp", NULL);
+  g_autofree gchar *config = g_build_filename (real_home, ".config", NULL);
+  g_autofree gchar *config2 = g_build_filename (real_home, "config", NULL);
+  g_autofree gchar *local = g_build_filename (real_home, ".local", NULL);
+  g_autofree gchar *data = g_build_filename (local, "share", NULL);
+  g_autofree gchar *data2 = g_build_filename (real_home, "data", NULL);
+
+  g_return_val_if_fail (bwrap != NULL, FALSE);
+  g_return_val_if_fail (exports != NULL, FALSE);
+  g_return_val_if_fail (error == NULL || *error == NULL, FALSE);
+
+  /* If the logical path to the home dir has a symlink among its ancestors
+   * (e.g. /home/user when /home -> var/home exists), make sure the
+   * symlink structure gets mirrored in the container */
+  flatpak_exports_add_path_dir (exports, home);
+
+  /* Mount the tmpfs home directory onto the physical path to real_home,
+   * so that it will not conflict with symlinks created by the exports.
+   * See also https://github.com/flatpak/flatpak/issues/1278 and
+   * Flatpak commit f1df5cb1 */
+  flatpak_bwrap_add_args (bwrap, "--tmpfs", real_home, NULL);
+
+  flatpak_bwrap_add_args (bwrap,
+                          "--dir", cache,
+                          "--dir", tmp,
+                          "--dir", config,
+                          "--dir", local,
+                          "--dir", data,
+                          "--symlink", ".cache", cache2,
+                          "--symlink", ".config", config2,
+                          "--symlink", ".local/share", data2,
+                          "--symlink", tmp, "/var/tmp",
+                          NULL);
+
+  pv_environ_lock_env (container_env, "XDG_CACHE_HOME", cache);
+  pv_environ_lock_env (container_env, "XDG_CONFIG_HOME", config);
+  pv_environ_lock_env (container_env, "XDG_DATA_HOME", data);
+
+  return expose_steam (exports, FLATPAK_FILESYSTEM_MODE_READ_ONLY, FALSE,
+                       real_home, NULL, error);
+}
+
 static gboolean
 use_fake_home (FlatpakExports *exports,
                FlatpakBwrap *bwrap,
@@ -498,13 +551,14 @@ use_fake_home (FlatpakExports *exports,
                                    FLATPAK_FILESYSTEM_MODE_READ_WRITE,
                                    fake_home);
 
-  return expose_steam (exports, FLATPAK_FILESYSTEM_MODE_READ_ONLY,
+  return expose_steam (exports, FLATPAK_FILESYSTEM_MODE_READ_ONLY, FALSE,
                        real_home, fake_home, error);
 }
 
 static gboolean
 expose_steam (FlatpakExports *exports,
               FlatpakFilesystemMode mode,
+              gboolean is_home_shared,
               const char *real_home,
               const char *fake_home,
               GError **error)
@@ -520,7 +574,7 @@ expose_steam (FlatpakExports *exports,
   /* We need ~/.steam to be visible in the container, even if it's a
    * symlink to somewhere outside $HOME. (It's better not to do this; use
    * a separate Steam library instead, or use bind-mounts.) */
-  if (fake_home != NULL)
+  if (!is_home_shared)
     {
       flatpak_exports_add_path_expose (exports, mode, dot_steam);
     }
@@ -1300,6 +1354,7 @@ main (int argc,
   int original_argc = argc;
   gboolean is_flatpak_env = g_file_test ("/.flatpak-info", G_FILE_TEST_IS_REGULAR);
   gboolean is_main_program;
+  gboolean is_home_shared = TRUE;
   gboolean search_cwd = FALSE;
   g_autoptr(FlatpakBwrap) flatpak_subsandbox = NULL;
   g_autoptr(FlatpakBwrap) flatpak_run_on_host = NULL;
@@ -1565,23 +1620,26 @@ main (int argc,
 
   if (opt_share_home == TRISTATE_YES)
     {
-      opt_fake_home = NULL;
+      is_home_shared = TRUE;
     }
   else if (opt_home)
     {
+      is_home_shared = FALSE;
       opt_fake_home = g_strdup (opt_home);
     }
   else if (opt_share_home == TRISTATE_MAYBE)
     {
-      opt_fake_home = NULL;
+      is_home_shared = TRUE;
     }
   else if (opt_freedesktop_app_id)
     {
+      is_home_shared = FALSE;
       opt_fake_home = g_build_filename (home, ".var", "app",
                                         opt_freedesktop_app_id, NULL);
     }
   else if (opt_steam_app_id)
     {
+      is_home_shared = FALSE;
       opt_freedesktop_app_id = g_strdup_printf ("com.steampowered.App%s",
                                                 opt_steam_app_id);
       opt_fake_home = g_build_filename (home, ".var", "app",
@@ -1589,6 +1647,7 @@ main (int argc,
     }
   else if (g_getenv ("STEAM_COMPAT_APP_ID") != NULL)
     {
+      is_home_shared = FALSE;
       opt_freedesktop_app_id = g_strdup_printf ("com.steampowered.App%s",
                                                 g_getenv ("STEAM_COMPAT_APP_ID"));
       opt_fake_home = g_build_filename (home, ".var", "app",
@@ -1596,11 +1655,19 @@ main (int argc,
     }
   else if (g_getenv ("SteamAppId") != NULL)
     {
+      is_home_shared = FALSE;
       opt_freedesktop_app_id = g_strdup_printf ("com.steampowered.App%s",
                                                 g_getenv ("SteamAppId"));
       opt_fake_home = g_build_filename (home, ".var", "app",
                                         opt_freedesktop_app_id, NULL);
     }
+  else if (opt_batch)
+    {
+      is_home_shared = FALSE;
+      opt_fake_home = NULL;
+      g_info ("Unsharing the home directory without choosing a valid "
+              "candidate, using tmpfs as a fallback");
+    }
   else
     {
       usage_error ("Either --home, --freedesktop-app-id, --steam-app-id "
@@ -2057,7 +2124,7 @@ main (int argc,
 
   if (flatpak_subsandbox != NULL)
     {
-      if (opt_fake_home == NULL)
+      if (is_home_shared)
         {
           /* Nothing special to do here: we'll use the same home directory
            * and exports that the parent Flatpak sandbox used. */
@@ -2078,7 +2145,7 @@ main (int argc,
       g_assert (bwrap_filesystem_arguments != NULL);
       g_assert (exports != NULL);
 
-      if (opt_fake_home == NULL)
+      if (is_home_shared)
         {
           flatpak_exports_add_path_expose (exports,
                                            FLATPAK_FILESYSTEM_MODE_READ_WRITE,
@@ -2094,17 +2161,26 @@ main (int argc,
            * should have a future "compat level" in which it's read-only,
            * like it already is when using a per-game home directory. */
           if (!expose_steam (exports, FLATPAK_FILESYSTEM_MODE_READ_WRITE,
-                             home, NULL, error))
+                             TRUE, home, NULL, error))
             goto out;
         }
       else
         {
           bwrap_home_arguments = flatpak_bwrap_new (flatpak_bwrap_empty_env);
 
-          if (!use_fake_home (exports, bwrap_home_arguments,
-                              container_env, opt_fake_home,
-                              error))
-            goto out;
+          if (opt_fake_home == NULL)
+            {
+              if (!use_tmpfs_home (exports, bwrap_home_arguments,
+                                   container_env, error))
+                goto out;
+            }
+          else
+            {
+              if (!use_fake_home (exports, bwrap_home_arguments,
+                                  container_env, opt_fake_home,
+                                  error))
+                goto out;
+            }
         }
     }