Merge git://git.denx.de/u-boot-sh
[oweals/u-boot.git] / common / console.c
index 7aa58d0a63674c21df6ad3ac89445599e498b512..1deca3cb78f81fabfdd541814775709c7ba49b07 100644 (file)
@@ -8,6 +8,7 @@
 #include <console.h>
 #include <debug_uart.h>
 #include <dm.h>
+#include <env.h>
 #include <stdarg.h>
 #include <iomux.h>
 #include <malloc.h>
@@ -16,8 +17,9 @@
 #include <serial.h>
 #include <stdio_dev.h>
 #include <exports.h>
-#include <environment.h>
+#include <env_internal.h>
 #include <watchdog.h>
+#include <linux/delay.h>
 
 DECLARE_GLOBAL_DATA_PTR;
 
@@ -251,10 +253,12 @@ static void console_puts(int file, const char *s)
        }
 }
 
+#if CONFIG_IS_ENABLED(SYS_CONSOLE_IS_IN_ENV)
 static inline void console_doenv(int file, struct stdio_dev *dev)
 {
        iomux_doenv(file, dev->name);
 }
+#endif
 #else
 static inline int console_getc(int file)
 {
@@ -282,10 +286,12 @@ static inline void console_puts(int file, const char *s)
        stdio_devices[file]->puts(stdio_devices[file], s);
 }
 
+#if CONFIG_IS_ENABLED(SYS_CONSOLE_IS_IN_ENV)
 static inline void console_doenv(int file, struct stdio_dev *dev)
 {
        console_setfile(file, dev);
 }
+#endif
 #endif /* CONIFIG_IS_ENABLED(CONSOLE_MUX) */
 
 /** U-Boot INITIAL CONSOLE-NOT COMPATIBLE FUNCTIONS *************************/
@@ -311,12 +317,12 @@ int serial_printf(const char *fmt, ...)
 int fgetc(int file)
 {
        if (file < MAX_FILES) {
-#if CONFIG_IS_ENABLED(CONSOLE_MUX)
                /*
                 * Effectively poll for input wherever it may be available.
                 */
                for (;;) {
                        WATCHDOG_RESET();
+#if CONFIG_IS_ENABLED(CONSOLE_MUX)
                        /*
                         * Upper layer may have already called tstc() so
                         * check for that first.
@@ -324,6 +330,10 @@ int fgetc(int file)
                        if (tstcdev != NULL)
                                return console_getc(file);
                        console_tstc(file);
+#else
+                       if (console_tstc(file))
+                               return console_getc(file);
+#endif
 #ifdef CONFIG_WATCHDOG
                        /*
                         * If the watchdog must be rate-limited then it should
@@ -332,9 +342,6 @@ int fgetc(int file)
                         udelay(1);
 #endif
                }
-#else
-               return console_getc(file);
-#endif
        }
 
        return -1;
@@ -395,7 +402,7 @@ int getc(void)
        if (gd->console_in.start) {
                int ch;
 
-               ch = membuff_getbyte(&gd->console_in);
+               ch = membuff_getbyte((struct membuff *)&gd->console_in);
                if (ch != -1)
                        return 1;
        }
@@ -420,7 +427,7 @@ int tstc(void)
                return 0;
 #ifdef CONFIG_CONSOLE_RECORD
        if (gd->console_in.start) {
-               if (membuff_peekbyte(&gd->console_in) != -1)
+               if (membuff_peekbyte((struct membuff *)&gd->console_in) != -1)
                        return 1;
        }
 #endif
@@ -462,6 +469,11 @@ static void print_pre_console_buffer(int flushpoint)
        char buf_out[CONFIG_PRE_CON_BUF_SZ + 1];
        char *buf_in;
 
+#ifdef CONFIG_SILENT_CONSOLE
+       if (gd->flags & GD_FLG_SILENT)
+               return;
+#endif
+
        buf_in = map_sysmem(CONFIG_PRE_CON_BUF_ADDR, CONFIG_PRE_CON_BUF_SZ);
        if (gd->precon_buf_idx > CONFIG_PRE_CON_BUF_SZ)
                in = gd->precon_buf_idx - CONFIG_PRE_CON_BUF_SZ;
@@ -507,11 +519,14 @@ void putc(const char c)
                return;
 #ifdef CONFIG_CONSOLE_RECORD
        if ((gd->flags & GD_FLG_RECORD) && gd->console_out.start)
-               membuff_putbyte(&gd->console_out, c);
+               membuff_putbyte((struct membuff *)&gd->console_out, c);
 #endif
 #ifdef CONFIG_SILENT_CONSOLE
-       if (gd->flags & GD_FLG_SILENT)
+       if (gd->flags & GD_FLG_SILENT) {
+               if (!(gd->flags & GD_FLG_DEVINIT))
+                       pre_console_putc(c);
                return;
+       }
 #endif
 
 #ifdef CONFIG_DISABLE_CONSOLE
@@ -534,6 +549,13 @@ void putc(const char c)
 
 void puts(const char *s)
 {
+#ifdef CONFIG_SANDBOX
+       /* sandbox can send characters to stdout before it has a console */
+       if (!gd || !(gd->flags & GD_FLG_SERIAL_READY)) {
+               os_puts(s);
+               return;
+       }
+#endif
 #ifdef CONFIG_DEBUG_UART
        if (!gd || !(gd->flags & GD_FLG_SERIAL_READY)) {
                while (*s) {
@@ -548,11 +570,14 @@ void puts(const char *s)
                return;
 #ifdef CONFIG_CONSOLE_RECORD
        if ((gd->flags & GD_FLG_RECORD) && gd->console_out.start)
-               membuff_put(&gd->console_out, s, strlen(s));
+               membuff_put((struct membuff *)&gd->console_out, s, strlen(s));
 #endif
 #ifdef CONFIG_SILENT_CONSOLE
-       if (gd->flags & GD_FLG_SILENT)
+       if (gd->flags & GD_FLG_SILENT) {
+               if (!(gd->flags & GD_FLG_DEVINIT))
+                       pre_console_puts(s);
                return;
+       }
 #endif
 
 #ifdef CONFIG_DISABLE_CONSOLE
@@ -578,18 +603,20 @@ int console_record_init(void)
 {
        int ret;
 
-       ret = membuff_new(&gd->console_out, CONFIG_CONSOLE_RECORD_OUT_SIZE);
+       ret = membuff_new((struct membuff *)&gd->console_out,
+                         CONFIG_CONSOLE_RECORD_OUT_SIZE);
        if (ret)
                return ret;
-       ret = membuff_new(&gd->console_in, CONFIG_CONSOLE_RECORD_IN_SIZE);
+       ret = membuff_new((struct membuff *)&gd->console_in,
+                         CONFIG_CONSOLE_RECORD_IN_SIZE);
 
        return ret;
 }
 
 void console_record_reset(void)
 {
-       membuff_purge(&gd->console_out);
-       membuff_purge(&gd->console_in);
+       membuff_purge((struct membuff *)&gd->console_out);
+       membuff_purge((struct membuff *)&gd->console_in);
 }
 
 void console_record_reset_enable(void)
@@ -597,6 +624,18 @@ void console_record_reset_enable(void)
        console_record_reset();
        gd->flags |= GD_FLG_RECORD;
 }
+
+int console_record_readline(char *str, int maxlen)
+{
+       return membuff_readline((struct membuff *)&gd->console_out, str,
+                               maxlen, ' ');
+}
+
+int console_record_avail(void)
+{
+       return membuff_avail((struct membuff *)&gd->console_out);
+}
+
 #endif
 
 /* test if ctrl-c was pressed */
@@ -712,14 +751,22 @@ int console_assign(int file, const char *devname)
        return -1;
 }
 
-static void console_update_silent(void)
+/* return true if the 'silent' flag is removed */
+static bool console_update_silent(void)
 {
 #ifdef CONFIG_SILENT_CONSOLE
-       if (env_get("silent") != NULL)
+       if (env_get("silent")) {
                gd->flags |= GD_FLG_SILENT;
-       else
+       } else {
+               unsigned long flags = gd->flags;
+
                gd->flags &= ~GD_FLG_SILENT;
+
+               return !!(flags & GD_FLG_SILENT);
+       }
 #endif
+
+       return false;
 }
 
 int console_announce_r(void)
@@ -784,6 +831,13 @@ int console_init_r(void)
 #if CONFIG_IS_ENABLED(CONSOLE_MUX)
        int iomux_err = 0;
 #endif
+       int flushpoint;
+
+       /* update silent for env loaded from flash (initr_env) */
+       if (console_update_silent())
+               flushpoint = PRE_CONSOLE_FLUSHPOINT1_SERIAL;
+       else
+               flushpoint = PRE_CONSOLE_FLUSHPOINT2_EVERYTHING_BUT_SERIAL;
 
        /* set default handlers at first */
        gd->jt->getc  = serial_getc;
@@ -861,7 +915,7 @@ done:
        if ((stdio_devices[stdin] == NULL) && (stdio_devices[stdout] == NULL))
                return 0;
 #endif
-       print_pre_console_buffer(PRE_CONSOLE_FLUSHPOINT2_EVERYTHING_BUT_SERIAL);
+       print_pre_console_buffer(flushpoint);
        return 0;
 }
 
@@ -875,8 +929,13 @@ int console_init_r(void)
        struct list_head *list = stdio_get_list();
        struct list_head *pos;
        struct stdio_dev *dev;
+       int flushpoint;
 
-       console_update_silent();
+       /* update silent for env loaded from flash (initr_env) */
+       if (console_update_silent())
+               flushpoint = PRE_CONSOLE_FLUSHPOINT1_SERIAL;
+       else
+               flushpoint = PRE_CONSOLE_FLUSHPOINT2_EVERYTHING_BUT_SERIAL;
 
 #ifdef CONFIG_SPLASH_SCREEN
        /*
@@ -939,7 +998,7 @@ int console_init_r(void)
        if ((stdio_devices[stdin] == NULL) && (stdio_devices[stdout] == NULL))
                return 0;
 #endif
-       print_pre_console_buffer(PRE_CONSOLE_FLUSHPOINT2_EVERYTHING_BUT_SERIAL);
+       print_pre_console_buffer(flushpoint);
        return 0;
 }