Skip to content

Commit

Permalink
Add support for timestamp related options (#1656)
Browse files Browse the repository at this point in the history
  • Loading branch information
vcomito-apexai committed Dec 10, 2024
1 parent 3d0717b commit 2ead59f
Show file tree
Hide file tree
Showing 2 changed files with 112 additions and 1 deletion.
53 changes: 52 additions & 1 deletion Pcap++/header/PcapLiveDevice.h
Original file line number Diff line number Diff line change
Expand Up @@ -186,6 +186,38 @@ namespace pcpp
PCPP_OUT
};

/**
* Set which source provides timestamps associated to each captured packet
* (you can read more here: <https://www.tcpdump.org/manpages/pcap-tstamp.7.html>)
*/
enum TimestampProvider
{
/** host-provided, unknown characteristics, default */
TimestampProviderHost = 0,
/** host-provided, low precision, synced with the system clock */
TimestampProviderHostLowPrec,
/** host-provided, high precision, synced with the system clock */
TimestampProviderHostHighPrec,
/** device-provided, synced with the system clock */
TimestampProviderAdapter,
/** device-provided, not synced with the system clock */
TimestampProviderAdapterUnsynced,
/** host-provided, high precision, not synced with the system clock */
TimestampProviderHostHighPrecUnsynced
};

/**
* Set the precision of timestamps associated to each captured packet
* (you can read more here: <https://www.tcpdump.org/manpages/pcap-tstamp.7.html>)
*/
enum TimestampPrecision
{
/** use timestamps with microsecond precision, default */
TimestampPrecisionMicroseconds = 0,
/** use timestamps with nanosecond precision */
TimestampPrecisionNanoseconds,
};

/**
* @struct DeviceConfiguration
* A struct that contains user configurable parameters for opening a device. All parameters have default values
Expand Down Expand Up @@ -236,6 +268,18 @@ namespace pcpp
/// In Unix-like system, use poll() for blocking mode.
bool usePoll;

/**
* Set which timestamp provider is used.
* Depending on the capture device and the software on the host, different types of time stamp can be used
*/
TimestampProvider timestampProvider;

/**
* Set which timestamp precision is used.
* Depending on the capture device and the software on the host, different precision can be used
*/
TimestampPrecision timestampPrecision;

/**
* A c'tor for this struct
* @param[in] mode The mode to open the device: promiscuous or non-promiscuous. Default value is promiscuous
Expand All @@ -252,10 +296,15 @@ namespace pcpp
* @param[in] nflogGroup NFLOG group for NFLOG devices. Default value is 0.
* @param[in] usePoll use `poll()` when capturing packets in blocking more (`startCaptureBlockingMode()`) on
* Unix-like system. Default value is false.
* @param[in] timestampProvider the source that will provide the timestamp associated to each captured
* packet.
* @param[in] timestampPrecision the precision of the timestamp associated to each captured packet.
*/
explicit DeviceConfiguration(DeviceMode mode = Promiscuous, int packetBufferTimeoutMs = 0,
int packetBufferSize = 0, PcapDirection direction = PCPP_INOUT,
int snapshotLength = 0, unsigned int nflogGroup = 0, bool usePoll = false)
int snapshotLength = 0, unsigned int nflogGroup = 0, bool usePoll = false,
TimestampProvider timestampProvider = TimestampProviderHost,
TimestampPrecision timestampPrecision = TimestampPrecisionMicroseconds)
{
this->mode = mode;
this->packetBufferTimeoutMs = packetBufferTimeoutMs;
Expand All @@ -264,6 +313,8 @@ namespace pcpp
this->snapshotLength = snapshotLength;
this->nflogGroup = nflogGroup;
this->usePoll = usePoll;
this->timestampProvider = timestampProvider;
this->timestampPrecision = timestampPrecision;
}
};

Expand Down
60 changes: 60 additions & 0 deletions Pcap++/src/PcapLiveDevice.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,38 @@ namespace pcpp
}
#endif

static int timestampProviderMap(const PcapLiveDevice::TimestampProvider timestampProvider)
{
switch (timestampProvider)
{
case PcapLiveDevice::TimestampProviderHost:
return PCAP_TSTAMP_HOST;
case PcapLiveDevice::TimestampProviderHostLowPrec:
return PCAP_TSTAMP_HOST_LOWPREC;
case PcapLiveDevice::TimestampProviderHostHighPrec:
return PCAP_TSTAMP_HOST_HIPREC;
case PcapLiveDevice::TimestampProviderAdapter:
return PCAP_TSTAMP_ADAPTER;
case PcapLiveDevice::TimestampProviderAdapterUnsynced:
return PCAP_TSTAMP_ADAPTER_UNSYNCED;
case PcapLiveDevice::TimestampProviderHostHighPrecUnsynced:
return PCAP_TSTAMP_HOST_HIPREC_UNSYNCED;
}
return PCAP_TSTAMP_HOST;
}

static int timestampPrecisionMap(const PcapLiveDevice::TimestampPrecision timestampPrecision)
{
switch (timestampPrecision)
{
case PcapLiveDevice::TimestampPrecisionMicroseconds:
return PCAP_TSTAMP_PRECISION_MICRO;
case PcapLiveDevice::TimestampPrecisionNanoseconds:
return PCAP_TSTAMP_PRECISION_NANO;
}
return PCAP_TSTAMP_PRECISION_MICRO;
}

PcapLiveDevice::DeviceInterfaceDetails::DeviceInterfaceDetails(pcap_if_t* pInterface)
: name(pInterface->name), isLoopback(pInterface->flags & PCAP_IF_LOOPBACK)
{
Expand Down Expand Up @@ -308,6 +340,34 @@ namespace pcpp
}
#endif

if (config.timestampProvider)
{
ret = pcap_set_tstamp_type(pcap, timestampProviderMap(config.timestampProvider));
if (ret == 0)
{
PCPP_LOG_DEBUG("Timestamp provider was set");
}
else
{
PCPP_LOG_ERROR("Failed to set timestamping provider: '" << ret << "', error message: '"
<< pcap_geterr(pcap) << "'");
}
}

if (config.timestampPrecision)
{
ret = pcap_set_tstamp_precision(pcap, timestampPrecisionMap(config.timestampPrecision));
if (ret == 0)
{
PCPP_LOG_DEBUG("Timestamp precision was set");
}
else
{
PCPP_LOG_ERROR("Failed to set timestamping precision: '" << ret << "', error message: '"
<< pcap_geterr(pcap) << "'");
}
}

ret = pcap_activate(pcap);
if (ret != 0)
{
Expand Down

0 comments on commit 2ead59f

Please sign in to comment.