]> Joshua Wise's Git repositories - mandelfpga.git/blobdiff - Main.v
Cut 1 at triple pumping the pipeline
[mandelfpga.git] / Main.v
diff --git a/Main.v b/Main.v
index 306c8a75ba23b6da4790bc97c62430dd436cca52..61cb8f1d9991a72ae15261f8b2bd8781e6840108 100644 (file)
--- a/Main.v
+++ b/Main.v
@@ -1,4 +1,4 @@
-/*
+/* 
  * MandelFPGA
  * by Joshua Wise and Chris Lu
  * 
@@ -113,6 +113,7 @@ module MandelUnit(
        output reg [7:0] obail, ocuriter);
 
        wire [14:0] r2, i2, ri, diff;
+       wire [15:0] twocdiff;
        wire r2sign, i2sign, risign, dsign;
        wire [16:0] bigsum;
        wire bigsum_ovf, rin_ovf, iin_ovf, throwaway;
@@ -132,8 +133,9 @@ module MandelUnit(
        assign bigsum_ovf = bigsum[16] | bigsum[15] | bigsum[14];
        assign rin_ovf = rd;
        assign iin_ovf = id;
-       assign diff = (r2 > i2) ? r2 - i2 : i2 - r2;
-       assign dsign = (r2 > i2) ? 0 : 1;
+       assign twocdiff = r2 - i2;
+       assign diff = twocdiff[15] ? -twocdiff : twocdiff;
+       assign dsign = twocdiff[15];
 
        always @ (posedge clk)
        begin
@@ -196,7 +198,7 @@ module Mandelbrot(
        input [2:0] scale,
        output reg [2:0] red, green, output reg [1:0] blue);
 
-`define MAXOUTN 12
+`define MAXOUTN 11
        
        wire [12:0] rx, ry;
        wire [13:0] nx, ny;
@@ -221,51 +223,103 @@ module Mandelbrot(
        wire [7:0] initci, initb;
        wire initxs, initys, initrs, initis;
        
-       reg [14:0] loopx, loopy, loopr, loopi;
-       reg [7:0] loopci, loopb;
-       reg loopxs, loopys, looprs, loopis;
+       // Values after the number of iterations denoted by the subscript.
+       reg [14:0] stagex [2:1], stagey [2:1], stager [2:1], stagei [2:1];
+       reg [7:0] stageci [2:1], stageb [2:1];
+       reg stagexs [2:1], stageys [2:1], stagers [2:1], stageis [2:1];
        
-       reg state = 0;
+       reg [2:0] state = 3'b001;       // One-hot encoded state.
        
        // On pixclk = 1,
        //    A new value to be loaded comes in, and a value in need of loopback comes out.
        // On pixclk = 0,
        //    A new value in need of loopback comes in, and a completed value comes out.
        
-       assign initx = state ? rx : loopx;
-       assign inity = state ? ry : loopy;
-       assign initr = state ? rx : loopr;
-       assign initi = state ? ry : loopi;
-       assign initxs = state ? rxsign : loopxs;
-       assign initys = state ? rysign : loopys;
-       assign initrs = state ? rxsign : looprs;
-       assign initis = state ? rysign : loopis;
-       assign initb = state ? 8'b11111111 : loopb;
-       assign initci = state ? 8'b00000000 : loopci;
+       assign initx = state[0] ? rx :
+                      state[1] ? stagex[1] :
+                      stagex[2];
+       assign inity = state[0] ? ry :
+                      state[1] ? stagey[1] :
+                      stagey[2];
+       assign initr = state[0] ? rx :
+                      state[1] ? stager[1] :
+                      stager[2];
+       assign initi = state[0] ? ry :
+                      state[1] ? stagei[1] :
+                      stagei[2];
+       assign initxs = state[0] ? rxsign :
+                       state[1] ? stagexs[1] :
+                       stagexs[2];
+       assign initys = state[0] ? rysign :
+                       state[1] ? stageys[1] :
+                       stageys[2];
+       assign initrs = state[0] ? rxsign :
+                       state[1] ? stagers[1] :
+                       stagers[2];
+       assign initis = state[0] ? rysign :
+                       state[1] ? stageis[1] :
+                       stageis[2];
+       assign initb = state[0] ? 8'b11111111 :
+                      state[1] ? stageb[1] :
+                      stageb[2];
+       assign initci = state[0] ? 8'b00000000 :
+                       state[1] ? stageb[1] : 
+                       stageb[2];
        
        reg [7:0] out;
-       reg pixclksync;
-       always @(negedge mclk)
-               pixclksync <= ~pixclk;
+       reg typethea = 0;       // Whether we have typed the A.
+       reg statekick = 0;      // State needs to be kicked back to 3'b010 on the next mclk.
+
+       // This is guaranteed to converge after two pixclks.
+       //always @(negedge mclk)
+       //      if (pixclk && !typethea) begin
+       //              typethea <= 1;
+       //              statekick <= 1;
+       //      end else if (typethea) begin // This is the edge of the falling anus.
+       //              typethea <= 0;
+       //              statekick <= 0;
+       //      end
        
        always @(posedge mclk)
        begin
-               if (!state) begin
-                       out <= ~mb[`MAXOUTN] + colorofs;
-               end else begin
+               // Data output handling
+               if (state[0]) begin
                        {red, green, blue} <= {out[0],out[3],out[6],out[1],out[4],out[7],out[2],out[5]};
-                       loopx <= xprop[`MAXOUTN];
-                       loopy <= yprop[`MAXOUTN];
-                       loopr <= mr[`MAXOUTN];
-                       loopi <= mi[`MAXOUTN];
-                       loopxs <= xsprop[`MAXOUTN];
-                       loopys <= ysprop[`MAXOUTN];
-                       looprs <= mrs[`MAXOUTN];
-                       loopis <= mis[`MAXOUTN];
-                       loopb <= mb[`MAXOUTN];
-                       loopci <= curiter[`MAXOUTN];
                end
-               state <= ~pixclksync;
+               if (state[2]) begin
+                       out <= ~mb[`MAXOUTN] + colorofs;
+               end
+               
+               if (state[1]) begin             // PnR0 in, PnR2 out
+                       stagex[2] <= xprop[`MAXOUTN];
+                       stagey[2] <= yprop[`MAXOUTN];
+                       stager[2] <= mr[`MAXOUTN];
+                       stagei[2] <= mi[`MAXOUTN];
+                       stagexs[2] <= xsprop[`MAXOUTN];
+                       stageys[2] <= ysprop[`MAXOUTN];
+                       stagers[2] <= mrs[`MAXOUTN];
+                       stageis[2] <= mis[`MAXOUTN];
+                       stageb[2] <= mb[`MAXOUTN];
+                       stageci[2] <= curiter[`MAXOUTN];
+               end
+               
+               if (state[0]) begin     // PnR2 in, PnR1 out
+                       stagex[1] <= xprop[`MAXOUTN];
+                       stagey[1] <= yprop[`MAXOUTN];
+                       stager[1] <= mr[`MAXOUTN];
+                       stagei[1] <= mi[`MAXOUTN];
+                       stagexs[1] <= xsprop[`MAXOUTN];
+                       stageys[1] <= ysprop[`MAXOUTN];
+                       stagers[1] <= mrs[`MAXOUTN];
+                       stageis[1] <= mis[`MAXOUTN];
+                       stageb[1] <= mb[`MAXOUTN];
+                       stageci[1] <= curiter[`MAXOUTN];
+               end
+               
+               if (statekick)          // If a pixclk has happened, the state should be reset.
+                       state <= 3'b010;
+               else                                            // Otherwise, just poke it forward.
+                       state <= {state[1], state[0], state[2]};
        end
 
        MandelUnit mu0(
@@ -310,9 +364,6 @@ module Mandelbrot(
        MandelUnit mub(mclk,
                xprop[10], yprop[10], xsprop[10], ysprop[10], mr[10], mi[10], mrs[10], mis[10], mb[10], curiter[10],
                xprop[11], yprop[11], xsprop[11], ysprop[11], mr[11], mi[11], mrs[11], mis[11], mb[11], curiter[11]);
-       MandelUnit muc(mclk,
-               xprop[11], yprop[11], xsprop[11], ysprop[11], mr[11], mi[11], mrs[11], mis[11], mb[11], curiter[11],
-               xprop[12], yprop[12], xsprop[12], ysprop[12], mr[12], mi[12], mrs[12], mis[12], mb[12], curiter[12]);
 
 endmodule
 
@@ -342,10 +393,26 @@ module MandelTop(
        input left, right, up, down, rst, cycle, logooff,
        input [2:0] scale);
 
+
+       wire pixclk, mclk, gclk2, clk;
+       wire dcm1ok, dcm2ok;
+       assign dcmok = dcm1ok && dcm2ok;
+       
+       IBUFG typeA(.O(clk), .I(gclk));
+       
+       pixDCM dcm(                                     // CLKIN is 50MHz xtal, CLKFX_OUT is 25MHz
+               .CLKIN_IN(clk), 
+               .CLKFX_OUT(pixclk),
+               .LOCKED_OUT(dcm1ok)
+               );
+       
+       mandelDCM dcm2(
+               .CLKIN_IN(clk),
+               .CLKFX_OUT(mclk),
+               .LOCKED_OUT(dcm2ok)
+               );
+       
        wire border;
-       wire pixclk;
-       wire [7:0] zero = 8'b0;
-       wire clk;
        wire [11:0] x, y;
        reg [13:0] xofs = -`XRES/2, yofs = -`YRES/2;
        reg [5:0] slowctr = 0;
@@ -356,15 +423,10 @@ module MandelTop(
        wire [2:0] mandelr, mandelg, logor, logog;
        wire [1:0] mandelb, logob;
        
-       pixDCM dcm(                                     // CLKIN is 50MHz xtal, CLKFX_OUT is 25MHz
-               .CLKIN_IN(gclk), 
-               .CLKFX_OUT(pixclk),
-               .CLKIN_IBUFG_OUT(clk),
-               .LOCKED_OUT(dcmok)
-               );
+       
 
        SyncGen sync(pixclk, vs, hs, x, y, realx, realy, border);
-       Mandelbrot mandel(clk, pixclk, x, y, xofs, yofs, cycle ? colorcycle : 0, scale, mandelr, mandelg, mandelb);
+       Mandelbrot mandel(mclk, pixclk, x, y, xofs, yofs, cycle ? colorcycle : 0, scale, mandelr, mandelg, mandelb);
        Logo logo(pixclk, realx, realy, logoenb, logor, logog, logob);
        
        assign {red,green,blue} =
This page took 0.03062 seconds and 4 git commands to generate.