1 // SPDX-License-Identifier: GPL-2.0
2 /*
3 * Copyright (C) 2011 The ChromiumOS Authors. All rights reserved.
4 */
5
6 #include <console.h>
7 #include <linux/string.h>
8 #include <asm/cb_sysinfo.h>
9
cbmemc_putc(struct stdio_dev * dev,char data)10 void cbmemc_putc(struct stdio_dev *dev, char data)
11 {
12 const struct sysinfo_t *sysinfo = cb_get_sysinfo();
13 struct cbmem_console *cons;
14 uint pos, flags;
15
16 if (!sysinfo)
17 return;
18 cons = sysinfo->cbmem_cons;
19 if (!cons)
20 return;
21
22 pos = cons->cursor & CBMC_CURSOR_MASK;
23
24 /* preserve the overflow flag if present */
25 flags = cons->cursor & ~CBMC_CURSOR_MASK;
26
27 cons->body[pos++] = data;
28
29 /*
30 * Deal with overflow - the flag may be cleared by another program which
31 * reads the buffer out later, e.g. Linux
32 */
33 if (pos >= cons->size) {
34 pos = 0;
35 flags |= CBMC_OVERFLOW;
36 }
37
38 cons->cursor = flags | pos;
39 }
40
cbmemc_puts(struct stdio_dev * dev,const char * str)41 void cbmemc_puts(struct stdio_dev *dev, const char *str)
42 {
43 char c;
44
45 while ((c = *str++) != 0)
46 cbmemc_putc(dev, c);
47 }
48
cbmemc_init(void)49 int cbmemc_init(void)
50 {
51 int rc;
52 struct stdio_dev cons_dev;
53
54 memset(&cons_dev, 0, sizeof(cons_dev));
55
56 strcpy(cons_dev.name, "cbmem");
57 cons_dev.flags = DEV_FLAGS_OUTPUT; /* Output only */
58 cons_dev.putc = cbmemc_putc;
59 cons_dev.puts = cbmemc_puts;
60
61 rc = stdio_register(&cons_dev);
62
63 return (rc == 0) ? 1 : rc;
64 }
65