xref: /minix3/minix/lib/libmagicrt/include/magic_analysis.h (revision b2ed49a5d83e311ee0fa9e5ff613639b1bf77aaf)
1*b2ed49a5SDavid van Moolenbroek #ifndef _MAGIC_ANALYSIS_H
2*b2ed49a5SDavid van Moolenbroek #define _MAGIC_ANALYSIS_H
3*b2ed49a5SDavid van Moolenbroek 
4*b2ed49a5SDavid van Moolenbroek #include <magic.h>
5*b2ed49a5SDavid van Moolenbroek #include <magic_mem.h>
6*b2ed49a5SDavid van Moolenbroek 
7*b2ed49a5SDavid van Moolenbroek /* Special convenience types. */
8*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_SPECIAL_INIT(STR) { 0, STR, NULL, 0, STR, 0, 0, 0, 0, 0, 0, \
9*b2ed49a5SDavid van Moolenbroek     0, MAGIC_TYPE_FUNCTION, MAGIC_TYPE_EXTERNAL, 0, NULL }
10*b2ed49a5SDavid van Moolenbroek EXTERN char magic_ne_str[];
11*b2ed49a5SDavid van Moolenbroek EXTERN char magic_enf_str[];
12*b2ed49a5SDavid van Moolenbroek EXTERN char magic_bo_str[];
13*b2ed49a5SDavid van Moolenbroek EXTERN char magic_be_str[];
14*b2ed49a5SDavid van Moolenbroek EXTERN char magic_bv_str[];
15*b2ed49a5SDavid van Moolenbroek EXTERN char magic_vf_str[];
16*b2ed49a5SDavid van Moolenbroek EXTERN const struct _magic_type magic_NULL_ENTRY_TYPE;
17*b2ed49a5SDavid van Moolenbroek EXTERN const struct _magic_type magic_ENTRY_NOT_FOUND_TYPE;
18*b2ed49a5SDavid van Moolenbroek EXTERN const struct _magic_type magic_BAD_OFFSET_TYPE;
19*b2ed49a5SDavid van Moolenbroek EXTERN const struct _magic_type magic_BAD_ENTRY_TYPE;
20*b2ed49a5SDavid van Moolenbroek EXTERN const struct _magic_type magic_BAD_VALUE_TYPE;
21*b2ed49a5SDavid van Moolenbroek EXTERN const struct _magic_type magic_VALUE_FOUND;
22*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_NULL_ENTRY               (&magic_NULL_ENTRY_TYPE)
23*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_ENTRY_NOT_FOUND          (&magic_ENTRY_NOT_FOUND_TYPE)
24*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_BAD_OFFSET               (&magic_BAD_OFFSET_TYPE)
25*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_BAD_ENTRY                (&magic_BAD_ENTRY_TYPE)
26*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_BAD_VALUE                (&magic_BAD_VALUE_TYPE)
27*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_VALUE_FOUND              (&magic_VALUE_FOUND)
28*b2ed49a5SDavid van Moolenbroek #define MAGIC_TYPE_IS_SPECIAL(T) (T == MAGIC_TYPE_NULL_ENTRY                   \
29*b2ed49a5SDavid van Moolenbroek     || T == MAGIC_TYPE_ENTRY_NOT_FOUND || T == MAGIC_TYPE_BAD_OFFSET           \
30*b2ed49a5SDavid van Moolenbroek     || T == MAGIC_TYPE_BAD_ENTRY || T == MAGIC_TYPE_BAD_VALUE                  \
31*b2ed49a5SDavid van Moolenbroek     || T == MAGIC_TYPE_VALUE_FOUND)
32*b2ed49a5SDavid van Moolenbroek 
33*b2ed49a5SDavid van Moolenbroek /* Magic state element macros. */
34*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_POINTERS          0x00001
35*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_NONPOINTERS       0x00002
36*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_LIKELYPOINTERS    0x00004
37*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_DATA              0x00008
38*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_INVARIANTS        0x00010
39*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_VIOLATIONS        0x00020
40*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_WALKABLE          0x00040
41*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_DYNAMIC           0x00080
42*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_OUT_OF_BAND       0x00100
43*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_LIB_SRC           0x00200
44*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_ALL                                                  \
45*b2ed49a5SDavid van Moolenbroek     (MAGIC_SEL_ANALYZE_POINTERS | MAGIC_SEL_ANALYZE_NONPOINTERS                \
46*b2ed49a5SDavid van Moolenbroek     | MAGIC_SEL_ANALYZE_DATA | MAGIC_SEL_ANALYZE_INVARIANTS                    \
47*b2ed49a5SDavid van Moolenbroek     | MAGIC_SEL_ANALYZE_VIOLATIONS | MAGIC_SEL_ANALYZE_WALKABLE                \
48*b2ed49a5SDavid van Moolenbroek     | MAGIC_SEL_ANALYZE_DYNAMIC | MAGIC_SEL_ANALYZE_OUT_OF_BAND                \
49*b2ed49a5SDavid van Moolenbroek     | MAGIC_SEL_ANALYZE_LIB_SRC)
50*b2ed49a5SDavid van Moolenbroek 
51*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_SKIP_UNIONS               0x00400
52*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_SKIP_INTEGERS             0x00800
53*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_NONPTRS_AS_PTRS   0x01000
54*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZE_RETURN_TRG_PTRS   0x02000
55*b2ed49a5SDavid van Moolenbroek 
56*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_FOUND_DATA                0x04000
57*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_FOUND_INVARIANTS          0x08000
58*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_FOUND_VIOLATIONS          0X10000
59*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_FOUND_WALKABLE            0x20000
60*b2ed49a5SDavid van Moolenbroek 
61*b2ed49a5SDavid van Moolenbroek /* Magic state element analyzed. */
62*b2ed49a5SDavid van Moolenbroek typedef enum {
63*b2ed49a5SDavid van Moolenbroek     _ptr_type_found,
64*b2ed49a5SDavid van Moolenbroek     _other_types_found,
65*b2ed49a5SDavid van Moolenbroek     _void_type_found,
66*b2ed49a5SDavid van Moolenbroek     _comp_trg_types_found,
67*b2ed49a5SDavid van Moolenbroek     _badentry_found
68*b2ed49a5SDavid van Moolenbroek } _magic_trg_stats_t;
69*b2ed49a5SDavid van Moolenbroek struct _magic_sel_analyzed_s {
70*b2ed49a5SDavid van Moolenbroek     unsigned type_id, contained_type_id;
71*b2ed49a5SDavid van Moolenbroek     int flags;
72*b2ed49a5SDavid van Moolenbroek     int num;
73*b2ed49a5SDavid van Moolenbroek     union {
74*b2ed49a5SDavid van Moolenbroek         struct {
75*b2ed49a5SDavid van Moolenbroek             void *value;
76*b2ed49a5SDavid van Moolenbroek             union {
77*b2ed49a5SDavid van Moolenbroek                 struct _magic_dsentry dsentry;
78*b2ed49a5SDavid van Moolenbroek                 struct _magic_dfunction dfunction;
79*b2ed49a5SDavid van Moolenbroek             } trg;
80*b2ed49a5SDavid van Moolenbroek             struct {
81*b2ed49a5SDavid van Moolenbroek                 struct _magic_dsentry *dsentry;
82*b2ed49a5SDavid van Moolenbroek                 struct _magic_dfunction *dfunction;
83*b2ed49a5SDavid van Moolenbroek             } trg_p;
84*b2ed49a5SDavid van Moolenbroek             int trg_flags;
85*b2ed49a5SDavid van Moolenbroek             int trg_offset;
86*b2ed49a5SDavid van Moolenbroek             _magic_selement_t trg_selements[MAGIC_MAX_RECURSIVE_TYPES + 1];
87*b2ed49a5SDavid van Moolenbroek             _magic_trg_stats_t trg_stats[MAGIC_MAX_RECURSIVE_TYPES + 1];
88*b2ed49a5SDavid van Moolenbroek             int first_legal_trg_type;
89*b2ed49a5SDavid van Moolenbroek             unsigned num_legal_trg_types;
90*b2ed49a5SDavid van Moolenbroek             unsigned num_trg_types;
91*b2ed49a5SDavid van Moolenbroek         } ptr;
92*b2ed49a5SDavid van Moolenbroek         struct {
93*b2ed49a5SDavid van Moolenbroek             int value;
94*b2ed49a5SDavid van Moolenbroek             int trg_flags;
95*b2ed49a5SDavid van Moolenbroek         } nonptr;
96*b2ed49a5SDavid van Moolenbroek     } u;
97*b2ed49a5SDavid van Moolenbroek };
98*b2ed49a5SDavid van Moolenbroek typedef struct _magic_sel_analyzed_s _magic_sel_analyzed_t;
99*b2ed49a5SDavid van Moolenbroek 
100*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_HAS_TRG_FUNCTION(E)                             \
101*b2ed49a5SDavid van Moolenbroek     (((E)->u.ptr.trg_flags & MAGIC_STATE_TEXT) != 0)
102*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_HAS_TRG_SENTRY(E)                               \
103*b2ed49a5SDavid van Moolenbroek     ((E)->u.ptr.trg_flags && !MAGIC_SEL_ANALYZED_PTR_HAS_TRG_FUNCTION(E))
104*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_SENTRY(E)                                       \
105*b2ed49a5SDavid van Moolenbroek     ((E)->u.ptr.trg_flags & MAGIC_SEL_ANALYZE_RETURN_TRG_PTRS)                 \
106*b2ed49a5SDavid van Moolenbroek     ? (E)->u.ptr.trg_p.dsentry->sentry                                         \
107*b2ed49a5SDavid van Moolenbroek     : (E)->u.ptr.trg.dsentry.sentry
108*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_SENTRY_ADDRESS(E)                               \
109*b2ed49a5SDavid van Moolenbroek     ((E)->u.ptr.trg_flags & MAGIC_SEL_ANALYZE_RETURN_TRG_PTRS)                 \
110*b2ed49a5SDavid van Moolenbroek     ? &((E)->u.ptr.trg_p.dsentry->sentry)                                      \
111*b2ed49a5SDavid van Moolenbroek     : &((E)->u.ptr.trg.dsentry.sentry)
112*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_FUNCTION(E)                                     \
113*b2ed49a5SDavid van Moolenbroek     ((E)->u.ptr.trg_flags & MAGIC_SEL_ANALYZE_RETURN_TRG_PTRS)                 \
114*b2ed49a5SDavid van Moolenbroek     ? (E)->u.ptr.trg_p.dfunction->function                                     \
115*b2ed49a5SDavid van Moolenbroek     : (E)->u.ptr.trg.dfunction.function
116*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_TRG_NAME(E)                                     \
117*b2ed49a5SDavid van Moolenbroek     (MAGIC_SEL_ANALYZED_PTR_HAS_SPECIAL_TRG_TYPE(E) ? ""                       \
118*b2ed49a5SDavid van Moolenbroek     : MAGIC_SEL_ANALYZED_PTR_HAS_TRG_FUNCTION(E)                               \
119*b2ed49a5SDavid van Moolenbroek     ? (MAGIC_SEL_ANALYZED_PTR_FUNCTION(E)).name                                \
120*b2ed49a5SDavid van Moolenbroek     : (MAGIC_SEL_ANALYZED_PTR_HAS_TRG_SENTRY(E)                                \
121*b2ed49a5SDavid van Moolenbroek     ? (MAGIC_SEL_ANALYZED_PTR_SENTRY(E)).name : "?"))
122*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_TRG_ADDRESS(E)                                  \
123*b2ed49a5SDavid van Moolenbroek     (MAGIC_SEL_ANALYZED_PTR_HAS_SPECIAL_TRG_TYPE(E) ? NULL                     \
124*b2ed49a5SDavid van Moolenbroek     : MAGIC_SEL_ANALYZED_PTR_HAS_TRG_FUNCTION(E)                               \
125*b2ed49a5SDavid van Moolenbroek     ? (MAGIC_SEL_ANALYZED_PTR_FUNCTION(E)).address                             \
126*b2ed49a5SDavid van Moolenbroek     : (MAGIC_SEL_ANALYZED_PTR_SENTRY(E)).address)
127*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_PRINT_TRG_ABS_NAME(E)                           \
128*b2ed49a5SDavid van Moolenbroek     do {                                                                       \
129*b2ed49a5SDavid van Moolenbroek         if (MAGIC_SEL_ANALYZED_PTR_HAS_SPECIAL_TRG_TYPE(E)                     \
130*b2ed49a5SDavid van Moolenbroek             || MAGIC_SEL_ANALYZED_PTR_HAS_TRG_FUNCTION(E)) {                   \
131*b2ed49a5SDavid van Moolenbroek             _magic_printf(MAGIC_SEL_ANALYZED_PTR_TRG_NAME(E));                 \
132*b2ed49a5SDavid van Moolenbroek         } else {                                                               \
133*b2ed49a5SDavid van Moolenbroek             magic_print_sentry_abs_name(                                       \
134*b2ed49a5SDavid van Moolenbroek                 MAGIC_SEL_ANALYZED_PTR_SENTRY_ADDRESS(E));                     \
135*b2ed49a5SDavid van Moolenbroek         }                                                                      \
136*b2ed49a5SDavid van Moolenbroek     } while(0)
137*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_FIRST_TRG_TYPE(E)                               \
138*b2ed49a5SDavid van Moolenbroek     ((E)->u.ptr.trg_selements[0].type)
139*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_HAS_SPECIAL_TRG_TYPE(E)                         \
140*b2ed49a5SDavid van Moolenbroek     (MAGIC_TYPE_IS_SPECIAL(MAGIC_SEL_ANALYZED_PTR_FIRST_TRG_TYPE(E)))
141*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PTR_SET_SPECIAL_TRG_TYPE(E,T)                       \
142*b2ed49a5SDavid van Moolenbroek     do {                                                                       \
143*b2ed49a5SDavid van Moolenbroek         (E)->u.ptr.trg_selements[0].type = T;                                  \
144*b2ed49a5SDavid van Moolenbroek         (E)->u.ptr.num_trg_types = 1;                                          \
145*b2ed49a5SDavid van Moolenbroek         (E)->u.ptr.num_legal_trg_types = 0;                                    \
146*b2ed49a5SDavid van Moolenbroek         (E)->u.ptr.first_legal_trg_type = -1;                                  \
147*b2ed49a5SDavid van Moolenbroek     } while(0)
148*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_TRG_FLAGS(E)                                        \
149*b2ed49a5SDavid van Moolenbroek     ((E)->type_id == MAGIC_TYPE_POINTER ? (E)->u.ptr.trg_flags                 \
150*b2ed49a5SDavid van Moolenbroek     : (E)->u.nonptr.trg_flags)
151*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_FLAG(E,F) (((E)->flags & F) != 0)
152*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_TRG_STATS_HAS_VIOLATIONS(E)                         \
153*b2ed49a5SDavid van Moolenbroek     ((E) == _other_types_found || (E) == _badentry_found)
154*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_TRG_STATS_C(E)                                      \
155*b2ed49a5SDavid van Moolenbroek     ((E) == _ptr_type_found ? 'p' : (E) == _other_types_found ? 'o'            \
156*b2ed49a5SDavid van Moolenbroek     : (E) == _void_type_found ? 'v' : (E) == _comp_trg_types_found ? 'c'       \
157*b2ed49a5SDavid van Moolenbroek     : (E) == _badentry_found ? 'b' : '?')
158*b2ed49a5SDavid van Moolenbroek 
159*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_ANALYZED_PRINT(E, FLAGS) do {                                \
160*b2ed49a5SDavid van Moolenbroek         _magic_printf("SEL_ANALYZED: (num=%d, type=%s, flags(DIVW)=%d%d%d%d",  \
161*b2ed49a5SDavid van Moolenbroek             (E)->num, (E)->type_id == MAGIC_TYPE_POINTER ? "ptr" : "nonptr",   \
162*b2ed49a5SDavid van Moolenbroek             MAGIC_SEL_ANALYZED_FLAG(E, MAGIC_SEL_FOUND_DATA),                  \
163*b2ed49a5SDavid van Moolenbroek             MAGIC_SEL_ANALYZED_FLAG(E, MAGIC_SEL_FOUND_INVARIANTS),            \
164*b2ed49a5SDavid van Moolenbroek             MAGIC_SEL_ANALYZED_FLAG(E, MAGIC_SEL_FOUND_VIOLATIONS),            \
165*b2ed49a5SDavid van Moolenbroek             MAGIC_SEL_ANALYZED_FLAG(E, MAGIC_SEL_FOUND_WALKABLE));             \
166*b2ed49a5SDavid van Moolenbroek         if((E)->type_id == MAGIC_TYPE_POINTER) {                               \
167*b2ed49a5SDavid van Moolenbroek             _magic_printf(", value=0x%08x, trg_name=", (E)->u.ptr.value);      \
168*b2ed49a5SDavid van Moolenbroek             MAGIC_SEL_ANALYZED_PTR_PRINT_TRG_ABS_NAME(E);                      \
169*b2ed49a5SDavid van Moolenbroek             _magic_printf(", trg_offset=%d, trg_flags(RL)=%c%c",               \
170*b2ed49a5SDavid van Moolenbroek                 (E)->u.ptr.trg_offset,                                         \
171*b2ed49a5SDavid van Moolenbroek                 (E)->u.ptr.trg_flags                                           \
172*b2ed49a5SDavid van Moolenbroek                     ? MAGIC_STATE_FLAGS_REGION_C((E)->u.ptr.trg_flags) : 0,    \
173*b2ed49a5SDavid van Moolenbroek                 (E)->u.ptr.trg_flags                                           \
174*b2ed49a5SDavid van Moolenbroek                     ? MAGIC_STATE_FLAGS_LIBSPEC_C((E)->u.ptr.trg_flags) : 0);  \
175*b2ed49a5SDavid van Moolenbroek             if((E)->u.ptr.num_trg_types > 0) {                                 \
176*b2ed49a5SDavid van Moolenbroek                 _magic_printf(", trg_selements=(");                            \
177*b2ed49a5SDavid van Moolenbroek                 magic_sel_analyzed_trg_selements_print(E, FLAGS);              \
178*b2ed49a5SDavid van Moolenbroek                 _magic_printf(")");                                            \
179*b2ed49a5SDavid van Moolenbroek             }                                                                  \
180*b2ed49a5SDavid van Moolenbroek         } else {                                                               \
181*b2ed49a5SDavid van Moolenbroek             _magic_printf(", value=%d/0x%08x",                                 \
182*b2ed49a5SDavid van Moolenbroek                 (E)->u.nonptr.value, (E)->u.nonptr.value);                     \
183*b2ed49a5SDavid van Moolenbroek             if((E)->u.nonptr.trg_flags) {                                      \
184*b2ed49a5SDavid van Moolenbroek                 _magic_printf(", trg_flags(RL)=%c%c",                          \
185*b2ed49a5SDavid van Moolenbroek                     MAGIC_STATE_FLAGS_REGION_C((E)->u.nonptr.trg_flags),       \
186*b2ed49a5SDavid van Moolenbroek                     MAGIC_STATE_FLAGS_LIBSPEC_C((E)->u.nonptr.trg_flags));     \
187*b2ed49a5SDavid van Moolenbroek             }                                                                  \
188*b2ed49a5SDavid van Moolenbroek         }                                                                      \
189*b2ed49a5SDavid van Moolenbroek         _magic_printf(")");                                                    \
190*b2ed49a5SDavid van Moolenbroek     } while(0)
191*b2ed49a5SDavid van Moolenbroek 
192*b2ed49a5SDavid van Moolenbroek /* Magic state element stats. */
193*b2ed49a5SDavid van Moolenbroek struct _magic_sel_stats_s {
194*b2ed49a5SDavid van Moolenbroek     unsigned ptr_found;
195*b2ed49a5SDavid van Moolenbroek     unsigned nonptr_found;
196*b2ed49a5SDavid van Moolenbroek     unsigned nonptr_unconstrained_found;
197*b2ed49a5SDavid van Moolenbroek     int trg_flags;
198*b2ed49a5SDavid van Moolenbroek     int ptr_type_found;
199*b2ed49a5SDavid van Moolenbroek     int other_types_found;
200*b2ed49a5SDavid van Moolenbroek     int null_type_found;
201*b2ed49a5SDavid van Moolenbroek     int badoffset_found;
202*b2ed49a5SDavid van Moolenbroek     int unknown_found;
203*b2ed49a5SDavid van Moolenbroek     int void_type_found;
204*b2ed49a5SDavid van Moolenbroek     int comp_trg_types_found;
205*b2ed49a5SDavid van Moolenbroek     int value_found;
206*b2ed49a5SDavid van Moolenbroek     int badvalue_found;
207*b2ed49a5SDavid van Moolenbroek     int badentry_found;
208*b2ed49a5SDavid van Moolenbroek };
209*b2ed49a5SDavid van Moolenbroek typedef struct _magic_sel_stats_s _magic_sel_stats_t;
210*b2ed49a5SDavid van Moolenbroek 
211*b2ed49a5SDavid van Moolenbroek /* Magic state element stats. */
212*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_STAT_INCR(S,I,F) ((S)->F += (I)->F)
213*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_STATS_INCR(S,I) do {                                         \
214*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, ptr_found);                                   \
215*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, nonptr_found);                                \
216*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, nonptr_unconstrained_found);                  \
217*b2ed49a5SDavid van Moolenbroek         S->trg_flags |= I->trg_flags;                                          \
218*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, ptr_type_found);                              \
219*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, other_types_found);                           \
220*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, null_type_found);                             \
221*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, badoffset_found);                             \
222*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, unknown_found);                               \
223*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, void_type_found);                             \
224*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, comp_trg_types_found);                        \
225*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, value_found);                                 \
226*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, badvalue_found);                              \
227*b2ed49a5SDavid van Moolenbroek         MAGIC_SEL_STAT_INCR(S,I, badentry_found);                              \
228*b2ed49a5SDavid van Moolenbroek     } while(0)
229*b2ed49a5SDavid van Moolenbroek 
230*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_STATS_HAS_VIOLATIONS(S)                                      \
231*b2ed49a5SDavid van Moolenbroek     (MAGIC_SEL_STATS_NUM_VIOLATIONS(S) > 0)
232*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_STATS_NUM_VIOLATIONS(S)                                      \
233*b2ed49a5SDavid van Moolenbroek     ((S)->ptr_found ? MAGIC_SEL_PTR_STATS_NUM_VIOLATIONS(S)                    \
234*b2ed49a5SDavid van Moolenbroek         : MAGIC_SEL_NONPTR_STATS_NUM_VIOLATIONS(S))
235*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_PTR_STATS_NUM_VIOLATIONS(S) ((S)->other_types_found          \
236*b2ed49a5SDavid van Moolenbroek     + (S)->badoffset_found + (S)->unknown_found + (S)->badvalue_found          \
237*b2ed49a5SDavid van Moolenbroek     + (S)->badentry_found)
238*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_NONPTR_STATS_NUM_VIOLATIONS(S) ((S)->badvalue_found)
239*b2ed49a5SDavid van Moolenbroek 
240*b2ed49a5SDavid van Moolenbroek #define MAGIC_SEL_STATS_PRINT(E) do {                                          \
241*b2ed49a5SDavid van Moolenbroek         _magic_printf("SEL_STATS: (type=%s",                                   \
242*b2ed49a5SDavid van Moolenbroek             (E)->ptr_found ? "ptr" : "nonptr");                                \
243*b2ed49a5SDavid van Moolenbroek         if((E)->trg_flags) {                                                   \
244*b2ed49a5SDavid van Moolenbroek             _magic_printf(", trg_flags(RL)=%c%c",                              \
245*b2ed49a5SDavid van Moolenbroek                 MAGIC_STATE_FLAGS_REGION_C((E)->trg_flags),                    \
246*b2ed49a5SDavid van Moolenbroek                 MAGIC_STATE_FLAGS_LIBSPEC_C((E)->trg_flags));                  \
247*b2ed49a5SDavid van Moolenbroek         }                                                                      \
248*b2ed49a5SDavid van Moolenbroek         if((E)->ptr_found) _magic_printf(", ptr_found=%d", (E)->ptr_found);    \
249*b2ed49a5SDavid van Moolenbroek         if((E)->nonptr_found)                                                  \
250*b2ed49a5SDavid van Moolenbroek             _magic_printf(", nonptr_found=%d", (E)->nonptr_found);             \
251*b2ed49a5SDavid van Moolenbroek         if((E)->nonptr_unconstrained_found)                                    \
252*b2ed49a5SDavid van Moolenbroek             _magic_printf(", nonptr_unconstrained_found=%d",                   \
253*b2ed49a5SDavid van Moolenbroek                 (E)->nonptr_unconstrained_found);                              \
254*b2ed49a5SDavid van Moolenbroek         if((E)->ptr_type_found)                                                \
255*b2ed49a5SDavid van Moolenbroek             _magic_printf(", ptr_type_found=%d", (E)->ptr_type_found);         \
256*b2ed49a5SDavid van Moolenbroek         if((E)->other_types_found)                                             \
257*b2ed49a5SDavid van Moolenbroek             _magic_printf(", other_types_found=%d", (E)->other_types_found);   \
258*b2ed49a5SDavid van Moolenbroek         if((E)->null_type_found)                                               \
259*b2ed49a5SDavid van Moolenbroek             _magic_printf(", null_type_found=%d", (E)->null_type_found);       \
260*b2ed49a5SDavid van Moolenbroek         if((E)->badoffset_found)                                               \
261*b2ed49a5SDavid van Moolenbroek             _magic_printf(", badoffset_found=%d", (E)->badoffset_found);       \
262*b2ed49a5SDavid van Moolenbroek         if((E)->unknown_found)                                                 \
263*b2ed49a5SDavid van Moolenbroek             _magic_printf(", unknown_found=%d", (E)->unknown_found);           \
264*b2ed49a5SDavid van Moolenbroek         if((E)->void_type_found)                                               \
265*b2ed49a5SDavid van Moolenbroek             _magic_printf(", void_type_found=%d", (E)->void_type_found);       \
266*b2ed49a5SDavid van Moolenbroek         if((E)->comp_trg_types_found)                                          \
267*b2ed49a5SDavid van Moolenbroek             _magic_printf(", comp_trg_types_found=%d",                         \
268*b2ed49a5SDavid van Moolenbroek                 (E)->comp_trg_types_found);                                    \
269*b2ed49a5SDavid van Moolenbroek         if((E)->value_found)                                                   \
270*b2ed49a5SDavid van Moolenbroek             _magic_printf(", value_found=%d", (E)->value_found);               \
271*b2ed49a5SDavid van Moolenbroek         if((E)->badvalue_found)                                                \
272*b2ed49a5SDavid van Moolenbroek             _magic_printf(", badvalue_found=%d", (E)->badvalue_found);         \
273*b2ed49a5SDavid van Moolenbroek         if((E)->badentry_found)                                                \
274*b2ed49a5SDavid van Moolenbroek             _magic_printf(", badentry_found=%d", (E)->badentry_found);         \
275*b2ed49a5SDavid van Moolenbroek         _magic_printf(", violations=%d", MAGIC_SEL_STATS_NUM_VIOLATIONS(E));   \
276*b2ed49a5SDavid van Moolenbroek         _magic_printf(")");                                                    \
277*b2ed49a5SDavid van Moolenbroek     } while(0)
278*b2ed49a5SDavid van Moolenbroek 
279*b2ed49a5SDavid van Moolenbroek /* Magic sentry macros. */
280*b2ed49a5SDavid van Moolenbroek #define MAGIC_SENTRY_ANALYZE_STOP           1
281*b2ed49a5SDavid van Moolenbroek #define MAGIC_SENTRY_ANALYZE_CONTINUE       2
282*b2ed49a5SDavid van Moolenbroek #define MAGIC_SENTRY_ANALYZE_SKIP_PATH      3
283*b2ed49a5SDavid van Moolenbroek #define MAGIC_SENTRY_ANALYZE_IS_VALID_RET(R)                                   \
284*b2ed49a5SDavid van Moolenbroek    ((R)>=MAGIC_SENTRY_ANALYZE_STOP && (R)<=MAGIC_SENTRY_ANALYZE_SKIP_PATH)
285*b2ed49a5SDavid van Moolenbroek 
286*b2ed49a5SDavid van Moolenbroek #ifndef __MINIX
287*b2ed49a5SDavid van Moolenbroek #define MAGIC_PTR_LIKELY_INTS_START         0xFFFFF000
288*b2ed49a5SDavid van Moolenbroek #else
289*b2ed49a5SDavid van Moolenbroek #define MAGIC_PTR_LIKELY_INTS_START         0xE0000000
290*b2ed49a5SDavid van Moolenbroek #endif
291*b2ed49a5SDavid van Moolenbroek #define MAGIC_PTR_LIKELY_INTS_END           0xFFF
292*b2ed49a5SDavid van Moolenbroek #define MAGIC_PTR_IS_LIKELY_INT(V)                                             \
293*b2ed49a5SDavid van Moolenbroek     ((V) && ((unsigned)(V)>=MAGIC_PTR_LIKELY_INTS_START                        \
294*b2ed49a5SDavid van Moolenbroek     || (unsigned)(V)<=MAGIC_PTR_LIKELY_INTS_END))
295*b2ed49a5SDavid van Moolenbroek #define MAGIC_INT_IS_LIKELY_PTR(V)                                             \
296*b2ed49a5SDavid van Moolenbroek     ((V) && !MAGIC_PTR_IS_LIKELY_INT((void*)V))
297*b2ed49a5SDavid van Moolenbroek 
298*b2ed49a5SDavid van Moolenbroek /* Magic callbacks. */
299*b2ed49a5SDavid van Moolenbroek typedef int (*magic_cb_sentries_analyze_pre_t)(void);
300*b2ed49a5SDavid van Moolenbroek PUBLIC void magic_setcb_sentries_analyze_pre(magic_cb_sentries_analyze_pre_t cb);
301*b2ed49a5SDavid van Moolenbroek 
302*b2ed49a5SDavid van Moolenbroek /* Magic state entry functions. */
303*b2ed49a5SDavid van Moolenbroek typedef int (*magic_sentry_analyze_cb_t)(_magic_selement_t* selement,
304*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats,
305*b2ed49a5SDavid van Moolenbroek     void* cb_args);
306*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_ptr_types(struct _magic_sentry* entry);
307*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_extract_ptrs(struct _magic_sentry* entry,
308*b2ed49a5SDavid van Moolenbroek     void ****ptr_map, const struct _magic_type ***ptr_type_map, int *ptr_num);
309*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_analyze(struct _magic_sentry* sentry, int flags,
310*b2ed49a5SDavid van Moolenbroek     const magic_sentry_analyze_cb_t cb, void* cb_args,
311*b2ed49a5SDavid van Moolenbroek     _magic_sel_stats_t *sentry_stats);
312*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentries_analyze(int flags, const magic_sentry_analyze_cb_t cb,
313*b2ed49a5SDavid van Moolenbroek     void* cb_args, _magic_sel_stats_t *sentries_stats);
314*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_selements(struct _magic_sentry* sentry);
315*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_ptr_selements(struct _magic_sentry* sentry,
316*b2ed49a5SDavid van Moolenbroek     int skip_null_ptrs, int max_target_recusions);
317*b2ed49a5SDavid van Moolenbroek 
318*b2ed49a5SDavid van Moolenbroek /* Magic dynamic state entry functions. */
319*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_dsentries_analyze(int flags,
320*b2ed49a5SDavid van Moolenbroek     const magic_sentry_analyze_cb_t cb, void* cb_args,
321*b2ed49a5SDavid van Moolenbroek     _magic_sel_stats_t *dsentries_stats);
322*b2ed49a5SDavid van Moolenbroek 
323*b2ed49a5SDavid van Moolenbroek /* Magic sentry analyze callbacks. */
324*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_el_cb(_magic_selement_t* selement,
325*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats,
326*b2ed49a5SDavid van Moolenbroek     void* cb_args);
327*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_ptr_el_cb(_magic_selement_t* selement,
328*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats,
329*b2ed49a5SDavid van Moolenbroek     void* cb_args);
330*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_el_with_trg_reg_cb(_magic_selement_t* selement,
331*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats,
332*b2ed49a5SDavid van Moolenbroek     void* cb_args);
333*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_sentry_print_el_with_trg_cb(_magic_selement_t* selement,
334*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats,
335*b2ed49a5SDavid van Moolenbroek     void* cb_args);
336*b2ed49a5SDavid van Moolenbroek 
337*b2ed49a5SDavid van Moolenbroek /* Magic sentry analyze helpers. */
338*b2ed49a5SDavid van Moolenbroek #define magic_sentry_analyze_invariants(sentry, cb, cb_args, sentry_stats)     \
339*b2ed49a5SDavid van Moolenbroek     magic_sentry_analyze(sentry, MAGIC_SEL_ANALYZE_POINTERS                    \
340*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_INVARIANTS, cb,    \
341*b2ed49a5SDavid van Moolenbroek         cb_args, sentry_stats)
342*b2ed49a5SDavid van Moolenbroek #define magic_sentries_analyze_invariants(cb, cb_args, sentries_stats)         \
343*b2ed49a5SDavid van Moolenbroek     magic_sentries_analyze(MAGIC_SEL_ANALYZE_POINTERS                          \
344*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_INVARIANTS, cb,    \
345*b2ed49a5SDavid van Moolenbroek         cb_args, sentries_stats)
346*b2ed49a5SDavid van Moolenbroek #define magic_dsentries_analyze_invariants(cb, cb_args, dsentries_stats)       \
347*b2ed49a5SDavid van Moolenbroek     magic_dsentries_analyze(MAGIC_SEL_ANALYZE_POINTERS                         \
348*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_INVARIANTS, cb,    \
349*b2ed49a5SDavid van Moolenbroek         cb_args, dsentries_stats)
350*b2ed49a5SDavid van Moolenbroek #define magic_allsentries_analyze_invariants(cb, cb_args, sentries_stats)      \
351*b2ed49a5SDavid van Moolenbroek     magic_sentries_analyze(MAGIC_SEL_ANALYZE_POINTERS                          \
352*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_INVARIANTS         \
353*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_DYNAMIC, cb, cb_args, sentries_stats)
354*b2ed49a5SDavid van Moolenbroek 
355*b2ed49a5SDavid van Moolenbroek #define magic_sentry_analyze_violations(sentry, cb, cb_args, sentry_stats)     \
356*b2ed49a5SDavid van Moolenbroek     magic_sentry_analyze(sentry, MAGIC_SEL_ANALYZE_POINTERS                    \
357*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_VIOLATIONS, cb,    \
358*b2ed49a5SDavid van Moolenbroek         cb_args, sentry_stats)
359*b2ed49a5SDavid van Moolenbroek #define magic_sentries_analyze_violations(cb, cb_args, sentries_stats)         \
360*b2ed49a5SDavid van Moolenbroek     magic_sentries_analyze(MAGIC_SEL_ANALYZE_POINTERS                          \
361*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_VIOLATIONS, cb,    \
362*b2ed49a5SDavid van Moolenbroek         cb_args, sentries_stats)
363*b2ed49a5SDavid van Moolenbroek #define magic_dsentries_analyze_violations(cb, cb_args, dsentries_stats)       \
364*b2ed49a5SDavid van Moolenbroek     magic_dsentries_analyze(MAGIC_SEL_ANALYZE_POINTERS                         \
365*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_VIOLATIONS, cb,    \
366*b2ed49a5SDavid van Moolenbroek         cb_args, dsentries_stats)
367*b2ed49a5SDavid van Moolenbroek #define magic_allsentries_analyze_violations(cb, cb_args, sentries_stats)      \
368*b2ed49a5SDavid van Moolenbroek     magic_sentries_analyze(MAGIC_SEL_ANALYZE_POINTERS                          \
369*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_NONPOINTERS | MAGIC_SEL_ANALYZE_VIOLATIONS         \
370*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_DYNAMIC, cb, cb_args, sentries_stats)
371*b2ed49a5SDavid van Moolenbroek 
372*b2ed49a5SDavid van Moolenbroek #define magic_sentry_analyze_likely_pointers(sentry, cb, cb_args, sentry_stats)\
373*b2ed49a5SDavid van Moolenbroek     magic_sentry_analyze(sentry, MAGIC_SEL_ANALYZE_LIKELYPOINTERS              \
374*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_DATA, cb, cb_args, sentry_stats)
375*b2ed49a5SDavid van Moolenbroek #define magic_sentries_analyze_likely_pointers(cb, cb_args, sentries_stats)    \
376*b2ed49a5SDavid van Moolenbroek     magic_sentries_analyze(MAGIC_SEL_ANALYZE_LIKELYPOINTERS                    \
377*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_DATA, cb, cb_args, sentries_stats)
378*b2ed49a5SDavid van Moolenbroek #define magic_dsentries_analyze_likely_pointers(cb, cb_args, dsentries_stats)  \
379*b2ed49a5SDavid van Moolenbroek     magic_dsentries_analyze(MAGIC_SEL_ANALYZE_LIKELYPOINTERS                   \
380*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_DATA, cb, cb_args, dsentries_stats)
381*b2ed49a5SDavid van Moolenbroek #define magic_allsentries_analyze_likely_pointers(cb, cb_args, sentries_stats) \
382*b2ed49a5SDavid van Moolenbroek     magic_sentries_analyze(MAGIC_SEL_ANALYZE_LIKELYPOINTERS                    \
383*b2ed49a5SDavid van Moolenbroek         | MAGIC_SEL_ANALYZE_DATA | MAGIC_SEL_ANALYZE_DYNAMIC, cb, cb_args,     \
384*b2ed49a5SDavid van Moolenbroek         sentries_stats)
385*b2ed49a5SDavid van Moolenbroek 
386*b2ed49a5SDavid van Moolenbroek /* Magic state type functions. */
387*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_type_count_ptrs(const struct _magic_type* type, int *ptr_num);
388*b2ed49a5SDavid van Moolenbroek 
389*b2ed49a5SDavid van Moolenbroek /* Magic type walk callbacks. */
390*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_type_examine_ptr_cb(const struct _magic_type* parent_type,
391*b2ed49a5SDavid van Moolenbroek     const unsigned parent_offset, int child_num, const struct _magic_type* type,
392*b2ed49a5SDavid van Moolenbroek     const unsigned offset, int depth, void* cb_args);
393*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_type_extract_ptr_cb(const struct _magic_type* parent_type,
394*b2ed49a5SDavid van Moolenbroek     const unsigned parent_offset, int child_num, const struct _magic_type* type,
395*b2ed49a5SDavid van Moolenbroek     const unsigned offset, int depth, void* cb_args);
396*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_type_analyzer_cb(const struct _magic_type* parent_type,
397*b2ed49a5SDavid van Moolenbroek     const unsigned parent_offset, int child_num, const struct _magic_type* type,
398*b2ed49a5SDavid van Moolenbroek     const unsigned offset, int depth, void* cb_args);
399*b2ed49a5SDavid van Moolenbroek 
400*b2ed49a5SDavid van Moolenbroek /* Magic state element functions. */
401*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_analyze(_magic_selement_t *selement, int flags,
402*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats);
403*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_analyze_ptr(_magic_selement_t *selement, int flags,
404*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats);
405*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_analyze_nonptr(_magic_selement_t *selement, int flags,
406*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats);
407*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_analyze_ptr_value_invs(_magic_selement_t *selement,
408*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats);
409*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_analyze_ptr_trg_invs(_magic_selement_t *selement,
410*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats);
411*b2ed49a5SDavid van Moolenbroek PUBLIC _magic_trg_stats_t
412*b2ed49a5SDavid van Moolenbroek magic_selement_analyze_ptr_target(const struct _magic_type *ptr_type,
413*b2ed49a5SDavid van Moolenbroek     const struct _magic_type *trg_type, int trg_flags);
414*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_analyze_ptr_type_invs(_magic_selement_t *selement,
415*b2ed49a5SDavid van Moolenbroek     _magic_sel_analyzed_t *sel_analyzed, _magic_sel_stats_t *sel_stats);
416*b2ed49a5SDavid van Moolenbroek PUBLIC int magic_selement_recurse_ptr(_magic_selement_t *selement,
417*b2ed49a5SDavid van Moolenbroek     _magic_selement_t *new_selement, int max_steps);
418*b2ed49a5SDavid van Moolenbroek PUBLIC void
419*b2ed49a5SDavid van Moolenbroek magic_sel_analyzed_trg_selements_print(_magic_sel_analyzed_t *sel_analyzed,
420*b2ed49a5SDavid van Moolenbroek     int flags);
421*b2ed49a5SDavid van Moolenbroek PUBLIC _magic_selement_t*
422*b2ed49a5SDavid van Moolenbroek magic_selement_type_cast(_magic_selement_t *selement, int flags,
423*b2ed49a5SDavid van Moolenbroek     const struct _magic_type* type, _magic_sel_analyzed_t *sel_analyzed,
424*b2ed49a5SDavid van Moolenbroek     _magic_sel_stats_t *sel_stats);
425*b2ed49a5SDavid van Moolenbroek 
426*b2ed49a5SDavid van Moolenbroek #endif /* _MAGIC_ANALYSIS_H */
427*b2ed49a5SDavid van Moolenbroek 
428