]> rtime.felk.cvut.cz Git - pes-rpp/rpp-lib.git/blobdiff - rpp/src/rpp/sci.c
Make the RPP layer thread safe
[pes-rpp/rpp-lib.git] / rpp / src / rpp / sci.c
index 96cec47c8ea6d62c4c9615989c72329dc0a0b9ee..f324c9ad8821f9ebc7b7df9476eb868e3a054816 100644 (file)
@@ -1,20 +1,12 @@
-/* Copyright (C) 2013 Czech Technical University in Prague
+/* Copyright (C) 2013, 2015 Czech Technical University in Prague
  *
  * Authors:
  *     - Carlos Jenkins <carlos@jenkins.co.cr>
  *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ * This document contains proprietary information belonging to Czech
+ * Technical University in Prague. Passing on and copying of this
+ * document, and communication of its contents is not permitted
+ * without prior written authorization.
  *
  * File : sci.c
  * Abstract:
 
 
 #include "rpp/rpp.h"
+#include <stdio.h>  // vsnprintf()
+#include <stdarg.h> // va_start, va_end
 
-#if rppCONFIG_INCLUDE_SCI == 1
-#include <stdio.h>
-
-#if rppCONFIG_DRV == 1
+#ifndef FREERTOS_POSIX
 #include "drv/drv.h"
 #endif
 
@@ -39,39 +30,199 @@ static boolean_t initialized = FALSE;
 
 int8_t rpp_sci_init()
 {
-    if(initialized) {
-        return FAILURE;
-    }
-    initialized = TRUE;
+       if (initialized)
+               return FAILURE;
+       initialized = TRUE;
+
+#ifndef FREERTOS_POSIX
+       drv_sci_init();
+       drv_sci_set_crlf_conv_en(TRUE);
+#endif
+       return SUCCESS;
+}
+
+
+boolean_t rpp_sci_setup(uint32_t baud)
+{
+       boolean_t known = FALSE;
+       // FIXME This is a standard list of baud rates. This should include only
+       // tested baud rates.
+       static const uint32_t baud_list[] = {110, 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 38400, 56000, 57600, 115200};
+
+       if (baud == 0)
+               baud = 9600;
+       uint32_t i;
+       for (i = 0; i < ARRAY_SIZE(baud_list); i++) {
+               if (baud == baud_list[i]) {
+                       known = TRUE;
+                       break;
+               }
+       }
+
+#ifndef FREERTOS_POSIX
+       drv_sci_set_baudrate(baud);
+#endif
+       return known;
+}
+
+
+#ifndef FREERTOS_POSIX
+uint16_t rpp_sci_available()
+{
+       uint16_t available = 0;
+
+       available = drv_sci_available();
+
+       return available;
+}
+
+
+int8_t rpp_sci_read(uint32_t amount, uint8_t *buffer)
+{
+       drv_sci_receive(amount, buffer, portMAX_DELAY);
+
+       return SUCCESS;
+}
+
+
+int8_t rpp_sci_read_nb(uint32_t amount, uint8_t *buffer)
+{
+       if (drv_sci_receive(amount, buffer, 0) != SUCCESS)
+               return FAILURE;
+
+       return SUCCESS;
+}
+
+
+int8_t rpp_sci_write(uint32_t amount, uint8_t *data)
+{
+       drv_sci_send(amount, data, portMAX_DELAY);
+
+       return SUCCESS;
+}
+
+
+int8_t rpp_sci_write_nb(uint32_t amount, uint8_t *data)
+{
+       if (drv_sci_send(amount, data, 0) != SUCCESS)
+               return FAILURE;
+
+       return SUCCESS;
+}
+
+
+int8_t rpp_sci_flush(boolean_t buff)
+{
+       return drv_sci_flush(buff);
+}
+
+int32_t rpp_sci_printk(const char *format, ...)
+{
+       char str[MAX_BUFFER_LEN];
+       int length = -1;
+       va_list argList;
+
+       va_start(argList, format);
+
+       length = vsnprintf(str, sizeof(str), format, argList);
+
+       va_end(argList);
+
+       if (length > 0) {
+               // According to the C stdlib about vsnprintf:
+               // If the resulting string would be longer than n-1 characters, the
+               // remaining characters are discarded and not stored, but counted
+               // for the value returned by the function.
+               // In consequence we need to trim the value if larger than buffer.
+               if (length > sizeof(str))
+                       length = sizeof(str);
+
+               drv_sci_send_imm((uint32_t)length, (uint8_t *)str);
+       }
+
+       return length;
+}
+
+int32_t rpp_sci_printkb(const char *format, ...)
+{
+       char str[MAX_BUFFER_LEN];
+       int length = -1;
+       va_list argList;
+
+       va_start(argList, format);
+
+       length = vsnprintf(str, sizeof(str), format, argList);
+
+       va_end(argList);
+
+       if (length > 0) {
+               // According to the C stdlib about vsnprintf:
+               // If the resulting string would be longer than n-1 characters, the
+               // remaining characters are discarded and not stored, but counted
+               // for the value returned by the function.
+               // In consequence we need to trim the value if larger than buffer.
+               if (length > sizeof(str))
+                       length = sizeof(str);
 
-    #if rppCONFIG_DRV == 1
-    drv_sci_init();
-    #endif
+               return drv_sci_send_try_append((uint32_t)length, (uint8_t *)str);
 
-   return SUCCESS;
+       }
+       return length;
 }
 
-int rpp_sci_printf(const char *format, ...)
+int32_t rpp_sci_printf(const char *format, ...)
 {
-    char str[128];
-    int length = -1;
+       int length = -1;
+       va_list argList;
 
-    va_list argList;
-    va_start(argList, format);
+       va_start(argList, format);
+       length = rpp_sci_vprintf(format, argList);
+       va_end(argList);
 
-    length = vsnprintf(str, sizeof(str), format, argList);
+       return length;
+}
+
+int32_t rpp_sci_vprintf(const char *format, va_list argList)
+{
+       char str[MAX_BUFFER_LEN];
+       int length = -1;
+
+       length = vsnprintf(str, sizeof(str), format, argList);
+
+       if (length > 0) {
+               // According to the C stdlib about vsnprintf:
+               // If the resulting string would be longer than n-1 characters, the
+               // remaining characters are discarded and not stored, but counted
+               // for the value returned by the function.
+               // In consequence we need to trim the value if larger than buffer.
+               if (length > sizeof(str))
+                       length = sizeof(str);
+               if (drv_sci_send(
+                               (uint32_t)length,
+                               (uint8_t *)str,
+                               portMAX_DELAY) != SUCCESS)
+                       return -1;
+       }
+
+       return length;
+}
 
-    va_end(argList);
 
-    if(length > 0) {
-        #if rppCONFIG_DRV == 1
-        drv_sci_send((unsigned)length, (unsigned char*)str);
-        #endif
-    }
+int8_t rpp_sci_putc(uint8_t byte)
+{
+       drv_sci_send(1, &byte, portMAX_DELAY);
 
-    return length;
+       return SUCCESS;
 }
 
 
-#endif /* rppCONFIG_INCLUDE_SCI */
+int16_t rpp_sci_getc()
+{
+       uint8_t result = 0;
+
+       if (drv_sci_receive(1, &result, portMAX_DELAY) == FAILURE)
+               return FAILURE;
 
+       return (int16_t)result;
+}
+#endif /* !FREERTOS_POSIX */