• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include <thread>
17 
18 #include "hitrace.h"
19 #include "distributed_object_impl.h"
20 #include "distributed_objectstore_impl.h"
21 #include "objectstore_errors.h"
22 #include "softbus_adapter.h"
23 #include "string_utils.h"
24 
25 namespace OHOS::ObjectStore {
DistributedObjectStoreImpl(FlatObjectStore * flatObjectStore)26 DistributedObjectStoreImpl::DistributedObjectStoreImpl(FlatObjectStore *flatObjectStore)
27     : flatObjectStore_(flatObjectStore)
28 {
29 }
30 
~DistributedObjectStoreImpl()31 DistributedObjectStoreImpl::~DistributedObjectStoreImpl()
32 {
33     delete flatObjectStore_;
34 }
35 
CacheObject(const std::string & sessionId,FlatObjectStore * flatObjectStore)36 DistributedObject *DistributedObjectStoreImpl::CacheObject(
37     const std::string &sessionId, FlatObjectStore *flatObjectStore)
38 {
39     DistributedObjectImpl *object = new (std::nothrow) DistributedObjectImpl(sessionId, flatObjectStore);
40     if (object == nullptr) {
41         return nullptr;
42     }
43     std::unique_lock<std::shared_mutex> cacheLock(dataMutex_);
44     objects_.push_back(object);
45     return object;
46 }
47 
RemoveCacheObject(const std::string & sessionId)48 void DistributedObjectStoreImpl::RemoveCacheObject(const std::string &sessionId)
49 {
50     std::unique_lock<std::shared_mutex> cacheLock(dataMutex_);
51     auto iter = objects_.begin();
52     while (iter != objects_.end()) {
53         if ((*iter)->GetSessionId() == sessionId) {
54             delete *iter;
55             iter = objects_.erase(iter);
56         } else {
57             iter++;
58         }
59     }
60     return;
61 }
62 
CreateObject(const std::string & sessionId)63 DistributedObject *DistributedObjectStoreImpl::CreateObject(const std::string &sessionId)
64 {
65     DataObjectHiTrace trace("DistributedObjectStoreImpl::CreateObject");
66     if (flatObjectStore_ == nullptr) {
67         LOG_ERROR("DistributedObjectStoreImpl::CreateObject store not opened!");
68         return nullptr;
69     }
70 
71     if (sessionId.empty()) {
72         LOG_ERROR("DistributedObjectStoreImpl::CreateObject Invalid sessionId");
73         return nullptr;
74     }
75 
76     uint32_t status = flatObjectStore_->CreateObject(sessionId);
77     if (status != SUCCESS) {
78         LOG_ERROR("DistributedObjectStoreImpl::CreateObject CreateTable err %{public}d", status);
79         return nullptr;
80     }
81     return CacheObject(sessionId, flatObjectStore_);
82 }
83 
CreateObject(const std::string & sessionId,uint32_t & status)84 DistributedObject *DistributedObjectStoreImpl::CreateObject(const std::string &sessionId, uint32_t &status)
85 {
86     DataObjectHiTrace trace("DistributedObjectStoreImpl::CreateObject");
87     if (flatObjectStore_ == nullptr) {
88         LOG_ERROR("DistributedObjectStoreImpl::CreateObject store not opened!");
89         status = ERR_NULL_OBJECTSTORE;
90         return nullptr;
91     }
92 
93     if (sessionId.empty()) {
94         LOG_ERROR("DistributedObjectStoreImpl::CreateObject Invalid sessionId");
95         status = ERR_INVALID_ARGS;
96         return nullptr;
97     }
98 
99     status = flatObjectStore_->CreateObject(sessionId);
100     if (status != SUCCESS) {
101         LOG_ERROR("DistributedObjectStoreImpl::CreateObject CreateTable err %{public}d", status);
102         return nullptr;
103     }
104     return CacheObject(sessionId, flatObjectStore_);
105 }
106 
DeleteObject(const std::string & sessionId)107 uint32_t DistributedObjectStoreImpl::DeleteObject(const std::string &sessionId)
108 {
109     DataObjectHiTrace trace("DistributedObjectStoreImpl::DeleteObject");
110     if (flatObjectStore_ == nullptr) {
111         LOG_ERROR("DistributedObjectStoreImpl::Sync object err ");
112         return ERR_NULL_OBJECTSTORE;
113     }
114     uint32_t status = flatObjectStore_->Delete(sessionId);
115     if (status != SUCCESS) {
116         LOG_ERROR("DistributedObjectStoreImpl::DeleteObject store delete err %{public}d", status);
117         return status;
118     }
119     RemoveCacheObject(sessionId);
120     return SUCCESS;
121 }
122 
Get(const std::string & sessionId,DistributedObject ** object)123 uint32_t DistributedObjectStoreImpl::Get(const std::string &sessionId, DistributedObject **object)
124 {
125     auto iter = objects_.begin();
126     while (iter != objects_.end()) {
127         if ((*iter)->GetSessionId() == sessionId) {
128             *object = *iter;
129             return SUCCESS;
130         }
131         iter++;
132     }
133     LOG_ERROR("DistributedObjectStoreImpl::Get object err, no object");
134     return ERR_GET_OBJECT;
135 }
136 
Watch(DistributedObject * object,std::shared_ptr<ObjectWatcher> watcher)137 uint32_t DistributedObjectStoreImpl::Watch(DistributedObject *object, std::shared_ptr<ObjectWatcher> watcher)
138 {
139     if (object == nullptr) {
140         LOG_ERROR("DistributedObjectStoreImpl::Sync object err ");
141         return ERR_NULL_OBJECT;
142     }
143     if (flatObjectStore_ == nullptr) {
144         LOG_ERROR("DistributedObjectStoreImpl::Sync object err ");
145         return ERR_NULL_OBJECTSTORE;
146     }
147     std::lock_guard<std::mutex> lock(watchersLock_);
148     if (watchers_.count(object) != 0) {
149         LOG_ERROR("DistributedObjectStoreImpl::Watch already gets object");
150         return ERR_EXIST;
151     }
152     std::shared_ptr<WatcherProxy> watcherProxy = std::make_shared<WatcherProxy>(watcher, object->GetSessionId());
153     uint32_t status = flatObjectStore_->Watch(object->GetSessionId(), watcherProxy);
154     if (status != SUCCESS) {
155         LOG_ERROR("DistributedObjectStoreImpl::Watch failed %{public}d", status);
156         return status;
157     }
158     watchers_.insert_or_assign(object, watcherProxy);
159     LOG_INFO("DistributedObjectStoreImpl:Watch object success.");
160     return SUCCESS;
161 }
162 
UnWatch(DistributedObject * object)163 uint32_t DistributedObjectStoreImpl::UnWatch(DistributedObject *object)
164 {
165     if (object == nullptr) {
166         LOG_ERROR("DistributedObjectStoreImpl::Sync object err ");
167         return ERR_NULL_OBJECT;
168     }
169     if (flatObjectStore_ == nullptr) {
170         LOG_ERROR("DistributedObjectStoreImpl::Sync object err ");
171         return ERR_NULL_OBJECTSTORE;
172     }
173     uint32_t status = flatObjectStore_->UnWatch(object->GetSessionId());
174     if (status != SUCCESS) {
175         LOG_ERROR("DistributedObjectStoreImpl::Watch failed %{public}d", status);
176         return status;
177     }
178     std::lock_guard<std::mutex> lock(watchersLock_);
179     watchers_.erase(object);
180     LOG_INFO("DistributedObjectStoreImpl:UnWatch object success.");
181     return SUCCESS;
182 }
183 
SetStatusNotifier(std::shared_ptr<StatusNotifier> notifier)184 uint32_t DistributedObjectStoreImpl::SetStatusNotifier(std::shared_ptr<StatusNotifier> notifier)
185 {
186     if (flatObjectStore_ == nullptr) {
187         LOG_ERROR("DistributedObjectStoreImpl::Sync object err ");
188         return ERR_NULL_OBJECTSTORE;
189     }
190     std::shared_ptr<StatusNotifierProxy> watcherProxy = std::make_shared<StatusNotifierProxy>(notifier);
191     return flatObjectStore_->SetStatusNotifier(watcherProxy);
192 }
193 
NotifyCachedStatus(const std::string & sessionId)194 void DistributedObjectStoreImpl::NotifyCachedStatus(const std::string &sessionId)
195 {
196     flatObjectStore_->CheckRetrieveCache(sessionId);
197 }
198 
WatcherProxy(const std::shared_ptr<ObjectWatcher> objectWatcher,const std::string & sessionId)199 WatcherProxy::WatcherProxy(const std::shared_ptr<ObjectWatcher> objectWatcher, const std::string &sessionId)
200     : FlatObjectWatcher(sessionId), objectWatcher_(objectWatcher)
201 {
202 }
203 
OnChanged(const std::string & sessionid,const std::vector<std::string> & changedData)204 void WatcherProxy::OnChanged(const std::string &sessionid, const std::vector<std::string> &changedData)
205 {
206     objectWatcher_->OnChanged(sessionid, changedData);
207 }
208 
GetInstance(const std::string & bundleName)209 DistributedObjectStore *DistributedObjectStore::GetInstance(const std::string &bundleName)
210 {
211     static std::mutex instLock_;
212     static DistributedObjectStore *instPtr = nullptr;
213     if (instPtr == nullptr) {
214         std::lock_guard<std::mutex> lock(instLock_);
215         if (instPtr == nullptr && !bundleName.empty()) {
216             LOG_INFO("new objectstore %{public}s", bundleName.c_str());
217             FlatObjectStore *flatObjectStore = new (std::nothrow) FlatObjectStore(bundleName);
218             if (flatObjectStore == nullptr) {
219                 LOG_ERROR("no memory for FlatObjectStore malloc!");
220                 return nullptr;
221             }
222             // Use instMemory to make sure this singleton not free before other object.
223             // This operation needn't to malloc memory, we needn't to check nullptr.
224             instPtr = new (std::nothrow) DistributedObjectStoreImpl(flatObjectStore);
225             if (instPtr == nullptr) {
226                 LOG_ERROR("no memory for DistributedObjectStoreImpl malloc!");
227                 return nullptr;
228             }
229         }
230     }
231     return instPtr;
232 }
233 
OnChanged(const std::string & sessionId,const std::string & networkId,const std::string & onlineStatus)234 void StatusNotifierProxy::OnChanged(
235     const std::string &sessionId, const std::string &networkId, const std::string &onlineStatus)
236 {
237     if (notifier != nullptr) {
238         notifier->OnChanged(sessionId, networkId, onlineStatus);
239     }
240 }
241 
StatusNotifierProxy(const std::shared_ptr<StatusNotifier> & notifier)242 StatusNotifierProxy::StatusNotifierProxy(const std::shared_ptr<StatusNotifier> &notifier) : notifier(notifier)
243 {
244 }
245 
~StatusNotifierProxy()246 StatusNotifierProxy::~StatusNotifierProxy()
247 {
248     LOG_ERROR("destroy");
249     notifier = nullptr;
250 }
251 } // namespace OHOS::ObjectStore
252