blob: a735b1dd189c0cb8281f8e04c16eff5dd1a070c5 [file] [log] [blame]
xj4049f512022-04-02 15:41:13 +08001/* //device/system/rild/rild.c
2**
3** Copyright 2006 The Android Open Source Project
4**
5** Licensed under the Apache License, Version 2.0 (the "License");
6** you may not use this file except in compliance with the License.
7** You may obtain a copy of the License at
8**
9** http://www.apache.org/licenses/LICENSE-2.0
10**
11** Unless required by applicable law or agreed to in writing, software
12** distributed under the License is distributed on an "AS IS" BASIS,
13** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14** See the License for the specific language governing permissions and
15** limitations under the License.
16*/
17
18#include <stdio.h>
19#include <stdlib.h>
xj9db5b622022-05-04 16:50:24 +080020#include <stdbool.h>
xj4049f512022-04-02 15:41:13 +080021#include <dlfcn.h>
22#include <string.h>
23#include <pthread.h>
24#include <stdint.h>
25#include <unistd.h>
26#include <fcntl.h>
27#include <errno.h>
xj9db5b622022-05-04 16:50:24 +080028#include <log/log.h>
xj4049f512022-04-02 15:41:13 +080029#include <liblog/lynq_deflog.h>
30#include <include/lynq_uci.h>
31#include <sys/socket.h>
32#include <sys/un.h>
33
xj9db5b622022-05-04 16:50:24 +080034
xj4049f512022-04-02 15:41:13 +080035#define LOG_UCI_MODULE "lynq_autosuspend"
36#define LOG_UCI_FILE "lynq_uci"
37
38#define LOG_TAG "AUTOSUSPEND"
39
40#define USER_LOG_TAG "PMS"
41
xj9db5b622022-05-04 16:50:24 +080042#define SOCK_PATH "/tmp/autosuspend.cmd.server" //不能在当前这个目录创建socket文件,否则报错找不到文件(可能是因为这是在共享文件夹下,不支持创建socket文件)
43
44#define SOCK_DATA_PATH "/tmp/autosuspend.data.server"
xj4049f512022-04-02 15:41:13 +080045
46// #define LYINFLOG(X...) lynq_log_global_output(LOG_INFO,X)
47
48#define TIME_OUT_TIME 30
49
50
xj4049f512022-04-02 15:41:13 +080051#define MAX_LIB_ARGS 16
52
53int adb_debug_mode = 0;
54
xj9db5b622022-05-04 16:50:24 +080055
56pthread_cond_t feedback_cond = PTHREAD_COND_INITIALIZER;
57pthread_mutex_t feedback_mutex = PTHREAD_MUTEX_INITIALIZER;
58pthread_mutex_t time_info_mutex = PTHREAD_MUTEX_INITIALIZER;
59
xj4049f512022-04-02 15:41:13 +080060extern int autosuspend_enable(void);
61extern int autosuspend_disable(void);
62extern void init_wakelock_func(void);
63extern void init_sim_func();
64extern void init_network_func();
xj9db5b622022-05-04 16:50:24 +080065extern void set_wakeup_callback(void (*func)(bool success));
66extern void wakeup_feedback(bool success);
xj4049f512022-04-02 15:41:13 +080067
68
xj9db5b622022-05-04 16:50:24 +080069struct time_info_t
70{
71 long sleep_start_time;
72 long wakeup_time;
73};
74
75struct time_info_t time_info;
76
xj4049f512022-04-02 15:41:13 +080077static void usage(const char *argv0) {
78 fprintf(stderr, "Usage: %s -l <possible_max_sleep_time> [-- <args for Autosuspend Service>]\n", argv0);
79 exit(EXIT_FAILURE);
80}
81
82
83
84static int make_argv(char * args, char ** argv) {
85 // Note: reserve argv[0]
86 int count = 1;
87 char * tok;
88 char * s = args;
89
90 while ((tok = strtok(s, " \0"))) {
91 argv[count] = tok;
92 s = NULL;
93 count++;
94 }
95 return count;
96}
97
98static int Accept(int fd, struct sockaddr *sa, socklen_t *salenptr)
99{
100 int n;
101
102 while((n = accept(fd, sa, salenptr)) < 0)
103 {
104 if((errno == ECONNABORTED) || (errno == EINTR))
105 continue;
106 else
107 {
108 ALOGI("accept error\n");
109 return -1;
110 }
111 }
112 return n;
113}
114
115static int Bind(int fd, const struct sockaddr *sa, socklen_t salen)
116{
117 if(bind(fd, sa, salen) < 0)
118 {
119 // ALOGI("bind error\n");
120 perror("bind error");
121 return -1;
122 }
123 return 0;
124}
125
xj4049f512022-04-02 15:41:13 +0800126
127static int Socket(int family, int type, int protocol)
128{
129 int n;
130
131 if ( (n = socket(family, type, protocol)) < 0)
132 {
133 ALOGI("socket error\n");
134 return -1;
135 }
136 return n;
137}
138
139static int Listen(int fd, int backlog)
140{
141 if(listen(fd, backlog) < 0)
142 {
143 ALOGI("listen error\n");
144 return -1;
145 }
146 return 0;
147}
148
xj4049f512022-04-02 15:41:13 +0800149
150static int listen_port(struct sockaddr_un *addr, char *sockpath)
151{
152 int listenfd;
153 listenfd = Socket(AF_UNIX,SOCK_STREAM,0);
154 if(listenfd == -1)
155 return -1;
156 memset(addr, 0, sizeof(struct sockaddr_un));
157 addr->sun_family = AF_UNIX;
158 strcpy(addr->sun_path,sockpath);
159 // int opt = 1;
160 // if(setsockopt(listenfd, SOL_SOCKET,SO_REUSEADDR, (const void *)&opt, sizeof(opt)) == -1)
161 // {
162 // perror("setsockopt error");
163 // return -1;
164 // }
165
166// 以上方法对非网络的本地socket无效,应该用unlink函数避免Address already in use的错误
167
168
169 unlink(sockpath);
170 if(Bind(listenfd,(struct sockaddr *)addr,sizeof(*addr)) == -1)
171 return -1;
172
173 if(Listen(listenfd,20) == -1)
174 return -1;
175
176 return listenfd;
177}
178
179static ssize_t Read(int fd, void *ptr, size_t nbytes)
180{
181 ssize_t n;
182
183 while((n = read(fd, ptr, nbytes)) == -1)
184 {
185 //printf("READ,%d\n",fd);
186 if (errno == EINTR)
187 {
188 ALOGI("read error eintr\n");
189 continue;
190 }
xj9db5b622022-05-04 16:50:24 +0800191 else if(errno == EAGAIN || errno == EWOULDBLOCK)
xj4049f512022-04-02 15:41:13 +0800192 {
xj9db5b622022-05-04 16:50:24 +0800193 ALOGI("read time out\n");
xj4049f512022-04-02 15:41:13 +0800194 return -1;
195 }
196 else
197 {
198 ALOGI("read error\n");
199 return -1;
200 }
201 }
202 //sleep(2);
203 //printf("READ1,%d\n", fd);
204 return n;
205}
206
207static ssize_t Write(int fd, const void *ptr, size_t nbytes)
208{
209 ssize_t n;
210
211 while((n = write(fd, ptr, nbytes)) == -1)
212 {
213 if (errno == EINTR)
214 continue;
215 else if(errno == EPIPE)
216 {
217 ALOGI("write error epipe\n");
218 return -1;
219 }
220 else
221 return -1;
222 }
223 return n;
224}
225
226static int Close(int fd)
227{
228 if (close(fd) == -1)
229 {
xj9db5b622022-05-04 16:50:24 +0800230 ALOGI("close error\n");
xj4049f512022-04-02 15:41:13 +0800231 return -1;
232 }
233 return 0;
234}
235
xj9db5b622022-05-04 16:50:24 +0800236
xj4049f512022-04-02 15:41:13 +0800237void *deal_autosuspend(void *sockfd)
238{
239 int commfd = *((int *)sockfd);
xj9db5b622022-05-04 16:50:24 +0800240 char buf[20];
241 char res[15];
xj4049f512022-04-02 15:41:13 +0800242
243 while(1)
244 {
245 memset(buf,0,sizeof(buf));
246 ALOGI("deal_autosuspend start to read.\n");
247 // 错误点:read函数在对端关闭后,也会直接返回0,不会阻塞,因此要判断是否返回0,返回0表示对端已经关闭,此时要跳出while循环不再监听
248 // 为什么对端会关闭?因为在客户端没有用nohup方式打开的情况下,系统睡眠后客户端进行会直接被杀死,对端会关闭,所以会导致read不阻塞,且总是返回0的现象
xj9db5b622022-05-04 16:50:24 +0800249 if(Read(commfd,buf,sizeof(buf)) <= 0)
xj4049f512022-04-02 15:41:13 +0800250 {
xj9db5b622022-05-04 16:50:24 +0800251 ALOGI("service receive suspend_cmd fail.\n");
252 Close(commfd);
xj4049f512022-04-02 15:41:13 +0800253 break;
254 }
255 if(strcmp(buf,"enable") == 0)
256 {
257 if(autosuspend_enable() < 0)
258 {
259 ALOGI("autosuspend_enable fail.\n");
xj9db5b622022-05-04 16:50:24 +0800260 strcpy(res,"fail");
261 if(Write(commfd,res,strlen(res)) <= 0)
262 {
263 ALOGI("service send respond fail.\n");
264 Close(commfd);
265 break;
266 }
xj4049f512022-04-02 15:41:13 +0800267 }
268 else
269 {
270 ALOGI("autosuspend_enable success.\n");
xj9db5b622022-05-04 16:50:24 +0800271 strcpy(res,"enabled");
272 if(Write(commfd,res,strlen(res)) <= 0)
273 {
274 ALOGI("service send respond fail.\n");
275 Close(commfd);
276 break;
277 }
xj4049f512022-04-02 15:41:13 +0800278 }
279 }
280 else if(strcmp(buf,"disable") == 0)
281 {
282 if(autosuspend_disable() < 0)
283 {
284 ALOGI("autosuspend_disable fail.\n");
xj9db5b622022-05-04 16:50:24 +0800285 strcpy(res,"fail");
286 if(Write(commfd,res,strlen(res)) <= 0)
287 {
288 ALOGI("service send respond fail.\n");
289 Close(commfd);
290 break;
291 }
xj4049f512022-04-02 15:41:13 +0800292 }
293 else
294 {
295 ALOGI("autosuspend_disable success.\n");
xj9db5b622022-05-04 16:50:24 +0800296 strcpy(res,"disabled");
297 if(Write(commfd,res,strlen(res)) <= 0)
298 {
299 ALOGI("service send respond fail.\n");
300 Close(commfd);
301 break;
302 }
xj4049f512022-04-02 15:41:13 +0800303 }
304 }
xj9db5b622022-05-04 16:50:24 +0800305 // else if(strcmp(buf,"feedback") == 0)
306 // {
307
308 // ALOGI("send_feedback thread wait to send.\n");
309 // if (pthread_cond_wait(&feedback_cond,&feedback_mutex) != 0)
310 // {
311 // strerror_r(errno, buf, sizeof(buf));
312 // ALOGI("Error waiting on cond: %s\n", buf);
313 // Close(commfd);
314 // break;
315 // }
316
317 // ALOGI("send_feedback thread is now sending the feedback to client.\n");
318 // if(Write(commfd,&time_info,sizeof(struct time_info_t)) <= 0)
319 // {
320 // ALOGI("service send wakeup_feedback struct fail.\n");
321 // Close(commfd);
322 // break ;
323 // }
324 // ALOGI("service send feedback success.\n");
325 // strcpy(res,"success");
326 // if(Write(commfd,res,strlen(res)) <= 0)
327 // {
328 // ALOGI("service send respond fail.\n");
329 // Close(commfd);
330 // break;
331 // }
332
333 // }
xj4049f512022-04-02 15:41:13 +0800334 else
335 {
xj9db5b622022-05-04 16:50:24 +0800336 ALOGI("Unknown cmd : %s\n",buf);
xj4049f512022-04-02 15:41:13 +0800337 }
xj9db5b622022-05-04 16:50:24 +0800338
xj4049f512022-04-02 15:41:13 +0800339 }
340
341
342
343}
344
345
xj9db5b622022-05-04 16:50:24 +0800346void *send_feedback(void *sockfd)
347{
348 int commfd = *((int *)sockfd);
349 char buf[80];
350
351 while (1)
352 {
353 memset(buf,0,sizeof(buf));
354 ALOGI("send_feedback thread wait to send.\n");
355 pthread_mutex_lock(&feedback_mutex);
356 pthread_cond_wait(&feedback_cond,&feedback_mutex);
357
358
359 // strcpy(buf,"System is woken up!");
360
361 // if(Write(commfd,buf,sizeof(buf)) <= 0)
362 // {
363 // ALOGI("service send wakeup_feedback fail.\n");
364 // return ;
365 // }
366 ALOGI("send_feedback thread is now sending the feedback to client.\n");
367 pthread_mutex_lock(&time_info_mutex);
368 if(Write(commfd,&time_info,sizeof(struct time_info_t)) <= 0)
369 {
370 ALOGI("service send wakeup_feedback struct fail.\n");
371 Close(commfd);
372 pthread_mutex_unlock(&time_info_mutex);
373 pthread_mutex_unlock(&feedback_mutex);
374 break ;
375 }
376 pthread_mutex_unlock(&time_info_mutex);
377
378 pthread_mutex_unlock(&feedback_mutex);
379
380
381
382 }
383
384}
385
xj4049f512022-04-02 15:41:13 +0800386
387int main(int argc, char **argv) {
388
389
390 // int i = 0;
391 // RLOGD("**Autosuspend Service Daemon Started**");
392 // RLOGD("**Autosuspend Service param count=%d**", argc);
393 char tmp[20];
xj9db5b622022-05-04 16:50:24 +0800394
395 int commfd, commfd_data, server_sock, server_data_sock,len, len_data;
396
xj4049f512022-04-02 15:41:13 +0800397 struct sockaddr_un server_sockaddr;
xj9db5b622022-05-04 16:50:24 +0800398 struct sockaddr_un server_data_sockaddr;
xj4049f512022-04-02 15:41:13 +0800399 struct sockaddr_un client_sockaddr;
xj9db5b622022-05-04 16:50:24 +0800400
xj4049f512022-04-02 15:41:13 +0800401 len = sizeof(server_sockaddr);
402
xj9db5b622022-05-04 16:50:24 +0800403
xj4049f512022-04-02 15:41:13 +0800404 pthread_t tid;
405
xj4049f512022-04-02 15:41:13 +0800406 LYLOGEINIT(USER_LOG_TAG);
407 LYLOGSET(LOG_DEBUG);
408 // LYLOGSET(LOG_ERROR);
409
xj9db5b622022-05-04 16:50:24 +0800410 int auto_enable = 0;
xj4049f512022-04-02 15:41:13 +0800411
412 lynq_get_value(LOG_UCI_FILE, LOG_UCI_MODULE, "debug", tmp);
xj9db5b622022-05-04 16:50:24 +0800413 ALOGI("Autosuspend Service Daemon. debug %s\n",tmp);
xj4049f512022-04-02 15:41:13 +0800414 adb_debug_mode=atoi(tmp);
415 lynq_get_value(LOG_UCI_FILE, LOG_UCI_MODULE, "auto_enable", tmp);
416 auto_enable=atoi(tmp);
417 ALOGI("Autosuspend Service Daemon. auto_enable %s\n",tmp);
418 init_wakelock_func();
419 init_sim_func();
xj9db5b622022-05-04 16:50:24 +0800420
421
xj4049f512022-04-02 15:41:13 +0800422 // init_network_func();
xj9db5b622022-05-04 16:50:24 +0800423
424 // if(pthread_cond_init(&feedback_cond,NULL) != 0)
425 // {
426 // strerror_r(errno, buf, sizeof(buf));
427 // ALOGI("Error creating cond: %s\n", buf);
428 // return -1;
429 // }
430
431 set_wakeup_callback(wakeup_feedback);
432
xj4049f512022-04-02 15:41:13 +0800433 if(auto_enable==0)
434 {
435 if(autosuspend_disable() < 0)
436 {
437 ALOGI("autosuspend_disable fail.\n");
438 }
439 else
440 {
441 ALOGI("autosuspend_disable success.\n");
442 }
443 }
444 if(auto_enable==1)
445 {
446 if(autosuspend_enable() < 0)
447 {
448 ALOGI("autosuspend_enable fail.\n");
449 }
450 else
451 {
452 ALOGI("autosuspend_enable success.\n");
453 }
454 }
455
456
457 server_sock = listen_port(&server_sockaddr,SOCK_PATH);
458 if(server_sock == -1)
459 return -1;
460
xj9db5b622022-05-04 16:50:24 +0800461 server_data_sock = listen_port(&server_data_sockaddr,SOCK_DATA_PATH);
462 if(server_data_sock == -1)
463 return -1;
464
465
xj4049f512022-04-02 15:41:13 +0800466 while (1)
467 {
468 ALOGI("service socket listening...\n");
469 commfd = Accept(server_sock,(struct sockaddr *)&client_sockaddr,&len);
470 if(commfd == -1)
471 {
472 return -1;
473 }
474 if(getpeername(commfd, (struct sockaddr *)&client_sockaddr, &len) == -1)
475 {
476 ALOGI("GETPEERNAME ERROR.\n");
xj9db5b622022-05-04 16:50:24 +0800477 // Close(server_sock);
478 Close(commfd);
xj4049f512022-04-02 15:41:13 +0800479 continue;
480 }
481 else
482 {
483 ALOGI("Client socket filepath: %s\n", client_sockaddr.sun_path);
484 }
xj9db5b622022-05-04 16:50:24 +0800485
486 commfd_data = Accept(server_data_sock,NULL,NULL);
487 if(commfd_data == -1)
488 {
489 return -1;
490 }
491 ALOGI("data channel connected.\n");
492
xj4049f512022-04-02 15:41:13 +0800493 pthread_create(&tid,NULL,deal_autosuspend,(void*)&commfd);//这里很容易错,最后一个参数要取地址,这是一个指针
xj9db5b622022-05-04 16:50:24 +0800494 pthread_detach(tid);
495
496 pthread_create(&tid,NULL,send_feedback,(void*)&commfd_data);
497 pthread_detach(tid);
498
xj4049f512022-04-02 15:41:13 +0800499
500 }
501
502 /* for (i = 1; i < argc ;) {
503 if (0 == strcmp(argv[i], "-l") && (argc - i > 1)) {
504 rilLibPath = argv[i + 1];
505 i += 2;
506 } else if (0 == strcmp(argv[i], "--")) {
507 i++;
508 hasLibArgs = 1;
509 break;
510 } else if (0 == strcmp(argv[i], "-c") && (argc - i > 1)) {
511 clientId = argv[i+1];
512 i += 2;
513 } else {
514 usage(argv[0]);
515 }
516 }
517
518 if (clientId == NULL) {
519 clientId = "0";
520 } else if (atoi(clientId) >= MAX_RILDS) {
521 RLOGE("Max Number of rild's supported is: %d", MAX_RILDS);
522 exit(0);
523 }
524 if (strncmp(clientId, "0", MAX_CLIENT_ID_LENGTH)) {
525 strncpy(ril_service_name, ril_service_name_base, MAX_SERVICE_NAME_LENGTH);
526 strncat(ril_service_name, clientId, MAX_SERVICE_NAME_LENGTH);
527 }
528
529 if (rilLibPath == NULL) {
530 if ( 0 == property_get(LIB_PATH_PROPERTY, libPath, NULL)) {
531 // No lib sepcified on the command line, and nothing set in props.
532 // Assume "no-ril" case.
533 goto done;
534 } else {
535 rilLibPath = libPath;
536 }
537 }
538
539 dlHandle = dlopen(rilLibPath, RTLD_NOW);
540
541 if (dlHandle == NULL) {
542 RLOGE("dlopen failed: %s", dlerror());
543 exit(EXIT_FAILURE);
544 }
545
546 RIL_startEventLoop();
547
548 rilInit =
549 (const RIL_RadioFunctions *(*)(const struct RIL_Env *, int, char **))
550 dlsym(dlHandle, "RIL_Init");
551
552 if (rilInit == NULL) {
553 RLOGE("RIL_Init not defined or exported in %s\n", rilLibPath);
554 exit(EXIT_FAILURE);
555 }
556
557 dlerror(); // Clear any previous dlerror
558 rilUimInit =
559 (RIL_RadioFunctions *(*)(const struct RIL_Env *, int, char **))
560 dlsym(dlHandle, "RIL_SAP_Init");
561 err_str = dlerror();
562 if (err_str) {
563 RLOGW("RIL_SAP_Init not defined or exported in %s: %s\n", rilLibPath, err_str);
564 } else if (!rilUimInit) {
565 RLOGW("RIL_SAP_Init defined as null in %s. SAP Not usable\n", rilLibPath);
566 }
567
568 if (hasLibArgs) {
569 rilArgv = argv + i - 1;
570 argc = argc -i + 1;
571 } else {
572 static char * newArgv[MAX_LIB_ARGS];
573 static char args[PROPERTY_VALUE_MAX];
574 rilArgv = newArgv;
575 property_get(LIB_ARGS_PROPERTY, args, "");
576 argc = make_argv(args, rilArgv);
577 }
578
579 rilArgv[argc++] = "-c";
580 rilArgv[argc++] = (char*)clientId;
581 RLOGD("RIL_Init argc = %d clientId = %s", argc, rilArgv[argc-1]);
582
583 // Make sure there's a reasonable argv[0]
584 rilArgv[0] = argv[0];
585
586 funcs = rilInit(&s_rilEnv, argc, rilArgv);
587 RLOGD("RIL_Init rilInit completed");
588
589 RIL_register(funcs);
590
591 RLOGD("RIL_Init RIL_register completed");
592
593 if (rilUimInit) {
594 RLOGD("RIL_register_socket started");
595 RIL_register_socket(rilUimInit, RIL_SAP_SOCKET, argc, rilArgv);
596 }
597
598 RLOGD("RIL_register_socket completed");
599
600done:
601
602 rilc_thread_pool();
603
604 RLOGD("RIL_Init starting sleep loop");*/
xj9db5b622022-05-04 16:50:24 +0800605 // while (1) {
606 // // ALOGI("start autosuspend_enable:%d\n",(i++));
607 // sleep(5);
xj4049f512022-04-02 15:41:13 +0800608
xj9db5b622022-05-04 16:50:24 +0800609 // }
xj4049f512022-04-02 15:41:13 +0800610}