1 /* 2 Haiku ATI video driver adapted from the X.org ATI driver which has the 3 following copyright: 4 5 Copyright 2003 through 2004 by Marc Aurele La France, tsi@xfree86.org 6 7 Copyright 2011 Haiku, Inc. All rights reserved. 8 Distributed under the terms of the MIT license. 9 10 Authors: 11 Gerald Zajac 12 */ 13 14 #include "accelerant.h" 15 #include "mach64.h" 16 17 18 19 bool 20 Mach64_DisplayOverlay(const overlay_window* window, 21 const overlay_buffer* buffer) 22 { 23 // Return true if setup is successful. 24 25 SharedInfo& si = *gInfo.sharedInfo; 26 27 if (window == NULL || buffer == NULL) 28 return false; 29 30 uint32 videoFormat; 31 32 if (buffer->space == B_YCbCr422) 33 videoFormat = SCALE_IN_VYUY422; 34 else 35 return false; // color space not supported 36 37 int32 x1 = (window->h_start < 0) ? 0 : window->h_start; 38 int32 y1 = (window->v_start < 0) ? 0 : window->v_start; 39 40 int32 x2 = window->h_start + window->width - 1; 41 int32 y2 = window->v_start + window->height - 1; 42 43 if (x2 > si.displayMode.timing.h_display) 44 x2 = si.displayMode.timing.h_display; 45 46 if (y2 > si.displayMode.timing.v_display) 47 y2 = si.displayMode.timing.v_display; 48 49 // If window is moved beyond edge of screen, do not allow width < 4 or 50 // height < 4; otherwise there is a possibilty of divide by zero when 51 // computing the scale factors.. 52 if (x2 < x1 + 4) 53 x2 = x1 + 4; 54 55 if (y2 < y1 + 4) 56 y2 = y1 + 4; 57 58 // Calculate overlay scale factors. 59 uint32 horzScale = (buffer->width << 12) / (x2 - x1 + 1); 60 uint32 vertScale = (buffer->height << 12) / (y2 - y1 + 1); 61 62 if (horzScale > 0xffff) // only 16 bits are used for scale factors 63 horzScale = 0xffff; 64 if (vertScale > 0xffff) 65 vertScale = 0xffff; 66 67 gInfo.WaitForFifo(2); 68 OUTREG(BUS_CNTL, INREG(BUS_CNTL) | BUS_EXT_REG_EN); // enable reg block 1 69 OUTREG(OVERLAY_SCALE_CNTL, SCALE_EN); // reset the video 70 71 if (si.chipType >= MACH64_264GTPRO) { 72 const uint32 brightness = 0; 73 const uint32 saturation = 12; 74 75 gInfo.WaitForFifo(6); 76 OUTREG(SCALER_COLOUR_CNTL, brightness | saturation << 8 77 | saturation << 16); 78 OUTREG(SCALER_H_COEFF0, 0x0002000); 79 OUTREG(SCALER_H_COEFF1, 0xd06200d); 80 OUTREG(SCALER_H_COEFF2, 0xd0a1c0d); 81 OUTREG(SCALER_H_COEFF3, 0xc0e1a0c); 82 OUTREG(SCALER_H_COEFF4, 0xc14140c); 83 } 84 85 uint32 keyColor = 0; 86 uint32 keyMask = 0; 87 88 switch (si.displayMode.bitsPerPixel) { 89 case 15: 90 keyMask = 0x7fff; 91 keyColor = (window->blue.value & window->blue.mask) << 0 92 | (window->green.value & window->green.mask) << 5 93 | (window->red.value & window->red.mask) << 10; 94 // 15 bit color has no alpha bits 95 break; 96 case 16: 97 keyMask = 0xffff; 98 keyColor = (window->blue.value & window->blue.mask) << 0 99 | (window->green.value & window->green.mask) << 5 100 | (window->red.value & window->red.mask) << 11; 101 // 16 bit color has no alpha bits 102 break; 103 default: 104 keyMask = 0xffffffff; 105 keyColor = (window->blue.value & window->blue.mask) << 0 106 | (window->green.value & window->green.mask) << 8 107 | (window->red.value & window->red.mask) << 16 108 | (window->alpha.value & window->alpha.mask) << 24; 109 break; 110 } 111 112 gInfo.WaitForFifo(3); 113 OUTREG(OVERLAY_GRAPHICS_KEY_MSK, keyMask); 114 OUTREG(OVERLAY_GRAPHICS_KEY_CLR, keyColor); 115 OUTREG(OVERLAY_KEY_CNTL, OVERLAY_MIX_FALSE | OVERLAY_MIX_EQUAL); 116 117 gInfo.WaitForFifo(8); 118 OUTREG(OVERLAY_Y_X_START, OVERLAY_LOCK_START | (x1 << 16) | y1); 119 OUTREG(OVERLAY_Y_X_END, (x2 << 16) | y2); 120 OUTREG(OVERLAY_SCALE_INC, (horzScale << 16) | vertScale); 121 OUTREG(SCALER_HEIGHT_WIDTH, (buffer->width << 16) | buffer->height); 122 OUTREG(VIDEO_FORMAT, videoFormat); 123 124 // Compute offset of overlay buffer in the video memory. 125 uint32 offset = uint32(buffer->buffer) - si.videoMemAddr; 126 127 if (si.chipType < MACH64_264VTB) { 128 OUTREG(BUF0_OFFSET, offset); 129 OUTREG(BUF0_PITCH, buffer->width); 130 } else { 131 OUTREG(SCALER_BUF0_OFFSET, offset); 132 OUTREG(SCALER_BUF0_PITCH, buffer->width); 133 } 134 135 OUTREG(OVERLAY_SCALE_CNTL, SCALE_PIX_EXPAND | OVERLAY_EN | SCALE_EN); 136 137 return true; 138 } 139 140 141 void 142 Mach64_StopOverlay(void) 143 { 144 OUTREG(OVERLAY_SCALE_CNTL, SCALE_EN); // reset the video 145 } 146