1/* $NetBSD: heimbase.h,v 1.3 2019/12/15 22:50:47 christos Exp $ */ 2 3/* 4 * Copyright (c) 2010 Kungliga Tekniska H��gskolan 5 * (Royal Institute of Technology, Stockholm, Sweden). 6 * All rights reserved. 7 * 8 * Portions Copyright (c) 2010 Apple Inc. All rights reserved. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 17 * 2. Redistributions in binary form must reproduce the above copyright 18 * notice, this list of conditions and the following disclaimer in the 19 * documentation and/or other materials provided with the distribution. 20 * 21 * 3. Neither the name of the Institute nor the names of its contributors 22 * may be used to endorse or promote products derived from this software 23 * without specific prior written permission. 24 * 25 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 26 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 27 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 28 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 29 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 30 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 31 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 32 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 33 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 34 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 35 * SUCH DAMAGE. 36 */ 37 38#ifndef HEIM_BASE_H 39#define HEIM_BASE_H 1 40 41#include <sys/types.h> 42#if !defined(WIN32) && !defined(HAVE_DISPATCH_DISPATCH_H) && defined(ENABLE_PTHREAD_SUPPORT) 43#include <pthread.h> 44#endif 45#include <krb5/krb5-types.h> 46#include <stdarg.h> 47#ifdef HAVE_STDBOOL_H 48#include <stdbool.h> 49#else 50#ifndef false 51#define false 0 52#endif 53#ifndef true 54#define true 1 55#endif 56#endif 57 58#define HEIM_BASE_API_VERSION 20130210 59 60typedef void * heim_object_t; 61typedef unsigned int heim_tid_t; 62typedef heim_object_t heim_bool_t; 63typedef heim_object_t heim_null_t; 64#ifdef WIN32 65typedef LONG heim_base_once_t; 66#define HEIM_BASE_ONCE_INIT 0 67#elif defined(HAVE_DISPATCH_DISPATCH_H) 68typedef long heim_base_once_t; /* XXX arch dependant */ 69#define HEIM_BASE_ONCE_INIT 0 70#elif defined(ENABLE_PTHREAD_SUPPORT) 71typedef pthread_once_t heim_base_once_t; 72#define HEIM_BASE_ONCE_INIT PTHREAD_ONCE_INIT 73#else 74typedef long heim_base_once_t; /* XXX arch dependant */ 75#define HEIM_BASE_ONCE_INIT 0 76#endif 77 78#if !defined(__has_extension) 79#define __has_extension(x) 0 80#endif 81 82#define HEIM_REQUIRE_GNUC(m,n,p) \ 83 (((__GNUC__ * 10000) + (__GNUC_MINOR__ * 100) + __GNUC_PATCHLEVEL__) >= \ 84 (((m) * 10000) + ((n) * 100) + (p))) 85 86 87#if __has_extension(__builtin_expect) || HEIM_REQUIRE_GNUC(3,0,0) 88#define heim_builtin_expect(_op,_res) __builtin_expect(_op,_res) 89#else 90#define heim_builtin_expect(_op,_res) (_op) 91#endif 92 93 94void * heim_retain(heim_object_t); 95void heim_release(heim_object_t); 96 97void heim_show(heim_object_t); 98 99typedef void (*heim_type_dealloc)(void *); 100 101void * 102heim_alloc(size_t size, const char *name, heim_type_dealloc dealloc); 103 104heim_tid_t 105heim_get_tid(heim_object_t object); 106 107int 108heim_cmp(heim_object_t a, heim_object_t b); 109 110unsigned long 111heim_get_hash(heim_object_t ptr); 112 113void 114heim_base_once_f(heim_base_once_t *, void *, void (*)(void *)); 115 116void 117heim_abort(const char *fmt, ...) 118 HEIMDAL_NORETURN_ATTRIBUTE 119 HEIMDAL_PRINTF_ATTRIBUTE((__printf__, 1, 2)); 120 121void 122heim_abortv(const char *fmt, va_list ap) 123 HEIMDAL_NORETURN_ATTRIBUTE 124 HEIMDAL_PRINTF_ATTRIBUTE((__printf__, 1, 0)); 125 126#define heim_assert(e,t) \ 127 (heim_builtin_expect(!(e), 0) ? heim_abort(t ":" #e) : (void)0) 128 129/* 130 * 131 */ 132 133heim_null_t 134heim_null_create(void); 135 136heim_bool_t 137heim_bool_create(int); 138 139int 140heim_bool_val(heim_bool_t); 141 142/* 143 * Array 144 */ 145 146typedef struct heim_array_data *heim_array_t; 147 148heim_array_t heim_array_create(void); 149heim_tid_t heim_array_get_type_id(void); 150 151typedef void (*heim_array_iterator_f_t)(heim_object_t, void *, int *); 152typedef int (*heim_array_filter_f_t)(heim_object_t, void *); 153 154int heim_array_append_value(heim_array_t, heim_object_t); 155int heim_array_insert_value(heim_array_t, size_t idx, heim_object_t); 156void heim_array_iterate_f(heim_array_t, void *, heim_array_iterator_f_t); 157void heim_array_iterate_reverse_f(heim_array_t, void *, heim_array_iterator_f_t); 158#ifdef __BLOCKS__ 159void heim_array_iterate(heim_array_t, void (^)(heim_object_t, int *)); 160void heim_array_iterate_reverse(heim_array_t, void (^)(heim_object_t, int *)); 161#endif 162size_t heim_array_get_length(heim_array_t); 163heim_object_t 164 heim_array_get_value(heim_array_t, size_t); 165heim_object_t 166 heim_array_copy_value(heim_array_t, size_t); 167void heim_array_set_value(heim_array_t, size_t, heim_object_t); 168void heim_array_delete_value(heim_array_t, size_t); 169void heim_array_filter_f(heim_array_t, void *, heim_array_filter_f_t); 170#ifdef __BLOCKS__ 171void heim_array_filter(heim_array_t, int (^)(heim_object_t)); 172#endif 173 174/* 175 * Dict 176 */ 177 178typedef struct heim_dict_data *heim_dict_t; 179 180heim_dict_t heim_dict_create(size_t size); 181heim_tid_t heim_dict_get_type_id(void); 182 183typedef void (*heim_dict_iterator_f_t)(heim_object_t, heim_object_t, void *); 184 185int heim_dict_set_value(heim_dict_t, heim_object_t, heim_object_t); 186void heim_dict_iterate_f(heim_dict_t, void *, heim_dict_iterator_f_t); 187#ifdef __BLOCKS__ 188void heim_dict_iterate(heim_dict_t, void (^)(heim_object_t, heim_object_t)); 189#endif 190 191heim_object_t 192 heim_dict_get_value(heim_dict_t, heim_object_t); 193heim_object_t 194 heim_dict_copy_value(heim_dict_t, heim_object_t); 195void heim_dict_delete_key(heim_dict_t, heim_object_t); 196 197/* 198 * String 199 */ 200 201typedef struct heim_string_data *heim_string_t; 202typedef void (*heim_string_free_f_t)(void *); 203 204heim_string_t heim_string_create(const char *); 205heim_string_t heim_string_ref_create(const char *, heim_string_free_f_t); 206heim_string_t heim_string_create_with_bytes(const void *, size_t); 207heim_string_t heim_string_ref_create_with_bytes(const void *, size_t, 208 heim_string_free_f_t); 209heim_string_t heim_string_create_with_format(const char *, ...); 210heim_tid_t heim_string_get_type_id(void); 211const char * heim_string_get_utf8(heim_string_t); 212 213#define HSTR(_str) (__heim_string_constant("" _str "")) 214heim_string_t __heim_string_constant(const char *); 215 216/* 217 * Errors 218 */ 219 220typedef struct heim_error * heim_error_t; 221 222heim_error_t heim_error_create_enomem(void); 223 224heim_error_t heim_error_create(int, const char *, ...) 225 HEIMDAL_PRINTF_ATTRIBUTE((__printf__, 2, 3)); 226 227void heim_error_create_opt(heim_error_t *error, int error_code, const char *fmt, ...) 228 HEIMDAL_PRINTF_ATTRIBUTE((__printf__, 3, 4)); 229 230heim_error_t heim_error_createv(int, const char *, va_list) 231 HEIMDAL_PRINTF_ATTRIBUTE((__printf__, 2, 0)); 232 233heim_string_t heim_error_copy_string(heim_error_t); 234int heim_error_get_code(heim_error_t); 235 236heim_error_t heim_error_append(heim_error_t, heim_error_t); 237 238/* 239 * Path 240 */ 241 242heim_object_t heim_path_get(heim_object_t ptr, heim_error_t *error, ...); 243heim_object_t heim_path_copy(heim_object_t ptr, heim_error_t *error, ...); 244heim_object_t heim_path_vget(heim_object_t ptr, heim_error_t *error, 245 va_list ap); 246heim_object_t heim_path_vcopy(heim_object_t ptr, heim_error_t *error, 247 va_list ap); 248 249int heim_path_vcreate(heim_object_t ptr, size_t size, heim_object_t leaf, 250 heim_error_t *error, va_list ap); 251int heim_path_create(heim_object_t ptr, size_t size, heim_object_t leaf, 252 heim_error_t *error, ...); 253 254void heim_path_vdelete(heim_object_t ptr, heim_error_t *error, va_list ap); 255void heim_path_delete(heim_object_t ptr, heim_error_t *error, ...); 256 257/* 258 * Data (octet strings) 259 */ 260 261#ifndef __HEIM_BASE_DATA__ 262#define __HEIM_BASE_DATA__ 263struct heim_base_data { 264 size_t length; 265 void *data; 266}; 267typedef struct heim_base_data heim_octet_string; 268#endif 269 270typedef struct heim_base_data * heim_data_t; 271typedef void (*heim_data_free_f_t)(void *); 272 273heim_data_t heim_data_create(const void *, size_t); 274heim_data_t heim_data_ref_create(const void *, size_t, heim_data_free_f_t); 275heim_tid_t heim_data_get_type_id(void); 276const heim_octet_string * 277 heim_data_get_data(heim_data_t); 278const void * heim_data_get_ptr(heim_data_t); 279size_t heim_data_get_length(heim_data_t); 280 281/* 282 * DB 283 */ 284 285typedef struct heim_db_data *heim_db_t; 286 287typedef void (*heim_db_iterator_f_t)(heim_data_t, heim_data_t, void *); 288 289typedef int (*heim_db_plug_open_f_t)(void *, const char *, const char *, 290 heim_dict_t, void **, heim_error_t *); 291typedef int (*heim_db_plug_clone_f_t)(void *, void **, heim_error_t *); 292typedef int (*heim_db_plug_close_f_t)(void *, heim_error_t *); 293typedef int (*heim_db_plug_lock_f_t)(void *, int, heim_error_t *); 294typedef int (*heim_db_plug_unlock_f_t)(void *, heim_error_t *); 295typedef int (*heim_db_plug_sync_f_t)(void *, heim_error_t *); 296typedef int (*heim_db_plug_begin_f_t)(void *, int, heim_error_t *); 297typedef int (*heim_db_plug_commit_f_t)(void *, heim_error_t *); 298typedef int (*heim_db_plug_rollback_f_t)(void *, heim_error_t *); 299typedef heim_data_t (*heim_db_plug_copy_value_f_t)(void *, heim_string_t, 300 heim_data_t, 301 heim_error_t *); 302typedef int (*heim_db_plug_set_value_f_t)(void *, heim_string_t, heim_data_t, 303 heim_data_t, heim_error_t *); 304typedef int (*heim_db_plug_del_key_f_t)(void *, heim_string_t, heim_data_t, 305 heim_error_t *); 306typedef void (*heim_db_plug_iter_f_t)(void *, heim_string_t, void *, 307 heim_db_iterator_f_t, heim_error_t *); 308 309struct heim_db_type { 310 int version; 311 heim_db_plug_open_f_t openf; 312 heim_db_plug_clone_f_t clonef; 313 heim_db_plug_close_f_t closef; 314 heim_db_plug_lock_f_t lockf; 315 heim_db_plug_unlock_f_t unlockf; 316 heim_db_plug_sync_f_t syncf; 317 heim_db_plug_begin_f_t beginf; 318 heim_db_plug_commit_f_t commitf; 319 heim_db_plug_rollback_f_t rollbackf; 320 heim_db_plug_copy_value_f_t copyf; 321 heim_db_plug_set_value_f_t setf; 322 heim_db_plug_del_key_f_t delf; 323 heim_db_plug_iter_f_t iterf; 324}; 325 326extern struct heim_db_type heim_sorted_text_file_dbtype; 327 328#define HEIM_DB_TYPE_VERSION_01 1 329 330int heim_db_register(const char *dbtype, 331 void *data, 332 struct heim_db_type *plugin); 333 334heim_db_t heim_db_create(const char *dbtype, const char *dbname, 335 heim_dict_t options, heim_error_t *error); 336heim_db_t heim_db_clone(heim_db_t, heim_error_t *); 337int heim_db_begin(heim_db_t, int, heim_error_t *); 338int heim_db_commit(heim_db_t, heim_error_t *); 339int heim_db_rollback(heim_db_t, heim_error_t *); 340heim_tid_t heim_db_get_type_id(void); 341 342int heim_db_set_value(heim_db_t, heim_string_t, heim_data_t, heim_data_t, 343 heim_error_t *); 344heim_data_t heim_db_copy_value(heim_db_t, heim_string_t, heim_data_t, 345 heim_error_t *); 346int heim_db_delete_key(heim_db_t, heim_string_t, heim_data_t, 347 heim_error_t *); 348void heim_db_iterate_f(heim_db_t, heim_string_t, void *, 349 heim_db_iterator_f_t, heim_error_t *); 350#ifdef __BLOCKS__ 351void heim_db_iterate(heim_db_t, heim_string_t, 352 void (^)(heim_data_t, heim_data_t), heim_error_t *); 353#endif 354 355 356/* 357 * Number 358 */ 359 360typedef struct heim_number_data *heim_number_t; 361 362heim_number_t heim_number_create(int); 363heim_tid_t heim_number_get_type_id(void); 364int heim_number_get_int(heim_number_t); 365 366/* 367 * 368 */ 369 370typedef struct heim_auto_release * heim_auto_release_t; 371 372heim_auto_release_t heim_auto_release_create(void); 373void heim_auto_release_drain(heim_auto_release_t); 374heim_object_t heim_auto_release(heim_object_t); 375 376/* 377 * JSON 378 */ 379typedef enum heim_json_flags { 380 HEIM_JSON_F_NO_C_NULL = 1, 381 HEIM_JSON_F_STRICT_STRINGS = 2, 382 HEIM_JSON_F_NO_DATA = 4, 383 HEIM_JSON_F_NO_DATA_DICT = 8, 384 HEIM_JSON_F_STRICT_DICT = 16, 385 HEIM_JSON_F_STRICT = 31, 386 HEIM_JSON_F_CNULL2JSNULL = 32, 387 HEIM_JSON_F_TRY_DECODE_DATA = 64, 388 HEIM_JSON_F_ONE_LINE = 128 389} heim_json_flags_t; 390 391heim_object_t heim_json_create(const char *, size_t, heim_json_flags_t, 392 heim_error_t *); 393heim_object_t heim_json_create_with_bytes(const void *, size_t, size_t, 394 heim_json_flags_t, 395 heim_error_t *); 396heim_string_t heim_json_copy_serialize(heim_object_t, heim_json_flags_t, 397 heim_error_t *); 398 399 400/* 401 * Debug 402 */ 403 404heim_string_t 405heim_description(heim_object_t ptr); 406 407/* 408 * Binary search. 409 * 410 * Note: these are private until integrated into the heimbase object system. 411 */ 412typedef struct bsearch_file_handle *bsearch_file_handle; 413int _bsearch_text(const char *buf, size_t buf_sz, const char *key, 414 char **value, size_t *location, size_t *loops); 415int _bsearch_file_open(const char *fname, size_t max_sz, size_t page_sz, 416 bsearch_file_handle *bfh, size_t *reads); 417int _bsearch_file(bsearch_file_handle bfh, const char *key, char **value, 418 size_t *location, size_t *loops, size_t *reads); 419void _bsearch_file_info(bsearch_file_handle bfh, size_t *page_sz, 420 size_t *max_sz, int *blockwise); 421void _bsearch_file_close(bsearch_file_handle *bfh); 422 423/* 424 * Thread-specific keys 425 */ 426 427int heim_w32_key_create(unsigned long *, void (*)(void *)); 428int heim_w32_delete_key(unsigned long); 429int heim_w32_setspecific(unsigned long, void *); 430void *heim_w32_getspecific(unsigned long); 431void heim_w32_service_thread_detach(void *); 432 433#endif /* HEIM_BASE_H */ 434