diff options
author | patacongo <patacongo@42af7a65-404d-4744-a932-0658087f49c3> | 2007-03-10 00:17:29 +0000 |
---|---|---|
committer | patacongo <patacongo@42af7a65-404d-4744-a932-0658087f49c3> | 2007-03-10 00:17:29 +0000 |
commit | af447e106c50246185a2b666900022043636d418 (patch) | |
tree | 3da31331ea2df513646279912b4e4b1b4d22fdb0 /nuttx/lib | |
parent | 713a462159cc5bb7e4574be4494d4e88024f010f (diff) | |
download | px4-nuttx-af447e106c50246185a2b666900022043636d418.tar.gz px4-nuttx-af447e106c50246185a2b666900022043636d418.tar.bz2 px4-nuttx-af447e106c50246185a2b666900022043636d418.zip |
Fix IRQ-related bugs, fix serial read logic, add fgets
git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@51 42af7a65-404d-4744-a932-0658087f49c3
Diffstat (limited to 'nuttx/lib')
-rw-r--r-- | nuttx/lib/Makefile | 4 | ||||
-rw-r--r-- | nuttx/lib/lib_fgets.c | 306 |
2 files changed, 308 insertions, 2 deletions
diff --git a/nuttx/lib/Makefile b/nuttx/lib/Makefile index 2189db7a5..cb77499c8 100644 --- a/nuttx/lib/Makefile +++ b/nuttx/lib/Makefile @@ -46,8 +46,8 @@ STRING_SRCS = lib_memset.c lib_memcpy.c lib_memcmp.c lib_memmove.c \ lib_strlen.c lib_strdup.c lib_strtol.c lib_strchr.c CTYPE_SRCS = STDIO_SRCS = lib_fopen.c lib_fclose.c \ - lib_fread.c lib_libfread.c lib_fgetc.c\ - lib_fwrite.c lib_libfwrite.c lib_fflush.c\ + lib_fread.c lib_libfread.c lib_fgetc.c lib_fgets.c \ + lib_fwrite.c lib_libfwrite.c lib_fflush.c \ lib_fputc.c lib_puts.c lib_fputs.c \ lib_ungetc.c \ lib_printf.c lib_vprintf.c lib_fprintf.c lib_rawprintf.c lib_lowprintf.c \ diff --git a/nuttx/lib/lib_fgets.c b/nuttx/lib/lib_fgets.c new file mode 100644 index 000000000..df18c239a --- /dev/null +++ b/nuttx/lib/lib_fgets.c @@ -0,0 +1,306 @@ +/************************************************************ + * lib_fgets.c + * + * Copyright (C) 2007 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <spudmonkey@racsa.co.cr> + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name Gregory Nutt nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ************************************************************/ + +/************************************************************ + * Compilation Switches + ************************************************************/ + +/************************************************************ + * Included Files + ************************************************************/ + +#include <stdio.h> +#include <string.h> +#include <ctype.h> +#include <debug.h> + +/************************************************************ + * Definitions + ************************************************************/ + +/************************************************************ + * Private Type Declarations + ************************************************************/ + +/************************************************************ + * Private Function Prototypes + ************************************************************/ + +/************************************************************ + * Global Function Prototypes + ************************************************************/ + +/************************************************************ + * Global Constant Data + ************************************************************/ + +/************************************************************ + * Global Variables + ************************************************************/ + +/************************************************************ + * Private Constant Data + ************************************************************/ + +/************************************************************ + * Private Variables + ************************************************************/ + +/************************************************************ + * Private Functions + ************************************************************/ + +/************************************************************ + * Name: _lib_rawgetc + ************************************************************/ + +static inline int _lib_rawgetc(int fd) +{ + char buffer; + (void)read(fd, &buffer, 1); + return buffer; +} + +/************************************************************ + * Name: _lib_consoleputc + ************************************************************/ + +static inline void _lib_consoleputc(int ch) +{ + char buffer = ch; + (void)write(1, &buffer, 1); +} + +/************************************************************ + * Name: _lib_consoleputs + ************************************************************/ + +static inline void _lib_consoleputs(char *s) +{ + (void)write(1, s, strlen(s)); +} + +/************************************************************ + * Global Functions + ************************************************************/ + +/************************************************************ + * Name: fgets + * + * Description: + * fgets() reads in at most one less than 'n' characters + * from stream and stores them into the buffer pointed to + * by 's'. Reading stops after an EOF or a newline. If a + * newline is read, it is stored into the buffer. A null + * terminator is stored after the last character in the + * buffer. + * + * Assumptions: + * If the stream corresponds to stdin (fd=0) this version + * will assume that we are reading characters from a + * VT100 console and that stdout (fd=1) is also available. + * This will not work well if fd=0 corresponds to a raw + * byte steam. + * + **********************************************************/ + +char *fgets(FAR char *s, int n, FILE *stream) +{ + int escape = 0; + boolean console; + int nch = 0; + + /* Sanity checks */ + + if (!stream || !s || n < 1 || stream->fs_filedes < 0) + { + return NULL; + } + + if (n < 2) + { + *s = '\0'; + return s; + } + + /* Check if the stream is stdin */ + + console = (stream->fs_filedes == 0); + + /* <esc>[K is the VT100 command that erases to the end of the line. */ + + if (console) + { + _lib_consoleputs("\033[K"); + } + + /* Read characters until we have a full line. On each + * the loop we must be assured that there are two free bytes + * in the line buffer: One for the next character and one for + * the null terminator. + */ + + for(;;) + { + /* Get the next character */ + + int ch = _lib_rawgetc(stream->fs_filedes); + + /* Are we processing a VT100 escape sequence */ + + if (escape) + { + /* Yes, is it an <esc>[, 3 byte sequence */ + + if (ch != 0x5b || escape == 2) + { + /* We are finished with the escape sequence */ + + escape = 0; + ch = 'a'; + } + else + { + /* The next character is the end of a 3-byte sequence. + * NOTE: Some of the <esc>[ sequences are longer than + * 3-bytes, but I have not encountered any in normal use + * yet and, so, have not provided the decoding logic. + */ + + escape = 2; + } + } + + /* Check for backspace */ + + else if (ch == 0x08) + { + /* Eliminate that last character in the buffer. */ + + if (nch > 0) + { + nch--; + + if (console) + { + /* Echo the backspace character on the console */ + + _lib_consoleputc(ch); + } + } + } + + /* Check for the beginning of a VT100 escape sequence */ + + else if (console && ch == 0x1b) + { + /* The next character is escaped */ + + escape = 1; + } + + /* Check for end-of-line or end-of-file */ + + else if (ch == 0x0d) + { + /* The newline is stored in the buffer along + * with the null terminator. + */ + + s[nch++] = '\n'; + s[nch] = '\0'; + + if (console) + { + /* Echo the newline to the console */ + + _lib_consoleputc('\n'); + } + + return s; + } + + /* Check for end-of-line or end-of-file */ + + else if (ch == EOF) + { + /* Terminate the line */ + + s[nch] = '\0'; + return s; + } + + /* Otherwise, check if the character is printable and, + * if so, put the character in the line buffer + */ + + else if (isprint(ch)) + { + s[nch++] = ch; + + if (console) + { + /* Echo the character to the console */ + + _lib_consoleputc(ch); + } + + /* Check if there is room for another character + * and the line's null terminator. If not then + * we have to end the line now. + */ + + if (nch + 1 >= n) + { + s[nch] = '\0'; + return s; + } + } + } + +} + +/************************************************************ + * Name: gets + * + * Description: + * gets() reads a line from stdin into the buffer pointed + * to by s until either a terminating newline or EOF, + * which it replaces with '\0'. No check for buffer + * overrun is performed + * + **********************************************************/ + +/* gets() is not supported because it is inherently un-safe */ |