supermario/base/SuperMarioProj.1994-02-09/Interfaces/CIncludes/MixedMode.h

368 lines
11 KiB
C
Raw Permalink Normal View History

2019-06-29 15:17:50 +00:00
/*
File: MixedMode.h
Contains: Headers and interfaces for the Mixed Mode mechanism
Written by: Bruce Jones
Copyright: © 1992 by Apple Computer, Inc., all rights reserved.
Change History (most recent first):
<1> 12/7/92 DRF first checked in
<18> 11/13/92 DRF Fix a bug in BuildRoutineDescriptor macro. We were building
kLoadAndExecute RDs and not kExecute types! Of course,
CodeFragMgrDispatch and MixedModeDispatch were the only two
users of this macro, so nobody knew it was broken.
<17> 11/8/92 BKJ Rolled back
<13+> 10/26/92 SP Adding definition for m68KRegisterSizePhase
<13> 10/22/92 DRF Added inline 68K trap glue for NewRoutineDescriptor and
DisposeRoutineDescriptor
<12> 10/19/92 DRF Changed declaration of NewRoutineDescriptor and
DisposeRoutineDescriptor to match Seans clearer syntax.
<11> 10/13/92 SP Changing all m68k's to m68K
<10> 10/08/92 SP Adding phase and offset enum for the parameters.
<9> 10/4/92 BKJ Current version is 1
<8> 10/1/92 jrg Made smaller enum blocks and changed typedef for InterfaceTool
<7> 9/29/92 BKJ Fix bug in BuildRoutineDescriptor macro.
<6> 9/28/92 stb add special cases as used by the rest of the public interfaces
<5> 9/18/92 LC changing kGoMixedMode to 0xFEED0000
<4> 9/10/92 EPT Added (long) typecasts to enum constants. Changed constants to
conform to new procInfo definition.
<3> 9/9/92 LC Added Macro "BuildRoutineDescriptor, which allows static
declaration of a routine descriptor at compile time. In order
to have this macro, many private declarations had to be brought
over from MixedModeApplePrivate.h, including kGoMixedMode, and
kMixedModeMagicCookie.
<2> 9/2/92 BKJ Get rid of numParams parameter to BuildProcInfo &
CallRoutineDescriptor calls.
<1> 9/1/92 BKJ first checked in
8/28/92 BKJ change to reflect latest ERS
6/5/92 BKJ Continued Development
4/17/92 BKJ Created
*/
#ifndef __MIXEDMODE__
#define __MIXEDMODE__
#ifndef __TYPES__
#include <Types.h>
#endif
#define kGoMixedMode 0xFEED0000
#define kMixedModeMagicCookie 0x4B4F4348
#define PARAMETER_SIZE(size) \
(((size) == 4) ? 3 : (((size) == 2) ? 1 : (((size) == 1) ? 2 : 0)))
enum {
kResultPhase = 4, /* bit offset for result field */
kParameterPhase = 6,
kParameterOffset = 2,
m68KRegisterOffset = 6,
m68KRegisterOut = 0x20,
m68KRegisterIn = 0x10,
m68KRegisterParameterPhase = 2,
m68KRegisterA0 = 0,
m68KRegisterA1 = 1,
m68KRegisterD0 = 2,
m68KRegisterD1 = 3
};
enum {
kPStackBased = 0,
kCStackBased = 1,
kRegisterBased = 2,
kD0DispStackBased = 8,
kD1DispStackBased = 12,
kStackDispStackBased = 14,
kStackDispRegisterBased = 10,
kSpecialCaseProcInfoType = 5
};
typedef short CallingConventionType;
enum {
// the Mixed Mode error codes
mmInternalError = -2526,
kMMErr2 = -2527,
kMMErr3 = -2528,
kMMErr4 = -2529,
kMMErr5 = -2530,
kMMErr6 = -2531,
kMMErr7 = -2532,
kMMErr8 = -2533,
kMMErr9 = -2534,
kMMErr10 = -2535
};
typedef short MMErrType;
enum {
kRegisterD0 = 0,
kRegisterD1,
kRegisterD2,
kRegisterD3,
kRegisterD4,
kRegisterD5,
kRegisterD6,
kRegisterD7,
kRegisterA0,
kRegisterA1,
kRegisterA2,
kRegisterA3,
kRegisterA4,
kRegisterA5,
kRegisterA6,
kRegisterA7
};
typedef short RegisterSelectorType;
enum {kLoadAndExecute = 0, kExecute, kReturnFrom};
typedef short SelectorType;
enum {kCodeTypeUnknown = -1, kCodeTypeCurrentWorld, kCodeType68K, kCodeTypePower};
typedef long CodeType;
typedef long ProcInfoType;
typedef struct private_RoutineDescriptor* RoutineDescriptor;
/* ProcInfo selectors for each of the parameters */
/* Pascal and C Stack based parameter constants */
/* Stack-based dispatched uses these, but only P2 and up */
enum {
m68KStackP1Byte = (long)0x00000080,
m68KStackP1Word = (long)0x00000040,
m68KStackP1Long = (long)0x000000C0,
m68KStackP2Byte = (long)0x00000200,
m68KStackP2Word = (long)0x00000100,
m68KStackP2Long = (long)0x00000300,
m68KStackP3Byte = (long)0x00000800,
m68KStackP3Word = (long)0x00000400,
m68KStackP3Long = (long)0x00000C00,
m68KStackP4Byte = (long)0x00002000,
m68KStackP4Word = (long)0x00001000,
m68KStackP4Long = (long)0x00003000,
m68KStackP5Byte = (long)0x00008000,
m68KStackP5Word = (long)0x00004000,
m68KStackP5Long = (long)0x0000C000,
m68KStackP6Byte = (long)0x00020000,
m68KStackP6Word = (long)0x00010000,
m68KStackP6Long = (long)0x00030000,
m68KStackP7Byte = (long)0x00080000,
m68KStackP7Word = (long)0x00040000,
m68KStackP7Long = (long)0x000C0000,
m68KStackP8Byte = (long)0x00200000,
m68KStackP8Word = (long)0x00100000,
m68KStackP8Long = (long)0x00300000,
m68KStackP9Byte = (long)0x00800000,
m68KStackP9Word = (long)0x00400000,
m68KStackP9Long = (long)0x00C00000,
m68KStackP10Byte = (long)0x02000000,
m68KStackP10Word = (long)0x01000000,
m68KStackP10Long = (long)0x03000000,
m68KStackP11Byte = (long)0x08000000,
m68KStackP11Word = (long)0x04000000,
m68KStackP11Long = (long)0x0C000000,
m68KStackP12Byte = (long)0x20000000,
m68KStackP12Word = (long)0x10000000,
m68KStackP12Long = (long)0x30000000,
m68KStackP13Byte = (long)0x80000000,
m68KStackP13Word = (long)0x40000000,
m68KStackP13Long = (long)0xC0000000
};
enum {
/* Register based parameter constants */
/* Also used for register-based dispatching */
m68KRegisterP1In = (long)0x00000400,
m68KRegisterP1Out = (long)0x00000800,
m68KRegisterP1InOut = (long)0x00000C00,
m68KRegisterP2In = (long)0x00010000,
m68KRegisterP2Out = (long)0x00020000,
m68KRegisterP2InOut = (long)0x00030000,
m68KRegisterP3In = (long)0x00400000,
m68KRegisterP3Out = (long)0x00800000,
m68KRegisterP3InOut = (long)0x00C00000,
m68KRegisterP4In = (long)0x10000000,
m68KRegisterP4Out = (long)0x20000000,
m68KRegisterP4InOut = (long)0x30000000
};
enum {
m68KRegisterP1Byte = (long)0x00000200,
m68KRegisterP1Word = (long)0x00000100,
m68KRegisterP1Long = (long)0x00000300,
m68KRegisterP2Byte = (long)0x00008000,
m68KRegisterP2Word = (long)0x00004000,
m68KRegisterP2Long = (long)0x0000C000,
m68KRegisterP3Byte = (long)0x00200000,
m68KRegisterP3Word = (long)0x00100000,
m68KRegisterP3Long = (long)0x00300000,
m68KRegisterP4Byte = (long)0x08000000,
m68KRegisterP4Word = (long)0x04000000,
m68KRegisterP4Long = (long)0x0C000000
};
enum {
m68KRegisterP1A0 = (long)0x00000000,
m68KRegisterP1A1 = (long)0x00000040,
m68KRegisterP1D0 = (long)0x00000080,
m68KRegisterP1D1 = (long)0x000000C0,
m68KRegisterP2A0 = (long)0x00000000,
m68KRegisterP2A1 = (long)0x00001000,
m68KRegisterP2D0 = (long)0x00002000,
m68KRegisterP2D1 = (long)0x00003000,
m68KRegisterP3A0 = (long)0x00000000,
m68KRegisterP3A1 = (long)0x00040000,
m68KRegisterP3D0 = (long)0x00080000,
m68KRegisterP3D1 = (long)0x000C0000,
m68KRegisterP4A0 = (long)0x00000000,
m68KRegisterP4A1 = (long)0x01000000,
m68KRegisterP4D0 = (long)0x02000000,
m68KRegisterP4D1 = (long)0x03000000
};
enum {
/* Dispatched constants for kStackDispRegisterBased type (selector on stack) */
m68KStackSelectorByte = (long)0x00000020,
m68KStackSelectorWord = (long)0x00000010,
m68KStackSelectorLong = (long)0x00000030,
/* Dispatched constants for all dispatched stack-based types */
m68KRegSelectorByte = (long)0x00000080,
m68KRegSelectorWord = (long)0x00000040,
m68KRegSelectorLong = (long)0x000000C0,
/* Selectors for the ProcInfo result size fields */
kNoReturnValue = (long)0x00000000,
k68KByteReturned = (long)0x00000020,
k68KWordReturned = (long)0x00000010, /* 68K word - two bytes */
k68KLongReturned = (long)0x00000030 /* 68K long - four bytes */
};
/* all of the special cases enumerated */
enum {
kSpecialCaseHighHook = 0x0100,
kSpecialCaseCaretHook = 0x0100,
kSpecialCaseEOLHook = 0x0200,
kSpecialCaseWidthHook = 0x0300,
kSpecialCaseNWidthHook = 0x0400,
kSpecialCaseTextWidthHook = 0x0500,
kSpecialCaseDrawHook = 0x0600,
kSpecialCaseHitTestHook = 0x0700,
kSpecialCaseTEFindWord = 0x0800,
kSpecialCaseADBRoutines = 0x0900,
kSpecialCaseProtocolHandler = 0x0A00,
kSpecialCaseSocketListener = 0x0B00
};
/*
Explanation of special cases:
*****************************
1 = C calling conventions, Rect on stack, pointer in A3, no return value
2 = Register-based; inputs in D0, A3, A4; output is Z flag of
status register (see VI-15-26)
3 = Register-based; inputs in D0, D1, A0, A3, A4; output in D1 (see VI-15-27)
4 = Register-based; inputs in D0, D1, D2, A0, A2, A3, A4; output in D1
(see VI-15-27)
5 = Register-based; inputs in D0, D1, A0, A3, A4; output in D1 (see VI-15-28)
6 = Register-based; inputs in D0, D1, A0, A3, A4; no output (see VI-15-28)
7 = Register-based; inputs in D0, D1, D21, A0, A3, A4; outputs in
D0, D1, D2 (See VI-15-29)
8 = Register-based; inputs in D0, D2, A3, A4; outputs in D0, D1 (see VI-15-30)
9 = Register-based; inputs in A0, A1, A2, D0; no outputs (see V-371)
A = Register-based; inputs in A0, A1, A2, A3, A4, D1.w; output in Z (see II-326)
B = Register-based; inputs in A0, A1, A2, A3, A4, D0.b, D1.w; output in Z
(see II-329)
*/
RoutineDescriptor
NewRoutineDescriptor(ProcPtr theProc,
ProcInfoType procInfo,
CodeType typeOfCode)
= {0x303C,0x0000,0xAA59}; /* <13> */
void
DisposeRoutineDescriptor (RoutineDescriptor theDescriptor)
= {0x303C,0x0001,0xAA59}; /* <13> */
long
CallRoutineDescriptor (RoutineDescriptor theRoutine,
ProcInfoType procInfo,
...);
CodeType
GetCodeType (RoutineDescriptor theDescriptor);
OSErr
SetCodeType (RoutineDescriptor theDescriptor,
CodeType newCodeType);
ProcInfoType
BuildProcInfo(CallingConventionType callingConvention,
short resultSize,
...);
ProcInfoType
GetProcInfo (RoutineDescriptor theDescriptor);
OSErr
SetProcInfo (RoutineDescriptor theDescriptor,
ProcInfoType newProcInfo);
ProcPtr
GetTheProc (RoutineDescriptor theDescriptor);
OSErr
SetTheProc (RoutineDescriptor theDescriptor,
ProcPtr newProc);
long
GetEmulatorRegister (RegisterSelectorType registerSelector);
long
SetEmulatorRegister (RegisterSelectorType registerSelector,
long newValue);
enum {kRoutineDescriptorVersion = 1};
struct private_RoutineDescriptor {
long goMixedMode; // unused 68K instruction 0
long magicCookie; // unique identifier 4
SelectorType selector; // mixed mode selector 8
short version; // 0 for now, increment as needed 10
ProcInfoType procInfo; // calling conventions 12
ProcPtr customParamProc; // Procedure to convert params 16
CodeType executionMode; // to different types of code 20
ProcPtr procDescriptor; // Descriptor of routine we are going to call 24
long unused; // must be 0 28
};
typedef struct private_RoutineDescriptor private_RoutineDescriptor;
typedef private_RoutineDescriptor *private_RoutineDescriptorPtr, **private_RoutineDescriptorHandle;
/* a macro which creates a static instance of a routine descriptor */
#define BuildRoutineDescriptor(procInfo, procedure) \
{ \
kGoMixedMode, /* GoMixedMode instruction */ \
kMixedModeMagicCookie, /* Mixed Mode magic cookie */ \
kExecute, /* selector <18> */ \
kRoutineDescriptorVersion, /* version */ \
(procInfo), /* ProcInfo */ \
0, /* custom param proc */ \
kCodeTypePower, /* execution mode */ \
(void *) (procedure), /* theProc */ \
0, /* list terminator */ \
}
#endif