resources: compiler: Add dependency generator

Bug #668532.
This commit is contained in:
Christian Persch 2012-01-23 20:42:20 +01:00
parent 45783c5927
commit 55d10d6bfd
3 changed files with 61 additions and 15 deletions

View File

@ -74,6 +74,23 @@ Generate a header file for use with C code generated by <option>--generate-sourc
</para></listitem> </para></listitem>
</varlistentry> </varlistentry>
<varlistentry>
<term><option>--generate-dependencies</option></term>
<listitem><para>
Prints the list of files that the resource bundle references to standard output.
This can be used to track dependencies in the build system. For example, the following
make rule would mark <replaceable>test.gresource</replaceable> as depending on all the
files that <replaceable>test.gresource.xm</replaceable> includes, so that is is automatically
rebuilt if any of them change:
<literal>
test.gresource: test.gresource.xml $(shell $(GLIB_COMPILE_RESOURCES) --generate-dependencies test.gresource.xml)
</literal>
Note that this may or may not be portable to non-GNU <command>make</command>.
</para>
<para>For example i
</para></listitem>
</varlistentry>
<varlistentry> <varlistentry>
<term><option>--c-name</option></term> <term><option>--c-name</option></term>
<listitem><para> <listitem><para>

View File

@ -47,6 +47,7 @@
typedef struct typedef struct
{ {
char *filename;
char *content; char *content;
gsize content_size; gsize content_size;
gsize size; gsize size;
@ -57,6 +58,8 @@ typedef struct
{ {
GHashTable *table; /* resource path -> FileData */ GHashTable *table; /* resource path -> FileData */
gboolean collect_data;
/* per gresource */ /* per gresource */
char *prefix; char *prefix;
@ -74,6 +77,7 @@ static gchar *xmllint = NULL;
static void static void
file_data_free (FileData *data) file_data_free (FileData *data)
{ {
g_free (data->filename);
g_free (data->content); g_free (data->content);
g_free (data); g_free (data);
} }
@ -187,7 +191,7 @@ end_element (GMarkupParseContext *context,
gchar *file, *real_file; gchar *file, *real_file;
gchar *key; gchar *key;
FileData *data; FileData *data;
char *tmp_file; char *tmp_file = NULL;
file = state->string->str; file = state->string->str;
key = file; key = file;
@ -214,7 +218,10 @@ end_element (GMarkupParseContext *context,
else else
real_file = g_strdup (file); real_file = g_strdup (file);
tmp_file = NULL; data->filename = g_strdup (real_file);
if (!state->collect_data)
goto done;
if (state->preproc_options) if (state->preproc_options)
{ {
gchar **options; gchar **options;
@ -328,6 +335,8 @@ end_element (GMarkupParseContext *context,
data->flags |= G_RESOURCE_FLAGS_COMPRESSED; data->flags |= G_RESOURCE_FLAGS_COMPRESSED;
} }
done:
g_hash_table_insert (state->table, key, data); g_hash_table_insert (state->table, key, data);
cleanup: cleanup:
@ -375,7 +384,8 @@ text (GMarkupParseContext *context,
} }
static GHashTable * static GHashTable *
parse_resource_file (const gchar *filename) parse_resource_file (const gchar *filename,
gboolean collect_data)
{ {
GMarkupParser parser = { start_element, end_element, text }; GMarkupParser parser = { start_element, end_element, text };
ParseState state = { 0, }; ParseState state = { 0, };
@ -393,6 +403,7 @@ parse_resource_file (const gchar *filename)
} }
state.table = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify)file_data_free); state.table = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify)file_data_free);
state.collect_data = collect_data;
context = g_markup_parse_context_new (&parser, context = g_markup_parse_context_new (&parser,
G_MARKUP_TREAT_CDATA_AS_TEXT | G_MARKUP_TREAT_CDATA_AS_TEXT |
@ -405,7 +416,7 @@ parse_resource_file (const gchar *filename)
g_printerr ("%s: %s.\n", filename, error->message); g_printerr ("%s: %s.\n", filename, error->message);
g_clear_error (&error); g_clear_error (&error);
} }
else else if (collect_data)
{ {
GHashTableIter iter; GHashTableIter iter;
const char *key; const char *key;
@ -445,8 +456,12 @@ parse_resource_file (const gchar *filename)
g_variant_builder_end (&builder)); g_variant_builder_end (&builder));
} }
} }
else
{
table = g_hash_table_ref (state.table);
}
g_hash_table_destroy (state.table); g_hash_table_unref (state.table);
g_markup_parse_context_free (context); g_markup_parse_context_free (context);
g_free (contents); g_free (contents);
@ -474,10 +489,11 @@ main (int argc, char **argv)
GHashTable *table; GHashTable *table;
gchar *srcfile; gchar *srcfile;
gchar *target = NULL; gchar *target = NULL;
gchar *binary_target; gchar *binary_target = NULL;
gboolean generate_source = FALSE; gboolean generate_source = FALSE;
gboolean generate_header = FALSE; gboolean generate_header = FALSE;
gboolean manual_register = FALSE; gboolean manual_register = FALSE;
gboolean generate_dependencies = FALSE;
char *c_name = NULL; char *c_name = NULL;
char *c_name_no_underscores; char *c_name_no_underscores;
GOptionContext *context; GOptionContext *context;
@ -486,6 +502,7 @@ main (int argc, char **argv)
{ "sourcedir", 0, 0, G_OPTION_ARG_FILENAME, &sourcedir, N_("The directory where files are to be read from (default to current directory)"), N_("DIRECTORY") }, { "sourcedir", 0, 0, G_OPTION_ARG_FILENAME, &sourcedir, N_("The directory where files are to be read from (default to current directory)"), N_("DIRECTORY") },
{ "generate-header", 0, 0, G_OPTION_ARG_NONE, &generate_header, N_("Generate source header"), NULL }, { "generate-header", 0, 0, G_OPTION_ARG_NONE, &generate_header, N_("Generate source header"), NULL },
{ "generate-source", 0, 0, G_OPTION_ARG_NONE, &generate_source, N_("Generate sourcecode used to link in the resource file into your code"), NULL }, { "generate-source", 0, 0, G_OPTION_ARG_NONE, &generate_source, N_("Generate sourcecode used to link in the resource file into your code"), NULL },
{ "generate-dependencies", 0, 0, G_OPTION_ARG_NONE, &generate_dependencies, N_("Generate dependency list"), NULL },
{ "manual-register", 0, 0, G_OPTION_ARG_NONE, &manual_register, N_("Don't automatically create and register resource"), NULL }, { "manual-register", 0, 0, G_OPTION_ARG_NONE, &manual_register, N_("Don't automatically create and register resource"), NULL },
{ "c-name", 0, 0, G_OPTION_ARG_STRING, &c_name, N_("C identifier name used for the generated source code"), NULL }, { "c-name", 0, 0, G_OPTION_ARG_STRING, &c_name, N_("C identifier name used for the generated source code"), NULL },
{ NULL } { NULL }
@ -575,13 +592,26 @@ main (int argc, char **argv)
g_free (base); g_free (base);
} }
if ((table = parse_resource_file (srcfile)) == NULL) if ((table = parse_resource_file (srcfile, !generate_dependencies)) == NULL)
{ {
g_free (target); g_free (target);
return 1; return 1;
} }
if (generate_source || generate_header) if (generate_dependencies)
{
GHashTableIter iter;
gpointer key, data;
FileData *file_data;
g_hash_table_iter_init (&iter, table);
while (g_hash_table_iter_next (&iter, &key, &data))
{
file_data = data;
g_print ("%s\n",file_data->filename);
}
}
else if (generate_source || generate_header)
{ {
if (generate_source) if (generate_source)
{ {
@ -593,8 +623,6 @@ main (int argc, char **argv)
} }
close (fd); close (fd);
} }
else
binary_target = NULL;
if (c_name == NULL) if (c_name == NULL)
{ {

View File

@ -395,6 +395,7 @@ appinfo_SOURCES = appinfo.c
appinfo_LDADD = $(progs_ldadd) appinfo_LDADD = $(progs_ldadd)
resources_SOURCES = resources.c test_resources.c test_resources2.c test_resources2.h resources_SOURCES = resources.c test_resources.c test_resources2.c test_resources2.h
resources_DEPENDENCIES = test.gresource
resources_LDADD = $(progs_ldadd) resources_LDADD = $(progs_ldadd)
appinfo_test_SOURCES = appinfo-test.c appinfo_test_SOURCES = appinfo-test.c
@ -588,19 +589,19 @@ else
endif endif
BUILT_SOURCES += test_resources.c test_resources2.c test_resources2.h BUILT_SOURCES += test_resources.c test_resources2.c test_resources2.h
test_resources.c: test2.gresource.xml test1.txt test_resources.c: test2.gresource.xml Makefile $(shell $(glib_compile_resources) --generate-dependencies test2.gresource.xml)
$(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-source --c-name _g_test1 $(srcdir)/test2.gresource.xml $(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-source --c-name _g_test1 $(srcdir)/test2.gresource.xml
test_resources2.c: test3.gresource.xml test1.txt test_resources2.c: test3.gresource.xml Makefile $(shell $(glib_compile_resources) --generate-dependencies test3.gresource.xml)
$(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-source --c-name _g_test2 --manual-register $(srcdir)/test3.gresource.xml $(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-source --c-name _g_test2 --manual-register $(srcdir)/test3.gresource.xml
test_resources2.h: test3.gresource.xml test_resources2.h: test3.gresource.xml Makefile $(shell $(glib_compile_resources) --generate-dependencies test3.gresource.xml)
$(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-header --c-name _g_test2 --manual-register $(srcdir)/test3.gresource.xml $(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-header --c-name _g_test2 --manual-register $(srcdir)/test3.gresource.xml
plugin_resources.c: test4.gresource.xml test1.txt plugin_resources.c: test4.gresource.xml Makefile $(shell $(glib_compile_resources) --generate-dependencies test4.gresource.xml)
$(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-source --c-name _g_plugin $(srcdir)/test4.gresource.xml $(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) --generate-source --c-name _g_plugin $(srcdir)/test4.gresource.xml
test.gresource: test.gresource.xml test1.txt test2.txt test3.txt test.gresource: test.gresource.xml Makefile $(shell $(glib_compile_resources) --generate-dependencies test.gresource.xml)
$(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) $(srcdir)/test.gresource.xml $(glib_compile_resources) --target=$@ --sourcedir=$(srcdir) $(srcdir)/test.gresource.xml
noinst_LTLIBRARIES = libresourceplugin.la noinst_LTLIBRARIES = libresourceplugin.la