Refactor to use new protocol module and sipo.
[bertos.git] / boards / triface / examples / triface / cmd.c
1 /**
2  * \file
3  * <!--
4  * This file is part of BeRTOS.
5  *
6  * Bertos is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
19  *
20  * As a special exception, you may use this file as part of a free software
21  * library without restriction.  Specifically, if other files instantiate
22  * templates or use macros or inline functions from this file, or you compile
23  * this file and link it with other files to produce an executable, this
24  * file does not by itself cause the resulting executable to be covered by
25  * the GNU General Public License.  This exception does not however
26  * invalidate any other reasons why the executable file might be covered by
27  * the GNU General Public License.
28  *
29  * Copyright 2003, 2004, 2006, 2012 Develer S.r.l. (http://www.develer.com/)
30  * Copyright 2000 Bernie Innocenti <bernie@codewiz.org>
31  *
32  * -->
33  *
34  * \brief Implementation of the command protocol between the board and the host
35  *
36  *
37  * \author Giovanni Bajo <rasky@develer.com>
38  * \author Marco Benelli <marco@develer.com>
39  * \author Bernie Innocenti <bernie@codewiz.org>
40  * \author Daniele Basile <asterix@develer.com>
41  */
42
43 #include "cmd.h"
44 #include "verstag.h"
45
46 #include "hw/hw_input.h"
47 #include "cfg/cfg_parser.h"
48 #include <cfg/compiler.h>
49 #include <cfg/debug.h>
50
51 #include <mware/parser.h>
52 #include <drv/adc.h>
53 #include <drv/timer.h>
54 #include <drv/ser.h>
55 #include <drv/sipo.h>
56 #include <drv/buzzer.h>
57
58 #include <avr/wdt.h>
59
60 // Define the format string for ADC
61 #define ADC_FORMAT_STR "dddd"
62 #define ADC_CHANNEL_NUM    4
63
64 static Sipo *local_sipo;
65 static uint8_t reg_status_dout;
66
67
68 MAKE_CMD(ver, "", "ddd",
69 ({
70         args[1].l = VERS_MAJOR;
71         args[2].l = VERS_MINOR;
72         args[3].l = VERS_REV;
73         0;
74 }), 0);
75
76 /* Sleep. Example of declaring function body directly in macro call.  */
77 MAKE_CMD(sleep, "d", "",
78 ({
79         timer_delay((mtime_t)args[1].l);
80         0;
81 }), 0)
82
83 /* Ping.  */
84 MAKE_CMD(ping, "", "",
85 ({
86         //Silence "args not used" warning.
87         (void)args;
88         0;
89 }), 0)
90
91 /* Dout  */
92 MAKE_CMD(dout, "d", "",
93 ({
94         kfile_putc((uint8_t)args[1].l, &local_sipo->fd);
95
96         //Store status of dout ports.
97         reg_status_dout = (uint8_t)args[1].l;
98         0;
99 }), 0)
100
101 /* rdout  read the status of out ports.*/
102 MAKE_CMD(rdout, "", "d",
103 ({
104         args[1].l = reg_status_dout;
105         0;
106 }), 0)
107
108
109 /* Reset */
110 MAKE_CMD(reset, "", "",
111 ({
112         //Silence "args not used" warning.
113         (void)args;
114         wdt_enable(WDTO_2S);
115
116         /*We want to have an infinite loop that lock access on watchdog timer.
117         This piece of code it's equivalent to a while(true), but we have done this because
118         gcc generate a warning message that suggest to use "noreturn" parameter in function reset.*/
119         ASSERT(args);
120         while(args);
121         0;
122
123 }), 0)
124
125 /* Din */
126 MAKE_CMD(din, "", "d",
127 ({
128         args[1].l = INPUT_GET();
129         0;
130 }), 0)
131
132
133 /* Ain */
134 MAKE_CMD(ain, "", ADC_FORMAT_STR,
135 ({
136         STATIC_ASSERT((sizeof(ADC_FORMAT_STR) - 1) == ADC_CHANNEL_NUM);
137         for(int i = 0; i < ADC_CHANNEL_NUM; i++)
138                 args[i+1].l = adc_read(i);
139
140         0;
141 }), 0)
142
143 /* Beep  */
144 MAKE_CMD(beep, "d", "",
145 ({
146         buz_beep(args[1].l);
147         0;
148 }), 0)
149
150 /* Register commands.  */
151 void cmd_register(void)
152 {
153         REGISTER_CMD(ver);
154         REGISTER_CMD(sleep);
155         REGISTER_CMD(ping);
156         REGISTER_CMD(dout);
157         REGISTER_CMD(rdout);
158         REGISTER_CMD(reset);
159         REGISTER_CMD(din);
160         REGISTER_CMD(ain);
161         REGISTER_CMD(beep);
162 }
163
164 void cmd_init(Sipo *sipo)
165 {
166         ASSERT(sipo);
167         local_sipo = sipo;
168         reg_status_dout = 0;
169 }