/*
 * (C) Copyright 2004
 * Pierre Aubert, Staubli Faverges , <p.aubert@staubli.com>
 * Copyright 2011 Freescale Semiconductor, Inc.
 *
 * SPDX-License-Identifier:	GPL-2.0+
 */

/************************************************************************
  Get Parameters for the video mode:
  The default video mode can be defined in CONFIG_SYS_DEFAULT_VIDEO_MODE.
  If undefined, default video mode is set to 0x301
  Parameters can be set via the variable "videomode" in the environment.
  2 diferent ways are possible:
  "videomode=301"   - 301 is a hexadecimal number describing the VESA
		      mode. Following modes are implemented:

		      Colors	640x480 800x600 1024x768 1152x864 1280x1024
		     --------+---------------------------------------------
		      8 bits |	0x301	0x303	 0x305	  0x161	    0x307
		     15 bits |	0x310	0x313	 0x316	  0x162	    0x319
		     16 bits |	0x311	0x314	 0x317	  0x163	    0x31A
		     24 bits |	0x312	0x315	 0x318	    ?	    0x31B
		     --------+---------------------------------------------
  "videomode=bootargs"
		   - the parameters are parsed from the bootargs.
		      The format is "NAME:VALUE,NAME:VALUE" etc.
		      Ex.:
		      "bootargs=video=ctfb:x:800,y:600,depth:16,pclk:25000"
		      Parameters not included in the list will be taken from
		      the default mode, which is one of the following:
		      mode:0  640x480x24
		      mode:1  800x600x16
		      mode:2  1024x768x8
		      mode:3  960x720x24
		      mode:4  1152x864x16
		      mode:5  1280x1024x8

		      if "mode" is not provided within the parameter list,
		      mode:0 is assumed.
		      Following parameters are supported:
		      x	      xres = visible resolution horizontal
		      y	      yres = visible resolution vertical
		      pclk    pixelclocks in pico sec
		      le      left_marging time from sync to picture in pixelclocks
		      ri      right_marging time from picture to sync in pixelclocks
		      up      upper_margin time from sync to picture
		      lo      lower_margin
		      hs      hsync_len length of horizontal sync
		      vs      vsync_len length of vertical sync
		      sync    see FB_SYNC_*
		      vmode   see FB_VMODE_*
		      depth   Color depth in bits per pixel
		      All other parameters in the variable bootargs are ignored.
		      It is also possible to set the parameters direct in the
		      variable "videomode", or in another variable i.e.
		      "myvideo" and setting the variable "videomode=myvideo"..
****************************************************************************/

#include <common.h>
#include <edid.h>
#include <errno.h>
#include <linux/ctype.h>

#include "videomodes.h"

const struct ctfb_vesa_modes vesa_modes[VESA_MODES_COUNT] = {
	{0x301, RES_MODE_640x480, 8},
	{0x310, RES_MODE_640x480, 15},
	{0x311, RES_MODE_640x480, 16},
	{0x312, RES_MODE_640x480, 24},
	{0x303, RES_MODE_800x600, 8},
	{0x313, RES_MODE_800x600, 15},
	{0x314, RES_MODE_800x600, 16},
	{0x315, RES_MODE_800x600, 24},
	{0x305, RES_MODE_1024x768, 8},
	{0x316, RES_MODE_1024x768, 15},
	{0x317, RES_MODE_1024x768, 16},
	{0x318, RES_MODE_1024x768, 24},
	{0x161, RES_MODE_1152x864, 8},
	{0x162, RES_MODE_1152x864, 15},
	{0x163, RES_MODE_1152x864, 16},
	{0x307, RES_MODE_1280x1024, 8},
	{0x319, RES_MODE_1280x1024, 15},
	{0x31A, RES_MODE_1280x1024, 16},
	{0x31B, RES_MODE_1280x1024, 24},
};
const struct ctfb_res_modes res_mode_init[RES_MODES_COUNT] = {
	/*  x     y  hz  pixclk ps/kHz   le   ri  up  lo   hs vs  s  vmode */
#ifndef CONFIG_VIDEO_STD_TIMINGS
	{ 640,  480, 60, 39721,  25180,  40,  24, 32, 11,  96, 2, 0, FB_VMODE_NONINTERLACED},
	{ 800,  600, 60, 27778,  36000,  64,  24, 22,  1,  72, 2, 0, FB_VMODE_NONINTERLACED},
	{1024,  768, 60, 15384,  65000, 168,   8, 29,  3, 144, 4, 0, FB_VMODE_NONINTERLACED},
	{ 960,  720, 80, 13100,  76335, 160,  40, 32,  8,  80, 4, 0, FB_VMODE_NONINTERLACED},
	{1152,  864, 60, 12004,  83300, 200,  64, 32, 16,  80, 4, 0, FB_VMODE_NONINTERLACED},
	{1280, 1024, 60,  9090, 110000, 200,  48, 26,  1, 184, 3, 0, FB_VMODE_NONINTERLACED},
#else
	{ 640,  480, 60, 39683,  25200,  48,  16, 33, 10,  96, 2, 0, FB_VMODE_NONINTERLACED},
	{ 800,  600, 60, 25000,  40000,  88,  40, 23,  1, 128, 4, FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED},
	{1024,  768, 60, 15384,  65000, 160,  24, 29,  3, 136, 6, 0, FB_VMODE_NONINTERLACED},
	{ 960,  720, 75, 13468,  74250, 176,  72, 27,  1, 112, 2, 0, FB_VMODE_NONINTERLACED},
	{1152,  864, 75,  9259, 108000, 256,  64, 32,  1, 128, 3, FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED},
	{1280, 1024, 60,  9259, 108000, 248,  48, 38,  1, 112, 3, FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED},
#endif
	{1280,  720, 60, 13468,  74250, 220, 110, 20,  5,  40, 5, FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED},
	{1360,  768, 60, 11696,  85500, 256,  64, 17,  3, 112, 7, 0, FB_VMODE_NONINTERLACED},
	{1920, 1080, 60,  6734, 148500, 148,  88, 36,  4,  44, 5, FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT, FB_VMODE_NONINTERLACED},
	{1920, 1200, 60,  6494, 154000,  80,  48, 26,  3,  32, 6, FB_SYNC_HOR_HIGH_ACT, FB_VMODE_NONINTERLACED},
};

/************************************************************************
 * Get Parameters for the video mode:
 */
/*********************************************************************
 * returns the length to the next seperator
 */
static int
video_get_param_len(const char *start, char sep)
{
	int i = 0;
	while ((*start != 0) && (*start != sep)) {
		start++;
		i++;
	}
	return i;
}

static int
video_search_param (char *start, char *param)
{
	int len, totallen, i;
	char *p = start;
	len = strlen (param);
	totallen = len + strlen (start);
	for (i = 0; i < totallen; i++) {
		if (strncmp (p++, param, len) == 0)
			return (i);
	}
	return -1;
}

/***************************************************************
 * Get parameter via the environment as it is done for the
 * linux kernel i.e:
 * video=ctfb:x:800,xv:1280,y:600,yv:1024,depth:16,mode:0,pclk:25000,
 *	 le:56,ri:48,up:26,lo:5,hs:152,vs:2,sync:0,vmode:0,accel:0
 *
 * penv is a pointer to the environment, containing the string, or the name of
 * another environment variable. It could even be the term "bootargs"
 */

#define GET_OPTION(name,var)				\
	if(strncmp(p,name,strlen(name))==0) {		\
		val_s=p+strlen(name);			\
		var=simple_strtoul(val_s, NULL, 10);	\
	}

int video_get_params (struct ctfb_res_modes *pPar, char *penv)
{
	char *p, *s, *val_s;
	int i = 0;
	int bpp;
	int mode;

	/* first search for the environment containing the real param string */
	s = penv;

	if ((p = getenv (s)) != NULL)
		s = p;

	/*
	 * in case of the bootargs line, we have to start
	 * after "video=ctfb:"
	 */
	i = video_search_param (s, "video=ctfb:");
	if (i >= 0) {
		s += i;
		s += strlen ("video=ctfb:");
	}
	/* search for mode as a default value */
	p = s;
	mode = 0;		/* default */

	while ((i = video_get_param_len (p, ',')) != 0) {
		GET_OPTION ("mode:", mode)
			p += i;
		if (*p != 0)
			p++;	/* skip ',' */
	}

	if (mode >= RES_MODES_COUNT)
		mode = 0;

	*pPar = res_mode_init[mode];	/* copy default values */
	bpp = 24 - ((mode % 3) * 8);
	p = s;			/* restart */

	while ((i = video_get_param_len (p, ',')) != 0) {
		GET_OPTION ("x:", pPar->xres)
			GET_OPTION ("y:", pPar->yres)
			GET_OPTION ("refresh:", pPar->refresh)
			GET_OPTION ("le:", pPar->left_margin)
			GET_OPTION ("ri:", pPar->right_margin)
			GET_OPTION ("up:", pPar->upper_margin)
			GET_OPTION ("lo:", pPar->lower_margin)
			GET_OPTION ("hs:", pPar->hsync_len)
			GET_OPTION ("vs:", pPar->vsync_len)
			GET_OPTION ("sync:", pPar->sync)
			GET_OPTION ("vmode:", pPar->vmode)
			GET_OPTION ("pclk:", pPar->pixclock)
			GET_OPTION ("pclk_khz:", pPar->pixclock_khz)
			GET_OPTION ("depth:", bpp)
			p += i;
		if (*p != 0)
			p++;	/* skip ',' */
	}
	return bpp;
}

/*
 * Parse the 'video-mode' environment variable
 *
 * Example: "video-mode=fslfb:1280x1024-32@60,monitor=dvi".  See
 * doc/README.video for more information on how to set the variable.
 *
 * @xres: returned value of X-resolution
 * @yres: returned value of Y-resolution
 * @depth: returned value of color depth
 * @freq: returned value of monitor frequency
 * @options: pointer to any remaining options, or NULL
 *
 * Returns 1 if valid values were found, 0 otherwise
 */
int video_get_video_mode(unsigned int *xres, unsigned int *yres,
	unsigned int *depth, unsigned int *freq, const char **options)
{
	char *p = getenv("video-mode");
	if (!p)
		return 0;

	/* Skip over the driver name, which we don't care about. */
	p = strchr(p, ':');
	if (!p)
		return 0;

	/* Get the X-resolution*/
	while (*p && !isdigit(*p))
		p++;
	*xres = simple_strtoul(p, &p, 10);
	if (!*xres)
		return 0;

	/* Get the Y-resolution */
	while (*p && !isdigit(*p))
		p++;
	*yres = simple_strtoul(p, &p, 10);
	if (!*yres)
		return 0;

	/* Get the depth */
	while (*p && !isdigit(*p))
		p++;
	*depth = simple_strtoul(p, &p, 10);
	if (!*depth)
		return 0;

	/* Get the frequency */
	while (*p && !isdigit(*p))
		p++;
	*freq = simple_strtoul(p, &p, 10);
	if (!*freq)
		return 0;

	/* Find the extra options, if any */
	p = strchr(p, ',');
	*options = p ? p + 1 : NULL;

	return 1;
}

/*
 * Parse the 'video-mode' environment variable using video_get_video_mode()
 * and lookup the matching ctfb_res_modes in res_mode_init.
 *
 * @default_mode: RES_MODE_##x## define for the mode to store in mode_ret
 *   when 'video-mode' is not set or does not contain a valid mode
 * @default_depth: depth to set when 'video-mode' is not set
 * @mode_ret: pointer where the mode will be stored
 * @depth_ret: pointer where the depth will be stored
 * @options: pointer to any remaining options, or NULL
 */
void video_get_ctfb_res_modes(int default_mode, unsigned int default_depth,
			      const struct ctfb_res_modes **mode_ret,
			      unsigned int *depth_ret,
			      const char **options)
{
	unsigned int i, xres, yres, depth, refresh;

	*mode_ret = &res_mode_init[default_mode];
	*depth_ret = default_depth;
	*options = NULL;

	if (!video_get_video_mode(&xres, &yres, &depth, &refresh, options))
		return;

	for (i = 0; i < RES_MODES_COUNT; i++) {
		if (res_mode_init[i].xres == xres &&
		    res_mode_init[i].yres == yres &&
		    res_mode_init[i].refresh == refresh) {
			*mode_ret = &res_mode_init[i];
			*depth_ret = depth;
			return;
		}
	}

	printf("video-mode %dx%d-%d@%d not available, falling back to %dx%d-%d@%d\n",
	       xres, yres, depth, refresh, (*mode_ret)->xres,
	       (*mode_ret)->yres, *depth_ret, (*mode_ret)->refresh);
}

/*
 * Find the named string option within the ',' separated options string, and
 * store its value in dest.
 *
 * @options: ',' separated options string
 * @name: name of the option to look for
 * @dest: destination buffer to store the value of the option in
 * @dest_len: length of dest
 * @def: value to store in dest if the option is not present in options
 */
void video_get_option_string(const char *options, const char *name,
			     char *dest, int dest_len, const char *def)
{
	const char *p = options;
	const int name_len = strlen(name);
	int i, len;

	while (p && (i = video_get_param_len(p, ',')) != 0) {
		if (strncmp(p, name, name_len) == 0 && p[name_len] == '=') {
			len = i - (name_len + 1);
			if (len >= dest_len)
				len = dest_len - 1;
			memcpy(dest, &p[name_len + 1], len);
			dest[len] = 0;
			return;
		}
		p += i;
		if (*p != 0)
			p++;	/* skip ',' */
	}
	strcpy(dest, def);
}

/*
 * Find the named integer option within the ',' separated options string, and
 * return its value.
 *
 * @options: ',' separated options string
 * @name: name of the option to look for
 * @def: value to return if the option is not present in options
 */
int video_get_option_int(const char *options, const char *name, int def)
{
	const char *p = options;
	const int name_len = strlen(name);
	int i;

	while (p && (i = video_get_param_len(p, ',')) != 0) {
		if (strncmp(p, name, name_len) == 0 && p[name_len] == '=')
			return simple_strtoul(&p[name_len + 1], NULL, 10);

		p += i;
		if (*p != 0)
			p++;	/* skip ',' */
	}
	return def;
}

/**
 * Convert an EDID detailed timing to a struct ctfb_res_modes
 *
 * @param t		The EDID detailed timing to be converted
 * @param mode		Returns the converted timing
 *
 * @return 0 on success, or a negative errno on error
 */
int video_edid_dtd_to_ctfb_res_modes(struct edid_detailed_timing *t,
				     struct ctfb_res_modes *mode)
{
	int margin, h_total, v_total;

	/* Check all timings are non 0 */
	if (EDID_DETAILED_TIMING_PIXEL_CLOCK(*t) == 0 ||
	    EDID_DETAILED_TIMING_HORIZONTAL_ACTIVE(*t) == 0 ||
	    EDID_DETAILED_TIMING_HORIZONTAL_BLANKING(*t) == 0 ||
	    EDID_DETAILED_TIMING_VERTICAL_ACTIVE(*t) == 0 ||
	    EDID_DETAILED_TIMING_VERTICAL_BLANKING(*t) == 0 ||
	    EDID_DETAILED_TIMING_HSYNC_OFFSET(*t) == 0 ||
	    EDID_DETAILED_TIMING_HSYNC_PULSE_WIDTH(*t) == 0 ||
	    EDID_DETAILED_TIMING_VSYNC_OFFSET(*t) == 0 ||
	    EDID_DETAILED_TIMING_VSYNC_PULSE_WIDTH(*t) == 0 ||
	    /* 3d formats are not supported*/
	    EDID_DETAILED_TIMING_FLAG_STEREO(*t) != 0)
		return -EINVAL;

	mode->xres = EDID_DETAILED_TIMING_HORIZONTAL_ACTIVE(*t);
	mode->yres = EDID_DETAILED_TIMING_VERTICAL_ACTIVE(*t);

	h_total = mode->xres + EDID_DETAILED_TIMING_HORIZONTAL_BLANKING(*t);
	v_total = mode->yres + EDID_DETAILED_TIMING_VERTICAL_BLANKING(*t);
	mode->refresh = EDID_DETAILED_TIMING_PIXEL_CLOCK(*t) /
			(h_total * v_total);

	mode->pixclock_khz = EDID_DETAILED_TIMING_PIXEL_CLOCK(*t) / 1000;
	mode->pixclock = 1000000000L / mode->pixclock_khz;

	mode->right_margin = EDID_DETAILED_TIMING_HSYNC_OFFSET(*t);
	mode->hsync_len = EDID_DETAILED_TIMING_HSYNC_PULSE_WIDTH(*t);
	margin = EDID_DETAILED_TIMING_HORIZONTAL_BLANKING(*t) -
			(mode->right_margin + mode->hsync_len);
	if (margin <= 0)
		return -EINVAL;

	mode->left_margin = margin;

	mode->lower_margin = EDID_DETAILED_TIMING_VSYNC_OFFSET(*t);
	mode->vsync_len = EDID_DETAILED_TIMING_VSYNC_PULSE_WIDTH(*t);
	margin = EDID_DETAILED_TIMING_VERTICAL_BLANKING(*t) -
			(mode->lower_margin + mode->vsync_len);
	if (margin <= 0)
		return -EINVAL;

	mode->upper_margin = margin;

	mode->sync = 0;
	if (EDID_DETAILED_TIMING_FLAG_HSYNC_POLARITY(*t))
		mode->sync |= FB_SYNC_HOR_HIGH_ACT;
	if (EDID_DETAILED_TIMING_FLAG_VSYNC_POLARITY(*t))
		mode->sync |= FB_SYNC_VERT_HIGH_ACT;

	if (EDID_DETAILED_TIMING_FLAG_INTERLACED(*t))
		mode->vmode = FB_VMODE_INTERLACED;
	else
		mode->vmode = FB_VMODE_NONINTERLACED;

	return 0;
}
