mirror of
https://github.com/lcbcFoo/ReonV.git
synced 2025-04-18 18:44:43 -04:00
Trying to implement stdout for printf
This commit is contained in:
parent
ff2eae4ea1
commit
4c56d9eb49
5 changed files with 3086 additions and 0 deletions
154
riscv/console.c
Normal file
154
riscv/console.c
Normal file
|
@ -0,0 +1,154 @@
|
|||
#include <stdlib.h>
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
#define LEON_REG_UART_CONTROL_RTD 0x000000FF /* RX/TX data */
|
||||
|
||||
/*
|
||||
* The following defines the bits in the LEON UART Status Register.
|
||||
*/
|
||||
|
||||
#define LEON_REG_UART_STATUS_DR 0x00000001 /* Data Ready */
|
||||
#define LEON_REG_UART_STATUS_TSE 0x00000002 /* TX Send Register Empty */
|
||||
#define LEON_REG_UART_STATUS_THE 0x00000004 /* TX Hold Register Empty */
|
||||
#define LEON_REG_UART_STATUS_BR 0x00000008 /* Break Error */
|
||||
#define LEON_REG_UART_STATUS_OE 0x00000010 /* RX Overrun Error */
|
||||
#define LEON_REG_UART_STATUS_PE 0x00000020 /* RX Parity Error */
|
||||
#define LEON_REG_UART_STATUS_FE 0x00000040 /* RX Framing Error */
|
||||
#define LEON_REG_UART_STATUS_TF 0x00000200 /* FIFO Full */
|
||||
#define LEON_REG_UART_STATUS_ERR 0x00000078 /* Error Mask */
|
||||
|
||||
/*
|
||||
* The following defines the bits in the LEON UART Control Register.
|
||||
*/
|
||||
|
||||
#define LEON_REG_UART_CTRL_RE 0x00000001 /* Receiver enable */
|
||||
#define LEON_REG_UART_CTRL_TE 0x00000002 /* Transmitter enable */
|
||||
#define LEON_REG_UART_CTRL_RI 0x00000004 /* Receiver interrupt enable */
|
||||
#define LEON_REG_UART_CTRL_TI 0x00000008 /* Transmitter interrupt enable */
|
||||
#define LEON_REG_UART_CTRL_PS 0x00000010 /* Parity select */
|
||||
#define LEON_REG_UART_CTRL_PE 0x00000020 /* Parity enable */
|
||||
#define LEON_REG_UART_CTRL_FL 0x00000040 /* Flow control enable */
|
||||
#define LEON_REG_UART_CTRL_LB 0x00000080 /* Loop Back enable */
|
||||
#define LEON_REG_UART_CTRL_DB 0x00000800 /* Debug FIFO enable */
|
||||
#define LEON_REG_UART_CTRL_SI 0x00004000 /* TX shift register empty IRQ enable */
|
||||
#define LEON_REG_UART_CTRL_FA 0x80000000 /* FIFO Available */
|
||||
#define LEON_REG_UART_CTRL_FA_BIT 31
|
||||
|
||||
#define APBUART_CTRL_RE 0x1
|
||||
#define APBUART_CTRL_TE 0x2
|
||||
#define APBUART_CTRL_RI 0x4
|
||||
#define APBUART_CTRL_TI 0x8
|
||||
#define APBUART_CTRL_PS 0x10
|
||||
#define APBUART_CTRL_PE 0x20
|
||||
#define APBUART_CTRL_FL 0x40
|
||||
#define APBUART_CTRL_LB 0x80
|
||||
#define APBUART_CTRL_EC 0x100
|
||||
#define APBUART_CTRL_TF 0x200
|
||||
#define APBUART_CTRL_RF 0x400
|
||||
#define APBUART_CTRL_BI 0x1000
|
||||
#define APBUART_CTRL_DI 0x2000
|
||||
#define APBUART_CTRL_FA 0x80000000
|
||||
|
||||
#define APBUART_STATUS_DR 0x1
|
||||
#define APBUART_STATUS_TS 0x2
|
||||
#define APBUART_STATUS_TE 0x4
|
||||
#define APBUART_STATUS_BR 0x8
|
||||
#define APBUART_STATUS_OV 0x10
|
||||
#define APBUART_STATUS_PE 0x20
|
||||
#define APBUART_STATUS_FE 0x40
|
||||
#define APBUART_STATUS_ERR 0x78
|
||||
#define APBUART_STATUS_TH 0x80
|
||||
#define APBUART_STATUS_RH 0x100
|
||||
#define APBUART_STATUS_TF 0x200
|
||||
#define APBUART_STATUS_RF 0x400
|
||||
|
||||
|
||||
|
||||
|
||||
/* APB UART */
|
||||
typedef struct apbuart_regs {
|
||||
volatile unsigned int data;
|
||||
volatile unsigned int status;
|
||||
volatile unsigned int ctrl;
|
||||
volatile unsigned int scaler;
|
||||
} apbuart_regs;
|
||||
|
||||
struct apbuart_regs *uart_regs = (struct apbuart_regs*) 0x80000100;
|
||||
|
||||
/* Before UART driver has registered (or when no UART is available), calls to
|
||||
* printk that gets to bsp_out_char() will be filling data into the
|
||||
* pre_printk_dbgbuf[] buffer, hopefully the buffer can help debugging the
|
||||
* early BSP boot.. At least the last printk() will be caught.
|
||||
*/
|
||||
static char pre_printk_dbgbuf[32] = {0};
|
||||
static int pre_printk_pos = 0;
|
||||
|
||||
void apbuart_outbyte_polled(unsigned char ch, int do_cr_on_newline, int wait_sent){
|
||||
send:
|
||||
while ( (uart_regs->status & APBUART_STATUS_TE) == 0 ) {
|
||||
/* Lower bus utilization while waiting for UART */
|
||||
__asm__ volatile ("nop"::); __asm__ volatile ("nop"::);
|
||||
__asm__ volatile ("nop"::); __asm__ volatile ("nop"::);
|
||||
__asm__ volatile ("nop"::); __asm__ volatile ("nop"::);
|
||||
__asm__ volatile ("nop"::); __asm__ volatile ("nop"::);
|
||||
}
|
||||
|
||||
if ((ch == '\n') && do_cr_on_newline) {
|
||||
uart_regs->data = (unsigned int) '\r';
|
||||
do_cr_on_newline = 0;
|
||||
goto send;
|
||||
}
|
||||
uart_regs->data = (unsigned int) ch;
|
||||
|
||||
/* Wait until the character has been sent? */
|
||||
if (wait_sent) {
|
||||
while ((uart_regs->status & APBUART_STATUS_TE) == 0);
|
||||
}
|
||||
}
|
||||
|
||||
void apbuart_write_polled(const char *buf, size_t len)
|
||||
{
|
||||
size_t nwrite = 0;
|
||||
|
||||
while (nwrite < len) {
|
||||
apbuart_outbyte_polled(*buf++, 0, 1);
|
||||
nwrite++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void bsp_debug_uart_init(void)
|
||||
{
|
||||
// int i;
|
||||
// struct ambapp_dev *adev;
|
||||
// struct ambapp_apb_info *apb;
|
||||
//
|
||||
// /* Update uart_regs_index to index used as debug console. Let user
|
||||
// * select Debug console by setting uart_regs_index. If the BSP is to
|
||||
// * provide the default UART (uart_regs_index==0):
|
||||
// * non-MP: APBUART[0] is debug console
|
||||
// * MP: LEON CPU index select UART
|
||||
// */
|
||||
// if (uart_regs_index == 0) {
|
||||
// uart_regs_index = 0;
|
||||
// } else {
|
||||
// uart_regs_index--; /* User selected dbg-console */
|
||||
// }
|
||||
//
|
||||
// /* Find APBUART core for System Debug Console */
|
||||
// i = uart_regs_index;
|
||||
// adev = (void *)ambapp_for_each(&ambapp_plb, (OPTIONS_ALL|OPTIONS_APB_SLVS),
|
||||
// VENDOR_GAISLER, GAISLER_APBUART,
|
||||
// ambapp_find_by_idx, (void *)&i);
|
||||
// if (adev) {
|
||||
// /* Found a matching debug console, initialize debug uart if present
|
||||
// * for printk
|
||||
// */
|
||||
// apb = (struct ambapp_apb_info *)adev->devinfo;
|
||||
// uart_regs = (struct apbuart_regs *)apb->start;
|
||||
uart_regs->ctrl |= APBUART_CTRL_RE | APBUART_CTRL_TE;
|
||||
uart_regs->status = 0;
|
||||
//}
|
||||
}
|
BIN
riscv/main.out
Executable file
BIN
riscv/main.out
Executable file
Binary file not shown.
176
riscv/main.read
Normal file
176
riscv/main.read
Normal file
|
@ -0,0 +1,176 @@
|
|||
93000000
|
||||
13010000
|
||||
93010000
|
||||
13020000
|
||||
93020000
|
||||
13030000
|
||||
93030000
|
||||
13040000
|
||||
93040000
|
||||
13050000
|
||||
93050000
|
||||
13060000
|
||||
93060000
|
||||
13070000
|
||||
93070000
|
||||
13080000
|
||||
93080000
|
||||
13090000
|
||||
93090000
|
||||
130A0000
|
||||
930A0000
|
||||
130B0000
|
||||
930B0000
|
||||
130C0000
|
||||
930C0000
|
||||
130D0000
|
||||
930D0000
|
||||
130E0000
|
||||
930E0000
|
||||
130F0000
|
||||
930F0000
|
||||
37010044
|
||||
130101FF
|
||||
EF000014
|
||||
EF004000
|
||||
EF004001
|
||||
EF00800B
|
||||
EF00C00E
|
||||
EF004006
|
||||
EF008002
|
||||
130101FE
|
||||
232E8100
|
||||
13040102
|
||||
2326A4FE
|
||||
73001000
|
||||
13000000
|
||||
0324C101
|
||||
13010102
|
||||
67800000
|
||||
130101FE
|
||||
232E8100
|
||||
13040102
|
||||
2326A4FE
|
||||
2324B4FE
|
||||
2322C4FE
|
||||
8322C4FE
|
||||
032384FE
|
||||
832344FE
|
||||
93870200
|
||||
13850700
|
||||
0324C101
|
||||
13010102
|
||||
67800000
|
||||
130101FE
|
||||
232E8100
|
||||
13040102
|
||||
2326A4FE
|
||||
2324B4FE
|
||||
2322C4FE
|
||||
8322C4FE
|
||||
032384FE
|
||||
832344FE
|
||||
B7070040
|
||||
83A70720
|
||||
37572341
|
||||
13078767
|
||||
23A0E700
|
||||
832744FE
|
||||
13850700
|
||||
0324C101
|
||||
13010102
|
||||
67800000
|
||||
130101FE
|
||||
232E8100
|
||||
13040102
|
||||
2326A4FE
|
||||
2324B4FE
|
||||
2322C4FE
|
||||
8322C4FE
|
||||
032384FE
|
||||
832344FE
|
||||
93070000
|
||||
13850700
|
||||
0324C101
|
||||
13010102
|
||||
67800000
|
||||
130101FE
|
||||
232E8100
|
||||
13040102
|
||||
2326A4FE
|
||||
8322C4FE
|
||||
93070000
|
||||
13850700
|
||||
0324C101
|
||||
13010102
|
||||
67800000
|
||||
00000000
|
||||
A0896745
|
||||
4743433A
|
||||
2028474E
|
||||
55292037
|
||||
2E322E30
|
||||
00000000
|
||||
130101FE
|
||||
232E1100
|
||||
232C8100
|
||||
13040102
|
||||
93073000
|
||||
2326F4FE
|
||||
232404FE
|
||||
B7373334
|
||||
93871723
|
||||
2320F4FE
|
||||
230204FE
|
||||
930704FE
|
||||
13064000
|
||||
93850700
|
||||
13050000
|
||||
EFF09FE9
|
||||
8327C4FE
|
||||
13850700
|
||||
8320C101
|
||||
03248101
|
||||
13010102
|
||||
67800000
|
||||
130101FE
|
||||
232E1100
|
||||
232C8100
|
||||
232A9100
|
||||
13040102
|
||||
2326A4FE
|
||||
0327C4FE
|
||||
93071000
|
||||
6308F700
|
||||
0327C4FE
|
||||
93072000
|
||||
6316F700
|
||||
93071000
|
||||
6F000003
|
||||
8327C4FE
|
||||
9387F7FF
|
||||
13850700
|
||||
EFF0DFFB
|
||||
93040500
|
||||
8327C4FE
|
||||
9387E7FF
|
||||
13850700
|
||||
EFF09FFA
|
||||
93070500
|
||||
B387F400
|
||||
13850700
|
||||
8320C101
|
||||
03248101
|
||||
83244101
|
||||
13010102
|
||||
67800000
|
||||
130101FE
|
||||
232E8100
|
||||
13040102
|
||||
2326A4FE
|
||||
2324B4FE
|
||||
93070000
|
||||
13850700
|
||||
0324C101
|
||||
13010102
|
||||
67800000
|
385
riscv/reonv_print.c
Normal file
385
riscv/reonv_print.c
Normal file
|
@ -0,0 +1,385 @@
|
|||
/*
|
||||
* Copyright (c) 2011 Aeroflex Gaisler
|
||||
*
|
||||
* BSD license:
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
*/
|
||||
|
||||
/* This is a modified version of some files on leon3 compiler bcc 2.0.2 source
|
||||
* code, avaiable with GPL license on Aeroflex Gaisler website.
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <ctype.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
|
||||
/*
|
||||
* The following defines the bits in the UART Control Registers.
|
||||
*
|
||||
*/
|
||||
|
||||
#define LEON_REG_UART_CONTROL_RTD 0x000000FF /* RX/TX data */
|
||||
|
||||
/*
|
||||
* The following defines the bits in the LEON UART Status Registers.
|
||||
*/
|
||||
|
||||
#define LEON_REG_UART_STATUS_DR 0x00000001 /* Data Ready */
|
||||
#define LEON_REG_UART_STATUS_TSE 0x00000002 /* TX Send Register Empty */
|
||||
#define LEON_REG_UART_STATUS_THE 0x00000004 /* TX Hold Register Empty */
|
||||
#define LEON_REG_UART_STATUS_BR 0x00000008 /* Break Error */
|
||||
#define LEON_REG_UART_STATUS_OE 0x00000010 /* RX Overrun Error */
|
||||
#define LEON_REG_UART_STATUS_PE 0x00000020 /* RX Parity Error */
|
||||
#define LEON_REG_UART_STATUS_FE 0x00000040 /* RX Framing Error */
|
||||
#define LEON_REG_UART_STATUS_ERR 0x00000078 /* Error Mask */
|
||||
|
||||
|
||||
/*
|
||||
* The following defines the bits in the LEON UART Status Registers.
|
||||
*/
|
||||
|
||||
#define LEON_REG_UART_CTRL_RE 0x00000001 /* Receiver enable */
|
||||
#define LEON_REG_UART_CTRL_TE 0x00000002 /* Transmitter enable */
|
||||
#define LEON_REG_UART_CTRL_RI 0x00000004 /* Receiver interrupt enable */
|
||||
#define LEON_REG_UART_CTRL_TI 0x00000008 /* Transmitter interrupt enable */
|
||||
#define LEON_REG_UART_CTRL_PS 0x00000010 /* Parity select */
|
||||
#define LEON_REG_UART_CTRL_PE 0x00000020 /* Parity enable */
|
||||
#define LEON_REG_UART_CTRL_FL 0x00000040 /* Flow control enable */
|
||||
#define LEON_REG_UART_CTRL_LB 0x00000080 /* Loop Back enable */
|
||||
|
||||
|
||||
typedef struct
|
||||
{
|
||||
volatile unsigned int data;
|
||||
volatile unsigned int status;
|
||||
volatile unsigned int ctrl;
|
||||
volatile unsigned int scaler;
|
||||
} LEON23_APBUART_Regs_Map;
|
||||
extern volatile LEON23_APBUART_Regs_Map *leon23_uarts[2]; /* in console.c */
|
||||
|
||||
|
||||
typedef struct amba_apb_device
|
||||
{
|
||||
unsigned int start, irq;
|
||||
} amba_apb_device;
|
||||
|
||||
|
||||
static size_t
|
||||
lo_strnlen (const char *s, size_t count)
|
||||
{
|
||||
const char *sc;
|
||||
|
||||
for (sc = s; count-- && *sc != '\0'; ++sc)
|
||||
/* nothing */ ;
|
||||
return sc - s;
|
||||
}
|
||||
|
||||
static int
|
||||
lo_vsnprintf (char *buf, size_t size, const char *fmt, va_list args)
|
||||
{
|
||||
int len;
|
||||
unsigned long long num;
|
||||
int i, j, n;
|
||||
char *str, *end, c;
|
||||
const char *s;
|
||||
int flags;
|
||||
int field_width;
|
||||
int precision;
|
||||
int qualifier;
|
||||
int filler;
|
||||
|
||||
str = buf;
|
||||
end = buf + size - 1;
|
||||
|
||||
if (end < buf - 1)
|
||||
{
|
||||
end = ((void *) -1);
|
||||
size = end - buf + 1;
|
||||
}
|
||||
|
||||
for (; *fmt; ++fmt)
|
||||
{
|
||||
if (*fmt != '%')
|
||||
{
|
||||
if (*fmt == '\n')
|
||||
{
|
||||
if (str <= end)
|
||||
{
|
||||
*str = '\r';
|
||||
}
|
||||
str++;
|
||||
}
|
||||
if (str <= end)
|
||||
*str = *fmt;
|
||||
++str;
|
||||
continue;
|
||||
}
|
||||
|
||||
/* process flags */
|
||||
flags = 0;
|
||||
/* get field width */
|
||||
field_width = 0;
|
||||
/* get the precision */
|
||||
precision = -1;
|
||||
/* get the conversion qualifier */
|
||||
qualifier = 'l';
|
||||
filler = ' ';
|
||||
|
||||
++fmt;
|
||||
|
||||
if (*fmt == '0')
|
||||
{
|
||||
filler = '0';
|
||||
++fmt;
|
||||
}
|
||||
|
||||
while (isdigit (*fmt))
|
||||
{
|
||||
field_width = field_width * 10 + ((*fmt) - '0');
|
||||
++fmt;
|
||||
}
|
||||
|
||||
/* default base */
|
||||
switch (*fmt)
|
||||
{
|
||||
case 'c':
|
||||
c = (unsigned char) va_arg (args, int);
|
||||
if (str <= end)
|
||||
*str = c;
|
||||
++str;
|
||||
while (--field_width > 0)
|
||||
{
|
||||
if (str <= end)
|
||||
*str = ' ';
|
||||
++str;
|
||||
}
|
||||
continue;
|
||||
|
||||
case 's':
|
||||
s = va_arg (args, char *);
|
||||
if (!s)
|
||||
s = "<NULL>";
|
||||
|
||||
len = lo_strnlen (s, precision);
|
||||
|
||||
for (i = 0; i < len; ++i)
|
||||
{
|
||||
if (str <= end)
|
||||
*str = *s;
|
||||
++str;
|
||||
++s;
|
||||
}
|
||||
while (len < field_width--)
|
||||
{
|
||||
if (str <= end)
|
||||
*str = ' ';
|
||||
++str;
|
||||
}
|
||||
continue;
|
||||
|
||||
|
||||
case '%':
|
||||
if (str <= end)
|
||||
*str = '%';
|
||||
++str;
|
||||
continue;
|
||||
|
||||
case 'x':
|
||||
break;
|
||||
case 'd':
|
||||
break;
|
||||
|
||||
default:
|
||||
if (str <= end)
|
||||
*str = '%';
|
||||
++str;
|
||||
if (*fmt)
|
||||
{
|
||||
if (str <= end)
|
||||
*str = *fmt;
|
||||
++str;
|
||||
}
|
||||
else
|
||||
{
|
||||
--fmt;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
num = va_arg (args, unsigned long);
|
||||
if (*fmt == 'd')
|
||||
{
|
||||
j = 0;
|
||||
while (num && str <= end)
|
||||
{
|
||||
*str = (num % 10) + '0';
|
||||
num = num / 10;
|
||||
++str;
|
||||
j++;
|
||||
}
|
||||
/* flip */
|
||||
for (i = 0; i < (j / 2); i++)
|
||||
{
|
||||
n = str[(-j) + i];
|
||||
str[(-j) + i] = str[-(i + 1)];
|
||||
str[-(i + 1)] = n;
|
||||
}
|
||||
/* shift */
|
||||
if (field_width > j)
|
||||
{
|
||||
i = field_width - j;
|
||||
for (n = 1; n <= j; n++)
|
||||
{
|
||||
if (str + i - n <= end)
|
||||
{
|
||||
str[i - n] = str[-n];
|
||||
}
|
||||
}
|
||||
for (i--; i >= 0; i--)
|
||||
{
|
||||
str[i - j] = filler;
|
||||
}
|
||||
str += field_width - j;
|
||||
j = 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (j = 0, i = 0; i < 8 && str <= end; i++)
|
||||
{
|
||||
if ((n =
|
||||
((unsigned long) (num & (0xf0000000ul >> (i * 4)))) >>
|
||||
((7 - i) * 4)) || j != 0)
|
||||
{
|
||||
if (n >= 10)
|
||||
n += 'a' - 10;
|
||||
else
|
||||
n += '0';
|
||||
*str = n;
|
||||
++str;
|
||||
j++;
|
||||
}
|
||||
}
|
||||
|
||||
/* shift */
|
||||
if (field_width > j)
|
||||
{
|
||||
i = field_width - j;
|
||||
for (n = 1; n <= j; n++)
|
||||
{
|
||||
if (str + i - n <= end)
|
||||
{
|
||||
str[i - n] = str[-n];
|
||||
}
|
||||
}
|
||||
for (i--; i >= 0; i--)
|
||||
{
|
||||
str[i - j] = filler;
|
||||
}
|
||||
str += field_width - j;
|
||||
j = 1;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
if (j == 0 && str <= end)
|
||||
{
|
||||
*str = '0';
|
||||
++str;
|
||||
}
|
||||
}
|
||||
if (str <= end)
|
||||
*str = '\0';
|
||||
else if (size > 0)
|
||||
/* don't write out a null byte if the buf size is zero */
|
||||
*end = '\0';
|
||||
/* the trailing null byte doesn't count towards the total
|
||||
* ++str;
|
||||
*/
|
||||
return str - buf;
|
||||
}
|
||||
|
||||
/**
|
||||
* lo_vsprintf - Format a string and place it in a buffer
|
||||
* @buf: The buffer to place the result into
|
||||
* @fmt: The format string to use
|
||||
* @args: Arguments for the format string
|
||||
*
|
||||
* Call this function if you are already dealing with a va_list.
|
||||
* You probably want lo_sprintf instead.
|
||||
*/
|
||||
static int
|
||||
lo_vsprintf (char *buf, const char *fmt, va_list args)
|
||||
{
|
||||
return lo_vsnprintf (buf, 0xFFFFFFFFUL, fmt, args);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
dbgleon_sprintf (char *buf, size_t size, const char *fmt, ...)
|
||||
{
|
||||
va_list args;
|
||||
int printed_len;
|
||||
|
||||
va_start (args, fmt);
|
||||
printed_len = lo_vsnprintf (buf, size, fmt, args);
|
||||
va_end (args);
|
||||
return printed_len;
|
||||
}
|
||||
|
||||
#define UART_TIMEOUT 100000
|
||||
static LEON23_APBUART_Regs_Map *uart_regs = 0;
|
||||
//int *console = (int *) 0x80000100;
|
||||
int
|
||||
dbgleon_printf (const char *fmt, ...)
|
||||
{
|
||||
unsigned int i, loops, ch;
|
||||
amba_apb_device apbdevs[1];
|
||||
va_list args;
|
||||
int printed_len;
|
||||
char printk_buf[1024];
|
||||
char *p = printk_buf;
|
||||
|
||||
/* Emit the output into the temporary buffer */
|
||||
va_start (args, fmt);
|
||||
printed_len = lo_vsnprintf (printk_buf, sizeof (printk_buf), fmt, args);
|
||||
va_end (args);
|
||||
|
||||
|
||||
uart_regs = (LEON23_APBUART_Regs_Map*) 0x80000100;
|
||||
if (uart_regs){
|
||||
while (printed_len-- != 0){
|
||||
ch = *p++;
|
||||
if (uart_regs){
|
||||
loops = 0;
|
||||
|
||||
while (!(uart_regs->status & LEON_REG_UART_STATUS_THE) && (loops < UART_TIMEOUT))
|
||||
loops++;
|
||||
|
||||
uart_regs->data = ch;
|
||||
loops = 0;
|
||||
while (!(uart_regs->status & LEON_REG_UART_STATUS_TSE) && (loops < UART_TIMEOUT))
|
||||
loops++;
|
||||
}
|
||||
}
|
||||
}
|
||||
//---------------------
|
||||
}
|
Loading…
Add table
Reference in a new issue