<commit_before>/* GLib testing framework runner
 * Copyright (C) 2007 <NAME>
 * Copyright (C) 2007 <NAME>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
 */
#include "config.h"

#include <glib.h>
#include <glib-unix.h>
#include <gstdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/wait.h>
#include <errno.h>
#include <signal.h>

/* the read buffer size in bytes */
#define READ_BUFFER_SIZE 4096

/* --- prototypes --- */
static int      main_selftest   (int    argc,
                                 char **argv);
static void     parse_args      (gint           *argc_p,
                                 gchar        ***argv_p);

/* --- variables --- */
static GIOChannel  *ioc_report = NULL;
static gboolean     gtester_quiet = FALSE;
static gboolean     gtester_verbose = FALSE;
static gboolean     gtester_list_tests = FALSE;
static gboolean     gtester_selftest = FALSE;
static gboolean     subtest_running = FALSE;
static gint         subtest_exitstatus = 0;
static gboolean     subtest_io_pending = FALSE;
static gboolean     subtest_quiet = TRUE;
static gboolean     subtest_verbose = FALSE;
static gboolean     subtest_mode_fatal = TRUE;
static gboolean     subtest_mode_perf = FALSE;
static gboolean     subtest_mode_quick = TRUE;
static gboolean     subtest_mode_undefined = TRUE;
static const gchar *subtest_seedstr = NULL;
static gchar       *subtest_last_seed = NULL;
static GSList      *subtest_paths = NULL;
static GSList      *skipped_paths = NULL;
static GSList      *subtest_args = NULL;
static gboolean     testcase_open = FALSE;
static guint        testcase_count = 0;
static guint        testcase_fail_count = 0;
static const gchar *output_filename = NULL;
static guint        log_indent = 0;
static gint         log_fd = -1;

/* --- functions --- */
static const char*
sindent (guint n)
{
  static const char spaces[] = "                                                                                                    ";
  int l = sizeof (spaces) - 1;
  n = MIN (n, l);
  return spaces + l - n;
}

static void G_GNUC_PRINTF (1, 2)
test_log_printfe (const char *format,
                  ...)
{
  char *result;
  int r;
  va_list args;
  va_start (args, format);
  result = g_markup_vprintf_escaped (format, args);
  va_end (args);
  do
    r = write (log_fd, result, strlen (result));
  while (r < 0 && errno == EINTR);
  g_free (result);
}

static void
terminate (void)
{
  kill (getpid(), SIGTERM);
  g_abort();
}

static void
testcase_close (long double duration,
                gint        exit_status,
                guint       n_forks)
{
  gboolean success;

  g_return_if_fail (testcase_open > 0);
  test_log_printfe ("%s<duration>%.6Lf</duration>\n", sindent (log_indent), duration);
  success = exit_status == G_TEST_RUN_SUCCESS || exit_status == G_TEST_RUN_SKIPPED;
  test_log_printfe ("%s<status exit-status=\"%d\" n-forks=\"%d\" result=\"%s\"/>\n",
                    sindent (log_indent), exit_status, n_forks,
                    success ? "failed" : "success");
  log_indent -= 2;
  test_log_printfe ("%s</testcase>\n", sindent (log_indent));
  testcase_open--;<commit_msg>gtester: fix test result in gtester XML report<commit_after>/* GLib testing framework runner
 * Copyright (C) 2007 <NAME>
 * Copyright (C) 2007 <NAME>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
 */
#include "config.h"

#include <glib.h>
#include <glib-unix.h>
#include <gstdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/wait.h>
#include <errno.h>
#include <signal.h>

/* the read buffer size in bytes */
#define READ_BUFFER_SIZE 4096

/* --- prototypes --- */
static int      main_selftest   (int    argc,
                                 char **argv);
static void     parse_args      (gint           *argc_p,
                                 gchar        ***argv_p);

/* --- variables --- */
static GIOChannel  *ioc_report = NULL;
static gboolean     gtester_quiet = FALSE;
static gboolean     gtester_verbose = FALSE;
static gboolean     gtester_list_tests = FALSE;
static gboolean     gtester_selftest = FALSE;
static gboolean     subtest_running = FALSE;
static gint         subtest_exitstatus = 0;
static gboolean     subtest_io_pending = FALSE;
static gboolean     subtest_quiet = TRUE;
static gboolean     subtest_verbose = FALSE;
static gboolean     subtest_mode_fatal = TRUE;
static gboolean     subtest_mode_perf = FALSE;
static gboolean     subtest_mode_quick = TRUE;
static gboolean     subtest_mode_undefined = TRUE;
static const gchar *subtest_seedstr = NULL;
static gchar       *subtest_last_seed = NULL;
static GSList      *subtest_paths = NULL;
static GSList      *skipped_paths = NULL;
static GSList      *subtest_args = NULL;
static gboolean     testcase_open = FALSE;
static guint        testcase_count = 0;
static guint        testcase_fail_count = 0;
static const gchar *output_filename = NULL;
static guint        log_indent = 0;
static gint         log_fd = -1;

/* --- functions --- */
static const char*
sindent (guint n)
{
  static const char spaces[] = "                                                                                                    ";
  int l = sizeof (spaces) - 1;
  n = MIN (n, l);
  return spaces + l - n;
}

static void G_GNUC_PRINTF (1, 2)
test_log_printfe (const char *format,
                  ...)
{
  char *result;
  int r;
  va_list args;
  va_start (args, format);
  result = g_markup_vprintf_escaped (format, args);
  va_end (args);
  do
    r = write (log_fd, result, strlen (result));
  while (r < 0 && errno == EINTR);
  g_free (result);
}

static void
terminate (void)
{
  kill (getpid(), SIGTERM);
  g_abort();
}

static void
testcase_close (long double duration,
                gint        exit_status,
                guint       n_forks)
{
  gboolean success;

  g_return_if_fail (testcase_open > 0);
  test_log_printfe ("%s<duration>%.6Lf</duration>\n", sindent (log_indent), duration);
  success = exit_status == G_TEST_RUN_SUCCESS || exit_status == G_TEST_RUN_SKIPPED;
  test_log_printfe ("%s<status exit-status=\"%d\" n-forks=\"%d\" result=\"%s\"/>\n",
                    sindent (log_indent), exit_status, n_forks,
                    success ? "success" : "failed");
  log_indent -= 2;
  test_log_printfe ("%s</testcase>\n", sindent (log_indent));
  testcase_open--;
{'fraction_non_alphanumeric': 0.10200866482867271, 'fraction_numerical': 0.006826834711828804, 'mean_word_length': 2.6873184898354308, 'pattern_counts': {'":': 0, '<': 39, '<?xml version=': 0, '>': 39, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 12, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6763500', 'n_tokens_mistral': 2419, 'n_tokens_neox': 2336, 'n_words': 762}