diff --git a/dist/rootfs/etc/openlan/switch/network/ceci.json.example b/dist/rootfs/etc/openlan/switch/network/ceci.json.example new file mode 100755 index 0000000..1a80a3c --- /dev/null +++ b/dist/rootfs/etc/openlan/switch/network/ceci.json.example @@ -0,0 +1,20 @@ +{ + "name": "ceci", + "provider": "ceci", + "specifies": { + "tcp": [ + { + "listen": "0.0.0.0:80", + "target": [ + "192.168.1.11:80", + "192.168.1.12:80" + ] + } + ], + "http": [ + { + "listen": "0.0.0.0:80" + } + ] + } +} \ No newline at end of file diff --git a/dist/rootfs/var/openlan/script/switch.sh b/dist/rootfs/var/openlan/script/switch.sh index ae818d7..e99bee0 100755 --- a/dist/rootfs/var/openlan/script/switch.sh +++ b/dist/rootfs/var/openlan/script/switch.sh @@ -14,15 +14,20 @@ sysctl -p /etc/sysctl.d/90-openlan.conf /usr/bin/env find /var/openlan/openvpn -name '*client.ovpn' -delete /usr/bin/env find /var/openlan/openvpn -name '*client.tmpl' -delete -if [ ! -e /etc/openlan/switch/switch.yaml ]; then - cat > /etc/openlan/switch/switch.yaml << EOF -crypt - secret: cb2ff088a34d +cs_dir="/etc/openlan/switch" + +if [ ! -e $cs_dir/switch.json ]; then + cat > $cs_dir/switch.json << EOF +{ + "crypt": { + "secret": "cb2ff088a34d" + } +} EOF fi -if [ ! -e /etc/openlan/switch/network/ipsec.json ]; then - cat > /etc/openlan/switch/network/ipsec.json << EOF +if [ ! -e $cs_dir/network/ipsec.json ]; then + cat > $cs_dir/network/ipsec.json << EOF { "name": "ipsec", "provider": "ipsec" @@ -30,8 +35,8 @@ if [ ! -e /etc/openlan/switch/network/ipsec.json ]; then EOF fi -if [ ! -e /etc/openlan/switch/network/bgp.json ]; then - cat > /etc/openlan/switch/network/bgp.json << EOF +if [ ! -e $cs_dir/network/bgp.json ]; then + cat > $cs_dir/network/bgp.json << EOF { "name": "bgp", "provider": "bgp" @@ -39,11 +44,20 @@ if [ ! -e /etc/openlan/switch/network/bgp.json ]; then EOF fi +if [ ! -e $cs_dir/network/proxy.json ]; then + cat > $cs_dir/network/proxy.json << EOF +{ + "name": "proxy", + "provider": "proxy" +} +EOF +fi + for dir in acl findhop link output route network qos dnat; do - if [ -e "/etc/openlan/switch/$dir" ]; then + if [ -e "$cs_dir/$dir" ]; then continue fi - mkdir -p "/etc/openlan/switch/$dir" + mkdir -p "$cs_dir/$dir" done # wait ipsec service @@ -54,4 +68,4 @@ while true; do sleep 5 done -exec /usr/bin/openlan-switch -conf:dir /etc/openlan/switch -log:level 20 +exec /usr/bin/openlan-switch -conf:dir $cs_dir -log:level 20 diff --git a/pkg/config/ceci.go b/pkg/config/ceci.go new file mode 100644 index 0000000..9426180 --- /dev/null +++ b/pkg/config/ceci.go @@ -0,0 +1,99 @@ +package config + +import "fmt" + +type CeciTcp struct { + Name string `json:"-" yaml:"-"` + Listen string `json:"listen" yaml:"listen"` + Target []string `json:"target,omitempty" yaml:"target,omitempty"` +} + +func (s *CeciTcp) Correct() { +} + +func (s *CeciTcp) Id() string { + return fmt.Sprintf("%s", s.Listen) +} + +type CeciHttp struct { + Name string `json:"-" yaml:"-"` + Listen string `json:"listen" yaml:"listen"` +} + +func (s *CeciHttp) Correct() { +} + +func (s *CeciHttp) Id() string { + return fmt.Sprintf("%s", s.Listen) +} + +type CeciSpecifies struct { + Name string `json:"-" yaml:"-"` + Tcp []*CeciTcp `json:"tcp" yaml:"tcp"` + Http []*CeciHttp `json:"http" yaml:"http"` +} + +func (s *CeciSpecifies) Correct() { + if s.Tcp == nil { + s.Tcp = make([]*CeciTcp, 0) + } + for _, t := range s.Tcp { + t.Correct() + } + if s.Http == nil { + s.Http = make([]*CeciHttp, 0) + } + for _, t := range s.Http { + t.Correct() + } +} + +func (s *CeciSpecifies) FindTcp(value *CeciTcp) (*CeciTcp, int) { + for index, obj := range s.Tcp { + if obj.Id() == value.Id() { + return obj, index + } + } + return nil, -1 +} + +func (s *CeciSpecifies) AddTcp(value *CeciTcp) bool { + _, find := s.FindTcp(value) + if find == -1 { + s.Tcp = append(s.Tcp, value) + } + return find == -1 +} + +func (s *CeciSpecifies) DelTcp(value *CeciTcp) (*CeciTcp, bool) { + obj, find := s.FindTcp(value) + if find != -1 { + s.Tcp = append(s.Tcp[:find], s.Tcp[find+1:]...) + } + return obj, find != -1 +} + +func (s *CeciSpecifies) FindHttp(value *CeciHttp) (*CeciHttp, int) { + for index, obj := range s.Http { + if obj.Id() == value.Id() { + return obj, index + } + } + return nil, -1 +} + +func (s *CeciSpecifies) AddHttp(value *CeciHttp) bool { + _, find := s.FindHttp(value) + if find == -1 { + s.Http = append(s.Http, value) + } + return find == -1 +} + +func (s *CeciSpecifies) DelHttp(value *CeciHttp) (*CeciHttp, bool) { + obj, find := s.FindHttp(value) + if find != -1 { + s.Http = append(s.Http[:find], s.Http[find+1:]...) + } + return obj, find != -1 +} diff --git a/pkg/config/network.go b/pkg/config/network.go index 44f3e0b..18d6d80 100755 --- a/pkg/config/network.go +++ b/pkg/config/network.go @@ -58,6 +58,8 @@ func (n *Network) NewSpecifies() any { n.Specifies = &RouterSpecifies{} case "bgp": n.Specifies = &BgpSpecifies{} + case "ceci": + n.Specifies = &CeciSpecifies{} default: n.Specifies = nil } @@ -92,6 +94,12 @@ func (n *Network) Correct(sw *Switch) { obj.Correct() obj.Name = n.Name } + case "ceci": + spec := n.Specifies + if obj, ok := spec.(*CeciSpecifies); ok { + obj.Correct() + obj.Name = n.Name + } default: br := n.Bridge br.Network = n.Name @@ -186,6 +194,7 @@ func (n *Network) Save() { obj.Outputs = nil obj.Dnat = nil obj.FindHop = nil + if err := libol.MarshalSave(&obj, obj.File, true); err != nil { libol.Error("Network.Save %s %s", obj.Name, err) } diff --git a/pkg/switch/ceci_linux.go b/pkg/switch/ceci_linux.go new file mode 100644 index 0000000..230c05e --- /dev/null +++ b/pkg/switch/ceci_linux.go @@ -0,0 +1,94 @@ +package cswitch + +import ( + "os/exec" + + "github.com/luscis/openlan/pkg/api" + co "github.com/luscis/openlan/pkg/config" + "github.com/luscis/openlan/pkg/libol" +) + +const ( + CeciBin = "/usr/bin/openceci" +) + +type CeciWorker struct { + *WorkerImpl + spec *co.CeciSpecifies +} + +func NewCeciWorker(c *co.Network) *CeciWorker { + w := &CeciWorker{ + WorkerImpl: NewWorkerApi(c), + } + w.spec, _ = c.Specifies.(*co.CeciSpecifies) + return w +} + +func (w *CeciWorker) Initialize() { + w.out.Info("CeciWorker.Initialize") +} + +func (w *CeciWorker) reloadTcp(obj *co.CeciTcp) { + name := "/var/openlan/ceci/" + obj.Id() + out, err := libol.CreateFile(name + ".log") + if err != nil { + w.out.Warn("CeciWorker.reloadTcp: %s", err) + return + } + + libol.MarshalSave(obj, name+".yaml", true) + libol.Go(func() { + w.out.Info("CeciWorker.reloadTcp: %s", obj.Id()) + cmd := exec.Command(CeciBin, "-mode", "tcp", "-conf", name+".yaml") + cmd.Stdout = out + cmd.Stderr = out + if err := cmd.Run(); err != nil { + w.out.Warn("CeciWorker.reloadTcp: %s", err) + return + } + }) +} + +func (w *CeciWorker) reloadHttp(obj *co.CeciHttp) { + name := "/var/openlan/ceci/" + obj.Id() + out, err := libol.CreateFile(name + ".log") + if err != nil { + w.out.Warn("CeciWorker.reloadTcp: %s", err) + return + } + + libol.MarshalSave(obj, name+".yaml", true) + libol.Go(func() { + w.out.Info("CeciWorker.reloadHttp: %s", obj.Id()) + cmd := exec.Command(CeciBin, "-mode", "http", "-conf", name+".yaml") + cmd.Stdout = out + cmd.Stderr = out + if err := cmd.Run(); err != nil { + w.out.Warn("CeciWorker.reloadHttp: %s", err) + return + } + }) +} + +func (w *CeciWorker) Start(v api.SwitchApi) { + w.uuid = v.UUID() + w.out.Info("CeciWorker.Start") + + for _, obj := range w.spec.Tcp { + w.reloadTcp(obj) + } + for _, obj := range w.spec.Http { + w.reloadHttp(obj) + } +} + +func (w *CeciWorker) Stop() { + w.out.Info("CeciWorker.Stop") +} + +func (w *CeciWorker) Reload(v api.SwitchApi) { + w.Stop() + w.Initialize() + w.Start(v) +} diff --git a/pkg/switch/network_linux.go b/pkg/switch/network_linux.go index 3fac68c..930e3aa 100755 --- a/pkg/switch/network_linux.go +++ b/pkg/switch/network_linux.go @@ -32,6 +32,10 @@ func NewNetworker(c *co.Network) api.NetworkApi { obj = bgper case "router": obj = NewRouterWorker(c) + case "ceci": + cecer := NewCeciWorker(c) + //api.Call.SetBgper(bgper) + obj = cecer default: obj = NewOpenLANWorker(c) } diff --git a/pkg/switch/openvpn.go b/pkg/switch/openvpn_linux.go similarity index 100% rename from pkg/switch/openvpn.go rename to pkg/switch/openvpn_linux.go diff --git a/pkg/switch/openvpn_test.go b/pkg/switch/openvpn_test_linux.go similarity index 100% rename from pkg/switch/openvpn_test.go rename to pkg/switch/openvpn_test_linux.go