blob: 7f4fad503a9fa289eca382fee745be0965bdaaef [file] [log] [blame]
Stephane Barbariea188d942018-10-16 16:43:04 -04001/*
2 * Copyright 2018-present Open Networking Foundation
3
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7
8 * http://www.apache.org/licenses/LICENSE-2.0
9
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16package model
17
18import (
19 "github.com/opencord/voltha-go/common/log"
20 "runtime/debug"
21 "sync"
22 "time"
23)
24
25type _singletonProxyAccessControl struct {
26 Cache sync.Map
27}
28
29var _instanceProxyAccessControl *_singletonProxyAccessControl
30var _onceProxyAccessControl sync.Once
31
32func GetProxyAccessControl() *_singletonProxyAccessControl {
33 _onceProxyAccessControl.Do(func() {
34 _instanceProxyAccessControl = &_singletonProxyAccessControl{}
35 })
36 return _instanceProxyAccessControl
37}
38
39type ProxyAccessControl interface {
40 Get(path string, depth int, deep bool, txid string, control bool) interface{}
41 Update(path string, data interface{}, strict bool, txid string, control bool) interface{}
42 Add(path string, data interface{}, txid string, control bool) interface{}
43 Remove(path string, txid string, control bool) interface{}
44}
45
46type proxyAccessControl struct {
47 //sync.Mutex
48 Proxy *Proxy
49 PathLock chan struct{}
50 Path string
51
52 start time.Time
53 stop time.Time
54}
55
56func NewProxyAccessControl(proxy *Proxy, path string) ProxyAccessControl {
57 return &proxyAccessControl{
58 Proxy: proxy,
59 Path: path,
60 PathLock: make(chan struct{}, 1),
61 }
62}
63
64func (pac *proxyAccessControl) lock() {
65 log.CleanUp()
66 log.Debugf("Before lock ... pac: %+v, stack = %s", pac, string(debug.Stack()))
67 pac.PathLock <- struct{}{}
68 pac.start = time.Now()
69 log.Debugf("Got lock ... pac: %+v, stack = %s", pac, string(debug.Stack()))
70 //time.Sleep(1 * time.Second)
71 log.Debugf("<<<<< %s >>>>>> locked, stack=%s", pac.Path, string(debug.Stack()))
72}
73func (pac *proxyAccessControl) unlock() {
74 log.CleanUp()
75 log.Debugf("Before unlock ... pac: %+v, stack = %s", pac, string(debug.Stack()))
76 <-pac.PathLock
77 pac.stop = time.Now()
78 GetProfiling().AddToInMemoryLockTime(pac.stop.Sub(pac.start).Seconds())
79 log.Debugf("Got unlock ... pac: %+v, stack = %s", pac, string(debug.Stack()))
80 log.Debugf("<<<<< %s >>>>>> unlocked, stack=%s", pac.Path, string(debug.Stack()))
81}
82
83func (pac *proxyAccessControl) Get(path string, depth int, deep bool, txid string, control bool) interface{} {
84 if control {
85 pac.lock()
86 defer pac.unlock()
87 log.Debugf("controlling get, stack = %s", string(debug.Stack()))
88 }
89 pac.Proxy.Root.Proxy = pac.Proxy
90 return pac.Proxy.Root.Get(path, "", depth, deep, txid)
91}
92func (pac *proxyAccessControl) Update(path string, data interface{}, strict bool, txid string, control bool) interface{} {
93 if control {
94 pac.lock()
95 defer pac.unlock()
96 log.Debugf("controlling update, stack = %s", string(debug.Stack()))
97 }
98 pac.Proxy.Root.Proxy = pac.Proxy
99 return pac.Proxy.Root.Update(path, data, strict, txid, nil)
100}
101func (pac *proxyAccessControl) Add(path string, data interface{}, txid string, control bool) interface{} {
102 if control {
103 pac.lock()
104 defer pac.unlock()
105 log.Debugf("controlling add, stack = %s", string(debug.Stack()))
106 }
107 pac.Proxy.Root.Proxy = pac.Proxy
108 return pac.Proxy.Root.Add(path, data, txid, nil)
109}
110func (pac *proxyAccessControl) Remove(path string, txid string, control bool) interface{} {
111 if control {
112 pac.lock()
113 defer pac.unlock()
114 log.Debugf("controlling remove, stack = %s", string(debug.Stack()))
115 }
116 pac.Proxy.Root.Proxy = pac.Proxy
117 return pac.Proxy.Root.Remove(path, txid, nil)
118}