/*
**      $RCSfile: sysmon.h,v $
**      $Filename: sysmon.h $
**      $Revision: 1.16 $
**      $Date: 2001/04/28 14:12:22 $
**
**	sysmon.library C header file (version 1.16)
**	
**	(C) Copyright 1995-2001 by Etienne Vogt
*/

#ifndef LIBRARIES_SYSMON_H
#define LIBRARIES_SYSMON_H

#ifndef EXEC_LIBRARIES_H
#include <exec/libraries.h>
#endif

#ifndef EXEC_SEMAPHORES_H
#include <exec/semaphores.h>
#endif

#ifndef EXEC_MEMORY_H
#include <exec/memory.h>
#endif

#ifndef DEVICES_TIMER_H
#include <devices/timer.h>
#endif

#ifndef DOS_DATETIME_H
#include <dos/datetime.h>
#endif

/* Library data structure
** All field in the SysmonBase structure are PRIVATE !!!
** Don't access these directly as they will change in future versions.
** You have been warned !!!
*/

#define	HASHSIZE	32
#define HASHMASK	0xf8

struct SysmonBase
{	struct Library sb_Lib;			/* Standard lib node */
	UBYTE	sb_Flags;			/* Some flags here */
	UBYTE	sb_pad;				/* We are now longword aligned */
	struct ExecBase *sb_ExecBase;		/* Pointer to exec */
	struct Library *sb_UtilityBase;		/* Pointer to utility */
	BPTR	sb_SegList;			/* SegList BCPL pointer */
	struct TaskInfo *sb_CurrTaskInfo;	/* Current TaskInfo Structure */
	APTR	sb_Switch;			/* Original Switch() entry point */
	APTR	sb_Dispatch;			/* Original Dispatch() entry point */
	APTR	sb_AddTask;			/* Original AddTask() entry point */
	APTR	sb_RemTask;			/* Original RemTask() entry point */
	APTR	sb_FindTask;			/* Original FindTask() entry point */
	APTR	sb_Alert;			/* Original Alert() entry point */
	APTR	sb_ExitIntr; 			/* Original ExitIntr() entry point */
	APTR	sb_Schedule; 			/* Original Schedule() entry point */
	APTR	sb_Exception; 			/* Original Exception() entry point */
	APTR	sb_SetTaskPri; 			/* Original SetTaskPri() entry point */
	APTR	sb_SetExcept; 			/* Original SetExcept() entry point */
	APTR	sb_SetSignal; 			/* Original SetSignal() entry point */
	APTR	sb_Signal; 			/* Original Signal() entry point */
	APTR	sb_Wait;			/* Original Wait() entry point */
	APTR	sb_TaskExit;			/* Original ExecBase->TaskExitCode */
	APTR	sb_TaskExcept;			/* Original ExecBase->TaskExceptCode */
	APTR	sb_TaskTrap;			/* Original ExecBase->TaskTrapCode */
	struct timerequest sb_TimeReq;		/* Time Request */
	struct EClockVal sb_TempTime;		/* Temporary EClock Time */
	struct List sb_TaskFrozen;		/* List of frozen tasks */
	BYTE	sb_ResetBit;			/* Signal bit for reset handler */
	UBYTE	sb_ResetFlags;			/* Flags for reset handler */
	struct TaskInfo *sb_TaskInfoHash[HASHSIZE]; /* TaskInfo hash table */
	APTR	sb_ServerEntry;			/* Server process entry point */
	STRPTR	sb_ServerName;			/* Server process name */
	STRPTR	sb_SyslogFile;			/* SysLog file name */
	STRPTR	sb_SyslogWindow;		/* Syslog Window Name */
	UBYTE	sb_FilePri;			/* File logging priority */
	UBYTE	sb_WindowPri;			/* Window logging priority */
	UBYTE	sb_ConsolePri;			/* Console logging priority */
	UBYTE	sb_NumLogBuffers;		/* Number of allocated Buffers */
	struct SysLogMsg *sb_Buffers;		/* Pointer to allocated buffers */
	struct DosLibrary *sb_DOSBase;		/* Pointer to dos */
	struct DateTime	*sb_DateTime;		/* SysLog DateTime structure */
	ULONG	sb_StampPeriod;			/* Period for syslog file stamp */
	BPTR	sb_LogWindowHandle;		/* LogWindow file handle */
	struct Library *sb_IntuitionBase;	/* Pointer to intuition */
	struct LastGuru	*sb_LastGuru;		/* Pointer to LastGuru structure */
	struct MsgPort *sb_SyslogPort;		/* Pointer to Syslog MsgPort */
	struct Process *sb_ServerProc;		/* Pointer to server process */
	struct Interrupt *sb_ResetHandler;	/* Pointer to reset handler */
	struct IOStdReq *sb_ResetReq;		/* Pointer to reset request */
	struct SignalSemaphore sb_BCPSem;	/* Semaphore for Broadcast Ports list */
	struct MinList sb_BroadcastPorts;	/* List of Registered Broadcast Ports */
	struct SignalSemaphore sb_TTASem;	/* Semaphore for Task Table Access */
	struct SignalSemaphore sb_TTRSem;	/* Semaphore for Task Table Removal */
	struct EClockVal sb_CPUTime;		/* Total CPU Time used by tasks */
	struct Library *sb_MMUBase;		/* Pointer to mmu library */
	APTR	sb_ColdReboot;			/* Cached ColdReboot() vector */
	ULONG	sb_VolTSw;			/* Voluntary Task Switches counter */
	ULONG	sb_InvTSw;			/* Involuntary Task Switches counter */
	struct Interrupt sb_LdAvrVBLInt;	/* Load Average VBL Interrupt */
	UWORD	sb_LdAvrPtr;			/* Pointer in Load Average circular buffer */
	UBYTE	sb_LdAvrBuffer[15*60];		/* Load Average circular Buffer, updated every
						   second from the sysmon.library VBlank interrupt */
};

/* The TaskInfo structure contains the CPU usage information in EClock ticks.
** The link pointers are private and should not be used. Use the smNextTaskInfo()
** function to traverse the list.
** This structure may be extended later with new fields. Also all fields are
** strictly READ ONLY.
*/

struct TaskInfo
{	struct TaskInfo *ti_Link;		/* PRIVATE pointer to next TaskInfo */
	struct TaskInfo *ti_Pred;		/* PRIVATE pointer to previous TaskInfo	*/
	struct Task *ti_Task;			/* pointer to Task Control Block */
	ULONG	ti_DispCount;			/* Task Dispatch counter */
	struct EClockVal ti_StartTime;		/* Starting EClock Time	*/
	struct EClockVal ti_LaunchTime;		/* Last Launch Time */
	struct EClockVal ti_CPUTime;		/* Cumulated CPU Time */
	UBYTE	ti_Flags;			/* Various flags */
	UBYTE	ti_ExcptState;			/* Task State saved by Exception() */
	BYTE	ti_EDNestCnt;			/* Exception Disable Nest Count */
	UBYTE	ti_FreezeState;			/* Task State saved by smFreeze() */
	ULONG	ti_VolTSw;			/* Voluntary Task Switches counter */
	ULONG	ti_InvTSw;			/* Involuntary Task Switches counter */
};

/* ti_Flags bits */

#define	TIB_INEXCEPT	0			/* Task is inside Exception code */
#define	TIF_INEXCEPT	(1L << 0)
#define	TIB_WAKEUP	1			/* A WakeUp request is pending */
#define TIF_WAKEUP	(1L << 1)

/* This is the private structure used by smVSysLog() to communicate with the
** Sysmon.server process.
*/

#define	SM_MAXLOGCHARS	256			/* Max bytes in SysLog message	*/

struct	SysLogMsg
{	struct Message	slm_MsgHead;		/* Message header	*/
	ULONG	slm_Priority;			/* SysLog priority and flags	*/
	UBYTE	slm_Text[SM_MAXLOGCHARS];	/* Syslog Message body	*/
};

#define	SYSMONNAME	"sysmon.library"
#define	SERVERNAME	"Sysmon.server"

/* Definition of sb_Flags bits	*/

#define SBFB_FPU	0			/* System has a FPU */
#define	SBFF_FPU	(1L << 0)
#define	SBFB_IDLELED	1			/* Dim power LED when CPU is idle */
#define	SBFF_IDLELED	(1L << 1)
#define SBFB_MMU	2			/* System has a MMU (according to mmu.library) */
#define SBFF_MMU	(1L << 2)

/* Definition of sb_ResetFlags bits */

#define	SBRSTB_ACTIVATE	0			/* Activate reset handler */
#define	SBRSTF_ACTIVATE	(1L << 0)
#define	SBRSTB_PENDING	1			/* Reset is pending */
#define SBRSTF_PENDING	(1L << 1)
#define	SBRSTB_OLDMMU	2			/* Restore old MMU setup before reboot */
#define	SBRSTF_OLDMMU	(1L << 2)
#define SBRSTB_CACHEREBOOT	3		/* Use a cached ColdReboot() vector */
#define SBRSTF_CACHEREBOOT	(1L << 3)

/* Alert Definitions
** These are the Guru codes that sysmon.library can spit out in a panic
** condition.
*/

#define	AN_Sysmon	0x40000000		/* SubSystem ID	*/
#define	AN_smNoTaskInfo	0x40000001		/* No TaskInfo structure for this task */
#define	AN_smNoTIMem	0x40010002		/* No mem for TaskInfo at startup	*/
#define	AN_smSysLogBuf	0x40010003		/* No memory for syslog buffers	*/
#define	AN_BadSysLogMsg	0x40000004		/* Bad SysLogMsg received by server */
#define	AN_smNoLastGuru	0x40010005		/* No memory for LastGuru buffer */
#define	AN_smNoAlertMem	0x40010006		/* No memory for new alert.hook module */
#define	AN_smSuperTaskSwitch 0xC0000007		/* Attempt to switch task from supervisor mode */
#define AO_Sysmon	0x00008040		/* Alert object	*/

/* These are reused obsolete exec alert codes */

#define	AN_UnInitExcpt	0x0100000A		/* Uninitialized task exception (not CPU trap) */

/* New Task States Definitions
** TS_STOP is not a real state. It is used by ShowSys to identify tasks that
** are stuck in a Wait(0) call, such as crashed tasks that have been suspended.
*/

#define	TS_STOP		0x80			/* Stopped task (Wait(0L)) */
#define	TS_FROZEN	0x81			/* Frozen task */
#define	TS_HIBERNATE	0x82			/* Hibernating task */
#define	TS_PAGEFLTWAIT	0x83			/* Task suspended for page fault processing */
#define	TS_WAITAND	0x84			/* Task waiting for several signals set together */
#define	TS_TRAP		0x85			/* Task suspended by exception trap code */
#define	TS_FREEWAIT	0x86			/* Task waiting for free memory */

/* SysLog Priorities, facilities and flags
** The priorities are similar to that used on UNIX systems. This means that
** the values use the UNIX ordering that is reversed from the Amiga one.
** The facilities are also UNIX like and indicate what part of the system
** produced the message. This is purely informational currently.
** The flags are Amiga and sysmon specifics.
*/

/* Priorities */

#define	LOG_EMERG	0			/* Panic condition (Guru time)	*/
#define	LOG_ALERT	1			/* Very serious problem	*/
#define LOG_CRIT	2			/* Critical error	*/
#define	LOG_ERR		3			/* General error condition	*/
#define	LOG_WARN	4			/* Warning condition	*/
#define	LOG_NOTICE	5			/* Noticeable event	*/
#define	LOG_INFO	6			/* General informational event	*/
#define	LOG_DEBUG	7			/* Debugging information	*/
#define	LOG_PRI		0x07			/* Mask for priority field	*/

/* Facilities */

#define	LOG_NOFAC	(0<<3)			/* no facility */
#define	LOG_KERN	(1<<3)			/* kernel/system messages */
#define	LOG_USER	(2<<3)			/* random user-level messages */
#define	LOG_MAIL	(3<<3)			/* mail system */
#define	LOG_DAEMON	(4<<3)			/* system daemons/commodities */
#define	LOG_AUTH	(5<<3)			/* security/authorization messages */
#define	LOG_SYSLOG	(6<<3)			/* messages generated internally by Syslog */
#define	LOG_NEWS	(7<<3)			/* network news subsystem */
#define	LOG_UUCP	(8<<3)			/* UUCP subsystem */
#define	LOG_CRON	(9<<3)			/* cron/queue_manager subsystem */
#define	LOG_AUTHPRIV	(10<<3)			/* private security/authorization messages */
#define	LOG_FTP		(11<<3)			/* ftp daemon */
/* other codes through 15 reserved for system use */
#define	LOG_LOCAL0	(16<<3)			/* reserved for local use */
#define	LOG_LOCAL1	(17<<3)			/* reserved for local use */
#define	LOG_LOCAL2	(18<<3)			/* reserved for local use */
#define	LOG_LOCAL3	(19<<3)			/* reserved for local use */
#define	LOG_LOCAL4	(20<<3)			/* reserved for local use */
#define	LOG_LOCAL5	(21<<3)			/* reserved for local use */
#define	LOG_LOCAL6	(22<<3)			/* reserved for local use */
#define	LOG_LOCAL7	(23<<3)			/* reserved for local use */
#define	LOG_MARK	(24<<3)			/* special time stamp mark */
#define LOG_UNKNOWN	(25<<3)			/* unknown facility code */
#define	LOG_FAC		0x03f8			/* Mask for facility field */

/* Flags */

#define	LOG_INUSE	0x80000000		/* Message is in use (private !) */
#define	LOG_NOHEAD	0x40000000		/* Don't prepend header	*/
#define	LOG_NOWIN	0x20000000		/* Don't output to window	*/
#define	LOG_NOFILE	0x10000000		/* Don't output to file	*/

#define	LOGB_INUSE	31			/* Bit numbers for flags	*/
#define	LOGB_NOHEAD	30
#define	LOGB_NOWIN	29
#define	LOGB_NOFILE	28


/* Flags definitions for smHalt()	*/

#define	HALTB_REBOOT	0		/* Reboot immediately	*/
#define	HALTF_REBOOT	(1L << 0)
#define	HALTB_REKICK	1		/* Reload kickstart on MMU-Kicked systems.	*/
#define	HALTF_REKICK	(1L << 1)

/* Broadcast Message send via smSendBroadcastMsg()
** The sender must allocate this structure and fill in the different fields.
*/

struct BroadcastMsg
{	struct Message bcm_Msg;			/* Standard Message structure */
	UBYTE	bcm_Level;			/* Event Level */
	UBYTE	bcm_Flags;			/* Flags */
	UWORD	bcm_TimeOut;			/* Reply Time Out in ticks */
	UWORD	bcm_CountDown;			/* Countdown to Event in seconds */
	UBYTE	bcm_ReplyCount;			/* Reply count after sending */
	UBYTE	bcm_TimeOutCount;		/* Time Out count after sending */
	struct Task *bcm_SenderTask;		/* Sender Task (Filled by smSendBroadcastMsg()) */
	STRPTR	bcm_EventTxt;			/* Text describing the event */
	ULONG	bcm_Reserved[4];		/* Reserved for future expansion */
};

/* defines for event levels */

#define	BCM_HALT	0		/* System Halt/Reboot imminent */
#define	BCM_UNMOUNT	1		/* FileSystems will be UnMounted now */
#define	BCM_SHUTDOWN	2		/* Shutdown countdown message */
#define	BCM_URGENT	3		/* Urgent Message */
#define	BCM_NORMAL	4		/* Normal Message */
#define	BCM_DEBUG	5		/* Debug Level Message */

/* defines for bcm_Flags */

#define	BCMB_DOOMSDAY	0		/* Keyboard reset pending */
#define	BCMF_DOOMSDAY	(1L << 0)	/*  (System reboot in 10 seconds at most) */
#define	BCMB_CANCEL	1		/* A previously announced event has been cancelled */
#define	BCMF_CANCEL	(1L << 1)

/* defines for smLockTaskTable()/smUnLockTaskTable() flags */

#define	LTTB_READ	0		/* Read access to task table */
#define	LTTF_READ	(1L << 0)
#define	LTTB_WRITE	1		/* Write access (PRIVATE !) */
#define	LTTF_WRITE	(1L << 1)
#define	LTTB_REMOVE	2		/* Prevent task removal */
#define	LTTF_REMOVE	(1L << 2)

/* The LastGuru structure contains information about the last Guru Meditation
** The data is stored in a high memory buffer by Alert() that is allocated by
** sysmon.library during initialisation.
** As this buffer is allocated early with AllocMem(MEMF_REVERSE), it will be
** kept at the same address after reboot. This trick was already used successfully
** on recoverable ram disks like vdisk.device
** Some Fields are only valid if the corresponding register exists on the CPU
** installed in the system.
*/

struct LastGuru
{	struct MemChunk lg_MC;		/* leave space for a memory chunk */
	ULONG	lg_Sig;			/* Alert signature ('HELP') */
	ULONG	lg_AlertNum;		/* Guru Meditation number */
	ULONG	lg_AlertAddr;		/* TCB Address of crashed task */
	UBYTE	lg_TaskName[32];	/* Task name limited to 32 bytes */
	ULONG	lg_DataRegs[8];		/* Data registers D0-D7 */
	ULONG	lg_AddrRegs[8];		/* Address registers A0-A7 */
	ULONG	lg_FloatRegs[3*8];	/* Floating point registers FP0-FP7 */
	ULONG	lg_FPCR;		/* Floating Point Control Register */
	ULONG	lg_FPSR;		/* Floating Point Status Register */
	ULONG	lg_FPIAR;		/* Floating Point Instruction Address Register */
	ULONG	lg_PC;			/* Program Counter */
	ULONG	lg_USP;			/* User Stack Pointer */
	ULONG	lg_SSP;			/* Supervisor/Interrupt Stack Pointer */
	ULONG	lg_MSP;			/* Master Stack Pointer / Processor Control Register [68060] */
	ULONG	lg_VBR;			/* Vector Base Register */
	ULONG	lg_SFC;			/* Source Function Codes */
	ULONG	lg_DFC;			/* Destination Function Codes */
	ULONG	lg_CACR;		/* Cache Control Register */
	ULONG	lg_TC;			/* Translation Control register */
	ULONG	lg_ITT0;		/* Intruction Transparent Translation 0 */
	ULONG	lg_ITT1;		/* Intruction Transparent Translation 1 */
	ULONG	lg_DTT0;		/* Data Transparent Translation 0 / Common Root Pointer [68030] */
	ULONG	lg_DTT1;		/* Data Transparent Translation 1 / Common Root Pointer [68030] */
	ULONG	lg_URP;			/* User Root Pointer / Supervisor Root Pointer [68030] */
	ULONG	lg_SRP;			/* Supervisor Root Pointer */
	ULONG	lg_MMUSR;		/* MMU Status Register / Bus Control Register [68060] */
	ULONG	lg_CAAR;		/* Cache Address Register */
	UWORD	lg_SR;			/* Status Register */
	UWORD	lg_AC;			/* Access Control register [68851] */
	ULONG	lg_DRP[2];		/* DMA Root Pointer [68851] */
	UWORD	lg_BAD[8];		/* Breakpoint Acknowledge Data registers [68851] */
	UWORD	lg_BAC[8];		/* Breakpoint Acknowledge Control registers [68851] */
	UBYTE	lg_CAL;			/* Current Access Level [68851] */
	UBYTE	lg_VAL;			/* Valid Access Level [68851] */
	UBYTE	lg_SCC;			/* Stack Change Control register [68851] */
	UBYTE	lg_Pad;			/* Padding byte */
};

#endif  /* LIBRARIES_SYSMON_H */
