#!/usr/bin/env python3

from nexys_base import *

from litevideo.output.hdmi.s7 import S7HDMIOutEncoderSerializer, S7HDMIOutPHY


class VideoOutSoC(BaseSoC):
    def __init__(self, platform, *args, **kwargs):
        BaseSoC.__init__(self, platform, *args, **kwargs)

        pads = platform.request("hdmi_out")
        self.comb += pads.scl.eq(1)

        pixel_clk = Signal()
        pixel_clk_x5 = Signal()
        reset = Signal()

        vga_hsync = Signal()
        vga_vsync = Signal()
        vga_red = Signal(8)
        vga_green = Signal(8)
        vga_blue = Signal(8)
        vga_blank = Signal()

        # # #

        mmcm_locked = Signal()
        mmcm_fb = Signal()

        self.specials += Instance("MMCME2_BASE",
                     p_BANDWIDTH="OPTIMIZED", i_RST=0, o_LOCKED=mmcm_locked,

                     # VCO
                     p_REF_JITTER1=0.01, p_CLKIN1_PERIOD=10.0,
                     p_CLKFBOUT_MULT_F=30.0, p_CLKFBOUT_PHASE=0.000, p_DIVCLK_DIVIDE=4,
                     i_CLKIN1=self.crg.clk100, i_CLKFBIN=mmcm_fb, o_CLKFBOUT=mmcm_fb,

                     # CLK0
                     p_CLKOUT0_DIVIDE_F=5.0, p_CLKOUT0_PHASE=0.000, o_CLKOUT0=pixel_clk,
                     # CLK1
                     p_CLKOUT1_DIVIDE=1, p_CLKOUT1_PHASE=0.000, o_CLKOUT1=pixel_clk_x5,
        )
        self.comb += reset.eq(~mmcm_locked)

        # # #

        self.specials += Instance("vga_gen",
                i_pixel_clk=pixel_clk,

                o_vga_hsync=vga_hsync,
                o_vga_vsync=vga_vsync,
                o_vga_red=vga_red,
                o_vga_green=vga_green,
                o_vga_blue=vga_blue,
                o_vga_blank=vga_blank,
        )

        self.clock_domains.cd_pix = ClockDomain("pix")
        self.clock_domains.cd_pix5x = ClockDomain("pix5x", reset_less=True)
        self.comb += [
            self.cd_pix.clk.eq(pixel_clk),
            self.cd_pix.rst.eq(reset),
            self.cd_pix5x.clk.eq(pixel_clk_x5)
        ]

        self.submodules.hdmi_out_phy = S7HDMIOutPHY(pads)
        self.comb += [
            self.hdmi_out_phy.hsync.eq(vga_hsync),
            self.hdmi_out_phy.vsync.eq(vga_vsync),
            self.hdmi_out_phy.de.eq(~vga_blank),
            self.hdmi_out_phy.r.eq(vga_red),
            self.hdmi_out_phy.g.eq(vga_green),
            self.hdmi_out_phy.b.eq(vga_blue)
        ]
        self.submodules.clk_es = S7HDMIOutEncoderSerializer(pads.clk_p, pads.clk_n, bypass_encoder=True)
        self.comb += self.clk_es.data.eq(Signal(10, reset=0b0000011111))

        # # #

        platform.add_source_dir(os.path.join("gateware", "hdmi_out"))


def main():
    parser = argparse.ArgumentParser(description="Nexys LiteX SoC")
    builder_args(parser)
    soc_sdram_args(parser)
    parser.add_argument("--nocompile-gateware", action="store_true")
    args = parser.parse_args()

    platform = nexys.Platform()
    soc = VideoOutSoC(platform, **soc_sdram_argdict(args))
    builder = Builder(soc, output_dir="build",
                      compile_gateware=not args.nocompile_gateware,
                      csr_csv="test/csr.csv")
    vns = builder.build()

if __name__ == "__main__":
    main()


@@ -93,26 +93,117 @@
 IOut
-EncoderSerializer,
+Clocking%0Afrom litevideo.output.hdmi.s7 import S7HDMIOutEncoderSerializer%0Afrom litevideo.output.hdmi.s7 import
  S7H
@@ -437,95 +437,8 @@
 1)%0A%0A
-        pixel_clk = Signal()%0A        pixel_clk_x5 = Signal()%0A        reset = Signal()%0A%0A
     
@@ -627,66 +627,8 @@
  #%0A%0A
-        mmcm_locked = Signal()%0A        mmcm_fb = Signal()%0A
 %0A   
@@ -663,19 +663,15 @@
 ce(%22
-MMCME2_BASE
+vga_gen
 %22,%0A 
@@ -689,1255 +689,354 @@
     
-     p_BANDWIDTH=%22OPTIMIZED%22, i_RST=0, o_LOCKED=mmcm_locked,%0A%0A                     # VCO%0A                     p_REF_JITTER1=0.01, p_CLKIN1_PERIOD=10.0,%0A                     p_CLKFBOUT_MULT_F=30.0, p_CLKFBOUT_PHASE=0.000, p_DIVCLK_DIVIDE=4,%0A                     i_CLKIN1=self.crg.clk100, i_CLKFBIN=mmcm_fb, o_CLKFBOUT=mmcm_fb,%0A%0A                     # CLK0%0A                     p_CLKOUT0_DIVIDE_F=5.0, p_CLKOUT0_PHASE=0.000, o_CLKOUT0=pixel_clk,%0A                     # CLK1%0A                     p_CLKOUT1_DIVIDE=1, p_CLKOUT1_PHASE=0.000, o_CLKOUT1=pixel_clk_x5,%0A        )%0A        self.comb += reset.eq(~mmcm_locked)%0A%0A        # # #%0A%0A        self.specials += Instance(%22vga_gen%22,%0A                i_pixel_clk=pixel_clk,%0A%0A                o_vga_hsync=vga_hsync,%0A                o_vga_vsync=vga_vsync,%0A                o_vga_red=vga_red,%0A                o_vga_green=vga_green,%0A                o_vga_blue=vga_blue,%0A                o_vga_blank=vga_blank,%0A        )%0A%0A        self.clock_domains.cd_pix = ClockDomain(%22pix%22)%0A        self.clock_domains.cd_pix5x = ClockDomain(%22pix5x%22, reset_less=True)%0A        self.comb += %5B%0A            self.cd_pix.clk.eq(pixel_clk),%0A            self.cd_pix.rst.eq(reset),%0A            self.cd_pix5x.clk.eq(pixel_clk_x5)%0A        %5D%0A
+i_pixel_clk=ClockSignal(%22pix%22),%0A%0A                o_vga_hsync=vga_hsync,%0A                o_vga_vsync=vga_vsync,%0A                o_vga_red=vga_red,%0A                o_vga_green=vga_green,%0A                o_vga_blue=vga_blue,%0A                o_vga_blank=vga_blank,%0A        )%0A%0A        self.submodules.hdmi_clocking = S7HDMIOutClocking(self.crg.clk100)
 %0A   
@@ -1061,20 +1061,16 @@
 es.hdmi_
-out_
 phy = S7
@@ -1127,28 +1127,24 @@
   self.hdmi_
-out_
 phy.hsync.eq
@@ -1174,28 +1174,24 @@
   self.hdmi_
-out_
 phy.vsync.eq
@@ -1221,28 +1221,24 @@
   self.hdmi_
-out_
 phy.de.eq(~v
@@ -1266,28 +1266,24 @@
   self.hdmi_
-out_
 phy.r.eq(vga
@@ -1307,28 +1307,24 @@
   self.hdmi_
-out_
 phy.g.eq(vga
@@ -1358,12 +1358,8 @@
 dmi_
-out_
 phy.

move clocking to litevideo