2 * QEMU Cirrus CLGD 54xx VGA Emulator.
4 * Copyright (c) 2004 Fabrice Bellard
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to deal
8 * in the Software without restriction, including without limitation the rights
9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 * copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
26 #define PUTPIXEL() ROP_OP(&d[0], col)
28 #define PUTPIXEL() ROP_OP_16((uint16_t *)&d[0], col)
30 #define PUTPIXEL() ROP_OP(&d[0], col); \
31 ROP_OP(&d[1], (col >> 8)); \
32 ROP_OP(&d[2], (col >> 16))
34 #define PUTPIXEL() ROP_OP_32(((uint32_t *)&d[0]), col)
36 #error unsupported DEPTH
40 glue(glue(glue(cirrus_patternfill_
, ROP_NAME
), _
),DEPTH
)
41 (CirrusVGAState
* s
, uint8_t * dst
,
43 int dstpitch
, int srcpitch
,
44 int bltwidth
, int bltheight
)
47 int x
, y
, pattern_y
, pattern_pitch
, pattern_x
;
51 int skipleft
= s
->vga
.gr
[0x2f] & 0x1f;
53 int skipleft
= (s
->vga
.gr
[0x2f] & 0x07) * (DEPTH
/ 8);
63 pattern_y
= s
->cirrus_blt_srcaddr
& 7;
64 for(y
= 0; y
< bltheight
; y
++) {
67 src1
= src
+ pattern_y
* pattern_pitch
;
68 for (x
= skipleft
; x
< bltwidth
; x
+= (DEPTH
/ 8)) {
70 col
= src1
[pattern_x
];
71 pattern_x
= (pattern_x
+ 1) & 7;
73 col
= ((uint16_t *)(src1
+ pattern_x
))[0];
74 pattern_x
= (pattern_x
+ 2) & 15;
77 const uint8_t *src2
= src1
+ pattern_x
* 3;
78 col
= src2
[0] | (src2
[1] << 8) | (src2
[2] << 16);
79 pattern_x
= (pattern_x
+ 1) & 7;
82 col
= ((uint32_t *)(src1
+ pattern_x
))[0];
83 pattern_x
= (pattern_x
+ 4) & 31;
88 pattern_y
= (pattern_y
+ 1) & 7;
93 /* NOTE: srcpitch is ignored */
95 glue(glue(glue(cirrus_colorexpand_transp_
, ROP_NAME
), _
),DEPTH
)
96 (CirrusVGAState
* s
, uint8_t * dst
,
98 int dstpitch
, int srcpitch
,
99 int bltwidth
, int bltheight
)
103 unsigned bits
, bits_xor
;
108 int dstskipleft
= s
->vga
.gr
[0x2f] & 0x1f;
109 int srcskipleft
= dstskipleft
/ 3;
111 int srcskipleft
= s
->vga
.gr
[0x2f] & 0x07;
112 int dstskipleft
= srcskipleft
* (DEPTH
/ 8);
115 if (s
->cirrus_blt_modeext
& CIRRUS_BLTMODEEXT_COLOREXPINV
) {
117 col
= s
->cirrus_blt_bgcol
;
120 col
= s
->cirrus_blt_fgcol
;
123 for(y
= 0; y
< bltheight
; y
++) {
124 bitmask
= 0x80 >> srcskipleft
;
125 bits
= *src
++ ^ bits_xor
;
126 d
= dst
+ dstskipleft
;
127 for (x
= dstskipleft
; x
< bltwidth
; x
+= (DEPTH
/ 8)) {
128 if ((bitmask
& 0xff) == 0) {
130 bits
= *src
++ ^ bits_xor
;
132 index
= (bits
& bitmask
);
144 glue(glue(glue(cirrus_colorexpand_
, ROP_NAME
), _
),DEPTH
)
145 (CirrusVGAState
* s
, uint8_t * dst
,
147 int dstpitch
, int srcpitch
,
148 int bltwidth
, int bltheight
)
156 int srcskipleft
= s
->vga
.gr
[0x2f] & 0x07;
157 int dstskipleft
= srcskipleft
* (DEPTH
/ 8);
159 colors
[0] = s
->cirrus_blt_bgcol
;
160 colors
[1] = s
->cirrus_blt_fgcol
;
161 for(y
= 0; y
< bltheight
; y
++) {
162 bitmask
= 0x80 >> srcskipleft
;
164 d
= dst
+ dstskipleft
;
165 for (x
= dstskipleft
; x
< bltwidth
; x
+= (DEPTH
/ 8)) {
166 if ((bitmask
& 0xff) == 0) {
170 col
= colors
[!!(bits
& bitmask
)];
180 glue(glue(glue(cirrus_colorexpand_pattern_transp_
, ROP_NAME
), _
),DEPTH
)
181 (CirrusVGAState
* s
, uint8_t * dst
,
183 int dstpitch
, int srcpitch
,
184 int bltwidth
, int bltheight
)
187 int x
, y
, bitpos
, pattern_y
;
188 unsigned int bits
, bits_xor
;
191 int dstskipleft
= s
->vga
.gr
[0x2f] & 0x1f;
192 int srcskipleft
= dstskipleft
/ 3;
194 int srcskipleft
= s
->vga
.gr
[0x2f] & 0x07;
195 int dstskipleft
= srcskipleft
* (DEPTH
/ 8);
198 if (s
->cirrus_blt_modeext
& CIRRUS_BLTMODEEXT_COLOREXPINV
) {
200 col
= s
->cirrus_blt_bgcol
;
203 col
= s
->cirrus_blt_fgcol
;
205 pattern_y
= s
->cirrus_blt_srcaddr
& 7;
207 for(y
= 0; y
< bltheight
; y
++) {
208 bits
= src
[pattern_y
] ^ bits_xor
;
209 bitpos
= 7 - srcskipleft
;
210 d
= dst
+ dstskipleft
;
211 for (x
= dstskipleft
; x
< bltwidth
; x
+= (DEPTH
/ 8)) {
212 if ((bits
>> bitpos
) & 1) {
216 bitpos
= (bitpos
- 1) & 7;
218 pattern_y
= (pattern_y
+ 1) & 7;
224 glue(glue(glue(cirrus_colorexpand_pattern_
, ROP_NAME
), _
),DEPTH
)
225 (CirrusVGAState
* s
, uint8_t * dst
,
227 int dstpitch
, int srcpitch
,
228 int bltwidth
, int bltheight
)
232 int x
, y
, bitpos
, pattern_y
;
235 int srcskipleft
= s
->vga
.gr
[0x2f] & 0x07;
236 int dstskipleft
= srcskipleft
* (DEPTH
/ 8);
238 colors
[0] = s
->cirrus_blt_bgcol
;
239 colors
[1] = s
->cirrus_blt_fgcol
;
240 pattern_y
= s
->cirrus_blt_srcaddr
& 7;
242 for(y
= 0; y
< bltheight
; y
++) {
243 bits
= src
[pattern_y
];
244 bitpos
= 7 - srcskipleft
;
245 d
= dst
+ dstskipleft
;
246 for (x
= dstskipleft
; x
< bltwidth
; x
+= (DEPTH
/ 8)) {
247 col
= colors
[(bits
>> bitpos
) & 1];
250 bitpos
= (bitpos
- 1) & 7;
252 pattern_y
= (pattern_y
+ 1) & 7;
258 glue(glue(glue(cirrus_fill_
, ROP_NAME
), _
),DEPTH
)
260 uint8_t *dst
, int dst_pitch
,
261 int width
, int height
)
267 col
= s
->cirrus_blt_fgcol
;
270 for(y
= 0; y
< height
; y
++) {
272 for(x
= 0; x
< width
; x
+= (DEPTH
/ 8)) {