/*********************************************************************
Project	:	Perl5				-	
File		:	macish.h			-	Mac specific things
Author	:	Matthias Neeracher
Started	:	29Dec94								Language	:	MPW C/C++
Modified	:	29Dec94	MN	
Last		:	29Dec94
*********************************************************************/

#include <sys_errno.h> /* kaar - changed from sys/errno.h */
#include <compat.h>
#include <sys_fcntl.h> /* kaar - changed from sys/fcntl.h */
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h> /* kaar - changed from StdLib.h */
#include <time.h>

#include <Types.h>
#include <ConditionalMacros.h>

#ifdef MAC_CONTEXT
#undef Move		/* kaar - Macro in handy.h that conflicts with QuickDraw.h function */
#include <Memory.h>
#include <Events.h>
#include <Files.h>
#include <Timer.h>
#else
typedef struct TMTask {
	short	fill[11];
} TMTask;
#endif

/*#include "icemalloc.h"*/ /* kaar - removed */

/* HAS_IOCTL:
 *	This symbol, if defined, indicates that the ioctl() routine is
 *	available to set I/O characteristics
 */
/*#define	HAS_IOCTL		/**/ /* kaar - removed */
 
/* HAS_UTIME:
 *	This symbol, if defined, indicates that the routine utime() is
 *	available to update the access and modification times of files.
 */
/*#define HAS_UTIME		/**/ /* kaar - removed */

#include <signal.h>

#define mktemp tmpnam

#define ABORT() abort();

#define BIT_BUCKET "Dev:Null"
#define PERL_SYS_INIT(c,v)
#define PERL_SYS_TERM()
#define dXSUB_SYS int dummy
#define SH_PATH    "Shell ? We don't need no stinking shell!"
/*
 * fwrite1() should be a routine with the same calling sequence as fwrite(),
 * but which outputs all of the bytes requested as a single stream (unlike
 * fwrite() itself, which on some systems outputs several distinct records
 * if the number_of_items parameter is >1).
 */
#define fwrite1 fwrite

/* Look up new %ENV values on the fly */
#define DYNAMIC_ENV_FETCH 1
#define ENV_HV_NAME "%EnV%MaC%"

#define Stat(fname,bufptr) stat((fname),(bufptr))
#define Fstat(fd,bufptr)   fstat((fd),(bufptr))
#define Fflush(fp)         fflush(fp)

struct tms {
	clock_t tms_utime;	/* User CPU time */
	clock_t tms_stime;	/* System CPU time */
	clock_t tms_cutime;	/* User CPU time of terminated child procs */
	clock_t tms_cstime;	/* System CPU time of terminated child procs */
};

typedef struct stat	Stat_t; /* kaar - added */

double 	mac_atof(const char *);
char ** init_env(char ** env);
#ifndef __MWERKS__
#define atof(a)  mac_atof(a)
#endif
#ifndef open
#define open(name, flags, perm) (open)(name, flags)
#endif
#define Mkdir(name, perm) (mkdir)(name)
#define Perl_debug_log		gPerlDbg

#ifndef X2P
void   MPWPosIndication(SV * sv, char * file, long line);
#endif
void   MPWPosCommit();
char * MPWFileName(char * file);
int OverrideExtract(char * origname);
typedef int (*EmulationProc)(FILE *, char *);
void AddWriteEmulationProc(const char * command, EmulationProc proc);
extern char *GetSysErrText(short msgNbr, char *errMsg);

#ifndef MP_EXT
#define MP_EXT extern
#define MP_INIT(x)
#endif

int 				run_perl(int, char **, char **);
void 				reenter();

#ifdef MAC_CONTEXT
MP_EXT Handle	gPerlReply										MP_INIT(nil);
MP_EXT Handle	gSacrificialGoat 								MP_INIT((Handle) -1);
MP_EXT FSSpec	gFirstErrorFile;
MP_EXT Boolean	gReturnTrueFSSpecs								MP_INIT(false);
MP_EXT Boolean	gMustPrime											MP_INIT(false);
MP_EXT Boolean	gInModalDialog										MP_INIT(false);
MP_EXT void  	(*gHandleEvent)(EventRecord * ev)			MP_INIT(nil);
MP_EXT void		(*gFilterEvent)(EventRecord * ev)			MP_INIT(nil);
MP_EXT Boolean	(*gFilterMenu)(long menuSelection)			MP_INIT(nil);
void MacWaitEvent(Boolean busy, long sleep, RgnHandle rgn);
MP_EXT void		(*gWaitEvent)(Boolean busy, long sleep, RgnHandle rgn)	MP_INIT(MacWaitEvent);
#endif

MP_EXT Boolean			gHasAsyncTasks;
void MacPerl_DoAsyncTasks();
#define MACPERL_DO_ASYNC_TASKS() while (gHasAsyncTasks) MacPerl_DoAsyncTasks()
typedef struct MacPerl_AsyncTask {
	void	*	qLink;		/* Don't set */
	short    qType;		/* Queue type. Ignore */
	Boolean  fPending;   /* Is element queued already? */
	Boolean  fill;
	void     (*fProc)(struct MacPerl_AsyncTask * task); /* Procedure to call */
} MacPerl_AsyncTask;
Boolean MacPerl_QueueAsyncTask(MacPerl_AsyncTask * task);

#ifndef X2P
//MP_EXT PerlIO * 		gPerlDbg								MP_INIT(PerlIO_stderr());
MP_EXT PerlIO * 		gPerlDbg								MP_INIT(NULL);
#endif
MP_EXT int				gPerlQuit								MP_INIT(0);
MP_EXT char * 			gDebugLogName							MP_INIT(0);
MP_EXT short 			gAppFile;
MP_EXT short			gAppVol									MP_INIT(0);
MP_EXT long				gAppDir									MP_INIT(0);
MP_EXT short 			gPrefsFile;
MP_EXT void  		 (*gExit)(int)								MP_INIT(exit);
MP_EXT int   		 (*gAtExit)(void (*func)(void)) 		MP_INIT(atexit);
MP_EXT char *		 (*gGetEnv)(const char * name) 		MP_INIT(getenv);
MP_EXT char 			gPseudoFileName[256];
MP_EXT long				gFirstErrorLine						MP_INIT(-1);
MP_EXT clock_t			gStartClock;
MP_EXT char				gSyntaxError;
MP_EXT char				gAlwaysExtract							MP_INIT(false);
/* kaar - removed */
/*MP_EXT _mem_pool_ptr	gPerlPool								MP_INIT(&_mem_system_pool);*/
MP_EXT short			gLastMacOSErr;
#ifdef MAC_CONTEXT
typedef short	MacOSRet;
typedef Handle	HandleRet;
typedef Ptr		PtrRet;
typedef Ptr		RawPtr;
#endif

#if !defined(ORIGINAL_WRAPPER) && !defined(X2P)
#define exit(status) 		gExit(status)
#define atexit(proc) 		gAtExit(proc)
#define getenv(name)			gGetEnv(name)
#endif

#define sys_nerr	80

char * sys_errlist[];

#if TARGET_CPU_PPC
#define ARCHNAME "MacPPC"
#else
#if TARGET_RT_MAC_CFM
#define ARCHNAME "MacCFM68K"
#else
#define ARCHNAME "Mac68K"
#endif
#endif
