UAVX Multicopter Flight Controller.

Dependencies:   mbed

Committer:
gke
Date:
Fri Feb 18 22:28:05 2011 +0000
Revision:
0:62a1c91a859a
Child:
2:90292f8bd179
First release

Who changed what in which revision?

UserRevisionLine numberNew contents of line
gke 0:62a1c91a859a 1 /*
gke 0:62a1c91a859a 2 Copyright (c) 2010 Andy Kirkham
gke 0:62a1c91a859a 3
gke 0:62a1c91a859a 4 Permission is hereby granted, free of charge, to any person obtaining a copy
gke 0:62a1c91a859a 5 of this software and associated documentation files (the "Software"), to deal
gke 0:62a1c91a859a 6 in the Software without restriction, including without limitation the rights
gke 0:62a1c91a859a 7 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
gke 0:62a1c91a859a 8 copies of the Software, and to permit persons to whom the Software is
gke 0:62a1c91a859a 9 furnished to do so, subject to the following conditions:
gke 0:62a1c91a859a 10
gke 0:62a1c91a859a 11 The above copyright notice and this permission notice shall be included in
gke 0:62a1c91a859a 12 all copies or substantial portions of the Software.
gke 0:62a1c91a859a 13
gke 0:62a1c91a859a 14 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
gke 0:62a1c91a859a 15 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
gke 0:62a1c91a859a 16 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
gke 0:62a1c91a859a 17 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
gke 0:62a1c91a859a 18 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
gke 0:62a1c91a859a 19 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
gke 0:62a1c91a859a 20 THE SOFTWARE.
gke 0:62a1c91a859a 21 */
gke 0:62a1c91a859a 22
gke 0:62a1c91a859a 23 #ifndef SERIALBUFFERED_H
gke 0:62a1c91a859a 24 #define SERIALBUFFERED_H
gke 0:62a1c91a859a 25
gke 0:62a1c91a859a 26 #include "mbed.h"
gke 0:62a1c91a859a 27
gke 0:62a1c91a859a 28
gke 0:62a1c91a859a 29
gke 0:62a1c91a859a 30 /** SerialBuffered based on Serial but fully buffered IO
gke 0:62a1c91a859a 31 *
gke 0:62a1c91a859a 32 * Example:
gke 0:62a1c91a859a 33 * @code
gke 0:62a1c91a859a 34 * #include "mbed.h"
gke 0:62a1c91a859a 35 * #include "SerialBuffered.h"
gke 0:62a1c91a859a 36 *
gke 0:62a1c91a859a 37 * SerialBuffered serial1 (p13, p14);
gke 0:62a1c91a859a 38 * SerialBuffered serial2 (p28, p27);
gke 0:62a1c91a859a 39 *
gke 0:62a1c91a859a 40 * int main() {
gke 0:62a1c91a859a 41 * while(1) {
gke 0:62a1c91a859a 42 * if (serial1.readable()) {
gke 0:62a1c91a859a 43 * while (!serial2.writeable());
gke 0:62a1c91a859a 44 * serial2.putc(serial1.getch());
gke 0:62a1c91a859a 45 * }
gke 0:62a1c91a859a 46 * if (serial2.readable()) {
gke 0:62a1c91a859a 47 * while (!serial1.writeable());
gke 0:62a1c91a859a 48 * serial1.putc(serial2.getc());
gke 0:62a1c91a859a 49 * }
gke 0:62a1c91a859a 50 * }
gke 0:62a1c91a859a 51 * }
gke 0:62a1c91a859a 52 * @endcode
gke 0:62a1c91a859a 53 *
gke 0:62a1c91a859a 54 * <b>Note</b>, because this system "traps" the interrupts for the UART
gke 0:62a1c91a859a 55 * being used <b>do not</b> use the .attach() method, otherwise the buffers
gke 0:62a1c91a859a 56 * will cease functioning. Or worse, behaviour becomes unpredictable.
gke 0:62a1c91a859a 57 */
gke 0:62a1c91a859a 58
gke 0:62a1c91a859a 59 class SerialBuffered : public Serial {
gke 0:62a1c91a859a 60
gke 0:62a1c91a859a 61 public:
gke 0:62a1c91a859a 62 enum { None = 0, One = 1, Two = 2 };
gke 0:62a1c91a859a 63 enum { WordLength5 = 0, WordLength6 = 1, WordLength7 = 2, WordLength8 = 3 };
gke 0:62a1c91a859a 64 enum { NoParity = 0, OddParity = (1UL << 3), EvenParity = (3UL << 3), Forced1 = (5UL << 3), Forced0 = (7UL << 3) };
gke 0:62a1c91a859a 65 enum { StopBit1 = (0UL << 2), StopBit2 = (1UL << 2) };
gke 0:62a1c91a859a 66
gke 0:62a1c91a859a 67 /** Create a SerialBuffered object connected to the specified pins
gke 0:62a1c91a859a 68 *
gke 0:62a1c91a859a 69 * @param PinName tx The Mbed TX pin for the uart port.
gke 0:62a1c91a859a 70 * @param PinName rx The Mbed RX pin for the uart port.
gke 0:62a1c91a859a 71 */
gke 0:62a1c91a859a 72 SerialBuffered(PinName tx, PinName rx);
gke 0:62a1c91a859a 73
gke 0:62a1c91a859a 74 virtual ~SerialBuffered();
gke 0:62a1c91a859a 75
gke 0:62a1c91a859a 76 /** Get a character from the serial stream.
gke 0:62a1c91a859a 77 *
gke 0:62a1c91a859a 78 * @return char A char value of the character read.
gke 0:62a1c91a859a 79 */
gke 0:62a1c91a859a 80 char getc(void);
gke 0:62a1c91a859a 81
gke 0:62a1c91a859a 82 /** Gets a character from the serial stream with optional blocking.
gke 0:62a1c91a859a 83 *
gke 0:62a1c91a859a 84 * This method allows for getting a character from the serial stream
gke 0:62a1c91a859a 85 * if one is available. If <b>blocking</b> is true, the method will
gke 0:62a1c91a859a 86 * wait for serial input if the RX buffer is empty. If <b>blocking</b>
gke 0:62a1c91a859a 87 * is false, the method will return immediately if the RX buffer is empty.
gke 0:62a1c91a859a 88 * On return, if not blocking and the buffer was empty, -1 is returned.
gke 0:62a1c91a859a 89 *
gke 0:62a1c91a859a 90 * @param blocking true or false, when true will block.
gke 0:62a1c91a859a 91 * @return int An int representation of the 8bit char or -1 on buffer empty.
gke 0:62a1c91a859a 92 */
gke 0:62a1c91a859a 93 int getc(bool blocking);
gke 0:62a1c91a859a 94
gke 0:62a1c91a859a 95 /** Puts a characher to the serial stream.
gke 0:62a1c91a859a 96 *
gke 0:62a1c91a859a 97 * This sends a character out of the uart port or, if no room in the
gke 0:62a1c91a859a 98 * TX FIFO, will place the character into the TX buffer. <b>Note</b>, if the
gke 0:62a1c91a859a 99 * TX buffer is also full, this method will <b>block</b> (wait) until
gke 0:62a1c91a859a 100 * there is room in the buffer.
gke 0:62a1c91a859a 101 *
gke 0:62a1c91a859a 102 * @param int An int representation of the 8bit character to send.
gke 0:62a1c91a859a 103 * @return int Always returns zero.
gke 0:62a1c91a859a 104 */
gke 0:62a1c91a859a 105 int putc(int c);
gke 0:62a1c91a859a 106
gke 0:62a1c91a859a 107 /** Puts a characher to the serial stream.
gke 0:62a1c91a859a 108 *
gke 0:62a1c91a859a 109 * As with putc(int c) this function allows for a character to be sent
gke 0:62a1c91a859a 110 * to the uart TX port. However, an extra parameter is added to allow
gke 0:62a1c91a859a 111 * the caller to decide if the method should block or not. If blocking
gke 0:62a1c91a859a 112 * is disabled then this method returns -1 to signal there was no room
gke 0:62a1c91a859a 113 * in the TX FIFO or the TX buffer. The character c passed is has not
gke 0:62a1c91a859a 114 * therefore been sent.
gke 0:62a1c91a859a 115 *
gke 0:62a1c91a859a 116 * @param int An int representation of the 8bit character to send.
gke 0:62a1c91a859a 117 * @param bool true if blocking required, false to disable blocking.
gke 0:62a1c91a859a 118 * @return int Zero on success, -1 if no room in TX FIFO or TX buffer.
gke 0:62a1c91a859a 119 */
gke 0:62a1c91a859a 120 int putc(int c, bool blocking);
gke 0:62a1c91a859a 121
gke 0:62a1c91a859a 122 /** Are there characters in the RX buffer we can read?
gke 0:62a1c91a859a 123 *
gke 0:62a1c91a859a 124 * @return int 1 if characters are available, 0 otherwise.
gke 0:62a1c91a859a 125 */
gke 0:62a1c91a859a 126 int readable(void);
gke 0:62a1c91a859a 127
gke 0:62a1c91a859a 128 /** Is there room in the TX buffer to send a character?
gke 0:62a1c91a859a 129 *
gke 0:62a1c91a859a 130 * @return int 1 if room available, 0 otherwise.
gke 0:62a1c91a859a 131 */
gke 0:62a1c91a859a 132 int writeable(void);
gke 0:62a1c91a859a 133
gke 0:62a1c91a859a 134 /** Set's the UART baud rate.
gke 0:62a1c91a859a 135 *
gke 0:62a1c91a859a 136 * Any allowed baudrate may be passed. However, you should
gke 0:62a1c91a859a 137 * ensure it matches the far end of the serial link.
gke 0:62a1c91a859a 138 *
gke 0:62a1c91a859a 139 * @param int The baudrate to set.
gke 0:62a1c91a859a 140 */
gke 0:62a1c91a859a 141 void baud(int baudrate);
gke 0:62a1c91a859a 142
gke 0:62a1c91a859a 143 /** Sets the serial format.
gke 0:62a1c91a859a 144 *
gke 0:62a1c91a859a 145 * Valid serial bit lengths are:-
gke 0:62a1c91a859a 146 * <ul>
gke 0:62a1c91a859a 147 * <li>SerialBuffered::WordLength5</li>
gke 0:62a1c91a859a 148 * <li>SerialBuffered::WordLength6</li>
gke 0:62a1c91a859a 149 * <li>SerialBuffered::WordLength7</li>
gke 0:62a1c91a859a 150 * <li>SerialBuffered::WordLength8</li>
gke 0:62a1c91a859a 151 * </ul>
gke 0:62a1c91a859a 152 *
gke 0:62a1c91a859a 153 * Valid serial parity are:-
gke 0:62a1c91a859a 154 * <ul>
gke 0:62a1c91a859a 155 * <li>SerialBuffered::NoParity</li>
gke 0:62a1c91a859a 156 * <li>SerialBuffered::OddParity</li>
gke 0:62a1c91a859a 157 * <li>SerialBuffered::EvenParity</li>
gke 0:62a1c91a859a 158 * <li>SerialBuffered::Forced1</li>
gke 0:62a1c91a859a 159 * <li>SerialBuffered::Forced0</li>
gke 0:62a1c91a859a 160 * </ul>
gke 0:62a1c91a859a 161 *
gke 0:62a1c91a859a 162 * Valid stop bits are:-
gke 0:62a1c91a859a 163 * <ul>
gke 0:62a1c91a859a 164 * <li>SerialBuffered::None</li>
gke 0:62a1c91a859a 165 * <li>SerialBuffered::One</li>
gke 0:62a1c91a859a 166 * <li>SerialBuffered::Two</li>
gke 0:62a1c91a859a 167 * </ul>
gke 0:62a1c91a859a 168 *
gke 0:62a1c91a859a 169 * @param int bits
gke 0:62a1c91a859a 170 * @param int parity
gke 0:62a1c91a859a 171 * @param int stopbits
gke 0:62a1c91a859a 172 */
gke 0:62a1c91a859a 173 void format(int bits, int parity, int stopbits);
gke 0:62a1c91a859a 174
gke 0:62a1c91a859a 175 /** Change the TX buffer size
gke 0:62a1c91a859a 176 *
gke 0:62a1c91a859a 177 * By default, when the SerialBuffer object is created, a default
gke 0:62a1c91a859a 178 * TX buffer of 256 bytes in size is created. If you need a bigger
gke 0:62a1c91a859a 179 * (or smaller) buffer then use this function to change the TX buffer
gke 0:62a1c91a859a 180 * size.
gke 0:62a1c91a859a 181 *
gke 0:62a1c91a859a 182 * <b>Note</b>, when a buffer is resized, any previous buffer
gke 0:62a1c91a859a 183 * in operation is discarded (destroyed and lost).
gke 0:62a1c91a859a 184 *
gke 0:62a1c91a859a 185 * @param int The size of the TX buffer required.
gke 0:62a1c91a859a 186 */
gke 0:62a1c91a859a 187 void set_tx_buffer_size(int buffer_size);
gke 0:62a1c91a859a 188
gke 0:62a1c91a859a 189 /** Change the TX buffer size and provide your own allocation.
gke 0:62a1c91a859a 190 *
gke 0:62a1c91a859a 191 * This methos allows for the buffer size to be changed and for the
gke 0:62a1c91a859a 192 * caller to pass a pointer to an area of RAM they have already set
gke 0:62a1c91a859a 193 * aside to hold the buffer. The standard method is to malloc space
gke 0:62a1c91a859a 194 * from the heap. This method allows that to be overriden and use a
gke 0:62a1c91a859a 195 * user supplied buffer.
gke 0:62a1c91a859a 196 *
gke 0:62a1c91a859a 197 * <b>Note</b>, the buffer you create must be of the size you specify!
gke 0:62a1c91a859a 198 * <b>Note</b>, when a buffer is resized, any previous buffer
gke 0:62a1c91a859a 199 * in operation is discarded (destroyed and lost).
gke 0:62a1c91a859a 200 *
gke 0:62a1c91a859a 201 * @param int The size of the TX buffer required.
gke 0:62a1c91a859a 202 * @param char* A pointer to a buffer area you previously allocated.
gke 0:62a1c91a859a 203 */
gke 0:62a1c91a859a 204 void set_tx_buffer_size(int buffer_size, char *buffer);
gke 0:62a1c91a859a 205
gke 0:62a1c91a859a 206 /** Change the RX buffer size
gke 0:62a1c91a859a 207 *
gke 0:62a1c91a859a 208 * By default, when the SerialBuffer object is created, a default
gke 0:62a1c91a859a 209 * RX buffer of 256 bytes in size is created. If you need a bigger
gke 0:62a1c91a859a 210 * (or smaller) buffer then use this function to change the RX buffer
gke 0:62a1c91a859a 211 * size.
gke 0:62a1c91a859a 212 *
gke 0:62a1c91a859a 213 * <b>Note</b>, when a buffer is resized, any previous buffer
gke 0:62a1c91a859a 214 * in operation is discarded (destroyed and lost).
gke 0:62a1c91a859a 215 *
gke 0:62a1c91a859a 216 * @param int The size of the RX buffer required.
gke 0:62a1c91a859a 217 */
gke 0:62a1c91a859a 218 void set_rx_buffer_size(int buffer_size);
gke 0:62a1c91a859a 219
gke 0:62a1c91a859a 220 /** Change the RX buffer size and provide your own allocation.
gke 0:62a1c91a859a 221 *
gke 0:62a1c91a859a 222 * This methos allows for the buffer size to be changed and for the
gke 0:62a1c91a859a 223 * caller to pass a pointer to an area of RAM they have already set
gke 0:62a1c91a859a 224 * aside to hold the buffer. The standard method is to malloc space
gke 0:62a1c91a859a 225 * from the heap. This method allows that to be overriden and use a
gke 0:62a1c91a859a 226 * user supplied buffer.
gke 0:62a1c91a859a 227 *
gke 0:62a1c91a859a 228 * <b>Note</b>, the buffer you create must be of the size you specify!
gke 0:62a1c91a859a 229 * <b>Note</b>, when a buffer is resized, any previous buffer
gke 0:62a1c91a859a 230 * in operation is discarded (destroyed and lost).
gke 0:62a1c91a859a 231 *
gke 0:62a1c91a859a 232 * @param int The size of the RX buffer required.
gke 0:62a1c91a859a 233 * @param char* A pointer to a buffer area you previously allocated.
gke 0:62a1c91a859a 234 */
gke 0:62a1c91a859a 235 void set_rx_buffer_size(int buffer_size, char *buffer);
gke 0:62a1c91a859a 236
gke 0:62a1c91a859a 237 protected:
gke 0:62a1c91a859a 238 /** Calculate the divisors for a UART's baud
gke 0:62a1c91a859a 239 *
gke 0:62a1c91a859a 240 * @param int The desired baud rate
gke 0:62a1c91a859a 241 * @param int The UART in use to calculate for
gke 0:62a1c91a859a 242 */
gke 0:62a1c91a859a 243 uint16_t calculate_baud(int baud, int uart);
gke 0:62a1c91a859a 244
gke 0:62a1c91a859a 245 private:
gke 0:62a1c91a859a 246 /** set_uart0
gke 0:62a1c91a859a 247 *
gke 0:62a1c91a859a 248 * Sets up the hardware and interrupts for the UART.
gke 0:62a1c91a859a 249 *
gke 0:62a1c91a859a 250 * @param PinName tx
gke 0:62a1c91a859a 251 * @param PinName rx
gke 0:62a1c91a859a 252 */
gke 0:62a1c91a859a 253 void set_uart0(PinName tx, PinName rx);
gke 0:62a1c91a859a 254
gke 0:62a1c91a859a 255 /** set_uart1
gke 0:62a1c91a859a 256 *
gke 0:62a1c91a859a 257 * Sets up the hardware and interrupts for the UART.
gke 0:62a1c91a859a 258 *
gke 0:62a1c91a859a 259 * @param PinName tx
gke 0:62a1c91a859a 260 * @param PinName rx
gke 0:62a1c91a859a 261 */
gke 0:62a1c91a859a 262 void set_uart1(PinName tx, PinName rx);
gke 0:62a1c91a859a 263
gke 0:62a1c91a859a 264 /** set_uart2
gke 0:62a1c91a859a 265 *
gke 0:62a1c91a859a 266 * Sets up the hardware and interrupts for the UART.
gke 0:62a1c91a859a 267 *
gke 0:62a1c91a859a 268 * @param PinName tx
gke 0:62a1c91a859a 269 * @param PinName rx
gke 0:62a1c91a859a 270 */
gke 0:62a1c91a859a 271 void set_uart2(PinName tx, PinName rx);
gke 0:62a1c91a859a 272
gke 0:62a1c91a859a 273 /** set_uart3
gke 0:62a1c91a859a 274 *
gke 0:62a1c91a859a 275 * Sets up the hardware and interrupts for the UART.
gke 0:62a1c91a859a 276 *
gke 0:62a1c91a859a 277 * @param PinName tx
gke 0:62a1c91a859a 278 * @param PinName rx
gke 0:62a1c91a859a 279 */
gke 0:62a1c91a859a 280 void set_uart3(PinName tx, PinName rx);
gke 0:62a1c91a859a 281
gke 0:62a1c91a859a 282 /** Reset the TX Buffer
gke 0:62a1c91a859a 283 *
gke 0:62a1c91a859a 284 * @param int The UART buffer to reset.
gke 0:62a1c91a859a 285 */
gke 0:62a1c91a859a 286 void reset_uart_tx(int uart_number);
gke 0:62a1c91a859a 287
gke 0:62a1c91a859a 288 /** Reset the RX Buffer
gke 0:62a1c91a859a 289 *
gke 0:62a1c91a859a 290 * @param int The UART buffer to reset.
gke 0:62a1c91a859a 291 */
gke 0:62a1c91a859a 292 void reset_uart_rx(int uart_number);
gke 0:62a1c91a859a 293
gke 0:62a1c91a859a 294 /** LPC1768 UART peripheral base address for UART in use.
gke 0:62a1c91a859a 295 */
gke 0:62a1c91a859a 296 unsigned long uart_base;
gke 0:62a1c91a859a 297
gke 0:62a1c91a859a 298 /** LPC1768 UART number for UART in use.
gke 0:62a1c91a859a 299 */
gke 0:62a1c91a859a 300 int uart_number;
gke 0:62a1c91a859a 301 };
gke 0:62a1c91a859a 302
gke 0:62a1c91a859a 303 #endif