diff --git a/config.c b/config.c index 53ad788..0cbab4c 100644 --- a/config.c +++ b/config.c @@ -271,6 +271,7 @@ struct config_item config_tab[] = { GLOB_ITEM_STR("manufacturerIdentity", "00:00:00"), GLOB_ITEM_INT("max_frequency", 900000000, 0, INT_MAX), PORT_ITEM_INT("min_neighbor_prop_delay", -20000000, INT_MIN, -1), + PORT_ITEM_INT("msg_interval_request", 0, 0, 1), PORT_ITEM_INT("neighborPropDelayThresh", 20000000, 0, INT_MAX), PORT_ITEM_INT("net_sync_monitor", 0, 0, 1), PORT_ITEM_ENU("network_transport", TRANS_UDP_IPV4, nw_trans_enu), diff --git a/configs/automotive-slave.cfg b/configs/automotive-slave.cfg index 8cc7221..0898660 100644 --- a/configs/automotive-slave.cfg +++ b/configs/automotive-slave.cfg @@ -33,5 +33,6 @@ ignore_source_id 1 step_threshold 1 operLogSyncInterval 0 operLogPdelayReqInterval 2 +msg_interval_request 1 servo_offset_threshold 30 servo_num_offset_values 10 diff --git a/configs/default.cfg b/configs/default.cfg index 119df7b..91f6aaa 100644 --- a/configs/default.cfg +++ b/configs/default.cfg @@ -77,6 +77,7 @@ max_frequency 900000000 clock_servo pi sanity_freq_limit 200000000 ntpshm_segment 0 +msg_interval_request 0 servo_num_offset_values 10 servo_offset_threshold 0 # diff --git a/port.c b/port.c index 6b87bc9..368c3b8 100644 --- a/port.c +++ b/port.c @@ -1131,6 +1131,30 @@ static void port_slave_priority_warning(struct port *p) pr_warning("port %hu: defaultDS.priority1 probably misconfigured", n); } +static void message_interval_request(struct port *p, + enum servo_state last_state, + Integer8 sync_interval) +{ + if (!p->msg_interval_request) + return; + + if (last_state == SERVO_LOCKED) { + p->logPdelayReqInterval = p->operLogPdelayReqInterval; + p->logSyncInterval = p->operLogSyncInterval; + port_tx_interval_request(p, SIGNAL_NO_CHANGE, + p->logSyncInterval, + SIGNAL_NO_CHANGE); + port_dispatch(p, EV_MASTER_CLOCK_SELECTED, 0); + } else if (sync_interval != p->operLogSyncInterval) { + /* + * The most likely reason for this to happen is the + * master daemon re-initialized due to some fault. + */ + servo_reset(clock_servo(p->clock)); + port_dispatch(p, EV_SYNCHRONIZATION_FAULT, 0); + } +} + static void port_synchronize(struct port *p, tmv_t ingress_ts, struct timestamp origin_ts, @@ -1174,21 +1198,7 @@ static void port_synchronize(struct port *p, port_dispatch(p, EV_MASTER_CLOCK_SELECTED, 0); break; case SERVO_LOCKED_STABLE: - if (last_state == SERVO_LOCKED) { - p->logPdelayReqInterval = p->operLogPdelayReqInterval; - p->logSyncInterval = p->operLogSyncInterval; - port_tx_interval_request(p, SIGNAL_NO_CHANGE, - p->logSyncInterval, - SIGNAL_NO_CHANGE); - port_dispatch(p, EV_MASTER_CLOCK_SELECTED, 0); - } else if (sync_interval != p->operLogSyncInterval) { - /* - * The most likely reason for this to happen is the - * master daemon re-initialized due to some fault. - */ - servo_reset(clock_servo(p->clock)); - port_dispatch(p, EV_SYNCHRONIZATION_FAULT, 0); - } + message_interval_request(p, last_state, sync_interval); break; } } @@ -3029,6 +3039,7 @@ struct port *port_open(const char *phc_device, p->announce_span = transport == TRANS_UDS ? 0 : ANNOUNCE_SPAN; p->follow_up_info = config_get_int(cfg, p->name, "follow_up_info"); p->freq_est_interval = config_get_int(cfg, p->name, "freq_est_interval"); + p->msg_interval_request = config_get_int(cfg, p->name, "msg_interval_request"); p->net_sync_monitor = config_get_int(cfg, p->name, "net_sync_monitor"); p->path_trace_enabled = config_get_int(cfg, p->name, "path_trace_enabled"); p->tc_spanning_tree = config_get_int(cfg, p->name, "tc_spanning_tree"); diff --git a/port_private.h b/port_private.h index bc16d95..82d1801 100644 --- a/port_private.h +++ b/port_private.h @@ -128,6 +128,7 @@ struct port { int hybrid_e2e; int master_only; int match_transport_specific; + int msg_interval_request; int min_neighbor_prop_delay; int net_sync_monitor; int path_trace_enabled; diff --git a/ptp4l.8 b/ptp4l.8 index c4e1464..79bc9d9 100644 --- a/ptp4l.8 +++ b/ptp4l.8 @@ -162,11 +162,12 @@ accuracy of the local clock. It's specified as a power of two in seconds. The default is 0 (1 second). .TP .B operLogSyncInterval -The mean time interval between Sync messages. This value is only used by the -slave device when interval_update_timer is enabled. Slave will send this -interval to the master to switch to. This is done via a signaling message after -interval_update_timer expires. It's specified as a power of two in seconds. The -default value is 0 (1 second). +The Sync message interval to be requested once the clock enters the +SERVO_LOCKED_STABLE state. If the 'msg_interval_request' option is +set, then the local slave port will request the remote master to +switch to the given message rate via a signaling message containing a +Message interval request TLV. This option is specified as a power of +two in seconds, and default value is 0 (1 second). .TP .B logMinDelayReqInterval The minimum permitted mean time interval between Delay_Req messages. A shorter @@ -180,11 +181,11 @@ specified as a power of two in seconds. The default is 0 (1 second). .TP .B operLogPdelayReqInterval -The mean time interval between Pdelay Request messages. This value is only used -by the slave device when interval_update_timer is enabled. Slave will switch to -the interval specified by this config option after the interval_update_timer -expires. It's specified as a power of two in seconds. The default value is 0 (1 -second). +The Pdelay Request messages interval to be used once the clock enters +the SERVO_LOCKED_STABLE state. If the 'msg_interval_request' option +is set, then the local slave port will adopt this rate when the local +clock enters the "locked stable" state. This option is specified as a +power of two in seconds, and the default value is 0 (1 second). .TP .B inhibit_delay_req Don't send any delay requests. This will need the asCapable config option to be @@ -740,21 +741,28 @@ messages. This is useful when the announce messages are disabled in the master and the slave does not have any way to know it's identity. The default is 0 (disabled). .TP +.B msg_interval_request +This option, when set, will trigger an adjustment to the Sync and peer +delay request message intervals when the clock servo transitions into +the SERVO_LOCKED_STABLE state. The Sync interval will be adjusted via +the signaling mechanism while the pdelay request interval is simply +adjusted locally. The values to use for the new Sync and peer delay +request intervals are specified by the operLogSyncInterval and +operLogPdelayReqInterval options, respectively. +The default value of msg_interval_request is 0 (disabled). +.TP .B servo_num_offset_values -The number of offset values calculated in previously received Sync messages to -consider when adjusting the Sync and Pdelay request intervals. More information -provided in the description of 'offset_threshold'. The default value is 10. +The number of offset values considered in order to transition from the +SERVO_LOCKED to the SERVO_LOCKED_STABLE state. +The transition occurs once the last 'servo_num_offset_values' offsets +are all below the 'servo_offset_threshold' value. +The default value is 10. .TP .B servo_offset_threshold -This value is used by the slave for adjusting the intervals for Sync and Pdelay -request messages. The slave will check the last 'num_offset_values' offsets and -if all those offsets are less than the offset_threshold, it will adjust both -the intervals. The Sync interval is adjusted via the signaling mechanism and -the pdelay request interval is just adjusted locally. The new values to use for -sync message intervals and pdelay request intervals can be indicated by -operLogSyncInterval and operLogPdelayReqInterval respectively. This mechanism -is currently only supported when BMCA == 'noop'. The default -value of offset_threshold is 0 (disabled). +The offset threshold used in order to transition from the SERVO_LOCKED +to the SERVO_LOCKED_STABLE state. The transition occurs once the last +'servo_num_offset_values' offsets are all below the threshold value. +The default value of offset_threshold is 0 (disabled). .SH UNICAST DISCOVERY OPTIONS