aqhome: started rewriting IPC module.
started with basic event interface using unix fd and timers.
This commit is contained in:
@@ -70,6 +70,7 @@
|
||||
hexfile
|
||||
data
|
||||
events
|
||||
events2
|
||||
client
|
||||
</subdirs>
|
||||
|
||||
@@ -82,6 +83,7 @@
|
||||
aqhhexfile
|
||||
aqhdata
|
||||
aqhevents
|
||||
aqhevents2
|
||||
aqhclient
|
||||
</useTargets>
|
||||
|
||||
|
||||
88
aqhome/events2/0BUILD
Normal file
88
aqhome/events2/0BUILD
Normal file
@@ -0,0 +1,88 @@
|
||||
<?xml?>
|
||||
|
||||
<gwbuild>
|
||||
|
||||
<target type="ConvenienceLibrary" name="aqhevents2" >
|
||||
|
||||
<includes type="c" >
|
||||
$(gwenhywfar_cflags)
|
||||
$(aqdatabase_cflags)
|
||||
-I$(topsrcdir)
|
||||
-I$(topbuilddir)
|
||||
</includes>
|
||||
|
||||
<includes type="tm2" >
|
||||
--include=$(builddir)
|
||||
--include=$(srcdir)
|
||||
--include=$(aqdatabase_AQDATABASE_TYPEMAKERDIR)/c
|
||||
</includes>
|
||||
|
||||
|
||||
<define name="BUILDING_AQHOME" />
|
||||
|
||||
<setVar name="local/cflags">$(visibility_cflags)</setVar>
|
||||
|
||||
|
||||
<setVar name="tm2flags" >
|
||||
--api=AQHOME_API
|
||||
</setVar>
|
||||
|
||||
<setVar name="local/typefiles" >
|
||||
</setVar>
|
||||
|
||||
<setVar name="local/built_sources" >
|
||||
</setVar>
|
||||
|
||||
<setVar name="local/built_headers_pub">
|
||||
</setVar>
|
||||
|
||||
|
||||
<setVar name="local/built_headers_priv" >
|
||||
</setVar>
|
||||
|
||||
|
||||
<headers dist="false" install="$(pkgincludedir)/data" >
|
||||
$(local/built_headers_pub)
|
||||
</headers>
|
||||
|
||||
|
||||
<headers dist="true" install="$(pkgincludedir)/data" >
|
||||
eventloop.h
|
||||
object.h
|
||||
fdobject.h
|
||||
</headers>
|
||||
|
||||
|
||||
<headers dist="true" >
|
||||
eventloop_p.h
|
||||
object_p.h
|
||||
fdobject_p.h
|
||||
</headers>
|
||||
|
||||
|
||||
<sources>
|
||||
$(local/typefiles)
|
||||
|
||||
eventloop.c
|
||||
eventloop_select.c
|
||||
object.c
|
||||
fdobject.c
|
||||
</sources>
|
||||
|
||||
|
||||
<extradist>
|
||||
</extradist>
|
||||
|
||||
|
||||
<useTargets>
|
||||
</useTargets>
|
||||
|
||||
<subdirs>
|
||||
</subdirs>
|
||||
|
||||
|
||||
|
||||
|
||||
</target>
|
||||
|
||||
</gwbuild>
|
||||
79
aqhome/events2/eventloop.c
Normal file
79
aqhome/events2/eventloop.c
Normal file
@@ -0,0 +1,79 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project AqHome.
|
||||
* AqHome (c) by 2025 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include "./eventloop_p.h"
|
||||
|
||||
#include <gwenhywfar/debug.h>
|
||||
|
||||
|
||||
|
||||
|
||||
AQH_EVENT_LOOP *AQH_EventLoop_new()
|
||||
{
|
||||
AQH_EVENT_LOOP *eventLoop;
|
||||
|
||||
GWEN_NEW_OBJECT(AQH_EVENT_LOOP, eventLoop);
|
||||
eventLoop->fdObjectList=AQH_Object_List2_new();
|
||||
eventLoop->timerObjectList=AQH_Object_List2_new();
|
||||
|
||||
return eventLoop;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_EventLoop_free(AQH_EVENT_LOOP *eventLoop)
|
||||
{
|
||||
if (eventLoop) {
|
||||
AQH_Object_List2_free(eventLoop->timerObjectList);
|
||||
AQH_Object_List2_free(eventLoop->fdObjectList);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_EventLoop_AddFdObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o)
|
||||
{
|
||||
if (eventLoop && o && NULL==AQH_Object_List2_Contains(eventLoop->fdObjectList, o)) {
|
||||
AQH_Object_List2_PushBack(eventLoop->fdObjectList, o);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_EventLoop_DelFdObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o)
|
||||
{
|
||||
if (eventLoop && o)
|
||||
AQH_Object_List2_Remove(eventLoop->fdObjectList, o);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_EventLoop_AddTimerObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o)
|
||||
{
|
||||
if (eventLoop && o && NULL==AQH_Object_List2_Contains(eventLoop->timerObjectList, o)) {
|
||||
AQH_Object_List2_PushBack(eventLoop->timerObjectList, o);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_EventLoop_DelTimerObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o)
|
||||
{
|
||||
if (eventLoop && o)
|
||||
AQH_Object_List2_Remove(eventLoop->timerObjectList, o);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
32
aqhome/events2/eventloop.h
Normal file
32
aqhome/events2/eventloop.h
Normal file
@@ -0,0 +1,32 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project AqHome.
|
||||
* AqHome (c) by 2025 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AQH_EVENTLOOP_H
|
||||
#define AQH_EVENTLOOP_H
|
||||
|
||||
typedef struct AQH_EVENT_LOOP AQH_EVENT_LOOP;
|
||||
|
||||
|
||||
#include <aqhome/events2/object.h>
|
||||
|
||||
|
||||
|
||||
AQHOME_API AQH_EVENT_LOOP *AQH_EventLoop_new();
|
||||
AQHOME_API void AQH_EventLoop_free(AQH_EVENT_LOOP *eventLoop);
|
||||
|
||||
AQHOME_API void AQH_EventLoop_Run(AQH_EVENT_LOOP *eventLoop);
|
||||
|
||||
AQHOME_API void AQH_EventLoop_AddFdObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o);
|
||||
AQHOME_API void AQH_EventLoop_DelFdObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o);
|
||||
|
||||
AQHOME_API void AQH_EventLoop_AddTimerObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o);
|
||||
AQHOME_API void AQH_EventLoop_DelTimerObject(AQH_EVENT_LOOP *eventLoop, AQH_OBJECT *o);
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
25
aqhome/events2/eventloop_p.h
Normal file
25
aqhome/events2/eventloop_p.h
Normal file
@@ -0,0 +1,25 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project AqHome.
|
||||
* AqHome (c) by 2025 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AQH_EVENTLOOP_P_H
|
||||
#define AQH_EVENTLOOP_P_H
|
||||
|
||||
#include "./eventloop.h"
|
||||
|
||||
|
||||
|
||||
struct AQH_EVENT_LOOP
|
||||
{
|
||||
AQH_OBJECT_LIST2 *fdObjectList;
|
||||
AQH_OBJECT_LIST2 *timerObjectList;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
173
aqhome/events2/eventloop_select.c
Normal file
173
aqhome/events2/eventloop_select.c
Normal file
@@ -0,0 +1,173 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project AqHome.
|
||||
* AqHome (c) by 2025 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include "./eventloop_p.h"
|
||||
#include "./fdobject.h"
|
||||
|
||||
#include <gwenhywfar/debug.h>
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/select.h>
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* forward declarations
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
static int _sampleFdsIntoSet(AQH_OBJECT_LIST2 *ol, fd_set *fds, int mode);
|
||||
static void _markReadyFdObjects(AQH_OBJECT_LIST2 *ol, fd_set *fds, int mode);
|
||||
static void _signalReadyFdObjects(AQH_OBJECT_LIST2 *ol);
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* code
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
void AQH_EventLoop_Run(AQH_EVENT_LOOP *eventLoop)
|
||||
{
|
||||
fd_set fdRead;
|
||||
fd_set fdWrite;
|
||||
int highestFd=-1;
|
||||
int rv;
|
||||
|
||||
FD_ZERO(&fdRead);
|
||||
FD_ZERO(&fdWrite);
|
||||
|
||||
highestFd=_sampleFdsIntoSet(eventLoop->fdObjectList, &fdRead, AQH_FDOBJECT_FDMODE_READ);
|
||||
rv=_sampleFdsIntoSet(eventLoop->fdObjectList, &fdWrite, AQH_FDOBJECT_FDMODE_WRITE);
|
||||
highestFd=(rv>highestFd)?rv:highestFd;
|
||||
|
||||
if (highestFd>-1) {
|
||||
struct timeval tv;
|
||||
|
||||
tv.tv_sec=0;
|
||||
tv.tv_usec=200000;
|
||||
rv=select(highestFd+1, &fdRead, &fdWrite, NULL, &tv);
|
||||
if (rv>0) {
|
||||
/* some fds became active */
|
||||
_markReadyFdObjects(eventLoop->fdObjectList, &fdRead, AQH_FDOBJECT_FDMODE_READ);
|
||||
_markReadyFdObjects(eventLoop->fdObjectList, &fdWrite, AQH_FDOBJECT_FDMODE_WRITE);
|
||||
_signalReadyFdObjects(eventLoop->fdObjectList);
|
||||
}
|
||||
else if (rv<0) {
|
||||
if (errno!=EINTR) {
|
||||
/* error */
|
||||
DBG_ERROR(AQH_LOGDOMAIN, "Error on SELECT: %d (%s)", errno, strerror(errno));
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* no fd became active (TODO: maybe signal deep idle objects?) */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
int _sampleFdsIntoSet(AQH_OBJECT_LIST2 *ol, fd_set *fds, int mode)
|
||||
{
|
||||
AQH_OBJECT_LIST2_ITERATOR *it;
|
||||
int highestFd=-1;
|
||||
|
||||
it=AQH_Object_List2_First(ol);
|
||||
if (it) {
|
||||
AQH_OBJECT *o;
|
||||
|
||||
o=AQH_Object_List2Iterator_Data(it);
|
||||
while(o) {
|
||||
int m;
|
||||
|
||||
m=AQH_FdObject_GetFdMode(o);
|
||||
if (m==mode) {
|
||||
int fd;
|
||||
|
||||
fd=AQH_FdObject_GetFd(o);
|
||||
if (fd>-1) {
|
||||
highestFd=(fd>highestFd)?fd:highestFd;
|
||||
FD_SET(fd, fds);
|
||||
}
|
||||
}
|
||||
o=AQH_Object_List2Iterator_Next(it);
|
||||
}
|
||||
AQH_Object_List2Iterator_free(it);
|
||||
}
|
||||
|
||||
return highestFd;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void _markReadyFdObjects(AQH_OBJECT_LIST2 *ol, fd_set *fds, int mode)
|
||||
{
|
||||
AQH_OBJECT_LIST2_ITERATOR *it;
|
||||
|
||||
it=AQH_Object_List2_First(ol);
|
||||
if (it) {
|
||||
AQH_OBJECT *o;
|
||||
|
||||
o=AQH_Object_List2Iterator_Data(it);
|
||||
while(o) {
|
||||
int m;
|
||||
|
||||
m=AQH_FdObject_GetFdMode(o);
|
||||
if (m==mode) {
|
||||
int fd;
|
||||
|
||||
fd=AQH_FdObject_GetFd(o);
|
||||
if (FD_ISSET(fd, fds))
|
||||
AQH_Object_AddFlags(o, AQH_OBJECT_FLAGS_FIRE);
|
||||
}
|
||||
o=AQH_Object_List2Iterator_Next(it);
|
||||
}
|
||||
|
||||
AQH_Object_List2Iterator_free(it);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void _signalReadyFdObjects(AQH_OBJECT_LIST2 *ol)
|
||||
{
|
||||
AQH_OBJECT_LIST2_ITERATOR *it;
|
||||
|
||||
it=AQH_Object_List2_First(ol);
|
||||
if (it) {
|
||||
AQH_OBJECT *o;
|
||||
|
||||
o=AQH_Object_List2Iterator_Data(it);
|
||||
while(o) {
|
||||
if (AQH_Object_GetFlags(o) & AQH_OBJECT_FLAGS_FIRE) {
|
||||
AQH_Object_SubFlags(o, AQH_OBJECT_FLAGS_FIRE);
|
||||
AQH_Object_EmitSignal(o, AQH_FDOBJECT_SIGNAL_ISREADY, 0, NULL);
|
||||
}
|
||||
o=AQH_Object_List2Iterator_Next(it);
|
||||
}
|
||||
|
||||
AQH_Object_List2Iterator_free(it);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
140
aqhome/events2/fdobject.c
Normal file
140
aqhome/events2/fdobject.c
Normal file
@@ -0,0 +1,140 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project Gwenhywfar.
|
||||
* Gwenhywfar (c) by 2023 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include "./fdobject_p.h"
|
||||
|
||||
#include <gwenhywfar/inherit.h>
|
||||
|
||||
|
||||
|
||||
GWEN_INHERIT(AQH_OBJECT, AQH_FDOBJECT)
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* forward declarations
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
static void GWENHYWFAR_CB _freeData(void *bp, void *p);
|
||||
static void _cbEnable(AQH_OBJECT *o);
|
||||
static void _cbDisable(AQH_OBJECT *o);
|
||||
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* implementations
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
AQH_OBJECT *AQH_FdObject_new(AQH_EVENT_LOOP *eventLoop, int fd, int mode)
|
||||
{
|
||||
AQH_OBJECT *o;
|
||||
AQH_FDOBJECT *xo;
|
||||
|
||||
o=AQH_Object_new(eventLoop);
|
||||
GWEN_NEW_OBJECT(AQH_FDOBJECT, xo);
|
||||
GWEN_INHERIT_SETDATA(AQH_OBJECT, AQH_FDOBJECT, o, xo, _freeData);
|
||||
xo->fd=fd;
|
||||
xo->fdMode=mode;
|
||||
|
||||
AQH_Object_SetEnableFn(o, _cbEnable);
|
||||
AQH_Object_SetDisableFn(o, _cbDisable);
|
||||
|
||||
return o;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void GWENHYWFAR_CB _freeData(GWEN_UNUSED void *bp, void *p)
|
||||
{
|
||||
AQH_FDOBJECT *xo;
|
||||
|
||||
xo=(AQH_FDOBJECT*)p;
|
||||
GWEN_FREE_OBJECT(xo);
|
||||
}
|
||||
|
||||
|
||||
|
||||
int AQH_FdObject_GetFdMode(const AQH_OBJECT *o)
|
||||
{
|
||||
if (o) {
|
||||
AQH_FDOBJECT *xo;
|
||||
|
||||
xo=GWEN_INHERIT_GETDATA(AQH_OBJECT, AQH_FDOBJECT, o);
|
||||
if (xo)
|
||||
return xo->fdMode;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_FdObject_SetFdMode(AQH_OBJECT *o, int i)
|
||||
{
|
||||
if (o) {
|
||||
AQH_FDOBJECT *xo;
|
||||
|
||||
xo=GWEN_INHERIT_GETDATA(AQH_OBJECT, AQH_FDOBJECT, o);
|
||||
if (xo)
|
||||
xo->fdMode=i;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
int AQH_FdObject_GetFd(const AQH_OBJECT *o)
|
||||
{
|
||||
if (o) {
|
||||
AQH_FDOBJECT *xo;
|
||||
|
||||
xo=GWEN_INHERIT_GETDATA(AQH_OBJECT, AQH_FDOBJECT, o);
|
||||
if (xo)
|
||||
return xo->fd;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void _cbEnable(AQH_OBJECT *o)
|
||||
{
|
||||
if (o) {
|
||||
AQH_EVENT_LOOP *eventLoop;
|
||||
|
||||
eventLoop=AQH_Object_GetEventLoop(o);
|
||||
if (eventLoop)
|
||||
AQH_EventLoop_AddFdObject(eventLoop, o);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void _cbDisable(AQH_OBJECT *o)
|
||||
{
|
||||
if (o) {
|
||||
AQH_EVENT_LOOP *eventLoop;
|
||||
|
||||
eventLoop=AQH_Object_GetEventLoop(o);
|
||||
if (eventLoop)
|
||||
AQH_EventLoop_DelFdObject(eventLoop, o);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
36
aqhome/events2/fdobject.h
Normal file
36
aqhome/events2/fdobject.h
Normal file
@@ -0,0 +1,36 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project Gwenhywfar.
|
||||
* Gwenhywfar (c) by 2023 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AQH_FDOBJECT_H
|
||||
#define AQH_FDOBJECT_H
|
||||
|
||||
|
||||
#include <aqhome/events2/object.h>
|
||||
|
||||
|
||||
enum {
|
||||
AQH_FDOBJECT_FDMODE_READ=1,
|
||||
AQH_FDOBJECT_FDMODE_WRITE
|
||||
};
|
||||
|
||||
|
||||
enum {
|
||||
AQH_FDOBJECT_SIGNAL_ISREADY=AQH_OBJECT_SIGNAL_LAST
|
||||
};
|
||||
|
||||
|
||||
|
||||
AQHOME_API AQH_OBJECT *AQH_FdObject_new(AQH_EVENT_LOOP *eventLoop, int fd, int mode);
|
||||
|
||||
AQHOME_API int AQH_FdObject_GetFdMode(const AQH_OBJECT *o);
|
||||
AQHOME_API void AQH_FdObject_SetFdMode(AQH_OBJECT *o, int i);
|
||||
|
||||
AQHOME_API int AQH_FdObject_GetFd(const AQH_OBJECT *o);
|
||||
|
||||
|
||||
#endif
|
||||
23
aqhome/events2/fdobject_p.h
Normal file
23
aqhome/events2/fdobject_p.h
Normal file
@@ -0,0 +1,23 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project Gwenhywfar.
|
||||
* Gwenhywfar (c) by 2023 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AQH_FDOBJECT_P_H
|
||||
#define AQH_FDOBJECT_P_H
|
||||
|
||||
|
||||
#include "./fdobject.h"
|
||||
|
||||
|
||||
typedef struct AQH_FDOBJECT AQH_FDOBJECT;
|
||||
struct AQH_FDOBJECT {
|
||||
int fdMode;
|
||||
int fd;
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
276
aqhome/events2/object.c
Normal file
276
aqhome/events2/object.c
Normal file
@@ -0,0 +1,276 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project AqHome.
|
||||
* AqHome (c) by 2025 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include "./object_p.h"
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* forward declarations
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
AQH_LINK *AQH_Link_new();
|
||||
void AQH_Link_free(AQH_LINK *ln);
|
||||
|
||||
AQH_LINK *_findLink(AQH_OBJECT *o, uint32_t signalId, uint32_t slotId, AQH_OBJECT *targetObject);
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* list, inherit
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
GWEN_LIST_FUNCTIONS(AQH_LINK, AQH_Link)
|
||||
|
||||
GWEN_INHERIT_FUNCTIONS(AQH_OBJECT)
|
||||
GWEN_LIST_FUNCTIONS(AQH_OBJECT, AQH_Object)
|
||||
GWEN_LIST2_FUNCTIONS(AQH_OBJECT, AQH_Object)
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* code
|
||||
* ------------------------------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
AQH_OBJECT *AQH_Object_new(AQH_EVENT_LOOP *eventLoop)
|
||||
{
|
||||
AQH_OBJECT *o;
|
||||
|
||||
GWEN_NEW_OBJECT(AQH_OBJECT, o);
|
||||
GWEN_INHERIT_INIT(AQH_OBJECT, o);
|
||||
GWEN_LIST_INIT(AQH_OBJECT, o);
|
||||
o->eventLoop=eventLoop;
|
||||
o->linkList=AQH_Link_List_new();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_free(AQH_OBJECT *o)
|
||||
{
|
||||
if (o) {
|
||||
GWEN_INHERIT_FINI(AQH_OBJECT, o);
|
||||
GWEN_LIST_FINI(AQH_OBJECT, o);
|
||||
|
||||
AQH_Link_List_free(o->linkList);
|
||||
|
||||
GWEN_FREE_OBJECT(o);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
uint32_t AQH_Object_GetFlags(const AQH_OBJECT *o)
|
||||
{
|
||||
return o?o->flags:0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_SetFlags(AQH_OBJECT *o, uint32_t i)
|
||||
{
|
||||
if (o)
|
||||
o->flags=i;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_AddFlags(AQH_OBJECT *o, uint32_t i)
|
||||
{
|
||||
if (o)
|
||||
o->flags|=i;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_SubFlags(AQH_OBJECT *o, uint32_t i)
|
||||
{
|
||||
if (o)
|
||||
o->flags&=~i;
|
||||
}
|
||||
|
||||
|
||||
|
||||
AQH_EVENT_LOOP *AQH_Object_GetEventLoop(const AQH_OBJECT *o)
|
||||
{
|
||||
return o?o->eventLoop:NULL;
|
||||
}
|
||||
|
||||
|
||||
|
||||
AQH_LINK *_findLink(AQH_OBJECT *o, uint32_t signalId, uint32_t slotId, AQH_OBJECT *targetObject)
|
||||
{
|
||||
if (o) {
|
||||
AQH_LINK *ln;
|
||||
|
||||
ln=AQH_Link_List_First(o->linkList);
|
||||
while(ln) {
|
||||
if (ln->signalIdForSender==signalId &&
|
||||
ln->signalIdForTarget==slotId &&
|
||||
ln->targetObject==targetObject)
|
||||
return ln;
|
||||
ln=AQH_Link_List_Next(ln);
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_AddLink(AQH_OBJECT *o, uint32_t signalId, uint32_t slotId, AQH_OBJECT *targetObject)
|
||||
{
|
||||
AQH_LINK *ln;
|
||||
|
||||
ln=_findLink(o, signalId, slotId, targetObject);
|
||||
if (ln==NULL) {
|
||||
ln=AQH_Link_new();
|
||||
ln->signalIdForSender=signalId;
|
||||
ln->signalIdForTarget=slotId;
|
||||
ln->targetObject=targetObject;
|
||||
AQH_Link_List_Add(ln, o->linkList);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_DelLink(AQH_OBJECT *o, uint32_t signalId, uint32_t slotId, AQH_OBJECT *targetObject)
|
||||
{
|
||||
AQH_LINK *ln;
|
||||
|
||||
ln=_findLink(o, signalId, slotId, targetObject);
|
||||
if (ln) {
|
||||
AQH_Link_List_Del(ln);
|
||||
AQH_Link_free(ln);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
int AQH_Object_EmitSignal(AQH_OBJECT *o, uint32_t signalId, int param1, void *param2)
|
||||
{
|
||||
int signalWasHandled=0;
|
||||
|
||||
if (o) {
|
||||
AQH_LINK *ln;
|
||||
|
||||
ln=AQH_Link_List_First(o->linkList);
|
||||
while(ln) {
|
||||
if (ln->signalIdForSender==signalId && ln->targetObject) {
|
||||
if (AQH_Object_HandleSignal(ln->targetObject, ln->signalIdForTarget, o, param1, param2))
|
||||
signalWasHandled=1;
|
||||
}
|
||||
ln=AQH_Link_List_Next(ln);
|
||||
}
|
||||
}
|
||||
return signalWasHandled;
|
||||
}
|
||||
|
||||
|
||||
|
||||
int AQH_Object_HandleSignal(AQH_OBJECT *o, uint32_t slotId, AQH_OBJECT *senderObject, int param1, void *param2)
|
||||
{
|
||||
if (o && o->signalHandlerFn)
|
||||
return o->signalHandlerFn(o, slotId, senderObject, param1, param2);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_Enable(AQH_OBJECT *o)
|
||||
{
|
||||
if (o && o->enableFn)
|
||||
o->enableFn(o);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Object_Disable(AQH_OBJECT *o)
|
||||
{
|
||||
if (o && o->disableFn)
|
||||
o->disableFn(o);
|
||||
}
|
||||
|
||||
|
||||
|
||||
AQH_OBJECT_SIGNALHANDLER_FN AQH_Object_SetSignalHandlerFn(AQH_OBJECT *o, AQH_OBJECT_SIGNALHANDLER_FN f)
|
||||
{
|
||||
if (o) {
|
||||
AQH_OBJECT_SIGNALHANDLER_FN oldFn;
|
||||
|
||||
oldFn=o->signalHandlerFn;
|
||||
o->signalHandlerFn=f;
|
||||
return oldFn;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
|
||||
AQH_OBJECT_ENABLE_FN AQH_Object_SetEnableFn(AQH_OBJECT *o, AQH_OBJECT_ENABLE_FN f)
|
||||
{
|
||||
if (o) {
|
||||
AQH_OBJECT_ENABLE_FN oldFn;
|
||||
|
||||
oldFn=o->enableFn;
|
||||
o->enableFn=f;
|
||||
return oldFn;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
|
||||
AQH_OBJECT_DISABLE_FN AQH_Object_SetDisableFn(AQH_OBJECT *o, AQH_OBJECT_DISABLE_FN f)
|
||||
{
|
||||
if (o) {
|
||||
AQH_OBJECT_DISABLE_FN oldFn;
|
||||
|
||||
oldFn=o->disableFn;
|
||||
o->disableFn=f;
|
||||
return oldFn;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
AQH_LINK *AQH_Link_new()
|
||||
{
|
||||
AQH_LINK *ln;
|
||||
|
||||
GWEN_NEW_OBJECT(AQH_LINK, ln);
|
||||
GWEN_LIST_INIT(AQH_LINK, ln);
|
||||
|
||||
return ln;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void AQH_Link_free(AQH_LINK *ln)
|
||||
{
|
||||
if (ln) {
|
||||
GWEN_LIST_FINI(AQH_LINK, ln);
|
||||
GWEN_FREE_OBJECT(ln);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
121
aqhome/events2/object.h
Normal file
121
aqhome/events2/object.h
Normal file
@@ -0,0 +1,121 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project AqHome.
|
||||
* AqHome (c) by 2025 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AQH_OBJECT_H
|
||||
#define AQH_OBJECT_H
|
||||
|
||||
#include "aqhome/api.h"
|
||||
|
||||
#include <gwenhywfar/inherit.h>
|
||||
#include <gwenhywfar/list.h>
|
||||
#include <gwenhywfar/list2.h>
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
|
||||
#define AQH_OBJECT_FLAGS_FIRE 0x80000000L
|
||||
|
||||
|
||||
enum {
|
||||
AQH_OBJECT_SIGNAL_LAST=10 /* reserve signal ids 0-9 */
|
||||
};
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Type Definition
|
||||
*/
|
||||
/*@{*/
|
||||
typedef struct AQH_OBJECT AQH_OBJECT;
|
||||
GWEN_INHERIT_FUNCTION_LIB_DEFS(AQH_OBJECT, AQHOME_API)
|
||||
GWEN_LIST_FUNCTION_LIB_DEFS(AQH_OBJECT, AQH_Object, AQHOME_API)
|
||||
GWEN_LIST2_FUNCTION_LIB_DEFS(AQH_OBJECT, AQH_Object, AQHOME_API)
|
||||
/*@}*/
|
||||
|
||||
|
||||
#include <aqhome/events2/eventloop.h>
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Virtual Function Declarations
|
||||
*/
|
||||
/*@{*/
|
||||
typedef int (*AQH_OBJECT_SIGNALHANDLER_FN)(AQH_OBJECT *o, uint32_t slotId, AQH_OBJECT *senderObject, int param1, void *param2);
|
||||
typedef void (*AQH_OBJECT_ENABLE_FN)(AQH_OBJECT *o);
|
||||
typedef void (*AQH_OBJECT_DISABLE_FN)(AQH_OBJECT *o);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Construction, Destruction
|
||||
*/
|
||||
/*@{*/
|
||||
AQHOME_API AQH_OBJECT *AQH_Object_new(AQH_EVENT_LOOP *eventLoop);
|
||||
AQHOME_API void AQH_Object_free(AQH_OBJECT *o);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Manipulate Flags
|
||||
*/
|
||||
/*@{*/
|
||||
AQHOME_API uint32_t AQH_Object_GetFlags(const AQH_OBJECT *o);
|
||||
AQHOME_API void AQH_Object_SetFlags(AQH_OBJECT *o, uint32_t i);
|
||||
AQHOME_API void AQH_Object_AddFlags(AQH_OBJECT *o, uint32_t i);
|
||||
AQHOME_API void AQH_Object_SubFlags(AQH_OBJECT *o, uint32_t i);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Getters, Setters
|
||||
*/
|
||||
/*@{*/
|
||||
AQHOME_API AQH_EVENT_LOOP *AQH_Object_GetEventLoop(const AQH_OBJECT *o);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Link Handling
|
||||
*/
|
||||
/*@{*/
|
||||
AQHOME_API void AQH_Object_AddLink(AQH_OBJECT *o, uint32_t signalId, uint32_t slotId, AQH_OBJECT *targetObject);
|
||||
AQHOME_API void AQH_Object_DelLink(AQH_OBJECT *o, uint32_t signalId, uint32_t slotId, AQH_OBJECT *targetObject);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Virtual Function Declarations
|
||||
*/
|
||||
/*@{*/
|
||||
AQHOME_API int AQH_Object_EmitSignal(AQH_OBJECT *o, uint32_t signalId, int param1, void *param2);
|
||||
AQHOME_API int AQH_Object_HandleSignal(AQH_OBJECT *o, uint32_t slotId, AQH_OBJECT *senderObject, int param1, void *param2);
|
||||
AQHOME_API void AQH_Object_Enable(AQH_OBJECT *o);
|
||||
AQHOME_API void AQH_Object_Disable(AQH_OBJECT *o);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
/* ------------------------------------------------------------------------------------------------
|
||||
* @name Setter for Virtual Functions
|
||||
*/
|
||||
/*@{*/
|
||||
AQHOME_API AQH_OBJECT_SIGNALHANDLER_FN AQH_Object_SetSignalHandlerFn(AQH_OBJECT *o, AQH_OBJECT_SIGNALHANDLER_FN f);
|
||||
AQHOME_API AQH_OBJECT_ENABLE_FN AQH_Object_SetEnableFn(AQH_OBJECT *o, AQH_OBJECT_ENABLE_FN f);
|
||||
AQHOME_API AQH_OBJECT_DISABLE_FN AQH_Object_SetDisableFn(AQH_OBJECT *o, AQH_OBJECT_DISABLE_FN f);
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
46
aqhome/events2/object_p.h
Normal file
46
aqhome/events2/object_p.h
Normal file
@@ -0,0 +1,46 @@
|
||||
/****************************************************************************
|
||||
* This file is part of the project Gwenhywfar.
|
||||
* Gwenhywfar (c) by 2023 Martin Preuss, all rights reserved.
|
||||
*
|
||||
* The license for this file can be found in the file COPYING which you
|
||||
* should have received along with this file.
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AQH_OBJECT_P_H
|
||||
#define AQH_OBJECT_P_H
|
||||
|
||||
|
||||
#include "./object.h"
|
||||
|
||||
|
||||
typedef struct AQH_LINK AQH_LINK;
|
||||
GWEN_LIST_FUNCTION_DEFS(AQH_LINK, AQH_Link)
|
||||
|
||||
|
||||
|
||||
struct AQH_LINK {
|
||||
GWEN_LIST_ELEMENT(AQH_LINK)
|
||||
|
||||
uint32_t signalIdForSender;
|
||||
uint32_t signalIdForTarget;
|
||||
AQH_OBJECT *targetObject;
|
||||
};
|
||||
|
||||
|
||||
|
||||
struct AQH_OBJECT {
|
||||
GWEN_INHERIT_ELEMENT(AQH_OBJECT)
|
||||
GWEN_LIST_ELEMENT(AQH_OBJECT)
|
||||
|
||||
uint32_t flags;
|
||||
AQH_EVENT_LOOP *eventLoop;
|
||||
|
||||
AQH_LINK_LIST *linkList;
|
||||
|
||||
AQH_OBJECT_SIGNALHANDLER_FN signalHandlerFn;
|
||||
AQH_OBJECT_ENABLE_FN enableFn;
|
||||
AQH_OBJECT_DISABLE_FN disableFn;
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
Reference in New Issue
Block a user