• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * This file is part of the openHiTLS project.
3  *
4  * openHiTLS is licensed under the Mulan PSL v2.
5  * You can use this software according to the terms and conditions of the Mulan PSL v2.
6  * You may obtain a copy of Mulan PSL v2 at:
7  *
8  *     http://license.coscl.org.cn/MulanPSL2
9  *
10  * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
11  * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
12  * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
13  * See the Mulan PSL v2 for more details.
14  */
15 
16 #include "simulate_io.h"
17 #include "hitls_error.h"
18 #include "bsl_sal.h"
19 #include "bsl_log_internal.h"
20 #include "bsl_log.h"
21 #include "bsl_errno.h"
22 #include "bsl_uio.h"
23 #include "securec.h"
24 
25 #define FAKE_BSL_UIO_FD 666
26 
FRAME_IO_CreateUserData(void)27 FrameUioUserData *FRAME_IO_CreateUserData(void)
28 {
29     FrameUioUserData *userData = BSL_SAL_Calloc(1u, sizeof(FrameUioUserData));
30     if (userData == NULL) {
31         return NULL;
32     }
33     return userData;
34 }
35 
FRAME_IO_FreeUserData(FrameUioUserData * userData)36 void FRAME_IO_FreeUserData(FrameUioUserData *userData)
37 {
38     if (userData == NULL) {
39         return;
40     }
41 
42     BSL_SAL_FREE(userData);
43     return;
44 }
45 
FRAME_Write(BSL_UIO * uio,const void * buf,uint32_t len,uint32_t * writeLen)46 int32_t FRAME_Write(BSL_UIO *uio, const void *buf, uint32_t len, uint32_t *writeLen)
47 {
48     *writeLen = 0;
49     FrameUioUserData *ioUserData = BSL_UIO_GetUserData(uio);
50     if (ioUserData == NULL) {
51         return BSL_NULL_INPUT;
52     }
53 
54     // This indicates that there is still a message in the buffer. The second message can be sent only after the peer
55     // end receives the message.
56     if (ioUserData->sndMsg.len != 0) {
57         return BSL_SUCCESS;
58     }
59 
60     memcpy_s(ioUserData->sndMsg.msg, MAX_RECORD_LENTH, buf, len);
61     ioUserData->sndMsg.len = len;
62     *writeLen = len;
63 
64     return BSL_SUCCESS;
65 }
66 
FRAME_Read(BSL_UIO * uio,void * buf,uint32_t len,uint32_t * readLen)67 int32_t FRAME_Read(BSL_UIO *uio, void *buf, uint32_t len, uint32_t *readLen)
68 {
69     *readLen = 0;
70     FrameUioUserData *ioUserData = BSL_UIO_GetUserData(uio);
71     if (ioUserData == NULL) {
72         return BSL_NULL_INPUT;
73     }
74     // This indicates that the user inserts data. Therefore, the simulated data inserted by the user is received first.
75     if (ioUserData->userInsertMsg.len != 0) {
76         if (len < ioUserData->userInsertMsg.len) {
77             return BSL_UIO_FAIL;
78         }
79 
80         memcpy_s(buf, len, ioUserData->userInsertMsg.msg, ioUserData->userInsertMsg.len);
81         *readLen = ioUserData->userInsertMsg.len;
82         ioUserData->userInsertMsg.len = 0;
83         return BSL_SUCCESS;
84     } else if (ioUserData->recMsg.len != 0) {
85         uint32_t copyLen = len < ioUserData->recMsg.len ? len : ioUserData->recMsg.len;
86         memcpy_s(buf, len, ioUserData->recMsg.msg, copyLen);
87         *readLen = copyLen;
88         if (copyLen < ioUserData->recMsg.len) {
89             memmove_s(ioUserData->recMsg.msg, ioUserData->recMsg.len,
90                 &ioUserData->recMsg.msg[copyLen], ioUserData->recMsg.len - copyLen);
91         }
92         ioUserData->recMsg.len -= copyLen;
93         return BSL_SUCCESS;
94     }  // If there is no data in the receive buffer, a success message is returned and *readLen is set to 0.
95 
96     return BSL_SUCCESS;
97 }
98 
FRAME_Ctrl(BSL_UIO * uio,int32_t cmd,int32_t larg,void * param)99 int32_t FRAME_Ctrl(BSL_UIO *uio, int32_t cmd, int32_t larg, void *param)
100 {
101     (void)uio;
102     (void)larg;
103     if (cmd == BSL_UIO_SCTP_SND_BUFF_IS_EMPTY) {
104         *(uint8_t *)param = true;
105     }
106 
107     if (cmd == BSL_UIO_GET_FD) {
108         *(int32_t *)param = FAKE_BSL_UIO_FD;
109     }
110 
111     return BSL_SUCCESS;
112 }
113 
114 /*
115     Frame_TransportSendMsg: Sends messages in the send buffer in the I/O.
116     Copy uio->userData to the buffer.
117 */
FRAME_TransportSendMsg(BSL_UIO * uio,void * buf,uint32_t len,uint32_t * readLen)118 int32_t FRAME_TransportSendMsg(BSL_UIO *uio, void *buf, uint32_t len, uint32_t *readLen)
119 {
120     *readLen = 0;
121     FrameUioUserData *ioUserData = BSL_UIO_GetUserData(uio);
122     if (ioUserData == NULL) {
123         return HITLS_NULL_INPUT;
124     }
125 
126     if (ioUserData->sndMsg.len != 0) {
127         // The length of the data in the buffer exceeds len.
128         if (len < ioUserData->sndMsg.len) {
129             return HITLS_UIO_FAIL;
130         }
131 
132         memcpy_s(buf, len, ioUserData->sndMsg.msg, ioUserData->sndMsg.len);
133         *readLen = ioUserData->sndMsg.len;
134         ioUserData->sndMsg.len = 0;
135     }  // If there is no data in the receive buffer, a success message is returned and *readLen is set to 0.
136 
137     return HITLS_SUCCESS;
138 }
139 
140 /*
141     Frame_TransportRecMsg simulates receiving messages from the I/O.
142     Copy the data in the buffer to uio->userData.
143 */
FRAME_TransportRecMsg(BSL_UIO * uio,void * buf,uint32_t len)144 int32_t FRAME_TransportRecMsg(BSL_UIO *uio, void *buf, uint32_t len)
145 {
146     FrameUioUserData *ioUserData = BSL_UIO_GetUserData(uio);
147     if (ioUserData == NULL) {
148         return HITLS_NULL_INPUT;
149     }
150 
151     if (ioUserData->recMsg.len != 0 || len > MAX_RECORD_LENTH) {
152         return HITLS_UIO_FAIL;
153     }
154 
155     memcpy_s(ioUserData->recMsg.msg, MAX_RECORD_LENTH, buf, len);
156     ioUserData->recMsg.len = len;
157 
158     return HITLS_SUCCESS;
159 }
160 
161 #ifdef __cplusplus
162 }
163 #endif
164