/*
 * Copyright (C)  2007-2009  Luc Verhaegen <libv@skynet.be>
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License as published by the Free
 * Software Foundation; either version 2 of the License, or (at your option)
 * any later version.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
 * more details.
 *
 * You should have received a copy of the GNU General Public License along with
 * this program; if not, write to the Free Software Foundation, Inc., 51
 * Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
 */

#include <pc80/vga.h>
#include <pc80/vga_io.h>

#include <string.h>
#include "vga.h"

/*
 * pci io enable should've happened before
 */
void
vga_io_init(void)
{
	vga_enable_mask(0x01, 0x01);

	/* cr io is at 0x3D4/0x3D5 */
	vga_misc_mask(0x01, 0x01);

	/* clear cr0-7 protection */
	vga_cr_mask(0x11, 0x00, 0x80);
}

/*
 *
 */
static void
vga_fb_init(void)
{
	vga_sr_write(0x02, 0x03);
	vga_sr_write(0x03, 0x00);
	vga_sr_write(0x04, 0x02); /* access all 256kB */

	vga_gr_write(0x00, 0x00);
	vga_gr_write(0x01, 0x00);
	vga_gr_write(0x02, 0x00);
	vga_gr_write(0x03, 0x00);
	vga_gr_write(0x04, 0x00);
	vga_gr_write(0x05, 0x10);
	vga_gr_write(0x06, 0x0E); /* map at 0xB8000 */
	vga_gr_write(0x07, 0x00);
	vga_gr_write(0x08, 0xFF);

	/* o/e enable: ram enable */
	vga_misc_mask(0x22, 0x22);
}

/*
 *
 */
static void
vga_fb_clear(void)
{
	memset((void *)VGA_FB, 0x00, 0x8000);
}

/*
 *
 */
static void
vga_palette_init(void)
{
	unsigned int i;

	/* set up attribute registers */
	for (i = 0; i < 0x10; i++)
		vga_ar_write(i, i);

	vga_ar_write(0x10, 0x0c);
	vga_ar_write(0x11, 0x00);
	vga_ar_write(0x12, 0x0F);
	vga_ar_write(0x13, 0x08);
	vga_ar_write(0x14, 0x00);

	vga_palette_disable();

	/* load actual palette */
	vga_dac_mask_write(0xFF);

	for (i = 0; i < 0x100; i++) {
		vga_dac_write_address(i);
		vga_dac_data_write(default_vga_palette[i].red);
		vga_dac_data_write(default_vga_palette[i].green);
		vga_dac_data_write(default_vga_palette[i].blue);
	}
}

/*
 *
 */
static void
vga_mode_set(int hdisplay, int hblankstart, int hsyncstart, int hsyncend,
	     int hblankend, int htotal, int vdisplay, int vblankstart,
	     int vsyncstart, int vsyncend, int vblankend, int vtotal,
	     int stride)
{
	/* htotal: 2080 */
	htotal /= 8;
	htotal -= 5;
	vga_cr_write(0x00, htotal);

	/* hdisplay: 2048 */
	hdisplay /= 8;
	hdisplay -= 1;
	vga_cr_write(0x01, hdisplay);

	/* hblankstart: 2048 */
	hblankstart /= 8;
	hblankstart -= 1;
	vga_cr_write(0x02, hblankstart);

	/* hblankend: hblankstart + 512 */
	hblankend /= 8;
	hblankend -= 1;
	vga_cr_mask(0x03, hblankend, 0x1F);
	vga_cr_mask(0x05, hblankend << 2, 0x80);

	/* hsyncstart: 255 * 8: 2040 */
	vga_cr_write(0x04, hsyncstart / 8);

	/* hsyncend: hsyncstart + 255 */
	vga_cr_mask(0x05, hsyncend / 8, 0x1F);

	/* vtotal: 1025 */
	vtotal -= 2;
	vga_cr_write(0x06, vtotal);
	vga_cr_mask(0x07, vtotal >> 8, 0x01);
	vga_cr_mask(0x07, vtotal >> 4, 0x20);

	/* vdisplay: 1024 */
	vdisplay -= 1;
	vga_cr_write(0x12, vdisplay);
	vga_cr_mask(0x07, vdisplay >> 7, 0x02);
	vga_cr_mask(0x07, vdisplay >> 3, 0x40);

	/* vblankstart: 1024 */
	vblankstart -= 1;
	vga_cr_write(0x15, vblankstart);
	vga_cr_mask(0x07, vblankstart >> 5, 0x08);
	vga_cr_mask(0x09, vblankstart >> 4, 0x20);

	/* vblankend: vblankstart + 256 */
	vblankend -= 1;
	vga_cr_write(0x16, vblankend);

	/* vsyncstart: 1023 */
	vga_cr_write(0x10, vsyncstart);
	vga_cr_mask(0x07, vsyncstart >> 6, 0x04);
	vga_cr_mask(0x07, vsyncstart >> 2, 0x80);

	/* vsyncend: vsyncstart + 16 */
	vga_cr_mask(0x11, vsyncend, 0x0F);

	/* stride */
	vga_cr_write(0x13, stride / 8);

	/* line compare */
	vga_cr_write(0x18, 0xFF);
	vga_cr_mask(0x07, 0x10, 0x10);
	vga_cr_mask(0x09, 0x40, 0x40);

	vga_misc_mask(0x44, 0xCC); /* set up clock: 27mhz and h/vsync */

	vga_cr_mask(0x09, 0x00, 0x80); /* disable doublescan */
}

static void
vga_font_8x16_load(void)
{
	unsigned char *p;
	int i, j;
	unsigned char sr2, sr4, gr5, gr6;

#define height 16
#define count 256

	sr2 = vga_sr_read(0x02);
	sr4 = vga_sr_read(0x04);
	gr5 = vga_gr_read(0x05);
	gr6 = vga_gr_read(0x06);

	/* disable odd/even */
	vga_sr_mask(0x04, 0x04, 0x04);
	vga_gr_mask(0x05, 0x00, 0x10);
	vga_gr_mask(0x06, 0x00, 0x02);

	/* plane 2 */
	vga_sr_write(0x02, 0x04);
	p = (unsigned char *) VGA_FB;
	for (i = 0; i < count; i++) {
		for (j = 0; j < 32; j++) {
			if (j < height)
				*p = vga_font_8x16[i][j];
			else
				*p = 0x00;
			p++;
		}
	}

	vga_gr_write(0x06, gr6);
	vga_gr_write(0x05, gr5);
	vga_sr_write(0x04, sr4);
	vga_sr_write(0x02, sr2);

	/* set up font size */
	vga_cr_mask(0x09, 16 - 1, 0x1F);
}

/*
 *
 */
void
vga_cursor_enable(int enable)
{
	if (enable)
		vga_cr_mask(0x0A, 0x00, 0x20);
	else
		vga_cr_mask(0x0A, 0x20, 0x20);
}

/*
 *
 */
void
vga_cursor_reset(void)
{
	vga_cr_write(0x0A, 0x2E);
	vga_cr_write(0x0B, 0x0E);
	vga_cr_write(0x0E, 0x00);
	vga_cr_write(0x0F, 0x00);
}

/*
 *
 */
void
vga_cursor_set(unsigned int line, unsigned int character)
{
	unsigned int offset = (80 * line + character) & 0xFFFF;

	vga_cr_write(0x0A, 0x0E);
	vga_cr_write(0x0B, 0x0E);
	vga_cr_write(0x0E, offset >> 8);
	vga_cr_write(0x0F, offset & 0xFF);
}

/*
 *
 */
void
vga_frame_set(unsigned int line, unsigned int character)
{
	unsigned int offset = (80 * line + character) & 0xFFFF;

	vga_cr_write(0x0C, offset >> 8);
	vga_cr_write(0x0D, offset & 0xFF);
}

/*
 * simply fills a line with the given string.
 */
void
vga_line_write(unsigned int line, const char *string)
{
	unsigned short *p = (unsigned short *) VGA_FB + (80 * line);
	int i, len = strlen(string);

	for (i = 0; i < 80; i++) {
		if (i < len)
			p[i] = 0x0F00 | string[i];
		else
			p[i] = 0x0F00;
	}
}

/*
 * set up everything to get a basic 80x25 textmode.
 */
void
vga_textmode_init(void)
{
	vga_sr_write(0x00, 0x01); /* clear reset */
	vga_sr_write(0x01, 0x00);

	/* set up cr */
	vga_cr_mask(0x03, 0x80, 0xE0);
	vga_cr_mask(0x05, 0x00, 0x60);

	vga_cr_write(0x08, 0x00);

	vga_cr_write(0x14, 0x00); /* */

	vga_cr_write(0x17, 0x23);

	vga_palette_init();

	vga_mode_set(640, 648, 680, 776, 792, 800,
		     400, 407, 412, 414, 442, 449, 320);

	vga_cursor_reset();
	vga_frame_set(0, 0);

	vga_fb_init();
	vga_fb_clear();
	vga_font_8x16_load();

	vga_sr_mask(0x00, 0x02, 0x02); /* take us out of reset */
	vga_cr_mask(0x17, 0x80, 0x80); /* sync! */
}
