136 lines
4.2 KiB
C
136 lines
4.2 KiB
C
/****************************************************************************
|
|
* This file is part of the project AqHome.
|
|
* AqHome (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 "aqhome/ipc/endpoint_ipcclient.h"
|
|
#include "aqhome/ipc/data/ipc_data.h"
|
|
#include "aqhome/ipc/endpoint_ipc.h"
|
|
#include "aqhome/ipc/data/msg_data_connect.h"
|
|
#include "aqhome/ipc/msg_ipc_result.h"
|
|
|
|
#include <gwenhywfar/endpoint_ipc.h>
|
|
#include <gwenhywfar/endpoint_tcpc.h>
|
|
#include <gwenhywfar/endpoint_multilayer.h>
|
|
#include <gwenhywfar/debug.h>
|
|
|
|
|
|
#define AQH_MSG_ENDPOINT_IPCCLIENT_NAME "ipc-client"
|
|
|
|
|
|
|
|
/* ------------------------------------------------------------------------------------------------
|
|
* forward declarations
|
|
* ------------------------------------------------------------------------------------------------
|
|
*/
|
|
|
|
static int _startConnect(GWEN_MSG_ENDPOINT *ep, GWEN_MSG_ENDPOINT *epChild);
|
|
static void _checkSockets(GWEN_MSG_ENDPOINT *ep,
|
|
GWEN_MSG_ENDPOINT *epChild,
|
|
GWEN_SOCKETSET *readSet,
|
|
GWEN_SOCKETSET *writeSet,
|
|
GWEN_SOCKETSET *xSet);
|
|
|
|
|
|
|
|
/* ------------------------------------------------------------------------------------------------
|
|
* implementations
|
|
* ------------------------------------------------------------------------------------------------
|
|
*/
|
|
|
|
GWEN_MSG_ENDPOINT *AQH_ClientIpcEndpoint_new(const char *name, int groupId)
|
|
{
|
|
GWEN_MSG_ENDPOINT *ep;
|
|
|
|
ep=GWEN_MultilayerEndpoint_new(name?name:AQH_MSG_ENDPOINT_IPCCLIENT_NAME, groupId);
|
|
GWEN_MultilayerEndpoint_SetStartConnectFn(ep, _startConnect);
|
|
GWEN_MultilayerEndpoint_SetCheckSocketsFn(ep, _checkSockets);
|
|
|
|
return ep;
|
|
}
|
|
|
|
|
|
|
|
int _startConnect(GWEN_MSG_ENDPOINT *ep, GWEN_MSG_ENDPOINT *epChild)
|
|
{
|
|
if (epChild) {
|
|
int rv;
|
|
GWEN_MSG *msg;
|
|
uint32_t flagsForConnectMsg;
|
|
|
|
flagsForConnectMsg=(GWEN_MsgEndpoint_GetFlags(ep) & AQH_ENDPOINT_IPCCLIENT_FLAGS_WANTUPDATES)?AQH_IPCENDPOINT_FLAGS_WANTUPDATES:0;
|
|
|
|
rv=GWEN_TcpcEndpoint_StartConnect(epChild);
|
|
if (rv<0 && rv!=GWEN_ERROR_IN_PROGRESS) {
|
|
DBG_INFO(AQH_LOGDOMAIN, "Error starting to connect child layer (%d)", rv);
|
|
return rv;
|
|
}
|
|
msg=AQH_ConnectDataIpcMsg_new(AQH_MSGTYPE_IPC_DATA_CONNECT_REQ,
|
|
AQH_IpcEndpoint_GetServiceName(epChild),
|
|
AQH_IpcEndpoint_GetUserName(epChild),
|
|
AQH_IpcEndpoint_GetPassword(epChild),
|
|
flagsForConnectMsg);
|
|
GWEN_MsgEndpoint_AddSendMessage(epChild, msg);
|
|
GWEN_MsgEndpoint_SetState(ep, GWEN_MSG_ENDPOINT_STATE_CONNECTING);
|
|
return rv; /* result from GWEN_TcpcEndpoint_StartConnect() above */
|
|
}
|
|
return GWEN_ERROR_GENERIC;
|
|
}
|
|
|
|
|
|
|
|
void _checkSockets(GWEN_MSG_ENDPOINT *ep,
|
|
GWEN_MSG_ENDPOINT *epChild,
|
|
GWEN_SOCKETSET *readSet,
|
|
GWEN_SOCKETSET *writeSet,
|
|
GWEN_SOCKETSET *xSet)
|
|
{
|
|
GWEN_MSG *msg;
|
|
|
|
GWEN_MsgEndpoint_CheckSockets(epChild, readSet, writeSet, xSet); /* let base layer work */
|
|
|
|
msg=GWEN_MsgEndpoint_GetFirstReceivedMessage(epChild);
|
|
while(msg) {
|
|
GWEN_MSG *msgNext;
|
|
uint16_t code;
|
|
|
|
msgNext=GWEN_Msg_List_Next(msg);
|
|
code=GWEN_IpcMsg_GetCode(msg);
|
|
if (code==AQH_MSGTYPE_IPC_DATA_RESULT) {
|
|
uint32_t resultCode;
|
|
|
|
GWEN_Msg_List_Del(msg); /* remove from list */
|
|
resultCode=AQH_ResultIpcMsg_GetResultCode(msg);
|
|
if (resultCode==AQH_MSG_IPC_SUCCESS) {
|
|
DBG_INFO(AQH_LOGDOMAIN, "Positive CONNECT response, connected");
|
|
GWEN_MsgEndpoint_SetState(ep, GWEN_MSG_ENDPOINT_STATE_CONNECTED);
|
|
}
|
|
else {
|
|
DBG_ERROR(AQH_LOGDOMAIN, "Negative CONNECT response (%d)", code);
|
|
GWEN_MsgEndpoint_Disconnect(epChild);
|
|
GWEN_MsgEndpoint_Disconnect(ep);
|
|
}
|
|
GWEN_Msg_free(msg);
|
|
break;
|
|
}
|
|
else {
|
|
DBG_ERROR(AQH_LOGDOMAIN, "Ignoring response (%u)", code);
|
|
GWEN_Msg_free(msg);
|
|
}
|
|
msg=msgNext;
|
|
} /* while */
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|