VOL-1156 Re-factor openolt driver

Allows re-use of common code among backends for multiple hardware
and simulators.

Change-Id: If5f0147d2eef7c1f9cbcda394d06a2070b4be275
diff --git a/Makefile b/Makefile
index 2928a1b..ea3f452 100644
--- a/Makefile
+++ b/Makefile
@@ -175,7 +175,7 @@
 ##
 OPENOLT_PROTOS_DIR = ./protos
 OPENOLT_API_LIB = $(OPENOLT_PROTOS_DIR)/libopenoltapi.a
-CXXFLAGS += -I./$(OPENOLT_PROTOS_DIR) -I $(OPENOLT_PROTOS_DIR)/googleapis/gens
+CXXFLAGS += -I$(OPENOLT_PROTOS_DIR) -I$(OPENOLT_PROTOS_DIR)/googleapis/gens
 protos:
 	make -C $(OPENOLT_PROTOS_DIR) all
 protos-clean:
@@ -184,23 +184,36 @@
 ########################################################################
 ##
 ##
-##        openoltsim
+##        common
 ##
 ##
-SIM_SRCS = $(wildcard openoltsim/*.cc)
-SIM_OBJS = $(SIM_SRCS:.cc=.o)
-SIM_DEPS = $(SIM_SRCS:.cc=.d)
-openoltsim: $(BUILD_DIR)/openoltsim
-$(BUILD_DIR)/openoltsim: protos $(SIM_OBJS)
-	$(CXX) -pthread -L/usr/local/lib $(SIM_OBJS) $(OPENOLT_API_LIB) /usr/local/lib/libprotobuf.a -o $@ -lgrpc++ -lgrpc -lpthread -ldl
+common/%.o: common/%.cc
+	$(CXX) $(CXXFLAGS) -I./common -c $< -o $@
 
 ########################################################################
 ##
 ##
-##        Main
+##        sim
 ##
 ##
-SRCS = $(wildcard src/*.cc)
+SIM_SRCS = $(wildcard sim/*.cc) $(wildcard common/*.cc)
+SIM_OBJS = $(SIM_SRCS:.cc=.o)
+SIM_DEPS = $(SIM_SRCS:.cc=.d)
+sim: sim/openoltsim
+sim/openoltsim: protos $(SIM_OBJS)
+	$(CXX) -pthread -L/usr/local/lib $(SIM_OBJS) $(OPENOLT_API_LIB) /usr/local/lib/libprotobuf.a -o $@ -lgrpc++ -lgrpc -lpthread -ldl
+sim/%.o: sim/%.cc
+	$(CXX) -std=c++11 -fpermissive -Wno-literal-suffix -I./common -I$(OPENOLT_PROTOS_DIR) -I$(OPENOLT_PROTOS_DIR)/googleapis/gens -c $< -o $@
+clean-sim:
+	rm -f sim/openoltsim $(SIM_OBJS) $(SIM_DEPS)
+
+########################################################################
+##
+##
+##        openolt
+##
+##
+SRCS = $(wildcard src/*.cc) $(wildcard common/*.cc)
 OBJS = $(SRCS:.cc=.o)
 DEPS = $(SRCS:.cc=.d)
 .DEFAULT_GOAL := all
@@ -212,6 +225,8 @@
 	ln -sf $(PWD)/$(BAL_DIR)/bal_release/build/core/src/apps/bal_core_dist/bal_core_dist $(BUILD_DIR)/.
 	ln -sf $(shell ldconfig -p | grep libgrpc.so.6 | tr ' ' '\n' | grep /) $(BUILD_DIR)/libgrpc.so.6
 	ln -sf $(shell ldconfig -p | grep libgrpc++.so.1 | tr ' ' '\n' | grep /) $(BUILD_DIR)/libgrpc++.so.1
+src/%.o: src/%.cc
+	$(CXX) $(CXXFLAGS) -I./common -c $< -o $@
 
 deb:
 	cp $(BUILD_DIR)/release_$(DEVICE)_V$(BAL_MAJOR_VER).$(ACCTON_VER).tar.gz mkdebian/debian
@@ -251,4 +266,4 @@
 distclean:
 	rm -rf $(BUILD_DIR)
 
-.PHONY: onl sdk bal protos prereq openoltsim
+.PHONY: onl sdk bal protos prereq sim
diff --git a/src/Queue.h b/common/Queue.h
similarity index 100%
rename from src/Queue.h
rename to common/Queue.h
diff --git a/src/core.h b/common/core.h
similarity index 86%
rename from src/core.h
rename to common/core.h
index b0c3b5f..be32f00 100644
--- a/src/core.h
+++ b/common/core.h
@@ -24,9 +24,11 @@
 
 #include "state.h"
 
+#define COLLECTION_PERIOD 15
+
 extern State state;
 
-Status Enable_();
+Status Enable_(int argc, char *argv[]);
 Status ActivateOnu_(uint32_t intf_id, uint32_t onu_id,
     const char *vendor_id, const char *vendor_specific, uint32_t pir);
 Status DeactivateOnu_(uint32_t intf_id, uint32_t onu_id,
@@ -50,16 +52,5 @@
 Status Disable_();
 Status Reenable_();
 
-
-static Status SchedAdd_(int intf_id, int onu_id, int agg_port_id);
-static Status SchedRemove_(int intf_id, int onu_id, int agg_port_id);
-
-static inline int mk_sched_id(int onu_id) {
-    return 1023 + onu_id;
-}
-
-static inline int mk_agg_port_id(int onu_id) {
-    return 1023 + onu_id;
-}
-
+void* stats_collection();
 #endif
diff --git a/src/main.cc b/common/main.cc
similarity index 66%
rename from src/main.cc
rename to common/main.cc
index 3c05489..2898219 100644
--- a/src/main.cc
+++ b/common/main.cc
@@ -16,36 +16,12 @@
 */
 #include <iostream>
 
-#include "indications.h"
 #include "server.h"
 #include "core.h"
 
-extern "C"
-{
-#include <bal_api.h>
-#include <bal_api_end.h>
-}
-
 int main(int argc, char** argv) {
 
-/*
-    if (argc < 5) {
-        std::cout << "Missing arguments" << std::endl;
-        exit(1);
-    }
-*/
-
-    bcmbal_init(argc, argv, NULL);
-
-    Status status = SubscribeIndication();
-    if (!status.ok()) {
-        std::cout << "ERROR: SubscribeIndication failed - "
-                  << status.error_code() << ": " << status.error_message()
-                  << std::endl;
-        return 1;
-    }
-
-    status = Enable_();
+    Status status = Enable_(argc, argv);
     if (!status.ok()) {
         std::cout << "ERROR: Enable_ failed - "
                   << status.error_code() << ": " << status.error_message()
@@ -55,5 +31,5 @@
 
     RunServer();
 
-  return 0;
+    return 0;
 }
diff --git a/src/server.cc b/common/server.cc
similarity index 98%
rename from src/server.cc
rename to common/server.cc
index 8cd83ff..54d32ac 100644
--- a/src/server.cc
+++ b/common/server.cc
@@ -27,8 +27,6 @@
 
 #include "server.h"
 #include "core.h"
-#include "indications.h"
-#include "stats_collection.h"
 #include "state.h"
 
 #include <grpc++/grpc++.h>
@@ -43,6 +41,8 @@
 const char *serverPort = "0.0.0.0:9191";
 int signature;
 
+Queue<openolt::Indication> oltIndQ;
+
 class OpenoltService final : public openolt::Openolt::Service {
 
     Status DisableOlt(
diff --git a/src/server.h b/common/server.h
similarity index 100%
rename from src/server.h
rename to common/server.h
diff --git a/src/state.h b/common/state.h
similarity index 100%
rename from src/state.h
rename to common/state.h
diff --git a/openoltsim/Queue.h b/openoltsim/Queue.h
deleted file mode 100644
index 854851e..0000000
--- a/openoltsim/Queue.h
+++ /dev/null
@@ -1,60 +0,0 @@
-//
-// Copyright (c) 2013 Juan Palacios juan.palacios.puyana@gmail.com
-// Subject to the BSD 2-Clause License
-// - see < http://opensource.org/licenses/BSD-2-Clause>
-//
-
-#ifndef CONCURRENT_QUEUE_
-#define CONCURRENT_QUEUE_
-
-#include <queue>
-#include <thread>
-#include <mutex>
-#include <condition_variable>
-
-template <typename T>
-class Queue
-{
- public:
-
-  T pop() 
-  {
-    std::unique_lock<std::mutex> mlock(mutex_);
-    while (queue_.empty())
-    {
-      cond_.wait(mlock);
-    }
-    auto val = queue_.front();
-    queue_.pop();
-    return val;
-  }
-
-  void pop(T& item)
-  {
-    std::unique_lock<std::mutex> mlock(mutex_);
-    while (queue_.empty())
-    {
-      cond_.wait(mlock);
-    }
-    item = queue_.front();
-    queue_.pop();
-  }
-
-  void push(const T& item)
-  {
-    std::unique_lock<std::mutex> mlock(mutex_);
-    queue_.push(item);
-    mlock.unlock();
-    cond_.notify_one();
-  }
-  Queue()=default;
-  Queue(const Queue&) = delete;            // disable copying
-  Queue& operator=(const Queue&) = delete; // disable assignment
-  
- private:
-  std::queue<T> queue_;
-  std::mutex mutex_;
-  std::condition_variable cond_;
-};
-
-#endif
diff --git a/openoltsim/main.cc b/openoltsim/main.cc
deleted file mode 100644
index 652378e..0000000
--- a/openoltsim/main.cc
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
-    Copyright (C) 2018 Open Networking Foundation 
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
-*/
-#include <iostream>
-#include <unistd.h>
-#include <pthread.h>
-
-#include "server.h"
-#include "core.h"
-#include "state.h"
-
-void* RunSim(void *) {
-    while (!state::is_connected()) {
-        sleep(5);
-    }
-
-    // Send Olt up indication
-    {
-        openolt::Indication ind;
-        openolt::OltIndication* olt_ind = new openolt::OltIndication;
-        olt_ind->set_oper_state("up");
-        ind.set_allocated_olt_ind(olt_ind);
-        std::cout << "olt indication, oper_state:" << ind.olt_ind().oper_state() << std::endl;
-        oltIndQ.push(ind);
-    }
-
-    // TODO - Add interface and onu indication events
-}
-
-int main(int argc, char** argv) {
-    pthread_t simThread;
-
-    pthread_create(&simThread, NULL, RunSim, NULL);
-    RunServer();
-
-    return 0;
-}
diff --git a/openoltsim/server.cc b/openoltsim/server.cc
deleted file mode 100644
index 1277798..0000000
--- a/openoltsim/server.cc
+++ /dev/null
@@ -1,222 +0,0 @@
-/*
-    Copyright (C) 2018 Open Networking Foundation
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include <iostream>
-#include <memory>
-#include <string>
-#include <time.h>
-#include <pthread.h>
-
-#include "Queue.h"
-#include <iostream>
-#include <sstream>
-
-#include "server.h"
-#include "core.h"
-#include "state.h"
-
-#include <grpc++/grpc++.h>
-#include <openolt.grpc.pb.h>
-
-using grpc::Server;
-using grpc::ServerBuilder;
-using grpc::ServerContext;
-using grpc::ServerWriter;
-using grpc::Status;
-
-const char *serverPort = "0.0.0.0:9191";
-int signature;
-
-Queue<openolt::Indication> oltIndQ;
-
-class OpenoltService final : public openolt::Openolt::Service {
-
-    Status DisableOlt(
-            ServerContext* context,
-            const openolt::Empty* request,
-            openolt::Empty* response) override {
-        return Disable_();
-    }
-
-    Status ReenableOlt(
-            ServerContext* context,
-            const openolt::Empty* request,
-            openolt::Empty* response) override {
-        return Reenable_();
-    }
-
-    Status ActivateOnu(
-            ServerContext* context,
-            const openolt::Onu* request,
-            openolt::Empty* response) override {
-        return ActivateOnu_(
-            request->intf_id(),
-            request->onu_id(),
-            ((request->serial_number()).vendor_id()).c_str(),
-            ((request->serial_number()).vendor_specific()).c_str(),
-            request->pir());
-    }
-
-    Status DeactivateOnu(
-            ServerContext* context,
-            const openolt::Onu* request,
-            openolt::Empty* response) override {
-        return DeactivateOnu_(
-            request->intf_id(),
-            request->onu_id(),
-            ((request->serial_number()).vendor_id()).c_str(),
-            ((request->serial_number()).vendor_specific()).c_str());
-    }
-
-    Status DeleteOnu(
-            ServerContext* context,
-            const openolt::Onu* request,
-            openolt::Empty* response) override {
-        return DeleteOnu_(
-            request->intf_id(),
-            request->onu_id(),
-            ((request->serial_number()).vendor_id()).c_str(),
-            ((request->serial_number()).vendor_specific()).c_str());
-    }
-
-    Status OmciMsgOut(
-            ServerContext* context,
-            const openolt::OmciMsg* request,
-            openolt::Empty* response) override {
-        return OmciMsgOut_(
-            request->intf_id(),
-            request->onu_id(),
-            request->pkt());
-    }
-
-    Status OnuPacketOut(
-            ServerContext* context,
-            const openolt::OnuPacket* request,
-            openolt::Empty* response) override {
-        return OnuPacketOut_(
-            request->intf_id(),
-            request->onu_id(),
-            request->pkt());
-    }
-
-    Status UplinkPacketOut(
-            ServerContext* context,
-            const openolt::UplinkPacket* request,
-            openolt::Empty* response) override {
-        return UplinkPacketOut_(
-            request->intf_id(),
-            request->pkt());
-    }
-
-    Status FlowAdd(
-            ServerContext* context,
-            const openolt::Flow* request,
-            openolt::Empty* response) override {
-        return FlowAdd_(
-            request->onu_id(),
-            request->flow_id(),
-            request->flow_type(),
-            request->access_intf_id(),
-            request->network_intf_id(),
-            request->gemport_id(),
-            request->priority(),
-            request->classifier(),
-            request->action());
-    }
-
-    Status EnableIndication(
-            ServerContext* context,
-            const ::openolt::Empty* request,
-            ServerWriter<openolt::Indication>* writer) override {
-        std::cout << "Connection to Voltha established. Indications enabled"
-        << std::endl;
-        state::connect();
-
-        while (state::is_connected) {
-            auto oltInd = oltIndQ.pop();
-            bool isConnected = writer->Write(oltInd);
-            if (!isConnected) {
-                //Lost connectivity to this Voltha instance
-                //Put the indication back in the queue for next connecting instance
-                oltIndQ.push(oltInd);
-                state::disconnect();
-            }
-            //oltInd.release_olt_ind()
-        }
-
-        return Status::OK;
-    }
-
-    Status HeartbeatCheck(
-            ServerContext* context,
-            const openolt::Empty* request,
-            openolt::Heartbeat* response) override {
-        response->set_heartbeat_signature(signature);
-
-        return Status::OK;
-    }
-
-    Status EnablePonIf(
-            ServerContext* context,
-            const openolt::Interface* request,
-            openolt::Empty* response) override {
-
-        return EnablePonIf_(request->intf_id());
-    }
-
-    Status DisablePonIf(
-            ServerContext* context,
-            const openolt::Interface* request,
-            openolt::Empty* response) override {
-
-        return DisablePonIf_(request->intf_id());
-    }
-
-    Status Reboot(
-            ServerContext* context,
-            const openolt::Empty* request,
-            openolt::Empty* response) override {
-
-        //system("shutdown -r now");
-
-        return Status::OK;
-
-    }
-
-
-};
-
-void RunServer() {
-  OpenoltService service;
-  std::string server_address(serverPort);
-  ServerBuilder builder;
-
-  builder.AddListeningPort(server_address, grpc::InsecureServerCredentials());
-  builder.RegisterService(&service);
-
-  std::unique_ptr<Server> server(builder.BuildAndStart());
-
-  time_t now;
-  time(&now);
-  signature = (int)now;
-
-  std::cout << "Server listening on " << server_address
-  << ", connection signature : " << signature << std::endl;
-
-
-  server->Wait();
-}
diff --git a/openoltsim/server.h b/openoltsim/server.h
deleted file mode 100644
index 52ef083..0000000
--- a/openoltsim/server.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
-    Copyright (C) 2018 Open Networking Foundation 
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
-*/
-
-#ifndef OPENOLT_SERVER_H_
-#define OPENOLT_SERVER_H_
-
-void RunServer();
-
-#endif
diff --git a/openoltsim/state.cc b/openoltsim/state.cc
deleted file mode 100644
index c3b2966..0000000
--- a/openoltsim/state.cc
+++ /dev/null
@@ -1,41 +0,0 @@
-#include <mutex>
-
-namespace state {
-
-    bool connected_to_voltha = false;
-    bool activated = false;
-    std::mutex state_lock;
-
-    bool is_connected() {
-        return connected_to_voltha;
-    }
-
-    bool is_activated() {
-        return activated;
-    }
-
-    void connect() {
-        state_lock.lock();
-        connected_to_voltha = true;
-        state_lock.unlock();
-    }
-
-    void disconnect() {
-        state_lock.lock();
-        connected_to_voltha = false;
-        state_lock.unlock();
-    }
-
-    void activate() {
-        state_lock.lock();
-        activated = true;
-        state_lock.unlock();
-    }
-
-    void deactivate() {
-        state_lock.lock();
-        activated = false;
-        state_lock.unlock();
-    }
-
-}
diff --git a/openoltsim/state.h b/openoltsim/state.h
deleted file mode 100644
index c392a01..0000000
--- a/openoltsim/state.h
+++ /dev/null
@@ -1,13 +0,0 @@
-#ifndef OPENOLT_STATE_H_
-#define OPENOLT_STATE_H_
-
-namespace state {
-    bool is_activated();
-    bool is_connected();
-    void connect();
-    void disconnect();
-    void activate();
-    void deactivate();
-}
-
-#endif
diff --git a/openoltsim/core.cc b/sim/core.cc
similarity index 75%
rename from openoltsim/core.cc
rename to sim/core.cc
index edba795..ce3d1fa 100644
--- a/openoltsim/core.cc
+++ b/sim/core.cc
@@ -18,14 +18,39 @@
 #include <iostream>
 #include <memory>
 #include <string>
+#include <unistd.h>
 
 #include "Queue.h"
 #include <iostream>
 #include <sstream>
 
 #include "core.h"
+#include "state.h"
 
-Status Enable_() {
+State state;
+
+void* RunSim(void *) {
+    while (!state.is_connected()) {
+        sleep(5);
+    }
+
+    // Send Olt up indication
+    {
+        openolt::Indication ind;
+        openolt::OltIndication* olt_ind = new openolt::OltIndication;
+        olt_ind->set_oper_state("up");
+        ind.set_allocated_olt_ind(olt_ind);
+        std::cout << "olt indication, oper_state:" << ind.olt_ind().oper_state() << std::endl;
+        oltIndQ.push(ind);
+    }
+
+    // TODO - Add interface and onu indication events
+}
+
+Status Enable_(int argc, char *argv[]) {
+    pthread_t simThread;
+
+    pthread_create(&simThread, NULL, RunSim, NULL);
     return Status::OK;
 }
 
@@ -96,3 +121,10 @@
 Status SchedRemove_(int intf_id, int onu_id, int agg_port_id) {
     return Status::OK;
 }
+
+Status FlowRemove_(uint32_t flow_id, const std::string flow_type) {
+    return Status::OK;
+}
+
+void* stats_collection() {
+}
diff --git a/openoltsim/core.h b/sim/core.h
similarity index 97%
rename from openoltsim/core.h
rename to sim/core.h
index ab7fbf7..7db554b 100644
--- a/openoltsim/core.h
+++ b/sim/core.h
@@ -25,7 +25,7 @@
 
 extern Queue<openolt::Indication> oltIndQ;
 
-Status Enable_();
+Status Enable_(int argc, char *argv[]);
 Status ActivateOnu_(uint32_t intf_id, uint32_t onu_id,
     const char *vendor_id, const char *vendor_specific, uint32_t pir);
 Status DeactivateOnu_(uint32_t intf_id, uint32_t onu_id,
diff --git a/src/core.cc b/src/core.cc
index ae54c56..9bdb72d 100644
--- a/src/core.cc
+++ b/src/core.cc
@@ -38,12 +38,34 @@
 
 State state;
 
-Status Enable_() {
+static Status SchedAdd_(int intf_id, int onu_id, int agg_port_id);
+static Status SchedRemove_(int intf_id, int onu_id, int agg_port_id);
+
+static inline int mk_sched_id(int onu_id) {
+    return 1023 + onu_id;
+}
+
+static inline int mk_agg_port_id(int onu_id) {
+    return 1023 + onu_id;
+}
+
+Status Enable_(int argc, char *argv[]) {
     bcmbal_access_terminal_cfg acc_term_obj;
     bcmbal_access_terminal_key key = { };
 
     if (!state.is_activated()) {
         std::cout << "Enable OLT" << std::endl;
+
+        bcmbal_init(argc, argv, NULL);
+
+        Status status = SubscribeIndication();
+        if (!status.ok()) {
+            std::cout << "ERROR: SubscribeIndication failed - "
+                      << status.error_code() << ": " << status.error_message()
+                      << std::endl;
+            return status;
+        }
+
         key.access_term_id = DEFAULT_ATERM_ID;
         BCMBAL_CFG_INIT(&acc_term_obj, access_terminal, key);
         BCMBAL_CFG_PROP_SET(&acc_term_obj, access_terminal, admin_state, BCMBAL_STATE_UP);
diff --git a/src/indications.cc b/src/indications.cc
index 4d7a393..203b675 100644
--- a/src/indications.cc
+++ b/src/indications.cc
@@ -32,7 +32,7 @@
 
 using grpc::Status;
 
-Queue<openolt::Indication> oltIndQ;
+extern Queue<openolt::Indication> oltIndQ;
 //Queue<openolt::Indication*> oltIndQ;
 
 
diff --git a/src/stats_collection.h b/src/stats_collection.h
index 0437634..fe3c27a 100644
--- a/src/stats_collection.h
+++ b/src/stats_collection.h
@@ -8,8 +8,6 @@
 #include <bal_model_types.h>
 }
 
-#define COLLECTION_PERIOD 15
-
 void init_stats();
 void stop_collecting_statistics();
 openolt::PortStatistics* get_default_port_statistics();
@@ -18,7 +16,6 @@
 openolt::FlowStatistics* get_default_flow_statistics();
 openolt::FlowStatistics* collectFlowStatistics(bcmbal_flow_id flow_id, bcmbal_flow_type flow_type);
 #endif
-void* stats_collection();
 void register_new_flow(bcmbal_flow_key key);