Imported Upstream version 1.15.1
[platform/upstream/krb5.git] / src / util / profile / prof_int.h
1 /*
2  * prof-int.h
3  */
4
5 #include "k5-platform.h"
6 #include "k5-thread.h"
7 #include "k5-plugin.h"
8
9 #include <time.h>
10
11 #if defined(__MACH__) && defined(__APPLE__)
12 #include <TargetConditionals.h>
13 #define PROFILE_SUPPORTS_FOREIGN_NEWLINES
14 #endif
15
16 #include "com_err.h"
17 #include "profile.h"
18
19 typedef long prf_magic_t;
20
21 /*
22  * This is the structure which stores the profile information for a
23  * particular configuration file.
24  *
25  * Locking strategy:
26  * - filespec, fslen are fixed after creation
27  * - refcount and next should only be tweaked with the global lock held
28  * - other fields can be tweaked after grabbing the in-struct lock
29  */
30 struct _prf_data_t {
31         prf_magic_t     magic;
32         k5_mutex_t      lock;
33         struct profile_node *root;
34         time_t          last_stat;
35         time_t          timestamp; /* time tree was last updated from file */
36         unsigned long   frac_ts;   /* fractional part of timestamp, if any */
37         int             flags;  /* r/w, dirty */
38         int             upd_serial; /* incremented when data changes */
39
40         size_t          fslen;
41
42         /* Some separation between fields controlled by different
43            mutexes.  Theoretically, both could be accessed at the same
44            time from different threads on different CPUs with separate
45            caches.  Don't let the threads clobber each other's
46            changes.  One mutex controlling the whole thing would be
47            better, but sufficient separation might suffice.
48
49            This is icky.  I just hope it's adequate.
50
51            For next major release, fix this.  */
52         union { double d; void *p; uint64_t ll; k5_mutex_t m; } pad;
53
54         int             refcount; /* prf_file_t references */
55         struct _prf_data_t *next;
56         /* Was: "profile_filespec_t filespec".  Now: flexible char
57            array ... except, we need to work in C89, so an array
58            length must be specified.  */
59         const char      filespec[sizeof("/etc/krb5.conf")];
60 };
61
62 typedef struct _prf_data_t *prf_data_t;
63 prf_data_t profile_make_prf_data(const char *);
64
65 struct _prf_file_t {
66         prf_magic_t     magic;
67         struct _prf_data_t      *data;
68         struct _prf_file_t *next;
69 };
70
71 typedef struct _prf_file_t *prf_file_t;
72
73 /*
74  * The profile flags
75  *
76  * Deprecated use of read/write profile flag.
77  * Check whether file is writable lazily so we don't call access as often.
78  */
79 #define PROFILE_FILE_DEPRECATED_RW      0x0001
80 #define PROFILE_FILE_DIRTY              0x0002
81 #define PROFILE_FILE_SHARED             0x0004
82
83 struct _prf_lib_handle_t {
84         k5_mutex_t lock;
85         int refcount;
86         struct plugin_file_handle *plugin_handle;
87 };
88
89 typedef struct _prf_lib_handle_t *prf_lib_handle_t;
90
91 /*
92  * This structure defines the high-level, user visible profile_t
93  * object, which is used as a handle by users who need to query some
94  * configuration file(s)
95  */
96 struct _profile_t {
97         prf_magic_t     magic;
98         prf_file_t      first_file;
99
100         /* If non-null, use vtable operations instead of native ones. */
101         struct profile_vtable *vt;
102         void            *cbdata;
103         prf_lib_handle_t lib_handle;
104 };
105
106 /*
107  * Used by the profile iterator in prof_get.c
108  */
109 #define PROFILE_ITER_LIST_SECTION       0x0001
110 #define PROFILE_ITER_SECTIONS_ONLY      0x0002
111 #define PROFILE_ITER_RELATIONS_ONLY     0x0004
112
113 #define PROFILE_ITER_FINAL_SEEN         0x0100
114
115 /*
116  * Check if a filespec is last in a list (NULL on UNIX, invalid FSSpec on MacOS
117  */
118
119 #define PROFILE_LAST_FILESPEC(x) (((x) == NULL) || ((x)[0] == '\0'))
120
121 /* profile_parse.c */
122
123 errcode_t profile_parse_file
124         (FILE *f, struct profile_node **root, char **ret_modspec);
125
126 errcode_t profile_process_directory
127         (const char *dirname, struct profile_node **root);
128
129 errcode_t profile_write_tree_file
130         (struct profile_node *root, FILE *dstfile);
131
132 errcode_t profile_write_tree_to_buffer
133         (struct profile_node *root, char **buf);
134
135
136 /* prof_tree.c */
137
138 void profile_free_node
139         (struct profile_node *relation);
140
141 errcode_t profile_create_node
142         (const char *name, const char *value,
143                    struct profile_node **ret_node);
144
145 errcode_t profile_verify_node
146         (struct profile_node *node);
147
148 errcode_t profile_add_node
149         (struct profile_node *section,
150                     const char *name, const char *value,
151                     struct profile_node **ret_node);
152
153 errcode_t profile_make_node_final
154         (struct profile_node *node);
155
156 int profile_is_node_final
157         (struct profile_node *node);
158
159 const char *profile_get_node_name
160         (struct profile_node *node);
161
162 const char *profile_get_node_value
163         (struct profile_node *node);
164
165 errcode_t profile_find_node
166         (struct profile_node *section,
167                     const char *name, const char *value,
168                     int section_flag, void **state,
169                     struct profile_node **node);
170
171 errcode_t profile_find_node_relation
172         (struct profile_node *section,
173                     const char *name, void **state,
174                     char **ret_name, char **value);
175
176 errcode_t profile_find_node_subsection
177         (struct profile_node *section,
178                     const char *name, void **state,
179                     char **ret_name, struct profile_node **subsection);
180
181 errcode_t profile_get_node_parent
182         (struct profile_node *section,
183                    struct profile_node **parent);
184
185 errcode_t profile_delete_node_relation
186         (struct profile_node *section, const char *name);
187
188 errcode_t profile_find_node_name
189         (struct profile_node *section, void **state,
190                     char **ret_name);
191
192 errcode_t profile_node_iterator_create
193         (profile_t profile, const char *const *names,
194                    int flags, void **ret_iter);
195
196 void profile_node_iterator_free
197         (void   **iter_p);
198
199 errcode_t profile_node_iterator
200         (void   **iter_p, struct profile_node **ret_node,
201                    char **ret_name, char **ret_value);
202
203 errcode_t profile_remove_node
204         (struct profile_node *node);
205
206 errcode_t profile_set_relation_value
207         (struct profile_node *node, const char *new_value);
208
209 errcode_t profile_rename_node
210         (struct profile_node *node, const char *new_name);
211
212 /* prof_file.c */
213
214 errcode_t KRB5_CALLCONV profile_copy (profile_t, profile_t *);
215
216 errcode_t profile_open_file
217         (const_profile_filespec_t file, prf_file_t *ret_prof,
218          char **ret_modspec);
219
220 #define profile_update_file(P, M) profile_update_file_data((P)->data, M)
221 errcode_t profile_update_file_data
222         (prf_data_t profile, char **ret_modspec);
223 #define profile_update_file_locked(P, M) profile_update_file_data_locked((P)->data, M)
224 errcode_t profile_update_file_data_locked
225         (prf_data_t data, char **ret_modspec);
226
227 #define profile_flush_file(P) (((P) && (P)->magic == PROF_MAGIC_FILE) ? profile_flush_file_data((P)->data) : PROF_MAGIC_FILE)
228 errcode_t profile_flush_file_data
229         (prf_data_t data);
230
231 #define profile_flush_file_to_file(P,F) (((P) && (P)->magic == PROF_MAGIC_FILE) ? profile_flush_file_data_to_file((P)->data, (F)) : PROF_MAGIC_FILE)
232 errcode_t profile_flush_file_data_to_file
233         (prf_data_t data, const char *outfile);
234
235 errcode_t profile_flush_file_data_to_buffer
236         (prf_data_t data, char **bufp);
237
238 void profile_free_file
239         (prf_file_t profile);
240
241 errcode_t profile_close_file
242         (prf_file_t profile);
243
244 int profile_file_is_writable
245         (prf_file_t profile);
246
247 void profile_dereference_data (prf_data_t);
248 void profile_dereference_data_locked (prf_data_t);
249
250 void profile_lock_global (void);
251 void profile_unlock_global (void);
252
253 /* prof_init.c -- included from profile.h */
254 errcode_t profile_ser_size
255         (const char *, profile_t, size_t *);
256
257 errcode_t profile_ser_externalize
258         (const char *, profile_t, unsigned char **, size_t *);
259
260 errcode_t profile_ser_internalize
261         (const char *, profile_t *, unsigned char **, size_t *);
262
263 /* prof_get.c */
264
265 errcode_t profile_get_value
266         (profile_t profile, const char **names, char **ret_value);
267 /* Others included from profile.h */
268
269 /* prof_set.c -- included from profile.h */