gstreamer_core/gst/gsterror.c
changeset 0 0e761a78d257
child 8 4a7fac7dd34a
equal deleted inserted replaced
-1:000000000000 0:0e761a78d257
       
     1 /* GStreamer
       
     2  * Copyright (C) <2003> David A. Schleef <ds@schleef.org>
       
     3  *
       
     4  * This library is free software; you can redistribute it and/or
       
     5  * modify it under the terms of the GNU Library General Public
       
     6  * License as published by the Free Software Foundation; either
       
     7  * version 2 of the License, or (at your option) any later version.
       
     8  *
       
     9  * This library is distributed in the hope that it will be useful,
       
    10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
       
    11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
       
    12  * Library General Public License for more details.
       
    13  *
       
    14  * You should have received a copy of the GNU Library General Public
       
    15  * License along with this library; if not, write to the
       
    16  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
       
    17  * Boston, MA 02111-1307, USA.
       
    18  */
       
    19 
       
    20 /**
       
    21  * SECTION:gsterror
       
    22  * @short_description: Categorized error messages
       
    23  * @see_also: #GstMessage
       
    24  *
       
    25  * GStreamer elements can throw non-fatal warnings and fatal errors.
       
    26  * Higher-level elements and applications can programatically filter
       
    27  * the ones they are interested in or can recover from,
       
    28  * and have a default handler handle the rest of them.
       
    29  *
       
    30  * The rest of this section will use the term <quote>error</quote>
       
    31  * to mean both (non-fatal) warnings and (fatal) errors; they are treated
       
    32  * similarly.
       
    33  *
       
    34  * Errors from elements are the combination of a #GError and a debug string.
       
    35  * The #GError contains:
       
    36  * - a domain type: CORE, LIBRARY, RESOURCE or STREAM
       
    37  * - a code: an enum value specific to the domain
       
    38  * - a translated, human-readable message
       
    39  * - a non-translated additional debug string, which also contains
       
    40  * - file and line information
       
    41  *
       
    42  * Elements do not have the context required to decide what to do with
       
    43  * errors.  As such, they should only inform about errors, and stop their
       
    44  * processing.  In short, an element doesn't know what it is being used for.
       
    45  *
       
    46  * It is the application or compound element using the given element that
       
    47  * has more context about the use of the element. Errors can be received by
       
    48  * listening to the #GstBus of the element/pipeline for #GstMessage objects with
       
    49  * the type %GST_MESSAGE_ERROR or %GST_MESSAGE_WARNING. The thrown errors should
       
    50  * be inspected, and filtered if appropriate.
       
    51  *
       
    52  * An application is expected to, by default, present the user with a
       
    53  * dialog box (or an equivalent) showing the error message.  The dialog
       
    54  * should also allow a way to get at the additional debug information,
       
    55  * so the user can provide bug reporting information.
       
    56  *
       
    57  * A compound element is expected to forward errors by default higher up
       
    58  * the hierarchy; this is done by default in the same way as for other types
       
    59  * of #GstMessage.
       
    60  *
       
    61  * When applications or compound elements trigger errors that they can
       
    62  * recover from, they can filter out these errors and take appropriate action.
       
    63  * For example, an application that gets an error from xvimagesink
       
    64  * that indicates all XVideo ports are taken, the application can attempt
       
    65  * to use another sink instead.
       
    66  *
       
    67  * Elements throw errors using the #GST_ELEMENT_ERROR convenience macro:
       
    68  *
       
    69  * <example>
       
    70  * <title>Throwing an error</title>
       
    71  *   <programlisting>
       
    72  *     GST_ELEMENT_ERROR (src, RESOURCE, NOT_FOUND,
       
    73  *       (_("No file name specified for reading.")), (NULL));
       
    74  *   </programlisting>
       
    75  * </example>
       
    76  *
       
    77  * Things to keep in mind:
       
    78  * <itemizedlist>
       
    79  *   <listitem><para>Don't go off inventing new error codes.  The ones
       
    80  *     currently provided should be enough.  If you find your type of error
       
    81  *     does not fit the current codes, you should use FAILED.</para></listitem>
       
    82  *   <listitem><para>Don't provide a message if the default one suffices.
       
    83  *     this keeps messages more uniform.  Use (NULL) - not forgetting the
       
    84  *     parentheses.</para></listitem>
       
    85  *   <listitem><para>If you do supply a custom message, it should be
       
    86  *     marked for translation.  The message should start with a capital
       
    87  *     and end with a period.  The message should describe the error in short,
       
    88  *     in a human-readable form, and without any complex technical terms.
       
    89  *     A user interface will present this message as the first thing a user
       
    90  *     sees.  Details, technical info, ... should go in the debug string.
       
    91  *   </para></listitem>
       
    92  *   <listitem><para>The debug string can be as you like.  Again, use (NULL)
       
    93  *     if there's nothing to add - file and line number will still be
       
    94  *     passed.  #GST_ERROR_SYSTEM can be used as a shortcut to give
       
    95  *     debug information on a system call error.</para></listitem>
       
    96  * </itemizedlist>
       
    97  *
       
    98  * Last reviewed on 2006-09-15 (0.10.10)
       
    99  */
       
   100 
       
   101 #ifdef HAVE_CONFIG_H
       
   102 #include "config.h"
       
   103 #endif
       
   104 
       
   105 #include "gst_private.h"
       
   106 #include <gst/gst.h>
       
   107 #include "gst-i18n-lib.h"
       
   108 
       
   109 #define TABLE(t, d, a, b) t[GST_ ## d ## _ERROR_ ## a] = g_strdup (b)
       
   110 #define QUARK_FUNC(string)                                              \
       
   111 __declspec(dllexport)	GQuark gst_ ## string ## _error_quark (void) {                          \
       
   112   static GQuark quark;                                                  \
       
   113   if (!quark)                                                           \
       
   114     quark = g_quark_from_static_string ("gst-" # string "-error-quark"); \
       
   115   return quark; }
       
   116 #ifdef __SYMBIAN32__
       
   117 EXPORT_C
       
   118 #endif
       
   119 
       
   120 
       
   121 GType
       
   122 gst_g_error_get_type (void)
       
   123 {
       
   124   static GType type = 0;
       
   125 
       
   126   if (G_UNLIKELY (type == 0))
       
   127     type = g_boxed_type_register_static ("GstGError",
       
   128         (GBoxedCopyFunc) g_error_copy, (GBoxedFreeFunc) g_error_free);
       
   129   return type;
       
   130 }
       
   131 
       
   132 #define FILE_A_BUG "  Please file a bug at " PACKAGE_BUGREPORT "."
       
   133 
       
   134 /* initialize the dynamic table of translated core errors */
       
   135 static gchar **
       
   136 _gst_core_errors_init (void)
       
   137 {
       
   138   gchar **t = NULL;
       
   139 
       
   140   t = g_new0 (gchar *, GST_CORE_ERROR_NUM_ERRORS);
       
   141 
       
   142   TABLE (t, CORE, FAILED,
       
   143       N_("GStreamer encountered a general core library error."));
       
   144   TABLE (t, CORE, TOO_LAZY,
       
   145       N_("GStreamer developers were too lazy to assign an error code "
       
   146           "to this error." FILE_A_BUG));
       
   147   TABLE (t, CORE, NOT_IMPLEMENTED,
       
   148       N_("Internal GStreamer error: code not implemented." FILE_A_BUG));
       
   149   TABLE (t, CORE, STATE_CHANGE,
       
   150       N_("Internal GStreamer error: state change failed." FILE_A_BUG));
       
   151   TABLE (t, CORE, PAD, N_("Internal GStreamer error: pad problem." FILE_A_BUG));
       
   152   TABLE (t, CORE, THREAD,
       
   153       N_("Internal GStreamer error: thread problem." FILE_A_BUG));
       
   154   TABLE (t, CORE, NEGOTIATION,
       
   155       N_("Internal GStreamer error: negotiation problem." FILE_A_BUG));
       
   156   TABLE (t, CORE, EVENT,
       
   157       N_("Internal GStreamer error: event problem." FILE_A_BUG));
       
   158   TABLE (t, CORE, SEEK,
       
   159       N_("Internal GStreamer error: seek problem." FILE_A_BUG));
       
   160   TABLE (t, CORE, CAPS,
       
   161       N_("Internal GStreamer error: caps problem." FILE_A_BUG));
       
   162   TABLE (t, CORE, TAG, N_("Internal GStreamer error: tag problem." FILE_A_BUG));
       
   163   TABLE (t, CORE, MISSING_PLUGIN,
       
   164       N_("Your GStreamer installation is missing a plug-in."));
       
   165   TABLE (t, CORE, CLOCK,
       
   166       N_("Internal GStreamer error: clock problem." FILE_A_BUG));
       
   167   TABLE (t, CORE, DISABLED,
       
   168       N_("This application is trying to use GStreamer functionality that "
       
   169           "has been disabled."));
       
   170 
       
   171   return t;
       
   172 }
       
   173 
       
   174 /* initialize the dynamic table of translated library errors */
       
   175 static gchar **
       
   176 _gst_library_errors_init (void)
       
   177 {
       
   178   gchar **t = NULL;
       
   179 
       
   180   t = g_new0 (gchar *, GST_LIBRARY_ERROR_NUM_ERRORS);
       
   181 
       
   182   TABLE (t, LIBRARY, FAILED,
       
   183       N_("GStreamer encountered a general supporting library error."));
       
   184   TABLE (t, LIBRARY, TOO_LAZY,
       
   185       N_("GStreamer developers were too lazy to assign an error code "
       
   186           "to this error." FILE_A_BUG));
       
   187   TABLE (t, LIBRARY, INIT, N_("Could not initialize supporting library."));
       
   188   TABLE (t, LIBRARY, SHUTDOWN, N_("Could not close supporting library."));
       
   189   TABLE (t, LIBRARY, SETTINGS, N_("Could not configure supporting library."));
       
   190 
       
   191   return t;
       
   192 }
       
   193 
       
   194 /* initialize the dynamic table of translated resource errors */
       
   195 static gchar **
       
   196 _gst_resource_errors_init (void)
       
   197 {
       
   198   gchar **t = NULL;
       
   199 
       
   200   t = g_new0 (gchar *, GST_RESOURCE_ERROR_NUM_ERRORS);
       
   201 
       
   202   TABLE (t, RESOURCE, FAILED,
       
   203       N_("GStreamer encountered a general resource error."));
       
   204   TABLE (t, RESOURCE, TOO_LAZY,
       
   205       N_("GStreamer developers were too lazy to assign an error code "
       
   206           "to this error." FILE_A_BUG));
       
   207   TABLE (t, RESOURCE, NOT_FOUND, N_("Resource not found."));
       
   208   TABLE (t, RESOURCE, BUSY, N_("Resource busy or not available."));
       
   209   TABLE (t, RESOURCE, OPEN_READ, N_("Could not open resource for reading."));
       
   210   TABLE (t, RESOURCE, OPEN_WRITE, N_("Could not open resource for writing."));
       
   211   TABLE (t, RESOURCE, OPEN_READ_WRITE,
       
   212       N_("Could not open resource for reading and writing."));
       
   213   TABLE (t, RESOURCE, CLOSE, N_("Could not close resource."));
       
   214   TABLE (t, RESOURCE, READ, N_("Could not read from resource."));
       
   215   TABLE (t, RESOURCE, WRITE, N_("Could not write to resource."));
       
   216   TABLE (t, RESOURCE, SEEK, N_("Could not perform seek on resource."));
       
   217   TABLE (t, RESOURCE, SYNC, N_("Could not synchronize on resource."));
       
   218   TABLE (t, RESOURCE, SETTINGS,
       
   219       N_("Could not get/set settings from/on resource."));
       
   220   TABLE (t, RESOURCE, NO_SPACE_LEFT, N_("No space left on the resource."));
       
   221 
       
   222   return t;
       
   223 }
       
   224 
       
   225 /* initialize the dynamic table of translated stream errors */
       
   226 static gchar **
       
   227 _gst_stream_errors_init (void)
       
   228 {
       
   229   gchar **t = NULL;
       
   230 
       
   231   t = g_new0 (gchar *, GST_STREAM_ERROR_NUM_ERRORS);
       
   232 
       
   233   TABLE (t, STREAM, FAILED,
       
   234       N_("GStreamer encountered a general stream error."));
       
   235   TABLE (t, STREAM, TOO_LAZY,
       
   236       N_("GStreamer developers were too lazy to assign an error code "
       
   237           "to this error." FILE_A_BUG));
       
   238   TABLE (t, STREAM, NOT_IMPLEMENTED,
       
   239       N_("Element doesn't implement handling of this stream. "
       
   240           "Please file a bug."));
       
   241   TABLE (t, STREAM, TYPE_NOT_FOUND, N_("Could not determine type of stream."));
       
   242   TABLE (t, STREAM, WRONG_TYPE,
       
   243       N_("The stream is of a different type than handled by this element."));
       
   244   TABLE (t, STREAM, CODEC_NOT_FOUND,
       
   245       N_("There is no codec present that can handle the stream's type."));
       
   246   TABLE (t, STREAM, DECODE, N_("Could not decode stream."));
       
   247   TABLE (t, STREAM, ENCODE, N_("Could not encode stream."));
       
   248   TABLE (t, STREAM, DEMUX, N_("Could not demultiplex stream."));
       
   249   TABLE (t, STREAM, MUX, N_("Could not multiplex stream."));
       
   250   TABLE (t, STREAM, FORMAT, N_("The stream is in the wrong format."));
       
   251 
       
   252   return t;
       
   253 }
       
   254 
       
   255 QUARK_FUNC (core);
       
   256 QUARK_FUNC (library);
       
   257 QUARK_FUNC (resource);
       
   258 QUARK_FUNC (stream);
       
   259 
       
   260 /**
       
   261  * gst_error_get_message:
       
   262  * @domain: the GStreamer error domain this error belongs to.
       
   263  * @code: the error code belonging to the domain.
       
   264  *
       
   265  * Get a string describing the error message in the current locale.
       
   266  *
       
   267  * Returns: a newly allocated string describing the error message in the
       
   268  * current locale.
       
   269  */
       
   270 #ifdef __SYMBIAN32__
       
   271 EXPORT_C
       
   272 #endif
       
   273 
       
   274 gchar *
       
   275 gst_error_get_message (GQuark domain, gint code)
       
   276 {
       
   277   static gchar **gst_core_errors = NULL;
       
   278   static gchar **gst_library_errors = NULL;
       
   279   static gchar **gst_resource_errors = NULL;
       
   280   static gchar **gst_stream_errors = NULL;
       
   281 
       
   282   gchar *message = NULL;
       
   283 
       
   284   /* initialize error message tables if necessary */
       
   285   if (gst_core_errors == NULL)
       
   286     gst_core_errors = _gst_core_errors_init ();
       
   287   if (gst_library_errors == NULL)
       
   288     gst_library_errors = _gst_library_errors_init ();
       
   289   if (gst_resource_errors == NULL)
       
   290     gst_resource_errors = _gst_resource_errors_init ();
       
   291   if (gst_stream_errors == NULL)
       
   292     gst_stream_errors = _gst_stream_errors_init ();
       
   293 
       
   294 
       
   295   if (domain == GST_CORE_ERROR)
       
   296     message = gst_core_errors[code];
       
   297   else if (domain == GST_LIBRARY_ERROR)
       
   298     message = gst_library_errors[code];
       
   299   else if (domain == GST_RESOURCE_ERROR)
       
   300     message = gst_resource_errors[code];
       
   301   else if (domain == GST_STREAM_ERROR)
       
   302     message = gst_stream_errors[code];
       
   303   else {
       
   304     g_warning ("No error messages for domain %s", g_quark_to_string (domain));
       
   305     return g_strdup_printf (_("No error message for domain %s."),
       
   306         g_quark_to_string (domain));
       
   307   }
       
   308   if (message)
       
   309     return g_strdup (_(message));
       
   310   else
       
   311     return
       
   312         g_strdup_printf (_
       
   313         ("No standard error message for domain %s and code %d."),
       
   314         g_quark_to_string (domain), code);
       
   315 }