aboutsummaryrefslogtreecommitdiff
path: root/src/soc/nvidia/tegra124/bootblock.c
diff options
context:
space:
mode:
authorGabe Black <gabeblack@google.com>2013-09-29 07:06:08 -0700
committerMarc Jones <marc.jones@se-eng.com>2014-08-29 06:47:24 +0200
commitca436cb247a78b234feb7975575883bdcbabc348 (patch)
treea62a50d28a7ca57c0b3bbe0e61ba06a7ca48c29d /src/soc/nvidia/tegra124/bootblock.c
parentd81f409514b99189c943d06fa9a8fa01d8178fc8 (diff)
tegra124: add custom uart
tegra124: Add a test function which spams exclamation points on the UART. This function spews characters on the console and, until we have a working console, is an easy way to see whether the system boots to a particular point. For some reason waiting for transmitter to be empty hangs, but transmitting characters still works. Old-Change-Id: I1622c8a58849f4b8bdcaa67500b81042d7346df4 Signed-off-by: Gabe Black <gabeblack@google.com> Reviewed-on: https://chromium-review.googlesource.com/171030 Reviewed-by: Ronald Minnich <rminnich@chromium.org> Commit-Queue: Gabe Black <gabeblack@chromium.org> Tested-by: Gabe Black <gabeblack@chromium.org> (cherry picked from commit e0059181958cfe8afec2f3a7ea732e81f5d55e5d) tegra124: Re-enable waiting for the transmitter to empty in the test function. The compiler was emitting code compatible with armv7-a, but the bootblock was running on a core which uses armv4t. By coincidence, it was emitting an instruction which is unavailable on armv4t when checking the value of the UART's LSR register. Now that the bootblock is compiled with more appropriate flags, this code can be re-introduced. Old-Change-Id: I7ecada4138b0889b963d1a8b19a4bab8e0bb1add Signed-off-by: Gabe Black <gabeblack@google.com> Reviewed-on: https://chromium-review.googlesource.com/170997 Reviewed-by: Gabe Black <gabeblack@chromium.org> Tested-by: Gabe Black <gabeblack@chromium.org> Commit-Queue: Gabe Black <gabeblack@chromium.org> (cherry picked from commit 2a0adceb5029c8ee633d17c82dbb11e48d30349d) tegra124: Seperate out the non-UART specific hardcoded init in the bootblock. The hardcoded init in the test function in the bootblock is actually useful generally because it doesn't belong in the UART driver itself but is necessary for the UART to work. Until we have real implementations for the pinmux, etc., we can use that code to get the UART and console going. Old-Change-Id: I2efe0b571d8b022eb2a2e5569620558540b28373 Signed-off-by: Gabe Black <gabeblack@google.com> Reviewed-on: https://chromium-review.googlesource.com/171334 Reviewed-by: Ronald Minnich <rminnich@chromium.org> Tested-by: Gabe Black <gabeblack@chromium.org> Commit-Queue: Gabe Black <gabeblack@chromium.org> (cherry picked from commit ae7d4d890be1936cc86dc15adeb33f3b46a51ae5) tegra124: Implement and enable serial console support for tegra124. The driver is very similar to the 8250 driver, except it isn't in two parts, and it also spaces its registers 4 bytes apart instead of having them directly adjacent to each other. Also, eliminate the UART test function in the bootblock. It's no longer needed since the actual console output serves the same purpose. Right now the clock divisor is fixed for now, and we'll want to actually figure out what value to use at some point. Old-Change-Id: Idd659222901eb76b0ed8cbb986deb5124096f2f6 Signed-off-by: Gabe Black <gabeblack@google.com> Reviewed-on: https://chromium-review.googlesource.com/171337 Reviewed-by: Gabe Black <gabeblack@chromium.org> Commit-Queue: Gabe Black <gabeblack@chromium.org> Tested-by: Gabe Black <gabeblack@chromium.org> (cherry picked from commit 86f5e2875b18901b349283cfbcd4f8cc88b7a019) Squashed 4 commits related to uart support for tegra124. Modified the new uart.c to look like the uart.c for exynos5420. Change-Id: I490cba014a43d58c30c48ca9ddcae2b00095b7a6 Signed-off-by: Isaac Christensen <isaac.christensen@se-eng.com> Reviewed-on: http://review.coreboot.org/6764 Tested-by: build bot (Jenkins) Reviewed-by: David Hendricks <dhendrix@chromium.org>
Diffstat (limited to 'src/soc/nvidia/tegra124/bootblock.c')
-rw-r--r--src/soc/nvidia/tegra124/bootblock.c52
1 files changed, 50 insertions, 2 deletions
diff --git a/src/soc/nvidia/tegra124/bootblock.c b/src/soc/nvidia/tegra124/bootblock.c
index 97180a0a33..cd7ea34147 100644
--- a/src/soc/nvidia/tegra124/bootblock.c
+++ b/src/soc/nvidia/tegra124/bootblock.c
@@ -18,19 +18,67 @@
*/
#include <arch/hlt.h>
-#include <arch/stages.h>
+#include <arch/io.h>
#include <cbfs.h>
#include <console/console.h>
+static void hacky_hardcoded_uart_setup_function(void)
+{
+ int i;
+
+ /*
+ * On poweron, AVP clock source (also called system clock) is set to
+ * PLLP_out0 with frequency set at 1MHz. Before initializing PLLP, we
+ * need to move the system clock's source to CLK_M temporarily. And
+ * then switch it to PLLP_out4 (204MHz) at a later time.
+ */
+ write32((0 << 12) | (0 << 8) | (0 << 4) | (0 << 0) | (2 << 28),
+ (void *)(0x60006000 + 0x28));
+
+ // wait a little bit (nominally 2-3 us)
+ for (i = 0; i < 0x10000; i++)
+ __asm__ __volatile__("");
+
+ // Set function.
+ setbits_le32((void *)(0x70000000 + 0x3000 + 0x2e0), 3 << 0);
+ setbits_le32((void *)(0x70000000 + 0x3000 + 0x2e4), 3 << 0);
+
+ // Output.
+ clrbits_le32((void *)(0x70000000 + 0x3000 + 0x2e0), 1 << 5);
+ // Input.
+ setbits_le32((void *)(0x70000000 + 0x3000 + 0x2e4), 1 << 5);
+
+ // Disable tristate.
+ clrbits_le32((void *)(0x70000000 + 0x3000 + 0x2e0), 1 << 4);
+ clrbits_le32((void *)(0x70000000 + 0x3000 + 0x2e4), 1 << 4);
+
+ // Assert UART reset and enable clock.
+ setbits_le32((void *)(0x60006000 + 4 + 0), 1 << 6);
+
+ // Enable the clock.
+ setbits_le32((void *)(0x60006000 + 4 * 4 + 0), 1 << 6);
+
+ // Set the clock source.
+ clrbits_le32((void *)(0x60006000 + 0x100 + 4 * 0x1e), 3 << 30);
+
+ // wait a little bit (nominally 2us?)
+ for (i = 0; i < 0x10000; i++)
+ __asm__ __volatile__("");
+
+ // De-assert reset to UART.
+ clrbits_le32((void *)(0x60006000 + 4 + 0), 1 << 6);
+}
+
void main(void)
{
void *entry;
+ hacky_hardcoded_uart_setup_function();
+
if (CONFIG_BOOTBLOCK_CONSOLE)
console_init();
entry = cbfs_load_stage(CBFS_DEFAULT_MEDIA, "fallback/romstage");
- if (entry) stage_exit(entry);
hlt();
}