important:
* PIThread::~PIThread() now unregister itself from introspection, if terminates than show warning * PISystemMonitor now correctly stops * PIPeer now can correctly stopAndWait * PIPeer::destroy(), protected method for close all eths and threads * new PIINTROSPECTION_STOP macro * Introspection now can be correctly stopped by macro, more safety ClientServer: * ClientBase::close() stop and disconnect channel * Server clients clean-up now event-based * No warnings on client destructor
This commit is contained in:
@@ -18,13 +18,15 @@
|
||||
|
||||
#include "piclientserver_client.h"
|
||||
|
||||
#include "piclientserver_server.h"
|
||||
#include "piethernet.h"
|
||||
|
||||
|
||||
void PIClientServer::ServerClient::createForServer(PIEthernet * tcp_) {
|
||||
void PIClientServer::ServerClient::createForServer(Server * parent, PIEthernet * tcp_) {
|
||||
tcp = tcp_;
|
||||
tcp->setParameter(PIEthernet::KeepConnection, false);
|
||||
init();
|
||||
CONNECTL(tcp, disconnected, ([this, parent](bool) { parent->clientDisconnected(this); }));
|
||||
}
|
||||
|
||||
|
||||
@@ -37,13 +39,14 @@ PIClientServer::Client::Client() {
|
||||
|
||||
|
||||
PIClientServer::Client::~Client() {
|
||||
stop();
|
||||
if (tcp) tcp->setDebug(false);
|
||||
close();
|
||||
}
|
||||
|
||||
|
||||
void PIClientServer::Client::connect(PINetworkAddress addr) {
|
||||
if (!tcp || !own_tcp) return;
|
||||
stop();
|
||||
close();
|
||||
tcp->connect(addr, true);
|
||||
tcp->startThreadedRead();
|
||||
piCout << "Connect to" << addr.toString();
|
||||
|
||||
@@ -26,17 +26,18 @@ PIClientServer::ClientBase::ClientBase() {}
|
||||
|
||||
|
||||
PIClientServer::ClientBase::~ClientBase() {
|
||||
stop();
|
||||
close();
|
||||
if (own_tcp) piDeleteSafety(tcp);
|
||||
}
|
||||
|
||||
|
||||
void PIClientServer::ClientBase::stop() {
|
||||
void PIClientServer::ClientBase::close() {
|
||||
if (!tcp) return;
|
||||
can_write = false;
|
||||
tcp->interrupt();
|
||||
tcp->stopAndWait(10_s);
|
||||
if (tcp->isThreadedRead()) tcp->terminateThreadedRead();
|
||||
tcp->close();
|
||||
stream.clear();
|
||||
}
|
||||
|
||||
|
||||
@@ -39,36 +39,37 @@ PIClientServer::Server::Server() {
|
||||
piCout << "ClientFactory returns nullptr!";
|
||||
return;
|
||||
}
|
||||
sc->createForServer(c);
|
||||
sc->createForServer(this, c);
|
||||
newClient(sc);
|
||||
});
|
||||
|
||||
clean_thread->start(
|
||||
[this]() {
|
||||
PIVector<ServerClient *> to_delete;
|
||||
clients_mutex.lock();
|
||||
for (auto c: clients) {
|
||||
const PIEthernet * eth = c->getTCP();
|
||||
if (!eth) continue;
|
||||
if (eth->isConnected()) continue;
|
||||
c->can_write = false;
|
||||
to_delete << c;
|
||||
}
|
||||
for (auto c: to_delete)
|
||||
clients.removeOne(c);
|
||||
clients_mutex.unlock();
|
||||
for (auto c: to_delete) {
|
||||
c->aboutDelete();
|
||||
c->destroy();
|
||||
delete c;
|
||||
}
|
||||
},
|
||||
5_Hz);
|
||||
clean_thread->start([this]() {
|
||||
clean_notifier.wait();
|
||||
PIVector<ServerClient *> to_delete;
|
||||
clients_mutex.lock();
|
||||
for (auto c: clients) {
|
||||
const PIEthernet * eth = c->getTCP();
|
||||
if (!eth) continue;
|
||||
if (eth->isConnected()) continue;
|
||||
c->can_write = false;
|
||||
to_delete << c;
|
||||
}
|
||||
for (auto c: to_delete)
|
||||
clients.removeOne(c);
|
||||
clients_mutex.unlock();
|
||||
for (auto c: to_delete) {
|
||||
c->aboutDelete();
|
||||
c->destroy();
|
||||
delete c;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
PIClientServer::Server::~Server() {
|
||||
clean_thread->stopAndWait();
|
||||
clean_thread->stop();
|
||||
clean_notifier.notify();
|
||||
clean_thread->waitForFinish();
|
||||
piDeleteSafety(clean_thread);
|
||||
stopServer();
|
||||
for (auto c: clients) {
|
||||
@@ -129,3 +130,8 @@ void PIClientServer::Server::newClient(ServerClient * c) {
|
||||
c->connected();
|
||||
piCout << "New client";
|
||||
}
|
||||
|
||||
|
||||
void PIClientServer::Server::clientDisconnected(ServerClient * c) {
|
||||
clean_notifier.notify();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user