• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 "stream_buffer.h"
17 
18 namespace OHOS {
19 namespace MMI {
StreamBuffer(const StreamBuffer & buf)20 StreamBuffer::StreamBuffer(const StreamBuffer &buf)
21 {
22     Clone(buf);
23 }
24 
operator =(const StreamBuffer & other)25 StreamBuffer &StreamBuffer::operator=(const StreamBuffer &other)
26 {
27     Clone(other);
28     return *this;
29 }
30 
Reset()31 void StreamBuffer::Reset()
32 {
33     rPos_ = 0;
34     wPos_ = 0;
35     rCount_ = 0;
36     wCount_ = 0;
37     rwErrorStatus_ = ErrorStatus::ERROR_STATUS_OK;
38 }
39 
Clean()40 void StreamBuffer::Clean()
41 {
42     Reset();
43     errno_t ret = memset_sp(&szBuff_, sizeof(szBuff_), 0, sizeof(szBuff_));
44     if (ret != EOK) {
45         MMI_HILOGE("Call memset_s fail");
46         return;
47     }
48 }
49 
SeekReadPos(int32_t n)50 bool StreamBuffer::SeekReadPos(int32_t n)
51 {
52     int32_t pos = rPos_ + n;
53     if (pos < 0 || pos > wPos_) {
54         MMI_HILOGE("The position in the calculation is not as expected. pos:%{public}d [0, %{public}d]",
55             pos, wPos_);
56         return false;
57     }
58     rPos_ = pos;
59     return true;
60 }
61 
Read(std::string & buf)62 bool StreamBuffer::Read(std::string &buf)
63 {
64     if (rPos_ == wPos_) {
65         MMI_HILOGE("Not enough memory to read, errCode:%{public}d", MEM_NOT_ENOUGH);
66         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_READ;
67         return false;
68     }
69     buf = ReadBuf();
70     rPos_ += static_cast<int32_t>(buf.length()) + 1;
71     return (buf.length() > 0);
72 }
73 
Write(const std::string & buf)74 bool StreamBuffer::Write(const std::string &buf)
75 {
76     return Write(buf.c_str(), buf.length()+1);
77 }
78 
Read(StreamBuffer & buf)79 bool StreamBuffer::Read(StreamBuffer &buf)
80 {
81     return buf.Write(Data(), Size());
82 }
83 
Write(const StreamBuffer & buf)84 bool StreamBuffer::Write(const StreamBuffer &buf)
85 {
86     return Write(buf.Data(), buf.Size());
87 }
88 
Read(char * buf,size_t size)89 bool StreamBuffer::Read(char *buf, size_t size)
90 {
91     if (ChkRWError()) {
92         return false;
93     }
94     if (buf == nullptr) {
95         MMI_HILOGE("Invalid input parameter buf=nullptr errCode:%{public}d", ERROR_NULL_POINTER);
96         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_READ;
97         return false;
98     }
99     if (size == 0) {
100         MMI_HILOGE("Invalid input parameter size=%{public}zu errCode:%{public}d", size, PARAM_INPUT_INVALID);
101         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_READ;
102         return false;
103     }
104     if (rPos_ + static_cast<int32_t>(size) > wPos_) {
105         MMI_HILOGE("Memory out of bounds on read... errCode:%{public}d", MEM_OUT_OF_BOUNDS);
106         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_READ;
107         return false;
108     }
109     errno_t ret = memcpy_sp(buf, size, ReadBuf(), size);
110     if (ret != EOK) {
111         MMI_HILOGE("Failed to call memcpy_sp. errCode:%{public}d", MEMCPY_SEC_FUN_FAIL);
112         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_READ;
113         return false;
114     }
115     rPos_ += static_cast<int32_t>(size);
116     rCount_ += 1;
117     return true;
118 }
119 
Write(const char * buf,size_t size)120 bool StreamBuffer::Write(const char *buf, size_t size)
121 {
122     if (ChkRWError()) {
123         return false;
124     }
125     if (buf == nullptr) {
126         MMI_HILOGE("Invalid input parameter buf=nullptr errCode:%{public}d", ERROR_NULL_POINTER);
127         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_WRITE;
128         return false;
129     }
130     if (size == 0) {
131         MMI_HILOGE("Invalid input parameter size=%{public}zu errCode:%{public}d", size, PARAM_INPUT_INVALID);
132         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_WRITE;
133         return false;
134     }
135     if (wPos_ + static_cast<int32_t>(size) > MAX_STREAM_BUF_SIZE) {
136         MMI_HILOGE("The write length exceeds buffer. wIdx:%{public}d size:%{public}zu maxBufSize:%{public}d "
137             "errCode:%{public}d", wPos_, size, MAX_STREAM_BUF_SIZE, MEM_OUT_OF_BOUNDS);
138         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_WRITE;
139         return false;
140     }
141     errno_t ret = memcpy_sp(&szBuff_[wPos_], GetAvailableBufSize(), buf, size);
142     if (ret != EOK) {
143         MMI_HILOGE("Failed to call memcpy_sp. errCode:%{public}d", MEMCPY_SEC_FUN_FAIL);
144         rwErrorStatus_ = ErrorStatus::ERROR_STATUS_WRITE;
145         return false;
146     }
147     wPos_ += static_cast<int32_t>(size);
148     wCount_ += 1;
149     return true;
150 }
151 
IsEmpty() const152 bool StreamBuffer::IsEmpty() const
153 {
154     return (rPos_ == wPos_);
155 }
156 
Size() const157 size_t StreamBuffer::Size() const
158 {
159     return static_cast<size_t>(wPos_);
160 }
161 
UnreadSize() const162 int32_t StreamBuffer::UnreadSize() const
163 {
164     return ((wPos_ <= rPos_) ? 0 : (wPos_ - rPos_));
165 }
166 
GetAvailableBufSize() const167 int32_t StreamBuffer::GetAvailableBufSize() const
168 {
169     return ((wPos_ >= MAX_STREAM_BUF_SIZE) ? 0 : (MAX_STREAM_BUF_SIZE - wPos_));
170 }
171 
ChkRWError() const172 bool StreamBuffer::ChkRWError() const
173 {
174     return (rwErrorStatus_ != ErrorStatus::ERROR_STATUS_OK);
175 }
176 
GetErrorStatusRemark() const177 const std::string &StreamBuffer::GetErrorStatusRemark() const
178 {
179     static const std::vector<std::pair<ErrorStatus, std::string>> remark {
180         { ErrorStatus::ERROR_STATUS_OK, "OK" },
181         { ErrorStatus::ERROR_STATUS_READ, "READ_ERROR" },
182         { ErrorStatus::ERROR_STATUS_WRITE, "WRITE_ERROR" },
183     };
184     for (const auto &it : remark) {
185         if (it.first == rwErrorStatus_) {
186             return it.second;
187         }
188     }
189     static const std::string invalidStatus = "UNKNOWN";
190     return invalidStatus;
191 }
192 
Data() const193 const char *StreamBuffer::Data() const
194 {
195     return &szBuff_[0];
196 }
197 
ReadBuf() const198 const char *StreamBuffer::ReadBuf() const
199 {
200     return &szBuff_[rPos_];
201 }
202 
WriteBuf() const203 const char *StreamBuffer::WriteBuf() const
204 {
205     return &szBuff_[wPos_];
206 }
207 
Clone(const StreamBuffer & buf)208 bool StreamBuffer::Clone(const StreamBuffer &buf)
209 {
210     Clean();
211     return Write(buf.Data(), buf.Size());
212 }
213 } // namespace MMI
214 } // namespace OHOS
215