Advanced Search
Apple Developer Connection
Member Login Log In | Not a Member? Contact ADC

Previous Book Contents Book Index Next

Inside Macintosh: Operating System Utilities /
Chapter 8 - Trap Manager


About the Trap Manager

The Trap Manager is a collection of routines that lets you add extra capabilities to system software routines.

In order to execute system software routines, system software takes advantage of the unimplemented instruction feature of the MC680x0 family of microprocessors, which are the central processing units (CPUs) used in the Macintosh family of computers.

The MC680x0, like other microprocessors, executes a stream of instructions. Information encoded in an instruction indicates the operation to be performed by the microprocessor. The MC680x0 family of microprocessors recognizes a defined set of instructions. When the microprocessor encounters an instruction that it doesn't recognize, an exception is generated. An exception refers to bus errors, interrupts, and unimplemented instructions. When an exception occurs, the microprocessor suspends normal execution and transfers control to an appropriate exception handler.

In the MC680x0 family of microprocessors, all instructions starting with the hexadecimal digit $A are unimplemented instructions. These unimplemented instructions are also called A-line instructions. System software uses these unimplemented A-line instructions to execute system software routines. When you call a system software routine, the call to the system software routine is translated into an A-line instruction. The MC680x0 microprocessor doesn't recognize this A-line instruction, and transfers control to an exception handler.

System software provides an exception handler, called a trap dispatcher, to handle exceptions generated by A-line instructions. Whenever a MC680x0 microprocessor encounters an A-line instruction, an exception is generated, and the microprocessor transfers control to the trap dispatcher. An exception generated by an A-line instruction is called a trap.

When the trap dispatcher receives the A-line instruction, it looks into a table, called a trap dispatch table, to find the address of the called system software routine. After the trap dispatcher retrieves the address, it transfers control to the specified system software routine. Figure 8-1 illustrates the processing of instructions that include the A-line instructions that the microprocessor does not recognize.

Figure 8-1 How the CPU processes A-line instructions

You can use the Trap Manager routines to read from and write to the two trap dispatch tables maintained by system software.

Trap Dispatch Tables

System software uses trap dispatch tables to locate the address of system software routines. System software maintains two trap dispatch tables: an Operating System trap dispatch table and a Toolbox trap dispatch table. Figure 8-2 illustrates the two trap dispatch tables.

Figure 8-2 Trap dispatch tables

At system startup time, system software builds the trap dispatch tables and places them in RAM. The Operating System trap dispatch table contains 256 entries, and the Toolbox trap dispatch table contains 1024 entries. Each entry in the Operating System trap dispatch table contains a 32-bit address of an Operating System routine, and each entry in the Toolbox trap dispatch table contains a 32-bit address of a Toolbox routine. The system software routines can be located in either ROM or RAM.

Process for Accessing System Software Routines

As previously described, when your application calls a system software routine, an A-line instruction is sent to the microprocessor. The microprocessor does not recognize this instruction, and an exception is generated. This exception is then handled by the trap dispatcher. When the trap dispatcher receives the A-line instruction, it looks into one of the two trap dispatch tables to find the address of the called system software routine. When the trap dispatcher retrieves the address, it transfers control to the specified system software routine. For example, Figure 8-3 illustrates a call to the Toolbox procedure, FillRect. When the application calls the FillRect procedure, an exception is generated. The trap dispatcher looks into the Toolbox trap dispatch table to find the address of the FillRect procedure. When the address is found, the trap dispatcher transfers control to the FillRect procedure.

Figure 8-3 Accessing the FillRect procedure

Note
Not all A-line instructions are defined. When the trap dispatcher receives an undefined A-line instruction, the trap dispatcher returns the address of the Toolbox procedure Unimplemented. When called, the Unimplemented procedure triggers a system error.

Patches and System Software Routines

You can modify the trap dispatch table so that the address that gets returned to the trap dispatcher points to a different routine instead of the intended system software routine; this is useful if you want to augment or override an existing system software routine. The routine that augment an existing system software routine is called a patch. The method of augmenting or overriding a system software routine is called patching a trap.

For example, you can augment the FillRect procedure with your own procedure MyPatchFillRect. Figure 8-4 illustrates another call to the Toolbox procedure FillRect. When the application calls the FillRect procedure the application-defined patch MyPatchFillRect is executed first. After the application-defined patch MyPatchFillRect completes its primary action, it transfers control (through a JMP instruction) to the original FillRect procedure.

IMPORTANT
Although this chapter describes patching in some detail, you should avoid any unnecessary patching of the system software. One very good reason to avoid patching is that is causes a performance reduction. The performance reduction is especially substantial when your patch is executed on a PowerPC processor-based Macintosh computer, where it is necessary to switch execution environments when entering and exiting your patch code. For more information about patching PowerPC system software, see Inside Macintosh: PowerPC System Software.
Figure 8-4 Augmenting the FillRect procedure with a single patch

Note
To prevent dangling patch addresses, you must ensure that your patch routine is in a locked memory block while its address is in the trap dispatch table.

Daisy Chain of Patches

It is possible to patch a system software routine with more than just one patch; this is called a daisy chain of patches. Typically, you extract from the trap dispatch table the address of the routine you wish to patch, save this address, and then install your own patch routine. When your patch has completed its tasks, it should jump to the address you previously extracted from the trap dispatch table. In this way, the patches take the general form of a daisy chain. Each patch will execute in turn and jump to the next patch until the last link in the chain, which returns control to the trap dispatcher.

IMPORTANT
Although this chapter describes patching in some depth, you should rarely, if ever, find a need to use patches in an application. The primary purposes of patches, as their name suggests, are to fix problems and augment routines in ROM code.
A patch can be implemented as either a head patch, tail patch, or come-from patch. These are described in the next sections.

Head Patch (Normal Patch)

A head patch, also referred to as a normal patch, is a routine that gets executed before the original system software routine. A head patch performs its primary action and then uses a jump instruction (JMP) to jump to the system software routine. Thus the head patch does not regain control after the execution of the system software routine. After the execution of the system software routine, control is transferred back to the trap dispatcher.

Tail Patch

A tail patch is a routine that gets executed before the original system software routine and regains control after the execution of the system software routine. A tail patch uses a jump-subroutine instruction (JSR) to transfer control to the system software routine. After the system software routine returns control to the tail patch, the tail patch returns control to the trap dispatcher.

WARNING
You should never install tail patches in system software versions earlier than System 7. Tail patches may conflict with come-from patches, installed by Apple.

Come-From Patch (Used Only by Apple)

A come-from patch, also called a system patch, is a type of patch used only by Apple. Come-from patches are used to replace erroneous code or to add capabilities not in ROM.

When a come-from patch is invoked, it examines the stack to determine where it was called from. If the come-from patch was invoked from a particular place in ROM (a spot where the code needs to be augmented or deleted), the come-from patch executes the modifying code. Otherwise, if the come-from patch was called from a part of the system that does not need to be augmented, it transfers control to the next routine in the daisy chain. This routine could be another patch or the system software routine.

Beginning with System 7, the addresses of come-from patches are permanently placed in the trap dispatch table at system startup time. The addresses of come-from patches are hidden and cannot be manipulated by any of the Trap Manger routines.

For example, if a system software routine has a come-from patch and if you use the Trap Manger function NGetTrapAddress to retrieve the address of the system software routine, you will not get the address in the trap dispatch table (which is the address of the come-from patch). NGetTrapAddress instead returns the address of the routine that is executed immediately after the come-from patch. This address could be the address of another patch or the system software routine.

If a system software routine has a come-from patch and if you use the Trap Manager procedure NSetTrapAddress to install a patch to the system software routine, the address of the patch is not written into the trap dispatch table. Instead, the NSetTrapAddress procedure installs the address of the patch into the last come-from patch. The patch is executed after the completion of the come-from patch.

WARNING
In system software before System 7, if a come-from patch is invoked by a tail-patch, the come-from patch does not work correctly. The come-from patch never sees the ROM address on the stack--only the return address of the tail-patch.

Patch for One Application

If you install a patch into your application heap, the patch applies only to your application. When your application is switched out, your application's heap (and patch) is swapped out. For example, if you patch FillRect with the patch MyPatchFillRect, the MyPatchFillRect patch is executed only when the FillRect procedure is called from your application.

Note
When running in System 7 or under MultiFinder in System 6, each application has its own copy of the trap dispatch tables. This ensures that an application's patches apply only when it is running and that they're discarded when the application quits.

Patch for All Applications

If you install a patch from a system extension during system startup, your patch is placed in the system heap and applies to all applications. For example, if you patch the FillRect procedure with the patch MyPatchFillRect from a system extension, the MyPatchFillRect patch is executed every time the FillRect procedure is called, no matter which application calls it.

A-Line Instructions

When your application calls a Toolbox or an Operating System routine, an A-line instruction is sent to the microprocessor. Each A-line instruction contains information about the called system software routine. Figure 8-5 shows the layout of an A-line instruction.

Figure 8-5 A-line instruction format

The high-order 4 bits of an A-line instruction have the hexadecimal value $A, hence the name A-line instruction. Bit 11 of the A-line instruction indicates the type of system software routine to be invoked: a value of 0 in bit 11 indicates an Operating System routine, a value of 1 in bit 11 indicates a Toolbox routine. The trap number in an A-line instruction is used as an index into the appropriate dispatch table. The meaning of the flags vary accordingly to the type of A-line instruction.

When your application calls a system software routine (thereby generating an exception), the microprocessor pushes an exception stack frame onto the stack. Figure 8-6 shows a typical exception stack frame. After pushing the exception stack frame on the stack, the microprocessor transfers control to the trap dispatcher.

Figure 8-6
Exception stack frame (on Macintosh computers with a MC68020 microprocessor or greater)

The trap dispatcher discards the status register and vector offset. Depending on whether the A-line instruction is used to invoke an Operating System routine or a Toolbox routine, the trap dispatcher deals with the stack and registers in two very different ways, as described in the next section, "A-line Instructions for Operating System Routines," and in the section "A-Line Instructions for Toolbox Routines" beginning on page 8-14.

Note
The exception handler is located at address $28 on computers with an MC68000 microprocessor and at address $28 offset from the address in the microprocessor's Vector Base Register (VBR) on computers with other MC680x0 microprocessors. Consult the relevant microprocessor handbook for the precise details of exception handling on the MC680x0 microprocessor of interest to you.

A-Line Instructions for Operating System Routines

An Operating System trap is an exception that is caused by an A-line instruction that executes an Operating System routine.

When dispatching an Operating System trap, the trap dispatcher extracts the trap number from the A-line instruction and uses it as an index into the Operating System trap dispatch table. The entry in the Operating System trap dispatch table contains the address of the desired Operating System routine. Figure 8-7 illustrates an A-line instruction for an Operating System routine.

Figure 8-7 An A-line instruction for an Operating System routine

Bit 11 tells the trap dispatcher that this A-line instruction invokes an Operating System routine. Two flag bits, bit 10 and bit 9, are reserved for use by the Operating System routine itself and are discussed in detail in "Flag Bits" on page 8-14. Bit 8 indicates whether the value in register A0 is returned from the Operating System routine. If bit 8 is 0, the value in register A0 is returned from the Operating System routine. If bit 8 is 1, the value in register A0 is not returned by the Operating System routine. As previously described, the trap number is in bits 7-0 and is used to determine which of the 256 possible Operating System routines is executed.

For example, a call to the Operating System function GetPtrSize is translated to the A-line instruction $A021. This A-line instruction causes the microprocessor to transfer control to the trap dispatcher, which deals with any instruction of the form $Axxx. The trap dispatcher first saves registers D0, D1, D2, A1, and, if bit 8 is 0, A0. The trap dispatcher places the A-line instruction itself into the low-order word of register D1 so that the Operating System routine can inspect the flag bits. Next, the trap dispatcher examines the other bits in the A-line instruction. The value (0) of bit 11 indicates that GetPtrSize is an Operating System routine, and that the value in bits 7-0 is the index into the Operating System trap dispatch table. The trap dispatcher uses the index (which is 33 in this example) to find the address of the GetPtrSize function in the Operating System trap dispatch table. When the address is found, the trap dispatcher transfers control to the GetPtrSize function.

Figure 8-8 illustrates the stack after the trap dispatcher has transferred control to an Operating System routine.

Figure 8-8 The stack on entry to an Operating System routine

The Operating System routine may alter any of the registers D0-D2 and A0-A2, but it must preserve registers D3-D7 and A3-A6. The Operating System routine may return information in register D0 (and A0 if bit 8 is set). To return to the trap dispatcher, the Operating System routine executes the RTS (return from subroutine) instruction.

When the trap dispatcher resumes control, first it restores the value of registers D1, D2, A1, A2, and, if bit 8 is 0, A0. The values in registers D0 and, if bit 8 is 1, in A0 are not restored.

Calling Conventions for Register-Based Routines

Register-based routines receive their parameters from microprocessor registers, and they pass their results in microprocessor registers. Virtually all Operating System routines are register-based routines.

An Operating System routine returns information only in registers D0 and, if bit 8 is 1, A0. The stack and all other registers are unchanged.

Many Operating System routines return a result code in the low-memory word of register D0 to report whether the requested operation was performed successfully. A result code of 0 indicates that the routine completed successfully; any other value typically indicates an error. Just before the trap dispatcher finishes execution, it tests the low-order word of register D0 with a TST.W instruction to set the condition codes of the microprocessor.

Note
Calling conventions for PowerPC microprocessor-based Macintosh computers are different from the calling conventions described for in this section. For information about calling conventions for PowerPC processor-based Macintosh computers, see Inside Macintosh: PowerPC System Software.

Parameter-Passing Conventions for Operating System Routines

By convention, register-based routines normally use register A0 for passing addresses (such as pointers to data objects) and register D0 for other data values (such as integers).

For routines that take more than two parameters, the parameters are normally collected in a parameter block in memory and a pointer to the parameter block is passed in register A0. See the description of an individual routine in the appropriate Inside Macintosh book for exact details.

Function Results

Most Operating System functions return their function result (or result code) in register D0. Parameters are returned through register A0, usually as a pointer to a parameter block.

Whether the trap dispatcher preserves register A0 depends on the setting of bit 8 in the A-line instruction. If bit 8 is 0, the trap dispatcher saves and restores register A0; if it's 1, the routine passes back register A0 unchanged. Thus, bit 8 of the A-line instruction should be set to 1 only for those routines that use register A0 to return information. The trap macros automatically set this bit correctly for each routine.

To see in which register the function passes the function result, see the description of the individual function in the appropriate Inside Macintosh book.

Flag Bits

Many Operating System routines use the flag bits in an A-line instruction to encode additional information used by the routine. For example, the A-line instructions that invoke Memory Manager routines define the two flag bits like this:
BitExplanation
9If 1, initialize all bytes in the allocated memory to 0.
If 0, do not initialize all bytes in the allocated memory to 0.
8If 1, allocate memory from the system heap.
If 0, allocate memory from the application heap.

These two bits are defined in assembly language as:

CLEAR    EQU      $200     ;initialize block to zero
SYS      EQU      $400     ;use the system heap
When used with a Memory Manager A-line instruction, these modifiers cause flag bits 9 and 10, respectively, to be set. They could be used in an assembly-language instruction sequence like

         MOVEQ    #124,D0        ;need 124 bytes
         _NewPtr     SYS,CLEAR   ;allocate requested memory in
                                 ; system heap and initialize to
                                 ; zeroes
The SYS modifier specifies allocation from the system heap, regardless of the value of the global variable TheZone, and the CLEAR modifier specifies that the Memory Manager should initialize the block contents to zero. For further details, consult Inside Macintosh: Memory.

A-Line Instructions for Toolbox Routines

A Toolbox trap is an exception that is caused by an A-line instruction that executes a Toolbox routine.

When dispatching a Toolbox trap, the trap dispatcher extracts the trap number from the A-line instruction and uses it as an index into the Toolbox trap dispatch table. The index points to the entry in the Toolbox trap dispatch table that contains the address of the desired Toolbox routine. Figure 8-9 illustrates an A-line instruction that is used to access a Toolbox routine.

Figure 8-9 An A-line instruction for a Toolbox routine

Bit 11 tells the trap dispatcher that this A-line instruction is used to access a Toolbox routine. Bit 10 is the auto-pop bit. Bits 9-0 contain the trap number which, as previously described, determine which of the 1024 possible Toolbox routines is executed. The auto-pop bit is described in detail in "The Auto-Pop Bit" on page 8-20.

For example, a call to the Toolbox function WaitNextEvent is translated to the A-line instruction $A860. This A-line instruction causes the microprocessor to transfer control to the trap dispatcher, which deals with any instruction of the form $Axxx. The trap dispatcher examines the other bits in the A-line instruction. The value (0) of bit 11 indicates that WaitNextEvent is a Toolbox routine and that the value in bits 9-0 is the index into the Toolbox trap dispatch table. The trap dispatcher uses the index (which is $60 in this example) to find the address of the WaitNextEvent function in the Toolbox trap dispatch table. When the address is found, the trap dispatcher transfers control to the WaitNextEvent function.

Figure 8-10 illustrates the stack after the trap dispatcher has transferred control to a Toolbox routine.

Figure 8-10 Stack when entering a Toolbox routine

The value of the Program Counter that is left on the stack before entry to the Toolbox routine points to the instruction that is executed after the completion of the Toolbox routine.

After the trap dispatcher completes execution, the internal status of the stack is restored, and normal execution resumes from the point at which processing was suspended.

A Toolbox routine changes the Stack Pointer in register A7 and pops the return address and any input parameters. A routine might also alter registers D0-D2, A0, and A1.

WARNING
Some Toolbox routines (for example the LongMul procedure described in the chapter "Mathematical and Logical Utilities" in this book) preserve more than the required set of registers. However, you should assume all of registers D0-D2, A0, and A1 are altered by Toolbox routines.

Calling Conventions for Stack-Based Routines

Stack-based routines receive their parameters on the stack and return their results on the stack. Virtually all Toolbox routines are stack-based routines.

Most Toolbox routines follow Pascal calling conventions; that is, Toolbox routine parameters are evaluated from left to right and are pushed onto the stack in the order in which they are evaluated. Function results are returned by value or by address on the stack. Space for the function result is allocated by the caller before the parameters are pushed on the stack. The caller is responsible for removing the result from the stack after the call.

Note
Calling conventions for PowerPC microprocessor-based Macintosh computers are different from the calling conventions described in this section. For information about calling conventions for PowerPC processor-based Macintosh computers, see Inside Macintosh: PowerPC System Software.
Figure 8-11 illustrates Pascal calling conventions. In this example, a routine calls the application-defined function MyPascalFn. When the application calls the function MyPascalFn, the application must first make room on the stack for the function result, then push the parameters on the stack in left-to-right order.

Figure 8-11 Pascal calling convention

Figure 8-12 illustrates C calling conventions. In this example, a routine calls the application-defined function MyCFn. When the application calls the function MyCFn, the application pushes the parameters on the stack in right-to-left order. The function result is returned in register D0, and not on the stack.

Figure 8-12 C calling convention

Parameter-Passing Conventions for Toolbox Routines

All variable parameters (parameters of type VAR) are passed as pointers to the actual storage location. In the case of byte-sized types, parameters of type VAR may have odd values.

Nonvariable parameters are passed in different ways, depending on the type of the parameter. Values of type Boolean, elements of an enumerated type with fewer than 128 elements, and subranges within the range -128 to 127 are passed as signed byte values. Values of type Integer and, Char and all other enumerations and subranges are passed as signed word values. Pointers and values of type LongInt are passed as signed 32-bit values. Table 8-1 summarizes the parameter-passing conventions.
Table 8-1 Toolbox parameter-passing conventions
Parameter typeData object pushed on stack
BooleanByte: range 0 to 1
Char16 bits: range 0 to 255
Integer16 bits: range -32768 to 32767
LongInt32 bits
Pointer32 bits
Enumeration: range 0 to 127Byte: range 0 to 127
Enumeration: range 0 to 3276716 bits: range 0 to 32767
Subrange: range -128 to 12716 bits: range -128 to 127
Subrange: range -32768 to 32767Word: range -32768 to 32767
RealAddress of Extended copy
DoubleAddress of Extended copy
CompAddress of Extended copy
ExtendedAddress of argument
ARRAY, RECORD, string 4 bytesValue (word or long word)
ARRAY, RECORD, string > 4 bytesAddress of value
SETSET value rounded to whole number of words

A parameter of type SET is passed by rounding its size up to the next whole word, if necessary, then pushing its value so that the lowest-order word is pushed last. In the case of a byte-size SET, the called procedure accesses only the low-order half of the word that is pushed.

Note
A byte pushed on the stack occupies the high-order byte of the word allocated for it, according to conventions for the MC680x0 microprocessors.
WARNING
A value of type Char is passed as a word value. The value occupies the low-order half of the word.

Function Results

Function results are returned by value or by address on the stack. Space for the function result is allocated by the caller before the parameters are pushed. The caller is responsible for removing the result from the stack after the call.

For types Boolean, Char, and Integer and for enumerated and subrange types, the caller allocates a word on the stack to make space for the function result. Values of type Boolean, enumerated types with fewer than 128 elements, and subranges within the range -128 to 127 are returned as signed byte values. The value is placed in the high-order byte of the word.

Values of type Integer and Char and all enumerated and subrange types not covered above are returned as signed word values.

Pointers and values of type LongInt are returned as signed 32-bit values. Values of type Real are returned as 32-bit real values. For types whose values are greater than 4 bytes in size, the caller pushes a pointer to a temporary location into which the function places the result; these types include Double (8 bytes), Comp (8 bytes), and Extended (10 or 12 bytes); types SET, ARRAY, RECORD; and strings greater than 4 bytes in size.

For a 1-byte SET, for types SET, ARRAY, and RECORD, and for strings whose size is one word, the caller allocates a word on the stack. For types SET, ARRAY, and RECORD and strings whose size is two words, the caller allocates a long word on the stack.

The conventions for returning results of functions are summarized in Table 8-2.
Table 8-2 Conventions for returning results from Toolbox functions
Function result typeData object left on stack or returned through pointer on stack
BooleanByte: range 0 to 1
Char16 bits: range 0 to 255
Integer16 bits: range -32768 to 32767
LongInt32 bits
Pointer32 bits
Enumeration: range 0 to 127Byte: range 0 to 127
Enumeration: range 0 to 3276716 bits: range 0 to 32767
 
Subrange: range -128 to 127Byte: range -128 to 127
Subrange: range -32768 to 3276716 bits: range -32768 to 32767
RealReal
DoubleDouble at address given by pointer
CompComp at address given by pointer
ExtendedExtended at address given by pointer
ARRAY, RECORD, string 4 bytesValue (word or long word)
ARRAY, RECORD, string > 4 bytesValue at address given by pointer
SET: one byteByte value
SET: one word16-bits value
SET: two words32-bits value
SET > two wordsValue at address given by pointer

Note
A 1 byte-size return value occupies the high-order byte of the word allocated for it.

The Auto-Pop Bit

The auto-pop bit is bit 10 in an A-line instruction for a Toolbox routine. Some language systems prefer to generate jump-subroutine calls (JSR) to intermediate routines, called glue routines, which then call Toolbox routines instead of executing the Toolbox routine directly. This glue method would normally interfere with Toolbox traps because the return address of the glue subroutine is placed on the stack between the Toolbox routine's parameters and the address of the place where the glue routine was called from (where control returns once the Toolbox routine has completed execution).

The auto-pop bit forces the trap dispatcher to remove the top 4 bytes from the stack before dispatching to the Toolbox routine. After the Toolbox routine completes execution, control is transferred back to the place where the glue routine was called from, not back to the glue routine.

Most development environments, including MPW, do not use this feature.

About Trap Macros

A trap macro is an assembly-language macro that assembles into an A-line instruction, used for calling a Toolbox or Operating System routine from assembly language. The names of all trap macros begin with the underscore character (_), followed by the name of the corresponding routine. As a rule, the macro name is the same as the name used to call the routine from Pascal. For example, to call the Window Manager function NewWindow, you should use an instruction with the macro name _NewWindow. There are some exceptions, however, in which the spelling of the macro differs from the name of the Pascal routine itself; these are noted in the documentation for the individual routines.

Trap macros for Toolbox routines take no arguments; any parameters must be pushed on the stack before invoking the routine. See "Calling Conventions for Stack-Based Routines" on page 8-16 for more information. Trap macros for Operating System routines may have as many as three optional arguments. The first argument, if present, is used to load a register with a parameter value for the routine you're calling. The remaining arguments control the settings of the various flag bits in the A-line instruction.

About Routine Selectors

A routine selector is a value that is pushed on the stack to select a particular routine from a group of routines to be executed. Many trap macros take routine selectors. For example, the trap macro _HFSDispatch has the possibility of calling 42 different system software routines. Hence, the trap macro has 42 different routine selectors. The routine selector that is passed on the stack (for _HFSDispacth to access) selects which of the 42 software routines _HFSDispatch executes.

Most system software routines that are accessed through a trap macro and a routine selector also have a corresponding macro that expands to call the original trap macro and automatically puts the correct routine selector on the stack. For example, the trap macro _GetCatInfo expands to call _HFSDispatch and places the selector $0009 on the stack after the parameters.


Previous Book Contents Book Index Next

© Apple Computer, Inc.
6 JUL 1996

Get information on Apple products.
Visit the Apple Store online or at retail locations.
1-800-MY-APPLE

Copyright © 2004 Apple Computer, Inc.
All rights reserved. | Terms of use | Privacy Notice