• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2023 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 "data_proxy_observer_stub.h"
17 
18 #include "dataproxy_handle_common.h"
19 #include "datashare_itypes_utils.h"
20 #include "datashare_log.h"
21 
22 namespace OHOS {
23 namespace DataShare {
24 static constexpr int MAX_VEC_SIZE = 1024;
25 static constexpr int REQUEST_CODE = 0;
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)26 int RdbObserverStub::OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &option)
27 {
28     std::u16string descriptor = RdbObserverStub::GetDescriptor();
29     std::u16string remoteDescriptor = data.ReadInterfaceToken();
30     if (descriptor != remoteDescriptor) {
31         LOG_ERROR("local descriptor is not equal to remote");
32         return ERR_INVALID_STATE;
33     }
34     if (code != REQUEST_CODE) {
35         LOG_ERROR("not support code:%u", code);
36         return ERR_INVALID_STATE;
37     }
38     RdbChangeNode changeNode;
39     if (!ITypesUtil::Unmarshal(data, changeNode)) {
40         LOG_ERROR("Unmarshalling  is nullptr");
41         return ERR_INVALID_VALUE;
42     }
43     OnChangeFromRdb(changeNode);
44     return ERR_OK;
45 }
46 
ReadAshmem(RdbChangeNode & changeNode,const void ** data,int size,int & offset)47 int RdbObserverStub::ReadAshmem(RdbChangeNode &changeNode, const void **data, int size, int &offset)
48 {
49     if (changeNode.memory_ == nullptr) {
50         LOG_ERROR("changeNode memory is nullptr.");
51         return E_ERROR;
52     }
53     const void *read = changeNode.memory_->ReadFromAshmem(size, offset);
54     if (read == nullptr) {
55         LOG_ERROR("failed to read from ashmem.");
56         changeNode.memory_->UnmapAshmem();
57         changeNode.memory_->CloseAshmem();
58         changeNode.memory_ = nullptr;
59         return E_ERROR;
60     }
61     *data = read;
62     offset += size;
63     return E_OK;
64 }
65 
DeserializeDataFromAshmem(RdbChangeNode & changeNode)66 int RdbObserverStub::DeserializeDataFromAshmem(RdbChangeNode &changeNode)
67 {
68     if (changeNode.memory_ == nullptr) {
69         LOG_ERROR("changeNode.memory_ is null.");
70         return E_ERROR;
71     }
72     bool mapRet = changeNode.memory_->MapReadAndWriteAshmem();
73     if (!mapRet) {
74         LOG_ERROR("failed to map read and write ashmem, ret=%{public}d", mapRet);
75         changeNode.memory_->CloseAshmem();
76         changeNode.memory_ = nullptr;
77         return E_ERROR;
78     }
79     LOG_DEBUG("receive data size: %{public}d", changeNode.size_);
80     // Read data size
81     int intLen = 4;
82     int offset = 0;
83     const int *vecLenRead;
84     if (ReadAshmem(changeNode, (const void **)&vecLenRead, intLen, offset) != E_OK) {
85         LOG_ERROR("failed to read data with len %{public}d, offset %{public}d.", intLen, offset);
86         return E_ERROR;
87     }
88     int vecLen = *vecLenRead;
89     if (vecLen > MAX_VEC_SIZE || vecLen < 0) {
90         LOG_ERROR("vecLen is invalid: %{public}d", vecLen);
91         return E_ERROR;
92     }
93     // Read data
94     for (int i = 0; i < vecLen; i++) {
95         const int *dataLenRead;
96         if (ReadAshmem(changeNode, (const void **)&dataLenRead, intLen, offset) != E_OK) {
97             LOG_ERROR(
98                 "failed to read data with index %{public}d, len %{public}d, offset %{public}d.", i, intLen, offset);
99             return E_ERROR;
100         }
101         int dataLen = *dataLenRead;
102         const char *dataRead;
103         if (ReadAshmem(changeNode, (const void **)&dataRead, dataLen, offset) != E_OK) {
104             LOG_ERROR(
105                 "failed to read data with index %{public}d, len %{public}d, offset %{public}d.", i, dataLen, offset);
106             return E_ERROR;
107         }
108         std::string data(dataRead, dataLen);
109         changeNode.data_.push_back(data);
110     }
111     return E_OK;
112 }
113 
RecoverRdbChangeNodeData(RdbChangeNode & changeNode)114 int RdbObserverStub::RecoverRdbChangeNodeData(RdbChangeNode &changeNode)
115 {
116     int ret = E_OK;
117     if (changeNode.isSharedMemory_) {
118         // Recover form Ashmem
119         if (DeserializeDataFromAshmem(changeNode) != E_OK) {
120             LOG_ERROR("failed to deserialize data from ashmem.");
121             ret = E_ERROR;
122         }
123         if (changeNode.memory_ != nullptr) {
124             changeNode.memory_->UnmapAshmem();
125             changeNode.memory_->CloseAshmem();
126             changeNode.memory_ = nullptr;
127         }
128         changeNode.isSharedMemory_ = false;
129         changeNode.size_ = 0;
130     }
131     return ret;
132 }
133 
OnChangeFromRdb(RdbChangeNode & changeNode)134 void RdbObserverStub::OnChangeFromRdb(RdbChangeNode &changeNode)
135 {
136     std::lock_guard<decltype(mutex_)> lock(mutex_);
137     if (RecoverRdbChangeNodeData(changeNode) != E_OK) {
138         LOG_ERROR("failed to recover RdbChangeNode data.");
139         return;
140     }
141     if (callback_) {
142         callback_(changeNode);
143     }
144 }
145 
RdbObserverStub(RdbCallback callback)146 RdbObserverStub::RdbObserverStub(RdbCallback callback) : callback_(callback)
147 {
148 }
149 
~RdbObserverStub()150 RdbObserverStub::~RdbObserverStub()
151 {
152     ClearCallback();
153 }
154 
ClearCallback()155 void RdbObserverStub::ClearCallback()
156 {
157     std::lock_guard<decltype(mutex_)> lock(mutex_);
158     callback_ = nullptr;
159 }
160 
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)161 int PublishedDataObserverStub::OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply,
162     MessageOption &option)
163 {
164     std::u16string descriptor = PublishedDataObserverStub::GetDescriptor();
165     std::u16string remoteDescriptor = data.ReadInterfaceToken();
166     if (descriptor != remoteDescriptor) {
167         LOG_ERROR("local descriptor is not equal to remote");
168         return ERR_INVALID_STATE;
169     }
170     if (code != REQUEST_CODE) {
171         LOG_ERROR("not support code:%u", code);
172         return ERR_INVALID_STATE;
173     }
174     PublishedDataChangeNode changeNode;
175     if (!ITypesUtil::Unmarshal(data, changeNode)) {
176         LOG_ERROR("Unmarshalling  is nullptr");
177         return ERR_INVALID_VALUE;
178     }
179     OnChangeFromPublishedData(changeNode);
180     return ERR_OK;
181 }
182 
OnChangeFromPublishedData(PublishedDataChangeNode & changeNode)183 void PublishedDataObserverStub::OnChangeFromPublishedData(PublishedDataChangeNode &changeNode)
184 {
185     std::lock_guard<decltype(mutex_)> lock(mutex_);
186     if (callback_) {
187         callback_(changeNode);
188     }
189 }
190 
ClearCallback()191 void PublishedDataObserverStub::ClearCallback()
192 {
193     std::lock_guard<decltype(mutex_)> lock(mutex_);
194     callback_ = nullptr;
195 }
196 
~PublishedDataObserverStub()197 PublishedDataObserverStub::~PublishedDataObserverStub()
198 {
199     ClearCallback();
200 }
201 
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)202 int ProxyDataObserverStub::OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply,
203     MessageOption &option)
204 {
205     std::u16string descriptor = PublishedDataObserverStub::GetDescriptor();
206     std::u16string remoteDescriptor = data.ReadInterfaceToken();
207     if (descriptor != remoteDescriptor) {
208         LOG_ERROR("local descriptor is not equal to remote");
209         return ERR_INVALID_STATE;
210     }
211     if (code != REQUEST_CODE) {
212         LOG_ERROR("not support code:%u", code);
213         return ERR_INVALID_STATE;
214     }
215     std::vector<DataProxyChangeInfo> changeInfo;
216     if (!ITypesUtil::Unmarshal(data, changeInfo)) {
217         LOG_ERROR("Unmarshalling  is nullptr");
218         return ERR_INVALID_VALUE;
219     }
220     OnChangeFromProxyData(changeInfo);
221     return ERR_OK;
222 }
223 
OnChangeFromProxyData(std::vector<DataProxyChangeInfo> & changeInfo)224 void ProxyDataObserverStub::OnChangeFromProxyData(std::vector<DataProxyChangeInfo> &changeInfo)
225 {
226     std::lock_guard<decltype(mutex_)> lock(mutex_);
227     if (callback_) {
228         callback_(changeInfo);
229     }
230 }
231 
ClearCallback()232 void ProxyDataObserverStub::ClearCallback()
233 {
234     std::lock_guard<decltype(mutex_)> lock(mutex_);
235     callback_ = nullptr;
236 }
237 
~ProxyDataObserverStub()238 ProxyDataObserverStub::~ProxyDataObserverStub()
239 {
240     ClearCallback();
241 }
242 } // namespace DataShare
243 } // namespace OHOS
244