fx: support for registering callable functions with types

This commit is contained in:
2026-05-05 21:16:31 +01:00
parent 703155affe
commit f3062222cb
16 changed files with 182 additions and 25 deletions
+8 -1
View File
@@ -73,9 +73,16 @@ fx_result fx_class_instantiate(
c_entry);
const struct fx_type_info *class_info = comp->c_type;
void *class_data = (char *)out + comp->c_class_data_offset;
struct fx_type_info *main_class_param = NULL;
if (class_info == type) {
main_class_param = type;
}
if (class_info->ty_class_init) {
class_info->ty_class_init(out, class_data);
class_info->ty_class_init(
out,
main_class_param,
class_data);
}
entry = fx_queue_next(entry);
+49 -5
View File
@@ -5,6 +5,7 @@
#include <fx/object.h>
#include <fx/thread.h>
#include <fx/type.h>
#include <fx/value.h>
#include <stdlib.h>
#define __FX_IFACE_I0(p, x) p##x
@@ -13,7 +14,10 @@
/* Type definitions macros (for use in .c source file) */
#define FX_TYPE_CLASS_BEGIN(type_name) \
static void type_name##_class_init(fx_class *p, void *d) \
static void type_name##_class_init( \
fx_class *p, \
fx_type_info *ty, \
void *d) \
{
#define FX_TYPE_CLASS_END(type_name) }
@@ -21,9 +25,49 @@
static void type_name##_type_functionality_init(void *opaque) \
{
#define FX_TYPE_FUNCTIONALITY_END(type_name) }
#define FX_TYPE_CONSTRUCTOR(name, impl, ...)
#define FX_TYPE_METHOD(return_type, name, impl, ...)
#define FX_TYPE_FUNCTION(return_type, name, impl, ...)
#define FX_TYPE_CONSTRUCTOR(name, impl, flags, ...) \
do { \
if (ty) { \
fx_value_type args[] = {__VA_ARGS__}; \
fx_function *func = fx_function_create( \
name, \
FX_FUNCTION_F_CONSTRUCTOR \
| FX_FUNCTION_F_STATIC | (flags), \
(fx_function_impl)impl, \
args, \
sizeof args / sizeof args[0], \
FX_VALUE_TYPE_POINTER); \
fx_type_add_function(ty, func); \
} \
} while (0)
#define FX_TYPE_METHOD(return_type, name, impl, flags, ...) \
do { \
if (ty) { \
fx_value_type args[] = {__VA_ARGS__}; \
fx_function *func = fx_function_create( \
name, \
(flags), \
(fx_function_impl)impl, \
args, \
sizeof args / sizeof args[0], \
return_type); \
fx_type_add_function(ty, func); \
} \
} while (0)
#define FX_TYPE_FUNCTION(return_type, name, impl, ...) \
do { \
if (ty) { \
fx_value_type args[] = {__VA_ARGS__}; \
fx_function *func = fx_function_create( \
name, \
FX_FUNCTION_F_STATIC | (flags), \
(fx_function_impl)impl, \
args, \
sizeof args / sizeof args[0], \
return_type); \
fx_type_add_function(ty, func); \
} \
} while (0)
#define FX_TYPE_VTABLE_INTERFACE_BEGIN(interface_name, interface_id) \
interface_name##_class *__FX_IFACE_I1(iface, __LINE__) \
@@ -43,7 +87,7 @@
#define FX_TYPE_DEFINITION_BEGIN(name) \
static fx_type_info name##_type_info = {0}; \
static void name##_class_init(fx_class *, void *); \
static void name##_class_init(fx_class *, fx_type_info *, void *); \
static void name##_type_init(void) \
{ \
fx_type_info *type_info = &name##_type_info; \
+7 -1
View File
@@ -14,8 +14,12 @@
struct _fx_class;
struct _fx_object;
struct fx_type_info;
typedef void (*fx_class_init_function)(struct _fx_class *, void *);
typedef void (*fx_class_init_function)(
struct _fx_class *,
struct fx_type_info *,
void *);
typedef void (*fx_instance_init_function)(struct _fx_object *, void *);
typedef void (*fx_instance_fini_function)(struct _fx_object *, void *);
@@ -86,5 +90,7 @@ static inline int fx_type_id_compare(fx_type_id a, fx_type_id b)
}
FX_API fx_result fx_type_register(fx_type_info *info);
FX_API fx_result
fx_type_add_function(fx_type_info *info, struct _fx_object *func);
#endif
+14
View File
@@ -1,4 +1,5 @@
#include <ctype.h>
#include <fx/reflection/function.h>
#include <fx/stream.h>
#include <fx/string.h>
#include <fx/stringstream.h>
@@ -1716,6 +1717,19 @@ FX_TYPE_CLASS_BEGIN(fx_string)
FX_INTERFACE_ENTRY(it_begin) = iterator_begin;
FX_INTERFACE_ENTRY(it_cbegin) = iterator_cbegin;
FX_TYPE_VTABLE_INTERFACE_END(fx_iterable, FX_TYPE_ITERABLE)
FX_TYPE_CONSTRUCTOR("create", fx_string_create, 0, FX_VALUE_TYPE_NONE);
FX_TYPE_CONSTRUCTOR(
"create_from_cstr",
fx_string_create_from_cstr,
1,
FX_VALUE_TYPE_CSTR);
FX_TYPE_METHOD(
FX_VALUE_TYPE_CSTR,
"get_cstr",
fx_string_get_cstr,
0,
FX_VALUE_TYPE_POINTER);
FX_TYPE_CLASS_END(fx_string)
FX_TYPE_DEFINITION_BEGIN(fx_string)
+40
View File
@@ -6,6 +6,7 @@
#include <fx/bst.h>
#include <fx/endian.h>
#include <fx/object.h>
#include <fx/reflection/function.h>
#include <fx/type.h>
#include <stdio.h>
#include <stdlib.h>
@@ -343,6 +344,29 @@ fx_result fx_type_register(struct fx_type_info *info)
return FX_RESULT_SUCCESS;
}
fx_result fx_type_add_function(fx_type_info *info, struct _fx_object *func)
{
const char *name = fx_function_get_name(func);
struct fx_namemap_entry *entry = fx_namemap_get(
&info->ty_functions,
name);
if (entry) {
return FX_RESULT_ERR(NAME_EXISTS);
}
struct fx_type_function *ty_func = malloc(sizeof *ty_func);
if (!ty_func) {
return FX_RESULT_ERR(NO_MEMORY);
}
memset(ty_func, 0x0, sizeof *ty_func);
ty_func->f_func = func;
fx_namemap_put(&info->ty_functions, name, &ty_func->f_entry);
return FX_RESULT_SUCCESS;
}
struct fx_type_info *fx_type_info_get_by_id(const union fx_type_id *key)
{
return get_type(&type_idmap, key);
@@ -357,3 +381,19 @@ struct fx_type_info *fx_type_info_get_by_name(const char *name)
return fx_unbox(struct fx_type_info, entry, ty_namemap_entry);
}
fx_function *fx_type_info_get_function_by_name(
const struct fx_type_info *ty,
const char *name)
{
fx_namemap_entry *entry = fx_namemap_get(&ty->ty_functions, name);
if (!entry) {
return NULL;
}
struct fx_type_function *func = fx_unbox(
struct fx_type_function,
entry,
f_entry);
return func->f_func;
}
+5 -1
View File
@@ -4,6 +4,7 @@
#include <fx/bst.h>
#include <fx/namemap.h>
#include <fx/queue.h>
#include <fx/reflection/function.h>
#include <fx/reflection/type.h>
#include <fx/type.h>
#include <stddef.h>
@@ -20,7 +21,7 @@ struct fx_type_component {
struct fx_type_function {
struct fx_namemap_entry f_entry;
struct fx_function *f_func;
fx_function *f_func;
};
extern struct fx_type_registration *fx_type_get_registration(fx_type_id id);
@@ -29,5 +30,8 @@ extern struct fx_type_component *fx_type_get_component(
const union fx_type_id *key);
extern struct fx_type_info *fx_type_info_get_by_id(const union fx_type_id *key);
extern struct fx_type_info *fx_type_info_get_by_name(const char *name);
extern fx_function *fx_type_info_get_function_by_name(
const struct fx_type_info *ty,
const char *name);
#endif