/*
 * linux/include/asm-arm/arch-s3c2400/uncompress.h
 *
 * (C) 1999 Nicolas Pitre <nico@cam.org>
 *
 * Modified for the S3C2400 by gj@denx.de
 * NB: this file is not used for pImage
 */

#include "hardware.h"
#include "serial_reg.h"

static volatile unsigned long* serial_port = (unsigned long*)0x15000000;

#define MPLLCON (0x14800004)
#define CLKDIVN (0x14800014)
static unsigned int fclk = 0;
static unsigned int uartclk = 0;
static void s3c2400_get_fclk(void)
{
	unsigned int mpllcon = *(unsigned int *)MPLLCON;
	int clkdivn = (*(unsigned int *)CLKDIVN) & 3;
	int clk_factor[4] = {1, 2, 2, 4};

	/* the S3C2400 uses a 12 MHz xtal */
	/* formula from page 6-22 */
	fclk = ((12000000 * (8 + ((mpllcon & 0xff000) >> 12)))/((2 + ((mpllcon & 0x1f0) >> 4)) * (1 << (mpllcon & 3))));
	uartclk = fclk/clk_factor[clkdivn];
}

/* armboot may run with a different clock, so have to set up the UART here */
// by chc 
static void init_uart()
{
        int i;
	unsigned short baud_div;

	// setting I/O (General I/O) 
        *(volatile unsigned long *)(0x1560002c) = 0x3c0;
        *(volatile unsigned long *)(0x15600023) = 0x18;
        *(volatile unsigned long *)(0x15600038) = 0xaaa;
        *(volatile unsigned long *)(0x15600040) = 0x3f;
        serial_port[UFCON0] = 0x0;
        serial_port[UMCON0] = 0x0;
	serial_port[ULCON0]  = 0x03;
	serial_port[UCON0]   = 0x245;
	sc32400_get_fclk();
	/* assumes 115200, should really check the value from armboot XXX */
        baud_div = (uartclk/(115200 * 16)) - 1;
	if (baud_div == 0)
		baud_div = 1;
        if (serial_port[UBRDIV0] != baud_div)
		serial_port[UBRDIV0] = baud_div;
	for (i=0; i<100; i++);
}

static void puts( const char *s )
{
	int i;
	const char *tmp=s;
	static int did_uart0_setup = 0;

	if (did_uart0_setup == 0)
	{
		init_uart();
		did_uart0_setup = 1;
	}

	for (i = 0; *s; i++, s++) {
		while( !(serial_port[UTRSTAT0] & 0x2) );
		serial_port[UTXH0] = *s;
		if (*s == 10) {
			while( !(serial_port[UTRSTAT0] & 0x2) );
			serial_port[UTXH0] = 13;
		}
	}
	s = tmp;
}

/*
 * Nothing to do for these
 */
#define arch_decomp_setup()
#define arch_decomp_wdog()
