blob: 21db357066a7c611ae9f88aa2d9c731cca62f85a [file] [log] [blame]
The Android Open Source Project88b60792009-03-03 19:28:42 -08001#ifndef RANGESORT_H
2#define RANGESORT_H
3
4/* This implements a simple sorted list of non-overlapping ranges. */
5
6#include <debug.h>
7#include <common.h>
8#include <gelf.h>
9
10typedef enum range_error_t {
11 ERROR_CONTAINS,
12 ERROR_OVERLAPS
13} range_error_t;
14
15typedef struct range_t range_t;
16struct range_t {
17 GElf_Off start;
18 GElf_Off length;
19 void *user;
20 void (*err_fn)(range_error_t, range_t *, range_t *);
21 void (*user_dtor)(void *);
22};
23
24typedef struct range_list_t range_list_t;
25
26range_list_t* init_range_list();
27void destroy_range_list(range_list_t *);
28
29/* Just adds a range to the list. We won't detect whether the range overlaps
30 other ranges or contains them, or is contained by them, till we call
31 sort_ranges(). */
32void add_unique_range_nosort(range_list_t *ranges,
33 GElf_Off start, GElf_Off length,
34 void *user,
35 void (*err_fn)(range_error_t, range_t *, range_t *),
36 void (*user_dtor)(void * ));
37
38/* Sorts the ranges. If there are overlapping ranges or ranges that contain
39 other ranges, it will cause the program to exit with a FAIL. */
40range_list_t* sort_ranges(range_list_t *ranges);
41/* Find which range value falls in. Return that range or NULL if value does
42 not fall within any range. */
43range_t *find_range(range_list_t *ranges, GElf_Off value);
44int get_num_ranges(const range_list_t *ranges);
45range_t *get_sorted_ranges(const range_list_t *ranges, int *num_ranges);
46GElf_Off get_last_address(const range_list_t *ranges);
47
48/* This returns a range_list_t handle that contains ranges composed of the
49 adjacent ranges of the input range list. The user data of each range in
50 the range list is a structure of the type contiguous_range_info_t.
51 This structure contains an array of pointers to copies of the original
52 range_t structures comprising each new contiguous range, as well as the
53 length of that array.
54
55 NOTE: The input range must be sorted!
56
57 NOTE: destroy_range_list() will take care of releasing the data that it
58 allocates as a result of calling get_contiguous_ranges(). Do not free that
59 data yourself.
60
61 NOTE: the user data of the original range_t structures is simply copied, so
62 be careful handling it. You can destroy the range_list_t with
63 destroy_range_list() as usual. On error, the function does not return--the
64 program terminates.
65
66 NOTE: The returned range is not sorted. You must call sort_ranges() if you
67 need to.
68*/
69
70typedef struct {
71 int num_ranges;
72 range_t *ranges;
73} contiguous_range_info_t;
74
75range_list_t* get_contiguous_ranges(const range_list_t *);
76
77/* The function below takes in two range lists: r and s, and subtracts the
78 ranges in s from those in r. For example, if r and s are as follows:
79
80 r = { [0, 10) }
81 s = { [3, 5), [7, 9) }
82
83 Then r - s is { [0, 3), [5, 7), [9, 10) }
84
85 NOTE: Both range lists must be sorted on input. This is guarded by an
86 assertion.
87
88 NOTE: Range s must contain ranges, which are fully contained by the span of
89 range r (the span being the interval between the start of the lowest
90 range in r, inclusive, and the end of the highest range in r,
91 exclusive).
92
93 NOTE: In addition to the requirement above, range s must contain ranges,
94 each of which is a subrange of one of the ranges of r.
95
96 NOTE: There is no user info associated with the resulting range.
97
98 NOTE: The resulting range is not sorted.
99
100 Ther returned list must be destroyed with destroy_range_list().
101*/
102
103range_list_t* subtract_ranges(const range_list_t *r, const range_list_t *s);
104
105#endif/*RANGESORT_H*/