source: rtems-libbsd/testsuite/usbserial01/init.c @ 534017c

55-freebsd-126-freebsd-12
Last change on this file since 534017c was 534017c, checked in by Kevin Kirspel <kevin-kirspel@…>, on 05/12/17 at 12:16:25

Adding USB Serial test

  • Property mode set to 100644
File size: 8.9 KB
Line 
1/*-
2 * COPYRIGHT (c) 2017 Kevin Kirspel
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 *    notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 *    notice, this list of conditions and the following disclaimer in the
12 *    documentation and/or other materials provided with the distribution.
13 *
14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24 * SUCH DAMAGE.
25 */
26
27#include <sys/malloc.h>
28#include <assert.h>
29#include <stdio.h>
30#include <stdlib.h>
31#include <errno.h>
32#include <fcntl.h>
33
34#include <rtems/console.h>
35#include <rtems/shell.h>
36#include <rtems/bsd/bsd.h>
37
38#define TEST_NAME "LIBBSD USB SERIAL"
39
40#define USB_SERIAL_TEST_BUFFER_SIZE 48
41#define PRIO_OPEN  (RTEMS_MAXIMUM_PRIORITY - 12)
42#define PRIO_READ  (RTEMS_MAXIMUM_PRIORITY - 11)
43#define PRIO_WRITE (RTEMS_MAXIMUM_PRIORITY - 10)
44
45struct usb_test_message {
46        int fd;
47        char rbuf[USB_SERIAL_TEST_BUFFER_SIZE];
48        char wbuf[USB_SERIAL_TEST_BUFFER_SIZE];
49};
50
51static rtems_id oid, rid, wid, omid, rmid, wmid;
52static volatile bool kill_otask, kill_rtask, kill_wtask;
53static volatile bool otask_active, rtask_active, wtask_active;
54
55static void
56usb_serial_read_task(rtems_task_argument arg)
57{
58        struct usb_test_message msg;
59        uint32_t size, end_time;
60        int bytes, index;
61
62        rtask_active = true;
63        kill_rtask = false;
64        while (!kill_rtask) {
65                rtems_message_queue_receive(rmid, &msg, &size, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
66                index = 0;
67                msg.rbuf[0] = 0;
68                end_time = rtems_clock_get_ticks_since_boot() + RTEMS_MILLISECONDS_TO_TICKS(500);
69                while ((rtems_clock_get_ticks_since_boot() < end_time) && (index < sizeof(msg.rbuf))) {
70                        bytes = read(msg.fd, &msg.rbuf[index], sizeof(msg.rbuf) - index - 1);
71                        if (bytes < 0) {
72                                msg.fd = -1;
73                                rtems_message_queue_send(omid, &msg, sizeof(msg));
74                                printf("serial device read error: %d\n", errno);
75                        } else if (bytes > 0) {
76                                index += bytes;
77                                msg.rbuf[index] = 0;
78                                if (strcmp(msg.rbuf, msg.wbuf) == 0) {
79                                        break;
80                                }
81                        }
82                        rtems_task_wake_after(RTEMS_MILLISECONDS_TO_TICKS(10));
83                }
84                printf("serial device read: %s - %s\n", msg.rbuf, strcmp(msg.rbuf, msg.wbuf) == 0 ? "PASS" : "FAIL");
85        }
86        rtask_active = false;
87}
88
89static void
90usb_serial_write_task(rtems_task_argument arg)
91{
92        struct usb_test_message msg;
93        uint32_t size;
94        int bytes, write_len, count = 0;
95
96        wtask_active = true;
97        kill_wtask = false;
98        while (!kill_wtask) {
99                rtems_message_queue_receive(wmid, &msg, &size, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
100                count++;
101                sprintf(msg.wbuf, "Hello World %d", count);
102                write_len = strlen(msg.wbuf);
103                bytes = write(msg.fd, msg.wbuf, write_len);
104                if (bytes < 0) {
105                        msg.fd = -1;
106                        rtems_message_queue_send(omid, &msg, sizeof(msg));
107                        printf("serial device write error: %d\n", errno);
108                } else if (bytes != write_len) {
109                        printf("serial device failed to write all bytes: %d\n", bytes);
110                } else {
111                        printf("serial device write: %s\n", msg.wbuf);
112                        rtems_message_queue_send(rmid, &msg, sizeof(msg));
113                }
114        }
115        wtask_active = false;
116}
117
118static void
119usb_serial_open_task(rtems_task_argument arg)
120{
121        rtems_status_code sc;
122        struct usb_test_message msg;
123        struct termios t;
124        uint32_t size;
125        int fd, iret;
126
127        fd = -2;
128        otask_active = true;
129        kill_otask = false;
130        while (!kill_otask) {
131                sc = rtems_message_queue_receive(omid, &msg, &size, RTEMS_WAIT, RTEMS_MILLISECONDS_TO_TICKS(1000));
132                if (sc == RTEMS_SUCCESSFUL) {
133                        if (fd >= 0) {
134                                close(fd);
135                                printf("serial device closed\n");
136                        }
137                        fd = msg.fd;
138                }
139                if (fd == -1) {
140                        fd = open("/dev/ttyU0", LIBIO_FLAGS_READ_WRITE);
141                        if (fd != -1) {
142                                printf("serial device opened\n");
143                                //get terminal settings
144                                iret = tcgetattr (fd, &t);
145                                assert(iret != -1);
146                                //set timeouts to zero for non-blocking mode
147                                t.c_lflag &= ~(ECHO | ICANON | IEXTEN | ISIG);
148                                //t.c_iflag &= ~(BRKINT | ICRNL | INLCR | PARMRK | INPCK | ISTRIP);
149                                //t.c_iflag &= ~(BRKINT | ICRNL | INPCK | ISTRIP);
150                                t.c_iflag &= ~(BRKINT | ICRNL | INPCK | ISTRIP | IXON);
151                                t.c_iflag |= IXON;    // Enable XON/XOFF flow control on output.
152                                t.c_cflag &= ~(CSIZE | PARENB);
153                                t.c_oflag &= ~(OPOST);
154                                t.c_cflag |= (CS8 | CREAD);
155                                t.c_cc[VMIN] = 0;
156                                t.c_cc[VTIME] = 0;
157                                //save settings
158                                iret = tcsetattr (fd, TCSANOW, &t);
159                                assert(iret != -1);
160                                msg.fd = fd;
161                                rtems_message_queue_send(wmid, &msg, sizeof(msg));
162                        }
163                } else {
164                        msg.fd = fd;
165                        rtems_message_queue_send(wmid, &msg, sizeof(msg));
166                }
167        }
168        otask_active = false;
169}
170
171static void
172Init(rtems_task_argument arg)
173{
174        rtems_status_code sc;
175        struct usb_test_message msg;
176        int ii;
177
178        (void) arg;
179        puts("*** " TEST_NAME " TEST ***");
180
181        sc = rtems_message_queue_create(
182                rtems_build_name ('M', 'U', 'O', 'P'),
183                16,
184                sizeof(struct usb_test_message),
185                RTEMS_PRIORITY,
186                &omid
187        );
188        assert(sc == RTEMS_SUCCESSFUL);
189
190        sc = rtems_message_queue_create(
191                rtems_build_name ('M', 'U', 'R', 'D'),
192                16,
193                sizeof(struct usb_test_message),
194                RTEMS_PRIORITY,
195                &rmid
196        );
197        assert(sc == RTEMS_SUCCESSFUL);
198
199        sc = rtems_message_queue_create(
200                rtems_build_name ('M', 'U', 'W', 'R'),
201                16,
202                sizeof(struct usb_test_message),
203                RTEMS_PRIORITY,
204                &wmid
205        );
206        assert(sc == RTEMS_SUCCESSFUL);
207
208        sc = rtems_task_create(
209                rtems_build_name('U', 'S', 'B', 'R'),
210                PRIO_READ,
211                RTEMS_MINIMUM_STACK_SIZE,
212                RTEMS_DEFAULT_MODES,
213                RTEMS_FLOATING_POINT,
214                &rid
215        );
216        assert(sc == RTEMS_SUCCESSFUL);
217
218        sc = rtems_task_create(
219                rtems_build_name('U', 'S', 'B', 'W'),
220                PRIO_WRITE,
221                RTEMS_MINIMUM_STACK_SIZE,
222                RTEMS_DEFAULT_MODES,
223                RTEMS_FLOATING_POINT,
224                &wid
225        );
226        assert(sc == RTEMS_SUCCESSFUL);
227
228        sc = rtems_task_create(
229                rtems_build_name('U', 'S', 'B', 'O'),
230                PRIO_OPEN,
231                RTEMS_MINIMUM_STACK_SIZE,
232                RTEMS_DEFAULT_MODES,
233                RTEMS_FLOATING_POINT,
234                &oid
235        );
236        assert(sc == RTEMS_SUCCESSFUL);
237
238        sc = rtems_task_start(rid, usb_serial_read_task, NULL);
239        assert(sc == RTEMS_SUCCESSFUL);
240
241        sc = rtems_task_start(oid, usb_serial_open_task, NULL);
242        assert(sc == RTEMS_SUCCESSFUL);
243
244        sc = rtems_task_start(wid, usb_serial_write_task, NULL);
245        assert(sc == RTEMS_SUCCESSFUL);
246
247        sc = rtems_bsd_initialize();
248        assert(sc == RTEMS_SUCCESSFUL);
249
250        msg.fd = -1;
251        rtems_message_queue_send(omid, &msg, sizeof(msg));
252
253        sc = rtems_shell_init("SHLL", 16 * 1024, 1, CONSOLE_DEVICE_NAME,
254            false, true, NULL);
255        assert(sc == RTEMS_SUCCESSFUL);
256
257        kill_otask = true;
258        kill_rtask = true;
259        kill_wtask = true;
260        while (otask_active || rtask_active || wtask_active) {
261                rtems_task_wake_after(RTEMS_MILLISECONDS_TO_TICKS(10));
262        }
263
264        sc = rtems_message_queue_delete(wmid);
265        assert(sc == RTEMS_SUCCESSFUL);
266
267        sc = rtems_message_queue_delete(rmid);
268        assert(sc == RTEMS_SUCCESSFUL);
269
270        sc = rtems_message_queue_delete(omid);
271        assert(sc == RTEMS_SUCCESSFUL);
272
273        exit(0);
274}
275
276#define CONFIGURE_MICROSECONDS_PER_TICK 1000
277
278#define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
279#define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
280#define CONFIGURE_APPLICATION_NEEDS_STUB_DRIVER
281#define CONFIGURE_APPLICATION_NEEDS_ZERO_DRIVER
282#define CONFIGURE_APPLICATION_NEEDS_LIBBLOCK
283
284#define CONFIGURE_MAXIMUM_DRIVERS 32
285
286#define CONFIGURE_LIBIO_MAXIMUM_FILE_DESCRIPTORS 32
287
288#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
289
290#define CONFIGURE_UNLIMITED_OBJECTS
291#define CONFIGURE_UNIFIED_WORK_AREAS
292
293#define CONFIGURE_STACK_CHECKER_ENABLED
294
295#define CONFIGURE_RTEMS_INIT_TASKS_TABLE
296
297#define CONFIGURE_INIT_TASK_STACK_SIZE (32 * 1024)
298#define CONFIGURE_INIT_TASK_INITIAL_MODES RTEMS_DEFAULT_MODES
299#define CONFIGURE_INIT_TASK_ATTRIBUTES RTEMS_FLOATING_POINT
300
301#define CONFIGURE_INIT
302
303#include <rtems/confdefs.h>
304
305#include <bsp/nexus-devices.h>
306
307SYSINIT_DRIVER_REFERENCE(uplcom, uhub);
308
309#define CONFIGURE_SHELL_COMMANDS_INIT
310
311#include <bsp/irq-info.h>
312
313#include <rtems/netcmds-config.h>
314
315#define CONFIGURE_SHELL_USER_COMMANDS \
316        &bsp_interrupt_shell_command,       \
317        &rtems_shell_STTY_Command,          \
318        &rtems_shell_SYSCTL_Command
319
320#define CONFIGURE_SHELL_COMMAND_CPUUSE
321#define CONFIGURE_SHELL_COMMAND_PERIODUSE
322#define CONFIGURE_SHELL_COMMAND_STACKUSE
323#define CONFIGURE_SHELL_COMMAND_PROFREPORT
324
325#define CONFIGURE_SHELL_COMMAND_CP
326#define CONFIGURE_SHELL_COMMAND_PWD
327#define CONFIGURE_SHELL_COMMAND_LS
328#define CONFIGURE_SHELL_COMMAND_LN
329#define CONFIGURE_SHELL_COMMAND_LSOF
Note: See TracBrowser for help on using the repository browser.