#include <iostream>
#include <map>
#include <functional>
#include <memory>
using namespace std;
using namespace std::placeholders;
#define REGISTER_CONNECTOR(map, connector, id) \
{ \
ConnectorFunc connectorFunc = {}; \
connectorFunc.openFunc = std::bind(&decltype(connector)::open, connector); \
connectorFunc.recvFunc = std::bind(&decltype(connector)::recv, connector, _1, _2); \
connectorFunc.sendFunc = std::bind(&decltype(connector)::send, connector, _1, _2); \
connectorFunc.closeFunc = std::bind(&decltype(connector)::close, connector); \
map.insert(std::make_pair(id, connectorFunc)); \
}
#define GET_CONNECTOR_FUNC(map, id, connectorFunc) \
{ \
auto iter = funcMap.find(type); \
if(iter != funcMap.end()) \
{ \
connectorFunc = iter->second; \
} \
}
typedef void (OPEN_FUNC)();
typedef size_t (RECV_FUNC)(void*, size_t);
typedef void (SEND_FUNC)(void*, size_t);
typedef void (CLOSE_FUNC)();
struct ConnectorFunc
{
std::function<OPEN_FUNC> openFunc;
std::function<RECV_FUNC> recvFunc;
std::function<SEND_FUNC> sendFunc;
std::function<CLOSE_FUNC> closeFunc;
};
typedef enum { TCP, SERIAL, CONNECT_COUNT} CONNECT_TYPE;
// Define interface
class IConnector
{
public:
virtual void open() = 0;
virtual size_t recv(void* buffer, size_t size) = 0;
virtual void send(void* buffer, size_t size) = 0;
virtual void close() = 0;
};
// Define CSerial
class CSerial /*: public IConnector*/ // From 3rd?
{
public:
void open();
size_t recv(void* buffer, size_t size);
void send(void* buffer, size_t size);
void close();
};
// Define CTcp
class CTcp /*: public IConnector*/ // From 3rd?
{
public:
void open();
size_t recv(void* buffer, size_t size);
void send(void* buffer, size_t size);
void close();
};
// Define CConnector
class CConnector: public IConnector
{
public:
CConnector();
void open();
size_t recv(void* buffer, size_t size);
void send(void* buffer, size_t size);
void close();
void setType(CONNECT_TYPE type);
private:
CONNECT_TYPE mType;
CTcp mTcp;
CSerial mSerial;
std::map<CONNECT_TYPE, ConnectorFunc> funcMap;
ConnectorFunc connectorFunc;
};
// Implement CSerial
void CSerial::open()
{
cout << "CSerial::" << __func__ << endl;
}
size_t CSerial::recv(void* buffer, size_t size)
{
cout << "CSerial::" << __func__ << endl;
return 0;
}
void CSerial::send(void* buffer, size_t size)
{
cout << "CSerial::" << __func__ << endl;
}
void CSerial::close()
{
cout << "CSerial::" << __func__ << endl;
}
// Implement CTcp
void CTcp::open()
{
cout << "CTcp::" << __func__ << endl;
}
size_t CTcp::recv(void* buffer, size_t size)
{
cout << "CTcp::" << __func__ << endl;
return 0;
}
void CTcp::send(void* buffer, size_t size)
{
cout << "CTcp::" << __func__ << endl;
}
void CTcp::close()
{
cout << "CTcp::" << __func__ << endl;
}
// Implement CConnector
CConnector::CConnector(): mType(CONNECT_TYPE::TCP), mTcp(), mSerial(), connectorFunc()
{
REGISTER_CONNECTOR(funcMap, mTcp, CONNECT_TYPE::TCP);
REGISTER_CONNECTOR(funcMap, mSerial, CONNECT_TYPE::SERIAL);
}
void CConnector::open()
{
if(connectorFunc.openFunc != NULL)
connectorFunc.openFunc();
}
size_t CConnector::recv(void* buffer, size_t size)
{
if(connectorFunc.recvFunc != NULL)
return connectorFunc.recvFunc(buffer, size);
return -1;
}
void CConnector::send(void* buffer, size_t size)
{
if(connectorFunc.sendFunc != NULL)
connectorFunc.sendFunc(buffer, size);
}
void CConnector::close()
{
if(connectorFunc.closeFunc != NULL)
connectorFunc.closeFunc();
}
void CConnector::setType(CONNECT_TYPE type)
{
mType = type;
GET_CONNECTOR_FUNC(funcMap, type, connectorFunc);
}
void testTCP()
{
CConnector* conector = new CConnector();
conector->setType(CONNECT_TYPE::TCP);
conector->open();
conector->recv(NULL, 0);
conector->send(NULL, 0);
conector->close();
delete conector;
cout << endl;
}
void testSerial()
{
CConnector* conector = new CConnector();
conector->setType(CONNECT_TYPE::SERIAL);
conector->open();
conector->recv(NULL, 0);
conector->send(NULL, 0);
conector->close();
delete conector;
cout << endl;
}
int main(int argc, char* argv[])
{
testTCP();
testSerial();
return 0;
}