CID Aplicatii 5

De la WikiLabs
Versiunea din 26 martie 2021 12:54, autor: Gvpopescu (discuție | contribuții) (Pagină nouă: ==Tri-State buffer== '''Tri-State Buffer''' este un circuit care, prin intermediul unui semnal de enable, controleaza daca intrarea sa va fi conectata la iesire sau nu. In cazul in...)
(dif) ← Versiunea anterioară | Versiunea curentă (dif) | Versiunea următoare → (dif)
Jump to navigationJump to search

Tri-State buffer

Tri-State Buffer este un circuit care, prin intermediul unui semnal de enable, controleaza daca intrarea sa va fi conectata la iesire sau nu. In cazul in care semnalul de enable este activ, la iesire va fi conectat semnalul de intrare (se comporta ca un buffer obisnuit). Daca enable nu este activ, iesirea sa va fi pusa in stare de high-Z (high-impendance sau open-circuit), deconectand iesirea de la circuitul la care este conectat.

Acest tip de buffer permite mai multor circuite sa foloseasca aceeasi linie de iesire. O aplicatie comuna a acestui tip de buffer este conectarea unui circuit la o magistrala bidirectionala. Modalitatea de conectare a unui circuitului la o astfel de magistrala este descrisa in figura urmatoare:

n schema de mai sus, TX reprezinta data ce trebuie transmisa, RX data ce se receptioneaza, data este magistrala bidirectionala, iar direction controleaza directia datelor (circuitul transmite sau receptioneaza). Transmisia si receptia nu se pot face in acelasi timp.

Implementarea Verilog a circuitului de conectare (magistrala pe 8 biti)

module Bidirectional(
    input [7:0] TX,
    input direction,
    output [7:0] RX,
    inout [7:0] data
);

//RX buffer
assign RX = data;
//TX Tri-State buffer
assign data = (direction == 1) ? TX : 8'bZ;

endmodule

Implementarea Verilog a modulului de test

Pentru a putea testa un circuit care contine un Tri-State buffer (un semnal de tip inout), trebuie sa procedam astfel: In modulul de test, pentru fiecare intrare se defineste un reg si pentru fiecare iesire se defineste un wire. Pentru fiecare semnal de tip inout se definesc doua semnale: un wire (aici, data_t), ce va fi conectat la modulul testat, si un reg (aici, data_in_t), ce va fi conectat printr-un Tri-State buffer (enable inversat fata de cel din modulul testat) la semnalul de tip wire (aici, data_t). Vom folosi acest reg pentru a genera stimuli in timpul simularii unei receptii.

`timescale 1ns/1ps

module Bidirectional_TB();

reg [7:0] TX_t;
reg direction_t;
wire [7:0] RX_t;
wire [7:0] data_t;
reg [7:0] data_in_t;

assign data_t = (direction_t == 0) ? data_in_t : 8'dZ;

initial begin
       data_in_t = 8'd0;
       TX_t = 8'd1;
       direction_t = 1; //transmitere
    #2 data_in_t = 8'd7;
       direction_t = 0; //receptie
    #2 TX_t = 8'd3;
       direction_t = 1; //transmitere
    #5 $stop();
end

Bidirectional DUT(
    .TX(TX_t),
    .direction(direction_t),
    .RX(RX_t),
    .data(data_t)
);
endmodule

Observatii

1. Semnalul data ia valoarea lui TX atunci cand direction este 1. De asemenea, RX ia valoarea lui TX deoarece este conectat la data printr-un buffer simplu. Valoarea lui RX va trebui sa fie ignorata de circuit atunci cand direction este 1 (transmisie).

2. Atunci cand direction este 0 avem o receptie, data si RX actualizandu-se cu valoarea lui data_in_t, care simuleaza un alt modul ce transmite catre circuitul testat. TX nu se modifica in acest caz deoarece este deconectat de catre Tri-State buffer de la magistrala data.


Realizarea unei unitati de adunare ce are capacitatea de a selecta intre mai multi operanzi

Circuitul ALU este format din trei module: doua multiplexoare identice (M1 si M2) si un modul de adunare (ADD). Modulul MUX are doua intrari pe 8 biti, selectand la iesire una dintre acestea pe baza intrarii de selectie (SEL). De exemplu, daca SEL este 0, iesirea multiplexorului va fi A. Daca SEL este 1, iesirea multiplexorului este B.

Sumatorul ADD va folosi ca operanzi cele doua iesiri ale multiplexoarelor. Daca SEL este 0, M1 va avea la iesire A, iar M2 va avea la iesire C. Asadar, operanzii sumatorului vor fi A si C, iar iesirea modulului ALU va fi A + C. Daca SEL este 1, M1 va avea la iesire B, iar M2 va avea la iesire D. Asadar, operanzii sumatorului vor fi B si D, iar iesirea modulului ALU va fi B + D.

Implementarea Verilog a modulului MUX

module MUX(
    input [7:0] in0,
    input [7:0] in1,
    input sel,
    output [7:0] out
);

assign out = (sel == 0) ? in0 : in1;

endmodule

Implementarea Verilog a modulului Adder

module Adder(
    input [7:0] in0,
    input [7:0] in1,
    output [7:0] sum
);

assign sum = in0 + in1;

endmodule

Implementarea Verilog a modulului ALU

module ALU(
    input [7:0] A,
    input [7:0] B,
    input [7:0] C,
    input [7:0] D,
    input SEL,
    output [7:0] OUT
);

wire [7:0] w1, w2;

MUX M1(
    .in0(A),
    .in1(B),
    .sel(SEL),
    .out(w1)
);

MUX M2(
    .in0(C),
    .in1(D),
    .sel(SEL),
    .out(w2)
);

Adder ADD(
    .in0(w1),
    .in1(w2),
    .sum(OUT)
);

endmodule

Implementarea Verilog a modulului de test

module ALU_TB();

reg [7:0] A_t, B_t, C_t, D_t;
reg SEL_t;
wire OUT_t;

initial begin
      A_t = 8'b00000001;
      B_t = 8'b00000101;
      C_t = 8'b00001111;
      D_t = 8'b00001101;
      SEL_t = 0;
   #1 SEL_t = 1;
   #1 B_t = 8'b00000000;
      A_t = 8'b00000011;
   #1 SEL_t = 0;
   #1 $stop();
end

ALU DUT(
    .A(A_t),
    .B(B_t),
    .C(C_t),
    .D(D_t),
    .SEL(SEL_t),
    .OUT(OUT_t)
);

endmodule