move adt headers
[libfirm] / include / libfirm / lower_intrinsics.h
1 /*
2  * Copyright (C) 1995-2007 University of Karlsruhe.  All right reserved.
3  *
4  * This file is part of libFirm.
5  *
6  * This file may be distributed and/or modified under the terms of the
7  * GNU General Public License version 2 as published by the Free Software
8  * Foundation and appearing in the file LICENSE.GPL included in the
9  * packaging of this file.
10  *
11  * Licensees holding valid libFirm Professional Edition licenses may use
12  * this file in accordance with the libFirm Commercial License.
13  * Agreement provided with the Software.
14  *
15  * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
16  * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE.
18  */
19
20 /**
21  * @file
22  * @brief   lowering of Calls of intrinsic functions
23  * @author  Michael Beck
24  * @version $Id$
25  */
26 #ifndef FIRM_LOWER_LOWER_INTRINSICS_H
27 #define FIRM_LOWER_LOWER_INTRINSICS_H
28
29 #include "firm_types.h"
30
31 /**
32  * An intrinsic mapper function.
33  *
34  * @param node   the IR-node that will be mapped
35  * @param ctx    a context
36  *
37  * @return  non-zero if the call was mapped
38  */
39 typedef int (*i_mapper_func)(ir_node *node, void *ctx);
40
41 enum ikind {
42         INTRINSIC_CALL  = 0,  /**< the record represents an intrinsic call */
43         INTRINSIC_INSTR       /**< the record represents an intrinsic instruction */
44 };
45
46 /**
47  * An intrinsic call record.
48  */
49 typedef struct _i_call_record {
50         enum ikind    kind;       /**< must be INTRINSIC_CALL */
51         ir_entity     *i_ent;     /**< the entity representing an intrinsic call */
52         i_mapper_func i_mapper;   /**< the mapper function to call */
53         void          *ctx;       /**< mapper context */
54         void          *link;      /**< used in the construction algorithm, must be NULL */
55 } i_call_record;
56
57 /**
58  * An intrinsic instruction record.
59  */
60 typedef struct _i_instr_record {
61         enum ikind    kind;       /**< must be INTRINSIC_INSTR */
62         ir_op         *op;        /**< the opcode that must be mapped. */
63         i_mapper_func i_mapper;   /**< the mapper function to call */
64         void          *ctx;       /**< mapper context */
65         void          *link;      /**< used in the construction algorithm, must be NULL */
66 } i_instr_record;
67
68 /**
69  * An intrinsic record.
70  */
71 typedef union _i_record {
72         i_call_record  i_call;
73         i_instr_record i_instr;
74 } i_record;
75
76 /**
77  * Go through all graphs and map calls to intrinsic functions and instructions.
78  *
79  * Every call or instruction is reported to its mapper function,
80  * which is responsible for rebuilding the graph.
81  *
82  * current_ir_graph is always set.
83  *
84  * @param list    an array of intrinsic map records
85  * @param length  the length of the array
86  *
87  * @return number of found intrinsics.
88  */
89 unsigned lower_intrinsics(i_record *list, int length);
90
91 /**
92  * A mapper for the integer absolute value: inttype abs(inttype v).
93  * Replaces the call by a Abs node.
94  *
95  * @return always 1
96  */
97 int i_mapper_Abs(ir_node *call, void *ctx);
98
99 /**
100  * A mapper for the alloca() function: pointer alloca(inttype size)
101  * Replaces the call by a Alloca(stack_alloc) node.
102  *
103  * @return always 1
104  */
105 int i_mapper_Alloca(ir_node *call, void *ctx);
106
107 /**
108  * A runtime routine description.
109  */
110 typedef struct _runtime_rt {
111         ir_entity *ent;            /**< The entity representing the runtime routine. */
112         ir_mode   *mode;           /**< The operation mode of the mapped instruction. */
113         ir_mode   *res_mode;       /**< The result mode of the mapped instruction or NULL. */
114         long      mem_proj_nr;     /**< if >= 0, create a memory ProjM() */
115         long      regular_proj_nr; /**< if >= 0, create a regular ProjX() */
116         long      exc_proj_nr;     /**< if >= 0, create a exception ProjX() */
117         long      exc_mem_proj_nr; /**< if >= 0, create a exception memory ProjM() */
118         long      res_proj_nr;     /**< if >= 0, first result projection number */
119 } runtime_rt;
120
121 /**
122  * A mapper for mapping unsupported instructions to runtime calls.
123  * Maps a op(arg_0, ..., arg_n) into a call to a runtime function
124  * rt(arg_0, ..., arg_n).
125  *
126  * The mapping is only done, if the modes of all arguments matches the
127  * modes of rt's argument.
128  * Further, if op has a memory input, the generated Call uses it, else
129  * it gets a NoMem.
130  * The pinned state of the Call will be set to the pinned state of op.
131  *
132  * Note that i_mapper_RuntimeCall() must be used with a i_instr_record.
133  *
134  * @return 1 if an op was mapped, 0 else
135  *
136  * Some examples:
137  *
138  * - Maps signed Div nodes to calls to rt_Div():
139    @code
140   runtime_rt rt_Div = {
141     ent("int rt_Div(int, int)"),
142     mode_T,
143     mode_Is,
144     pn_Div_M,
145     pn_Div_X_regular,
146     pn_Div_X_except,
147     pn_Div_M,
148     pn_Div_res
149   };
150   i_instr_record map_Div = {
151     INTRINSIC_INSTR,
152     op_Div,
153     i_mapper_RuntimeCall,
154     &rt_Div,
155     NULL
156   };
157   @endcode
158  *
159  * - Maps ConvD(F) to calls to rt_Float2Div():
160   @code
161   runtime_rt rt_Float2Double = {
162     ent("double rt_Float2Div(float)"),
163     get_type_mode("double"),
164     NULL,
165     -1,
166     -1,
167     -1,
168     -1,
169     -1
170   };
171   i_instr_record map_Float2Double = {
172     INTRINSIC_INSTR,
173     op_Conv,
174     i_mapper_RuntimeCall,
175     &rt_Float2Double,
176     NULL
177   };
178   @endcode
179  */
180 int i_mapper_RuntimeCall(ir_node *node, runtime_rt *rt);
181
182 #endif /* FIRM_LOWER_LOWER_INTRINSICS_H */