PreviousUpNext

15.3.82  src/lib/compiler/back/low/ccalls/ccalls.api

## ccalls.api
#
# Calling C functions directly from Mythryl (i.e., no wrapper layer between).

# Compiled by:
#     src/lib/compiler/back/low/lib/lowhalf.lib


stipulate
    package cty =  ctypes;                                                      # ctypes                is from   src/lib/compiler/back/low/ccalls/ctypes.pkg
    package rkj =  registerkinds_junk;                                          # registerkinds_junk    is from   src/lib/compiler/back/low/code/registerkinds-junk.pkg
herein

    api Ccalls {
        #
        package tcf:  Treecode_Form;                                            # Treecode_Form         is from   src/lib/compiler/back/low/treecode/treecode-form.api

        Ckit_Arg 
          = FARG  tcf::Float_Expression                                         # float_expression specifies floating-point argument 
          | ARGS  List( Ckit_Arg )                                              # list of arguments corresponding to the contents of a C struct. 
          | ARG   tcf::Int_Expression                                           # int_expression specifies integer or pointer; if the 
          ;                                                                     # corresponding parameter is a C struct, then 
                                                                                # this argument is the address of the struct. 



        param_area_offset:  Int;
            #
            # This constant is the offset
            # from the caller's SP to the
            # low-address of the parameter area.
            # (see the paramAlloc callback below).


        natural_int_size:  tcf::Int_Bitsize;
            #
            # The lowhalf type that describes the natural size of
            # integer arguments (i.e., what small integers are promoted to).

        make_inline_c_call:
            {
              name:           tcf::Int_Expression,
              fn_prototype:   cty::Cfun_Type,
              param_allot:  { szb:  Int, align:  Int } -> Bool,
              struct_ret:   { szb:  Int, align:  Int } -> tcf::Int_Expression,
              save_restore_global_registers :
                 List( tcf::Expression ) -> { save: List( tcf::Void_Expression ), restore: List( tcf::Void_Expression ) },
              call_comment:  Null_Or( String ),
              args:  List( Ckit_Arg )
            }
            ->
            { callseq:  List( tcf::Void_Expression ),
              result:   List( tcf::Expression )
            };
            #
            # Translate a C function call with
            # the given argument list into
            # a treecode statement list.
            # The arguments are as follows:
            #
            #   name                    -- An expression that specifies the function.
            #
            #   fn_prototype            -- The function's prototype
            #
            #   param_allot             -- This callback takes the size and alignment
            #                              constraints on the parameter-passing area
            #                              in the stack.  If it returns TRUE, then the
            #                              space for the parameters is allocated by
            #                              client; otherwise make_inline_c_call allocates the space.
            #
            #   struct_ret              -- This callback takes the size and alignment
            #                              of space required for returning a struct
            #                              value.  It returns the address of the
            #                              reserved space.
            #
            #   save_restore_global_registers   -- This callback takes a list of registers
            #                              that the call kills and should return an
            #                              instruction sequence to save/restore any
            #                              registers that the client run-time model
            #                              expects to be preserved (e.g., allocation
            #                              pointers).
            #
            #    call_comment           -- If present, the comment string is attached to
            #                              the CALL instruction as a COMMENT annotation.
            #
            #    args                   -- The arguments to the call.  We assume that
            #                              any required sign or zero extension has
            #                              already been done.
            #
            # The result of make_inline_c_call is a treecode instruction list specifying where
            # the result is and the treecode statements implementing the calling sequence.
            # Functions with void return type have no result, most others have
            # one result, but some conventions may flatten larger arguments into
            # multiple registers (e.g., a register pair for long long results).
            #
            # The implementation of make_inline_c_call will return a
            # statement sequence with the following order:
            #
            #   <argument area allocation>
            #   <set up arguments>
            #   <save global registers>
            #   <call C function>
            #   <restore global registers>
            #   <free argument area>
            #   <copy result into fresh registers>
            #
            # WARNING: if the client's implementation of struct_ret uses the stack
            # pointer to address the struct-return area, then param_allot should always
            # handle allocating space for the parameter area (i.e., return TRUE).



        # The location of arguments/parameters;
        # offsets are given with respect to the
        # low end of the parameter area -- see
        # param_area_offset above:
        #
        Arg_Location
          #
          = REG   (tcf::Int_Bitsize,    tcf::Register, Null_Or( tcf::mi::Machine_Int ))                         #  integer/pointer argument in register 
          | FREG  (tcf::Float_Bitsize,  tcf::Register, Null_Or( tcf::mi::Machine_Int ))                         #  floating-point  argument in register 
          #
          | STK   (tcf::Int_Bitsize,    tcf::mi::Machine_Int)                                                   #  integer/pointer argument in parameter area 
          | FSTK  (tcf::Float_Bitsize,  tcf::mi::Machine_Int)                                                   #  floating-point  argument in parameter area 
          #
          | ARG_LOCS  List( Arg_Location );


        layout:
            cty::Cfun_Type
            ->
            {
              arg_locs:  List( Arg_Location ),                  # Argument/parameter assignment.

              arg_mem:  { szb:  Int, align:  Int },             # Memory requirements for stack-allocated 
                                                                # arguments. This value can be passed to 
                                                                # the param_allot callback. 

              result_loc:  Null_Or( Arg_Location ),             # Result location. NULL for void functions. 

              struct_ret_loc:  Null_Or { szb:  Int, align:  Int }
            };

        # Callee-save registers as defined in the C calling convention.
        #
        # Note that these do not include special registers
        # (e::g., stack and frame-pointers)
        # that are preserved across calls.
        #
        callee_save_regs:   List( tcf::Register );              # C callee-save registers 
        callee_save_fregs:  List( tcf::Register );              # C callee-save floating-point registers 
    };
end;

## COPYRIGHT (c) 2002 Bell Labs, Lucent Technologies
## Subsequent changes by Jeff Prothero Copyright (c) 2010-2015,
## released per terms of SMLNJ-COPYRIGHT.


Comments and suggestions to: bugs@mythryl.org

PreviousUpNext