1 /*
2 * Copyright (c) 2022 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 return HDF_ERR_MALLOC_FAIL;
49 }
50
51 new->rxBox = CanRxBoxCreate();
52 if (new->rxBox == NULL) {
53 OsalMemFree(new);
54 return HDF_ERR_MALLOC_FAIL;
55 }
56
57 ret = CanClientAttach(new, cntlr);
58 if (ret != HDF_SUCCESS) {
59 CanRxBoxDestroy(new->rxBox);
60 OsalMemFree(new);
61 return ret;
62 }
63
64 *client = new;
65 return HDF_SUCCESS;
66 }
67
CanClientCreateByNumber(int32_t busNum,struct CanClient ** client)68 int32_t CanClientCreateByNumber(int32_t busNum, struct CanClient **client)
69 {
70 int32_t ret;
71 struct CanCntlr *cntlr = NULL;
72
73 cntlr = CanCntlrGetByNumber(busNum);
74 if (cntlr == NULL) {
75 return HDF_PLT_ERR_DEV_GET;
76 }
77
78 ret = CanClientCreate(cntlr, client);
79 if (ret != HDF_SUCCESS) {
80 CanCntlrPut(cntlr);
81 return ret;
82 }
83 return HDF_SUCCESS;
84 }
85
CanClientDestroy(struct CanClient * client)86 void CanClientDestroy(struct CanClient *client)
87 {
88 struct CanCntlr *cntlr = NULL;
89
90 if (client != NULL) {
91 cntlr = client->cntlr;
92 CanClientDetach(client);
93 CanCntlrPut(cntlr);
94 CanRxBoxDestroy(client->rxBox);
95 OsalMemFree(client);
96 }
97 }
98
CanClientWriteMsg(struct CanClient * client,const struct CanMsg * msg)99 int32_t CanClientWriteMsg(struct CanClient *client, const struct CanMsg *msg)
100 {
101 if (client == NULL) {
102 return HDF_ERR_INVALID_OBJECT;
103 }
104 return CanCntlrWriteMsg(client->cntlr, msg);
105 }
106
CanClientReadMsg(struct CanClient * client,struct CanMsg * msg,uint32_t tms)107 int32_t CanClientReadMsg(struct CanClient *client, struct CanMsg *msg, uint32_t tms)
108 {
109 int32_t ret;
110 struct CanMsg *cmsg = NULL;
111
112 if (client == NULL) {
113 return HDF_ERR_INVALID_OBJECT;
114 }
115
116 ret = CanRxBoxGetMsg(client->rxBox, &cmsg, tms);
117 if (ret != HDF_SUCCESS) {
118 return ret;
119 }
120
121 ret = memcpy_s(msg, sizeof(*msg), cmsg, sizeof(*cmsg));
122 CanMsgPut(cmsg); // decrease ref cnt after mem cpoy
123 return (ret == EOK) ? HDF_SUCCESS : HDF_ERR_IO;
124 }
125
CanClientAddFilter(struct CanClient * client,const struct CanFilter * filter)126 int32_t CanClientAddFilter(struct CanClient *client, const struct CanFilter *filter)
127 {
128 if (client == NULL) {
129 return HDF_ERR_INVALID_OBJECT;
130 }
131 return CanRxBoxAddFilter(client->rxBox, filter);
132 }
133
CanClientDelFilter(struct CanClient * client,const struct CanFilter * filter)134 int32_t CanClientDelFilter(struct CanClient *client, const struct CanFilter *filter)
135 {
136 if (client == NULL) {
137 return HDF_ERR_INVALID_OBJECT;
138 }
139 return CanRxBoxDelFilter(client->rxBox, filter);
140 }
141
CanClientSetCfg(struct CanClient * client,const struct CanConfig * cfg)142 int32_t CanClientSetCfg(struct CanClient *client, const struct CanConfig *cfg)
143 {
144 if (client == NULL) {
145 return HDF_ERR_INVALID_OBJECT;
146 }
147 return CanCntlrSetCfg(client->cntlr, cfg);
148 }
149
CanClientGetCfg(struct CanClient * client,struct CanConfig * cfg)150 int32_t CanClientGetCfg(struct CanClient *client, struct CanConfig *cfg)
151 {
152 if (client == NULL) {
153 return HDF_ERR_INVALID_OBJECT;
154 }
155 return CanCntlrGetCfg(client->cntlr, cfg);
156 }
157
CanClientGetState(struct CanClient * client)158 int32_t CanClientGetState(struct CanClient *client)
159 {
160 if (client == NULL) {
161 return HDF_ERR_INVALID_OBJECT;
162 }
163 return CanCntlrGetState(client->cntlr);
164 }
165