object.h
Go to the documentation of this file.
#ifndef PROTON_OBJECT_H
#define PROTON_OBJECT_H 1
/*
*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*/
#include <proton/cid.h>
#include <proton/types.h>
#include <stdarg.h>
#include <proton/type_compat.h>
#include <stddef.h>
#include <proton/import_export.h>
#ifdef __cplusplus
extern "C" {
#endif
typedef void* pn_handle_t;
typedef intptr_t pn_shandle_t;
typedef struct pn_class_t pn_class_t;
typedef struct pn_string_t pn_string_t;
typedef struct pn_list_t pn_list_t;
typedef struct pn_map_t pn_map_t;
typedef struct pn_hash_t pn_hash_t;
typedef void *(*pn_iterator_next_t)(void *state);
typedef struct pn_iterator_t pn_iterator_t;
typedef struct pn_record_t pn_record_t;
struct pn_class_t {
const char *name;
const pn_cid_t cid;
void *(*newinst)(const pn_class_t *, size_t);
void (*initialize)(void *);
void (*incref)(void *);
void (*decref)(void *);
int (*refcount)(void *);
void (*finalize)(void *);
void (*free)(void *);
const pn_class_t *(*reify)(void *);
uintptr_t (*hashcode)(void *);
intptr_t (*compare)(void *, void *);
int (*inspect)(void *, pn_string_t *);
};
// Hack alert: Declare these as arrays so we can treat the name
// of the single object as the address
PN_EXTERN extern const pn_class_t PN_OBJECT[];
PN_EXTERN extern const pn_class_t PN_VOID[];
PN_EXTERN extern const pn_class_t PN_WEAKREF[];
#define PN_CLASSDEF(PREFIX) \
static void PREFIX ## _initialize_cast(void *object) { \
PREFIX ## _initialize((PREFIX ## _t *) object); \
} \
\
static void PREFIX ## _finalize_cast(void *object) { \
PREFIX ## _finalize((PREFIX ## _t *) object); \
} \
\
static uintptr_t PREFIX ## _hashcode_cast(void *object) { \
uintptr_t (*fp)(PREFIX ## _t *) = PREFIX ## _hashcode; \
if (fp) { \
return fp((PREFIX ## _t *) object); \
} else { \
return (uintptr_t) object; \
} \
} \
\
static intptr_t PREFIX ## _compare_cast(void *a, void *b) { \
intptr_t (*fp)(PREFIX ## _t *, PREFIX ## _t *) = PREFIX ## _compare; \
if (fp) { \
return fp((PREFIX ## _t *) a, (PREFIX ## _t *) b); \
} else { \
return (intptr_t) a - (intptr_t) b; \
} \
} \
\
static int PREFIX ## _inspect_cast(void *object, pn_string_t *str) { \
int (*fp)(PREFIX ## _t *, pn_string_t *) = PREFIX ## _inspect; \
if (fp) { \
return fp((PREFIX ## _t *) object, str); \
} else { \
return pn_string_addf(str, "%s<%p>", #PREFIX, object); \
} \
} \
\
const pn_class_t *PREFIX ## __class(void) { \
static const pn_class_t clazz = { \
#PREFIX, \
CID_ ## PREFIX, \
pn_object_new, \
PREFIX ## _initialize_cast, \
pn_object_incref, \
pn_object_decref, \
pn_object_refcount, \
PREFIX ## _finalize_cast, \
pn_object_free, \
pn_object_reify, \
PREFIX ## _hashcode_cast, \
PREFIX ## _compare_cast, \
PREFIX ## _inspect_cast \
}; \
return &clazz; \
} \
\
PREFIX ## _t *PREFIX ## _new(void) { \
return (PREFIX ## _t *) pn_class_new(PREFIX ## __class(), \
sizeof(PREFIX ## _t)); \
}
#define PN_CLASS(PREFIX) { \
#PREFIX, \
CID_ ## PREFIX, \
pn_object_new, \
PREFIX ## _initialize, \
pn_object_incref, \
pn_object_decref, \
pn_object_refcount, \
PREFIX ## _finalize, \
pn_object_free, \
pn_object_reify, \
PREFIX ## _hashcode, \
PREFIX ## _compare, \
PREFIX ## _inspect \
}
#define PN_METACLASS(PREFIX) { \
#PREFIX, \
CID_ ## PREFIX, \
PREFIX ## _new, \
PREFIX ## _initialize, \
PREFIX ## _incref, \
PREFIX ## _decref, \
PREFIX ## _refcount, \
PREFIX ## _finalize, \
PREFIX ## _free, \
PREFIX ## _reify, \
PREFIX ## _hashcode, \
PREFIX ## _compare, \
PREFIX ## _inspect \
}
PN_EXTERN pn_cid_t pn_class_id(const pn_class_t *clazz);
PN_EXTERN const char *pn_class_name(const pn_class_t *clazz);
PN_EXTERN void *pn_class_new(const pn_class_t *clazz, size_t size);
PN_EXTERN void *pn_class_incref(const pn_class_t *clazz, void *object);
PN_EXTERN int pn_class_refcount(const pn_class_t *clazz, void *object);
PN_EXTERN int pn_class_decref(const pn_class_t *clazz, void *object);
PN_EXTERN void pn_class_free(const pn_class_t *clazz, void *object);
PN_EXTERN const pn_class_t *pn_class_reify(const pn_class_t *clazz, void *object);
PN_EXTERN uintptr_t pn_class_hashcode(const pn_class_t *clazz, void *object);
PN_EXTERN intptr_t pn_class_compare(const pn_class_t *clazz, void *a, void *b);
PN_EXTERN bool pn_class_equals(const pn_class_t *clazz, void *a, void *b);
PN_EXTERN int pn_class_inspect(const pn_class_t *clazz, void *object, pn_string_t *dst);
PN_EXTERN uintptr_t pn_void_hashcode(void *object);
PN_EXTERN intptr_t pn_void_compare(void *a, void *b);
PN_EXTERN int pn_void_inspect(void *object, pn_string_t *dst);
PN_EXTERN void *pn_object_new(const pn_class_t *clazz, size_t size);
PN_EXTERN const pn_class_t *pn_object_reify(void *object);
PN_EXTERN void pn_object_incref(void *object);
PN_EXTERN int pn_object_refcount(void *object);
PN_EXTERN void pn_object_decref(void *object);
PN_EXTERN void pn_object_free(void *object);
PN_EXTERN void *pn_incref(void *object);
PN_EXTERN int pn_decref(void *object);
PN_EXTERN int pn_refcount(void *object);
PN_EXTERN void pn_free(void *object);
PN_EXTERN const pn_class_t *pn_class(void* object);
PN_EXTERN uintptr_t pn_hashcode(void *object);
PN_EXTERN intptr_t pn_compare(void *a, void *b);
PN_EXTERN bool pn_equals(void *a, void *b);
PN_EXTERN int pn_inspect(void *object, pn_string_t *dst);
#define PN_REFCOUNT (0x1)
PN_EXTERN pn_list_t *pn_list(const pn_class_t *clazz, size_t capacity);
PN_EXTERN size_t pn_list_size(pn_list_t *list);
PN_EXTERN void *pn_list_get(pn_list_t *list, int index);
PN_EXTERN void pn_list_set(pn_list_t *list, int index, void *value);
PN_EXTERN int pn_list_add(pn_list_t *list, void *value);
PN_EXTERN void *pn_list_pop(pn_list_t *list);
PN_EXTERN ssize_t pn_list_index(pn_list_t *list, void *value);
PN_EXTERN bool pn_list_remove(pn_list_t *list, void *value);
PN_EXTERN void pn_list_del(pn_list_t *list, int index, int n);
PN_EXTERN void pn_list_clear(pn_list_t *list);
PN_EXTERN void pn_list_iterator(pn_list_t *list, pn_iterator_t *iter);
PN_EXTERN void pn_list_minpush(pn_list_t *list, void *value);
PN_EXTERN void *pn_list_minpop(pn_list_t *list);
#define PN_REFCOUNT_KEY (0x2)
#define PN_REFCOUNT_VALUE (0x4)
PN_EXTERN pn_map_t *pn_map(const pn_class_t *key, const pn_class_t *value,
size_t capacity, float load_factor);
PN_EXTERN size_t pn_map_size(pn_map_t *map);
PN_EXTERN int pn_map_put(pn_map_t *map, void *key, void *value);
PN_EXTERN void *pn_map_get(pn_map_t *map, void *key);
PN_EXTERN void pn_map_del(pn_map_t *map, void *key);
PN_EXTERN pn_handle_t pn_map_head(pn_map_t *map);
PN_EXTERN pn_handle_t pn_map_next(pn_map_t *map, pn_handle_t entry);
PN_EXTERN void *pn_map_key(pn_map_t *map, pn_handle_t entry);
PN_EXTERN void *pn_map_value(pn_map_t *map, pn_handle_t entry);
PN_EXTERN pn_hash_t *pn_hash(const pn_class_t *clazz, size_t capacity, float load_factor);
PN_EXTERN size_t pn_hash_size(pn_hash_t *hash);
PN_EXTERN int pn_hash_put(pn_hash_t *hash, uintptr_t key, void *value);
PN_EXTERN void *pn_hash_get(pn_hash_t *hash, uintptr_t key);
PN_EXTERN void pn_hash_del(pn_hash_t *hash, uintptr_t key);
PN_EXTERN pn_handle_t pn_hash_head(pn_hash_t *hash);
PN_EXTERN pn_handle_t pn_hash_next(pn_hash_t *hash, pn_handle_t entry);
PN_EXTERN uintptr_t pn_hash_key(pn_hash_t *hash, pn_handle_t entry);
PN_EXTERN void *pn_hash_value(pn_hash_t *hash, pn_handle_t entry);
PN_EXTERN pn_string_t *pn_string(const char *bytes);
PN_EXTERN pn_string_t *pn_stringn(const char *bytes, size_t n);
PN_EXTERN const char *pn_string_get(pn_string_t *string);
PN_EXTERN size_t pn_string_size(pn_string_t *string);
PN_EXTERN int pn_string_set(pn_string_t *string, const char *bytes);
PN_EXTERN int pn_string_setn(pn_string_t *string, const char *bytes, size_t n);
PN_EXTERN ssize_t pn_string_put(pn_string_t *string, char *dst);
PN_EXTERN void pn_string_clear(pn_string_t *string);
PN_EXTERN int pn_string_format(pn_string_t *string, const char *format, ...)
#ifdef __GNUC__
__attribute__ ((format (printf, 2, 3)))
#endif
;
PN_EXTERN int pn_string_vformat(pn_string_t *string, const char *format, va_list ap);
PN_EXTERN int pn_string_addf(pn_string_t *string, const char *format, ...)
#ifdef __GNUC__
__attribute__ ((format (printf, 2, 3)))
#endif
;
PN_EXTERN int pn_string_vaddf(pn_string_t *string, const char *format, va_list ap);
PN_EXTERN int pn_string_grow(pn_string_t *string, size_t capacity);
PN_EXTERN char *pn_string_buffer(pn_string_t *string);
PN_EXTERN size_t pn_string_capacity(pn_string_t *string);
PN_EXTERN int pn_string_resize(pn_string_t *string, size_t size);
PN_EXTERN int pn_string_copy(pn_string_t *string, pn_string_t *src);
PN_EXTERN pn_iterator_t *pn_iterator(void);
PN_EXTERN void *pn_iterator_start(pn_iterator_t *iterator,
pn_iterator_next_t next, size_t size);
PN_EXTERN void *pn_iterator_next(pn_iterator_t *iterator);
#define PN_LEGCTX ((pn_handle_t) 0)
/**
PN_HANDLE is a trick to define a unique identifier by using the address of a static variable.
You MUST NOT use it in a .h file, since it must be defined uniquely in one compilation unit.
Your .h file can provide access to the handle (if needed) via a function. For example:
/// my_thing.h
pn_handle_t get_my_thing(void);
/// my_thing.c
PN_HANDLE(MY_THING);
pn_handle_t get_my_thing(void) { return MY_THING; }
Note that the name "MY_THING" is not exported and is not required to be
unique except in the .c file. The linker will guarantee that the *address* of
MY_THING, as returned by get_my_thing() *is* unique across the entire linked
executable.
*/
#define PN_HANDLE(name) \
static const char _PN_HANDLE_ ## name = 0; \
static const pn_handle_t name = ((pn_handle_t) &_PN_HANDLE_ ## name);
PN_EXTERN pn_record_t *pn_record(void);
PN_EXTERN void pn_record_def(pn_record_t *record, pn_handle_t key, const pn_class_t *clazz);
PN_EXTERN bool pn_record_has(pn_record_t *record, pn_handle_t key);
PN_EXTERN void *pn_record_get(pn_record_t *record, pn_handle_t key);
PN_EXTERN void pn_record_set(pn_record_t *record, pn_handle_t key, void *value);
PN_EXTERN void pn_record_clear(pn_record_t *record);
#ifdef __cplusplus
}
#endif
#endif /* object.h */
pn_string
PN_EXTERN pn_string_t * pn_string(const char *bytes)
pn_hash_key
PN_EXTERN uintptr_t pn_hash_key(pn_hash_t *hash, pn_handle_t entry)
pn_list_add
PN_EXTERN int pn_list_add(pn_list_t *list, void *value)
pn_class_t::cid
const pn_cid_t cid
Definition: object.h:50
pn_class
PN_EXTERN const pn_class_t * pn_class(void *object)
pn_string_set
PN_EXTERN int pn_string_set(pn_string_t *string, const char *bytes)
types.h
pn_list
PN_EXTERN pn_list_t * pn_list(const pn_class_t *clazz, size_t capacity)
pn_record_get
PN_EXTERN void * pn_record_get(pn_record_t *record, pn_handle_t key)
pn_object_free
PN_EXTERN void pn_object_free(void *object)
pn_class_t::incref
void(* incref)(void *)
Definition: object.h:53
pn_class_t::compare
intptr_t(* compare)(void *, void *)
Definition: object.h:60
import_export.h
pn_class_t::free
void(* free)(void *)
Definition: object.h:57
pn_iterator_next
PN_EXTERN void * pn_iterator_next(pn_iterator_t *iterator)
pn_hash_head
PN_EXTERN pn_handle_t pn_hash_head(pn_hash_t *hash)
pn_list_index
PN_EXTERN ssize_t pn_list_index(pn_list_t *list, void *value)
pn_record_t
struct pn_record_t pn_record_t
Definition: object.h:46
pn_list_minpush
PN_EXTERN void pn_list_minpush(pn_list_t *list, void *value)
pn_map_next
PN_EXTERN pn_handle_t pn_map_next(pn_map_t *map, pn_handle_t entry)
pn_stringn
PN_EXTERN pn_string_t * pn_stringn(const char *bytes, size_t n)
pn_list_remove
PN_EXTERN bool pn_list_remove(pn_list_t *list, void *value)
pn_list_iterator
PN_EXTERN void pn_list_iterator(pn_list_t *list, pn_iterator_t *iter)
pn_map_del
PN_EXTERN void pn_map_del(pn_map_t *map, void *key)
pn_hash_del
PN_EXTERN void pn_hash_del(pn_hash_t *hash, uintptr_t key)
pn_string_addf
PN_EXTERN int pn_string_addf(pn_string_t *string, const char *format,...)
pn_string_t
struct pn_string_t pn_string_t
Definition: object.h:40
pn_class_compare
PN_EXTERN intptr_t pn_class_compare(const pn_class_t *clazz, void *a, void *b)
pn_object_refcount
PN_EXTERN int pn_object_refcount(void *object)
pn_list_size
PN_EXTERN size_t pn_list_size(pn_list_t *list)
pn_map_head
PN_EXTERN pn_handle_t pn_map_head(pn_map_t *map)
type_compat.h
pn_void_inspect
PN_EXTERN int pn_void_inspect(void *object, pn_string_t *dst)
pn_refcount
PN_EXTERN int pn_refcount(void *object)
PN_EXTERN
#define PN_EXTERN
Definition: import_export.h:53
pn_list_pop
PN_EXTERN void * pn_list_pop(pn_list_t *list)
pn_inspect
PN_EXTERN int pn_inspect(void *object, pn_string_t *dst)
pn_decref
PN_EXTERN int pn_decref(void *object)
pn_class_id
PN_EXTERN pn_cid_t pn_class_id(const pn_class_t *clazz)
pn_string_buffer
PN_EXTERN char * pn_string_buffer(pn_string_t *string)
pn_hashcode
PN_EXTERN uintptr_t pn_hashcode(void *object)
pn_handle_t
void * pn_handle_t
Definition: object.h:36
pn_map_put
PN_EXTERN int pn_map_put(pn_map_t *map, void *key, void *value)
pn_void_hashcode
PN_EXTERN uintptr_t pn_void_hashcode(void *object)
pn_list_get
PN_EXTERN void * pn_list_get(pn_list_t *list, int index)
pn_object_new
PN_EXTERN void * pn_object_new(const pn_class_t *clazz, size_t size)
pn_class_t::hashcode
uintptr_t(* hashcode)(void *)
Definition: object.h:59
pn_object_decref
PN_EXTERN void pn_object_decref(void *object)
pn_string_copy
PN_EXTERN int pn_string_copy(pn_string_t *string, pn_string_t *src)
pn_map_size
PN_EXTERN size_t pn_map_size(pn_map_t *map)
pn_hash_value
PN_EXTERN void * pn_hash_value(pn_hash_t *hash, pn_handle_t entry)
pn_string_vaddf
PN_EXTERN int pn_string_vaddf(pn_string_t *string, const char *format, va_list ap)
pn_string_format
PN_EXTERN int pn_string_format(pn_string_t *string, const char *format,...)
pn_map_get
PN_EXTERN void * pn_map_get(pn_map_t *map, void *key)
pn_class_new
PN_EXTERN void * pn_class_new(const pn_class_t *clazz, size_t size)
pn_list_t
struct pn_list_t pn_list_t
Definition: object.h:41
pn_hash_get
PN_EXTERN void * pn_hash_get(pn_hash_t *hash, uintptr_t key)
pn_free
PN_EXTERN void pn_free(void *object)
pn_string_get
PN_EXTERN const char * pn_string_get(pn_string_t *string)
PN_WEAKREF
PN_EXTERN const pn_class_t PN_WEAKREF[]
pn_record_set
PN_EXTERN void pn_record_set(pn_record_t *record, pn_handle_t key, void *value)
pn_string_size
PN_EXTERN size_t pn_string_size(pn_string_t *string)
PN_VOID
PN_EXTERN const pn_class_t PN_VOID[]
pn_iterator
PN_EXTERN pn_iterator_t * pn_iterator(void)
pn_list_set
PN_EXTERN void pn_list_set(pn_list_t *list, int index, void *value)
pn_equals
PN_EXTERN bool pn_equals(void *a, void *b)
pn_list_del
PN_EXTERN void pn_list_del(pn_list_t *list, int index, int n)
pn_record_def
PN_EXTERN void pn_record_def(pn_record_t *record, pn_handle_t key, const pn_class_t *clazz)
pn_void_compare
PN_EXTERN intptr_t pn_void_compare(void *a, void *b)
pn_record_has
PN_EXTERN bool pn_record_has(pn_record_t *record, pn_handle_t key)
pn_class_refcount
PN_EXTERN int pn_class_refcount(const pn_class_t *clazz, void *object)
pn_map_t
struct pn_map_t pn_map_t
Definition: object.h:42
pn_list_clear
PN_EXTERN void pn_list_clear(pn_list_t *list)
pn_string_capacity
PN_EXTERN size_t pn_string_capacity(pn_string_t *string)
pn_string_resize
PN_EXTERN int pn_string_resize(pn_string_t *string, size_t size)
pn_class_t::inspect
int(* inspect)(void *, pn_string_t *)
Definition: object.h:61
pn_class_t
Definition: object.h:48
pn_iterator_next_t
void *(* pn_iterator_next_t)(void *state)
Definition: object.h:44
pn_map
PN_EXTERN pn_map_t * pn_map(const pn_class_t *key, const pn_class_t *value, size_t capacity, float load_factor)
pn_hash_size
PN_EXTERN size_t pn_hash_size(pn_hash_t *hash)
pn_list_minpop
PN_EXTERN void * pn_list_minpop(pn_list_t *list)
pn_incref
PN_EXTERN void * pn_incref(void *object)
pn_class_t::name
const char * name
Definition: object.h:49
pn_class_t::initialize
void(* initialize)(void *)
Definition: object.h:52
cid.h
pn_class_equals
PN_EXTERN bool pn_class_equals(const pn_class_t *clazz, void *a, void *b)
pn_hash_t
struct pn_hash_t pn_hash_t
Definition: object.h:43
pn_class_decref
PN_EXTERN int pn_class_decref(const pn_class_t *clazz, void *object)
pn_cid_t
pn_cid_t
Definition: cid.h:24
pn_record_clear
PN_EXTERN void pn_record_clear(pn_record_t *record)
pn_class_name
PN_EXTERN const char * pn_class_name(const pn_class_t *clazz)
pn_class_incref
PN_EXTERN void * pn_class_incref(const pn_class_t *clazz, void *object)
pn_compare
PN_EXTERN intptr_t pn_compare(void *a, void *b)
pn_string_clear
PN_EXTERN void pn_string_clear(pn_string_t *string)
pn_class_inspect
PN_EXTERN int pn_class_inspect(const pn_class_t *clazz, void *object, pn_string_t *dst)
pn_class_t::decref
void(* decref)(void *)
Definition: object.h:54
pn_string_grow
PN_EXTERN int pn_string_grow(pn_string_t *string, size_t capacity)
pn_map_key
PN_EXTERN void * pn_map_key(pn_map_t *map, pn_handle_t entry)
pn_string_setn
PN_EXTERN int pn_string_setn(pn_string_t *string, const char *bytes, size_t n)
pn_hash_put
PN_EXTERN int pn_hash_put(pn_hash_t *hash, uintptr_t key, void *value)
pn_object_reify
PN_EXTERN const pn_class_t * pn_object_reify(void *object)
pn_class_free
PN_EXTERN void pn_class_free(const pn_class_t *clazz, void *object)
pn_record
PN_EXTERN pn_record_t * pn_record(void)
pn_class_hashcode
PN_EXTERN uintptr_t pn_class_hashcode(const pn_class_t *clazz, void *object)
pn_string_vformat
PN_EXTERN int pn_string_vformat(pn_string_t *string, const char *format, va_list ap)
pn_map_value
PN_EXTERN void * pn_map_value(pn_map_t *map, pn_handle_t entry)
pn_shandle_t
intptr_t pn_shandle_t
Definition: object.h:37
pn_class_reify
PN_EXTERN const pn_class_t * pn_class_reify(const pn_class_t *clazz, void *object)
pn_class_t::finalize
void(* finalize)(void *)
Definition: object.h:56
PN_OBJECT
PN_EXTERN const pn_class_t PN_OBJECT[]
pn_hash_next
PN_EXTERN pn_handle_t pn_hash_next(pn_hash_t *hash, pn_handle_t entry)
pn_string_put
PN_EXTERN ssize_t pn_string_put(pn_string_t *string, char *dst)
pn_hash
PN_EXTERN pn_hash_t * pn_hash(const pn_class_t *clazz, size_t capacity, float load_factor)
pn_object_incref
PN_EXTERN void pn_object_incref(void *object)
pn_class_t::refcount
int(* refcount)(void *)
Definition: object.h:55
pn_iterator_start
PN_EXTERN void * pn_iterator_start(pn_iterator_t *iterator, pn_iterator_next_t next, size_t size)
pn_iterator_t
struct pn_iterator_t pn_iterator_t
Definition: object.h:45