diff --git a/core/include/blue/core/object.h b/core/include/blue/core/object.h index a9b75b9..3063420 100644 --- a/core/include/blue/core/object.h +++ b/core/include/blue/core/object.h @@ -2,22 +2,21 @@ #define BLUE_CORE_OBJECT_H_ #include -#include #include -#define B_OBJECT_MAGIC 0xDECAFC0C0ABEEF13ULL +#define B_OBJECT_MAGIC 0xDECAFC0C0ABEEF13ULL -#define B_OBJECT(p) ((b_object *)(p)) -#define B_TYPE_OBJECT (b_object_get_type()) +#define B_OBJECT(p) ((b_object *)(p)) +#define B_TYPE_OBJECT (b_object_get_type()) -#define B_RV(p) (b_object_make_rvalue(p)) +#define B_TYPE_FWDREF(name) struct _b_object -struct b_stream; +#define B_RV(p) (b_object_make_rvalue(p)) -typedef struct _b_object b_object; +typedef B_TYPE_FWDREF(b_object) b_object; typedef struct _b_object_class { - void (*to_string)(const b_object *, struct b_stream *); + void (*to_string)(const b_object *, B_TYPE_FWDREF(b_stream) *); } b_object_class; BLUE_API b_type b_object_get_type(void); @@ -25,13 +24,16 @@ BLUE_API b_type b_object_get_type(void); BLUE_API void *b_object_get_private(const b_object *object, b_type type); BLUE_API void *b_object_get_protected(const b_object *object, b_type type); BLUE_API void *b_object_get_interface(const b_object *object, b_type type); +BLUE_API b_status b_object_get_data( + const b_object *object, b_type type, void **priv, void **prot, + void **iface); BLUE_API b_object *b_object_ref(b_object *p); BLUE_API void b_object_unref(b_object *p); BLUE_API b_object *b_object_make_rvalue(b_object *p); BLUE_API b_object *b_object_create(b_type type); -BLUE_API void b_object_to_string(const b_object *p, struct b_stream *out); +BLUE_API void b_object_to_string(const b_object *p, B_TYPE_FWDREF(b_stream) * out); BLUE_API bool b_object_is_type(const b_object *p, b_type type); #endif diff --git a/core/object.c b/core/object.c index 8e9cd45..2d8016e 100644 --- a/core/object.c +++ b/core/object.c @@ -5,6 +5,7 @@ #include #include #include +#include #include B_TYPE_CLASS_DEFINITION_BEGIN(b_object) @@ -71,9 +72,9 @@ struct _b_object *b_object_create(b_type type) return out; } -void b_object_to_string(const struct _b_object *p, struct b_stream *out) +void b_object_to_string(const struct _b_object *p, b_stream *out) { - B_CLASS_DISPATCH_VIRTUAL_V(b_object, B_TYPE_OBJECT, p, to_string, p, out); + B_CLASS_DISPATCH_VIRTUAL_V(b_object, B_TYPE_OBJECT, to_string, p, out); b_stream_write_fmt(out, NULL, "<%s@%p>", p->obj_type->r_info->t_name, p); } @@ -120,6 +121,32 @@ void *b_object_get_interface(const struct _b_object *object, b_type type) return b_class_get_interface(object->obj_type->r_class, type); } +enum b_status b_object_get_data( + const struct _b_object *object, b_type type, void **priv, void **prot, + void **iface) +{ + struct b_type_component *comp + = b_type_get_component(&object->obj_type->r_components, type); + if (!comp) { + return B_ERR_INVALID_ARGUMENT; + } + + if (priv) { + *priv = (char *)object + comp->c_instance_private_data_offset; + } + + if (prot) { + *prot = (char *)object + comp->c_instance_protected_data_offset; + } + + if (iface) { + *iface = (char *)object->obj_type->r_class + + comp->c_class_data_offset; + } + + return B_SUCCESS; +} + struct _b_object *b_object_ref(struct _b_object *p) { p->obj_ref++;