/* Run a function on the main thread
   Copyright (C) 2019-2025 Free Software Foundation, Inc.

   This file is part of GDB.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program 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 General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */

#include "run-on-main-thread.h"
#include "ser-event.h"
#if CXX_STD_THREAD
#include <thread>
#include <mutex>
#endif
#include "gdbsupport/cleanups.h"
#include "gdbsupport/event-loop.h"

/* The serial event used when posting runnables.  */

static struct serial_event *runnable_event;

/* Runnables that have been posted.  */

static std::vector<std::function<void ()>> runnables;

#if CXX_STD_THREAD

/* Mutex to hold when handling RUNNABLE_EVENT or RUNNABLES.  */

static std::mutex runnable_mutex;

/* The main thread's thread id.  */

static std::thread::id main_thread_id;

#endif

/* Run all the queued runnables.  */

static void
run_events (int error, gdb_client_data client_data)
{
  std::vector<std::function<void ()>> local;

  /* Hold the lock while changing the globals, but not while running
     the runnables.  */
  {
#if CXX_STD_THREAD
    std::lock_guard<std::mutex> lock (runnable_mutex);
#endif

    /* Clear the event fd.  Do this before flushing the events list,
       so that any new event post afterwards is sure to re-awaken the
       event loop.  */
    serial_event_clear (runnable_event);

    /* Move the vector in case running a runnable pushes a new
       runnable.  */
    local = std::move (runnables);
  }

  for (auto &item : local)
    {
      try
	{
	  item ();
	}
      catch (const gdb_exception_forced_quit &e)
	{
	  /* GDB is terminating, so:
	     - make sure this is propagated, and
	     - no need to keep running things, so propagate immediately.  */
	  throw;
	}
      catch (const gdb_exception_quit &e)
	{
	  /* Should cancellation of a runnable event cancel the execution of
	     the following one?  The answer is not clear, so keep doing what
	     we've done so far: ignore this exception.  */
	}
      catch (const gdb_exception &)
	{
	  /* Ignore exceptions in the callback.  */
	}
    }
}

/* See run-on-main-thread.h.  */

void
run_on_main_thread (std::function<void ()> &&func)
{
#if CXX_STD_THREAD
  std::lock_guard<std::mutex> lock (runnable_mutex);
#endif
  runnables.emplace_back (std::move (func));
  serial_event_set (runnable_event);
}

#if CXX_STD_THREAD
static bool main_thread_id_initialized = false;
#endif

/* See run-on-main-thread.h.  */

bool
is_main_thread ()
{
#if CXX_STD_THREAD
  /* Initialize main_thread_id on first use of is_main_thread.  */
  if (!main_thread_id_initialized)
    {
      main_thread_id_initialized = true;

      main_thread_id = std::this_thread::get_id ();
    }

  return std::this_thread::get_id () == main_thread_id;
#else
  return true;
#endif
}

INIT_GDB_FILE (run_on_main_thread)
{
#if CXX_STD_THREAD
  /* The variable main_thread_id should be initialized when entering main, or
     at an earlier use, so it should already be initialized here.  */
  gdb_assert (main_thread_id_initialized);

  /* Assume that we execute this in the main thread.  */
  gdb_assert (is_main_thread ());
#endif
  runnable_event = make_serial_event ();
  add_file_handler (serial_event_fd (runnable_event), run_events, nullptr,
		    "run-on-main-thread");

  /* A runnable may refer to an extension language.  So, we want to
     make sure any pending ones have been deleted before the extension
     languages are shut down.  */
  add_final_cleanup ([] ()
    {
#if CXX_STD_THREAD
      std::lock_guard lock (runnable_mutex);
#endif
      runnables.clear ();
    });
}
