• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021 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 "dbinder_test_service_skeleton.h"
17 
18 #include <cinttypes>
19 
20 #include "if_system_ability_manager.h"
21 #include "ipc_skeleton.h"
22 #include "ipc_object_proxy.h"
23 #include "iremote_proxy.h"
24 #include "iservice_registry.h"
25 #include "string_ex.h"
26 #include "system_ability_definition.h"
27 
28 namespace OHOS {
29 using namespace OHOS::HiviewDFX;
30 
31 #ifndef TITLE
32 #define TITLE __PRETTY_FUNCTION__
33 #endif
34 
35 static constexpr OHOS::HiviewDFX::HiLogLabel LOG_LABEL = { LOG_CORE, LOG_ID_RPC, "DBinderTestServiceProxy" };
36 #define DBINDER_LOGE(fmt, args...) \
37     (void)OHOS::HiviewDFX::HiLog::Error(LOG_LABEL, "%{public}s %{public}d: " fmt, TITLE, __LINE__, ##args)
38 
39 // set wait time for raw data
40 static constexpr int RAW_DATA_TIMEOUT = 300;
41 
DBinderTestServiceProxy(const sptr<IRemoteObject> & impl)42 DBinderTestServiceProxy::DBinderTestServiceProxy(const sptr<IRemoteObject> &impl)
43     : IRemoteProxy<IDBinderTestService>(impl)
44 {}
45 
ReverseInt(int data,int & rep)46 int DBinderTestServiceProxy::ReverseInt(int data, int &rep)
47 {
48     DBINDER_LOGE("data = %{public}d", data);
49     int error;
50     MessageOption option;
51     MessageParcel dataParcel, replyParcel;
52     if (!dataParcel.WriteInt32(data)) {
53         DBINDER_LOGE("fail to write parcel");
54         return ERR_INVALID_STATE;
55     }
56     error = Remote()->SendRequest(REVERSEINT, dataParcel, replyParcel, option);
57 
58     rep = replyParcel.ReadInt32();
59     DBINDER_LOGE("rep = %{public}d, error = %{public}d", rep, error);
60     return error;
61 }
62 
GetChildId(uint64_t & rep)63 int DBinderTestServiceProxy::GetChildId(uint64_t &rep)
64 {
65     int error;
66     MessageOption option;
67     MessageParcel dataParcel, replyParcel;
68     error = Remote()->SendRequest(TRANS_TRACE_ID, dataParcel, replyParcel, option);
69 
70     rep = replyParcel.ReadUint64();
71     DBINDER_LOGE("rep = %{public}" PRIu64 ", error = %{public}d", rep, error);
72     return error;
73 }
74 
TransProxyObject(int data,sptr<IRemoteObject> & transObject,int operation,int & rep,int & withdrawRes)75 int DBinderTestServiceProxy::TransProxyObject(int data, sptr<IRemoteObject> &transObject, int operation, int &rep,
76     int &withdrawRes)
77 {
78     int error;
79     MessageOption option;
80     MessageParcel dataParcel, replyParcel;
81     if (!dataParcel.WriteInt32(data) || !dataParcel.WriteInt32(operation) ||
82         !dataParcel.WriteRemoteObject(transObject)) {
83         DBINDER_LOGE("fail to write parcel");
84         return ERR_INVALID_STATE;
85     }
86     error = Remote()->SendRequest(TRANS_OBJECT, dataParcel, replyParcel, option);
87 
88     rep = replyParcel.ReadInt32();
89     withdrawRes = replyParcel.ReadInt32();
90     return error;
91 }
92 
TransProxyObjectAgain(int data,sptr<IRemoteObject> & transObject,int operation,int & rep,int & withdrawRes)93 int DBinderTestServiceProxy::TransProxyObjectAgain(int data, sptr<IRemoteObject> &transObject, int operation, int &rep,
94     int &withdrawRes)
95 {
96     int error;
97     MessageOption option;
98     MessageParcel dataParcel, replyParcel;
99     if (!dataParcel.WriteInt32(data) || !dataParcel.WriteInt32(operation) ||
100         !dataParcel.WriteRemoteObject(transObject)) {
101         DBINDER_LOGE("fail to write parcel");
102         return ERR_INVALID_STATE;
103     }
104     error = Remote()->SendRequest(TRANS_OBJECT_OVER_DEVICE_OVER_PROCESS, dataParcel, replyParcel, option);
105 
106     rep = replyParcel.ReadInt32();
107     withdrawRes = replyParcel.ReadInt32();
108     return error;
109 }
110 
TransStubObject(int data,sptr<IRemoteObject> & transObject,int & rep,int & stubRep)111 int DBinderTestServiceProxy::TransStubObject(int data, sptr<IRemoteObject> &transObject, int &rep, int &stubRep)
112 {
113     int error;
114     MessageOption option;
115     MessageParcel dataParcel, replyParcel;
116     if (!dataParcel.WriteInt32(data) || !dataParcel.WriteRemoteObject(transObject)) {
117         DBINDER_LOGE("fail to write parcel");
118         return ERR_INVALID_STATE;
119     }
120 
121     error = Remote()->SendRequest(TRANS_STUB_OBJECT, dataParcel, replyParcel, option);
122     if (error != ERR_NONE) {
123         DBINDER_LOGE("fail to send stub object");
124         return ERR_INVALID_STATE;
125     }
126 
127     rep = replyParcel.ReadInt32();
128 
129     sptr<IRemoteObject> proxy = replyParcel.ReadRemoteObject();
130     if (proxy == nullptr) {
131         DBINDER_LOGE("fail to get remote stub object");
132         return ERR_INVALID_STATE;
133     }
134 
135     MessageParcel dataStubParcel, replyStubParcel;
136     if (!dataStubParcel.WriteInt32(rep)) {
137         DBINDER_LOGE("fail to write parcel");
138         return ERR_INVALID_STATE;
139     }
140 
141     error = proxy->SendRequest(REVERSEINT, dataStubParcel, replyStubParcel, option);
142     if (error != ERR_NONE) {
143         DBINDER_LOGE("fail to send data info");
144         return ERR_INVALID_STATE;
145     }
146 
147     stubRep = replyStubParcel.ReadInt32();
148     return error;
149 }
150 
GetRemoteObject(int type)151 sptr<IRemoteObject> DBinderTestServiceProxy::GetRemoteObject(int type)
152 {
153     MessageOption option;
154     MessageParcel dataParcel, replyParcel;
155     if (!dataParcel.WriteInt32(type)) {
156         DBINDER_LOGE("fail to write parcel");
157         return nullptr;
158     }
159 
160     int error = Remote()->SendRequest(GET_REMOTE_STUB_OBJECT, dataParcel, replyParcel, option);
161     if (error != ERR_NONE) {
162         DBINDER_LOGE("fail to send data info");
163         return nullptr;
164     }
165 
166     sptr<IRemoteObject> proxy = replyParcel.ReadRemoteObject();
167     if (proxy == nullptr) {
168         DBINDER_LOGE("fail to get remote stub object");
169         return nullptr;
170     }
171     return proxy;
172 }
173 
GetRemoteDecTimes()174 int DBinderTestServiceProxy::GetRemoteDecTimes()
175 {
176     MessageOption option;
177     MessageParcel dataParcel, replyParcel;
178 
179     int error = Remote()->SendRequest(GET_REMOTE_DES_TIMES, dataParcel, replyParcel, option);
180     if (error != ERR_NONE) {
181         DBINDER_LOGE("fail to send data info");
182         return 0;
183     }
184 
185     return replyParcel.ReadInt32();
186 }
187 
ClearRemoteDecTimes()188 void DBinderTestServiceProxy::ClearRemoteDecTimes()
189 {
190     MessageOption option;
191     MessageParcel dataParcel, replyParcel;
192 
193     int error = Remote()->SendRequest(CLEAR_REMOTE_DES_TIMES, dataParcel, replyParcel, option);
194     if (error != ERR_NONE) {
195         DBINDER_LOGE("fail to send data info");
196     }
197 }
198 
TransOversizedPkt(const std::string & dataStr,std::string & repStr)199 int DBinderTestServiceProxy::TransOversizedPkt(const std::string &dataStr, std::string &repStr)
200 {
201     int error;
202     MessageOption option;
203     MessageParcel dataParcel, replyParcel;
204     if (!dataParcel.WriteString(dataStr)) {
205         DBINDER_LOGE("fail to write parcel");
206         return ERR_INVALID_STATE;
207     }
208     error = Remote()->SendRequest(TRANS_OVERSIZED_PKT, dataParcel, replyParcel, option);
209 
210     repStr = replyParcel.ReadString();
211     return error;
212 }
213 
ProxyTransRawData(int length)214 int DBinderTestServiceProxy::ProxyTransRawData(int length)
215 {
216     MessageParcel dataParcel, replyParcel;
217 
218     MessageOption option;
219     option.SetWaitTime(RAW_DATA_TIMEOUT);
220     int waitTime = option.GetWaitTime();
221     DBINDER_LOGE("data length = %{public}d, wait time = %{public}d", length, waitTime);
222 
223     if (length <= 1) {
224         DBINDER_LOGE("length should > 1, length is %{public}d", length);
225         return ERR_INVALID_STATE;
226     }
227     unsigned char *buffer = new (std::nothrow) unsigned char[length];
228     if (buffer == nullptr) {
229         DBINDER_LOGE("new buffer failed of length = %{public}d", length);
230         return ERR_INVALID_STATE;
231     }
232     buffer[0] = 'a';
233     buffer[length - 1] = 'z';
234     if (!dataParcel.WriteInt32(length) || !dataParcel.WriteRawData(buffer, length) || !dataParcel.WriteInt32(length)) {
235         DBINDER_LOGE("fail to write parcel");
236         delete[] buffer;
237         return ERR_INVALID_STATE;
238     }
239     delete[] buffer;
240     int ret = Remote()->SendRequest(TRANS_RAW_DATA, dataParcel, replyParcel, option);
241     if (ret != ERR_NONE) {
242         DBINDER_LOGE("fail to send request, ret = %{public}d", ret);
243         return ret;
244     }
245     if (length != replyParcel.ReadInt32()) {
246         DBINDER_LOGE("reply wrong length");
247         ret += ERR_TRANSACTION_FAILED;
248     }
249     return ret;
250 }
251 
StubTransRawData(int length)252 int DBinderTestServiceProxy::StubTransRawData(int length)
253 {
254     MessageParcel dataParcel, replyParcel;
255 
256     MessageOption option;
257     option.SetWaitTime(RAW_DATA_TIMEOUT);
258     int waitTime = option.GetWaitTime();
259     DBINDER_LOGE("data length = %{public}d, wait time = %{public}d", length, waitTime);
260 
261     if (length <= 1) {
262         DBINDER_LOGE("length should > 1, length is %{public}d", length);
263         return ERR_INVALID_STATE;
264     }
265 
266     if (!dataParcel.WriteInt32(length)) {
267         DBINDER_LOGE("fail to write parcel");
268         return ERR_INVALID_STATE;
269     }
270 
271     int ret = Remote()->SendRequest(RECEIVE_RAW_DATA, dataParcel, replyParcel, option);
272     if (ret != ERR_NONE) {
273         DBINDER_LOGE("fail to send request, ret = %{public}d", ret);
274         return ret;
275     }
276 
277     if (replyParcel.ReadInt32() != length) {
278         DBINDER_LOGE("reply false data");
279         return ERR_INVALID_DATA;
280     }
281 
282     const char *buffer = nullptr;
283     if ((buffer = reinterpret_cast<const char *>(replyParcel.ReadRawData(length))) == nullptr) {
284         DBINDER_LOGE("fail to read raw data, length = %{public}d", length);
285         return ERR_INVALID_DATA;
286     }
287     if (buffer[0] != 'a' || buffer[length - 1] != 'z') {
288         DBINDER_LOGE("received raw data is wrong, length = %{public}d", length);
289         return ERR_INVALID_DATA;
290     }
291 
292     if (replyParcel.ReadInt32() != length) {
293         DBINDER_LOGE("fail to read length after raw data, length = %{public}d", length);
294         return ERR_INVALID_DATA;
295     }
296 
297     return ERR_NONE;
298 }
299 
FlushAsyncCommands(int count,int length)300 int DBinderTestServiceProxy::FlushAsyncCommands(int count, int length)
301 {
302     int ret;
303     MessageOption option = { MessageOption::TF_ASYNC };
304     MessageParcel dataParcel, replyParcel;
305     std::string dataStr(length, 'a');
306     if (!dataParcel.WriteString(dataStr)) {
307         DBINDER_LOGE("fail to write parcel");
308         return ERR_INVALID_STATE;
309     }
310     for (int i = 0; i < count; i++) {
311         ret = Remote()->SendRequest(TRANS_OVERSIZED_PKT, dataParcel, replyParcel, option);
312         if (ret != ERR_NONE) {
313             DBINDER_LOGE("fail to send request when count = %{public}d ret = %{public}d", i, ret);
314             return ret;
315         }
316     }
317     ret = IPCSkeleton::FlushCommands(this->AsObject());
318     return ret;
319 }
320 
ReverseIntNullReply(int data,int & rep)321 int DBinderTestServiceProxy::ReverseIntNullReply(int data, int &rep)
322 {
323     int error;
324     MessageOption option;
325     MessageParcel dataParcel, replyParcel;
326     if (!dataParcel.WriteInt32(data)) {
327         DBINDER_LOGE("fail to write parcel");
328         return ERR_INVALID_STATE;
329     }
330     error = Remote()->SendRequest(REVERSEINT, dataParcel, replyParcel, option);
331 
332     rep = replyParcel.ReadInt32();
333     return error;
334 }
335 
ReverseIntVoidData(int data,int & rep)336 int DBinderTestServiceProxy::ReverseIntVoidData(int data, int &rep)
337 {
338     int error;
339     MessageOption option;
340     MessageParcel dataParcel, replyParcel;
341     // do not write data to parcel;
342     error = Remote()->SendRequest(REVERSEINT, dataParcel, replyParcel, option);
343 
344     rep = replyParcel.ReadInt32();
345     return error;
346 }
347 
ReverseIntDelay(int data,int & rep)348 int DBinderTestServiceProxy::ReverseIntDelay(int data, int &rep)
349 {
350     int error;
351     MessageOption option;
352     MessageParcel dataParcel, replyParcel;
353     if (!dataParcel.WriteInt32(data)) {
354         DBINDER_LOGE("fail to write parcel");
355         return ERR_INVALID_STATE;
356     }
357     error = Remote()->SendRequest(REVERSEINTDELAY, dataParcel, replyParcel, option);
358 
359     rep = replyParcel.ReadInt32();
360     return error;
361 }
362 
Delay(int data,int & rep)363 int DBinderTestServiceProxy::Delay(int data, int &rep)
364 {
365     int error;
366     MessageOption option;
367     MessageParcel dataParcel, replyParcel;
368     if (!dataParcel.WriteInt32(data)) {
369         DBINDER_LOGE("fail to write parcel");
370         return ERR_INVALID_STATE;
371     }
372     error = Remote()->SendRequest(ONLY_DELAY, dataParcel, replyParcel, option);
373 
374     rep = replyParcel.ReadInt32();
375     return error;
376 }
377 
ReverseIntDelayAsync(int data,int & rep)378 int DBinderTestServiceProxy::ReverseIntDelayAsync(int data, int &rep)
379 {
380     int error;
381     MessageOption option;
382     MessageParcel dataParcel, replyParcel;
383     if (!dataParcel.WriteInt32(data) ||
384         // 2:for data update check, only in test case
385         !replyParcel.WriteInt32(data * 2)) {
386         DBINDER_LOGE("fail to write parcel");
387         return ERR_INVALID_STATE;
388     }
389     error = Remote()->SendRequest(REVERSEINTDELAY, dataParcel, replyParcel, option);
390 
391     rep = replyParcel.ReadInt32();
392     return error;
393 }
394 
PingService(std::u16string & serviceName)395 int DBinderTestServiceProxy::PingService(std::u16string &serviceName)
396 {
397     int error;
398     MessageOption option;
399     MessageParcel dataParcel, replyParcel;
400     DBINDER_LOGE("TestServiceProxy:PingService");
401     if (!dataParcel.WriteString16(serviceName.data())) {
402         DBINDER_LOGE("fail to write parcel");
403         return ERR_INVALID_STATE;
404     }
405     error = Remote()->SendRequest(REVERSEINT, dataParcel, replyParcel, option);
406     replyParcel.ReadInt32();
407     return error;
408 }
409 
410 pid_t DBinderTestServiceStub::g_lastCallingPid = 0;
411 pid_t DBinderTestServiceStub::g_lastCallinguid = 0;
412 
GetLastCallingPid()413 pid_t DBinderTestServiceStub::GetLastCallingPid()
414 {
415     return g_lastCallingPid;
416 }
417 
GetLastCallingUid()418 uid_t DBinderTestServiceStub::GetLastCallingUid()
419 {
420     return g_lastCallinguid;
421 }
422 
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)423 int DBinderTestServiceStub::OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply,
424     MessageOption &option)
425 {
426     DBINDER_LOGE("TestServiceStub::OnReceived, cmd = %{public}d", code);
427     g_lastCallingPid = IPCSkeleton::GetCallingPid();
428     g_lastCallinguid = IPCSkeleton::GetCallingUid();
429     switch (code) {
430         case REVERSEINT: {
431             return OnReverseInt(data, reply);
432         }
433         case REVERSEINTDELAY: {
434             return OnReverseIntDelay(data, reply);
435         }
436         case PING_SERVICE: {
437             return OnPingService(data, reply);
438         }
439         case ONLY_DELAY: {
440             return OnDelay(data, reply);
441         }
442         case TRANS_OBJECT:
443         case TRANS_RPC_OBJECT_TO_LOCAL: {
444             DBINDER_LOGE("TestServiceStub::TRANS_RPC_OBJECT_TO_LOCAL?, cmd = %{public}d", code);
445             return OnReceivedObject(data, reply);
446         }
447         case TRANS_OBJECT_OVER_DEVICE_OVER_PROCESS: {
448             return OnReceivedObjectTransAgain(data, reply);
449         }
450         case TRANS_STUB_OBJECT: {
451             return OnReceivedStubObject(data, reply);
452         }
453         case TRANS_OVERSIZED_PKT: {
454             return OnReceivedOversizedPkt(data, reply);
455         }
456         case TRANS_RAW_DATA: {
457             return OnReceivedRawData(data, reply);
458         }
459         case RECEIVE_RAW_DATA: {
460             return OnSentRawData(data, reply);
461         }
462         case TRANS_TRACE_ID: {
463             return OnGetChildId(data, reply);
464         }
465         case GET_REMOTE_STUB_OBJECT: {
466             return OnReceivedGetStubObject(data, reply);
467         }
468         case GET_REMOTE_DES_TIMES: {
469             return OnReceivedGetDecTimes(data, reply);
470         }
471         case CLEAR_REMOTE_DES_TIMES: {
472             return OnReceivedClearDecTimes(data, reply);
473         }
474         default: {
475             return IPCObjectStub::OnRemoteRequest(code, data, reply, option);
476         }
477     }
478 }
479 
ReverseIntDelayAsync(int data,int & rep)480 int DBinderTestServiceStub::ReverseIntDelayAsync(int data, int &rep)
481 {
482     (void)data;
483     HiLog::Error(LABEL, "%{public}s: not valid operate", __func__);
484     return 0;
485 }
486 
OnReverseInt(MessageParcel & data,MessageParcel & reply)487 int DBinderTestServiceStub::OnReverseInt(MessageParcel &data, MessageParcel &reply)
488 {
489     int result;
490     int32_t reqData = data.ReadInt32();
491     int ret = ReverseInt(reqData, result);
492     HiLog::Info(LABEL, "ReverseInt result = %{public}d", result);
493     if (!reply.WriteInt32(result)) {
494         DBINDER_LOGE("fail to write parcel");
495         ret = ERR_INVALID_STATE;
496     }
497 
498     return ret;
499 }
500 
OnGetChildId(MessageParcel & data,MessageParcel & reply)501 int DBinderTestServiceStub::OnGetChildId(MessageParcel &data, MessageParcel &reply)
502 {
503     uint64_t reqData = HiTrace::GetId().GetChainId();
504     if (!reply.WriteUint64(reqData)) {
505         DBINDER_LOGE("fail to write parcel");
506         return ERR_INVALID_STATE;
507     }
508 
509     DBINDER_LOGE("before reset uid = %{public}d, callerId = %{public}s, localId = %{public}s, islocal = %{public}d",
510         IPCSkeleton::GetCallingUid(), IPCSkeleton::GetCallingDeviceID().c_str(),
511         IPCSkeleton::GetLocalDeviceID().c_str(), IPCSkeleton::IsLocalCalling());
512     std::string token = IPCSkeleton::ResetCallingIdentity();
513 
514     DBINDER_LOGE("before set uid = %{public}d, callerId = %{public}s, localId = %{public}s, islocal = %{public}d",
515         IPCSkeleton::GetCallingUid(), IPCSkeleton::GetCallingDeviceID().c_str(),
516         IPCSkeleton::GetLocalDeviceID().c_str(), IPCSkeleton::IsLocalCalling());
517     if (!IPCSkeleton::SetCallingIdentity(token)) {
518         DBINDER_LOGE("Set Calling Identity fail");
519     }
520 
521     DBINDER_LOGE("after set uid = %{public}d, callerId = %{public}s, localId = %{public}s, islocal = %{public}d",
522         IPCSkeleton::GetCallingUid(), IPCSkeleton::GetCallingDeviceID().c_str(),
523         IPCSkeleton::GetLocalDeviceID().c_str(), IPCSkeleton::IsLocalCalling());
524     return ERR_NONE;
525 }
526 
OnReverseIntDelay(MessageParcel & data,MessageParcel & reply)527 int DBinderTestServiceStub::OnReverseIntDelay(MessageParcel &data, MessageParcel &reply)
528 {
529     int result;
530     int32_t reqData = data.ReadInt32();
531     int ret = ReverseIntDelay(reqData, result);
532     if (!reply.WriteInt32(result)) {
533         DBINDER_LOGE("fail to write parcel");
534         ret = ERR_INVALID_STATE;
535     }
536 
537     return ret;
538 }
539 
OnPingService(MessageParcel & data,MessageParcel & reply)540 int DBinderTestServiceStub::OnPingService(MessageParcel &data, MessageParcel &reply)
541 {
542     std::u16string serviceName = data.ReadString16();
543     int ret = PingService(serviceName);
544     HiLog::Info(LABEL, "%s:PingService: ret=%d", __func__, ret);
545     if (!reply.WriteInt32(ret)) {
546         DBINDER_LOGE("fail to write parcel");
547         ret = ERR_INVALID_STATE;
548     }
549 
550     return ret;
551 }
552 
OnDelay(MessageParcel & data,MessageParcel & reply)553 int DBinderTestServiceStub::OnDelay(MessageParcel &data, MessageParcel &reply)
554 {
555     int result;
556     int32_t reqData = data.ReadInt32();
557     int ret = Delay(reqData, result);
558     if (!reply.WriteInt32(result)) {
559         DBINDER_LOGE("fail to write parcel");
560         ret = ERR_INVALID_STATE;
561     }
562 
563     return ret;
564 }
565 
OnReceivedObject(MessageParcel & data,MessageParcel & reply)566 int DBinderTestServiceStub::OnReceivedObject(MessageParcel &data, MessageParcel &reply)
567 {
568     int32_t reqData = data.ReadInt32();
569     int32_t operation = data.ReadInt32();
570     sptr<IRemoteObject> proxy = data.ReadRemoteObject();
571     if (proxy == nullptr) {
572         DBINDER_LOGE("null proxy");
573         return ERR_INVALID_STATE;
574     }
575 
576     // use the received proxy to communicate
577     MessageOption option;
578     MessageParcel dataParcel, replyParcel;
579     if (!dataParcel.WriteInt32(reqData)) {
580         DBINDER_LOGE("fail to write parcel");
581         return ERR_INVALID_STATE;
582     }
583     HiLog::Info(LABEL, "%{public}s:TRANSOBJECT: reqData=%{public}d", __func__, reqData);
584     int ret = proxy->SendRequest(REVERSEINT, dataParcel, replyParcel, option);
585     int reqResult = replyParcel.ReadInt32();
586     HiLog::Info(LABEL, "%{public}s:TRANSOBJECT: result=%{public}d", __func__, reqResult);
587 
588     if (!reply.WriteInt32(reqResult)) {
589         DBINDER_LOGE("fail to write parcel");
590         return ERR_INVALID_STATE;
591     }
592 
593     if (operation == SAVE) {
594         recvProxy_ = proxy;
595     }
596 
597     // received proxy is different from that of last time
598     if ((operation == WITHDRAW) && (recvProxy_ != proxy)) {
599         if (!reply.WriteInt32(1)) {
600             DBINDER_LOGE("fail to write parcel");
601             ret = ERR_INVALID_STATE;
602         }
603         return ret;
604     }
605 
606     if (!reply.WriteInt32(0)) {
607         DBINDER_LOGE("fail to write parcel");
608         return ERR_INVALID_STATE;
609     }
610     return ret;
611 }
612 
OnReceivedObjectTransAgain(MessageParcel & data,MessageParcel & reply)613 int DBinderTestServiceStub::OnReceivedObjectTransAgain(MessageParcel &data, MessageParcel &reply)
614 {
615     int32_t reqData = data.ReadInt32();
616     int32_t operation = data.ReadInt32();
617     sptr<IRemoteObject> proxy = data.ReadRemoteObject();
618     if (proxy == nullptr) {
619         DBINDER_LOGE("null proxy");
620         return ERR_INVALID_STATE;
621     }
622     sptr<ISystemAbilityManager> manager_ = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
623     if (manager_ == nullptr) {
624         DBINDER_LOGE("null manager_");
625         return ERR_INVALID_STATE;
626     }
627     HiLog::Info(LABEL, "%{public}s:OnReceivedObjectTransAgain-1: reqData=%{public}d", __func__, reqData);
628 
629     sptr<IRemoteObject> object = manager_->GetSystemAbility(RPC_TEST_SERVICE2);
630     if (object == nullptr) {
631         DBINDER_LOGE("null object of RPC_TEST_SERVICE2");
632         return ERR_INVALID_STATE;
633     }
634 
635     MessageOption option;
636     MessageParcel dataParcel, replyParcel;
637     if (!dataParcel.WriteInt32(reqData) || !dataParcel.WriteInt32(operation) ||
638         !dataParcel.WriteRemoteObject(proxy)) {
639         DBINDER_LOGE("fail to write parcel");
640         return ERR_INVALID_STATE;
641     }
642     HiLog::Info(LABEL, "%{public}s:OnReceivedObjectTransAgain-2: reqData=%{public}d", __func__, reqData);
643     int ret = object->SendRequest(TRANS_RPC_OBJECT_TO_LOCAL, dataParcel, replyParcel, option);
644 
645     int reqResult = replyParcel.ReadInt32();
646     HiLog::Info(LABEL, "%{public}s:OnReceivedObjectTransAgain-3: result=%{public}d", __func__, reqResult);
647 
648     if (!reply.WriteInt32(reqResult)) {
649         DBINDER_LOGE("fail to write parcel");
650         return ERR_INVALID_STATE;
651     }
652     HiLog::Info(LABEL, "%{public}s:OnReceivedObjectTransAgain-4: result=%{public}d", __func__, reqResult);
653     if (!reply.WriteInt32(0)) {
654         DBINDER_LOGE("fail to write parcel");
655         return ERR_INVALID_STATE;
656     }
657     HiLog::Info(LABEL, "%{public}s:OnReceivedObjectTransAgain-5: result=%{public}d", __func__, reqResult);
658     return ret;
659 }
660 
OnReceivedStubObject(MessageParcel & data,MessageParcel & reply)661 int DBinderTestServiceStub::OnReceivedStubObject(MessageParcel &data, MessageParcel &reply)
662 {
663     int32_t reqData = data.ReadInt32();
664     sptr<IRemoteObject> proxy = data.ReadRemoteObject();
665     if (proxy == nullptr) {
666         DBINDER_LOGE("fail to get proxy");
667         return ERR_INVALID_STATE;
668     }
669 
670     MessageOption option;
671     MessageParcel dataParcel, replyParcel;
672     if (!dataParcel.WriteInt32(reqData)) {
673         DBINDER_LOGE("fail to write parcel");
674         return ERR_INVALID_STATE;
675     }
676 
677     int error = proxy->SendRequest(REVERSEINT, dataParcel, replyParcel, option);
678     if (error != ERR_NONE) {
679         DBINDER_LOGE("fail to send data info");
680         return ERR_INVALID_STATE;
681     }
682     int reqResult = replyParcel.ReadInt32();
683     if (!reply.WriteInt32(reqResult)) {
684         DBINDER_LOGE("fail to write parcel");
685         return ERR_INVALID_STATE;
686     }
687 
688     if (!reply.WriteRemoteObject(this)) {
689         DBINDER_LOGE("fail to write parcel stub");
690         return ERR_INVALID_STATE;
691     }
692 
693     return error;
694 }
695 
OnReceivedGetStubObject(MessageParcel & data,MessageParcel & reply)696 int DBinderTestServiceStub::OnReceivedGetStubObject(MessageParcel &data, MessageParcel &reply)
697 {
698     if (!reply.WriteRemoteObject(GetRemoteObject(data.ReadInt32()))) {
699         DBINDER_LOGE("fail to write parcel");
700         return ERR_INVALID_STATE;
701     }
702 
703     return ERR_NONE;
704 }
705 
OnReceivedGetDecTimes(MessageParcel & data,MessageParcel & reply)706 int DBinderTestServiceStub::OnReceivedGetDecTimes(MessageParcel &data, MessageParcel &reply)
707 {
708     if (!reply.WriteInt32(GetRemoteDecTimes())) {
709         DBINDER_LOGE("fail to write parcel");
710         return ERR_INVALID_STATE;
711     }
712 
713     return ERR_NONE;
714 }
715 
OnReceivedClearDecTimes(MessageParcel & data,MessageParcel & reply)716 int DBinderTestServiceStub::OnReceivedClearDecTimes(MessageParcel &data, MessageParcel &reply)
717 {
718     DBINDER_LOGE("OnReceivedClearDecTimes");
719 
720     ClearRemoteDecTimes();
721     return ERR_NONE;
722 }
723 
OnReceivedOversizedPkt(MessageParcel & data,MessageParcel & reply)724 int DBinderTestServiceStub::OnReceivedOversizedPkt(MessageParcel &data, MessageParcel &reply)
725 {
726     std::string reqStr = data.ReadString();
727     std::string resultStr = reqStr;
728     if (!reply.WriteString(resultStr)) {
729         DBINDER_LOGE("fail to write parcel");
730         return ERR_INVALID_STATE;
731     }
732 
733     return ERR_NONE;
734 }
735 
OnReceivedRawData(MessageParcel & data,MessageParcel & reply)736 int DBinderTestServiceStub::OnReceivedRawData(MessageParcel &data, MessageParcel &reply)
737 {
738     int length = data.ReadInt32();
739     if (length <= 1) {
740         DBINDER_LOGE("length should > 1, length is %{public}d", length);
741         if (!reply.WriteInt32(length)) {
742             DBINDER_LOGE("fail to write parcel");
743         }
744         return ERR_INVALID_DATA;
745     }
746     const char *buffer = nullptr;
747     if ((buffer = reinterpret_cast<const char *>(data.ReadRawData(length))) == nullptr) {
748         if (!reply.WriteInt32(0)) {
749             DBINDER_LOGE("fail to write parcel");
750         }
751         DBINDER_LOGE("read raw data failed, length = %{public}d", length);
752         return ERR_INVALID_DATA;
753     }
754     if (buffer[0] != 'a' || buffer[length - 1] != 'z') {
755         if (!reply.WriteInt32(0)) {
756             DBINDER_LOGE("fail to write parcel");
757         }
758         DBINDER_LOGE("buffer error, length = %{public}d", length);
759         return ERR_INVALID_DATA;
760     }
761     if (data.ReadInt32() != length) {
762         if (!reply.WriteInt32(0)) {
763             DBINDER_LOGE("fail to write parcel");
764         }
765         DBINDER_LOGE("read raw data after failed, length = %{public}d", length);
766         return ERR_INVALID_DATA;
767     }
768     if (!reply.WriteInt32(length)) {
769         DBINDER_LOGE("fail to write parcel");
770         return ERR_INVALID_STATE;
771     }
772 
773     return ERR_NONE;
774 }
775 
OnSentRawData(MessageParcel & data,MessageParcel & reply)776 int DBinderTestServiceStub::OnSentRawData(MessageParcel &data, MessageParcel &reply)
777 {
778     int length = data.ReadInt32();
779     if (length <= 1) {
780         DBINDER_LOGE("length should > 1, length is %{public}d", length);
781         if (!reply.WriteInt32(length)) {
782             DBINDER_LOGE("fail to write parcel");
783         }
784         return ERR_INVALID_DATA;
785     }
786 
787     unsigned char *buffer = new (std::nothrow) unsigned char[length];
788     if (buffer == nullptr) {
789         DBINDER_LOGE("new buffer failed of length = %{public}d", length);
790         return ERR_INVALID_STATE;
791     }
792     buffer[0] = 'a';
793     buffer[length - 1] = 'z';
794     if (!reply.WriteInt32(length) || !reply.WriteRawData(buffer, length) || !reply.WriteInt32(length)) {
795         DBINDER_LOGE("fail to write parcel");
796         delete[] buffer;
797         return ERR_INVALID_STATE;
798     }
799     delete[] buffer;
800     return ERR_NONE;
801 }
802 
803 bool DBinderTestDeathRecipient::g_gotDeathRecipient = false;
GotDeathRecipient()804 bool DBinderTestDeathRecipient::GotDeathRecipient()
805 {
806     return g_gotDeathRecipient;
807 }
808 
ClearDeathRecipient()809 void DBinderTestDeathRecipient::ClearDeathRecipient()
810 {
811     g_gotDeathRecipient = false;
812 }
813 
OnRemoteDied(const wptr<IRemoteObject> & remote)814 void DBinderTestDeathRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
815 {
816     g_gotDeathRecipient = true;
817     printf("Succ! Remote Died!\n");
818     DBINDER_LOGE("recv death notification");
819 }
820 
DBinderTestDeathRecipient()821 DBinderTestDeathRecipient::DBinderTestDeathRecipient() {}
822 
~DBinderTestDeathRecipient()823 DBinderTestDeathRecipient::~DBinderTestDeathRecipient() {}
824 } // namespace OHOS
825