diff --git a/config.c b/config.c index b5cf397..747a735 100644 --- a/config.c +++ b/config.c @@ -451,8 +451,8 @@ static int config_switch_unicast_mtab(struct config *cfg, int idx, int line_num) return 0; } -static int config_unicast_mtab_address(enum transport_type type, char *address, - int line_num) +static int config_unicast_mtab_address_prio(enum transport_type type, char *address, + int line_num, unsigned char prio) { struct unicast_master_address *item; @@ -472,6 +472,7 @@ static int config_unicast_mtab_address(enum transport_type type, char *address, } memset(&item->portIdentity, 0xff, sizeof(item->portIdentity)); item->type = type; + item->localPriority = prio; STAILQ_INSERT_TAIL(¤t_uc_mtab->addrs, item, list); current_uc_mtab->count++; @@ -662,7 +663,7 @@ static int parse_unicast_mtab_line(struct config *cfg, char *line, int line_num) char address[64 + 1] = {0}, transport[16 + 1] = {0}; enum transport_type type = TRANS_UDS; struct config_enum *cte; - int cnt, lqi, table_id; + int cnt, lqi, table_id, prio; cnt = sscanf(line, " table_id %d", &table_id); if (cnt == 1) { @@ -676,18 +677,27 @@ static int parse_unicast_mtab_line(struct config *cfg, char *line, int line_num) if (cnt == 1) { return config_unicast_mtab_peer(address, line_num); } - cnt = sscanf(line, " %16s %64s", transport, address); - if (cnt != 2) { + cnt = sscanf(line, " %16s %64s %d", transport, address, &prio); + if (cnt < 2) { fprintf(stderr, "bad master table at line %d\n", line_num); return -1; } + if (cnt == 3 && (prio < 0 || prio > 255)) { + fprintf(stderr, "bad address priority(%d) at line %d\n", prio, line_num); + prio = 0; + } + if (cnt == 2) { + fprintf(stderr, "address priority is not parsed at line %d\n", line_num); + prio = 0; + } + for (cte = nw_trans_enu; cte->label; cte++) { if (!strcasecmp(cte->label, transport)) { type = cte->value; break; } } - return config_unicast_mtab_address(type, address, line_num); + return config_unicast_mtab_address_prio(type, address, line_num, prio); } static enum parser_result parse_setting_line(char *line, diff --git a/mtab.h b/mtab.h index 949929f..412bcc9 100644 --- a/mtab.h +++ b/mtab.h @@ -37,6 +37,7 @@ struct unicast_master_address { unsigned int granted; unsigned int sydymsk; time_t renewal_tmo; + unsigned char localPriority; }; struct unicast_master_table { diff --git a/port.c b/port.c index c3a06c8..eaf77e6 100644 --- a/port.c +++ b/port.c @@ -80,7 +80,8 @@ static void announce_to_dataset(struct ptp_message *m, struct port *p, out->identity = a->grandmasterIdentity; out->quality = a->grandmasterClockQuality; out->priority2 = a->grandmasterPriority2; - out->localPriority = p->localPriority; + if (!out->localPriority) + out->localPriority = p->localPriority; out->stepsRemoved = a->stepsRemoved; out->sender = m->header.sourcePortIdentity; out->receiver = p->portIdentity; @@ -405,6 +406,9 @@ static int add_foreign_master(struct port *p, struct ptp_message *m) LIST_INSERT_HEAD(&p->foreign_masters, fc, list); fc->port = p; fc->dataset.sender = m->header.sourcePortIdentity; + fc->dataset.localPriority = unicast_client_get_priority(p, m); + pr_notice("%s: new foreign master %s with prio %d", p->log_name, + pid2str(&fc->dataset.sender), fc->dataset.localPriority); /* We do not count this first message, see 9.5.3(b) */ return 0; } diff --git a/unicast_client.c b/unicast_client.c index 5bb383f..71dd18e 100644 --- a/unicast_client.c +++ b/unicast_client.c @@ -619,3 +619,14 @@ out: msg_put(msg); return err; } + +unsigned char unicast_client_get_priority(struct port *p, struct ptp_message *m) +{ + struct unicast_master_address *ucma; + + ucma = unicast_client_ok(p, m); + if (!ucma) { + return 0; + } + return p->localPriority + ucma->localPriority; +} diff --git a/unicast_client.h b/unicast_client.h index 18a12c8..9d21a8a 100644 --- a/unicast_client.h +++ b/unicast_client.h @@ -90,7 +90,7 @@ int unicast_client_timer(struct port *p); * @return One (1) if the message is from an entry in the unicast * master table, or zero otherwise. */ -int unicast_client_msg_is_from_master_table_entry(struct port *p, +int unicast_client_msg_is_from_master_table_entry(struct port *p, struct ptp_message *m); /** @@ -101,4 +101,12 @@ int unicast_client_msg_is_from_master_table_entry(struct port *p, */ int unicast_client_tx_cancel(struct port *p, struct unicast_master_address *dst); + +/** + * Return local priority configured for unicast client + * @param p The port on which the signaling message was received. + * @param m The signaling message containing the announce. + * @return Unicast client local priority if configured otherwise zero. + */ +unsigned char unicast_client_get_priority(struct port *p, struct ptp_message *m); #endif