DPDK-dev Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v3 1/1] pcapng: add user-supplied timestamp support
@ 2026-06-18 14:38 Dawid Wesierski
  2026-06-18 15:22 ` Stephen Hemminger
  0 siblings, 1 reply; 6+ messages in thread
From: Dawid Wesierski @ 2026-06-18 14:38 UTC (permalink / raw)
  To: dev; +Cc: stephen, thomas, Marek Kasiewicz, Dawid Wesierski

From: Marek Kasiewicz <marek.kasiewicz@intel.com>

Add rte_pcapng_copy_ts() which accepts a timestamp parameter in
nanoseconds since the Unix epoch. When non-zero, the supplied value is
used directly. This allows applications to provide hardware PTP
timestamps from the NIC, enabling accurate packet capture with
PTP-domain timing rather than host-local TSC values.

The existing rte_pcapng_copy() function is preserved as a static
inline wrapper that passes zero, keeping the original TSC-based
behaviour for callers that do not have a hardware timestamp.

To support both timestamp sources, the per-mbuf timestamp now carries
a sentinel bit: when rte_pcapng_copy_ts() is called with ts == 0 it
stores the current TSC with bit 63 set. rte_pcapng_write_packets()
detects the sentinel, clears it and converts TSC -> epoch ns using
the per-file clock before writing. A timestamp supplied by the caller
has bit 63 clear and is written unchanged. The sentinel space is safe
because the TSC counter does not reach bit 63 for centuries and
epoch-ns values stay below bit 63 until the year 2554.

Signed-off-by: Marek Kasiewicz <marek.kasiewicz@intel.com>
Signed-off-by: Dawid Wesierski <dawid.wesierski@intel.com>
---
 .mailmap                |  2 ++
 lib/pcapng/rte_pcapng.c | 42 +++++++++++++++++++++++++++-------------
 lib/pcapng/rte_pcapng.h | 43 +++++++++++++++++++++++++++++++++++++++--
 3 files changed, 72 insertions(+), 15 deletions(-)

diff --git a/.mailmap b/.mailmap
index 4001e5fb0e..a7d97a631e 100644
--- a/.mailmap
+++ b/.mailmap
@@ -366,6 +366,7 @@ David Zeng <zengxhsh@cn.ibm.com>
 Davide Caratti <dcaratti@redhat.com>
 Dawid Gorecki <dgr@semihalf.com>
 Dawid Jurczak <dawid_jurek@vp.pl>
+Dawid Wesierski <dawid.wesierski@intel.com> Wesierski, Dawid <dawid.wesierski@intel.com>
 Dawid Zielinski <dawid.zielinski@intel.com>
 Dawid Łukwiński <dawid.lukwinski@intel.com>
 Daxue Gao <daxuex.gao@intel.com>
@@ -1014,6 +1015,7 @@ Marcin Wilk <marcin.wilk@caviumnetworks.com>
 Marcin Wojtas <mw@semihalf.com>
 Marcin Zapolski <marcinx.a.zapolski@intel.com>
 Marco Varlese <mvarlese@suse.de>
+Marek Kasiewicz <marek.kasiewicz@intel.com>
 Marek Mical <marekx.mical@intel.com>
 Marek Zalfresso-jundzillo <marekx.zalfresso-jundzillo@intel.com>
 Maria Lingemark <maria.lingemark@ericsson.com>
diff --git a/lib/pcapng/rte_pcapng.c b/lib/pcapng/rte_pcapng.c
index b5d1026891..29090a2ae4 100644
--- a/lib/pcapng/rte_pcapng.c
+++ b/lib/pcapng/rte_pcapng.c
@@ -546,14 +546,14 @@ pcapng_vlan_insert(struct rte_mbuf *m, uint16_t ether_type, uint16_t tci)
  */
 
 /* Make a copy of original mbuf with pcapng header and options */
-RTE_EXPORT_SYMBOL(rte_pcapng_copy)
+RTE_EXPORT_SYMBOL(rte_pcapng_copy_ts)
 struct rte_mbuf *
-rte_pcapng_copy(uint16_t port_id, uint32_t queue,
+rte_pcapng_copy_ts(uint16_t port_id, uint32_t queue,
 		const struct rte_mbuf *md,
 		struct rte_mempool *mp,
 		uint32_t length,
 		enum rte_pcapng_direction direction,
-		const char *comment)
+		const char *comment, uint64_t ts)
 {
 	struct pcapng_enhance_packet_block *epb;
 	uint32_t orig_len, pkt_len, padding, flags;
@@ -690,8 +690,20 @@ rte_pcapng_copy(uint16_t port_id, uint32_t queue,
 	/* Interface index is filled in later during write */
 	mc->port = port_id;
 
-	/* Put timestamp in cycles here - adjust in packet write */
-	timestamp = rte_get_tsc_cycles();
+	/*
+	 * Timestamp handling:
+	 *  - If the caller supplied an explicit timestamp (ts != 0), it is
+	 *    already in nanoseconds since the Unix epoch, so store it as-is.
+	 *  - If the caller did not (ts == 0), store the current TSC and set
+	 *    the high bit as a sentinel so rte_pcapng_write_packets() knows
+	 *    it must convert TSC -> epoch ns at write time. The TSC counter
+	 *    will not reach bit 63 for centuries, and epoch-ns values stay
+	 *    below bit 63 until the year 2554, so the bit is safe to use.
+	 */
+	if (ts != 0)
+		timestamp = ts;
+	else
+		timestamp = rte_get_tsc_cycles() | (UINT64_C(1) << 63);
 	epb->timestamp_hi = timestamp >> 32;
 	epb->timestamp_lo = (uint32_t)timestamp;
 	epb->capture_length = pkt_len;
@@ -720,7 +732,7 @@ rte_pcapng_write_packets(rte_pcapng_t *self,
 	for (i = 0; i < nb_pkts; i++) {
 		struct rte_mbuf *m = pkts[i];
 		struct pcapng_enhance_packet_block *epb;
-		uint64_t cycles, timestamp;
+		uint64_t timestamp;
 
 		/* sanity check that is really a pcapng mbuf */
 		epb = rte_pktmbuf_mtod(m, struct pcapng_enhance_packet_block *);
@@ -738,14 +750,18 @@ rte_pcapng_write_packets(rte_pcapng_t *self,
 		}
 
 		/*
-		 * When data is captured by pcapng_copy the current TSC is stored.
-		 * Adjust the value recorded in file to PCAP epoch units.
+		 * If rte_pcapng_copy[_ts]() stored a TSC value (high bit set
+		 * as sentinel), convert it to nanoseconds since the Unix epoch
+		 * using the per-file clock. Otherwise the timestamp is already
+		 * in epoch ns and is written unchanged.
 		 */
-		cycles = (uint64_t)epb->timestamp_hi << 32;
-		cycles += epb->timestamp_lo;
-		timestamp = tsc_to_ns_epoch(&self->clock, cycles);
-		epb->timestamp_hi = timestamp >> 32;
-		epb->timestamp_lo = (uint32_t)timestamp;
+		timestamp = ((uint64_t)epb->timestamp_hi << 32) | epb->timestamp_lo;
+		if (timestamp & (UINT64_C(1) << 63)) {
+			timestamp &= ~(UINT64_C(1) << 63);
+			timestamp = tsc_to_ns_epoch(&self->clock, timestamp);
+			epb->timestamp_hi = timestamp >> 32;
+			epb->timestamp_lo = (uint32_t)timestamp;
+		}
 
 		/*
 		 * Handle case of highly fragmented and large burst size
diff --git a/lib/pcapng/rte_pcapng.h b/lib/pcapng/rte_pcapng.h
index d8d328f710..975e7996f0 100644
--- a/lib/pcapng/rte_pcapng.h
+++ b/lib/pcapng/rte_pcapng.h
@@ -109,7 +109,7 @@ enum rte_pcapng_direction {
 };
 
 /**
- * Format an mbuf for writing to file.
+ * Format an mbuf with time stamp for writing to file.
  *
  * @param port_id
  *   The Ethernet port on which packet was received
@@ -129,16 +129,55 @@ enum rte_pcapng_direction {
  * @param comment
  *   Optional per packet comment.
  *   Truncated to UINT16_MAX characters.
+ * @param ts
+ *   Packet timestamp in nanoseconds since the Unix epoch. If zero, the
+ *   current TSC is captured and converted to epoch ns by
+ *   rte_pcapng_write_packets() when the packet is written.
  *
  * @return
  *   - The pointer to the new mbuf formatted for pcapng_write
  *   - NULL on error such as invalid port or out of memory.
  */
 struct rte_mbuf *
+rte_pcapng_copy_ts(uint16_t port_id, uint32_t queue,
+		const struct rte_mbuf *m, struct rte_mempool *mp,
+		uint32_t length,
+		enum rte_pcapng_direction direction, const char *comment, uint64_t ts);
+
+/**
+ * Format an mbuf for writing to file.
+ *
+ * @param port_id
+ *   The Ethernet port on which packet was received
+ *   or is going to be transmitted.
+ * @param queue
+ *   The queue on the Ethernet port where packet was received
+ *   or is going to be transmitted.
+ * @param mp
+ *   The mempool from which the "clone" mbufs are allocated.
+ * @param m
+ *   The mbuf to copy
+ * @param length
+ *   The upper limit on bytes to copy.  Passing UINT32_MAX
+ *   means all data (after offset).
+ * @param direction
+ *   The direction of the packer: receive, transmit or unknown.
+ * @param comment
+ *   Packet comment.
+ *
+ * @return
+ *   - The pointer to the new mbuf formatted for pcapng_write
+ *   - NULL if allocation fails.
+ */
+static inline struct rte_mbuf *
 rte_pcapng_copy(uint16_t port_id, uint32_t queue,
 		const struct rte_mbuf *m, struct rte_mempool *mp,
 		uint32_t length,
-		enum rte_pcapng_direction direction, const char *comment);
+		enum rte_pcapng_direction direction, const char *comment)
+{
+	return rte_pcapng_copy_ts(port_id, queue, m, mp, length, direction,
+				  comment, 0);
+}
 
 
 /**
-- 
2.47.3

---------------------------------------------------------------------
Intel Technology Poland sp. z o.o.
ul. Slowackiego 173 | 80-298 Gdansk | Sad Rejonowy Gdansk Polnoc | VII Wydzial Gospodarczy Krajowego Rejestru Sadowego - KRS 101882 | NIP 957-07-52-316 | Kapital zakladowy 200.000 PLN.
Spolka oswiadcza, ze posiada status duzego przedsiebiorcy w rozumieniu ustawy z dnia 8 marca 2013 r. o przeciwdzialaniu nadmiernym opoznieniom w transakcjach handlowych.

Ta wiadomosc wraz z zalacznikami jest przeznaczona dla okreslonego adresata i moze zawierac informacje poufne. W razie przypadkowego otrzymania tej wiadomosci, prosimy o powiadomienie nadawcy oraz trwale jej usuniecie; jakiekolwiek przegladanie lub rozpowszechnianie jest zabronione.
This e-mail and any attachments may contain confidential material for the sole use of the intended recipient(s). If you are not the intended recipient, please contact the sender and delete all copies; any review or distribution by others is strictly prohibited.

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v3 1/1] pcapng: add user-supplied timestamp support
  2026-06-08 16:40 [PATCH 0/7] intel network and pcapng updates Dawid Wesierski
@ 2026-06-18 14:44 ` Dawid Wesierski
  2026-06-18 15:20   ` Stephen Hemminger
  0 siblings, 1 reply; 6+ messages in thread
From: Dawid Wesierski @ 2026-06-18 14:44 UTC (permalink / raw)
  To: dev; +Cc: stephen, thomas, Marek Kasiewicz, Dawid Wesierski

From: Marek Kasiewicz <marek.kasiewicz@intel.com>

Add rte_pcapng_copy_ts() which accepts a timestamp parameter in
nanoseconds since the Unix epoch. When non-zero, the supplied value is
used directly. This allows applications to provide hardware PTP
timestamps from the NIC, enabling accurate packet capture with
PTP-domain timing rather than host-local TSC values.

The existing rte_pcapng_copy() function is preserved as a static
inline wrapper that passes zero, keeping the original TSC-based
behaviour for callers that do not have a hardware timestamp.

To support both timestamp sources, the per-mbuf timestamp now carries
a sentinel bit: when rte_pcapng_copy_ts() is called with ts == 0 it
stores the current TSC with bit 63 set. rte_pcapng_write_packets()
detects the sentinel, clears it and converts TSC -> epoch ns using
the per-file clock before writing. A timestamp supplied by the caller
has bit 63 clear and is written unchanged. The sentinel space is safe
because the TSC counter does not reach bit 63 for centuries and
epoch-ns values stay below bit 63 until the year 2554.

Signed-off-by: Marek Kasiewicz <marek.kasiewicz@intel.com>
Signed-off-by: Dawid Wesierski <dawid.wesierski@intel.com>
---
 .mailmap                |  2 ++
 lib/pcapng/rte_pcapng.c | 42 +++++++++++++++++++++++++++-------------
 lib/pcapng/rte_pcapng.h | 43 +++++++++++++++++++++++++++++++++++++++--
 3 files changed, 72 insertions(+), 15 deletions(-)

diff --git a/.mailmap b/.mailmap
index 4001e5fb0e..a7d97a631e 100644
--- a/.mailmap
+++ b/.mailmap
@@ -366,6 +366,7 @@ David Zeng <zengxhsh@cn.ibm.com>
 Davide Caratti <dcaratti@redhat.com>
 Dawid Gorecki <dgr@semihalf.com>
 Dawid Jurczak <dawid_jurek@vp.pl>
+Dawid Wesierski <dawid.wesierski@intel.com> Wesierski, Dawid <dawid.wesierski@intel.com>
 Dawid Zielinski <dawid.zielinski@intel.com>
 Dawid Łukwiński <dawid.lukwinski@intel.com>
 Daxue Gao <daxuex.gao@intel.com>
@@ -1014,6 +1015,7 @@ Marcin Wilk <marcin.wilk@caviumnetworks.com>
 Marcin Wojtas <mw@semihalf.com>
 Marcin Zapolski <marcinx.a.zapolski@intel.com>
 Marco Varlese <mvarlese@suse.de>
+Marek Kasiewicz <marek.kasiewicz@intel.com>
 Marek Mical <marekx.mical@intel.com>
 Marek Zalfresso-jundzillo <marekx.zalfresso-jundzillo@intel.com>
 Maria Lingemark <maria.lingemark@ericsson.com>
diff --git a/lib/pcapng/rte_pcapng.c b/lib/pcapng/rte_pcapng.c
index b5d1026891..29090a2ae4 100644
--- a/lib/pcapng/rte_pcapng.c
+++ b/lib/pcapng/rte_pcapng.c
@@ -546,14 +546,14 @@ pcapng_vlan_insert(struct rte_mbuf *m, uint16_t ether_type, uint16_t tci)
  */
 
 /* Make a copy of original mbuf with pcapng header and options */
-RTE_EXPORT_SYMBOL(rte_pcapng_copy)
+RTE_EXPORT_SYMBOL(rte_pcapng_copy_ts)
 struct rte_mbuf *
-rte_pcapng_copy(uint16_t port_id, uint32_t queue,
+rte_pcapng_copy_ts(uint16_t port_id, uint32_t queue,
 		const struct rte_mbuf *md,
 		struct rte_mempool *mp,
 		uint32_t length,
 		enum rte_pcapng_direction direction,
-		const char *comment)
+		const char *comment, uint64_t ts)
 {
 	struct pcapng_enhance_packet_block *epb;
 	uint32_t orig_len, pkt_len, padding, flags;
@@ -690,8 +690,20 @@ rte_pcapng_copy(uint16_t port_id, uint32_t queue,
 	/* Interface index is filled in later during write */
 	mc->port = port_id;
 
-	/* Put timestamp in cycles here - adjust in packet write */
-	timestamp = rte_get_tsc_cycles();
+	/*
+	 * Timestamp handling:
+	 *  - If the caller supplied an explicit timestamp (ts != 0), it is
+	 *    already in nanoseconds since the Unix epoch, so store it as-is.
+	 *  - If the caller did not (ts == 0), store the current TSC and set
+	 *    the high bit as a sentinel so rte_pcapng_write_packets() knows
+	 *    it must convert TSC -> epoch ns at write time. The TSC counter
+	 *    will not reach bit 63 for centuries, and epoch-ns values stay
+	 *    below bit 63 until the year 2554, so the bit is safe to use.
+	 */
+	if (ts != 0)
+		timestamp = ts;
+	else
+		timestamp = rte_get_tsc_cycles() | (UINT64_C(1) << 63);
 	epb->timestamp_hi = timestamp >> 32;
 	epb->timestamp_lo = (uint32_t)timestamp;
 	epb->capture_length = pkt_len;
@@ -720,7 +732,7 @@ rte_pcapng_write_packets(rte_pcapng_t *self,
 	for (i = 0; i < nb_pkts; i++) {
 		struct rte_mbuf *m = pkts[i];
 		struct pcapng_enhance_packet_block *epb;
-		uint64_t cycles, timestamp;
+		uint64_t timestamp;
 
 		/* sanity check that is really a pcapng mbuf */
 		epb = rte_pktmbuf_mtod(m, struct pcapng_enhance_packet_block *);
@@ -738,14 +750,18 @@ rte_pcapng_write_packets(rte_pcapng_t *self,
 		}
 
 		/*
-		 * When data is captured by pcapng_copy the current TSC is stored.
-		 * Adjust the value recorded in file to PCAP epoch units.
+		 * If rte_pcapng_copy[_ts]() stored a TSC value (high bit set
+		 * as sentinel), convert it to nanoseconds since the Unix epoch
+		 * using the per-file clock. Otherwise the timestamp is already
+		 * in epoch ns and is written unchanged.
 		 */
-		cycles = (uint64_t)epb->timestamp_hi << 32;
-		cycles += epb->timestamp_lo;
-		timestamp = tsc_to_ns_epoch(&self->clock, cycles);
-		epb->timestamp_hi = timestamp >> 32;
-		epb->timestamp_lo = (uint32_t)timestamp;
+		timestamp = ((uint64_t)epb->timestamp_hi << 32) | epb->timestamp_lo;
+		if (timestamp & (UINT64_C(1) << 63)) {
+			timestamp &= ~(UINT64_C(1) << 63);
+			timestamp = tsc_to_ns_epoch(&self->clock, timestamp);
+			epb->timestamp_hi = timestamp >> 32;
+			epb->timestamp_lo = (uint32_t)timestamp;
+		}
 
 		/*
 		 * Handle case of highly fragmented and large burst size
diff --git a/lib/pcapng/rte_pcapng.h b/lib/pcapng/rte_pcapng.h
index d8d328f710..975e7996f0 100644
--- a/lib/pcapng/rte_pcapng.h
+++ b/lib/pcapng/rte_pcapng.h
@@ -109,7 +109,7 @@ enum rte_pcapng_direction {
 };
 
 /**
- * Format an mbuf for writing to file.
+ * Format an mbuf with time stamp for writing to file.
  *
  * @param port_id
  *   The Ethernet port on which packet was received
@@ -129,16 +129,55 @@ enum rte_pcapng_direction {
  * @param comment
  *   Optional per packet comment.
  *   Truncated to UINT16_MAX characters.
+ * @param ts
+ *   Packet timestamp in nanoseconds since the Unix epoch. If zero, the
+ *   current TSC is captured and converted to epoch ns by
+ *   rte_pcapng_write_packets() when the packet is written.
  *
  * @return
  *   - The pointer to the new mbuf formatted for pcapng_write
  *   - NULL on error such as invalid port or out of memory.
  */
 struct rte_mbuf *
+rte_pcapng_copy_ts(uint16_t port_id, uint32_t queue,
+		const struct rte_mbuf *m, struct rte_mempool *mp,
+		uint32_t length,
+		enum rte_pcapng_direction direction, const char *comment, uint64_t ts);
+
+/**
+ * Format an mbuf for writing to file.
+ *
+ * @param port_id
+ *   The Ethernet port on which packet was received
+ *   or is going to be transmitted.
+ * @param queue
+ *   The queue on the Ethernet port where packet was received
+ *   or is going to be transmitted.
+ * @param mp
+ *   The mempool from which the "clone" mbufs are allocated.
+ * @param m
+ *   The mbuf to copy
+ * @param length
+ *   The upper limit on bytes to copy.  Passing UINT32_MAX
+ *   means all data (after offset).
+ * @param direction
+ *   The direction of the packer: receive, transmit or unknown.
+ * @param comment
+ *   Packet comment.
+ *
+ * @return
+ *   - The pointer to the new mbuf formatted for pcapng_write
+ *   - NULL if allocation fails.
+ */
+static inline struct rte_mbuf *
 rte_pcapng_copy(uint16_t port_id, uint32_t queue,
 		const struct rte_mbuf *m, struct rte_mempool *mp,
 		uint32_t length,
-		enum rte_pcapng_direction direction, const char *comment);
+		enum rte_pcapng_direction direction, const char *comment)
+{
+	return rte_pcapng_copy_ts(port_id, queue, m, mp, length, direction,
+				  comment, 0);
+}
 
 
 /**
-- 
2.47.3

---------------------------------------------------------------------
Intel Technology Poland sp. z o.o.
ul. Slowackiego 173 | 80-298 Gdansk | Sad Rejonowy Gdansk Polnoc | VII Wydzial Gospodarczy Krajowego Rejestru Sadowego - KRS 101882 | NIP 957-07-52-316 | Kapital zakladowy 200.000 PLN.
Spolka oswiadcza, ze posiada status duzego przedsiebiorcy w rozumieniu ustawy z dnia 8 marca 2013 r. o przeciwdzialaniu nadmiernym opoznieniom w transakcjach handlowych.

Ta wiadomosc wraz z zalacznikami jest przeznaczona dla okreslonego adresata i moze zawierac informacje poufne. W razie przypadkowego otrzymania tej wiadomosci, prosimy o powiadomienie nadawcy oraz trwale jej usuniecie; jakiekolwiek przegladanie lub rozpowszechnianie jest zabronione.
This e-mail and any attachments may contain confidential material for the sole use of the intended recipient(s). If you are not the intended recipient, please contact the sender and delete all copies; any review or distribution by others is strictly prohibited.

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH v3 1/1] pcapng: add user-supplied timestamp support
  2026-06-18 14:44 ` [PATCH v3 1/1] pcapng: add user-supplied timestamp support Dawid Wesierski
@ 2026-06-18 15:20   ` Stephen Hemminger
  0 siblings, 0 replies; 6+ messages in thread
From: Stephen Hemminger @ 2026-06-18 15:20 UTC (permalink / raw)
  To: Dawid Wesierski; +Cc: dev, thomas, Marek Kasiewicz

On Thu, 18 Jun 2026 10:44:29 -0400
Dawid Wesierski <dawid.wesierski@intel.com> wrote:

> +static inline struct rte_mbuf *
>  rte_pcapng_copy(uint16_t port_id, uint32_t queue,
>  		const struct rte_mbuf *m, struct rte_mempool *mp,
>  		uint32_t length,
> -		enum rte_pcapng_direction direction, const char *comment);
> +		enum rte_pcapng_direction direction, const char *comment)
> +{
> +	return rte_pcapng_copy_ts(port_id, queue, m, mp, length, direction,
> +				  comment, 0);
> +}
>  

Switching from function to inline in header would cause ABI breakage.
New build would not have old function to runtime linking.

In this case, please just keep the old function name but add
a parameter using function versioning.



^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v3 1/1] pcapng: add user-supplied timestamp support
  2026-06-18 14:38 [PATCH v3 1/1] pcapng: add user-supplied timestamp support Dawid Wesierski
@ 2026-06-18 15:22 ` Stephen Hemminger
  2026-06-18 16:45   ` Morten Brørup
  0 siblings, 1 reply; 6+ messages in thread
From: Stephen Hemminger @ 2026-06-18 15:22 UTC (permalink / raw)
  To: Dawid Wesierski; +Cc: dev, thomas, Marek Kasiewicz

On Thu, 18 Jun 2026 10:38:15 -0400
Dawid Wesierski <dawid.wesierski@intel.com> wrote:

> + * @param ts
> + *   Packet timestamp in nanoseconds since the Unix epoch. If zero, the
> + *   current TSC is captured and converted to epoch ns by
> + *   rte_pcapng_write_packets() when the packet is written.
>   *

It might help users if a helper rte_tsc_to_epoch() was exposed.

^ permalink raw reply	[flat|nested] 6+ messages in thread

* RE: [PATCH v3 1/1] pcapng: add user-supplied timestamp support
  2026-06-18 15:22 ` Stephen Hemminger
@ 2026-06-18 16:45   ` Morten Brørup
  2026-06-18 18:51     ` Stephen Hemminger
  0 siblings, 1 reply; 6+ messages in thread
From: Morten Brørup @ 2026-06-18 16:45 UTC (permalink / raw)
  To: Stephen Hemminger, Dawid Wesierski; +Cc: dev, thomas, Marek Kasiewicz

> From: Stephen Hemminger [mailto:stephen@networkplumber.org]
> Sent: Thursday, 18 June 2026 17.23
> 
> On Thu, 18 Jun 2026 10:38:15 -0400
> Dawid Wesierski <dawid.wesierski@intel.com> wrote:
> 
> > + * @param ts
> > + *   Packet timestamp in nanoseconds since the Unix epoch. If zero,
> the
> > + *   current TSC is captured and converted to epoch ns by
> > + *   rte_pcapng_write_packets() when the packet is written.
> >   *
> 
> It might help users if a helper rte_tsc_to_epoch() was exposed.

+1

Please note that such a helper would need to compensate for rte_rdtsc() drift.

Simplified:

int64_t rte_tsc_to_ns(tsc)
{
  struct timespec ts = clock_gettime(CLOCK_REALTIME);
  int64_t now_ns = ts.tv_sec * NS_PER_S + ts.tv_nsec;
  int64_t now_tsc = rte_rdtsc();
  int64_t diff_tsc = tsc - tsc_now;
  return now_ns + diff_tsc * NS_PER_S / rte_get_tsc_hz();
}

A performance optimized version would take "now_ns" and "now_tsc" as parameters.
And with "now_ns" passed as a parameter, the function also works with other clocks, such as CLOCK_MONOTONIC.

Also see this discussion on the Grout mailing list:
https://inbox.dpdk.org/grout/98CBD80474FA8B44BF855DF32C47DC35F6590E@smartserver.smartshare.dk/T/#m465a04ca2e8219612dd9c3efb4198d23d5813422



^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v3 1/1] pcapng: add user-supplied timestamp support
  2026-06-18 16:45   ` Morten Brørup
@ 2026-06-18 18:51     ` Stephen Hemminger
  0 siblings, 0 replies; 6+ messages in thread
From: Stephen Hemminger @ 2026-06-18 18:51 UTC (permalink / raw)
  To: Morten Brørup; +Cc: Dawid Wesierski, dev, thomas, Marek Kasiewicz

On Thu, 18 Jun 2026 18:45:19 +0200
Morten Brørup <mb@smartsharesystems.com> wrote:

> > From: Stephen Hemminger [mailto:stephen@networkplumber.org]
> > Sent: Thursday, 18 June 2026 17.23
> > 
> > On Thu, 18 Jun 2026 10:38:15 -0400
> > Dawid Wesierski <dawid.wesierski@intel.com> wrote:
> >   
> > > + * @param ts
> > > + *   Packet timestamp in nanoseconds since the Unix epoch. If zero,  
> > the  
> > > + *   current TSC is captured and converted to epoch ns by
> > > + *   rte_pcapng_write_packets() when the packet is written.
> > >   *  
> > 
> > It might help users if a helper rte_tsc_to_epoch() was exposed.  
> 
> +1
> 
> Please note that such a helper would need to compensate for rte_rdtsc() drift.
> 
> Simplified:
> 
> int64_t rte_tsc_to_ns(tsc)
> {
>   struct timespec ts = clock_gettime(CLOCK_REALTIME);
>   int64_t now_ns = ts.tv_sec * NS_PER_S + ts.tv_nsec;
>   int64_t now_tsc = rte_rdtsc();
>   int64_t diff_tsc = tsc - tsc_now;
>   return now_ns + diff_tsc * NS_PER_S / rte_get_tsc_hz();
> }
> 
> A performance optimized version would take "now_ns" and "now_tsc" as parameters.
> And with "now_ns" passed as a parameter, the function also works with other clocks, such as CLOCK_MONOTONIC.
> 
> Also see this discussion on the Grout mailing list:
> https://inbox.dpdk.org/grout/98CBD80474FA8B44BF855DF32C47DC35F6590E@smartserver.smartshare.dk/T/#m465a04ca2e8219612dd9c3efb4198d23d5813422
> 
> 

Inside rte_pcapng is already all the necessary state and setup.
Just not exposed to user. It does it without divide operation

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2026-06-18 18:51 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-06-18 14:38 [PATCH v3 1/1] pcapng: add user-supplied timestamp support Dawid Wesierski
2026-06-18 15:22 ` Stephen Hemminger
2026-06-18 16:45   ` Morten Brørup
2026-06-18 18:51     ` Stephen Hemminger
  -- strict thread matches above, loose matches on Subject: below --
2026-06-08 16:40 [PATCH 0/7] intel network and pcapng updates Dawid Wesierski
2026-06-18 14:44 ` [PATCH v3 1/1] pcapng: add user-supplied timestamp support Dawid Wesierski
2026-06-18 15:20   ` Stephen Hemminger

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox