OpenCores
URL https://opencores.org/ocsvn/m16c5x/m16c5x/trunk

Subversion Repositories m16c5x

[/] [m16c5x/] [trunk/] [RTL/] [Src/] [UART_RXSM.v] - Blame information for rev 2

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 MichaelA
////////////////////////////////////////////////////////////////////////////////
2
//
3
//  Copyright 2008-2013 by Michael A. Morris, dba M. A. Morris & Associates
4
//
5
//  All rights reserved. The source code contained herein is publicly released
6
//  under the terms and conditions of the GNU Lesser Public License. No part of
7
//  this source code may be reproduced or transmitted in any form or by any
8
//  means, electronic or mechanical, including photocopying, recording, or any
9
//  information storage and retrieval system in violation of the license under
10
//  which the source code is released.
11
//
12
//  The source code contained herein is free; it may be redistributed and/or
13
//  modified in accordance with the terms of the GNU Lesser General Public
14
//  License as published by the Free Software Foundation; either version 2.1 of
15
//  the GNU Lesser General Public License, or any later version.
16
//
17
//  The source code contained herein is freely released WITHOUT ANY WARRANTY;
18
//  without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
19
//  PARTICULAR PURPOSE. (Refer to the GNU Lesser General Public License for
20
//  more details.)
21
//
22
//  A copy of the GNU Lesser General Public License should have been received
23
//  along with the source code contained herein; if not, a copy can be obtained
24
//  by writing to:
25
//
26
//  Free Software Foundation, Inc.
27
//  51 Franklin Street, Fifth Floor
28
//  Boston, MA  02110-1301 USA
29
//
30
//  Further, no use of this source code is permitted in any form or means
31
//  without inclusion of this banner prominently in any derived works.
32
//
33
//  Michael A. Morris
34
//  Huntsville, AL
35
//
36
////////////////////////////////////////////////////////////////////////////////
37
 
38
`timescale 1ns / 1ps
39
 
40
///////////////////////////////////////////////////////////////////////////////
41
// Company:         M. A. Morris & Associates
42
// Engineer:        Michael A. Morris
43
//
44
// Create Date:     08:44:44 05/31/2008 
45
// Design Name:     Synchronous Serial Peripheral (SSP) Interface UART 
46
// Module Name:     ../VerilogCoponentsLib/SSP_UART/UART_RXSM.v
47
// Project Name:    Verilog Components Library
48
// Target Devices:  XC3S50A-4VQG100I, XC3S20A-4VQG100I, XC3S700AN-4FFG484I 
49
// Tool versions:   ISE 10.1i SP3 
50
//
51
// Description: This module implements the SSP UART Receive State Machine
52
//
53
// Dependencies:    None 
54
//
55
// Revision History:
56
//
57
//  0.01    08E31   MAM     File Created
58
//
59
//  1.00    08F08   MAM     Module Released
60
//
61
//  1.01    08F12   MAM     Pulled Format Decoder ROM and added its outputs to 
62
//                          the port list. Allows greater format specification
63
//                          flexibility. 7-bit formats require parity. If ParEn
64
//                          is not set, the parity will be tested according to 
65
//                          the settings of the Par bits, which may result in 
66
//                          anomalous behavior.
67
//
68
//  2.00    11B06   MAM     Converted to Verilog 2001.
69
//
70
// Additional Comments: 
71
//
72
///////////////////////////////////////////////////////////////////////////////
73
 
74
module UART_RXSM(
75
    input   Rst,
76
    input   Clk,
77
 
78
    input   CE_16x,         // 16x Clock Enable - Baud Rate x16
79
 
80
    input   Len,            // Word length: 0 - 8-bits; 1 - 7 bits
81
    input   NumStop,        // Number Stop Bits: 0 - 1 Stop; 1 - 2 Stop
82
    input   ParEn,          // Parity Enable
83
    input   [1:0] Par,      // 0 - Odd; 1 - Even; 2 - Space (0); 3 - Mark (1)
84
 
85
    input   RxD,            // Input Asynchronous Serial Receive Data
86
 
87
    output  reg [8:0] RD,   // Receive Data Output - bit 8 = Rcv Error (RERR)
88
    output  reg WE_RHR,     // Write Enable - Receive Holding Register
89
 
90
    output  RxWait,         // RxSM - Wait State
91
    output  RxIdle,         // RxSM - Idle State
92
    output  RxStart,        // RxSM - Start Bit Check State
93
    output  RxShift,        // RxSM - RxD Shift State
94
    output  RxParity,       // RxSM - RxD Parity Shift State
95
    output  RxStop,         // RxSM - RxD Stop Bit Check States
96
    output  RxError         // RxSM - Error State
97
);
98
 
99
///////////////////////////////////////////////////////////////////////////////
100
//
101
//  Module Parameters
102
// 
103
 
104
//  Receive State Machine Declarations (Binary)
105
 
106
localparam pWaitMark  =  0;
107
localparam pChkMark   =  1;
108
localparam pIdle      =  3;
109
localparam pChkStart  =  2;
110
localparam pShift0    = 10;
111
localparam pShift1    = 11;
112
localparam pShift2    =  9;
113
localparam pShift3    =  8;
114
localparam pShift4    = 12;
115
localparam pShift5    = 13;
116
localparam pShift6    = 15;
117
localparam pShift7    = 14;
118
localparam pChkStop1  =  6;
119
localparam pChkStop2  =  7;
120
localparam pChkParity =  5;
121
localparam pRcvError  =  4;
122
 
123
///////////////////////////////////////////////////////////////////////////////    
124
//
125
//  Local Signal Declarations
126
//
127
 
128
    (* FSM_ENCODING="SEQUENTIAL",
129
       SAFE_IMPLEMENTATION="YES",
130
       SAFE_RECOVERY_STATE="4'b0" *) reg [3:0] RxSM = pWaitMark;
131
 
132
    reg     [3:0] BCnt;
133
    reg     [7:0] RSR;
134
 
135
    reg     Err;
136
 
137
///////////////////////////////////////////////////////////////////////////////    
138
//
139
//  Implementation
140
//
141
 
142
///////////////////////////////////////////////////////////////////////////////    
143
//
144
//  RxSM Decode
145
//
146
 
147
assign RxSM_Wait = (  (RxSM == pWaitMark)
148
                    | (RxSM == pChkMark)
149
                    | (RxSM == pIdle)
150
                    | (RxSM == pRcvError) );
151
 
152
assign RxWait   = RxSM_Wait;
153
assign RxIdle   = (RxSM == pIdle);
154
assign RxStart  = (RxSM == pChkStart);
155
assign RxShift  = (  (RxSM == pShift0)
156
                   | (RxSM == pShift1)
157
                   | (RxSM == pShift2)
158
                   | (RxSM == pShift3)
159
                   | (RxSM == pShift4)
160
                   | (RxSM == pShift5)
161
                   | (RxSM == pShift6)
162
                   | (RxSM == pShift7) );
163
assign RxParity = (RxSM == pChkParity);
164
assign RxStop   = (RxSM == pChkStop1) | (RxSM == pChkStop2);
165
assign RxError  = (RxSM == pRcvError);
166
 
167
///////////////////////////////////////////////////////////////////////////////    
168
//
169
//  Bit Rate Prescaler
170
//
171
//      Prescaler is held in the half-bit load state during reset and when the 
172
//      RXSM is in the RxSM_Wait states. As a consequence, the first overflow
173
//      is only half a bit period, and only occurs in the pChkStart state. 
174
//      Subsequent, overflows are occur once per bit period in the middle of
175
//      each of the remaining bits.
176
//
177
 
178
assign Rst_BCnt = Rst | RxSM_Wait;
179
 
180
always @(posedge Clk)
181
begin
182
    if(Rst_BCnt)
183
         BCnt <= #1 4'b1000;
184
    else if(CE_16x)
185
         BCnt <= #1 BCnt + 1;
186
end
187
 
188
assign TC_BCnt = CE_16x & (BCnt == 4'b1111);
189
 
190
///////////////////////////////////////////////////////////////////////////////    
191
 
192
assign CE_RxSM = (RxSM_Wait ? CE_16x : TC_BCnt);
193
 
194
///////////////////////////////////////////////////////////////////////////////    
195
//
196
//  Receive Shift Register
197
//
198
 
199
always @(posedge Clk)
200
begin
201
    if(Rst)
202
         RSR <= #1 8'b0;
203
    else if(CE_RxSM)
204
        case(RxSM)
205
            pChkStart :  RSR    <= #1 8'b0;
206
            pShift0   :  RSR[0] <= #1 RxD;
207
            pShift1   :  RSR[1] <= #1 RxD;
208
            pShift2   :  RSR[2] <= #1 RxD;
209
            pShift3   :  RSR[3] <= #1 RxD;
210
            pShift4   :  RSR[4] <= #1 RxD;
211
            pShift5   :  RSR[5] <= #1 RxD;
212
            pShift6   :  RSR[6] <= #1 RxD;
213
            pShift7   :  RSR[7] <= #1 RxD;
214
            default   :  RSR    <= #1 RSR;
215
        endcase
216
end
217
 
218
///////////////////////////////////////////////////////////////////////////////    
219
//
220
//  Parity Checker
221
//      if not Check Parity State, then ParErr = 0
222
//
223
 
224
assign OddPar = ^{RxD, RSR};
225
assign EvnPar = ~OddPar;
226
 
227
always @(*)
228
begin
229
    case(Par)
230
        2'b00 : Err <= ~OddPar;
231
        2'b01 : Err <= ~EvnPar;
232
        2'b10 : Err <=  RxD;
233
        2'b11 : Err <= ~RxD;
234
    endcase
235
end
236
 
237
assign ParErr = Err & (RxSM == pChkParity);
238
 
239
///////////////////////////////////////////////////////////////////////////////    
240
//
241
//  Receive Holding Register Data
242
//
243
 
244
assign CE_RD = CE_RxSM & (((RxSM == pChkStop1) & RxD) | (RxSM == pRcvError));
245
 
246
always @(posedge Clk)
247
begin
248
    if(Rst)
249
         RD <= #1 9'b0;
250
    else if(CE_RD)
251
         RD <= #1 {(RxSM == pRcvError), RSR};
252
end
253
 
254
always @(posedge Clk)
255
begin
256
    if(Rst)
257
         WE_RHR <= #1 1'b0;
258
    else
259
         WE_RHR <= #1 CE_RD;
260
end
261
 
262
///////////////////////////////////////////////////////////////////////////////    
263
//
264
//  RxSM - Receive State Machine
265
//
266
//      The Receive State Machine starts in the WaitMark state to insure that
267
//      the receive line is in the marking state before continuing. The ChkMark
268
//      state validates that the receive line is in the marking state. If it 
269
//      is, then the RxSM is adanced to the Idle state to wait for the start
270
//      bit. Otherwise, RxSM returns to the WaitMark state to wait for the line
271
//      to return to the marking (idle) state.
272
//
273
//      The format is processed through the receive sequence. The length,
274
//      parity options, and the number of stop bits determine the state tran-
275
//      sitions that the RxSM makes. A parity or a framing error is simply 
276
//      recorded as an error with the 9th bit of the receive holding register.
277
//      Line break conditions, invalid stop bits, etc. are handled through the
278
//      pRcvError and the pWaitMark states. Thus, line break conditions are not
279
//      expected to cause the RxSM to receive more than one character, and the
280
//      pWaitMark state holds the receiver in a wait state until the line 
281
//      returns to the marking (idle) state.
282
//
283
 
284
always @(posedge Clk)
285
begin
286
    if(Rst)
287
         RxSM <= #1 pWaitMark;
288
    else if(CE_RxSM)
289
        case(RxSM)
290
            pWaitMark  :  RxSM <= #1 ( RxD ? pChkMark
291
                                           : pWaitMark);
292
 
293
            pChkMark   :  RxSM <= #1 ( RxD ? pIdle
294
                                           : pWaitMark);
295
 
296
            pIdle      :  RxSM <= #1 (~RxD ? pChkStart
297
                                           : pIdle);
298
 
299
            pChkStart  :  RxSM <= #1 ( RxD ? pIdle
300
                                           : pShift0);
301
 
302
            pShift0    :  RxSM <= #1 pShift1;
303
            pShift1    :  RxSM <= #1 pShift2;
304
            pShift2    :  RxSM <= #1 pShift3;
305
            pShift3    :  RxSM <= #1 pShift4;
306
            pShift4    :  RxSM <= #1 pShift5;
307
            pShift5    :  RxSM <= #1 pShift6;
308
 
309
            pShift6    :  RxSM <= #1 (Len    ? pChkParity
310
                                             : pShift7);
311
 
312
            pShift7    :  RxSM <= #1 (ParEn  ? pChkParity
313
                                             : (NumStop ? pChkStop2
314
                                                        : pChkStop1));
315
 
316
            pChkParity :  RxSM <= #1 (ParErr ? pRcvError
317
                                             : (NumStop ? pChkStop2
318
                                                        : pChkStop1));
319
 
320
            pChkStop2  :  RxSM <= #1 (RxD ? pChkStop1
321
                                          : pRcvError);
322
 
323
            pChkStop1  :  RxSM <= #1 (RxD ? pIdle
324
                                          : pRcvError);
325
 
326
            pRcvError  :  RxSM <= #1 pWaitMark;
327
 
328
            default    :  RxSM <= #1 pWaitMark;
329
        endcase
330
end
331
 
332
endmodule

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.