1 /*
2 * Copyright (c) 2022-2023 Huawei Device Co., Ltd.
3 *
4 * HDF is dual licensed: you can use it either under the terms of
5 * the GPL, or the BSD license, at your option.
6 * See the LICENSE file in the root of this repository for complete details.
7 */
8
9 #include "can/can_client.h"
10 #include "can/can_msg.h"
11 #include "osal_mem.h"
12 #include "securec.h"
13
14 struct CanClient {
15 struct CanCntlr *cntlr;
16 struct CanRxBox *rxBox; // receive message box
17 };
18
CanClientAttach(struct CanClient * client,struct CanCntlr * cntlr)19 static int32_t CanClientAttach(struct CanClient *client, struct CanCntlr *cntlr)
20 {
21 int32_t ret;
22
23 ret = CanCntlrAddRxBox(cntlr, client->rxBox);
24 if (ret == HDF_SUCCESS) {
25 client->cntlr = cntlr;
26 }
27 return ret;
28 }
29
CanClientDetach(struct CanClient * client)30 static int32_t CanClientDetach(struct CanClient *client)
31 {
32 int32_t ret;
33
34 ret = CanCntlrDelRxBox(client->cntlr, client->rxBox);
35 if (ret == HDF_SUCCESS) {
36 client->cntlr = NULL;
37 }
38 return ret;
39 }
40
CanClientCreate(struct CanCntlr * cntlr,struct CanClient ** client)41 static int32_t CanClientCreate(struct CanCntlr *cntlr, struct CanClient **client)
42 {
43 int32_t ret;
44 struct CanClient *new = NULL;
45
46 new = (struct CanClient *)OsalMemCalloc(sizeof(*new));
47 if (new == NULL) {
48 HDF_LOGE("CanClientCreate: memcalloc new fail!");
49 return HDF_ERR_MALLOC_FAIL;
50 }
51
52 new->rxBox = CanRxBoxCreate();
53 if (new->rxBox == NULL) {
54 OsalMemFree(new);
55 HDF_LOGE("CanClientCreate: can rxBox create fail!");
56 return HDF_ERR_MALLOC_FAIL;
57 }
58
59 ret = CanClientAttach(new, cntlr);
60 if (ret != HDF_SUCCESS) {
61 CanRxBoxDestroy(new->rxBox);
62 OsalMemFree(new);
63 HDF_LOGE("CanClientCreate: can client attach fail!");
64 return ret;
65 }
66
67 *client = new;
68 return HDF_SUCCESS;
69 }
70
CanClientCreateByNumber(int32_t busNum,struct CanClient ** client)71 int32_t CanClientCreateByNumber(int32_t busNum, struct CanClient **client)
72 {
73 int32_t ret;
74 struct CanCntlr *cntlr = NULL;
75
76 cntlr = CanCntlrGetByNumber(busNum);
77 if (cntlr == NULL) {
78 HDF_LOGE("CanClientCreateByNumber: busNum get can cntlr fail!");
79 return HDF_PLT_ERR_DEV_GET;
80 }
81
82 ret = CanClientCreate(cntlr, client);
83 if (ret != HDF_SUCCESS) {
84 CanCntlrPut(cntlr);
85 HDF_LOGE("CanClientCreateByNumber: can client create fail!");
86 return ret;
87 }
88 return HDF_SUCCESS;
89 }
90
CanClientDestroy(struct CanClient * client)91 void CanClientDestroy(struct CanClient *client)
92 {
93 struct CanCntlr *cntlr = NULL;
94
95 if (client != NULL) {
96 cntlr = client->cntlr;
97 CanClientDetach(client);
98 CanCntlrPut(cntlr);
99 CanRxBoxDestroy(client->rxBox);
100 OsalMemFree(client);
101 }
102 }
103
CanClientWriteMsg(struct CanClient * client,const struct CanMsg * msg)104 int32_t CanClientWriteMsg(struct CanClient *client, const struct CanMsg *msg)
105 {
106 if (client == NULL) {
107 HDF_LOGE("CanClientWriteMsg: client is null!");
108 return HDF_ERR_INVALID_OBJECT;
109 }
110 return CanCntlrWriteMsg(client->cntlr, msg);
111 }
112
CanClientReadMsg(struct CanClient * client,struct CanMsg * msg,uint32_t tms)113 int32_t CanClientReadMsg(struct CanClient *client, struct CanMsg *msg, uint32_t tms)
114 {
115 int32_t ret;
116 struct CanMsg *cmsg = NULL;
117
118 if (client == NULL) {
119 HDF_LOGE("CanClientReadMsg: client is null!");
120 return HDF_ERR_INVALID_OBJECT;
121 }
122
123 ret = CanRxBoxGetMsg(client->rxBox, &cmsg, tms);
124 if (ret != HDF_SUCCESS) {
125 HDF_LOGE("CanClientReadMsg: can rxBox get msg fail!");
126 return ret;
127 }
128
129 ret = memcpy_s(msg, sizeof(*msg), cmsg, sizeof(*cmsg));
130 CanMsgPut(cmsg); // decrease ref cnt after mem cpoy
131 return (ret == EOK) ? HDF_SUCCESS : HDF_ERR_IO;
132 }
133
CanClientAddFilter(struct CanClient * client,const struct CanFilter * filter)134 int32_t CanClientAddFilter(struct CanClient *client, const struct CanFilter *filter)
135 {
136 if (client == NULL) {
137 HDF_LOGE("CanClientAddFilter: client is null!");
138 return HDF_ERR_INVALID_OBJECT;
139 }
140 return CanRxBoxAddFilter(client->rxBox, filter);
141 }
142
CanClientDelFilter(struct CanClient * client,const struct CanFilter * filter)143 int32_t CanClientDelFilter(struct CanClient *client, const struct CanFilter *filter)
144 {
145 if (client == NULL) {
146 HDF_LOGE("CanClientDelFilter: client is null!");
147 return HDF_ERR_INVALID_OBJECT;
148 }
149 return CanRxBoxDelFilter(client->rxBox, filter);
150 }
151
CanClientSetCfg(struct CanClient * client,const struct CanConfig * cfg)152 int32_t CanClientSetCfg(struct CanClient *client, const struct CanConfig *cfg)
153 {
154 if (client == NULL) {
155 HDF_LOGE("CanClientSetCfg: client is null!");
156 return HDF_ERR_INVALID_OBJECT;
157 }
158 return CanCntlrSetCfg(client->cntlr, cfg);
159 }
160
CanClientGetCfg(struct CanClient * client,struct CanConfig * cfg)161 int32_t CanClientGetCfg(struct CanClient *client, struct CanConfig *cfg)
162 {
163 if (client == NULL) {
164 HDF_LOGE("CanClientGetCfg: client is null!");
165 return HDF_ERR_INVALID_OBJECT;
166 }
167 return CanCntlrGetCfg(client->cntlr, cfg);
168 }
169
CanClientGetState(struct CanClient * client)170 int32_t CanClientGetState(struct CanClient *client)
171 {
172 if (client == NULL) {
173 HDF_LOGE("CanClientGetState: client is null!");
174 return HDF_ERR_INVALID_OBJECT;
175 }
176 return CanCntlrGetState(client->cntlr);
177 }
178