ast_driver.c revision 6c78137b
1/* 2 * Copyright (c) 2005 ASPEED Technology Inc. 3 * 4 * Permission to use, copy, modify, distribute, and sell this software and its 5 * documentation for any purpose is hereby granted without fee, provided that 6 * the above copyright notice appear in all copies and that both that 7 * copyright notice and this permission notice appear in supporting 8 * documentation, and that the name of the authors not be used in 9 * advertising or publicity pertaining to distribution of the software without 10 * specific, written prior permission. The authors makes no representations 11 * about the suitability of this software for any purpose. It is provided 12 * "as is" without express or implied warranty. 13 * 14 * THE AUTHORS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, 15 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO 16 * EVENT SHALL THE AUTHORS BE LIABLE FOR ANY SPECIAL, INDIRECT OR 17 * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, 18 * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER 19 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 20 * PERFORMANCE OF THIS SOFTWARE. 21 */ 22 23#ifdef HAVE_CONFIG_H 24#include <config.h> 25#endif 26#include "xf86.h" 27#include "xf86_OSproc.h" 28#if GET_ABI_MAJOR(ABI_VIDEODRV_VERSION) < 6 29#include "xf86Resources.h" 30#include "xf86RAC.h" 31#endif 32#include "xf86cmap.h" 33#include "compiler.h" 34#include "mibstore.h" 35#include "vgaHW.h" 36#include "mipointer.h" 37#include "micmap.h" 38 39#include "fb.h" 40#include "regionstr.h" 41#include "xf86xv.h" 42#include <X11/extensions/Xv.h> 43#include "vbe.h" 44 45#include "xf86PciInfo.h" 46#include "xf86Pci.h" 47 48/* framebuffer offscreen manager */ 49#include "xf86fbman.h" 50 51/* include xaa includes */ 52#include "xaa.h" 53#include "xaarop.h" 54 55/* H/W cursor support */ 56#include "xf86Cursor.h" 57 58/* Driver specific headers */ 59#include "ast.h" 60 61/* external reference fucntion */ 62extern Bool ASTMapMem(ScrnInfoPtr pScrn); 63extern Bool ASTUnmapMem(ScrnInfoPtr pScrn); 64extern Bool ASTMapMMIO(ScrnInfoPtr pScrn); 65extern void ASTUnmapMMIO(ScrnInfoPtr pScrn); 66 67extern void vASTOpenKey(ScrnInfoPtr pScrn); 68extern Bool bASTRegInit(ScrnInfoPtr pScrn); 69extern void GetDRAMInfo(ScrnInfoPtr pScrn); 70extern ULONG GetVRAMInfo(ScrnInfoPtr pScrn); 71extern ULONG GetMaxDCLK(ScrnInfoPtr pScrn); 72extern void GetChipType(ScrnInfoPtr pScrn); 73extern void vASTLoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices, LOCO *colors, VisualPtr pVisual); 74extern void ASTDisplayPowerManagementSet(ScrnInfoPtr pScrn, int PowerManagementMode, int flags); 75extern void vSetStartAddressCRT1(ASTRecPtr pAST, ULONG base); 76extern Bool ASTSetMode(ScrnInfoPtr pScrn, DisplayModePtr mode); 77extern Bool GetVGA2EDID(ScrnInfoPtr pScrn, unsigned char *pEDIDBuffer); 78extern void vInitDRAMReg(ScrnInfoPtr pScrn); 79extern Bool bIsVGAEnabled(ScrnInfoPtr pScrn); 80extern void ASTBlankScreen(ScrnInfoPtr pScreen, Bool unblack); 81extern Bool InitVGA(ScrnInfoPtr pScrn, ULONG Flags); 82extern Bool GetVGAEDID(ScrnInfoPtr pScrn, unsigned char *pEDIDBuffer); 83extern Bool bInitAST1180(ScrnInfoPtr pScrn); 84extern void GetAST1180DRAMInfo(ScrnInfoPtr pScrn); 85 86extern Bool bInitCMDQInfo(ScrnInfoPtr pScrn, ASTRecPtr pAST); 87extern Bool bEnableCMDQ(ScrnInfoPtr pScrn, ASTRecPtr pAST); 88extern void vDisable2D(ScrnInfoPtr pScrn, ASTRecPtr pAST); 89 90extern Bool ASTAccelInit(ScreenPtr pScreen); 91 92extern Bool ASTCursorInit(ScreenPtr pScreen); 93extern void ASTDisableHWC(ScrnInfoPtr pScrn); 94 95/* Mandatory functions */ 96static void ASTIdentify(int flags); 97const OptionInfoRec *ASTAvailableOptions(int chipid, int busid); 98static Bool ASTProbe(DriverPtr drv, int flags); 99static Bool ASTPreInit(ScrnInfoPtr pScrn, int flags); 100static Bool ASTScreenInit(int Index, ScreenPtr pScreen, int argc, char **argv); 101Bool ASTSwitchMode(int scrnIndex, DisplayModePtr mode, int flags); 102void ASTAdjustFrame(int scrnIndex, int x, int y, int flags); 103static Bool ASTEnterVT(int scrnIndex, int flags); 104static void ASTLeaveVT(int scrnIndex, int flags); 105static void ASTFreeScreen(int scrnIndex, int flags); 106static ModeStatus ASTValidMode(int scrnIndex, DisplayModePtr mode, Bool verbose, int flags); 107 108/* Internally used functions */ 109static Bool ASTGetRec(ScrnInfoPtr pScrn); 110static void ASTFreeRec(ScrnInfoPtr pScrn); 111static Bool ASTSaveScreen(ScreenPtr pScreen, Bool unblack); 112static Bool ASTCloseScreen(int scrnIndex, ScreenPtr pScreen); 113static void ASTSave(ScrnInfoPtr pScrn); 114static void ASTRestore(ScrnInfoPtr pScrn); 115static void ASTProbeDDC(ScrnInfoPtr pScrn, int index); 116static xf86MonPtr ASTDoDDC(ScrnInfoPtr pScrn, int index); 117static void vFillASTModeInfo (ScrnInfoPtr pScrn); 118static Bool ASTModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode); 119 120#ifdef AstVideo 121/* video function */ 122static void ASTInitVideo(ScreenPtr pScreen); 123static int ASTPutImage( ScrnInfoPtr, 124 short, short, short, short, short, short, short, short, 125 int, unsigned char*, short, short, Bool, RegionPtr, pointer, 126 DrawablePtr); 127#endif 128 129/* 130 * This is intentionally screen-independent. It indicates the binding 131 * choice made in the first PreInit. 132 */ 133_X_EXPORT DriverRec AST = { 134 AST_VERSION, 135 AST_DRIVER_NAME, 136 ASTIdentify, 137 ASTProbe, 138 ASTAvailableOptions, 139 NULL, 140 0 141}; 142 143/* Chipsets */ 144static SymTabRec ASTChipsets[] = { 145 {PCI_CHIP_AST2000, "ASPEED Graphics Family"}, 146 {PCI_CHIP_AST2100, "ASPEED Graphics Family"}, 147 {PCI_CHIP_AST1180, "ASPEED AST1180 Graphics"}, 148 {-1, NULL} 149}; 150 151static PciChipsets ASTPciChipsets[] = { 152 {PCI_CHIP_AST2000, PCI_CHIP_AST2000, RES_SHARED_VGA}, 153 {PCI_CHIP_AST2100, PCI_CHIP_AST2100, RES_SHARED_VGA}, 154 {PCI_CHIP_AST1180, PCI_CHIP_AST1180, RES_SHARED_VGA}, 155 {-1, -1, RES_UNDEFINED } 156}; 157 158typedef enum { 159 OPTION_NOACCEL, 160 OPTION_MMIO2D, 161 OPTION_SW_CURSOR, 162 OPTION_HWC_NUM, 163 OPTION_ENG_CAPS, 164 OPTION_DBG_SELECT, 165 OPTION_NO_DDC, 166 OPTION_VGA2_CLONE 167} ASTOpts; 168 169static const OptionInfoRec ASTOptions[] = { 170 {OPTION_NOACCEL, "NoAccel", OPTV_BOOLEAN, {0}, FALSE}, 171 {OPTION_MMIO2D, "MMIO2D", OPTV_BOOLEAN, {0}, FALSE}, 172 {OPTION_SW_CURSOR, "SWCursor", OPTV_BOOLEAN, {0}, FALSE}, 173 {OPTION_HWC_NUM, "HWCNumber", OPTV_INTEGER, {0}, FALSE}, 174 {OPTION_ENG_CAPS, "ENGCaps", OPTV_INTEGER, {0}, FALSE}, 175 {OPTION_DBG_SELECT, "DBGSelect", OPTV_INTEGER, {0}, FALSE}, 176 {OPTION_NO_DDC, "NoDDC", OPTV_BOOLEAN, {0}, FALSE}, 177 {OPTION_VGA2_CLONE, "VGA2Clone", OPTV_BOOLEAN, {0}, FALSE}, 178 {-1, NULL, OPTV_NONE, {0}, FALSE} 179}; 180 181#ifdef XFree86LOADER 182 183static MODULESETUPPROTO(astSetup); 184 185static XF86ModuleVersionInfo astVersRec = { 186 AST_DRIVER_NAME, 187 MODULEVENDORSTRING, 188 MODINFOSTRING1, 189 MODINFOSTRING2, 190 XORG_VERSION_CURRENT, 191 AST_MAJOR_VERSION, AST_MINOR_VERSION, AST_PATCH_VERSION, 192 ABI_CLASS_VIDEODRV, 193#ifdef PATCH_ABI_VERSION 194 ABI_VIDEODRV_VERSION_PATCH, 195#else 196 ABI_VIDEODRV_VERSION, 197#endif 198 MOD_CLASS_VIDEODRV, 199 {0, 0, 0, 0} 200}; 201 202_X_EXPORT XF86ModuleData astModuleData = { &astVersRec, astSetup, NULL }; 203 204static pointer 205astSetup(pointer module, pointer opts, int *errmaj, int *errmin) 206{ 207 static Bool setupDone = FALSE; 208 209 /* This module should be loaded only once, but check to be sure. 210 */ 211 if (!setupDone) { 212 setupDone = TRUE; 213 xf86AddDriver(&AST, module, 0); 214 215 /* 216 * The return value must be non-NULL on success even though there 217 * is no TearDownProc. 218 */ 219 return (pointer) TRUE; 220 } else { 221 if (errmaj) 222 *errmaj = LDR_ONCEONLY; 223 return NULL; 224 } 225} 226 227#endif /* XFree86LOADER */ 228 229/* 230 * ASTIdentify -- 231 * 232 * Returns the string name for the driver based on the chipset. In this 233 * case it will always be an AST, so we can return a static string. 234 * 235 */ 236static void 237ASTIdentify(int flags) 238{ 239 xf86PrintChipsets(AST_NAME, "Driver for ASPEED Graphics Chipsets", 240 ASTChipsets); 241} 242 243const OptionInfoRec * 244ASTAvailableOptions(int chipid, int busid) 245{ 246 247 return ASTOptions; 248 249} 250 251/* 252 * ASTProbe -- 253 * 254 * Look through the PCI bus to find cards that are AST boards. 255 * Setup the dispatch table for the rest of the driver functions. 256 * 257 */ 258static Bool 259ASTProbe(DriverPtr drv, int flags) 260{ 261 int i, numUsed, numDevSections, *usedChips; 262 Bool foundScreen = FALSE; 263 GDevPtr *devSections; 264 265 /* 266 * Find the config file Device sections that match this 267 * driver, and return if there are none. 268 */ 269 if ((numDevSections = 270 xf86MatchDevice(AST_DRIVER_NAME, &devSections)) <= 0) { 271 return FALSE; 272 } 273 274#ifndef XSERVER_LIBPCIACCESS 275 /* 276 * This probing is just checking the PCI data the server already 277 * collected. 278 */ 279 if (xf86GetPciVideoInfo() == NULL) { 280 return FALSE; 281 } 282#endif 283 284 numUsed = xf86MatchPciInstances(AST_NAME, PCI_VENDOR_AST, 285 ASTChipsets, ASTPciChipsets, 286 devSections, numDevSections, 287 drv, &usedChips); 288 289 free(devSections); 290 291 if (flags & PROBE_DETECT) { 292 if (numUsed > 0) 293 foundScreen = TRUE; 294 } else { 295 for (i = 0; i < numUsed; i++) { 296 ScrnInfoPtr pScrn = NULL; 297 298 /* Allocate new ScrnInfoRec and claim the slot */ 299 if ((pScrn = xf86ConfigPciEntity(pScrn, 0, usedChips[i], 300 ASTPciChipsets, 0, 0, 0, 0, 0))) 301 { 302 EntityInfoPtr pEnt; 303 304 pEnt = xf86GetEntityInfo(usedChips[i]); 305 306 pScrn->driverVersion = AST_VERSION; 307 pScrn->driverName = AST_DRIVER_NAME; 308 pScrn->name = AST_NAME; 309 310 pScrn->Probe = ASTProbe; 311 pScrn->PreInit = ASTPreInit; 312 pScrn->ScreenInit = ASTScreenInit; 313 pScrn->SwitchMode = ASTSwitchMode; 314 pScrn->AdjustFrame = ASTAdjustFrame; 315 pScrn->EnterVT = ASTEnterVT; 316 pScrn->LeaveVT = ASTLeaveVT; 317 pScrn->FreeScreen = ASTFreeScreen; 318 pScrn->ValidMode = ASTValidMode; 319 320 foundScreen = TRUE; 321 322 } /* end of if */ 323 } /* end of for-loop */ 324 } /* end of if flags */ 325 326 free(usedChips); 327 328 return foundScreen; 329} 330 331/* 332 * ASTPreInit -- 333 * 334 * Do initial setup of the board before we know what resolution we will 335 * be running at. 336 * 337 */ 338static Bool 339ASTPreInit(ScrnInfoPtr pScrn, int flags) 340{ 341 EntityInfoPtr pEnt; 342 vgaHWPtr hwp; 343 int flags24; 344 rgb defaultWeight = { 0, 0, 0 }; 345 346 ASTRecPtr pAST; 347 348 ClockRangePtr clockRanges; 349 int i; 350 MessageType from; 351 int maxPitch, maxHeight; 352 353 /* Suport one adapter only now */ 354 if (pScrn->numEntities != 1) 355 return FALSE; 356 357 pEnt = xf86GetEntityInfo(pScrn->entityList[0]); 358 359 if (flags & PROBE_DETECT) { 360 ASTProbeDDC(pScrn, pEnt->index); 361 return TRUE; 362 } 363 364 if (pEnt->location.type != BUS_PCI) 365 return FALSE; 366 367#ifndef XSERVER_LIBPCIACCESS 368 if (xf86RegisterResources(pEnt->index, 0, ResExclusive)) 369 return FALSE; 370#endif 371 372 /* The vgahw module should be loaded here when needed */ 373 if (!xf86LoadSubModule(pScrn, "vgahw")) 374 return FALSE; 375 376 /* The fb module should be loaded here when needed */ 377 if (!xf86LoadSubModule(pScrn, "fb")) 378 return FALSE; 379 380 /* Allocate a vgaHWRec */ 381 if (!vgaHWGetHWRec(pScrn)) 382 return FALSE; 383 hwp = VGAHWPTR(pScrn); 384 385 /* Color Depth Check */ 386 flags24 = Support32bppFb; 387 if (!xf86SetDepthBpp(pScrn, 0, 0, 0, flags24)) { 388 return FALSE; 389 } else { 390 switch (pScrn->depth) { 391 case 8: 392 case 16: 393 case 24: 394 break; 395 default: 396 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, 397 "Given depth (%d) is not supported by ast driver\n", 398 pScrn->depth); 399 return FALSE; 400 } 401 } 402 xf86PrintDepthBpp(pScrn); 403 404 switch (pScrn->bitsPerPixel) { 405 case 8: 406 case 16: 407 case 32: 408 break; 409 default: 410 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, 411 "Given bpp (%d) is not supported by ast driver\n", 412 pScrn->bitsPerPixel); 413 return FALSE; 414 } 415 416 /* fill pScrn misc. */ 417 pScrn->progClock = TRUE; 418 pScrn->rgbBits = 6; 419 pScrn->monitor = pScrn->confScreen->monitor; /* should be initialized before set gamma */ 420#ifndef XSERVER_LIBPCIACCESS 421 pScrn->racMemFlags = RAC_FB | RAC_COLORMAP | RAC_CURSOR | RAC_VIEWPORT; 422 pScrn->racIoFlags = RAC_COLORMAP | RAC_CURSOR | RAC_VIEWPORT; 423#endif 424 425 /* 426 * If the driver can do gamma correction, it should call xf86SetGamma() 427 * here. 428 */ 429 { 430 Gamma zeros = { 0.0, 0.0, 0.0 }; 431 432 if (!xf86SetGamma(pScrn, zeros)) { 433 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "call xf86SetGamma failed \n"); 434 return FALSE; 435 } 436 } 437 438 439 if (!xf86SetWeight(pScrn, defaultWeight, defaultWeight)) { 440 return FALSE; 441 } 442 443 if (!xf86SetDefaultVisual(pScrn, -1)) { 444 return FALSE; 445 } 446 447 /* Allocate driverPrivate */ 448 if (!ASTGetRec(pScrn)) { 449 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "call ASTGetRec failed \n"); 450 return FALSE; 451 } 452 453 /* Fill AST Info */ 454 pAST = ASTPTR(pScrn); 455 pAST->pEnt = xf86GetEntityInfo(pScrn->entityList[0]); 456 pAST->PciInfo = xf86GetPciInfoForEntity(pAST->pEnt->index); 457#ifndef XSERVER_LIBPCIACCESS 458 pAST->PciTag = pciTag(pAST->PciInfo->bus, pAST->PciInfo->device, 459 pAST->PciInfo->func); 460#endif 461 462 /* Process the options 463 * pScrn->confScreen, pScrn->display, pScrn->monitor, pScrn->numEntities, 464 * and pScrn->entityList should be initialized before 465 */ 466 xf86CollectOptions(pScrn, NULL); 467 if (!(pAST->Options = malloc(sizeof(ASTOptions)))) 468 { 469 ASTFreeRec(pScrn); 470 return FALSE; 471 } 472 memcpy(pAST->Options, ASTOptions, sizeof(ASTOptions)); 473 xf86ProcessOptions(pScrn->scrnIndex, pScrn->options, pAST->Options); 474 475 /* 476 * Set the Chipset and ChipRev, allowing config file entries to 477 * override. 478 */ 479 if (pAST->pEnt->device->chipset && *pAST->pEnt->device->chipset) { 480 pScrn->chipset = pAST->pEnt->device->chipset; 481 from = X_CONFIG; 482 } else if (pAST->pEnt->device->chipID >= 0) { 483 pScrn->chipset = (char *)xf86TokenToString(ASTChipsets, 484 pAST->pEnt->device->chipID); 485 from = X_CONFIG; 486 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "ChipID override: 0x%04X\n", 487 pAST->pEnt->device->chipID); 488 } else { 489 from = X_PROBED; 490 pScrn->chipset = (char *)xf86TokenToString(ASTChipsets, 491 PCI_DEV_DEVICE_ID(pAST->PciInfo)); 492 } 493 if (pAST->pEnt->device->chipRev >= 0) { 494 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "ChipRev override: %d\n", 495 pAST->pEnt->device->chipRev); 496 } 497 498 xf86DrvMsg(pScrn->scrnIndex, from, "Chipset: \"%s\"\n", 499 (pScrn->chipset != NULL) ? pScrn->chipset : "Unknown ast"); 500 501 /* Resource Allocation */ 502 pAST->IODBase = pScrn->domainIOBase; 503 /* "Patch" the PIOOffset inside vgaHW in order to force 504 * the vgaHW module to use our relocated i/o ports. 505 */ 506 VGAHWPTR(pScrn)->PIOOffset = pAST->PIOOffset = pAST->IODBase + PCI_REGION_BASE(pAST->PciInfo, 2, REGION_IO) - 0x380; 507 508 pAST->RelocateIO = (IOADDRESS)(PCI_REGION_BASE(pAST->PciInfo, 2, REGION_IO) + pAST->IODBase); 509 510 if (pAST->pEnt->device->MemBase != 0) { 511 pAST->FBPhysAddr = pAST->pEnt->device->MemBase; 512 from = X_CONFIG; 513 } else { 514 if (PCI_REGION_BASE(pAST->PciInfo, 0, REGION_MEM) != 0) { 515 pAST->FBPhysAddr = PCI_REGION_BASE(pAST->PciInfo, 0, REGION_MEM) & 0xFFF00000; 516 from = X_PROBED; 517 } else { 518 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, 519 "No valid FB address in PCI config space\n"); 520 ASTFreeRec(pScrn); 521 return FALSE; 522 } 523 } 524 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Linear framebuffer at 0x%lX\n", 525 (unsigned long) pAST->FBPhysAddr); 526 527 if (pAST->pEnt->device->IOBase != 0) { 528 pAST->MMIOPhysAddr = pAST->pEnt->device->IOBase; 529 from = X_CONFIG; 530 } else { 531 if (PCI_REGION_BASE(pAST->PciInfo, 1, REGION_MEM)) { 532 pAST->MMIOPhysAddr = PCI_REGION_BASE(pAST->PciInfo, 1, REGION_MEM) & 0xFFFF0000; 533 from = X_PROBED; 534 } else { 535 xf86DrvMsg(pScrn->scrnIndex, X_INFO, 536 "No valid MMIO address in PCI config space\n"); 537 ASTFreeRec(pScrn); 538 return FALSE; 539 } 540 } 541 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "IO registers at addr 0x%lX\n", 542 (unsigned long) pAST->MMIOPhysAddr); 543 544 /* Map MMIO */ 545 pAST->MMIOMapSize = DEFAULT_MMIO_SIZE; 546 if (!ASTMapMMIO(pScrn)) { 547 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Map Memory Map IO Failed \n"); 548 return FALSE; 549 } 550 551 if (PCI_DEV_DEVICE_ID(pAST->PciInfo) == PCI_CHIP_AST1180) 552 { 553 pAST->jChipType = AST1180; 554 555 /* validate mode */ 556 if ( (pScrn->bitsPerPixel == 8) || (pScrn->depth == 8) ) 557 { 558 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, 559 "Given bpp (%d) is not supported by ast driver\n", 560 pScrn->bitsPerPixel); 561 return FALSE; 562 } 563 564 /* Init AST1180 */ 565 bInitAST1180(pScrn); 566 567 /* Get AST1180 Information */ 568 GetAST1180DRAMInfo(pScrn); 569 pScrn->videoRam = pAST->ulVRAMSize / 1024; 570 571 } 572 else 573 { 574 /* Init VGA Adapter */ 575 if (!xf86IsPrimaryPci(pAST->PciInfo)) 576 { 577 InitVGA(pScrn, 0); 578 } 579 580 vASTOpenKey(pScrn); 581 bASTRegInit(pScrn); 582 583 /* Get Chip Type */ 584 if (PCI_DEV_REVISION(pAST->PciInfo) >= 0x20) 585 pAST->jChipType = AST2300; 586 else if (PCI_DEV_REVISION(pAST->PciInfo) >= 0x10) 587 GetChipType(pScrn); 588 else 589 pAST->jChipType = AST2000; 590 591 /* Get DRAM Info */ 592 GetDRAMInfo(pScrn); 593 pAST->ulVRAMSize = GetVRAMInfo(pScrn); 594 pScrn->videoRam = pAST->ulVRAMSize / 1024; 595 } 596 597 /* Map Framebuffer */ 598 from = X_DEFAULT; 599 if (pAST->pEnt->device->videoRam) { 600 pScrn->videoRam = pAST->pEnt->device->videoRam; 601 from = X_CONFIG; 602 } 603 604 pAST->FbMapSize = pScrn->videoRam * 1024; 605 606#if 0 607 if (!ASTMapMem(pScrn)) { 608 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Map FB Memory Failed \n"); 609 return FALSE; 610 } 611#endif 612 613 pScrn->memPhysBase = (ULONG)pAST->FBPhysAddr; 614 pScrn->fbOffset = 0; 615 616 /* Do DDC 617 * should be done after xf86CollectOptions 618 */ 619 pScrn->monitor->DDC = ASTDoDDC(pScrn, pAST->pEnt->index); 620 621 /* Mode Valid */ 622 clockRanges = xnfcalloc(sizeof(ClockRange), 1); 623 clockRanges->next = NULL; 624 clockRanges->minClock = 9500; 625 clockRanges->maxClock = GetMaxDCLK(pScrn) * 1000; 626 clockRanges->clockIndex = -1; 627 clockRanges->interlaceAllowed = FALSE; 628 clockRanges->doubleScanAllowed = FALSE; 629 630 /* Add for AST2100, ycchen@061807 */ 631 if ((pAST->jChipType == AST2100) || (pAST->jChipType == AST2200) || (pAST->jChipType == AST2300) || (pAST->jChipType == AST1180)) 632 { 633 maxPitch = 1920; 634 maxHeight = 1200; 635 } 636 else 637 { 638 maxPitch = 1600; 639 maxHeight = 1200; 640 } 641 642 i = xf86ValidateModes(pScrn, pScrn->monitor->Modes, 643 pScrn->display->modes, clockRanges, 644 0, 320, maxPitch, 8 * pScrn->bitsPerPixel, 645 200, maxHeight, 646 pScrn->display->virtualX, pScrn->display->virtualY, 647 pAST->FbMapSize, LOOKUP_BEST_REFRESH); 648 649 /* fixed some monitors can't get propery validate modes using estimated ratio modes */ 650 if (i < 2) /* validate modes are too few */ 651 { 652 i = xf86ValidateModes(pScrn, pScrn->monitor->Modes, 653 pScrn->display->modes, clockRanges, 654 0, 320, maxPitch, 8 * pScrn->bitsPerPixel, 655 200, maxHeight, 656 pAST->mon_h_active, pAST->mon_v_active, 657 pAST->FbMapSize, LOOKUP_BEST_REFRESH); 658 } 659 660 if (i == -1) { 661 ASTFreeRec(pScrn); 662 return FALSE; 663 } 664 665 xf86PruneDriverModes(pScrn); 666 667 if (!i || !pScrn->modes) { 668 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "No valid modes found\n"); 669 ASTFreeRec(pScrn); 670 return FALSE; 671 } 672 673 xf86SetCrtcForModes(pScrn, INTERLACE_HALVE_V); 674 675 pScrn->currentMode = pScrn->modes; 676 677 xf86PrintModes(pScrn); 678 679 xf86SetDpi(pScrn, 0, 0); 680 681 /* Accelaration Check */ 682 pAST->noAccel = TRUE; 683 pAST->AccelInfoPtr = NULL; 684 pAST->pCMDQPtr = NULL; 685 pAST->CMDQInfo.ulCMDQSize = 0; 686#ifdef Accel_2D 687 if (!xf86ReturnOptValBool(pAST->Options, OPTION_NOACCEL, FALSE)) 688 { 689 if (!xf86LoadSubModule(pScrn, "xaa")) { 690 ASTFreeRec(pScrn); 691 return FALSE; 692 } 693 694 pAST->noAccel = FALSE; 695 696 pAST->MMIO2D = TRUE; 697#ifndef MMIO_2D 698 if (!xf86ReturnOptValBool(pAST->Options, OPTION_MMIO2D, FALSE)) { 699 pAST->CMDQInfo.ulCMDQSize = DEFAULT_CMDQ_SIZE; 700 pAST->MMIO2D = FALSE; 701 } 702#endif 703 704 pAST->ENGCaps = ENG_CAP_ALL; 705 if (!xf86GetOptValInteger(pAST->Options, OPTION_ENG_CAPS, &pAST->ENGCaps)) { 706 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "No ENG Capability options found\n"); 707 } 708 709 pAST->DBGSelect = 0; 710 if (!xf86GetOptValInteger(pAST->Options, OPTION_DBG_SELECT, &pAST->DBGSelect)) { 711 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "No DBG Seleclt options found\n"); 712 } 713 } 714#endif 715 716 /* HW Cursor Check */ 717 pAST->noHWC = TRUE; 718 pAST->HWCInfoPtr = NULL; 719 pAST->pHWCPtr = NULL; 720#ifdef HWC 721 if (!xf86ReturnOptValBool(pAST->Options, OPTION_SW_CURSOR, FALSE)) { 722 if (!xf86LoadSubModule(pScrn, "ramdac")) { 723 ASTFreeRec(pScrn); 724 return FALSE; 725 } 726 727 pAST->noHWC = FALSE; 728 pAST->HWCInfo.HWC_NUM = DEFAULT_HWC_NUM; 729 if (!xf86GetOptValInteger(pAST->Options, OPTION_HWC_NUM, &pAST->HWCInfo.HWC_NUM)) { 730 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "No HWC_NUM options found\n"); 731 } 732 733 } 734#endif 735 736#ifndef XSERVER_LIBPCIACCESS 737 /* We won't be using the VGA access after the probe */ 738 xf86SetOperatingState(resVgaIo, pAST->pEnt->index, ResUnusedOpr); 739 xf86SetOperatingState(resVgaMem, pAST->pEnt->index, ResDisableOpr); 740#endif 741 742 return TRUE; 743} 744 745 746static Bool 747ASTScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv) 748{ 749 ScrnInfoPtr pScrn; 750 ASTRecPtr pAST; 751 vgaHWPtr hwp; 752 VisualPtr visual; 753 754 /* for FB Manager */ 755 BoxRec FBMemBox; 756 int AvailFBSize; 757 758 pScrn = xf86Screens[pScreen->myNum]; 759 pAST = ASTPTR(pScrn); 760 hwp = VGAHWPTR(pScrn); 761 762 if (!ASTMapMem(pScrn)) { 763 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Map FB Memory Failed \n"); 764 return FALSE; 765 } 766 767/* if (!pAST->noAccel) */ 768 { 769 /* AvailFBSize = pAST->FbMapSize - pAST->CMDQInfo.ulCMDQSize; */ 770 AvailFBSize = pAST->FbMapSize; 771 772 FBMemBox.x1 = 0; 773 FBMemBox.y1 = 0; 774 FBMemBox.x2 = pScrn->displayWidth; 775 FBMemBox.y2 = (AvailFBSize / (pScrn->displayWidth * ((pScrn->bitsPerPixel+1)/8))) - 1; 776 777 if (FBMemBox.y2 < 0) 778 FBMemBox.y2 = 32767; 779 if (FBMemBox.y2 < pScrn->virtualY) 780 return FALSE; 781 782 if (!xf86InitFBManager(pScreen, &FBMemBox)) { 783 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to init memory manager\n"); 784 return FALSE; 785 } 786 787 } 788 789 vgaHWGetIOBase(hwp); 790 791 vFillASTModeInfo (pScrn); 792 793 ASTSave(pScrn); 794 if (!ASTModeInit(pScrn, pScrn->currentMode)) { 795 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Mode Init Failed \n"); 796 return FALSE; 797 } 798 799 ASTSaveScreen(pScreen, FALSE); 800 ASTAdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0); 801 802 miClearVisualTypes(); 803 804 /* Re-implemented Direct Color support, -jens */ 805 if (!miSetVisualTypes(pScrn->depth, miGetDefaultVisualMask(pScrn->depth), 806 pScrn->rgbBits, pScrn->defaultVisual)) 807 return FALSE; 808 809 if (!miSetPixmapDepths()) 810 { 811 ASTSaveScreen(pScreen, SCREEN_SAVER_OFF); 812 return FALSE; 813 } 814 815 switch(pScrn->bitsPerPixel) { 816 case 8: 817 case 16: 818 case 32: 819 if (!fbScreenInit(pScreen, pAST->FBVirtualAddr + pScrn->fbOffset, 820 pScrn->virtualX, pScrn->virtualY, 821 pScrn->xDpi, pScrn->yDpi, 822 pScrn->displayWidth, pScrn->bitsPerPixel)) 823 return FALSE; 824 break; 825 default: 826 return FALSE; 827 828 } 829 830 if (pScrn->bitsPerPixel > 8) { 831 /* Fixup RGB ordering */ 832 visual = pScreen->visuals + pScreen->numVisuals; 833 while (--visual >= pScreen->visuals) { 834 if ((visual->class | DynamicClass) == DirectColor) { 835 visual->offsetRed = pScrn->offset.red; 836 visual->offsetGreen = pScrn->offset.green; 837 visual->offsetBlue = pScrn->offset.blue; 838 visual->redMask = pScrn->mask.red; 839 visual->greenMask = pScrn->mask.green; 840 visual->blueMask = pScrn->mask.blue; 841 } 842 } 843 } 844 845 fbPictureInit(pScreen, 0, 0); 846 847 xf86SetBlackWhitePixels(pScreen); 848 849#ifdef Accel_2D 850 if (!pAST->noAccel) 851 { 852 if (!ASTAccelInit(pScreen)) { 853 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,"Hardware acceleration initialization failed\n"); 854 pAST->noAccel = TRUE; 855 } 856 } 857#endif /* end of Accel_2D */ 858 859 miInitializeBackingStore(pScreen); 860 xf86SetBackingStore(pScreen); 861 xf86SetSilkenMouse(pScreen); 862 863 miDCInitialize(pScreen, xf86GetPointerScreenFuncs()); 864 865 if (!pAST->noHWC) 866 { 867 if (!ASTCursorInit(pScreen)) { 868 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,"Hardware cursor initialization failed\n"); 869 pAST->noHWC = TRUE; 870 } 871 } 872 873 if (!miCreateDefColormap(pScreen)) 874 return FALSE; 875 876 if (pAST->jChipType != AST1180) 877 { 878 if(!xf86HandleColormaps(pScreen, 256, (pScrn->depth == 8) ? 8 : pScrn->rgbBits, 879 vASTLoadPalette, NULL, 880 CMAP_PALETTED_TRUECOLOR | CMAP_RELOAD_ON_MODE_SWITCH)) { 881 return FALSE; 882 } 883 } 884 885 xf86DPMSInit(pScreen, ASTDisplayPowerManagementSet, 0); 886 887#ifdef AstVideo 888 if ( (pAST->jChipType == AST1180) || (pAST->jChipType == AST2300) ) 889 { 890 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"AST Initial Video()\n"); 891 ASTInitVideo(pScreen); 892 } 893#endif 894 895 pScreen->SaveScreen = ASTSaveScreen; 896 pAST->CloseScreen = pScreen->CloseScreen; 897 pScreen->CloseScreen = ASTCloseScreen; 898 899 if (serverGeneration == 1) 900 xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options); 901 902 return TRUE; 903 904} /* ASTScreenInit */ 905 906 907Bool 908ASTSwitchMode(int scrnIndex, DisplayModePtr mode, int flags) 909{ 910 ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; 911 ASTRecPtr pAST = ASTPTR(pScrn); 912 913 /* VideoMode validate */ 914 if (mode->CrtcHDisplay > pScrn->displayWidth) 915 return FALSE; 916 if ((pAST->VideoModeInfo.ScreenPitch * mode->CrtcVDisplay) > pAST->ulVRAMSize) 917 return FALSE; 918 919 /* VideModeInfo Update */ 920 pAST->VideoModeInfo.ScreenWidth = mode->CrtcHDisplay; 921 pAST->VideoModeInfo.ScreenHeight = mode->CrtcVDisplay; 922 pAST->VideoModeInfo.ScreenPitch = pScrn->displayWidth * ((pScrn->bitsPerPixel + 1) / 8) ; 923 924#ifdef HWC 925 if (pAST->pHWCPtr) { 926 xf86FreeOffscreenLinear(pAST->pHWCPtr); /* free HWC Cache */ 927 pAST->pHWCPtr = NULL; 928 } 929 ASTDisableHWC(pScrn); 930#endif 931 932#ifdef Accel_2D 933 if (pAST->pCMDQPtr) { 934 xf86FreeOffscreenLinear(pAST->pCMDQPtr); /* free CMDQ */ 935 pAST->pCMDQPtr = NULL; 936 } 937 vDisable2D(pScrn, pAST); 938#endif 939 940 /* Fixed display abnormal on the of the screen if run xvidtune, ycchen@122909 */ 941 /* ASTRestore(pScrn); */ 942 943 return ASTModeInit(pScrn, mode); 944 945} 946 947void 948ASTAdjustFrame(int scrnIndex, int x, int y, int flags) 949{ 950 ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; 951 ASTRecPtr pAST = ASTPTR(pScrn); 952 ULONG base; 953 954 base = y * pAST->VideoModeInfo.ScreenPitch + x * ((pAST->VideoModeInfo.bitsPerPixel + 1) / 8); 955 /* base = base >> 2; */ /* DW unit */ 956 957 vSetStartAddressCRT1(pAST, base); 958 959} 960 961/* enter into X Server */ 962static Bool 963ASTEnterVT(int scrnIndex, int flags) 964{ 965 ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; 966 ASTRecPtr pAST = ASTPTR(pScrn); 967 968 /* Fixed suspend can't resume issue */ 969 if (!bIsVGAEnabled(pScrn)) 970 { 971 if (pAST->jChipType == AST1180) 972 bInitAST1180(pScrn); 973 else 974 InitVGA(pScrn, 1); 975 ASTRestore(pScrn); 976 } 977 978 if (!ASTModeInit(pScrn, pScrn->currentMode)) 979 return FALSE; 980 ASTAdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0); 981 982 return TRUE; 983 984} 985 986/* leave X server */ 987static void 988ASTLeaveVT(int scrnIndex, int flags) 989{ 990 991 ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; 992 ASTRecPtr pAST = ASTPTR(pScrn); 993 vgaHWPtr hwp = VGAHWPTR(pScrn); 994 995#ifdef HWC 996 if (pAST->pHWCPtr) { 997 xf86FreeOffscreenLinear(pAST->pHWCPtr); /* free HWC Cache */ 998 pAST->pHWCPtr = NULL; 999 } 1000 ASTDisableHWC(pScrn); 1001#endif 1002 1003#ifdef Accel_2D 1004 if (pAST->pCMDQPtr) { 1005 xf86FreeOffscreenLinear(pAST->pCMDQPtr); /* free CMDQ */ 1006 pAST->pCMDQPtr = NULL; 1007 } 1008 vDisable2D(pScrn, pAST); 1009#endif 1010 1011 ASTRestore(pScrn); 1012 1013 if (pAST->jChipType == AST1180) 1014 ASTBlankScreen(pScrn, 0); 1015 1016 vgaHWLock(hwp); 1017 1018} 1019 1020static void 1021ASTFreeScreen(int scrnIndex, int flags) 1022{ 1023 ASTFreeRec(xf86Screens[scrnIndex]); 1024 if (xf86LoaderCheckSymbol("vgaHWFreeHWRec")) 1025 vgaHWFreeHWRec(xf86Screens[scrnIndex]); 1026} 1027 1028static ModeStatus 1029ASTValidMode(int scrnIndex, DisplayModePtr mode, Bool verbose, int flags) 1030{ 1031 1032 ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; 1033 ASTRecPtr pAST = ASTPTR(pScrn); 1034 ModeStatus Flags = MODE_NOMODE; 1035 UCHAR jReg; 1036 ULONG RequestBufferSize; 1037 1038 if (mode->Flags & V_INTERLACE) { 1039 if (verbose) { 1040 xf86DrvMsg(scrnIndex, X_PROBED, 1041 "Removing interlaced mode \"%s\"\n", mode->name); 1042 } 1043 return MODE_NO_INTERLACE; 1044 } 1045 1046 if ((mode->CrtcHDisplay > MAX_HResolution) || (mode->CrtcVDisplay > MAX_VResolution)) { 1047 if (verbose) { 1048 xf86DrvMsg(scrnIndex, X_PROBED, 1049 "Removing the mode \"%s\"\n", mode->name); 1050 } 1051 return Flags; 1052 } 1053 1054 /* Valid Framebuffer size */ 1055 RequestBufferSize = mode->CrtcHDisplay * ((pScrn->bitsPerPixel + 1) / 8) * mode->CrtcVDisplay; 1056 if (RequestBufferSize > pAST->ulVRAMSize) 1057 return Flags; 1058 1059 /* Check BMC scratch for iKVM compatible */ 1060 if (pAST->jChipType == AST2000) 1061 jReg = 0x80; 1062 else if (pAST->jChipType == AST1180) 1063 jReg = 0x01; 1064 else 1065 { 1066 GetIndexRegMask(CRTC_PORT, 0xD0, 0xFF, jReg); 1067 } 1068 1069 if ( !(jReg & 0x80) || (jReg & 0x01) ) 1070 { 1071 if ( (mode->CrtcHDisplay == 1680) && (mode->CrtcVDisplay == 1050) ) 1072 return MODE_OK; 1073 if ( (mode->CrtcHDisplay == 1280) && (mode->CrtcVDisplay == 800) ) 1074 return MODE_OK; 1075 if ( (mode->CrtcHDisplay == 1440) && (mode->CrtcVDisplay == 900) ) 1076 return MODE_OK; 1077 1078 if ( (pAST->jChipType == AST2100) || (pAST->jChipType == AST2200) || (pAST->jChipType == AST2300) || (pAST->jChipType == AST1180) ) 1079 { 1080 if ( (mode->CrtcHDisplay == 1920) && (mode->CrtcVDisplay == 1080) ) 1081 return MODE_OK; 1082 } 1083 } 1084 1085 /* Add for AST2100, ycchen@061807 */ 1086 if ( (pAST->jChipType == AST2100) || (pAST->jChipType == AST2200) || (pAST->jChipType == AST2300) || (pAST->jChipType == AST1180) ) 1087 { 1088 if ( (mode->CrtcHDisplay == 1920) && (mode->CrtcVDisplay == 1200) ) 1089 return MODE_OK; 1090 } 1091 1092 switch (mode->CrtcHDisplay) 1093 { 1094 case 640: 1095 if (mode->CrtcVDisplay == 480) Flags=MODE_OK; 1096 break; 1097 case 800: 1098 if (mode->CrtcVDisplay == 600) Flags=MODE_OK; 1099 break; 1100 case 1024: 1101 if (mode->CrtcVDisplay == 768) Flags=MODE_OK; 1102 break; 1103 case 1280: 1104 if (mode->CrtcVDisplay == 1024) Flags=MODE_OK; 1105 break; 1106 case 1600: 1107 if (mode->CrtcVDisplay == 1200) Flags=MODE_OK; 1108 break; 1109 default: 1110 return Flags; 1111 } 1112 1113 return Flags; 1114} 1115 1116/* Internal used modules */ 1117/* 1118 * ASTGetRec and ASTFreeRec -- 1119 * 1120 * Private data for the driver is stored in the screen structure. 1121 * These two functions create and destroy that private data. 1122 * 1123 */ 1124static Bool 1125ASTGetRec(ScrnInfoPtr pScrn) 1126{ 1127 if (pScrn->driverPrivate) 1128 return TRUE; 1129 1130 pScrn->driverPrivate = xnfcalloc(sizeof(ASTRec), 1); 1131 return TRUE; 1132} 1133 1134static void 1135ASTFreeRec(ScrnInfoPtr pScrn) 1136{ 1137 if (!pScrn) 1138 return; 1139 if (!pScrn->driverPrivate) 1140 return; 1141 free(pScrn->driverPrivate); 1142 pScrn->driverPrivate = 0; 1143} 1144 1145static Bool 1146ASTSaveScreen(ScreenPtr pScreen, Bool unblack) 1147{ 1148 /* replacement of vgaHWBlankScreen(pScrn, unblank) without seq reset */ 1149 /* return vgaHWSaveScreen(pScreen, unblack); */ 1150 ScrnInfoPtr pScrn = NULL; 1151 1152 if (pScreen != NULL) 1153 pScrn = xf86Screens[pScreen->myNum]; 1154 1155 if ((pScrn != NULL) && pScrn->vtSema) { 1156 ASTBlankScreen(pScrn, unblack); 1157 } 1158 return (TRUE); 1159} 1160 1161static Bool 1162ASTCloseScreen(int scrnIndex, ScreenPtr pScreen) 1163{ 1164 ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; 1165 vgaHWPtr hwp = VGAHWPTR(pScrn); 1166 ASTRecPtr pAST = ASTPTR(pScrn); 1167 1168 if (pScrn->vtSema == TRUE) 1169 { 1170#ifdef HWC 1171 if (pAST->pHWCPtr) { 1172 xf86FreeOffscreenLinear(pAST->pHWCPtr); /* free HWC Cache */ 1173 pAST->pHWCPtr = NULL; 1174 } 1175 ASTDisableHWC(pScrn); 1176#endif 1177 1178#ifdef Accel_2D 1179 if (pAST->pCMDQPtr) { 1180 xf86FreeOffscreenLinear(pAST->pCMDQPtr); /* free CMDQ */ 1181 pAST->pCMDQPtr = NULL; 1182 } 1183 vDisable2D(pScrn, pAST); 1184#endif 1185 1186 ASTRestore(pScrn); 1187 1188 if (pAST->jChipType == AST1180) 1189 ASTBlankScreen(pScrn, 0); 1190 1191 vgaHWLock(hwp); 1192 } 1193 1194 ASTUnmapMem(pScrn); 1195 vgaHWUnmapMem(pScrn); 1196 1197 if(pAST->AccelInfoPtr) { 1198 XAADestroyInfoRec(pAST->AccelInfoPtr); 1199 pAST->AccelInfoPtr = NULL; 1200 } 1201 1202 if(pAST->HWCInfoPtr) { 1203 xf86DestroyCursorInfoRec(pAST->HWCInfoPtr); 1204 pAST->HWCInfoPtr = NULL; 1205 } 1206 1207 pScrn->vtSema = FALSE; 1208 pScreen->CloseScreen = pAST->CloseScreen; 1209 return (*pScreen->CloseScreen) (scrnIndex, pScreen); 1210} 1211 1212static void 1213ASTSave(ScrnInfoPtr pScrn) 1214{ 1215 ASTRecPtr pAST; 1216 vgaRegPtr vgaReg; 1217 ASTRegPtr astReg; 1218 int i, icount=0; 1219 ULONG ulData; 1220 1221 pAST = ASTPTR(pScrn); 1222 vgaReg = &VGAHWPTR(pScrn)->SavedReg; 1223 astReg = &pAST->SavedReg; 1224 1225 /* do save */ 1226 if (xf86IsPrimaryPci(pAST->PciInfo)) { 1227 vgaHWSave(pScrn, vgaReg, VGA_SR_ALL); 1228 } 1229 else { 1230 vgaHWSave(pScrn, vgaReg, VGA_SR_MODE); 1231 } 1232 1233 /* Ext. Save */ 1234 if (pAST->jChipType == AST1180) 1235 { 1236 for (i=0; i<12; i++) 1237 { 1238 ReadAST1180SOC(AST1180_GFX_BASE + AST1180_VGA1_CTRL+i*4, ulData); 1239 astReg->GFX[i] = ulData; 1240 } 1241 } 1242 else 1243 { 1244 vASTOpenKey(pScrn); 1245 1246 /* fixed Console Switch Refresh Rate Incorrect issue, ycchen@051106 */ 1247 for (i=0x81; i<=0xB6; i++) 1248 GetIndexReg(CRTC_PORT, (UCHAR) (i), astReg->ExtCRTC[icount++]); 1249 for (i=0xBC; i<=0xC1; i++) 1250 GetIndexReg(CRTC_PORT, (UCHAR) (i), astReg->ExtCRTC[icount++]); 1251 GetIndexReg(CRTC_PORT, (UCHAR) (0xBB), astReg->ExtCRTC[icount]); 1252 } 1253 1254} 1255 1256static void 1257ASTRestore(ScrnInfoPtr pScrn) 1258{ 1259 ASTRecPtr pAST; 1260 vgaRegPtr vgaReg; 1261 ASTRegPtr astReg; 1262 int i, icount=0; 1263 ULONG ulData; 1264 1265 pAST = ASTPTR(pScrn); 1266 vgaReg = &VGAHWPTR(pScrn)->SavedReg; 1267 astReg = &pAST->SavedReg; 1268 1269 /* do restore */ 1270 vgaHWProtect(pScrn, TRUE); 1271 if (xf86IsPrimaryPci(pAST->PciInfo)) 1272 vgaHWRestore(pScrn, vgaReg, VGA_SR_ALL); 1273 else 1274 vgaHWRestore(pScrn, vgaReg, VGA_SR_MODE); 1275 vgaHWProtect(pScrn, FALSE); 1276 1277 if (pAST->jChipType == AST1180) 1278 { 1279 for (i=0; i<12; i++) 1280 { 1281 ulData = astReg->GFX[i]; 1282 WriteAST1180SOC(AST1180_GFX_BASE + AST1180_VGA1_CTRL+i*4, ulData); 1283 } 1284 } 1285 else 1286 { 1287 /* Ext. restore */ 1288 vASTOpenKey(pScrn); 1289 1290 /* fixed Console Switch Refresh Rate Incorrect issue, ycchen@051106 */ 1291 for (i=0x81; i<=0xB6; i++) 1292 SetIndexReg(CRTC_PORT, (UCHAR) (i), astReg->ExtCRTC[icount++]); 1293 for (i=0xBC; i<=0xC1; i++) 1294 SetIndexReg(CRTC_PORT, (UCHAR) (i), astReg->ExtCRTC[icount++]); 1295 SetIndexReg(CRTC_PORT, (UCHAR) (0xBB), astReg->ExtCRTC[icount]); 1296 } 1297 1298} 1299 1300static void 1301ASTProbeDDC(ScrnInfoPtr pScrn, int index) 1302{ 1303 vbeInfoPtr pVbe; 1304 ASTRecPtr pAST = ASTPTR(pScrn); 1305 unsigned char DDC_data[128]; 1306 Bool Flags; 1307 1308 if ( (pAST->jChipType == AST1180) || (!xf86IsPrimaryPci(pAST->PciInfo)) ) 1309 { 1310 if (pAST->jChipType == AST1180) 1311 Flags = GetVGA2EDID(pScrn, DDC_data); 1312 else 1313 Flags = GetVGAEDID(pScrn, DDC_data); 1314 1315 if (Flags) 1316 { 1317 ConfiguredMonitor = xf86InterpretEDID(pScrn->scrnIndex, DDC_data); 1318 } 1319 else 1320 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"[ASTProbeDDC] Can't Get EDID Properly \n"); 1321 } 1322 else 1323 { 1324 if (xf86LoadSubModule(pScrn, "vbe")) { 1325 pVbe = VBEInit(NULL, index); 1326 ConfiguredMonitor = vbeDoEDID(pVbe, NULL); 1327 vbeFree(pVbe); 1328 } 1329 } 1330} 1331 1332#define SkipDT 0x00 1333#define DT1 0x01 1334#define DT2 0x02 1335 1336static xf86MonPtr 1337ASTDoDDC(ScrnInfoPtr pScrn, int index) 1338{ 1339 vbeInfoPtr pVbe; 1340 xf86MonPtr MonInfo = NULL, MonInfo1 = NULL, MonInfo2 = NULL; 1341 ASTRecPtr pAST = ASTPTR(pScrn); 1342 unsigned long i, j, k; 1343 unsigned char DDC_data[128]; 1344 struct monitor_ranges ranges, ranges1, ranges2; 1345 int DTSelect, dclock1=0, h_active1=0, v_active1=0, dclock2=0, h_active2=0, v_active2=0; 1346 struct std_timings stdtiming, *stdtiming1, *stdtiming2; 1347 Bool Flags; 1348 1349 /* Honour Option "noDDC" */ 1350 if (xf86ReturnOptValBool(pAST->Options, OPTION_NO_DDC, FALSE)) { 1351 return MonInfo; 1352 } 1353 1354 if ( (pAST->jChipType == AST1180) || (!xf86IsPrimaryPci(pAST->PciInfo)) ) 1355 { 1356 1357 if (pAST->jChipType == AST1180) 1358 Flags = GetVGA2EDID(pScrn, DDC_data); 1359 else 1360 Flags = GetVGAEDID(pScrn, DDC_data); 1361 1362 if (Flags) 1363 { 1364 MonInfo = xf86InterpretEDID(pScrn->scrnIndex, DDC_data); 1365 xf86PrintEDID(MonInfo); 1366 xf86SetDDCproperties(pScrn, MonInfo); 1367 } 1368 else 1369 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"[ASTDoDDC] Can't Get EDID Properly \n"); 1370 1371 } 1372 else 1373 { 1374 1375 if (xf86LoadSubModule(pScrn, "vbe") && (pVbe = VBEInit(NULL, index))) { 1376 MonInfo1 = vbeDoEDID(pVbe, NULL); 1377 MonInfo = MonInfo1; 1378 1379 /* For VGA2 CLONE Support, ycchen@012508 */ 1380 if ((xf86ReturnOptValBool(pAST->Options, OPTION_VGA2_CLONE, FALSE)) || pAST->VGA2Clone) { 1381 if (GetVGA2EDID(pScrn, DDC_data) == TRUE) { 1382 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Get VGA2 EDID Correctly!! \n"); 1383 MonInfo2 = xf86InterpretEDID(pScrn->scrnIndex, DDC_data); 1384 if (MonInfo1 == NULL) /* No DDC1 EDID */ 1385 MonInfo = MonInfo2; 1386 else { /* Check with VGA1 & VGA2 EDID */ 1387 /* Update establishment timing */ 1388 MonInfo->timings1.t1 = MonInfo1->timings1.t1 & MonInfo2->timings1.t1; 1389 MonInfo->timings1.t2 = MonInfo1->timings1.t2 & MonInfo2->timings1.t2; 1390 MonInfo->timings1.t_manu = MonInfo1->timings1.t_manu & MonInfo2->timings1.t_manu; 1391 1392 /* Update Std. Timing */ 1393 for (i=0; i<8; i++) { 1394 stdtiming.hsize = stdtiming.vsize = stdtiming.refresh = stdtiming.id = 0; 1395 for (j=0; j<8; j++) { 1396 if ((MonInfo1->timings2[i].hsize == MonInfo2->timings2[j].hsize) && \ 1397 (MonInfo1->timings2[i].vsize == MonInfo2->timings2[j].vsize) && \ 1398 (MonInfo1->timings2[i].refresh == MonInfo2->timings2[j].refresh)) { 1399 stdtiming = MonInfo1->timings2[i]; 1400 break; 1401 } 1402 } 1403 1404 MonInfo->timings2[i] = stdtiming; 1405 } /* Std. Timing */ 1406 1407 /* Get Detailed Timing */ 1408 for (i=0;i<4;i++) { 1409 if (MonInfo1->det_mon[i].type == 0xFD) 1410 ranges1 = MonInfo1->det_mon[i].section.ranges; 1411 else if (MonInfo1->det_mon[i].type == 0xFA) 1412 stdtiming1 = MonInfo1->det_mon[i].section.std_t; 1413 else if (MonInfo1->det_mon[i].type == 0x00) { 1414 if (MonInfo1->det_mon[i].section.d_timings.clock > dclock1) 1415 dclock1 = MonInfo1->det_mon[i].section.d_timings.clock; 1416 if (MonInfo1->det_mon[i].section.d_timings.h_active > h_active1) 1417 h_active1 = MonInfo1->det_mon[i].section.d_timings.h_active; 1418 if (MonInfo1->det_mon[i].section.d_timings.v_active > v_active1) 1419 v_active1 = MonInfo1->det_mon[i].section.d_timings.v_active; 1420 } 1421 if (MonInfo2->det_mon[i].type == 0xFD) 1422 ranges2 = MonInfo2->det_mon[i].section.ranges; 1423 else if (MonInfo1->det_mon[i].type == 0xFA) 1424 stdtiming2 = MonInfo2->det_mon[i].section.std_t; 1425 else if (MonInfo2->det_mon[i].type == 0x00) { 1426 if (MonInfo2->det_mon[i].section.d_timings.clock > dclock2) 1427 dclock2 = MonInfo2->det_mon[i].section.d_timings.clock; 1428 if (MonInfo2->det_mon[i].section.d_timings.h_active > h_active2) 1429 h_active2 = MonInfo2->det_mon[i].section.d_timings.h_active; 1430 if (MonInfo2->det_mon[i].section.d_timings.v_active > v_active2) 1431 v_active2 = MonInfo2->det_mon[i].section.d_timings.v_active; 1432 } 1433 } /* Get Detailed Timing */ 1434 1435 /* Chk Detailed Timing */ 1436 if ((dclock1 >= dclock2) && (h_active1 >= h_active2) && (v_active1 >= v_active2)) 1437 DTSelect = DT2; 1438 else if ((dclock2 >= dclock1) && (h_active2 >= h_active1) && (v_active2 >= v_active1)) 1439 DTSelect = DT1; 1440 else 1441 DTSelect = SkipDT; 1442 1443 /* Chk Monitor Descriptor */ 1444 ranges = ranges1; 1445 ranges.min_h = ranges1.min_h > ranges2.min_h ? ranges1.min_h:ranges2.min_h; 1446 ranges.min_v = ranges1.min_v > ranges2.min_v ? ranges1.min_v:ranges2.min_v; 1447 ranges.max_h = ranges1.max_h < ranges2.max_h ? ranges1.max_h:ranges2.max_h; 1448 ranges.max_v = ranges1.max_v < ranges2.max_v ? ranges1.max_v:ranges2.max_v; 1449 ranges.max_clock = ranges1.max_clock < ranges2.max_clock ? ranges1.max_clock:ranges2.max_clock; 1450 1451 /* Update Detailed Timing */ 1452 for (i=0; i<4; i++) 1453 { 1454 if (MonInfo->det_mon[i].type == 0xFD) { 1455 MonInfo->det_mon[i].section.ranges = ranges; 1456 } 1457 else if (MonInfo->det_mon[i].type == 0xFA) { 1458 for (j=0; j<5; j++) { 1459 stdtiming.hsize = stdtiming.vsize = stdtiming.refresh = stdtiming.id = 0; 1460 for (k=0; k<5; k++) { 1461 if ((stdtiming1[j].hsize == stdtiming2[k].hsize) && \ 1462 (stdtiming1[j].vsize == stdtiming2[k].vsize) && \ 1463 (stdtiming1[j].refresh == stdtiming2[k].refresh)) { 1464 stdtiming = stdtiming1[j]; 1465 break; 1466 } 1467 } 1468 stdtiming1[j] = stdtiming; 1469 } /* Std. Timing */ 1470 } /* FA */ 1471 else if (MonInfo->det_mon[i].type == 0x00) { 1472 if (DTSelect == DT2) 1473 MonInfo->det_mon[i] = MonInfo2->det_mon[i]; 1474 else if (DTSelect == DT1) 1475 MonInfo->det_mon[i] = MonInfo1->det_mon[i]; 1476 else /* SkipDT */ 1477 { /* use 1024x768 as default */ 1478 MonInfo->det_mon[i] = MonInfo1->det_mon[i]; 1479 MonInfo->det_mon[i].section.d_timings.clock = 65000000; 1480 MonInfo->det_mon[i].section.d_timings.h_active = 1024; 1481 MonInfo->det_mon[i].section.d_timings.h_blanking = 320; 1482 MonInfo->det_mon[i].section.d_timings.v_active = 768; 1483 MonInfo->det_mon[i].section.d_timings.v_blanking = 38; 1484 MonInfo->det_mon[i].section.d_timings.h_sync_off = 24; 1485 MonInfo->det_mon[i].section.d_timings.h_sync_width = 136; 1486 MonInfo->det_mon[i].section.d_timings.v_sync_off = 3; 1487 MonInfo->det_mon[i].section.d_timings.v_sync_width = 6; 1488 } 1489 } /* 00 */ 1490 else { /* use Monitor 1 as default */ 1491 MonInfo->det_mon[i] = MonInfo1->det_mon[i]; 1492 } 1493 1494 } /* Update Detailed Timing */ 1495 1496 /* set feature size */ 1497 if (DTSelect == DT2) { 1498 MonInfo->features.hsize = MonInfo2->features.hsize; 1499 MonInfo->features.vsize = MonInfo2->features.vsize; 1500 } 1501 else if (DTSelect == DT1) { 1502 MonInfo->features.hsize = MonInfo1->features.hsize; 1503 MonInfo->features.vsize = MonInfo1->features.vsize; 1504 } 1505 else /* Skip DT */ 1506 { /* use 1024x768 as default */ 1507 MonInfo->features.hsize = 0x20; 1508 MonInfo->features.vsize = 0x18; 1509 } 1510 1511 } /* Check with VGA1 & VGA2 EDID */ 1512 1513 } /* GetVGA2EDID */ 1514 else { 1515 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Can't Get VGA2 EDID Correctly!! \n"); 1516 } 1517 1518 } 1519 1520 /* save MonInfo to Private */ 1521 pAST->mon_h_active = MonInfo->det_mon[0].section.d_timings.h_active; 1522 pAST->mon_v_active = MonInfo->det_mon[0].section.d_timings.v_active; 1523 1524 xf86PrintEDID(MonInfo); 1525 xf86SetDDCproperties(pScrn, MonInfo); 1526 vbeFree(pVbe); 1527 } else { 1528 xf86DrvMsg(pScrn->scrnIndex, X_INFO, 1529 "this driver cannot do DDC without VBE\n"); 1530 } 1531 1532 } /* AST1180 */ 1533 1534 return MonInfo; 1535} 1536 1537static void 1538vFillASTModeInfo (ScrnInfoPtr pScrn) 1539{ 1540 ASTRecPtr pAST; 1541 1542 pAST = ASTPTR(pScrn); 1543 1544 pAST->VideoModeInfo.ScreenWidth = pScrn->virtualX; 1545 pAST->VideoModeInfo.ScreenHeight = pScrn->virtualY; 1546 pAST->VideoModeInfo.bitsPerPixel = pScrn->bitsPerPixel; 1547 /* Fixed screen pitch incorrect in some specific monitor, ycchen@071707 */ 1548 pAST->VideoModeInfo.ScreenPitch = pScrn->displayWidth * ((pScrn->bitsPerPixel + 1) / 8) ; 1549 1550} 1551 1552static Bool 1553ASTModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode) 1554{ 1555 vgaHWPtr hwp; 1556 ASTRecPtr pAST; 1557 1558 hwp = VGAHWPTR(pScrn); 1559 pAST = ASTPTR(pScrn); 1560 1561 vgaHWUnlock(hwp); 1562 1563 if (!vgaHWInit(pScrn, mode)) 1564 return FALSE; 1565 1566 pScrn->vtSema = TRUE; 1567 pAST->ModePtr = mode; 1568 1569 if (!ASTSetMode(pScrn, mode)) 1570 return FALSE; 1571 1572 vgaHWProtect(pScrn, FALSE); 1573 1574 return TRUE; 1575} 1576 1577#ifdef AstVideo 1578/* 1579 * Video Part by ic_yang 1580 */ 1581#include "fourcc.h" 1582 1583#define NUM_ATTRIBUTES 8 1584#define NUM_IMAGES 8 1585#define NUM_FORMATS 3 1586 1587#define IMAGE_MIN_WIDTH 32 1588#define IMAGE_MIN_HEIGHT 24 1589#define IMAGE_MAX_WIDTH 1920 1590#define IMAGE_MAX_HEIGHT 1080 1591 1592#define MAKE_ATOM(a) MakeAtom(a, sizeof(a) - 1, TRUE) 1593 1594static XF86ImageRec ASTImages[NUM_IMAGES] = 1595{ 1596 XVIMAGE_YUY2, /* If order is changed, ASTOffscreenImages must be adapted */ 1597}; 1598 1599static XF86VideoFormatRec ASTFormats[NUM_FORMATS] = 1600{ 1601 { 8, PseudoColor}, 1602 {16, TrueColor}, 1603 {24, TrueColor} 1604}; 1605 1606/* client libraries expect an encoding */ 1607static XF86VideoEncodingRec DummyEncoding = 1608{ 1609 0, 1610 "XV_IMAGE", 1611 0, 0, /* Will be filled in */ 1612 {1, 1} 1613}; 1614 1615static char astxvcolorkey[] = "XV_COLORKEY"; 1616static char astxvbrightness[] = "XV_BRIGHTNESS"; 1617static char astxvcontrast[] = "XV_CONTRAST"; 1618static char astxvsaturation[] = "XV_SATURATION"; 1619static char astxvhue[] = "XV_HUE"; 1620static char astxvgammared[] = "XV_GAMMA_RED"; 1621static char astxvgammagreen[] = "XV_GAMMA_GREEN"; 1622static char astxvgammablue[] = "XV_GAMMA_BLUE"; 1623 1624static XF86AttributeRec ASTAttributes[NUM_ATTRIBUTES] = 1625{ 1626 {XvSettable | XvGettable, 0, (1 << 24) - 1, astxvcolorkey}, 1627 {XvSettable | XvGettable, -128, 127, astxvbrightness}, 1628 {XvSettable | XvGettable, 0, 255, astxvcontrast}, 1629 {XvSettable | XvGettable, -180, 180, astxvsaturation}, 1630 {XvSettable | XvGettable, -180, 180, astxvhue}, 1631 {XvSettable | XvGettable, 100, 10000, astxvgammared}, 1632 {XvSettable | XvGettable, 100, 10000, astxvgammagreen}, 1633 {XvSettable | XvGettable, 100, 10000, astxvgammablue}, 1634}; 1635 1636static void ASTStopVideo(ScrnInfoPtr pScrn, pointer data, Bool exit) 1637{ 1638 ASTPortPrivPtr pPriv = (ASTPortPrivPtr)data; 1639 ASTPtr pAST = ASTPTR(pScrn); 1640 1641 REGION_EMPTY(pScrn->pScreen, &pPriv->clip); 1642 1643 if(exit) 1644 { 1645 if(pPriv->fbAreaPtr) 1646 { 1647 xf86FreeOffscreenArea(pPriv->fbAreaPtr); 1648 pPriv->fbAreaPtr = NULL; 1649 pPriv->fbSize = 0; 1650 } 1651 /* clear all flag */ 1652 pPriv->videoStatus = 0; 1653 } 1654 else 1655 { 1656#if 0 1657 if(pPriv->videoStatus & CLIENT_VIDEO_ON) 1658 { 1659 pPriv->videoStatus |= OFF_TIMER; 1660 1661 } 1662#endif 1663 } 1664} 1665 1666static int ASTSetPortAttribute(ScrnInfoPtr pScrn, Atom attribute, INT32 value, pointer data) 1667{ 1668 ASTPortPrivPtr pPriv = (ASTPortPrivPtr)data; 1669 ASTPtr pAST = ASTPTR(pScrn); 1670 1671 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"ASTSetPortAttribute(),attribute=%x\n", attribute); 1672 1673 if (attribute == pAST->xvBrightness) 1674 { 1675 if((value < -128) || (value > 127)) 1676 return BadValue; 1677 1678 pPriv->brightness = value; 1679 } 1680 else if (attribute == pAST->xvContrast) 1681 { 1682 if ((value < 0) || (value > 255)) 1683 return BadValue; 1684 1685 pPriv->contrast = value; 1686 } 1687 else if (attribute == pAST->xvSaturation) 1688 { 1689 if ((value < -180) || (value > 180)) 1690 return BadValue; 1691 1692 pPriv->saturation = value; 1693 } 1694 else if (attribute == pAST->xvHue) 1695 { 1696 if ((value < -180) || (value > 180)) 1697 return BadValue; 1698 1699 pPriv->hue = value; 1700 } 1701 else if (attribute == pAST->xvColorKey) 1702 { 1703 pPriv->colorKey = value; 1704 REGION_EMPTY(pScrn->pScreen, &pPriv->clip); 1705 } 1706 else if(attribute == pAST->xvGammaRed) 1707 { 1708 if((value < 100) || (value > 10000)) 1709 return BadValue; 1710 pPriv->gammaR = value; 1711 } 1712 else if(attribute == pAST->xvGammaGreen) 1713 { 1714 if((value < 100) || (value > 10000)) 1715 return BadValue; 1716 pPriv->gammaG = value; 1717 } 1718 else if(attribute == pAST->xvGammaBlue) 1719 { 1720 if((value < 100) || (value > 10000)) 1721 return BadValue; 1722 pPriv->gammaB = value; 1723 } 1724 else 1725 { 1726 return BadMatch; 1727 } 1728 1729 return Success; 1730} 1731 1732static int ASTGetPortAttribute(ScrnInfoPtr pScrn, Atom attribute, INT32 *value, pointer data) 1733{ 1734 ASTPortPrivPtr pPriv = (ASTPortPrivPtr)data; 1735 ASTPtr pAST = ASTPTR(pScrn); 1736 1737 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"ASTGetPortAttribute(),attribute=%x\n", attribute); 1738 1739 if (attribute == pAST->xvBrightness) 1740 { 1741 *value = pPriv->brightness; 1742 } 1743 else if (attribute == pAST->xvContrast) 1744 { 1745 *value = pPriv->contrast; 1746 } 1747 else if (attribute == pAST->xvSaturation) 1748 { 1749 *value = pPriv->saturation; 1750 } 1751 else if (attribute == pAST->xvHue) 1752 { 1753 *value = pPriv->hue; 1754 } 1755 else if(attribute == pAST->xvGammaRed) 1756 { 1757 *value = pPriv->gammaR; 1758 1759 } 1760 else if(attribute == pAST->xvGammaGreen) 1761 { 1762 *value = pPriv->gammaG; 1763 } 1764 else if(attribute == pAST->xvGammaBlue) 1765 { 1766 *value = pPriv->gammaB; 1767 } 1768 else if (attribute == pAST->xvColorKey) 1769 { 1770 *value = pPriv->colorKey; 1771 } 1772 else 1773 return BadMatch; 1774 1775 return Success; 1776} 1777 1778static void ASTQueryBestSize(ScrnInfoPtr pScrn, Bool motion, 1779 short vid_w, short vid_h, 1780 short drw_w, short drw_h, 1781 unsigned int *p_w, unsigned int *p_h, 1782 pointer data) 1783{ 1784 *p_w = drw_w; 1785 *p_h = drw_h; 1786 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"ASTQueryBestSize()\n"); 1787 /* TODO: report the HW limitation */ 1788} 1789 1790static int ASTQueryImageAttributes(ScrnInfoPtr pScrn, int id, 1791 unsigned short *w, unsigned short *h, 1792 int *pitches, int *offsets) 1793{ 1794 int pitchY, pitchUV; 1795 int size, sizeY, sizeUV; 1796 1797 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"ASTQueryImageAttributes()\n"); 1798 1799 if(*w < IMAGE_MIN_WIDTH) *w = IMAGE_MIN_WIDTH; 1800 if(*h < IMAGE_MIN_HEIGHT) *h = IMAGE_MIN_HEIGHT; 1801 1802 switch(id) { 1803 case PIXEL_FMT_YV12: 1804 *w = (*w + 7) & ~7; 1805 *h = (*h + 1) & ~1; 1806 pitchY = *w; 1807 pitchUV = *w >> 1; 1808 if(pitches) { 1809 pitches[0] = pitchY; 1810 pitches[1] = pitches[2] = pitchUV; 1811 } 1812 sizeY = pitchY * (*h); 1813 sizeUV = pitchUV * ((*h) >> 1); 1814 if(offsets) { 1815 offsets[0] = 0; 1816 offsets[1] = sizeY; 1817 offsets[2] = sizeY + sizeUV; 1818 } 1819 size = sizeY + (sizeUV << 1); 1820 break; 1821 case PIXEL_FMT_NV12: 1822 case PIXEL_FMT_NV21: 1823 *w = (*w + 7) & ~7; 1824 *h = (*h + 1) & ~1; 1825 pitchY = *w; 1826 pitchUV = *w; 1827 if(pitches) { 1828 pitches[0] = pitchY; 1829 pitches[1] = pitchUV; 1830 } 1831 sizeY = pitchY * (*h); 1832 sizeUV = pitchUV * ((*h) >> 1); 1833 if(offsets) { 1834 offsets[0] = 0; 1835 offsets[1] = sizeY; 1836 } 1837 size = sizeY + (sizeUV << 1); 1838 break; 1839 case PIXEL_FMT_YUY2: 1840 case PIXEL_FMT_UYVY: 1841 case PIXEL_FMT_YVYU: 1842 case PIXEL_FMT_RGB6: 1843 case PIXEL_FMT_RGB5: 1844 default: 1845 *w = (*w + 1) & ~1; 1846 pitchY = *w << 1; 1847 if(pitches) pitches[0] = pitchY; 1848 if(offsets) offsets[0] = 0; 1849 size = pitchY * (*h); 1850 break; 1851 } 1852 1853 return size; 1854} 1855 1856extern void ASTDisplayVideo(ScrnInfoPtr pScrn, ASTPortPrivPtr pPriv, RegionPtr clipBoxes, int id); 1857 1858static int ASTPutImage(ScrnInfoPtr pScrn, 1859 short src_x, short src_y, 1860 short drw_x, short drw_y, 1861 short src_w, short src_h, 1862 short drw_w, short drw_h, 1863 int id, unsigned char* buf, 1864 short width, short height, 1865 Bool sync, 1866 RegionPtr clipBoxes, pointer data, 1867 DrawablePtr pDraw 1868) 1869{ 1870 ASTPtr pAST = ASTPTR(pScrn); 1871 ASTPortPrivPtr pPriv = (ASTPortPrivPtr)data; 1872 int i; 1873 int totalSize=0; 1874 1875 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"ASTPutImage()\n"); 1876 /* int depth = pAST->CurrentLayout.bitsPerPixel >> 3; */ 1877 1878 pPriv->drw_x = drw_x; 1879 pPriv->drw_y = drw_y; 1880 pPriv->drw_w = drw_w; 1881 pPriv->drw_h = drw_h; 1882 pPriv->src_x = src_x; 1883 pPriv->src_y = src_y; 1884 pPriv->src_w = src_w; 1885 pPriv->src_h = src_h; 1886 pPriv->id = id; 1887 pPriv->height = height; 1888 1889 switch(id) 1890 { 1891 case PIXEL_FMT_YV12: 1892 case PIXEL_FMT_NV12: 1893 case PIXEL_FMT_NV21: 1894 pPriv->srcPitch = (width + 7) & ~7; 1895 totalSize = (pPriv->srcPitch * height * 3) >> 1; /* Verified */ 1896 break; 1897 case PIXEL_FMT_YUY2: 1898 case PIXEL_FMT_UYVY: 1899 case PIXEL_FMT_YVYU: 1900 case PIXEL_FMT_RGB6: 1901 case PIXEL_FMT_RGB5: 1902 default: 1903 pPriv->srcPitch = ((width << 1) + 3) & ~3; /* Verified */ 1904 totalSize = pPriv->srcPitch * height; 1905 } 1906 1907 totalSize += 15; 1908 totalSize &= ~15; 1909 /* allocate memory */ 1910 1911 if(totalSize == pPriv->fbSize) 1912 { 1913 ; 1914 } 1915 else 1916 { 1917 int lines, pitch, depth; 1918 BoxPtr pBox = NULL; 1919 1920 pPriv->fbSize = totalSize; 1921 1922 if(pPriv->fbAreaPtr) 1923 { 1924 xf86FreeOffscreenArea(pPriv->fbAreaPtr); 1925 } 1926 1927 depth = (pScrn->bitsPerPixel + 7 ) / 8; 1928 pitch = pScrn->displayWidth * depth; 1929 lines = ((totalSize * 2) / pitch) + 1; 1930 xf86DrvMsg(pScrn->scrnIndex, X_INFO,"ASTPutImagelines=%x, pitch=%x, displayWidth=%x\n", lines, pitch, pScrn->displayWidth); 1931 1932 1933 pPriv->fbAreaPtr = xf86AllocateOffscreenArea(pScrn->pScreen, 1934 pScrn->displayWidth, 1935 lines, 0, NULL, NULL, NULL); 1936 1937 if(!pPriv->fbAreaPtr) 1938 { 1939 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Allocate video memory fails\n"); 1940 return BadAlloc; 1941 } 1942 1943 pBox = &(pPriv->fbAreaPtr->box); 1944 pPriv->bufAddr[0] = (pBox->y1 * pitch) + (pBox->x1 * depth); 1945 pPriv->bufAddr[1] = pPriv->bufAddr[0] + totalSize; 1946 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Put Image, pPriv->bufAddr[0]=0x%08X\n", pPriv->bufAddr[0]); 1947 1948 } 1949 1950 /* copy data */ 1951 if(totalSize < 16) 1952 { 1953 #ifdef NewPath 1954 memcpy(pAST->FBVirtualAddr + pPriv->bufAddr[pPriv->currentBuf], buf, totalSize); 1955 #else /* NewPath */ 1956 switch(id) 1957 { 1958 case PIXEL_FMT_YUY2: 1959 case PIXEL_FMT_UYVY: 1960 case PIXEL_FMT_YVYU: 1961 { 1962 BYTE *Base = (BYTE *)(pAST->FBVirtualAddr + pPriv->bufAddr[pPriv->currentBuf]); 1963 for(i=0; i<height; i++) 1964 memcpy( Base + i * pPriv->srcPitch, buf + i*width*2, width*2); 1965 break; 1966 } 1967 default: 1968 memcpy(pAST->FBVirtualAddr + pPriv->bufAddr[pPriv->currentBuf], buf, totalSize); 1969 break; 1970 } /* switch */ 1971 #endif /* NewPath */ 1972 } 1973 else 1974 { 1975 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Put Image, copy buf\n"); 1976 1977 #ifdef NewPath 1978 memcpy(pAST->FBVirtualAddr + pPriv->bufAddr[pPriv->currentBuf], buf, totalSize); 1979 #else /* NewPath */ 1980 switch(id) 1981 { 1982 case PIXEL_FMT_YUY2: 1983 case PIXEL_FMT_UYVY: 1984 case PIXEL_FMT_YVYU: 1985 { 1986 BYTE *Base = (BYTE *)(pAST->FBVirtualAddr + pPriv->bufAddr[pPriv->currentBuf]); 1987 for(i=0; i<height; i++) 1988 memcpy( Base + i * pPriv->srcPitch, buf + i*width*2, width*2); 1989 1990 /*for(i=0; i<height; i++) 1991 for(j=0; j<width*2; j++) 1992 *(Base+i*pPriv->srcPitch+j) = *(buf + width*i + j);*/ 1993 break; 1994 } 1995 default: 1996 { BYTE *Base = (BYTE *)(pAST->FBVirtualAddr + pPriv->bufAddr[pPriv->currentBuf]); 1997 int j; 1998 for(i=0; i<height; i++) 1999 for(j=0; j<width; j++) 2000 *(Base + width*i + j) = *(buf + width * i + j); 2001 break; 2002 } 2003 } /* end of switch */ 2004 #endif /* NewPath */ 2005 } 2006 2007 ASTDisplayVideo(pScrn, pPriv, clipBoxes, id); 2008 2009 /* update cliplist 2010 if(!REGION_EQUAL(pScrn->pScreen, &pPriv->clip, clipBoxes)) 2011 { 2012 REGION_COPY(pScrn->pScreen, &pPriv->clip, clipBoxes); 2013 } 2014 else 2015 { 2016 xf86XVFillKeyHelper(pScrn->pScreen, 0xFFFFFFFF, clipBoxes); 2017 } 2018 */ 2019 pPriv->currentBuf ^= 1; 2020 2021 return Success; 2022} 2023 2024static XF86VideoAdaptorPtr ASTSetupImageVideo(ScreenPtr pScreen) 2025{ 2026 ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; 2027 ASTPtr pAST = ASTPTR(pScrn); 2028 XF86VideoAdaptorPtr adapt; 2029 ASTPortPrivPtr pPriv; 2030 2031 2032 if(!(adapt = calloc(1, sizeof(XF86VideoAdaptorRec) + 2033 sizeof(DevUnion) + 2034 sizeof(ASTPortPrivRec)))) 2035 return NULL; 2036 2037 adapt->type = XvWindowMask | XvInputMask | XvImageMask | XvVideoMask; 2038 adapt->flags = VIDEO_OVERLAID_IMAGES | VIDEO_CLIP_TO_VIEWPORT; 2039 adapt->name = "AST Video"; 2040 2041 adapt->nEncodings = 1; 2042 adapt->pEncodings = &DummyEncoding; 2043 2044 adapt->nFormats = NUM_FORMATS; 2045 adapt->pFormats = ASTFormats; 2046 adapt->nPorts = 1; 2047 adapt->pPortPrivates = (DevUnion*)(&adapt[1]); 2048 2049 pPriv = (ASTPortPrivPtr)(&adapt->pPortPrivates[1]); 2050 2051 adapt->pPortPrivates->ptr = (pointer)(pPriv); 2052 adapt->pAttributes = ASTAttributes; 2053 adapt->nAttributes = NUM_ATTRIBUTES; 2054 adapt->nImages = NUM_IMAGES; 2055 adapt->pImages = ASTImages; 2056 2057 adapt->PutVideo = NULL; 2058 2059 adapt->PutStill = NULL; 2060 adapt->GetVideo = NULL; 2061 adapt->GetStill = NULL; 2062 adapt->StopVideo = ASTStopVideo; 2063 adapt->SetPortAttribute = ASTSetPortAttribute; 2064 adapt->GetPortAttribute = ASTGetPortAttribute; 2065 adapt->QueryBestSize = ASTQueryBestSize; 2066 adapt->PutImage = ASTPutImage; 2067 adapt->QueryImageAttributes = ASTQueryImageAttributes; 2068 2069 2070 pPriv->currentBuf = 0; 2071 pPriv->linear = NULL; 2072 pPriv->fbAreaPtr = NULL; 2073 pPriv->fbSize = 0; 2074 pPriv->videoStatus = 0; 2075 2076 pPriv->colorKey = 0x000101fe; 2077 pPriv->brightness = 0; 2078 pPriv->contrast = 128; 2079 pPriv->saturation = 0; 2080 pPriv->hue = 0; 2081 2082 /* gotta uninit this someplace */ 2083#if defined(REGION_NULL) 2084 REGION_NULL(pScreen, &pPriv->clip); 2085#else 2086 REGION_INIT(pScreen, &pPriv->clip, NullBox, 0); 2087#endif 2088 2089 pAST->adaptor = adapt; 2090 2091 pAST->xvBrightness = MAKE_ATOM(astxvbrightness); 2092 pAST->xvContrast = MAKE_ATOM(astxvcontrast); 2093 pAST->xvColorKey = MAKE_ATOM(astxvcolorkey); 2094 pAST->xvSaturation = MAKE_ATOM(astxvsaturation); 2095 pAST->xvHue = MAKE_ATOM(astxvhue); 2096 pAST->xvGammaRed = MAKE_ATOM(astxvgammared); 2097 pAST->xvGammaGreen = MAKE_ATOM(astxvgammagreen); 2098 pAST->xvGammaBlue = MAKE_ATOM(astxvgammablue); 2099 2100 return adapt; 2101} 2102 2103void ASTInitVideo(ScreenPtr pScreen) 2104{ 2105 ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; 2106 XF86VideoAdaptorPtr *adaptors, *newAdaptors = NULL; 2107 XF86VideoAdaptorPtr ASTAdaptor = NULL; 2108 int num_adaptors; 2109 2110 ASTAdaptor = ASTSetupImageVideo(pScreen); 2111 2112 num_adaptors = xf86XVListGenericAdaptors(pScrn, &adaptors); 2113 2114 if(ASTAdaptor) 2115 { 2116 if(!num_adaptors) 2117 { 2118 num_adaptors = 1; 2119 adaptors = &ASTAdaptor; 2120 } 2121 else 2122 { 2123 newAdaptors = malloc((num_adaptors + 1) * sizeof(XF86VideoAdaptorPtr*)); 2124 if(newAdaptors) 2125 { 2126 memcpy(newAdaptors, adaptors, num_adaptors * 2127 sizeof(XF86VideoAdaptorPtr)); 2128 newAdaptors[num_adaptors] = ASTAdaptor; 2129 adaptors = newAdaptors; 2130 num_adaptors++; 2131 } 2132 } 2133 } 2134 2135 if(num_adaptors) 2136 xf86XVScreenInit(pScreen, adaptors, num_adaptors); 2137 2138 if(newAdaptors) 2139 free(newAdaptors); 2140 2141} 2142#endif /* AstVideo */ 2143