BWS_2011_TFT.vhd


1
----------------------------------------------------------------------------------
2
-- Engineer: Ralph_H Stand 17.02.2011
3
-- Module Name: BWS_2011_TFT 
4
----------------------------------------------------------------------------------
5
library IEEE;
6
use IEEE.STD_LOGIC_1164.ALL;
7
use IEEE.NUMERIC_STD.ALL ; --nötig für die Zähler !
8
9
entity BWS_2011_TFT is
10
   Port ( 
11
      ADR  : in  STD_LOGIC_VECTOR (15 downto 0);
12
      DB    : inout  STD_LOGIC_VECTOR (7 downto 0)  ;
13
      MREQ  : in  STD_LOGIC;
14
      WR    : in  STD_LOGIC;
15
      RD    : in  STD_LOGIC;
16
      Reset : in  STD_LOGIC;
17
      IORQ  : in  STD_LOGIC;
18
      MEMDI : in  STD_LOGIC;    -- L wenn Speicher daktiviert 
19
      MEMDI_Mod1: in  STD_LOGIC;  -- L wenn Modul1 deaktiviert (damit AC1 Speicher)
20
                         --   dieses Signal ist auch das "CPM ein" Signal vom AC1 2010
21
      RAMADR   : out    STD_LOGIC_VECTOR (10 downto 0);-- Adresse BWSRAM
22
      RAMDB     : inout  STD_LOGIC_VECTOR (7 downto 0) ;-- bidirektional
23
      RAMWR     : out STD_LOGIC;                -- WR Signal für RAM
24
         ZGADR     : out STD_LOGIC_VECTOR (2 downto 0);    -- Adresse A0..A2 ZG-Eprom
25
      CSD35_36  : out STD_LOGIC;  -- Clock Signal zum Laden Latch 74LS374 L/H Flanke
26
         ZG_Out    : in  STD_LOGIC_VECTOR (5 downto 0);    -- Ausgänge ZG-Eprom
27
      ZGADR11   : out STD_LOGIC;  --Umschaltung ZG ACC<-->SCCH Modus
28
         Video_out : out STD_LOGIC; -- VideoSignal        negiert (wegen Treiber)
29
      HK_Sync    : out STD_LOGIC; -- HK SynchronImpuls  negiert (wegen Treiber)
30
      VK_Sync    : out STD_LOGIC; -- VK SynchronImpuls  negiert (wegen Treiber)
31
      Takt_in    : in  STD_LOGIC  -- 20 Mhz Eingangstakt
32
      );
33
34
end BWS_2011_TFT;
35
36
architecture VERHALTEN of BWS_2011_TFT is
37
  signal   VDCLK       : STD_LOGIC :=  '0'                         ;-- VDCLK = Punkttakt 16Mhz
38
  signal  QD19      : UNSIGNED (2 downto 0) := (others => '0')  ; -- Ausgang D19 6:1 Taktteiler
39
  signal  TaktD41    : STD_LOGIC :=  '0'                      ; -- Takt für D41
40
  signal  QD41_42    : UNSIGNED (6 downto 0)  := (others => '0'); -- Ausgang D41 und 42 Zeichenzähler
41
  signal   Takt_Zeile  : STD_LOGIC :=  '0'                      ; -- Takt für 2.Zeile wegen TFT
42
  signal  QD_TFT    : UNSIGNED (1 downto 0)  := (others => '0'); -- 2:1 Teiler wegen TFT Modus
43
  signal   TaktD43     : STD_LOGIC :=  '0'                      ; -- Takt für Zeilen pro ZeichenZähler D43
44
  signal  QD43_44_20  : UNSIGNED (8 downto 0)  := (others => '0'); -- Ausgang D43,D44,D20 Zähler
45
  signal  CPU_Zugriff : STD_LOGIC := '0' ; --Signal 1 für Zugriff der CPU auf BWS (nur Adresse ausgewählt)
46
  signal  BWS_Zugriff : STD_LOGIC := '0' ; --Signal 1 für Zugriff auf BWS, Umschaltung Adressen & DB Umschaltung
47
  signal  BWS_RW      : STD_LOGIC := '0' ; --Signal 1 wenn WR oder (RD & !! RW Modus)
48
  signal  BWS_aus    : STD_LOGIC := '1' ; --Signal 0 wenn BWS ausgeschaltet
49
  signal  D35_36    : STD_LOGIC_VECTOR(7 downto 0) := (others => '0') ; -- Latch Adresse für ZG
50
  signal   SR_ZG_Out   : STD_LOGIC_VECTOR (5 downto 0) := (others => '0') ; -- Ausgänge Schieberegister ZG
51
  signal  DG13      : STD_LOGIC :=  '0'  ; -- Dunkeltastung = 1 bei Strahlrücklauf
52
  signal  DTVDU       : STD_LOGIC := '0'  ; -- Dunkeltastung BWS Zugriff und
53
  signal   BWS_INV    : STD_LOGIC := '0'  ; -- BWS INVERS Umschaltung
54
  signal  Zei_INV    : STD_LOGIC := '0'  ; -- Zeichen INVERS Umschaltung
55
   signal   IO5_Latch   : STD_LOGIC := '0'  ; -- PIO Port B ZG Umschaltung
56
   signal   IO11_Latch  : STD_LOGIC := '0'  ; -- LatchIO11 Bit1=H Bildschirm INVERS
57
58
-- ***********************************************************************************
59
begin
60
-- ab hier nun der CPLD Programmcode 
61
62
-- IO5 Latch fängt Ausgaben an PIO Port B ab (ZG Umschaltung)
63
  IO5_Latch  <= DB(3) when 
64
            (ADR(7 downto 0) = x"05" and IORQ = '0' and WR = '0') 
65
                        else IO5_Latch ;
66
   ZGADR11    <=  IO5_Latch  ; -- ZG-Umschaltung
67
68
-- IO11H Register..  nur DB Bit 1 = Invers Umschaltung H=INVERS L=Standart
69
  IO11_Latch  <= '0' when Reset = '0'
70
                else DB(1) when (ADR(7 downto 0) = x"11" and IORQ = '0' and WR = '0') 
71
                  else IO11_Latch ;
72
73
-- Takteingang auf intern VDCLK legen.. 
74
  VDCLK    <= Takt_In    ;   --  20Mhz Eingangstakt = VDCLK
75
76
-- Takterzeugung  mit D19 (Basis ist VDCLK)
77
D19:
78
  process(VDCLK)      -- Basis ist VDCLK Takt der durch 6 geteilt wird
79
  begin
80
  if rising_edge(VDCLK) then QD19 <= QD19 + 1 ; end if ;--zählen..
81
  if QD19 = 6        then QD19 <= "000"     ; end if ;--max. bis 6
82
  end process D19;
83
  TaktD41 <=  '1'  when QD19 = 0   Else '0' ; --Zählerstand 0 decodieren OK=0
84
  -- Hinweis, das beste Bild liefert weiterschalten bei Zählerstand 0, 
85
  -- Latch D35_36 laden und SR Rausschieben (falling_edge) bei Zählerstand 5
86
  -- Takttiming: Zählerstand 0 weiterschalten Zeichenzähler
87
  --             Zählerstand 5 laden DB, Latches und Schieberegister laden
88
  
89
-- Latch D35_36 welches Zeichen für ZG speichert laden 
90
  D35_36  <= RAMDB when QD19 = 5 Else D35_36 ;   -- 5 LD Impuls(H-aktiv)
91
  -- der Zeitpunkt des Ladens bestimmt offensichtlich wie breit der INVERS Balken ist ???
92
   CSD35_36  <=  '1' when QD19 = 5 else '0' ; -- Clock Signal für Latch 74LS374 L/H speichert
93
  
94
-- ZG Daten ins Schieberegister SR_ZG_Out holen
95
ZG_Out_ausschieben: --ZG Daten aus D38&39=SR_ZG_Out(0) rausschieben
96
process(VDCLK)  -- Zeichentakt
97
  begin
98
  if falling_edge(VDCLK) then
99
      if QD19 = 5 then  SR_ZG_Out(5 downto 0) <= ZG_Out(5 downto 0) ; -- parallel laden      
100
              else SR_ZG_Out <= '0' & SR_ZG_Out(5 downto 1) ;     -- serial schieben
101
    end if;
102
   end if;
103
end process ZG_Out_ausschieben; -- fertig Videodaten ausschieben
104
105
-- *** ab hier Zählerkette ********************************************************
106
-- ZeichenZähler pro Zeile  (64 Zeichen) mit D41 & D42
107
D41_42: 
108
  process(TaktD41) -- Basis ist Zählerstand 0 von Zähler D19
109
  begin
110
  if rising_edge(TaktD41) then QD41_42 <= QD41_42 + 1 ; end if ;--zählen..
111
    if QD41_42 = 84 then QD41_42 <= "0000000"   ; end if ;--bis 84 64 Zeichen/Zeile
112
end process D41_42;
113
114
  Takt_Zeile <=  '1'  when QD41_42 = 84 Else '0' ;  -- Zählerstand 84 als Takt
115
                
116
-- der 2:1 Teiler D_TFT der hier eingeschoben wird, bewirkt ein 2.Mal Schreiben der Zeile
117
-- und gleichzeitig die Halbierung des VK-Taktes, was durch den höheren Bildtakt nötig ist
118
D_TFT: 
119
  process(Takt_Zeile) -- Basis ist Zählerstand 84 oder 104 von Zähler QD41_42
120
  begin
121
  if rising_edge(Takt_Zeile) then QD_TFT <= QD_TFT + 1 ; end if ;--zählen..
122
      if QD_TFT = 2       then QD_TFT <= "00"       ; end if ;--max. bis 2
123
end process D_TFT;
124
  TaktD43   <= QD_TFT(0)  ; -- Takt für Zeilenzähler
125
 
126
-- ZeilenZähler D43 & D44 & D20 zählt Zeilen 0 bis 320
127
D43_44_20:
128
  process(TaktD43) -- Basis ist QD_TFT(0) 84Zeichen * 2
129
  begin
130
  if rising_edge(TaktD43) then QD43_44_20 <= QD43_44_20 + 1 ; end if ; --zählen..
131
  if QD43_44_20 = 320     then QD43_44_20 <= "000000000"    ; end if ; --max. bis 320
132
end process D43_44_20;
133
-- *** BWS Zählerkette --Ende----------------------------------------------
134
-- hier wird Adressdekodierung & Zugriff für BWS gemacht 1000H..17FFH
135
   CPU_Zugriff <= '1' when ADR(15 downto 12) =x"1" -- Adresse 1xxxH 
136
                and ADR(11)='0'         -- Adresse 1000H..17FFH
137
                and MREQ='0'               -- Speicherzugriff
138
                and BWS_aus = '0'            -- wenn BWS aktiv sein darf
139
                else '0' ;                   -- BWS auslesen
140
141
-- Signal BWS_aus bilden, immer wenn der BWS mittels MEMDI deaktiviert wird
142
  BWS_aus  <=  '1'  when  MEMDI_Mod1 = '0'     -- Modul 3 Zugriff
143
                or 
144
                  MEMDI ='1'        -- CPM Zugriff
145
                else '0' ; 
146
147
-- hier wirklicher Zugriff auf BWS, vorerst ohne WAIT
148
  BWS_Zugriff <= '1' when CPU_Zugriff='1'  else '0' ;
149
150
-- WR Signal für den BWS-RAM (zusätzlich ist noch ein Widerstand gegen +5V)
151
  RAMWR     <= '0' when BWS_Zugriff = '1' and WR = '0' else '1' ; --WR Signal RAM
152
153
-- ** Adressmultiplexer ** ------------------------------------------------
154
-- .. wenn BWS_Zugriff=1 dann Adressen von ADR.. sonst Zähleradressen
155
  RAMADR(5 downto 0)  <= not ADR(5  downto 0) when BWS_Zugriff = '1'  
156
                    else STD_LOGIC_VECTOR(QD41_42(5 downto 0))  ;-- A5..A0
157
158
  RAMADR(10 downto 6) <= not ADR(10 downto 6) when BWS_Zugriff = '1' -- AC1 BWS Zugriff 
159
                    else STD_LOGIC_VECTOR(QD43_44_20(7 downto 3));
160
-- ** Adressmultiplexer ** OK** ------------------------------------------------
161
162
-- ** BWS RAM Datenbussteuerung **  ** ------------------------------------------------
163
  RAMDB <= DB when  BWS_Zugriff = '1' and WR = '0' ELSE "ZZZZZZZZ" ; -- RAMDB TriState wenn kein WR
164
  -- das Einlesen der RAM-Daten auf RAMDB erfolgt immer nur zum Zeitpunkt des Laden des Latches
165
   DB    <= RAMDB when BWS_Zugriff = '1' and RD = '0' ELSE "ZZZZZZZZ" ; -- DB TriState wenn kein BWS Read  
166
  
167
-- ZG Adresse erzeugen
168
  ZGADR(2 downto 0)     <= STD_LOGIC_VECTOR(QD43_44_20(2 downto 0)) ; -- Bits 0..2 D43
169
170
-- INVERS Modus 10H/11H 
171
  Zei_INV   <= '1'  when  D35_36 = x"11"             -- InversModus ein
172
                else '0' when D35_36 = x"10"     -- InversModus aus 
173
                      or   QD41_42 = 65  ;  -- InversModus aus Zeilenende
174
-- INVERS-Auswertung  
175
  BWS_Inv     <= IO11_Latch when Zei_INV ='0'        -- Umschaltung INVERS
176
                      else not IO11_Latch ; -- Umschaltung Invertieren  
177
178
-- Hinweis.. durch die Treiber nach dem CPLD muss die Invertierung des Signales beachtet werden! 
179
  Video_Out <= '1' when DTVDU = '1'     -- Dunkeltastung
180
              or BWS_Zugriff  ='1' -- BWS Zugriff dunkeltasten
181
              else SR_ZG_out(0) when BWS_INV = '1'   -- INVERS oder NICHT INVERS
182
                           else not SR_ZG_out(0) ; -- Ausgang Schieberegister ;
183
184
-- Signal DTVDU bilden.. das ist das Dunkeltastsignal für die Ränder und Austastlücken
185
  DTVDU  <= '1'   when   DG13 = '1'       --  Ausgang FlipFlop DG13
186
              or  QD43_44_20(8)='1'  --  invertierter D20 
187
              else '0' ;      
188
189
-- Signal DG13 bilden, es stellt die Zeit des Strahlrücklaufes dar und wird bei
190
-- ZeichenZählerstand(D41_42) 2 rückgesetzt und bei 66 gesetzt
191
  DG13  <= '1'  when QD41_42 = 66        -- Setzen bei Zählerstand 66
192
            else '0' when QD41_42 = 2; -- rücksetzen bei Zählerstand 2 
193
194
-- ******** Erzeugung HK Synchronimpuls aus Zählerkette
195
196
-- HK Impuls startet bei Zählerstand 69 von QD41_42 und sollte 4,7us=4700ns lang sein
197
  HK_Sync    <=    '1'  when  QD41_42 = 69 -- 69 im Normalmodus Start bei 69 
198
                    else '0' 
199
                  when  QD41_42 = 82 -- 83 im Normalmodus Ende bei 82 (nicht84!")
200
                    ;
201
-- dieses FlipFlop funktioniert nicht richtig bei CPLD POWER MODE "STD"
202
203
-- 69 bis 84 wenn Bild steht dann ist es synchron (69..83 wäre richtig) aber Zeilenanfang Schatten
204
-- 69 bis 82 liefert perfektes Bild !!
205
206
-- ***Ende HK_Sync Impuls ****************************************************************
207
208
-- ******** Erzeugung VK Synchronimpuls aus Zählerkette
209
-- VK Impuls startet bei Zählerstand 290 von QD43_44_20  und sollte 2,5x64uS=160us(=160.000ns)
210
211
  VK_Sync      <=    '1'  when  QD43_44_20 = 290           -- setzen bei 290
212
                    else '0' 
213
                      when QD43_44_20 = 293 ;
214
-- dieses FlipFlop funktioniert nicht richtig bei CPLD POWER MODE "STD"
215
                      
216
-- ***Ende VK_Sync Impuls ****************************************************************
217
        
218
end VERHALTEN;