/*
 * Copyright (C) 2017 Jernej Skrabec <jernej.skrabec@siol.net>
 *
 * Coefficients are taken from BSP driver, which is:
 * Copyright (C) 2014-2015 Allwinner
 *
 * This file is licensed under the terms of the GNU General Public
 * License version 2.  This program is licensed "as is" without any
 * warranty of any kind, whether express or implied.
 */

#include "sun8i_ui_scaler.h"
#include "sun8i_vi_scaler.h"

static const u32 lan2coefftab16[240] = {
	0x00004000, 0x00033ffe, 0x00063efc, 0x000a3bfb,
	0xff0f37fb, 0xfe1433fb, 0xfd192ffb, 0xfd1f29fb,
	0xfc2424fc, 0xfb291ffd, 0xfb2f19fd, 0xfb3314fe,
	0xfb370fff, 0xfb3b0a00, 0xfc3e0600, 0xfe3f0300,

	0xff053804, 0xff083801, 0xff0a3700, 0xff0e34ff,
	0xff1232fd, 0xfe162ffd, 0xfd1b2cfc, 0xfd1f28fc,
	0xfd2323fd, 0xfc281ffd, 0xfc2c1bfd, 0xfd2f16fe,
	0xfd3212ff, 0xff340eff, 0x00360a00, 0x02370700,

	0xff083207, 0xff0a3205, 0xff0d3103, 0xfe113001,
	0xfe142e00, 0xfe182bff, 0xfe1b29fe, 0xfe1f25fe,
	0xfe2222fe, 0xfe251ffe, 0xfe291bfe, 0xff2b18fe,
	0x002e14fe, 0x013010ff, 0x03310dff, 0x05310a00,

	0xff0a2e09, 0xff0c2e07, 0xff0f2d05, 0xff122c03,
	0xfe152b02, 0xfe182901, 0xfe1b2700, 0xff1e24ff,
	0xff2121ff, 0xff241eff, 0x00261bff, 0x012818ff,
	0x022a15ff, 0x032c12ff, 0x052d0fff, 0x072d0c00,

	0xff0c2a0b, 0xff0e2a09, 0xff102a07, 0xff132905,
	0xff162803, 0xff182702, 0xff1b2501, 0xff1e2300,
	0x00202000, 0x01221d00, 0x01251bff, 0x032618ff,
	0x042815ff, 0x052913ff, 0x072a10ff, 0x092a0d00,

	0xff0d280c, 0xff0f280a, 0xff112808, 0xff142706,
	0xff162605, 0xff192503, 0x001b2302, 0x001d2201,
	0x011f1f01, 0x01221d00, 0x02231b00, 0x04241800,
	0x052616ff, 0x072713ff, 0x08271100, 0x0a280e00,

	0xff0e260d, 0xff10260b, 0xff122609, 0xff142508,
	0x00152506, 0x00182305, 0x001b2203, 0x011d2002,
	0x011f1f01, 0x02201d01, 0x03221b00, 0x04231801,
	0x06241600, 0x08251300, 0x09261100, 0x0b260f00,

	0xff0e250e, 0xff10250c, 0x0011250a, 0x00142408,
	0x00162307, 0x00182206, 0x011a2104, 0x011c2003,
	0x021e1e02, 0x03201c01, 0x04211a01, 0x05221801,
	0x07231600, 0x08241400, 0x0a241200, 0x0c241000,

	0x000e240e, 0x0010240c, 0x0013230a, 0x00142309,
	0x00162208, 0x01182106, 0x011a2005, 0x021b1f04,
	0x031d1d03, 0x041e1c02, 0x05201a01, 0x06211801,
	0x07221601, 0x09231400, 0x0a231300, 0x0c231100,

	0x000f220f, 0x0011220d, 0x0013220b, 0x0015210a,
	0x01162108, 0x01182007, 0x02191f06, 0x031a1e05,
	0x041c1c04, 0x051d1b03, 0x061f1902, 0x07201801,
	0x08211601, 0x0a211500, 0x0b221300, 0x0d221100,

	0x0010210f, 0x0011210e, 0x0013210c, 0x0114200b,
	0x01161f0a, 0x02171f08, 0x03181e07, 0x031a1d06,
	0x041c1c04, 0x051d1a04, 0x071d1903, 0x081e1802,
	0x091f1602, 0x0b1f1501, 0x0c211300, 0x0e201200,

	0x00102010, 0x0012200e, 0x0013200d, 0x01151f0b,
	0x01161f0a, 0x02171e09, 0x03191d07, 0x041a1c06,
	0x051b1b05, 0x061c1a04, 0x071d1903, 0x081e1703,
	0x0a1f1601, 0x0b1f1501, 0x0d201300, 0x0e201200,

	0x00102010, 0x00121f0f, 0x00141f0d, 0x01141f0c,
	0x02161e0a, 0x03171d09, 0x03181d08, 0x041a1c06,
	0x051b1b05, 0x061c1a04, 0x081c1903, 0x091d1703,
	0x0a1e1602, 0x0c1e1501, 0x0d1f1400, 0x0e1f1201,

	0x00111e11, 0x00131e0f, 0x01131e0e, 0x02151d0c,
	0x02161d0b, 0x03171c0a, 0x04181b09, 0x05191b07,
	0x061a1a06, 0x071b1905, 0x091b1804, 0x0a1c1703,
	0x0b1d1602, 0x0c1d1502, 0x0e1d1401, 0x0f1e1300,

	0x00111e11, 0x00131d10, 0x01141d0e, 0x02151c0d,
	0x03161c0b, 0x04171b0a, 0x05171b09, 0x06181a08,
	0x07191907, 0x081a1806, 0x091a1805, 0x0a1b1704,
	0x0b1c1603, 0x0d1c1502, 0x0e1d1401, 0x0f1d1301,
};

static u32 sun8i_ui_scaler_base(struct sun8i_mixer *mixer, int channel)
{
	int vi_num = mixer->cfg->vi_num;

	if (mixer->cfg->is_de3)
		return DE3_VI_SCALER_UNIT_BASE +
		       DE3_VI_SCALER_UNIT_SIZE * vi_num +
		       DE3_UI_SCALER_UNIT_SIZE * (channel - vi_num);
	else
		return DE2_VI_SCALER_UNIT_BASE +
		       DE2_VI_SCALER_UNIT_SIZE * vi_num +
		       DE2_UI_SCALER_UNIT_SIZE * (channel - vi_num);
}

static int sun8i_ui_scaler_coef_index(unsigned int step)
{
	unsigned int scale, int_part, float_part;

	scale = step >> (SUN8I_UI_SCALER_SCALE_FRAC - 3);
	int_part = scale >> 3;
	float_part = scale & 0x7;

	switch (int_part) {
	case 0:
		return 0;
	case 1:
		return float_part;
	case 2:
		return 8 + (float_part >> 1);
	case 3:
		return 12;
	case 4:
		return 13;
	default:
		return 14;
	}
}

void sun8i_ui_scaler_enable(struct sun8i_mixer *mixer, int layer, bool enable)
{
	u32 val, base;

	if (WARN_ON(layer < mixer->cfg->vi_num))
		return;

	base = sun8i_ui_scaler_base(mixer, layer);

	if (enable)
		val = SUN8I_SCALER_GSU_CTRL_EN |
		      SUN8I_SCALER_GSU_CTRL_COEFF_RDY;
	else
		val = 0;

	regmap_write(mixer->engine.regs, SUN8I_SCALER_GSU_CTRL(base), val);
}

void sun8i_ui_scaler_setup(struct sun8i_mixer *mixer, int layer,
			   u32 src_w, u32 src_h, u32 dst_w, u32 dst_h,
			   u32 hscale, u32 vscale, u32 hphase, u32 vphase)
{
	u32 insize, outsize;
	int i, offset;
	u32 base;

	if (WARN_ON(layer < mixer->cfg->vi_num))
		return;

	base = sun8i_ui_scaler_base(mixer, layer);

	hphase <<= SUN8I_UI_SCALER_PHASE_FRAC - 16;
	vphase <<= SUN8I_UI_SCALER_PHASE_FRAC - 16;
	hscale <<= SUN8I_UI_SCALER_SCALE_FRAC - 16;
	vscale <<= SUN8I_UI_SCALER_SCALE_FRAC - 16;

	insize = SUN8I_UI_SCALER_SIZE(src_w, src_h);
	outsize = SUN8I_UI_SCALER_SIZE(dst_w, dst_h);

	regmap_write(mixer->engine.regs,
		     SUN8I_SCALER_GSU_OUTSIZE(base), outsize);
	regmap_write(mixer->engine.regs,
		     SUN8I_SCALER_GSU_INSIZE(base), insize);
	regmap_write(mixer->engine.regs,
		     SUN8I_SCALER_GSU_HSTEP(base), hscale);
	regmap_write(mixer->engine.regs,
		     SUN8I_SCALER_GSU_VSTEP(base), vscale);
	regmap_write(mixer->engine.regs,
		     SUN8I_SCALER_GSU_HPHASE(base), hphase);
	regmap_write(mixer->engine.regs,
		     SUN8I_SCALER_GSU_VPHASE(base), vphase);
	offset = sun8i_ui_scaler_coef_index(hscale) *
			SUN8I_UI_SCALER_COEFF_COUNT;
	for (i = 0; i < SUN8I_UI_SCALER_COEFF_COUNT; i++)
		regmap_write(mixer->engine.regs,
			     SUN8I_SCALER_GSU_HCOEFF(base, i),
			     lan2coefftab16[offset + i]);
}
