diff --git a/drivers/ti/uart/aarch32/16550_console.S b/drivers/ti/uart/aarch32/16550_console.S
index 692188412fb9a3f97fdb5eeabe936d3a07f144d5..5cd9b30cd89f50db890c877b666f774eb707a601 100644
--- a/drivers/ti/uart/aarch32/16550_console.S
+++ b/drivers/ti/uart/aarch32/16550_console.S
@@ -89,16 +89,19 @@ endfunc console_16550_core_init
 	.globl console_16550_register
 
 	/* -------------------------------------------------------
-	 * int console_stm32_register(uintptr_t baseaddr,
+	 * int console_16550_register(uintptr_t baseaddr,
 	 *     uint32_t clock, uint32_t baud,
-	 *     struct console_stm32 *console);
-	 * Function to initialize and register a new STM32
+	 *     console_16550_t *console);
+	 * Function to initialize and register a new 16550
 	 * console. Storage passed in for the console struct
 	 * *must* be persistent (i.e. not from the stack).
+	 * If r1 (UART clock) is 0, initialisation will be
+         * skipped, relying on previous code to have done
+         * this already. r2 is ignored then as well.
 	 * In: r0 - UART register base address
 	 *     r1 - UART clock in Hz
-	 *     r2 - Baud rate
-	 *     r3 - pointer to empty console_stm32 struct
+	 *     r2 - Baud rate (ignored if r1 is 0)
+	 *     r3 - pointer to empty console_16550_t struct
 	 * Out: return 1 on success, 0 on error
 	 * Clobber list : r0, r1, r2
 	 * -------------------------------------------------------
@@ -110,10 +113,15 @@ func console_16550_register
 	beq	register_fail
 	str	r0, [r4, #CONSOLE_T_16550_BASE]
 
+	/* A clock rate of zero means to skip the initialisation. */
+	cmp	r1, #0
+	beq	register_16550
+
 	bl	console_16550_core_init
 	cmp	r0, #0
 	beq	register_fail
 
+register_16550:
 	mov	r0, r4
 	pop	{r4, lr}
 	finish_console_register 16550 putc=1, getc=1, flush=1
diff --git a/drivers/ti/uart/aarch64/16550_console.S b/drivers/ti/uart/aarch64/16550_console.S
index dab46e8c509935a8087c9b1d081dd68f5ac0c07d..80c1b86462294eab40f3ac5024743ea91c805d40 100644
--- a/drivers/ti/uart/aarch64/16550_console.S
+++ b/drivers/ti/uart/aarch64/16550_console.S
@@ -92,9 +92,12 @@ endfunc console_16550_core_init
 	 * Function to initialize and register a new 16550
 	 * console. Storage passed in for the console struct
 	 * *must* be persistent (i.e. not from the stack).
+	 * If w1 (UART clock) is 0, initialisation will be
+	 * skipped, relying on previous code to have done
+	 * this already. w2 is ignored then as well.
 	 * In: x0 - UART register base address
 	 *     w1 - UART clock in Hz
-	 *     w2 - Baud rate
+	 *     w2 - Baud rate (ignored if w1 is 0)
 	 *     x3 - pointer to empty console_16550_t struct
 	 * Out: return 1 on success, 0 on error
 	 * Clobber list : x0, x1, x2, x6, x7, x14
@@ -106,9 +109,13 @@ func console_16550_register
 	cbz	x6, register_fail
 	str	x0, [x6, #CONSOLE_T_16550_BASE]
 
+	/* A clock rate of zero means to skip the initialisation. */
+	cbz	w1, register_16550
+
 	bl	console_16550_core_init
 	cbz	x0, register_fail
 
+register_16550:
 	mov	x0, x6
 	mov	x30, x7
 	finish_console_register 16550 putc=1, getc=1, flush=1
diff --git a/include/drivers/ti/uart/uart_16550.h b/include/drivers/ti/uart/uart_16550.h
index 32e38f0ac1ef5e462892db41666e19a75c32edb6..2b95fa33a685c69fdeaed656097e2dd3f27afd00 100644
--- a/include/drivers/ti/uart/uart_16550.h
+++ b/include/drivers/ti/uart/uart_16550.h
@@ -87,6 +87,11 @@ typedef struct {
  * framework. The |console| pointer must point to storage that will be valid
  * for the lifetime of the console, such as a global or static local variable.
  * Its contents will be reinitialized from scratch.
+ * When |clock| has a value of 0, the UART will *not* be initialised. This
+ * means the UART should already be enabled and the baudrate and clock setup
+ * should have been done already, either by platform specific code or by
+ * previous firmware stages. The |baud| parameter will be ignored in this
+ * case as well.
  */
 int console_16550_register(uintptr_t baseaddr, uint32_t clock, uint32_t baud,
 			   console_16550_t *console);