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

Subversion Repositories manchesterwireless

[/] [manchesterwireless/] [trunk/] [decode/] [decode.vhd] - Blame information for rev 13

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 kingmu
-----------------------------------------------------------------------------
2
--      Copyright (C) 2009 Sam Green
3
--
4
-- This code is free software; you can redistribute it and/or
5
-- modify it under the terms of the GNU Lesser General Public
6
-- License as published by the Free Software Foundation; either
7
-- version 2.1 of the License, or (at your option) any later version.
8
--
9
-- This code is distributed in the hope that it will be useful,
10
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
11
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12
-- Lesser General Public License for more details.
13
--
14 3 kingmu
-- Decodes manchester encoded data
15
-- 
16 2 kingmu
-----------------------------------------------------------------------------
17
 
18
library IEEE;
19
use IEEE.STD_LOGIC_1164.ALL;
20
 
21
use work.globals.all;
22
 
23 3 kingmu
entity decode is
24 2 kingmu
 
25
  port (
26
    clk_i     : in  std_logic;
27
    rst_i     : in  std_logic;
28
    nd_i      : in  std_logic;
29
    encoded_i : in  std_logic_vector(3 downto 0);
30
    decoded_o : out std_logic_vector(WORD_LENGTH-1 downto 0);
31
    nd_o      : out std_logic
32
  );
33
 
34 3 kingmu
end;
35 2 kingmu
 
36 3 kingmu
architecture behavioral of decode is
37 2 kingmu
 
38
  type state_type is (reset, pause, one_0, one_1, two_0, two_1);
39
  signal state, next_state : state_type;
40
 
41
  -- *2 comes from each bit in the word is manchester encoded.
42
  -- +2 comes from protocol transmitting -------_ to initiate
43 3 kingmu
  -- a transmission; +1 from the ------- and +1 from the _
44 2 kingmu
  constant STRING_LENGTH : integer := WORD_LENGTH*2+2;
45
  -- the range -1 comes from the state machine which will
46
  -- update index_n while the protocol finishes transmission
47 3 kingmu
  signal index, index_n   : integer range -1 to STRING_LENGTH-1;
48 2 kingmu
  signal str_buffer : std_logic_vector(STRING_LENGTH-3 downto 0);
49
  signal insert : std_logic_vector(1 downto 0);
50
  signal nd_o_buff : std_logic;
51
begin
52
 
53 3 kingmu
  controller : process(nd_i, rst_i)
54 2 kingmu
  begin
55
    if rst_i = '1' then
56
 
57
      index <= STRING_LENGTH-1;
58
      state <= reset;
59
      str_buffer <= (others => '0');
60
      nd_o_buff <= '0';
61
 
62
    elsif rising_edge(nd_i) then
63
      -- index is initalized at STRING_LENGTH-1
64
      -- the protocol initializes with two bits
65
      -- which are trashed, hence we wait until the first
66
      -- trashed bits have been passed
67
      -- 
68
      -- processing stops when the WORD_LENGTH bits have arrived (nd_o_buff = '1')
69
      if STRING_LENGTH - index >= 3 and nd_o_buff = '0' then
70 3 kingmu
        -- Adding a single/double zero/one?
71 2 kingmu
        if index - index_n = 2 then -- update 2
72 3 kingmu
          str_buffer(index downto index-1) <= insert; -- insert double
73 2 kingmu
        else -- update 1
74 3 kingmu
          str_buffer(index) <= insert(1); -- insert single
75 2 kingmu
        end if;
76
      end if;
77
 
78
      -- finished?
79
      if index = 0 then
80
        nd_o_buff <= '1';
81
        state <= reset;
82
      else
83
        index <= index_n;
84
        state <= next_state;
85
      end if;
86
    end if;
87
  end process;
88
 
89
  output_decode: process(state, index, nd_i)
90
  begin
91
    case state is
92
 
93
      when one_1 =>
94 3 kingmu
        insert <= "10";
95 2 kingmu
        if (index > -1) then
96 3 kingmu
          index_n <= index - 1;
97
        else
98 2 kingmu
          index_n <= 0; -- error
99 3 kingmu
        end if;
100 2 kingmu
 
101
      when one_0 =>
102
        insert <= "00";
103
        if (index > -1) then
104
          index_n <= index - 1;
105
        else
106 3 kingmu
          index_n <= 0; -- error
107 2 kingmu
        end if;
108
 
109
      when two_1 =>
110
        insert <= "11";
111 3 kingmu
 
112 2 kingmu
        if (index > 0) then
113
          index_n <= index - 2;
114
        else
115 3 kingmu
          index_n <= 0; -- error
116 2 kingmu
        end if;
117
 
118
      when two_0 =>
119
        insert <= "00";
120 3 kingmu
 
121 2 kingmu
        if (index > 0) then
122
          index_n <= index - 2;
123
        else
124
          index_n <= 0; -- error
125
        end if;
126
 
127
      when others =>
128
        insert <= "00";
129
        index_n <= index;
130
 
131
    end case;
132 3 kingmu
  end process;
133
 
134
  -- For encoded_i:
135
  --
136
  -- 0000 = null
137
  -- 0001 = single one
138
  -- 0010 = double one
139
  -- 0100 = single zero
140
  -- 1000 = double zero  
141 2 kingmu
 
142
  next_state_decode: process(state, encoded_i)
143
  begin
144
    next_state <= state;
145
    case(state) is
146
      when reset =>
147
 
148
        next_state <= pause;
149
 
150
      when pause =>
151
 
152 3 kingmu
        next_state <= one_1; -- only if we came from reset. The long
153
        -- initialization string of ones --------- is considered a 
154
        -- single one.
155
 
156 2 kingmu
      when one_0 =>
157
 
158
        case(encoded_i) is
159
          when "0100" => next_state <= one_0; -- remain here until change
160 3 kingmu
          when "0001" => next_state <= one_1; -- because of the protocol, a 
161
          -- single 0 can only be followed by a single one.        
162 2 kingmu
          when others => next_state <= reset; -- only on error
163
        end case;
164
 
165
      when one_1 =>
166
 
167
        case(encoded_i) is
168
          when "0001" => next_state <= one_1; -- remain here until change                                              
169
          when "0100" => next_state <= one_0;
170
          when "1000" => next_state <= two_0;
171
          when others => next_state <= reset; -- only on error
172
        end case;
173
 
174
      when two_0 =>
175
 
176
        case(encoded_i) is
177
          when "1000" => next_state <= two_0; -- remain here until change
178
          when "0001" => next_state <= one_1;
179
          when "0010" => next_state <= two_1;
180
          when others => next_state <= reset; -- only on error
181
        end case;
182
 
183
      when two_1 =>
184
 
185
        case(encoded_i) is
186
          when "0010" => next_state <= two_1; -- remain here until change
187
          when "0100" => next_state <= one_0;
188
          when "1000" => next_state <= two_0;
189
          when others => next_state <= reset; -- only on error
190
        end case;
191
 
192
      when others =>
193
        next_state <= reset;  -- only on error
194
 
195
    end case;
196
  end process;
197
 
198
  -- decoded!
199 3 kingmu
  rearrange : process(clk_i, rst_i)
200 2 kingmu
  begin
201
    if rst_i = '1' then
202
      decoded_o <= (others => '0');
203
      nd_o <= '0';
204
    elsif rising_edge(clk_i) then
205
      if nd_o_buff = '1' then
206
        for i in 0 to WORD_LENGTH-1 loop
207
          -- the bits are ror when transmitted, thus the left-most
208
          -- bit in decoded_buffer (excluding the xmitter protocol bits)
209
          -- describe the right-most bit in the original data word. 
210
          -- The following line of code turns 01 to 1 and 10 to 0 and it converts
211
          -- the big endian decoded_buffer to little endian decoded_o.        
212
          if str_buffer(str_buffer'left-2*i downto str_buffer'left-1-2*i) = "01" then
213
            decoded_o(i) <= '1';
214
          else
215
            decoded_o(i) <= '0';
216
          end if;
217
        end loop;
218
 
219
        nd_o <= '1';
220
      end if;
221
    end if;
222
  end process;
223
 
224 3 kingmu
end;
225 2 kingmu
 

powered by: WebSVN 2.1.0

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