Importing vendor version xf86-4_3_99_903 on Wed Feb 26 01:21:00 PST 2004
[xf86-video-sis/mirage.git] / src / sis_cursor.c
blob715b88c8b4cda73b5a2290d2567c93c9382a4a62
1 /* $XFree86$ */
2 /*
3 * SiS hardware cursor handling
5 * Copyright (C) 2001-2004 by Thomas Winischhofer, Vienna, Austria.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1) Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2) Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3) All advertising materials mentioning features or use of this software
16 * must display the following acknowledgement: "This product includes
17 * software developed by Thomas Winischhofer, Vienna, Austria."
18 * 4) The name of the author may not be used to endorse or promote products
19 * derived from this software without specific prior written permission.
21 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESSED OR
22 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
23 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
24 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
25 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
26 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
30 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 * Author: Thomas Winischhofer <thomas@winischhofer.net>
34 * Idea based on code by Can-Ru Yeou, SiS Inc.
38 #include "xf86.h"
39 #include "xf86PciInfo.h"
40 #include "cursorstr.h"
41 #include "vgaHW.h"
43 #include "sis.h"
44 #include "sis_regs.h"
45 #include "sis_cursor.h"
47 #if 0
48 #define SIS300_USE_ARGB16
49 #else
50 #undef SIS300_USE_ARGB16
51 #endif
53 extern void SISWaitRetraceCRT1(ScrnInfoPtr pScrn);
54 extern void SISWaitRetraceCRT2(ScrnInfoPtr pScrn);
56 /* Helper function for Xabre to convert mono image to ARGB */
57 /* The Xabre's cursor engine for CRT2 is buggy and can't
58 * handle mono cursors. We therefore convert the mono image
59 * to ARGB
61 static void
62 SiSXConvertMono2ARGB(SISPtr pSiS)
64 unsigned char *src = pSiS->CurMonoSrc;
65 CARD32 *dest = pSiS->CurARGBDest;
66 CARD8 chunk, mask;
67 CARD32 fg = pSiS->CurFGCol | 0xff000000;
68 CARD32 bg = pSiS->CurBGCol | 0xff000000;
69 int i,j,k;
71 if(!dest || !src) return;
73 for(i = 0; i < 64; i++) {
74 for(j = 0; j < 8; j++) {
75 chunk = *(src + 8); mask = *src++;
76 for(k = 128; k != 0; k >>= 1) {
77 if(mask & k) *dest++ = 0x00000000;
78 else if(chunk & k) *dest++ = fg;
79 else *dest++ = bg;
82 src += 8;
86 static void
87 SiSHideCursor(ScrnInfoPtr pScrn)
89 SISPtr pSiS = SISPTR(pScrn);
90 unsigned char sridx, cridx;
92 sridx = inSISREG(SISSR); cridx = inSISREG(SISCR);
94 #ifdef UNLOCK_ALWAYS
95 sisSaveUnlockExtRegisterLock(pSiS, NULL, NULL);
96 #endif
98 andSISIDXREG(SISSR, 0x06, 0xBF);
100 outSISREG(SISSR, sridx); outSISREG(SISCR, cridx);
103 static void
104 SiS300HideCursor(ScrnInfoPtr pScrn)
106 SISPtr pSiS = SISPTR(pScrn);
108 #ifdef SISDUALHEAD
109 if(pSiS->DualHeadMode && (!pSiS->ForceCursorOff)) {
110 if(pSiS->SecondHead) {
111 /* Head 2 is always CRT1 */
112 sis300DisableHWCursor()
113 sis300SetCursorPositionY(2000, 0)
114 } else {
115 /* Head 1 is always CRT2 */
116 sis301DisableHWCursor()
117 sis301SetCursorPositionY(2000, 0)
119 } else {
120 #endif
121 sis300DisableHWCursor()
122 sis300SetCursorPositionY(2000, 0)
123 if(pSiS->VBFlags & CRT2_ENABLE) {
124 sis301DisableHWCursor()
125 sis301SetCursorPositionY(2000, 0)
127 #ifdef SISDUALHEAD
129 #endif
132 static void
133 SiS310HideCursor(ScrnInfoPtr pScrn)
135 SISPtr pSiS = SISPTR(pScrn);
137 pSiS->HWCursorIsVisible = FALSE;
139 #ifdef SISDUALHEAD
140 if(pSiS->DualHeadMode && (!pSiS->ForceCursorOff)) {
141 if(pSiS->SecondHead) {
142 /* Head 2 is always CRT1 */
143 sis310DisableHWCursor()
144 sis310SetCursorPositionY(2000, 0)
145 } else {
146 /* Head 1 is always CRT2 */
147 sis301DisableHWCursor310()
148 sis301SetCursorPositionY310(2000, 0)
150 } else {
151 #endif
152 sis310DisableHWCursor()
153 sis310SetCursorPositionY(2000, 0)
154 if(pSiS->VBFlags & VB_VIDEOBRIDGE) {
155 sis301DisableHWCursor310()
156 sis301SetCursorPositionY310(2000, 0)
158 #ifdef SISDUALHEAD
160 #endif
163 static void
164 SiSShowCursor(ScrnInfoPtr pScrn)
166 SISPtr pSiS = SISPTR(pScrn);
167 unsigned char sridx, cridx;
169 /* Backup current indices of SR and CR since we run async:ly
170 * and might be interrupting an on-going register read/write
172 sridx = inSISREG(SISSR); cridx = inSISREG(SISCR);
174 #ifdef UNLOCK_ALWAYS
175 sisSaveUnlockExtRegisterLock(pSiS, NULL, NULL);
176 #endif
178 orSISIDXREG(SISSR, 0x06, 0x40);
180 outSISREG(SISSR, sridx); outSISREG(SISCR, cridx);
183 static void
184 SiS300ShowCursor(ScrnInfoPtr pScrn)
186 SISPtr pSiS = SISPTR(pScrn);
188 #ifdef SISDUALHEAD
189 if(pSiS->DualHeadMode) {
190 if(pSiS->SecondHead) {
191 /* Head 2 is always CRT1 */
192 if(pSiS->UseHWARGBCursor) {
193 #ifdef SIS300_USE_ARGB16
194 sis300EnableHWARGB16Cursor()
195 #else
196 sis300EnableHWARGBCursor()
197 #endif
198 } else {
199 sis300EnableHWCursor()
201 } else {
202 /* Head 1 is always CRT2 */
203 if(pSiS->UseHWARGBCursor) {
204 #ifdef SIS300_USE_ARGB16
205 sis301EnableHWARGB16Cursor()
206 #else
207 sis301EnableHWARGBCursor()
208 #endif
209 } else {
210 sis301EnableHWCursor()
213 } else {
214 #endif
215 if(pSiS->UseHWARGBCursor) {
216 #ifdef SIS300_USE_ARGB16
217 sis300EnableHWARGB16Cursor()
218 #else
219 sis300EnableHWARGBCursor()
220 #endif
221 if(pSiS->VBFlags & CRT2_ENABLE) {
222 #ifdef SIS300_USE_ARGB16
223 sis301EnableHWARGB16Cursor()
224 #else
225 sis301EnableHWARGBCursor()
226 #endif
228 } else {
229 sis300EnableHWCursor()
230 if(pSiS->VBFlags & CRT2_ENABLE) {
231 sis301EnableHWCursor()
234 #ifdef SISDUALHEAD
236 #endif
239 static void
240 SiS310ShowCursor(ScrnInfoPtr pScrn)
242 SISPtr pSiS = SISPTR(pScrn);
244 if(pSiS->HideHWCursor) {
245 SiS310HideCursor(pScrn);
246 pSiS->HWCursorIsVisible = TRUE;
247 return;
250 pSiS->HWCursorIsVisible = TRUE;
252 #ifdef SISDUALHEAD
253 if(pSiS->DualHeadMode) {
254 if(pSiS->SecondHead) {
255 /* Head 2 is always CRT1 */
256 if(pSiS->UseHWARGBCursor) {
257 sis310EnableHWARGBCursor()
258 } else {
259 sis310EnableHWCursor()
261 } else {
262 /* Head 1 is always CRT2 */
263 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
264 sis301EnableHWCursor330()
265 } else {
266 if(pSiS->UseHWARGBCursor) {
267 sis301EnableHWARGBCursor310()
268 } else {
269 sis301EnableHWCursor310()
273 } else {
274 #endif
275 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
276 if(pSiS->UseHWARGBCursor) {
277 sis310EnableHWARGBCursor()
278 } else {
279 sis310EnableHWCursor()
281 if(pSiS->VBFlags & CRT2_ENABLE) {
282 sis301EnableHWCursor330()
284 } else {
285 if(pSiS->UseHWARGBCursor) {
286 sis310EnableHWARGBCursor()
287 if(pSiS->VBFlags & CRT2_ENABLE) {
288 sis301EnableHWARGBCursor310()
290 } else {
291 sis310EnableHWCursor()
292 if(pSiS->VBFlags & CRT2_ENABLE) {
293 sis301EnableHWCursor310()
297 #ifdef SISDUALHEAD
299 #endif
302 static void
303 SiSSetCursorPosition(ScrnInfoPtr pScrn, int x, int y)
305 SISPtr pSiS = SISPTR(pScrn);
306 DisplayModePtr mode = pSiS->CurrentLayout.mode;
307 unsigned char x_preset = 0;
308 unsigned char y_preset = 0;
309 int temp;
310 unsigned char sridx, cridx;
312 sridx = inSISREG(SISSR); cridx = inSISREG(SISCR);
314 #ifdef UNLOCK_ALWAYS
315 sisSaveUnlockExtRegisterLock(pSiS, NULL, NULL);
316 #endif
318 if(x < 0) {
319 x_preset = (-x);
320 x = 0;
323 if(y < 0) {
324 y_preset = (-y);
325 y = 0;
328 if(mode->Flags & V_INTERLACE) y /= 2;
329 else if(mode->Flags & V_DBLSCAN) y *= 2;
331 outSISIDXREG(SISSR, 0x1A, x & 0xff);
332 outSISIDXREG(SISSR, 0x1B, (x & 0xff00) >> 8);
333 outSISIDXREG(SISSR, 0x1D, y & 0xff);
335 inSISIDXREG(SISSR, 0x1E, temp);
336 temp &= 0xF8;
337 outSISIDXREG(SISSR, 0x1E, temp | ((y >> 8) & 0x07));
339 outSISIDXREG(SISSR, 0x1C, x_preset);
340 outSISIDXREG(SISSR, 0x1F, y_preset);
342 outSISREG(SISSR, sridx); outSISREG(SISCR, cridx);
345 #ifdef SISMERGED
346 static void
347 SiSSetCursorPositionMerged(ScrnInfoPtr pScrn1, int x, int y)
349 SISPtr pSiS = SISPTR(pScrn1);
350 ScrnInfoPtr pScrn2 = pSiS->CRT2pScrn;
351 DisplayModePtr mode1 = CDMPTR->CRT1;
352 DisplayModePtr mode2 = CDMPTR->CRT2;
353 unsigned short x1_preset = 0, x2_preset = 0;
354 unsigned short y1_preset = 0, y2_preset = 0;
355 unsigned short maxpreset;
356 int x1, y1, x2, y2;
358 x += pScrn1->frameX0;
359 y += pScrn1->frameY0;
361 x1 = x - pSiS->CRT1frameX0;
362 y1 = y - pSiS->CRT1frameY0;
364 x2 = x - pScrn2->frameX0;
365 y2 = y - pScrn2->frameY0;
367 maxpreset = 63;
368 if((pSiS->VGAEngine == SIS_300_VGA) && (pSiS->UseHWARGBCursor)) maxpreset = 31;
370 if(x1 < 0) {
371 x1_preset = (-x1);
372 if(x1_preset > maxpreset) x1_preset = maxpreset;
373 x1 = 0;
375 if(y1 < 0) {
376 y1_preset = (-y1);
377 if(y1_preset > maxpreset) y1_preset = maxpreset;
378 y1 = 0;
380 if(x2 < 0) {
381 x2_preset = (-x2);
382 if(x2_preset > maxpreset) x2_preset = maxpreset;
383 x2 = 0;
385 if(y2 < 0) {
386 y2_preset = (-y2);
387 if(y2_preset > maxpreset) y2_preset = maxpreset;
388 y2 = 0;
391 if(mode1->Flags & V_INTERLACE) { y1 /= 2; y1_preset /= 2; }
392 else if(mode1->Flags & V_DBLSCAN) { y1 *= 2; y1_preset *= 2; }
394 if(mode2->Flags & V_INTERLACE) { y2 /= 2; y2_preset /= 2; }
395 else if(mode2->Flags & V_DBLSCAN) { y2 *= 2; y2_preset *= 2; }
397 /* Work around bug in Cursor engine */
398 if(x1 > mode1->HDisplay) { y1 = 2000; y1_preset = 0; }
399 if(x2 > mode2->HDisplay) { y2 = 2000; y2_preset = 0; }
401 if(pSiS->VGAEngine == SIS_300_VGA) {
402 sis300SetCursorPositionX(x1, x1_preset)
403 sis300SetCursorPositionY(y1, y1_preset)
404 sis301SetCursorPositionX(x2 + 13, x2_preset)
405 sis301SetCursorPositionY(y2, y2_preset)
406 } else {
407 sis310SetCursorPositionX(x1, x1_preset)
408 sis310SetCursorPositionY(y1, y1_preset)
409 sis301SetCursorPositionX310(x2 + 17, x2_preset)
410 sis301SetCursorPositionY310(y2, y2_preset)
413 #endif
415 static void
416 SiS300SetCursorPosition(ScrnInfoPtr pScrn, int x, int y)
418 SISPtr pSiS = SISPTR(pScrn);
419 DisplayModePtr mode = pSiS->CurrentLayout.mode; /* pScrn->currentMode; */
420 unsigned short x_preset = 0;
421 unsigned short y_preset = 0;
423 #ifdef SISMERGED
424 if(pSiS->MergedFB) {
425 SiSSetCursorPositionMerged(pScrn, x, y);
426 return;
428 #endif
430 if(x < 0) {
431 x_preset = (-x);
432 x = 0;
434 if(y < 0) {
435 y_preset = (-y);
436 y = 0;
439 if(mode->Flags & V_INTERLACE) y /= 2;
440 else if(mode->Flags & V_DBLSCAN) y *= 2;
442 #ifdef SISDUALHEAD
443 if(pSiS->DualHeadMode) {
444 if(pSiS->SecondHead) {
445 /* Head 2 is always CRT1 */
446 sis300SetCursorPositionX(x, x_preset)
447 sis300SetCursorPositionY(y, y_preset)
448 } else {
449 /* Head 1 is always CRT2 */
450 sis301SetCursorPositionX(x + 13, x_preset)
451 sis301SetCursorPositionY(y, y_preset)
453 } else {
454 #endif
455 sis300SetCursorPositionX(x, x_preset)
456 sis300SetCursorPositionY(y, y_preset)
457 if(pSiS->VBFlags & CRT2_ENABLE) {
458 sis301SetCursorPositionX(x + 13, x_preset)
459 sis301SetCursorPositionY(y, y_preset)
461 #ifdef SISDUALHEAD
463 #endif
466 static void
467 SiS310SetCursorPosition(ScrnInfoPtr pScrn, int x, int y)
469 SISPtr pSiS = SISPTR(pScrn);
470 DisplayModePtr mode = pSiS->CurrentLayout.mode;
471 unsigned short x_preset = 0;
472 unsigned short y_preset = 0;
474 #ifdef SISMERGED
475 if(pSiS->MergedFB) {
476 SiSSetCursorPositionMerged(pScrn, x, y);
477 return;
479 #endif
481 if(x < 0) {
482 x_preset = (-x);
483 x = 0;
485 if(y < 0) {
486 y_preset = (-y);
487 y = 0;
490 if(mode->Flags & V_INTERLACE) y /= 2;
491 else if(mode->Flags & V_DBLSCAN) y *= 2;
493 #ifdef SISDUALHEAD
494 if(pSiS->DualHeadMode) {
495 if(pSiS->SecondHead) {
496 /* Head 2 is always CRT1 */
497 sis310SetCursorPositionX(x, x_preset)
498 sis310SetCursorPositionY(y, y_preset)
499 } else {
500 /* Head 1 is always CRT2 */
501 sis301SetCursorPositionX310(x + 17, x_preset)
502 sis301SetCursorPositionY310(y, y_preset)
504 } else {
505 #endif
506 sis310SetCursorPositionX(x, x_preset)
507 sis310SetCursorPositionY(y, y_preset)
508 if(pSiS->VBFlags & CRT2_ENABLE) {
509 sis301SetCursorPositionX310(x + 17, x_preset)
510 sis301SetCursorPositionY310(y, y_preset)
512 #ifdef SISDUALHEAD
514 #endif
518 static void
519 SiSSetCursorColors(ScrnInfoPtr pScrn, int bg, int fg)
521 SISPtr pSiS = SISPTR(pScrn);
522 unsigned char f_red, f_green, f_blue;
523 unsigned char b_red, b_green, b_blue;
524 unsigned char sridx, cridx;
526 sridx = inSISREG(SISSR); cridx = inSISREG(SISCR);
528 #ifdef UNLOCK_ALWAYS
529 sisSaveUnlockExtRegisterLock(pSiS, NULL, NULL);
530 #endif
532 f_red = (fg & 0x00FF0000) >> (16+2);
533 f_green = (fg & 0x0000FF00) >> (8+2);
534 f_blue = (fg & 0x000000FF) >> 2;
535 b_red = (bg & 0x00FF0000) >> (16+2);
536 b_green = (bg & 0x0000FF00) >> (8+2);
537 b_blue = (bg & 0x000000FF) >> 2;
539 outSISIDXREG(SISSR, 0x14, b_red);
540 outSISIDXREG(SISSR, 0x15, b_green);
541 outSISIDXREG(SISSR, 0x16, b_blue);
542 outSISIDXREG(SISSR, 0x17, f_red);
543 outSISIDXREG(SISSR, 0x18, f_green);
544 outSISIDXREG(SISSR, 0x19, f_blue);
546 outSISREG(SISSR, sridx); outSISREG(SISCR, cridx);
549 static void
550 SiS300SetCursorColors(ScrnInfoPtr pScrn, int bg, int fg)
552 SISPtr pSiS = SISPTR(pScrn);
554 if(pSiS->UseHWARGBCursor) return;
556 #ifdef SISDUALHEAD
557 if(pSiS->DualHeadMode) {
558 if(pSiS->SecondHead) {
559 /* Head 2 is always CRT1 */
560 sis300SetCursorBGColor(bg)
561 sis300SetCursorFGColor(fg)
562 } else {
563 /* Head 1 is always CRT2 */
564 sis301SetCursorBGColor(bg)
565 sis301SetCursorFGColor(fg)
567 } else {
568 #endif
569 sis300SetCursorBGColor(bg)
570 sis300SetCursorFGColor(fg)
571 if(pSiS->VBFlags & CRT2_ENABLE) {
572 sis301SetCursorBGColor(bg)
573 sis301SetCursorFGColor(fg)
575 #ifdef SISDUALHEAD
577 #endif
580 static void
581 SiS310SetCursorColors(ScrnInfoPtr pScrn, int bg, int fg)
583 SISPtr pSiS = SISPTR(pScrn);
585 if(pSiS->UseHWARGBCursor) return;
587 #ifdef SISDUALHEAD
588 if(pSiS->DualHeadMode) {
589 if(pSiS->SecondHead) {
590 /* Head 2 is always CRT1 */
591 sis310SetCursorBGColor(bg)
592 sis310SetCursorFGColor(fg)
593 } else {
594 /* Head 1 is always CRT2 */
595 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
596 if((fg != pSiS->CurFGCol) || (bg != pSiS->CurBGCol)) {
597 pSiS->CurFGCol = fg;
598 pSiS->CurBGCol = bg;
599 SiSXConvertMono2ARGB(pSiS);
601 } else {
602 sis301SetCursorBGColor310(bg)
603 sis301SetCursorFGColor310(fg)
606 } else {
607 #endif
608 sis310SetCursorBGColor(bg)
609 sis310SetCursorFGColor(fg)
611 if(pSiS->VBFlags & CRT2_ENABLE) {
612 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
613 if((fg != pSiS->CurFGCol) || (bg != pSiS->CurBGCol)) {
614 pSiS->CurFGCol = fg;
615 pSiS->CurBGCol = bg;
616 SiSXConvertMono2ARGB(pSiS);
618 } else {
619 sis301SetCursorBGColor310(bg)
620 sis301SetCursorFGColor310(fg)
623 #ifdef SISDUALHEAD
625 #endif
628 static void
629 SiSLoadCursorImage(ScrnInfoPtr pScrn, unsigned char *src)
631 SISPtr pSiS = SISPTR(pScrn);
632 DisplayModePtr mode = pSiS->CurrentLayout.mode;
633 int cursor_addr;
634 unsigned char temp;
635 unsigned char sridx, cridx;
637 sridx = inSISREG(SISSR); cridx = inSISREG(SISCR);
639 #ifdef UNLOCK_ALWAYS
640 sisSaveUnlockExtRegisterLock(pSiS, NULL, NULL);
641 #endif
643 cursor_addr = pScrn->videoRam - 1;
644 if(mode->Flags & V_DBLSCAN) {
645 int i;
646 for(i = 0; i < 32; i++) {
647 memcpy((unsigned char *)pSiS->FbBase + (cursor_addr * 1024) + (32 * i),
648 src + (16 * i), 16);
649 memcpy((unsigned char *)pSiS->FbBase + (cursor_addr * 1024) + (32 * i) + 16,
650 src + (16 * i), 16);
652 } else {
653 memcpy((unsigned char *)pSiS->FbBase + (cursor_addr * 1024), src, 1024);
656 /* copy bits [21:18] into the top bits of SR38 */
657 inSISIDXREG(SISSR, 0x38, temp);
658 temp &= 0x0F;
659 outSISIDXREG(SISSR, 0x38, temp | ((cursor_addr & 0xF00) >> 4));
661 if(pSiS->Chipset == PCI_CHIP_SIS530) {
662 /* store the bit [22] to SR3E */
663 if(cursor_addr & 0x1000) {
664 orSISIDXREG(SISSR, 0x3E, 0x04);
665 } else {
666 andSISIDXREG(SISSR, 0x3E, ~0x04);
670 /* set HW cursor pattern, use pattern 0xF */
671 orSISIDXREG(SISSR, 0x1E, 0xF0);
673 /* disable the hardware cursor side pattern */
674 andSISIDXREG(SISSR, 0x1E, 0xF7);
676 outSISREG(SISSR, sridx); outSISREG(SISCR, cridx);
679 static void
680 SiS300LoadCursorImage(ScrnInfoPtr pScrn, unsigned char *src)
682 SISPtr pSiS = SISPTR(pScrn);
683 int cursor_addr;
684 CARD32 status1 = 0, status2 = 0;
685 unsigned char *dest = pSiS->FbBase;
686 BOOLEAN sizedouble = FALSE;
687 #ifdef SISDUALHEAD
688 SISEntPtr pSiSEnt = pSiS->entityPrivate;
689 #endif
691 #ifdef SISMERGED
692 if(pSiS->MergedFB) {
693 if((CDMPTR->CRT1->Flags & V_DBLSCAN) && (CDMPTR->CRT2->Flags & V_DBLSCAN)) {
694 sizedouble = TRUE;
696 } else
697 #endif
698 if(pSiS->CurrentLayout.mode->Flags & V_DBLSCAN) {
699 sizedouble = TRUE;
702 cursor_addr = pScrn->videoRam - pSiS->cursorOffset - (pSiS->CursorSize/1024); /* 1K boundary */
704 #ifdef SISDUALHEAD
705 /* TW: Use the global (real) FbBase in DHM */
706 if(pSiS->DualHeadMode) dest = pSiSEnt->FbBase;
707 #endif
709 if(sizedouble) {
710 int i;
711 for(i = 0; i < 32; i++) {
712 memcpy((unsigned char *)dest + (cursor_addr * 1024) + (32 * i),
713 src + (16 * i), 16);
714 memcpy((unsigned char *)dest + (cursor_addr * 1024) + (32 * i) + 16,
715 src + (16 * i), 16);
717 } else {
718 memcpy((unsigned char *)dest + (cursor_addr * 1024), src, 1024);
721 if(pSiS->UseHWARGBCursor) {
722 if(pSiS->VBFlags & DISPTYPE_CRT1) {
723 status1 = sis300GetCursorStatus;
724 sis300DisableHWCursor()
725 if(pSiS->VBFlags & CRT2_ENABLE) {
726 status2 = sis301GetCursorStatus;
727 sis301DisableHWCursor()
729 SISWaitRetraceCRT1(pScrn);
730 sis300SwitchToMONOCursor();
731 if(pSiS->VBFlags & CRT2_ENABLE) {
732 SISWaitRetraceCRT2(pScrn);
733 sis301SwitchToMONOCursor();
737 sis300SetCursorAddress(cursor_addr);
738 if(status1) sis300SetCursorStatus(status1)
740 if(pSiS->VBFlags & CRT2_ENABLE) {
741 if((pSiS->UseHWARGBCursor) && (!pSiS->VBFlags & DISPTYPE_CRT1)) {
742 status2 = sis301GetCursorStatus;
743 sis301DisableHWCursor()
744 SISWaitRetraceCRT2(pScrn);
745 sis301SwitchToMONOCursor();
747 sis301SetCursorAddress(cursor_addr)
748 if(status2) sis301SetCursorStatus(status2)
751 pSiS->UseHWARGBCursor = FALSE;
754 static void
755 SiS310LoadCursorImage(ScrnInfoPtr pScrn, unsigned char *src)
757 SISPtr pSiS = SISPTR(pScrn);
758 unsigned long cursor_addr, cursor_addr2 = 0;
759 CARD32 status1 = 0, status2 = 0;
760 unsigned char *dest = pSiS->FbBase;
761 BOOLEAN sizedouble = FALSE;
762 int bufnum;
763 #ifdef SISDUALHEAD
764 SISEntPtr pSiSEnt = pSiS->entityPrivate;
766 if(pSiS->DualHeadMode) {
767 pSiSEnt->HWCursorMBufNum ^= 1;
768 bufnum = 1 << pSiSEnt->HWCursorMBufNum;
769 } else {
770 #endif
771 pSiS->HWCursorMBufNum ^= 1;
772 bufnum = 1 << pSiS->HWCursorMBufNum;
773 #ifdef SISDUALHEAD
775 #endif
777 #ifdef SISMERGED
778 if(pSiS->MergedFB) {
779 if((CDMPTR->CRT1->Flags & V_DBLSCAN) && (CDMPTR->CRT2->Flags & V_DBLSCAN)) {
780 sizedouble = TRUE;
782 } else
783 #endif
784 if(pSiS->CurrentLayout.mode->Flags & V_DBLSCAN) {
785 sizedouble = TRUE;
788 #ifdef SISDUALHEAD
789 /* Use the global (real) FbBase in DHM */
790 if(pSiS->DualHeadMode) dest = pSiSEnt->FbBase;
791 #endif
793 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
794 cursor_addr = pScrn->videoRam - pSiS->cursorOffset - (pSiS->CursorSize/1024);
795 } else {
796 cursor_addr = pScrn->videoRam - pSiS->cursorOffset - ((pSiS->CursorSize/1024) * bufnum);
799 if(sizedouble) {
800 int i;
801 for(i = 0; i < 32; i++) {
802 memcpy((unsigned char *)dest + (cursor_addr * 1024) + (32 * i),
803 src + (16 * i), 16);
804 memcpy((unsigned char *)dest + (cursor_addr * 1024) + (32 * i) + 16,
805 src + (16 * i), 16);
807 } else {
808 memcpy((unsigned char *)dest + (cursor_addr * 1024), src, 1024);
811 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
813 /* Convert Mono image to color image */
815 cursor_addr2 = pScrn->videoRam - pSiS->cursorOffset - ((pSiS->CursorSize/1024) * 2);
817 pSiS->CurMonoSrc = (unsigned char *)dest + (cursor_addr * 1024);
818 pSiS->CurARGBDest = (CARD32 *)((unsigned char *)dest + (cursor_addr2 * 1024));
820 SiSXConvertMono2ARGB(pSiS);
822 if(pSiS->UseHWARGBCursor) {
823 if(pSiS->VBFlags & DISPTYPE_CRT1) {
824 status1 = sis310GetCursorStatus;
825 sis310DisableHWCursor();
826 SISWaitRetraceCRT1(pScrn);
827 sis310SwitchToMONOCursor();
831 } else {
833 if(pSiS->UseHWARGBCursor) {
834 if(pSiS->VBFlags & DISPTYPE_CRT1) {
835 status1 = sis310GetCursorStatus;
836 sis310DisableHWCursor()
837 if(pSiS->VBFlags & CRT2_ENABLE) {
838 status2 = sis301GetCursorStatus310;
839 sis301DisableHWCursor310()
841 SISWaitRetraceCRT1(pScrn);
842 sis310SwitchToMONOCursor();
843 if(pSiS->VBFlags & CRT2_ENABLE) {
844 SISWaitRetraceCRT2(pScrn);
845 sis301SwitchToMONOCursor310();
848 } else if(pSiS->Chipset == PCI_CHIP_SIS315H) {
849 if(pSiS->VBFlags & DISPTYPE_CRT1) {
850 SISWaitRetraceCRT1(pScrn);
855 sis310SetCursorAddress(cursor_addr);
856 if(status1) sis310SetCursorStatus(status1)
858 if(pSiS->VBFlags & CRT2_ENABLE) {
859 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
860 sis301SetCursorAddress310(cursor_addr2)
861 } else {
862 if((pSiS->UseHWARGBCursor) && (!pSiS->VBFlags & DISPTYPE_CRT1)) {
863 status2 = sis301GetCursorStatus310;
864 sis301DisableHWCursor310()
865 SISWaitRetraceCRT2(pScrn);
866 sis301SwitchToMONOCursor310();
868 sis301SetCursorAddress310(cursor_addr)
869 if(status2) sis301SetCursorStatus310(status2)
873 pSiS->UseHWARGBCursor = FALSE;
876 static Bool
877 SiSUseHWCursor(ScreenPtr pScreen, CursorPtr pCurs)
879 ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
880 SISPtr pSiS = SISPTR(pScrn);
881 DisplayModePtr mode = pSiS->CurrentLayout.mode;
883 if(pSiS->Chipset != PCI_CHIP_SIS6326) return TRUE;
884 if(!(pSiS->SiS6326Flags & SIS6326_TVDETECTED)) return TRUE;
885 if((strcmp(mode->name, "PAL800x600U") == 0) ||
886 (strcmp(mode->name, "NTSC640x480U") == 0))
887 return FALSE;
888 else
889 return TRUE;
892 static Bool
893 SiS300UseHWCursor(ScreenPtr pScreen, CursorPtr pCurs)
895 ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
896 SISPtr pSiS = SISPTR(pScrn);
897 DisplayModePtr mode = pSiS->CurrentLayout.mode;
898 #ifdef SISMERGED
899 DisplayModePtr mode2 = NULL;
901 if(pSiS->MergedFB) {
902 mode = CDMPTR->CRT1;
903 mode2 = CDMPTR->CRT2;
905 #endif
907 switch (pSiS->Chipset) {
908 case PCI_CHIP_SIS300:
909 case PCI_CHIP_SIS630:
910 case PCI_CHIP_SIS540:
911 if(mode->Flags & V_INTERLACE)
912 return FALSE;
913 if((mode->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
914 return FALSE;
915 #ifdef SISMERGED
916 if(pSiS->MergedFB) {
917 if(mode2->Flags & V_INTERLACE)
918 return FALSE;
919 if((mode2->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
920 return FALSE;
922 #endif
923 break;
924 case PCI_CHIP_SIS330:
925 #ifdef SISDUALHEAD
926 if((!pSiS->DualHeadMode) || (!pSiS->SecondHead))
927 #endif
928 if(pSiS->MiscFlags & MISC_TVNTSC1024) return FALSE;
929 /* fall through */
930 case PCI_CHIP_SIS550:
931 case PCI_CHIP_SIS650:
932 case PCI_CHIP_SIS315:
933 case PCI_CHIP_SIS315H:
934 case PCI_CHIP_SIS315PRO:
935 case PCI_CHIP_SIS660:
936 if(mode->Flags & V_INTERLACE)
937 return FALSE;
938 if((mode->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
939 return FALSE;
940 #ifdef SISMERGED
941 if(pSiS->MergedFB) {
942 if(mode2->Flags & V_INTERLACE)
943 return FALSE;
944 if((mode2->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
945 return FALSE;
947 #endif
948 break;
949 default:
950 if(mode->Flags & V_INTERLACE)
951 return FALSE;
952 if((mode->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
953 return FALSE;
954 break;
956 return TRUE;
959 #if XF86_VERSION_CURRENT >= XF86_VERSION_NUMERIC(4,2,99,0,0)
960 #ifdef ARGB_CURSOR
961 #ifdef SIS_ARGB_CURSOR
962 static Bool
963 SiSUseHWCursorARGB(ScreenPtr pScreen, CursorPtr pCurs)
965 ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
966 SISPtr pSiS = SISPTR(pScrn);
967 DisplayModePtr mode = pSiS->CurrentLayout.mode;
968 #ifdef SISMERGED
969 DisplayModePtr mode2 = NULL;
971 if(pSiS->MergedFB) {
972 mode = CDMPTR->CRT1;
973 mode2 = CDMPTR->CRT2;
975 #endif
977 switch (pSiS->Chipset) {
978 case PCI_CHIP_SIS300:
979 case PCI_CHIP_SIS630:
980 case PCI_CHIP_SIS540:
981 if(mode->Flags & V_INTERLACE)
982 return FALSE;
983 if((pCurs->bits->height > 32) || (pCurs->bits->width > 32))
984 return FALSE;
985 if((mode->Flags & V_DBLSCAN) && (pCurs->bits->height > 16))
986 return FALSE;
987 #ifdef SISMERGED
988 if(pSiS->MergedFB) {
989 if(mode2->Flags & V_INTERLACE)
990 return FALSE;
991 if((mode2->Flags & V_DBLSCAN) && (pCurs->bits->height > 16))
992 return FALSE;
994 #endif
995 break;
996 case PCI_CHIP_SIS330:
997 #ifdef SISDUALHEAD
998 if((!pSiS->DualHeadMode) || (!pSiS->SecondHead))
999 #endif
1000 if(pSiS->MiscFlags & MISC_TVNTSC1024) return FALSE;
1001 /* fall through */
1002 case PCI_CHIP_SIS550:
1003 case PCI_CHIP_SIS650:
1004 case PCI_CHIP_SIS315:
1005 case PCI_CHIP_SIS315H:
1006 case PCI_CHIP_SIS315PRO:
1007 case PCI_CHIP_SIS660:
1008 if(mode->Flags & V_INTERLACE)
1009 return FALSE;
1010 if((pCurs->bits->height > 64) || (pCurs->bits->width > 64))
1011 return FALSE;
1012 if((mode->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
1013 return FALSE;
1014 if((pSiS->CurrentLayout.bitsPerPixel == 8) && (pSiS->VBFlags & CRT2_ENABLE))
1015 return FALSE;
1016 #ifdef SISMERGED
1017 if(pSiS->MergedFB) {
1018 if(mode2->Flags & V_INTERLACE)
1019 return FALSE;
1020 if((mode->Flags & V_DBLSCAN) && (pCurs->bits->height > 32))
1021 return FALSE;
1023 #endif
1024 break;
1025 default:
1026 return FALSE;
1028 return TRUE;
1031 static void SiS300LoadCursorImageARGB(ScrnInfoPtr pScrn, CursorPtr pCurs)
1033 SISPtr pSiS = SISPTR(pScrn);
1034 int cursor_addr, i, j, maxheight = 32;
1035 CARD32 *src = pCurs->bits->argb, *p;
1036 #ifdef SIS300_USE_ARGB16
1037 CARD16 *dest, *pb;
1038 CARD16 temp1;
1039 #define MYSISPTRTYPE CARD16
1040 #else
1041 CARD32 *pb, *dest;
1042 #define MYSISPTRTYPE CARD32
1043 #endif
1044 int srcwidth = pCurs->bits->width;
1045 int srcheight = pCurs->bits->height;
1046 CARD32 temp, status1 = 0, status2 = 0;
1047 BOOLEAN sizedouble = FALSE;
1048 #ifdef SISDUALHEAD
1049 SISEntPtr pSiSEnt = pSiS->entityPrivate;
1050 #endif
1052 #ifdef SISMERGED
1053 if(pSiS->MergedFB) {
1054 if((CDMPTR->CRT1->Flags & V_DBLSCAN) && (CDMPTR->CRT2->Flags & V_DBLSCAN)) {
1055 sizedouble = TRUE;
1057 } else
1058 #endif
1059 if(pSiS->CurrentLayout.mode->Flags & V_DBLSCAN) {
1060 sizedouble = TRUE;
1063 cursor_addr = pScrn->videoRam - pSiS->cursorOffset - ((pSiS->CursorSize/1024) * 2);
1065 if(srcwidth > 32) srcwidth = 32;
1066 if(srcheight > 32) srcheight = 32;
1068 #ifdef SISDUALHEAD
1069 if (pSiS->DualHeadMode)
1070 /* TW: Use the global (real) FbBase in DHM */
1071 dest = (MYSISPTRTYPE *)((unsigned char *)pSiSEnt->FbBase + (cursor_addr * 1024));
1072 else
1073 #endif
1074 dest = (MYSISPTRTYPE *)((unsigned char *)pSiS->FbBase + (cursor_addr * 1024));
1076 if(sizedouble) {
1077 if(srcheight > 16) srcheight = 16;
1078 maxheight = 16;
1081 #ifdef SIS300_USE_ARGB16 /* Use 16 Bit RGB pointer */
1082 for(i = 0; i < srcheight; i++) {
1083 p = src;
1084 pb = dest;
1085 src += pCurs->bits->width;
1086 for(j = 0; j < srcwidth; j++) {
1087 temp = *p++;
1088 if(temp & 0xffffff) {
1089 temp1 = ((temp & 0xff) >> 3) |
1090 ((((temp & 0xff00) >> (8 + 3)) << 5) & 0x03e0) |
1091 ((((temp & 0xff0000) >> (16 + 3)) << 10) & 0x7c00);
1092 } else temp1 = 0x8000;
1093 *dest++ = temp1;
1095 if(srcwidth < 32) {
1096 for(; j < 32; j++) {
1097 *dest++ = 0x8000;
1101 if(srcheight < maxheight) {
1102 for(; i < maxheight; i++)
1103 for(j = 0; j < 32; j++) {
1104 *dest++ = 0x8000;
1106 if(sizedouble) {
1107 for(j = 0; j < 32; j++)
1108 *dest++ = 0x0000;
1111 #else /* Use 32bit RGB pointer - preferred, saves us from the conversion */
1112 for(i = 0; i < srcheight; i++) {
1113 p = src;
1114 pb = dest;
1115 src += pCurs->bits->width;
1116 for(j = 0; j < srcwidth; j++) {
1117 temp = *p++;
1118 /* *dest1++ = ((temp ^ 0xff000000) << 4) | (((temp ^ 0xff000000) & 0xf0000000) >> 28); */
1119 if(pSiS->OptUseColorCursorBlend) {
1120 if(temp & 0xffffff) {
1121 if((temp & 0xff000000) > pSiS->OptColorCursorBlendThreshold) {
1122 temp &= 0x00ffffff;
1123 } else {
1124 temp = 0xff111111;
1126 } else temp = 0xff000000;
1127 } else {
1128 if(temp & 0xffffff) temp &= 0x00ffffff;
1129 else temp = 0xff000000;
1131 *dest++ = temp;
1133 if(srcwidth < 32) {
1134 for(; j < 32; j++) {
1135 *dest++ = 0xff000000;
1138 if(sizedouble) {
1139 for(j = 0; j < 32; j++) {
1140 *dest++ = *pb++;
1145 if(srcheight < maxheight) {
1146 for(; i < maxheight; i++) {
1147 for(j = 0; j < 32; j++) {
1148 *dest++ = 0xff000000;
1150 if(sizedouble) {
1151 for(j = 0; j < 32; j++) {
1152 *dest++ = 0xff000000;
1157 #endif
1159 if(!pSiS->UseHWARGBCursor) {
1160 if(pSiS->VBFlags & DISPTYPE_CRT1) {
1161 status1 = sis300GetCursorStatus;
1162 sis300DisableHWCursor()
1163 if(pSiS->VBFlags & CRT2_ENABLE) {
1164 status2 = sis301GetCursorStatus;
1165 sis301DisableHWCursor()
1167 SISWaitRetraceCRT1(pScrn);
1168 sis300SwitchToRGBCursor();
1169 if(pSiS->VBFlags & CRT2_ENABLE) {
1170 SISWaitRetraceCRT2(pScrn);
1171 sis301SwitchToRGBCursor();
1176 sis300SetCursorAddress(cursor_addr);
1177 if(status1) sis300SetCursorStatus(status1)
1179 if(pSiS->VBFlags & CRT2_ENABLE) {
1180 if((!pSiS->UseHWARGBCursor) && (!pSiS->VBFlags & DISPTYPE_CRT1)) {
1181 status2 = sis301GetCursorStatus;
1182 sis301DisableHWCursor()
1183 SISWaitRetraceCRT2(pScrn);
1184 sis301SwitchToRGBCursor();
1186 sis301SetCursorAddress(cursor_addr)
1187 if(status2) sis301SetCursorStatus(status2)
1190 pSiS->UseHWARGBCursor = TRUE;
1193 static void SiS310LoadCursorImageARGB(ScrnInfoPtr pScrn, CursorPtr pCurs)
1195 SISPtr pSiS = SISPTR(pScrn);
1196 int cursor_addr, i, j, maxheight = 64;
1197 CARD32 *src = pCurs->bits->argb, *p, *pb, *dest;
1198 int srcwidth = pCurs->bits->width;
1199 int srcheight = pCurs->bits->height;
1200 CARD32 status1 = 0, status2 = 0;
1201 BOOLEAN sizedouble = FALSE;
1202 int bufnum;
1203 #ifdef SISDUALHEAD
1204 SISEntPtr pSiSEnt = pSiS->entityPrivate;
1205 #endif
1207 #ifdef SISMERGED
1208 if(pSiS->MergedFB) {
1209 if((CDMPTR->CRT1->Flags & V_DBLSCAN) && (CDMPTR->CRT2->Flags & V_DBLSCAN)) {
1210 sizedouble = TRUE;
1212 } else
1213 #endif
1214 if(pSiS->CurrentLayout.mode->Flags & V_DBLSCAN) {
1215 sizedouble = TRUE;
1218 #ifdef SISDUALHEAD
1219 if(pSiS->DualHeadMode) {
1220 pSiSEnt->HWCursorCBufNum ^= 1;
1221 bufnum = 1 << pSiSEnt->HWCursorCBufNum;
1222 } else {
1223 #endif
1224 pSiS->HWCursorCBufNum ^= 1;
1225 bufnum = 1 << pSiS->HWCursorCBufNum;
1226 #ifdef SISDUALHEAD
1228 #endif
1230 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
1231 cursor_addr = pScrn->videoRam - pSiS->cursorOffset - ((pSiS->CursorSize/1024) * 2);
1232 } else {
1233 cursor_addr = pScrn->videoRam - pSiS->cursorOffset - ((pSiS->CursorSize/1024) * (2 + bufnum));
1236 if(srcwidth > 64) srcwidth = 64;
1237 if(srcheight > 64) srcheight = 64;
1239 #ifdef SISDUALHEAD
1240 if(pSiS->DualHeadMode)
1241 /* Use the global (real) FbBase in DHM */
1242 dest = (CARD32 *)((unsigned char *)pSiSEnt->FbBase + (cursor_addr * 1024));
1243 else
1244 #endif
1245 dest = (CARD32 *)((unsigned char *)pSiS->FbBase + (cursor_addr * 1024));
1247 if(sizedouble) {
1248 if(srcheight > 32) srcheight = 32;
1249 maxheight = 32;
1252 for(i = 0; i < srcheight; i++) {
1253 p = src;
1254 pb = dest;
1255 src += pCurs->bits->width;
1256 for(j = 0; j < srcwidth; j++) *dest++ = *p++;
1257 if(srcwidth < 64) {
1258 for(; j < 64; j++) *dest++ = 0;
1260 if(sizedouble) {
1261 for(j = 0; j < 64; j++) {
1262 *dest++ = *pb++;
1266 if(srcheight < maxheight) {
1267 for(; i < maxheight; i++) {
1268 for(j = 0; j < 64; j++) *dest++ = 0;
1269 if(sizedouble) {
1270 for(j = 0; j < 64; j++) *dest++ = 0;
1275 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
1277 if(!pSiS->UseHWARGBCursor) {
1278 if(pSiS->VBFlags & DISPTYPE_CRT1) {
1279 status1 = sis310GetCursorStatus;
1280 sis310DisableHWCursor()
1282 SISWaitRetraceCRT1(pScrn);
1283 sis310SwitchToRGBCursor();
1286 } else {
1288 if(!pSiS->UseHWARGBCursor) {
1289 if(pSiS->VBFlags & DISPTYPE_CRT1) {
1290 status1 = sis310GetCursorStatus;
1291 sis310DisableHWCursor()
1292 if(pSiS->VBFlags & CRT2_ENABLE) {
1293 status2 = sis301GetCursorStatus310;
1294 sis301DisableHWCursor310()
1297 SISWaitRetraceCRT1(pScrn);
1298 sis310SwitchToRGBCursor();
1299 if(pSiS->VBFlags & CRT2_ENABLE) {
1300 SISWaitRetraceCRT2(pScrn);
1301 sis301SwitchToRGBCursor310();
1306 sis310SetCursorAddress(cursor_addr);
1307 if(status1) sis310SetCursorStatus(status1)
1309 if(pSiS->VBFlags & CRT2_ENABLE) {
1310 if(pSiS->ChipFlags & SiSCF_CRT2HWCKaputt) {
1311 sis301SetCursorAddress310(cursor_addr)
1312 } else {
1313 if((!pSiS->UseHWARGBCursor) && (!pSiS->VBFlags & DISPTYPE_CRT1)) {
1314 status2 = sis301GetCursorStatus310;
1315 sis301DisableHWCursor310()
1316 SISWaitRetraceCRT2(pScrn);
1317 sis301SwitchToRGBCursor310();
1319 sis301SetCursorAddress310(cursor_addr)
1320 if(status2) sis301SetCursorStatus310(status2)
1324 pSiS->UseHWARGBCursor = TRUE;
1326 #endif
1327 #endif
1328 #endif
1330 Bool
1331 SiSHWCursorInit(ScreenPtr pScreen)
1333 ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
1334 SISPtr pSiS = SISPTR(pScrn);
1335 xf86CursorInfoPtr infoPtr;
1337 infoPtr = xf86CreateCursorInfoRec();
1338 if(!infoPtr) return FALSE;
1340 pSiS->CursorInfoPtr = infoPtr;
1341 pSiS->UseHWARGBCursor = FALSE;
1343 switch (pSiS->Chipset) {
1345 case PCI_CHIP_SIS300:
1346 case PCI_CHIP_SIS630:
1347 case PCI_CHIP_SIS540:
1348 infoPtr->MaxWidth = 64;
1349 infoPtr->MaxHeight = 64;
1350 infoPtr->ShowCursor = SiS300ShowCursor;
1351 infoPtr->HideCursor = SiS300HideCursor;
1352 infoPtr->SetCursorPosition = SiS300SetCursorPosition;
1353 infoPtr->SetCursorColors = SiS300SetCursorColors;
1354 infoPtr->LoadCursorImage = SiS300LoadCursorImage;
1355 infoPtr->UseHWCursor = SiS300UseHWCursor;
1356 #if XF86_VERSION_CURRENT >= XF86_VERSION_NUMERIC(4,2,99,0,0)
1357 #ifdef ARGB_CURSOR
1358 #ifdef SIS_ARGB_CURSOR
1359 if(pSiS->OptUseColorCursor) {
1360 infoPtr->UseHWCursorARGB = SiSUseHWCursorARGB;
1361 infoPtr->LoadCursorARGB = SiS300LoadCursorImageARGB;
1363 #endif
1364 #endif
1365 #endif
1366 infoPtr->Flags =
1367 HARDWARE_CURSOR_TRUECOLOR_AT_8BPP |
1368 HARDWARE_CURSOR_INVERT_MASK |
1369 HARDWARE_CURSOR_BIT_ORDER_MSBFIRST |
1370 HARDWARE_CURSOR_AND_SOURCE_WITH_MASK |
1371 HARDWARE_CURSOR_SWAP_SOURCE_AND_MASK |
1372 HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_64;
1373 break;
1375 case PCI_CHIP_SIS550:
1376 case PCI_CHIP_SIS650:
1377 case PCI_CHIP_SIS315:
1378 case PCI_CHIP_SIS315H:
1379 case PCI_CHIP_SIS315PRO:
1380 case PCI_CHIP_SIS330:
1381 case PCI_CHIP_SIS660:
1382 infoPtr->MaxWidth = 64;
1383 infoPtr->MaxHeight = 64;
1384 infoPtr->ShowCursor = SiS310ShowCursor;
1385 infoPtr->HideCursor = SiS310HideCursor;
1386 infoPtr->SetCursorPosition = SiS310SetCursorPosition;
1387 infoPtr->SetCursorColors = SiS310SetCursorColors;
1388 infoPtr->LoadCursorImage = SiS310LoadCursorImage;
1389 infoPtr->UseHWCursor = SiS300UseHWCursor;
1390 #if XF86_VERSION_CURRENT >= XF86_VERSION_NUMERIC(4,2,99,0,0)
1391 #ifdef ARGB_CURSOR
1392 #ifdef SIS_ARGB_CURSOR
1393 if(pSiS->OptUseColorCursor) {
1394 infoPtr->UseHWCursorARGB = SiSUseHWCursorARGB;
1395 infoPtr->LoadCursorARGB = SiS310LoadCursorImageARGB;
1397 #endif
1398 #endif
1399 #endif
1400 infoPtr->Flags =
1401 HARDWARE_CURSOR_TRUECOLOR_AT_8BPP |
1402 HARDWARE_CURSOR_INVERT_MASK |
1403 HARDWARE_CURSOR_BIT_ORDER_MSBFIRST |
1404 HARDWARE_CURSOR_AND_SOURCE_WITH_MASK |
1405 HARDWARE_CURSOR_SWAP_SOURCE_AND_MASK |
1406 HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_64;
1407 break;
1409 default:
1410 infoPtr->MaxWidth = 64;
1411 infoPtr->MaxHeight = 64;
1412 infoPtr->SetCursorPosition = SiSSetCursorPosition;
1413 infoPtr->ShowCursor = SiSShowCursor;
1414 infoPtr->HideCursor = SiSHideCursor;
1415 infoPtr->SetCursorColors = SiSSetCursorColors;
1416 infoPtr->LoadCursorImage = SiSLoadCursorImage;
1417 infoPtr->UseHWCursor = SiSUseHWCursor;
1418 infoPtr->Flags =
1419 HARDWARE_CURSOR_TRUECOLOR_AT_8BPP |
1420 HARDWARE_CURSOR_INVERT_MASK |
1421 HARDWARE_CURSOR_BIT_ORDER_MSBFIRST |
1422 HARDWARE_CURSOR_AND_SOURCE_WITH_MASK |
1423 HARDWARE_CURSOR_NIBBLE_SWAPPED |
1424 HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_1;
1425 break;
1428 return(xf86InitCursor(pScreen, infoPtr));