/* Unit tests for GThread
 * Copyright (C) 2011 Red Hat, Inc
 * Author: Matthias Clasen
 *
 * This work is provided "as is"; redistribution and modification
 * in whole or in part, in any medium, physical or electronic is
 * permitted without restriction.
 *
 * This work 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.
 *
 * In no event shall the authors or contributors be liable for any
 * direct, indirect, incidental, special, exemplary, or consequential
 * damages (including, but not limited to, procurement of substitute
 * goods or services; loss of use, data, or profits; or business
 * interruption) however caused and on any theory of liability, whether
 * in contract, strict liability, or tort (including negligence or
 * otherwise) arising in any way out of the use of this software, even
 * if advised of the possibility of such damage.
 */

#include <config.h>

#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
#endif
#include <sys/types.h>
#ifdef HAVE_SYS_PRCTL_H
#include <sys/prctl.h>
#endif

#include <glib.h>

#ifdef G_OS_UNIX
#include <unistd.h>
#include <sys/resource.h>
#endif

static gpointer
thread1_func (gpointer data)
{
  g_thread_exit (GINT_TO_POINTER (1));

  g_assert_not_reached ();

  return NULL;
}

/* test that g_thread_exit() works */
static void
test_thread1 (void)
{
  gpointer result;
  GThread *thread;
  GError *error = NULL;

  thread = g_thread_try_new ("test", thread1_func, NULL, &error);
  g_assert_no_error (error);

  result = g_thread_join (thread);

  g_assert_cmpint (GPOINTER_TO_INT (result), ==, 1);
}

static gpointer
thread2_func (gpointer data)
{
  return g_thread_self ();
}

/* test that g_thread_self() works */
static void
test_thread2 (void)
{
  gpointer result;
  GThread *thread;

  thread = g_thread_new ("test", thread2_func, NULL);

  g_assert (g_thread_self () != thread);

  result = g_thread_join (thread);

  g_assert (result == thread);
}

static gpointer
thread3_func (gpointer data)
{
  GThread *peer = data;
  gint retval;

  retval = 3;

  if (peer)
    {
      gpointer result;

      result = g_thread_join (peer);

      retval += GPOINTER_TO_INT (result);
    }

  return GINT_TO_POINTER (retval);
}

/* test that g_thread_join() works across peers */
static void
test_thread3 (void)
{
  gpointer result;
  GThread *thread1, *thread2, *thread3;

  thread1 = g_thread_new ("a", thread3_func, NULL);
  thread2 = g_thread_new ("b", thread3_func, thread1);
  thread3 = g_thread_new ("c", thread3_func, thread2);

  result = g_thread_join (thread3);

  g_assert_cmpint (GPOINTER_TO_INT(result), ==, 9);
}

/* test that thread creation fails as expected,
 * by setting RLIMIT_NPROC ridiculously low
 */
static void
test_thread4 (void)
{
#ifdef HAVE_PRLIMIT
  struct rlimit ol, nl;
  GThread *thread;
  GError *error;
  gint ret;

  /* Linux CAP_SYS_RESOURCE overrides RLIMIT_NPROC, and probably similar
   * things are true on other systems.
   */
  if (getuid () == 0 || geteuid () == 0)
    return;

  getrlimit (RLIMIT_NPROC, &nl);
  nl.rlim_cur = 1;

  if ((ret = prlimit (getpid(), RLIMIT_NPROC, &nl, &ol)) != 0)
    g_error ("prlimit failed: %s\n", g_strerror (ret));

  error = NULL;
  thread = g_thread_try_new ("a", thread1_func, NULL, &error);
  g_assert (thread == NULL);
  g_assert_error (error, G_THREAD_ERROR, G_THREAD_ERROR_AGAIN);
  g_error_free (error);

  if ((ret = prlimit (getpid (), RLIMIT_NPROC, &ol, NULL)) != 0)
    g_error ("resetting RLIMIT_NPROC failed: %s\n", g_strerror (ret));
#endif
}

static void
test_thread5 (void)
{
  GThread *thread;

  thread = g_thread_new ("a", thread3_func, NULL);
  g_thread_ref (thread);
  g_thread_join (thread);
  g_thread_unref (thread);
}

static gpointer
thread6_func (gpointer data)
{
#ifdef HAVE_SYS_PRCTL_H
#ifdef PR_GET_NAME
  const gchar name[16];

  prctl (PR_GET_NAME, name, 0, 0, 0, 0);

  g_assert_cmpstr (name, ==, (gchar*)data);
#endif
#endif

  return NULL;
}

static void
test_thread6 (void)
{
  GThread *thread;

  thread = g_thread_new ("abc", thread6_func, "abc");
  g_thread_join (thread);
}

int
main (int argc, char *argv[])
{
  g_test_init (&argc, &argv, NULL);

  g_test_add_func ("/thread/thread1", test_thread1);
  g_test_add_func ("/thread/thread2", test_thread2);
  g_test_add_func ("/thread/thread3", test_thread3);
  g_test_add_func ("/thread/thread4", test_thread4);
  g_test_add_func ("/thread/thread5", test_thread5);
  g_test_add_func ("/thread/thread6", test_thread6);

  return g_test_run ();
}
