From 769761d6a256f3135d9ee22a0ca7ba425e1c87ca Mon Sep 17 00:00:00 2001 From: Shuotian Cheng Date: Fri, 22 Apr 2016 18:40:13 -0700 Subject: [PATCH] portsyncd: Adding ConfigDone notification in portsyncd As most of the applications depend on port initialization, we add a 'ConfigDone' notification in portsyncd after finishing reading the file 'port_config.ini'. Before orchagent receives this notification, all other tasks from other applications are stored without actually being executed. Only when the orchagent get this notification will all other tasks been executed. Signed-off-by: Shuotian Cheng --- orchagent/intfsorch.cpp | 3 +++ orchagent/neighorch.cpp | 3 +++ orchagent/portsorch.cpp | 19 +++++++++++++++++++ orchagent/portsorch.h | 3 +++ orchagent/routeorch.cpp | 3 +++ portsyncd/portsyncd.cpp | 15 ++++++++++++++- 6 files changed, 45 insertions(+), 1 deletion(-) diff --git a/orchagent/intfsorch.cpp b/orchagent/intfsorch.cpp index 89887d0ad9f..5c30197c25e 100644 --- a/orchagent/intfsorch.cpp +++ b/orchagent/intfsorch.cpp @@ -25,6 +25,9 @@ void IntfsOrch::doTask(Consumer &consumer) if (consumer.m_toSync.empty()) return; + if (!m_portsOrch->isInitDone()) + return; + auto it = consumer.m_toSync.begin(); while (it != consumer.m_toSync.end()) { diff --git a/orchagent/neighorch.cpp b/orchagent/neighorch.cpp index d24a308bff0..ebb701e1a7d 100644 --- a/orchagent/neighorch.cpp +++ b/orchagent/neighorch.cpp @@ -12,6 +12,9 @@ void NeighOrch::doTask(Consumer &consumer) if (consumer.m_toSync.empty()) return; + if (!m_portsOrch->isInitDone()) + return; + auto it = consumer.m_toSync.begin(); while (it != consumer.m_toSync.end()) { diff --git a/orchagent/portsorch.cpp b/orchagent/portsorch.cpp index 5cfce1ff4ae..044807d323a 100644 --- a/orchagent/portsorch.cpp +++ b/orchagent/portsorch.cpp @@ -179,6 +179,25 @@ void PortsOrch::doTask(Consumer &consumer) string alias = kfvKey(t); string op = kfvOp(t); + /* Get notification from application */ + /* portsyncd application: + * When portsorch receives 'ConfigDone' message, it indicates port initialization + * procedure is done. Before port initialization procedure, none of other tasks + * are executed. + */ + if (alias == "ConfigDone") + { + /* portsyncd restarting case: + * When portsyncd restarts, duplicate notifications may be received. + */ + if (m_initDone) + return; + + m_initDone = true; + SWSS_LOG_INFO("Get ConfigDone notification from portsyncd.\n"); + return; + } + if (op == "SET") { set lane_set; diff --git a/orchagent/portsorch.h b/orchagent/portsorch.h index 853d325fe8f..1ebbbab18dc 100644 --- a/orchagent/portsorch.h +++ b/orchagent/portsorch.h @@ -13,11 +13,14 @@ class PortsOrch : public Orch public: PortsOrch(DBConnector *db, string tableName); + inline bool isInitDone() { return m_initDone; } + bool getPort(string alias, Port &p); bool setPortAdminStatus(sai_object_id_t id, bool up); private: + bool m_initDone = false; sai_object_id_t m_cpuPort; sai_uint32_t m_portCount; diff --git a/orchagent/routeorch.cpp b/orchagent/routeorch.cpp index cdba76a61f6..1e17f1fa8e3 100644 --- a/orchagent/routeorch.cpp +++ b/orchagent/routeorch.cpp @@ -14,6 +14,9 @@ void RouteOrch::doTask(Consumer& consumer) if (consumer.m_toSync.empty()) return; + if (!m_portsOrch->isInitDone()) + return; + auto it = consumer.m_toSync.begin(); while (it != consumer.m_toSync.end()) { diff --git a/portsyncd/portsyncd.cpp b/portsyncd/portsyncd.cpp index 240f20c84eb..ad869242e6c 100644 --- a/portsyncd/portsyncd.cpp +++ b/portsyncd/portsyncd.cpp @@ -56,6 +56,8 @@ int main(int argc, char **argv) return EXIT_FAILURE; } + cout << "Read port configuration file..." << endl; + string line; while (getline(infile, line)) { @@ -73,6 +75,17 @@ int main(int argc, char **argv) p.set(alias, attrs); } + infile.close(); + + /* + * After finishing reading port configuration file, this daemon shall send + * out a signal to orchagent indicating port initialization procedure is + * done and other application could start syncing. + */ + FieldValueTuple finish_notice("lanes", "0"); + vector attrs = { finish_notice }; + p.set("ConfigDone", attrs); + LinkSync sync(&db); NetDispatcher::getInstance().registerMessageHandler(RTM_NEWLINK, &sync); NetDispatcher::getInstance().registerMessageHandler(RTM_DELLINK, &sync); @@ -85,7 +98,7 @@ int main(int argc, char **argv) Select s; netlink.registerGroup(RTNLGRP_LINK); - cout << "Listens to link messages..." << endl; + cout << "Listen to link messages..." << endl; netlink.dumpRequest(RTM_GETLINK); s.addSelectable(&netlink);