import linuxptp-3.1.1-6.el9_2.1
This commit is contained in:
parent
a6200bae87
commit
1cc1c4d830
30
SOURCES/linuxptp-eintr.patch
Normal file
30
SOURCES/linuxptp-eintr.patch
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
commit c8de9f33e437fb15cff32c0028f651d7cb916a37
|
||||||
|
Author: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
Date: Tue Sep 13 13:44:10 2022 +0200
|
||||||
|
|
||||||
|
sk: Handle EINTR when waiting for transmit timestamp.
|
||||||
|
|
||||||
|
If ptp4l received a signal in poll() waiting for a transmit timestamp,
|
||||||
|
multiple (possibly confusing) error messages are logged before exit.
|
||||||
|
|
||||||
|
If poll() returns with EINTR, call it once again to get the timestamp
|
||||||
|
and avoid logging the errors. Don't call it in a loop to avoid getting
|
||||||
|
stuck in case the timestamp is lost and the signal is repeated before
|
||||||
|
the poll timeout can be reached.
|
||||||
|
|
||||||
|
Signed-off-by: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
|
||||||
|
diff --git a/sk.c b/sk.c
|
||||||
|
index 80075be..d27abff 100644
|
||||||
|
--- a/sk.c
|
||||||
|
+++ b/sk.c
|
||||||
|
@@ -354,6 +354,9 @@ int sk_receive(int fd, void *buf, int buflen,
|
||||||
|
if (flags == MSG_ERRQUEUE) {
|
||||||
|
struct pollfd pfd = { fd, sk_events, 0 };
|
||||||
|
res = poll(&pfd, 1, sk_tx_timeout);
|
||||||
|
+ /* Retry once on EINTR to avoid logging errors before exit */
|
||||||
|
+ if (res < 0 && errno == EINTR)
|
||||||
|
+ res = poll(&pfd, 1, sk_tx_timeout);
|
||||||
|
if (res < 1) {
|
||||||
|
pr_err(res ? "poll for tx timestamp failed: %m" :
|
||||||
|
"timed out while polling for tx timestamp");
|
208
SOURCES/linuxptp-freqcheck.patch
Normal file
208
SOURCES/linuxptp-freqcheck.patch
Normal file
@ -0,0 +1,208 @@
|
|||||||
|
commit 513c7457865dba262a43e03fbe9178f4b08ba319
|
||||||
|
Author: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
Date: Mon Oct 24 15:25:30 2022 +0200
|
||||||
|
|
||||||
|
Drop support for old kernels returning zero frequency.
|
||||||
|
|
||||||
|
Kernels before 3.10 had a bug in reading of the system clock frequency,
|
||||||
|
which was worked around by commit da347d7a36f2 ("ptp4l: Set clock
|
||||||
|
frequency on start").
|
||||||
|
|
||||||
|
Drop this workaround and support for the old kernels to make
|
||||||
|
clockadj_get_freq() useful.
|
||||||
|
|
||||||
|
(Rebased to 3.1.1)
|
||||||
|
|
||||||
|
Signed-off-by: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
|
||||||
|
diff --git a/clock.c b/clock.c
|
||||||
|
index f3df220..9079428 100644
|
||||||
|
--- a/clock.c
|
||||||
|
+++ b/clock.c
|
||||||
|
@@ -1147,11 +1147,6 @@ struct clock *clock_create(enum clock_type type, struct config *config,
|
||||||
|
|
||||||
|
if (c->clkid != CLOCK_INVALID) {
|
||||||
|
fadj = (int) clockadj_get_freq(c->clkid);
|
||||||
|
- /* Due to a bug in older kernels, the reading may silently fail
|
||||||
|
- and return 0. Set the frequency back to make sure fadj is
|
||||||
|
- the actual frequency of the clock. */
|
||||||
|
- clockadj_set_freq(c->clkid, fadj);
|
||||||
|
-
|
||||||
|
/* Disable write phase mode if not implemented by driver */
|
||||||
|
if (c->write_phase_mode && !phc_has_writephase(c->clkid)) {
|
||||||
|
pr_err("clock does not support write phase mode");
|
||||||
|
@@ -1746,7 +1741,6 @@ int clock_switch_phc(struct clock *c, int phc_index)
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
fadj = (int) clockadj_get_freq(clkid);
|
||||||
|
- clockadj_set_freq(clkid, fadj);
|
||||||
|
servo = servo_create(c->config, c->servo_type, -fadj, max_adj, 0);
|
||||||
|
if (!servo) {
|
||||||
|
pr_err("Switching PHC, failed to create clock servo");
|
||||||
|
diff --git a/phc2sys.c b/phc2sys.c
|
||||||
|
index 5f6fbaa..af948eb 100644
|
||||||
|
--- a/phc2sys.c
|
||||||
|
+++ b/phc2sys.c
|
||||||
|
@@ -147,9 +147,6 @@ static struct servo *servo_add(struct phc2sys_private *priv,
|
||||||
|
|
||||||
|
clockadj_init(clock->clkid);
|
||||||
|
ppb = clockadj_get_freq(clock->clkid);
|
||||||
|
- /* The reading may silently fail and return 0, reset the frequency to
|
||||||
|
- make sure ppb is the actual frequency of the clock. */
|
||||||
|
- clockadj_set_freq(clock->clkid, ppb);
|
||||||
|
if (clock->clkid == CLOCK_REALTIME) {
|
||||||
|
sysclk_set_leap(0);
|
||||||
|
max_ppb = sysclk_max_freq();
|
||||||
|
diff --git a/ts2phc_slave.c b/ts2phc_slave.c
|
||||||
|
index 749efe5..5541d91 100644
|
||||||
|
--- a/ts2phc_slave.c
|
||||||
|
+++ b/ts2phc_slave.c
|
||||||
|
@@ -183,10 +183,6 @@ static struct ts2phc_slave *ts2phc_slave_create(struct config *cfg, const char *
|
||||||
|
pr_debug("PHC slave %s has ptp index %d", device, junk);
|
||||||
|
|
||||||
|
fadj = (int) clockadj_get_freq(slave->clk);
|
||||||
|
- /* Due to a bug in older kernels, the reading may silently fail
|
||||||
|
- and return 0. Set the frequency back to make sure fadj is
|
||||||
|
- the actual frequency of the clock. */
|
||||||
|
- clockadj_set_freq(slave->clk, fadj);
|
||||||
|
|
||||||
|
max_adj = phc_max_adj(slave->clk);
|
||||||
|
|
||||||
|
|
||||||
|
commit 80d6875b0072c7ea636a5631e590fa72d169c351
|
||||||
|
Author: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
Date: Mon Oct 24 15:25:31 2022 +0200
|
||||||
|
|
||||||
|
Don't accept errors in clockadj_get_freq().
|
||||||
|
|
||||||
|
Exit if an error is returned from the clock_adjtime() call in
|
||||||
|
clockadj_get_freq(). No recoverable errors are expected.
|
||||||
|
|
||||||
|
Signed-off-by: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
|
||||||
|
diff --git a/clockadj.c b/clockadj.c
|
||||||
|
index 957dc57..4c920b9 100644
|
||||||
|
--- a/clockadj.c
|
||||||
|
+++ b/clockadj.c
|
||||||
|
@@ -19,6 +19,7 @@
|
||||||
|
|
||||||
|
#include <errno.h>
|
||||||
|
#include <math.h>
|
||||||
|
+#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
@@ -72,6 +73,7 @@ double clockadj_get_freq(clockid_t clkid)
|
||||||
|
memset(&tx, 0, sizeof(tx));
|
||||||
|
if (clock_adjtime(clkid, &tx) < 0) {
|
||||||
|
pr_err("failed to read out the clock frequency adjustment: %m");
|
||||||
|
+ exit(1);
|
||||||
|
} else {
|
||||||
|
f = tx.freq / 65.536;
|
||||||
|
if (clkid == CLOCK_REALTIME && realtime_nominal_tick && tx.tick)
|
||||||
|
|
||||||
|
commit 211cbfe810ef4082d1af8e9b50f65d4f6fd7246a
|
||||||
|
Author: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
Date: Mon Oct 24 15:25:32 2022 +0200
|
||||||
|
|
||||||
|
Extend clockcheck to check for changes in frequency.
|
||||||
|
|
||||||
|
Before setting the new frequency offset on a clock update, compare the
|
||||||
|
current frequency returned by the kernel with the value saved from the
|
||||||
|
previous update. Print a warning message if the difference is larger
|
||||||
|
than 1 ppb, allowing for rounding errors in conversion to and from
|
||||||
|
double. The kernel caches the value set by clock_adjtime() in shifted
|
||||||
|
ppm, it doesn't request it from the driver, which can have a lower
|
||||||
|
resulution.
|
||||||
|
|
||||||
|
This should detect misconfigurations where multiple processes are trying
|
||||||
|
to control the clock (e.g. another ptp4l/phc2sys instance or an NTP
|
||||||
|
client), even when they don't step the clock.
|
||||||
|
|
||||||
|
Signed-off-by: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
|
||||||
|
diff --git a/clock.c b/clock.c
|
||||||
|
index 9079428..eea7983 100644
|
||||||
|
--- a/clock.c
|
||||||
|
+++ b/clock.c
|
||||||
|
@@ -1760,6 +1760,9 @@ int clock_switch_phc(struct clock *c, int phc_index)
|
||||||
|
|
||||||
|
static void clock_synchronize_locked(struct clock *c, double adj)
|
||||||
|
{
|
||||||
|
+ if (c->sanity_check) {
|
||||||
|
+ clockcheck_freq(c->sanity_check, clockadj_get_freq(c->clkid));
|
||||||
|
+ }
|
||||||
|
clockadj_set_freq(c->clkid, -adj);
|
||||||
|
if (c->clkid == CLOCK_REALTIME) {
|
||||||
|
sysclk_set_sync();
|
||||||
|
diff --git a/clockcheck.c b/clockcheck.c
|
||||||
|
index f0141be..b5a69cc 100644
|
||||||
|
--- a/clockcheck.c
|
||||||
|
+++ b/clockcheck.c
|
||||||
|
@@ -123,6 +123,16 @@ void clockcheck_set_freq(struct clockcheck *cc, int freq)
|
||||||
|
cc->freq_known = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
+int clockcheck_freq(struct clockcheck *cc, int freq)
|
||||||
|
+{
|
||||||
|
+ /* Allow difference of 1 ppb due to conversion to/from double */
|
||||||
|
+ if (cc->freq_known && abs(cc->current_freq - freq) > 1) {
|
||||||
|
+ pr_warning("clockcheck: clock frequency changed unexpectedly!");
|
||||||
|
+ return 1;
|
||||||
|
+ }
|
||||||
|
+ return 0;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void clockcheck_step(struct clockcheck *cc, int64_t step)
|
||||||
|
{
|
||||||
|
if (cc->last_ts)
|
||||||
|
diff --git a/clockcheck.h b/clockcheck.h
|
||||||
|
index 1ff86eb..4b09b98 100644
|
||||||
|
--- a/clockcheck.h
|
||||||
|
+++ b/clockcheck.h
|
||||||
|
@@ -54,6 +54,14 @@ int clockcheck_sample(struct clockcheck *cc, uint64_t ts);
|
||||||
|
*/
|
||||||
|
void clockcheck_set_freq(struct clockcheck *cc, int freq);
|
||||||
|
|
||||||
|
+/**
|
||||||
|
+ * Check whether the frequency correction did not change unexpectedly.
|
||||||
|
+ * @param cc Pointer to a clock check obtained via @ref clockcheck_create().
|
||||||
|
+ * @param freq Current reading of the frequency correction in ppb.
|
||||||
|
+ * @return Zero if the frequency did not change, non-zero otherwise.
|
||||||
|
+ */
|
||||||
|
+int clockcheck_freq(struct clockcheck *cc, int freq);
|
||||||
|
+
|
||||||
|
/**
|
||||||
|
* Inform clock check that the clock was stepped.
|
||||||
|
* @param cc Pointer to a clock check obtained via @ref clockcheck_create().
|
||||||
|
diff --git a/phc2sys.c b/phc2sys.c
|
||||||
|
index af948eb..4daa1bf 100644
|
||||||
|
--- a/phc2sys.c
|
||||||
|
+++ b/phc2sys.c
|
||||||
|
@@ -566,6 +566,9 @@ static void update_clock(struct phc2sys_private *priv, struct clock *clock,
|
||||||
|
/* Fall through. */
|
||||||
|
case SERVO_LOCKED:
|
||||||
|
case SERVO_LOCKED_STABLE:
|
||||||
|
+ if (clock->sanity_check)
|
||||||
|
+ clockcheck_freq(clock->sanity_check,
|
||||||
|
+ clockadj_get_freq(clock->clkid));
|
||||||
|
clockadj_set_freq(clock->clkid, -ppb);
|
||||||
|
if (clock->clkid == CLOCK_REALTIME)
|
||||||
|
sysclk_set_sync();
|
||||||
|
diff --git a/ptp4l.8 b/ptp4l.8
|
||||||
|
index 4917240..f760e2b 100644
|
||||||
|
--- a/ptp4l.8
|
||||||
|
+++ b/ptp4l.8
|
||||||
|
@@ -605,8 +605,10 @@ This option used to be called
|
||||||
|
The maximum allowed frequency offset between uncorrected clock and the system
|
||||||
|
monotonic clock in parts per billion (ppb). This is used as a sanity check of
|
||||||
|
the synchronized clock. When a larger offset is measured, a warning message
|
||||||
|
-will be printed and the servo will be reset. When set to 0, the sanity check is
|
||||||
|
-disabled. The default is 200000000 (20%).
|
||||||
|
+will be printed and the servo will be reset. If the frequency correction set by
|
||||||
|
+ptp4l changes unexpectedly between updates of the clock (e.g. due to another
|
||||||
|
+process trying to control the clock), a warning message will be printed. When
|
||||||
|
+set to 0, the sanity check is disabled. The default is 200000000 (20%).
|
||||||
|
.TP
|
||||||
|
.B initial_delay
|
||||||
|
The initial path delay of the clock in nanoseconds used for synchronization of
|
451
SOURCES/linuxptp-vlanbond.patch
Normal file
451
SOURCES/linuxptp-vlanbond.patch
Normal file
@ -0,0 +1,451 @@
|
|||||||
|
commit afd709924edcea26fec24a6253d1b85fc94c88e6
|
||||||
|
Author: Hangbin Liu <liuhangbin@gmail.com>
|
||||||
|
Date: Wed May 25 14:46:14 2022 +0800
|
||||||
|
|
||||||
|
ptp4l: init iface->ts_label when interface created
|
||||||
|
|
||||||
|
It's redundant to ensure tslabel if we could get ts_info directly from
|
||||||
|
the interface. By init iface->ts_label when interface created, there is
|
||||||
|
no need to take care of ts_label on other places.
|
||||||
|
|
||||||
|
It will also make the later vlan over bonding support patch more clear
|
||||||
|
after removing function interface_ensure_tslabel().
|
||||||
|
|
||||||
|
Signed-off-by: Hangbin Liu <liuhangbin@gmail.com>
|
||||||
|
|
||||||
|
diff --git a/clock.c b/clock.c
|
||||||
|
index 7ffbd6a..d4f273f 100644
|
||||||
|
--- a/clock.c
|
||||||
|
+++ b/clock.c
|
||||||
|
@@ -1006,9 +1006,8 @@ struct clock *clock_create(enum clock_type type, struct config *config,
|
||||||
|
required_modes = clock_required_modes(c);
|
||||||
|
STAILQ_FOREACH(iface, &config->interfaces, list) {
|
||||||
|
memset(ts_label, 0, sizeof(ts_label));
|
||||||
|
- rtnl_get_ts_device(interface_name(iface), ts_label);
|
||||||
|
- interface_set_label(iface, ts_label);
|
||||||
|
- interface_ensure_tslabel(iface);
|
||||||
|
+ if (!rtnl_get_ts_device(interface_name(iface), ts_label))
|
||||||
|
+ interface_set_label(iface, ts_label);
|
||||||
|
interface_get_tsinfo(iface);
|
||||||
|
if (interface_tsinfo_valid(iface) &&
|
||||||
|
!interface_tsmodes_supported(iface, required_modes)) {
|
||||||
|
diff --git a/interface.c b/interface.c
|
||||||
|
index 445a270..6c2630c 100644
|
||||||
|
--- a/interface.c
|
||||||
|
+++ b/interface.c
|
||||||
|
@@ -24,6 +24,7 @@ struct interface *interface_create(const char *name)
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
strncpy(iface->name, name, MAX_IFNAME_SIZE);
|
||||||
|
+ strncpy(iface->ts_label, name, MAX_IFNAME_SIZE);
|
||||||
|
iface->vclock = -1;
|
||||||
|
|
||||||
|
return iface;
|
||||||
|
@@ -34,13 +35,6 @@ void interface_destroy(struct interface *iface)
|
||||||
|
free(iface);
|
||||||
|
}
|
||||||
|
|
||||||
|
-void interface_ensure_tslabel(struct interface *iface)
|
||||||
|
-{
|
||||||
|
- if (!iface->ts_label[0]) {
|
||||||
|
- memcpy(iface->ts_label, iface->name, MAX_IFNAME_SIZE);
|
||||||
|
- }
|
||||||
|
-}
|
||||||
|
-
|
||||||
|
int interface_get_tsinfo(struct interface *iface)
|
||||||
|
{
|
||||||
|
return sk_get_ts_info(iface->ts_label, &iface->ts_info);
|
||||||
|
diff --git a/interface.h b/interface.h
|
||||||
|
index 752f4f1..5fc7836 100644
|
||||||
|
--- a/interface.h
|
||||||
|
+++ b/interface.h
|
||||||
|
@@ -33,12 +33,6 @@ struct interface *interface_create(const char *name);
|
||||||
|
*/
|
||||||
|
void interface_destroy(struct interface *iface);
|
||||||
|
|
||||||
|
-/**
|
||||||
|
- * Ensures that an interface has a proper time stamping label.
|
||||||
|
- * @param iface The interface of interest.
|
||||||
|
- */
|
||||||
|
-void interface_ensure_tslabel(struct interface *iface);
|
||||||
|
-
|
||||||
|
/**
|
||||||
|
* Populate the time stamping information of a given interface.
|
||||||
|
* @param iface The interface of interest.
|
||||||
|
diff --git a/nsm.c b/nsm.c
|
||||||
|
index 5aa925b..8d4a362 100644
|
||||||
|
--- a/nsm.c
|
||||||
|
+++ b/nsm.c
|
||||||
|
@@ -274,9 +274,8 @@ static int nsm_open(struct nsm *nsm, struct config *cfg)
|
||||||
|
STAILQ_FOREACH(iface, &cfg->interfaces, list) {
|
||||||
|
ifname = interface_name(iface);
|
||||||
|
memset(ts_label, 0, sizeof(ts_label));
|
||||||
|
- rtnl_get_ts_device(ifname, ts_label);
|
||||||
|
- interface_set_label(iface, ts_label);
|
||||||
|
- interface_ensure_tslabel(iface);
|
||||||
|
+ if (!rtnl_get_ts_device(ifname, ts_label))
|
||||||
|
+ interface_set_label(iface, ts_label);
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
if (count != 1) {
|
||||||
|
diff --git a/pmc_common.c b/pmc_common.c
|
||||||
|
index 756edf5..ee2ece6 100644
|
||||||
|
--- a/pmc_common.c
|
||||||
|
+++ b/pmc_common.c
|
||||||
|
@@ -405,7 +405,6 @@ struct pmc *pmc_create(struct config *cfg, enum transport_type transport_type,
|
||||||
|
pr_err("failed to create interface");
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
- interface_ensure_tslabel(pmc->iface);
|
||||||
|
|
||||||
|
if (transport_open(pmc->transport, pmc->iface,
|
||||||
|
&pmc->fdarray, TS_SOFTWARE)) {
|
||||||
|
|
||||||
|
commit 6aab466eb0563c1025c78ab496b22a8833b02d20
|
||||||
|
Author: Vincent Cheng <vincent.cheng.xh@renesas.com>
|
||||||
|
Date: Fri Jan 8 10:21:14 2021 -0500
|
||||||
|
|
||||||
|
port: Fix link down/up to continue using phc_index set from command line -p option.
|
||||||
|
|
||||||
|
In the scenario where a port link goes down and up, current code checks
|
||||||
|
the port's phc_index against the interface's phc_index and if they are
|
||||||
|
different will set the port phc_index to the interface phc_index.
|
||||||
|
|
||||||
|
If the phc_index was initially set by the command line -p option, then we
|
||||||
|
end up using the wrong phc_index.
|
||||||
|
|
||||||
|
Fix is to skip updating the port phc_index with the interface phc_index
|
||||||
|
when port link is back up if it was initialy set from the command line.
|
||||||
|
|
||||||
|
Signed-off-by: Vincent Cheng <vincent.cheng.xh@renesas.com>
|
||||||
|
|
||||||
|
diff --git a/port.c b/port.c
|
||||||
|
index 70b6e60..d22f30f 100644
|
||||||
|
--- a/port.c
|
||||||
|
+++ b/port.c
|
||||||
|
@@ -2601,6 +2601,11 @@ void port_link_status(void *ctx, int linkup, int ts_index)
|
||||||
|
"timestamping mode, set link status down by force.",
|
||||||
|
interface_label(p->iface));
|
||||||
|
p->link_status = LINK_DOWN | LINK_STATE_CHANGED;
|
||||||
|
+ } else if (p->phc_from_cmdline) {
|
||||||
|
+ pr_warning("port %d: taking /dev/ptp%d from the "
|
||||||
|
+ "command line, not the attached ptp%d",
|
||||||
|
+ portnum(p), p->phc_index,
|
||||||
|
+ interface_phc_index(p->iface));
|
||||||
|
} else if (p->phc_index != interface_phc_index(p->iface)) {
|
||||||
|
p->phc_index = interface_phc_index(p->iface);
|
||||||
|
|
||||||
|
@@ -3107,6 +3112,7 @@ struct port *port_open(const char *phc_device,
|
||||||
|
"not the attached ptp%d", number, phc_device,
|
||||||
|
interface_phc_index(interface));
|
||||||
|
p->phc_index = phc_index;
|
||||||
|
+ p->phc_from_cmdline = 1;
|
||||||
|
} else {
|
||||||
|
pr_err("port %d: PHC device mismatch", number);
|
||||||
|
pr_err("port %d: /dev/ptp%d requested, ptp%d attached",
|
||||||
|
diff --git a/port_private.h b/port_private.h
|
||||||
|
index fcabaa6..6e40e15 100644
|
||||||
|
--- a/port_private.h
|
||||||
|
+++ b/port_private.h
|
||||||
|
@@ -69,6 +69,7 @@ struct port {
|
||||||
|
struct fdarray fda;
|
||||||
|
int fault_fd;
|
||||||
|
int phc_index;
|
||||||
|
+ int phc_from_cmdline;
|
||||||
|
|
||||||
|
void (*dispatch)(struct port *p, enum fsm_event event, int mdiff);
|
||||||
|
enum fsm_event (*event)(struct port *p, int fd_index);
|
||||||
|
|
||||||
|
commit 45f20e824fdfb8748d73495ccc7578dc70866282
|
||||||
|
Author: Hangbin Liu <liuhangbin@gmail.com>
|
||||||
|
Date: Wed May 25 14:46:15 2022 +0800
|
||||||
|
|
||||||
|
port: refactor port_link_status
|
||||||
|
|
||||||
|
Split port_change_phc() logic form port_link_status() to improve the
|
||||||
|
readability of the code
|
||||||
|
|
||||||
|
(Rebased to 3.1.1)
|
||||||
|
|
||||||
|
Signed-off-by: Hangbin Liu <liuhangbin@gmail.com>
|
||||||
|
|
||||||
|
diff --git a/port.c b/port.c
|
||||||
|
index d22f30f..031b212 100644
|
||||||
|
--- a/port.c
|
||||||
|
+++ b/port.c
|
||||||
|
@@ -2563,10 +2563,43 @@ static void bc_dispatch(struct port *p, enum fsm_event event, int mdiff)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
+static void port_change_phc(struct port *p)
|
||||||
|
+{
|
||||||
|
+ int required_modes;
|
||||||
|
+
|
||||||
|
+ /* Only switch a non-vclock PHC with HW time stamping. */
|
||||||
|
+ if (!interface_tsinfo_valid(p->iface) ||
|
||||||
|
+ interface_get_vclock(p->iface) >= 0 ||
|
||||||
|
+ interface_phc_index(p->iface) < 0)
|
||||||
|
+ return;
|
||||||
|
+
|
||||||
|
+ required_modes = clock_required_modes(p->clock);
|
||||||
|
+ if (!interface_tsmodes_supported(p->iface, required_modes)) {
|
||||||
|
+ pr_err("interface '%s' does not support requested "
|
||||||
|
+ "timestamping mode, set link status down by force.",
|
||||||
|
+ interface_label(p->iface));
|
||||||
|
+ p->link_status = LINK_DOWN | LINK_STATE_CHANGED;
|
||||||
|
+ } else if (p->phc_from_cmdline) {
|
||||||
|
+ pr_warning("port %d: taking /dev/ptp%d from the "
|
||||||
|
+ "command line, not the attached ptp%d",
|
||||||
|
+ portnum(p), p->phc_index,
|
||||||
|
+ interface_phc_index(p->iface));
|
||||||
|
+ } else if (p->phc_index != interface_phc_index(p->iface)) {
|
||||||
|
+ p->phc_index = interface_phc_index(p->iface);
|
||||||
|
+
|
||||||
|
+ if (clock_switch_phc(p->clock, p->phc_index)) {
|
||||||
|
+ p->last_fault_type = FT_SWITCH_PHC;
|
||||||
|
+ port_dispatch(p, EV_FAULT_DETECTED, 0);
|
||||||
|
+ return;
|
||||||
|
+ }
|
||||||
|
+ clock_sync_interval(p->clock, p->log_sync_interval);
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void port_link_status(void *ctx, int linkup, int ts_index)
|
||||||
|
{
|
||||||
|
char ts_label[MAX_IFNAME_SIZE + 1] = {0};
|
||||||
|
- int link_state, required_modes;
|
||||||
|
+ int link_state;
|
||||||
|
const char *old_ts_label;
|
||||||
|
struct port *p = ctx;
|
||||||
|
|
||||||
|
@@ -2590,33 +2623,7 @@ void port_link_status(void *ctx, int linkup, int ts_index)
|
||||||
|
if (p->link_status & LINK_UP &&
|
||||||
|
(p->link_status & LINK_STATE_CHANGED || p->link_status & TS_LABEL_CHANGED)) {
|
||||||
|
interface_get_tsinfo(p->iface);
|
||||||
|
-
|
||||||
|
- /* Only switch a non-vclock PHC with HW time stamping. */
|
||||||
|
- if (interface_tsinfo_valid(p->iface) &&
|
||||||
|
- interface_get_vclock(p->iface) < 0 &&
|
||||||
|
- interface_phc_index(p->iface) >= 0) {
|
||||||
|
- required_modes = clock_required_modes(p->clock);
|
||||||
|
- if (!interface_tsmodes_supported(p->iface, required_modes)) {
|
||||||
|
- pr_err("interface '%s' does not support requested "
|
||||||
|
- "timestamping mode, set link status down by force.",
|
||||||
|
- interface_label(p->iface));
|
||||||
|
- p->link_status = LINK_DOWN | LINK_STATE_CHANGED;
|
||||||
|
- } else if (p->phc_from_cmdline) {
|
||||||
|
- pr_warning("port %d: taking /dev/ptp%d from the "
|
||||||
|
- "command line, not the attached ptp%d",
|
||||||
|
- portnum(p), p->phc_index,
|
||||||
|
- interface_phc_index(p->iface));
|
||||||
|
- } else if (p->phc_index != interface_phc_index(p->iface)) {
|
||||||
|
- p->phc_index = interface_phc_index(p->iface);
|
||||||
|
-
|
||||||
|
- if (clock_switch_phc(p->clock, p->phc_index)) {
|
||||||
|
- p->last_fault_type = FT_SWITCH_PHC;
|
||||||
|
- port_dispatch(p, EV_FAULT_DETECTED, 0);
|
||||||
|
- return;
|
||||||
|
- }
|
||||||
|
- clock_sync_interval(p->clock, p->log_sync_interval);
|
||||||
|
- }
|
||||||
|
- }
|
||||||
|
+ port_change_phc(p);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
|
||||||
|
commit 878c2eac77cc7abd1d86620a82ae9046545439ea
|
||||||
|
Author: Hangbin Liu <liuhangbin@gmail.com>
|
||||||
|
Date: Wed May 25 14:46:16 2022 +0800
|
||||||
|
|
||||||
|
ptp4l: add VLAN over bond support
|
||||||
|
|
||||||
|
Latest Linux kernel has supported getting active port's PHC from bond
|
||||||
|
directly. This would help topology like VLAN over bond to get PHC natively,
|
||||||
|
as VLAN also albe to get downlink's PHC.
|
||||||
|
|
||||||
|
To achieve this, the new hwtstamp flag is needed when passing hwtstamp_config
|
||||||
|
to kernel. Let's supply the flag first, and fall back without flag if user
|
||||||
|
run on old kernel.
|
||||||
|
|
||||||
|
We also need to update the PHC index in port_link_status() when there is
|
||||||
|
a RTNL event. The PHC info will be update in later port_change_phc().
|
||||||
|
|
||||||
|
Signed-off-by: Hangbin Liu <liuhangbin@gmail.com>
|
||||||
|
|
||||||
|
diff --git a/clock.c b/clock.c
|
||||||
|
index d4f273f..f3df220 100644
|
||||||
|
--- a/clock.c
|
||||||
|
+++ b/clock.c
|
||||||
|
@@ -1758,6 +1758,9 @@ int clock_switch_phc(struct clock *c, int phc_index)
|
||||||
|
c->clkid = clkid;
|
||||||
|
c->servo = servo;
|
||||||
|
c->servo_state = SERVO_UNLOCKED;
|
||||||
|
+
|
||||||
|
+ pr_info("Switched to /dev/ptp%d as PTP clock", phc_index);
|
||||||
|
+
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
diff --git a/missing.h b/missing.h
|
||||||
|
index c5194f4..5f684dd 100644
|
||||||
|
--- a/missing.h
|
||||||
|
+++ b/missing.h
|
||||||
|
@@ -73,6 +73,12 @@ struct so_timestamping {
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
+#ifndef HWTSTAMP_FLAG_BONDED_PHC_INDEX
|
||||||
|
+enum {
|
||||||
|
+ HWTSTAMP_FLAG_BONDED_PHC_INDEX = (1<<0),
|
||||||
|
+};
|
||||||
|
+#endif
|
||||||
|
+
|
||||||
|
#ifdef PTP_EXTTS_REQUEST2
|
||||||
|
#define PTP_EXTTS_REQUEST_FAILED "PTP_EXTTS_REQUEST2 failed: %m"
|
||||||
|
#else
|
||||||
|
diff --git a/port.c b/port.c
|
||||||
|
index 031b212..ae9c4d3 100644
|
||||||
|
--- a/port.c
|
||||||
|
+++ b/port.c
|
||||||
|
@@ -2619,12 +2619,18 @@ void port_link_status(void *ctx, int linkup, int ts_index)
|
||||||
|
pr_notice("port %hu: ts label changed to %s", portnum(p), ts_label);
|
||||||
|
}
|
||||||
|
|
||||||
|
+ /* phc index may changed while ts_label keeps the same after failover.
|
||||||
|
+ * e.g. vlan over bond. Since the lower link changed, we still set
|
||||||
|
+ * the TS_LABEL_CHANGED flag.
|
||||||
|
+ */
|
||||||
|
+ interface_get_tsinfo(p->iface);
|
||||||
|
+ if (p->phc_index != interface_phc_index(p->iface))
|
||||||
|
+ p->link_status |= TS_LABEL_CHANGED;
|
||||||
|
+
|
||||||
|
/* Both link down/up and change ts_label may change phc index. */
|
||||||
|
if (p->link_status & LINK_UP &&
|
||||||
|
- (p->link_status & LINK_STATE_CHANGED || p->link_status & TS_LABEL_CHANGED)) {
|
||||||
|
- interface_get_tsinfo(p->iface);
|
||||||
|
+ (p->link_status & LINK_STATE_CHANGED || p->link_status & TS_LABEL_CHANGED))
|
||||||
|
port_change_phc(p);
|
||||||
|
- }
|
||||||
|
|
||||||
|
/*
|
||||||
|
* A port going down can affect the BMCA result.
|
||||||
|
diff --git a/sk.c b/sk.c
|
||||||
|
index b55d6b5..80075be 100644
|
||||||
|
--- a/sk.c
|
||||||
|
+++ b/sk.c
|
||||||
|
@@ -66,6 +66,11 @@ static int hwts_init(int fd, const char *device, int rx_filter,
|
||||||
|
|
||||||
|
init_ifreq(&ifreq, &cfg, device);
|
||||||
|
|
||||||
|
+ cfg.flags = HWTSTAMP_FLAG_BONDED_PHC_INDEX;
|
||||||
|
+ /* Fall back without flag if user run new build on old kernel */
|
||||||
|
+ if (ioctl(fd, SIOCGHWTSTAMP, &ifreq) == -EINVAL)
|
||||||
|
+ init_ifreq(&ifreq, &cfg, device);
|
||||||
|
+
|
||||||
|
switch (sk_hwts_filter_mode) {
|
||||||
|
case HWTS_FILTER_CHECK:
|
||||||
|
err = ioctl(fd, SIOCGHWTSTAMP, &ifreq);
|
||||||
|
|
||||||
|
commit 98edb4d72b3d1d4e988f810b9a9cb1078212e5dc
|
||||||
|
Author: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
Date: Tue Nov 22 17:07:16 2022 +0100
|
||||||
|
|
||||||
|
port: Avoid faults with vclocks and PHC from command line.
|
||||||
|
|
||||||
|
After commit afeabf3c90ed ("ptp4l: add VLAN over bond support") the
|
||||||
|
TS_LABEL_CHANGED flag was set on link status changes when the used
|
||||||
|
PHC index was different from the PHC index of the interface.
|
||||||
|
|
||||||
|
This caused the port to be constantly switching to the faulty state when
|
||||||
|
using vclocks, or a different PHC device was forced with the -p option,
|
||||||
|
where it is expected the used PHC doesn't match the interface's PHC.
|
||||||
|
|
||||||
|
Rework port_link_status() and port_change_phc() to avoid setting the
|
||||||
|
flag and switch the clock only in the cases where it is expected.
|
||||||
|
|
||||||
|
Fixes: afeabf3c90ed ("ptp4l: add VLAN over bond support")
|
||||||
|
Signed-off-by: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
|
||||||
|
diff --git a/port.c b/port.c
|
||||||
|
index ae9c4d3..96e097a 100644
|
||||||
|
--- a/port.c
|
||||||
|
+++ b/port.c
|
||||||
|
@@ -2567,10 +2567,13 @@ static void port_change_phc(struct port *p)
|
||||||
|
{
|
||||||
|
int required_modes;
|
||||||
|
|
||||||
|
- /* Only switch a non-vclock PHC with HW time stamping. */
|
||||||
|
- if (!interface_tsinfo_valid(p->iface) ||
|
||||||
|
+ /* Try to switch only if the interface is up, it has HW time stamping
|
||||||
|
+ using a non-vclock PHC, and the PHC actually changed. */
|
||||||
|
+ if (!(p->link_status & LINK_UP) ||
|
||||||
|
+ !interface_tsinfo_valid(p->iface) ||
|
||||||
|
interface_get_vclock(p->iface) >= 0 ||
|
||||||
|
- interface_phc_index(p->iface) < 0)
|
||||||
|
+ interface_phc_index(p->iface) < 0 ||
|
||||||
|
+ p->phc_index == interface_phc_index(p->iface))
|
||||||
|
return;
|
||||||
|
|
||||||
|
required_modes = clock_required_modes(p->clock);
|
||||||
|
@@ -2584,7 +2587,7 @@ static void port_change_phc(struct port *p)
|
||||||
|
"command line, not the attached ptp%d",
|
||||||
|
portnum(p), p->phc_index,
|
||||||
|
interface_phc_index(p->iface));
|
||||||
|
- } else if (p->phc_index != interface_phc_index(p->iface)) {
|
||||||
|
+ } else {
|
||||||
|
p->phc_index = interface_phc_index(p->iface);
|
||||||
|
|
||||||
|
if (clock_switch_phc(p->clock, p->phc_index)) {
|
||||||
|
@@ -2619,18 +2622,12 @@ void port_link_status(void *ctx, int linkup, int ts_index)
|
||||||
|
pr_notice("port %hu: ts label changed to %s", portnum(p), ts_label);
|
||||||
|
}
|
||||||
|
|
||||||
|
- /* phc index may changed while ts_label keeps the same after failover.
|
||||||
|
- * e.g. vlan over bond. Since the lower link changed, we still set
|
||||||
|
- * the TS_LABEL_CHANGED flag.
|
||||||
|
- */
|
||||||
|
+ /* The PHC index may change even with the same ts_label, e.g. after
|
||||||
|
+ failover with VLAN over bond. */
|
||||||
|
interface_get_tsinfo(p->iface);
|
||||||
|
- if (p->phc_index != interface_phc_index(p->iface))
|
||||||
|
- p->link_status |= TS_LABEL_CHANGED;
|
||||||
|
|
||||||
|
- /* Both link down/up and change ts_label may change phc index. */
|
||||||
|
- if (p->link_status & LINK_UP &&
|
||||||
|
- (p->link_status & LINK_STATE_CHANGED || p->link_status & TS_LABEL_CHANGED))
|
||||||
|
- port_change_phc(p);
|
||||||
|
+ /* Switch the clock if needed */
|
||||||
|
+ port_change_phc(p);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* A port going down can affect the BMCA result.
|
||||||
|
commit 730a775fec159f012f3e0f65bb059465e9f7b49b
|
||||||
|
Author: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
Date: Wed Mar 15 11:24:16 2023 +0100
|
||||||
|
|
||||||
|
port: Don't switch to PHC with SW timestamping.
|
||||||
|
|
||||||
|
When ptp4l was configured to use SW timestamping, but the interface
|
||||||
|
supported also HW timestamping, ptp4l detected a change of the PHC on
|
||||||
|
start, switched to it from the system clock, and tried to control the
|
||||||
|
PHC using SW timestamps.
|
||||||
|
|
||||||
|
Don't switch the PHC if the current PHC index is -1, which is expected
|
||||||
|
with SW timestamping and in the free-running mode.
|
||||||
|
|
||||||
|
Fixes: afeabf3c90ed ("ptp4l: add VLAN over bond support")
|
||||||
|
Signed-off-by: Miroslav Lichvar <mlichvar@redhat.com>
|
||||||
|
|
||||||
|
diff --git a/port.c b/port.c
|
||||||
|
index 96e097a..32ee83b 100644
|
||||||
|
--- a/port.c
|
||||||
|
+++ b/port.c
|
||||||
|
@@ -2570,6 +2570,7 @@ static void port_change_phc(struct port *p)
|
||||||
|
/* Try to switch only if the interface is up, it has HW time stamping
|
||||||
|
using a non-vclock PHC, and the PHC actually changed. */
|
||||||
|
if (!(p->link_status & LINK_UP) ||
|
||||||
|
+ p->phc_index < 0 ||
|
||||||
|
!interface_tsinfo_valid(p->iface) ||
|
||||||
|
interface_get_vclock(p->iface) >= 0 ||
|
||||||
|
interface_phc_index(p->iface) < 0 ||
|
@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
Name: linuxptp
|
Name: linuxptp
|
||||||
Version: 3.1.1
|
Version: 3.1.1
|
||||||
Release: 5%{?dist}
|
Release: 6%{?dist}.1
|
||||||
Summary: PTP implementation for Linux
|
Summary: PTP implementation for Linux
|
||||||
|
|
||||||
License: GPLv2+
|
License: GPLv2+
|
||||||
@ -45,6 +45,12 @@ Patch11: linuxptp-clockcheck.patch
|
|||||||
Patch12: linuxptp-vclock.patch
|
Patch12: linuxptp-vclock.patch
|
||||||
# handle PHC read failing with EBUSY in phc2sys
|
# handle PHC read failing with EBUSY in phc2sys
|
||||||
Patch13: linuxptp-phcerr.patch
|
Patch13: linuxptp-phcerr.patch
|
||||||
|
# add support for VLAN over bond
|
||||||
|
Patch14: linuxptp-vlanbond.patch
|
||||||
|
# handle EINTR when waiting for transmit timestamp
|
||||||
|
Patch15: linuxptp-eintr.patch
|
||||||
|
# check for unexpected changes in frequency offset
|
||||||
|
Patch16: linuxptp-freqcheck.patch
|
||||||
|
|
||||||
BuildRequires: gcc gcc-c++ make systemd
|
BuildRequires: gcc gcc-c++ make systemd
|
||||||
|
|
||||||
@ -71,6 +77,9 @@ Supporting legacy APIs and other platforms is not a goal.
|
|||||||
%patch11 -p1 -b .clockcheck
|
%patch11 -p1 -b .clockcheck
|
||||||
%patch12 -p1 -b .vclock
|
%patch12 -p1 -b .vclock
|
||||||
%patch13 -p1 -b .phcerr
|
%patch13 -p1 -b .phcerr
|
||||||
|
%patch14 -p1 -b .vlanbond
|
||||||
|
%patch15 -p1 -b .eintr
|
||||||
|
%patch16 -p1 -b .freqcheck
|
||||||
mv linuxptp-testsuite-%{testsuite_ver}* testsuite
|
mv linuxptp-testsuite-%{testsuite_ver}* testsuite
|
||||||
mv clknetsim-%{clknetsim_ver}* testsuite/clknetsim
|
mv clknetsim-%{clknetsim_ver}* testsuite/clknetsim
|
||||||
|
|
||||||
@ -133,6 +142,14 @@ PATH=..:$PATH ./run
|
|||||||
%{_mandir}/man8/*.8*
|
%{_mandir}/man8/*.8*
|
||||||
|
|
||||||
%changelog
|
%changelog
|
||||||
|
* Mon Mar 20 2023 Miroslav Lichvar <mlichvar@redhat.com> 3.1.1-6.el9_2.1
|
||||||
|
- don't switch from system clock to PHC with SW timestamping (#2178233)
|
||||||
|
|
||||||
|
* Thu Jan 05 2023 Miroslav Lichvar <mlichvar@redhat.com> 3.1.1-6
|
||||||
|
- add support for VLAN over bond (#2120521)
|
||||||
|
- handle EINTR when waiting for transmit timestamp (#2128786)
|
||||||
|
- check for unexpected changes in frequency offset (#2150815)
|
||||||
|
|
||||||
* Thu Jul 28 2022 Miroslav Lichvar <mlichvar@redhat.com> 3.1.1-5
|
* Thu Jul 28 2022 Miroslav Lichvar <mlichvar@redhat.com> 3.1.1-5
|
||||||
- disable PHC switch with vclocks (#2066452)
|
- disable PHC switch with vclocks (#2066452)
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user