1ac9f1b55SMasahiro Yamada /* 2ac9f1b55SMasahiro Yamada * Copyright (c) 2019, Socionext Inc. All rights reserved. 3ac9f1b55SMasahiro Yamada * 4ac9f1b55SMasahiro Yamada * SPDX-License-Identifier: BSD-3-Clause 5ac9f1b55SMasahiro Yamada */ 6ac9f1b55SMasahiro Yamada 7ac9f1b55SMasahiro Yamada #include <drivers/console.h> 8ac9f1b55SMasahiro Yamada #include <errno.h> 9ac9f1b55SMasahiro Yamada #include <lib/mmio.h> 10ac9f1b55SMasahiro Yamada #include <plat/common/platform.h> 11ac9f1b55SMasahiro Yamada 12ac9f1b55SMasahiro Yamada #include "uniphier.h" 13ac9f1b55SMasahiro Yamada #include "uniphier_console.h" 14ac9f1b55SMasahiro Yamada 15ac9f1b55SMasahiro Yamada #define UNIPHIER_UART_BASE 0x54006800 16ac9f1b55SMasahiro Yamada #define UNIPHIER_UART_END 0x54006c00 17ac9f1b55SMasahiro Yamada #define UNIPHIER_UART_OFFSET 0x100 18ac9f1b55SMasahiro Yamada 19ac9f1b55SMasahiro Yamada struct uniphier_console { 20ac9f1b55SMasahiro Yamada struct console console; 21ac9f1b55SMasahiro Yamada uintptr_t base; 22ac9f1b55SMasahiro Yamada }; 23ac9f1b55SMasahiro Yamada 24ac9f1b55SMasahiro Yamada /* These callbacks are implemented in assembly to use crash_console_helpers.S */ 25ac9f1b55SMasahiro Yamada int uniphier_console_putc(int character, struct console *console); 26ac9f1b55SMasahiro Yamada int uniphier_console_getc(struct console *console); 27ac9f1b55SMasahiro Yamada int uniphier_console_flush(struct console *console); 28ac9f1b55SMasahiro Yamada 29ac9f1b55SMasahiro Yamada static struct uniphier_console uniphier_console = { 30ac9f1b55SMasahiro Yamada .console = { 31ac9f1b55SMasahiro Yamada .flags = CONSOLE_FLAG_BOOT | 32ac9f1b55SMasahiro Yamada #if DEBUG 33ac9f1b55SMasahiro Yamada CONSOLE_FLAG_RUNTIME | 34ac9f1b55SMasahiro Yamada #endif 35*abfd5719SMasahiro Yamada CONSOLE_FLAG_CRASH | 36*abfd5719SMasahiro Yamada CONSOLE_FLAG_TRANSLATE_CRLF, 37ac9f1b55SMasahiro Yamada .putc = uniphier_console_putc, 38ac9f1b55SMasahiro Yamada .getc = uniphier_console_getc, 39ac9f1b55SMasahiro Yamada .flush = uniphier_console_flush, 40ac9f1b55SMasahiro Yamada }, 41ac9f1b55SMasahiro Yamada }; 42ac9f1b55SMasahiro Yamada 43ac9f1b55SMasahiro Yamada /* 44ac9f1b55SMasahiro Yamada * There are 4 UART ports available on this platform. By default, we want to 45ac9f1b55SMasahiro Yamada * use the same one as used in the previous firmware stage. 46ac9f1b55SMasahiro Yamada */ 47ac9f1b55SMasahiro Yamada static uintptr_t uniphier_console_get_base(void) 48ac9f1b55SMasahiro Yamada { 49ac9f1b55SMasahiro Yamada uintptr_t base = UNIPHIER_UART_BASE; 50ac9f1b55SMasahiro Yamada uint32_t div; 51ac9f1b55SMasahiro Yamada 52ac9f1b55SMasahiro Yamada while (base < UNIPHIER_UART_END) { 53ac9f1b55SMasahiro Yamada div = mmio_read_32(base + UNIPHIER_UART_DLR); 54ac9f1b55SMasahiro Yamada if (div) 55ac9f1b55SMasahiro Yamada return base; 56ac9f1b55SMasahiro Yamada base += UNIPHIER_UART_OFFSET; 57ac9f1b55SMasahiro Yamada } 58ac9f1b55SMasahiro Yamada 59ac9f1b55SMasahiro Yamada return 0; 60ac9f1b55SMasahiro Yamada } 61ac9f1b55SMasahiro Yamada 62ac9f1b55SMasahiro Yamada static void uniphier_console_init(uintptr_t base) 63ac9f1b55SMasahiro Yamada { 64ac9f1b55SMasahiro Yamada mmio_write_32(base + UNIPHIER_UART_FCR, UNIPHIER_UART_FCR_ENABLE_FIFO); 65ac9f1b55SMasahiro Yamada mmio_write_32(base + UNIPHIER_UART_LCR_MCR, 66ac9f1b55SMasahiro Yamada UNIPHIER_UART_LCR_WLEN8 << 8); 67ac9f1b55SMasahiro Yamada } 68ac9f1b55SMasahiro Yamada 69ac9f1b55SMasahiro Yamada void uniphier_console_setup(void) 70ac9f1b55SMasahiro Yamada { 71ac9f1b55SMasahiro Yamada uintptr_t base; 72ac9f1b55SMasahiro Yamada 73ac9f1b55SMasahiro Yamada base = uniphier_console_get_base(); 74ac9f1b55SMasahiro Yamada if (!base) 75ac9f1b55SMasahiro Yamada plat_error_handler(-EINVAL); 76ac9f1b55SMasahiro Yamada 77ac9f1b55SMasahiro Yamada uniphier_console.base = base; 78ac9f1b55SMasahiro Yamada console_register(&uniphier_console.console); 79ac9f1b55SMasahiro Yamada 80ac9f1b55SMasahiro Yamada /* 81ac9f1b55SMasahiro Yamada * The hardware might be still printing characters queued up in the 82ac9f1b55SMasahiro Yamada * previous firmware stage. Make sure the transmitter is empty before 83ac9f1b55SMasahiro Yamada * any initialization. Otherwise, the console might get corrupted. 84ac9f1b55SMasahiro Yamada */ 85ac9f1b55SMasahiro Yamada console_flush(); 86ac9f1b55SMasahiro Yamada 87ac9f1b55SMasahiro Yamada uniphier_console_init(base); 88ac9f1b55SMasahiro Yamada } 89