xref: /OK3568_Linux_fs/external/rk_pcba_test/echo_ir_test.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /*
2*4882a593Smuzhiyun  *  echo_ir_test.c  --  Infrared ray test application
3*4882a593Smuzhiyun  *
4*4882a593Smuzhiyun  *  Copyright (c) 2018 Rockchip Electronics Co. Ltd.
5*4882a593Smuzhiyun  *  Author: chad.ma <chad.ma@rock-chips.com>
6*4882a593Smuzhiyun  *
7*4882a593Smuzhiyun  * Licensed under the Apache License, Version 2.0 (the "License");
8*4882a593Smuzhiyun  * you may not use this file except in compliance with the License.
9*4882a593Smuzhiyun  * You may obtain a copy of the License at
10*4882a593Smuzhiyun  *
11*4882a593Smuzhiyun  *   http://www.apache.org/licenses/LICENSE-2.0
12*4882a593Smuzhiyun  *
13*4882a593Smuzhiyun  * Unless required by applicable law or agreed to in writing, software
14*4882a593Smuzhiyun  * distributed under the License is distributed on an "AS IS" BASIS,
15*4882a593Smuzhiyun  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16*4882a593Smuzhiyun  * See the License for the specific language governing permissions and
17*4882a593Smuzhiyun  * limitations under the License.
18*4882a593Smuzhiyun  */
19*4882a593Smuzhiyun 
20*4882a593Smuzhiyun #include <assert.h>
21*4882a593Smuzhiyun #include <stdio.h>
22*4882a593Smuzhiyun #include <stdlib.h>
23*4882a593Smuzhiyun #include <string.h>
24*4882a593Smuzhiyun #include <errno.h>
25*4882a593Smuzhiyun #include <fcntl.h>
26*4882a593Smuzhiyun #include <linux/input.h>
27*4882a593Smuzhiyun #include <signal.h>
28*4882a593Smuzhiyun #include <unistd.h>
29*4882a593Smuzhiyun 
30*4882a593Smuzhiyun #define LOG_TAG "IR_test"
31*4882a593Smuzhiyun #include "common.h"
32*4882a593Smuzhiyun 
33*4882a593Smuzhiyun #define IR_INPUT_EVENT "/dev/input/event0"
34*4882a593Smuzhiyun 
35*4882a593Smuzhiyun #define IR_TIMEOUT_DOWN    60
36*4882a593Smuzhiyun #define IR_TIMEOUT_UP      5
37*4882a593Smuzhiyun 
38*4882a593Smuzhiyun 
39*4882a593Smuzhiyun /* TV Remote Controler
40*4882a593Smuzhiyun  * here accord kernel ir drivers keymap,./driver/media/rc/keymaps/rc-360.c
41*4882a593Smuzhiyun  * just defien 10 keys.
42*4882a593Smuzhiyun */
43*4882a593Smuzhiyun #define IR_VALID_NUM              10
44*4882a593Smuzhiyun 
45*4882a593Smuzhiyun typedef struct IR_CONTRALOR_st {
46*4882a593Smuzhiyun     char *key_name;
47*4882a593Smuzhiyun     int key_value;
48*4882a593Smuzhiyun     int key_press_flag;
49*4882a593Smuzhiyun } IR_st;
50*4882a593Smuzhiyun 
51*4882a593Smuzhiyun 
52*4882a593Smuzhiyun IR_st gIR_test[IR_VALID_NUM] = {
53*4882a593Smuzhiyun     {"NUM_0",    KEY_0,    0},
54*4882a593Smuzhiyun     {"NUM_1",    KEY_1,    0},
55*4882a593Smuzhiyun     {"NUM_2",    KEY_2,    0},
56*4882a593Smuzhiyun     {"NUM_3",    KEY_3,    0},
57*4882a593Smuzhiyun     {"NUM_4",    KEY_4,    0},
58*4882a593Smuzhiyun     {"NUM_5",    KEY_5,    0},
59*4882a593Smuzhiyun     {"NUM_6",    KEY_6,    0},
60*4882a593Smuzhiyun     {"NUM_7",    KEY_7,    0},
61*4882a593Smuzhiyun     {"NUM_8",    KEY_8,    0},
62*4882a593Smuzhiyun     {"NUM_9",    KEY_9,    0},
63*4882a593Smuzhiyun 
64*4882a593Smuzhiyun };
isAllIRKeyPressed(IR_st * key_array)65*4882a593Smuzhiyun static int isAllIRKeyPressed(IR_st *key_array)
66*4882a593Smuzhiyun {
67*4882a593Smuzhiyun     int i = 0;
68*4882a593Smuzhiyun 
69*4882a593Smuzhiyun     if (key_array == NULL)
70*4882a593Smuzhiyun         return 0;
71*4882a593Smuzhiyun 
72*4882a593Smuzhiyun     for (i = 0; i < IR_VALID_NUM; i++) {
73*4882a593Smuzhiyun         if (key_array[i].key_press_flag)
74*4882a593Smuzhiyun             continue;
75*4882a593Smuzhiyun         else
76*4882a593Smuzhiyun             break;
77*4882a593Smuzhiyun     }
78*4882a593Smuzhiyun 
79*4882a593Smuzhiyun     if (i == IR_VALID_NUM) {
80*4882a593Smuzhiyun         log_info("########### All IR key had pressed!!! ######### \n");
81*4882a593Smuzhiyun         return 1;
82*4882a593Smuzhiyun     } else
83*4882a593Smuzhiyun         return 0;
84*4882a593Smuzhiyun }
85*4882a593Smuzhiyun 
dumpKeyPressInfo(IR_st * key_array)86*4882a593Smuzhiyun static void dumpKeyPressInfo(IR_st *key_array)
87*4882a593Smuzhiyun {
88*4882a593Smuzhiyun     int i = 0;
89*4882a593Smuzhiyun 
90*4882a593Smuzhiyun     if (key_array == NULL)
91*4882a593Smuzhiyun         return;
92*4882a593Smuzhiyun 
93*4882a593Smuzhiyun     for (i = 0; i < IR_VALID_NUM; i++) {
94*4882a593Smuzhiyun         log_info("KEYNAME : %s: \t KEY_press: %d \n", key_array[i].key_name,
95*4882a593Smuzhiyun                  key_array[i].key_press_flag);
96*4882a593Smuzhiyun     }
97*4882a593Smuzhiyun }
98*4882a593Smuzhiyun 
assemble_info(char * key_info_buf,int buf_size,int key_index)99*4882a593Smuzhiyun static char *assemble_info(char *key_info_buf, int buf_size, int key_index)
100*4882a593Smuzhiyun {
101*4882a593Smuzhiyun     int error_code = 0;
102*4882a593Smuzhiyun     char msg[32] = {0};
103*4882a593Smuzhiyun 
104*4882a593Smuzhiyun     memset(msg, sizeof(msg), 0);
105*4882a593Smuzhiyun 
106*4882a593Smuzhiyun     if (key_info_buf == NULL)
107*4882a593Smuzhiyun         return NULL;
108*4882a593Smuzhiyun 
109*4882a593Smuzhiyun     memset(key_info_buf, buf_size, 0);
110*4882a593Smuzhiyun 
111*4882a593Smuzhiyun     snprintf(msg, sizeof(msg), "ir-key name:%s", gIR_test[key_index].key_name);
112*4882a593Smuzhiyun     snprintf(key_info_buf, buf_size, "x<%s>,<%s>,<%d>", msg, RESULT_KEY_PRESS, error_code);
113*4882a593Smuzhiyun 
114*4882a593Smuzhiyun     return key_info_buf;
115*4882a593Smuzhiyun }
save_scan_result(char * result_buf)116*4882a593Smuzhiyun static int save_scan_result(char *result_buf)
117*4882a593Smuzhiyun {
118*4882a593Smuzhiyun     int fd = -1;
119*4882a593Smuzhiyun     int ret = 0;
120*4882a593Smuzhiyun     char *bin_name = "echo_ir_test";
121*4882a593Smuzhiyun     char result_filename[COMMAND_VALUESIZE] = {0};
122*4882a593Smuzhiyun 
123*4882a593Smuzhiyun     snprintf(result_filename, sizeof(result_filename),
124*4882a593Smuzhiyun              "%s/%s_result",
125*4882a593Smuzhiyun              TEST_RESULT_SAVE_PATH,
126*4882a593Smuzhiyun              bin_name);
127*4882a593Smuzhiyun 
128*4882a593Smuzhiyun     fd = open(result_filename, O_CREAT | O_WRONLY   | O_TRUNC);
129*4882a593Smuzhiyun 
130*4882a593Smuzhiyun     if (fd < 0) {
131*4882a593Smuzhiyun         log_err("open %s fail, errno = %d\n", result_filename, errno);
132*4882a593Smuzhiyun         ret = errno;
133*4882a593Smuzhiyun     }
134*4882a593Smuzhiyun 
135*4882a593Smuzhiyun     assert(strlen(result_buf) <= COMMAND_VALUESIZE);
136*4882a593Smuzhiyun     int w_len = write(fd, result_buf, strlen(result_buf));
137*4882a593Smuzhiyun 
138*4882a593Smuzhiyun     if (w_len <= 0) {
139*4882a593Smuzhiyun         log_err("Write %s fail, errno = %d\n", result_filename, errno);
140*4882a593Smuzhiyun         ret = errno;
141*4882a593Smuzhiyun     }
142*4882a593Smuzhiyun 
143*4882a593Smuzhiyun     log_info("\t -------IR_test_result: %s -------\n", result_buf);
144*4882a593Smuzhiyun     log_info("########## write to %s len %d ##########\n", result_filename, w_len);
145*4882a593Smuzhiyun 
146*4882a593Smuzhiyun     close(fd);
147*4882a593Smuzhiyun 
148*4882a593Smuzhiyun     return ret;
149*4882a593Smuzhiyun }
150*4882a593Smuzhiyun 
151*4882a593Smuzhiyun static char result[COMMAND_VALUESIZE] = RESULT_FAIL;
152*4882a593Smuzhiyun 
ir_wait_event(int maxfd,fd_set * readfds,int time)153*4882a593Smuzhiyun static int ir_wait_event(int maxfd, fd_set *readfds, int time)
154*4882a593Smuzhiyun {
155*4882a593Smuzhiyun     int ret;
156*4882a593Smuzhiyun     struct timeval timeout;
157*4882a593Smuzhiyun 
158*4882a593Smuzhiyun     FD_ZERO(readfds);
159*4882a593Smuzhiyun     FD_SET(maxfd, readfds);
160*4882a593Smuzhiyun     timeout.tv_sec = time;
161*4882a593Smuzhiyun     timeout.tv_usec = 0;
162*4882a593Smuzhiyun     ret = select(maxfd + 1, readfds, NULL, NULL, &timeout);
163*4882a593Smuzhiyun 
164*4882a593Smuzhiyun     switch (ret) {
165*4882a593Smuzhiyun     case -1:
166*4882a593Smuzhiyun         return -1;
167*4882a593Smuzhiyun 
168*4882a593Smuzhiyun     case 0:
169*4882a593Smuzhiyun         log_err("select timeout(%ds)\n", time);
170*4882a593Smuzhiyun         return 1;
171*4882a593Smuzhiyun 
172*4882a593Smuzhiyun     default:
173*4882a593Smuzhiyun         if (FD_ISSET(maxfd, readfds)) {
174*4882a593Smuzhiyun             FD_CLR (maxfd, readfds);
175*4882a593Smuzhiyun             return 0;
176*4882a593Smuzhiyun         }
177*4882a593Smuzhiyun 
178*4882a593Smuzhiyun         break;
179*4882a593Smuzhiyun     }
180*4882a593Smuzhiyun 
181*4882a593Smuzhiyun     return -1;
182*4882a593Smuzhiyun }
183*4882a593Smuzhiyun 
ir_event_read(int fd,struct input_event * buf)184*4882a593Smuzhiyun static int ir_event_read(int fd, struct input_event *buf)
185*4882a593Smuzhiyun {
186*4882a593Smuzhiyun     int read_len = 0;
187*4882a593Smuzhiyun 
188*4882a593Smuzhiyun     read_len = read(fd, buf, sizeof(*buf));
189*4882a593Smuzhiyun 
190*4882a593Smuzhiyun     if (read_len < 0) {
191*4882a593Smuzhiyun         if ((errno != EINTR) && (errno != EAGAIN))
192*4882a593Smuzhiyun             return 0;
193*4882a593Smuzhiyun 
194*4882a593Smuzhiyun         return -1;
195*4882a593Smuzhiyun     }
196*4882a593Smuzhiyun 
197*4882a593Smuzhiyun     if (buf->type)
198*4882a593Smuzhiyun         return 1;
199*4882a593Smuzhiyun 
200*4882a593Smuzhiyun     return 0;
201*4882a593Smuzhiyun }
202*4882a593Smuzhiyun 
203*4882a593Smuzhiyun //* 信号处理函数,在结束进程前,为按键测试返回一个结果;
ir_result_send(int sign_no)204*4882a593Smuzhiyun static int ir_result_send(int sign_no)
205*4882a593Smuzhiyun {
206*4882a593Smuzhiyun     int err_code = 0;
207*4882a593Smuzhiyun     printf("====================function : %s start =================\n", __func__);
208*4882a593Smuzhiyun 
209*4882a593Smuzhiyun     if (!memcmp(result, RESULT_VERIFY, strlen(RESULT_VERIFY)))
210*4882a593Smuzhiyun         err_code = IR_QUERY_FAIL;
211*4882a593Smuzhiyun 
212*4882a593Smuzhiyun     send_msg_to_server("key_test", result, err_code);
213*4882a593Smuzhiyun 
214*4882a593Smuzhiyun     printf("====================function : %s finished =================\n", __func__);
215*4882a593Smuzhiyun     exit(0);
216*4882a593Smuzhiyun }
217*4882a593Smuzhiyun 
218*4882a593Smuzhiyun #define MAX_INPUT_COUNT (4)
main(int argc,char ** argv)219*4882a593Smuzhiyun int main(int argc, char **argv)
220*4882a593Smuzhiyun {
221*4882a593Smuzhiyun     int fd;
222*4882a593Smuzhiyun     int ret = 0;
223*4882a593Smuzhiyun     int err_code = 0;
224*4882a593Smuzhiyun     int time = IR_TIMEOUT_DOWN;
225*4882a593Smuzhiyun     fd_set rdfds;
226*4882a593Smuzhiyun     struct input_event key_event;
227*4882a593Smuzhiyun     int modifier;
228*4882a593Smuzhiyun     char buf[COMMAND_VALUESIZE] = "ir_test";
229*4882a593Smuzhiyun     int idx = 0;
230*4882a593Smuzhiyun     int fds[MAX_INPUT_COUNT] = {0};
231*4882a593Smuzhiyun     char path[64];
232*4882a593Smuzhiyun     int fdcount = 0;
233*4882a593Smuzhiyun     int max_fd = 0;
234*4882a593Smuzhiyun     int i, k;
235*4882a593Smuzhiyun     struct timeval sel_timeout_tv;
236*4882a593Smuzhiyun 
237*4882a593Smuzhiyun     log_info("key test process start...\n");
238*4882a593Smuzhiyun     //* 注册信号处理函数
239*4882a593Smuzhiyun     signal(SIGTERM, (__sighandler_t)ir_result_send);
240*4882a593Smuzhiyun 
241*4882a593Smuzhiyun     for (i = 0; i < MAX_INPUT_COUNT; i++) {
242*4882a593Smuzhiyun         sprintf(path, "/dev/input/event%d", i);
243*4882a593Smuzhiyun         fd = open(path, O_RDONLY | O_NOCTTY);
244*4882a593Smuzhiyun 
245*4882a593Smuzhiyun         if (fd < 0) {
246*4882a593Smuzhiyun             log_err("open fail:%s\n", strerror(errno));
247*4882a593Smuzhiyun             continue;
248*4882a593Smuzhiyun         }
249*4882a593Smuzhiyun 
250*4882a593Smuzhiyun         fds[fdcount++] = fd;
251*4882a593Smuzhiyun     }
252*4882a593Smuzhiyun 
253*4882a593Smuzhiyun     if (fdcount < 1) {
254*4882a593Smuzhiyun         err_code = IR_OPEN_FAIL;
255*4882a593Smuzhiyun         goto EXIT;
256*4882a593Smuzhiyun     }
257*4882a593Smuzhiyun 
258*4882a593Smuzhiyun     for (i = 0 ; i < fdcount; i++)
259*4882a593Smuzhiyun         if (max_fd < fds[i])
260*4882a593Smuzhiyun             max_fd = fds[i];
261*4882a593Smuzhiyun 
262*4882a593Smuzhiyun     while (1) {
263*4882a593Smuzhiyun         FD_ZERO(&rdfds);
264*4882a593Smuzhiyun         sel_timeout_tv.tv_sec = time;
265*4882a593Smuzhiyun         sel_timeout_tv.tv_usec = 0;
266*4882a593Smuzhiyun 
267*4882a593Smuzhiyun         for (i = 0 ; i < fdcount; i++)
268*4882a593Smuzhiyun             FD_SET(fds[i], &rdfds);
269*4882a593Smuzhiyun 
270*4882a593Smuzhiyun         if (isAllIRKeyPressed(gIR_test))
271*4882a593Smuzhiyun             break;
272*4882a593Smuzhiyun 
273*4882a593Smuzhiyun         ret = select(max_fd + 1, &rdfds, NULL, NULL, &sel_timeout_tv);
274*4882a593Smuzhiyun         if (ret > 0) {
275*4882a593Smuzhiyun             k = 0;
276*4882a593Smuzhiyun 
277*4882a593Smuzhiyun             while (k < fdcount) {
278*4882a593Smuzhiyun                 int fd = fds[k++];
279*4882a593Smuzhiyun 
280*4882a593Smuzhiyun                 if (FD_ISSET(fd, &rdfds)) {
281*4882a593Smuzhiyun                     ret = ir_event_read(fd, &key_event);
282*4882a593Smuzhiyun 
283*4882a593Smuzhiyun                     if (ret > 0) {
284*4882a593Smuzhiyun                         if (key_event.value) {
285*4882a593Smuzhiyun                             log_info("key(%d) is down\n", key_event.code);
286*4882a593Smuzhiyun                             time = IR_TIMEOUT_UP;
287*4882a593Smuzhiyun                         } else {
288*4882a593Smuzhiyun                             log_info("key(%d) is up\n", key_event.code);
289*4882a593Smuzhiyun                             time = IR_TIMEOUT_DOWN;
290*4882a593Smuzhiyun 
291*4882a593Smuzhiyun                             for (idx = 0; idx < IR_VALID_NUM; idx ++) {
292*4882a593Smuzhiyun                                 if (key_event.code == gIR_test[idx].key_value) {
293*4882a593Smuzhiyun                                     if (gIR_test[idx].key_press_flag == 0)
294*4882a593Smuzhiyun                                         gIR_test[idx].key_press_flag = 1;
295*4882a593Smuzhiyun 
296*4882a593Smuzhiyun                                     assemble_info(buf, COMMAND_VALUESIZE, idx);
297*4882a593Smuzhiyun                                     save_scan_result(buf);
298*4882a593Smuzhiyun                                 } else
299*4882a593Smuzhiyun                                     continue;
300*4882a593Smuzhiyun                             }
301*4882a593Smuzhiyun 
302*4882a593Smuzhiyun                             if (isAllIRKeyPressed(gIR_test)) {
303*4882a593Smuzhiyun                                 //int i =0;
304*4882a593Smuzhiyun                                 log_info(" ======== key test is over ========= \n");
305*4882a593Smuzhiyun                                 strcpy(result, RESULT_VERIFY);
306*4882a593Smuzhiyun                                 break;
307*4882a593Smuzhiyun                             }
308*4882a593Smuzhiyun                         }
309*4882a593Smuzhiyun                     }
310*4882a593Smuzhiyun                 }
311*4882a593Smuzhiyun             }
312*4882a593Smuzhiyun         } else if (ret == 0) {
313*4882a593Smuzhiyun             log_err("wait key event fail, errno=%d\n", errno);
314*4882a593Smuzhiyun 
315*4882a593Smuzhiyun             if (idx != IR_VALID_NUM) {
316*4882a593Smuzhiyun                 int i = 0;
317*4882a593Smuzhiyun 
318*4882a593Smuzhiyun                 for (i  = 0; i < IR_VALID_NUM; ++i)  {
319*4882a593Smuzhiyun                     if (gIR_test[i].key_press_flag == 0) {
320*4882a593Smuzhiyun                         strcat(buf, gIR_test[i].key_name);
321*4882a593Smuzhiyun                         strcat(buf, " ");
322*4882a593Smuzhiyun                     }
323*4882a593Smuzhiyun                 }
324*4882a593Smuzhiyun 
325*4882a593Smuzhiyun                 strcat(buf, " NOT PRESS!");
326*4882a593Smuzhiyun             }
327*4882a593Smuzhiyun 
328*4882a593Smuzhiyun             err_code = IR_EVENT_TIMEOUT;
329*4882a593Smuzhiyun             goto EXIT;
330*4882a593Smuzhiyun         }
331*4882a593Smuzhiyun     }
332*4882a593Smuzhiyun 
333*4882a593Smuzhiyun     //snprintf(buf, sizeof(buf), "key_code:%d", key_event.code);
334*4882a593Smuzhiyun     dumpKeyPressInfo(gIR_test);
335*4882a593Smuzhiyun EXIT:
336*4882a593Smuzhiyun     sleep(1);
337*4882a593Smuzhiyun     memset(buf, 0 , sizeof(buf));
338*4882a593Smuzhiyun 
339*4882a593Smuzhiyun     if (!err_code)
340*4882a593Smuzhiyun         strcpy(result, RESULT_VERIFY);
341*4882a593Smuzhiyun 
342*4882a593Smuzhiyun     send_msg_to_server(buf, result, err_code);
343*4882a593Smuzhiyun 
344*4882a593Smuzhiyun     return err_code;
345*4882a593Smuzhiyun }
346*4882a593Smuzhiyun 
347*4882a593Smuzhiyun 
348