Rabbit Remote Control 0.1.0-bate8
Loading...
Searching...
No Matches
OperateTelnet.cpp
1// Author: Kang Lin <kl222@126.com>
2
3#include <QLoggingCategory>
4#include <QAbstractSocket>
5#include <QRegularExpression>
6
7#include "OperateTelnet.h"
8#include "DlgSettingsTelnet.h"
9#include "Plugin.h"
10
11static Q_LOGGING_CATEGORY(log, "Plugin.Telnet")
12
14 : COperateTerminal(parent)
15 , m_Telnet(QTelnet::TCP)
16 , m_bLogin(false)
17{
18 qDebug(log) << Q_FUNC_INFO;
19 auto &net = m_Parameters.m_Net;
20 net.SetPort(23);
21 QList<CParameterUser::TYPE> lstType;
22 lstType << CParameterUser::TYPE::UserPassword;
23 net.m_User.SetType(lstType);
24 SetParameter(&m_Parameters);
25}
26
27COperateTelnet::~COperateTelnet()
28{
29 qDebug(log) << Q_FUNC_INFO;
30}
31
32QDialog *COperateTelnet::OnOpenDialogSettings(QWidget *parent)
33{
34 return new CDlgSettingsTelnet(&m_Parameters, parent);
35}
36
38{
39 return nullptr;
40}
41
42int COperateTelnet::Start()
43{
44 if(!m_pTerminal)
45 return -1;
46
47 slotUpdateParameter(this);
48
49 slotSetSecurityLevel(CSecurityLevel::Level::Risk);
50
51 bool check = false;
52 check = connect(&m_Telnet, &QTelnet::stateChanged,
53 this, [=](QAbstractSocket::SocketState socketState){
54 if(socketState == QAbstractSocket::ConnectedState) {
55 emit sigRunning();
56 } else if(socketState == QAbstractSocket::UnconnectedState) {
57 emit sigStop();
58 }
59 });
60 Q_ASSERT(check);
61 check = connect(&m_Telnet, &QTelnet::error,
62 this, [=](QAbstractSocket::SocketError err){
63 QString szErr = tr("Telnet error:\n%1.").arg(m_Telnet.errorString());
64 emit sigError(err, szErr);
65 emit sigStop();
66 });
67 Q_ASSERT(check);
68 check = connect(&m_Telnet, SIGNAL(newData(const char*, int)),
69 this, SLOT(slotNewData(const char*, int)));
70 Q_ASSERT(check);
71 check = connect(m_pTerminal, &QTermWidget::sendData,
72 this, [&](const char* buf, int len){
73 QByteArray data(buf, len);
74 //qDebug(log) << "Send data:" << data << data.toHex(':');
75 m_Telnet.sendData(data);
76 if(GetStats())
77 GetStats()->AddSends(len);
78 });
79 Q_ASSERT(check);
80 check = connect(&m_Telnet, SIGNAL(stateChanged(QAbstractSocket::SocketState)),
81 this, SLOT(slotStateChanged(QAbstractSocket::SocketState)));
82 Q_ASSERT(check);
83
84 auto &net = m_Parameters.m_Net;
85 m_Telnet.setCustomCR();
86 m_Telnet.connectToHost(net.GetHost(), net.GetPort());
87
88 m_pTerminal->startTerminalTeletype();
89
90 emit sigRunning();
91 return 0;
92}
93
94int COperateTelnet::Stop()
95{
96 if(m_pTerminal)
97 m_pTerminal->close();
98
99 m_Telnet.disconnectFromHost();
100 emit sigFinished();
101 return 0;
102}
103
104void COperateTelnet::slotStateChanged(QAbstractSocket::SocketState state)
105{
106 switch( state )
107 {
108 case QAbstractSocket::UnconnectedState:
109 qDebug(log) << tr("Unconnected");
110 break;
111 case QAbstractSocket::HostLookupState:
112 qDebug(log) << tr("Resolve DNS %1").arg(m_Telnet.peerName());
113 break;
114 case QAbstractSocket::ConnectingState:
115 qDebug(log) << tr("Connecting a %1").arg(m_Telnet.peerInfo());
116 break;
117 case QAbstractSocket::ConnectedState:
118 qDebug(log) << tr("Connected a %1").arg(m_Telnet.peerInfo());
119 break;
120 case QAbstractSocket::BoundState:
121 qDebug(log) << tr("Bound");
122 break;
123 case QAbstractSocket::ListeningState:
124 qDebug(log) << tr("Listening");
125 break;
126 case QAbstractSocket::ClosingState:
127 qDebug(log) << tr("Close");
128 break;
129 }
130}
131
132const QString COperateTelnet::Id()
133{
134 QString szId = COperate::Id();
135 if(GetParameter()) {
136 if(GetParameter()->GetName().isEmpty()) {
137 auto &net = m_Parameters.m_Net;
138 if(!net.GetHost().isEmpty())
139 szId += "_" + net.GetHost()
140 + "_" + QString::number(net.GetPort());
141 } else
142 szId += "_" + GetParameter()->GetName();
143 }
144 static QRegularExpression exp("[-@:/#%!^&* \\.]");
145 szId = szId.replace(exp, "_");
146 return szId;
147}
148
149const QString COperateTelnet::Name()
150{
151 QString szName = m_Parameters.GetName();
152 if(szName.isEmpty()) {
153 auto &net = m_Parameters.m_Net;
154 if(!net.GetHost().isEmpty()) {
155 if(m_Parameters.GetGlobalParameters()
156 && (m_Parameters.GetGlobalParameters()->GetNameStyles()
157 & CParameterPlugin::NameStyle::Protocol)
158 && !Protocol().isEmpty())
159 szName = Protocol() + ":";
160 szName += net.GetHost()
161 + ":" + QString::number(net.GetPort());
162 }
163 }
164 if(szName.isEmpty())
165 szName = COperateTerminal::Name();
166
167 QString szSecurityLevel;
169 if(m_Parameters.GetGlobalParameters()
170 && (m_Parameters.GetGlobalParameters()->GetNameStyles()
171 & CParameterPlugin::NameStyle::SecurityLevel)
172 && !(GetSecurityLevel() & CSecurityLevel::Level::No)
173 && !sl.GetUnicodeIcon().isEmpty())
174 szSecurityLevel = sl.GetUnicodeIcon().left(2);
175
176 return szSecurityLevel + szName;
177}
178
180{
181 QString szDescription;
182 if(!Name().isEmpty())
183 szDescription = tr("Name: ") + Name() + "\n";
184
185 if(!GetTypeName().isEmpty())
186 szDescription += tr("Type: ") + GetTypeName() + "\n";
187
188 if(!Protocol().isEmpty()) {
189 szDescription += tr("Protocol: ") + Protocol();
190#ifdef DEBUG
191 if(!GetPlugin()->DisplayName().isEmpty())
192 szDescription += " - " + GetPlugin()->DisplayName();
193#endif
194 szDescription += "\n";
195 }
196
197 auto &net = m_Parameters.m_Net;
198 if(!net.GetHost().isEmpty())
199 szDescription += tr("Server address: ") + net.GetHost()
200 + ":" + QString::number(net.GetPort()) + "\n";
201
203 if(!(GetSecurityLevel() & CSecurityLevel::Level::No)) {
204 szDescription += tr("Security level: ");
205 if(!sl.GetUnicodeIcon().isEmpty())
206 szDescription += sl.GetUnicodeIcon() + " ";
207 szDescription += sl.GetString() + "\n";
208 }
209
210 if(!GetPlugin()->Description().isEmpty())
211 szDescription += tr("Description: ") + GetPlugin()->Description();
212
213 return szDescription;
214}
215
216void COperateTelnet::slotNewData(const char *buf, int len)
217{
218 //QByteArray data(buf, len);
219 //qDebug(log) << "Receive data:" << data << data.toHex(':');
220 WriteTerminal(buf, len);
221
222 if(GetStats())
223 GetStats()->AddReceives(len);
224
225 if(!m_bLogin) {
226 QRegularExpression reLogin(m_Parameters.GetLogin(), QRegularExpression::CaseInsensitiveOption);
227 QRegularExpressionMatch match = reLogin.match(QByteArray(buf, len));
228 bool bLogin = match.hasMatch();
229 if(bLogin) {
230 QString user = m_Parameters.m_Net.m_User.GetUser();
231 if(!user.isEmpty()) {
232 m_Telnet.sendData(user.toStdString().c_str(), user.length());
233 m_Telnet.sendData("\n", 1);
234 }
235 qDebug(log) << "User:" << user;
236 }
237 QRegularExpression rePassword(m_Parameters.GetPassword(), QRegularExpression::CaseInsensitiveOption);
238 match = rePassword.match(QByteArray(buf, len));
239 bool bPassword = match.hasMatch();
240 if(bPassword) {
241 QString password = m_Parameters.m_Net.m_User.GetPassword();
242 if(!password.isEmpty()) {
243 m_Telnet.sendData(password.toStdString().c_str(), password.length());
244 m_Telnet.sendData("\n", 1);
245 m_bLogin = true;
246 slotSetSecurityLevel(CSecurityLevel::Level::Authentication);
247 }
248 qDebug(log) << "Password:" << password;
249
250 if(!m_Parameters.GetCommands().isEmpty()) {
251 foreach (auto c, m_Parameters.GetCommands()) {
252 m_Telnet.sendData(c.toStdString().c_str(), c.length());
253 m_Telnet.sendData("\n", 1);
254 }
255 }
256 }
257 }
258}
259
Backend interface.
Definition Backend.h:42
virtual const QString Description() override
Description.
virtual const QString Name() override
Name.
virtual CBackend * InstanceBackend() override
New CBackend.
virtual QDialog * OnOpenDialogSettings(QWidget *parent) override
Open settgins dialog.
Terminal operate interface.
CStats * GetStats() override
Get statistics.
virtual const QString Name() override
Name.
virtual CParameterTerminalBase * GetParameter() const
Get parameters.
virtual CSecurityLevel::Levels GetSecurityLevel() const
Get Security Level.
Definition Operate.cpp:129
void sigFinished()
Successful disconnection signal.
void sigRunning()
Start success signal.
void sigError(const int nError, const QString &szError)
Triggered when an error is generated.
void sigStop()
Notify the user to stop.
Q_INVOKABLE CPlugin * GetPlugin() const
Get plugin.
Definition Operate.cpp:219
CParameterUser m_User
[Instance user]
CParameterPlugin * GetGlobalParameters()
Get CParameterPlugin.
QString GetPassword() const
Password Regular Expression.
QString GetLogin() const
Login Regular Expression.
Plugin interface.
Definition Plugin.h:15
virtual const QString DisplayName() const
The plugin display name.
Definition Plugin.cpp:76
virtual const QString Description() const =0
Plugin description.
Security level.
Definition Stats.h:79