1 /*
2 * Copyright (C) 2019-2020 Alibaba Group Holding Limited
3 */
4
5 #include <string.h>
6
7 //#include <aos/osal_debug.h>
8 #include <aos/kernel.h>
9
10 #include "internal.h"
11
12 #define TAG "uSrv"
13
14
uservice_lock(uservice_t * srv)15 void uservice_lock(uservice_t *srv)
16 {
17 aos_assert(srv);
18 if (srv->task)
19 TASK_LOCK(srv->task);
20 }
21
uservice_unlock(uservice_t * srv)22 void uservice_unlock(uservice_t *srv)
23 {
24 aos_assert(srv);
25 if (srv->task)
26 TASK_UNLOCK(srv->task);
27 }
28
uservice_call(uservice_t * srv,rpc_t * rpc)29 int uservice_call(uservice_t *srv, rpc_t *rpc)
30 {
31 aos_assert(srv);
32 aos_assert(srv->task);
33
34 rpc->srv = srv;
35
36 #ifdef CONFIG_DEBUG
37 if(rpc->data && rpc->data->timeout_ms != 0) {
38 aos_assert(aos_task_self() != srv->task->task);
39 }
40 #endif
41
42 int count = 10;
43 while (count--) {
44 if (aos_queue_send(&srv->task->queue, rpc, sizeof(rpc_t)) == 0) {
45 return rpc_wait(rpc);
46 } else {
47 if ( count == 1) {
48 printf("uService %s queue full,send id:%d cur id: %d", srv->name,rpc->cmd_id, srv->task->current_rpc->cmd_id);
49 }
50 //if (!aos_irq_context())
51 aos_msleep(100);
52 }
53 }
54
55 return -1;
56 }
57
uservice_call_sync(uservice_t * srv,int cmd,void * param,void * resp,size_t size)58 int uservice_call_sync(uservice_t *srv, int cmd, void *param, void *resp, size_t size)
59 {
60 aos_assert(srv);
61
62 rpc_t rpc;
63 int ret;
64
65 ret = rpc_init(&rpc, cmd, AOS_WAIT_FOREVER);
66
67 if (ret < 0)
68 return ret;
69
70 if (param)
71 rpc_put_point(&rpc, param);
72
73 ret = uservice_call(srv, &rpc);
74
75 if (resp != NULL && size > 0 && ret == 0) {
76 int count;
77 void *data = rpc_get_buffer(&rpc, &count);
78 aos_assert(count == size && data != NULL);
79 if (data)
80 memcpy(resp, data, size);
81 }
82
83 rpc_deinit(&rpc);
84
85 return ret;
86 }
87
uservice_call_async(uservice_t * srv,int cmd,void * param,size_t param_size)88 int uservice_call_async(uservice_t *srv, int cmd, void *param, size_t param_size)
89 {
90 aos_assert(srv);
91
92 rpc_t rpc;
93 int ret;
94
95 ret = rpc_init(&rpc, cmd, 0);
96
97 if (ret == 0) {
98 if (param && param_size > 0)
99 rpc_put_buffer(&rpc, param, param_size);
100
101 ret = uservice_call(srv, &rpc);
102 rpc_deinit(&rpc);
103 }
104
105 return ret;
106 }
107
uservice_new(const char * name,process_t process_rpc,void * context)108 uservice_t *uservice_new(const char *name, process_t process_rpc, void *context)
109 {
110 aos_assert(process_rpc && name);
111 uservice_t *srv = aos_zalloc(sizeof(uservice_t));
112
113 if (srv == NULL)
114 return NULL;
115
116 srv->name = name;
117 srv->context = context;
118 srv->process_rpc = process_rpc;
119
120 return srv;
121 }
122
uservice_destroy(uservice_t * srv)123 void uservice_destroy(uservice_t *srv)
124 {
125 aos_assert(srv);
126
127 aos_free(srv);
128 }
129
uservice_process(void * context,rpc_t * rpc,const rpc_process_t rpcs[])130 int uservice_process(void *context, rpc_t *rpc, const rpc_process_t rpcs[])
131 {
132 for (int i = 0; rpcs[i].process != NULL; i++) {
133 if (rpcs[i].cmd_id == rpc->cmd_id) {
134 if (rpcs[i].process(context, rpc) >= 0)
135 rpc_reply(rpc);
136 return 0;
137 }
138 }
139
140 return -1;
141 }
142
uservice_event_process(uint32_t event_id,const void * data,void * context)143 static void uservice_event_process(uint32_t event_id, const void *data, void *context)
144 {
145 uservice_t *srv = (uservice_t*)context;
146 rpc_t rpc;
147
148 aos_assert(srv);
149
150 if (rpc_init(&rpc, event_id, 0) == 0) {
151 rpc_put_point(&rpc, data);
152 uservice_call(srv, &rpc);
153 rpc_deinit(&rpc);
154 }
155 }
156
uservice_subscribe(uservice_t * srv,uint32_t event_id)157 void uservice_subscribe(uservice_t *srv, uint32_t event_id)
158 {
159 aos_assert(srv);
160 event_subscribe(event_id, uservice_event_process, srv);
161 }
162