-- file Videoin.vhd
-- Videoin easy model controller implementation
-- copyright: (C) 2016-2020 MPSI Technologies GmbH
-- author: Alexander Wirthmueller (auto-generation)
-- date created: 10 May 2025
-- IP header --- ABOVE

library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

use work.Dbecore.all;
use work.Zuvsp.all;

entity Videoin is
	port (
		reset: in std_logic;
		mclk: in std_logic;

		fromCamifAXIS_tready: out std_logic;
		fromCamifAXIS_tvalid: in std_logic;
		fromCamifAXIS_tdata: in std_logic_vector(23 downto 0);
		fromCamifAXIS_tlast: in std_logic;

		vsync: in std_logic;
		NCol: in std_logic_vector(10 downto 0);

		grayToManyAXIS_tready: in std_logic;
		grayToManyAXIS_tvalid: out std_logic;
		grayToManyAXIS_tdata: out std_logic_vector(71 downto 0);
		grayToManyAXIS_tlast: out std_logic;

		rgbToManyAXIS_tready: in std_logic;
		rgbToManyAXIS_tvalid: out std_logic;
		rgbToManyAXIS_tdata: out std_logic_vector(35 downto 0);
		rgbToManyAXIS_tlast: out std_logic;

		stateIgr_dbg: out std_logic_vector(7 downto 0);
		stateRgbegr_dbg: out std_logic_vector(7 downto 0)
	);
end Videoin;

architecture Rtl of Videoin is

	------------------------------------------------------------------------
	-- component declarations
	------------------------------------------------------------------------

	component Dpbram_size6kB_a64b64 is
		port (
			rstA: in std_logic;
			clkA: in std_logic;

			enA: in std_logic;
			weA: in std_logic;

			aA: in std_logic_vector(9 downto 0);
			drdA: out std_logic_vector(63 downto 0);
			dwrA: in std_logic_vector(63 downto 0);

			rstB: in std_logic;
			clkB: in std_logic;

			enB: in std_logic;
			weB: in std_logic;

			aB: in std_logic_vector(9 downto 0);
			drdB: out std_logic_vector(63 downto 0);
			dwrB: in std_logic_vector(63 downto 0)
		);
	end component;

	component Dpbram_size4kB_a64b64 is
		port (
			rstA: in std_logic;
			clkA: in std_logic;

			enA: in std_logic;
			weA: in std_logic;

			aA: in std_logic_vector(8 downto 0);
			drdA: out std_logic_vector(63 downto 0);
			dwrA: in std_logic_vector(63 downto 0);

			rstB: in std_logic;
			clkB: in std_logic;

			enB: in std_logic;
			weB: in std_logic;

			aB: in std_logic_vector(8 downto 0);
			drdB: out std_logic_vector(63 downto 0);
			dwrB: in std_logic_vector(63 downto 0)
		);
	end component;

	------------------------------------------------------------------------
	-- signal declarations
	------------------------------------------------------------------------

	---- gray egress from buffers operation (grayegr)
	type stateGrayegr_t is (
		stateGrayegrInit,
		stateGrayegrIdle,
		stateGrayegrLoad,
		stateGrayegrRun,
		stateGrayegrEol
	);
	signal stateGrayegr: stateGrayegr_t;

	signal abcde: natural range 0 to 4; -- used jointly between graypack and grayegr
	signal nop: natural range 0 to 15;
	signal enRowbufB: std_logic;

	signal aRowbufB: natural range 0 to 511;
	signal aRowbufB_vec: std_logic_vector(8 downto 0);

	signal drdRow0bufBm1: std_logic_vector(63 downto 0);
	signal drdRow1bufBm1: std_logic_vector(63 downto 0);
	signal drdRow2bufBm1: std_logic_vector(63 downto 0);
	signal drdRow3bufBm1: std_logic_vector(63 downto 0);
	signal drdRow4bufBm1: std_logic_vector(63 downto 0);

	signal grayToManyAXIS_tvalid_sig: std_logic;
	signal grayToManyAXIS_tlast_sig: std_logic;

	signal gr0: std_logic_vector(11 downto 0);
	signal gr1: std_logic_vector(11 downto 0);
	signal gr2: std_logic_vector(11 downto 0);
	signal gr3: std_logic_vector(11 downto 0);
	signal gr4: std_logic_vector(11 downto 0);

	-- IP sigs.grayegr.cust --- INSERT

	---- RGB-to-gray packing operation (graypack)
	type stateGraypack_t is (
		stateGraypackInit,
		stateGraypackIdle,
		stateGraypackRun,
		stateGraypackEol
	);
	signal stateGraypack: stateGraypack_t;

	signal tuv: natural range 0 to 15;

	signal enRowbuf: std_logic;
	signal enRow0buf: std_logic;
	signal enRow1buf: std_logic;
	signal enRow2buf: std_logic;
	signal enRow3buf: std_logic;
	signal enRow4buf: std_logic;

	signal aRowbuf: natural range 0 to 511;
	signal aRowbuf_vec: std_logic_vector(8 downto 0);

	signal dwrRowbuf: std_logic_vector(63 downto 0);
	signal dwrRowbufp1: std_logic_vector(63 downto 0);

	-- IP sigs.graypack.cust --- INSERT

	---- ingress and even/odd buffer packing operation (igr)
	type stateIgr_t is (
		stateIgrInit,
		stateIgrRun,
		stateIgrEolA, stateIgrEolB
	);
	signal stateIgr: stateIgr_t;

	signal klm: natural range 0 to 7;

	signal fillBNotA: std_logic;
	signal oddNotEven: std_logic;

	signal enEobuf: std_logic;

	signal enEvenAbuf: std_logic;
	signal enEvenBbuf: std_logic;

	signal enOddbuf: std_logic;

	signal aEobuf: natural range 0 to 767;
	signal aEobuf_vec: std_logic_vector(9 downto 0);

	signal dwrEobuf: std_logic_vector(63 downto 0);
	signal dwrEobufp1: std_logic_vector(63 downto 0);

	signal rawcolEgrstart: natural range 0 to 3999;
	signal strbEgrstart: std_logic;

	-- IP sigs.igr.cust --- INSERT

	---- RGB and internal egress from buffers operation (rgbegr)
	type stateRgbegr_t is (
		stateRgbegrInit,
		stateRgbegrIdle,
		stateRgbegrLoad,
		stateRgbegrRun,
		stateRgbegrHold,
		stateRgbegrEol
	);
	signal stateRgbegr: stateRgbegr_t;

	signal qrs: natural range 0 to 7;
	signal enEobufB: std_logic;

	signal enEvenAbufB: std_logic;
	signal enEvenBbufB: std_logic;

	signal aEobufB: natural range 0 to 767;
	signal aEobufB_vec: std_logic_vector(9 downto 0);

	signal drdEvenbufB: std_logic_vector(63 downto 0);
	signal drdEvenbufBm1: std_logic_vector(63 downto 0);

	signal drdOddbufBm1: std_logic_vector(63 downto 0);

	signal rgbToManyAXIS_tvalid_sig: std_logic;
	signal rgbToManyAXIS_tdata_sig: std_logic_vector(35 downto 0);
	signal rgbToManyAXIS_tlast_sig: std_logic;

	signal gr: std_logic_vector(11 downto 0);

	-- IP sigs.rgbegr.cust --- INSERT

	---- myEvenAbuf
	signal drdEvenAbufB: std_logic_vector(63 downto 0);

	---- myEvenBbuf
	signal drdEvenBbufB: std_logic_vector(63 downto 0);

	---- myOddbuf
	signal drdOddbufB: std_logic_vector(63 downto 0);

	---- myRow0buf
	signal drdRow0bufB: std_logic_vector(63 downto 0);

	---- myRow1buf
	signal drdRow1bufB: std_logic_vector(63 downto 0);

	---- myRow2buf
	signal drdRow2bufB: std_logic_vector(63 downto 0);

	---- myRow3buf
	signal drdRow3bufB: std_logic_vector(63 downto 0);

	---- myRow4buf
	signal drdRow4bufB: std_logic_vector(63 downto 0);

	---- other
	signal sprsNotFull: std_logic := '1';
	-- IP sigs.oth.cust --- INSERT

begin

	------------------------------------------------------------------------
	-- sub-module instantiation
	------------------------------------------------------------------------

	myEvenAbuf : Dpbram_size6kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enEvenAbuf,
			weA => '1',

			aA => aEobuf_vec,
			drdA => open,
			dwrA => dwrEobuf,

			rstB => reset,
			clkB => mclk,

			enB => enEvenAbufB,
			weB => '0',

			aB => aEobufB_vec,
			drdB => drdEvenAbufB,
			dwrB => (others => '0')
		);

	myEvenBbuf : Dpbram_size6kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enEvenBbuf,
			weA => '1',

			aA => aEobuf_vec,
			drdA => open,
			dwrA => dwrEobuf,

			rstB => reset,
			clkB => mclk,

			enB => enEvenBbufB,
			weB => '0',

			aB => aEobufB_vec,
			drdB => drdEvenBbufB,
			dwrB => (others => '0')
		);

	myOddbuf : Dpbram_size6kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enOddbuf,
			weA => '1',

			aA => aEobuf_vec,
			drdA => open,
			dwrA => dwrEobuf,

			rstB => reset,
			clkB => mclk,

			enB => enEobufB,
			weB => '0',

			aB => aEobufB_vec,
			drdB => drdOddbufB,
			dwrB => (others => '0')
		);

	myRow0buf : Dpbram_size4kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enRow0buf,
			weA => '1',

			aA => aRowbuf_vec,
			drdA => open,
			dwrA => dwrRowbuf,

			rstB => reset,
			clkB => mclk,

			enB => enRowbufB,
			weB => '0',

			aB => aRowbufB_vec,
			drdB => drdRow0bufB,
			dwrB => (others => '0')
		);

	myRow1buf : Dpbram_size4kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enRow1buf,
			weA => '1',

			aA => aRowbuf_vec,
			drdA => open,
			dwrA => dwrRowbuf,

			rstB => reset,
			clkB => mclk,

			enB => enRowbufB,
			weB => '0',

			aB => aRowbufB_vec,
			drdB => drdRow1bufB,
			dwrB => (others => '0')
		);

	myRow2buf : Dpbram_size4kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enRow2buf,
			weA => '1',

			aA => aRowbuf_vec,
			drdA => open,
			dwrA => dwrRowbuf,

			rstB => reset,
			clkB => mclk,

			enB => enRowbufB,
			weB => '0',

			aB => aRowbufB_vec,
			drdB => drdRow2bufB,
			dwrB => (others => '0')
		);

	myRow3buf : Dpbram_size4kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enRow3buf,
			weA => '1',

			aA => aRowbuf_vec,
			drdA => open,
			dwrA => dwrRowbuf,

			rstB => reset,
			clkB => mclk,

			enB => enRowbufB,
			weB => '0',

			aB => aRowbufB_vec,
			drdB => drdRow3bufB,
			dwrB => (others => '0')
		);

	myRow4buf : Dpbram_size4kB_a64b64
		port map (
			rstA => reset,
			clkA => mclk,

			enA => enRow4buf,
			weA => '1',

			aA => aRowbuf_vec,
			drdA => open,
			dwrA => dwrRowbuf,

			rstB => reset,
			clkB => mclk,

			enB => enRowbufB,
			weB => '0',

			aB => aRowbufB_vec,
			drdB => drdRow4bufB,
			dwrB => (others => '0')
		);

	------------------------------------------------------------------------
	-- implementation: gray egress from buffers operation (grayegr)
	------------------------------------------------------------------------

	-- IP impl.grayegr.wiring --- BEGIN
	aRowbufB_vec <= std_logic_vector(to_unsigned(aRowbufB, 9));

	grayToManyAXIS_tvalid <= grayToManyAXIS_tvalid_sig;
	grayToManyAXIS_tlast <= grayToManyAXIS_tlast_sig;
	-- IP impl.grayegr.wiring --- END

	-- IP impl.grayegr.wiring.cust --- RBEGIN
	grayToManyAXIS_tdata <= gr0 & gr1 & gr2 & gr3 & gr4 & gr when abcde=0
				else gr1 & gr2 & gr3 & gr4 & gr0 & gr when abcde=1
				else gr2 & gr3 & gr4 & gr0 & gr1 & gr when abcde=2
				else gr3 & gr4 & gr0 & gr1 & gr2 & gr when abcde=3
				else gr4 & gr0 & gr1 & gr2 & gr3 & gr when abcde=4
				else (others => '0');
	-- IP impl.grayegr.wiring.cust --- REND

	-- IP impl.grayegr.rising --- BEGIN
	process (reset, mclk)
		-- IP impl.grayegr.vars --- RBEGIN
		variable col_lcl: natural range 0 to 2000;

		variable enRowbufB_lcl: std_logic;
		-- IP impl.grayegr.vars --- REND

	begin
		if reset='1' then
			-- IP impl.grayegr.asyncrst --- BEGIN
			stateGrayegr <= stateGrayegrInit;
			abcde <= 0;
			nop <= 0;
			enRowbufB <= '0';
			aRowbufB <= 0;
			drdRow0bufBm1 <= (others => '0');
			drdRow1bufBm1 <= (others => '0');
			drdRow2bufBm1 <= (others => '0');
			drdRow3bufBm1 <= (others => '0');
			drdRow4bufBm1 <= (others => '0');
			grayToManyAXIS_tvalid_sig <= '0';
			grayToManyAXIS_tlast_sig <= '1';
			gr0 <= (others => '0');
			gr1 <= (others => '0');
			gr2 <= (others => '0');
			gr3 <= (others => '0');
			gr4 <= (others => '0');

			-- IP impl.grayegr.asyncrst --- END
			-- IP impl.grayegr.asyncrst.cust --- IBEGIN
			col_lcl := 0;
			enRowbufB_lcl := '0';
			-- IP impl.grayegr.asyncrst.cust --- IEND

		elsif rising_edge(mclk) then
			if stateGrayegr=stateGrayegrInit then
				-- IP impl.grayegr.syncrst --- BEGIN
				abcde <= 0;
				nop <= 0;
				enRowbufB <= '0';
				aRowbufB <= 0;
				drdRow0bufBm1 <= (others => '0');
				drdRow1bufBm1 <= (others => '0');
				drdRow2bufBm1 <= (others => '0');
				drdRow3bufBm1 <= (others => '0');
				drdRow4bufBm1 <= (others => '0');
				grayToManyAXIS_tvalid_sig <= '0';
				grayToManyAXIS_tlast_sig <= '1';
				gr0 <= (others => '0');
				gr1 <= (others => '0');
				gr2 <= (others => '0');
				gr3 <= (others => '0');
				gr4 <= (others => '0');

				-- IP impl.grayegr.syncrst --- END
				-- IP impl.grayegr.syncrst.cust --- IBEGIN
				col_lcl := 0;
				enRowbufB_lcl := '0';
				-- IP impl.grayegr.syncrst.cust --- IEND

				if vsync='1' then
					stateGrayegr <= stateGrayegrInit;

				else
					stateGrayegr <= stateGrayegrIdle;
				end if;

			elsif stateGrayegr=stateGrayegrIdle then
				if strbEgrstart='1' then
					enRowbufB <= '1'; -- IP impl.grayegr.idle.start --- ILINE

					stateGrayegr <= stateGrayegrLoad;
				end if;

			elsif stateGrayegr=stateGrayegrLoad then
				-- IP impl.grayegr.load --- IBEGIN
				grayToManyAXIS_tlast_sig <= '0';

				enRowbufB <= '0';
				aRowbufB <= aRowbufB + 1;

				enRowbufB_lcl := '0';
				-- IP impl.grayegr.load --- IEND

				stateGrayegr <= stateGrayegrRun;

			elsif stateGrayegr=stateGrayegrRun then
				if rgbToManyAXIS_tvalid_sig='1' then
					-- IP impl.grayegr.run --- IBEGIN
					if nop=0 then -- en at nop 14
						gr0 <= drdRow0bufB(11 downto 0);
						gr1 <= drdRow1bufB(11 downto 0);
						gr2 <= drdRow2bufB(11 downto 0);
						gr3 <= drdRow3bufB(11 downto 0);
						gr4 <= drdRow4bufB(11 downto 0);
					elsif nop=1 then
						gr0 <= drdRow0bufB(23 downto 12);
						gr1 <= drdRow1bufB(23 downto 12);
						gr2 <= drdRow2bufB(23 downto 12);
						gr3 <= drdRow3bufB(23 downto 12);
						gr4 <= drdRow4bufB(23 downto 12);
					elsif nop=2 then
						gr0 <= drdRow0bufB(35 downto 24);
						gr1 <= drdRow1bufB(35 downto 24);
						gr2 <= drdRow2bufB(35 downto 24);
						gr3 <= drdRow3bufB(35 downto 24);
						gr4 <= drdRow4bufB(35 downto 24);
					elsif nop=3 then
						gr0 <= drdRow0bufB(47 downto 36);
						gr1 <= drdRow1bufB(47 downto 36);
						gr2 <= drdRow2bufB(47 downto 36);
						gr3 <= drdRow3bufB(47 downto 36);
						gr4 <= drdRow4bufB(47 downto 36);
					elsif nop=4 then
						gr0 <= drdRow0bufB(59 downto 48);
						gr1 <= drdRow1bufB(59 downto 48);
						gr2 <= drdRow2bufB(59 downto 48);
						gr3 <= drdRow3bufB(59 downto 48);
						gr4 <= drdRow4bufB(59 downto 48);
					elsif nop=5 then -- en at nop 3
						gr0 <= drdRow0bufB(7 downto 0) & drdRow0bufBm1(63 downto 60);
						gr1 <= drdRow1bufB(7 downto 0) & drdRow1bufBm1(63 downto 60);
						gr2 <= drdRow2bufB(7 downto 0) & drdRow2bufBm1(63 downto 60);
						gr3 <= drdRow3bufB(7 downto 0) & drdRow3bufBm1(63 downto 60);
						gr4 <= drdRow4bufB(7 downto 0) & drdRow4bufBm1(63 downto 60);
					elsif nop=6 then
						gr0 <= drdRow0bufB(19 downto 8);
						gr1 <= drdRow1bufB(19 downto 8);
						gr2 <= drdRow2bufB(19 downto 8);
						gr3 <= drdRow3bufB(19 downto 8);
						gr4 <= drdRow4bufB(19 downto 8);
					elsif nop=7 then
						gr0 <= drdRow0bufB(31 downto 20);
						gr1 <= drdRow1bufB(31 downto 20);
						gr2 <= drdRow2bufB(31 downto 20);
						gr3 <= drdRow3bufB(31 downto 20);
						gr4 <= drdRow4bufB(31 downto 20);
					elsif nop=8 then
						gr0 <= drdRow0bufB(43 downto 32);
						gr1 <= drdRow1bufB(43 downto 32);
						gr2 <= drdRow2bufB(43 downto 32);
						gr3 <= drdRow3bufB(43 downto 32);
						gr4 <= drdRow4bufB(43 downto 32);
					elsif nop=9 then
						gr0 <= drdRow0bufB(55 downto 44);
						gr1 <= drdRow1bufB(55 downto 44);
						gr2 <= drdRow2bufB(55 downto 44);
						gr3 <= drdRow3bufB(55 downto 44);
						gr4 <= drdRow4bufB(55 downto 44);
					elsif nop=10 then -- en at nop 8
						gr0 <= drdRow0bufB(3 downto 0) & drdRow0bufBm1(63 downto 56);
						gr1 <= drdRow1bufB(3 downto 0) & drdRow1bufBm1(63 downto 56);
						gr2 <= drdRow2bufB(3 downto 0) & drdRow2bufBm1(63 downto 56);
						gr3 <= drdRow3bufB(3 downto 0) & drdRow3bufBm1(63 downto 56);
						gr4 <= drdRow4bufB(3 downto 0) & drdRow4bufBm1(63 downto 56);
					elsif nop=11 then
						gr0 <= drdRow0bufB(15 downto 4);
						gr1 <= drdRow1bufB(15 downto 4);
						gr2 <= drdRow2bufB(15 downto 4);
						gr3 <= drdRow3bufB(15 downto 4);
						gr4 <= drdRow4bufB(15 downto 4);
					elsif nop=12 then
						gr0 <= drdRow0bufB(27 downto 16);
						gr1 <= drdRow1bufB(27 downto 16);
						gr2 <= drdRow2bufB(27 downto 16);
						gr3 <= drdRow3bufB(27 downto 16);
						gr4 <= drdRow4bufB(27 downto 16);
					elsif nop=13 then
						gr0 <= drdRow0bufB(39 downto 28);
						gr1 <= drdRow1bufB(39 downto 28);
						gr2 <= drdRow2bufB(39 downto 28);
						gr3 <= drdRow3bufB(39 downto 28);
						gr4 <= drdRow4bufB(39 downto 28);
					elsif nop=14 then
						gr0 <= drdRow0bufB(51 downto 40);
						gr1 <= drdRow1bufB(51 downto 40);
						gr2 <= drdRow2bufB(51 downto 40);
						gr3 <= drdRow3bufB(51 downto 40);
						gr4 <= drdRow4bufB(51 downto 40);
					elsif nop=15 then
						gr0 <= drdRow0bufB(63 downto 52);
						gr1 <= drdRow1bufB(63 downto 52);
						gr2 <= drdRow2bufB(63 downto 52);
						gr3 <= drdRow3bufB(63 downto 52);
						gr4 <= drdRow4bufB(63 downto 52);
					end if;

					if nop=14 or nop=3 or nop=8 then
						enRowbufB_lcl := '1';

						drdRow0bufBm1 <= drdRow0bufB;
						drdRow1bufBm1 <= drdRow1bufB;
						drdRow2bufBm1 <= drdRow2bufB;
						drdRow3bufBm1 <= drdRow3bufB;
						drdRow4bufBm1 <= drdRow4bufB;

					else
						enRowbufB_lcl := '0';
					end if;

					if (nop=15 or nop=4 or nop=9) then
						aRowbufB <= aRowbufB + 1;
					end if;

					if nop=15 then
						nop <= 0;
					else
						nop <= nop + 1;
					end if;

					grayToManyAXIS_tvalid_sig <= '1';

					col_lcl := col_lcl + 1; -- in next clock cycle
					-- IP impl.grayegr.run --- IEND

					if col_lcl=unsigned(NCol) then
						grayToManyAXIS_tlast_sig <= '1'; -- IP impl.grayegr.run.rowDone --- ILINE

						stateGrayegr <= stateGrayegrEol;

					else
						-- IP impl.grayegr.run.nextCol --- IBEGIN
						if sprsNotFull='0' then
							enRowbufB <= enRowbufB_lcl;
						else
							enRowbufB <= '0';
						end if;
						-- IP impl.grayegr.run.nextCol --- IEND

						stateGrayegr <= stateGrayegrRun;
					end if;

				else
					-- IP impl.grayegr.run.reset --- IBEGIN
					if sprsNotFull='1' then
						enRowbufB <= enRowbufB_lcl;
					else
						enRowbufB <= '0';
					end if;

					grayToManyAXIS_tvalid_sig <= '0';
					-- IP impl.grayegr.run.reset --- IEND

					stateGrayegr <= stateGrayegrRun;
				end if;

			elsif stateGrayegr=stateGrayegrEol then
				grayToManyAXIS_tvalid_sig <= '0'; -- IP impl.grayegr.eol.pre --- ILINE

				if vsync='1' then
					stateGrayegr <= stateGrayegrInit;

				else
					-- IP impl.grayegr.eol.nextRow --- IBEGIN
					if abcde=4 then
						abcde <= 0;
					else
						abcde <= abcde + 1;
					end if;

					nop <= 0;

					enRowbufB <= '0';
					aRowbufB <= 0;

					col_lcl := 0;
					-- IP impl.grayegr.eol.nextRow --- IEND

					stateGrayegr <= stateGrayegrIdle;
				end if;
			end if;
		end if;
	end process;
	-- IP impl.grayegr.rising --- END

	------------------------------------------------------------------------
	-- implementation: RGB-to-gray packing operation (graypack)
	------------------------------------------------------------------------

	-- IP impl.graypack.wiring --- BEGIN
	enRow0buf <= '1' when (enRowbuf='1' and abcde=0) else '0';
	enRow1buf <= '1' when (enRowbuf='1' and abcde=1) else '0';
	enRow2buf <= '1' when (enRowbuf='1' and abcde=2) else '0';
	enRow3buf <= '1' when (enRowbuf='1' and abcde=3) else '0';
	enRow4buf <= '1' when (enRowbuf='1' and abcde=4) else '0';

	aRowbuf_vec <= std_logic_vector(to_unsigned(aRowbuf, 9));
	-- IP impl.graypack.wiring --- END

	-- IP impl.graypack.wiring.cust --- RBEGIN

	-- row*buf write side

	-- 12 = (2^2)*3, 64 = (2^2)*2^4 => 16 entries in three words
	-- 0: Gr5/4 Gr4/12 Gr3/12 Gr2/12 Gr1/12 Gr0/12
	-- 1: Gr10/8 Gr9/12 Gr8/12 Gr7/12 Gr6/12 /8
	-- 2: Gr15/12 Gr14/12 Gr13/12 Gr12/12 Gr11/12 /4

	-- population sequence: rowbuf0-1-2-3-4-0-1-2-3-4

	-- IP impl.graypack.wiring.cust --- REND

	-- IP impl.graypack.rising --- BEGIN
	process (reset, mclk)
		-- IP impl.graypack.vars --- RBEGIN
		variable col_lcl: natural range 0 to 2000;
		-- IP impl.graypack.vars --- REND

	begin
		if reset='1' then
			-- IP impl.graypack.asyncrst --- BEGIN
			stateGraypack <= stateGraypackInit;
			tuv <= 0;
			enRowbuf <= '0';
			aRowbuf <= 0;
			dwrRowbuf <= (others => '0');
			dwrRowbufp1 <= (others => '0');

			-- IP impl.graypack.asyncrst --- END
			-- IP impl.graypack.asyncrst.cust --- IBEGIN
			col_lcl := 0;
			-- IP impl.graypack.asyncrst.cust --- IEND

		elsif rising_edge(mclk) then
			if stateGraypack=stateGraypackInit then
				-- IP impl.graypack.syncrst --- BEGIN
				tuv <= 0;
				enRowbuf <= '0';
				aRowbuf <= 0;
				dwrRowbuf <= (others => '0');
				dwrRowbufp1 <= (others => '0');

				-- IP impl.graypack.syncrst --- END
				-- IP impl.graypack.syncrst.cust --- IBEGIN
				col_lcl := 0;
				-- IP impl.graypack.syncrst.cust --- IEND

				if vsync='1' then
					stateGraypack <= stateGraypackInit;

				else
					stateGraypack <= stateGraypackIdle;
				end if;

			elsif stateGraypack=stateGraypackIdle then
				if strbEgrstart='1' then
					stateGraypack <= stateGraypackRun;
				end if;

			elsif stateGraypack=stateGraypackRun then
				if rgbToManyAXIS_tvalid_sig='1' then
					-- IP impl.graypack.run --- IBEGIN
					if tuv=0 then
						dwrRowbuf(11 downto 0) <= gr;
					elsif tuv=1 then
						dwrRowbuf(23 downto 12) <= gr;
					elsif tuv=2 then
						dwrRowbuf(35 downto 24) <= gr;
					elsif tuv=3 then
						dwrRowbuf(47 downto 36) <= gr;
					elsif tuv=4 then
						dwrRowbuf(59 downto 48) <= gr;
					elsif tuv=5 then
						dwrRowbuf(63 downto 60) <= gr(3 downto 0);
						dwrRowbufp1(7 downto 0) <= gr(11 downto 4);
					elsif tuv=6 then
						dwrRowbuf(7 downto 0) <= dwrRowbufp1(7 downto 0);
						dwrRowbuf(19 downto 8) <= gr;
					elsif tuv=7 then
						dwrRowbuf(31 downto 20) <= gr;
					elsif tuv=8 then
						dwrRowbuf(43 downto 32) <= gr;
					elsif tuv=9 then
						dwrRowbuf(55 downto 44) <= gr;
					elsif tuv=10 then
						dwrRowbuf(63 downto 56) <= gr(7 downto 0);
						dwrRowbufp1(3 downto 0) <= gr(11 downto 8);
					elsif tuv=11 then
						dwrRowbuf(3 downto 0) <= dwrRowbufp1(3 downto 0);
						dwrRowbuf(15 downto 4) <= gr;
					elsif tuv=12 then
						dwrRowbuf(27 downto 16) <= gr;
					elsif tuv=13 then
						dwrRowbuf(39 downto 28) <= gr;
					elsif tuv=14 then
						dwrRowbuf(51 downto 40) <= gr;
					elsif tuv=15 then
						dwrRowbuf(63 downto 52) <= gr;
					end if;

					col_lcl := col_lcl + 1; -- in next clock cycle

					if (tuv=5 or tuv=10 or tuv=15) or col_lcl=unsigned(NCol) then
						enRowbuf <= '1';
					else
						enRowbuf <= '0';
					end if;

					if tuv=6 or tuv=11 or (tuv=0 and col_lcl/=1) then
						aRowbuf <= aRowbuf + 1;
					end if;

					if tuv=15 then
						tuv <= 0;
					else
						tuv <= tuv + 1;
					end if;
					-- IP impl.graypack.run --- IEND

					if col_lcl=unsigned(NCol) then
						stateGraypack <= stateGraypackEol;

					else
						stateGraypack <= stateGraypackRun;
					end if;
				end if;

			elsif stateGraypack=stateGraypackEol then
				if vsync='1' then
					stateGraypack <= stateGraypackInit;

				else
					-- IP impl.graypack.eol.nextRow --- IBEGIN
					tuv <= 0;

					enRowbuf <= '0';
					aRowbuf <= 0;
					
					col_lcl := 0;
					-- IP impl.graypack.eol.nextRow --- IEND

					stateGraypack <= stateGraypackIdle;
				end if;
			end if;
		end if;
	end process;
	-- IP impl.graypack.rising --- END

	------------------------------------------------------------------------
	-- implementation: ingress and even/odd buffer packing operation (igr)
	------------------------------------------------------------------------

	-- IP impl.igr.wiring --- BEGIN
	enEvenAbuf <= '1' when (enEobuf='1' and fillBNotA='0' and oddNotEven='0') else '0';
	enEvenBbuf <= '1' when (enEobuf='1' and fillBNotA='1' and oddNotEven='0') else '0';

	enOddbuf <= '1' when (enEobuf='1' and oddNotEven='1') else '0';

	aEobuf_vec <= std_logic_vector(to_unsigned(aEobuf, 10));
	-- IP impl.igr.wiring --- END

	-- IP impl.igr.wiring.cust --- RBEGIN

	-- input: r/12 & g/12 or g/12 & b/12 (up to each clock)
	-- output: 64 bit (sparse)

	-- 24 = (2^3)*3, 64 = (2^3)*2^3 => 8 entries in three words
	-- 0: (R2G2)/16 (R1/12,G1/12)/24 (R0/12,G0/12)/24
	-- 1: (R5G5)/8 (R4G4)/24 (R3G3)/24 /8
	-- 2: (R7G7)/24 (R6G6)/24 /16

	-- IP impl.igr.wiring.cust --- REND

	stateIgr_dbg <= x"00" when stateIgr=stateIgrInit
				else x"10" when stateIgr=stateIgrRun
				else x"20" when stateIgr=stateIgrEolA
				else x"21" when stateIgr=stateIgrEolB
				else (others => '1');

	-- IP impl.igr.rising --- BEGIN
	process (reset, mclk)
		-- IP impl.igr.vars --- RBEGIN
		variable rawcol_lcl: natural range 0 to 4000;
		-- IP impl.igr.vars --- REND

	begin
		if reset='1' then
			-- IP impl.igr.asyncrst --- BEGIN
			stateIgr <= stateIgrInit;
			klm <= 0;
			fillBNotA <= '0';
			oddNotEven <= '0';
			enEobuf <= '0';
			aEobuf <= 0;
			dwrEobuf <= (others => '0');
			dwrEobufp1 <= (others => '0');
			rawcolEgrstart <= 12;
			strbEgrstart <= '0';

			-- IP impl.igr.asyncrst --- END
			-- IP impl.igr.asyncrst.cust --- IBEGIN
			rawcol_lcl := 0;
			-- IP impl.igr.asyncrst.cust --- IEND

		elsif rising_edge(mclk) then
			if stateIgr=stateIgrInit then
				-- IP impl.igr.syncrst --- BEGIN
				klm <= 0;
				fillBNotA <= '0';
				oddNotEven <= '0';
				enEobuf <= '0';
				aEobuf <= 0;
				dwrEobuf <= (others => '0');
				dwrEobufp1 <= (others => '0');
				rawcolEgrstart <= 12;
				strbEgrstart <= '0';

				-- IP impl.igr.syncrst --- END
				-- IP impl.igr.syncrst.cust --- IBEGIN
				rawcol_lcl := 0;
				-- IP impl.igr.syncrst.cust --- IEND

				if vsync='1' then
					stateIgr <= stateIgrRun;

				else
					stateIgr <= stateIgrInit;
				end if;

			elsif stateIgr=stateIgrRun then
				-- IP impl.igr.run.pre --- IBEGIN
				if strbEgrstart='1' then
					strbEgrstart <= '0';
				elsif oddNotEven='1' and rawcol_lcl=rawcolEgrstart then
					strbEgrstart <= '1';
				end if;
				-- IP impl.igr.run.pre --- IEND

				if (vsync='0' and fromCamifAXIS_tvalid='1') then
					-- IP impl.igr.run --- IBEGIN
					if klm=0 then
						dwrEobuf(23 downto 0) <= fromCamifAXIS_tdata;
					elsif klm=1 then
						dwrEobuf(47 downto 24) <= fromCamifAXIS_tdata;
					elsif klm=2 then
						dwrEobuf(63 downto 48) <= fromCamifAXIS_tdata(15 downto 0);
						dwrEobufp1(7 downto 0) <= fromCamifAXIS_tdata(23 downto 16);
					elsif klm=3 then
						dwrEobuf(7 downto 0) <= dwrEobufp1(7 downto 0);
						dwrEobuf(31 downto 8) <= fromCamifAXIS_tdata;
					elsif klm=4 then
						dwrEobuf(55 downto 32) <= fromCamifAXIS_tdata;
					elsif klm=5 then
						dwrEobuf(63 downto 56) <= fromCamifAXIS_tdata(7 downto 0);
						dwrEobufp1(15 downto 0) <= fromCamifAXIS_tdata(23 downto 8);
					elsif klm=6 then
						dwrEobuf(15 downto 0) <= dwrEobufp1(15 downto 0);
						dwrEobuf(39 downto 16) <= fromCamifAXIS_tdata;
					elsif klm=7 then
						dwrEobuf(63 downto 40) <= fromCamifAXIS_tdata;
					end if;

					if klm=2 or klm=5 or klm=7 then
						enEobuf <= '1';
					else
						enEobuf <= '0';
					end if;

					if klm=3 or klm=6 or (klm=0 and rawcol_lcl/=0) then
						aEobuf <= aEobuf + 1;
					end if;

					if klm=7 then
						klm <= 0;
					else
						klm <= klm + 1;
					end if;

					rawcol_lcl := rawcol_lcl + 1;
					-- IP impl.igr.run --- IEND

					if fromCamifAXIS_tlast='1' then
						if (klm=2 or klm=5 or klm=7) then
							stateIgr <= stateIgrEolB;

						else
							stateIgr <= stateIgrEolA;
						end if;

					else
						stateIgr <= stateIgrRun;
					end if;
				end if;

			elsif stateIgr=stateIgrEolA then
				-- IP impl.igr.eolA --- IBEGIN
				enEobuf <= '1';
				
				if klm=3 or klm=6 or klm=0 then
					aEobuf <= aEobuf + 1;
				end if;
				-- IP impl.igr.eolA --- IEND

				stateIgr <= stateIgrEolB;

			elsif stateIgr=stateIgrEolB then
				if vsync='1' then
					stateIgr <= stateIgrInit;

				else
					-- IP impl.igr.eolB.nextRow --- IBEGIN
					klm <= 0;

					if oddNotEven='0' then
						fillBNotA <= not fillBNotA;
					end if;

					oddNotEven <= not oddNotEven;

					enEobuf <= '0';
					aEobuf <= 0;

					rawcol_lcl := 0;
					-- IP impl.igr.eolB.nextRow --- IEND

					stateIgr <= stateIgrRun;
				end if;
			end if;
		end if;
	end process;
	-- IP impl.igr.rising --- END

	------------------------------------------------------------------------
	-- implementation: RGB and internal egress from buffers operation (rgbegr)
	------------------------------------------------------------------------

	-- IP impl.rgbegr.wiring --- BEGIN
	enEvenAbufB <= '1' when (enEobufB='1' and fillBNotA='1') else '0';
	enEvenBbufB <= '1' when (enEobufB='1' and fillBNotA='0') else '0';

	aEobufB_vec <= std_logic_vector(to_unsigned(aEobufB, 10));

	drdEvenbufB <= drdEvenAbufB when fillBNotA='1' else drdEvenBbufB;

	rgbToManyAXIS_tvalid <= rgbToManyAXIS_tvalid_sig;
	rgbToManyAXIS_tdata <= rgbToManyAXIS_tdata_sig;
	rgbToManyAXIS_tlast <= rgbToManyAXIS_tlast_sig;
	-- IP impl.rgbegr.wiring --- END

	-- IP impl.rgbegr.wiring.cust --- RBEGIN

	-- even/odd buf B/read side

	-- sparse:
	-- enEobufB  100010000010000
	-- drdEobufB  000011111122222
	-- _tvalid     1010101010101010 1010
	-- qrs         0011223344556677

	-- full:
	-- enEobufB  10100100
	-- drdEobufB  00111222
	-- _tvalid     11111111 1111
	-- qrs       6701234567

	-- IP impl.rgbegr.wiring.cust --- REND

	stateRgbegr_dbg <= x"00" when stateRgbegr=stateRgbegrInit
				else x"10" when stateRgbegr=stateRgbegrIdle
				else x"20" when stateRgbegr=stateRgbegrLoad
				else x"30" when stateRgbegr=stateRgbegrRun
				else x"40" when stateRgbegr=stateRgbegrHold
				else x"50" when stateRgbegr=stateRgbegrEol
				else (others => '1');

	-- IP impl.rgbegr.rising --- BEGIN
	process (reset, mclk)
		-- IP impl.rgbegr.vars --- RBEGIN
		variable col_lcl: natural range 0 to 2000;

		variable r_lcl: std_logic_vector(11 downto 0);
		variable g0_lcl: std_logic_vector(11 downto 0);
		variable g1_lcl: std_logic_vector(11 downto 0);
		variable g01_lcl: unsigned(12 downto 0);
		variable b_lcl: std_logic_vector(11 downto 0);
		variable gr_lcl: unsigned(13 downto 0);

		variable enEobufB_lcl: std_logic;
		-- IP impl.rgbegr.vars --- REND

	begin
		if reset='1' then
			-- IP impl.rgbegr.asyncrst --- BEGIN
			stateRgbegr <= stateRgbegrInit;
			qrs <= 0;
			enEobufB <= '0';
			aEobufB <= 0;
			drdEvenbufBm1 <= (others => '0');
			drdOddbufBm1 <= (others => '0');
			rgbToManyAXIS_tvalid_sig <= '0';
			rgbToManyAXIS_tdata_sig <= (others => '0');
			rgbToManyAXIS_tlast_sig <= '1';
			gr <= (others => '0');

			-- IP impl.rgbegr.asyncrst --- END
			-- IP impl.rgbegr.asyncrst.cust --- IBEGIN
			col_lcl := 0;
			r_lcl := (others => '0');
			g0_lcl := (others => '0');
			g1_lcl := (others => '0');
			g01_lcl := (others => '0');
			b_lcl := (others => '0');
			gr_lcl := (others => '0');
			enEobufB_lcl := '0';
			-- IP impl.rgbegr.asyncrst.cust --- IEND

		elsif rising_edge(mclk) then
			if stateRgbegr=stateRgbegrInit then
				-- IP impl.rgbegr.syncrst --- BEGIN
				qrs <= 0;
				enEobufB <= '0';
				aEobufB <= 0;
				drdEvenbufBm1 <= (others => '0');
				drdOddbufBm1 <= (others => '0');
				rgbToManyAXIS_tvalid_sig <= '0';
				rgbToManyAXIS_tdata_sig <= (others => '0');
				rgbToManyAXIS_tlast_sig <= '1';
				gr <= (others => '0');

				-- IP impl.rgbegr.syncrst --- END
				-- IP impl.rgbegr.syncrst.cust --- IBEGIN
				col_lcl := 0;
				r_lcl := (others => '0');
				g0_lcl := (others => '0');
				g1_lcl := (others => '0');
				g01_lcl := (others => '0');
				b_lcl := (others => '0');
				gr_lcl := (others => '0');
				enEobufB_lcl := '0';
				-- IP impl.rgbegr.syncrst.cust --- IEND

				if vsync='1' then
					stateRgbegr <= stateRgbegrInit;

				else
					stateRgbegr <= stateRgbegrIdle;
				end if;

			elsif stateRgbegr=stateRgbegrIdle then
				if strbEgrstart='1' then
					enEobufB <= '1'; -- IP impl.rgbegr.idle.start --- ILINE

					stateRgbegr <= stateRgbegrLoad;
				end if;

			elsif stateRgbegr=stateRgbegrLoad then
				-- IP impl.rgbegr.load --- IBEGIN
				rgbToManyAXIS_tlast_sig <= '0';

				enEobufB <= '0';
				aEobufB <= aEobufB + 1;
				-- IP impl.rgbegr.load --- IEND

				stateRgbegr <= stateRgbegrRun;

			elsif stateRgbegr=stateRgbegrRun then
				-- IP impl.rgbegr.run.pre --- IBEGIN
				if qrs=0 then -- en at qrs 6
					r_lcl := drdEvenbufB(23 downto 12);
					g0_lcl := drdEvenbufB(11 downto 0);
					g1_lcl := drdOddbufB(23 downto 12);
					b_lcl := drdOddbufB(11 downto 0);
				elsif qrs=1 then
					r_lcl := drdEvenbufB(47 downto 36);
					g0_lcl := drdEvenbufB(35 downto 24);
					g1_lcl := drdOddbufB(47 downto 36);
					b_lcl := drdOddbufB(35 downto 24);
				elsif qrs=2 then -- en at qrs 0
					r_lcl := drdEvenbufB(7 downto 0) & drdEvenbufBm1(63 downto 60);
					g0_lcl := drdEvenbufBm1(59 downto 48);
					g1_lcl := drdOddbufB(7 downto 0) & drdOddbufBm1(63 downto 60);
					b_lcl := drdOddbufBm1(59 downto 48);
				elsif qrs=3 then
					r_lcl := drdEvenbufB(31 downto 20);
					g0_lcl := drdEvenbufB(19 downto 8);
					g1_lcl := drdOddbufB(31 downto 20);
					b_lcl := drdOddbufB(19 downto 8);
				elsif qrs=4 then
					r_lcl := drdEvenbufB(55 downto 44);
					g0_lcl := drdEvenbufB(43 downto 32);
					g1_lcl := drdOddbufB(55 downto 44);
					b_lcl := drdOddbufB(43 downto 32);
				elsif qrs=5 then -- en at qrs 3
					r_lcl := drdEvenbufB(15 downto 4);
					g0_lcl := drdEvenbufB(3 downto 0) & drdEvenbufBm1(63 downto 56);
					g1_lcl := drdOddbufB(15 downto 4);
					b_lcl := drdOddbufB(3 downto 0) & drdOddbufBm1(63 downto 56);
				elsif qrs=6 then
					r_lcl := drdEvenbufB(39 downto 28);
					g0_lcl := drdEvenbufB(27 downto 16);
					g1_lcl := drdOddbufB(39 downto 28);
					b_lcl := drdOddbufB(27 downto 16);
				elsif qrs=7 then
					r_lcl := drdEvenbufB(63 downto 52);
					g0_lcl := drdEvenbufB(51 downto 40);
					g1_lcl := drdOddbufB(63 downto 52);
					b_lcl := drdOddbufB(51 downto 40);
				end if;

				g01_lcl := resize(unsigned(g0_lcl), 13) + resize(unsigned(g1_lcl), 13);
				rgbToManyAXIS_tdata_sig <= r_lcl & std_logic_vector(g01_lcl(12 downto 1)) & b_lcl;

				gr_lcl := resize(unsigned(r_lcl), 14) + resize(unsigned(g0_lcl), 14) + resize(unsigned(g1_lcl), 14) + resize(unsigned(b_lcl), 14);
				gr <= std_logic_vector(gr_lcl(13 downto 2));

				if qrs=6 or qrs=0 or qrs=3 then
					enEobufB_lcl := '1';

					drdEvenbufBm1 <= drdEvenbufB;
					drdOddbufBm1 <= drdOddbufB;

				else
					enEobufB_lcl := '0';
				end if;

				if qrs=7 or qrs=1 or qrs=4 then
					aEobufB <= aEobufB + 1;
				end if;

				if qrs=7 then
					qrs <= 0;
				else
					qrs <= qrs + 1;
				end if;

				rgbToManyAXIS_tvalid_sig <= '1';

				col_lcl := col_lcl + 1; -- in next clock cycle
				-- IP impl.rgbegr.run.pre --- IEND

				if col_lcl=unsigned(NCol) then
					rgbToManyAXIS_tlast_sig <= '1'; -- IP impl.rgbegr.run.rowDone --- ILINE

					stateRgbegr <= stateRgbegrEol;

				else
					if sprsNotFull='0' then
						enEobufB <= enEobufB_lcl; -- IP impl.rgbegr.run.nextCol --- ILINE

						stateRgbegr <= stateRgbegrRun;

					else
						enEobufB <= '0'; -- IP impl.rgbegr.run.wait --- ILINE

						stateRgbegr <= stateRgbegrHold;
					end if;
				end if;

			elsif stateRgbegr=stateRgbegrHold then
				-- IP impl.rgbegr.hold --- IBEGIN
				enEobufB <= enEobufB_lcl;
				rgbToManyAXIS_tvalid_sig <= '0';
				-- IP impl.rgbegr.hold --- IEND

				stateRgbegr <= stateRgbegrRun;

			elsif stateRgbegr=stateRgbegrEol then
				rgbToManyAXIS_tvalid_sig <= '0'; -- IP impl.rgbegr.eol.pre --- ILINE

				if vsync='1' then
					stateRgbegr <= stateRgbegrInit;

				else
					-- IP impl.rgbegr.eol.nextRow --- IBEGIN
					qrs <= 0;

					enEobufB <= '0';
					aEobufB <= 0;

					col_lcl := 0;
					-- IP impl.rgbegr.eol.nextRow --- IEND

					stateRgbegr <= stateRgbegrIdle;
				end if;
			end if;
		end if;
	end process;
	-- IP impl.rgbegr.rising --- END

	------------------------------------------------------------------------
	-- implementation: other 
	------------------------------------------------------------------------

	
	-- IP impl.oth.cust --- INSERT

end Rtl;
