summaryrefslogtreecommitdiff
path: root/techlibs/xilinx
diff options
context:
space:
mode:
Diffstat (limited to 'techlibs/xilinx')
-rw-r--r--techlibs/xilinx/Makefile.inc3
-rw-r--r--techlibs/xilinx/arith_map.v282
-rw-r--r--techlibs/xilinx/cells_map.v208
-rw-r--r--techlibs/xilinx/cells_sim.v178
-rw-r--r--techlibs/xilinx/cells_xtra.sh32
-rw-r--r--techlibs/xilinx/cells_xtra.v710
-rw-r--r--techlibs/xilinx/drams.txt24
-rw-r--r--techlibs/xilinx/drams_map.v34
-rw-r--r--techlibs/xilinx/ff_map.v42
-rw-r--r--techlibs/xilinx/lut2lut.v65
-rw-r--r--techlibs/xilinx/lut_map.v94
-rw-r--r--techlibs/xilinx/synth_xilinx.cc294
12 files changed, 1622 insertions, 344 deletions
diff --git a/techlibs/xilinx/Makefile.inc b/techlibs/xilinx/Makefile.inc
index 887ea27d..d68f03bb 100644
--- a/techlibs/xilinx/Makefile.inc
+++ b/techlibs/xilinx/Makefile.inc
@@ -28,7 +28,8 @@ $(eval $(call add_share_file,share/xilinx,techlibs/xilinx/brams_bb.v))
$(eval $(call add_share_file,share/xilinx,techlibs/xilinx/drams.txt))
$(eval $(call add_share_file,share/xilinx,techlibs/xilinx/drams_map.v))
$(eval $(call add_share_file,share/xilinx,techlibs/xilinx/arith_map.v))
-$(eval $(call add_share_file,share/xilinx,techlibs/xilinx/lut2lut.v))
+$(eval $(call add_share_file,share/xilinx,techlibs/xilinx/ff_map.v))
+$(eval $(call add_share_file,share/xilinx,techlibs/xilinx/lut_map.v))
$(eval $(call add_gen_share_file,share/xilinx,techlibs/xilinx/brams_init_36.vh))
$(eval $(call add_gen_share_file,share/xilinx,techlibs/xilinx/brams_init_32.vh))
diff --git a/techlibs/xilinx/arith_map.v b/techlibs/xilinx/arith_map.v
index 03719659..09a5f07e 100644
--- a/techlibs/xilinx/arith_map.v
+++ b/techlibs/xilinx/arith_map.v
@@ -17,6 +17,9 @@
*
*/
+// ============================================================================
+// LCU
+
(* techmap_celltype = "$lcu" *)
module _80_xilinx_lcu (P, G, CI, CO);
parameter WIDTH = 2;
@@ -28,10 +31,78 @@ module _80_xilinx_lcu (P, G, CI, CO);
wire _TECHMAP_FAIL_ = WIDTH <= 2;
+ genvar i;
+
+`ifdef _CLB_CARRY
+
+ localparam CARRY4_COUNT = (WIDTH + 3) / 4;
+ localparam MAX_WIDTH = CARRY4_COUNT * 4;
+ localparam PAD_WIDTH = MAX_WIDTH - WIDTH;
+
+ wire [MAX_WIDTH-1:0] S = {{PAD_WIDTH{1'b0}}, P & ~G};
+ wire [MAX_WIDTH-1:0] C = CO;
+
+ generate for (i = 0; i < CARRY4_COUNT; i = i + 1) begin:slice
+
+ // Partially occupied CARRY4
+ if ((i+1)*4 > WIDTH) begin
+
+ // First one
+ if (i == 0) begin
+ CARRY4 carry4_1st_part
+ (
+ .CYINIT(CI),
+ .CI (1'd0),
+ .DI (G [(Y_WIDTH - 1):i*4]),
+ .S (S [(Y_WIDTH - 1):i*4]),
+ .CO (CO[(Y_WIDTH - 1):i*4]),
+ );
+ // Another one
+ end else begin
+ CARRY4 carry4_part
+ (
+ .CYINIT(1'd0),
+ .CI (C [i*4 - 1]),
+ .DI (G [(Y_WIDTH - 1):i*4]),
+ .S (S [(Y_WIDTH - 1):i*4]),
+ .CO (CO[(Y_WIDTH - 1):i*4]),
+ );
+ end
+
+ // Fully occupied CARRY4
+ end else begin
+
+ // First one
+ if (i == 0) begin
+ CARRY4 carry4_1st_full
+ (
+ .CYINIT(CI),
+ .CI (1'd0),
+ .DI (G [((i+1)*4 - 1):i*4]),
+ .S (S [((i+1)*4 - 1):i*4]),
+ .CO (CO[((i+1)*4 - 1):i*4]),
+ );
+ // Another one
+ end else begin
+ CARRY4 carry4_full
+ (
+ .CYINIT(1'd0),
+ .CI (C [i*4 - 1]),
+ .DI (G [((i+1)*4 - 1):i*4]),
+ .S (S [((i+1)*4 - 1):i*4]),
+ .CO (CO[((i+1)*4 - 1):i*4]),
+ );
+ end
+
+ end
+
+ end endgenerate
+
+`elsif _EXPLICIT_CARRY
+
wire [WIDTH-1:0] C = {CO, CI};
wire [WIDTH-1:0] S = P & ~G;
- genvar i;
generate for (i = 0; i < WIDTH; i = i + 1) begin:slice
MUXCY muxcy (
.CI(C[i]),
@@ -40,8 +111,28 @@ module _80_xilinx_lcu (P, G, CI, CO);
.O(CO[i])
);
end endgenerate
+
+`else
+
+ wire [WIDTH-1:0] C = {CO, CI};
+ wire [WIDTH-1:0] S = P & ~G;
+
+ generate for (i = 0; i < WIDTH; i = i + 1) begin:slice
+ MUXCY muxcy (
+ .CI(C[i]),
+ .DI(G[i]),
+ .S(S[i]),
+ .O(CO[i])
+ );
+ end endgenerate
+`endif
+
endmodule
+
+// ============================================================================
+// ALU
+
(* techmap_celltype = "$alu" *)
module _80_xilinx_alu (A, B, CI, BI, X, Y, CO);
parameter A_SIGNED = 0;
@@ -49,6 +140,8 @@ module _80_xilinx_alu (A, B, CI, BI, X, Y, CO);
parameter A_WIDTH = 1;
parameter B_WIDTH = 1;
parameter Y_WIDTH = 1;
+ parameter _TECHMAP_CONSTVAL_CI_ = 0;
+ parameter _TECHMAP_CONSTMSK_CI_ = 0;
input [A_WIDTH-1:0] A;
input [B_WIDTH-1:0] B;
@@ -66,16 +159,189 @@ module _80_xilinx_alu (A, B, CI, BI, X, Y, CO);
wire [Y_WIDTH-1:0] AA = A_buf;
wire [Y_WIDTH-1:0] BB = BI ? ~B_buf : B_buf;
- wire [Y_WIDTH-1:0] P = AA ^ BB;
- wire [Y_WIDTH-1:0] G = AA & BB;
- wire [Y_WIDTH-1:0] C = {CO, CI};
- wire [Y_WIDTH-1:0] S = P & ~G;
+ genvar i;
+
+`ifdef _CLB_CARRY
+
+ localparam CARRY4_COUNT = (Y_WIDTH + 3) / 4;
+ localparam MAX_WIDTH = CARRY4_COUNT * 4;
+ localparam PAD_WIDTH = MAX_WIDTH - Y_WIDTH;
+
+ wire [MAX_WIDTH-1:0] S = {{PAD_WIDTH{1'b0}}, AA ^ BB};
+ wire [MAX_WIDTH-1:0] DI = {{PAD_WIDTH{1'b0}}, AA & BB};
+
+ wire [MAX_WIDTH-1:0] C = CO;
genvar i;
+ generate for (i = 0; i < CARRY4_COUNT; i = i + 1) begin:slice
+
+ // Partially occupied CARRY4
+ if ((i+1)*4 > Y_WIDTH) begin
+
+ // First one
+ if (i == 0) begin
+ CARRY4 #(.IS_INITIALIZED(1'd1)) carry4_1st_part
+ (
+ .CYINIT(CI),
+ .CI (1'd0),
+ .DI (DI[(Y_WIDTH - 1):i*4]),
+ .S (S [(Y_WIDTH - 1):i*4]),
+ .O (Y [(Y_WIDTH - 1):i*4]),
+ .CO (CO[(Y_WIDTH - 1):i*4])
+ );
+ // Another one
+ end else begin
+ CARRY4 carry4_part
+ (
+ .CYINIT(1'd0),
+ .CI (C [i*4 - 1]),
+ .DI (DI[(Y_WIDTH - 1):i*4]),
+ .S (S [(Y_WIDTH - 1):i*4]),
+ .O (Y [(Y_WIDTH - 1):i*4]),
+ .CO (CO[(Y_WIDTH - 1):i*4])
+ );
+ end
+
+ // Fully occupied CARRY4
+ end else begin
+
+ // First one
+ if (i == 0) begin
+ CARRY4 #(.IS_INITIALIZED(1'd1)) carry4_1st_full
+ (
+ .CYINIT(CI),
+ .CI (1'd0),
+ .DI (DI[((i+1)*4 - 1):i*4]),
+ .S (S [((i+1)*4 - 1):i*4]),
+ .O (Y [((i+1)*4 - 1):i*4]),
+ .CO (CO[((i+1)*4 - 1):i*4])
+ );
+ // Another one
+ end else begin
+ CARRY4 carry4_full
+ (
+ .CYINIT(1'd0),
+ .CI (C [i*4 - 1]),
+ .DI (DI[((i+1)*4 - 1):i*4]),
+ .S (S [((i+1)*4 - 1):i*4]),
+ .O (Y [((i+1)*4 - 1):i*4]),
+ .CO (CO[((i+1)*4 - 1):i*4])
+ );
+ end
+
+ end
+
+ end endgenerate
+
+`elsif _EXPLICIT_CARRY
+
+ wire [Y_WIDTH-1:0] S = AA ^ BB;
+ wire [Y_WIDTH-1:0] DI = AA & BB;
+
+ wire CINIT;
+ // Carry chain.
+ //
+ // VPR requires that the carry chain never hit the fabric. The CO input
+ // to this techmap is the carry outputs for synthesis, e.g. might hit the
+ // fabric.
+ //
+ // So we maintain two wire sets, CO_CHAIN is the carry that is for VPR,
+ // e.g. off fabric dedicated chain. CO is the carry outputs that are
+ // available to the fabric.
+ wire [Y_WIDTH-1:0] CO_CHAIN;
+ wire [Y_WIDTH-1:0] C = {CO_CHAIN, CINIT};
+
+ // If carry chain is being initialized to a constant, techmap the constant
+ // source. Otherwise techmap the fabric source.
+ generate for (i = 0; i < 1; i = i + 1) begin:slice
+ CARRY0 #(.CYINIT_FABRIC(1)) carry(
+ .CI_INIT(CI),
+ .DI(DI[0]),
+ .S(S[0]),
+ .CO_CHAIN(CO_CHAIN[0]),
+ .CO_FABRIC(CO[0]),
+ .O(Y[0])
+ );
+ end endgenerate
+
+ generate for (i = 1; i < Y_WIDTH-1; i = i + 1) begin:slice
+ if(i % 4 == 0) begin
+ CARRY0 carry (
+ .CI(C[i]),
+ .DI(DI[i]),
+ .S(S[i]),
+ .CO_CHAIN(CO_CHAIN[i]),
+ .CO_FABRIC(CO[i]),
+ .O(Y[i])
+ );
+ end
+ else
+ begin
+ CARRY carry (
+ .CI(C[i]),
+ .DI(DI[i]),
+ .S(S[i]),
+ .CO_CHAIN(CO_CHAIN[i]),
+ .CO_FABRIC(CO[i]),
+ .O(Y[i])
+ );
+ end
+ end endgenerate
+
+ generate for (i = Y_WIDTH-1; i < Y_WIDTH; i = i + 1) begin:slice
+ if(i % 4 == 0) begin
+ CARRY0 top_of_carry (
+ .CI(C[i]),
+ .DI(DI[i]),
+ .S(S[i]),
+ .CO_CHAIN(CO_CHAIN[i]),
+ .O(Y[i])
+ );
+ end
+ else
+ begin
+ CARRY top_of_carry (
+ .CI(C[i]),
+ .DI(DI[i]),
+ .S(S[i]),
+ .CO_CHAIN(CO_CHAIN[i]),
+ .O(Y[i])
+ );
+ end
+ // Turns out CO_FABRIC and O both use [ABCD]MUX, so provide
+ // a non-congested path to output the top of the carry chain.
+ // Registering the output of the CARRY block would solve this, but not
+ // all designs do that.
+ if((i+1) % 4 == 0) begin
+ CARRY0 carry_output (
+ .CI(CO_CHAIN[i]),
+ .DI(0),
+ .S(0),
+ .O(CO[i])
+ );
+ end
+ else
+ begin
+ CARRY carry_output (
+ .CI(CO_CHAIN[i]),
+ .DI(0),
+ .S(0),
+ .O(CO[i])
+ );
+ end
+ end endgenerate
+
+`else
+
+ wire [Y_WIDTH-1:0] S = AA ^ BB;
+ wire [Y_WIDTH-1:0] DI = AA & BB;
+
+ wire [Y_WIDTH-1:0] C = {CO, CI};
+
generate for (i = 0; i < Y_WIDTH; i = i + 1) begin:slice
MUXCY muxcy (
.CI(C[i]),
- .DI(G[i]),
+ .DI(DI[i]),
.S(S[i]),
.O(CO[i])
);
@@ -86,6 +352,8 @@ module _80_xilinx_alu (A, B, CI, BI, X, Y, CO);
);
end endgenerate
- assign X = P;
+`endif
+
+ assign X = S;
endmodule
diff --git a/techlibs/xilinx/cells_map.v b/techlibs/xilinx/cells_map.v
index 0771be0b..40789ddb 100644
--- a/techlibs/xilinx/cells_map.v
+++ b/techlibs/xilinx/cells_map.v
@@ -1,86 +1,156 @@
+/*
+ * yosys -- Yosys Open SYnthesis Suite
+ *
+ * Copyright (C) 2012 Clifford Wolf <clifford@clifford.at>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ */
-module \$_DFF_N_ (input D, C, output Q); FDRE #(.INIT(|0), .IS_C_INVERTED(|1), .IS_D_INVERTED(|0), .IS_R_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .R(1'b0)); endmodule
-module \$_DFF_P_ (input D, C, output Q); FDRE #(.INIT(|0), .IS_C_INVERTED(|0), .IS_D_INVERTED(|0), .IS_R_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .R(1'b0)); endmodule
+// Convert negative-polarity reset to positive-polarity
+(* techmap_celltype = "$_DFF_NN0_" *)
+module _90_dff_nn0_to_np0 (input D, C, R, output Q); \$_DFF_NP0_ _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .R(~R)); endmodule
+(* techmap_celltype = "$_DFF_PN0_" *)
+module _90_dff_pn0_to_pp0 (input D, C, R, output Q); \$_DFF_PP0_ _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .R(~R)); endmodule
+(* techmap_celltype = "$_DFF_NN1_" *)
+module _90_dff_nn1_to_np1 (input D, C, R, output Q); \$_DFF_NP1 _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .R(~R)); endmodule
+(* techmap_celltype = "$_DFF_PN1_" *)
+module _90_dff_pn1_to_pp1 (input D, C, R, output Q); \$_DFF_PP1 _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .R(~R)); endmodule
-module \$_DFFE_NP_ (input D, C, E, output Q); FDRE #(.INIT(|0), .IS_C_INVERTED(|1), .IS_D_INVERTED(|0), .IS_R_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(E), .R(1'b0)); endmodule
-module \$_DFFE_PP_ (input D, C, E, output Q); FDRE #(.INIT(|0), .IS_C_INVERTED(|0), .IS_D_INVERTED(|0), .IS_R_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(E), .R(1'b0)); endmodule
+module \$__SHREG_ (input C, input D, input E, output Q);
+ parameter DEPTH = 0;
+ parameter [DEPTH-1:0] INIT = 0;
+ parameter CLKPOL = 1;
+ parameter ENPOL = 2;
-module \$_DFF_NN0_ (input D, C, R, output Q); FDCE #(.INIT(|0), .IS_C_INVERTED(|1), .IS_D_INVERTED(|0), .IS_CLR_INVERTED(|1)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR(R)); endmodule
-module \$_DFF_NP0_ (input D, C, R, output Q); FDCE #(.INIT(|0), .IS_C_INVERTED(|1), .IS_D_INVERTED(|0), .IS_CLR_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR(R)); endmodule
-module \$_DFF_PN0_ (input D, C, R, output Q); FDCE #(.INIT(|0), .IS_C_INVERTED(|0), .IS_D_INVERTED(|0), .IS_CLR_INVERTED(|1)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR(R)); endmodule
-module \$_DFF_PP0_ (input D, C, R, output Q); FDCE #(.INIT(|0), .IS_C_INVERTED(|0), .IS_D_INVERTED(|0), .IS_CLR_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR(R)); endmodule
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH), .INIT(INIT), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) _TECHMAP_REPLACE_ (.C(C), .D(D), .L(DEPTH-1), .E(E), .Q(Q));
+endmodule
-module \$_DFF_NN1_ (input D, C, R, output Q); FDPE #(.INIT(|0), .IS_C_INVERTED(|1), .IS_D_INVERTED(|0), .IS_PRE_INVERTED(|1)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE(R)); endmodule
-module \$_DFF_NP1_ (input D, C, R, output Q); FDPE #(.INIT(|0), .IS_C_INVERTED(|1), .IS_D_INVERTED(|0), .IS_PRE_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE(R)); endmodule
-module \$_DFF_PN1_ (input D, C, R, output Q); FDPE #(.INIT(|0), .IS_C_INVERTED(|0), .IS_D_INVERTED(|0), .IS_PRE_INVERTED(|1)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE(R)); endmodule
-module \$_DFF_PP1_ (input D, C, R, output Q); FDPE #(.INIT(|0), .IS_C_INVERTED(|0), .IS_D_INVERTED(|0), .IS_PRE_INVERTED(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE(R)); endmodule
+module \$__XILINX_SHREG_ (input C, input D, input [31:0] L, input E, output Q, output SO);
+ parameter DEPTH = 0;
+ parameter [DEPTH-1:0] INIT = 0;
+ parameter CLKPOL = 1;
+ parameter ENPOL = 2;
-`ifndef NO_LUT
-module \$lut (A, Y);
- parameter WIDTH = 0;
- parameter LUT = 0;
+ // shregmap's INIT parameter shifts out LSB first;
+ // however Xilinx expects MSB first
+ function [DEPTH-1:0] brev;
+ input [DEPTH-1:0] din;
+ integer i;
+ begin
+ for (i = 0; i < DEPTH; i=i+1)
+ brev[i] = din[DEPTH-1-i];
+ end
+ endfunction
+ localparam [DEPTH-1:0] INIT_R = brev(INIT);
- input [WIDTH-1:0] A;
- output Y;
+ parameter _TECHMAP_CONSTMSK_L_ = 0;
+ parameter _TECHMAP_CONSTVAL_L_ = 0;
+ wire CE;
generate
- if (WIDTH == 1) begin
- LUT1 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
- .I0(A[0]));
- end else
- if (WIDTH == 2) begin
- LUT2 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
- .I0(A[0]), .I1(A[1]));
- end else
- if (WIDTH == 3) begin
- LUT3 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
- .I0(A[0]), .I1(A[1]), .I2(A[2]));
+ if (ENPOL == 0)
+ assign CE = ~E;
+ else if (ENPOL == 1)
+ assign CE = E;
+ else
+ assign CE = 1'b1;
+ if (DEPTH == 1) begin
+ if (CLKPOL)
+ FDRE #(.INIT(INIT_R)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(CE), .R(1'b0));
+ else
+ FDRE_1 #(.INIT(INIT_R)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(CE), .R(1'b0));
end else
- if (WIDTH == 4) begin
- LUT4 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]));
+ if (DEPTH <= 16) begin
+ SRL16E #(.INIT(INIT_R), .IS_CLK_INVERTED(~CLKPOL[0])) _TECHMAP_REPLACE_ (.A0(L[0]), .A1(L[1]), .A2(L[2]), .A3(L[3]), .CE(CE), .CLK(C), .D(D), .Q(Q));
end else
- if (WIDTH == 5) begin
- LUT5 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]));
+ if (DEPTH > 17 && DEPTH <= 32) begin
+ SRLC32E #(.INIT(INIT_R), .IS_CLK_INVERTED(~CLKPOL[0])) _TECHMAP_REPLACE_ (.A(L[4:0]), .CE(CE), .CLK(C), .D(D), .Q(Q));
end else
- if (WIDTH == 6) begin
- LUT6 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ if (DEPTH > 33 && DEPTH <= 64) begin
+ wire T0, T1, T2;
+ SRLC32E #(.INIT(INIT_R[32-1:0]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_0 (.A(L[4:0]), .CE(CE), .CLK(C), .D(D), .Q(T0), .Q31(T1));
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH-32), .INIT(INIT[DEPTH-32-1:0]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_1 (.C(C), .D(T1), .L(L), .E(E), .Q(T2));
+ if (&_TECHMAP_CONSTMSK_L_)
+ assign Q = T2;
+ else
+ MUXF7 fpga_mux_0 (.O(Q), .I0(T0), .I1(T2), .S(L[5]));
end else
- if (WIDTH == 7) begin
- wire T0, T1;
- LUT6 #(.INIT(LUT[63:0])) fpga_lut_0 (.O(T0),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
- LUT6 #(.INIT(LUT[127:64])) fpga_lut_1 (.O(T1),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
- MUXF7 fpga_mux_0 (.O(Y), .I0(T0), .I1(T1), .S(A[6]));
+ if (DEPTH > 65 && DEPTH <= 96) begin
+ wire T0, T1, T2, T3, T4, T5, T6;
+ SRLC32E #(.INIT(INIT_R[32-1:0]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_0 (.A(L[4:0]), .CE(CE), .CLK(C), .D(D), .Q(T0), .Q31(T1));
+ SRLC32E #(.INIT(INIT_R[64-1:32]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_1 (.A(L[4:0]), .CE(CE), .CLK(C), .D(T1), .Q(T2), .Q31(T3));
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH-64), .INIT(INIT[DEPTH-64-1:0]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_2 (.C(C), .D(T3), .L(L[4:0]), .E(E), .Q(T4));
+ if (&_TECHMAP_CONSTMSK_L_)
+ assign Q = T4;
+ else begin
+ MUXF7 fpga_mux_0 (.O(T5), .I0(T0), .I1(T2), .S(L[5]));
+ MUXF7 fpga_mux_1 (.O(T6), .I0(T4), .I1(1'b0 /* unused */), .S(L[5]));
+ MUXF8 fpga_mux_2 (.O(Q), .I0(T5), .I1(T6), .S(L[6]));
+ end
end else
- if (WIDTH == 8) begin
- wire T0, T1, T2, T3, T4, T5;
- LUT6 #(.INIT(LUT[63:0])) fpga_lut_0 (.O(T0),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
- LUT6 #(.INIT(LUT[127:64])) fpga_lut_1 (.O(T1),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
- LUT6 #(.INIT(LUT[191:128])) fpga_lut_2 (.O(T2),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
- LUT6 #(.INIT(LUT[255:192])) fpga_lut_3 (.O(T3),
- .I0(A[0]), .I1(A[1]), .I2(A[2]),
- .I3(A[3]), .I4(A[4]), .I5(A[5]));
- MUXF7 fpga_mux_0 (.O(T4), .I0(T0), .I1(T1), .S(A[6]));
- MUXF7 fpga_mux_1 (.O(T5), .I0(T2), .I1(T3), .S(A[6]));
- MUXF8 fpga_mux_2 (.O(Y), .I0(T4), .I1(T5), .S(A[7]));
- end else begin
- wire _TECHMAP_FAIL_ = 1;
+ if (DEPTH > 97 && DEPTH < 128) begin
+ wire T0, T1, T2, T3, T4, T5, T6, T7, T8;
+ SRLC32E #(.INIT(INIT_R[32-1:0]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_0 (.A(L[4:0]), .CE(CE), .CLK(C), .D(D), .Q(T0), .Q31(T1));
+ SRLC32E #(.INIT(INIT_R[64-1:32]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_1 (.A(L[4:0]), .CE(CE), .CLK(C), .D(T1), .Q(T2), .Q31(T3));
+ SRLC32E #(.INIT(INIT_R[96-1:64]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_2 (.A(L[4:0]), .CE(CE), .CLK(C), .D(T3), .Q(T4), .Q31(T5));
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH-96), .INIT(INIT[DEPTH-96-1:0]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_3 (.C(C), .D(T5), .L(L[4:0]), .E(E), .Q(T6));
+ if (&_TECHMAP_CONSTMSK_L_)
+ assign Q = T6;
+ else begin
+ MUXF7 fpga_mux_0 (.O(T7), .I0(T0), .I1(T2), .S(L[5]));
+ MUXF7 fpga_mux_1 (.O(T8), .I0(T4), .I1(T6), .S(L[5]));
+ MUXF8 fpga_mux_2 (.O(Q), .I0(T7), .I1(T8), .S(L[6]));
+ end
+ end
+ else if (DEPTH == 128) begin
+ wire T0, T1, T2, T3, T4, T5, T6;
+ SRLC32E #(.INIT(INIT_R[32-1:0]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_0 (.A(L[4:0]), .CE(CE), .CLK(C), .D(D), .Q(T0), .Q31(T1));
+ SRLC32E #(.INIT(INIT_R[64-1:32]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_1 (.A(L[4:0]), .CE(CE), .CLK(C), .D(T1), .Q(T2), .Q31(T3));
+ SRLC32E #(.INIT(INIT_R[96-1:64]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_2 (.A(L[4:0]), .CE(CE), .CLK(C), .D(T3), .Q(T4), .Q31(T5));
+ SRLC32E #(.INIT(INIT_R[128-1:96]), .IS_CLK_INVERTED(~CLKPOL[0])) fpga_srl_3 (.A(L[4:0]), .CE(CE), .CLK(C), .D(T5), .Q(T6), .Q31(SO));
+ if (&_TECHMAP_CONSTMSK_L_)
+ assign Q = T6;
+ else begin
+ wire T7, T8;
+ MUXF7 fpga_mux_0 (.O(T7), .I0(T0), .I1(T2), .S(L[5]));
+ MUXF7 fpga_mux_1 (.O(T8), .I0(T4), .I1(T6), .S(L[5]));
+ MUXF8 fpga_mux_2 (.O(Q), .I0(T7), .I1(T8), .S(L[6]));
+ end
+ end
+ else if (DEPTH <= 129 && ~&_TECHMAP_CONSTMSK_L_) begin
+ // Handle cases where fixed-length depth is
+ // just 1 over a convenient value
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH+1), .INIT({INIT,1'b0}), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) _TECHMAP_REPLACE_ (.C(C), .D(D), .L(L), .E(E), .Q(Q));
+ end
+ else begin
+ localparam lower_clog2 = $clog2((DEPTH+1)/2);
+ localparam lower_depth = 2 ** lower_clog2;
+ wire T0, T1, T2, T3;
+ if (&_TECHMAP_CONSTMSK_L_) begin
+ \$__XILINX_SHREG_ #(.DEPTH(lower_depth), .INIT(INIT[DEPTH-1:DEPTH-lower_depth]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_0 (.C(C), .D(D), .L(lower_depth-1), .E(E), .Q(T0));
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH-lower_depth), .INIT(INIT[DEPTH-lower_depth-1:0]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_1 (.C(C), .D(T0), .L(DEPTH-lower_depth-1), .E(E), .Q(Q), .SO(T3));
+ end
+ else begin
+ \$__XILINX_SHREG_ #(.DEPTH(lower_depth), .INIT(INIT[DEPTH-1:DEPTH-lower_depth]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_0 (.C(C), .D(D), .L(L[lower_clog2-1:0]), .E(E), .Q(T0), .SO(T1));
+ \$__XILINX_SHREG_ #(.DEPTH(DEPTH-lower_depth), .INIT(INIT[DEPTH-lower_depth-1:0]), .CLKPOL(CLKPOL), .ENPOL(ENPOL)) fpga_srl_1 (.C(C), .D(T1), .L(L[lower_clog2-1:0]), .E(E), .Q(T2), .SO(T3));
+ assign Q = L[lower_clog2] ? T2 : T0;
+ end
+ if (DEPTH == 2 * lower_depth)
+ assign SO = T3;
end
endgenerate
endmodule
+
+`ifndef SRL_ONLY
`endif
diff --git a/techlibs/xilinx/cells_sim.v b/techlibs/xilinx/cells_sim.v
index eba17ac9..f4598dcf 100644
--- a/techlibs/xilinx/cells_sim.v
+++ b/techlibs/xilinx/cells_sim.v
@@ -1,3 +1,21 @@
+/*
+ * yosys -- Yosys Open SYnthesis Suite
+ *
+ * Copyright (C) 2012 Clifford Wolf <clifford@clifford.at>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ */
// See Xilinx UG953 and UG474 for a description of the cell types below.
// http://www.xilinx.com/support/documentation/user_guides/ug474_7Series_CLB.pdf
@@ -12,10 +30,15 @@ module GND(output G);
endmodule
module IBUF(output O, input I);
+ parameter IOSTANDARD = "default";
+ parameter IBUF_LOW_PWR = 0;
assign O = I;
endmodule
module OBUF(output O, input I);
+ parameter IOSTANDARD = "default";
+ parameter DRIVE = 12;
+ parameter SLEW = "SLOW";
assign O = I;
endmodule
@@ -23,6 +46,42 @@ module BUFG(output O, input I);
assign O = I;
endmodule
+module BUFGCTRL(
+ output O,
+ input I0, input I1,
+ input S0, input S1,
+ input CE0, input CE1,
+ input IGNORE0, input IGNORE1);
+
+parameter [0:0] INIT_OUT = 1'b0;
+parameter PRESELECT_I0 = "FALSE";
+parameter PRESELECT_I1 = "FALSE";
+parameter [0:0] IS_CE0_INVERTED = 1'b0;
+parameter [0:0] IS_CE1_INVERTED = 1'b0;
+parameter [0:0] IS_S0_INVERTED = 1'b0;
+parameter [0:0] IS_S1_INVERTED = 1'b0;
+parameter [0:0] IS_IGNORE0_INVERTED = 1'b0;
+parameter [0:0] IS_IGNORE1_INVERTED = 1'b0;
+
+wire I0_internal = ((CE0 ^ IS_CE0_INVERTED) ? I0 : INIT_OUT);
+wire I1_internal = ((CE1 ^ IS_CE1_INVERTED) ? I1 : INIT_OUT);
+wire S0_true = (S0 ^ IS_S0_INVERTED);
+wire S1_true = (S1 ^ IS_S1_INVERTED);
+
+assign O = S0_true ? I0_internal : (S1_true ? I1_internal : INIT_OUT);
+
+endmodule
+
+module BUFHCE(output O, input I, input CE);
+
+parameter [0:0] INIT_OUT = 1'b0;
+parameter CE_TYPE = "SYNC";
+parameter [0:0] IS_CE_INVERTED = 1'b0;
+
+assign O = ((CE ^ IS_CE_INVERTED) ? I : INIT_OUT);
+
+endmodule
+
// module OBUFT(output O, input I, T);
// assign O = T ? 1'bz : I;
// endmodule
@@ -80,6 +139,22 @@ module LUT6(output O, input I0, I1, I2, I3, I4, I5);
assign O = I0 ? s1[1] : s1[0];
endmodule
+module LUT6_2(output O6, output O5, input I0, I1, I2, I3, I4, I5);
+ parameter [63:0] INIT = 0;
+ wire [31: 0] s5 = I5 ? INIT[63:32] : INIT[31: 0];
+ wire [15: 0] s4 = I4 ? s5[31:16] : s5[15: 0];
+ wire [ 7: 0] s3 = I3 ? s4[15: 8] : s4[ 7: 0];
+ wire [ 3: 0] s2 = I2 ? s3[ 7: 4] : s3[ 3: 0];
+ wire [ 1: 0] s1 = I1 ? s2[ 3: 2] : s2[ 1: 0];
+ assign O6 = I0 ? s1[1] : s1[0];
+
+ wire [15: 0] s5_4 = I4 ? INIT[31:16] : INIT[15: 0];
+ wire [ 7: 0] s5_3 = I3 ? s5_4[15: 8] : s5_4[ 7: 0];
+ wire [ 3: 0] s5_2 = I2 ? s5_3[ 7: 4] : s5_3[ 3: 0];
+ wire [ 1: 0] s5_1 = I1 ? s5_2[ 3: 2] : s5_2[ 1: 0];
+ assign O5 = I0 ? s5_1[1] : s5_1[0];
+endmodule
+
module MUXCY(output O, input CI, DI, S);
assign O = S ? CI : DI;
endmodule
@@ -104,6 +179,29 @@ module CARRY4(output [3:0] CO, O, input CI, CYINIT, input [3:0] DI, S);
assign CO[3] = S[3] ? CO[2] : DI[3];
endmodule
+`ifdef _EXPLICIT_CARRY
+
+module CARRY0(output CO_CHAIN, CO_FABRIC, O, input CI, CI_INIT, DI, S);
+ parameter CYINIT_FABRIC = 0;
+ wire CI_COMBINE;
+ if(CYINIT_FABRIC) begin
+ assign CI_COMBINE = CI_INIT;
+ end else begin
+ assign CI_COMBINE = CI;
+ end
+ assign CO_CHAIN = S ? CI_COMBINE : DI;
+ assign CO_FABRIC = S ? CI_COMBINE : DI;
+ assign O = S ^ CI_COMBINE;
+endmodule
+
+module CARRY(output CO_CHAIN, CO_FABRIC, O, input CI, DI, S);
+ assign CO_CHAIN = S ? CI : DI;
+ assign CO_FABRIC = S ? CI : DI;
+ assign O = S ^ CI;
+endmodule
+
+`endif
+
module FDRE (output reg Q, input C, CE, D, R);
parameter [0:0] INIT = 1'b0;
parameter [0:0] IS_C_INVERTED = 1'b0;
@@ -156,6 +254,47 @@ module FDPE (output reg Q, input C, CE, D, PRE);
endcase endgenerate
endmodule
+module FDRE_1 (output reg Q, input C, CE, D, R);
+ parameter [0:0] INIT = 1'b0;
+ initial Q <= INIT;
+ always @(negedge C) if (R) Q <= 1'b0; else if(CE) Q <= D;
+endmodule
+
+module FDSE_1 (output reg Q, input C, CE, D, S);
+ parameter [0:0] INIT = 1'b1;
+ initial Q <= INIT;
+ always @(negedge C) if (S) Q <= 1'b1; else if(CE) Q <= D;
+endmodule
+
+module FDCE_1 (output reg Q, input C, CE, D, CLR);
+ parameter [0:0] INIT = 1'b0;
+ initial Q <= INIT;
+ always @(negedge C, posedge CLR) if (CLR) Q <= 1'b0; else if (CE) Q <= D;
+endmodule
+
+module FDPE_1 (output reg Q, input C, CE, D, PRE);
+ parameter [0:0] INIT = 1'b1;
+ initial Q <= INIT;
+ always @(negedge C, posedge PRE) if (PRE) Q <= 1'b1; else if (CE) Q <= D;
+endmodule
+
+module RAM32X1D (
+ output DPO, SPO,
+ input D, WCLK, WE,
+ input A0, A1, A2, A3, A4,
+ input DPRA0, DPRA1, DPRA2, DPRA3, DPRA4
+);
+ parameter INIT = 32'h0;
+ parameter IS_WCLK_INVERTED = 1'b0;
+ wire [4:0] a = {A4, A3, A2, A1, A0};
+ wire [4:0] dpra = {DPRA4, DPRA3, DPRA2, DPRA1, DPRA0};
+ reg [31:0] mem = INIT;
+ assign SPO = mem[a];
+ assign DPO = mem[dpra];
+ wire clk = WCLK ^ IS_WCLK_INVERTED;
+ always @(posedge clk) if (WE) mem[a] <= D;
+endmodule
+
module RAM64X1D (
output DPO, SPO,
input D, WCLK, WE,
@@ -186,3 +325,42 @@ module RAM128X1D (
wire clk = WCLK ^ IS_WCLK_INVERTED;
always @(posedge clk) if (WE) mem[A] <= D;
endmodule
+
+module SRL16E (
+ output Q,
+ input A0, A1, A2, A3, CE, CLK, D
+);
+ parameter [15:0] INIT = 16'h0000;
+ parameter [0:0] IS_CLK_INVERTED = 1'b0;
+
+ reg [15:0] r = INIT;
+ assign Q = r[{A3,A2,A1,A0}];
+ generate
+ if (IS_CLK_INVERTED) begin
+ always @(negedge CLK) if (CE) r <= { r[14:0], D };
+ end
+ else
+ always @(posedge CLK) if (CE) r <= { r[14:0], D };
+ endgenerate
+endmodule
+
+module SRLC32E (
+ output Q,
+ output Q31,
+ input [4:0] A,
+ input CE, CLK, D
+);
+ parameter [31:0] INIT = 32'h00000000;
+ parameter [0:0] IS_CLK_INVERTED = 1'b0;
+
+ reg [31:0] r = INIT;
+ assign Q31 = r[31];
+ assign Q = r[A];
+ generate
+ if (IS_CLK_INVERTED) begin
+ always @(negedge CLK) if (CE) r <= { r[30:0], D };
+ end
+ else
+ always @(posedge CLK) if (CE) r <= { r[30:0], D };
+ endgenerate
+endmodule
diff --git a/techlibs/xilinx/cells_xtra.sh b/techlibs/xilinx/cells_xtra.sh
index c7ad1604..83863bf0 100644
--- a/techlibs/xilinx/cells_xtra.sh
+++ b/techlibs/xilinx/cells_xtra.sh
@@ -1,13 +1,14 @@
#!/bin/bash
set -e
-libdir="/opt/Xilinx/Vivado/2015.4/data/verilog/src"
+libdir="/opt/Xilinx/Vivado/2018.1/data/verilog/src"
function xtract_cell_decl()
{
for dir in $libdir/xeclib $libdir/retarget; do
[ -f $dir/$1.v ] || continue
- egrep '^\s*((end)?module|parameter|input|output|(end)?function|(end)?task)' $dir/$1.v |
+ [ -z "$2" ] || echo $2
+ egrep '^\s*((end)?module|parameter|input|inout|output|(end)?function|(end)?task)' $dir/$1.v |
sed -re '/UNPLACED/ d; /^\s*function/,/endfunction/ d; /^\s*task/,/endtask/ d;
s,//.*,,; s/#?\(.*/(...);/; s/^(input|output|parameter)/ \1/;
s/\s+$//; s/,$/;/; /input|output|parameter/ s/[^;]$/&;/; s/\s+/ /g;
@@ -27,20 +28,20 @@ function xtract_cell_decl()
# xtract_cell_decl BUFG
xtract_cell_decl BUFGCE
xtract_cell_decl BUFGCE_1
- xtract_cell_decl BUFGCTRL
+ #xtract_cell_decl BUFGCTRL
xtract_cell_decl BUFGMUX
xtract_cell_decl BUFGMUX_1
xtract_cell_decl BUFGMUX_CTRL
xtract_cell_decl BUFH
- xtract_cell_decl BUFHCE
+ #xtract_cell_decl BUFHCE
xtract_cell_decl BUFIO
xtract_cell_decl BUFMR
xtract_cell_decl BUFMRCE
xtract_cell_decl BUFR
- xtract_cell_decl CAPTUREE2
+ xtract_cell_decl CAPTUREE2 "(* keep *)"
# xtract_cell_decl CARRY4
xtract_cell_decl CFGLUT5
- xtract_cell_decl DCIRESET
+ xtract_cell_decl DCIRESET "(* keep *)"
xtract_cell_decl DNA_PORT
xtract_cell_decl DSP48E1
xtract_cell_decl EFUSE_USR
@@ -67,10 +68,10 @@ function xtract_cell_decl()
xtract_cell_decl IBUFDS_GTE2
xtract_cell_decl IBUFDS_IBUFDISABLE
xtract_cell_decl IBUFDS_INTERMDISABLE
- xtract_cell_decl ICAPE2
+ xtract_cell_decl ICAPE2 "(* keep *)"
xtract_cell_decl IDDR
xtract_cell_decl IDDR_2CLK
- xtract_cell_decl IDELAYCTRL
+ xtract_cell_decl IDELAYCTRL "(* keep *)"
xtract_cell_decl IDELAYE2
xtract_cell_decl IN_FIFO
xtract_cell_decl IOBUF
@@ -91,7 +92,7 @@ function xtract_cell_decl()
# xtract_cell_decl LUT4
# xtract_cell_decl LUT5
# xtract_cell_decl LUT6
- xtract_cell_decl LUT6_2
+ #xtract_cell_decl LUT6_2
xtract_cell_decl MMCME2_ADV
xtract_cell_decl MMCME2_BASE
# xtract_cell_decl MUXF7
@@ -112,18 +113,19 @@ function xtract_cell_decl()
xtract_cell_decl PHY_CONTROL
xtract_cell_decl PLLE2_ADV
xtract_cell_decl PLLE2_BASE
+ xtract_cell_decl PS7 "(* keep *)"
xtract_cell_decl PULLDOWN
xtract_cell_decl PULLUP
- # xtract_cell_decl RAM128X1D
+ #xtract_cell_decl RAM128X1D
xtract_cell_decl RAM128X1S
xtract_cell_decl RAM256X1S
xtract_cell_decl RAM32M
- xtract_cell_decl RAM32X1D
+ #xtract_cell_decl RAM32X1D
xtract_cell_decl RAM32X1S
xtract_cell_decl RAM32X1S_1
xtract_cell_decl RAM32X2S
xtract_cell_decl RAM64M
- # xtract_cell_decl RAM64X1D
+ xtract_cell_decl RAM64X1D
xtract_cell_decl RAM64X1S
xtract_cell_decl RAM64X1S_1
xtract_cell_decl RAM64X2S
@@ -133,9 +135,9 @@ function xtract_cell_decl()
xtract_cell_decl ROM256X1
xtract_cell_decl ROM32X1
xtract_cell_decl ROM64X1
- xtract_cell_decl SRL16E
- xtract_cell_decl SRLC32E
- xtract_cell_decl STARTUPE2
+ #xtract_cell_decl SRL16E
+ #xtract_cell_decl SRLC32E
+ xtract_cell_decl STARTUPE2 "(* keep *)"
xtract_cell_decl USR_ACCESSE2
xtract_cell_decl XADC
} > cells_xtra.new
diff --git a/techlibs/xilinx/cells_xtra.v b/techlibs/xilinx/cells_xtra.v
index a2dd01ad..6220da70 100644
--- a/techlibs/xilinx/cells_xtra.v
+++ b/techlibs/xilinx/cells_xtra.v
@@ -30,29 +30,6 @@ module BUFGCE_1 (...);
input CE, I;
endmodule
-module BUFGCTRL (...);
- output O;
- input CE0;
- input CE1;
- input I0;
- input I1;
- input IGNORE0;
- input IGNORE1;
- input S0;
- input S1;
- parameter integer INIT_OUT = 0;
- parameter PRESELECT_I0 = "FALSE";
- parameter PRESELECT_I1 = "FALSE";
- parameter [0:0] IS_CE0_INVERTED = 1'b0;
- parameter [0:0] IS_CE1_INVERTED = 1'b0;
- parameter [0:0] IS_I0_INVERTED = 1'b0;
- parameter [0:0] IS_I1_INVERTED = 1'b0;
- parameter [0:0] IS_IGNORE0_INVERTED = 1'b0;
- parameter [0:0] IS_IGNORE1_INVERTED = 1'b0;
- parameter [0:0] IS_S0_INVERTED = 1'b0;
- parameter [0:0] IS_S1_INVERTED = 1'b0;
-endmodule
-
module BUFGMUX (...);
parameter CLK_SEL_TYPE = "SYNC";
output O;
@@ -77,15 +54,6 @@ module BUFH (...);
input I;
endmodule
-module BUFHCE (...);
- parameter CE_TYPE = "SYNC";
- parameter integer INIT_OUT = 0;
- parameter [0:0] IS_CE_INVERTED = 1'b0;
- output O;
- input CE;
- input I;
-endmodule
-
module BUFIO (...);
output O;
input I;
@@ -114,6 +82,7 @@ module BUFR (...);
parameter SIM_DEVICE = "7SERIES";
endmodule
+(* keep *)
module CAPTUREE2 (...);
parameter ONESHOT = "TRUE";
input CAP;
@@ -130,6 +99,7 @@ module CFGLUT5 (...);
input CDI, CE, CLK;
endmodule
+(* keep *)
module DCIRESET (...);
output LOCKED;
input RST;
@@ -2102,6 +2072,7 @@ module IBUFDS_INTERMDISABLE (...);
input INTERMDISABLE;
endmodule
+(* keep *)
module ICAPE2 (...);
parameter [31:0] DEVICE_ID = 32'h04244093;
parameter ICAP_WIDTH = "X32";
@@ -2149,6 +2120,7 @@ module IDDR_2CLK (...);
input S;
endmodule
+(* keep *)
module IDELAYCTRL (...);
parameter SIM_DEVICE = "7SERIES";
output RDY;
@@ -2225,6 +2197,7 @@ module IOBUF (...);
parameter IOSTANDARD = "DEFAULT";
parameter SLEW = "SLOW";
output O;
+ inout IO;
input I, T;
endmodule
@@ -2236,6 +2209,7 @@ module IOBUF_DCIEN (...);
parameter SLEW = "SLOW";
parameter USE_IBUFDISABLE = "TRUE";
output O;
+ inout IO;
input DCITERMDISABLE;
input I;
input IBUFDISABLE;
@@ -2250,6 +2224,7 @@ module IOBUF_INTERMDISABLE (...);
parameter SLEW = "SLOW";
parameter USE_IBUFDISABLE = "TRUE";
output O;
+ inout IO;
input I;
input IBUFDISABLE;
input INTERMDISABLE;
@@ -2263,6 +2238,7 @@ module IOBUFDS (...);
parameter IOSTANDARD = "DEFAULT";
parameter SLEW = "SLOW";
output O;
+ inout IO, IOB;
input I, T;
endmodule
@@ -2275,6 +2251,8 @@ module IOBUFDS_DCIEN (...);
parameter SLEW = "SLOW";
parameter USE_IBUFDISABLE = "TRUE";
output O;
+ inout IO;
+ inout IOB;
input DCITERMDISABLE;
input I;
input IBUFDISABLE;
@@ -2288,6 +2266,8 @@ module IOBUFDS_DIFF_OUT (...);
parameter IOSTANDARD = "DEFAULT";
output O;
output OB;
+ inout IO;
+ inout IOB;
input I;
input TM;
input TS;
@@ -2302,6 +2282,8 @@ module IOBUFDS_DIFF_OUT_DCIEN (...);
parameter USE_IBUFDISABLE = "TRUE";
output O;
output OB;
+ inout IO;
+ inout IOB;
input DCITERMDISABLE;
input I;
input IBUFDISABLE;
@@ -2318,6 +2300,8 @@ module IOBUFDS_DIFF_OUT_INTERMDISABLE (...);
parameter USE_IBUFDISABLE = "TRUE";
output O;
output OB;
+ inout IO;
+ inout IOB;
input I;
input IBUFDISABLE;
input INTERMDISABLE;
@@ -2381,6 +2365,7 @@ module ISERDESE2 (...);
endmodule
module KEEPER (...);
+ inout O;
endmodule
module LDCE (...);
@@ -2403,12 +2388,6 @@ module LDPE (...);
input D, G, GE, PRE;
endmodule
-module LUT6_2 (...);
- parameter [63:0] INIT = 64'h0000000000000000;
- input I0, I1, I2, I3, I4, I5;
- output O5, O6;
-endmodule
-
module MMCME2_ADV (...);
parameter BANDWIDTH = "OPTIMIZED";
parameter real CLKFBOUT_MULT_F = 5.000;
@@ -3044,6 +3023,630 @@ module PLLE2_BASE (...);
input RST;
endmodule
+(* keep *)
+module PS7 (...);
+ output DMA0DAVALID;
+ output DMA0DRREADY;
+ output DMA0RSTN;
+ output DMA1DAVALID;
+ output DMA1DRREADY;
+ output DMA1RSTN;
+ output DMA2DAVALID;
+ output DMA2DRREADY;
+ output DMA2RSTN;
+ output DMA3DAVALID;
+ output DMA3DRREADY;
+ output DMA3RSTN;
+ output EMIOCAN0PHYTX;
+ output EMIOCAN1PHYTX;
+ output EMIOENET0GMIITXEN;
+ output EMIOENET0GMIITXER;
+ output EMIOENET0MDIOMDC;
+ output EMIOENET0MDIOO;
+ output EMIOENET0MDIOTN;
+ output EMIOENET0PTPDELAYREQRX;
+ output EMIOENET0PTPDELAYREQTX;
+ output EMIOENET0PTPPDELAYREQRX;
+ output EMIOENET0PTPPDELAYREQTX;
+ output EMIOENET0PTPPDELAYRESPRX;
+ output EMIOENET0PTPPDELAYRESPTX;
+ output EMIOENET0PTPSYNCFRAMERX;
+ output EMIOENET0PTPSYNCFRAMETX;
+ output EMIOENET0SOFRX;
+ output EMIOENET0SOFTX;
+ output EMIOENET1GMIITXEN;
+ output EMIOENET1GMIITXER;
+ output EMIOENET1MDIOMDC;
+ output EMIOENET1MDIOO;
+ output EMIOENET1MDIOTN;
+ output EMIOENET1PTPDELAYREQRX;
+ output EMIOENET1PTPDELAYREQTX;
+ output EMIOENET1PTPPDELAYREQRX;
+ output EMIOENET1PTPPDELAYREQTX;
+ output EMIOENET1PTPPDELAYRESPRX;
+ output EMIOENET1PTPPDELAYRESPTX;
+ output EMIOENET1PTPSYNCFRAMERX;
+ output EMIOENET1PTPSYNCFRAMETX;
+ output EMIOENET1SOFRX;
+ output EMIOENET1SOFTX;
+ output EMIOI2C0SCLO;
+ output EMIOI2C0SCLTN;
+ output EMIOI2C0SDAO;
+ output EMIOI2C0SDATN;
+ output EMIOI2C1SCLO;
+ output EMIOI2C1SCLTN;
+ output EMIOI2C1SDAO;
+ output EMIOI2C1SDATN;
+ output EMIOPJTAGTDO;
+ output EMIOPJTAGTDTN;
+ output EMIOSDIO0BUSPOW;
+ output EMIOSDIO0CLK;
+ output EMIOSDIO0CMDO;
+ output EMIOSDIO0CMDTN;
+ output EMIOSDIO0LED;
+ output EMIOSDIO1BUSPOW;
+ output EMIOSDIO1CLK;
+ output EMIOSDIO1CMDO;
+ output EMIOSDIO1CMDTN;
+ output EMIOSDIO1LED;
+ output EMIOSPI0MO;
+ output EMIOSPI0MOTN;
+ output EMIOSPI0SCLKO;
+ output EMIOSPI0SCLKTN;
+ output EMIOSPI0SO;
+ output EMIOSPI0SSNTN;
+ output EMIOSPI0STN;
+ output EMIOSPI1MO;
+ output EMIOSPI1MOTN;
+ output EMIOSPI1SCLKO;
+ output EMIOSPI1SCLKTN;
+ output EMIOSPI1SO;
+ output EMIOSPI1SSNTN;
+ output EMIOSPI1STN;
+ output EMIOTRACECTL;
+ output EMIOUART0DTRN;
+ output EMIOUART0RTSN;
+ output EMIOUART0TX;
+ output EMIOUART1DTRN;
+ output EMIOUART1RTSN;
+ output EMIOUART1TX;
+ output EMIOUSB0VBUSPWRSELECT;
+ output EMIOUSB1VBUSPWRSELECT;
+ output EMIOWDTRSTO;
+ output EVENTEVENTO;
+ output MAXIGP0ARESETN;
+ output MAXIGP0ARVALID;
+ output MAXIGP0AWVALID;
+ output MAXIGP0BREADY;
+ output MAXIGP0RREADY;
+ output MAXIGP0WLAST;
+ output MAXIGP0WVALID;
+ output MAXIGP1ARESETN;
+ output MAXIGP1ARVALID;
+ output MAXIGP1AWVALID;
+ output MAXIGP1BREADY;
+ output MAXIGP1RREADY;
+ output MAXIGP1WLAST;
+ output MAXIGP1WVALID;
+ output SAXIACPARESETN;
+ output SAXIACPARREADY;
+ output SAXIACPAWREADY;
+ output SAXIACPBVALID;
+ output SAXIACPRLAST;
+ output SAXIACPRVALID;
+ output SAXIACPWREADY;
+ output SAXIGP0ARESETN;
+ output SAXIGP0ARREADY;
+ output SAXIGP0AWREADY;
+ output SAXIGP0BVALID;
+ output SAXIGP0RLAST;
+ output SAXIGP0RVALID;
+ output SAXIGP0WREADY;
+ output SAXIGP1ARESETN;
+ output SAXIGP1ARREADY;
+ output SAXIGP1AWREADY;
+ output SAXIGP1BVALID;
+ output SAXIGP1RLAST;
+ output SAXIGP1RVALID;
+ output SAXIGP1WREADY;
+ output SAXIHP0ARESETN;
+ output SAXIHP0ARREADY;
+ output SAXIHP0AWREADY;
+ output SAXIHP0BVALID;
+ output SAXIHP0RLAST;
+ output SAXIHP0RVALID;
+ output SAXIHP0WREADY;
+ output SAXIHP1ARESETN;
+ output SAXIHP1ARREADY;
+ output SAXIHP1AWREADY;
+ output SAXIHP1BVALID;
+ output SAXIHP1RLAST;
+ output SAXIHP1RVALID;
+ output SAXIHP1WREADY;
+ output SAXIHP2ARESETN;
+ output SAXIHP2ARREADY;
+ output SAXIHP2AWREADY;
+ output SAXIHP2BVALID;
+ output SAXIHP2RLAST;
+ output SAXIHP2RVALID;
+ output SAXIHP2WREADY;
+ output SAXIHP3ARESETN;
+ output SAXIHP3ARREADY;
+ output SAXIHP3AWREADY;
+ output SAXIHP3BVALID;
+ output SAXIHP3RLAST;
+ output SAXIHP3RVALID;
+ output SAXIHP3WREADY;
+ output [11:0] MAXIGP0ARID;
+ output [11:0] MAXIGP0AWID;
+ output [11:0] MAXIGP0WID;
+ output [11:0] MAXIGP1ARID;
+ output [11:0] MAXIGP1AWID;
+ output [11:0] MAXIGP1WID;
+ output [1:0] DMA0DATYPE;
+ output [1:0] DMA1DATYPE;
+ output [1:0] DMA2DATYPE;
+ output [1:0] DMA3DATYPE;
+ output [1:0] EMIOUSB0PORTINDCTL;
+ output [1:0] EMIOUSB1PORTINDCTL;
+ output [1:0] EVENTSTANDBYWFE;
+ output [1:0] EVENTSTANDBYWFI;
+ output [1:0] MAXIGP0ARBURST;
+ output [1:0] MAXIGP0ARLOCK;
+ output [1:0] MAXIGP0ARSIZE;
+ output [1:0] MAXIGP0AWBURST;
+ output [1:0] MAXIGP0AWLOCK;
+ output [1:0] MAXIGP0AWSIZE;
+ output [1:0] MAXIGP1ARBURST;
+ output [1:0] MAXIGP1ARLOCK;
+ output [1:0] MAXIGP1ARSIZE;
+ output [1:0] MAXIGP1AWBURST;
+ output [1:0] MAXIGP1AWLOCK;
+ output [1:0] MAXIGP1AWSIZE;
+ output [1:0] SAXIACPBRESP;
+ output [1:0] SAXIACPRRESP;
+ output [1:0] SAXIGP0BRESP;
+ output [1:0] SAXIGP0RRESP;
+ output [1:0] SAXIGP1BRESP;
+ output [1:0] SAXIGP1RRESP;
+ output [1:0] SAXIHP0BRESP;
+ output [1:0] SAXIHP0RRESP;
+ output [1:0] SAXIHP1BRESP;
+ output [1:0] SAXIHP1RRESP;
+ output [1:0] SAXIHP2BRESP;
+ output [1:0] SAXIHP2RRESP;
+ output [1:0] SAXIHP3BRESP;
+ output [1:0] SAXIHP3RRESP;
+ output [28:0] IRQP2F;
+ output [2:0] EMIOSDIO0BUSVOLT;
+ output [2:0] EMIOSDIO1BUSVOLT;
+ output [2:0] EMIOSPI0SSON;
+ output [2:0] EMIOSPI1SSON;
+ output [2:0] EMIOTTC0WAVEO;
+ output [2:0] EMIOTTC1WAVEO;
+ output [2:0] MAXIGP0ARPROT;
+ output [2:0] MAXIGP0AWPROT;
+ output [2:0] MAXIGP1ARPROT;
+ output [2:0] MAXIGP1AWPROT;
+ output [2:0] SAXIACPBID;
+ output [2:0] SAXIACPRID;
+ output [2:0] SAXIHP0RACOUNT;
+ output [2:0] SAXIHP1RACOUNT;
+ output [2:0] SAXIHP2RACOUNT;
+ output [2:0] SAXIHP3RACOUNT;
+ output [31:0] EMIOTRACEDATA;
+ output [31:0] FTMTP2FDEBUG;
+ output [31:0] MAXIGP0ARADDR;
+ output [31:0] MAXIGP0AWADDR;
+ output [31:0] MAXIGP0WDATA;
+ output [31:0] MAXIGP1ARADDR;
+ output [31:0] MAXIGP1AWADDR;
+ output [31:0] MAXIGP1WDATA;
+ output [31:0] SAXIGP0RDATA;
+ output [31:0] SAXIGP1RDATA;
+ output [3:0] EMIOSDIO0DATAO;
+ output [3:0] EMIOSDIO0DATATN;
+ output [3:0] EMIOSDIO1DATAO;
+ output [3:0] EMIOSDIO1DATATN;
+ output [3:0] FCLKCLK;
+ output [3:0] FCLKRESETN;
+ output [3:0] FTMTF2PTRIGACK;
+ output [3:0] FTMTP2FTRIG;
+ output [3:0] MAXIGP0ARCACHE;
+ output [3:0] MAXIGP0ARLEN;
+ output [3:0] MAXIGP0ARQOS;
+ output [3:0] MAXIGP0AWCACHE;
+ output [3:0] MAXIGP0AWLEN;
+ output [3:0] MAXIGP0AWQOS;
+ output [3:0] MAXIGP0WSTRB;
+ output [3:0] MAXIGP1ARCACHE;
+ output [3:0] MAXIGP1ARLEN;
+ output [3:0] MAXIGP1ARQOS;
+ output [3:0] MAXIGP1AWCACHE;
+ output [3:0] MAXIGP1AWLEN;
+ output [3:0] MAXIGP1AWQOS;
+ output [3:0] MAXIGP1WSTRB;
+ output [5:0] SAXIGP0BID;
+ output [5:0] SAXIGP0RID;
+ output [5:0] SAXIGP1BID;
+ output [5:0] SAXIGP1RID;
+ output [5:0] SAXIHP0BID;
+ output [5:0] SAXIHP0RID;
+ output [5:0] SAXIHP0WACOUNT;
+ output [5:0] SAXIHP1BID;
+ output [5:0] SAXIHP1RID;
+ output [5:0] SAXIHP1WACOUNT;
+ output [5:0] SAXIHP2BID;
+ output [5:0] SAXIHP2RID;
+ output [5:0] SAXIHP2WACOUNT;
+ output [5:0] SAXIHP3BID;
+ output [5:0] SAXIHP3RID;
+ output [5:0] SAXIHP3WACOUNT;
+ output [63:0] EMIOGPIOO;
+ output [63:0] EMIOGPIOTN;
+ output [63:0] SAXIACPRDATA;
+ output [63:0] SAXIHP0RDATA;
+ output [63:0] SAXIHP1RDATA;
+ output [63:0] SAXIHP2RDATA;
+ output [63:0] SAXIHP3RDATA;
+ output [7:0] EMIOENET0GMIITXD;
+ output [7:0] EMIOENET1GMIITXD;
+ output [7:0] SAXIHP0RCOUNT;
+ output [7:0] SAXIHP0WCOUNT;
+ output [7:0] SAXIHP1RCOUNT;
+ output [7:0] SAXIHP1WCOUNT;
+ output [7:0] SAXIHP2RCOUNT;
+ output [7:0] SAXIHP2WCOUNT;
+ output [7:0] SAXIHP3RCOUNT;
+ output [7:0] SAXIHP3WCOUNT;
+ inout DDRCASB;
+ inout DDRCKE;
+ inout DDRCKN;
+ inout DDRCKP;
+ inout DDRCSB;
+ inout DDRDRSTB;
+ inout DDRODT;
+ inout DDRRASB;
+ inout DDRVRN;
+ inout DDRVRP;
+ inout DDRWEB;
+ inout PSCLK;
+ inout PSPORB;
+ inout PSSRSTB;
+ inout [14:0] DDRA;
+ inout [2:0] DDRBA;
+ inout [31:0] DDRDQ;
+ inout [3:0] DDRDM;
+ inout [3:0] DDRDQSN;
+ inout [3:0] DDRDQSP;
+ inout [53:0] MIO;
+ input DMA0ACLK;
+ input DMA0DAREADY;
+ input DMA0DRLAST;
+ input DMA0DRVALID;
+ input DMA1ACLK;
+ input DMA1DAREADY;
+ input DMA1DRLAST;
+ input DMA1DRVALID;
+ input DMA2ACLK;
+ input DMA2DAREADY;
+ input DMA2DRLAST;
+ input DMA2DRVALID;
+ input DMA3ACLK;
+ input DMA3DAREADY;
+ input DMA3DRLAST;
+ input DMA3DRVALID;
+ input EMIOCAN0PHYRX;
+ input EMIOCAN1PHYRX;
+ input EMIOENET0EXTINTIN;
+ input EMIOENET0GMIICOL;
+ input EMIOENET0GMIICRS;
+ input EMIOENET0GMIIRXCLK;
+ input EMIOENET0GMIIRXDV;
+ input EMIOENET0GMIIRXER;
+ input EMIOENET0GMIITXCLK;
+ input EMIOENET0MDIOI;
+ input EMIOENET1EXTINTIN;
+ input EMIOENET1GMIICOL;
+ input EMIOENET1GMIICRS;
+ input EMIOENET1GMIIRXCLK;
+ input EMIOENET1GMIIRXDV;
+ input EMIOENET1GMIIRXER;
+ input EMIOENET1GMIITXCLK;
+ input EMIOENET1MDIOI;
+ input EMIOI2C0SCLI;
+ input EMIOI2C0SDAI;
+ input EMIOI2C1SCLI;
+ input EMIOI2C1SDAI;
+ input EMIOPJTAGTCK;
+ input EMIOPJTAGTDI;
+ input EMIOPJTAGTMS;
+ input EMIOSDIO0CDN;
+ input EMIOSDIO0CLKFB;
+ input EMIOSDIO0CMDI;
+ input EMIOSDIO0WP;
+ input EMIOSDIO1CDN;
+ input EMIOSDIO1CLKFB;
+ input EMIOSDIO1CMDI;
+ input EMIOSDIO1WP;
+ input EMIOSPI0MI;
+ input EMIOSPI0SCLKI;
+ input EMIOSPI0SI;
+ input EMIOSPI0SSIN;
+ input EMIOSPI1MI;
+ input EMIOSPI1SCLKI;
+ input EMIOSPI1SI;
+ input EMIOSPI1SSIN;
+ input EMIOSRAMINTIN;
+ input EMIOTRACECLK;
+ input EMIOUART0CTSN;
+ input EMIOUART0DCDN;
+ input EMIOUART0DSRN;
+ input EMIOUART0RIN;
+ input EMIOUART0RX;
+ input EMIOUART1CTSN;
+ input EMIOUART1DCDN;
+ input EMIOUART1DSRN;
+ input EMIOUART1RIN;
+ input EMIOUART1RX;
+ input EMIOUSB0VBUSPWRFAULT;
+ input EMIOUSB1VBUSPWRFAULT;
+ input EMIOWDTCLKI;
+ input EVENTEVENTI;
+ input FPGAIDLEN;
+ input FTMDTRACEINCLOCK;
+ input FTMDTRACEINVALID;
+ input MAXIGP0ACLK;
+ input MAXIGP0ARREADY;
+ input MAXIGP0AWREADY;
+ input MAXIGP0BVALID;
+ input MAXIGP0RLAST;
+ input MAXIGP0RVALID;
+ input MAXIGP0WREADY;
+ input MAXIGP1ACLK;
+ input MAXIGP1ARREADY;
+ input MAXIGP1AWREADY;
+ input MAXIGP1BVALID;
+ input MAXIGP1RLAST;
+ input MAXIGP1RVALID;
+ input MAXIGP1WREADY;
+ input SAXIACPACLK;
+ input SAXIACPARVALID;
+ input SAXIACPAWVALID;
+ input SAXIACPBREADY;
+ input SAXIACPRREADY;
+ input SAXIACPWLAST;
+ input SAXIACPWVALID;
+ input SAXIGP0ACLK;
+ input SAXIGP0ARVALID;
+ input SAXIGP0AWVALID;
+ input SAXIGP0BREADY;
+ input SAXIGP0RREADY;
+ input SAXIGP0WLAST;
+ input SAXIGP0WVALID;
+ input SAXIGP1ACLK;
+ input SAXIGP1ARVALID;
+ input SAXIGP1AWVALID;
+ input SAXIGP1BREADY;
+ input SAXIGP1RREADY;
+ input SAXIGP1WLAST;
+ input SAXIGP1WVALID;
+ input SAXIHP0ACLK;
+ input SAXIHP0ARVALID;
+ input SAXIHP0AWVALID;
+ input SAXIHP0BREADY;
+ input SAXIHP0RDISSUECAP1EN;
+ input SAXIHP0RREADY;
+ input SAXIHP0WLAST;
+ input SAXIHP0WRISSUECAP1EN;
+ input SAXIHP0WVALID;
+ input SAXIHP1ACLK;
+ input SAXIHP1ARVALID;
+ input SAXIHP1AWVALID;
+ input SAXIHP1BREADY;
+ input SAXIHP1RDISSUECAP1EN;
+ input SAXIHP1RREADY;
+ input SAXIHP1WLAST;
+ input SAXIHP1WRISSUECAP1EN;
+ input SAXIHP1WVALID;
+ input SAXIHP2ACLK;
+ input SAXIHP2ARVALID;
+ input SAXIHP2AWVALID;
+ input SAXIHP2BREADY;
+ input SAXIHP2RDISSUECAP1EN;
+ input SAXIHP2RREADY;
+ input SAXIHP2WLAST;
+ input SAXIHP2WRISSUECAP1EN;
+ input SAXIHP2WVALID;
+ input SAXIHP3ACLK;
+ input SAXIHP3ARVALID;
+ input SAXIHP3AWVALID;
+ input SAXIHP3BREADY;
+ input SAXIHP3RDISSUECAP1EN;
+ input SAXIHP3RREADY;
+ input SAXIHP3WLAST;
+ input SAXIHP3WRISSUECAP1EN;
+ input SAXIHP3WVALID;
+ input [11:0] MAXIGP0BID;
+ input [11:0] MAXIGP0RID;
+ input [11:0] MAXIGP1BID;
+ input [11:0] MAXIGP1RID;
+ input [19:0] IRQF2P;
+ input [1:0] DMA0DRTYPE;
+ input [1:0] DMA1DRTYPE;
+ input [1:0] DMA2DRTYPE;
+ input [1:0] DMA3DRTYPE;
+ input [1:0] MAXIGP0BRESP;
+ input [1:0] MAXIGP0RRESP;
+ input [1:0] MAXIGP1BRESP;
+ input [1:0] MAXIGP1RRESP;
+ input [1:0] SAXIACPARBURST;
+ input [1:0] SAXIACPARLOCK;
+ input [1:0] SAXIACPARSIZE;
+ input [1:0] SAXIACPAWBURST;
+ input [1:0] SAXIACPAWLOCK;
+ input [1:0] SAXIACPAWSIZE;
+ input [1:0] SAXIGP0ARBURST;
+ input [1:0] SAXIGP0ARLOCK;
+ input [1:0] SAXIGP0ARSIZE;
+ input [1:0] SAXIGP0AWBURST;
+ input [1:0] SAXIGP0AWLOCK;
+ input [1:0] SAXIGP0AWSIZE;
+ input [1:0] SAXIGP1ARBURST;
+ input [1:0] SAXIGP1ARLOCK;
+ input [1:0] SAXIGP1ARSIZE;
+ input [1:0] SAXIGP1AWBURST;
+ input [1:0] SAXIGP1AWLOCK;
+ input [1:0] SAXIGP1AWSIZE;
+ input [1:0] SAXIHP0ARBURST;
+ input [1:0] SAXIHP0ARLOCK;
+ input [1:0] SAXIHP0ARSIZE;
+ input [1:0] SAXIHP0AWBURST;
+ input [1:0] SAXIHP0AWLOCK;
+ input [1:0] SAXIHP0AWSIZE;
+ input [1:0] SAXIHP1ARBURST;
+ input [1:0] SAXIHP1ARLOCK;
+ input [1:0] SAXIHP1ARSIZE;
+ input [1:0] SAXIHP1AWBURST;
+ input [1:0] SAXIHP1AWLOCK;
+ input [1:0] SAXIHP1AWSIZE;
+ input [1:0] SAXIHP2ARBURST;
+ input [1:0] SAXIHP2ARLOCK;
+ input [1:0] SAXIHP2ARSIZE;
+ input [1:0] SAXIHP2AWBURST;
+ input [1:0] SAXIHP2AWLOCK;
+ input [1:0] SAXIHP2AWSIZE;
+ input [1:0] SAXIHP3ARBURST;
+ input [1:0] SAXIHP3ARLOCK;
+ input [1:0] SAXIHP3ARSIZE;
+ input [1:0] SAXIHP3AWBURST;
+ input [1:0] SAXIHP3AWLOCK;
+ input [1:0] SAXIHP3AWSIZE;
+ input [2:0] EMIOTTC0CLKI;
+ input [2:0] EMIOTTC1CLKI;
+ input [2:0] SAXIACPARID;
+ input [2:0] SAXIACPARPROT;
+ input [2:0] SAXIACPAWID;
+ input [2:0] SAXIACPAWPROT;
+ input [2:0] SAXIACPWID;
+ input [2:0] SAXIGP0ARPROT;
+ input [2:0] SAXIGP0AWPROT;
+ input [2:0] SAXIGP1ARPROT;
+ input [2:0] SAXIGP1AWPROT;
+ input [2:0] SAXIHP0ARPROT;
+ input [2:0] SAXIHP0AWPROT;
+ input [2:0] SAXIHP1ARPROT;
+ input [2:0] SAXIHP1AWPROT;
+ input [2:0] SAXIHP2ARPROT;
+ input [2:0] SAXIHP2AWPROT;
+ input [2:0] SAXIHP3ARPROT;
+ input [2:0] SAXIHP3AWPROT;
+ input [31:0] FTMDTRACEINDATA;
+ input [31:0] FTMTF2PDEBUG;
+ input [31:0] MAXIGP0RDATA;
+ input [31:0] MAXIGP1RDATA;
+ input [31:0] SAXIACPARADDR;
+ input [31:0] SAXIACPAWADDR;
+ input [31:0] SAXIGP0ARADDR;
+ input [31:0] SAXIGP0AWADDR;
+ input [31:0] SAXIGP0WDATA;
+ input [31:0] SAXIGP1ARADDR;
+ input [31:0] SAXIGP1AWADDR;
+ input [31:0] SAXIGP1WDATA;
+ input [31:0] SAXIHP0ARADDR;
+ input [31:0] SAXIHP0AWADDR;
+ input [31:0] SAXIHP1ARADDR;
+ input [31:0] SAXIHP1AWADDR;
+ input [31:0] SAXIHP2ARADDR;
+ input [31:0] SAXIHP2AWADDR;
+ input [31:0] SAXIHP3ARADDR;
+ input [31:0] SAXIHP3AWADDR;
+ input [3:0] DDRARB;
+ input [3:0] EMIOSDIO0DATAI;
+ input [3:0] EMIOSDIO1DATAI;
+ input [3:0] FCLKCLKTRIGN;
+ input [3:0] FTMDTRACEINATID;
+ input [3:0] FTMTF2PTRIG;
+ input [3:0] FTMTP2FTRIGACK;
+ input [3:0] SAXIACPARCACHE;
+ input [3:0] SAXIACPARLEN;
+ input [3:0] SAXIACPARQOS;
+ input [3:0] SAXIACPAWCACHE;
+ input [3:0] SAXIACPAWLEN;
+ input [3:0] SAXIACPAWQOS;
+ input [3:0] SAXIGP0ARCACHE;
+ input [3:0] SAXIGP0ARLEN;
+ input [3:0] SAXIGP0ARQOS;
+ input [3:0] SAXIGP0AWCACHE;
+ input [3:0] SAXIGP0AWLEN;
+ input [3:0] SAXIGP0AWQOS;
+ input [3:0] SAXIGP0WSTRB;
+ input [3:0] SAXIGP1ARCACHE;
+ input [3:0] SAXIGP1ARLEN;
+ input [3:0] SAXIGP1ARQOS;
+ input [3:0] SAXIGP1AWCACHE;
+ input [3:0] SAXIGP1AWLEN;
+ input [3:0] SAXIGP1AWQOS;
+ input [3:0] SAXIGP1WSTRB;
+ input [3:0] SAXIHP0ARCACHE;
+ input [3:0] SAXIHP0ARLEN;
+ input [3:0] SAXIHP0ARQOS;
+ input [3:0] SAXIHP0AWCACHE;
+ input [3:0] SAXIHP0AWLEN;
+ input [3:0] SAXIHP0AWQOS;
+ input [3:0] SAXIHP1ARCACHE;
+ input [3:0] SAXIHP1ARLEN;
+ input [3:0] SAXIHP1ARQOS;
+ input [3:0] SAXIHP1AWCACHE;
+ input [3:0] SAXIHP1AWLEN;
+ input [3:0] SAXIHP1AWQOS;
+ input [3:0] SAXIHP2ARCACHE;
+ input [3:0] SAXIHP2ARLEN;
+ input [3:0] SAXIHP2ARQOS;
+ input [3:0] SAXIHP2AWCACHE;
+ input [3:0] SAXIHP2AWLEN;
+ input [3:0] SAXIHP2AWQOS;
+ input [3:0] SAXIHP3ARCACHE;
+ input [3:0] SAXIHP3ARLEN;
+ input [3:0] SAXIHP3ARQOS;
+ input [3:0] SAXIHP3AWCACHE;
+ input [3:0] SAXIHP3AWLEN;
+ input [3:0] SAXIHP3AWQOS;
+ input [4:0] SAXIACPARUSER;
+ input [4:0] SAXIACPAWUSER;
+ input [5:0] SAXIGP0ARID;
+ input [5:0] SAXIGP0AWID;
+ input [5:0] SAXIGP0WID;
+ input [5:0] SAXIGP1ARID;
+ input [5:0] SAXIGP1AWID;
+ input [5:0] SAXIGP1WID;
+ input [5:0] SAXIHP0ARID;
+ input [5:0] SAXIHP0AWID;
+ input [5:0] SAXIHP0WID;
+ input [5:0] SAXIHP1ARID;
+ input [5:0] SAXIHP1AWID;
+ input [5:0] SAXIHP1WID;
+ input [5:0] SAXIHP2ARID;
+ input [5:0] SAXIHP2AWID;
+ input [5:0] SAXIHP2WID;
+ input [5:0] SAXIHP3ARID;
+ input [5:0] SAXIHP3AWID;
+ input [5:0] SAXIHP3WID;
+ input [63:0] EMIOGPIOI;
+ input [63:0] SAXIACPWDATA;
+ input [63:0] SAXIHP0WDATA;
+ input [63:0] SAXIHP1WDATA;
+ input [63:0] SAXIHP2WDATA;
+ input [63:0] SAXIHP3WDATA;
+ input [7:0] EMIOENET0GMIIRXD;
+ input [7:0] EMIOENET1GMIIRXD;
+ input [7:0] SAXIACPWSTRB;
+ input [7:0] SAXIHP0WSTRB;
+ input [7:0] SAXIHP1WSTRB;
+ input [7:0] SAXIHP2WSTRB;
+ input [7:0] SAXIHP3WSTRB;
+endmodule
+
module PULLDOWN (...);
output O;
endmodule
@@ -3091,13 +3694,6 @@ module RAM32M (...);
input WE;
endmodule
-module RAM32X1D (...);
- parameter [31:0] INIT = 32'h00000000;
- parameter [0:0] IS_WCLK_INVERTED = 1'b0;
- output DPO, SPO;
- input A0, A1, A2, A3, A4, D, DPRA0, DPRA1, DPRA2, DPRA3, DPRA4, WCLK, WE;
-endmodule
-
module RAM32X1S (...);
parameter [31:0] INIT = 32'h00000000;
parameter [0:0] IS_WCLK_INVERTED = 1'b0;
@@ -3142,6 +3738,13 @@ module RAM64M (...);
input WE;
endmodule
+module RAM64X1D (...);
+ parameter [63:0] INIT = 64'h0000000000000000;
+ parameter [0:0] IS_WCLK_INVERTED = 1'b0;
+ output DPO, SPO;
+ input A0, A1, A2, A3, A4, A5, D, DPRA0, DPRA1, DPRA2, DPRA3, DPRA4, DPRA5, WCLK, WE;
+endmodule
+
module RAM64X1S (...);
parameter [63:0] INIT = 64'h0000000000000000;
parameter [0:0] IS_WCLK_INVERTED = 1'b0;
@@ -3188,22 +3791,7 @@ module ROM64X1 (...);
input A0, A1, A2, A3, A4, A5;
endmodule
-module SRL16E (...);
- parameter [15:0] INIT = 16'h0000;
- parameter [0:0] IS_CLK_INVERTED = 1'b0;
- output Q;
- input A0, A1, A2, A3, CE, CLK, D;
-endmodule
-
-module SRLC32E (...);
- parameter [31:0] INIT = 32'h00000000;
- parameter [0:0] IS_CLK_INVERTED = 1'b0;
- output Q;
- output Q31;
- input [4:0] A;
- input CE, CLK, D;
-endmodule
-
+(* keep *)
module STARTUPE2 (...);
parameter PROG_USR = "FALSE";
parameter real SIM_CCLK_FREQ = 0.0;
diff --git a/techlibs/xilinx/drams.txt b/techlibs/xilinx/drams.txt
index e6635d0e..2613c206 100644
--- a/techlibs/xilinx/drams.txt
+++ b/techlibs/xilinx/drams.txt
@@ -1,4 +1,17 @@
+bram $__XILINX_RAM32X1D
+ init 1
+ abits 5
+ dbits 1
+ groups 2
+ ports 1 1
+ wrmode 0 1
+ enable 0 1
+ transp 0 0
+ clocks 0 1
+ clkpol 0 2
+endbram
+
bram $__XILINX_RAM64X1D
init 1
abits 6
@@ -25,12 +38,23 @@ bram $__XILINX_RAM128X1D
clkpol 0 2
endbram
+match $__XILINX_RAM32X1D
+ min bits 3
+ min wports 1
+ make_outreg
+ or_next_if_better
+endmatch
+
match $__XILINX_RAM64X1D
+ min bits 5
+ min wports 1
make_outreg
or_next_if_better
endmatch
match $__XILINX_RAM128X1D
+ min bits 9
+ min wports 1
make_outreg
endmatch
diff --git a/techlibs/xilinx/drams_map.v b/techlibs/xilinx/drams_map.v
index 47476b59..77041ca8 100644
--- a/techlibs/xilinx/drams_map.v
+++ b/techlibs/xilinx/drams_map.v
@@ -1,4 +1,38 @@
+module \$__XILINX_RAM32X1D (CLK1, A1ADDR, A1DATA, B1ADDR, B1DATA, B1EN);
+ parameter [31:0] INIT = 32'bx;
+ parameter CLKPOL2 = 1;
+ input CLK1;
+
+ input [4:0] A1ADDR;
+ output A1DATA;
+
+ input [4:0] B1ADDR;
+ input B1DATA;
+ input B1EN;
+
+ RAM32X1D #(
+ .INIT(INIT),
+ .IS_WCLK_INVERTED(!CLKPOL2)
+ ) _TECHMAP_REPLACE_ (
+ .DPRA0(A1ADDR[0]),
+ .DPRA1(A1ADDR[1]),
+ .DPRA2(A1ADDR[2]),
+ .DPRA3(A1ADDR[3]),
+ .DPRA4(A1ADDR[4]),
+ .DPO(A1DATA),
+
+ .A0(B1ADDR[0]),
+ .A1(B1ADDR[1]),
+ .A2(B1ADDR[2]),
+ .A3(B1ADDR[3]),
+ .A4(B1ADDR[4]),
+ .D(B1DATA),
+ .WCLK(CLK1),
+ .WE(B1EN)
+ );
+endmodule
+
module \$__XILINX_RAM64X1D (CLK1, A1ADDR, A1DATA, B1ADDR, B1DATA, B1EN);
parameter [63:0] INIT = 64'bx;
parameter CLKPOL2 = 1;
diff --git a/techlibs/xilinx/ff_map.v b/techlibs/xilinx/ff_map.v
new file mode 100644
index 00000000..13beaa6a
--- /dev/null
+++ b/techlibs/xilinx/ff_map.v
@@ -0,0 +1,42 @@
+/*
+ * yosys -- Yosys Open SYnthesis Suite
+ *
+ * Copyright (C) 2012 Clifford Wolf <clifford@clifford.at>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ */
+
+// ============================================================================
+// FF mapping
+
+`ifndef _NO_FFS
+
+module \$_DFF_N_ (input D, C, output Q); FDRE_1 #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .R(1'b0)); endmodule
+module \$_DFF_P_ (input D, C, output Q); FDRE #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .R(1'b0)); endmodule
+
+module \$_DFFE_NP_ (input D, C, E, output Q); FDRE_1 #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(E), .R(1'b0)); endmodule
+module \$_DFFE_PP_ (input D, C, E, output Q); FDRE #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(E), .R(1'b0)); endmodule
+
+module \$_DFF_NN0_ (input D, C, R, output Q); FDCE_1 #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR(!R)); endmodule
+module \$_DFF_NP0_ (input D, C, R, output Q); FDCE_1 #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR( R)); endmodule
+module \$_DFF_PN0_ (input D, C, R, output Q); FDCE #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR(!R)); endmodule
+module \$_DFF_PP0_ (input D, C, R, output Q); FDCE #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .CLR( R)); endmodule
+
+module \$_DFF_NN1_ (input D, C, R, output Q); FDPE_1 #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE(!R)); endmodule
+module \$_DFF_NP1_ (input D, C, R, output Q); FDPE_1 #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE( R)); endmodule
+module \$_DFF_PN1_ (input D, C, R, output Q); FDPE #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE(!R)); endmodule
+module \$_DFF_PP1_ (input D, C, R, output Q); FDPE #(.INIT(|0)) _TECHMAP_REPLACE_ (.D(D), .Q(Q), .C(C), .CE(1'b1), .PRE( R)); endmodule
+
+`endif
+
diff --git a/techlibs/xilinx/lut2lut.v b/techlibs/xilinx/lut2lut.v
deleted file mode 100644
index 061ad204..00000000
--- a/techlibs/xilinx/lut2lut.v
+++ /dev/null
@@ -1,65 +0,0 @@
-module LUT1(output O, input I0);
- parameter [1:0] INIT = 0;
- \$lut #(
- .WIDTH(1),
- .LUT(INIT)
- ) _TECHMAP_REPLACE_ (
- .A(I0),
- .Y(O)
- );
-endmodule
-
-module LUT2(output O, input I0, I1);
- parameter [3:0] INIT = 0;
- \$lut #(
- .WIDTH(2),
- .LUT(INIT)
- ) _TECHMAP_REPLACE_ (
- .A({I1, I0}),
- .Y(O)
- );
-endmodule
-
-module LUT3(output O, input I0, I1, I2);
- parameter [7:0] INIT = 0;
- \$lut #(
- .WIDTH(3),
- .LUT(INIT)
- ) _TECHMAP_REPLACE_ (
- .A({I2, I1, I0}),
- .Y(O)
- );
-endmodule
-
-module LUT4(output O, input I0, I1, I2, I3);
- parameter [15:0] INIT = 0;
- \$lut #(
- .WIDTH(4),
- .LUT(INIT)
- ) _TECHMAP_REPLACE_ (
- .A({I3, I2, I1, I0}),
- .Y(O)
- );
-endmodule
-
-module LUT5(output O, input I0, I1, I2, I3, I4);
- parameter [31:0] INIT = 0;
- \$lut #(
- .WIDTH(5),
- .LUT(INIT)
- ) _TECHMAP_REPLACE_ (
- .A({I4, I3, I2, I1, I0}),
- .Y(O)
- );
-endmodule
-
-module LUT6(output O, input I0, I1, I2, I3, I4, I5);
- parameter [63:0] INIT = 0;
- \$lut #(
- .WIDTH(6),
- .LUT(INIT)
- ) _TECHMAP_REPLACE_ (
- .A({I5, I4, I3, I2, I1, I0}),
- .Y(O)
- );
-endmodule
diff --git a/techlibs/xilinx/lut_map.v b/techlibs/xilinx/lut_map.v
new file mode 100644
index 00000000..d07c59de
--- /dev/null
+++ b/techlibs/xilinx/lut_map.v
@@ -0,0 +1,94 @@
+/*
+ * yosys -- Yosys Open SYnthesis Suite
+ *
+ * Copyright (C) 2012 Clifford Wolf <clifford@clifford.at>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ */
+
+// ============================================================================
+// LUT mapping
+
+`ifndef _NO_LUTS
+
+module \$lut (A, Y);
+ parameter WIDTH = 0;
+ parameter LUT = 0;
+
+ input [WIDTH-1:0] A;
+ output Y;
+
+ generate
+ if (WIDTH == 1) begin
+ LUT1 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
+ .I0(A[0]));
+ end else
+ if (WIDTH == 2) begin
+ LUT2 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
+ .I0(A[0]), .I1(A[1]));
+ end else
+ if (WIDTH == 3) begin
+ LUT3 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]));
+ end else
+ if (WIDTH == 4) begin
+ LUT4 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]));
+ end else
+ if (WIDTH == 5) begin
+ LUT5 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]));
+ end else
+ if (WIDTH == 6) begin
+ LUT6 #(.INIT(LUT)) _TECHMAP_REPLACE_ (.O(Y),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ end else
+ if (WIDTH == 7) begin
+ wire T0, T1;
+ LUT6 #(.INIT(LUT[63:0])) fpga_lut_0 (.O(T0),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ LUT6 #(.INIT(LUT[127:64])) fpga_lut_1 (.O(T1),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ MUXF7 fpga_mux_0 (.O(Y), .I0(T0), .I1(T1), .S(A[6]));
+ end else
+ if (WIDTH == 8) begin
+ wire T0, T1, T2, T3, T4, T5;
+ LUT6 #(.INIT(LUT[63:0])) fpga_lut_0 (.O(T0),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ LUT6 #(.INIT(LUT[127:64])) fpga_lut_1 (.O(T1),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ LUT6 #(.INIT(LUT[191:128])) fpga_lut_2 (.O(T2),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ LUT6 #(.INIT(LUT[255:192])) fpga_lut_3 (.O(T3),
+ .I0(A[0]), .I1(A[1]), .I2(A[2]),
+ .I3(A[3]), .I4(A[4]), .I5(A[5]));
+ MUXF7 fpga_mux_0 (.O(T4), .I0(T0), .I1(T1), .S(A[6]));
+ MUXF7 fpga_mux_1 (.O(T5), .I0(T2), .I1(T3), .S(A[6]));
+ MUXF8 fpga_mux_2 (.O(Y), .I0(T4), .I1(T5), .S(A[7]));
+ end else begin
+ wire _TECHMAP_FAIL_ = 1;
+ end
+ endgenerate
+endmodule
+
+`endif
+
diff --git a/techlibs/xilinx/synth_xilinx.cc b/techlibs/xilinx/synth_xilinx.cc
index 590fe61d..7dc9915e 100644
--- a/techlibs/xilinx/synth_xilinx.cc
+++ b/techlibs/xilinx/synth_xilinx.cc
@@ -25,18 +25,9 @@
USING_YOSYS_NAMESPACE
PRIVATE_NAMESPACE_BEGIN
-bool check_label(bool &active, std::string run_from, std::string run_to, std::string label)
+struct SynthXilinxPass : public ScriptPass
{
- if (label == run_from)
- active = true;
- if (label == run_to)
- active = false;
- return active;
-}
-
-struct SynthXilinxPass : public Pass
-{
- SynthXilinxPass() : Pass("synth_xilinx", "synthesis for Xilinx FPGAs") { }
+ SynthXilinxPass() : ScriptPass("synth_xilinx", "synthesis for Xilinx FPGAs") { }
void help() YS_OVERRIDE
{
@@ -51,6 +42,11 @@ struct SynthXilinxPass : public Pass
log(" -top <module>\n");
log(" use the specified module as top module\n");
log("\n");
+ log(" -family {xcup|xcu|xc7|xc6s}\n");
+ log(" run synthesis for the specified Xilinx architecture\n");
+ log(" generate the synthesis netlist for the specified family.\n");
+ log(" default: xc7\n");
+ log("\n");
log(" -edif <file>\n");
log(" write the design to the specified edif file. writing of an output file\n");
log(" is omitted if this parameter is not specified.\n");
@@ -63,6 +59,21 @@ struct SynthXilinxPass : public Pass
log(" generate an output netlist (and BLIF file) suitable for VPR\n");
log(" (this feature is experimental and incomplete)\n");
log("\n");
+ log(" -nobram\n");
+ log(" disable inference of block rams\n");
+ log("\n");
+ log(" -nodram\n");
+ log(" disable inference of distributed rams\n");
+ log("\n");
+ log(" -nosrl\n");
+ log(" disable inference of shift registers\n");
+ log("\n");
+ log(" -nocarry\n");
+ log(" do not use XORCY/MUXCY/CARRY4 cells in output netlist\n");
+ log("\n");
+ log(" -nowidelut\n");
+ log(" do not use MUXF[78] resources to implement LUTs larger than LUT6s\n");
+ log("\n");
log(" -run <from_label>:<to_label>\n");
log(" only run the commands between the labels (see below). an empty\n");
log(" from label is synonymous to 'begin', and empty to label is\n");
@@ -76,67 +87,33 @@ struct SynthXilinxPass : public Pass
log("\n");
log("\n");
log("The following commands are executed by this synthesis command:\n");
- log("\n");
- log(" begin:\n");
- log(" read_verilog -lib +/xilinx/cells_sim.v\n");
- log(" read_verilog -lib +/xilinx/cells_xtra.v\n");
- log(" read_verilog -lib +/xilinx/brams_bb.v\n");
- log(" hierarchy -check -top <top>\n");
- log("\n");
- log(" flatten: (only if -flatten)\n");
- log(" proc\n");
- log(" flatten\n");
- log("\n");
- log(" coarse:\n");
- log(" synth -run coarse\n");
- log("\n");
- log(" bram:\n");
- log(" memory_bram -rules +/xilinx/brams.txt\n");
- log(" techmap -map +/xilinx/brams_map.v\n");
- log("\n");
- log(" dram:\n");
- log(" memory_bram -rules +/xilinx/drams.txt\n");
- log(" techmap -map +/xilinx/drams_map.v\n");
- log("\n");
- log(" fine:\n");
- log(" opt -fast -full\n");
- log(" memory_map\n");
- log(" dffsr2dff\n");
- log(" dff2dffe\n");
- log(" opt -full\n");
- log(" techmap -map +/techmap.v -map +/xilinx/arith_map.v\n");
- log(" opt -fast\n");
- log("\n");
- log(" map_luts:\n");
- log(" abc -luts 2:2,3,6:5,10,20 [-dff]\n");
- log(" clean\n");
- log("\n");
- log(" map_cells:\n");
- log(" techmap -map +/xilinx/cells_map.v (with -D NO_LUT in vpr mode)\n");
- log(" dffinit -ff FDRE Q INIT -ff FDCE Q INIT -ff FDPE Q INIT\n");
- log(" clean\n");
- log("\n");
- log(" check:\n");
- log(" hierarchy -check\n");
- log(" stat\n");
- log(" check -noinit\n");
- log("\n");
- log(" edif: (only if -edif)\n");
- log(" write_edif <file-name>\n");
- log("\n");
- log(" blif: (only if -blif)\n");
- log(" write_blif <file-name>\n");
+ help_script();
log("\n");
}
+
+ std::string top_opt, edif_file, blif_file, family;
+ bool flatten, retime, vpr, nobram, nodram, nosrl, nocarry, nowidelut;
+
+ void clear_flags() YS_OVERRIDE
+ {
+ top_opt = "-auto-top";
+ edif_file.clear();
+ blif_file.clear();
+ flatten = false;
+ retime = false;
+ vpr = false;
+ nobram = false;
+ nodram = false;
+ nosrl = false;
+ nocarry = false;
+ nowidelut = false;
+ family = "xc7";
+ }
+
void execute(std::vector<std::string> args, RTLIL::Design *design) YS_OVERRIDE
{
- std::string top_opt = "-auto-top";
- std::string edif_file;
- std::string blif_file;
std::string run_from, run_to;
- bool flatten = false;
- bool retime = false;
- bool vpr = false;
+ clear_flags();
size_t argidx;
for (argidx = 1; argidx < args.size(); argidx++)
@@ -145,6 +122,10 @@ struct SynthXilinxPass : public Pass
top_opt = "-top " + args[++argidx];
continue;
}
+ if ((args[argidx] == "-family" || args[argidx] == "-arch") && argidx+1 < args.size()) {
+ family = args[++argidx];
+ continue;
+ }
if (args[argidx] == "-edif" && argidx+1 < args.size()) {
edif_file = args[++argidx];
continue;
@@ -169,99 +150,160 @@ struct SynthXilinxPass : public Pass
retime = true;
continue;
}
+ if (args[argidx] == "-nocarry") {
+ nocarry = true;
+ continue;
+ }
+ if (args[argidx] == "-nowidelut") {
+ nowidelut = true;
+ continue;
+ }
if (args[argidx] == "-vpr") {
vpr = true;
continue;
}
+ if (args[argidx] == "-nobram") {
+ nobram = true;
+ continue;
+ }
+ if (args[argidx] == "-nodram") {
+ nodram = true;
+ continue;
+ }
+ if (args[argidx] == "-nosrl") {
+ nosrl = true;
+ continue;
+ }
break;
}
extra_args(args, argidx, design);
- if (!design->full_selection())
- log_cmd_error("This comannd only operates on fully selected designs!\n");
+ if (family != "xcup" && family != "xcu" && family != "xc7" && family != "xc6s")
+ log_cmd_error("Invalid Xilinx -family setting: %s\n", family.c_str());
- bool active = run_from.empty();
+ if (!design->full_selection())
+ log_cmd_error("This command only operates on fully selected designs!\n");
log_header(design, "Executing SYNTH_XILINX pass.\n");
log_push();
- if (check_label(active, run_from, run_to, "begin"))
- {
- Pass::call(design, "read_verilog -lib +/xilinx/cells_sim.v");
- Pass::call(design, "read_verilog -lib +/xilinx/cells_xtra.v");
- Pass::call(design, "read_verilog -lib +/xilinx/brams_bb.v");
- Pass::call(design, stringf("hierarchy -check %s", top_opt.c_str()));
+ run_script(design, run_from, run_to);
+
+ log_pop();
+ }
+
+ void script() YS_OVERRIDE
+ {
+ if (check_label("begin")) {
+ if (vpr)
+ run("read_verilog -lib -D_EXPLICIT_CARRY +/xilinx/cells_sim.v");
+ else
+ run("read_verilog -lib +/xilinx/cells_sim.v");
+
+ run("read_verilog -lib +/xilinx/cells_xtra.v");
+
+ if (!nobram || help_mode)
+ run("read_verilog -lib +/xilinx/brams_bb.v", "(skip if '-nobram')");
+
+ run(stringf("hierarchy -check %s", top_opt.c_str()));
}
- if (flatten && check_label(active, run_from, run_to, "flatten"))
- {
- Pass::call(design, "proc");
- Pass::call(design, "flatten");
+ if (check_label("flatten", "(with '-flatten' only)")) {
+ if (flatten || help_mode) {
+ run("proc");
+ run("flatten");
+ }
}
- if (check_label(active, run_from, run_to, "coarse"))
- {
- Pass::call(design, "synth -run coarse");
+ if (check_label("coarse")) {
+ run("synth -run coarse");
}
- if (check_label(active, run_from, run_to, "bram"))
- {
- Pass::call(design, "memory_bram -rules +/xilinx/brams.txt");
- Pass::call(design, "techmap -map +/xilinx/brams_map.v");
+ if (check_label("bram", "(skip if '-nobram')")) {
+ if (!nobram || help_mode) {
+ run("memory_bram -rules +/xilinx/brams.txt");
+ run("techmap -map +/xilinx/brams_map.v");
+ }
}
- if (check_label(active, run_from, run_to, "dram"))
- {
- Pass::call(design, "memory_bram -rules +/xilinx/drams.txt");
- Pass::call(design, "techmap -map +/xilinx/drams_map.v");
+ if (check_label("dram", "(skip if '-nodram')")) {
+ if (!nodram || help_mode) {
+ run("memory_bram -rules +/xilinx/drams.txt");
+ run("techmap -map +/xilinx/drams_map.v");
+ }
}
- if (check_label(active, run_from, run_to, "fine"))
- {
- Pass::call(design, "opt -fast -full");
- Pass::call(design, "memory_map");
- Pass::call(design, "dffsr2dff");
- Pass::call(design, "dff2dffe");
- Pass::call(design, "opt -full");
- Pass::call(design, "techmap -map +/techmap.v -map +/xilinx/arith_map.v");
- Pass::call(design, "opt -fast");
+ if (check_label("fine")) {
+ // shregmap -tech xilinx can cope with $shiftx and $mux
+ // cells for identifiying variable-length shift registers,
+ // so attempt to convert $pmux-es to the former
+ if (!nosrl || help_mode)
+ run("pmux2shiftx", "(skip if '-nosrl')");
+
+ run("opt -fast -full");
+ run("memory_map");
+ run("dffsr2dff");
+ run("dff2dffe");
+ run("opt -full");
+
+ if (!nosrl || help_mode) {
+ // shregmap operates on bit-level flops, not word-level,
+ // so break those down here
+ run("simplemap t:$dff t:$dffe", "(skip if '-nosrl')");
+ // shregmap with '-tech xilinx' infers variable length shift regs
+ run("shregmap -tech xilinx -minlen 3", "(skip if '-nosrl')");
+ }
+
+ if (help_mode)
+ run("techmap -map +/techmap.v [-map +/xilinx/arith_map.v]", "(skip if '-nocarry')");
+ else if (!nocarry) {
+ if (!vpr)
+ run("techmap -map +/techmap.v -map +/xilinx/arith_map.v");
+ else
+ run("techmap -map +/techmap.v -map +/xilinx/arith_map.v -D _EXPLICIT_CARRY");
+ }
+
+ run("opt -fast");
}
- if (check_label(active, run_from, run_to, "map_luts"))
- {
- Pass::call(design, "abc -luts 2:2,3,6:5,10,20" + string(retime ? " -dff" : ""));
- Pass::call(design, "clean");
+ if (check_label("map_cells")) {
+ run("techmap -map +/techmap.v -map +/xilinx/cells_map.v");
+ run("clean");
}
- if (check_label(active, run_from, run_to, "map_cells"))
- {
- if (vpr)
- Pass::call(design, "techmap -D NO_LUT -map +/xilinx/cells_map.v");
+ if (check_label("map_luts")) {
+ if (help_mode)
+ run("abc -luts 2:2,3,6:5[,10,20] [-dff]", "(skip if 'nowidelut', only for '-retime')");
+ else if (nowidelut)
+ run("abc -luts 2:2,3,6:5" + string(retime ? " -dff" : ""));
else
- Pass::call(design, "techmap -map +/xilinx/cells_map.v");
- Pass::call(design, "dffinit -ff FDRE Q INIT -ff FDCE Q INIT -ff FDPE Q INIT");
- Pass::call(design, "clean");
+ run("abc -luts 2:2,3,6:5,10,20" + string(retime ? " -dff" : ""));
+ run("clean");
+ // This shregmap call infers fixed length shift registers after abc
+ // has performed any necessary retiming
+ if (!nosrl || help_mode)
+ run("shregmap -minlen 3 -init -params -enpol any_or_none", "(skip if '-nosrl')");
+ run("techmap -map +/xilinx/lut_map.v -map +/xilinx/ff_map.v -map +/xilinx/cells_map.v");
+ run("dffinit -ff FDRE Q INIT -ff FDCE Q INIT -ff FDPE Q INIT -ff FDSE Q INIT "
+ "-ff FDRE_1 Q INIT -ff FDCE_1 Q INIT -ff FDPE_1 Q INIT -ff FDSE_1 Q INIT");
+ run("clean");
}
- if (check_label(active, run_from, run_to, "check"))
- {
- Pass::call(design, "hierarchy -check");
- Pass::call(design, "stat");
- Pass::call(design, "check -noinit");
+ if (check_label("check")) {
+ run("hierarchy -check");
+ run("stat -tech xilinx");
+ run("check -noinit");
}
- if (check_label(active, run_from, run_to, "edif"))
- {
- if (!edif_file.empty())
- Pass::call(design, stringf("write_edif %s", edif_file.c_str()));
- }
- if (check_label(active, run_from, run_to, "blif"))
- {
- if (!blif_file.empty())
- Pass::call(design, stringf("write_blif %s", edif_file.c_str()));
+ if (check_label("edif")) {
+ if (!edif_file.empty() || help_mode)
+ run(stringf("write_edif -pvector bra %s", edif_file.c_str()));
}
- log_pop();
+ if (check_label("blif")) {
+ if (!blif_file.empty() || help_mode)
+ run(stringf("write_blif %s", edif_file.c_str()));
+ }
}
} SynthXilinxPass;