- improve the interface of rtti to pass meta_obj_t* as parameter of type function to easy to access private/data

- rename some macro with RTTI
- add RTTI_MAGIC in object header
- add new rtti api
This commit is contained in:
Rongsong Shen 2026-01-30 12:26:23 +08:00
parent c8c1749347
commit f78ed03591
15 changed files with 252 additions and 114 deletions

View file

@ -3,10 +3,10 @@
#include "rtti.h"
static void* objAlloc(typeinfo_t* type, size_t sz)
static meta_obj_t* objAlloc(typeinfo_t* type, size_t sz)
{
size_t privateSize = SIZE_ROUNDUP(type->privateSize);
size_t headerSize = OBJ_HEADER_SIZE;
size_t privateSize = RTTI_SIZE_ROUNDUP(type->privateSize);
size_t headerSize = RTTI_OBJ_HEADER_SIZE;
char* p = NULL;
meta_obj_t* obj = NULL;
size_t total = privateSize + headerSize + sz;
@ -16,18 +16,21 @@ static void* objAlloc(typeinfo_t* type, size_t sz)
return NULL;
}
obj = (meta_obj_t*)(p + privateSize);
obj->type = type;
obj = (meta_obj_t*)(p + privateSize);
obj->type = type;
obj->magic = RTTI_MAGIC;
obj->privdata = p;
obj->data = (void*)(p + privateSize + headerSize);
return (void*)(p + privateSize + headerSize);
return obj;
}
var makeInstance(typeinfo_t* type, ...)
{
va_list ap;
va_list ap1;
var v = NULL;
int rc = 0;
va_list ap;
va_list ap1;
meta_obj_t* obj;
int rc = 0;
if ((type == NULL) || (type->init == NULL) || (type->dataSize == NULL)) {
errno = EINVAL;
@ -36,46 +39,57 @@ var makeInstance(typeinfo_t* type, ...)
va_start(ap, type);
va_copy(ap1, ap);
v = objAlloc(type, type->dataSize(ap1));
obj = objAlloc(type, type->dataSize(ap1));
va_end(ap1);
if (v != NULL) {
rc = type->init(v, ap);
if (obj != NULL) {
rc = type->init(obj, ap);
}
va_end(ap);
if (rc < 0) {
destroy(v);
v = NULL;
destroy(obj);
return NULL;
}
return v;
return obj->data;
}
void destroy(var v)
{
typeinfo_t* type = NULL;
meta_obj_t* obj = NULL;
void* p = NULL;
meta_obj_t* obj = NULL;
if (v == NULL) {
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return;
}
obj = DATA_TO_OBJ(v);
type = obj->type;
if (type == NULL) {
return;
}
if (type->destroy != NULL) {
type->destroy(v);
type->destroy(obj);
}
p = OBJ_TO_PRIV(obj);
p = RTTI_OBJ_TO_PRIV(obj);
free(p);
return;
}
int is_rtti_obj(var v)
{
meta_obj_t* obj = NULL;
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return 0;
}
return 1;
}

22
src/hash.c Normal file
View file

@ -0,0 +1,22 @@
#include <errno.h>
#include <stdint.h>
#include <stdlib.h>
#include "rtti.h"
int32_t hash(var v) {
meta_obj_t* obj = NULL;
hash_fn_t method = NULL;
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, obj, hash, hash);
if (method == NULL) {
return -EINVAL;
}
return method(obj);
}

View file

@ -6,32 +6,42 @@
int iter_make(iterator_t* it, var v)
{
meta_obj_t* obj = NULL;
iter_make_fn_t method = NULL;
if (it == NULL) {
return -EINVAL;
}
RTTI_GET_METHOD(method, v, iter, make);
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, obj, iter, make);
if (method == NULL) {
return -EINVAL;
}
memset(it, 0x0, sizeof(*it));
it->v = v;
return method(it, v);
memset(it, 0x0, sizeof(*it));
it->obj = obj;
return method(it);
}
int iter_next(iterator_t* it, void** data)
{
iter_next_fn_t method = NULL;
if ((it == NULL) || (data == NULL) || (it->v == NULL)) {
if ((it == NULL) || (data == NULL)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, it->v, iter, next);
if (RTTI_OBJ_INVALID(it->obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, it->obj, iter, next);
if (method == NULL) {
return -EINVAL;
}
@ -43,11 +53,15 @@ int iter_reset(iterator_t* it)
{
iter_reset_fn_t method = NULL;
if ((it == NULL) || (it->v == NULL)) {
if (it == NULL) {
return -EINVAL;
}
RTTI_GET_METHOD(method, it->v, iter, reset);
if (RTTI_OBJ_INVALID(it->obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, it->obj, iter, reset);
if (method == NULL) {
return -EINVAL;
}
@ -59,16 +73,20 @@ void iter_destroy(iterator_t* it)
{
iter_destroy_fn_t method = NULL;
if ((it == NULL) || (it->v == NULL)) {
if (it == NULL) {
return;
}
RTTI_GET_METHOD(method, it->v, iter, destroy);
if (RTTI_OBJ_INVALID(it->obj)) {
return;
}
RTTI_GET_METHOD(method, it->obj, iter, destroy);
if (method == NULL) {
return;
}
method(it);
return;
}

23
src/length.c Normal file
View file

@ -0,0 +1,23 @@
#include <errno.h>
#include <stdint.h>
#include <stdlib.h>
#include "rtti.h"
int64_t length(var v)
{
meta_obj_t* obj = NULL;
length_fn_t method = NULL;
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, obj, length, length);
if (method == NULL) {
return -EINVAL;
}
return method(obj);
}

View file

@ -5,21 +5,33 @@
int lock(var v, uint64_t option)
{
lock_fn_t method = NULL;
meta_obj_t* obj = NULL;
lock_fn_t method = NULL;
RTTI_GET_METHOD(method, v, lock, lock);
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, obj, lock, lock);
if (method == NULL) {
return -EINVAL;
}
return method(v, option);
return method(obj, option);
}
void unlock(var v)
{
meta_obj_t* obj = NULL;
unlock_fn_t method = NULL;
RTTI_GET_METHOD(method, v, lock, unlock);
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return;
}
RTTI_GET_METHOD(method, obj, lock, unlock);
if (method == NULL) {
return;
}

View file

@ -6,6 +6,8 @@ librtti_c_srcs=[
'iter.c',
'ref.c',
'str.c',
'hash.c',
'length.c',
]
@ -19,7 +21,6 @@ rtti_top_headers = [
rtti_headers = [
'../include/rtti/typeinfo.h',
'../include/rtti/utils.h',
]
librtti_deps = [

View file

@ -6,23 +6,35 @@
int32_t reference(var v)
{
meta_obj_t* obj = NULL;
reference_fn_t method = NULL;
RTTI_GET_METHOD(method, v, reference, reference);
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return -EINVAL;
}
RTTI_GET_METHOD(method, obj, reference, reference);
if (method == NULL) {
return -EINVAL;
}
return method(v);
return method(obj);
}
void dereference(var v)
{
meta_obj_t* obj = NULL;
dereference_fn_t method = NULL;
RTTI_GET_METHOD(method,v, reference, dereference);
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
return;
}
RTTI_GET_METHOD(method, obj, reference, dereference);
if (method != NULL) {
method(v);
method(obj);
}
return;

View file

@ -5,13 +5,20 @@
char* toString(var v, ...)
{
meta_obj_t* obj = NULL;
to_string_fn_t method = NULL;
va_list ap;
char* s = NULL;
RTTI_GET_METHOD(method, v, toString, toString);
obj = RTTI_DATA_TO_OBJ(v);
if (RTTI_OBJ_INVALID(obj)) {
errno = EINVAL;
return NULL;
}
RTTI_GET_METHOD(method, obj, toString, toString);
if (method == NULL) {
errno = -EINVAL;
errno = EINVAL;
return NULL;
}