mirror of
https://github.com/eclipse/paho.mqtt-sn.embedded-c.git
synced 2025-12-15 08:26:51 +01:00
Add ClientPool
Clients are created and kept in the pool at first. ClientList gets a free client from the pool. Signed-off-by: tomoaki <tomoaki@tomy-tech.com>
This commit is contained in:
@@ -32,14 +32,15 @@ char* currentDateTime(void);
|
|||||||
Class Client
|
Class Client
|
||||||
=====================================*/
|
=====================================*/
|
||||||
static const char* theClientStatus[] =
|
static const char* theClientStatus[] =
|
||||||
{ "Disconnected", "TryConnecting", "Connecting", "Active", "Asleep", "Awake",
|
{ "InPool", "Disconnected", "TryConnecting", "Connecting", "Active", "Asleep",
|
||||||
|
"Awake",
|
||||||
"Lost" };
|
"Lost" };
|
||||||
|
|
||||||
Client::Client(bool secure)
|
Client::Client(bool secure)
|
||||||
{
|
{
|
||||||
_packetId = 0;
|
_packetId = 0;
|
||||||
_snMsgId = 0;
|
_snMsgId = 0;
|
||||||
_status = Cstat_Disconnected;
|
_status = Cstat_Free;
|
||||||
_keepAliveMsec = 0;
|
_keepAliveMsec = 0;
|
||||||
_topics = new Topics();
|
_topics = new Topics();
|
||||||
_clientId = nullptr;
|
_clientId = nullptr;
|
||||||
|
|||||||
@@ -152,7 +152,8 @@ private:
|
|||||||
=====================================*/
|
=====================================*/
|
||||||
typedef enum
|
typedef enum
|
||||||
{
|
{
|
||||||
Cstat_Disconnected = 0,
|
Cstat_Free = 0,
|
||||||
|
Cstat_Disconnected,
|
||||||
Cstat_TryConnecting,
|
Cstat_TryConnecting,
|
||||||
Cstat_Connecting,
|
Cstat_Connecting,
|
||||||
Cstat_Active,
|
Cstat_Active,
|
||||||
@@ -176,6 +177,7 @@ class Forwarder;
|
|||||||
class Client
|
class Client
|
||||||
{
|
{
|
||||||
friend class ClientList;
|
friend class ClientList;
|
||||||
|
friend class ClientsPool;
|
||||||
public:
|
public:
|
||||||
Client(bool secure = false);
|
Client(bool secure = false);
|
||||||
Client(uint8_t maxInflightMessages, bool secure);
|
Client(uint8_t maxInflightMessages, bool secure);
|
||||||
|
|||||||
@@ -20,18 +20,20 @@
|
|||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
using namespace MQTTSNGW;
|
using namespace MQTTSNGW;
|
||||||
extern Gateway* theGateway;
|
char* currentDateTime(void);
|
||||||
/*=====================================
|
/*=====================================
|
||||||
Class ClientList
|
Class ClientList
|
||||||
=====================================*/
|
=====================================*/
|
||||||
const char* common_topic = "*";
|
const char* common_topic = "*";
|
||||||
|
|
||||||
ClientList::ClientList()
|
ClientList::ClientList(Gateway* gw)
|
||||||
{
|
{
|
||||||
_clientCnt = 0;
|
_clientCnt = 0;
|
||||||
_authorize = false;
|
_authorize = false;
|
||||||
_firstClient = nullptr;
|
_firstClient = nullptr;
|
||||||
_endClient = nullptr;
|
_endClient = nullptr;
|
||||||
|
_clientsPool = new ClientsPool();
|
||||||
|
_gateway = gw;
|
||||||
}
|
}
|
||||||
|
|
||||||
ClientList::~ClientList()
|
ClientList::~ClientList()
|
||||||
@@ -46,12 +48,19 @@ ClientList::~ClientList()
|
|||||||
delete cl;
|
delete cl;
|
||||||
cl = ncl;
|
cl = ncl;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (_clientsPool)
|
||||||
|
{
|
||||||
|
delete _clientsPool;
|
||||||
|
}
|
||||||
_mutex.unlock();
|
_mutex.unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
void ClientList::initialize(bool aggregate)
|
void ClientList::initialize(bool aggregate)
|
||||||
{
|
{
|
||||||
if (theGateway->getGWParams()->clientAuthentication)
|
_clientsPool->allocate(_gateway->getGWParams()->maxClients);
|
||||||
|
|
||||||
|
if (_gateway->getGWParams()->clientAuthentication)
|
||||||
{
|
{
|
||||||
int type = TRANSPEARENT_TYPE;
|
int type = TRANSPEARENT_TYPE;
|
||||||
if (aggregate)
|
if (aggregate)
|
||||||
@@ -62,7 +71,7 @@ void ClientList::initialize(bool aggregate)
|
|||||||
_authorize = true;
|
_authorize = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (theGateway->getGWParams()->predefinedTopic)
|
if (_gateway->getGWParams()->predefinedTopic)
|
||||||
{
|
{
|
||||||
setPredefinedTopics(aggregate);
|
setPredefinedTopics(aggregate);
|
||||||
}
|
}
|
||||||
@@ -70,20 +79,21 @@ void ClientList::initialize(bool aggregate)
|
|||||||
|
|
||||||
void ClientList::setClientList(int type)
|
void ClientList::setClientList(int type)
|
||||||
{
|
{
|
||||||
if (!createList(theGateway->getGWParams()->clientListName, type))
|
if (!createList(_gateway->getGWParams()->clientListName, type))
|
||||||
{
|
{
|
||||||
throw EXCEPTION(
|
throw EXCEPTION(
|
||||||
"ClientList::setClientList No client list defined by config file.", 0);
|
"ClientList::setClientList Client list not found!", 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ClientList::setPredefinedTopics(bool aggrecate)
|
void ClientList::setPredefinedTopics(bool aggrecate)
|
||||||
{
|
{
|
||||||
if (!readPredefinedList(theGateway->getGWParams()->predefinedTopicFileName,
|
if (!readPredefinedList(_gateway->getGWParams()->predefinedTopicFileName,
|
||||||
aggrecate))
|
aggrecate))
|
||||||
{
|
{
|
||||||
throw EXCEPTION(
|
throw EXCEPTION(
|
||||||
"ClientList::setPredefinedTopics No predefindTopi list defined by config file.",0);
|
"ClientList::setPredefinedTopics PredefindTopic list not found!",
|
||||||
|
0);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -158,7 +168,7 @@ bool ClientList::createList(const char* fileName, int type)
|
|||||||
}
|
}
|
||||||
else if (forwarder && type == FORWARDER_TYPE)
|
else if (forwarder && type == FORWARDER_TYPE)
|
||||||
{
|
{
|
||||||
theGateway->getAdapterManager()->getForwarderList()->addForwarder(
|
_gateway->getAdapterManager()->getForwarderList()->addForwarder(
|
||||||
&netAddr, &clientId);
|
&netAddr, &clientId);
|
||||||
}
|
}
|
||||||
else if (type == TRANSPEARENT_TYPE)
|
else if (type == TRANSPEARENT_TYPE)
|
||||||
@@ -338,22 +348,23 @@ Client* ClientList::createClient(SensorNetAddress* addr, MQTTSNString* clientId,
|
|||||||
Client* ClientList::createClient(SensorNetAddress* addr, MQTTSNString* clientId,
|
Client* ClientList::createClient(SensorNetAddress* addr, MQTTSNString* clientId,
|
||||||
bool unstableLine, bool secure, int type)
|
bool unstableLine, bool secure, int type)
|
||||||
{
|
{
|
||||||
Client* client = nullptr;
|
Client* client = getClient(addr);
|
||||||
|
|
||||||
/* anonimous clients */
|
|
||||||
if (_clientCnt > MAX_CLIENTS)
|
|
||||||
{
|
|
||||||
return 0; // full of clients
|
|
||||||
}
|
|
||||||
|
|
||||||
client = getClient(addr);
|
|
||||||
if (client)
|
if (client)
|
||||||
{
|
{
|
||||||
return client;
|
return client;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* creat a new client */
|
/* acquire a free client */
|
||||||
client = new Client(secure);
|
client = _clientsPool->getClient();
|
||||||
|
|
||||||
|
if (!client)
|
||||||
|
{
|
||||||
|
WRITELOG("%s%sMax number of Clients%s\n", currentDateTime(),
|
||||||
|
ERRMSG_HEADER, ERRMSG_FOOTER);
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
client->disconnected();
|
||||||
if (addr)
|
if (addr)
|
||||||
{
|
{
|
||||||
client->setClientAddress(addr);
|
client->setClientAddress(addr);
|
||||||
@@ -411,7 +422,7 @@ Client* ClientList::createPredefinedTopic(MQTTSNString* clientId,
|
|||||||
|
|
||||||
if (strcmp(clientId->cstring, common_topic) == 0)
|
if (strcmp(clientId->cstring, common_topic) == 0)
|
||||||
{
|
{
|
||||||
theGateway->getTopics()->add((const char*) topicName.c_str(), topicId);
|
_gateway->getTopics()->add((const char*) topicName.c_str(), topicId);
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -473,3 +484,69 @@ bool ClientList::isAuthorized()
|
|||||||
return _authorize;
|
return _authorize;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/******************************
|
||||||
|
* Class ClientsPool
|
||||||
|
******************************/
|
||||||
|
|
||||||
|
ClientsPool::ClientsPool()
|
||||||
|
{
|
||||||
|
_clientCnt = 0;
|
||||||
|
_firstClient = nullptr;
|
||||||
|
_endClient = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
ClientsPool::~ClientsPool()
|
||||||
|
{
|
||||||
|
Client* cl = _firstClient;
|
||||||
|
Client* ncl;
|
||||||
|
|
||||||
|
while (cl != nullptr)
|
||||||
|
{
|
||||||
|
ncl = cl->_nextClient;
|
||||||
|
delete cl;
|
||||||
|
cl = ncl;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
void ClientsPool::allocate(int maxClients)
|
||||||
|
{
|
||||||
|
Client* cl = nullptr;
|
||||||
|
|
||||||
|
_firstClient = new Client();
|
||||||
|
|
||||||
|
for (int i = 0; i < maxClients; i++)
|
||||||
|
{
|
||||||
|
if ((cl = new Client()) == nullptr)
|
||||||
|
{
|
||||||
|
throw Exception(
|
||||||
|
"ClientsPool::Can't allocate max number of clients\n", 0);
|
||||||
|
}
|
||||||
|
cl->_nextClient = _firstClient;
|
||||||
|
_firstClient = cl;
|
||||||
|
_clientCnt++;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
Client* ClientsPool::getClient(void)
|
||||||
|
{
|
||||||
|
while (_firstClient != nullptr)
|
||||||
|
{
|
||||||
|
Client* cl = _firstClient;
|
||||||
|
_firstClient = cl->_nextClient;
|
||||||
|
cl->_nextClient = nullptr;
|
||||||
|
_clientCnt--;
|
||||||
|
return cl;
|
||||||
|
}
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ClientsPool::setClient(Client* client)
|
||||||
|
{
|
||||||
|
if (client)
|
||||||
|
{
|
||||||
|
client->_nextClient = _firstClient;
|
||||||
|
_firstClient = client;
|
||||||
|
_clientCnt++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -30,13 +30,31 @@ namespace MQTTSNGW
|
|||||||
|
|
||||||
class Client;
|
class Client;
|
||||||
|
|
||||||
|
/*=====================================
|
||||||
|
Class ClientsPool
|
||||||
|
=====================================*/
|
||||||
|
class ClientsPool
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
ClientsPool();
|
||||||
|
~ClientsPool();
|
||||||
|
void allocate(int maxClients);
|
||||||
|
Client* getClient(void);
|
||||||
|
void setClient(Client* client);
|
||||||
|
|
||||||
|
private:
|
||||||
|
Client* _firstClient;
|
||||||
|
Client* _endClient;
|
||||||
|
int _clientCnt;
|
||||||
|
};
|
||||||
|
|
||||||
/*=====================================
|
/*=====================================
|
||||||
Class ClientList
|
Class ClientList
|
||||||
=====================================*/
|
=====================================*/
|
||||||
class ClientList
|
class ClientList
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
ClientList();
|
ClientList(Gateway* gw);
|
||||||
~ClientList();
|
~ClientList();
|
||||||
|
|
||||||
void initialize(bool aggregate);
|
void initialize(bool aggregate);
|
||||||
@@ -57,7 +75,8 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
bool readPredefinedList(const char* fileName, bool _aggregate);
|
bool readPredefinedList(const char* fileName, bool _aggregate);
|
||||||
Gateway* _gateway { nullptr };
|
ClientsPool* _clientsPool;
|
||||||
|
Gateway* _gateway;
|
||||||
Client* createPredefinedTopic(MQTTSNString* clientId, string topicName,
|
Client* createPredefinedTopic(MQTTSNString* clientId, string topicName,
|
||||||
uint16_t toipcId, bool _aggregate);
|
uint16_t toipcId, bool _aggregate);
|
||||||
Client* _firstClient;
|
Client* _firstClient;
|
||||||
|
|||||||
Reference in New Issue
Block a user