Statistics
| Branch: | Tag: | Revision:

root / usrp2 / vrt / vita_rx_framer.v @ 4f79676f

History | View | Annotate | Download (7.6 kB)

1

    
2
module vita_rx_framer
3
  #(parameter BASE=0,
4
    parameter MAXCHAN=1)
5
   (input clk, input reset, input clear,
6
    input set_stb, input [7:0] set_addr, input [31:0] set_data,
7
    
8
    // To FIFO interface of Buffer Pool
9
    output [35:0] data_o,
10
    input dst_rdy_i,
11
    output src_rdy_o,
12
    
13
    // From vita_rx_control
14
    input [4+64+(32*MAXCHAN)-1:0] sample_fifo_i,
15
    input sample_fifo_src_rdy_i,
16
    output sample_fifo_dst_rdy_o,
17
    
18
    // FIFO Levels
19
    output [15:0] fifo_occupied,
20
    output fifo_full,
21
    output fifo_empty,
22
    
23
    output [31:0] debug_rx
24
    );
25

    
26
   localparam SAMP_WIDTH  = 4+64+(32*MAXCHAN);
27
   reg [3:0] 	  sample_phase;
28
   wire [3:0] 	  numchan;
29
   wire [3:0] 	  flags_fifo_o = sample_fifo_i[SAMP_WIDTH-1:SAMP_WIDTH-4];
30
   wire [63:0] 	  vita_time_fifo_o = sample_fifo_i[SAMP_WIDTH-5:SAMP_WIDTH-68];
31

    
32
   reg [31:0] 	  data_fifo_o;
33

    
34
   // The tools won't synthesize properly without this kludge because of the variable
35
   // parameter length
36
   
37
   wire [127:0]   FIXED_WIDTH_KLUDGE = sample_fifo_i;
38
   always @*
39
     case(sample_phase)
40
       4'd0 : data_fifo_o = FIXED_WIDTH_KLUDGE[31:0];
41
       4'd1 : data_fifo_o = FIXED_WIDTH_KLUDGE[63:32];
42
       4'd2 : data_fifo_o = FIXED_WIDTH_KLUDGE[95:64];
43
       4'd3 : data_fifo_o = FIXED_WIDTH_KLUDGE[127:96];
44
       default : data_fifo_o = 32'hDEADBEEF;
45
     endcase // case (sample_phase)
46
   
47
   wire 	  clear_pkt_count, pkt_fifo_rdy, sample_fifo_in_rdy;
48
   
49
   wire [31:0] 	  vita_header, vita_streamid, vita_trailer;
50
   wire [15:0] 	  samples_per_packet;
51
   
52
   reg [33:0] 	  pkt_fifo_line;
53
   reg [3:0] 	  vita_state;
54
   reg [15:0] 	  sample_ctr;
55
   reg [3:0] 	  pkt_count;
56
   
57
   wire [15:0] 	  vita_pkt_len = samples_per_packet + 6;
58
   //wire [3:0] flags = {signal_overrun,signal_brokenchain,signal_latecmd,signal_cmd_done};
59

    
60
   wire 	  clear_reg;
61
   wire 	  clear_int  = clear | clear_reg;
62

    
63
   setting_reg #(.my_addr(BASE+3)) sr_clear
64
     (.clk(clk),.rst(reset),.strobe(set_stb),.addr(set_addr),
65
      .in(set_data),.out(),.changed(clear_reg));
66

    
67
   setting_reg #(.my_addr(BASE+4)) sr_header
68
     (.clk(clk),.rst(reset),.strobe(set_stb),.addr(set_addr),
69
      .in(set_data),.out(vita_header),.changed());
70

    
71
   setting_reg #(.my_addr(BASE+5)) sr_streamid
72
     (.clk(clk),.rst(reset),.strobe(set_stb),.addr(set_addr),
73
      .in(set_data),.out(vita_streamid),.changed(clear_pkt_count));
74

    
75
   setting_reg #(.my_addr(BASE+6)) sr_trailer
76
     (.clk(clk),.rst(reset),.strobe(set_stb),.addr(set_addr),
77
      .in(set_data),.out(vita_trailer),.changed());
78

    
79
   setting_reg #(.my_addr(BASE+7)) sr_samples_per_pkt
80
     (.clk(clk),.rst(reset),.strobe(set_stb),.addr(set_addr),
81
      .in(set_data),.out(samples_per_packet),.changed());
82

    
83
   setting_reg #(.my_addr(BASE+8), .at_reset(1)) sr_numchan
84
     (.clk(clk),.rst(reset),.strobe(set_stb),.addr(set_addr),
85
      .in(set_data),.out(numchan),.changed());
86

    
87
   // Output FIFO for packetized data
88
   localparam VITA_IDLE 	 = 0;
89
   localparam VITA_HEADER 	 = 1;
90
   localparam VITA_STREAMID 	 = 2;
91
   localparam VITA_SECS 	 = 3;
92
   localparam VITA_TICS 	 = 4;
93
   localparam VITA_TICS2 	 = 5;
94
   localparam VITA_PAYLOAD 	 = 6;
95
   localparam VITA_TRAILER 	 = 7;
96
   localparam VITA_ERR_HEADER 	 = 9;  // All ERR at 4'b1000 or'ed with base
97
   localparam VITA_ERR_STREAMID  = 10;
98
   localparam VITA_ERR_SECS 	 = 11;
99
   localparam VITA_ERR_TICS 	 = 12;
100
   localparam VITA_ERR_TICS2 	 = 13;
101
   localparam VITA_ERR_PAYLOAD 	 = 14;
102
   localparam VITA_ERR_TRAILER 	 = 15; // Extension context packets have no trailer
103
      
104
   always @(posedge clk)
105
     if(reset | clear_pkt_count)
106
       pkt_count <= 0;
107
     else if((vita_state == VITA_TRAILER) & pkt_fifo_rdy)
108
       pkt_count <= pkt_count + 1;
109

    
110
   wire 	  has_streamid = vita_header[28];
111
   wire 	  has_trailer = vita_header[26];
112
   reg 		  trl_eob;
113
   
114
   always @*
115
     case(vita_state)
116
       // Data packets are IF Data packets with or w/o streamid, no classid, with trailer
117
       VITA_HEADER : pkt_fifo_line <= {2'b01,3'b000,vita_header[28],2'b01,vita_header[25:20],pkt_count,vita_pkt_len};
118
       VITA_STREAMID : pkt_fifo_line <= {2'b00,vita_streamid};
119
       VITA_SECS : pkt_fifo_line <= {2'b00,vita_time_fifo_o[63:32]};
120
       VITA_TICS : pkt_fifo_line <= {2'b00,32'd0};
121
       VITA_TICS2 : pkt_fifo_line <= {2'b00,vita_time_fifo_o[31:0]};
122
       VITA_PAYLOAD : pkt_fifo_line <= {2'b00,data_fifo_o};
123
       VITA_TRAILER : pkt_fifo_line <= {2'b10,vita_trailer[31:21],1'b1,vita_trailer[19:9],trl_eob,8'd0};
124

    
125
       // Error packets are Extension Context packets, which have no trailer
126
       VITA_ERR_HEADER : pkt_fifo_line <= {2'b01,4'b0101,4'b0000,vita_header[23:20],pkt_count,16'd6};
127
       VITA_ERR_STREAMID : pkt_fifo_line <= {2'b00,vita_streamid};
128
       VITA_ERR_SECS : pkt_fifo_line <= {2'b00,vita_time_fifo_o[63:32]};
129
       VITA_ERR_TICS : pkt_fifo_line <= {2'b00,32'd0};
130
       VITA_ERR_TICS2 : pkt_fifo_line <= {2'b00,vita_time_fifo_o[31:0]};
131
       VITA_ERR_PAYLOAD : pkt_fifo_line <= {2'b11,28'd0,flags_fifo_o};
132
       //VITA_ERR_TRAILER : pkt_fifo_line <= {2'b11,vita_trailer};
133
       
134
       default : pkt_fifo_line <= 34'h0_FFFF_FFFF;
135
       endcase // case (vita_state)
136

    
137
   always @(posedge clk)
138
     if(reset)
139
       begin
140
	  vita_state   <= VITA_IDLE;
141
	  sample_ctr   <= 0;
142
	  sample_phase <= 0;
143
       end
144
     else
145
       if(vita_state==VITA_IDLE)
146
	 begin
147
	    sample_ctr <= 1;
148
	    sample_phase <= 0;
149
	    if(sample_fifo_src_rdy_i)
150
	      if(|flags_fifo_o[3:1])
151
		vita_state <= VITA_ERR_HEADER;
152
	      else
153
		vita_state <= VITA_HEADER;
154
	 end
155
       else if(pkt_fifo_rdy)
156
	 case(vita_state)
157
	   VITA_HEADER :
158
	     if(has_streamid)
159
	       vita_state <= VITA_STREAMID;
160
	     else
161
	       vita_state <= VITA_SECS;
162
	   VITA_PAYLOAD :
163
	     if(sample_fifo_src_rdy_i)
164
	       begin
165
		  if(sample_phase == (numchan-4'd1))
166
		    begin
167
		       sample_phase <= 0;
168
		       sample_ctr   <= sample_ctr + 1;
169
		       trl_eob <= flags_fifo_o[0];
170
		       if(sample_ctr == samples_per_packet)
171
			 vita_state <= VITA_TRAILER;
172
		       if(|flags_fifo_o)   // end early if any flag is set
173
			 vita_state <= VITA_TRAILER;
174
		    end
175
		  else
176
		    sample_phase <= sample_phase + 1;
177
	       end // if (sample_fifo_src_rdy_i)
178
	   VITA_ERR_PAYLOAD :
179
	     vita_state <= VITA_IDLE;
180
	   VITA_TRAILER :
181
	     vita_state <= VITA_IDLE;
182
	   default :
183
	     vita_state 	   <= vita_state + 1;
184
	 endcase // case (vita_state)
185

    
186
   reg req_write_pkt_fifo;
187
   always @*
188
     case(vita_state)
189
       VITA_IDLE :
190
	 req_write_pkt_fifo <= 0;
191
       VITA_HEADER, VITA_STREAMID, VITA_SECS, VITA_TICS, VITA_TICS2, VITA_TRAILER :
192
	 req_write_pkt_fifo <= 1;
193
       VITA_PAYLOAD :
194
	 // Write if sample ready and no error flags
195
     	 req_write_pkt_fifo <= (sample_fifo_src_rdy_i & ~|flags_fifo_o[3:1]);
196
       VITA_ERR_HEADER, VITA_ERR_STREAMID, VITA_ERR_SECS, VITA_ERR_TICS, VITA_ERR_TICS2, VITA_ERR_PAYLOAD :
197
	 req_write_pkt_fifo <= 1;
198
       default :
199
	 req_write_pkt_fifo <= 0;
200
     endcase // case (vita_state)
201
   
202
   //wire req_write_pkt_fifo  = (vita_state != VITA_IDLE) & (sample_fifo_src_rdy_i | (vita_state != VITA_PAYLOAD));
203
   
204
   // Short FIFO to buffer between us and the FIFOs outside
205
   fifo_short #(.WIDTH(34)) rx_pkt_fifo 
206
     (.clk(clk), .reset(reset), .clear(clear_int),
207
      .datain(pkt_fifo_line), .src_rdy_i(req_write_pkt_fifo), .dst_rdy_o(pkt_fifo_rdy),
208
      .dataout(data_o[33:0]), .src_rdy_o(src_rdy_o), .dst_rdy_i(dst_rdy_i),
209
      .space(),.occupied(fifo_occupied[4:0]) );
210
   assign fifo_occupied[15:5] = 0;
211
   assign data_o[35:34] = 2'b00;  // Always write full lines
212
   assign sample_fifo_dst_rdy_o  = pkt_fifo_rdy & 
213
				   ( ((vita_state==VITA_PAYLOAD) & 
214
				      (sample_phase == (numchan-4'd1)) & 
215
				      ~|flags_fifo_o[3:1]) |
216
				     (vita_state==VITA_ERR_PAYLOAD));
217
   
218
   assign debug_rx  = vita_state;
219
   
220
endmodule // rx_control