NOX: ICMP - Separated protocol and widget as per new framework

This commit is contained in:
Srivats P. 2014-04-17 07:10:13 +05:30
parent bbe645725a
commit 30c70a73e4
9 changed files with 356 additions and 240 deletions

View File

@ -17,165 +17,16 @@ You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>
*/
#include "icmp.h"
#include <QSet>
#include <qendian.h>
enum IcmpType
{
kIcmpEchoReply = 0,
kIcmpDestinationUnreachable = 3,
kIcmpSourceQuench = 4,
kIcmpRedirect = 5,
kIcmpEchoRequest = 8,
kIcmpTimeExceeded = 11,
kIcmpParameterProblem = 12,
kIcmpTimestampRequest = 13,
kIcmpTimestampReply = 14,
kIcmpInformationRequest = 15,
kIcmpInformationReply = 16,
kIcmpAddressMaskRequest = 17,
kIcmpAddressMaskReply = 18
};
enum Icmp6Type
{
kIcmp6DestinationUnreachable = 1,
kIcmp6PacketTooBig = 2,
kIcmp6TimeExceeded = 3,
kIcmp6ParameterProblem = 4,
kIcmp6EchoRequest = 128,
kIcmp6EchoReply = 129,
kIcmp6RouterSolicitation = 133,
kIcmp6RouterAdvertisement = 134,
kIcmp6NeighbourSolicitation = 135,
kIcmp6NeighbourAdvertisement = 136,
kIcmp6Redirect = 137,
kIcmp6InformationQuery = 139,
kIcmp6InformationResponse = 140
};
static QSet<int> icmpIdSeqSet = QSet<int>()
<< kIcmpEchoRequest
<< kIcmpEchoReply
<< kIcmpInformationRequest
<< kIcmpInformationReply;
static QSet<int> icmp6IdSeqSet = QSet<int>()
<< kIcmp6EchoRequest
<< kIcmp6EchoReply;
static bool isIdSeqType(OstProto::Icmp::Version ver, int type)
{
//qDebug("%s: ver = %d, type = %d", __FUNCTION__, ver, type);
switch(ver)
{
case OstProto::Icmp::kIcmp4:
return icmpIdSeqSet.contains(type);
case OstProto::Icmp::kIcmp6:
return icmp6IdSeqSet.contains(type);
default:
break;
}
Q_ASSERT(false); // unreachable
return false;
}
IcmpConfigForm::IcmpConfigForm(QWidget *parent)
: QWidget(parent)
{
versionGroup = new QButtonGroup(this);
setupUi(this);
// auto-connect's not working, for some reason I can't figure out!
// slot name changed to when_ instead of on_ so that connectSlotsByName()
// doesn't complain
connect(versionGroup,
SIGNAL(buttonClicked(int)),
SLOT(when_versionGroup_buttonClicked(int)));
versionGroup->addButton(icmp4Button, OstProto::Icmp::kIcmp4);
versionGroup->addButton(icmp6Button, OstProto::Icmp::kIcmp6);
typeCombo->setValidator(new QIntValidator(0, 0xFF, this));
icmp4Button->click();
idEdit->setValidator(new QIntValidator(0, 0xFFFF, this));
seqEdit->setValidator(new QIntValidator(0, 0xFFFF, this));
}
void IcmpConfigForm::on_typeCombo_currentIndexChanged(int /*index*/)
{
idSeqFrame->setVisible(
isIdSeqType(
OstProto::Icmp::Version(versionGroup->checkedId()),
typeCombo->currentValue()));
}
void IcmpConfigForm::when_versionGroup_buttonClicked(int id)
{
int value = typeCombo->currentValue();
typeCombo->clear();
switch(id)
{
case OstProto::Icmp::kIcmp4:
typeCombo->addItem(kIcmpEchoReply, "Echo Reply");
typeCombo->addItem(kIcmpDestinationUnreachable,
"Destination Unreachable");
typeCombo->addItem(kIcmpSourceQuench, "Source Quench");
typeCombo->addItem(kIcmpRedirect, "Redirect");
typeCombo->addItem(kIcmpEchoRequest, "Echo Request");
typeCombo->addItem(kIcmpTimeExceeded, "Time Exceeded");
typeCombo->addItem(kIcmpParameterProblem, "Parameter Problem");
typeCombo->addItem(kIcmpTimestampRequest, "Timestamp Request");
typeCombo->addItem(kIcmpTimestampReply, "Timestamp Reply");
typeCombo->addItem(kIcmpInformationRequest, "Information Request");
typeCombo->addItem(kIcmpInformationReply, "Information Reply");
typeCombo->addItem(kIcmpAddressMaskRequest, "Address Mask Request");
typeCombo->addItem(kIcmpAddressMaskReply, "Address Mask Reply");
break;
case OstProto::Icmp::kIcmp6:
typeCombo->addItem(kIcmp6DestinationUnreachable,
"Destination Unreachable");
typeCombo->addItem(kIcmp6PacketTooBig, "Packet Too Big");
typeCombo->addItem(kIcmp6TimeExceeded, "Time Exceeded");
typeCombo->addItem(kIcmp6ParameterProblem, "Parameter Problem");
typeCombo->addItem(kIcmp6EchoRequest, "Echo Request");
typeCombo->addItem(kIcmp6EchoReply, "Echo Reply");
typeCombo->addItem(kIcmp6RouterSolicitation, "Router Solicitation");
typeCombo->addItem(kIcmp6RouterAdvertisement, "Router Advertisement");
typeCombo->addItem(kIcmp6NeighbourSolicitation,
"Neighbour Solicitation");
typeCombo->addItem(kIcmp6NeighbourAdvertisement,
"Neighbour Advertisement");
typeCombo->addItem(kIcmp6Redirect, "Redirect");
typeCombo->addItem(kIcmp6InformationQuery, "Information Query");
typeCombo->addItem(kIcmp6InformationResponse, "Information Response");
break;
default:
Q_ASSERT(false);
}
typeCombo->setValue(value);
}
#include "icmphelper.h"
IcmpProtocol::IcmpProtocol(StreamBase *stream, AbstractProtocol *parent)
: AbstractProtocol(stream, parent)
{
configForm = NULL;
}
IcmpProtocol::~IcmpProtocol()
{
delete configForm;
}
AbstractProtocol* IcmpProtocol::createInstance(StreamBase *stream,
@ -541,54 +392,5 @@ _exit:
return isOk;
}
QWidget* IcmpProtocol::configWidget()
{
if (configForm == NULL)
{
configForm = new IcmpConfigForm;
loadConfigWidget();
}
return configForm;
}
void IcmpProtocol::loadConfigWidget()
{
configWidget();
configForm->versionGroup->button(icmpVersion())->click();
configForm->typeCombo->setValue(fieldData(icmp_type, FieldValue).toUInt());
configForm->codeEdit->setText(fieldData(icmp_code, FieldValue).toString());
configForm->overrideCksum->setChecked(
fieldData(icmp_is_override_checksum, FieldValue).toBool());
configForm->cksumEdit->setText(uintToHexStr(
fieldData(icmp_checksum, FieldValue).toUInt(), 2));
configForm->idEdit->setText(
fieldData(icmp_identifier, FieldValue).toString());
configForm->seqEdit->setText(
fieldData(icmp_sequence, FieldValue).toString());
}
void IcmpProtocol::storeConfigWidget()
{
bool isOk;
configWidget();
setFieldData(icmp_version, configForm->versionGroup->checkedId());
setFieldData(icmp_type, configForm->typeCombo->currentValue());
setFieldData(icmp_code, configForm->codeEdit->text());
setFieldData(icmp_is_override_checksum,
configForm->overrideCksum->isChecked());
setFieldData(icmp_checksum, configForm->cksumEdit->text().toUInt(&isOk, BASE_HEX));
setFieldData(icmp_identifier, configForm->idEdit->text());
setFieldData(icmp_sequence, configForm->seqEdit->text());
}

View File

@ -20,12 +20,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#ifndef _ICMP_H
#define _ICMP_H
#include "icmp.pb.h"
#include "ui_icmp.h"
#include "abstractprotocol.h"
#include <QButtonGroup>
#include "icmp.pb.h"
/*
Icmp Protocol Frame Format -
@ -37,23 +33,9 @@ Fields within [] are applicable only to certain TYPEs
Figures in braces represent field width in bytes
*/
class IcmpConfigForm : public QWidget, public Ui::Icmp
{
Q_OBJECT
public:
QButtonGroup *versionGroup;
IcmpConfigForm(QWidget *parent = 0);
private slots:
void on_typeCombo_currentIndexChanged(int index);
void when_versionGroup_buttonClicked(int id);
};
class IcmpProtocol : public AbstractProtocol
{
private:
OstProto::Icmp data;
IcmpConfigForm *configForm;
public:
enum icmpfield
{
// Frame Fields
@ -73,18 +55,6 @@ private:
icmp_fieldCount
};
OstProto::Icmp::Version icmpVersion() const
{
return OstProto::Icmp::Version(
fieldData(icmp_version, FieldValue).toUInt());
}
int icmpType() const
{
return fieldData(icmp_type, FieldValue).toInt();
}
public:
IcmpProtocol(StreamBase *stream, AbstractProtocol *parent = 0);
virtual ~IcmpProtocol();
@ -109,9 +79,18 @@ public:
virtual bool setFieldData(int index, const QVariant &value,
FieldAttrib attrib = FieldValue);
virtual QWidget* configWidget();
virtual void loadConfigWidget();
virtual void storeConfigWidget();
private:
OstProto::Icmp data;
OstProto::Icmp::Version icmpVersion() const
{
return OstProto::Icmp::Version(
fieldData(icmp_version, FieldValue).toUInt());
}
int icmpType() const
{
return fieldData(icmp_type, FieldValue).toInt();
}
};
#endif

191
common/icmpconfig.cpp Normal file
View File

@ -0,0 +1,191 @@
/*
Copyright (C) 2010 Srivats P.
This file is part of "Ostinato"
This is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>
*/
#include "icmpconfig.h"
#include "icmp.h"
#include "icmphelper.h"
#include <QButtonGroup>
IcmpConfigForm::IcmpConfigForm(QWidget *parent)
: AbstractProtocolConfigForm(parent)
{
versionGroup = new QButtonGroup(this);
setupUi(this);
// auto-connect's not working, for some reason I can't figure out!
// slot name changed to when_ instead of on_ so that connectSlotsByName()
// doesn't complain
connect(versionGroup,
SIGNAL(buttonClicked(int)),
SLOT(when_versionGroup_buttonClicked(int)));
versionGroup->addButton(icmp4Button, OstProto::Icmp::kIcmp4);
versionGroup->addButton(icmp6Button, OstProto::Icmp::kIcmp6);
typeCombo->setValidator(new QIntValidator(0, 0xFF, this));
icmp4Button->click();
idEdit->setValidator(new QIntValidator(0, 0xFFFF, this));
seqEdit->setValidator(new QIntValidator(0, 0xFFFF, this));
}
IcmpConfigForm::~IcmpConfigForm()
{
}
IcmpConfigForm* IcmpConfigForm::createInstance()
{
return new IcmpConfigForm;
}
void IcmpConfigForm::loadWidget(AbstractProtocol *proto)
{
versionGroup->button(
proto->fieldData(
IcmpProtocol::icmp_version,
AbstractProtocol::FieldValue
).toUInt())->click();
typeCombo->setValue(
proto->fieldData(
IcmpProtocol::icmp_type,
AbstractProtocol::FieldValue
).toUInt());
codeEdit->setText(
proto->fieldData(
IcmpProtocol::icmp_code,
AbstractProtocol::FieldValue
).toString());
overrideCksum->setChecked(
proto->fieldData(
IcmpProtocol::icmp_is_override_checksum,
AbstractProtocol::FieldValue
).toBool());
cksumEdit->setText(uintToHexStr(
proto->fieldData(
IcmpProtocol::icmp_checksum,
AbstractProtocol::FieldValue
).toUInt(), 2));
idEdit->setText(
proto->fieldData(
IcmpProtocol::icmp_identifier,
AbstractProtocol::FieldValue
).toString());
seqEdit->setText(
proto->fieldData(
IcmpProtocol::icmp_sequence,
AbstractProtocol::FieldValue
).toString());
}
void IcmpConfigForm::storeWidget(AbstractProtocol *proto)
{
proto->setFieldData(
IcmpProtocol::icmp_version,
versionGroup->checkedId());
proto->setFieldData(
IcmpProtocol::icmp_type,
typeCombo->currentValue());
proto->setFieldData(
IcmpProtocol::icmp_code,
codeEdit->text());
proto->setFieldData(
IcmpProtocol::icmp_is_override_checksum,
overrideCksum->isChecked());
proto->setFieldData(
IcmpProtocol::icmp_checksum,
hexStrToUInt(cksumEdit->text()));
proto->setFieldData(
IcmpProtocol::icmp_identifier,
idEdit->text());
proto->setFieldData(
IcmpProtocol::icmp_sequence,
seqEdit->text());
}
//
// -------- private slots
//
void IcmpConfigForm::on_typeCombo_currentIndexChanged(int /*index*/)
{
idSeqFrame->setVisible(
isIdSeqType(
OstProto::Icmp::Version(versionGroup->checkedId()),
typeCombo->currentValue()));
}
void IcmpConfigForm::when_versionGroup_buttonClicked(int id)
{
int value = typeCombo->currentValue();
typeCombo->clear();
switch(id)
{
case OstProto::Icmp::kIcmp4:
typeCombo->addItem(kIcmpEchoReply, "Echo Reply");
typeCombo->addItem(kIcmpDestinationUnreachable,
"Destination Unreachable");
typeCombo->addItem(kIcmpSourceQuench, "Source Quench");
typeCombo->addItem(kIcmpRedirect, "Redirect");
typeCombo->addItem(kIcmpEchoRequest, "Echo Request");
typeCombo->addItem(kIcmpTimeExceeded, "Time Exceeded");
typeCombo->addItem(kIcmpParameterProblem, "Parameter Problem");
typeCombo->addItem(kIcmpTimestampRequest, "Timestamp Request");
typeCombo->addItem(kIcmpTimestampReply, "Timestamp Reply");
typeCombo->addItem(kIcmpInformationRequest, "Information Request");
typeCombo->addItem(kIcmpInformationReply, "Information Reply");
typeCombo->addItem(kIcmpAddressMaskRequest, "Address Mask Request");
typeCombo->addItem(kIcmpAddressMaskReply, "Address Mask Reply");
break;
case OstProto::Icmp::kIcmp6:
typeCombo->addItem(kIcmp6DestinationUnreachable,
"Destination Unreachable");
typeCombo->addItem(kIcmp6PacketTooBig, "Packet Too Big");
typeCombo->addItem(kIcmp6TimeExceeded, "Time Exceeded");
typeCombo->addItem(kIcmp6ParameterProblem, "Parameter Problem");
typeCombo->addItem(kIcmp6EchoRequest, "Echo Request");
typeCombo->addItem(kIcmp6EchoReply, "Echo Reply");
typeCombo->addItem(kIcmp6RouterSolicitation, "Router Solicitation");
typeCombo->addItem(kIcmp6RouterAdvertisement, "Router Advertisement");
typeCombo->addItem(kIcmp6NeighbourSolicitation,
"Neighbour Solicitation");
typeCombo->addItem(kIcmp6NeighbourAdvertisement,
"Neighbour Advertisement");
typeCombo->addItem(kIcmp6Redirect, "Redirect");
typeCombo->addItem(kIcmp6InformationQuery, "Information Query");
typeCombo->addItem(kIcmp6InformationResponse, "Information Response");
break;
default:
Q_ASSERT(false);
}
typeCombo->setValue(value);
}

50
common/icmpconfig.h Normal file
View File

@ -0,0 +1,50 @@
/*
Copyright (C) 2010 Srivats P.
This file is part of "Ostinato"
This is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>
*/
#ifndef _ICMP_CONFIG_H
#define _ICMP_CONFIG_H
#include "abstractprotocolconfig.h"
#include "ui_icmp.h"
class QButtonGroup;
class IcmpConfigForm :
public AbstractProtocolConfigForm,
private Ui::Icmp
{
Q_OBJECT
public:
IcmpConfigForm(QWidget *parent = 0);
virtual ~IcmpConfigForm();
static IcmpConfigForm* createInstance();
virtual void loadWidget(AbstractProtocol *proto);
virtual void storeWidget(AbstractProtocol *proto);
private:
QButtonGroup *versionGroup;
private slots:
void on_typeCombo_currentIndexChanged(int index);
void when_versionGroup_buttonClicked(int id);
};
#endif

88
common/icmphelper.h Normal file
View File

@ -0,0 +1,88 @@
/*
Copyright (C) 2010 Srivats P.
This file is part of "Ostinato"
This is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>
*/
#ifndef _ICMP_HELPER_H
#define _ICMP_HELPER_H
#include "icmp.pb.h"
#include <QSet>
enum IcmpType
{
kIcmpEchoReply = 0,
kIcmpDestinationUnreachable = 3,
kIcmpSourceQuench = 4,
kIcmpRedirect = 5,
kIcmpEchoRequest = 8,
kIcmpTimeExceeded = 11,
kIcmpParameterProblem = 12,
kIcmpTimestampRequest = 13,
kIcmpTimestampReply = 14,
kIcmpInformationRequest = 15,
kIcmpInformationReply = 16,
kIcmpAddressMaskRequest = 17,
kIcmpAddressMaskReply = 18
};
enum Icmp6Type
{
kIcmp6DestinationUnreachable = 1,
kIcmp6PacketTooBig = 2,
kIcmp6TimeExceeded = 3,
kIcmp6ParameterProblem = 4,
kIcmp6EchoRequest = 128,
kIcmp6EchoReply = 129,
kIcmp6RouterSolicitation = 133,
kIcmp6RouterAdvertisement = 134,
kIcmp6NeighbourSolicitation = 135,
kIcmp6NeighbourAdvertisement = 136,
kIcmp6Redirect = 137,
kIcmp6InformationQuery = 139,
kIcmp6InformationResponse = 140
};
static QSet<int> icmpIdSeqSet = QSet<int>()
<< kIcmpEchoRequest
<< kIcmpEchoReply
<< kIcmpInformationRequest
<< kIcmpInformationReply;
static QSet<int> icmp6IdSeqSet = QSet<int>()
<< kIcmp6EchoRequest
<< kIcmp6EchoReply;
bool inline isIdSeqType(OstProto::Icmp::Version ver, int type)
{
//qDebug("%s: ver = %d, type = %d", __FUNCTION__, ver, type);
switch(ver)
{
case OstProto::Icmp::kIcmp4:
return icmpIdSeqSet.contains(type);
case OstProto::Icmp::kIcmp6:
return icmp6IdSeqSet.contains(type);
default:
break;
}
Q_ASSERT(false); // unreachable
return false;
}
#endif

View File

@ -64,13 +64,13 @@ HEADERS += \
ip6over4.h \
ip6over6.h \
gmp.h \
icmp.h \
igmp.h \
mld.h \
tcp.h \
udp.h
HEADERS1 += \
icmp.h \
textproto.h \
userscript.h \
hexdump.h \
@ -97,13 +97,13 @@ SOURCES += \
ip4.cpp \
ip6.cpp \
gmp.cpp \
icmp.cpp \
igmp.cpp \
mld.cpp \
tcp.cpp \
udp.cpp
SOURCES1 += \
icmp.cpp \
textproto.cpp \
userscript.cpp \
hexdump.cpp \

View File

@ -19,11 +19,11 @@ FORMS += \
ip4.ui \
ip6.ui \
gmp.ui \
icmp.ui \
tcp.ui \
udp.ui
FORMS1 += \
icmp.ui \
textproto.ui \
userscript.ui \
hexdump.ui \
@ -65,6 +65,7 @@ HEADERS += \
ip6config.h \
ip4over4config.h \
gmpconfig.h \
icmpconfig.h \
igmpconfig.h \
mldconfig.h \
tcpconfig.h \
@ -93,6 +94,7 @@ SOURCES += \
ip4config.cpp \
ip6config.cpp \
gmpconfig.cpp \
icmpconfig.cpp \
igmpconfig.cpp \
mldconfig.cpp \
tcpconfig.cpp \

View File

@ -22,7 +22,6 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#include "protocol.pb.h"
#if 0
#include "icmp.h"
#include "textproto.h"
#include "userscript.h"
#include "hexdump.h"
@ -48,6 +47,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#include "ip6over4.h"
#include "ip6over6.h"
// L4 Protos
#include "icmp.h"
#include "igmp.h"
#include "mld.h"
#include "tcp.h"
@ -62,8 +62,6 @@ ProtocolManager::ProtocolManager()
themselves (once this is done remove the #includes for all the protocols)
*/
#if 0
registerProtocol(OstProto::Protocol::kIcmpFieldNumber,
(void*) IcmpProtocol::createInstance);
registerProtocol(OstProto::Protocol::kTextProtocolFieldNumber,
(void*) TextProtocol::createInstance);
@ -118,6 +116,8 @@ ProtocolManager::ProtocolManager()
(void*) Ip6over6Protocol::createInstance);
// Layer 4 Protocols
registerProtocol(OstProto::Protocol::kIcmpFieldNumber,
(void*) IcmpProtocol::createInstance);
registerProtocol(OstProto::Protocol::kIgmpFieldNumber,
(void*) IgmpProtocol::createInstance);
registerProtocol(OstProto::Protocol::kMldFieldNumber,

View File

@ -39,6 +39,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#include "ip6over4config.h"
#include "ip6over6config.h"
// L4 Protocol Widgets
#include "icmpconfig.h"
#include "igmpconfig.h"
#include "mldconfig.h"
#include "tcpconfig.h"
@ -114,6 +115,9 @@ ProtocolWidgetFactory::ProtocolWidgetFactory()
(void*) Ip6over6ConfigForm::createInstance);
// Layer 4 Protocols
OstProtocolWidgetFactory->registerProtocolConfigWidget(
OstProto::Protocol::kIcmpFieldNumber,
(void*) IcmpConfigForm::createInstance);
OstProtocolWidgetFactory->registerProtocolConfigWidget(
OstProto::Protocol::kIgmpFieldNumber,
(void*) IgmpConfigForm::createInstance);