
/*--------------------------------------------------------------------*/
/*--- The thread state.                            m_threadstate.c ---*/
/*--------------------------------------------------------------------*/

/*
   This file is part of Valgrind, a dynamic binary instrumentation
   framework.

   Copyright (C) 2000-2013 Julian Seward 
      jseward@acm.org

   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 2 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, write to the Free Software
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
   02111-1307, USA.

   The GNU General Public License is contained in the file COPYING.
*/

#include "pub_core_basics.h"
#include "pub_core_vki.h"
#include "pub_core_libcsetjmp.h"    // to keep _threadstate.h happy
#include "pub_core_threadstate.h"
#include "pub_core_mallocfree.h"    // VG_(malloc)
#include "pub_core_libcassert.h"
#include "pub_core_inner.h"
#if defined(ENABLE_INNER_CLIENT_REQUEST)
#include "helgrind/helgrind.h"
#endif

/*------------------------------------------------------------*/
/*--- Data structures.                                     ---*/
/*------------------------------------------------------------*/

ThreadId VG_(running_tid) = VG_INVALID_THREADID;

ThreadState *VG_(threads);
UInt VG_N_THREADS;

/*------------------------------------------------------------*/
/*--- Operations.                                          ---*/
/*------------------------------------------------------------*/

void VG_(init_Threads)(void)
{
   ThreadId tid;
   UChar *addr, *aligned_addr;

   addr = VG_(malloc)("init_Threads",
          VG_N_THREADS * sizeof VG_(threads)[0] + LibVEX_GUEST_STATE_ALIGN - 1);

   // Align
   aligned_addr = addr + (Addr)addr % LibVEX_GUEST_STATE_ALIGN;
   VG_(threads) = (ThreadState *)aligned_addr;

   for (tid = 1; tid < VG_N_THREADS; tid++) {
      INNER_REQUEST(
         ANNOTATE_BENIGN_RACE_SIZED(&VG_(threads)[tid].status,
                                    sizeof(VG_(threads)[tid].status), ""));
      INNER_REQUEST(
         ANNOTATE_BENIGN_RACE_SIZED(&VG_(threads)[tid].os_state.exitcode,
                                    sizeof(VG_(threads)[tid].os_state.exitcode),
                                    ""));
   }
}

const HChar* VG_(name_of_ThreadStatus) ( ThreadStatus status )
{
   switch (status) {
   case VgTs_Empty:     return "VgTs_Empty";
   case VgTs_Init:      return "VgTs_Init";
   case VgTs_Runnable:  return "VgTs_Runnable";
   case VgTs_WaitSys:   return "VgTs_WaitSys";
   case VgTs_Yielding:  return "VgTs_Yielding";
   case VgTs_Zombie:    return "VgTs_Zombie";
   default:             return "VgTs_???";
  }
}

const HChar* VG_(name_of_VgSchedReturnCode) ( VgSchedReturnCode retcode )
{
   switch (retcode) {
   case VgSrc_None:        return "VgSrc_None";
   case VgSrc_ExitThread:  return "VgSrc_ExitThread";
   case VgSrc_ExitProcess: return "VgSrc_ExitProcess";
   case VgSrc_FatalSig:    return "VgSrc_FatalSig";
   default:                return "VgSrc_???";
  }
}

ThreadState *VG_(get_ThreadState)(ThreadId tid)
{
   vg_assert(tid >= 0 && tid < VG_N_THREADS);
   vg_assert(VG_(threads)[tid].tid == tid);
   return &VG_(threads)[tid];
}

Bool VG_(is_valid_tid) ( ThreadId tid )
{
   /* tid is unsigned, hence no < 0 test. */
   if (tid == 0) return False;
   if (tid >= VG_N_THREADS) return False;
   if (VG_(threads)[tid].status == VgTs_Empty) return False;
   return True;
}

// This function is for tools to call.
ThreadId VG_(get_running_tid)(void)
{
   return VG_(running_tid);
}

Bool VG_(is_running_thread)(ThreadId tid)
{
   ThreadState *tst = VG_(get_ThreadState)(tid);

   return 
//      tst->os_state.lwpid == VG_(gettid)() &&	// check we're this tid
      VG_(running_tid) == tid	           &&	// and that we've got the lock
      tst->status == VgTs_Runnable;		// and we're runnable
}

/* Return true if the thread is still alive but in the process of exiting. */
inline Bool VG_(is_exiting)(ThreadId tid)
{
   vg_assert(VG_(is_valid_tid)(tid));
   return VG_(threads)[tid].exitreason != VgSrc_None;
}

/* Return the number of non-dead Threads */
Int VG_(count_living_threads)(void)
{
   Int count = 0;
   ThreadId tid;

   for(tid = 1; tid < VG_N_THREADS; tid++)
      if (VG_(threads)[tid].status != VgTs_Empty &&
	  VG_(threads)[tid].status != VgTs_Zombie)
	 count++;

   return count;
}

/* Return the number of threads in VgTs_Runnable state */
Int VG_(count_runnable_threads)(void)
{
   Int count = 0;
   ThreadId tid;

   for(tid = 1; tid < VG_N_THREADS; tid++)
      if (VG_(threads)[tid].status == VgTs_Runnable)
	 count++;

   return count;
}

/* Given an LWP id (ie, real kernel thread id), find the corresponding
   ThreadId */
ThreadId VG_(lwpid_to_vgtid)(Int lwp)
{
   ThreadId tid;
   
   for(tid = 1; tid < VG_N_THREADS; tid++)
      if (VG_(threads)[tid].status != VgTs_Empty 
          && VG_(threads)[tid].os_state.lwpid == lwp)
	 return tid;

   return VG_INVALID_THREADID;
}

/*--------------------------------------------------------------------*/
/*--- end                                                          ---*/
/*--------------------------------------------------------------------*/
