/*
 *  drivers/s390/char/con3270.c
 *    IBM/3270 Driver - console view.
 *
 *  Author(s):
 *    Original 3270 Code for 2.4 written by Richard Hitt (UTS Global)
 *    Rewritten for 2.5 by Martin Schwidefsky <schwidefsky@de.ibm.com>
 *	-- Copyright (C) 2003 IBM Deutschland Entwicklung GmbH, IBM Corporation
 */

#include <linux/config.h>
#include <linux/bootmem.h>
#include <linux/console.h>
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/types.h>
#include <linux/err.h>

#include <asm/ccwdev.h>
#include <asm/cio.h>
#include <asm/cpcmd.h>
#include <asm/ebcdic.h>

#include "raw3270.h"
#include "ctrlchar.h"

#define CON3270_OUTPUT_BUFFER_SIZE 1024
#define CON3270_STRING_PAGES 4

static struct raw3270_fn con3270_fn;

/*
 * Main 3270 console view data structure.
 */
struct con3270 {
	struct raw3270_view view;
	spinlock_t lock;
	struct list_head freemem;	/* list of free memory for strings. */

	/* Output stuff. */
	struct list_head lines;		/* list of lines. */
	struct list_head update;	/* list of lines to update. */
	int line_nr;			/* line number for next update. */
	int nr_lines;			/* # lines in list. */
	int nr_up;			/* # lines up in history. */
	unsigned long update_flags;	/* Update indication bits. */
	struct string *cline;		/* current output line. */
	struct string *status;		/* last line of display. */
	struct raw3270_request *write;	/* single write request. */
	struct timer_list timer;

	/* Input stuff. */
	struct string *input;		/* input string for read request. */
	struct raw3270_request *read;	/* single read request. */
	struct raw3270_request *kreset;	/* single keyboard reset request. */
	struct tasklet_struct readlet;	/* tasklet to issue read request. */
};

static struct con3270 *condev;

/* con3270->update_flags. See con3270_update for details. */
#define CON_UPDATE_ERASE	1	/* Use EWRITEA instead of WRITE. */
#define CON_UPDATE_LIST		2	/* Update lines in tty3270->update. */
#define CON_UPDATE_STATUS	4	/* Update status line. */
#define CON_UPDATE_ALL		7

static void con3270_update(struct con3270 *);

/*
 * Setup timeout for a device. On timeout trigger an update.
 */
void
con3270_set_timer(struct con3270 *cp, int expires)
{
	if (expires == 0) {
		if (timer_pending(&cp->timer))
			del_timer(&cp->timer);
		return;
	}
	if (timer_pending(&cp->timer) &&
	    mod_timer(&cp->timer, jiffies + expires))
		return;
	cp->timer.function = (void (*)(unsigned long)) con3270_update;
	cp->timer.data = (unsigned long) cp;
	cp->timer.expires = jiffies + expires;
	add_timer(&cp->timer);
}

/*
 * The status line is the last line of the screen. It shows the string
 * "console view" in the lower left corner and "Running"/"More..."/"Holding"
 * in the lower right corner of the screen.
 */
static void
con3270_update_status(struct con3270 *cp)
{
	char *str;

	str = (cp->nr_up != 0) ? "History" : "Running";
	memcpy(cp->status->string + 24, str, 7);
	codepage_convert(cp->view.ascebc, cp->status->string + 24, 7);
	cp->update_flags |= CON_UPDATE_STATUS;
}

static void
con3270_create_status(struct con3270 *cp)
{
	static const unsigned char blueprint[] =
		{ TO_SBA, 0, 0, TO_SF,TF_LOG,TO_SA,TAT_COLOR, TAC_GREEN,
		  'c','o','n','s','o','l','e',' ','v','i','e','w',
		  TO_RA,0,0,0,'R','u','n','n','i','n','g',TO_SF,TF_LOG };

	cp->status = alloc_string(&cp->freemem, sizeof(blueprint));
	/* Copy blueprint to status line */
	memcpy(cp->status->string, blueprint, sizeof(blueprint));
	/* Set TO_RA addresses. */
	raw3270_buffer_address(cp->view.dev, cp->status->string + 1,
			       cp->view.cols * (cp->view.rows - 1));
	raw3270_buffer_address(cp->view.dev, cp->status->string + 21,
			       cp->view.cols * cp->view.rows - 8);
	/* Convert strings to ebcdic. */
	codepage_convert(cp->view.ascebc, cp->status->string + 8, 12);
	codepage_convert(cp->view.ascebc, cp->status->string + 24, 7);
}

/*
 * Set output offsets to 3270 datastream fragment of a console string.
 */
static void
con3270_update_string(struct con3270 *cp, struct string *s, int nr)
{
	if (s->len >= cp->view.cols - 5)
		return;
	raw3270_buffer_address(cp->view.dev, s->string + s->len - 3,
			       cp->view.cols * (nr + 1));
}

/*
 * Rebuild update list to print all lines.
 */
static void
con3270_rebuild_update(struct con3270 *cp)
{
	struct string *s, *n;
	int nr;

	/* 
	 * Throw away update list and create a new one,
	 * containing all lines that will fit on the screen.
	 */
	list_for_each_entry_safe(s, n, &cp->update, update)
		list_del_init(&s->update);
	nr = cp->view.rows - 2 + cp->nr_up;
	list_for_each_entry_reverse(s, &cp->lines, list) {
		if (nr < cp->view.rows - 1)
			list_add(&s->update, &cp->update);
		if (--nr < 0)
			break;
	}
	cp->line_nr = 0;
	cp->update_flags |= CON_UPDATE_LIST;
}

/*
 * Alloc string for size bytes. Free strings from history if necessary.
 */
static struct string *
con3270_alloc_string(struct con3270 *cp, size_t size)
{
	struct string *s, *n;

	s = alloc_string(&cp->freemem, size);
	if (s)
		return s;
	list_for_each_entry_safe(s, n, &cp->lines, list) {
		list_del(&s->list);
		if (!list_empty(&s->update))
			list_del(&s->update);
		cp->nr_lines--;
		if (free_string(&cp->freemem, s) >= size)
			break;
	}
	s = alloc_string(&cp->freemem, size);
	BUG_ON(!s);
	if (cp->nr_up != 0 && cp->nr_up + cp->view.rows > cp->nr_lines) {
		cp->nr_up = cp->nr_lines - cp->view.rows + 1;
		con3270_rebuild_update(cp);
		con3270_update_status(cp);
	}
	return s;
}

/*
 * Write completion callback.
 */
static void
con3270_write_callback(struct raw3270_request *rq, void *data)
{
	raw3270_request_reset(rq);
	xchg(&((struct con3270 *) rq->view)->write, rq);
}

/*
 * Update console display.
 */
static void
con3270_update(struct con3270 *cp)
{
	struct raw3270_request *wrq;
	char wcc, prolog[6];
	unsigned long flags;
	unsigned long updated;
	struct string *s, *n;
	int rc;

	if (cp->view.dev)
		raw3270_activate_view(&cp->view);

	wrq = xchg(&cp->write, 0);
	if (!wrq) {
		con3270_set_timer(cp, 1);
		return;
	}

	spin_lock_irqsave(&cp->view.lock, flags);
	updated = 0;
	if (cp->update_flags & CON_UPDATE_ERASE) {
		/* Use erase write alternate to initialize display. */
		raw3270_request_set_cmd(wrq, TC_EWRITEA);
		updated |= CON_UPDATE_ERASE;
	} else
		raw3270_request_set_cmd(wrq, TC_WRITE);

	wcc = TW_NONE;
	raw3270_request_add_data(wrq, &wcc, 1);

	/*
	 * Update status line.
	 */
	if (cp->update_flags & CON_UPDATE_STATUS)
		if (raw3270_request_add_data(wrq, cp->status->string,
					     cp->status->len) == 0)
			updated |= CON_UPDATE_STATUS;

	if (cp->update_flags & CON_UPDATE_LIST) {
		prolog[0] = TO_SBA;
		prolog[3] = TO_SA;
		prolog[4] = TAT_COLOR;
		prolog[5] = TAC_TURQ;
		raw3270_buffer_address(cp->view.dev, prolog + 1,
				       cp->view.cols * cp->line_nr);
		raw3270_request_add_data(wrq, prolog, 6);
		/* Write strings in the update list to the screen. */
		list_for_each_entry_safe(s, n, &cp->update, update) {
			if (s != cp->cline)
				con3270_update_string(cp, s, cp->line_nr);
			if (raw3270_request_add_data(wrq, s->string,
						     s->len) != 0)
				break;
			list_del_init(&s->update);
			if (s != cp->cline)
				cp->line_nr++;
		}
		if (list_empty(&cp->update))
			updated |= CON_UPDATE_LIST;
	}
	wrq->callback = con3270_write_callback;
	rc = raw3270_start(&cp->view, wrq);
	if (rc == 0) {
		cp->update_flags &= ~updated;
		if (cp->update_flags)
			con3270_set_timer(cp, 1);
	} else {
		raw3270_request_reset(wrq);
		xchg(&cp->write, wrq);
	}
	spin_unlock_irqrestore(&cp->view.lock, flags);
}

/*
 * Read tasklet.
 */
static void
con3270_read_tasklet(struct raw3270_request *rrq)
{
	static char kreset_data = TW_KR;
	struct con3270 *cp;
	unsigned long flags;
	int nr_up, deactivate;

	cp = (struct con3270 *) rrq->view;
	spin_lock_irqsave(&cp->view.lock, flags);
	nr_up = cp->nr_up;
	deactivate = 0;
	/* Check aid byte. */
	switch (cp->input->string[0]) {
	case 0x7d:	/* enter: jump to bottom. */
		nr_up = 0;
		break;
	case 0xf3:	/* PF3: deactivate the console view. */
		deactivate = 1;
		break;
	case 0x6d:	/* clear: start from scratch. */
		con3270_rebuild_update(cp);
		cp->update_flags = CON_UPDATE_ALL;
		con3270_set_timer(cp, 1);
		break;
	case 0xf7:	/* PF7: do a page up in the console log. */
		nr_up += cp->view.rows - 2;
		if (nr_up + cp->view.rows - 1 > cp->nr_lines) {
			nr_up = cp->nr_lines - cp->view.rows + 1;
			if (nr_up < 0)
				nr_up = 0;
		}
		break;
	case 0xf8:	/* PF8: do a page down in the console log. */
		nr_up -= cp->view.rows - 2;
		if (nr_up < 0)
			nr_up = 0;
		break;
	}
	if (nr_up != cp->nr_up) {
		cp->nr_up = nr_up;
		con3270_rebuild_update(cp);
		con3270_update_status(cp);
		con3270_set_timer(cp, 1);
	}
	spin_unlock_irqrestore(&cp->view.lock, flags);

	/* Start keyboard reset command. */
	raw3270_request_reset(cp->kreset);
	raw3270_request_set_cmd(cp->kreset, TC_WRITE);
	raw3270_request_add_data(cp->kreset, &kreset_data, 1);
	raw3270_start(&cp->view, cp->kreset);

	if (deactivate)
		raw3270_deactivate_view(&cp->view);

	raw3270_request_reset(rrq);
	xchg(&cp->read, rrq);
	raw3270_put_view(&cp->view);
}

/*
 * Read request completion callback.
 */
static void
con3270_read_callback(struct raw3270_request *rq, void *data)
{
	raw3270_get_view(rq->view);
	/* Schedule tasklet to pass input to tty. */
	tasklet_schedule(&((struct con3270 *) rq->view)->readlet);
}

/*
 * Issue a read request. Called only from interrupt function.
 */
static void
con3270_issue_read(struct con3270 *cp)
{
	struct raw3270_request *rrq;
	int rc;

	rrq = xchg(&cp->read, 0);
	if (!rrq)
		/* Read already scheduled. */
		return;
	rrq->callback = con3270_read_callback;
	rrq->callback_data = cp;
	raw3270_request_set_cmd(rrq, TC_READMOD);
	raw3270_request_set_data(rrq, cp->input->string, cp->input->len);
	/* Issue the read modified request. */
	rc = raw3270_start_irq(&cp->view, rrq);
	if (rc)
		raw3270_request_reset(rrq);
}

/*
 * Switch to the console view.
 */
static int
con3270_activate(struct raw3270_view *view)
{
	unsigned long flags;
	struct con3270 *cp;

	cp = (struct con3270 *) view;
	spin_lock_irqsave(&cp->view.lock, flags);
	cp->nr_up = 0;
	con3270_rebuild_update(cp);
	con3270_update_status(cp);
	cp->update_flags = CON_UPDATE_ALL;
	con3270_set_timer(cp, 1);
	spin_unlock_irqrestore(&cp->view.lock, flags);
	return 0;
}

static void
con3270_deactivate(struct raw3270_view *view)
{
	unsigned long flags;
	struct con3270 *cp;

	cp = (struct con3270 *) view;
	spin_lock_irqsave(&cp->view.lock, flags);
	del_timer(&cp->timer);
	spin_unlock_irqrestore(&cp->view.lock, flags);
}

static int
con3270_irq(struct con3270 *cp, struct raw3270_request *rq, struct irb *irb)
{
	/* Handle ATTN. Schedule tasklet to read aid. */
	if (irb->scsw.dstat & DEV_STAT_ATTENTION)
		con3270_issue_read(cp);

	if (rq) {
		if (irb->scsw.dstat & DEV_STAT_UNIT_CHECK)
			rq->rc = -EIO;
		else
			/* Normal end. Copy residual count. */
			rq->rescnt = irb->scsw.count;
	}
	return RAW3270_IO_DONE;
}

/* Console view to a 3270 device. */
static struct raw3270_fn con3270_fn = {
	.activate = con3270_activate,
	.deactivate = con3270_deactivate,
	.intv = (void *) con3270_irq
};

static inline void
con3270_cline_add(struct con3270 *cp)
{
	if (!list_empty(&cp->cline->list))
		/* Already added. */
		return;
	list_add_tail(&cp->cline->list, &cp->lines);
	cp->nr_lines++;
	con3270_rebuild_update(cp);
}

static inline void
con3270_cline_insert(struct con3270 *cp, unsigned char c)
{
	cp->cline->string[cp->cline->len++] = 
		cp->view.ascebc[(c < ' ') ? ' ' : c];
	if (list_empty(&cp->cline->update)) {
		list_add_tail(&cp->cline->update, &cp->update);
		cp->update_flags |= CON_UPDATE_LIST;
	}
}

static inline void
con3270_cline_end(struct con3270 *cp)
{
	struct string *s;
	unsigned int size;

	/* Copy cline. */
	size = (cp->cline->len < cp->view.cols - 5) ?
		cp->cline->len + 4 : cp->view.cols;
	s = con3270_alloc_string(cp, size);
	memcpy(s->string, cp->cline->string, cp->cline->len);
	if (s->len < cp->view.cols - 5) {
		s->string[s->len - 4] = TO_RA;
		s->string[s->len - 1] = 0;
	} else {
		while (--size > cp->cline->len)
			s->string[size] = cp->view.ascebc[' '];
	}
	/* Replace cline with allocated line s and reset cline. */
	list_add(&s->list, &cp->cline->list);
	list_del_init(&cp->cline->list);
	if (!list_empty(&cp->cline->update)) {
		list_add(&s->update, &cp->cline->update);
		list_del_init(&cp->cline->update);
	}
	cp->cline->len = 0;
}

/*
 * Write a string to the 3270 console
 */
static void
con3270_write(struct console *co, const char *str, unsigned int count)
{
	struct con3270 *cp;
	unsigned long flags;
	unsigned char c;

	cp = condev;
	spin_lock_irqsave(&cp->view.lock, flags);
	while (count-- > 0) {
		c = *str++;
		if (cp->cline->len == 0)
			con3270_cline_add(cp);
		if (c != '\n')
			con3270_cline_insert(cp, c);
		if (c == '\n' || cp->cline->len >= cp->view.cols)
			con3270_cline_end(cp);
	}
	/* Setup timer to output current console buffer after 1/10 second */
	if (cp->view.dev && !timer_pending(&cp->timer))
		con3270_set_timer(cp, HZ/10);
	spin_unlock_irqrestore(&cp->view.lock,flags);
}

extern struct tty_driver *tty3270_driver;

static struct tty_driver *
con3270_device(struct console *c, int *index)
{
	*index = c->index;
	return tty3270_driver;
}

/*
 * Wait for end of write request.
 */
static void
con3270_wait_write(struct con3270 *cp)
{
	while (!cp->write) {
		raw3270_wait_cons_dev(cp->view.dev);
		barrier();
	}
}

/*
 * panic() calls console_unblank before the system enters a
 * disabled, endless loop.
 */
static void
con3270_unblank(void)
{
	struct con3270 *cp;
	unsigned long flags;

	cp = condev;
	if (!cp->view.dev)
		return;
	spin_lock_irqsave(&cp->view.lock, flags);
	con3270_wait_write(cp);
	cp->nr_up = 0;
	con3270_rebuild_update(cp);
	con3270_update_status(cp);
	while (cp->update_flags != 0) {
		spin_unlock_irqrestore(&cp->view.lock, flags);
		con3270_update(cp);
		spin_lock_irqsave(&cp->view.lock, flags);
		con3270_wait_write(cp);
	}
	spin_unlock_irqrestore(&cp->view.lock, flags);
}

static int __init 
con3270_consetup(struct console *co, char *options)
{
	return 0;
}

/*
 *  The console structure for the 3270 console
 */
static struct console con3270 = {
	.name	 = "tty3270",
	.write	 = con3270_write,
	.device	 = con3270_device,
	.unblank = con3270_unblank,
	.setup	 = con3270_consetup,
	.flags	 = CON_PRINTBUFFER,
};

/*
 * 3270 console initialization code called from console_init().
 * NOTE: This is called before kmalloc is available.
 */
static int __init
con3270_init(void)
{
	struct ccw_device *cdev;
	struct raw3270 *rp;
	void *cbuf;
	int i;

	/* Check if 3270 is to be the console */
	if (!CONSOLE_IS_3270)
		return -ENODEV;

	/* Set the console mode for VM */
	if (MACHINE_IS_VM) {
		cpcmd("TERM CONMODE 3270", NULL, 0, NULL);
		cpcmd("TERM AUTOCR OFF", NULL, 0, NULL);
	}

	cdev = ccw_device_probe_console();
	if (IS_ERR(cdev))
		return -ENODEV;
	rp = raw3270_setup_console(cdev);
	if (IS_ERR(rp))
		return PTR_ERR(rp);

	condev = (struct con3270 *) alloc_bootmem_low(sizeof(struct con3270));
	memset(condev, 0, sizeof(struct con3270));
	condev->view.dev = rp;

	condev->read = raw3270_request_alloc_bootmem(0);
	condev->read->callback = con3270_read_callback;
	condev->read->callback_data = condev;
	condev->write = 
		raw3270_request_alloc_bootmem(CON3270_OUTPUT_BUFFER_SIZE);
	condev->kreset = raw3270_request_alloc_bootmem(1);

	INIT_LIST_HEAD(&condev->lines);
	INIT_LIST_HEAD(&condev->update);
	init_timer(&condev->timer);
	tasklet_init(&condev->readlet, 
		     (void (*)(unsigned long)) con3270_read_tasklet,
		     (unsigned long) condev->read);

	raw3270_add_view(&condev->view, &con3270_fn, 1);

	INIT_LIST_HEAD(&condev->freemem);
	for (i = 0; i < CON3270_STRING_PAGES; i++) {
		cbuf = (void *) alloc_bootmem_low_pages(PAGE_SIZE);
		add_string_memory(&condev->freemem, cbuf, PAGE_SIZE);
	}
	condev->cline = alloc_string(&condev->freemem, condev->view.cols);
	condev->cline->len = 0;
	con3270_create_status(condev);
	condev->input = alloc_string(&condev->freemem, 80);
	register_console(&con3270);
	return 0;
}

console_initcall(con3270_init);
