論理回路デザイン |
|
/* **************************** MODULE PREAMBLE ******************************** Copyright (c) 2011, ArchiTek This document constitutes confidential and proprietary information of ArchiTek. All rights reserved. */ // ***************************** MODULE HEADER ********************************* module fft ( iVld, iStall, oVld, oStall, mRdStrb, mRdAck, mRdData, mWrStrb, mWrAck, mWrData, reset, clk ); // ************************* PARAMETER DECLARATIONS **************************** // 最大のポイント数の指数はカウンタ等のビット範囲を定める parameter MRR = 10; // Max Radix Radix // 処理するポイント数は予め指定、可変にする場合はiVldと同期させる parameter RADIX = 4'd10; // *************************** I/O DECLARATIONS ******************************** // Pipe Input input iVld; output iStall; // Pipe Output output oVld; input oStall; // データは16ビットの半精度浮動小数点が8つ並ぶ(4x2ペア) // Memory Interface (Read Data) output mRdStrb; input mRdAck; input [127:0] mRdData; // Memory Interface (Write Data) output mWrStrb; input mWrAck; output [127:0] mWrData; // Utility input reset; input clk; // ************************** LOCAL DECLARATIONS ******************************* // ここから各ユニットの入出力信号を定義する // Load Data wire oLoadDataVld; wire oLoadDataStall; wire [1:0] oLoadDataFlip; wire ldRam0WE, ldRam1WE, ldRam2WE, ldRam3WE; wire [7:0] ldRam0WA, ldRam1WA, ldRam2WA, ldRam3WA; wire [31:0] ldRam0WD, ldRam1WD, ldRam2WD, ldRam3WD; // Butterfly Calc FIFO wire iBFIFOVld; wire iBFIFOStall; wire oBFIFOVld; wire oBFIFOStall; // Butterfly Calc wire iBfCalcVld; wire iBfCalcStall; wire oBfCalcVld; wire oBfCalcStall; wire [1:0] bcRamRF; reg [1:0] bcRamRFB; wire bcRamRP; wire bcRam0RE, bcRam1RE, bcRam2RE, bcRam3RE; wire [7:0] bcRam0RA, bcRam1RA, bcRam2RA, bcRam3RA; wire [31:0] bcRam0RD, bcRam1RD, bcRam2RD, bcRam3RD; wire bcRamWP; wire [1:0] bcRamWF; wire bcRam0WE, bcRam1WE, bcRam2WE, bcRam3WE; wire [7:0] bcRam0WA, bcRam1WA, bcRam2WA, bcRam3WA; wire [31:0] bcRam0WD, bcRam1WD, bcRam2WD, bcRam3WD; // Coefficients of Fourier wire [MRR-3:0] wIndex; wire [2:0] wPhase; wire [15:0] wRe0, wIm0, wRe1, wIm1, wRe2, wIm2, wRe3, wIm3; // Store Data FIFO wire iSdFIFOVld; wire iSdFIFOStall; wire oSdFIFOVld; wire oSdFIFOStall; // Store Data wire iStoreDataVld; wire iStoreDataStall; wire [1:0] oStoreDataFlip; reg [1:0] oStoreDataFlipB; wire stRam0RE, stRam1RE, stRam2RE, stRam3RE; wire [7:0] stRam0RA, stRam1RA, stRam2RA, stRam3RA; wire [31:0] stRam0RD, stRam1RD, stRam2RD, stRam3RD; // 8つ(4Bank x2セット)あるSRAM信号の入出力信号を定義する // アドレスレンジは4Bankに分かれていることから2を引く // データには実数と虚数のペアが入る // SRAM Signals wire ram0WE0, ram0WE1, ram1WE0, ram1WE1, ram2WE0, ram2WE1, ram3WE0, ram3WE1; wire [MRR-2:0] ram0WA0, ram0WA1, ram1WA0, ram1WA1, ram2WA0, ram2WA1, ram3WA0, ram3WA1; wire [31:0] ram0WD0, ram0WD1, ram1WD0, ram1WD1, ram2WD0, ram2WD1, ram3WD0, ram3WD1; wire ram0RE0, ram0RE1, ram1RE0, ram1RE1, ram2RE0, ram2RE1, ram3RE0, ram3RE1; wire [MRR-2:0] ram0RA0, ram0RA1, ram1RA0, ram1RA1, ram2RA0, ram2RA1, ram3RA0, ram3RA1; wire [31:0] ram0RD0, ram0RD1, ram1RD0, ram1RD1, ram2RD0, ram2RD1, ram3RD0, ram3RD1; // ****************************** MODULE BODY ********************************** // ----------------------------------------------------------------------------- // Load Data // RADIXが可変なら、iVldに同期させる // iStallはLoadDataの処理がほぼ終わるまでアサートするため、突き放したい場合は前段にFIFOを入れる fftLoadData #(MRR) loadData_0 ( .iVld (iVld), .iStall (iStall), .iRadix (RADIX), .oVld (oLoadDataVld), .oStall (oLoadDataStall), .oFlip (oLoadDataFlip), // SRAMダブルバッファ制御に使用 .mStrb (mRdStrb), .mAck (mRdAck), .mData (mRdData), .ram0WE (ldRam0WE), // SRAMへのWrite信号グループ .ram0WA (ldRam0WA), .ram0WD (ldRam0WD), .ram1WE (ldRam1WE), .ram1WA (ldRam1WA), .ram1WD (ldRam1WD), .ram2WE (ldRam2WE), .ram2WA (ldRam2WA), .ram2WD (ldRam2WD), .ram3WE (ldRam3WE), .ram3WA (ldRam3WA), .ram3WD (ldRam3WD), .reset (reset), .clk (clk) ); assign oLoadDataStall = iBFIFOStall; // ----------------------------------------------------------------------------- // Butterfly Calc FIFO // LoadDataとBcCalcを繋ぐFIFO、データがないのでSignalingだけ sig_2 sig_0 ( .iVld (iBFIFOVld), .iStall (iBFIFOStall), .oVld (oBFIFOVld), .oStall (oBFIFOStall), .reset (reset), .clk (clk) ); assign iBFIFOVld = oLoadDataVld; assign oBFIFOStall = iBfCalcStall; // ----------------------------------------------------------------------------- // Butterfly Calculation // RADIXが可変なら、iVldに同期させる // 逆変換が必要な場合もiVldに同期したフラグが必要 fftBfCalc #(MRR) bfCalc_0 ( .iVld (iBfCalcVld), .iStall (iBfCalcStall), .iRadix (RADIX), .oVld (oBfCalcVld), .oStall (oBfCalcStall), .wIndex (wIndex), // 係数テーブルへのインターフェイス .wPhase (wPhase), .wRe0 (wRe0), .wIm0 (wIm0), .wRe1 (wRe1), .wIm1 (wIm1), .wRe2 (wRe2), .wIm2 (wIm2), .wRe3 (wRe3), .wIm3 (wIm3), .ramRF (bcRamRF), // SRAMダブルバッファ制御に使用(Read) .ramRP (bcRamRP), // SRAM領域制御に使用(Read) .ram0RE (bcRam0RE), // SRAMへのRead信号グループ .ram0RA (bcRam0RA), .ram0RD (bcRam0RD), .ram1RE (bcRam1RE), .ram1RA (bcRam1RA), .ram1RD (bcRam1RD), .ram2RE (bcRam2RE), .ram2RA (bcRam2RA), .ram2RD (bcRam2RD), .ram3RE (bcRam3RE), .ram3RA (bcRam3RA), .ram3RD (bcRam3RD), .ramWF (bcRamWF), // SRAMダブルバッファ制御に使用(Write) .ramWP (bcRamWP), // SRAM領域制御に使用(Write) .ram0WE (bcRam0WE), // SRAMへのWrite信号グループ .ram0WA (bcRam0WA), .ram0WD (bcRam0WD), .ram1WE (bcRam1WE), .ram1WA (bcRam1WA), .ram1WD (bcRam1WD), .ram2WE (bcRam2WE), .ram2WA (bcRam2WA), .ram2WD (bcRam2WD), .ram3WE (bcRam3WE), .ram3WA (bcRam3WA), .ram3WD (bcRam3WD), .reset (reset), .clk (clk) ); assign iBfCalcVld = oBFIFOVld; assign oBfCalcStall = iSdFIFOStall; // ----------------------------------------------------------------------------- // Coefficients of Fourier // 係数テーブルモジュール、レイテンシ0のROMとして振る舞う fftCoef #(MRR) coef_0 ( .wIndex (wIndex), .wPhase (wPhase), .wRe0 (wRe0), .wIm0 (wIm0), .wRe1 (wRe1), .wIm1 (wIm1), .wRe2 (wRe2), .wIm2 (wIm2), .wRe3 (wRe3), .wIm3 (wIm3) ); // ----------------------------------------------------------------------------- // Store Data FIFO // BcCalcとStoreDataを繋ぐFIFO、データがないのでSignalingだけ sig_2 sig_1 ( .iVld (iSdFIFOVld), .iStall (iSdFIFOStall), .oVld (oSdFIFOVld), .oStall (oSdFIFOStall), .reset (reset), .clk (clk) ); assign iSdFIFOVld = oBfCalcVld; assign oSdFIFOStall = iStoreDataStall; // ----------------------------------------------------------------------------- // Store Data // RADIXが可変なら、iVldに同期させる // oVldは最後のデータを出し切った時点でアサート // アサート期間以外でoStallをアサートしてもパイプラインは止まらない fftStoreData #(MRR) storeData_0 ( .iVld (iStoreDataVld), .iStall (iStoreDataStall), .iRadix (RADIX), .oVld (oVld), .oStall (oStall), .oFlip (oStoreDataFlip), // SRAMダブルバッファ制御に使用 .mStrb (mWrStrb), .mAck (mWrAck), .mData (mWrData), .ram0RE (stRam0RE), // SRAMへのRead信号グループ .ram0RA (stRam0RA), .ram0RD (stRam0RD), .ram1RE (stRam1RE), .ram1RA (stRam1RA), .ram1RD (stRam1RD), .ram2RE (stRam2RE), .ram2RA (stRam2RA), .ram2RD (stRam2RD), .ram3RE (stRam3RE), .ram3RA (stRam3RA), .ram3RD (stRam3RD), .reset (reset), .clk (clk) ); assign iStoreDataVld = oSdFIFOVld; // ----------------------------------------------------------------------------- // SRAM Signals // LoadData, BcCalcのSRAM Write信号をマージ // oLoadDataFlipとbcRamWFは0か排他的な関係になっているため信号は重ならない // また、それぞれのMSBとLSBも排他的になっており、同じユニットが2セット同時アクセスすることはない assign { ram0WE0, ram0WA0, ram0WD0, ram1WE0, ram1WA0, ram1WD0, ram2WE0, ram2WA0, ram2WD0, ram3WE0, ram3WA0, ram3WD0 } = {4*(MRR+32){oLoadDataFlip[0]}} & { ldRam0WE, 1'b0, ldRam0WA, ldRam0WD, ldRam1WE, 1'b0, ldRam1WA, ldRam1WD, ldRam2WE, 1'b0, ldRam2WA, ldRam2WD, ldRam3WE, 1'b0, ldRam3WA, ldRam3WD } | {4*(MRR+32){bcRamWF[0]}} & { bcRam0WE, bcRamWP, bcRam0WA, bcRam0WD, bcRam1WE, bcRamWP, bcRam1WA, bcRam1WD, bcRam2WE, bcRamWP, bcRam2WA, bcRam2WD, bcRam3WE, bcRamWP, bcRam3WA, bcRam3WD }; assign { ram0WE1, ram0WA1, ram0WD1, ram1WE1, ram1WA1, ram1WD1, ram2WE1, ram2WA1, ram2WD1, ram3WE1, ram3WA1, ram3WD1 } = {4*(MRR+32){oLoadDataFlip[1]}} & { ldRam0WE, 1'b0, ldRam0WA, ldRam0WD, ldRam1WE, 1'b0, ldRam1WA, ldRam1WD, ldRam2WE, 1'b0, ldRam2WA, ldRam2WD, ldRam3WE, 1'b0, ldRam3WA, ldRam3WD } | {4*(MRR+32){bcRamWF[1]}} & { bcRam0WE, bcRamWP, bcRam0WA, bcRam0WD, bcRam1WE, bcRamWP, bcRam1WA, bcRam1WD, bcRam2WE, bcRamWP, bcRam2WA, bcRam2WD, bcRam3WE, bcRamWP, bcRam3WA, bcRam3WD }; // BcCalc, StoreDataのSRAM Read信号をマージ // 仕組みは上記Writeと同じ assign { ram0RE0, ram0RA0, ram1RE0, ram1RA0, ram2RE0, ram2RA0, ram3RE0, ram3RA0 } = {4*MRR{oStoreDataFlip[0]}} & { stRam0RE, 1'b1, stRam0RA, stRam1RE, 1'b1, stRam1RA, stRam2RE, 1'b1, stRam2RA, stRam3RE, 1'b1, stRam3RA } | {4*MRR{bcRamRF[0]}} & { bcRam0RE, bcRamRP, bcRam0RA, bcRam1RE, bcRamRP, bcRam1RA, bcRam2RE, bcRamRP, bcRam2RA, bcRam3RE, bcRamRP, bcRam3RA }; assign { ram0RE1, ram0RA1, ram1RE1, ram1RA1, ram2RE1, ram2RA1, ram3RE1, ram3RA1 } = {4*MRR{oStoreDataFlip[1]}} & { stRam0RE, 1'b1, stRam0RA, stRam1RE, 1'b1, stRam1RA, stRam2RE, 1'b1, stRam2RA, stRam3RE, 1'b1, stRam3RA } | {4*MRR{bcRamRF[1]}} & { bcRam0RE, bcRamRP, bcRam0RA, bcRam1RE, bcRamRP, bcRam1RA, bcRam2RE, bcRamRP, bcRam2RA, bcRam3RE, bcRamRP, bcRam3RA }; // Readデータを分配 assign {stRam0RD, stRam1RD, stRam2RD, stRam3RD} = {128{oStoreDataFlipB[0]}} & {ram0RD0, ram1RD0, ram2RD0, ram3RD0} | {128{oStoreDataFlipB[1]}} & {ram0RD1, ram1RD1, ram2RD1, ram3RD1}; assign {bcRam0RD, bcRam1RD, bcRam2RD, bcRam3RD} = {128{bcRamRFB[0]}} & {ram0RD0, ram1RD0, ram2RD0, ram3RD0} | {128{bcRamRFB[1]}} & {ram0RD1, ram1RD1, ram2RD1, ram3RD1}; // Readデータはアクセスに対し遅延するため、データ配分に関わるbcRamRFとoStoreDataFlipのラッチが必要 always @(posedge clk) if (reset) bcRamRFB <= #1 2'h0; else if (|bcRamRF) // パイプラインStallを加味(bcRamRFにStallが織り込まれている) bcRamRFB <= #1 bcRamRF; always @(posedge clk) if (reset) oStoreDataFlipB <= #1 2'h0; else if (|oStoreDataFlip) oStoreDataFlipB <= #1 oStoreDataFlip; // ----------------------------------------------------------------------------- // SRAM #0 dualSRAM #(32, MRR-1) ram_00 ( .WE (ram0WE0), .WA (ram0WA0), .WD (ram0WD0), .RE (ram0RE0), .RA (ram0RA0), .RD (ram0RD0), .CK (clk) ); dualSRAM #(32, MRR-1) ram_01 ( .WE (ram0WE1), .WA (ram0WA1), .WD (ram0WD1), .RE (ram0RE1), .RA (ram0RA1), .RD (ram0RD1), .CK (clk) ); // ----------------------------------------------------------------------------- // SRAM #1 dualSRAM #(32, MRR-1) ram_10 ( .WE (ram1WE0), .WA (ram1WA0), .WD (ram1WD0), .RE (ram1RE0), .RA (ram1RA0), .RD (ram1RD0), .CK (clk) ); dualSRAM #(32, MRR-1) ram_11 ( .WE (ram1WE1), .WA (ram1WA1), .WD (ram1WD1), .RE (ram1RE1), .RA (ram1RA1), .RD (ram1RD1), .CK (clk) ); // ----------------------------------------------------------------------------- // SRAM #2 dualSRAM #(32, MRR-1) ram_20 ( .WE (ram2WE0), .WA (ram2WA0), .WD (ram2WD0), .RE (ram2RE0), .RA (ram2RA0), .RD (ram2RD0), .CK (clk) ); dualSRAM #(32, MRR-1) ram_21 ( .WE (ram2WE1), .WA (ram2WA1), .WD (ram2WD1), .RE (ram2RE1), .RA (ram2RA1), .RD (ram2RD1), .CK (clk) ); // ----------------------------------------------------------------------------- // SRAM #3 dualSRAM #(32, MRR-1) ram_30 ( .WE (ram3WE0), .WA (ram3WA0), .WD (ram3WD0), .RE (ram3RE0), .RA (ram3RA0), .RD (ram3RD0), .CK (clk) ); dualSRAM #(32, MRR-1) ram_31 ( .WE (ram3WE1), .WA (ram3WA1), .WD (ram3WD1), .RE (ram3RE1), .RA (ram3RA1), .RD (ram3RD1), .CK (clk) ); // ************************** FUNCTIONS and TASKS ****************************** endmodule // *****************************************************************************
/* **************************** MODULE PREAMBLE ******************************** Copyright (c) 2011, ArchiTek This document constitutes confidential and proprietary information of ArchiTek. All rights reserved. // FIFO記述からデータを抜いたもの */ // ***************************** MODULE HEADER ********************************* module sig_2 ( iVld, iStall, oVld, oStall, reset, clk ); // *************************** I/O DECLARATIONS ******************************** input iVld; output iStall; output oVld; input oStall; input reset; input clk; // ************************** LOCAL DECLARATIONS ******************************* reg sVld; reg sVldD; reg oVld; reg oVldD; // ******************************** MODULE BODY ******************************** // ----------------------------------------------------------------------------- // FIFO In always @(posedge clk) if (reset) sVld <= #1 1'b0; else sVld <= #1 sVldD; always @( iVld or sVld or oVld or oStall ) casex ({iVld, sVld, !oVld | !oStall}) 3'bx11: sVldD = 1'b0; 3'b1x0: sVldD = 1'b1; default: sVldD = sVld; endcase assign iStall = sVld; // ----------------------------------------------------------------------------- // FIFO Out always @(posedge clk) if (reset) oVld <= #1 1'b0; else oVld <= #1 oVldD; always @( iVld or sVld or oVld or oStall ) if (!oVld | !oStall) oVldD = iVld | sVld; else oVldD = oVld; // **************************** FUNCTIONS and TASKS **************************** endmodule // *****************************************************************************
回路デザイン > 設計例 [FFT] > コーディング1 次のページ(コーディング2) このページのTOP ▲