diff --git a/builder/Makefile.am.inc b/builder/Makefile.am.inc
index e3f2bfc3..b9af2058 100644
--- a/builder/Makefile.am.inc
+++ b/builder/Makefile.am.inc
@@ -10,6 +10,8 @@ flatpak_builder_SOURCES = \
builder/builder-options.h \
builder/builder-module.c \
builder/builder-module.h \
+ builder/builder-post-process.c \
+ builder/builder-post-process.h \
builder/builder-source.c \
builder/builder-source.h \
builder/builder-source-archive.c \
diff --git a/builder/builder-module.c b/builder/builder-module.c
index d1ff149e..57cb4bb3 100644
--- a/builder/builder-module.c
+++ b/builder/builder-module.c
@@ -33,6 +33,7 @@
#include "flatpak-utils.h"
#include "builder-utils.h"
#include "builder-module.h"
+#include "builder-post-process.h"
struct BuilderModule
{
@@ -843,182 +844,6 @@ build (GFile *app_dir,
return TRUE;
}
-static gboolean
-builder_module_handle_debuginfo (BuilderModule *self,
- GFile *app_dir,
- BuilderCache *cache,
- BuilderContext *context,
- GError **error)
-{
- g_autofree char *app_dir_path = g_file_get_path (app_dir);
- int i;
-
- g_autoptr(GPtrArray) changed = NULL;
-
- if (!builder_cache_get_outstanding_changes (cache, &changed, error))
- return FALSE;
-
- for (i = 0; i < changed->len; i++)
- {
- const char *rel_path = (char *) g_ptr_array_index (changed, i);
- g_autoptr(GFile) file = g_file_resolve_relative_path (app_dir, rel_path);
- g_autofree char *path = g_file_get_path (file);
- g_autofree char *debug_path = NULL;
- g_autofree char *real_debug_path = NULL;
- gboolean is_shared, is_stripped;
-
- if (is_elf_file (path, &is_shared, &is_stripped))
- {
- if (builder_options_get_strip (self->build_options, context))
- {
- g_print ("stripping: %s\n", rel_path);
- if (is_shared)
- {
- if (!strip (error, "--remove-section=.comment", "--remove-section=.note", "--strip-unneeded", path, NULL))
- {
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
- }
- else
- {
- if (!strip (error, "--remove-section=.comment", "--remove-section=.note", path, NULL))
- {
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
- }
- }
- else if (!builder_options_get_no_debuginfo (self->build_options, context) &&
- /* No support for debuginfo for extensions atm */
- !builder_context_get_build_extension (context))
- {
- g_autofree char *rel_path_dir = g_path_get_dirname (rel_path);
- g_autofree char *filename = g_path_get_basename (rel_path);
- g_autofree char *filename_debug = g_strconcat (filename, ".debug", NULL);
- g_autofree char *debug_dir = NULL;
- g_autofree char *source_dir_path = NULL;
- g_autoptr(GFile) source_dir = NULL;
- g_autofree char *real_debug_dir = NULL;
-
- if (g_str_has_prefix (rel_path_dir, "files/"))
- {
- debug_dir = g_build_filename (app_dir_path, "files/lib/debug", rel_path_dir + strlen ("files/"), NULL);
- real_debug_dir = g_build_filename ("/app/lib/debug", rel_path_dir + strlen ("files/"), NULL);
- source_dir_path = g_build_filename (app_dir_path, "files/lib/debug/source", NULL);
- }
- else if (g_str_has_prefix (rel_path_dir, "usr/"))
- {
- debug_dir = g_build_filename (app_dir_path, "usr/lib/debug", rel_path_dir, NULL);
- real_debug_dir = g_build_filename ("/usr/lib/debug", rel_path_dir, NULL);
- source_dir_path = g_build_filename (app_dir_path, "usr/lib/debug/source", NULL);
- }
-
- if (debug_dir)
- {
- const char *builddir;
- g_autoptr(GError) local_error = NULL;
- g_auto(GStrv) file_refs = NULL;
-
- if (g_mkdir_with_parents (debug_dir, 0755) != 0)
- {
- glnx_set_error_from_errno (error);
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
-
- source_dir = g_file_new_for_path (source_dir_path);
- if (g_mkdir_with_parents (source_dir_path, 0755) != 0)
- {
- glnx_set_error_from_errno (error);
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
-
- if (builder_context_get_build_runtime (context))
- builddir = "/run/build-runtime/";
- else
- builddir = "/run/build/";
-
- debug_path = g_build_filename (debug_dir, filename_debug, NULL);
- real_debug_path = g_build_filename (real_debug_dir, filename_debug, NULL);
-
- file_refs = builder_get_debuginfo_file_references (path, &local_error);
-
- if (file_refs == NULL)
- {
- g_warning ("%s", local_error->message);
- }
- else
- {
- GFile *build_dir = builder_context_get_build_dir (context);
- int i;
- for (i = 0; file_refs[i] != NULL; i++)
- {
- if (g_str_has_prefix (file_refs[i], builddir))
- {
- const char *relative_path = file_refs[i] + strlen (builddir);
- g_autoptr(GFile) src = g_file_resolve_relative_path (build_dir, relative_path);
- g_autoptr(GFile) dst = g_file_resolve_relative_path (source_dir, relative_path);
- g_autoptr(GFile) dst_parent = g_file_get_parent (dst);
- GFileType file_type;
-
- if (!flatpak_mkdir_p (dst_parent, NULL, error))
- {
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
-
- file_type = g_file_query_file_type (src, 0, NULL);
- if (file_type == G_FILE_TYPE_DIRECTORY)
- {
- if (!flatpak_mkdir_p (dst, NULL, error))
- {
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
- }
- else if (file_type == G_FILE_TYPE_REGULAR)
- {
- /* Make sure the target is gone, because g_file_copy does
- truncation on hardlinked destinations */
- g_file_delete (dst, NULL, NULL);
-
- if (!g_file_copy (src, dst,
- G_FILE_COPY_OVERWRITE,
- NULL, NULL, NULL, error))
- {
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
- }
- }
- }
- }
-
- g_print ("stripping %s to %s\n", path, debug_path);
-
- /* Some files are hardlinked and eu-strip modifies in-place,
- which breaks rofiles-fuse. Unlink them */
- if (!flatpak_unbreak_hardlink (file, error))
- return FALSE;
-
- if (!eu_strip (error, "--remove-comment", "--reloc-debug-sections",
- "-f", debug_path,
- "-F", real_debug_path,
- path, NULL))
- {
- g_prefix_error (error, "module %s: ", self->name);
- return FALSE;
- }
- }
- }
- }
- }
-
- return TRUE;
-}
-
static gboolean
fixup_python_timestamp (int dfd,
const char *rel_path,
@@ -1221,6 +1046,7 @@ builder_module_build (BuilderModule *self,
g_autofree char *source_dir_path = NULL;
g_autofree char *buildname = NULL;
g_autoptr(GError) my_error = NULL;
+ BuilderPostProcessFlags post_process_flags = 0;
int count;
build_parent_dir = builder_context_get_build_dir (context);
@@ -1590,8 +1416,19 @@ builder_module_build (BuilderModule *self,
return FALSE;
}
- if (!builder_module_handle_debuginfo (self, app_dir, cache, context, error))
- return FALSE;
+ if (builder_options_get_strip (self->build_options, context))
+ post_process_flags |= BUILDER_POST_PROCESS_FLAGS_STRIP;
+ else if (!builder_options_get_no_debuginfo (self->build_options, context) &&
+ /* No support for debuginfo for extensions atm */
+ !builder_context_get_build_extension (context))
+ post_process_flags |= BUILDER_POST_PROCESS_FLAGS_DEBUGINFO;
+
+ if (!builder_post_process (post_process_flags, app_dir,
+ cache, context, error))
+ {
+ g_prefix_error (error, "module %s: ", self->name);
+ return FALSE;
+ }
/* Clean up build dir */
diff --git a/builder/builder-post-process.c b/builder/builder-post-process.c
new file mode 100644
index 00000000..cdf845b6
--- /dev/null
+++ b/builder/builder-post-process.c
@@ -0,0 +1,225 @@
+/* builder-post-process.c
+ *
+ * Copyright (C) 2017 Red Hat, Inc
+ *
+ * This file is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This file is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program. If not, see .
+ *
+ * Authors:
+ * Alexander Larsson
+ */
+
+#include "config.h"
+
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include "libglnx/libglnx.h"
+
+#include "flatpak-utils.h"
+#include "builder-utils.h"
+#include "builder-post-process.h"
+
+static gboolean
+builder_post_process_strip (GFile *app_dir,
+ GPtrArray *changed,
+ GError **error)
+{
+ int i;
+
+ for (i = 0; i < changed->len; i++)
+ {
+ const char *rel_path = (char *) g_ptr_array_index (changed, i);
+ g_autoptr(GFile) file = g_file_resolve_relative_path (app_dir, rel_path);
+ g_autofree char *path = g_file_get_path (file);
+ gboolean is_shared, is_stripped;
+
+ if (!is_elf_file (path, &is_shared, &is_stripped))
+ continue;
+
+ g_print ("stripping: %s\n", rel_path);
+ if (is_shared)
+ {
+ if (!strip (error, "--remove-section=.comment", "--remove-section=.note", "--strip-unneeded", path, NULL))
+ return FALSE;
+ }
+ else
+ {
+ if (!strip (error, "--remove-section=.comment", "--remove-section=.note", path, NULL))
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
+
+static gboolean
+builder_post_process_debuginfo (GFile *app_dir,
+ GPtrArray *changed,
+ BuilderContext *context,
+ GError **error)
+{
+ g_autofree char *app_dir_path = g_file_get_path (app_dir);
+ int j;
+
+ for (j = 0; j < changed->len; j++)
+ {
+ const char *rel_path = (char *) g_ptr_array_index (changed, j);
+ g_autoptr(GFile) file = g_file_resolve_relative_path (app_dir, rel_path);
+ g_autofree char *path = g_file_get_path (file);
+ g_autofree char *debug_path = NULL;
+ g_autofree char *real_debug_path = NULL;
+ g_autofree char *rel_path_dir = g_path_get_dirname (rel_path);
+ g_autofree char *filename = g_path_get_basename (rel_path);
+ g_autofree char *filename_debug = g_strconcat (filename, ".debug", NULL);
+ g_autofree char *debug_dir = NULL;
+ g_autofree char *source_dir_path = NULL;
+ g_autoptr(GFile) source_dir = NULL;
+ g_autofree char *real_debug_dir = NULL;
+ gboolean is_shared, is_stripped;
+
+ if (!is_elf_file (path, &is_shared, &is_stripped))
+ continue;
+
+ if (g_str_has_prefix (rel_path_dir, "files/"))
+ {
+ debug_dir = g_build_filename (app_dir_path, "files/lib/debug", rel_path_dir + strlen ("files/"), NULL);
+ real_debug_dir = g_build_filename ("/app/lib/debug", rel_path_dir + strlen ("files/"), NULL);
+ source_dir_path = g_build_filename (app_dir_path, "files/lib/debug/source", NULL);
+ }
+ else if (g_str_has_prefix (rel_path_dir, "usr/"))
+ {
+ debug_dir = g_build_filename (app_dir_path, "usr/lib/debug", rel_path_dir, NULL);
+ real_debug_dir = g_build_filename ("/usr/lib/debug", rel_path_dir, NULL);
+ source_dir_path = g_build_filename (app_dir_path, "usr/lib/debug/source", NULL);
+ }
+
+ if (debug_dir)
+ {
+ const char *builddir;
+ g_autoptr(GError) local_error = NULL;
+ g_auto(GStrv) file_refs = NULL;
+
+ if (g_mkdir_with_parents (debug_dir, 0755) != 0)
+ {
+ glnx_set_error_from_errno (error);
+ return FALSE;
+ }
+
+ source_dir = g_file_new_for_path (source_dir_path);
+ if (g_mkdir_with_parents (source_dir_path, 0755) != 0)
+ {
+ glnx_set_error_from_errno (error);
+ return FALSE;
+ }
+
+ if (builder_context_get_build_runtime (context))
+ builddir = "/run/build-runtime/";
+ else
+ builddir = "/run/build/";
+
+ debug_path = g_build_filename (debug_dir, filename_debug, NULL);
+ real_debug_path = g_build_filename (real_debug_dir, filename_debug, NULL);
+
+ file_refs = builder_get_debuginfo_file_references (path, &local_error);
+
+ if (file_refs == NULL)
+ {
+ g_warning ("%s", local_error->message);
+ }
+ else
+ {
+ GFile *build_dir = builder_context_get_build_dir (context);
+ int i;
+ for (i = 0; file_refs[i] != NULL; i++)
+ {
+ if (g_str_has_prefix (file_refs[i], builddir))
+ {
+ const char *relative_path = file_refs[i] + strlen (builddir);
+ g_autoptr(GFile) src = g_file_resolve_relative_path (build_dir, relative_path);
+ g_autoptr(GFile) dst = g_file_resolve_relative_path (source_dir, relative_path);
+ g_autoptr(GFile) dst_parent = g_file_get_parent (dst);
+ GFileType file_type;
+
+ if (!flatpak_mkdir_p (dst_parent, NULL, error))
+ return FALSE;
+
+ file_type = g_file_query_file_type (src, 0, NULL);
+ if (file_type == G_FILE_TYPE_DIRECTORY)
+ {
+ if (!flatpak_mkdir_p (dst, NULL, error))
+ return FALSE;
+ }
+ else if (file_type == G_FILE_TYPE_REGULAR)
+ {
+ /* Make sure the target is gone, because g_file_copy does
+ truncation on hardlinked destinations */
+ g_file_delete (dst, NULL, NULL);
+
+ if (!g_file_copy (src, dst,
+ G_FILE_COPY_OVERWRITE,
+ NULL, NULL, NULL, error))
+ return FALSE;
+ }
+ }
+ }
+ }
+
+ g_print ("stripping %s to %s\n", path, debug_path);
+
+ /* Some files are hardlinked and eu-strip modifies in-place,
+ which breaks rofiles-fuse. Unlink them */
+ if (!flatpak_unbreak_hardlink (file, error))
+ return FALSE;
+
+ if (!eu_strip (error, "--remove-comment", "--reloc-debug-sections",
+ "-f", debug_path,
+ "-F", real_debug_path,
+ path, NULL))
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
+
+gboolean
+builder_post_process (BuilderPostProcessFlags flags,
+ GFile *app_dir,
+ BuilderCache *cache,
+ BuilderContext *context,
+ GError **error)
+{
+ g_autofree char *app_dir_path = g_file_get_path (app_dir);
+ g_autoptr(GPtrArray) changed = NULL;
+
+ if (!builder_cache_get_outstanding_changes (cache, &changed, error))
+ return FALSE;
+
+ if (flags & BUILDER_POST_PROCESS_FLAGS_STRIP)
+ {
+ if (!builder_post_process_strip (app_dir, changed, error))
+ return FALSE;
+ }
+ else if (flags & BUILDER_POST_PROCESS_FLAGS_DEBUGINFO)
+ {
+ if (!builder_post_process_debuginfo (app_dir, changed, context, error))
+ return FALSE;
+ }
+
+ return TRUE;
+}
diff --git a/builder/builder-post-process.h b/builder/builder-post-process.h
new file mode 100644
index 00000000..ddbf39c0
--- /dev/null
+++ b/builder/builder-post-process.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright © 2017 Red Hat, Inc
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library. If not, see .
+ *
+ * Authors:
+ * Alexander Larsson
+ */
+
+#ifndef __BUILDER_POST_PROCESS_H__
+#define __BUILDER_POST_PROCESS_H__
+
+#include "builder-cache.h"
+#include "builder-context.h"
+
+G_BEGIN_DECLS
+
+typedef enum {
+ BUILDER_POST_PROCESS_FLAGS_NONE = 0,
+ BUILDER_POST_PROCESS_FLAGS_PYTHON_TIMESTAMPS = 1<<0,
+ BUILDER_POST_PROCESS_FLAGS_STRIP = 1<<1,
+ BUILDER_POST_PROCESS_FLAGS_DEBUGINFO = 1<<2,
+} BuilderPostProcessFlags;
+
+gboolean builder_post_process (BuilderPostProcessFlags flags,
+ GFile *app_dir,
+ BuilderCache *cache,
+ BuilderContext *context,
+ GError **error);
+
+G_END_DECLS
+
+#endif /* __BUILDER_POST_PROCESS_H__ */