/*
 * arch/v850/kernel/memcons.c -- Console I/O to a memory buffer
 *
 *  Copyright (C) 2001,02  NEC Corporation
 *  Copyright (C) 2001,02  Miles Bader <miles@gnu.org>
 *
 * This file is subject to the terms and conditions of the GNU General
 * Public License.  See the file COPYING in the main directory of this
 * archive for more details.
 *
 * Written by Miles Bader <miles@gnu.org>
 */

#include <linux/kernel.h>
#include <linux/console.h>
#include <linux/tty.h>
#include <linux/tty_driver.h>
#include <linux/init.h>

/* If this device is enabled, the linker map should define start and
   end points for its buffer. */
extern char memcons_output[], memcons_output_end;

/* Current offset into the buffer.  */
static unsigned long memcons_offs = 0;

/* Spinlock protecting memcons_offs.  */
static DEFINE_SPINLOCK(memcons_lock);


static size_t write (const char *buf, size_t len)
{
	unsigned long flags;
	char *point;

	spin_lock_irqsave (memcons_lock, flags);

	point = memcons_output + memcons_offs;
	if (point + len >= &memcons_output_end) {
		len = &memcons_output_end - point;
		memcons_offs = 0;
	} else
		memcons_offs += len;

	spin_unlock_irqrestore (memcons_lock, flags);

	memcpy (point, buf, len);

	return len;
}


/*  Low-level console. */

static void memcons_write (struct console *co, const char *buf, unsigned len)
{
	while (len > 0)
		len -= write (buf, len);
}

static struct tty_driver *tty_driver;

static struct tty_driver *memcons_device (struct console *co, int *index)
{
	*index = co->index;
	return tty_driver;
}

static struct console memcons =
{
    .name	= "memcons",
    .write	= memcons_write,
    .device	= memcons_device,
    .flags	= CON_PRINTBUFFER,
    .index	= -1,
};

void memcons_setup (void)
{
	register_console (&memcons);
	printk (KERN_INFO "Console: static memory buffer (memcons)\n");
}

/* Higher level TTY interface.  */

int memcons_tty_open (struct tty_struct *tty, struct file *filp)
{
	return 0;
}

int memcons_tty_write (struct tty_struct *tty, const unsigned char *buf, int len)
{
	return write (buf, len);
}

int memcons_tty_write_room (struct tty_struct *tty)
{
	return &memcons_output_end - (memcons_output + memcons_offs);
}

int memcons_tty_chars_in_buffer (struct tty_struct *tty)
{
	/* We have no buffer.  */
	return 0;
}

static const struct tty_operations ops = {
	.open = memcons_tty_open,
	.write = memcons_tty_write,
	.write_room = memcons_tty_write_room,
	.chars_in_buffer = memcons_tty_chars_in_buffer,
};

int __init memcons_tty_init (void)
{
	int err;
	struct tty_driver *driver = alloc_tty_driver(1);
	if (!driver)
		return -ENOMEM;

	driver->name = "memcons";
	driver->major = TTY_MAJOR;
	driver->minor_start = 64;
	driver->type = TTY_DRIVER_TYPE_SYSCONS;
	driver->init_termios = tty_std_termios;
	tty_set_operations(driver, &ops);
	err = tty_register_driver(driver);
	if (err) {
		put_tty_driver(driver);
		return err;
	}
	tty_driver = driver;
	return 0;
}
__initcall (memcons_tty_init);
