OSDN Git Service

[VM][General][WIP] Start to merge upstream 2018-10-14.Open branch upstream_20181014 .
[csp-qt/common_source_project-fm7.git] / source / src / vm / ex80 / display.cpp
1 /*
2         TOSHIBA EX-80 Emulator 'eEX-80'
3
4         Author : Takeda.Toshiya
5         Date   : 2015.12.10-
6
7         [ display ]
8 */
9
10 #include "display.h"
11 #include "../f9368.h"
12
13 namespace EX80 {
14 #define EVENT_HBLANK 0
15
16 /*
17 @ABCDEFGHIJKLMNO
18 PQRSTUVWXYZ[\]^_
19  !"#$%&'()*+,-./
20 0123456789:;<=>?
21 ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏ
22 ÐÑÒÓÔÕÖ×ØÙÚÛÜÝÞß
23  ¡¢£¤¥¦§¨©ª«¬­®¯
24 °±²³´µ¶·¸¹º»¼½¾¿
25 */
26
27 uint8_t font_pattern[8 * 128] = {
28         0x0e, 0x11, 0x1d, 0x15, 0x1d, 0x01, 0x0e, 0x00,
29         0x04, 0x0a, 0x0a, 0x11, 0x1f, 0x11, 0x11, 0x00,
30         0x0f, 0x11, 0x11, 0x0f, 0x11, 0x11, 0x0f, 0x00,
31         0x0e, 0x11, 0x01, 0x01, 0x01, 0x11, 0x0e, 0x00,
32         0x07, 0x09, 0x11, 0x11, 0x11, 0x09, 0x07, 0x00,
33         0x1f, 0x01, 0x01, 0x1f, 0x01, 0x01, 0x1f, 0x00,
34         0x1f, 0x01, 0x01, 0x1f, 0x01, 0x01, 0x01, 0x00,
35         0x0e, 0x11, 0x01, 0x1d, 0x11, 0x11, 0x0e, 0x00,
36         0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11, 0x00,
37         0x0e, 0x04, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00,
38         0x1c, 0x08, 0x08, 0x08, 0x09, 0x09, 0x06, 0x00,
39         0x11, 0x09, 0x05, 0x03, 0x05, 0x09, 0x11, 0x00,
40         0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x1f, 0x00,
41         0x11, 0x1b, 0x15, 0x15, 0x11, 0x11, 0x11, 0x00,
42         0x11, 0x11, 0x13, 0x15, 0x19, 0x11, 0x11, 0x00,
43         0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00,
44         0x0f, 0x11, 0x11, 0x0f, 0x01, 0x01, 0x01, 0x00,
45         0x0e, 0x11, 0x11, 0x15, 0x19, 0x0e, 0x10, 0x00,
46         0x0f, 0x11, 0x11, 0x0f, 0x05, 0x09, 0x11, 0x00,
47         0x0e, 0x11, 0x01, 0x0e, 0x10, 0x11, 0x0e, 0x00,
48         0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00,
49         0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00,
50         0x11, 0x11, 0x11, 0x0a, 0x0a, 0x0a, 0x04, 0x00,
51         0x11, 0x11, 0x15, 0x15, 0x15, 0x0a, 0x0a, 0x00,
52         0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11, 0x00,
53         0x11, 0x11, 0x0a, 0x0a, 0x04, 0x04, 0x04, 0x00,
54         0x1f, 0x10, 0x08, 0x04, 0x02, 0x01, 0x1f, 0x00,
55         0x0e, 0x02, 0x02, 0x02, 0x02, 0x02, 0x0e, 0x00,
56         0x11, 0x0a, 0x1f, 0x04, 0x1f, 0x04, 0x04, 0x00,
57         0x0e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x0e, 0x00,
58         0x04, 0x0a, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00,
59         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x00,
60         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
61         0x04, 0x0e, 0x0e, 0x04, 0x04, 0x00, 0x04, 0x00,
62         0x12, 0x12, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00,
63         0x0a, 0x0a, 0x1f, 0x0a, 0x1f, 0x0a, 0x0a, 0x00,
64         0x04, 0x1e, 0x05, 0x0e, 0x14, 0x0f, 0x04, 0x00,
65         0x13, 0x0b, 0x08, 0x04, 0x02, 0x1a, 0x19, 0x00,
66         0x0c, 0x12, 0x0a, 0x04, 0x0a, 0x11, 0x16, 0x00,
67         0x04, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00,
68         0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08, 0x00,
69         0x02, 0x04, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00,
70         0x04, 0x15, 0x0e, 0x04, 0x0e, 0x15, 0x04, 0x00,
71         0x04, 0x04, 0x04, 0x1f, 0x04, 0x04, 0x04, 0x00,
72         0x00, 0x00, 0x00, 0x00, 0x04, 0x04, 0x02, 0x00,
73         0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00,
74         0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x04, 0x00,
75         0x10, 0x08, 0x08, 0x04, 0x02, 0x02, 0x01, 0x00,
76         0x0e, 0x11, 0x19, 0x15, 0x13, 0x11, 0x0e, 0x00,
77         0x04, 0x06, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00,
78         0x0e, 0x11, 0x10, 0x08, 0x04, 0x02, 0x1f, 0x00,
79         0x0e, 0x11, 0x10, 0x0e, 0x10, 0x11, 0x0e, 0x00,
80         0x08, 0x0c, 0x0a, 0x09, 0x1f, 0x08, 0x08, 0x00,
81         0x1f, 0x01, 0x01, 0x0f, 0x10, 0x11, 0x0e, 0x00,
82         0x0c, 0x02, 0x01, 0x0f, 0x11, 0x11, 0x0e, 0x00,
83         0x1f, 0x11, 0x11, 0x08, 0x08, 0x04, 0x04, 0x00,
84         0x0e, 0x11, 0x11, 0x0e, 0x11, 0x11, 0x0e, 0x00,
85         0x0e, 0x11, 0x11, 0x1e, 0x10, 0x11, 0x0e, 0x00,
86         0x00, 0x04, 0x04, 0x00, 0x04, 0x04, 0x00, 0x00,
87         0x00, 0x04, 0x04, 0x00, 0x04, 0x04, 0x02, 0x00,
88         0x10, 0x08, 0x04, 0x02, 0x04, 0x08, 0x10, 0x00,
89         0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00,
90         0x01, 0x02, 0x04, 0x08, 0x04, 0x02, 0x01, 0x00,
91         0x0e, 0x11, 0x10, 0x08, 0x04, 0x00, 0x04, 0x00,
92         0x1e, 0x12, 0x11, 0x14, 0x08, 0x04, 0x02, 0x00,
93         0x18, 0x0f, 0x08, 0x1f, 0x08, 0x04, 0x02, 0x00,
94         0x15, 0x15, 0x1a, 0x10, 0x08, 0x04, 0x02, 0x00,
95         0x0e, 0x00, 0x1f, 0x08, 0x08, 0x04, 0x02, 0x00,
96         0x02, 0x02, 0x06, 0x0a, 0x12, 0x02, 0x02, 0x00,
97         0x08, 0x08, 0x1f, 0x08, 0x08, 0x04, 0x02, 0x00,
98         0x00, 0x0e, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00,
99         0x00, 0x1f, 0x10, 0x0a, 0x04, 0x0a, 0x11, 0x00,
100         0x04, 0x1f, 0x08, 0x04, 0x0e, 0x15, 0x04, 0x00,
101         0x08, 0x08, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00,
102         0x04, 0x08, 0x0a, 0x12, 0x11, 0x11, 0x11, 0x00,
103         0x01, 0x11, 0x0f, 0x01, 0x01, 0x01, 0x1e, 0x00,
104         0x00, 0x1f, 0x10, 0x10, 0x08, 0x04, 0x02, 0x00,
105         0x00, 0x06, 0x05, 0x09, 0x10, 0x10, 0x00, 0x00,
106         0x04, 0x1f, 0x04, 0x15, 0x15, 0x15, 0x06, 0x00,
107         0x00, 0x1f, 0x10, 0x10, 0x0a, 0x04, 0x08, 0x00,
108         0x07, 0x18, 0x03, 0x1c, 0x00, 0x07, 0x18, 0x00,
109         0x04, 0x02, 0x02, 0x02, 0x09, 0x1f, 0x10, 0x00,
110         0x08, 0x08, 0x0b, 0x0c, 0x18, 0x04, 0x03, 0x00,
111         0x00, 0x1f, 0x02, 0x1f, 0x02, 0x02, 0x1c, 0x00,
112         0x02, 0x1f, 0x12, 0x12, 0x02, 0x04, 0x04, 0x00,
113         0x00, 0x0e, 0x08, 0x08, 0x08, 0x08, 0x1f, 0x00,
114         0x00, 0x1f, 0x10, 0x1e, 0x10, 0x10, 0x1f, 0x00,
115         0x0e, 0x00, 0x1f, 0x10, 0x10, 0x08, 0x04, 0x00,
116         0x09, 0x09, 0x09, 0x08, 0x08, 0x04, 0x02, 0x00,
117         0x04, 0x04, 0x05, 0x05, 0x05, 0x15, 0x0d, 0x00,
118         0x01, 0x01, 0x01, 0x11, 0x09, 0x05, 0x03, 0x00,
119         0x00, 0x1f, 0x11, 0x11, 0x11, 0x11, 0x1f, 0x00,
120         0x00, 0x1f, 0x11, 0x11, 0x10, 0x08, 0x04, 0x00,
121         0x00, 0x01, 0x12, 0x14, 0x10, 0x08, 0x07, 0x00,
122         0x05, 0x0a, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00,
123         0x02, 0x05, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00,
124         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
125         0x00, 0x00, 0x00, 0x00, 0x04, 0x0a, 0x04, 0x00,
126         0x0e, 0x02, 0x02, 0x02, 0x00, 0x00, 0x00, 0x00,
127         0x00, 0x00, 0x00, 0x08, 0x08, 0x08, 0x0f, 0x00,
128         0x00, 0x00, 0x00, 0x00, 0x02, 0x04, 0x08, 0x00,
129         0x00, 0x00, 0x00, 0x04, 0x04, 0x00, 0x00, 0x00,
130         0x00, 0x1f, 0x10, 0x1f, 0x10, 0x08, 0x04, 0x00,
131         0x00, 0x00, 0x1f, 0x10, 0x1c, 0x04, 0x02, 0x00,
132         0x00, 0x00, 0x08, 0x04, 0x07, 0x04, 0x04, 0x00,
133         0x00, 0x00, 0x04, 0x1f, 0x11, 0x08, 0x04, 0x00,
134         0x00, 0x00, 0x00, 0x0e, 0x04, 0x04, 0x1f, 0x00,
135         0x00, 0x00, 0x08, 0x1f, 0x0c, 0x0a, 0x0d, 0x00,
136         0x00, 0x00, 0x02, 0x1f, 0x12, 0x02, 0x04, 0x00,
137         0x00, 0x00, 0x00, 0x0e, 0x08, 0x08, 0x1f, 0x00,
138         0x00, 0x00, 0x0f, 0x08, 0x0f, 0x08, 0x0f, 0x00,
139         0x00, 0x00, 0x15, 0x15, 0x10, 0x08, 0x04, 0x00,
140         0x00, 0x00, 0x00, 0x01, 0x1e, 0x00, 0x00, 0x00,
141         0x1f, 0x10, 0x14, 0x0c, 0x04, 0x04, 0x02, 0x00,
142         0x10, 0x08, 0x04, 0x06, 0x05, 0x04, 0x04, 0x00,
143         0x04, 0x1f, 0x11, 0x11, 0x10, 0x08, 0x04, 0x00,
144         0x00, 0x1f, 0x04, 0x04, 0x04, 0x04, 0x1f, 0x00,
145         0x08, 0x08, 0x1f, 0x0c, 0x0a, 0x09, 0x0c, 0x00,
146         0x04, 0x04, 0x1f, 0x14, 0x12, 0x11, 0x0c, 0x00,
147         0x04, 0x04, 0x1f, 0x04, 0x1f, 0x04, 0x04, 0x00,
148         0x1e, 0x12, 0x11, 0x10, 0x08, 0x04, 0x02, 0x00,
149         0x02, 0x02, 0x1e, 0x09, 0x08, 0x08, 0x04, 0x00,
150         0x00, 0x1f, 0x10, 0x10, 0x10, 0x10, 0x1f, 0x00,
151         0x0a, 0x1f, 0x0a, 0x08, 0x08, 0x04, 0x02, 0x00,
152         0x01, 0x06, 0x11, 0x16, 0x10, 0x08, 0x07, 0x00,
153         0x00, 0x1f, 0x10, 0x08, 0x04, 0x0a, 0x11, 0x00,
154         0x02, 0x1f, 0x12, 0x0a, 0x02, 0x02, 0x1c, 0x00,
155         0x11, 0x11, 0x12, 0x10, 0x08, 0x04, 0x02, 0x00,
156 };
157
158 static const int led_pattern[LED_HEIGHT][LED_WIDTH] = {
159         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
160         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
161         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
162         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
163         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
164         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
165         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
166         {0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,2,0,0,0},
167         {0,0,0,0,6,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,2,2,0,0,0},
168         {0,0,0,0,6,6,0,1,1,1,1,1,1,1,1,1,1,1,1,0,2,2,2,0,0,0},
169         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
170         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
171         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
172         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
173         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
174         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
175         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
176         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
177         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
178         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
179         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
180         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
181         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
182         {0,0,0,0,6,6,6,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0},
183         {0,0,0,0,0,6,0,7,7,7,7,7,7,7,7,7,7,7,7,7,0,2,0,0,0,0},
184         {0,0,0,0,0,0,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,0,0,0,0,0},
185         {0,0,0,0,5,0,7,7,7,7,7,7,7,7,7,7,7,7,7,0,3,0,0,0,0,0},
186         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
187         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
188         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
189         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
190         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
191         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
192         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
193         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
194         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
195         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
196         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
197         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
198         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
199         {0,0,0,5,5,5,0,0,0,0,0,0,0,0,0,0,0,0,0,3,3,3,0,0,0,0},
200         {0,0,0,5,5,0,4,4,4,4,4,4,4,4,4,4,4,4,0,3,3,3,0,0,0,0},
201         {0,0,0,5,0,4,4,4,4,4,4,4,4,4,4,4,4,4,4,0,3,3,0,0,0,0},
202         {0,0,0,0,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,0,3,0,0,0,0},
203         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
204         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
205         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
206         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
207         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
208         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
209         {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
210 };
211
212 void DISPLAY::initialize()
213 {
214         // load rom image
215         FILEIO* fio = new FILEIO();
216         if(fio->Fopen(create_local_path(_T("FONT.ROM")), FILEIO_READ_BINARY)) {
217                 fio->Fread(font, sizeof(font), 1);
218                 fio->Fclose();
219         } else {
220                 memcpy(font, font_pattern, sizeof(font));
221         }
222         delete fio;
223         
224         memset(screen, 0, sizeof(screen));
225         odd_even = 0;
226         dma = true;
227         
228         register_frame_event(this);
229         register_vline_event(this);
230 }
231
232 void DISPLAY::write_signal(int id, uint32_t data, uint32_t mask)
233 {
234         if(id == SIG_DISPLAY_DMA) {
235                 dma = ((data & mask) != 0);
236         }
237 }
238
239 void DISPLAY::event_frame()
240 {
241         odd_even = (odd_even + 1) & 1;
242 }
243
244 void DISPLAY::event_vline(int v, int clock)
245 {
246         if((v & 1) == odd_even && v < 8 * 29 * 2) {
247                 uint8_t* dest = screen[v];
248                 if(dma) {
249 /*
250                         SW2     ON = CHAR / OFF = BIT
251                         SW3-1/2 ON ,ON  = 8000H-81FFH
252                                 OFF,ON  = 8200H-83FFH
253                                 ON ,OFF = 8400H-85FFH
254                                 OFF,OFF = 8600H-87FFH
255 */
256                         int line = v >> 4;
257                         int raster = (v >> 1) & 7;
258                         uint8_t* base = ram + (~(config.dipswitch >> 2) & 3) * 0x200 + (line + 1) * 16;
259                         
260                         for(int x = 0; x < 12; x++) {
261                                 uint8_t pat = base[x];
262                                 if(config.dipswitch & 2) {
263                                         pat = (font[(pat & 0x7f) * 8 + raster] & 0x1f) << 2;
264                                 }
265                                 dest[0] = (pat & 0x01) >> 0;
266                                 dest[1] = (pat & 0x02) >> 1;
267                                 dest[2] = (pat & 0x04) >> 2;
268                                 dest[3] = (pat & 0x08) >> 3;
269                                 dest[4] = (pat & 0x10) >> 4;
270                                 dest[5] = (pat & 0x20) >> 5;
271                                 dest[6] = (pat & 0x40) >> 6;
272                                 dest[7] = (pat & 0x80) >> 7;
273                                 dest += 8;
274                         }
275                         d_cpu->write_signal(SIG_CPU_BUSREQ, 1, 1);
276                         // wait 8clk/byte
277                         register_event_by_clock(this, EVENT_HBLANK, 8 * 12, false, NULL);
278                 } else {
279                         memset(dest, 0, 8 * 12);
280                 }
281         }
282 }
283
284 void DISPLAY::event_callback(int event_id, int err)
285 {
286         if(event_id == EVENT_HBLANK) {
287                 d_cpu->write_signal(SIG_CPU_BUSREQ, 0, 0);
288         }
289 }
290
291 void DISPLAY::draw_screen()
292 {
293         // draw screen
294         scrntype_t color_crt[2] = {RGB_COLOR(255, 255, 255), 0};
295         for(int y = 0; y < 8 * 29 * 2; y++) {
296                 scrntype_t* dest = emu->get_screen_buffer(y + vm_ranges[8].y) + vm_ranges[8].x;
297                 uint8_t* src = screen[y];
298                 for(int x = 0; x < 8 * 12; x++) {
299                         dest[0] = dest[1] = dest[2] = dest[3] = dest[4] = dest[5] = color_crt[src[x] & 1];
300                         dest += 6;
301                 }
302         }
303         
304         // draw 7-seg LEDs
305         scrntype_t color_on = RGB_COLOR(255, 8, 72);
306         scrntype_t color_off = RGB_COLOR(56, 0, 0);
307         scrntype_t color_led[9];
308         uint8_t* base = ram + (~(config.dipswitch >> 2) & 3) * 0x200;
309         color_led[0] = RGB_COLOR(38, 8, 0);
310         
311         for(int i = 0; i < 8; i++) {
312                 uint8_t val = (base[i >> 1] >> ((i & 1) ? 0 : 4)) & 0x0f;
313                 
314                 for(int b = 0; b < 8; b++) {
315                         color_led[b + 1] = (dma && f9368[val][b]) ? color_on : color_off;
316                 }
317                 for(int y = 0; y < LED_HEIGHT; y++) {
318                         scrntype_t* dest = emu->get_screen_buffer(vm_ranges[i].y + y) + vm_ranges[i].x;
319                         for(int x = 0; x < LED_WIDTH; x++) {
320                                 dest[x] = color_led[led_pattern[y][x]];
321                         }
322                 }
323         }
324 }
325
326 #define STATE_VERSION   1
327
328 bool DISPLAY::process_state(FILEIO* state_fio, bool loading)
329 {
330         if(!state_fio->StateCheckUint32(STATE_VERSION)) {
331                 return false;
332         }
333         if(!state_fio->StateCheckInt32(this_device_id)) {
334                 return false;
335         }
336         state_fio->StateValue(odd_even);
337         state_fio->StateValue(dma);
338         return true;
339 }
340 }