summaryrefslogtreecommitdiff
path: root/pango/modules.c
diff options
context:
space:
mode:
Diffstat (limited to 'pango/modules.c')
-rw-r--r--pango/modules.c791
1 files changed, 25 insertions, 766 deletions
diff --git a/pango/modules.c b/pango/modules.c
index d8ff79c1..4705979b 100644
--- a/pango/modules.c
+++ b/pango/modules.c
@@ -29,113 +29,7 @@
*/
#include "config.h"
-#include <string.h>
-#include <limits.h>
-#include <errno.h>
-
-#include <gmodule.h>
-#include <glib/gstdio.h>
-
-#include "pango-enum-types.h"
#include "pango-modules.h"
-#include "pango-impl-utils.h"
-#include "modules.h"
-
-typedef struct _PangoModule PangoModule;
-typedef struct _PangoModuleClass PangoModuleClass;
-
-#define PANGO_TYPE_MODULE (pango_module_get_type ())
-#define PANGO_MODULE(module) (G_TYPE_CHECK_INSTANCE_CAST ((module), PANGO_TYPE_MODULE, PangoModule))
-#define PANGO_IS_MODULE(module) (G_TYPE_CHECK_INSTANCE_TYPE ((module), PANGO_TYPE_MODULE))
-
-typedef struct _PangoMapInfo PangoMapInfo;
-typedef struct _PangoEnginePair PangoEnginePair;
-typedef struct _PangoSubmap PangoSubmap;
-
-/**
- * PangoMap:
- *
- * A #PangoMap structure can be used to determine the engine to
- * use for each character.
- */
-struct _PangoMap
-{
- GArray *entries;
-};
-
-/**
- * PangoMapEntry:
- *
- * A #PangoMapEntry contains information about the engine that should be used
- * for the codepoint to which this entry belongs and also whether the engine
- * matches the language tag for this entry's map exactly or just approximately.
- */
-struct _PangoMapEntry
-{
- GSList *exact;
- GSList *fallback;
-};
-
-struct _PangoMapInfo
-{
- PangoLanguage *language;
- guint engine_type_id;
- guint render_type_id;
- PangoMap *map;
-};
-
-struct _PangoEnginePair
-{
- PangoEngineInfo info;
- PangoModule *module;
- PangoEngine *engine;
-};
-
-struct _PangoModule
-{
- GTypeModule parent_instance;
-
- char *path;
- GModule *library;
-
- void (*list) (PangoEngineInfo **engines, gint *n_engines);
- void (*init) (GTypeModule *module);
- void (*exit) (void);
- PangoEngine *(*create) (const gchar *id);
-};
-
-struct _PangoModuleClass
-{
- GTypeModuleClass parent_class;
-};
-
-G_LOCK_DEFINE_STATIC (maps);
-static GList *maps = NULL;
-/* the following are readonly after init_modules */
-static GSList *registered_engines = NULL;
-static GSList *dlloaded_engines = NULL;
-static GHashTable *dlloaded_modules;
-
-static void build_map (PangoMapInfo *info);
-static void init_modules (void);
-
-static GType pango_module_get_type (void);
-
-/* If a module cannot be used, or does not create an engine
- * correctly, we print out an error containing module name and id,
- * but to not flood the terminal with zillions of the message, we
- * set a flag on the module to only err once per module.
- */
-static GQuark
-get_warned_quark (void)
-{
- static GQuark warned_quark = 0; /* MT-safe */
-
- if (G_UNLIKELY (!warned_quark))
- warned_quark = g_quark_from_static_string ("pango-module-warned");
-
- return warned_quark;
-}
/**
* pango_find_map:
@@ -143,588 +37,18 @@ get_warned_quark (void)
* @engine_type_id: the engine type for the map to find
* @render_type_id: the render type for the map to find
*
- * Locate a #PangoMap for a particular engine type and render
- * type. The resulting map can be used to determine the engine
- * for each character.
+ * Do not use. Does not do anything.
*
- * Return value: the suitable #PangoMap.
+ * Return value: %NULL.
+ *
+ * Deprecated: 1.37
**/
PangoMap *
-pango_find_map (PangoLanguage *language,
- guint engine_type_id,
- guint render_type_id)
-{
- GList *tmp_list;
- PangoMapInfo *map_info = NULL;
- gboolean found_earlier = FALSE;
-
- G_LOCK (maps);
-
- tmp_list = maps;
- while (tmp_list)
- {
- map_info = tmp_list->data;
- if (map_info->engine_type_id == engine_type_id &&
- map_info->render_type_id == render_type_id)
- {
- if (map_info->language == language)
- break;
- else
- found_earlier = TRUE;
- }
-
- tmp_list = tmp_list->next;
- }
-
- if (!tmp_list)
- {
- map_info = g_slice_new (PangoMapInfo);
- map_info->language = language;
- map_info->engine_type_id = engine_type_id;
- map_info->render_type_id = render_type_id;
-
- build_map (map_info);
-
- maps = g_list_prepend (maps, map_info);
- }
- else if (found_earlier)
- {
- /* Move the found map to the beginning of the list
- * for speed next time around if we had to do
- * any failing comparison. (No longer so important,
- * since we don't strcmp.)
- */
- maps = g_list_remove_link(maps, tmp_list);
- maps = g_list_prepend(maps, tmp_list->data);
- g_list_free_1(tmp_list);
- }
-
- G_UNLOCK (maps);
-
- return map_info->map;
-}
-
-G_DEFINE_TYPE (PangoModule, pango_module, G_TYPE_TYPE_MODULE);
-
-static gboolean
-pango_module_load (GTypeModule *module)
-{
- PangoModule *pango_module = PANGO_MODULE (module);
-
- if (pango_module->path)
- {
- pango_module->library = g_module_open (pango_module->path, G_MODULE_BIND_LOCAL);
- if (!pango_module->library)
- {
- GQuark warned_quark = get_warned_quark ();
- if (!g_object_get_qdata (G_OBJECT (pango_module), warned_quark))
- {
- g_warning ("%s", g_module_error());
- g_object_set_qdata_full (G_OBJECT (pango_module), warned_quark,
- GINT_TO_POINTER (1), NULL);
- }
- return FALSE;
- }
-
- /* extract symbols from the lib */
- if (!g_module_symbol (pango_module->library, "script_engine_init",
- (gpointer *)(void *)&pango_module->init) ||
- !g_module_symbol (pango_module->library, "script_engine_exit",
- (gpointer *)(void *)&pango_module->exit) ||
- !g_module_symbol (pango_module->library, "script_engine_list",
- (gpointer *)(void *)&pango_module->list) ||
- !g_module_symbol (pango_module->library, "script_engine_create",
- (gpointer *)(void *)&pango_module->create))
- {
- GQuark warned_quark = get_warned_quark ();
- if (!g_object_get_qdata (G_OBJECT (pango_module), warned_quark))
- {
- g_warning ("%s", g_module_error());
- g_object_set_qdata_full (G_OBJECT (pango_module), warned_quark,
- GINT_TO_POINTER (1), NULL);
- }
-
- g_module_close (pango_module->library);
-
- return FALSE;
- }
- }
-
- /* call the module's init function to let it */
- /* setup anything it needs to set up. */
- pango_module->init (module);
-
- return TRUE;
-}
-
-static void
-pango_module_unload (GTypeModule *module)
-{
- PangoModule *pango_module = PANGO_MODULE (module);
-
- pango_module->exit();
-
- if (pango_module->path)
- {
- g_module_close (pango_module->library);
- pango_module->library = NULL;
-
- pango_module->init = NULL;
- pango_module->exit = NULL;
- pango_module->list = NULL;
- pango_module->create = NULL;
- }
-}
-
-/* This only will ever be called if an error occurs during
- * initialization
- */
-static void
-pango_module_finalize (GObject *object)
-{
- PangoModule *module = PANGO_MODULE (object);
-
- g_free (module->path);
-
- G_OBJECT_CLASS (pango_module_parent_class)->finalize (object);
-}
-
-static void
-pango_module_init (PangoModule *self)
+pango_find_map (PangoLanguage *language G_GNUC_UNUSED,
+ guint engine_type_id G_GNUC_UNUSED,
+ guint render_type_id G_GNUC_UNUSED)
{
-}
-
-static void
-pango_module_class_init (PangoModuleClass *class)
-{
- GTypeModuleClass *module_class = G_TYPE_MODULE_CLASS (class);
- GObjectClass *gobject_class = G_OBJECT_CLASS (class);
-
- module_class->load = pango_module_load;
- module_class->unload = pango_module_unload;
-
- gobject_class->finalize = pango_module_finalize;
-}
-
-G_LOCK_DEFINE_STATIC (engine);
-
-static PangoEngine *
-pango_engine_pair_get_engine (PangoEnginePair *pair)
-{
- G_LOCK (engine);
-
- if (!pair->engine)
- {
- if (g_type_module_use (G_TYPE_MODULE (pair->module)))
- {
- pair->engine = pair->module->create (pair->info.id);
- g_type_module_unuse (G_TYPE_MODULE (pair->module));
- }
-
- if (!pair->engine)
- {
- GQuark warned_quark = get_warned_quark ();
- if (!g_object_get_qdata (G_OBJECT (pair->module), warned_quark))
- {
- g_warning ("Failed to load Pango module '%s' for id '%s'", pair->module->path, pair->info.id);
-
- g_object_set_qdata_full (G_OBJECT (pair->module), warned_quark,
- GINT_TO_POINTER (1), NULL);
- }
- }
- }
-
- G_UNLOCK (engine);
-
- return pair->engine;
-}
-
-static void
-handle_included_module (PangoIncludedModule *included_module,
- GSList **engine_list)
-{
- PangoModule *module = g_object_new (PANGO_TYPE_MODULE, NULL);
- PangoEngineInfo *engine_info;
- int n_engines;
- int i;
-
- module->list = included_module->list;
- module->init = included_module->init;
- module->exit = included_module->exit;
- module->create = included_module->create;
-
- module->list (&engine_info, &n_engines);
-
- for (i = 0; i < n_engines; i++)
- {
- PangoEnginePair *pair = g_slice_new (PangoEnginePair);
-
- pair->info = engine_info[i];
- pair->module = module;
- pair->engine = NULL;
-
- *engine_list = g_slist_prepend (*engine_list, pair);
- }
-}
-
-static PangoModule *
-find_or_create_module (const char *raw_path)
-{
- PangoModule *module;
- char *path;
-
-#if defined(G_OS_WIN32) && defined(LIBDIR)
- if (strncmp (raw_path,
- LIBDIR "/pango/" MODULE_VERSION "/modules/",
- strlen (LIBDIR "/pango/" MODULE_VERSION "/modules/")) == 0)
- {
- /* This is an entry put there by make install on the
- * packager's system. On Windows a prebuilt Pango
- * package can be installed in a random
- * location. The pango.modules file distributed in
- * such a package contains paths from the package
- * builder's machine. Replace the path with the real
- * one on this machine. */
- path =
- g_strconcat (pango_get_lib_subdirectory (),
- "\\" MODULE_VERSION "\\modules\\",
- raw_path + strlen (LIBDIR "/pango/" MODULE_VERSION "/modules/"),
- NULL);
- }
- else
-#endif
- {
- path = g_strdup (raw_path);
- }
-
- module = g_hash_table_lookup (dlloaded_modules, path);
- if (module)
- g_free (path);
- else
- {
- module = g_object_new (PANGO_TYPE_MODULE, NULL);
- module->path = path;
- g_hash_table_insert (dlloaded_modules, path, module);
- }
-
- return module;
-}
-
-static PangoScript
-script_from_string (const char *str)
-{
- static GEnumClass *class = NULL;
- GEnumValue *value;
- if (g_once_init_enter (&class))
- g_once_init_leave (&class, g_type_class_ref (PANGO_TYPE_SCRIPT));
-
- value = g_enum_get_value_by_nick (class, str);
- if (!value)
- return PANGO_SCRIPT_INVALID_CODE;
-
- return value->value;
-}
-
-static void
-script_info_free (PangoEngineScriptInfo *script_info,
- gpointer data G_GNUC_UNUSED)
-{
- g_slice_free (PangoEngineScriptInfo, script_info);
-}
-
-static gboolean /* Returns true if succeeded, false if failed */
-process_module_file (FILE *module_file, const gchar *module_file_dir)
-{
- GString *line_buf = g_string_new (NULL);
- GString *tmp_buf = g_string_new (NULL);
- gboolean have_error = FALSE;
-
- while (pango_read_line (module_file, line_buf))
- {
- PangoEnginePair *pair = g_slice_new (PangoEnginePair);
- PangoEngineScriptInfo *script_info;
- PangoScript script;
- GList *scripts = NULL;
- GList *tmp_list;
-
- const char *p;
- char *q;
- int i;
-
- p = line_buf->str;
-
- if (!pango_skip_space (&p))
- {
- g_slice_free (PangoEnginePair, pair);
- continue;
- }
-
- i = 0;
- while (1)
- {
- if (!pango_scan_string (&p, tmp_buf))
- {
- have_error = TRUE;
- goto error;
- }
-
- switch (i)
- {
- case 0:
- if (!g_path_is_absolute (tmp_buf->str)
-#ifdef __APPLE__
- && strncmp (tmp_buf->str, "@executable_path/", 17)
- && strncmp (tmp_buf->str, "@loader_path/", 13)
- && strncmp (tmp_buf->str, "@rpath/", 7)
-#endif
- )
- {
- const gchar *lib_dir = pango_get_lib_subdirectory ();
- const gchar *abs_file_name = g_build_filename (lib_dir,
- MODULE_VERSION,
- "modules",
- tmp_buf->str,
- NULL);
- g_string_assign (tmp_buf, abs_file_name);
- g_free ((gpointer) abs_file_name);
- }
- pair->module = find_or_create_module (tmp_buf->str);
- break;
- case 1:
- pair->info.id = g_strdup (tmp_buf->str);
- break;
- case 2:
- pair->info.engine_type = g_strdup (tmp_buf->str);
- break;
- case 3:
- pair->info.render_type = g_strdup (tmp_buf->str);
- break;
- default:
- q = strchr (tmp_buf->str, ':');
- if (!q)
- {
- have_error = TRUE;
- goto error;
- }
- *q = '\0';
- script = script_from_string (tmp_buf->str);
- if (script == PANGO_SCRIPT_INVALID_CODE)
- {
- have_error = TRUE;
- goto error;
- }
-
- script_info = g_slice_new (PangoEngineScriptInfo);
- script_info->script = script;
- script_info->langs = g_strdup (q + 1);
-
- scripts = g_list_prepend (scripts, script_info);
- }
-
- if (!pango_skip_space (&p))
- break;
-
- i++;
- }
-
- if (i<3)
- {
- have_error = TRUE;
- goto error;
- }
-
- scripts = g_list_reverse (scripts);
- pair->info.n_scripts = g_list_length (scripts);
- pair->info.scripts = g_new (PangoEngineScriptInfo, pair->info.n_scripts);
-
- tmp_list = scripts;
- for (i=0; i<pair->info.n_scripts; i++)
- {
- pair->info.scripts[i] = *(PangoEngineScriptInfo *)tmp_list->data;
- tmp_list = tmp_list->next;
- }
-
- pair->engine = NULL;
-
- dlloaded_engines = g_slist_prepend (dlloaded_engines, pair);
-
- error:
- g_list_foreach (scripts, (GFunc)script_info_free, NULL);
- g_list_free (scripts);
-
- if (have_error)
- {
- g_printerr ("Error reading Pango modules file\n");
- g_slice_free(PangoEnginePair, pair);
- break;
- }
- }
-
- g_string_free (line_buf, TRUE);
- g_string_free (tmp_buf, TRUE);
-
- return !have_error;
-}
-
-static void
-read_modules (void)
-{
- FILE *module_file;
-
- char *file_str = pango_config_key_get ("Pango/ModuleFiles");
- char **files;
- int n;
-
- dlloaded_modules = g_hash_table_new (g_str_hash, g_str_equal);
-
- if (!file_str)
- {
- files = g_new (char *, 3);
-
- files[0] = g_build_filename (pango_get_sysconf_subdirectory (),
- "pango.modules",
- NULL);
- files[1] = g_build_filename (pango_get_lib_subdirectory (),
- MODULE_VERSION,
- "modules.cache",
- NULL);
- files[2] = NULL;
- }
- else
- files = pango_split_file_list (file_str);
-
- n = 0;
- while (files[n])
- n++;
-
- while (n-- > 0)
- {
- module_file = g_fopen (files[n], "r");
- if (module_file)
- {
- const gchar *module_file_dir = g_path_get_dirname (files[n]);
- process_module_file (module_file, module_file_dir);
- g_free ((gpointer) module_file_dir);
- fclose(module_file);
- }
- }
-
- g_strfreev (files);
- g_free (file_str);
-
- dlloaded_engines = g_slist_reverse (dlloaded_engines);
-}
-
-static void
-init_modules (void)
-{
- static gsize init = 0;
- int i;
-
- if (g_once_init_enter (&init))
- {
-#if !GLIB_CHECK_VERSION (2, 35, 3)
- /* Make sure that the type system is initialized */
- g_type_init ();
-#endif
-
- for (i = 0; _pango_included_lang_modules[i].list; i++)
- pango_module_register (&_pango_included_lang_modules[i]);
- read_modules ();
-
- g_once_init_leave (&init, 1);
- }
-}
-
-static void
-map_add_engine (PangoMapInfo *info,
- PangoEnginePair *pair)
-{
- PangoMap *map = info->map;
- int i;
-
- for (i=0; i<pair->info.n_scripts; i++)
- {
- PangoScript script;
- PangoMapEntry *entry;
- gboolean is_exact = FALSE;
-
- if (pair->info.scripts[i].langs)
- {
- if (pango_language_matches (info->language, pair->info.scripts[i].langs))
- is_exact = TRUE;
- }
-
- script = pair->info.scripts[i].script;
- if ((guint)script >= map->entries->len)
- g_array_set_size (map->entries, script + 1);
-
- entry = &g_array_index (map->entries, PangoMapEntry, script);
-
- if (is_exact)
- entry->exact = g_slist_prepend (entry->exact, pair);
- else
- entry->fallback = g_slist_prepend (entry->fallback, pair);
- }
-}
-
-static void
-map_add_engine_list (PangoMapInfo *info,
- GSList *engines,
- const char *engine_type,
- const char *render_type)
-{
- GSList *tmp_list = engines;
-
- while (tmp_list)
- {
- PangoEnginePair *pair = tmp_list->data;
- tmp_list = tmp_list->next;
-
- if (strcmp (pair->info.engine_type, engine_type) == 0 &&
- strcmp (pair->info.render_type, render_type) == 0)
- {
- map_add_engine (info, pair);
- }
- }
-}
-
-static void
-build_map (PangoMapInfo *info)
-{
- const char *engine_type = g_quark_to_string (info->engine_type_id);
- const char *render_type = g_quark_to_string (info->render_type_id);
-
- init_modules();
-
- if (!dlloaded_engines && !registered_engines)
- {
- static gboolean no_module_warning = FALSE; /* MT-safe */
- if (!no_module_warning)
- {
- gchar *filename = g_build_filename (pango_get_sysconf_subdirectory (),
- "pango.modules",
- NULL);
- g_critical ("No modules found:\n"
- "No builtin or dynamically loaded modules were found.\n"
- "PangoFc will not work correctly.\n"
- "This probably means there was an error in the creation of:\n"
- " '%s'\n"
- "You should create this file by running:\n"
- " pango-querymodules > '%s'",
- filename,
- filename);
- g_free (filename);
-
- no_module_warning = TRUE;
- }
- }
-
- info->map = g_slice_new (PangoMap);
- info->map->entries = g_array_new (FALSE, TRUE, sizeof (PangoMapEntry));
-
- map_add_engine_list (info, dlloaded_engines, engine_type, render_type);
- map_add_engine_list (info, registered_engines, engine_type, render_type);
+ return NULL;
}
/**
@@ -732,51 +56,17 @@ build_map (PangoMapInfo *info)
* @map: a #PangoMap
* @script: a #PangoScript
*
- * Returns the best engine listed in the map for a given script
+ * Do not use. Does not do anything.
+ *
+ * Return value: %NULL.
*
- * Return value: (nullable): the best engine, if one is listed for the
- * script, or %NULL. The lookup may cause the engine to be loaded;
- * once an engine is loaded, it won't be unloaded. If multiple
- * engines are exact for the script, the choice of which is
- * returned is arbitrary.
+ * Deprecated: 1.37
**/
PangoEngine *
-pango_map_get_engine (PangoMap *map,
- PangoScript script)
-{
- PangoMapEntry *entry = NULL;
- PangoMapEntry *common_entry = NULL;
-
- if ((guint)script < map->entries->len)
- entry = &g_array_index (map->entries, PangoMapEntry, script);
-
- if (PANGO_SCRIPT_COMMON < map->entries->len)
- common_entry = &g_array_index (map->entries, PangoMapEntry, PANGO_SCRIPT_COMMON);
-
- if (entry && entry->exact)
- return pango_engine_pair_get_engine (entry->exact->data);
- else if (common_entry && common_entry->exact)
- return pango_engine_pair_get_engine (common_entry->exact->data);
- else if (entry && entry->fallback)
- return pango_engine_pair_get_engine (entry->fallback->data);
- else if (common_entry && common_entry->fallback)
- return pango_engine_pair_get_engine (common_entry->fallback->data);
- else
- return NULL;
-}
-
-static void
-append_engines (GSList **engine_list,
- GSList *pair_list)
+pango_map_get_engine (PangoMap *map G_GNUC_UNUSED,
+ PangoScript script G_GNUC_UNUSED)
{
- GSList *l;
-
- for (l = pair_list; l; l = l->next)
- {
- PangoEngine *engine = pango_engine_pair_get_engine (l->data);
- if (engine)
- *engine_list = g_slist_append (*engine_list, engine);
- }
+ return NULL;
}
/**
@@ -788,63 +78,32 @@ append_engines (GSList **engine_list,
* @fallback_engines: location to store list of engines that approximately
* handle this script.
*
- * Finds engines in the map that handle the given script. The returned
- * lists should be freed with g_slist_free, but the engines in the
- * lists are owned by GLib and will be kept around permanently, so
- * they should not be unref'ed.
+ * Do not use. Does not do anything.
*
* Since: 1.4
+ * Deprecated: 1.37
**/
void
-pango_map_get_engines (PangoMap *map,
- PangoScript script,
+pango_map_get_engines (PangoMap *map G_GNUC_UNUSED,
+ PangoScript script G_GNUC_UNUSED,
GSList **exact_engines,
GSList **fallback_engines)
{
- PangoMapEntry *entry = NULL;
- PangoMapEntry *common_entry = NULL;
-
- if ((guint)script < map->entries->len)
- entry = &g_array_index (map->entries, PangoMapEntry, script);
-
- if (PANGO_SCRIPT_COMMON < map->entries->len)
- common_entry = &g_array_index (map->entries, PangoMapEntry, PANGO_SCRIPT_COMMON);
-
if (exact_engines)
- {
- *exact_engines = NULL;
- if (entry && entry->exact)
- append_engines (exact_engines, entry->exact);
- else if (common_entry && common_entry->exact)
- append_engines (exact_engines, common_entry->exact);
- }
-
+ *exact_engines = NULL;
if (fallback_engines)
- {
- *fallback_engines = NULL;
- if (entry && entry->fallback)
- append_engines (fallback_engines, entry->fallback);
- else if (common_entry && common_entry->fallback)
- append_engines (fallback_engines, common_entry->fallback);
- }
+ *fallback_engines = NULL;
}
/**
* pango_module_register:
* @module: a #PangoIncludedModule
*
- * Registers a statically linked module with Pango. The
- * #PangoIncludedModule structure that is passed in contains the
- * functions that would otherwise be loaded from a dynamically loaded
- * module.
+ * Do not use. Does not do anything.
+ *
+ * Deprecated: 1.37
**/
void
-pango_module_register (PangoIncludedModule *module)
+pango_module_register (PangoIncludedModule *module G_GNUC_UNUSED)
{
- GSList *tmp_list = NULL;
-
- handle_included_module (module, &tmp_list);
-
- registered_engines = g_slist_concat (registered_engines,
- g_slist_reverse (tmp_list));
}