1/* 2 * Copyright (c) 2021-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 "uds_client.h" 17 18#include "util.h" 19 20#undef MMI_LOG_TAG 21#define MMI_LOG_TAG "UDSClient" 22 23namespace OHOS { 24namespace MMI { 25UDSClient::UDSClient() 26{ 27 CALL_DEBUG_ENTER; 28} 29 30UDSClient::~UDSClient() 31{ 32 CALL_DEBUG_ENTER; 33} 34 35int32_t UDSClient::ConnectTo() 36{ 37 CALL_DEBUG_ENTER; 38 if (Socket() < 0) { 39 MMI_HILOGE("Socket failed"); 40 return RET_ERR; 41 } 42 OnConnected(); 43 return RET_OK; 44} 45 46bool UDSClient::SendMsg(const char *buf, size_t size) const 47{ 48 CHKPF(buf); 49 if ((size == 0) || (size > MAX_PACKET_BUF_SIZE)) { 50 MMI_HILOGE("Stream buffer size out of range"); 51 return false; 52 } 53 if (fd_ < 0) { 54 MMI_HILOGE("The fd_ is less than 0"); 55 return false; 56 } 57 58 int32_t idx = 0; 59 int32_t retryCount = 0; 60 const int32_t bufSize = static_cast<int32_t>(size); 61 int32_t remSize = bufSize; 62 while (remSize > 0 && retryCount < SEND_RETRY_LIMIT) { 63 retryCount += 1; 64 auto count = send(fd_, &buf[idx], remSize, MSG_DONTWAIT | MSG_NOSIGNAL); 65 if (count < 0) { 66 if (errno == EAGAIN || errno == EINTR || errno == EWOULDBLOCK) { 67 MMI_HILOGW("Continue for errno EAGAIN|EINTR|EWOULDBLOCK, errno:%{public}d", errno); 68 continue; 69 } 70 MMI_HILOGE("Send return failed,error:%{public}d fd:%{public}d", errno, fd_); 71 return false; 72 } 73 idx += count; 74 remSize -= count; 75 if (remSize > 0) { 76 MMI_HILOGW("Remsize:%{public}d", remSize); 77 usleep(SEND_RETRY_SLEEP_TIME); 78 } 79 } 80 if (retryCount >= SEND_RETRY_LIMIT || remSize != 0) { 81 MMI_HILOGE("Send too many times:%{public}d/%{public}d,size:%{public}d/%{public}d fd:%{public}d", 82 retryCount, SEND_RETRY_LIMIT, idx, bufSize, fd_); 83 return false; 84 } 85 return true; 86} 87 88bool UDSClient::SendMsg(const NetPacket &pkt) const 89{ 90 if (pkt.ChkRWError()) { 91 MMI_HILOGE("Read and write status is error"); 92 return false; 93 } 94 StreamBuffer buf; 95 pkt.MakeData(buf); 96 return SendMsg(buf.Data(), buf.Size()); 97} 98 99bool UDSClient::StartClient(MsgClientFunCallback fun) 100{ 101 CALL_DEBUG_ENTER; 102 if (isRunning_ || isConnected_) { 103 MMI_HILOGE("Client is connected or started"); 104 return false; 105 } 106 isExit = false; 107 recvFun_ = fun; 108 if (ConnectTo() < 0) { 109 MMI_HILOGW("Client connection failed, Try again later"); 110 return false; 111 } 112 return true; 113} 114 115void UDSClient::Stop() 116{ 117 CALL_DEBUG_ENTER; 118 isExit = true; 119 isRunning_ = false; 120 Close(); 121} 122} // namespace MMI 123} // namespace OHOS