/*
 * This file is part of the flashrom project.
 *
 * Copyright (C) 2009 Uwe Hermann <uwe@hermann-uwe.de>
 * Copyright (C) 2009 Carl-Daniel Hailfinger
 *
 * 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.
 */

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <time.h>
#include "flash.h"
#include "flashchips.h"
#include "programmer.h"

static const char wiki_header[] = "= Supported devices =\n\n\
<div style=\"margin-top:0.5em; padding:0.5em 0.5em 0.5em 0.5em; \
background-color:#eeeeee; text-align:left; border:1px solid #aabbcc;\">\
<small>\n\
'''Last update:''' %s (generated by flashprog %s)<br />\n\
The tables below are generated from flashprog's source by copying the output of '''flashprog -z'''.<br /><br />\n\
A short explanation of the cells representing the support state follows:<br />\n\
{| border=\"0\" valign=\"top\"\n\
! style=\"text-align:left;\" |\n\
! style=\"text-align:left;\" |\n\
|-\n\
|{{OK}}\n\
| The feature was '''tested and should work''' in general unless there is a bug in flashprog or another component in \
the system prohibits some functionality.\n\
|-\n\
|{{Dep}}\n\
| '''Configuration-dependent'''. The feature was tested and should work in general but there are common \
configurations that drastically limit flashprog's capabilities or make it completely stop working.\n\
|-\n\
|{{?3}}\n\
| The feature is '''untested''' but believed to be working.\n\
|-\n\
|{{NA}}\n\
| The feature is '''not applicable''' in this configuration (e.g. write operations on ROM chips).\n\
|-\n\
|{{No}}\n\
| The feature is '''known to not work'''. Don't bother testing (nor reporting. Patches welcome! ;).\n\
|}\n\
</small></div>\n";

static const char th_start[] = "| valign=\"top\"|\n\n\
{| border=\"0\" style=\"font-size: smaller\" valign=\"top\"\n\
|- bgcolor=\"#6699dd\"\n";

#if CONFIG_INTERNAL == 1
static const char chipset_th[] = "\
! align=\"left\" | Vendor\n\
! align=\"left\" | Southbridge\n\
! align=\"center\" | PCI IDs\n\
! align=\"center\" | Status\n\n";

static const char board_th[] = "\
! align=\"left\" | Vendor\n\
! align=\"left\" | Mainboard\n\
! align=\"left\" | Required option\n\
! align=\"center\" | Status\n\n";

static const char board_intro[] = "\
\n== Supported mainboards ==\n\n\
In general, it is very likely that flashprog works out of the box even if your \
mainboard is not listed below.\n\nThis is a list of mainboards where we have \
verified that they either do or do not need any special initialization to \
make flashprog work (given flashprog supports the respective chipset and flash \
chip), or that they do not yet work at all. If they do not work, support may \
or may not be added later.\n\n\
Mainboards (or individual revisions) which don't appear in the list may or may \
not work (we don't know, someone has to give it a try). Please report any \
further verified mainboards on the [[Contact#Mailing_List|mailing list]].\n";
#endif

static const char chip_th[] = "\
! align=\"left\" | Vendor\n\
! align=\"left\" | Device\n\
! align=\"center\" | Size [kB]\n\
! align=\"center\" | Type\n\
! align=\"center\" colspan=\"4\" | Status\n\
! align=\"center\" colspan=\"2\" | Voltage [V]\n\n\
|- bgcolor=\"#6699ff\"\n| colspan=\"4\" | &nbsp;\n\
| Probe\n| Read\n| Erase\n| Write\n\
| align=\"center\" | Min\n| align=\"center\" | Max\n\n";

static const char chip_intro[] = "\
\n== Supported flash chips ==\n\n\
The list below contains all chips that have some kind of explicit support added to flashprog and their last \
known test status. Newer SPI flash chips might work even without explicit support if they implement SFDP ([\
http://www.jedec.org/standards-documents/docs/jesd216 Serial Flash Discoverable Parameters - JESD216]). \
Flashprog will detect this automatically and inform you about it.\n\n\
The names used below are designed to be as concise as possible and hence contain only the characters \
describing properties that are relevant to flashprog. Irrelevant characters specify attributes flashprog can not \
use or even detect by itself (e.g. the physical package) and have no effect on flashprog's operation. They are \
replaced by dots ('.') functioning as wildcards (like in Regular Expressions) or are completely omitted at the \
end of a name.\n";

static const char programmer_th[] = "\
! align=\"left\" | Programmer\n\
! align=\"left\" | Vendor\n\
! align=\"left\" | Device\n\
! align=\"center\" | IDs\n\
! align=\"center\" | Status\n\n";

/* The output of this module relies on MediaWiki templates to select special formatting styles for table cells
 * reflecting the test status of the respective hardware. This functions returns the correct template name for
 * the supplied enum flashprog_test_state. */
static const char *test_state_to_template(enum flashprog_test_state test_state)
{
	switch (test_state) {
	case OK: return "OK";
	case BAD: return "No";
	case NA: return "NA";
	case DEP: return "Dep";
	case NT:
	default: return "?3";
	}
}

#if CONFIG_INTERNAL == 1
static const char laptop_intro[] = "\n== Supported mobile devices (laptops, tablets etc.) ==\n\n\
In general, flashing mobile devices is more difficult because they\n\n\
* often use the flash chip for stuff besides the BIOS,\n\
* often have special protection stuff which has to be handled by flashprog,\n\
* often use flash translation circuits which need drivers in flashprog.\n\n\
<div style=\"margin-top:0.5em; padding:0.5em 0.5em 0.5em 0.5em; \
background-color:#ff6666; align:right; border:1px solid #000000;\">\n\
'''IMPORTANT:''' At this point we recommend to '''not''' use flashprog on \
untested mobile devices unless you have a means to recover from a flashing that goes \
wrong (a working backup flash chip and/or good soldering skills).\n</div>\n";

static void print_supported_chipsets_wiki(int cols)
{
	int i;
	unsigned int lines_per_col;
	const struct penable *e;
	int enablescount = 0, color = 1;

	for (e = chipset_enables; e->vendor_name != NULL; e++)
		enablescount++;

	/* +1 to force the resulting number of columns to be < cols */
	lines_per_col = enablescount / cols + ((enablescount%cols) > 0 ? 1 : 0);

	printf("\n== Supported chipsets ==\n\nTotal amount of supported chipsets: '''%d'''\n\n"
	       "{| border=\"0\" valign=\"top\"\n", enablescount);

	e = chipset_enables;
	for (i = 0; e[i].vendor_name != NULL; i++) {
		if ((i % lines_per_col) == 0)
			printf("%s%s", th_start, chipset_th);

		/* Alternate colors if the vendor changes. */
		if (i > 0 && strcmp(e[i].vendor_name, e[i - 1].vendor_name))
			color = !color;

		printf("|- bgcolor=\"#%s\"\n| %s || %s "
		       "|| %04x:%04x || {{%s}}\n", (color) ? "eeeeee" : "dddddd",
		       e[i].vendor_name, e[i].device_name,
		       e[i].vendor_id, e[i].device_id,
		       test_state_to_template(e[i].status));

		if (((i % lines_per_col) + 1) == lines_per_col)
			printf("\n|}\n\n");
	}

	/* end inner table if it did not fill the last column fully */
	if (((i % lines_per_col)) > 0)
		printf("\n|}\n\n");
	printf("\n\n|}\n");
}

static void print_supported_boards_wiki_helper(const char *devicetype, int cols, const struct board_info boards[])
{
	int i, k;
	unsigned int boardcount, lines_per_col;
	unsigned int boardcount_good = 0, boardcount_bad = 0, boardcount_nt = 0;
	int num_notes = 0, color = 1;
	char *notes = calloc(1, 1);
	char tmp[900 + 1];
	const struct board_match *b = board_matches;

	for (i = 0; boards[i].vendor != NULL; i++) {
		if (boards[i].working == OK)
			boardcount_good++;
		else if (boards[i].working == NT)
			boardcount_nt++;
		else
			boardcount_bad++;
	}
	boardcount = boardcount_good + boardcount_nt + boardcount_bad;

	/* +1 to force the resulting number of columns to be < cols */
	lines_per_col = boardcount / cols + ((boardcount%cols) > 0 ? 1 : 0);

	printf("\n\nTotal amount of known good %s: '''%d'''; "
	       "Untested (e.g. user vanished before testing new code): '''%d'''; "
	       "Not yet supported (i.e. known-bad): '''%d'''.\n\n"
	       "{| border=\"0\" valign=\"top\"\n", devicetype, boardcount_good, boardcount_nt, boardcount_bad);

	for (i = 0; boards[i].vendor != NULL; i++) {
		if ((i % lines_per_col) == 0)
			printf("%s%s", th_start, board_th);

		/* Alternate colors if the vendor changes. */
		if (i > 0 && strcmp(boards[i].vendor, boards[i - 1].vendor))
			color = !color;

		k = 0;
		while ((b[k].vendor_name != NULL) &&
			(strcmp(b[k].vendor_name, boards[i].vendor) ||
			 strcmp(b[k].board_name, boards[i].name))) {
			k++;
		}

		printf("|- bgcolor=\"#%s\"\n| %s || %s%s %s%s || %s%s%s%s "
		       "|| {{%s}}", (color) ? "eeeeee" : "dddddd",
		       boards[i].vendor,
		       boards[i].url ? "[" : "",
		       boards[i].url ? boards[i].url : "",
		       boards[i].name,
		       boards[i].url ? "]" : "",
		       b[k].lb_vendor ? "-p internal:mainboard=" : "&mdash;",
		       b[k].lb_vendor ? b[k].lb_vendor : "",
		       b[k].lb_vendor ? ":" : "",
		       b[k].lb_vendor ? b[k].lb_part : "",
		       test_state_to_template(boards[i].working));

		if (boards[i].note) {
			num_notes++;
			printf(" <span id=\"%s_ref%d\"><sup>[[#%s_note%d|%d]]</sup></span>\n",
			       devicetype, num_notes, devicetype, num_notes, num_notes);
			int ret = snprintf(tmp, sizeof(tmp),
					   "<span id=\"%s_note%d\">%d. [[#%s_ref%d|&#x2191;]]</span>"
					   " <nowiki>%s</nowiki><br />\n", devicetype, num_notes, num_notes,
					   devicetype, num_notes, boards[i].note);
			if (ret < 0 || (unsigned int)ret >= sizeof(tmp)) {
				fprintf(stderr, "Footnote text #%d of %s truncated (ret=%d, sizeof(tmp)=%zu)\n",
					num_notes, devicetype, ret, sizeof(tmp));
			}
			notes = strcat_realloc(notes, tmp);
		} else {
			printf("\n");
		}

		if (((i % lines_per_col) + 1) == lines_per_col)
			printf("\n|}\n\n");
	}

	/* end inner table if it did not fill the last column fully */
	if (((i % lines_per_col)) > 0)
		printf("\n|}\n\n");
	printf("|}\n");

	if (num_notes > 0)
		printf("\n<small>\n%s</small>\n", notes);
	free(notes);
}

static void print_supported_boards_wiki(void)
{
	printf("%s", board_intro);
	print_supported_boards_wiki_helper("mainboards", 2, boards_known);

	printf("%s", laptop_intro);
	print_supported_boards_wiki_helper("mobile devices", 1, laptops_known);
}
#endif

static void print_supported_chips_wiki(int cols)
{
	unsigned int lines_per_col;
	char *s;
	char vmax[6];
	char vmin[6];
	const struct flashchip *f, *old = NULL;
	int i = 0, c = 1, chipcount = 0;

	for (f = flashchips; f->name != NULL; f++) {
		/* Don't count generic entries. */
		if (!strncmp(f->vendor, "Unknown", 7) ||
		    !strncmp(f->vendor, "Programmer", 10) ||
		    !strncmp(f->name, "unknown", 7))
			continue;
		chipcount++;
	}

	/* +1 to force the resulting number of columns to be < cols */
	lines_per_col = chipcount / cols + ((chipcount%cols) > 0 ? 1 : 0);

	printf("%s", chip_intro);
	printf("\nTotal amount of supported chips: '''%d'''\n\n"
	       "{| border=\"0\" valign=\"top\"\n", chipcount);

	for (f = flashchips; f->name != NULL; f++) {
		/* Don't print generic entries. */
		if (!strncmp(f->vendor, "Unknown", 7) ||
		    !strncmp(f->vendor, "Programmer", 10) ||
		    !strncmp(f->name, "unknown", 7))
			continue;

		if ((i % lines_per_col) == 0)
			printf("%s%s", th_start, chip_th);

		/* Alternate colors if the vendor changes. */
		if (old != NULL && strcmp(old->vendor, f->vendor))
			c = !c;

		old = f;
		s = flashbuses_to_text(f->bustype);
		sprintf(vmin, "%0.03f", f->voltage.min / (double)1000);
		sprintf(vmax, "%0.03f", f->voltage.max / (double)1000);
		printf("|- bgcolor=\"#%s\"\n| %s || %s || align=\"right\" | %d "
		       "|| %s || {{%s}} || {{%s}} || {{%s}} || {{%s}}"
		       "|| %s || %s\n",
		       (c == 1) ? "eeeeee" : "dddddd", f->vendor, f->name,
		       f->total_size, s,
		       test_state_to_template(f->tested.probe),
		       test_state_to_template(f->tested.read),
		       test_state_to_template(f->tested.erase),
		       test_state_to_template(f->tested.write),
		       f->voltage.min ? vmin : "?",
		       f->voltage.max ? vmax : "?");
		free(s);

		if (((i % lines_per_col) + 1) == lines_per_col)
			printf("\n|}\n\n");
		i++;
	}
	/* end inner table if it did not fill the last column fully */
	if (((i % lines_per_col)) > 0)
		printf("\n|}\n\n");
	printf("|}\n\n");
}

/* Following functions are not needed when no PCI/USB programmers are compiled in,
 * but since print_wiki code has no size constraints we include it unconditionally. */
static int count_supported_devs_wiki(const struct dev_entry *devs)
{
	unsigned int count = 0;
	unsigned int i = 0;
	for (i = 0; devs[i].vendor_id != 0; i++)
		count++;
	return count;
}

static void print_supported_devs_wiki_helper(const struct programmer_entry *const prog)
{
	int i = 0;
	static int c = 0;
	const struct dev_entry *devs = prog->devs.dev;
	const unsigned int count = count_supported_devs_wiki(devs);

	/* Alternate colors if the vendor changes. */
	c = !c;

	for (i = 0; devs[i].vendor_id != 0; i++) {
		printf("|- bgcolor=\"#%s\"\n", (c) ? "eeeeee" : "dddddd");
		if (i == 0)
			printf("| rowspan=\"%u\" | %s |", count, prog->name);
		printf("| %s || %s || %04x:%04x || {{%s}}\n", devs[i].vendor_name, devs[i].device_name,
		       devs[i].vendor_id, devs[i].device_id, test_state_to_template(devs[i].status));
	}
}

static void print_supported_devs_wiki()
{
	unsigned int pci_count = 0;
	unsigned int usb_count = 0;
	unsigned int i;

	for (i = 0; i < programmer_table_size; i++) {
		const struct programmer_entry *const prog = programmer_table[i];
		switch (prog->type) {
		case USB:
			usb_count += count_supported_devs_wiki(prog->devs.dev);
			break;
		case PCI:
			pci_count += count_supported_devs_wiki(prog->devs.dev);
			break;
		case OTHER:
		default:
			break;
		}
	}

	printf("\n== PCI Devices ==\n\n"
	       "Total amount of supported PCI devices flashprog can use as a programmer: '''%d'''\n\n"
	       "{%s%s", pci_count, th_start, programmer_th);

	for (i = 0; i < programmer_table_size; i++) {
		const struct programmer_entry *const prog = programmer_table[i];
		if (prog->type == PCI) {
			print_supported_devs_wiki_helper(prog);
		}
	}
	printf("\n|}\n\n|}\n");

	printf("\n== USB Devices ==\n\n"
	       "Total amount of supported USB devices flashprog can use as a programmer: '''%d'''\n\n"
	       "{%s%s", usb_count, th_start, programmer_th);

	for (i = 0; i < programmer_table_size; i++) {
		const struct programmer_entry *const prog = programmer_table[i];
		if (prog->type == USB) {
			print_supported_devs_wiki_helper(prog);
		}
	}
	printf("\n|}\n\n|}\n");

	printf("\n== Other programmers ==\n\n"
	       "{%s", th_start);
	printf("! align=\"left\" | Programmer\n"
	       "! align=\"left\" | Note\n\n");

	for (i = 0; i < programmer_table_size; i++) {
		static int c = 0;
		const struct programmer_entry *const prog = programmer_table[i];
		if (prog->type == OTHER && prog->devs.note != NULL) {
			c = !c;
			printf("|- bgcolor=\"#%s\"\n", (c) ? "eeeeee" : "dddddd");
			printf("| %s || %s", prog->name, prog->devs.note);
		}
	}
	printf("\n|}\n\n|}\n");
}

void print_supported_wiki(void)
{
	time_t t = time(NULL);
	char buf[sizeof("1986-02-28T12:37:42Z")];
	strftime(buf, sizeof(buf), "%Y-%m-%dT%H:%M:%SZ", gmtime(&t));

	printf(wiki_header, buf, flashprog_version);
	print_supported_chips_wiki(2);
#if CONFIG_INTERNAL == 1
	print_supported_chipsets_wiki(3);
	print_supported_boards_wiki();
#endif
	print_supported_devs_wiki();
}
