Coverage Report

Created: 2025-10-10 07:05

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/glib/glib/gmessages.c
Line
Count
Source
1
/* GLIB - Library of useful routines for C programming
2
 * Copyright (C) 1995-1997  Peter Mattis, Spencer Kimball and Josh MacDonald
3
 *
4
 * This library is free software; you can redistribute it and/or
5
 * modify it under the terms of the GNU Lesser General Public
6
 * License as published by the Free Software Foundation; either
7
 * version 2.1 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
 * Lesser General Public License for more details.
13
 *
14
 * You should have received a copy of the GNU Lesser General Public
15
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
16
 */
17
18
/*
19
 * Modified by the GLib Team and others 1997-2000.  See the AUTHORS
20
 * file for a list of people on the GLib Team.  See the ChangeLog
21
 * files for a list of changes.  These files are distributed with
22
 * GLib at ftp://ftp.gtk.org/pub/gtk/.
23
 */
24
25
/*
26
 * MT safe
27
 */
28
29
/**
30
 * SECTION:messages
31
 * @Title: Message Output and Debugging Functions
32
 * @Short_description: functions to output messages and help debug applications
33
 *
34
 * These functions provide support for outputting messages.
35
 *
36
 * The g_return family of macros (g_return_if_fail(),
37
 * g_return_val_if_fail(), g_return_if_reached(),
38
 * g_return_val_if_reached()) should only be used for programming
39
 * errors, a typical use case is checking for invalid parameters at
40
 * the beginning of a public function. They should not be used if
41
 * you just mean "if (error) return", they should only be used if
42
 * you mean "if (bug in program) return". The program behavior is
43
 * generally considered undefined after one of these checks fails.
44
 * They are not intended for normal control flow, only to give a
45
 * perhaps-helpful warning before giving up.
46
 *
47
 * Structured logging output is supported using g_log_structured(). This differs
48
 * from the traditional g_log() API in that log messages are handled as a
49
 * collection of key–value pairs representing individual pieces of information,
50
 * rather than as a single string containing all the information in an arbitrary
51
 * format.
52
 *
53
 * The convenience macros g_info(), g_message(), g_debug(), g_warning() and g_error()
54
 * will use the traditional g_log() API unless you define the symbol
55
 * %G_LOG_USE_STRUCTURED before including `glib.h`. But note that even messages
56
 * logged through the traditional g_log() API are ultimatively passed to
57
 * g_log_structured(), so that all log messages end up in same destination.
58
 * If %G_LOG_USE_STRUCTURED is defined, g_test_expect_message() will become
59
 * ineffective for the wrapper macros g_warning() and friends (see
60
 * [Testing for Messages][testing-for-messages]).
61
 *
62
 * The support for structured logging was motivated by the following needs (some
63
 * of which were supported previously; others weren’t):
64
 *  * Support for multiple logging levels.
65
 *  * Structured log support with the ability to add `MESSAGE_ID`s (see
66
 *    g_log_structured()).
67
 *  * Moving the responsibility for filtering log messages from the program to
68
 *    the log viewer — instead of libraries and programs installing log handlers
69
 *    (with g_log_set_handler()) which filter messages before output, all log
70
 *    messages are outputted, and the log viewer program (such as `journalctl`)
71
 *    must filter them. This is based on the idea that bugs are sometimes hard
72
 *    to reproduce, so it is better to log everything possible and then use
73
 *    tools to analyse the logs than it is to not be able to reproduce a bug to
74
 *    get additional log data. Code which uses logging in performance-critical
75
 *    sections should compile out the g_log_structured() calls in
76
 *    release builds, and compile them in in debugging builds.
77
 *  * A single writer function which handles all log messages in a process, from
78
 *    all libraries and program code; rather than multiple log handlers with
79
 *    poorly defined interactions between them. This allows a program to easily
80
 *    change its logging policy by changing the writer function, for example to
81
 *    log to an additional location or to change what logging output fallbacks
82
 *    are used. The log writer functions provided by GLib are exposed publicly
83
 *    so they can be used from programs’ log writers. This allows log writer
84
 *    policy and implementation to be kept separate.
85
 *  * If a library wants to add standard information to all of its log messages
86
 *    (such as library state) or to redact private data (such as passwords or
87
 *    network credentials), it should use a wrapper function around its
88
 *    g_log_structured() calls or implement that in the single log writer
89
 *    function.
90
 *  * If a program wants to pass context data from a g_log_structured() call to
91
 *    its log writer function so that, for example, it can use the correct
92
 *    server connection to submit logs to, that user data can be passed as a
93
 *    zero-length #GLogField to g_log_structured_array().
94
 *  * Color output needed to be supported on the terminal, to make reading
95
 *    through logs easier.
96
 *
97
 * ## Using Structured Logging ## {#using-structured-logging}
98
 *
99
 * To use structured logging (rather than the old-style logging), either use
100
 * the g_log_structured() and g_log_structured_array() functions; or define
101
 * `G_LOG_USE_STRUCTURED` before including any GLib header, and use the
102
 * g_message(), g_debug(), g_error() (etc.) macros.
103
 *
104
 * You do not need to define `G_LOG_USE_STRUCTURED` to use g_log_structured(),
105
 * but it is a good idea to avoid confusion.
106
 *
107
 * ## Log Domains ## {#log-domains}
108
 *
109
 * Log domains may be used to broadly split up the origins of log messages.
110
 * Typically, there are one or a few log domains per application or library.
111
 * %G_LOG_DOMAIN should be used to define the default log domain for the current
112
 * compilation unit — it is typically defined at the top of a source file, or in
113
 * the preprocessor flags for a group of source files.
114
 *
115
 * Log domains must be unique, and it is recommended that they are the
116
 * application or library name, optionally followed by a hyphen and a sub-domain
117
 * name. For example, `bloatpad` or `bloatpad-io`.
118
 *
119
 * ## Debug Message Output ## {#debug-message-output}
120
 *
121
 * The default log functions (g_log_default_handler() for the old-style API and
122
 * g_log_writer_default() for the structured API) both drop debug and
123
 * informational messages by default, unless the log domains of those messages
124
 * are listed in the `G_MESSAGES_DEBUG` environment variable (or it is set to
125
 * `all`).
126
 *
127
 * It is recommended that custom log writer functions re-use the
128
 * `G_MESSAGES_DEBUG` environment variable, rather than inventing a custom one,
129
 * so that developers can re-use the same debugging techniques and tools across
130
 * projects. Since GLib 2.68, this can be implemented by dropping messages
131
 * for which g_log_writer_default_would_drop() returns %TRUE.
132
 *
133
 * ## Testing for Messages ## {#testing-for-messages}
134
 *
135
 * With the old g_log() API, g_test_expect_message() and
136
 * g_test_assert_expected_messages() could be used in simple cases to check
137
 * whether some code under test had emitted a given log message. These
138
 * functions have been deprecated with the structured logging API, for several
139
 * reasons:
140
 *  * They relied on an internal queue which was too inflexible for many use
141
 *    cases, where messages might be emitted in several orders, some
142
 *    messages might not be emitted deterministically, or messages might be
143
 *    emitted by unrelated log domains.
144
 *  * They do not support structured log fields.
145
 *  * Examining the log output of code is a bad approach to testing it, and
146
 *    while it might be necessary for legacy code which uses g_log(), it should
147
 *    be avoided for new code using g_log_structured().
148
 *
149
 * They will continue to work as before if g_log() is in use (and
150
 * %G_LOG_USE_STRUCTURED is not defined). They will do nothing if used with the
151
 * structured logging API.
152
 *
153
 * Examining the log output of code is discouraged: libraries should not emit to
154
 * `stderr` during defined behaviour, and hence this should not be tested. If
155
 * the log emissions of a library during undefined behaviour need to be tested,
156
 * they should be limited to asserting that the library aborts and prints a
157
 * suitable error message before aborting. This should be done with
158
 * g_test_trap_assert_stderr().
159
 *
160
 * If it is really necessary to test the structured log messages emitted by a
161
 * particular piece of code – and the code cannot be restructured to be more
162
 * suitable to more conventional unit testing – you should write a custom log
163
 * writer function (see g_log_set_writer_func()) which appends all log messages
164
 * to a queue. When you want to check the log messages, examine and clear the
165
 * queue, ignoring irrelevant log messages (for example, from log domains other
166
 * than the one under test).
167
 */
168
169
#include "config.h"
170
171
#include <stdlib.h>
172
#include <stdarg.h>
173
#include <stdio.h>
174
#include <string.h>
175
#include <signal.h>
176
#include <locale.h>
177
#include <errno.h>
178
179
#if defined(__linux__) && !defined(__BIONIC__)
180
#include <sys/types.h>
181
#include <sys/socket.h>
182
#include <sys/un.h>
183
#include <fcntl.h>
184
#include <sys/uio.h>
185
#endif
186
187
#include "glib-init.h"
188
#include "galloca.h"
189
#include "gbacktrace.h"
190
#include "gcharset.h"
191
#include "gconvert.h"
192
#include "genviron.h"
193
#include "gmain.h"
194
#include "gmem.h"
195
#include "gprintfint.h"
196
#include "gtestutils.h"
197
#include "gthread.h"
198
#include "gstrfuncs.h"
199
#include "gstring.h"
200
#include "gpattern.h"
201
#include "gthreadprivate.h"
202
203
#ifdef G_OS_UNIX
204
#include <unistd.h>
205
#endif
206
207
#ifdef G_OS_WIN32
208
#include <process.h>    /* For getpid() */
209
#include <io.h>
210
#  include <windows.h>
211
212
#ifndef ENABLE_VIRTUAL_TERMINAL_PROCESSING
213
#define ENABLE_VIRTUAL_TERMINAL_PROCESSING 0x0004
214
#endif
215
216
#if defined (_MSC_VER) && (_MSC_VER >=1400)
217
/* This is ugly, but we need it for isatty() in case we have bad fd's,
218
 * otherwise Windows will abort() the program on msvcrt80.dll and later
219
 */
220
#include <crtdbg.h>
221
222
_GLIB_EXTERN void
223
myInvalidParameterHandler(const wchar_t *expression,
224
                          const wchar_t *function,
225
                          const wchar_t *file,
226
                          unsigned int   line,
227
                          uintptr_t      pReserved)
228
{
229
}
230
#endif
231
232
#include "gwin32.h"
233
#endif
234
235
/**
236
 * G_LOG_DOMAIN:
237
 *
238
 * Defines the log domain. See [Log Domains](#log-domains).
239
 *
240
 * Libraries should define this so that any messages
241
 * which they log can be differentiated from messages from other
242
 * libraries and application code. But be careful not to define
243
 * it in any public header files.
244
 *
245
 * Log domains must be unique, and it is recommended that they are the
246
 * application or library name, optionally followed by a hyphen and a sub-domain
247
 * name. For example, `bloatpad` or `bloatpad-io`.
248
 *
249
 * If undefined, it defaults to the default %NULL (or `""`) log domain; this is
250
 * not advisable, as it cannot be filtered against using the `G_MESSAGES_DEBUG`
251
 * environment variable.
252
 *
253
 * For example, GTK+ uses this in its `Makefile.am`:
254
 * |[
255
 * AM_CPPFLAGS = -DG_LOG_DOMAIN=\"Gtk\"
256
 * ]|
257
 *
258
 * Applications can choose to leave it as the default %NULL (or `""`)
259
 * domain. However, defining the domain offers the same advantages as
260
 * above.
261
 *
262
263
 */
264
265
/**
266
 * G_LOG_FATAL_MASK:
267
 *
268
 * GLib log levels that are considered fatal by default.
269
 *
270
 * This is not used if structured logging is enabled; see
271
 * [Using Structured Logging][using-structured-logging].
272
 */
273
274
/**
275
 * GLogFunc:
276
 * @log_domain: the log domain of the message
277
 * @log_level: the log level of the message (including the
278
 *     fatal and recursion flags)
279
 * @message: the message to process
280
 * @user_data: user data, set in g_log_set_handler()
281
 *
282
 * Specifies the prototype of log handler functions.
283
 *
284
 * The default log handler, g_log_default_handler(), automatically appends a
285
 * new-line character to @message when printing it. It is advised that any
286
 * custom log handler functions behave similarly, so that logging calls in user
287
 * code do not need modifying to add a new-line character to the message if the
288
 * log handler is changed.
289
 *
290
 * This is not used if structured logging is enabled; see
291
 * [Using Structured Logging][using-structured-logging].
292
 */
293
294
/**
295
 * GLogLevelFlags:
296
 * @G_LOG_FLAG_RECURSION: internal flag
297
 * @G_LOG_FLAG_FATAL: internal flag
298
 * @G_LOG_LEVEL_ERROR: log level for errors, see g_error().
299
 *     This level is also used for messages produced by g_assert().
300
 * @G_LOG_LEVEL_CRITICAL: log level for critical warning messages, see
301
 *     g_critical().
302
 *     This level is also used for messages produced by g_return_if_fail()
303
 *     and g_return_val_if_fail().
304
 * @G_LOG_LEVEL_WARNING: log level for warnings, see g_warning()
305
 * @G_LOG_LEVEL_MESSAGE: log level for messages, see g_message()
306
 * @G_LOG_LEVEL_INFO: log level for informational messages, see g_info()
307
 * @G_LOG_LEVEL_DEBUG: log level for debug messages, see g_debug()
308
 * @G_LOG_LEVEL_MASK: a mask including all log levels
309
 *
310
 * Flags specifying the level of log messages.
311
 *
312
 * It is possible to change how GLib treats messages of the various
313
 * levels using g_log_set_handler() and g_log_set_fatal_mask().
314
 */
315
316
/**
317
 * G_LOG_LEVEL_USER_SHIFT:
318
 *
319
 * Log levels below 1<<G_LOG_LEVEL_USER_SHIFT are used by GLib.
320
 * Higher bits can be used for user-defined log levels.
321
 */
322
323
/**
324
 * g_message:
325
 * @...: format string, followed by parameters to insert
326
 *     into the format string (as with printf())
327
 *
328
 * A convenience function/macro to log a normal message.
329
 *
330
 * If g_log_default_handler() is used as the log handler function, a new-line
331
 * character will automatically be appended to @..., and need not be entered
332
 * manually.
333
 *
334
 * If structured logging is enabled, this will use g_log_structured();
335
 * otherwise it will use g_log(). See
336
 * [Using Structured Logging][using-structured-logging].
337
 */
338
339
/**
340
 * g_warning:
341
 * @...: format string, followed by parameters to insert
342
 *     into the format string (as with printf())
343
 *
344
 * A convenience function/macro to log a warning message. The message should
345
 * typically *not* be translated to the user's language.
346
 *
347
 * This is not intended for end user error reporting. Use of #GError is
348
 * preferred for that instead, as it allows calling functions to perform actions
349
 * conditional on the type of error.
350
 *
351
 * Warning messages are intended to be used in the event of unexpected
352
 * external conditions (system misconfiguration, missing files,
353
 * other trusted programs violating protocol, invalid contents in
354
 * trusted files, etc.)
355
 *
356
 * If attempting to deal with programmer errors (for example, incorrect function
357
 * parameters) then you should use %G_LOG_LEVEL_CRITICAL instead.
358
 *
359
 * g_warn_if_reached() and g_warn_if_fail() log at %G_LOG_LEVEL_WARNING.
360
 *
361
 * You can make warnings fatal at runtime by setting the `G_DEBUG`
362
 * environment variable (see
363
 * [Running GLib Applications](glib-running.html)):
364
 *
365
 * |[
366
 *   G_DEBUG=fatal-warnings gdb ./my-program
367
 * ]|
368
 *
369
 * Any unrelated failures can be skipped over in
370
 * [gdb](https://www.gnu.org/software/gdb/) using the `continue` command.
371
 *
372
 * If g_log_default_handler() is used as the log handler function,
373
 * a newline character will automatically be appended to @..., and
374
 * need not be entered manually.
375
 *
376
 * If structured logging is enabled, this will use g_log_structured();
377
 * otherwise it will use g_log(). See
378
 * [Using Structured Logging][using-structured-logging].
379
 */
380
381
/**
382
 * g_critical:
383
 * @...: format string, followed by parameters to insert
384
 *     into the format string (as with printf())
385
 *
386
 * Logs a "critical warning" (#G_LOG_LEVEL_CRITICAL).
387
 *
388
 * Critical warnings are intended to be used in the event of an error
389
 * that originated in the current process (a programmer error).
390
 * Logging of a critical error is by definition an indication of a bug
391
 * somewhere in the current program (or its libraries).
392
 *
393
 * g_return_if_fail(), g_return_val_if_fail(), g_return_if_reached() and
394
 * g_return_val_if_reached() log at %G_LOG_LEVEL_CRITICAL.
395
 *
396
 * You can make critical warnings fatal at runtime by
397
 * setting the `G_DEBUG` environment variable (see
398
 * [Running GLib Applications](glib-running.html)):
399
 *
400
 * |[
401
 *   G_DEBUG=fatal-warnings gdb ./my-program
402
 * ]|
403
 *
404
 * You can also use g_log_set_always_fatal().
405
 *
406
 * Any unrelated failures can be skipped over in
407
 * [gdb](https://www.gnu.org/software/gdb/) using the `continue` command.
408
 *
409
 * The message should typically *not* be translated to the
410
 * user's language.
411
 *
412
 * If g_log_default_handler() is used as the log handler function, a new-line
413
 * character will automatically be appended to @..., and need not be entered
414
 * manually.
415
 *
416
 * If structured logging is enabled, this will use g_log_structured();
417
 * otherwise it will use g_log(). See
418
 * [Using Structured Logging][using-structured-logging].
419
 */
420
421
/**
422
 * g_error:
423
 * @...: format string, followed by parameters to insert
424
 *     into the format string (as with printf())
425
 *
426
 * A convenience function/macro to log an error message. The message should
427
 * typically *not* be translated to the user's language.
428
 *
429
 * This is not intended for end user error reporting. Use of #GError is
430
 * preferred for that instead, as it allows calling functions to perform actions
431
 * conditional on the type of error.
432
 *
433
 * Error messages are always fatal, resulting in a call to G_BREAKPOINT()
434
 * to terminate the application. This function will
435
 * result in a core dump; don't use it for errors you expect.
436
 * Using this function indicates a bug in your program, i.e.
437
 * an assertion failure.
438
 *
439
 * If g_log_default_handler() is used as the log handler function, a new-line
440
 * character will automatically be appended to @..., and need not be entered
441
 * manually.
442
 *
443
 * If structured logging is enabled, this will use g_log_structured();
444
 * otherwise it will use g_log(). See
445
 * [Using Structured Logging][using-structured-logging].
446
 */
447
448
/**
449
 * g_info:
450
 * @...: format string, followed by parameters to insert
451
 *     into the format string (as with printf())
452
 *
453
 * A convenience function/macro to log an informational message. Seldom used.
454
 *
455
 * If g_log_default_handler() is used as the log handler function, a new-line
456
 * character will automatically be appended to @..., and need not be entered
457
 * manually.
458
 *
459
 * Such messages are suppressed by the g_log_default_handler() and
460
 * g_log_writer_default() unless the `G_MESSAGES_DEBUG` environment variable is
461
 * set appropriately.
462
 *
463
 * If structured logging is enabled, this will use g_log_structured();
464
 * otherwise it will use g_log(). See
465
 * [Using Structured Logging][using-structured-logging].
466
 *
467
 * Since: 2.40
468
 */
469
470
/**
471
 * g_debug:
472
 * @...: format string, followed by parameters to insert
473
 *     into the format string (as with printf())
474
 *
475
 * A convenience function/macro to log a debug message. The message should
476
 * typically *not* be translated to the user's language.
477
 *
478
 * If g_log_default_handler() is used as the log handler function, a new-line
479
 * character will automatically be appended to @..., and need not be entered
480
 * manually.
481
 *
482
 * Such messages are suppressed by the g_log_default_handler() and
483
 * g_log_writer_default() unless the `G_MESSAGES_DEBUG` environment variable is
484
 * set appropriately.
485
 *
486
 * If structured logging is enabled, this will use g_log_structured();
487
 * otherwise it will use g_log(). See
488
 * [Using Structured Logging][using-structured-logging].
489
 *
490
 * Since: 2.6
491
 */
492
493
/* --- structures --- */
494
typedef struct _GLogDomain  GLogDomain;
495
typedef struct _GLogHandler GLogHandler;
496
struct _GLogDomain
497
{
498
  gchar   *log_domain;
499
  GLogLevelFlags fatal_mask;
500
  GLogHandler *handlers;
501
  GLogDomain  *next;
502
};
503
struct _GLogHandler
504
{
505
  guint    id;
506
  GLogLevelFlags log_level;
507
  GLogFunc   log_func;
508
  gpointer   data;
509
  GDestroyNotify destroy;
510
  GLogHandler *next;
511
};
512
513
514
/* --- variables --- */
515
static GMutex         g_messages_lock;
516
static GLogDomain    *g_log_domains = NULL;
517
static GPrintFunc     glib_print_func = NULL;
518
static GPrintFunc     glib_printerr_func = NULL;
519
static GPrivate       g_log_depth;
520
static GPrivate       g_log_structured_depth;
521
static GLogFunc       default_log_func = g_log_default_handler;
522
static gpointer       default_log_data = NULL;
523
static GTestLogFatalFunc fatal_log_func = NULL;
524
static gpointer          fatal_log_data;
525
static GLogWriterFunc log_writer_func = g_log_writer_default;
526
static gpointer       log_writer_user_data = NULL;
527
static GDestroyNotify log_writer_user_data_free = NULL;
528
529
/* --- functions --- */
530
531
static void _g_log_abort (gboolean breakpoint);
532
533
static void
534
_g_log_abort (gboolean breakpoint)
535
0
{
536
0
  gboolean debugger_present;
537
538
0
  if (g_test_subprocess ())
539
0
    {
540
      /* If this is a test case subprocess then it probably caused
541
       * this error message on purpose, so just exit() rather than
542
       * abort()ing, to avoid triggering any system crash-reporting
543
       * daemon.
544
       */
545
0
      _exit (1);
546
0
    }
547
548
#ifdef G_OS_WIN32
549
  debugger_present = IsDebuggerPresent ();
550
#else
551
  /* Assume GDB is attached. */
552
0
  debugger_present = TRUE;
553
0
#endif /* !G_OS_WIN32 */
554
555
0
  if (debugger_present && breakpoint)
556
0
    G_BREAKPOINT ();
557
0
  else
558
0
    g_abort ();
559
0
}
560
561
#ifdef G_OS_WIN32
562
static gboolean win32_keep_fatal_message = FALSE;
563
564
/* This default message will usually be overwritten. */
565
/* Yes, a fixed size buffer is bad. So sue me. But g_error() is never
566
 * called with huge strings, is it?
567
 */
568
static gchar  fatal_msg_buf[1000] = "Unspecified fatal error encountered, aborting.";
569
static gchar *fatal_msg_ptr = fatal_msg_buf;
570
571
#undef write
572
static inline int
573
dowrite (int          fd,
574
   const void  *buf,
575
   unsigned int len)
576
{
577
  if (win32_keep_fatal_message)
578
    {
579
      memcpy (fatal_msg_ptr, buf, len);
580
      fatal_msg_ptr += len;
581
      *fatal_msg_ptr = 0;
582
      return len;
583
    }
584
585
  write (fd, buf, len);
586
587
  return len;
588
}
589
#define write(fd, buf, len) dowrite(fd, buf, len)
590
591
#endif
592
593
static void
594
write_string (FILE        *stream,
595
        const gchar *string)
596
0
{
597
0
  fputs (string, stream);
598
0
}
599
600
static void
601
write_string_sized (FILE        *stream,
602
                    const gchar *string,
603
                    gssize       length)
604
0
{
605
  /* Is it nul-terminated? */
606
0
  if (length < 0)
607
0
    write_string (stream, string);
608
0
  else
609
0
    fwrite (string, 1, length, stream);
610
0
}
611
612
static GLogDomain*
613
g_log_find_domain_L (const gchar *log_domain)
614
3.98M
{
615
3.98M
  GLogDomain *domain;
616
  
617
3.98M
  domain = g_log_domains;
618
3.98M
  while (domain)
619
0
    {
620
0
      if (strcmp (domain->log_domain, log_domain) == 0)
621
0
  return domain;
622
0
      domain = domain->next;
623
0
    }
624
3.98M
  return NULL;
625
3.98M
}
626
627
static GLogDomain*
628
g_log_domain_new_L (const gchar *log_domain)
629
0
{
630
0
  GLogDomain *domain;
631
632
0
  domain = g_new (GLogDomain, 1);
633
0
  domain->log_domain = g_strdup (log_domain);
634
0
  domain->fatal_mask = G_LOG_FATAL_MASK;
635
0
  domain->handlers = NULL;
636
  
637
0
  domain->next = g_log_domains;
638
0
  g_log_domains = domain;
639
  
640
0
  return domain;
641
0
}
642
643
static void
644
g_log_domain_check_free_L (GLogDomain *domain)
645
0
{
646
0
  if (domain->fatal_mask == G_LOG_FATAL_MASK &&
647
0
      domain->handlers == NULL)
648
0
    {
649
0
      GLogDomain *last, *work;
650
      
651
0
      last = NULL;  
652
653
0
      work = g_log_domains;
654
0
      while (work)
655
0
  {
656
0
    if (work == domain)
657
0
      {
658
0
        if (last)
659
0
    last->next = domain->next;
660
0
        else
661
0
    g_log_domains = domain->next;
662
0
        g_free (domain->log_domain);
663
0
        g_free (domain);
664
0
        break;
665
0
      }
666
0
    last = work;
667
0
    work = last->next;
668
0
  }  
669
0
    }
670
0
}
671
672
static GLogFunc
673
g_log_domain_get_handler_L (GLogDomain  *domain,
674
          GLogLevelFlags log_level,
675
          gpointer  *data)
676
3.98M
{
677
3.98M
  if (domain && log_level)
678
0
    {
679
0
      GLogHandler *handler;
680
      
681
0
      handler = domain->handlers;
682
0
      while (handler)
683
0
  {
684
0
    if ((handler->log_level & log_level) == log_level)
685
0
      {
686
0
        *data = handler->data;
687
0
        return handler->log_func;
688
0
      }
689
0
    handler = handler->next;
690
0
  }
691
0
    }
692
693
3.98M
  *data = default_log_data;
694
3.98M
  return default_log_func;
695
3.98M
}
696
697
/**
698
 * g_log_set_always_fatal:
699
 * @fatal_mask: the mask containing bits set for each level
700
 *     of error which is to be fatal
701
 *
702
 * Sets the message levels which are always fatal, in any log domain.
703
 * When a message with any of these levels is logged the program terminates.
704
 * You can only set the levels defined by GLib to be fatal.
705
 * %G_LOG_LEVEL_ERROR is always fatal.
706
 *
707
 * You can also make some message levels fatal at runtime by setting
708
 * the `G_DEBUG` environment variable (see
709
 * [Running GLib Applications](glib-running.html)).
710
 *
711
 * Libraries should not call this function, as it affects all messages logged
712
 * by a process, including those from other libraries.
713
 *
714
 * Structured log messages (using g_log_structured() and
715
 * g_log_structured_array()) are fatal only if the default log writer is used;
716
 * otherwise it is up to the writer function to determine which log messages
717
 * are fatal. See [Using Structured Logging][using-structured-logging].
718
 *
719
 * Returns: the old fatal mask
720
 */
721
GLogLevelFlags
722
g_log_set_always_fatal (GLogLevelFlags fatal_mask)
723
0
{
724
0
  GLogLevelFlags old_mask;
725
726
  /* restrict the global mask to levels that are known to glib
727
   * since this setting applies to all domains
728
   */
729
0
  fatal_mask &= (1 << G_LOG_LEVEL_USER_SHIFT) - 1;
730
  /* force errors to be fatal */
731
0
  fatal_mask |= G_LOG_LEVEL_ERROR;
732
  /* remove bogus flag */
733
0
  fatal_mask &= ~G_LOG_FLAG_FATAL;
734
735
0
  g_mutex_lock (&g_messages_lock);
736
0
  old_mask = g_log_always_fatal;
737
0
  g_log_always_fatal = fatal_mask;
738
0
  g_mutex_unlock (&g_messages_lock);
739
740
0
  return old_mask;
741
0
}
742
743
/**
744
 * g_log_set_fatal_mask:
745
 * @log_domain: the log domain
746
 * @fatal_mask: the new fatal mask
747
 *
748
 * Sets the log levels which are fatal in the given domain.
749
 * %G_LOG_LEVEL_ERROR is always fatal.
750
 *
751
 * This has no effect on structured log messages (using g_log_structured() or
752
 * g_log_structured_array()). To change the fatal behaviour for specific log
753
 * messages, programs must install a custom log writer function using
754
 * g_log_set_writer_func(). See
755
 * [Using Structured Logging][using-structured-logging].
756
 *
757
 * This function is mostly intended to be used with
758
 * %G_LOG_LEVEL_CRITICAL.  You should typically not set
759
 * %G_LOG_LEVEL_WARNING, %G_LOG_LEVEL_MESSAGE, %G_LOG_LEVEL_INFO or
760
 * %G_LOG_LEVEL_DEBUG as fatal except inside of test programs.
761
 *
762
 * Returns: the old fatal mask for the log domain
763
 */
764
GLogLevelFlags
765
g_log_set_fatal_mask (const gchar   *log_domain,
766
          GLogLevelFlags fatal_mask)
767
0
{
768
0
  GLogLevelFlags old_flags;
769
0
  GLogDomain *domain;
770
  
771
0
  if (!log_domain)
772
0
    log_domain = "";
773
774
  /* force errors to be fatal */
775
0
  fatal_mask |= G_LOG_LEVEL_ERROR;
776
  /* remove bogus flag */
777
0
  fatal_mask &= ~G_LOG_FLAG_FATAL;
778
  
779
0
  g_mutex_lock (&g_messages_lock);
780
781
0
  domain = g_log_find_domain_L (log_domain);
782
0
  if (!domain)
783
0
    domain = g_log_domain_new_L (log_domain);
784
0
  old_flags = domain->fatal_mask;
785
  
786
0
  domain->fatal_mask = fatal_mask;
787
0
  g_log_domain_check_free_L (domain);
788
789
0
  g_mutex_unlock (&g_messages_lock);
790
791
0
  return old_flags;
792
0
}
793
794
/**
795
 * g_log_set_handler:
796
 * @log_domain: (nullable): the log domain, or %NULL for the default ""
797
 *     application domain
798
 * @log_levels: the log levels to apply the log handler for.
799
 *     To handle fatal and recursive messages as well, combine
800
 *     the log levels with the #G_LOG_FLAG_FATAL and
801
 *     #G_LOG_FLAG_RECURSION bit flags.
802
 * @log_func: the log handler function
803
 * @user_data: data passed to the log handler
804
 *
805
 * Sets the log handler for a domain and a set of log levels.
806
 * To handle fatal and recursive messages the @log_levels parameter
807
 * must be combined with the #G_LOG_FLAG_FATAL and #G_LOG_FLAG_RECURSION
808
 * bit flags.
809
 *
810
 * Note that since the #G_LOG_LEVEL_ERROR log level is always fatal, if
811
 * you want to set a handler for this log level you must combine it with
812
 * #G_LOG_FLAG_FATAL.
813
 *
814
 * This has no effect if structured logging is enabled; see
815
 * [Using Structured Logging][using-structured-logging].
816
 *
817
 * Here is an example for adding a log handler for all warning messages
818
 * in the default domain:
819
 * |[<!-- language="C" --> 
820
 * g_log_set_handler (NULL, G_LOG_LEVEL_WARNING | G_LOG_FLAG_FATAL
821
 *                    | G_LOG_FLAG_RECURSION, my_log_handler, NULL);
822
 * ]|
823
 *
824
 * This example adds a log handler for all critical messages from GTK+:
825
 * |[<!-- language="C" --> 
826
 * g_log_set_handler ("Gtk", G_LOG_LEVEL_CRITICAL | G_LOG_FLAG_FATAL
827
 *                    | G_LOG_FLAG_RECURSION, my_log_handler, NULL);
828
 * ]|
829
 *
830
 * This example adds a log handler for all messages from GLib:
831
 * |[<!-- language="C" --> 
832
 * g_log_set_handler ("GLib", G_LOG_LEVEL_MASK | G_LOG_FLAG_FATAL
833
 *                    | G_LOG_FLAG_RECURSION, my_log_handler, NULL);
834
 * ]|
835
 *
836
 * Returns: the id of the new handler
837
 */
838
guint
839
g_log_set_handler (const gchar   *log_domain,
840
                   GLogLevelFlags log_levels,
841
                   GLogFunc       log_func,
842
                   gpointer       user_data)
843
0
{
844
0
  return g_log_set_handler_full (log_domain, log_levels, log_func, user_data, NULL);
845
0
}
846
847
/**
848
 * g_log_set_handler_full: (rename-to g_log_set_handler)
849
 * @log_domain: (nullable): the log domain, or %NULL for the default ""
850
 *     application domain
851
 * @log_levels: the log levels to apply the log handler for.
852
 *     To handle fatal and recursive messages as well, combine
853
 *     the log levels with the #G_LOG_FLAG_FATAL and
854
 *     #G_LOG_FLAG_RECURSION bit flags.
855
 * @log_func: the log handler function
856
 * @user_data: data passed to the log handler
857
 * @destroy: destroy notify for @user_data, or %NULL
858
 *
859
 * Like g_log_set_handler(), but takes a destroy notify for the @user_data.
860
 *
861
 * This has no effect if structured logging is enabled; see
862
 * [Using Structured Logging][using-structured-logging].
863
 *
864
 * Returns: the id of the new handler
865
 *
866
 * Since: 2.46
867
 */
868
guint
869
g_log_set_handler_full (const gchar    *log_domain,
870
                        GLogLevelFlags  log_levels,
871
                        GLogFunc        log_func,
872
                        gpointer        user_data,
873
                        GDestroyNotify  destroy)
874
0
{
875
0
  static guint handler_id = 0;
876
0
  GLogDomain *domain;
877
0
  GLogHandler *handler;
878
  
879
0
  g_return_val_if_fail ((log_levels & G_LOG_LEVEL_MASK) != 0, 0);
880
0
  g_return_val_if_fail (log_func != NULL, 0);
881
  
882
0
  if (!log_domain)
883
0
    log_domain = "";
884
885
0
  handler = g_new (GLogHandler, 1);
886
887
0
  g_mutex_lock (&g_messages_lock);
888
889
0
  domain = g_log_find_domain_L (log_domain);
890
0
  if (!domain)
891
0
    domain = g_log_domain_new_L (log_domain);
892
  
893
0
  handler->id = ++handler_id;
894
0
  handler->log_level = log_levels;
895
0
  handler->log_func = log_func;
896
0
  handler->data = user_data;
897
0
  handler->destroy = destroy;
898
0
  handler->next = domain->handlers;
899
0
  domain->handlers = handler;
900
901
0
  g_mutex_unlock (&g_messages_lock);
902
  
903
0
  return handler_id;
904
0
}
905
906
/**
907
 * g_log_set_default_handler:
908
 * @log_func: the log handler function
909
 * @user_data: data passed to the log handler
910
 *
911
 * Installs a default log handler which is used if no
912
 * log handler has been set for the particular log domain
913
 * and log level combination. By default, GLib uses
914
 * g_log_default_handler() as default log handler.
915
 *
916
 * This has no effect if structured logging is enabled; see
917
 * [Using Structured Logging][using-structured-logging].
918
 *
919
 * Returns: the previous default log handler
920
 *
921
 * Since: 2.6
922
 */
923
GLogFunc
924
g_log_set_default_handler (GLogFunc log_func,
925
         gpointer user_data)
926
0
{
927
0
  GLogFunc old_log_func;
928
  
929
0
  g_mutex_lock (&g_messages_lock);
930
0
  old_log_func = default_log_func;
931
0
  default_log_func = log_func;
932
0
  default_log_data = user_data;
933
0
  g_mutex_unlock (&g_messages_lock);
934
  
935
0
  return old_log_func;
936
0
}
937
938
/**
939
 * g_test_log_set_fatal_handler:
940
 * @log_func: the log handler function.
941
 * @user_data: data passed to the log handler.
942
 *
943
 * Installs a non-error fatal log handler which can be
944
 * used to decide whether log messages which are counted
945
 * as fatal abort the program.
946
 *
947
 * The use case here is that you are running a test case
948
 * that depends on particular libraries or circumstances
949
 * and cannot prevent certain known critical or warning
950
 * messages. So you install a handler that compares the
951
 * domain and message to precisely not abort in such a case.
952
 *
953
 * Note that the handler is reset at the beginning of
954
 * any test case, so you have to set it inside each test
955
 * function which needs the special behavior.
956
 *
957
 * This handler has no effect on g_error messages.
958
 *
959
 * This handler also has no effect on structured log messages (using
960
 * g_log_structured() or g_log_structured_array()). To change the fatal
961
 * behaviour for specific log messages, programs must install a custom log
962
 * writer function using g_log_set_writer_func().See
963
 * [Using Structured Logging][using-structured-logging].
964
 *
965
 * Since: 2.22
966
 **/
967
void
968
g_test_log_set_fatal_handler (GTestLogFatalFunc log_func,
969
                              gpointer          user_data)
970
0
{
971
0
  g_mutex_lock (&g_messages_lock);
972
0
  fatal_log_func = log_func;
973
0
  fatal_log_data = user_data;
974
0
  g_mutex_unlock (&g_messages_lock);
975
0
}
976
977
/**
978
 * g_log_remove_handler:
979
 * @log_domain: the log domain
980
 * @handler_id: the id of the handler, which was returned
981
 *     in g_log_set_handler()
982
 *
983
 * Removes the log handler.
984
 *
985
 * This has no effect if structured logging is enabled; see
986
 * [Using Structured Logging][using-structured-logging].
987
 */
988
void
989
g_log_remove_handler (const gchar *log_domain,
990
          guint    handler_id)
991
0
{
992
0
  GLogDomain *domain;
993
  
994
0
  g_return_if_fail (handler_id > 0);
995
  
996
0
  if (!log_domain)
997
0
    log_domain = "";
998
  
999
0
  g_mutex_lock (&g_messages_lock);
1000
0
  domain = g_log_find_domain_L (log_domain);
1001
0
  if (domain)
1002
0
    {
1003
0
      GLogHandler *work, *last;
1004
      
1005
0
      last = NULL;
1006
0
      work = domain->handlers;
1007
0
      while (work)
1008
0
  {
1009
0
    if (work->id == handler_id)
1010
0
      {
1011
0
        if (last)
1012
0
    last->next = work->next;
1013
0
        else
1014
0
    domain->handlers = work->next;
1015
0
        g_log_domain_check_free_L (domain); 
1016
0
        g_mutex_unlock (&g_messages_lock);
1017
0
              if (work->destroy)
1018
0
                work->destroy (work->data);
1019
0
        g_free (work);
1020
0
        return;
1021
0
      }
1022
0
    last = work;
1023
0
    work = last->next;
1024
0
  }
1025
0
    } 
1026
0
  g_mutex_unlock (&g_messages_lock);
1027
0
  g_warning ("%s: could not find handler with id '%d' for domain \"%s\"",
1028
0
       G_STRLOC, handler_id, log_domain);
1029
0
}
1030
1031
2.05M
#define CHAR_IS_SAFE(wc) (!((wc < 0x20 && wc != '\t' && wc != '\n' && wc != '\r') || \
1032
2.05M
          (wc == 0x7f) || \
1033
2.05M
          (wc >= 0x80 && wc < 0xa0)))
1034
     
1035
static gchar*
1036
strdup_convert (const gchar *string,
1037
    const gchar *charset)
1038
33.9k
{
1039
33.9k
  if (!g_utf8_validate (string, -1, NULL))
1040
0
    {
1041
0
      GString *gstring = g_string_new ("[Invalid UTF-8] ");
1042
0
      guchar *p;
1043
1044
0
      for (p = (guchar *)string; *p; p++)
1045
0
  {
1046
0
    if (CHAR_IS_SAFE(*p) &&
1047
0
        !(*p == '\r' && *(p + 1) != '\n') &&
1048
0
        *p < 0x80)
1049
0
      g_string_append_c (gstring, *p);
1050
0
    else
1051
0
      g_string_append_printf (gstring, "\\x%02x", (guint)(guchar)*p);
1052
0
  }
1053
      
1054
0
      return g_string_free (gstring, FALSE);
1055
0
    }
1056
33.9k
  else
1057
33.9k
    {
1058
33.9k
      GError *err = NULL;
1059
      
1060
33.9k
      gchar *result = g_convert_with_fallback (string, -1, charset, "UTF-8", "?", NULL, NULL, &err);
1061
33.9k
      if (result)
1062
33.9k
  return result;
1063
0
      else
1064
0
  {
1065
    /* Not thread-safe, but doesn't matter if we print the warning twice
1066
     */
1067
0
    static gboolean warned = FALSE; 
1068
0
    if (!warned)
1069
0
      {
1070
0
        warned = TRUE;
1071
0
        _g_fprintf (stderr, "GLib: Cannot convert message: %s\n", err->message);
1072
0
      }
1073
0
    g_error_free (err);
1074
    
1075
0
    return g_strdup (string);
1076
0
  }
1077
33.9k
    }
1078
33.9k
}
1079
1080
/* For a radix of 8 we need at most 3 output bytes for 1 input
1081
 * byte. Additionally we might need up to 2 output bytes for the
1082
 * readix prefix and 1 byte for the trailing NULL.
1083
 */
1084
0
#define FORMAT_UNSIGNED_BUFSIZE ((GLIB_SIZEOF_LONG * 3) + 3)
1085
1086
static void
1087
format_unsigned (gchar  *buf,
1088
     gulong  num,
1089
     guint   radix)
1090
0
{
1091
0
  gulong tmp;
1092
0
  gchar c;
1093
0
  gint i, n;
1094
1095
  /* we may not call _any_ GLib functions here (or macros like g_return_if_fail()) */
1096
1097
0
  if (radix != 8 && radix != 10 && radix != 16)
1098
0
    {
1099
0
      *buf = '\000';
1100
0
      return;
1101
0
    }
1102
  
1103
0
  if (!num)
1104
0
    {
1105
0
      *buf++ = '0';
1106
0
      *buf = '\000';
1107
0
      return;
1108
0
    } 
1109
  
1110
0
  if (radix == 16)
1111
0
    {
1112
0
      *buf++ = '0';
1113
0
      *buf++ = 'x';
1114
0
    }
1115
0
  else if (radix == 8)
1116
0
    {
1117
0
      *buf++ = '0';
1118
0
    }
1119
  
1120
0
  n = 0;
1121
0
  tmp = num;
1122
0
  while (tmp)
1123
0
    {
1124
0
      tmp /= radix;
1125
0
      n++;
1126
0
    }
1127
1128
0
  i = n;
1129
1130
  /* Again we can't use g_assert; actually this check should _never_ fail. */
1131
0
  if (n > FORMAT_UNSIGNED_BUFSIZE - 3)
1132
0
    {
1133
0
      *buf = '\000';
1134
0
      return;
1135
0
    }
1136
1137
0
  while (num)
1138
0
    {
1139
0
      i--;
1140
0
      c = (num % radix);
1141
0
      if (c < 10)
1142
0
  buf[i] = c + '0';
1143
0
      else
1144
0
  buf[i] = c + 'a' - 10;
1145
0
      num /= radix;
1146
0
    }
1147
  
1148
0
  buf[n] = '\000';
1149
0
}
1150
1151
/* string size big enough to hold level prefix */
1152
#define STRING_BUFFER_SIZE  (FORMAT_UNSIGNED_BUFSIZE + 32)
1153
1154
67.8k
#define ALERT_LEVELS    (G_LOG_LEVEL_ERROR | G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_WARNING)
1155
1156
/* these are emitted by the default log handler */
1157
3.98M
#define DEFAULT_LEVELS (G_LOG_LEVEL_ERROR | G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_WARNING | G_LOG_LEVEL_MESSAGE)
1158
/* these are filtered by G_MESSAGES_DEBUG by the default log handler */
1159
3.94M
#define INFO_LEVELS (G_LOG_LEVEL_INFO | G_LOG_LEVEL_DEBUG)
1160
1161
static const gchar *log_level_to_color (GLogLevelFlags log_level,
1162
                                        gboolean       use_color);
1163
static const gchar *color_reset        (gboolean       use_color);
1164
1165
static gboolean gmessages_use_stderr = FALSE;
1166
1167
/**
1168
 * g_log_writer_default_set_use_stderr:
1169
 * @use_stderr: If %TRUE, use `stderr` for log messages that would
1170
 *  normally have appeared on `stdout`
1171
 *
1172
 * Configure whether the built-in log functions
1173
 * (g_log_default_handler() for the old-style API, and both
1174
 * g_log_writer_default() and g_log_writer_standard_streams() for the
1175
 * structured API) will output all log messages to `stderr`.
1176
 *
1177
 * By default, log messages of levels %G_LOG_LEVEL_INFO and
1178
 * %G_LOG_LEVEL_DEBUG are sent to `stdout`, and other log messages are
1179
 * sent to `stderr`. This is problematic for applications that intend
1180
 * to reserve `stdout` for structured output such as JSON or XML.
1181
 *
1182
 * This function sets global state. It is not thread-aware, and should be
1183
 * called at the very start of a program, before creating any other threads
1184
 * or creating objects that could create worker threads of their own.
1185
 *
1186
 * Since: 2.68
1187
 */
1188
void
1189
g_log_writer_default_set_use_stderr (gboolean use_stderr)
1190
0
{
1191
0
  g_return_if_fail (g_thread_n_created () == 0);
1192
0
  gmessages_use_stderr = use_stderr;
1193
0
}
1194
1195
static FILE *
1196
mklevel_prefix (gchar          level_prefix[STRING_BUFFER_SIZE],
1197
                GLogLevelFlags log_level,
1198
                gboolean       use_color)
1199
33.9k
{
1200
33.9k
  gboolean to_stdout = !gmessages_use_stderr;
1201
1202
  /* we may not call _any_ GLib functions here */
1203
1204
33.9k
  strcpy (level_prefix, log_level_to_color (log_level, use_color));
1205
1206
33.9k
  switch (log_level & G_LOG_LEVEL_MASK)
1207
33.9k
    {
1208
0
    case G_LOG_LEVEL_ERROR:
1209
0
      strcat (level_prefix, "ERROR");
1210
0
      to_stdout = FALSE;
1211
0
      break;
1212
4
    case G_LOG_LEVEL_CRITICAL:
1213
4
      strcat (level_prefix, "CRITICAL");
1214
4
      to_stdout = FALSE;
1215
4
      break;
1216
33.9k
    case G_LOG_LEVEL_WARNING:
1217
33.9k
      strcat (level_prefix, "WARNING");
1218
33.9k
      to_stdout = FALSE;
1219
33.9k
      break;
1220
0
    case G_LOG_LEVEL_MESSAGE:
1221
0
      strcat (level_prefix, "Message");
1222
0
      to_stdout = FALSE;
1223
0
      break;
1224
0
    case G_LOG_LEVEL_INFO:
1225
0
      strcat (level_prefix, "INFO");
1226
0
      break;
1227
0
    case G_LOG_LEVEL_DEBUG:
1228
0
      strcat (level_prefix, "DEBUG");
1229
0
      break;
1230
0
    default:
1231
0
      if (log_level)
1232
0
  {
1233
0
    strcat (level_prefix, "LOG-");
1234
0
    format_unsigned (level_prefix + 4, log_level & G_LOG_LEVEL_MASK, 16);
1235
0
  }
1236
0
      else
1237
0
  strcat (level_prefix, "LOG");
1238
0
      break;
1239
33.9k
    }
1240
1241
33.9k
  strcat (level_prefix, color_reset (use_color));
1242
1243
33.9k
  if (log_level & G_LOG_FLAG_RECURSION)
1244
0
    strcat (level_prefix, " (recursed)");
1245
33.9k
  if (log_level & ALERT_LEVELS)
1246
33.9k
    strcat (level_prefix, " **");
1247
1248
#ifdef G_OS_WIN32
1249
  if ((log_level & G_LOG_FLAG_FATAL) != 0 && !g_test_initialized ())
1250
    win32_keep_fatal_message = TRUE;
1251
#endif
1252
33.9k
  return to_stdout ? stdout : stderr;
1253
33.9k
}
1254
1255
typedef struct {
1256
  gchar          *log_domain;
1257
  GLogLevelFlags  log_level;
1258
  gchar          *pattern;
1259
} GTestExpectedMessage;
1260
1261
static GSList *expected_messages = NULL;
1262
1263
/**
1264
 * g_logv:
1265
 * @log_domain: (nullable): the log domain, or %NULL for the default ""
1266
 * application domain
1267
 * @log_level: the log level
1268
 * @format: the message format. See the printf() documentation
1269
 * @args: the parameters to insert into the format string
1270
 *
1271
 * Logs an error or debugging message.
1272
 *
1273
 * If the log level has been set as fatal, G_BREAKPOINT() is called
1274
 * to terminate the program. See the documentation for G_BREAKPOINT() for
1275
 * details of the debugging options this provides.
1276
 *
1277
 * If g_log_default_handler() is used as the log handler function, a new-line
1278
 * character will automatically be appended to @..., and need not be entered
1279
 * manually.
1280
 *
1281
 * If [structured logging is enabled][using-structured-logging] this will
1282
 * output via the structured log writer function (see g_log_set_writer_func()).
1283
 */
1284
void
1285
g_logv (const gchar   *log_domain,
1286
  GLogLevelFlags log_level,
1287
  const gchar   *format,
1288
  va_list        args)
1289
3.98M
{
1290
3.98M
  gboolean was_fatal = (log_level & G_LOG_FLAG_FATAL) != 0;
1291
3.98M
  gboolean was_recursion = (log_level & G_LOG_FLAG_RECURSION) != 0;
1292
3.98M
  gchar buffer[1025], *msg, *msg_alloc = NULL;
1293
3.98M
  gint i;
1294
1295
3.98M
  log_level &= G_LOG_LEVEL_MASK;
1296
3.98M
  if (!log_level)
1297
0
    return;
1298
1299
3.98M
  if (log_level & G_LOG_FLAG_RECURSION)
1300
0
    {
1301
      /* we use a stack buffer of fixed size, since we're likely
1302
       * in an out-of-memory situation
1303
       */
1304
0
      gsize size G_GNUC_UNUSED;
1305
1306
0
      size = _g_vsnprintf (buffer, 1024, format, args);
1307
0
      msg = buffer;
1308
0
    }
1309
3.98M
  else
1310
3.98M
    msg = msg_alloc = g_strdup_vprintf (format, args);
1311
1312
3.98M
  if (expected_messages)
1313
0
    {
1314
0
      GTestExpectedMessage *expected = expected_messages->data;
1315
1316
0
      if (g_strcmp0 (expected->log_domain, log_domain) == 0 &&
1317
0
          ((log_level & expected->log_level) == expected->log_level) &&
1318
0
          g_pattern_match_simple (expected->pattern, msg))
1319
0
        {
1320
0
          expected_messages = g_slist_delete_link (expected_messages,
1321
0
                                                   expected_messages);
1322
0
          g_free (expected->log_domain);
1323
0
          g_free (expected->pattern);
1324
0
          g_free (expected);
1325
0
          g_free (msg_alloc);
1326
0
          return;
1327
0
        }
1328
0
      else if ((log_level & G_LOG_LEVEL_DEBUG) != G_LOG_LEVEL_DEBUG)
1329
0
        {
1330
0
          gchar level_prefix[STRING_BUFFER_SIZE];
1331
0
          gchar *expected_message;
1332
1333
0
          mklevel_prefix (level_prefix, expected->log_level, FALSE);
1334
0
          expected_message = g_strdup_printf ("Did not see expected message %s-%s: %s",
1335
0
                                              expected->log_domain ? expected->log_domain : "**",
1336
0
                                              level_prefix, expected->pattern);
1337
0
          g_log_default_handler (G_LOG_DOMAIN, G_LOG_LEVEL_CRITICAL, expected_message, NULL);
1338
0
          g_free (expected_message);
1339
1340
0
          log_level |= G_LOG_FLAG_FATAL;
1341
0
        }
1342
0
    }
1343
1344
7.96M
  for (i = g_bit_nth_msf (log_level, -1); i >= 0; i = g_bit_nth_msf (log_level, i))
1345
3.98M
    {
1346
3.98M
      GLogLevelFlags test_level;
1347
1348
3.98M
      test_level = 1L << i;
1349
3.98M
      if (log_level & test_level)
1350
3.98M
  {
1351
3.98M
    GLogDomain *domain;
1352
3.98M
    GLogFunc log_func;
1353
3.98M
    GLogLevelFlags domain_fatal_mask;
1354
3.98M
    gpointer data = NULL;
1355
3.98M
          gboolean masquerade_fatal = FALSE;
1356
3.98M
          guint depth;
1357
1358
3.98M
    if (was_fatal)
1359
0
      test_level |= G_LOG_FLAG_FATAL;
1360
3.98M
    if (was_recursion)
1361
0
      test_level |= G_LOG_FLAG_RECURSION;
1362
1363
    /* check recursion and lookup handler */
1364
3.98M
    g_mutex_lock (&g_messages_lock);
1365
3.98M
          depth = GPOINTER_TO_UINT (g_private_get (&g_log_depth));
1366
3.98M
    domain = g_log_find_domain_L (log_domain ? log_domain : "");
1367
3.98M
    if (depth)
1368
0
      test_level |= G_LOG_FLAG_RECURSION;
1369
3.98M
    depth++;
1370
3.98M
    domain_fatal_mask = domain ? domain->fatal_mask : G_LOG_FATAL_MASK;
1371
3.98M
    if ((domain_fatal_mask | g_log_always_fatal) & test_level)
1372
0
      test_level |= G_LOG_FLAG_FATAL;
1373
3.98M
    if (test_level & G_LOG_FLAG_RECURSION)
1374
0
      log_func = _g_log_fallback_handler;
1375
3.98M
    else
1376
3.98M
      log_func = g_log_domain_get_handler_L (domain, test_level, &data);
1377
3.98M
    domain = NULL;
1378
3.98M
    g_mutex_unlock (&g_messages_lock);
1379
1380
3.98M
    g_private_set (&g_log_depth, GUINT_TO_POINTER (depth));
1381
1382
3.98M
          log_func (log_domain, test_level, msg, data);
1383
1384
3.98M
          if ((test_level & G_LOG_FLAG_FATAL)
1385
0
              && !(test_level & G_LOG_LEVEL_ERROR))
1386
0
            {
1387
0
              masquerade_fatal = fatal_log_func
1388
0
                && !fatal_log_func (log_domain, test_level, msg, fatal_log_data);
1389
0
            }
1390
1391
3.98M
          if ((test_level & G_LOG_FLAG_FATAL) && !masquerade_fatal)
1392
0
            {
1393
              /* MessageBox is allowed on UWP apps only when building against
1394
               * the debug CRT, which will set -D_DEBUG */
1395
#if defined(G_OS_WIN32) && (defined(_DEBUG) || !defined(G_WINAPI_ONLY_APP))
1396
              if (win32_keep_fatal_message)
1397
                {
1398
                  WCHAR *wide_msg;
1399
1400
                  wide_msg = g_utf8_to_utf16 (fatal_msg_buf, -1, NULL, NULL, NULL);
1401
1402
                  MessageBoxW (NULL, wide_msg, NULL,
1403
                               MB_ICONERROR | MB_SETFOREGROUND);
1404
1405
                  g_free (wide_msg);
1406
                }
1407
#endif
1408
1409
0
              _g_log_abort (!(test_level & G_LOG_FLAG_RECURSION));
1410
0
      }
1411
    
1412
3.98M
    depth--;
1413
3.98M
    g_private_set (&g_log_depth, GUINT_TO_POINTER (depth));
1414
3.98M
  }
1415
3.98M
    }
1416
1417
3.98M
  g_free (msg_alloc);
1418
3.98M
}
1419
1420
/**
1421
 * g_log:
1422
 * @log_domain: (nullable): the log domain, usually #G_LOG_DOMAIN, or %NULL
1423
 * for the default
1424
 * @log_level: the log level, either from #GLogLevelFlags
1425
 *     or a user-defined level
1426
 * @format: the message format. See the printf() documentation
1427
 * @...: the parameters to insert into the format string
1428
 *
1429
 * Logs an error or debugging message.
1430
 *
1431
 * If the log level has been set as fatal, G_BREAKPOINT() is called
1432
 * to terminate the program. See the documentation for G_BREAKPOINT() for
1433
 * details of the debugging options this provides.
1434
 *
1435
 * If g_log_default_handler() is used as the log handler function, a new-line
1436
 * character will automatically be appended to @..., and need not be entered
1437
 * manually.
1438
 *
1439
 * If [structured logging is enabled][using-structured-logging] this will
1440
 * output via the structured log writer function (see g_log_set_writer_func()).
1441
 */
1442
void
1443
g_log (const gchar   *log_domain,
1444
       GLogLevelFlags log_level,
1445
       const gchar   *format,
1446
       ...)
1447
3.98M
{
1448
3.98M
  va_list args;
1449
  
1450
3.98M
  va_start (args, format);
1451
3.98M
  g_logv (log_domain, log_level, format, args);
1452
3.98M
  va_end (args);
1453
3.98M
}
1454
1455
/* Return value must be 1 byte long (plus nul byte).
1456
 * Reference: http://man7.org/linux/man-pages/man3/syslog.3.html#DESCRIPTION
1457
 */
1458
static const gchar *
1459
log_level_to_priority (GLogLevelFlags log_level)
1460
3.98M
{
1461
3.98M
  if (log_level & G_LOG_LEVEL_ERROR)
1462
0
    return "3";
1463
3.98M
  else if (log_level & G_LOG_LEVEL_CRITICAL)
1464
4
    return "4";
1465
3.98M
  else if (log_level & G_LOG_LEVEL_WARNING)
1466
33.9k
    return "4";
1467
3.94M
  else if (log_level & G_LOG_LEVEL_MESSAGE)
1468
0
    return "5";
1469
3.94M
  else if (log_level & G_LOG_LEVEL_INFO)
1470
0
    return "6";
1471
3.94M
  else if (log_level & G_LOG_LEVEL_DEBUG)
1472
3.94M
    return "7";
1473
1474
  /* Default to LOG_NOTICE for custom log levels. */
1475
0
  return "5";
1476
3.98M
}
1477
1478
static FILE *
1479
log_level_to_file (GLogLevelFlags log_level)
1480
33.9k
{
1481
33.9k
  if (gmessages_use_stderr)
1482
0
    return stderr;
1483
1484
33.9k
  if (log_level & (G_LOG_LEVEL_ERROR | G_LOG_LEVEL_CRITICAL |
1485
33.9k
                   G_LOG_LEVEL_WARNING | G_LOG_LEVEL_MESSAGE))
1486
33.9k
    return stderr;
1487
0
  else
1488
0
    return stdout;
1489
33.9k
}
1490
1491
static const gchar *
1492
log_level_to_color (GLogLevelFlags log_level,
1493
                    gboolean       use_color)
1494
33.9k
{
1495
  /* we may not call _any_ GLib functions here */
1496
1497
33.9k
  if (!use_color)
1498
33.9k
    return "";
1499
1500
0
  if (log_level & G_LOG_LEVEL_ERROR)
1501
0
    return "\033[1;31m"; /* red */
1502
0
  else if (log_level & G_LOG_LEVEL_CRITICAL)
1503
0
    return "\033[1;35m"; /* magenta */
1504
0
  else if (log_level & G_LOG_LEVEL_WARNING)
1505
0
    return "\033[1;33m"; /* yellow */
1506
0
  else if (log_level & G_LOG_LEVEL_MESSAGE)
1507
0
    return "\033[1;32m"; /* green */
1508
0
  else if (log_level & G_LOG_LEVEL_INFO)
1509
0
    return "\033[1;32m"; /* green */
1510
0
  else if (log_level & G_LOG_LEVEL_DEBUG)
1511
0
    return "\033[1;32m"; /* green */
1512
1513
  /* No color for custom log levels. */
1514
0
  return "";
1515
0
}
1516
1517
static const gchar *
1518
color_reset (gboolean use_color)
1519
67.8k
{
1520
  /* we may not call _any_ GLib functions here */
1521
1522
67.8k
  if (!use_color)
1523
67.8k
    return "";
1524
1525
0
  return "\033[0m";
1526
67.8k
}
1527
1528
#ifdef G_OS_WIN32
1529
1530
/* We might be using tty emulators such as mintty, so try to detect it, if we passed in a valid FD
1531
 * so we need to check the name of the pipe if _isatty (fd) == 0
1532
 */
1533
1534
static gboolean
1535
win32_is_pipe_tty (int fd)
1536
{
1537
  gboolean result = FALSE;
1538
  HANDLE h_fd;
1539
  FILE_NAME_INFO *info = NULL;
1540
  gint info_size = sizeof (FILE_NAME_INFO) + sizeof (WCHAR) * MAX_PATH;
1541
  wchar_t *name = NULL;
1542
  gint length;
1543
1544
  h_fd = (HANDLE) _get_osfhandle (fd);
1545
1546
  if (h_fd == INVALID_HANDLE_VALUE || GetFileType (h_fd) != FILE_TYPE_PIPE)
1547
    goto done_query;
1548
1549
  /* mintty uses a pipe, in the form of \{cygwin|msys}-xxxxxxxxxxxxxxxx-ptyN-{from|to}-master */
1550
1551
  info = g_try_malloc (info_size);
1552
1553
  if (info == NULL ||
1554
      !GetFileInformationByHandleEx (h_fd, FileNameInfo, info, info_size))
1555
    goto done_query;
1556
1557
  info->FileName[info->FileNameLength / sizeof (WCHAR)] = L'\0';
1558
  name = info->FileName;
1559
1560
  length = wcslen (L"\\cygwin-");
1561
  if (wcsncmp (name, L"\\cygwin-", length))
1562
    {
1563
      length = wcslen (L"\\msys-");
1564
      if (wcsncmp (name, L"\\msys-", length))
1565
        goto done_query;
1566
    }
1567
1568
  name += length;
1569
  length = wcsspn (name, L"0123456789abcdefABCDEF");
1570
  if (length != 16)
1571
    goto done_query;
1572
1573
  name += length;
1574
  length = wcslen (L"-pty");
1575
  if (wcsncmp (name, L"-pty", length))
1576
    goto done_query;
1577
1578
  name += length;
1579
  length = wcsspn (name, L"0123456789");
1580
  if (length != 1)
1581
    goto done_query;
1582
1583
  name += length;
1584
  length = wcslen (L"-to-master");
1585
  if (wcsncmp (name, L"-to-master", length))
1586
    {
1587
      length = wcslen (L"-from-master");
1588
      if (wcsncmp (name, L"-from-master", length))
1589
        goto done_query;
1590
    }
1591
1592
  result = TRUE;
1593
1594
done_query:
1595
  if (info != NULL)
1596
    g_free (info);
1597
1598
  return result;
1599
}
1600
#endif
1601
1602
#pragma GCC diagnostic push
1603
#pragma GCC diagnostic ignored "-Wformat-nonliteral"
1604
1605
/**
1606
 * g_log_structured:
1607
 * @log_domain: log domain, usually %G_LOG_DOMAIN
1608
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
1609
 *    level
1610
 * @...: key-value pairs of structured data to add to the log entry, followed
1611
 *    by the key "MESSAGE", followed by a printf()-style message format,
1612
 *    followed by parameters to insert in the format string
1613
 *
1614
 * Log a message with structured data. The message will be passed through to
1615
 * the log writer set by the application using g_log_set_writer_func(). If the
1616
 * message is fatal (i.e. its log level is %G_LOG_LEVEL_ERROR), the program will
1617
 * be aborted by calling G_BREAKPOINT() at the end of this function. If the log writer returns
1618
 * %G_LOG_WRITER_UNHANDLED (failure), no other fallback writers will be tried.
1619
 * See the documentation for #GLogWriterFunc for information on chaining
1620
 * writers.
1621
 *
1622
 * The structured data is provided as key–value pairs, where keys are UTF-8
1623
 * strings, and values are arbitrary pointers — typically pointing to UTF-8
1624
 * strings, but that is not a requirement. To pass binary (non-nul-terminated)
1625
 * structured data, use g_log_structured_array(). The keys for structured data
1626
 * should follow the [systemd journal
1627
 * fields](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html)
1628
 * specification. It is suggested that custom keys are namespaced according to
1629
 * the code which sets them. For example, custom keys from GLib all have a
1630
 * `GLIB_` prefix.
1631
 *
1632
 * The @log_domain will be converted into a `GLIB_DOMAIN` field. @log_level will
1633
 * be converted into a
1634
 * [`PRIORITY`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#PRIORITY=)
1635
 * field. The format string will have its placeholders substituted for the provided
1636
 * values and be converted into a
1637
 * [`MESSAGE`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#MESSAGE=)
1638
 * field.
1639
 *
1640
 * Other fields you may commonly want to pass into this function:
1641
 *
1642
 *  * [`MESSAGE_ID`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#MESSAGE_ID=)
1643
 *  * [`CODE_FILE`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#CODE_FILE=)
1644
 *  * [`CODE_LINE`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#CODE_LINE=)
1645
 *  * [`CODE_FUNC`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#CODE_FUNC=)
1646
 *  * [`ERRNO`](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#ERRNO=)
1647
 *
1648
 * Note that `CODE_FILE`, `CODE_LINE` and `CODE_FUNC` are automatically set by
1649
 * the logging macros, G_DEBUG_HERE(), g_message(), g_warning(), g_critical(),
1650
 * g_error(), etc, if the symbols `G_LOG_USE_STRUCTURED` is defined before including
1651
 * glib.h.
1652
 *
1653
 * For example:
1654
 * |[<!-- language="C" -->
1655
 * g_log_structured (G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG,
1656
 *                   "MESSAGE_ID", "06d4df59e6c24647bfe69d2c27ef0b4e",
1657
 *                   "MY_APPLICATION_CUSTOM_FIELD", "some debug string",
1658
 *                   "MESSAGE", "This is a debug message about pointer %p and integer %u.",
1659
 *                   some_pointer, some_integer);
1660
 * ]|
1661
 *
1662
 * Note that each `MESSAGE_ID` must be [uniquely and randomly
1663
 * generated](https://www.freedesktop.org/software/systemd/man/systemd.journal-fields.html#MESSAGE_ID=).
1664
 * If adding a `MESSAGE_ID`, consider shipping a [message
1665
 * catalog](https://www.freedesktop.org/wiki/Software/systemd/catalog/) with
1666
 * your software.
1667
 *
1668
 * To pass a user data pointer to the log writer function which is specific to
1669
 * this logging call, you must use g_log_structured_array() and pass the pointer
1670
 * as a field with #GLogField.length set to zero, otherwise it will be
1671
 * interpreted as a string.
1672
 *
1673
 * For example:
1674
 * |[<!-- language="C" -->
1675
 * const GLogField fields[] = {
1676
 *   { "MESSAGE", "This is a debug message.", -1 },
1677
 *   { "MESSAGE_ID", "fcfb2e1e65c3494386b74878f1abf893", -1 },
1678
 *   { "MY_APPLICATION_CUSTOM_FIELD", "some debug string", -1 },
1679
 *   { "MY_APPLICATION_STATE", state_object, 0 },
1680
 * };
1681
 * g_log_structured_array (G_LOG_LEVEL_DEBUG, fields, G_N_ELEMENTS (fields));
1682
 * ]|
1683
 *
1684
 * Note also that, even if no other structured fields are specified, there
1685
 * must always be a `MESSAGE` key before the format string. The `MESSAGE`-format
1686
 * pair has to be the last of the key-value pairs, and `MESSAGE` is the only
1687
 * field for which printf()-style formatting is supported.
1688
 *
1689
 * The default writer function for `stdout` and `stderr` will automatically
1690
 * append a new-line character after the message, so you should not add one
1691
 * manually to the format string.
1692
 *
1693
 * Since: 2.50
1694
 */
1695
void
1696
g_log_structured (const gchar    *log_domain,
1697
                  GLogLevelFlags  log_level,
1698
                  ...)
1699
0
{
1700
0
  va_list args;
1701
0
  gchar buffer[1025], *message_allocated = NULL;
1702
0
  const char *format;
1703
0
  const gchar *message;
1704
0
  gpointer p;
1705
0
  gsize n_fields, i;
1706
0
  GLogField stack_fields[16];
1707
0
  GLogField *fields = stack_fields;
1708
0
  GLogField *fields_allocated = NULL;
1709
0
  GArray *array = NULL;
1710
1711
0
  va_start (args, log_level);
1712
1713
  /* MESSAGE and PRIORITY are a given */
1714
0
  n_fields = 2;
1715
1716
0
  if (log_domain)
1717
0
    n_fields++;
1718
1719
0
  for (p = va_arg (args, gchar *), i = n_fields;
1720
0
       strcmp (p, "MESSAGE") != 0;
1721
0
       p = va_arg (args, gchar *), i++)
1722
0
    {
1723
0
      GLogField field;
1724
0
      const gchar *key = p;
1725
0
      gconstpointer value = va_arg (args, gpointer);
1726
1727
0
      field.key = key;
1728
0
      field.value = value;
1729
0
      field.length = -1;
1730
1731
0
      if (i < 16)
1732
0
        stack_fields[i] = field;
1733
0
      else
1734
0
        {
1735
          /* Don't allow dynamic allocation, since we're likely
1736
           * in an out-of-memory situation. For lack of a better solution,
1737
           * just ignore further key-value pairs.
1738
           */
1739
0
          if (log_level & G_LOG_FLAG_RECURSION)
1740
0
            continue;
1741
1742
0
          if (i == 16)
1743
0
            {
1744
0
              array = g_array_sized_new (FALSE, FALSE, sizeof (GLogField), 32);
1745
0
              g_array_append_vals (array, stack_fields, 16);
1746
0
            }
1747
1748
0
          g_array_append_val (array, field);
1749
0
        }
1750
0
    }
1751
1752
0
  n_fields = i;
1753
1754
0
  if (array)
1755
0
    fields = fields_allocated = (GLogField *) g_array_free (array, FALSE);
1756
1757
0
  format = va_arg (args, gchar *);
1758
1759
0
  if (log_level & G_LOG_FLAG_RECURSION)
1760
0
    {
1761
      /* we use a stack buffer of fixed size, since we're likely
1762
       * in an out-of-memory situation
1763
       */
1764
0
      gsize size G_GNUC_UNUSED;
1765
1766
0
      size = _g_vsnprintf (buffer, sizeof (buffer), format, args);
1767
0
      message = buffer;
1768
0
    }
1769
0
  else
1770
0
    {
1771
0
      message = message_allocated = g_strdup_vprintf (format, args);
1772
0
    }
1773
1774
  /* Add MESSAGE, PRIORITY and GLIB_DOMAIN. */
1775
0
  fields[0].key = "MESSAGE";
1776
0
  fields[0].value = message;
1777
0
  fields[0].length = -1;
1778
1779
0
  fields[1].key = "PRIORITY";
1780
0
  fields[1].value = log_level_to_priority (log_level);
1781
0
  fields[1].length = -1;
1782
1783
0
  if (log_domain)
1784
0
    {
1785
0
      fields[2].key = "GLIB_DOMAIN";
1786
0
      fields[2].value = log_domain;
1787
0
      fields[2].length = -1;
1788
0
    }
1789
1790
  /* Log it. */
1791
0
  g_log_structured_array (log_level, fields, n_fields);
1792
1793
0
  g_free (fields_allocated);
1794
0
  g_free (message_allocated);
1795
1796
0
  va_end (args);
1797
0
}
1798
1799
/**
1800
 * g_log_variant:
1801
 * @log_domain: (nullable): log domain, usually %G_LOG_DOMAIN
1802
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
1803
 *    level
1804
 * @fields: a dictionary (#GVariant of the type %G_VARIANT_TYPE_VARDICT)
1805
 * containing the key-value pairs of message data.
1806
 *
1807
 * Log a message with structured data, accepting the data within a #GVariant. This
1808
 * version is especially useful for use in other languages, via introspection.
1809
 *
1810
 * The only mandatory item in the @fields dictionary is the "MESSAGE" which must
1811
 * contain the text shown to the user.
1812
 *
1813
 * The values in the @fields dictionary are likely to be of type String
1814
 * (#G_VARIANT_TYPE_STRING). Array of bytes (#G_VARIANT_TYPE_BYTESTRING) is also
1815
 * supported. In this case the message is handled as binary and will be forwarded
1816
 * to the log writer as such. The size of the array should not be higher than
1817
 * %G_MAXSSIZE. Otherwise it will be truncated to this size. For other types
1818
 * g_variant_print() will be used to convert the value into a string.
1819
 *
1820
 * For more details on its usage and about the parameters, see g_log_structured().
1821
 *
1822
 * Since: 2.50
1823
 */
1824
1825
void
1826
g_log_variant (const gchar    *log_domain,
1827
               GLogLevelFlags  log_level,
1828
               GVariant       *fields)
1829
0
{
1830
0
  GVariantIter iter;
1831
0
  GVariant *value;
1832
0
  gchar *key;
1833
0
  GArray *fields_array;
1834
0
  GLogField field;
1835
0
  GSList *values_list, *print_list;
1836
1837
0
  g_return_if_fail (g_variant_is_of_type (fields, G_VARIANT_TYPE_VARDICT));
1838
1839
0
  values_list = print_list = NULL;
1840
0
  fields_array = g_array_new (FALSE, FALSE, sizeof (GLogField));
1841
1842
0
  field.key = "PRIORITY";
1843
0
  field.value = log_level_to_priority (log_level);
1844
0
  field.length = -1;
1845
0
  g_array_append_val (fields_array, field);
1846
1847
0
  if (log_domain)
1848
0
    {
1849
0
      field.key = "GLIB_DOMAIN";
1850
0
      field.value = log_domain;
1851
0
      field.length = -1;
1852
0
      g_array_append_val (fields_array, field);
1853
0
    }
1854
1855
0
  g_variant_iter_init (&iter, fields);
1856
0
  while (g_variant_iter_next (&iter, "{&sv}", &key, &value))
1857
0
    {
1858
0
      gboolean defer_unref = TRUE;
1859
1860
0
      field.key = key;
1861
0
      field.length = -1;
1862
1863
0
      if (g_variant_is_of_type (value, G_VARIANT_TYPE_STRING))
1864
0
        {
1865
0
          field.value = g_variant_get_string (value, NULL);
1866
0
        }
1867
0
      else if (g_variant_is_of_type (value, G_VARIANT_TYPE_BYTESTRING))
1868
0
        {
1869
0
          gsize s;
1870
0
          field.value = g_variant_get_fixed_array (value, &s, sizeof (guchar));
1871
0
          if (G_LIKELY (s <= G_MAXSSIZE))
1872
0
            {
1873
0
              field.length = s;
1874
0
            }
1875
0
          else
1876
0
            {
1877
0
               _g_fprintf (stderr,
1878
0
                           "Byte array too large (%" G_GSIZE_FORMAT " bytes)"
1879
0
                           " passed to g_log_variant(). Truncating to " G_STRINGIFY (G_MAXSSIZE)
1880
0
                           " bytes.", s);
1881
0
              field.length = G_MAXSSIZE;
1882
0
            }
1883
0
        }
1884
0
      else
1885
0
        {
1886
0
          char *s = g_variant_print (value, FALSE);
1887
0
          field.value = s;
1888
0
          print_list = g_slist_prepend (print_list, s);
1889
0
          defer_unref = FALSE;
1890
0
        }
1891
1892
0
      g_array_append_val (fields_array, field);
1893
1894
0
      if (G_LIKELY (defer_unref))
1895
0
        values_list = g_slist_prepend (values_list, value);
1896
0
      else
1897
0
        g_variant_unref (value);
1898
0
    }
1899
1900
  /* Log it. */
1901
0
  g_log_structured_array (log_level, (GLogField *) fields_array->data, fields_array->len);
1902
1903
0
  g_array_free (fields_array, TRUE);
1904
0
  g_slist_free_full (values_list, (GDestroyNotify) g_variant_unref);
1905
0
  g_slist_free_full (print_list, g_free);
1906
0
}
1907
1908
1909
#pragma GCC diagnostic pop
1910
1911
static GLogWriterOutput _g_log_writer_fallback (GLogLevelFlags   log_level,
1912
                                                const GLogField *fields,
1913
                                                gsize            n_fields,
1914
                                                gpointer         user_data);
1915
1916
/**
1917
 * g_log_structured_array:
1918
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
1919
 *    level
1920
 * @fields: (array length=n_fields): key–value pairs of structured data to add
1921
 *    to the log message
1922
 * @n_fields: number of elements in the @fields array
1923
 *
1924
 * Log a message with structured data. The message will be passed through to the
1925
 * log writer set by the application using g_log_set_writer_func(). If the
1926
 * message is fatal (i.e. its log level is %G_LOG_LEVEL_ERROR), the program will
1927
 * be aborted at the end of this function.
1928
 *
1929
 * See g_log_structured() for more documentation.
1930
 *
1931
 * This assumes that @log_level is already present in @fields (typically as the
1932
 * `PRIORITY` field).
1933
 *
1934
 * Since: 2.50
1935
 */
1936
void
1937
g_log_structured_array (GLogLevelFlags   log_level,
1938
                        const GLogField *fields,
1939
                        gsize            n_fields)
1940
3.98M
{
1941
3.98M
  GLogWriterFunc writer_func;
1942
3.98M
  gpointer writer_user_data;
1943
3.98M
  gboolean recursion;
1944
3.98M
  guint depth;
1945
1946
3.98M
  if (n_fields == 0)
1947
0
    return;
1948
1949
  /* Check for recursion and look up the writer function. */
1950
3.98M
  depth = GPOINTER_TO_UINT (g_private_get (&g_log_structured_depth));
1951
3.98M
  recursion = (depth > 0);
1952
1953
3.98M
  g_mutex_lock (&g_messages_lock);
1954
1955
3.98M
  writer_func = recursion ? _g_log_writer_fallback : log_writer_func;
1956
3.98M
  writer_user_data = log_writer_user_data;
1957
1958
3.98M
  g_mutex_unlock (&g_messages_lock);
1959
1960
  /* Write the log entry. */
1961
3.98M
  g_private_set (&g_log_structured_depth, GUINT_TO_POINTER (++depth));
1962
1963
3.98M
  g_assert (writer_func != NULL);
1964
3.98M
  writer_func (log_level, fields, n_fields, writer_user_data);
1965
1966
3.98M
  g_private_set (&g_log_structured_depth, GUINT_TO_POINTER (--depth));
1967
1968
  /* Abort if the message was fatal. */
1969
3.98M
  if (log_level & G_LOG_FATAL_MASK)
1970
0
    _g_log_abort (!(log_level & G_LOG_FLAG_RECURSION));
1971
3.98M
}
1972
1973
/* Semi-private helper function to implement the g_message() (etc.) macros
1974
 * with support for G_GNUC_PRINTF so that @message_format can be checked
1975
 * with -Wformat. */
1976
void
1977
g_log_structured_standard (const gchar    *log_domain,
1978
                           GLogLevelFlags  log_level,
1979
                           const gchar    *file,
1980
                           const gchar    *line,
1981
                           const gchar    *func,
1982
                           const gchar    *message_format,
1983
                           ...)
1984
0
{
1985
0
  GLogField fields[] =
1986
0
    {
1987
0
      { "PRIORITY", log_level_to_priority (log_level), -1 },
1988
0
      { "CODE_FILE", file, -1 },
1989
0
      { "CODE_LINE", line, -1 },
1990
0
      { "CODE_FUNC", func, -1 },
1991
      /* Filled in later: */
1992
0
      { "MESSAGE", NULL, -1 },
1993
      /* If @log_domain is %NULL, we will not pass this field: */
1994
0
      { "GLIB_DOMAIN", log_domain, -1 },
1995
0
    };
1996
0
  gsize n_fields;
1997
0
  gchar *message_allocated = NULL;
1998
0
  gchar buffer[1025];
1999
0
  va_list args;
2000
2001
0
  va_start (args, message_format);
2002
2003
0
  if (log_level & G_LOG_FLAG_RECURSION)
2004
0
    {
2005
      /* we use a stack buffer of fixed size, since we're likely
2006
       * in an out-of-memory situation
2007
       */
2008
0
      gsize size G_GNUC_UNUSED;
2009
2010
0
      size = _g_vsnprintf (buffer, sizeof (buffer), message_format, args);
2011
0
      fields[4].value = buffer;
2012
0
    }
2013
0
  else
2014
0
    {
2015
0
      fields[4].value = message_allocated = g_strdup_vprintf (message_format, args);
2016
0
    }
2017
2018
0
  va_end (args);
2019
2020
0
  n_fields = G_N_ELEMENTS (fields) - ((log_domain == NULL) ? 1 : 0);
2021
0
  g_log_structured_array (log_level, fields, n_fields);
2022
2023
0
  g_free (message_allocated);
2024
0
}
2025
2026
/**
2027
 * g_log_set_writer_func:
2028
 * @func: log writer function, which must not be %NULL
2029
 * @user_data: (closure func): user data to pass to @func
2030
 * @user_data_free: (destroy func): function to free @user_data once it’s
2031
 *    finished with, if non-%NULL
2032
 *
2033
 * Set a writer function which will be called to format and write out each log
2034
 * message. Each program should set a writer function, or the default writer
2035
 * (g_log_writer_default()) will be used.
2036
 *
2037
 * Libraries **must not** call this function — only programs are allowed to
2038
 * install a writer function, as there must be a single, central point where
2039
 * log messages are formatted and outputted.
2040
 *
2041
 * There can only be one writer function. It is an error to set more than one.
2042
 *
2043
 * Since: 2.50
2044
 */
2045
void
2046
g_log_set_writer_func (GLogWriterFunc func,
2047
                       gpointer       user_data,
2048
                       GDestroyNotify user_data_free)
2049
0
{
2050
0
  g_return_if_fail (func != NULL);
2051
2052
0
  g_mutex_lock (&g_messages_lock);
2053
0
  log_writer_func = func;
2054
0
  log_writer_user_data = user_data;
2055
0
  log_writer_user_data_free = user_data_free;
2056
0
  g_mutex_unlock (&g_messages_lock);
2057
0
}
2058
2059
/**
2060
 * g_log_writer_supports_color:
2061
 * @output_fd: output file descriptor to check
2062
 *
2063
 * Check whether the given @output_fd file descriptor supports ANSI color
2064
 * escape sequences. If so, they can safely be used when formatting log
2065
 * messages.
2066
 *
2067
 * Returns: %TRUE if ANSI color escapes are supported, %FALSE otherwise
2068
 * Since: 2.50
2069
 */
2070
gboolean
2071
g_log_writer_supports_color (gint output_fd)
2072
33.9k
{
2073
#ifdef G_OS_WIN32
2074
  gboolean result = FALSE;
2075
2076
#if (defined (_MSC_VER) && _MSC_VER >= 1400)
2077
  _invalid_parameter_handler oldHandler, newHandler;
2078
  int prev_report_mode = 0;
2079
#endif
2080
2081
#endif
2082
2083
33.9k
  g_return_val_if_fail (output_fd >= 0, FALSE);
2084
2085
  /* FIXME: This check could easily be expanded in future to be more robust
2086
   * against different types of terminal, which still vary in their color
2087
   * support. cmd.exe on Windows, for example, supports ANSI colors only
2088
   * from Windows 10 onwards; bash on Windows has always supported ANSI colors.
2089
   * The Windows 10 color support is supported on:
2090
   * -Output in the cmd.exe, MSYS/Cygwin standard consoles.
2091
   * -Output in the cmd.exe, MSYS/Cygwin piped to the less program.
2092
   * but not:
2093
   * -Output in Cygwin via mintty (https://github.com/mintty/mintty/issues/482)
2094
   * -Color code output when output redirected to file (i.e. program 2> some.txt)
2095
   *
2096
   * On UNIX systems, we probably want to use the functions from terminfo to
2097
   * work out whether colors are supported.
2098
   *
2099
   * Some examples:
2100
   *  - https://github.com/chalk/supports-color/blob/9434c93918301a6b47faa01999482adfbf1b715c/index.js#L61
2101
   *  - http://stackoverflow.com/questions/16755142/how-to-make-win32-console-recognize-ansi-vt100-escape-sequences
2102
   *  - http://blog.mmediasys.com/2010/11/24/we-all-love-colors/
2103
   *  - http://unix.stackexchange.com/questions/198794/where-does-the-term-environment-variable-default-get-set
2104
   */
2105
#ifdef G_OS_WIN32
2106
2107
#if (defined (_MSC_VER) && _MSC_VER >= 1400)
2108
  /* Set up our empty invalid parameter handler, for isatty(),
2109
   * in case of bad fd's passed in for isatty(), so that
2110
   * msvcrt80.dll+ won't abort the program
2111
   */
2112
  newHandler = myInvalidParameterHandler;
2113
  oldHandler = _set_invalid_parameter_handler (newHandler);
2114
2115
  /* Disable the message box for assertions. */
2116
  prev_report_mode = _CrtSetReportMode(_CRT_ASSERT, 0);
2117
#endif
2118
2119
  if (g_win32_check_windows_version (10, 0, 0, G_WIN32_OS_ANY))
2120
    {
2121
      HANDLE h_output;
2122
      DWORD dw_mode;
2123
2124
      if (_isatty (output_fd))
2125
        {
2126
          h_output = (HANDLE) _get_osfhandle (output_fd);
2127
2128
          if (!GetConsoleMode (h_output, &dw_mode))
2129
            goto reset_invalid_param_handler;
2130
2131
          if (dw_mode & ENABLE_VIRTUAL_TERMINAL_PROCESSING)
2132
            result = TRUE;
2133
2134
          if (!SetConsoleMode (h_output, dw_mode | ENABLE_VIRTUAL_TERMINAL_PROCESSING))
2135
            goto reset_invalid_param_handler;
2136
2137
          result = TRUE;
2138
        }
2139
    }
2140
2141
  /* FIXME: Support colored outputs for structured logs for pre-Windows 10,
2142
   *        perhaps using WriteConsoleOutput or SetConsoleTextAttribute
2143
   *        (bug 775468), on standard Windows consoles, such as cmd.exe
2144
   */
2145
  if (!result)
2146
    result = win32_is_pipe_tty (output_fd);
2147
2148
reset_invalid_param_handler:
2149
#if defined (_MSC_VER) && (_MSC_VER >= 1400)
2150
      _CrtSetReportMode(_CRT_ASSERT, prev_report_mode);
2151
      _set_invalid_parameter_handler (oldHandler);
2152
#endif
2153
2154
  return result;
2155
#else
2156
33.9k
  return isatty (output_fd);
2157
33.9k
#endif
2158
33.9k
}
2159
2160
#if defined(__linux__) && !defined(__BIONIC__)
2161
static int journal_fd = -1;
2162
2163
#ifndef SOCK_CLOEXEC
2164
#define SOCK_CLOEXEC 0
2165
#else
2166
#define HAVE_SOCK_CLOEXEC 1
2167
#endif
2168
2169
static void
2170
open_journal (void)
2171
0
{
2172
0
  if ((journal_fd = socket (AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0)) < 0)
2173
0
    return;
2174
2175
#ifndef HAVE_SOCK_CLOEXEC
2176
  if (fcntl (journal_fd, F_SETFD, FD_CLOEXEC) < 0)
2177
    {
2178
      close (journal_fd);
2179
      journal_fd = -1;
2180
    }
2181
#endif
2182
0
}
2183
#endif
2184
2185
/**
2186
 * g_log_writer_is_journald:
2187
 * @output_fd: output file descriptor to check
2188
 *
2189
 * Check whether the given @output_fd file descriptor is a connection to the
2190
 * systemd journal, or something else (like a log file or `stdout` or
2191
 * `stderr`).
2192
 *
2193
 * Invalid file descriptors are accepted and return %FALSE, which allows for
2194
 * the following construct without needing any additional error handling:
2195
 * |[<!-- language="C" -->
2196
 *   is_journald = g_log_writer_is_journald (fileno (stderr));
2197
 * ]|
2198
 *
2199
 * Returns: %TRUE if @output_fd points to the journal, %FALSE otherwise
2200
 * Since: 2.50
2201
 */
2202
gboolean
2203
g_log_writer_is_journald (gint output_fd)
2204
8
{
2205
8
#if defined(__linux__) && !defined(__BIONIC__)
2206
  /* FIXME: Use the new journal API for detecting whether we’re writing to the
2207
   * journal. See: https://github.com/systemd/systemd/issues/2473
2208
   */
2209
8
  union {
2210
8
    struct sockaddr_storage storage;
2211
8
    struct sockaddr sa;
2212
8
    struct sockaddr_un un;
2213
8
  } addr;
2214
8
  socklen_t addr_len;
2215
8
  int err;
2216
2217
8
  if (output_fd < 0)
2218
0
    return FALSE;
2219
2220
8
  addr_len = sizeof(addr);
2221
8
  err = getpeername (output_fd, &addr.sa, &addr_len);
2222
8
  if (err == 0 && addr.storage.ss_family == AF_UNIX)
2223
0
    return g_str_has_prefix (addr.un.sun_path, "/run/systemd/journal/");
2224
8
#endif
2225
2226
8
  return FALSE;
2227
8
}
2228
2229
static void escape_string (GString *string);
2230
2231
/**
2232
 * g_log_writer_format_fields:
2233
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
2234
 *    level
2235
 * @fields: (array length=n_fields): key–value pairs of structured data forming
2236
 *    the log message
2237
 * @n_fields: number of elements in the @fields array
2238
 * @use_color: %TRUE to use ANSI color escape sequences when formatting the
2239
 *    message, %FALSE to not
2240
 *
2241
 * Format a structured log message as a string suitable for outputting to the
2242
 * terminal (or elsewhere). This will include the values of all fields it knows
2243
 * how to interpret, which includes `MESSAGE` and `GLIB_DOMAIN` (see the
2244
 * documentation for g_log_structured()). It does not include values from
2245
 * unknown fields.
2246
 *
2247
 * The returned string does **not** have a trailing new-line character. It is
2248
 * encoded in the character set of the current locale, which is not necessarily
2249
 * UTF-8.
2250
 *
2251
 * Returns: (transfer full): string containing the formatted log message, in
2252
 *    the character set of the current locale
2253
 * Since: 2.50
2254
 */
2255
gchar *
2256
g_log_writer_format_fields (GLogLevelFlags   log_level,
2257
                            const GLogField *fields,
2258
                            gsize            n_fields,
2259
                            gboolean         use_color)
2260
33.9k
{
2261
33.9k
  gsize i;
2262
33.9k
  const gchar *message = NULL;
2263
33.9k
  const gchar *log_domain = NULL;
2264
33.9k
  gchar level_prefix[STRING_BUFFER_SIZE];
2265
33.9k
  GString *gstring;
2266
33.9k
  gint64 now;
2267
33.9k
  time_t now_secs;
2268
33.9k
  struct tm *now_tm;
2269
33.9k
  gchar time_buf[128];
2270
2271
  /* Extract some common fields. */
2272
169k
  for (i = 0; (message == NULL || log_domain == NULL) && i < n_fields; i++)
2273
135k
    {
2274
135k
      const GLogField *field = &fields[i];
2275
2276
135k
      if (g_strcmp0 (field->key, "MESSAGE") == 0)
2277
33.9k
        message = field->value;
2278
101k
      else if (g_strcmp0 (field->key, "GLIB_DOMAIN") == 0)
2279
33.9k
        log_domain = field->value;
2280
135k
    }
2281
2282
  /* Format things. */
2283
33.9k
  mklevel_prefix (level_prefix, log_level, use_color);
2284
2285
33.9k
  gstring = g_string_new (NULL);
2286
33.9k
  if (log_level & ALERT_LEVELS)
2287
33.9k
    g_string_append (gstring, "\n");
2288
33.9k
  if (!log_domain)
2289
0
    g_string_append (gstring, "** ");
2290
2291
33.9k
  if ((g_log_msg_prefix & (log_level & G_LOG_LEVEL_MASK)) ==
2292
33.9k
      (log_level & G_LOG_LEVEL_MASK))
2293
33.9k
    {
2294
33.9k
      const gchar *prg_name = g_get_prgname ();
2295
33.9k
      gulong pid = getpid ();
2296
2297
33.9k
      if (prg_name == NULL)
2298
33.9k
        g_string_append_printf (gstring, "(process:%lu): ", pid);
2299
0
      else
2300
0
        g_string_append_printf (gstring, "(%s:%lu): ", prg_name, pid);
2301
33.9k
    }
2302
2303
33.9k
  if (log_domain != NULL)
2304
33.9k
    {
2305
33.9k
      g_string_append (gstring, log_domain);
2306
33.9k
      g_string_append_c (gstring, '-');
2307
33.9k
    }
2308
33.9k
  g_string_append (gstring, level_prefix);
2309
2310
33.9k
  g_string_append (gstring, ": ");
2311
2312
  /* Timestamp */
2313
33.9k
  now = g_get_real_time ();
2314
33.9k
  now_secs = (time_t) (now / 1000000);
2315
33.9k
  now_tm = localtime (&now_secs);
2316
33.9k
  strftime (time_buf, sizeof (time_buf), "%H:%M:%S", now_tm);
2317
2318
33.9k
  g_string_append_printf (gstring, "%s%s.%03d%s: ",
2319
33.9k
                          use_color ? "\033[34m" : "",
2320
33.9k
                          time_buf, (gint) ((now / 1000) % 1000),
2321
33.9k
                          color_reset (use_color));
2322
2323
33.9k
  if (message == NULL)
2324
0
    {
2325
0
      g_string_append (gstring, "(NULL) message");
2326
0
    }
2327
33.9k
  else
2328
33.9k
    {
2329
33.9k
      GString *msg;
2330
33.9k
      const gchar *charset;
2331
2332
33.9k
      msg = g_string_new (message);
2333
33.9k
      escape_string (msg);
2334
2335
33.9k
      if (g_get_console_charset (&charset))
2336
0
        {
2337
          /* charset is UTF-8 already */
2338
0
          g_string_append (gstring, msg->str);
2339
0
        }
2340
33.9k
      else
2341
33.9k
        {
2342
33.9k
          gchar *lstring = strdup_convert (msg->str, charset);
2343
33.9k
          g_string_append (gstring, lstring);
2344
33.9k
          g_free (lstring);
2345
33.9k
        }
2346
2347
33.9k
      g_string_free (msg, TRUE);
2348
33.9k
    }
2349
2350
33.9k
  return g_string_free (gstring, FALSE);
2351
33.9k
}
2352
2353
/* Enable support for the journal if we're on a recent enough Linux */
2354
#if defined(__linux__) && !defined(__BIONIC__) && defined(HAVE_MKOSTEMP) && defined(O_CLOEXEC)
2355
#define ENABLE_JOURNAL_SENDV
2356
#endif
2357
2358
#ifdef ENABLE_JOURNAL_SENDV
2359
static int
2360
journal_sendv (struct iovec *iov,
2361
               gsize         iovlen)
2362
0
{
2363
0
  int buf_fd = -1;
2364
0
  struct msghdr mh;
2365
0
  struct sockaddr_un sa;
2366
0
  union {
2367
0
    struct cmsghdr cmsghdr;
2368
0
    guint8 buf[CMSG_SPACE(sizeof(int))];
2369
0
  } control;
2370
0
  struct cmsghdr *cmsg;
2371
0
  char path[] = "/dev/shm/journal.XXXXXX";
2372
2373
0
  if (journal_fd < 0)
2374
0
    open_journal ();
2375
2376
0
  if (journal_fd < 0)
2377
0
    return -1;
2378
2379
0
  memset (&sa, 0, sizeof (sa));
2380
0
  sa.sun_family = AF_UNIX;
2381
0
  if (g_strlcpy (sa.sun_path, "/run/systemd/journal/socket", sizeof (sa.sun_path)) >= sizeof (sa.sun_path))
2382
0
    return -1;
2383
2384
0
  memset (&mh, 0, sizeof (mh));
2385
0
  mh.msg_name = &sa;
2386
0
  mh.msg_namelen = offsetof (struct sockaddr_un, sun_path) + strlen (sa.sun_path);
2387
0
  mh.msg_iov = iov;
2388
0
  mh.msg_iovlen = iovlen;
2389
2390
0
retry:
2391
0
  if (sendmsg (journal_fd, &mh, MSG_NOSIGNAL) >= 0)
2392
0
    return 0;
2393
2394
0
  if (errno == EINTR)
2395
0
    goto retry;
2396
2397
0
  if (errno != EMSGSIZE && errno != ENOBUFS)
2398
0
    return -1;
2399
2400
  /* Message was too large, so dump to temporary file
2401
   * and pass an FD to the journal
2402
   */
2403
0
  if ((buf_fd = mkostemp (path, O_CLOEXEC|O_RDWR)) < 0)
2404
0
    return -1;
2405
2406
0
  if (unlink (path) < 0)
2407
0
    {
2408
0
      close (buf_fd);
2409
0
      return -1;
2410
0
    }
2411
2412
0
  if (writev (buf_fd, iov, iovlen) < 0)
2413
0
    {
2414
0
      close (buf_fd);
2415
0
      return -1;
2416
0
    }
2417
2418
0
  mh.msg_iov = NULL;
2419
0
  mh.msg_iovlen = 0;
2420
2421
0
  memset (&control, 0, sizeof (control));
2422
0
  mh.msg_control = &control;
2423
0
  mh.msg_controllen = sizeof (control);
2424
2425
0
  cmsg = CMSG_FIRSTHDR (&mh);
2426
0
  cmsg->cmsg_level = SOL_SOCKET;
2427
0
  cmsg->cmsg_type = SCM_RIGHTS;
2428
0
  cmsg->cmsg_len = CMSG_LEN (sizeof (int));
2429
0
  memcpy (CMSG_DATA (cmsg), &buf_fd, sizeof (int));
2430
2431
0
  mh.msg_controllen = cmsg->cmsg_len;
2432
2433
0
retry2:
2434
0
  if (sendmsg (journal_fd, &mh, MSG_NOSIGNAL) >= 0)
2435
0
    return 0;
2436
2437
0
  if (errno == EINTR)
2438
0
    goto retry2;
2439
2440
0
  return -1;
2441
0
}
2442
#endif /* ENABLE_JOURNAL_SENDV */
2443
2444
/**
2445
 * g_log_writer_journald:
2446
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
2447
 *    level
2448
 * @fields: (array length=n_fields): key–value pairs of structured data forming
2449
 *    the log message
2450
 * @n_fields: number of elements in the @fields array
2451
 * @user_data: user data passed to g_log_set_writer_func()
2452
 *
2453
 * Format a structured log message and send it to the systemd journal as a set
2454
 * of key–value pairs. All fields are sent to the journal, but if a field has
2455
 * length zero (indicating program-specific data) then only its key will be
2456
 * sent.
2457
 *
2458
 * This is suitable for use as a #GLogWriterFunc.
2459
 *
2460
 * If GLib has been compiled without systemd support, this function is still
2461
 * defined, but will always return %G_LOG_WRITER_UNHANDLED.
2462
 *
2463
 * Returns: %G_LOG_WRITER_HANDLED on success, %G_LOG_WRITER_UNHANDLED otherwise
2464
 * Since: 2.50
2465
 */
2466
GLogWriterOutput
2467
g_log_writer_journald (GLogLevelFlags   log_level,
2468
                       const GLogField *fields,
2469
                       gsize            n_fields,
2470
                       gpointer         user_data)
2471
0
{
2472
0
#ifdef ENABLE_JOURNAL_SENDV
2473
0
  const char equals = '=';
2474
0
  const char newline = '\n';
2475
0
  gsize i, k;
2476
0
  struct iovec *iov, *v;
2477
0
  char *buf;
2478
0
  gint retval;
2479
2480
0
  g_return_val_if_fail (fields != NULL, G_LOG_WRITER_UNHANDLED);
2481
0
  g_return_val_if_fail (n_fields > 0, G_LOG_WRITER_UNHANDLED);
2482
2483
  /* According to systemd.journal-fields(7), the journal allows fields in any
2484
   * format (including arbitrary binary), but expects text fields to be UTF-8.
2485
   * This is great, because we require input strings to be in UTF-8, so no
2486
   * conversion is necessary and we don’t need to care about the current
2487
   * locale’s character set.
2488
   */
2489
2490
0
  iov = g_alloca (sizeof (struct iovec) * 5 * n_fields);
2491
0
  buf = g_alloca (32 * n_fields);
2492
2493
0
  k = 0;
2494
0
  v = iov;
2495
0
  for (i = 0; i < n_fields; i++)
2496
0
    {
2497
0
      guint64 length;
2498
0
      gboolean binary;
2499
2500
0
      if (fields[i].length < 0)
2501
0
        {
2502
0
          length = strlen (fields[i].value);
2503
0
          binary = strchr (fields[i].value, '\n') != NULL;
2504
0
        }
2505
0
      else
2506
0
        {
2507
0
          length = fields[i].length;
2508
0
          binary = TRUE;
2509
0
        }
2510
2511
0
      if (binary)
2512
0
        {
2513
0
          guint64 nstr;
2514
2515
0
          v[0].iov_base = (gpointer)fields[i].key;
2516
0
          v[0].iov_len = strlen (fields[i].key);
2517
2518
0
          v[1].iov_base = (gpointer)&newline;
2519
0
          v[1].iov_len = 1;
2520
2521
0
          nstr = GUINT64_TO_LE(length);
2522
0
          memcpy (&buf[k], &nstr, sizeof (nstr));
2523
2524
0
          v[2].iov_base = &buf[k];
2525
0
          v[2].iov_len = sizeof (nstr);
2526
0
          v += 3;
2527
0
          k += sizeof (nstr);
2528
0
        }
2529
0
      else
2530
0
        {
2531
0
          v[0].iov_base = (gpointer)fields[i].key;
2532
0
          v[0].iov_len = strlen (fields[i].key);
2533
2534
0
          v[1].iov_base = (gpointer)&equals;
2535
0
          v[1].iov_len = 1;
2536
0
          v += 2;
2537
0
        }
2538
2539
0
      v[0].iov_base = (gpointer)fields[i].value;
2540
0
      v[0].iov_len = length;
2541
2542
0
      v[1].iov_base = (gpointer)&newline;
2543
0
      v[1].iov_len = 1;
2544
0
      v += 2;
2545
0
    }
2546
2547
0
  retval = journal_sendv (iov, v - iov);
2548
2549
0
  return retval == 0 ? G_LOG_WRITER_HANDLED : G_LOG_WRITER_UNHANDLED;
2550
#else
2551
  return G_LOG_WRITER_UNHANDLED;
2552
#endif /* ENABLE_JOURNAL_SENDV */
2553
0
}
2554
2555
/**
2556
 * g_log_writer_standard_streams:
2557
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
2558
 *    level
2559
 * @fields: (array length=n_fields): key–value pairs of structured data forming
2560
 *    the log message
2561
 * @n_fields: number of elements in the @fields array
2562
 * @user_data: user data passed to g_log_set_writer_func()
2563
 *
2564
 * Format a structured log message and print it to either `stdout` or `stderr`,
2565
 * depending on its log level. %G_LOG_LEVEL_INFO and %G_LOG_LEVEL_DEBUG messages
2566
 * are sent to `stdout`, or to `stderr` if requested by
2567
 * g_log_writer_default_set_use_stderr();
2568
 * all other log levels are sent to `stderr`. Only fields
2569
 * which are understood by this function are included in the formatted string
2570
 * which is printed.
2571
 *
2572
 * If the output stream supports ANSI color escape sequences, they will be used
2573
 * in the output.
2574
 *
2575
 * A trailing new-line character is added to the log message when it is printed.
2576
 *
2577
 * This is suitable for use as a #GLogWriterFunc.
2578
 *
2579
 * Returns: %G_LOG_WRITER_HANDLED on success, %G_LOG_WRITER_UNHANDLED otherwise
2580
 * Since: 2.50
2581
 */
2582
GLogWriterOutput
2583
g_log_writer_standard_streams (GLogLevelFlags   log_level,
2584
                               const GLogField *fields,
2585
                               gsize            n_fields,
2586
                               gpointer         user_data)
2587
33.9k
{
2588
33.9k
  FILE *stream;
2589
33.9k
  gchar *out = NULL;  /* in the current locale’s character set */
2590
2591
33.9k
  g_return_val_if_fail (fields != NULL, G_LOG_WRITER_UNHANDLED);
2592
33.9k
  g_return_val_if_fail (n_fields > 0, G_LOG_WRITER_UNHANDLED);
2593
2594
33.9k
  stream = log_level_to_file (log_level);
2595
33.9k
  if (!stream || fileno (stream) < 0)
2596
0
    return G_LOG_WRITER_UNHANDLED;
2597
2598
33.9k
  out = g_log_writer_format_fields (log_level, fields, n_fields,
2599
33.9k
                                    g_log_writer_supports_color (fileno (stream)));
2600
33.9k
  _g_fprintf (stream, "%s\n", out);
2601
33.9k
  fflush (stream);
2602
33.9k
  g_free (out);
2603
2604
33.9k
  return G_LOG_WRITER_HANDLED;
2605
33.9k
}
2606
2607
/* The old g_log() API is implemented in terms of the new structured log API.
2608
 * However, some of the checks do not line up between the two APIs: the
2609
 * structured API only handles fatalness of messages for log levels; the old API
2610
 * handles it per-domain as well. Consequently, we need to disable fatalness
2611
 * handling in the structured log API when called from the old g_log() API.
2612
 *
2613
 * We can guarantee that g_log_default_handler() will pass GLIB_OLD_LOG_API as
2614
 * the first field to g_log_structured_array(), if that is the case.
2615
 */
2616
static gboolean
2617
log_is_old_api (const GLogField *fields,
2618
                gsize            n_fields)
2619
0
{
2620
0
  return (n_fields >= 1 &&
2621
0
          g_strcmp0 (fields[0].key, "GLIB_OLD_LOG_API") == 0 &&
2622
0
          g_strcmp0 (fields[0].value, "1") == 0);
2623
0
}
2624
2625
/*
2626
 * Internal version of g_log_writer_default_would_drop(), which can
2627
 * read from either a log_domain or an array of fields. This avoids
2628
 * having to iterate through the fields if the @log_level is sufficient
2629
 * to make the decision.
2630
 */
2631
static gboolean
2632
should_drop_message (GLogLevelFlags   log_level,
2633
                     const char      *log_domain,
2634
                     const GLogField *fields,
2635
                     gsize            n_fields)
2636
3.98M
{
2637
  /* Disable debug message output unless specified in G_MESSAGES_DEBUG. */
2638
3.98M
  if (!(log_level & DEFAULT_LEVELS) && !(log_level >> G_LOG_LEVEL_USER_SHIFT))
2639
3.94M
    {
2640
3.94M
      const gchar *domains;
2641
3.94M
      gsize i;
2642
2643
3.94M
      domains = g_getenv ("G_MESSAGES_DEBUG");
2644
2645
3.94M
      if ((log_level & INFO_LEVELS) == 0 ||
2646
3.94M
          domains == NULL)
2647
3.94M
        return TRUE;
2648
2649
0
      if (log_domain == NULL)
2650
0
        {
2651
0
          for (i = 0; i < n_fields; i++)
2652
0
            {
2653
0
              if (g_strcmp0 (fields[i].key, "GLIB_DOMAIN") == 0)
2654
0
                {
2655
0
                  log_domain = fields[i].value;
2656
0
                  break;
2657
0
                }
2658
0
            }
2659
0
        }
2660
2661
0
      if (strcmp (domains, "all") != 0 &&
2662
0
          (log_domain == NULL || !strstr (domains, log_domain)))
2663
0
        return TRUE;
2664
0
    }
2665
2666
33.9k
  return FALSE;
2667
3.98M
}
2668
2669
/**
2670
 * g_log_writer_default_would_drop:
2671
 * @log_domain: (nullable): log domain
2672
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
2673
 *    level
2674
 *
2675
 * Check whether g_log_writer_default() and g_log_default_handler() would
2676
 * ignore a message with the given domain and level.
2677
 *
2678
 * As with g_log_default_handler(), this function drops debug and informational
2679
 * messages unless their log domain (or `all`) is listed in the space-separated
2680
 * `G_MESSAGES_DEBUG` environment variable.
2681
 *
2682
 * This can be used when implementing log writers with the same filtering
2683
 * behaviour as the default, but a different destination or output format:
2684
 *
2685
 * |[<!-- language="C" -->
2686
 *   if (g_log_writer_default_would_drop (log_level, log_domain))
2687
 *     return G_LOG_WRITER_HANDLED;
2688
 * ]|
2689
 *
2690
 * or to skip an expensive computation if it is only needed for a debugging
2691
 * message, and `G_MESSAGES_DEBUG` is not set:
2692
 *
2693
 * |[<!-- language="C" -->
2694
 *   if (!g_log_writer_default_would_drop (G_LOG_LEVEL_DEBUG, G_LOG_DOMAIN))
2695
 *     {
2696
 *       gchar *result = expensive_computation (my_object);
2697
 *
2698
 *       g_debug ("my_object result: %s", result);
2699
 *       g_free (result);
2700
 *     }
2701
 * ]|
2702
 *
2703
 * Returns: %TRUE if the log message would be dropped by GLib's
2704
 *  default log handlers
2705
 * Since: 2.68
2706
 */
2707
gboolean
2708
g_log_writer_default_would_drop (GLogLevelFlags  log_level,
2709
                                 const char     *log_domain)
2710
0
{
2711
0
  return should_drop_message (log_level, log_domain, NULL, 0);
2712
0
}
2713
2714
/**
2715
 * g_log_writer_default:
2716
 * @log_level: log level, either from #GLogLevelFlags, or a user-defined
2717
 *    level
2718
 * @fields: (array length=n_fields): key–value pairs of structured data forming
2719
 *    the log message
2720
 * @n_fields: number of elements in the @fields array
2721
 * @user_data: user data passed to g_log_set_writer_func()
2722
 *
2723
 * Format a structured log message and output it to the default log destination
2724
 * for the platform. On Linux, this is typically the systemd journal, falling
2725
 * back to `stdout` or `stderr` if running from the terminal or if output is
2726
 * being redirected to a file.
2727
 *
2728
 * Support for other platform-specific logging mechanisms may be added in
2729
 * future. Distributors of GLib may modify this function to impose their own
2730
 * (documented) platform-specific log writing policies.
2731
 *
2732
 * This is suitable for use as a #GLogWriterFunc, and is the default writer used
2733
 * if no other is set using g_log_set_writer_func().
2734
 *
2735
 * As with g_log_default_handler(), this function drops debug and informational
2736
 * messages unless their log domain (or `all`) is listed in the space-separated
2737
 * `G_MESSAGES_DEBUG` environment variable.
2738
 *
2739
 * g_log_writer_default() uses the mask set by g_log_set_always_fatal() to
2740
 * determine which messages are fatal. When using a custom writer func instead it is
2741
 * up to the writer function to determine which log messages are fatal.
2742
 *
2743
 * Returns: %G_LOG_WRITER_HANDLED on success, %G_LOG_WRITER_UNHANDLED otherwise
2744
 * Since: 2.50
2745
 */
2746
GLogWriterOutput
2747
g_log_writer_default (GLogLevelFlags   log_level,
2748
                      const GLogField *fields,
2749
                      gsize            n_fields,
2750
                      gpointer         user_data)
2751
3.98M
{
2752
3.98M
  static gsize initialized = 0;
2753
3.98M
  static gboolean stderr_is_journal = FALSE;
2754
2755
3.98M
  g_return_val_if_fail (fields != NULL, G_LOG_WRITER_UNHANDLED);
2756
3.98M
  g_return_val_if_fail (n_fields > 0, G_LOG_WRITER_UNHANDLED);
2757
2758
3.98M
  if (should_drop_message (log_level, NULL, fields, n_fields))
2759
3.94M
    return G_LOG_WRITER_HANDLED;
2760
2761
  /* Mark messages as fatal if they have a level set in
2762
   * g_log_set_always_fatal().
2763
   */
2764
33.9k
  if ((log_level & g_log_always_fatal) && !log_is_old_api (fields, n_fields))
2765
0
    log_level |= G_LOG_FLAG_FATAL;
2766
2767
  /* Try logging to the systemd journal as first choice. */
2768
33.9k
  if (g_once_init_enter (&initialized))
2769
8
    {
2770
8
      stderr_is_journal = g_log_writer_is_journald (fileno (stderr));
2771
8
      g_once_init_leave (&initialized, TRUE);
2772
8
    }
2773
2774
33.9k
  if (stderr_is_journal &&
2775
0
      g_log_writer_journald (log_level, fields, n_fields, user_data) ==
2776
0
      G_LOG_WRITER_HANDLED)
2777
0
    goto handled;
2778
2779
  /* FIXME: Add support for the Windows log. */
2780
2781
33.9k
  if (g_log_writer_standard_streams (log_level, fields, n_fields, user_data) ==
2782
33.9k
      G_LOG_WRITER_HANDLED)
2783
33.9k
    goto handled;
2784
2785
0
  return G_LOG_WRITER_UNHANDLED;
2786
2787
33.9k
handled:
2788
  /* Abort if the message was fatal. */
2789
33.9k
  if (log_level & G_LOG_FLAG_FATAL)
2790
0
    {
2791
      /* MessageBox is allowed on UWP apps only when building against
2792
       * the debug CRT, which will set -D_DEBUG */
2793
#if defined(G_OS_WIN32) && (defined(_DEBUG) || !defined(G_WINAPI_ONLY_APP))
2794
      if (!g_test_initialized ())
2795
        {
2796
          WCHAR *wide_msg;
2797
2798
          wide_msg = g_utf8_to_utf16 (fatal_msg_buf, -1, NULL, NULL, NULL);
2799
2800
          MessageBoxW (NULL, wide_msg, NULL, MB_ICONERROR | MB_SETFOREGROUND);
2801
2802
          g_free (wide_msg);
2803
        }
2804
#endif /* !G_OS_WIN32 */
2805
2806
0
      _g_log_abort (!(log_level & G_LOG_FLAG_RECURSION));
2807
0
    }
2808
2809
33.9k
  return G_LOG_WRITER_HANDLED;
2810
33.9k
}
2811
2812
static GLogWriterOutput
2813
_g_log_writer_fallback (GLogLevelFlags   log_level,
2814
                        const GLogField *fields,
2815
                        gsize            n_fields,
2816
                        gpointer         user_data)
2817
0
{
2818
0
  FILE *stream;
2819
0
  gsize i;
2820
2821
  /* we cannot call _any_ GLib functions in this fallback handler,
2822
   * which is why we skip UTF-8 conversion, etc.
2823
   * since we either recursed or ran out of memory, we're in a pretty
2824
   * pathologic situation anyways, what we can do is giving the
2825
   * the process ID unconditionally however.
2826
   */
2827
2828
0
  stream = log_level_to_file (log_level);
2829
2830
0
  for (i = 0; i < n_fields; i++)
2831
0
    {
2832
0
      const GLogField *field = &fields[i];
2833
2834
      /* Only print fields we definitely recognise, otherwise we could end up
2835
       * printing a random non-string pointer provided by the user to be
2836
       * interpreted by their writer function.
2837
       */
2838
0
      if (strcmp (field->key, "MESSAGE") != 0 &&
2839
0
          strcmp (field->key, "MESSAGE_ID") != 0 &&
2840
0
          strcmp (field->key, "PRIORITY") != 0 &&
2841
0
          strcmp (field->key, "CODE_FILE") != 0 &&
2842
0
          strcmp (field->key, "CODE_LINE") != 0 &&
2843
0
          strcmp (field->key, "CODE_FUNC") != 0 &&
2844
0
          strcmp (field->key, "ERRNO") != 0 &&
2845
0
          strcmp (field->key, "SYSLOG_FACILITY") != 0 &&
2846
0
          strcmp (field->key, "SYSLOG_IDENTIFIER") != 0 &&
2847
0
          strcmp (field->key, "SYSLOG_PID") != 0 &&
2848
0
          strcmp (field->key, "GLIB_DOMAIN") != 0)
2849
0
        continue;
2850
2851
0
      write_string (stream, field->key);
2852
0
      write_string (stream, "=");
2853
0
      write_string_sized (stream, field->value, field->length);
2854
0
    }
2855
2856
0
#ifndef G_OS_WIN32
2857
0
  {
2858
0
    gchar pid_string[FORMAT_UNSIGNED_BUFSIZE];
2859
2860
0
    format_unsigned (pid_string, getpid (), 10);
2861
0
    write_string (stream, "_PID=");
2862
0
    write_string (stream, pid_string);
2863
0
  }
2864
0
#endif
2865
2866
0
  return G_LOG_WRITER_HANDLED;
2867
0
}
2868
2869
/**
2870
 * g_return_if_fail_warning: (skip)
2871
 * @log_domain: (nullable): log domain
2872
 * @pretty_function: function containing the assertion
2873
 * @expression: (nullable): expression which failed
2874
 *
2875
 * Internal function used to print messages from the public g_return_if_fail()
2876
 * and g_return_val_if_fail() macros.
2877
 */
2878
void
2879
g_return_if_fail_warning (const char *log_domain,
2880
        const char *pretty_function,
2881
        const char *expression)
2882
4
{
2883
4
  g_log (log_domain,
2884
4
   G_LOG_LEVEL_CRITICAL,
2885
4
   "%s: assertion '%s' failed",
2886
4
   pretty_function,
2887
4
   expression);
2888
4
}
2889
2890
/**
2891
 * g_warn_message: (skip)
2892
 * @domain: (nullable): log domain
2893
 * @file: file containing the warning
2894
 * @line: line number of the warning
2895
 * @func: function containing the warning
2896
 * @warnexpr: (nullable): expression which failed
2897
 *
2898
 * Internal function used to print messages from the public g_warn_if_reached()
2899
 * and g_warn_if_fail() macros.
2900
 */
2901
void
2902
g_warn_message (const char     *domain,
2903
                const char     *file,
2904
                int             line,
2905
                const char     *func,
2906
                const char     *warnexpr)
2907
0
{
2908
0
  char *s, lstr[32];
2909
0
  g_snprintf (lstr, 32, "%d", line);
2910
0
  if (warnexpr)
2911
0
    s = g_strconcat ("(", file, ":", lstr, "):",
2912
0
                     func, func[0] ? ":" : "",
2913
0
                     " runtime check failed: (", warnexpr, ")", NULL);
2914
0
  else
2915
0
    s = g_strconcat ("(", file, ":", lstr, "):",
2916
0
                     func, func[0] ? ":" : "",
2917
0
                     " ", "code should not be reached", NULL);
2918
0
  g_log (domain, G_LOG_LEVEL_WARNING, "%s", s);
2919
0
  g_free (s);
2920
0
}
2921
2922
void
2923
g_assert_warning (const char *log_domain,
2924
      const char *file,
2925
      const int   line,
2926
      const char *pretty_function,
2927
      const char *expression)
2928
0
{
2929
0
  if (expression)
2930
0
    g_log (log_domain,
2931
0
     G_LOG_LEVEL_ERROR,
2932
0
     "file %s: line %d (%s): assertion failed: (%s)",
2933
0
     file,
2934
0
     line,
2935
0
     pretty_function,
2936
0
     expression);
2937
0
  else
2938
0
    g_log (log_domain,
2939
0
     G_LOG_LEVEL_ERROR,
2940
0
     "file %s: line %d (%s): should not be reached",
2941
0
     file,
2942
0
     line,
2943
0
     pretty_function);
2944
0
  _g_log_abort (FALSE);
2945
0
  g_abort ();
2946
0
}
2947
2948
/**
2949
 * g_test_expect_message:
2950
 * @log_domain: (nullable): the log domain of the message
2951
 * @log_level: the log level of the message
2952
 * @pattern: a glob-style [pattern][glib-Glob-style-pattern-matching]
2953
 *
2954
 * Indicates that a message with the given @log_domain and @log_level,
2955
 * with text matching @pattern, is expected to be logged. When this
2956
 * message is logged, it will not be printed, and the test case will
2957
 * not abort.
2958
 *
2959
 * This API may only be used with the old logging API (g_log() without
2960
 * %G_LOG_USE_STRUCTURED defined). It will not work with the structured logging
2961
 * API. See [Testing for Messages][testing-for-messages].
2962
 *
2963
 * Use g_test_assert_expected_messages() to assert that all
2964
 * previously-expected messages have been seen and suppressed.
2965
 *
2966
 * You can call this multiple times in a row, if multiple messages are
2967
 * expected as a result of a single call. (The messages must appear in
2968
 * the same order as the calls to g_test_expect_message().)
2969
 *
2970
 * For example:
2971
 *
2972
 * |[<!-- language="C" --> 
2973
 *   // g_main_context_push_thread_default() should fail if the
2974
 *   // context is already owned by another thread.
2975
 *   g_test_expect_message (G_LOG_DOMAIN,
2976
 *                          G_LOG_LEVEL_CRITICAL,
2977
 *                          "assertion*acquired_context*failed");
2978
 *   g_main_context_push_thread_default (bad_context);
2979
 *   g_test_assert_expected_messages ();
2980
 * ]|
2981
 *
2982
 * Note that you cannot use this to test g_error() messages, since
2983
 * g_error() intentionally never returns even if the program doesn't
2984
 * abort; use g_test_trap_subprocess() in this case.
2985
 *
2986
 * If messages at %G_LOG_LEVEL_DEBUG are emitted, but not explicitly
2987
 * expected via g_test_expect_message() then they will be ignored.
2988
 *
2989
 * Since: 2.34
2990
 */
2991
void
2992
g_test_expect_message (const gchar    *log_domain,
2993
                       GLogLevelFlags  log_level,
2994
                       const gchar    *pattern)
2995
0
{
2996
0
  GTestExpectedMessage *expected;
2997
2998
0
  g_return_if_fail (log_level != 0);
2999
0
  g_return_if_fail (pattern != NULL);
3000
0
  g_return_if_fail (~log_level & G_LOG_LEVEL_ERROR);
3001
3002
0
  expected = g_new (GTestExpectedMessage, 1);
3003
0
  expected->log_domain = g_strdup (log_domain);
3004
0
  expected->log_level = log_level;
3005
0
  expected->pattern = g_strdup (pattern);
3006
3007
0
  expected_messages = g_slist_append (expected_messages, expected);
3008
0
}
3009
3010
void
3011
g_test_assert_expected_messages_internal (const char     *domain,
3012
                                          const char     *file,
3013
                                          int             line,
3014
                                          const char     *func)
3015
0
{
3016
0
  if (expected_messages)
3017
0
    {
3018
0
      GTestExpectedMessage *expected;
3019
0
      gchar level_prefix[STRING_BUFFER_SIZE];
3020
0
      gchar *message;
3021
3022
0
      expected = expected_messages->data;
3023
3024
0
      mklevel_prefix (level_prefix, expected->log_level, FALSE);
3025
0
      message = g_strdup_printf ("Did not see expected message %s-%s: %s",
3026
0
                                 expected->log_domain ? expected->log_domain : "**",
3027
0
                                 level_prefix, expected->pattern);
3028
0
      g_assertion_message (G_LOG_DOMAIN, file, line, func, message);
3029
0
      g_free (message);
3030
0
    }
3031
0
}
3032
3033
/**
3034
 * g_test_assert_expected_messages:
3035
 *
3036
 * Asserts that all messages previously indicated via
3037
 * g_test_expect_message() have been seen and suppressed.
3038
 *
3039
 * This API may only be used with the old logging API (g_log() without
3040
 * %G_LOG_USE_STRUCTURED defined). It will not work with the structured logging
3041
 * API. See [Testing for Messages][testing-for-messages].
3042
 *
3043
 * If messages at %G_LOG_LEVEL_DEBUG are emitted, but not explicitly
3044
 * expected via g_test_expect_message() then they will be ignored.
3045
 *
3046
 * Since: 2.34
3047
 */
3048
3049
void
3050
_g_log_fallback_handler (const gchar   *log_domain,
3051
       GLogLevelFlags log_level,
3052
       const gchar   *message,
3053
       gpointer       unused_data)
3054
0
{
3055
0
  gchar level_prefix[STRING_BUFFER_SIZE];
3056
0
#ifndef G_OS_WIN32
3057
0
  gchar pid_string[FORMAT_UNSIGNED_BUFSIZE];
3058
0
#endif
3059
0
  FILE *stream;
3060
3061
  /* we cannot call _any_ GLib functions in this fallback handler,
3062
   * which is why we skip UTF-8 conversion, etc.
3063
   * since we either recursed or ran out of memory, we're in a pretty
3064
   * pathologic situation anyways, what we can do is giving the
3065
   * the process ID unconditionally however.
3066
   */
3067
3068
0
  stream = mklevel_prefix (level_prefix, log_level, FALSE);
3069
0
  if (!message)
3070
0
    message = "(NULL) message";
3071
3072
0
#ifndef G_OS_WIN32
3073
0
  format_unsigned (pid_string, getpid (), 10);
3074
0
#endif
3075
3076
0
  if (log_domain)
3077
0
    write_string (stream, "\n");
3078
0
  else
3079
0
    write_string (stream, "\n** ");
3080
3081
0
#ifndef G_OS_WIN32
3082
0
  write_string (stream, "(process:");
3083
0
  write_string (stream, pid_string);
3084
0
  write_string (stream, "): ");
3085
0
#endif
3086
3087
0
  if (log_domain)
3088
0
    {
3089
0
      write_string (stream, log_domain);
3090
0
      write_string (stream, "-");
3091
0
    }
3092
0
  write_string (stream, level_prefix);
3093
0
  write_string (stream, ": ");
3094
0
  write_string (stream, message);
3095
0
}
3096
3097
static void
3098
escape_string (GString *string)
3099
33.9k
{
3100
33.9k
  const char *p = string->str;
3101
33.9k
  gunichar wc;
3102
3103
2.09M
  while (p < string->str + string->len)
3104
2.05M
    {
3105
2.05M
      gboolean safe;
3106
      
3107
2.05M
      wc = g_utf8_get_char_validated (p, -1);
3108
2.05M
      if (wc == (gunichar)-1 || wc == (gunichar)-2)  
3109
0
  {
3110
0
    gchar *tmp;
3111
0
    guint pos;
3112
3113
0
    pos = p - string->str;
3114
3115
    /* Emit invalid UTF-8 as hex escapes 
3116
           */
3117
0
    tmp = g_strdup_printf ("\\x%02x", (guint)(guchar)*p);
3118
0
    g_string_erase (string, pos, 1);
3119
0
    g_string_insert (string, pos, tmp);
3120
3121
0
    p = string->str + (pos + 4); /* Skip over escape sequence */
3122
3123
0
    g_free (tmp);
3124
0
    continue;
3125
0
  }
3126
2.05M
      if (wc == '\r')
3127
0
  {
3128
0
    safe = *(p + 1) == '\n';
3129
0
  }
3130
2.05M
      else
3131
2.05M
  {
3132
2.05M
    safe = CHAR_IS_SAFE (wc);
3133
2.05M
  }
3134
      
3135
2.05M
      if (!safe)
3136
0
  {
3137
0
    gchar *tmp;
3138
0
    guint pos;
3139
3140
0
    pos = p - string->str;
3141
    
3142
    /* Largest char we escape is 0x0a, so we don't have to worry
3143
     * about 8-digit \Uxxxxyyyy
3144
     */
3145
0
    tmp = g_strdup_printf ("\\u%04x", wc); 
3146
0
    g_string_erase (string, pos, g_utf8_next_char (p) - p);
3147
0
    g_string_insert (string, pos, tmp);
3148
0
    g_free (tmp);
3149
3150
0
    p = string->str + (pos + 6); /* Skip over escape sequence */
3151
0
  }
3152
2.05M
      else
3153
2.05M
  p = g_utf8_next_char (p);
3154
2.05M
    }
3155
33.9k
}
3156
3157
/**
3158
 * g_log_default_handler:
3159
 * @log_domain: (nullable): the log domain of the message, or %NULL for the
3160
 * default "" application domain
3161
 * @log_level: the level of the message
3162
 * @message: (nullable): the message
3163
 * @unused_data: (nullable): data passed from g_log() which is unused
3164
 *
3165
 * The default log handler set up by GLib; g_log_set_default_handler()
3166
 * allows to install an alternate default log handler.
3167
 * This is used if no log handler has been set for the particular log
3168
 * domain and log level combination. It outputs the message to stderr
3169
 * or stdout and if the log level is fatal it calls G_BREAKPOINT(). It automatically
3170
 * prints a new-line character after the message, so one does not need to be
3171
 * manually included in @message.
3172
 *
3173
 * The behavior of this log handler can be influenced by a number of
3174
 * environment variables:
3175
 *
3176
 * - `G_MESSAGES_PREFIXED`: A :-separated list of log levels for which
3177
 *   messages should be prefixed by the program name and PID of the
3178
 *   application.
3179
 *
3180
 * - `G_MESSAGES_DEBUG`: A space-separated list of log domains for
3181
 *   which debug and informational messages are printed. By default
3182
 *   these messages are not printed.
3183
 *
3184
 * stderr is used for levels %G_LOG_LEVEL_ERROR, %G_LOG_LEVEL_CRITICAL,
3185
 * %G_LOG_LEVEL_WARNING and %G_LOG_LEVEL_MESSAGE. stdout is used for
3186
 * the rest, unless stderr was requested by
3187
 * g_log_writer_default_set_use_stderr().
3188
 *
3189
 * This has no effect if structured logging is enabled; see
3190
 * [Using Structured Logging][using-structured-logging].
3191
 */
3192
void
3193
g_log_default_handler (const gchar   *log_domain,
3194
           GLogLevelFlags log_level,
3195
           const gchar   *message,
3196
           gpointer       unused_data)
3197
3.98M
{
3198
3.98M
  GLogField fields[4];
3199
3.98M
  int n_fields = 0;
3200
3201
  /* we can be called externally with recursion for whatever reason */
3202
3.98M
  if (log_level & G_LOG_FLAG_RECURSION)
3203
0
    {
3204
0
      _g_log_fallback_handler (log_domain, log_level, message, unused_data);
3205
0
      return;
3206
0
    }
3207
3208
3.98M
  fields[0].key = "GLIB_OLD_LOG_API";
3209
3.98M
  fields[0].value = "1";
3210
3.98M
  fields[0].length = -1;
3211
3.98M
  n_fields++;
3212
3213
3.98M
  fields[1].key = "MESSAGE";
3214
3.98M
  fields[1].value = message;
3215
3.98M
  fields[1].length = -1;
3216
3.98M
  n_fields++;
3217
3218
3.98M
  fields[2].key = "PRIORITY";
3219
3.98M
  fields[2].value = log_level_to_priority (log_level);
3220
3.98M
  fields[2].length = -1;
3221
3.98M
  n_fields++;
3222
3223
3.98M
  if (log_domain)
3224
3.89M
    {
3225
3.89M
      fields[3].key = "GLIB_DOMAIN";
3226
3.89M
      fields[3].value = log_domain;
3227
3.89M
      fields[3].length = -1;
3228
3.89M
      n_fields++;
3229
3.89M
    }
3230
3231
  /* Print out via the structured log API, but drop any fatal flags since we
3232
   * have already handled them. The fatal handling in the structured logging
3233
   * API is more coarse-grained than in the old g_log() API, so we don't want
3234
   * to use it here.
3235
   */
3236
3.98M
  g_log_structured_array (log_level & ~G_LOG_FLAG_FATAL, fields, n_fields);
3237
3.98M
}
3238
3239
/**
3240
 * g_set_print_handler:
3241
 * @func: the new print handler
3242
 *
3243
 * Sets the print handler.
3244
 *
3245
 * Any messages passed to g_print() will be output via
3246
 * the new handler. The default handler simply outputs
3247
 * the message to stdout. By providing your own handler
3248
 * you can redirect the output, to a GTK+ widget or a
3249
 * log file for example.
3250
 *
3251
 * Returns: the old print handler
3252
 */
3253
GPrintFunc
3254
g_set_print_handler (GPrintFunc func)
3255
0
{
3256
0
  GPrintFunc old_print_func;
3257
3258
0
  g_mutex_lock (&g_messages_lock);
3259
0
  old_print_func = glib_print_func;
3260
0
  glib_print_func = func;
3261
0
  g_mutex_unlock (&g_messages_lock);
3262
3263
0
  return old_print_func;
3264
0
}
3265
3266
/**
3267
 * g_print:
3268
 * @format: the message format. See the printf() documentation
3269
 * @...: the parameters to insert into the format string
3270
 *
3271
 * Outputs a formatted message via the print handler.
3272
 * The default print handler simply outputs the message to stdout, without
3273
 * appending a trailing new-line character. Typically, @format should end with
3274
 * its own new-line character.
3275
 *
3276
 * g_print() should not be used from within libraries for debugging
3277
 * messages, since it may be redirected by applications to special
3278
 * purpose message windows or even files. Instead, libraries should
3279
 * use g_log(), g_log_structured(), or the convenience macros g_message(),
3280
 * g_warning() and g_error().
3281
 */
3282
void
3283
g_print (const gchar *format,
3284
         ...)
3285
0
{
3286
0
  va_list args;
3287
0
  gchar *string;
3288
0
  GPrintFunc local_glib_print_func;
3289
3290
0
  g_return_if_fail (format != NULL);
3291
3292
0
  va_start (args, format);
3293
0
  string = g_strdup_vprintf (format, args);
3294
0
  va_end (args);
3295
3296
0
  g_mutex_lock (&g_messages_lock);
3297
0
  local_glib_print_func = glib_print_func;
3298
0
  g_mutex_unlock (&g_messages_lock);
3299
3300
0
  if (local_glib_print_func)
3301
0
    local_glib_print_func (string);
3302
0
  else
3303
0
    {
3304
0
      const gchar *charset;
3305
3306
0
      if (g_get_console_charset (&charset))
3307
0
        fputs (string, stdout); /* charset is UTF-8 already */
3308
0
      else
3309
0
        {
3310
0
          gchar *lstring = strdup_convert (string, charset);
3311
3312
0
          fputs (lstring, stdout);
3313
0
          g_free (lstring);
3314
0
        }
3315
0
      fflush (stdout);
3316
0
    }
3317
0
  g_free (string);
3318
0
}
3319
3320
/**
3321
 * g_set_printerr_handler:
3322
 * @func: the new error message handler
3323
 *
3324
 * Sets the handler for printing error messages.
3325
 *
3326
 * Any messages passed to g_printerr() will be output via
3327
 * the new handler. The default handler simply outputs the
3328
 * message to stderr. By providing your own handler you can
3329
 * redirect the output, to a GTK+ widget or a log file for
3330
 * example.
3331
 *
3332
 * Returns: the old error message handler
3333
 */
3334
GPrintFunc
3335
g_set_printerr_handler (GPrintFunc func)
3336
0
{
3337
0
  GPrintFunc old_printerr_func;
3338
3339
0
  g_mutex_lock (&g_messages_lock);
3340
0
  old_printerr_func = glib_printerr_func;
3341
0
  glib_printerr_func = func;
3342
0
  g_mutex_unlock (&g_messages_lock);
3343
3344
0
  return old_printerr_func;
3345
0
}
3346
3347
/**
3348
 * g_printerr:
3349
 * @format: the message format. See the printf() documentation
3350
 * @...: the parameters to insert into the format string
3351
 *
3352
 * Outputs a formatted message via the error message handler.
3353
 * The default handler simply outputs the message to stderr, without appending
3354
 * a trailing new-line character. Typically, @format should end with its own
3355
 * new-line character.
3356
 *
3357
 * g_printerr() should not be used from within libraries.
3358
 * Instead g_log() or g_log_structured() should be used, or the convenience
3359
 * macros g_message(), g_warning() and g_error().
3360
 */
3361
void
3362
g_printerr (const gchar *format,
3363
            ...)
3364
0
{
3365
0
  va_list args;
3366
0
  gchar *string;
3367
0
  GPrintFunc local_glib_printerr_func;
3368
3369
0
  g_return_if_fail (format != NULL);
3370
3371
0
  va_start (args, format);
3372
0
  string = g_strdup_vprintf (format, args);
3373
0
  va_end (args);
3374
3375
0
  g_mutex_lock (&g_messages_lock);
3376
0
  local_glib_printerr_func = glib_printerr_func;
3377
0
  g_mutex_unlock (&g_messages_lock);
3378
3379
0
  if (local_glib_printerr_func)
3380
0
    local_glib_printerr_func (string);
3381
0
  else
3382
0
    {
3383
0
      const gchar *charset;
3384
3385
0
      if (g_get_console_charset (&charset))
3386
0
        fputs (string, stderr); /* charset is UTF-8 already */
3387
0
      else
3388
0
        {
3389
0
          gchar *lstring = strdup_convert (string, charset);
3390
3391
0
          fputs (lstring, stderr);
3392
0
          g_free (lstring);
3393
0
        }
3394
0
      fflush (stderr);
3395
0
    }
3396
0
  g_free (string);
3397
0
}
3398
3399
/**
3400
 * g_printf_string_upper_bound:
3401
 * @format: the format string. See the printf() documentation
3402
 * @args: the parameters to be inserted into the format string
3403
 *
3404
 * Calculates the maximum space needed to store the output
3405
 * of the sprintf() function.
3406
 *
3407
 * Returns: the maximum space needed to store the formatted string
3408
 */
3409
gsize
3410
g_printf_string_upper_bound (const gchar *format,
3411
                             va_list      args)
3412
0
{
3413
0
  gchar c;
3414
0
  return _g_vsnprintf (&c, 1, format, args) + 1;
3415
0
}