summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKaleb Keithley <kaleb@freedesktop.org>2003-11-14 16:48:55 +0000
committerKaleb Keithley <kaleb@freedesktop.org>2003-11-14 16:48:55 +0000
commitdc74177b8c1a750d4108ed0b9b5099399672dbb3 (patch)
treef6472119ccb061b6fc5a63aa5d76f34e6dedd708
Initial revisionXORG-STABLE
-rw-r--r--DRI.txt407
-rw-r--r--README.pm357
-rw-r--r--man/glint.man110
-rw-r--r--src/IBMramdac.c125
-rw-r--r--src/TIramdac.c232
-rw-r--r--src/glint.h365
-rw-r--r--src/glint_common.h63
-rw-r--r--src/glint_dga.c273
-rw-r--r--src/glint_dri.c1955
-rw-r--r--src/glint_dri.h123
-rw-r--r--src/glint_dripriv.h296
-rw-r--r--src/glint_driver.c3875
-rw-r--r--src/glint_regs.h1361
-rw-r--r--src/glint_shadow.c46
-rw-r--r--src/pm2_accel.c1487
-rw-r--r--src/pm2_dac.c506
-rw-r--r--src/pm2_video.c3204
-rw-r--r--src/pm2ramdac.c165
-rw-r--r--src/pm2v_dac.c567
-rw-r--r--src/pm2vramdac.c64
-rw-r--r--src/pm3_accel.c1223
-rw-r--r--src/pm3_dac.c842
-rw-r--r--src/pm3_regs.h1111
-rw-r--r--src/pm3_video.c1322
-rw-r--r--src/pm_accel.c1199
-rw-r--r--src/pm_dac.c251
-rw-r--r--src/sx_accel.c872
-rw-r--r--src/tx_accel.c961
-rw-r--r--src/tx_dac.c397
29 files changed, 23459 insertions, 0 deletions
diff --git a/DRI.txt b/DRI.txt
new file mode 100644
index 0000000..5bac4f3
--- /dev/null
+++ b/DRI.txt
@@ -0,0 +1,407 @@
+
+ GLINT State Transition Strategy
+
+
+Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
+All Rights Reserved.
+
+Permission is granted to make and distribute verbatim copies
+of this document provided the copyright notice and this permission
+notice are preserved on all copies.
+
+$XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/DRI.txt,v 1.2 2000/02/23 04:47:06 martin Exp $
+
+GLINT State Transition Strategy
+
+Direct Rendering requires a coordinated method of state management
+across all drivers accessing this device. This document defines the
+expected behavior of all drivers participating in direct rendering with
+this device.
+
+Currently only the GMX2000 supports direct rendering.
+
+
+Section 1) State Transition Types
+
+The direct rendering document entitled "state-mgmt.txt" gives a device
+independent overview on the different types of state transitions. This
+section gives a more detailed description of GLINT specific hardware state.
+
+No context switch--no state saves or restores will be done for transitions,
+however the device can be busy executing commands from previous accesses to
+the device.
+
+X context switch--the intersection of 2D and 3D state will be saved
+and restored. This is the state marked as DDX/3DClient in Appendix A.
+The device will be synced and idle after this switch.
+
+3D context switch--all 3D state will be saved and restored. 3D state is
+defined as all registered owned by the 3DClient driver. See Appendix A
+for more details. The device will be synced and idle after this switch.
+
+The registers owned by the DRM kernel module and submodules are not
+managed by context switches.
+
+
+Section 2) VT Switching and DGA Access
+
+VT Switching away from the X Server or client access to the device
+framebuffer via DGA require the device to be locked away from 3D direct
+rendering accesses. The X Server will hold the lock on behalf of these
+services until access is restored.
+
+
+Section 3) Potential Optimizations
+
+Lighten the number of registers required for context switches by using a
+mechanism to determine whether stipple or pattern registers need to be
+saved/restored. This optimization has not been done for the initial
+direct rendering infrastructure sample implementation.
+
+
+Appendix A: GMX2000 Register Ownership
+
+driver column contains:
+ DDX - DDX driver manages register
+ DRM - DRM or DRM subdriver manages register
+ 3DClient - 3D Client Driver manges register
+ DDX/3DClient, DDX/DRM, 3DClient/DRM - register access is shared
+
+if the RO (read only) column is marked with a *, then no writes are
+permitted to this register, and thus no drivers own it.
+
+primary and secondary columns contain the default values after
+initialization. primary is the master rasterizer, secondary is the
+slave rasterizer.
+
+
+Name offset primary secondary RO driver
+------------------------------------------------------------------------------
+ResetStatus o=0000 0x00000000 0x00000000 DDX/DRM
+IntEnable o=0008 0x00000000 0x00000000 DRM
+IntFlags o=0010 0x00000000 0x00000018 DRM
+InFIFOSpace o=0018 0x00000000 0x00000021 *
+OutFIFOWords o=0020 0x00000000 0x00000000 *
+DMAAddress o=0028 0x00000000 0x00000000 DRM
+DMACount o=0030 0x00000000 0x00000000 DRM
+ErrorFlags o=0038 0x00000000 0x00000002 DRM
+VClkCtl o=0040 0x00000000 0x00000000 DDX
+TestRegister o=0048 0x00000000 0x00000000 DDX
+Aperture0 o=0050 0x00000000 0x00000000 DDX
+Aperture1 o=0058 0x00000000 0x00000000 DDX
+DMAControl o=0060 0x00000000 0x00000000 DRM
+FIFODis o=0068 0x00000000 0x00000001 DDX
+LBMemoryCtl o=1000 0x00000000 0x770883ff DDX
+LBMemoryEDO o=1008 0x00000000 0x77080000 DDX
+FBMemoryCtl o=1800 0x00000000 0x63c00800 DDX
+FBModeSel o=1808 0x00000000 0x00000907 DDX
+FBGCWrMask o=1810 0x00000000 0xffffffff *
+FBGCColorLower o=1818 0x00000000 0x00828282 *
+FBTXMemCtl o=1820 0x00000000 0x00000002 DDX
+FBWrMask o=1830 0x00000000 0xffffffff *
+FBGCColorUpper o=1838 0x00000000 0x00828282 *
+VTGHLimit o=3000 0x00000000 0x000000c8 DDX
+VTGHSyncStart o=3008 0x00ffffff 0x00000006 DDX
+VTGHSyncEnd o=3010 0x00000000 0x00000016 DDX
+VTGHBlankEnd o=3018 0x00ffffff 0x00000028 DDX
+VTGVLimit o=3020 0x00000000 0x000001fb DDX
+VTGVSyncStart o=3028 0x00ffffff 0x00000004 DDX
+VTGVSyncEnd o=3030 0x00000000 0x0000000a DDX
+VTGVBlankEnd o=3038 0x00ffffff 0x0000001b DDX
+VTGHGateStart o=3040 0x00000000 0x00000027 DDX
+VTGHGateEnd o=3048 0x00ffffff 0x000000c7 DDX
+VTGVGateStart o=3050 0x00000000 0x0000001a DDX
+VTGVGateEnd o=3058 0x00ffffff 0x0000001b DDX
+VTGPolarity o=3060 0x00000000 0x000000ba DDX
+VTGFrameRowAddr o=3068 0x00ffffff 0x00000000 DDX
+VTGVLineNumber o=3070 0x00000000 0x00000079 DDX
+VTGSerialClk o=3078 0x00ffffff 0x00000002 DDX
+VTGModeCtl o=3080 0x00000000 0x00000000 DDX
+GInFIFOSpace o=0018 0x00000000 *
+GDMAAddress o=0028 0x00000000 DRM
+GDMACount o=0030 0x00000000 DRM
+GDMAControl o=0060 0x00000000 DRM
+GOutDMA o=0080 0x00000000 DRM
+GOutDMACount o=0088 0x00000000 DRM
+GResetStatus o=0800 0x00000000 DRM
+GIntEnable o=0808 0x00000000 DRM
+GIntFlags o=0810 0x00000000 DRM
+GErrorFlags o=0838 0x00000000 DRM
+GTestRegister o=0848 0x00000000 DDX
+GFIFODis o=0868 0x00000000 DDX
+GChipConfig o=0870 0x00000000 DDX
+GCSRAperture o=0878 0x00000000 DDX
+GPageTableAddr o=0c00 0x00000000 DRM
+GPageTableLength o=0c08 0x00000000 DRM
+GDelayTimer o=0c38 0x00000000 DRM
+GCommandMode o=0c40 0x00000000 DRM
+GCommandIntEnable o=0c48 0x00000000 DRM
+GCommandIntFlags o=0c50 0x00000000 DRM
+GCommandErrorFlags o=0c58 0x00000000 DRM
+GCommandStatus o=0c60 0x00000000 *
+GCommandFaultingAddr o=0c68 0x00000000 *
+GVertexFaultingAddr o=0c70 0x00000000 *
+GWriteFaultingAddr o=0c88 0x00000000 *
+GFeedbackSelectCount o=0c98 0x00000000 *
+GGammaProcessorMode o=0cb8 0x00000000 DDX
+GVGAShadow o=0d00 0x00000000 DDX
+GMultGLINTAperture o=0d08 0x00000000 DDX
+GMultGLINT1 o=0d10 0x00000000 DDX
+GMultGLINT2 o=0d18 0x00000000 DDX
+StartXDom t=0000 undefined undefined DDX/3DClient
+dXDom t=0001 undefined undefined DDX/3DClient
+StartXSub t=0002 undefined undefined DDX/3DClient
+dXSub t=0003 undefined undefined DDX/3DClient
+StartY t=0004 undefined undefined DDX/3DClient
+dY t=0005 undefined undefined DDX/3DClient
+GLINTCount t=0006 undefined undefined DDX/3DClient
+PointTable0 t=0010 undefined undefined DDX/3DClient
+PointTable1 t=0011 undefined undefined DDX/3DClient
+PointTable2 t=0012 undefined undefined DDX/3DClient
+PointTable3 t=0013 undefined undefined DDX/3DClient
+RasterizerMode t=0014 undefined undefined DDX/3DClient
+YLimits t=0015 undefined undefined DDX/3DClient
+ScanLineOwnership t=0016 0x00000001 0x00000005 DDX
+PixelSize t=0018 undefined undefined DDX/3DClient
+ScissorMode t=0030 undefined undefined DDX/3DClient
+ScissorMinXY t=0031 undefined undefined DDX/3DClient
+ScissorMaxXY t=0032 undefined undefined DDX/3DClient
+ScreenSize t=0033 undefined undefined DDX/3DClient
+AreaStippleMode t=0034 undefined undefined DDX/3DClient
+LineStippleMode t=0035 undefined undefined DDX/3DClient
+LoadLineStippleCounters t=0036 undefined undefined DDX/3DClient
+WindowOrigin t=0039 undefined undefined DDX/3DClient
+AreaStipplePattern0 t=0040 undefined undefined DDX/3DClient
+AreaStipplePattern1 t=0041 undefined undefined DDX/3DClient
+AreaStipplePattern2 t=0042 undefined undefined DDX/3DClient
+AreaStipplePattern3 t=0043 undefined undefined DDX/3DClient
+AreaStipplePattern4 t=0044 undefined undefined DDX/3DClient
+AreaStipplePattern5 t=0045 undefined undefined DDX/3DClient
+AreaStipplePattern6 t=0046 undefined undefined DDX/3DClient
+AreaStipplePattern7 t=0047 undefined undefined DDX/3DClient
+AreaStipplePattern8 t=0048 undefined undefined DDX/3DClient
+AreaStipplePattern9 t=0049 undefined undefined DDX/3DClient
+AreaStipplePattern10 t=004a undefined undefined DDX/3DClient
+AreaStipplePattern11 t=004b undefined undefined DDX/3DClient
+AreaStipplePattern12 t=004c undefined undefined DDX/3DClient
+AreaStipplePattern13 t=004d undefined undefined DDX/3DClient
+AreaStipplePattern14 t=004e undefined undefined DDX/3DClient
+AreaStipplePattern15 t=004f undefined undefined DDX/3DClient
+AreaStipplePattern16 t=0050 undefined undefined DDX/3DClient
+AreaStipplePattern17 t=0051 undefined undefined DDX/3DClient
+AreaStipplePattern18 t=0052 undefined undefined DDX/3DClient
+AreaStipplePattern19 t=0053 undefined undefined DDX/3DClient
+AreaStipplePattern20 t=0054 undefined undefined DDX/3DClient
+AreaStipplePattern21 t=0055 undefined undefined DDX/3DClient
+AreaStipplePattern22 t=0056 undefined undefined DDX/3DClient
+AreaStipplePattern23 t=0057 undefined undefined DDX/3DClient
+AreaStipplePattern24 t=0058 undefined undefined DDX/3DClient
+AreaStipplePattern25 t=0059 undefined undefined DDX/3DClient
+AreaStipplePattern26 t=005a undefined undefined DDX/3DClient
+AreaStipplePattern27 t=005b undefined undefined DDX/3DClient
+AreaStipplePattern28 t=005c undefined undefined DDX/3DClient
+AreaStipplePattern29 t=005d undefined undefined DDX/3DClient
+AreaStipplePattern30 t=005e undefined undefined DDX/3DClient
+AreaStipplePattern31 t=005f undefined undefined DDX/3DClient
+RouterMode t=0108 undefined undefined DDX/3DClient
+TextureAddressMode t=0070 undefined undefined DDX/3DClient
+SStart t=0071 undefined undefined 3DClient
+dSdx t=0072 undefined undefined 3DClient
+dSdyDom t=0073 undefined undefined 3DClient
+TStart t=0074 undefined undefined 3DClient
+dTdx t=0075 undefined undefined 3DClient
+dTdyDom t=0076 undefined undefined 3DClient
+QStart t=0077 undefined undefined 3DClient
+dQdx t=0078 undefined undefined 3DClient
+dQdyDom t=0079 undefined undefined 3DClient
+LOD t=007a undefined undefined 3DClient
+dSdy t=007b undefined undefined 3DClient
+dTdy t=007c undefined undefined 3DClient
+dQdy t=007d undefined undefined 3DClient
+TextureReadMode t=0090 undefined undefined DDX/3DClient
+TextureFormat t=0091 undefined undefined 3DClient
+TextureCacheControl t=0092 undefined undefined 3DClient
+GLINTBorderColor t=0095 undefined undefined 3DClient
+TexelLUTIndex t=0098 undefined undefined 3DClient
+TexelLUTData t=0099 undefined undefined 3DClient
+TexelLUTAddress t=009a undefined undefined 3DClient
+TexelLUTTransfer t=009b undefined undefined 3DClient
+TextureFilterMode t=009c undefined undefined 3DClient
+TextureChromaUpper t=009d undefined undefined 3DClient
+TextureChromaLower t=009e undefined undefined 3DClient
+TxBaseAddr0 t=00a0 undefined undefined 3DClient
+TxBaseAddr1 t=00a1 undefined undefined 3DClient
+TxBaseAddr2 t=00a2 undefined undefined 3DClient
+TxBaseAddr3 t=00a3 undefined undefined 3DClient
+TxBaseAddr4 t=00a4 undefined undefined 3DClient
+TxBaseAddr5 t=00a5 undefined undefined 3DClient
+TxBaseAddr6 t=00a6 undefined undefined 3DClient
+TxBaseAddr7 t=00a7 undefined undefined 3DClient
+TxBaseAddr8 t=00a8 undefined undefined 3DClient
+TxBaseAddr9 t=00a9 undefined undefined 3DClient
+TxBaseAddr10 t=00aa undefined undefined 3DClient
+TxBaseAddr11 t=00ab undefined undefined 3DClient
+TexelLUT0 t=01d0 undefined undefined 3DClient
+TexelLUT1 t=01d1 undefined undefined 3DClient
+TexelLUT2 t=01d2 undefined undefined 3DClient
+TexelLUT3 t=01d3 undefined undefined 3DClient
+TexelLUT4 t=01d4 undefined undefined 3DClient
+TexelLUT5 t=01d5 undefined undefined 3DClient
+TexelLUT6 t=01d6 undefined undefined 3DClient
+TexelLUT7 t=01d7 undefined undefined 3DClient
+TexelLUT8 t=01d8 undefined undefined 3DClient
+TexelLUT9 t=01d9 undefined undefined 3DClient
+TexelLUT10 t=01da undefined undefined 3DClient
+TexelLUT11 t=01db undefined undefined 3DClient
+TexelLUT12 t=01dc undefined undefined 3DClient
+TexelLUT13 t=01dd undefined undefined 3DClient
+TexelLUT14 t=01de undefined undefined 3DClient
+TexelLUT15 t=01df undefined undefined 3DClient
+Texel0 t=00c0 undefined undefined 3DClient
+Texel1 t=00c1 undefined undefined 3DClient
+Texel2 t=00c2 undefined undefined 3DClient
+Texel3 t=00c3 undefined undefined 3DClient
+Texel4 t=00c4 undefined undefined 3DClient
+Texel5 t=00c5 undefined undefined 3DClient
+Texel6 t=00c6 undefined undefined 3DClient
+Texel7 t=00c7 undefined undefined 3DClient
+Interp0 t=00c8 undefined undefined 3DClient
+Interp1 t=00c9 undefined undefined 3DClient
+Interp2 t=00ca undefined undefined 3DClient
+Interp3 t=00cb undefined undefined 3DClient
+Interp4 t=00cc undefined undefined 3DClient
+TextureFilter t=00cd undefined undefined 3DClient
+TextureColorMode t=00d0 undefined undefined DDX/3DClient
+TextureEnvColor t=00d1 undefined undefined 3DClient
+FogMode t=00d2 undefined undefined DDX/3DClient
+FogColor t=00d3 undefined undefined 3DClient
+FStart t=00d4 undefined undefined 3DClient
+dFdx t=00d5 undefined undefined 3DClient
+dFdyDom t=00d6 undefined undefined 3DClient
+KsStart t=00d9 undefined undefined 3DClient
+dKsdx t=00da undefined undefined 3DClient
+dKsdyDom t=00db undefined undefined 3DClient
+KdStart t=00dc undefined undefined 3DClient
+dKdStart t=00dd undefined undefined 3DClient
+dKddyDom t=00de undefined undefined 3DClient
+RStart t=00f0 undefined undefined 3DClient
+dRdx t=00f1 undefined undefined 3DClient
+dRdyDom t=00f2 undefined undefined 3DClient
+GStart t=00f3 undefined undefined 3DClient
+dGdx t=00f4 undefined undefined 3DClient
+dGdyDom t=00f5 undefined undefined 3DClient
+BStart t=00f6 undefined undefined 3DClient
+dBdx t=00f7 undefined undefined 3DClient
+dBdyDom t=00f8 undefined undefined 3DClient
+AStart t=00f9 undefined undefined 3DClient
+dAdx t=00fa undefined undefined 3DClient
+dAdyDom t=00fb undefined undefined 3DClient
+ColorDDAMode t=00fc undefined undefined DDX/3DClient
+ConstantColor t=00fd undefined undefined 3DClient
+GLINTColor t=00fe undefined undefined DDX/3DClient
+AlphaTestMode t=0100 undefined undefined DDX/3DClient
+AntialiasMode t=0101 undefined undefined DDX/3DClient
+AlphaBlendMode t=0102 undefined undefined DDX/3DClient
+ChromaUpper t=01e1 undefined undefined 3DClient
+ChromaLower t=01e2 undefined undefined 3DClient
+ChromaTestMode t=01e3 undefined undefined 3DClient
+DitherMode t=0103 undefined undefined DDX/3DClient
+FBSoftwareWriteMask t=0104 undefined undefined DDX/3DClient
+LogicalOpMode t=0105 undefined undefined DDX/3DClient
+FBWriteData t=0106 undefined undefined DDX/3DClient
+LBReadMode t=0110 undefined undefined DDX/3DClient
+ Partial Product bit 0-5 need by 3DClient
+LBReadFormat t=0111 set by DDX set by DDX DDX
+LBSourceOffset t=0112 undefined undefined DDX/3DClient
+LBStencil t=0115 undefined undefined *
+LBDepth t=0116 undefined undefined *
+LBWindowBase t=0117 undefined undefined DDX/3DClient
+LBWriteMode t=0118 undefined undefined DDX/3DClient
+LBWriteFormat t=0119 set by DDX set by DDX DDX
+TextureDownloadOffset t=011e undefined undefined DDX/3DClient
+LBWindowOffset t=011f undefined undefined DDX/3DClient
+GLINTWindow t=0130 undefined undefined DDX/3DClient
+StencilMode t=0131 undefined undefined DDX/3DClient
+StencilData t=0132 undefined undefined 3DClient
+GLINTStencil t=0133 undefined undefined 3DClient
+DepthMode t=0134 undefined undefined DDX/3DClient
+GLINTDepth t=0135 undefined undefined DDX/3DClient
+ZStartU t=0136 undefined undefined 3DClient
+ZStartL t=0137 undefined undefined 3DClient
+dZdxU t=0138 undefined undefined 3DClient
+dZdxL t=0139 undefined undefined 3DClient
+dZdyDomU t=013a undefined undefined 3DClient
+dZdyDomL t=013b undefined undefined 3DClient
+FastClearDepth t=013c undefined undefined 3DClient
+FBReadMode t=0150 set by DDX set by DDX DDX/3DClient
+ Partial Product bit 0-5 need by 3DClient
+LBReadFormat t=0111 set by DDX set by DDX DDX
+FBSourceOffset t=0151 undefined undefined DDX/3DClient
+FBPixelOffset t=0152 undefined undefined DDX/3DClient
+FBWindowBase t=0156 undefined undefined DDX/3DClient
+FBWriteMode t=0157 undefined undefined DDX/3DClient
+FBHardwareWriteMask t=0158 undefined undefined DDX/3DClient
+FBBlockColor t=0159 undefined undefined DDX/3DClient
+PatternRamMode t=015f undefined undefined DDX/3DClient
+PatternRamData0 t=0160 undefined undefined DDX/3DClient
+PatternRamData1 t=0161 undefined undefined DDX/3DClient
+PatternRamData2 t=0162 undefined undefined DDX/3DClient
+PatternRamData3 t=0163 undefined undefined DDX/3DClient
+PatternRamData4 t=0164 undefined undefined DDX/3DClient
+PatternRamData5 t=0165 undefined undefined DDX/3DClient
+PatternRamData6 t=0166 undefined undefined DDX/3DClient
+PatternRamData7 t=0167 undefined undefined DDX/3DClient
+PatternRamData8 t=0168 undefined undefined DDX/3DClient
+PatternRamData9 t=0169 undefined undefined DDX/3DClient
+PatternRamData10 t=016a undefined undefined DDX/3DClient
+PatternRamData11 t=016b undefined undefined DDX/3DClient
+PatternRamData12 t=016c undefined undefined DDX/3DClient
+PatternRamData13 t=016d undefined undefined DDX/3DClient
+PatternRamData14 t=016e undefined undefined DDX/3DClient
+PatternRamData15 t=016f undefined undefined DDX/3DClient
+PatternRamData16 t=0170 undefined undefined DDX/3DClient
+PatternRamData17 t=0171 undefined undefined DDX/3DClient
+PatternRamData18 t=0172 undefined undefined DDX/3DClient
+PatternRamData19 t=0173 undefined undefined DDX/3DClient
+PatternRamData20 t=0174 undefined undefined DDX/3DClient
+PatternRamData21 t=0175 undefined undefined DDX/3DClient
+PatternRamData22 t=0176 undefined undefined DDX/3DClient
+PatternRamData23 t=0177 undefined undefined DDX/3DClient
+PatternRamData24 t=0178 undefined undefined DDX/3DClient
+PatternRamData25 t=0179 undefined undefined DDX/3DClient
+PatternRamData26 t=017a undefined undefined DDX/3DClient
+PatternRamData27 t=017b undefined undefined DDX/3DClient
+PatternRamData28 t=017c undefined undefined DDX/3DClient
+PatternRamData29 t=017d undefined undefined DDX/3DClient
+PatternRamData30 t=017e undefined undefined DDX/3DClient
+PatternRamData31 t=017f undefined undefined DDX/3DClient
+FBBlockColorU t=018d undefined undefined DDX/3DClient
+FBBlockColorL t=018e undefined undefined DDX/3DClient
+FilterMode t=0180 undefined undefined DDX/3DClient
+StatisticMode t=0181 undefined undefined DDX/3DClient
+MinRegion t=0182 undefined undefined 3DClient
+MaxRegion t=0183 undefined undefined 3DClient
+KsRStart t=0190 undefined undefined 3DClient
+dKsRdx t=0191 undefined undefined 3DClient
+dKsRdyDom t=0192 undefined undefined 3DClient
+KsGStart t=0193 undefined undefined 3DClient
+dKsGdx t=0194 undefined undefined 3DClient
+dKsGdyDom t=0195 undefined undefined 3DClient
+KsBStart t=0196 undefined undefined 3DClient
+dKsBdx t=0197 undefined undefined 3DClient
+dKsBdyDom t=0198 undefined undefined 3DClient
+KdRStart t=01a0 undefined undefined 3DClient
+dKdRdx t=01a1 undefined undefined 3DClient
+dKdRdyDom t=01a2 undefined undefined 3DClient
+KdGStart t=01a3 undefined undefined 3DClient
+dKdGdx t=01a4 undefined undefined 3DClient
+dKdGdyDom t=01a5 undefined undefined 3DClient
+KdBStart t=01a6 undefined undefined 3DClient
+dKdBdx t=01a7 undefined undefined 3DClient
+dKdBdyDom t=01a8 undefined undefined 3DClient
+
+All Gamma State is undefined and owned by 3DClient driver except for:
+
+BroadcastMask o=026f 0x00000003 DDX/3DClient
+
+All TI RAMDAC State is owned by DDX driver.
diff --git a/README.pm3 b/README.pm3
new file mode 100644
index 0000000..4d6972e
--- /dev/null
+++ b/README.pm3
@@ -0,0 +1,57 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/README.pm3,v 1.13 2002/05/07 23:15:58 alanh Exp $ */
+
+STATUS as of Tue, 8 May 2001 19:01:39 +0200
+
+Working :
+ * Unaccelerated : Depth 8, 15, 16 and 24 are ok. I tested them upto
+ 1280x1024 only as my monitor don't support higher modes.
+ * Endianess clean, thanks to Romain Dolbeau <dolbeaur@club-internet.fr> for
+ helping me debug this.
+ * HW cursor.
+ * ShadowFb.
+ * Full 2D Accels.
+ - Sync.
+ - Pixmap cache.
+ - Offscreen pixmaps.
+ - Clipping.
+ - Screen to screen copy.
+ - Solid fills.
+ - HorVert Solid Lines .
+ - 8x8 Mono Pattern Fills.
+ - Color Expansion Fills.
+ - Images Writes.
+ - Bitmap Writes using direct FIFO writes with or without FIFO Disconnect.
+ - Pixmap Writes using direct FIFO writes with or without FIFO Disconnect.
+ * Appian J2000 second head initialization.
+ * Xv : Hardware video scaler :
+ - Needs checking on a big endian machine.
+ - Needs acceleration to work - there is a hardware bug in YV12 mode.
+ - Support both dual head and single head, trough gamma or permedia3.
+ - NOTE: depth 15 and 16 currently broken as I can't figure out the
+ colorKey equation. From the docs it needs to be padded to 8bits per RGB,
+ but that doesn't seem to work either. FIXME.
+ - Attributes are :
+ - FILTER : None, Partial (X only) or Full filtering.
+ - COLORKEY : Speaks for itself
+ - DOUBLE_BUFFER : Speaks for itself
+ - AUTOPAINT_COLORKEY : Speaks for itself
+ - MIRROR : X and/or Y Axis mirroring. (NOT DONE)
+ - ALPHA : (NOT DONE)
+ - 0 -> FB Only
+ - 1 -> 25% Video, 75% FB
+ - 2 -> 75% Video, 25% FB
+ - 3 -> Video Only
+
+Not Working :
+
+ * [NOT POSSIBLE] 2D Accel :
+ - Solid & Dashed Lines are not possible on glint hardware.
+ - 8x8 Color Pattern Fill is almost never used.
+ - Clipping needs cleaning up.
+ * [TODO] 2D Accel hooks for the Rendering extension :
+ - Render extension initialization.
+ - CPUToScreenTexture.
+ - CPUToScreenAlphaTexture.
+
+Sven Luther <luther@dpt-info.u-strasbg.fr>
+Alan Hourihane <alanh@fairlite.demon.co.uk>
diff --git a/man/glint.man b/man/glint.man
new file mode 100644
index 0000000..166de51
--- /dev/null
+++ b/man/glint.man
@@ -0,0 +1,110 @@
+.\" $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint.man,v 1.6 2003/02/14 12:03:09 alanh Exp $
+.\" shorthand for double quote that works everywhere.
+.ds q \N'34'
+.TH GLINT __drivermansuffix__ __vendorversion__
+.SH NAME
+glint \- GLINT/Permedia video driver
+.SH SYNOPSIS
+.nf
+.B "Section \*qDevice\*q"
+.BI " Identifier \*q" devname \*q
+.B " Driver \*qglint\*q"
+\ \ ...
+.B EndSection
+.fi
+.SH DESCRIPTION
+.B glint
+is an XFree86 driver for 3Dlabs & Texas Instruments GLINT/Permedia based video
+cards. The driver is rather fully accelerated, and provides support for the
+following framebuffer depths: 8, 15 (may give bad results with FBDev support),
+16, 24 (32 bpp recommended, 24 bpp has problems), 30, and an 8+24 overlay mode.
+.SH SUPPORTED HARDWARE
+The
+.B glint
+driver supports 3Dlabs (GLINT MX, GLINT 500TX, GLINT 300SX, GLINT GAMMA,
+GLINT DELTA, GLINT GAMMA2, Permedia, Permedia 2, Permedia 2v, Permedia 3, R3,
+R4) and Texas Instruments (Permedia, Permedia 2) chips.
+.SH CONFIGURATION DETAILS
+Please refer to XF86Config(__filemansuffix__) for general configuration
+details. This section only covers configuration details specific to this
+driver.
+.PP
+The driver auto-detects the chipset type, but the following
+.B ChipSet
+names may optionally be specified in the config file
+.B \*qDevice\*q
+section, and will override the auto-detection:
+.PP
+.RS 4
+"ti_pm2", "ti_pm", "r4", "pm3", "pm2v", "pm2", "pm", "300sx", "500tx", "mx",
+"gamma", "gamma2", "delta"
+.RE
+.PP
+The driver will try to auto-detect the amount of video memory present for all
+chips. If it's not detected correctly, the actual amount of video memory should
+be specified with a
+.B VideoRam
+entry in the config file
+.B \*qDevice\*q
+section.
+.PP
+Additionally, you may need to specify the bus ID of your card with a
+.B BusID
+entry in the config file
+.B \*qDevice\*q
+section, especially with FBDev support.
+.PP
+The following driver
+.B Options
+are supported:
+.TP
+.BI "Option \*qUseFlatPanel\*q \*q" boolean \*q
+Enable the FlatPanel feature on the Permedia3. Default: off.
+.TP
+.BI "Option \*qSWCursor\*q \*q" boolean \*q
+Enable or disable the SW cursor. Default: off.
+This option disables the
+.B HWCursor
+option and vice versa.
+.TP
+.BI "Option \*qNoAccel\*q \*q" boolean \*q
+Disable or enable acceleration. Default: acceleration is enabled.
+.TP
+.BI "Option \*qOverlay\*q"
+Enable 8+24 overlay mode. Only appropriate for depth 24, 32 bpp.
+.RB ( Note:
+This hasn't been tested with FBDev support and probably won't work.)
+Recognized values are: "8,24", "24,8". Default: off.
+.TP
+.BI "Option \*qPciRetry\*q \*q" boolean \*q
+Enable or disable PCI retries.
+.RB ( Note:
+This doesn't work with Permedia2 based cards for Amigas.) Default: off.
+.TP
+.BI "Option \*qShadowFB\*q \*q" boolean \*q
+Enable or disable use of the shadow framebuffer layer.
+.RB ( Note:
+This disables hardware acceleration.) Default: off.
+.TP
+.BI "Option \*qUseFBDev\*q \*q" boolean \*q
+Enable or disable use of an OS-specific fb interface (which is not supported
+on all OSs). See fbdevhw(__drivermansuffix__) for further information.
+Default: off.
+.ig
+.TP
+.BI "Option \*qRGBbits\*q \*q" integer \*q
+Each gun of the RGB triple can have either 8 or 10 bits. Default: 8
+..
+.TP
+.BI "Option \*qBlockWrite\*q \*q" boolean \*q
+Enable or disable block writes for the various Permedia 2 chips. This improves
+acceleration in general, but disables it for some special cases. Default: off.
+.TP
+.BI "Option \*qFireGL3000\*q \*q" boolean \*q
+If you have a card of the same name, turn this on. Default: off.
+.TP
+.SH "SEE ALSO"
+XFree86(1), XF86Config(__filemansuffix__), xf86config(1), Xserver(1), X(__miscmansuffix__)
+.SH AUTHORS
+Authors include: Alan Hourihane, Dirk Hohndel, Stefan Dirsch, Michel Dänzer,
+Sven Luther
diff --git a/src/IBMramdac.c b/src/IBMramdac.c
new file mode 100644
index 0000000..2a41fab
--- /dev/null
+++ b/src/IBMramdac.c
@@ -0,0 +1,125 @@
+/*
+ * Copyright 1998 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ *
+ * glintOutIBMRGBIndReg() and glintInIBMRGBIndReg() are used to access
+ * the indirect IBM RAMDAC registers only.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/IBMramdac.c,v 1.6 1999/02/12 22:52:02 hohndel Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "IBM.h"
+#include "glint_regs.h"
+#include "glint.h"
+
+#define IBMRGB_WRITE_ADDR 0x4000
+#define IBMRGB_RAMDAC_DATA 0x4008
+#define IBMRGB_PIXEL_MASK 0x4010
+#define IBMRGB_READ_ADDR 0x4018
+#define IBMRGB_INDEX_LOW 0x4020
+#define IBMRGB_INDEX_HIGH 0x4028
+#define IBMRGB_INDEX_DATA 0x4030
+#define IBMRGB_INDEX_CONTROL 0x4038
+
+void
+glintOutIBMRGBIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char tmp = 0x00;
+
+ GLINT_SLOW_WRITE_REG((reg>>8) & 0xff, IBMRGB_INDEX_HIGH);
+ GLINT_SLOW_WRITE_REG (reg & 0xFF, IBMRGB_INDEX_LOW);
+
+ if (mask != 0x00)
+ tmp = GLINT_READ_REG (IBMRGB_INDEX_DATA) & mask;
+
+ GLINT_SLOW_WRITE_REG (tmp | data, IBMRGB_INDEX_DATA);
+}
+
+unsigned char
+glintInIBMRGBIndReg (ScrnInfoPtr pScrn, CARD32 reg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char ret;
+
+ GLINT_SLOW_WRITE_REG(reg & 0xFF, IBMRGB_INDEX_LOW);
+ GLINT_SLOW_WRITE_REG((reg>>8) & 0xff, IBMRGB_INDEX_HIGH);
+ ret = GLINT_READ_REG(IBMRGB_INDEX_DATA);
+ return (ret);
+}
+
+void
+glintIBMWriteAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(index, IBMRGB_WRITE_ADDR);
+}
+
+void
+glintIBMWriteData (ScrnInfoPtr pScrn, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(data, IBMRGB_RAMDAC_DATA);
+}
+
+void
+glintIBMReadAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(0xFF, IBMRGB_PIXEL_MASK);
+ GLINT_SLOW_WRITE_REG(index, IBMRGB_READ_ADDR);
+}
+
+unsigned char
+glintIBMReadData (ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ return(GLINT_READ_REG(IBMRGB_RAMDAC_DATA));
+}
+
+Bool
+glintIBMHWCursorInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ xf86CursorInfoPtr infoPtr;
+
+ infoPtr = xf86CreateCursorInfoRec();
+ if(!infoPtr) return FALSE;
+
+ pGlint->CursorInfoRec = infoPtr;
+
+ (*pGlint->RamDac->HWCursorInit)(infoPtr);
+
+ return(xf86InitCursor(pScreen, infoPtr));
+}
diff --git a/src/TIramdac.c b/src/TIramdac.c
new file mode 100644
index 0000000..e471c01
--- /dev/null
+++ b/src/TIramdac.c
@@ -0,0 +1,232 @@
+/*
+ * Copyright 1998-2001 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ *
+ * Modified from IBMramdac.c to support TI RAMDAC routines
+ * by Jens Owen, <jens@tungstengraphics.com>.
+ *
+ * glintOutTIIndReg() and glintInTIIndReg() are used to access
+ * the indirect TI RAMDAC registers only.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/TIramdac.c,v 1.5 2002/10/30 12:52:15 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "TI.h"
+#include "glint_regs.h"
+#include "glint.h"
+
+#define TI_WRITE_ADDR 0x4000
+#define TI_RAMDAC_DATA 0x4008
+#define TI_PIXEL_MASK 0x4010
+#define TI_READ_ADDR 0x4018
+#define TI_CURS_COLOR_WRITE_ADDR 0x4020
+#define TI_CURS_COLOR_DATA 0x4028
+#define TI_CURS_COLOR_READ_ADDR 0x4038
+#define TI_DIRECT_CURS_CTRL 0x4048
+#define TI_INDEX_DATA 0x4050
+#define TI_CURS_RAM_DATA 0x4058
+#define TI_CURS_X_LOW 0x4060
+#define TI_CURS_X_HIGH 0x4068
+#define TI_CURS_Y_LOW 0x4070
+#define TI_CURS_Y_HIGH 0x4078
+
+void
+glintOutTIIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char tmp = 0x00;
+ int offset;
+
+ if ((reg & 0xf0) == 0xa0) { /* this is really a direct register write */
+ offset = TI_WRITE_ADDR + ((reg & 0xf) << 3);
+ if (mask != 0x00)
+ tmp = GLINT_READ_REG(offset) & mask;
+
+ GLINT_SLOW_WRITE_REG(tmp | data, offset);
+ }
+ else { /* normal indirect access */
+ GLINT_SLOW_WRITE_REG(reg & 0xFF, TI_WRITE_ADDR);
+
+ if (mask != 0x00)
+ tmp = GLINT_READ_REG(TI_INDEX_DATA) & mask;
+
+ GLINT_SLOW_WRITE_REG(tmp | data, TI_INDEX_DATA);
+ }
+}
+
+unsigned char
+glintInTIIndReg (ScrnInfoPtr pScrn, CARD32 reg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char ret;
+ int offset;
+
+ if ((reg & 0xf0) == 0xa0) { /* this is really a direct register write */
+ offset = TI_WRITE_ADDR + ((reg & 0xf) << 3);
+ ret = GLINT_READ_REG(offset);
+ }
+ else { /* normal indirect access */
+ GLINT_SLOW_WRITE_REG(reg & 0xFF, TI_WRITE_ADDR);
+ ret = GLINT_READ_REG(TI_INDEX_DATA);
+ }
+
+ return (ret);
+}
+
+void
+glintTIWriteAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(index, TI_WRITE_ADDR);
+}
+
+void
+glintTIWriteData (ScrnInfoPtr pScrn, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(data, TI_RAMDAC_DATA);
+}
+
+void
+glintTIReadAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(0xFF, TI_PIXEL_MASK);
+ GLINT_SLOW_WRITE_REG(index, TI_READ_ADDR);
+}
+
+unsigned char
+glintTIReadData (ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ return(GLINT_READ_REG(TI_RAMDAC_DATA));
+}
+
+Bool
+glintTIHWCursorInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ xf86CursorInfoPtr infoPtr;
+
+ infoPtr = xf86CreateCursorInfoRec();
+ if(!infoPtr) return FALSE;
+
+ pGlint->CursorInfoRec = infoPtr;
+
+ (*pGlint->RamDac->HWCursorInit)(infoPtr);
+
+ return(xf86InitCursor(pScreen, infoPtr));
+}
+
+/* Special cases */
+
+/* GMX2000 */
+void
+GMX2000OutIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ ACCESSCHIP2();
+
+ glintOutTIIndReg(pScrn, reg, mask, data);
+
+ ACCESSCHIP1();
+}
+
+unsigned char
+GMX2000InIndReg (ScrnInfoPtr pScrn, CARD32 reg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char ret;
+
+ ACCESSCHIP2();
+
+ ret = glintInTIIndReg(pScrn, reg);
+
+ ACCESSCHIP1();
+
+ return (ret);
+}
+
+void
+GMX2000WriteAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ ACCESSCHIP2();
+
+ glintTIWriteAddress(pScrn, index);
+
+ ACCESSCHIP1();
+}
+
+void
+GMX2000WriteData (ScrnInfoPtr pScrn, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ ACCESSCHIP2();
+
+ glintTIWriteData(pScrn, data);
+
+ ACCESSCHIP1();
+}
+
+void
+GMX2000ReadAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ ACCESSCHIP2();
+
+ glintTIReadAddress(pScrn, index);
+
+ ACCESSCHIP1();
+}
+
+unsigned char
+GMX2000ReadData (ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char ret;
+
+ ACCESSCHIP2();
+
+ ret = glintTIReadData(pScrn);
+
+ ACCESSCHIP1();
+
+ return (ret);
+}
diff --git a/src/glint.h b/src/glint.h
new file mode 100644
index 0000000..58c1a8c
--- /dev/null
+++ b/src/glint.h
@@ -0,0 +1,365 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint.h,v 1.58 2003/02/17 16:08:28 dawes Exp $ */
+/*
+ * Copyright 1997-2001 by Alan Hourihane <alanh@fairlite.demon.co.uk>
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ */
+#ifndef _GLINT_H_
+#define _GLINT_H_
+
+#include "xaa.h"
+#include "xf86RamDac.h"
+#include "xf86cmap.h"
+#include "xf86i2c.h"
+#include "xf86DDC.h"
+#include "xf86xv.h"
+#ifdef XF86DRI
+#include "xf86drm.h"
+#include "sarea.h"
+#define _XF86DRI_SERVER_
+#include "xf86dri.h"
+#include "dri.h"
+#include "GL/glxint.h"
+#include "glint_dripriv.h"
+#endif
+
+#define GLINT_MAX_MULTI_DEVICES 2
+
+#define VERSION 4000
+#define GLINT_NAME "GLINT"
+#define GLINT_DRIVER_NAME "glint"
+#define GLINT_MAJOR_VERSION 1
+#define GLINT_MINOR_VERSION 0
+#define GLINT_PATCHLEVEL 0
+
+typedef struct {
+ CARD32 glintRegs[0x2000];
+ CARD32 DacRegs[0x100];
+ CARD8 cmap[0x300];
+} GLINTRegRec, *GLINTRegPtr;
+
+#define GLINTPTR(p) ((GLINTPtr)((p)->driverPrivate))
+
+typedef struct {
+ int lastInstance;
+ int refCount;
+} GLINTEntRec, *GLINTEntPtr;
+
+typedef struct {
+ pciVideoPtr PciInfo;
+ pciVideoPtr MultiPciInfo[GLINT_MAX_MULTI_DEVICES];
+ int MultiIndex;
+ int numMultiDevices;
+ int MultiChip;
+ Bool MultiAperture;
+ PCITAG PciTag;
+ EntityInfoPtr pEnt;
+ GLINTEntPtr entityPrivate;
+ RamDacHelperRecPtr RamDac;
+ int Chipset;
+ int ChipRev;
+ int HwBpp;
+ int BppShift;
+ int pprod;
+ CARD32 ForeGroundColor;
+ CARD32 BackGroundColor;
+ int bppalign;
+ CARD32 startxdom;
+ CARD32 startxsub;
+ CARD32 starty;
+ CARD32 count;
+ CARD32 dy;
+ CARD32 x;
+ CARD32 y;
+ CARD32 w;
+ CARD32 h;
+ CARD32 dxdom;
+ int dwords;
+ int cpuheight;
+ int cpucount;
+ CARD32 planemask;
+ int realWidth;
+ CARD32 IOAddress;
+ unsigned long FbAddress;
+ int irq;
+ unsigned char * IOBase;
+ unsigned char * FbBase;
+ long FbMapSize;
+ long IOOffset;
+ DGAModePtr DGAModes;
+ int numDGAModes;
+ Bool DGAactive;
+ int DGAViewportStatus;
+ Bool DoubleBuffer;
+ Bool NoAccel;
+ Bool FBDev;
+ Bool ShadowFB;
+ unsigned char * ShadowPtr;
+ int ShadowPitch;
+ Bool Dac6Bit;
+ Bool HWCursor;
+ Bool ClippingOn;
+ Bool UseBlockWrite;
+ Bool UseFlatPanel;
+ Bool UseFireGL3000;
+ CARD8 VGAdata[65536];
+ Bool STATE;
+ Bool ScanlineDirect;
+ int MXFbSize;
+ CARD32 rasterizerMode;
+ int MinClock;
+ int MaxClock;
+ int RefClock;
+ GLINTRegRec SavedReg[GLINT_MAX_MULTI_DEVICES];
+ GLINTRegRec ModeReg[GLINT_MAX_MULTI_DEVICES];
+ CARD32 AccelFlags;
+ CARD32 ROP;
+ CARD32 FrameBufferReadMode;
+ CARD32 BltScanDirection;
+ CARD32 TexMapFormat;
+ CARD32 PixelWidth;
+ RamDacRecPtr RamDacRec;
+ xf86CursorInfoPtr CursorInfoRec;
+ XAAInfoRecPtr AccelInfoRec;
+ CloseScreenProcPtr CloseScreen;
+ ScreenBlockHandlerProcPtr BlockHandler;
+ GCPtr CurrentGC;
+ DrawablePtr CurrentDrawable;
+ I2CBusPtr DDCBus, VSBus;
+ CARD32 FGCursor;
+ CARD32 BGCursor;
+ CARD8 HardwareCursorPattern[1024];
+ CARD8* XAAScanlineColorExpandBuffers[2];
+ CARD8* ScratchBuffer;
+ CARD32 RasterizerSwap;
+ void (*LoadCursorCallback)(ScrnInfoPtr);
+ void (*CursorColorCallback)(ScrnInfoPtr);
+ CARD32 PM3_PixelSize;
+ CARD32 PM3_Config2D;
+ CARD32 PM3_Render2D;
+ CARD32 PM3_AreaStippleMode;
+ CARD32 PM3_VideoControl;
+ int FIFOSize;
+ int InFifoSpace;
+#ifdef XvExtension
+ void (*VideoTimerCallback)(ScrnInfoPtr, Time);
+ XF86VideoAdaptorPtr adaptor;
+ int videoKey;
+#endif
+#ifdef XF86DRI
+ Bool directRenderingEnabled;
+ Bool PCIMode;
+ DRIInfoPtr pDRIInfo;
+ int drmSubFD;
+ drmBufMapPtr drmBufs; /* Map of DMA buffers */
+ drmRegion agp;
+ drmRegion buffers;
+ int numVisualConfigs;
+ __GLXvisualConfig* pVisualConfigs;
+ GLINTConfigPrivPtr pVisualConfigsPriv;
+ GLINTRegRec DRContextRegs;
+ int DRIctx;
+ unsigned char *buf2D;
+#endif
+ OptionInfoPtr Options;
+ Bool PM3_UsingSGRAM;
+} GLINTRec, *GLINTPtr;
+
+/* Defines for PCI data */
+
+#define PCI_VENDOR_TI_CHIP_PERMEDIA2 \
+ ((PCI_VENDOR_TI << 16) | PCI_CHIP_TI_PERMEDIA2)
+#define PCI_VENDOR_TI_CHIP_PERMEDIA \
+ ((PCI_VENDOR_TI << 16) | PCI_CHIP_TI_PERMEDIA)
+#define PCI_VENDOR_3DLABS_CHIP_PERMEDIA \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_PERMEDIA)
+#define PCI_VENDOR_3DLABS_CHIP_PERMEDIA2 \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_PERMEDIA2)
+#define PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_PERMEDIA2V)
+#define PCI_VENDOR_3DLABS_CHIP_PERMEDIA3 \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_PERMEDIA3)
+#define PCI_VENDOR_3DLABS_CHIP_PERMEDIA4 \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_PERMEDIA4)
+#define PCI_VENDOR_3DLABS_CHIP_R4 \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_R4)
+#define PCI_VENDOR_3DLABS_CHIP_300SX \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_300SX)
+#define PCI_VENDOR_3DLABS_CHIP_500TX \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_500TX)
+#define PCI_VENDOR_3DLABS_CHIP_MX \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_MX)
+#define PCI_VENDOR_3DLABS_CHIP_GAMMA \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_GAMMA)
+#define PCI_VENDOR_3DLABS_CHIP_GAMMA2 \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_GAMMA2)
+#define PCI_VENDOR_3DLABS_CHIP_DELTA \
+ ((PCI_VENDOR_3DLABS << 16) | PCI_CHIP_DELTA)
+
+/* Prototypes */
+
+void Permedia2StoreColors(ColormapPtr pmap, int ndef, xColorItem *pdefs);
+void Permedia2InstallColormap(ColormapPtr pmap);
+void Permedia2UninstallColormap(ColormapPtr pmap);
+int Permedia2ListInstalledColormaps(ScreenPtr pScreen, Colormap *pmaps);
+void Permedia2HandleColormaps(ScreenPtr pScreen, ScrnInfoPtr scrnp);
+void Permedia2RestoreDACValues(ScrnInfoPtr pScrn);
+void Permedia2Restore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+void Permedia2Save(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+Bool Permedia2Init(ScrnInfoPtr pScrn, DisplayModePtr mode);
+void Permedia2PreInit(ScrnInfoPtr pScrn);
+Bool Permedia2AccelInit(ScreenPtr pScreen);
+void Permedia2Sync(ScrnInfoPtr pScrn);
+void Permedia2InitializeEngine(ScrnInfoPtr pScrn);
+Bool Permedia2HWCursorInit(ScreenPtr pScreen);
+
+void PermediaRestore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+void PermediaSave(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+Bool PermediaInit(ScrnInfoPtr pScrn, DisplayModePtr mode);
+Bool PermediaAccelInit(ScreenPtr pScreen);
+void PermediaInitializeEngine(ScrnInfoPtr pScrn);
+void Permedia2VRestore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+void Permedia2VSave(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+Bool Permedia2VInit(ScrnInfoPtr pScrn, DisplayModePtr mode);
+void Permedia2VPreInit(ScrnInfoPtr pScrn);
+Bool Permedia2vHWCursorInit(ScreenPtr pScreen);
+
+void Permedia3PreInit(ScrnInfoPtr pScrn);
+int Permedia3MemorySizeDetect(ScrnInfoPtr pScrn);
+void Permedia3Restore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+void Permedia3Save(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+Bool Permedia3Init(ScrnInfoPtr pScrn, DisplayModePtr mode, GLINTRegPtr pReg);
+Bool Permedia3AccelInit(ScreenPtr pScreen);
+void Permedia3InitializeEngine(ScrnInfoPtr pScrn);
+void Permedia3EnableOffscreen(ScreenPtr pScreen);
+void Permedia3Sync(ScrnInfoPtr pScrn);
+void DualPermedia3Sync(ScrnInfoPtr pScrn);
+void Permedia3InitVideo(ScreenPtr pScreen);
+
+void TXRestore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+void TXSave(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+Bool TXInit(ScrnInfoPtr pScrn, DisplayModePtr mode, GLINTRegPtr glintReg);
+Bool TXAccelInit(ScreenPtr pScreen);
+void TXInitializeEngine(ScrnInfoPtr pScrn);
+
+void SXInitializeEngine(ScrnInfoPtr pScrn);
+Bool SXAccelInit(ScreenPtr pScreen);
+
+void DualMXRestore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+void DualMXSave(ScrnInfoPtr pScrn, GLINTRegPtr glintReg);
+Bool DualMXInit(ScrnInfoPtr pScrn, DisplayModePtr mode);
+Bool DualMXAccelInit(ScreenPtr pScreen);
+void DualMXInitializeEngine(ScrnInfoPtr pScrn);
+
+void glintOutIBMRGBIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data);
+unsigned char glintInIBMRGBIndReg(ScrnInfoPtr pScrn, CARD32 reg);
+void glintIBMWriteAddress(ScrnInfoPtr pScrn, CARD32 index);
+void glintIBMReadAddress(ScrnInfoPtr pScrn, CARD32 index);
+void glintIBMWriteData(ScrnInfoPtr pScrn, unsigned char data);
+Bool glintIBMHWCursorInit(ScreenPtr pScreen);
+unsigned char glintIBMReadData(ScrnInfoPtr pScrn);
+Bool glintIBM526HWCursorInit(ScreenPtr pScreen);
+Bool glintIBM640HWCursorInit(ScreenPtr pScreen);
+
+void glintOutTIIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data);
+unsigned char glintInTIIndReg(ScrnInfoPtr pScrn, CARD32 reg);
+void GMX2000OutIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data);
+unsigned char GMX2000InIndReg(ScrnInfoPtr pScrn, CARD32 reg);
+void glintTIWriteAddress(ScrnInfoPtr pScrn, CARD32 index);
+void glintTIReadAddress(ScrnInfoPtr pScrn, CARD32 index);
+void glintTIWriteData(ScrnInfoPtr pScrn, unsigned char data);
+unsigned char glintTIReadData(ScrnInfoPtr pScrn);
+void GMX2000WriteAddress(ScrnInfoPtr pScrn, CARD32 index);
+void GMX2000ReadAddress(ScrnInfoPtr pScrn, CARD32 index);
+void GMX2000WriteData(ScrnInfoPtr pScrn, unsigned char data);
+unsigned char GMX2000ReadData(ScrnInfoPtr pScrn);
+Bool glintTIHWCursorInit(ScreenPtr pScreen);
+
+void Permedia2OutIndReg(ScrnInfoPtr pScrn,
+ CARD32, unsigned char mask, unsigned char data);
+unsigned char Permedia2InIndReg(ScrnInfoPtr pScrn, CARD32);
+void Permedia2WriteAddress(ScrnInfoPtr pScrn, CARD32 index);
+void Permedia2ReadAddress(ScrnInfoPtr pScrn, CARD32 index);
+void Permedia2WriteData(ScrnInfoPtr pScrn, unsigned char data);
+unsigned char Permedia2ReadData(ScrnInfoPtr pScrn);
+void Permedia2LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices,
+ LOCO *colors, VisualPtr pVisual);
+void Permedia2LoadPalette16(ScrnInfoPtr pScrn, int numColors, int *indices,
+ LOCO *colors, VisualPtr pVisual);
+void Permedia3LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices,
+ LOCO *colors, VisualPtr pVisual);
+void Permedia3LoadPalette16(ScrnInfoPtr pScrn, int numColors, int *indices,
+ LOCO *colors, VisualPtr pVisual);
+void Permedia2I2CUDelay(I2CBusPtr b, int usec);
+void Permedia2I2CPutBits(I2CBusPtr b, int scl, int sda);
+void Permedia2I2CGetBits(I2CBusPtr b, int *scl, int *sda);
+
+void Permedia2VideoInit(ScreenPtr pScreen);
+void Permedia2VideoUninit(ScrnInfoPtr pScrn);
+void Permedia2VideoEnterVT(ScrnInfoPtr pScrn);
+void Permedia2VideoLeaveVT(ScrnInfoPtr pScrn);
+
+void Permedia3VideoInit(ScreenPtr pScreen);
+void Permedia3VideoUninit(ScrnInfoPtr pScrn);
+void Permedia3VideoEnterVT(ScrnInfoPtr pScrn);
+void Permedia3VideoLeaveVT(ScrnInfoPtr pScrn);
+
+void Permedia2vOutIndReg(ScrnInfoPtr pScrn,
+ CARD32, unsigned char mask, unsigned char data);
+unsigned char Permedia2vInIndReg(ScrnInfoPtr pScrn, CARD32);
+
+Bool GLINTSwitchMode(int scrnIndex, DisplayModePtr mode, int flags);
+void GLINTAdjustFrame(int scrnIndex, int x, int y, int flags);
+
+extern int partprodPermedia[];
+extern const char *GLINTint10Symbols[];
+
+Bool GLINTDGAInit(ScreenPtr pScreen);
+
+Bool GLINTDRIScreenInit(ScreenPtr pScreen);
+Bool GLINTDRIFinishScreenInit(ScreenPtr pScreen);
+void GLINTDRICloseScreen(ScreenPtr pScreen);
+Bool GLINTInitGLXVisuals(ScreenPtr pScreen);
+void GLINTDRIWakeupHandler(ScreenPtr pScreen);
+void GLINTDRIBlockHandler(ScreenPtr pScreen);
+void GLINTDRIInitBuffers(WindowPtr pWin, RegionPtr prgn, CARD32 index);
+void GLINTDRIMoveBuffers(WindowPtr pWin, DDXPointRec ptOldOrg,
+ RegionPtr prgnSrc, CARD32 index);
+
+void GLINT_VERB_WRITE_REG(GLINTPtr, CARD32 v, int r, char *file, int line);
+CARD32 GLINT_VERB_READ_REG(GLINTPtr, CARD32 r, char *file, int line);
+
+void GLINTRefreshArea(ScrnInfoPtr pScrn, int num, BoxPtr pbox);
+
+void GLINT_MoveBYTE(CARD32* dest, unsigned char* src, int dwords);
+void GLINT_MoveWORDS(CARD32* dest, unsigned short* src, int dwords);
+void GLINT_MoveDWORDS(CARD32* dest, CARD32* src, int dwords);
+
+int Shiftbpp(ScrnInfoPtr pScrn, int value);
+#endif /* _GLINT_H_ */
diff --git a/src/glint_common.h b/src/glint_common.h
new file mode 100644
index 0000000..4845be7
--- /dev/null
+++ b/src/glint_common.h
@@ -0,0 +1,63 @@
+/* glint_common.h -- common header definitions for Gamma 2D/3D/DRM suite
+ *
+ * Copyright 2002 Tungsten Graphics, Inc., Cedar Park, Texas.
+ * All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ *
+ * Converted to common header format:
+ * Jens Owen <jens@tungstengraphics.com>
+ *
+ * $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_common.h,v 1.1 2002/10/30 12:52:15 alanh Exp $
+ *
+ */
+
+#ifndef _GLINT_COMMON_H_
+#define _GLINT_COMMON_H_
+
+/*
+ * WARNING: If you change any of these defines, make sure to change
+ * the kernel include file as well (gamma_drm.h)
+ */
+
+/* Driver specific DRM command indices
+ * NOTE: these are not OS specific, but they are driver specific
+ */
+#define DRM_GAMMA_INIT 0x00
+#define DRM_GAMMA_COPY 0x01
+
+typedef struct {
+ enum {
+ GAMMA_INIT_DMA = 0x01,
+ GAMMA_CLEANUP_DMA = 0x02
+ } func;
+ int sarea_priv_offset;
+ int pcimode;
+ unsigned int mmio0;
+ unsigned int mmio1;
+ unsigned int mmio2;
+ unsigned int mmio3;
+ unsigned int buffers_offset;
+} drmGAMMAInit;
+
+extern int drmGAMMAInitDMA( int fd, drmGAMMAInit *info );
+extern int drmGAMMACleanupDMA( int fd );
+
+#endif
diff --git a/src/glint_dga.c b/src/glint_dga.c
new file mode 100644
index 0000000..ece7657
--- /dev/null
+++ b/src/glint_dga.c
@@ -0,0 +1,273 @@
+/*
+ * Copyright 2000-2001 by Alan Hourihane, Sychdyn, North Wales, UK.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_dga.c,v 1.4 2001/12/16 21:36:50 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+#include "xf86Pci.h"
+#include "xf86PciInfo.h"
+#include "xaa.h"
+#include "xaalocal.h"
+#include "glint.h"
+#include "glint_regs.h"
+#include "dgaproc.h"
+
+static Bool GLINT_OpenFramebuffer(ScrnInfoPtr, char **, unsigned char **,
+ int *, int *, int *);
+static Bool GLINT_SetMode(ScrnInfoPtr, DGAModePtr);
+static void GLINT_Sync(ScrnInfoPtr);
+static int GLINT_GetViewport(ScrnInfoPtr);
+static void GLINT_SetViewport(ScrnInfoPtr, int, int, int);
+static void GLINT_FillRect(ScrnInfoPtr, int, int, int, int, unsigned long);
+static void GLINT_BlitRect(ScrnInfoPtr, int, int, int, int, int, int);
+
+static
+DGAFunctionRec GLINTDGAFuncs = {
+ GLINT_OpenFramebuffer,
+ NULL,
+ GLINT_SetMode,
+ GLINT_SetViewport,
+ GLINT_GetViewport,
+ GLINT_Sync,
+ GLINT_FillRect,
+ GLINT_BlitRect,
+ NULL
+};
+
+Bool
+GLINTDGAInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ DGAModePtr modes = NULL, newmodes = NULL, currentMode;
+ DisplayModePtr pMode, firstMode;
+ int Bpp = pScrn->bitsPerPixel >> 3;
+ int num = 0;
+ Bool oneMore;
+
+ pMode = firstMode = pScrn->modes;
+
+ while(pMode) {
+
+ if(0 /*pScrn->displayWidth != pMode->HDisplay*/) {
+ newmodes = xrealloc(modes, (num + 2) * sizeof(DGAModeRec));
+ oneMore = TRUE;
+ } else {
+ newmodes = xrealloc(modes, (num + 1) * sizeof(DGAModeRec));
+ oneMore = FALSE;
+ }
+
+ if(!newmodes) {
+ xfree(modes);
+ return FALSE;
+ }
+ modes = newmodes;
+
+SECOND_PASS:
+
+ currentMode = modes + num;
+ num++;
+
+ currentMode->mode = pMode;
+ currentMode->flags = DGA_CONCURRENT_ACCESS | DGA_PIXMAP_AVAILABLE;
+ if(!pGlint->NoAccel)
+ currentMode->flags |= DGA_FILL_RECT | DGA_BLIT_RECT;
+ if(pMode->Flags & V_DBLSCAN)
+ currentMode->flags |= DGA_DOUBLESCAN;
+ if(pMode->Flags & V_INTERLACE)
+ currentMode->flags |= DGA_INTERLACED;
+ currentMode->byteOrder = pScrn->imageByteOrder;
+ currentMode->depth = pScrn->depth;
+ currentMode->bitsPerPixel = pScrn->bitsPerPixel;
+ currentMode->red_mask = pScrn->mask.red;
+ currentMode->green_mask = pScrn->mask.green;
+ currentMode->blue_mask = pScrn->mask.blue;
+ currentMode->visualClass = (Bpp == 1) ? PseudoColor : TrueColor;
+ currentMode->viewportWidth = pMode->HDisplay;
+ currentMode->viewportHeight = pMode->VDisplay;
+ currentMode->xViewportStep = 1;
+ currentMode->yViewportStep = 1;
+ currentMode->viewportFlags = DGA_FLIP_RETRACE;
+ currentMode->offset = 0;
+ currentMode->address = pGlint->FbBase;
+
+ if(oneMore) { /* first one is narrow width */
+ currentMode->bytesPerScanline = ((pMode->HDisplay * Bpp) + 3) & ~3L;
+ currentMode->imageWidth = pMode->HDisplay;
+ currentMode->imageHeight = pMode->VDisplay;
+ currentMode->pixmapWidth = currentMode->imageWidth;
+ currentMode->pixmapHeight = currentMode->imageHeight;
+ currentMode->maxViewportX = currentMode->imageWidth -
+ currentMode->viewportWidth;
+ /* this might need to get clamped to some maximum */
+ currentMode->maxViewportY = currentMode->imageHeight -
+ currentMode->viewportHeight;
+ oneMore = FALSE;
+ goto SECOND_PASS;
+ } else {
+ currentMode->bytesPerScanline =
+ ((pScrn->displayWidth * Bpp) + 3) & ~3L;
+ currentMode->imageWidth = pScrn->displayWidth;
+ currentMode->imageHeight = pMode->VDisplay;
+ currentMode->pixmapWidth = currentMode->imageWidth;
+ currentMode->pixmapHeight = currentMode->imageHeight;
+ currentMode->maxViewportX = currentMode->imageWidth -
+ currentMode->viewportWidth;
+ /* this might need to get clamped to some maximum */
+ currentMode->maxViewportY = currentMode->imageHeight -
+ currentMode->viewportHeight;
+ }
+
+ pMode = pMode->next;
+ if(pMode == firstMode)
+ break;
+ }
+
+ pGlint->numDGAModes = num;
+ pGlint->DGAModes = modes;
+
+ return DGAInit(pScreen, &GLINTDGAFuncs, modes, num);
+}
+
+
+static Bool
+GLINT_SetMode(
+ ScrnInfoPtr pScrn,
+ DGAModePtr pMode
+){
+ static int OldDisplayWidth[MAXSCREENS];
+ int index = pScrn->pScreen->myNum;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if(!pMode) { /* restore the original mode */
+ /* put the ScreenParameters back */
+
+ pScrn->displayWidth = OldDisplayWidth[index];
+
+ GLINTSwitchMode(index, pScrn->currentMode, 0);
+ pGlint->DGAactive = FALSE;
+ } else {
+ if(!pGlint->DGAactive) { /* save the old parameters */
+ OldDisplayWidth[index] = pScrn->displayWidth;
+
+ pGlint->DGAactive = TRUE;
+ }
+
+ pScrn->displayWidth = pMode->bytesPerScanline /
+ (pMode->bitsPerPixel >> 3);
+
+ GLINTSwitchMode(index, pMode->mode, 0);
+ }
+
+ return TRUE;
+}
+
+static int
+GLINT_GetViewport(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ return pGlint->DGAViewportStatus;
+}
+
+static void
+GLINT_SetViewport(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int flags
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINTAdjustFrame(pScrn->pScreen->myNum, x, y, flags);
+ pGlint->DGAViewportStatus = 0; /* GLINTAdjustFrame loops until finished */
+}
+
+static void
+GLINT_FillRect (
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned long color
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if(pGlint->AccelInfoRec) {
+ (*pGlint->AccelInfoRec->SetupForSolidFill)(pScrn, color, GXcopy, ~0);
+ (*pGlint->AccelInfoRec->SubsequentSolidFillRect)(pScrn, x, y, w, h);
+ SET_SYNC_FLAG(pGlint->AccelInfoRec);
+ }
+}
+
+static void
+GLINT_Sync(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if(pGlint->AccelInfoRec) {
+ (*pGlint->AccelInfoRec->Sync)(pScrn);
+ }
+}
+
+static void
+GLINT_BlitRect(
+ ScrnInfoPtr pScrn,
+ int srcx, int srcy,
+ int w, int h,
+ int dstx, int dsty
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if(pGlint->AccelInfoRec) {
+ int xdir = ((srcx < dstx) && (srcy == dsty)) ? -1 : 1;
+ int ydir = (srcy < dsty) ? -1 : 1;
+
+ (*pGlint->AccelInfoRec->SetupForScreenToScreenCopy)(
+ pScrn, xdir, ydir, GXcopy, ~0, -1);
+ (*pGlint->AccelInfoRec->SubsequentScreenToScreenCopy)(
+ pScrn, srcx, srcy, dstx, dsty, w, h);
+ SET_SYNC_FLAG(pGlint->AccelInfoRec);
+ }
+}
+
+static Bool
+GLINT_OpenFramebuffer(
+ ScrnInfoPtr pScrn,
+ char **name,
+ unsigned char **mem,
+ int *size,
+ int *offset,
+ int *flags
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ *name = NULL; /* no special device */
+ *mem = (unsigned char*)pGlint->FbAddress;
+ *size = pGlint->FbMapSize;
+ *offset = 0;
+ *flags = DGA_NEED_ROOT;
+
+ return TRUE;
+}
diff --git a/src/glint_dri.c b/src/glint_dri.c
new file mode 100644
index 0000000..506fb7e
--- /dev/null
+++ b/src/glint_dri.c
@@ -0,0 +1,1955 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_dri.c,v 1.32 2003/02/10 13:20:10 alanh Exp $ */
+/**************************************************************************
+
+Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
+All Rights Reserved.
+
+Permission is hereby granted, free of charge, to any person obtaining a
+copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sub license, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice (including the
+next paragraph) shall be included in all copies or substantial portions
+of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
+ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+
+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+**************************************************************************/
+
+/*
+ * Authors:
+ * Jens Owen <jens@tungstengraphics.com>
+ * Alan Hourihane <alanh@fairlite.demon.co.uk>
+ *
+ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+#include "xf86Priv.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+#include "fb.h"
+
+#include "miline.h"
+
+#include "GL/glxtokens.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+#include "glint_dri.h"
+
+static char GLINTKernelDriverName[] = "gamma";
+static char GLINTClientDriverName[] = "gamma";
+
+static void GLINTDestroyContext(ScreenPtr pScreen, drmContext hwContext,
+ DRIContextType contextStore);
+
+
+static unsigned int mylog2( unsigned int n )
+{
+ unsigned int log2 = 1;
+ while ( n > 1 ) n >>= 1, log2++;
+ return log2;
+}
+
+static int
+GLINTDRIControlInit(int drmSubFD, int irq)
+{
+ int retcode;
+
+ if ((retcode = drmCtlInstHandler(drmSubFD, irq))) return 1;
+ return 0;
+}
+
+static Bool
+GLINTInitVisualConfigs(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int numConfigs = 0;
+ __GLXvisualConfig *pConfigs = NULL;
+ GLINTConfigPrivPtr pGlintConfigs = NULL;
+ GLINTConfigPrivPtr *pGlintConfigPtrs = NULL;
+ int db, depth, stencil, accum;
+ int i;
+
+ switch ( pScrn->depth ) {
+ case 15:
+ numConfigs = 8;
+
+ pConfigs = (__GLXvisualConfig*)xnfcalloc( sizeof(__GLXvisualConfig),
+ numConfigs );
+ if ( !pConfigs ) {
+ return FALSE;
+ }
+
+ pGlintConfigs = (GLINTConfigPrivPtr)xnfcalloc( sizeof(GLINTConfigPrivRec),
+ numConfigs );
+ if ( !pGlintConfigs ) {
+ xfree( pConfigs );
+ return FALSE;
+ }
+
+ pGlintConfigPtrs = (GLINTConfigPrivPtr*)xnfcalloc( sizeof(GLINTConfigPrivPtr),
+ numConfigs );
+ if ( !pGlintConfigPtrs ) {
+ xfree( pConfigs );
+ xfree( pGlintConfigs );
+ return FALSE;
+ }
+
+ for ( i = 0 ; i < numConfigs ; i++ ) {
+ pGlintConfigPtrs[i] = &pGlintConfigs[i];
+ }
+
+ i = 0;
+ depth = 1;
+ for ( accum = 0 ; accum <= 1 ; accum++ ) {
+ for ( stencil = 0 ; stencil <= 1 ; stencil++ ) {
+ for ( db = 1 ; db >= 0 ; db-- ) {
+ pConfigs[i].vid = -1;
+ pConfigs[i].class = -1;
+ pConfigs[i].rgba = TRUE;
+ pConfigs[i].redSize = 5;
+ pConfigs[i].greenSize = 5;
+ pConfigs[i].blueSize = 5;
+ pConfigs[i].alphaSize = 1;
+ pConfigs[i].redMask = 0x00007C00;
+ pConfigs[i].greenMask = 0x000003E0;
+ pConfigs[i].blueMask = 0x0000001F;
+ pConfigs[i].alphaMask = 0x00008000;
+ if ( accum ) {
+ pConfigs[i].accumRedSize = 16;
+ pConfigs[i].accumGreenSize = 16;
+ pConfigs[i].accumBlueSize = 16;
+ pConfigs[i].accumAlphaSize = 0;
+ } else {
+ pConfigs[i].accumRedSize = 0;
+ pConfigs[i].accumGreenSize = 0;
+ pConfigs[i].accumBlueSize = 0;
+ pConfigs[i].accumAlphaSize = 0;
+ }
+ if ( db ) {
+ pConfigs[i].doubleBuffer = TRUE;
+ } else {
+ pConfigs[i].doubleBuffer = FALSE;
+ }
+ pConfigs[i].stereo = FALSE;
+ pConfigs[i].bufferSize = 20;
+ if ( depth ) {
+ pConfigs[i].depthSize = 16;
+ } else {
+ pConfigs[i].depthSize = 0;
+ }
+ if ( stencil ) {
+ pConfigs[i].stencilSize = 8;
+ } else {
+ pConfigs[i].stencilSize = 0;
+ }
+ pConfigs[i].auxBuffers = 0;
+ pConfigs[i].level = 0;
+ if ( accum || stencil ) {
+ pConfigs[i].visualRating = GLX_SLOW_VISUAL_EXT;
+ } else {
+ pConfigs[i].visualRating = GLX_NONE_EXT;
+ }
+ pConfigs[i].transparentPixel = 0;
+ pConfigs[i].transparentRed = 0;
+ pConfigs[i].transparentGreen = 0;
+ pConfigs[i].transparentBlue = 0;
+ pConfigs[i].transparentAlpha = 0;
+ pConfigs[i].transparentIndex = 0;
+ i++;
+ }
+ }
+ }
+ if ( i != numConfigs ) {
+ xf86DrvMsg( pScrn->scrnIndex, X_ERROR,
+ "[drm] Incorrect initialization of visuals\n" );
+ return FALSE;
+ }
+ break;
+
+ case 24:
+ numConfigs = 8;
+
+ pConfigs = (__GLXvisualConfig*)xnfcalloc( sizeof(__GLXvisualConfig),
+ numConfigs );
+ if ( !pConfigs ) {
+ return FALSE;
+ }
+
+ pGlintConfigs = (GLINTConfigPrivPtr)xnfcalloc( sizeof(GLINTConfigPrivRec),
+ numConfigs );
+ if ( !pGlintConfigs ) {
+ xfree( pConfigs );
+ return FALSE;
+ }
+
+ pGlintConfigPtrs = (GLINTConfigPrivPtr*)xnfcalloc( sizeof(GLINTConfigPrivPtr),
+ numConfigs );
+ if ( !pGlintConfigPtrs ) {
+ xfree( pConfigs );
+ xfree( pGlintConfigs );
+ return FALSE;
+ }
+
+ for ( i = 0 ; i < numConfigs ; i++ ) {
+ pGlintConfigPtrs[i] = &pGlintConfigs[i];
+ }
+
+ i = 0;
+ for ( accum = 0 ; accum <= 1 ; accum++ ) {
+ for ( depth = 0 ; depth <= 1 ; depth++ ) { /* and stencil */
+ for ( db = 1 ; db >= 0 ; db-- ) {
+ pConfigs[i].vid = -1;
+ pConfigs[i].class = -1;
+ pConfigs[i].rgba = TRUE;
+ pConfigs[i].redSize = 8;
+ pConfigs[i].greenSize = 8;
+ pConfigs[i].blueSize = 8;
+ pConfigs[i].alphaSize = 0;
+ pConfigs[i].redMask = 0x00FF0000;
+ pConfigs[i].greenMask = 0x0000FF00;
+ pConfigs[i].blueMask = 0x000000FF;
+ pConfigs[i].alphaMask = 0;
+ if ( accum ) {
+ pConfigs[i].accumRedSize = 16;
+ pConfigs[i].accumGreenSize = 16;
+ pConfigs[i].accumBlueSize = 16;
+ pConfigs[i].accumAlphaSize = 0;
+ } else {
+ pConfigs[i].accumRedSize = 0;
+ pConfigs[i].accumGreenSize = 0;
+ pConfigs[i].accumBlueSize = 0;
+ pConfigs[i].accumAlphaSize = 0;
+ }
+ if ( db ) {
+ pConfigs[i].doubleBuffer = TRUE;
+ } else {
+ pConfigs[i].doubleBuffer = FALSE;
+ }
+ pConfigs[i].stereo = FALSE;
+ pConfigs[i].bufferSize = 24;
+ if ( depth ) {
+ pConfigs[i].depthSize = 16;
+ pConfigs[i].stencilSize = 8;
+ }
+ else {
+ pConfigs[i].depthSize = 0;
+ pConfigs[i].stencilSize = 0;
+ }
+ pConfigs[i].auxBuffers = 0;
+ pConfigs[i].level = 0;
+ if ( accum ) {
+ pConfigs[i].visualRating = GLX_SLOW_VISUAL_EXT;
+ } else {
+ pConfigs[i].visualRating = GLX_NONE_EXT;
+ }
+ pConfigs[i].transparentPixel = 0;
+ pConfigs[i].transparentRed = 0;
+ pConfigs[i].transparentGreen = 0;
+ pConfigs[i].transparentBlue = 0;
+ pConfigs[i].transparentAlpha = 0;
+ pConfigs[i].transparentIndex = 0;
+ i++;
+ }
+ }
+ }
+ if ( i != numConfigs ) {
+ xf86DrvMsg( pScrn->scrnIndex, X_ERROR,
+ "[drm] Incorrect initialization of visuals\n" );
+ return FALSE;
+ }
+ break;
+
+ default: /* Can't do depth 8 or 16, just 15 or 24 */
+ return FALSE;
+ break;
+ }
+
+ pGlint->numVisualConfigs = numConfigs;
+ pGlint->pVisualConfigs = pConfigs;
+ pGlint->pVisualConfigsPriv = pGlintConfigs;
+ GlxSetVisualConfigs(numConfigs, pConfigs, (void **)pGlintConfigPtrs);
+
+ return TRUE;
+}
+
+static Bool GLINTDRIAgpInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int ret, count;
+ CARD32 mode;
+
+ /* FIXME: Make these configurable...
+ */
+ pGlint->agp.size = 2 * 1024 * 1024;
+ pGlint->buffers.offset = 0;
+ pGlint->buffers.size = GLINT_DRI_BUF_COUNT * GLINT_DRI_BUF_SIZE;
+
+ if ( drmAgpAcquire( pGlint->drmSubFD ) < 0 ) {
+ xf86DrvMsg( pScreen->myNum, X_ERROR, "[agp] AGP not available\n" );
+ return FALSE;
+ }
+
+ /* Read AGP Capabilities */
+ mode = drmAgpGetMode(pGlint->drmSubFD) & ~0x03; /* Mask Host capabilities */
+
+ mode |= 0x01; /* Gamma only supports AGP 1x */
+
+ /* Now enable AGP only on the specified BusID */
+ if ( drmAgpEnable( pGlint->drmSubFD, mode ) < 0 ) {
+ xf86DrvMsg( pScreen->myNum, X_ERROR, "[agp] AGP not enabled\n" );
+ drmAgpRelease( pGlint->drmSubFD );
+ return FALSE;
+ }
+
+ ret = drmAgpAlloc( pGlint->drmSubFD, pGlint->agp.size, 0, NULL,
+ &pGlint->agp.handle);
+
+ if ( ret < 0 ) {
+ xf86DrvMsg( pScreen->myNum, X_ERROR, "[agp] Out of memory (%d)\n", ret );
+ drmAgpRelease( pGlint->drmSubFD );
+ return FALSE;
+ }
+ xf86DrvMsg( pScreen->myNum, X_INFO,
+ "[agp] %d kB allocated with handle 0x%08x\n",
+ pGlint->agp.size/1024, pGlint->agp.handle );
+
+ if ( drmAgpBind( pGlint->drmSubFD, pGlint->agp.handle, 0 ) < 0 ) {
+ xf86DrvMsg( pScreen->myNum, X_ERROR, "[agp] Could not bind memory\n" );
+ drmAgpFree( pGlint->drmSubFD, pGlint->agp.handle );
+ drmAgpRelease( pGlint->drmSubFD );
+ return FALSE;
+ }
+
+ /* DMA buffers
+ */
+ if ( drmAddMap( pGlint->drmSubFD, pGlint->buffers.offset,
+ pGlint->buffers.size, DRM_AGP, 0,
+ &pGlint->buffers.handle ) < 0 ) {
+ xf86DrvMsg( pScreen->myNum, X_ERROR,
+ "[agp] Could not add DMA buffers mapping\n" );
+ return FALSE;
+ }
+ xf86DrvMsg( pScreen->myNum, X_INFO,
+ "[agp] DMA buffers handle = 0x%08lx\n",
+ pGlint->buffers.handle );
+
+ if ( drmMap( pGlint->drmSubFD, pGlint->buffers.handle,
+ pGlint->buffers.size, &pGlint->buffers.map ) < 0 ) {
+ xf86DrvMsg( pScreen->myNum, X_ERROR,
+ "[agp] Could not map DMA buffers\n" );
+ return FALSE;
+ }
+ xf86DrvMsg( pScreen->myNum, X_INFO,
+ "[agp] DMA buffers mapped at 0x%08lx\n", pGlint->buffers.map);
+
+ count = drmAddBufs( pGlint->drmSubFD,
+ GLINT_DRI_BUF_COUNT, GLINT_DRI_BUF_SIZE,
+ DRM_AGP_BUFFER, pGlint->buffers.offset );
+ if ( count <= 0 ) {
+ xf86DrvMsg( pScrn->scrnIndex, X_INFO,
+ "[drm] failure adding %d %d byte DMA buffers\n",
+ GLINT_DRI_BUF_COUNT, GLINT_DRI_BUF_SIZE );
+ return FALSE;
+ }
+ xf86DrvMsg( pScreen->myNum, X_INFO,
+ "[drm] Added %d %d byte DMA buffers\n",
+ count, GLINT_DRI_BUF_SIZE );
+
+ {
+ int bufs;
+
+ if ((bufs = drmAddBufs(pGlint->drmSubFD,
+ 1,
+ 8192, /* 8K = 8MB physical memory */
+ 0,
+ DRM_RESTRICTED /* flags */)) <= 0) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] 0x%x failure adding page table buffer\n",bufs);
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] added 1 page table buffer\n");
+ }
+
+ pGlint->PCIMode = FALSE;
+
+ return TRUE;
+}
+
+static Bool GLINTDRIKernelInit( ScreenPtr pScreen )
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ DRIInfoPtr pDRIInfo = pGlint->pDRIInfo;
+ GLINTDRIPtr pGlintDRI = pDRIInfo->devPrivate;
+ drmGAMMAInit init;
+ int ret;
+
+ memset( &init, 0, sizeof(drmGAMMAInit) );
+
+ init.func = GAMMA_INIT_DMA;
+ init.sarea_priv_offset = sizeof(XF86DRISAREARec);
+
+ init.mmio0 = pGlintDRI->registers0.handle;
+ init.mmio1 = pGlintDRI->registers1.handle;
+ init.mmio2 = pGlintDRI->registers2.handle;
+ init.mmio3 = pGlintDRI->registers3.handle;
+
+ if (!pGlint->PCIMode) {
+ init.pcimode = 0;
+ init.buffers_offset = pGlint->buffers.handle;
+ } else {
+ init.pcimode = 1;
+ }
+
+ ret = drmCommandWrite( pGlint->drmSubFD, DRM_GAMMA_INIT,
+ &init, sizeof(drmGAMMAInit) );
+
+ if ( ret < 0 ) {
+ xf86DrvMsg( pScrn->scrnIndex, X_ERROR,
+ "[drm] Failed to initialize DMA! (%d)\n", ret );
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+Bool
+GLINTDRIScreenInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ DRIInfoPtr pDRIInfo;
+ GLINTDRIPtr pGlintDRI;
+ int dmabufs = 0;
+
+ /* Check that the GLX, DRI, and DRM modules have been loaded by testing
+ for canonical symbols in each module. */
+ if (!xf86LoaderCheckSymbol("GlxSetVisualConfigs")) return FALSE;
+ if (!xf86LoaderCheckSymbol("DRIScreenInit")) return FALSE;
+ if (!xf86LoaderCheckSymbol("drmAvailable")) return FALSE;
+ if (!xf86LoaderCheckSymbol("DRIQueryVersion")) {
+ xf86DrvMsg(pScreen->myNum, X_ERROR,
+ "[dri] GLINTDRIScreenInit failed (libdri.a too old)\n");
+ return FALSE;
+ }
+
+ /* Check the DRI version */
+ {
+ int major, minor, patch;
+ DRIQueryVersion(&major, &minor, &patch);
+ if (major != 4 || minor < 0) {
+ xf86DrvMsg(pScreen->myNum, X_ERROR,
+ "[dri] GLINTDRIScreenInit failed because of a version mismatch.\n"
+ "[dri] libDRI version is %d.%d.%d but version 4.0.x is needed.\n"
+ "[dri] Disabling DRI.\n",
+ major, minor, patch);
+ return FALSE;
+ }
+ }
+
+ if (pGlint->Chipset != PCI_VENDOR_3DLABS_CHIP_GAMMA) return FALSE;
+
+ if (pGlint->numMultiDevices > 2) return FALSE;
+
+ if (pGlint->MultiChip != PCI_CHIP_MX) return FALSE;
+
+ pDRIInfo = DRICreateInfoRec();
+ if(pDRIInfo == NULL)
+ return FALSE;
+
+ pGlint->pDRIInfo = pDRIInfo;
+
+ /* setup device info */
+ pDRIInfo->drmDriverName = GLINTKernelDriverName;
+ pDRIInfo->clientDriverName = GLINTClientDriverName;
+ pDRIInfo->busIdString = xalloc(64); /* Freed in DRIDestroyInfoRec */
+ sprintf(pDRIInfo->busIdString, "PCI:%d:%d:%d",
+ ((pciConfigPtr)pGlint->PciInfo->thisCard)->busnum,
+ ((pciConfigPtr)pGlint->PciInfo->thisCard)->devnum,
+ ((pciConfigPtr)pGlint->PciInfo->thisCard)->funcnum);
+ pDRIInfo->ddxDriverMajorVersion = GLINT_MAJOR_VERSION;
+ pDRIInfo->ddxDriverMinorVersion = GLINT_MINOR_VERSION;
+ pDRIInfo->ddxDriverPatchVersion = GLINT_PATCHLEVEL;
+ pDRIInfo->frameBufferPhysicalAddress = pGlint->FbAddress;
+ pDRIInfo->frameBufferSize = pGlint->FbMapSize;
+ pDRIInfo->frameBufferStride =
+ pScrn->displayWidth * (pScrn->bitsPerPixel >> 3);
+ pDRIInfo->ddxDrawableTableEntry = GLINT_MAX_DRAWABLES;
+
+ /* MAX_DRAWABLES set to number of GID's minus one for DDX */
+ if (SAREA_MAX_DRAWABLES < GLINT_MAX_DRAWABLES) {
+ pDRIInfo->maxDrawableTableEntry = SAREA_MAX_DRAWABLES;
+ }
+ else {
+ pDRIInfo->maxDrawableTableEntry = GLINT_MAX_DRAWABLES;
+ }
+
+#ifdef NOT_DONE
+ /* FIXME need to extend DRI protocol to pass this size back to client
+ * for SAREA mapping that includes a device private record
+ */
+ pDRIInfo->SAREASize =
+ ((sizeof(XF86DRISAREARec) + 0xfff) & 0x1000); /* round to page */
+ /* + shared memory device private rec */
+#else
+ /* For now the mapping works by using a fixed size defined
+ * in the SAREA header
+ */
+ pDRIInfo->SAREASize = SAREA_MAX;
+#endif
+
+ if (!(pGlintDRI = (GLINTDRIPtr)xcalloc(sizeof(GLINTDRIRec),1))) {
+ DRIDestroyInfoRec(pGlint->pDRIInfo);
+ return FALSE;
+ }
+
+ /* setup visual configurations */
+ if (!(GLINTInitVisualConfigs(pScreen))) {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "visual configs initialized\n" );
+
+ pDRIInfo->devPrivate = pGlintDRI;
+ pDRIInfo->devPrivateSize = sizeof(GLINTDRIRec);
+ pDRIInfo->contextSize = sizeof(GLINTDRIContextRec);
+
+ /* setup call backs */
+ pDRIInfo->CreateContext = GLINTCreateContext;
+ pDRIInfo->DestroyContext = GLINTDestroyContext;
+ pDRIInfo->SwapContext = GLINTDRISwapContext;
+ pDRIInfo->InitBuffers = GLINTDRIInitBuffers;
+ pDRIInfo->MoveBuffers = GLINTDRIMoveBuffers;
+ pDRIInfo->bufferRequests = DRI_ALL_WINDOWS;
+
+ pDRIInfo->createDummyCtx = TRUE;
+ pDRIInfo->createDummyCtxPriv = FALSE;
+
+ /* So DRICloseScreen does the right thing if we abort */
+ pGlint->buffers.map = 0;
+ pGlint->agp.handle = 0;
+
+ if (!DRIScreenInit(pScreen, pDRIInfo, &(pGlint->drmSubFD))) {
+ DRIDestroyInfoRec(pGlint->pDRIInfo);
+ xfree(pGlintDRI);
+ return FALSE;
+ }
+
+ /* Check the DRM versioning */
+ {
+ drmVersionPtr version;
+
+ /* Check the DRM lib version.
+ drmGetLibVersion was not supported in version 1.0, so check for
+ symbol first to avoid possible crash or hang.
+ */
+ if (xf86LoaderCheckSymbol("drmGetLibVersion")) {
+ version = drmGetLibVersion(pGlint->drmSubFD);
+ }
+ else {
+ /* drmlib version 1.0.0 didn't have the drmGetLibVersion
+ entry point. Fake it by allocating a version record
+ via drmGetVersion and changing it to version 1.0.0
+ */
+ version = drmGetVersion(pGlint->drmSubFD);
+ version->version_major = 1;
+ version->version_minor = 0;
+ version->version_patchlevel = 0;
+ }
+
+ if (version) {
+ if (version->version_major != 1 ||
+ version->version_minor < 1) {
+ /* incompatible drm library version */
+ xf86DrvMsg(pScreen->myNum, X_ERROR,
+ "[dri] GLINTDRIScreenInit failed because of a version mismatch.\n"
+ "[dri] libdrm.a module version is %d.%d.%d but version 1.1.x is needed.\n"
+ "[dri] Disabling DRI.\n",
+ version->version_major,
+ version->version_minor,
+ version->version_patchlevel);
+ drmFreeVersion(version);
+ GLINTDRICloseScreen(pScreen);
+ return FALSE;
+ }
+ drmFreeVersion(version);
+ }
+
+ /* Check the GLINT DRM version */
+ version = drmGetVersion(pGlint->drmSubFD);
+ if (version) {
+ if (version->version_major != 2 ||
+ version->version_minor < 0) {
+ /* incompatible drm version */
+ xf86DrvMsg(pScreen->myNum, X_ERROR,
+ "[dri] GLINTDRIScreenInit failed because of a version mismatch.\n"
+ "[dri] gamma.o kernel module version is %d.%d.%d but version 2.0.x is needed.\n"
+ "[dri] Disabling DRI.\n",
+ version->version_major,
+ version->version_minor,
+ version->version_patchlevel);
+ GLINTDRICloseScreen(pScreen);
+ drmFreeVersion(version);
+ return FALSE;
+ }
+ drmFreeVersion(version);
+ }
+ }
+
+ /* Tell the client driver how many MX's we have */
+ pGlintDRI->numMultiDevices = pGlint->numMultiDevices;
+ /* Tell the client about our screen size setup */
+ pGlintDRI->pprod = pGlint->pprod;
+
+ pGlintDRI->cpp = pScrn->bitsPerPixel / 8;
+ pGlintDRI->frontPitch = pScrn->displayWidth;
+ pGlintDRI->frontOffset = 0;
+
+ pGlintDRI->textureSize = 32 * 1024 * 1024;
+ pGlintDRI->logTextureGranularity =
+ mylog2( pGlintDRI->textureSize / GAMMA_NR_TEX_REGIONS );
+
+ /* setup device specific direct rendering memory maps */
+
+ /* pci region 0: control regs, first 4k page, priveledged writes */
+ pGlintDRI->registers0.size = 0x1000;
+ if (drmAddMap( pGlint->drmSubFD,
+ (drmHandle)pGlint->IOAddress,
+ pGlintDRI->registers0.size,
+ DRM_REGISTERS, DRM_READ_ONLY,
+ &pGlintDRI->registers0.handle) < 0)
+ {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScreen->myNum, X_INFO,
+ "[drm] Register handle 0 = 0x%08lx\n",
+ pGlintDRI->registers0.handle);
+
+ /* pci region 0: control regs, following region, client access */
+ pGlintDRI->registers1.size = 0xf000;
+ if (drmAddMap( pGlint->drmSubFD,
+ (drmHandle)(pGlint->IOAddress + 0x1000),
+ pGlintDRI->registers1.size,
+ DRM_REGISTERS, 0,
+ &pGlintDRI->registers1.handle) < 0)
+ {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScreen->myNum, X_INFO,
+ "[drm] Register handle 1 = 0x%08lx\n",
+ pGlintDRI->registers1.handle);
+
+ /* pci region 0: control regs, second MX, first 4k page */
+ pGlintDRI->registers2.size = 0x1000;
+ if (drmAddMap( pGlint->drmSubFD,
+ (drmHandle)(pGlint->IOAddress + 0x10000),
+ pGlintDRI->registers2.size,
+ DRM_REGISTERS, DRM_READ_ONLY,
+ &pGlintDRI->registers2.handle) < 0)
+ {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScreen->myNum, X_INFO,
+ "[drm] Register handle 2 = 0x%08lx\n",
+ pGlintDRI->registers2.handle);
+
+ /* pci region 0: control regs, second MX, following region */
+ pGlintDRI->registers3.size = 0xf000;
+ if (drmAddMap( pGlint->drmSubFD,
+ (drmHandle)(pGlint->IOAddress + 0x11000),
+ pGlintDRI->registers3.size,
+ DRM_REGISTERS, 0,
+ &pGlintDRI->registers3.handle) < 0)
+ {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScreen->myNum, X_INFO,
+ "[drm] Register handle 3 = 0x%08lx\n",
+ pGlintDRI->registers3.handle);
+
+ /* setup DMA buffers */
+
+ /* TRY AGP */
+ if ( !GLINTDRIAgpInit( pScreen ) ) {
+ /* OUCH, NO AGP, TRY PCI */
+ pGlint->PCIMode = TRUE;
+ if (xf86ConfigDRI.bufs_count) {
+ int i;
+ int bufs;
+
+ for (i = 0; i < xf86ConfigDRI.bufs_count; i++) {
+ if ((bufs = drmAddBufs(pGlint->drmSubFD,
+ xf86ConfigDRI.bufs[i].count,
+ xf86ConfigDRI.bufs[i].size,
+ 0,
+ 0 /* flags */)) <= 0) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "[drm] failure adding %d %d byte DMA buffers\n",
+ xf86ConfigDRI.bufs[i].count,
+ xf86ConfigDRI.bufs[i].size);
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "[drm] added %d %d byte DMA buffers\n",
+ bufs, xf86ConfigDRI.bufs[i].size);
+ dmabufs += bufs;
+ }
+ }
+ }
+
+ if (dmabufs <= 0) {
+ int bufs;
+
+ if ((bufs = drmAddBufs(pGlint->drmSubFD,
+ GLINT_DRI_BUF_COUNT,
+ GLINT_DRI_BUF_SIZE,
+ 0,
+ 0 /* flags */)) <= 0) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] failure adding %d %d byte DMA buffers\n",
+ GLINT_DRI_BUF_COUNT,
+ GLINT_DRI_BUF_SIZE);
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] added %d %d byte DMA buffers\n",
+ bufs, GLINT_DRI_BUF_SIZE);
+
+ if ((bufs = drmAddBufs(pGlint->drmSubFD,
+ 1,
+ 8192, /* 8K = 8MB physical memory */
+ 0,
+ DRM_RESTRICTED /* flags */)) <= 0) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] 0x%x failure adding page table buffer\n",bufs);
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] added 1 page table buffer\n");
+ }
+
+ if (!(pGlint->drmBufs = drmMapBufs(pGlint->drmSubFD))) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] failure mapping DMA buffers\n");
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "[drm] buffers mapped with %p\n",
+ pGlint->drmBufs);
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "[drm] %d DMA buffers mapped\n",
+ pGlint->drmBufs->count);
+ } /* PCIMODE */
+
+ if (pGlint->irq <= 0) {
+ pGlint->irq = drmGetInterruptFromBusID(pGlint->drmSubFD,
+ ((pciConfigPtr)pGlint->PciInfo
+ ->thisCard)->busnum,
+ ((pciConfigPtr)pGlint->PciInfo
+ ->thisCard)->devnum,
+ ((pciConfigPtr)pGlint->PciInfo
+ ->thisCard)->funcnum);
+ }
+
+ return TRUE;
+}
+
+void
+GLINTDRICloseScreen(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (pGlint->buffers.map) {
+ drmUnmap( pGlint->buffers.map, pGlint->buffers.size);
+ pGlint->buffers.map = NULL;
+ }
+
+ if (pGlint->agp.handle) {
+ drmAgpUnbind( pGlint->drmSubFD, pGlint->agp.handle );
+ drmAgpFree( pGlint->drmSubFD, pGlint->agp.handle );
+ pGlint->agp.handle = 0;
+ drmAgpRelease( pGlint->drmSubFD );
+ }
+
+ if (pGlint->drmBufs) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] unmapping %d buffers\n",
+ pGlint->drmBufs->count);
+ if (drmUnmapBufs(pGlint->drmBufs)) {
+ xf86DrvMsg(pScreen->myNum, X_INFO,
+ "[drm] unable to unmap DMA buffers\n");
+ }
+
+ }
+
+ DRICloseScreen(pScreen);
+
+ if (pGlint->pDRIInfo) {
+ if (pGlint->pDRIInfo->devPrivate) {
+ xfree(pGlint->pDRIInfo->devPrivate);
+ }
+ DRIDestroyInfoRec(pGlint->pDRIInfo);
+ }
+
+ if (pGlint->pVisualConfigs) xfree(pGlint->pVisualConfigs);
+ if (pGlint->pVisualConfigsPriv) xfree(pGlint->pVisualConfigsPriv);
+}
+
+Bool
+GLINTCreateContext(ScreenPtr pScreen,
+ VisualPtr visual,
+ drmContext hwContext,
+ void *pVisualConfigPriv,
+ DRIContextType contextStore)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTConfigPrivPtr pGlintConfig = (GLINTConfigPrivPtr)pVisualConfigPriv;
+
+ /* These are really assertions rather than necessary logic,
+ just using this to exercise device private region until really needed */
+
+ if (!pGlintConfig)
+ return TRUE; /* no GLX driver private support, yet */
+
+#if 0
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[GLINTCreateContext] context priv index = %d\n",
+ pGlintConfig->index);
+#endif
+
+ if (pGlintConfig->index >= pGlint->numVisualConfigs)
+ return FALSE;
+
+ if (pGlint->pVisualConfigs[pGlintConfig->index].redMask != visual->redMask)
+ return FALSE;
+
+ return TRUE;
+}
+
+static void
+GLINTDestroyContext(ScreenPtr pScreen,
+ drmContext hwContext,
+ DRIContextType contextStore)
+{
+}
+
+Bool
+GLINTDRIFinishScreenInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ DRIInfoPtr pDRIInfo = pGlint->pDRIInfo;
+ GLINTDRIPtr pGlintDRI = pDRIInfo->devPrivate;
+ FBAreaPtr fbarea;
+
+ /*
+ * Setup one of 4 types of context swap handling methods
+ *
+ * Option A: HIDE X CONTEXT SWAPS. X contexts will be flagged as
+ * preserved by the server. The kernel will never swap a preserved
+ * context. The kernel will call back into the server for swapping
+ * all other contexts.
+ *
+ * pGlint->pDRIInfo->driverSwapMethod = DRI_HIDE_X_CONTEXT;
+ *
+ *
+ * Option B: SERVER SIDE CONTEXT SWAPS. X contexts will be flagged
+ * as 2D contexts, but the flag will be ignored by the kernel. The
+ * preserved flag will not be used, so the kernel will call back into
+ * the server for swapping all contexts. The 2D flag will be used by
+ * the server to optimize for 2D/3D switching between a single 3D
+ * context and the servers 2D context.
+ *
+ * pGlint->pDRIInfo->driverSwapMethod = DRI_SERVER_SWAP;
+ *
+ *
+ * Option C: KERNEL SIDE GENERIC SWAPS. X server will provide generic
+ * kernel driver with byte codes for performing swap. X contexts will
+ * be flagged as 2D contexts, so 2D/3D switching optimizations can still
+ * be done. This is not supported, yet. Additional work is required
+ * to support generic kernel driver and provide byte code examples.
+ *
+ * pGlint->pDRIInfo->driverSwapMethod = DRI_KERNEL_SWAP;
+ *
+ * add byte codes for context swap here:
+ * drmCtlAddCommand(drmSubFD, ...
+ *
+ *
+ * Option D: KERNEL SIDE DEVICE SPECIFIC SWAPS. DrmSubdriver will
+ * have device specific code for handling swaps. X context will be
+ * flagged as 2D contexts, so 2D/3D switching optimizations can still
+ * be done. This is not supported by gamma driver, yet; however, the
+ * framework is in place to use this option.
+ *
+ * pGlint->pDRIInfo->driverSwapMethod = DRI_KERNEL_SWAP;
+ */
+
+ pGlint->pDRIInfo->driverSwapMethod = DRI_HIDE_X_CONTEXT;
+
+ /* Allocate the shared back buffer */
+ if ((fbarea = xf86AllocateOffscreenArea(pScreen,
+ pScrn->virtualX,
+ pScrn->virtualY,
+ 32, NULL, NULL, NULL))) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "Reserved back buffer from (%d,%d) to (%d,%d)\n",
+ fbarea->box.x1, fbarea->box.y1,
+ fbarea->box.x2, fbarea->box.y2);
+
+ pGlintDRI->backPitch = pScrn->displayWidth;
+ pGlintDRI->backOffset = (fbarea->box.y1 * pScrn->displayWidth *
+ pScrn->bitsPerPixel / 8) +
+ (fbarea->box.x1 * pScrn->bitsPerPixel / 8);
+ pGlintDRI->backX = fbarea->box.x1;
+ pGlintDRI->backY = fbarea->box.y1;
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Unable to reserve back buffer\n");
+ pGlintDRI->backPitch = -1;
+ pGlintDRI->backOffset = -1;
+ }
+
+ if (!DRIFinishScreenInit(pScreen)) {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+
+ if (!GLINTDRIKernelInit(pScreen)) {
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+
+ if ( (pGlint->irq <= 0) ||
+ GLINTDRIControlInit(pGlint->drmSubFD, pGlint->irq) ) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] cannot initialize dma with IRQ %d\n",
+ pGlint->irq);
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] dma control initialized, using IRQ %d\n",
+ pGlint->irq);
+
+ if (!pGlint->PCIMode) {
+ if (!(pGlint->drmBufs = drmMapBufs(pGlint->drmSubFD))) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "[drm] failure mapping DMA buffers\n");
+ DRICloseScreen(pScreen);
+ return FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "[agp] buffers mapped with %p\n",
+ pGlint->drmBufs);
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "[agp] %d DMA buffers mapped\n",
+ pGlint->drmBufs->count);
+ }
+
+#if 0
+ /* Get the X server's context */
+ pGlint->DRIctx = DRIGetContext(pScreen);
+ pGlint->buf2D = pGlint->drmBufs->list[GLINT_DRI_BUF_COUNT + 1].address;
+#endif
+
+ return TRUE;
+}
+
+#define ContextDump_tag 0x1b8
+#define ContextRestore_tag 0x1b9
+#define ContextData_tag 0x1ba
+
+void
+GLINTDRISwapContext(
+ ScreenPtr pScreen,
+ DRISyncType syncType,
+ DRIContextType readContextType,
+ void *readContextStore,
+ DRIContextType writeContextType,
+ void *writeContextStore)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTDRIContextPtr pRC = (GLINTDRIContextPtr)readContextStore;
+ GLINTDRIContextPtr pWC = (GLINTDRIContextPtr)writeContextStore;
+ int dumpIndex;
+ CARD32 readValue;
+
+ /* Sync here covers both read and write context of contexts */
+ if (pGlint->AccelInfoRec->Sync) {
+ (*pGlint->AccelInfoRec->Sync)(pGlint->AccelInfoRec->pScrn);
+ }
+ pGlint->AccelInfoRec->NeedToSync = FALSE;
+
+ if (readContextType != DRI_NO_CONTEXT) {
+
+ /* save the 2D portion of the old context */
+ pRC->MX1.CStartXDom = GLINT_READ_REG(StartXDom);
+ pRC->MX1.CdXDom = GLINT_READ_REG(dXDom);
+ pRC->MX1.CStartXSub = GLINT_READ_REG(StartXSub);
+ pRC->MX1.CdXSub = GLINT_READ_REG(dXSub);
+ pRC->MX1.CStartY = GLINT_READ_REG(StartY);
+ pRC->MX1.CdY = GLINT_READ_REG(dY);
+ pRC->MX1.CGLINTCount = GLINT_READ_REG(GLINTCount);
+ pRC->MX1.CPointTable0 = GLINT_READ_REG(PointTable0);
+ pRC->MX1.CPointTable1 = GLINT_READ_REG(PointTable1);
+ pRC->MX1.CPointTable2 = GLINT_READ_REG(PointTable2);
+ pRC->MX1.CPointTable3 = GLINT_READ_REG(PointTable3);
+ pRC->MX1.CRasterizerMode = GLINT_READ_REG(RasterizerMode);
+ pRC->MX1.CYLimits = GLINT_READ_REG(YLimits);
+ pRC->MX1.CScanLineOwnership = GLINT_READ_REG(ScanLineOwnership);
+ pRC->MX1.CPixelSize = GLINT_READ_REG(PixelSize);
+ pRC->MX1.CScissorMode = GLINT_READ_REG(ScissorMode);
+ pRC->MX1.CScissorMinXY = GLINT_READ_REG(ScissorMinXY);
+ pRC->MX1.CScissorMaxXY = GLINT_READ_REG(ScissorMaxXY);
+ pRC->MX1.CScreenSize = GLINT_READ_REG(ScreenSize);
+ pRC->MX1.CAreaStippleMode = GLINT_READ_REG(AreaStippleMode);
+ pRC->MX1.CLineStippleMode = GLINT_READ_REG(LineStippleMode);
+ pRC->MX1.CLoadLineStippleCounters = GLINT_READ_REG(LoadLineStippleCounters);
+ pRC->MX1.CWindowOrigin = GLINT_READ_REG(WindowOrigin);
+ pRC->MX1.CRouterMode = GLINT_READ_REG(RouterMode);
+ pRC->MX1.CTextureAddressMode = GLINT_READ_REG(TextureAddressMode);
+ pRC->MX1.CTextureReadMode = GLINT_READ_REG(TextureReadMode);
+ pRC->MX1.CTextureColorMode = GLINT_READ_REG(TextureColorMode);
+ pRC->MX1.CFogMode = GLINT_READ_REG(FogMode);
+ pRC->MX1.CColorDDAMode = GLINT_READ_REG(ColorDDAMode);
+ pRC->MX1.CGLINTColor = GLINT_READ_REG(GLINTColor);
+ pRC->MX1.CAlphaTestMode = GLINT_READ_REG(AlphaTestMode);
+ pRC->MX1.CAntialiasMode = GLINT_READ_REG(AntialiasMode);
+ pRC->MX1.CAlphaBlendMode = GLINT_READ_REG(AlphaBlendMode);
+ pRC->MX1.CDitherMode = GLINT_READ_REG(DitherMode);
+ pRC->MX1.CFBSoftwareWriteMask = GLINT_READ_REG(FBSoftwareWriteMask);
+ pRC->MX1.CLogicalOpMode = GLINT_READ_REG(LogicalOpMode);
+ pRC->MX1.CFBWriteData = GLINT_READ_REG(FBWriteData);
+ pRC->MX1.CLBReadMode = GLINT_READ_REG(LBReadMode);
+ pRC->MX1.CLBSourceOffset = GLINT_READ_REG(LBSourceOffset);
+ pRC->MX1.CLBWindowBase = GLINT_READ_REG(LBWindowBase);
+ pRC->MX1.CLBWriteMode = GLINT_READ_REG(LBWriteMode);
+ pRC->MX1.CTextureDownloadOffset = GLINT_READ_REG(TextureDownloadOffset);
+ pRC->MX1.CLBWindowOffset = GLINT_READ_REG(LBWindowOffset);
+ pRC->MX1.CGLINTWindow = GLINT_READ_REG(GLINTWindow);
+ pRC->MX1.CStencilMode = GLINT_READ_REG(StencilMode);
+ pRC->MX1.CDepthMode = GLINT_READ_REG(DepthMode);
+ pRC->MX1.CGLINTDepth = GLINT_READ_REG(GLINTDepth);
+ pRC->MX1.CFBReadMode = GLINT_READ_REG(FBReadMode);
+ pRC->MX1.CFBSourceOffset = GLINT_READ_REG(FBSourceOffset);
+ pRC->MX1.CFBPixelOffset = GLINT_READ_REG(FBPixelOffset);
+ pRC->MX1.CFBWindowBase = GLINT_READ_REG(FBWindowBase);
+ pRC->MX1.CFBWriteMode = GLINT_READ_REG(FBWriteMode);
+ pRC->MX1.CFBHardwareWriteMask = GLINT_READ_REG(FBHardwareWriteMask);
+ pRC->MX1.CFBBlockColor = GLINT_READ_REG(FBBlockColor);
+ pRC->MX1.CPatternRamMode = GLINT_READ_REG(PatternRamMode);
+ pRC->MX1.CFBBlockColorU = GLINT_READ_REG(FBBlockColorU);
+ pRC->MX1.CFBBlockColorL = GLINT_READ_REG(FBBlockColorL);
+ pRC->MX1.CFilterMode = GLINT_READ_REG(FilterMode);
+ pRC->MX1.CStatisticMode = GLINT_READ_REG(StatisticMode);
+
+ if (pGlint->numMultiDevices == 2) {
+ pRC->MX1.CBroadcastMask = GLINT_READ_REG(BroadcastMask);
+
+ ACCESSCHIP2();
+ pRC->MX2.CStartXDom = GLINT_READ_REG(StartXDom);
+ pRC->MX2.CdXDom = GLINT_READ_REG(dXDom);
+ pRC->MX2.CStartXSub = GLINT_READ_REG(StartXSub);
+ pRC->MX2.CdXSub = GLINT_READ_REG(dXSub);
+ pRC->MX2.CStartY = GLINT_READ_REG(StartY);
+ pRC->MX2.CdY = GLINT_READ_REG(dY);
+ pRC->MX2.CGLINTCount = GLINT_READ_REG(GLINTCount);
+ pRC->MX2.CPointTable0 = GLINT_READ_REG(PointTable0);
+ pRC->MX2.CPointTable1 = GLINT_READ_REG(PointTable1);
+ pRC->MX2.CPointTable2 = GLINT_READ_REG(PointTable2);
+ pRC->MX2.CPointTable3 = GLINT_READ_REG(PointTable3);
+ pRC->MX2.CRasterizerMode = GLINT_READ_REG(RasterizerMode);
+ pRC->MX2.CYLimits = GLINT_READ_REG(YLimits);
+ pRC->MX2.CScanLineOwnership = GLINT_READ_REG(ScanLineOwnership);
+ pRC->MX2.CPixelSize = GLINT_READ_REG(PixelSize);
+ pRC->MX2.CScissorMode = GLINT_READ_REG(ScissorMode);
+ pRC->MX2.CScissorMinXY = GLINT_READ_REG(ScissorMinXY);
+ pRC->MX2.CScissorMaxXY = GLINT_READ_REG(ScissorMaxXY);
+ pRC->MX2.CScreenSize = GLINT_READ_REG(ScreenSize);
+ pRC->MX2.CAreaStippleMode = GLINT_READ_REG(AreaStippleMode);
+ pRC->MX2.CLineStippleMode = GLINT_READ_REG(LineStippleMode);
+ pRC->MX2.CLoadLineStippleCounters = GLINT_READ_REG(LoadLineStippleCounters);
+ pRC->MX2.CWindowOrigin = GLINT_READ_REG(WindowOrigin);
+ pRC->MX2.CRouterMode = GLINT_READ_REG(RouterMode);
+ pRC->MX2.CTextureAddressMode = GLINT_READ_REG(TextureAddressMode);
+ pRC->MX2.CTextureReadMode = GLINT_READ_REG(TextureReadMode);
+ pRC->MX2.CTextureColorMode = GLINT_READ_REG(TextureColorMode);
+ pRC->MX2.CFogMode = GLINT_READ_REG(FogMode);
+ pRC->MX2.CColorDDAMode = GLINT_READ_REG(ColorDDAMode);
+ pRC->MX2.CGLINTColor = GLINT_READ_REG(GLINTColor);
+ pRC->MX2.CAlphaTestMode = GLINT_READ_REG(AlphaTestMode);
+ pRC->MX2.CAntialiasMode = GLINT_READ_REG(AntialiasMode);
+ pRC->MX2.CAlphaBlendMode = GLINT_READ_REG(AlphaBlendMode);
+ pRC->MX2.CDitherMode = GLINT_READ_REG(DitherMode);
+ pRC->MX2.CFBSoftwareWriteMask = GLINT_READ_REG(FBSoftwareWriteMask);
+ pRC->MX2.CLogicalOpMode = GLINT_READ_REG(LogicalOpMode);
+ pRC->MX2.CFBWriteData = GLINT_READ_REG(FBWriteData);
+ pRC->MX2.CLBReadMode = GLINT_READ_REG(LBReadMode);
+ pRC->MX2.CLBSourceOffset = GLINT_READ_REG(LBSourceOffset);
+ pRC->MX2.CLBWindowBase = GLINT_READ_REG(LBWindowBase);
+ pRC->MX2.CLBWriteMode = GLINT_READ_REG(LBWriteMode);
+ pRC->MX2.CTextureDownloadOffset = GLINT_READ_REG(TextureDownloadOffset);
+ pRC->MX2.CLBWindowOffset = GLINT_READ_REG(LBWindowOffset);
+ pRC->MX2.CGLINTWindow = GLINT_READ_REG(GLINTWindow);
+ pRC->MX2.CStencilMode = GLINT_READ_REG(StencilMode);
+ pRC->MX2.CDepthMode = GLINT_READ_REG(DepthMode);
+ pRC->MX2.CGLINTDepth = GLINT_READ_REG(GLINTDepth);
+ pRC->MX2.CFBReadMode = GLINT_READ_REG(FBReadMode);
+ pRC->MX2.CFBSourceOffset = GLINT_READ_REG(FBSourceOffset);
+ pRC->MX2.CFBPixelOffset = GLINT_READ_REG(FBPixelOffset);
+ pRC->MX2.CFBWindowBase = GLINT_READ_REG(FBWindowBase);
+ pRC->MX2.CFBWriteMode = GLINT_READ_REG(FBWriteMode);
+ pRC->MX2.CFBHardwareWriteMask = GLINT_READ_REG(FBHardwareWriteMask);
+ pRC->MX2.CFBBlockColor = GLINT_READ_REG(FBBlockColor);
+ pRC->MX2.CPatternRamMode = GLINT_READ_REG(PatternRamMode);
+ pRC->MX2.CFBBlockColorU = GLINT_READ_REG(FBBlockColorU);
+ pRC->MX2.CFBBlockColorL = GLINT_READ_REG(FBBlockColorL);
+ pRC->MX2.CFilterMode = GLINT_READ_REG(FilterMode);
+ pRC->MX2.CStatisticMode = GLINT_READ_REG(StatisticMode);
+ ACCESSCHIP1();
+ }
+
+ if (readContextType == DRI_3D_CONTEXT) {
+ /* save the 3D portion of the old context */
+
+ /* first the MX portions */
+ pRC->MX1.CSStart = GLINT_READ_REG(SStart);
+ pRC->MX1.CdSdx = GLINT_READ_REG(dSdx);
+ pRC->MX1.CdSdyDom = GLINT_READ_REG(dSdyDom);
+ pRC->MX1.CTStart = GLINT_READ_REG(TStart);
+ pRC->MX1.CdTdx = GLINT_READ_REG(dTdx);
+ pRC->MX1.CdTdyDom = GLINT_READ_REG(dTdyDom);
+ pRC->MX1.CQStart = GLINT_READ_REG(QStart);
+ pRC->MX1.CdQdx = GLINT_READ_REG(dQdx);
+ pRC->MX1.CdQdyDom = GLINT_READ_REG(dQdyDom);
+ pRC->MX1.CLOD = GLINT_READ_REG(LOD);
+ pRC->MX1.CdSdy = GLINT_READ_REG(dSdy);
+ pRC->MX1.CdTdy = GLINT_READ_REG(dTdy);
+ pRC->MX1.CdQdy = GLINT_READ_REG(dQdy);
+ pRC->MX1.CTextureFormat = GLINT_READ_REG(TextureFormat);
+ pRC->MX1.CTextureCacheControl = GLINT_READ_REG(TextureCacheControl);
+ pRC->MX1.CGLINTBorderColor = GLINT_READ_REG(GLINTBorderColor);
+ pRC->MX1.CTexelLUTIndex = GLINT_READ_REG(TexelLUTIndex);
+ pRC->MX1.CTexelLUTData = GLINT_READ_REG(TexelLUTData);
+ pRC->MX1.CTexelLUTAddress = GLINT_READ_REG(TexelLUTAddress);
+ pRC->MX1.CTexelLUTTransfer = GLINT_READ_REG(TexelLUTTransfer);
+ pRC->MX1.CTextureFilterMode = GLINT_READ_REG(TextureFilterMode);
+ pRC->MX1.CTextureChromaUpper = GLINT_READ_REG(TextureChromaUpper);
+ pRC->MX1.CTextureChromaLower = GLINT_READ_REG(TextureChromaLower);
+ pRC->MX1.CTxBaseAddr0 = GLINT_READ_REG(TxBaseAddr0);
+ pRC->MX1.CTxBaseAddr1 = GLINT_READ_REG(TxBaseAddr1);
+ pRC->MX1.CTxBaseAddr2 = GLINT_READ_REG(TxBaseAddr2);
+ pRC->MX1.CTxBaseAddr3 = GLINT_READ_REG(TxBaseAddr3);
+ pRC->MX1.CTxBaseAddr4 = GLINT_READ_REG(TxBaseAddr4);
+ pRC->MX1.CTxBaseAddr5 = GLINT_READ_REG(TxBaseAddr5);
+ pRC->MX1.CTxBaseAddr6 = GLINT_READ_REG(TxBaseAddr6);
+ pRC->MX1.CTxBaseAddr7 = GLINT_READ_REG(TxBaseAddr7);
+ pRC->MX1.CTxBaseAddr8 = GLINT_READ_REG(TxBaseAddr8);
+ pRC->MX1.CTxBaseAddr9 = GLINT_READ_REG(TxBaseAddr9);
+ pRC->MX1.CTxBaseAddr10 = GLINT_READ_REG(TxBaseAddr10);
+ pRC->MX1.CTxBaseAddr11 = GLINT_READ_REG(TxBaseAddr11);
+ pRC->MX1.CTexelLUT0 = GLINT_READ_REG(TexelLUT0);
+ pRC->MX1.CTexelLUT1 = GLINT_READ_REG(TexelLUT1);
+ pRC->MX1.CTexelLUT2 = GLINT_READ_REG(TexelLUT2);
+ pRC->MX1.CTexelLUT3 = GLINT_READ_REG(TexelLUT3);
+ pRC->MX1.CTexelLUT4 = GLINT_READ_REG(TexelLUT4);
+ pRC->MX1.CTexelLUT5 = GLINT_READ_REG(TexelLUT5);
+ pRC->MX1.CTexelLUT6 = GLINT_READ_REG(TexelLUT6);
+ pRC->MX1.CTexelLUT7 = GLINT_READ_REG(TexelLUT7);
+ pRC->MX1.CTexelLUT8 = GLINT_READ_REG(TexelLUT8);
+ pRC->MX1.CTexelLUT9 = GLINT_READ_REG(TexelLUT9);
+ pRC->MX1.CTexelLUT10 = GLINT_READ_REG(TexelLUT10);
+ pRC->MX1.CTexelLUT11 = GLINT_READ_REG(TexelLUT11);
+ pRC->MX1.CTexelLUT12 = GLINT_READ_REG(TexelLUT12);
+ pRC->MX1.CTexelLUT13 = GLINT_READ_REG(TexelLUT13);
+ pRC->MX1.CTexelLUT14 = GLINT_READ_REG(TexelLUT14);
+ pRC->MX1.CTexelLUT15 = GLINT_READ_REG(TexelLUT15);
+ pRC->MX1.CTexel0 = GLINT_READ_REG(Texel0);
+ pRC->MX1.CTexel1 = GLINT_READ_REG(Texel1);
+ pRC->MX1.CTexel2 = GLINT_READ_REG(Texel2);
+ pRC->MX1.CTexel3 = GLINT_READ_REG(Texel3);
+ pRC->MX1.CTexel4 = GLINT_READ_REG(Texel4);
+ pRC->MX1.CTexel5 = GLINT_READ_REG(Texel5);
+ pRC->MX1.CTexel6 = GLINT_READ_REG(Texel6);
+ pRC->MX1.CTexel7 = GLINT_READ_REG(Texel7);
+ pRC->MX1.CInterp0 = GLINT_READ_REG(Interp0);
+ pRC->MX1.CInterp1 = GLINT_READ_REG(Interp1);
+ pRC->MX1.CInterp2 = GLINT_READ_REG(Interp2);
+ pRC->MX1.CInterp3 = GLINT_READ_REG(Interp3);
+ pRC->MX1.CInterp4 = GLINT_READ_REG(Interp4);
+ pRC->MX1.CTextureFilter = GLINT_READ_REG(TextureFilter);
+ pRC->MX1.CTextureEnvColor = GLINT_READ_REG(TextureEnvColor);
+ pRC->MX1.CFogColor = GLINT_READ_REG(FogColor);
+ pRC->MX1.CFStart = GLINT_READ_REG(FStart);
+ pRC->MX1.CdFdx = GLINT_READ_REG(dFdx);
+ pRC->MX1.CdFdyDom = GLINT_READ_REG(dFdyDom);
+ pRC->MX1.CKsStart = GLINT_READ_REG(KsStart);
+ pRC->MX1.CdKsdx = GLINT_READ_REG(dKsdx);
+ pRC->MX1.CdKsdyDom = GLINT_READ_REG(dKsdyDom);
+ pRC->MX1.CKdStart = GLINT_READ_REG(KdStart);
+ pRC->MX1.CdKdStart = GLINT_READ_REG(dKdStart);
+ pRC->MX1.CdKddyDom = GLINT_READ_REG(dKddyDom);
+ pRC->MX1.CRStart = GLINT_READ_REG(RStart);
+ pRC->MX1.CdRdx = GLINT_READ_REG(dRdx);
+ pRC->MX1.CdRdyDom = GLINT_READ_REG(dRdyDom);
+ pRC->MX1.CGStart = GLINT_READ_REG(GStart);
+ pRC->MX1.CdGdx = GLINT_READ_REG(dGdx);
+ pRC->MX1.CdGdyDom = GLINT_READ_REG(dGdyDom);
+ pRC->MX1.CBStart = GLINT_READ_REG(BStart);
+ pRC->MX1.CdBdx = GLINT_READ_REG(dBdx);
+ pRC->MX1.CdBdyDom = GLINT_READ_REG(dBdyDom);
+ pRC->MX1.CAStart = GLINT_READ_REG(AStart);
+ pRC->MX1.CdAdx = GLINT_READ_REG(dAdx);
+ pRC->MX1.CdAdyDom = GLINT_READ_REG(dAdyDom);
+ pRC->MX1.CConstantColor = GLINT_READ_REG(ConstantColor);
+ pRC->MX1.CChromaUpper = GLINT_READ_REG(ChromaUpper);
+ pRC->MX1.CChromaLower = GLINT_READ_REG(ChromaLower);
+ pRC->MX1.CChromaTestMode = GLINT_READ_REG(ChromaTestMode);
+ pRC->MX1.CStencilData = GLINT_READ_REG(StencilData);
+ pRC->MX1.CGLINTStencil = GLINT_READ_REG(GLINTStencil);
+ pRC->MX1.CZStartU = GLINT_READ_REG(ZStartU);
+ pRC->MX1.CZStartL = GLINT_READ_REG(ZStartL);
+ pRC->MX1.CdZdxU = GLINT_READ_REG(dZdxU);
+ pRC->MX1.CdZdxL = GLINT_READ_REG(dZdxL);
+ pRC->MX1.CdZdyDomU = GLINT_READ_REG(dZdyDomU);
+ pRC->MX1.CdZdyDomL = GLINT_READ_REG(dZdyDomL);
+ pRC->MX1.CFastClearDepth = GLINT_READ_REG(FastClearDepth);
+ pRC->MX1.CMinRegion = GLINT_READ_REG(MinRegion);
+ pRC->MX1.CMaxRegion = GLINT_READ_REG(MaxRegion);
+ pRC->MX1.CKsRStart = GLINT_READ_REG(KsRStart);
+ pRC->MX1.CdKsRdx = GLINT_READ_REG(dKsRdx);
+ pRC->MX1.CdKsRdyDom = GLINT_READ_REG(dKsRdyDom);
+ pRC->MX1.CKsGStart = GLINT_READ_REG(KsGStart);
+ pRC->MX1.CdKsGdx = GLINT_READ_REG(dKsGdx);
+ pRC->MX1.CdKsGdyDom = GLINT_READ_REG(dKsGdyDom);
+ pRC->MX1.CKsBStart = GLINT_READ_REG(KsBStart);
+ pRC->MX1.CdKsBdx = GLINT_READ_REG(dKsBdx);
+ pRC->MX1.CdKsBdyDom = GLINT_READ_REG(dKsBdyDom);
+ pRC->MX1.CKdRStart = GLINT_READ_REG(KdRStart);
+ pRC->MX1.CdKdRdx = GLINT_READ_REG(dKdRdx);
+ pRC->MX1.CdKdRdyDom = GLINT_READ_REG(dKdRdyDom);
+ pRC->MX1.CKdGStart = GLINT_READ_REG(KdGStart);
+ pRC->MX1.CdKdGdx = GLINT_READ_REG(dKdGdx);
+ pRC->MX1.CdKdGdyDom = GLINT_READ_REG(dKdGdyDom);
+ pRC->MX1.CKdBStart = GLINT_READ_REG(KdBStart);
+ pRC->MX1.CdKdBdx = GLINT_READ_REG(dKdBdx);
+ pRC->MX1.CdKdBdyDom = GLINT_READ_REG(dKdBdyDom);
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ pRC->MX2.CSStart = GLINT_READ_REG(SStart);
+ pRC->MX2.CdSdx = GLINT_READ_REG(dSdx);
+ pRC->MX2.CdSdyDom = GLINT_READ_REG(dSdyDom);
+ pRC->MX2.CTStart = GLINT_READ_REG(TStart);
+ pRC->MX2.CdTdx = GLINT_READ_REG(dTdx);
+ pRC->MX2.CdTdyDom = GLINT_READ_REG(dTdyDom);
+ pRC->MX2.CQStart = GLINT_READ_REG(QStart);
+ pRC->MX2.CdQdx = GLINT_READ_REG(dQdx);
+ pRC->MX2.CdQdyDom = GLINT_READ_REG(dQdyDom);
+ pRC->MX2.CLOD = GLINT_READ_REG(LOD);
+ pRC->MX2.CdSdy = GLINT_READ_REG(dSdy);
+ pRC->MX2.CdTdy = GLINT_READ_REG(dTdy);
+ pRC->MX2.CdQdy = GLINT_READ_REG(dQdy);
+ pRC->MX2.CTextureFormat = GLINT_READ_REG(TextureFormat);
+ pRC->MX2.CTextureCacheControl = GLINT_READ_REG(TextureCacheControl);
+ pRC->MX2.CGLINTBorderColor = GLINT_READ_REG(GLINTBorderColor);
+ pRC->MX2.CTexelLUTIndex = GLINT_READ_REG(TexelLUTIndex);
+ pRC->MX2.CTexelLUTData = GLINT_READ_REG(TexelLUTData);
+ pRC->MX2.CTexelLUTAddress = GLINT_READ_REG(TexelLUTAddress);
+ pRC->MX2.CTexelLUTTransfer = GLINT_READ_REG(TexelLUTTransfer);
+ pRC->MX2.CTextureFilterMode = GLINT_READ_REG(TextureFilterMode);
+ pRC->MX2.CTextureChromaUpper = GLINT_READ_REG(TextureChromaUpper);
+ pRC->MX2.CTextureChromaLower = GLINT_READ_REG(TextureChromaLower);
+ pRC->MX2.CTxBaseAddr0 = GLINT_READ_REG(TxBaseAddr0);
+ pRC->MX2.CTxBaseAddr1 = GLINT_READ_REG(TxBaseAddr1);
+ pRC->MX2.CTxBaseAddr2 = GLINT_READ_REG(TxBaseAddr2);
+ pRC->MX2.CTxBaseAddr3 = GLINT_READ_REG(TxBaseAddr3);
+ pRC->MX2.CTxBaseAddr4 = GLINT_READ_REG(TxBaseAddr4);
+ pRC->MX2.CTxBaseAddr5 = GLINT_READ_REG(TxBaseAddr5);
+ pRC->MX2.CTxBaseAddr6 = GLINT_READ_REG(TxBaseAddr6);
+ pRC->MX2.CTxBaseAddr7 = GLINT_READ_REG(TxBaseAddr7);
+ pRC->MX2.CTxBaseAddr8 = GLINT_READ_REG(TxBaseAddr8);
+ pRC->MX2.CTxBaseAddr9 = GLINT_READ_REG(TxBaseAddr9);
+ pRC->MX2.CTxBaseAddr10 = GLINT_READ_REG(TxBaseAddr10);
+ pRC->MX2.CTxBaseAddr11 = GLINT_READ_REG(TxBaseAddr11);
+ pRC->MX2.CTexelLUT0 = GLINT_READ_REG(TexelLUT0);
+ pRC->MX2.CTexelLUT1 = GLINT_READ_REG(TexelLUT1);
+ pRC->MX2.CTexelLUT2 = GLINT_READ_REG(TexelLUT2);
+ pRC->MX2.CTexelLUT3 = GLINT_READ_REG(TexelLUT3);
+ pRC->MX2.CTexelLUT4 = GLINT_READ_REG(TexelLUT4);
+ pRC->MX2.CTexelLUT5 = GLINT_READ_REG(TexelLUT5);
+ pRC->MX2.CTexelLUT6 = GLINT_READ_REG(TexelLUT6);
+ pRC->MX2.CTexelLUT7 = GLINT_READ_REG(TexelLUT7);
+ pRC->MX2.CTexelLUT8 = GLINT_READ_REG(TexelLUT8);
+ pRC->MX2.CTexelLUT9 = GLINT_READ_REG(TexelLUT9);
+ pRC->MX2.CTexelLUT10 = GLINT_READ_REG(TexelLUT10);
+ pRC->MX2.CTexelLUT11 = GLINT_READ_REG(TexelLUT11);
+ pRC->MX2.CTexelLUT12 = GLINT_READ_REG(TexelLUT12);
+ pRC->MX2.CTexelLUT13 = GLINT_READ_REG(TexelLUT13);
+ pRC->MX2.CTexelLUT14 = GLINT_READ_REG(TexelLUT14);
+ pRC->MX2.CTexelLUT15 = GLINT_READ_REG(TexelLUT15);
+ pRC->MX2.CTexel0 = GLINT_READ_REG(Texel0);
+ pRC->MX2.CTexel1 = GLINT_READ_REG(Texel1);
+ pRC->MX2.CTexel2 = GLINT_READ_REG(Texel2);
+ pRC->MX2.CTexel3 = GLINT_READ_REG(Texel3);
+ pRC->MX2.CTexel4 = GLINT_READ_REG(Texel4);
+ pRC->MX2.CTexel5 = GLINT_READ_REG(Texel5);
+ pRC->MX2.CTexel6 = GLINT_READ_REG(Texel6);
+ pRC->MX2.CTexel7 = GLINT_READ_REG(Texel7);
+ pRC->MX2.CInterp0 = GLINT_READ_REG(Interp0);
+ pRC->MX2.CInterp1 = GLINT_READ_REG(Interp1);
+ pRC->MX2.CInterp2 = GLINT_READ_REG(Interp2);
+ pRC->MX2.CInterp3 = GLINT_READ_REG(Interp3);
+ pRC->MX2.CInterp4 = GLINT_READ_REG(Interp4);
+ pRC->MX2.CTextureFilter = GLINT_READ_REG(TextureFilter);
+ pRC->MX2.CTextureEnvColor = GLINT_READ_REG(TextureEnvColor);
+ pRC->MX2.CFogColor = GLINT_READ_REG(FogColor);
+ pRC->MX2.CFStart = GLINT_READ_REG(FStart);
+ pRC->MX2.CdFdx = GLINT_READ_REG(dFdx);
+ pRC->MX2.CdFdyDom = GLINT_READ_REG(dFdyDom);
+ pRC->MX2.CKsStart = GLINT_READ_REG(KsStart);
+ pRC->MX2.CdKsdx = GLINT_READ_REG(dKsdx);
+ pRC->MX2.CdKsdyDom = GLINT_READ_REG(dKsdyDom);
+ pRC->MX2.CKdStart = GLINT_READ_REG(KdStart);
+ pRC->MX2.CdKdStart = GLINT_READ_REG(dKdStart);
+ pRC->MX2.CdKddyDom = GLINT_READ_REG(dKddyDom);
+ pRC->MX2.CRStart = GLINT_READ_REG(RStart);
+ pRC->MX2.CdRdx = GLINT_READ_REG(dRdx);
+ pRC->MX2.CdRdyDom = GLINT_READ_REG(dRdyDom);
+ pRC->MX2.CGStart = GLINT_READ_REG(GStart);
+ pRC->MX2.CdGdx = GLINT_READ_REG(dGdx);
+ pRC->MX2.CdGdyDom = GLINT_READ_REG(dGdyDom);
+ pRC->MX2.CBStart = GLINT_READ_REG(BStart);
+ pRC->MX2.CdBdx = GLINT_READ_REG(dBdx);
+ pRC->MX2.CdBdyDom = GLINT_READ_REG(dBdyDom);
+ pRC->MX2.CAStart = GLINT_READ_REG(AStart);
+ pRC->MX2.CdAdx = GLINT_READ_REG(dAdx);
+ pRC->MX2.CdAdyDom = GLINT_READ_REG(dAdyDom);
+ pRC->MX2.CConstantColor = GLINT_READ_REG(ConstantColor);
+ pRC->MX2.CChromaUpper = GLINT_READ_REG(ChromaUpper);
+ pRC->MX2.CChromaLower = GLINT_READ_REG(ChromaLower);
+ pRC->MX2.CChromaTestMode = GLINT_READ_REG(ChromaTestMode);
+ pRC->MX2.CStencilData = GLINT_READ_REG(StencilData);
+ pRC->MX2.CGLINTStencil = GLINT_READ_REG(GLINTStencil);
+ pRC->MX2.CZStartU = GLINT_READ_REG(ZStartU);
+ pRC->MX2.CZStartL = GLINT_READ_REG(ZStartL);
+ pRC->MX2.CdZdxU = GLINT_READ_REG(dZdxU);
+ pRC->MX2.CdZdxL = GLINT_READ_REG(dZdxL);
+ pRC->MX2.CdZdyDomU = GLINT_READ_REG(dZdyDomU);
+ pRC->MX2.CdZdyDomL = GLINT_READ_REG(dZdyDomL);
+ pRC->MX2.CFastClearDepth = GLINT_READ_REG(FastClearDepth);
+ pRC->MX2.CMinRegion = GLINT_READ_REG(MinRegion);
+ pRC->MX2.CMaxRegion = GLINT_READ_REG(MaxRegion);
+ pRC->MX2.CKsRStart = GLINT_READ_REG(KsRStart);
+ pRC->MX2.CdKsRdx = GLINT_READ_REG(dKsRdx);
+ pRC->MX2.CdKsRdyDom = GLINT_READ_REG(dKsRdyDom);
+ pRC->MX2.CKsGStart = GLINT_READ_REG(KsGStart);
+ pRC->MX2.CdKsGdx = GLINT_READ_REG(dKsGdx);
+ pRC->MX2.CdKsGdyDom = GLINT_READ_REG(dKsGdyDom);
+ pRC->MX2.CKsBStart = GLINT_READ_REG(KsBStart);
+ pRC->MX2.CdKsBdx = GLINT_READ_REG(dKsBdx);
+ pRC->MX2.CdKsBdyDom = GLINT_READ_REG(dKsBdyDom);
+ pRC->MX2.CKdRStart = GLINT_READ_REG(KdRStart);
+ pRC->MX2.CdKdRdx = GLINT_READ_REG(dKdRdx);
+ pRC->MX2.CdKdRdyDom = GLINT_READ_REG(dKdRdyDom);
+ pRC->MX2.CKdGStart = GLINT_READ_REG(KdGStart);
+ pRC->MX2.CdKdGdx = GLINT_READ_REG(dKdGdx);
+ pRC->MX2.CdKdGdyDom = GLINT_READ_REG(dKdGdyDom);
+ pRC->MX2.CKdBStart = GLINT_READ_REG(KdBStart);
+ pRC->MX2.CdKdBdx = GLINT_READ_REG(dKdBdx);
+ pRC->MX2.CdKdBdyDom = GLINT_READ_REG(dKdBdyDom);
+ ACCESSCHIP1();
+ }
+
+ /* send gamma the context dump command */
+ GLINT_WAIT(3);
+ if (pGlint->numMultiDevices == 2)
+ GLINT_WRITE_REG(1, BroadcastMask);
+ GLINT_WRITE_REG(3<<14, FilterMode); /* context bits on gamma */
+ GLINT_WRITE_REG(GLINT_GAMMA_CONTEXT_MASK, ContextDump);
+
+ /* save context data from output fifo */
+ dumpIndex = 0;
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+#ifdef DEBUG
+xf86DrvMsg(pScreen->myNum, X_INFO, "pRC tag [%d]: %x\n",
+dumpIndex,readValue);
+#endif
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+#ifdef DEBUG
+xf86DrvMsg(pScreen->myNum, X_INFO, "pRC data [%d]: %x\n",
+dumpIndex,readValue);
+#endif
+ pRC->Gamma[dumpIndex++] = readValue;
+ } while (dumpIndex < GLINT_GAMMA_CONTEXT_SIZE);
+
+ /* clear contextDump tag and data out of fifo */
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+ if (readValue != ContextDump_tag) {
+ xf86DrvMsg(pScreen->myNum, X_ERROR, "Context dump error\n");
+ }
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+
+ GLINT_SLOW_WRITE_REG(1<<10, FilterMode);
+ if (pGlint->numMultiDevices == 2)
+ GLINT_SLOW_WRITE_REG(3,BroadcastMask);
+ }
+ }
+
+ if (writeContextType != DRI_NO_CONTEXT) {
+
+ if (writeContextType == DRI_3D_CONTEXT) {
+ /* restore the 3D portion of the new context */
+
+ /* send context restore command */
+ GLINT_WAIT(1);
+ if (pGlint->numMultiDevices == 2)
+ GLINT_WRITE_REG(1, BroadcastMask);
+
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(ContextRestore_tag, OutputFIFO);
+ GLINT_WRITE_REG(GLINT_GAMMA_CONTEXT_MASK, OutputFIFO);
+ GLINT_WRITE_REG((((GLINT_GAMMA_CONTEXT_SIZE-1) << 16) |
+ ContextData_tag), OutputFIFO);
+
+ /* restore context data to context data register */
+ dumpIndex = 0;
+ do {
+ GLINT_WAIT(1);
+#ifdef DEBUG
+xf86DrvMsg(pScreen->myNum, X_INFO, "pWC data [%d]: %x\n",
+dumpIndex,pWC->Gamma[dumpIndex]);
+#endif
+ GLINT_WRITE_REG(pWC->Gamma[dumpIndex++], OutputFIFO);
+ } while (dumpIndex < (GLINT_GAMMA_CONTEXT_SIZE));
+
+ /* Sync after writing gamma context and
+ before writing MX context */
+ if (pGlint->AccelInfoRec->Sync) {
+ (*pGlint->AccelInfoRec->Sync)(pGlint->AccelInfoRec->pScrn);
+ }
+ /* Update XAA's NeedToSync flag */
+ pGlint->AccelInfoRec->NeedToSync = TRUE;
+
+ /* finally the MX portions */
+ if (pGlint->numMultiDevices == 2)
+ GLINT_SLOW_WRITE_REG(1, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CSStart, SStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdSdx, dSdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdSdyDom, dSdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTStart, TStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdTdx, dTdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdTdyDom, dTdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CQStart, QStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdQdx, dQdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdQdyDom, dQdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLOD, LOD);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdSdy, dSdy);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdTdy, dTdy);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdQdy, dQdy);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureFormat, TextureFormat);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureCacheControl, TextureCacheControl);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGLINTBorderColor, GLINTBorderColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUTIndex, TexelLUTIndex);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUTData, TexelLUTData);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUTAddress, TexelLUTAddress);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUTTransfer, TexelLUTTransfer);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureFilterMode, TextureFilterMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureChromaUpper, TextureChromaUpper);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureChromaLower, TextureChromaLower);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr0, TxBaseAddr0);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr1, TxBaseAddr1);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr2, TxBaseAddr2);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr3, TxBaseAddr3);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr4, TxBaseAddr4);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr5, TxBaseAddr5);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr6, TxBaseAddr6);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr7, TxBaseAddr7);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr8, TxBaseAddr8);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr9, TxBaseAddr9);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr10, TxBaseAddr10);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTxBaseAddr11, TxBaseAddr11);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT0, TexelLUT0);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT1, TexelLUT1);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT2, TexelLUT2);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT3, TexelLUT3);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT4, TexelLUT4);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT5, TexelLUT5);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT6, TexelLUT6);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT7, TexelLUT7);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT8, TexelLUT8);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT9, TexelLUT9);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT10, TexelLUT10);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT11, TexelLUT11);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT12, TexelLUT12);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT13, TexelLUT13);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT14, TexelLUT14);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexelLUT15, TexelLUT15);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel0, Texel0);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel1, Texel1);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel2, Texel2);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel3, Texel3);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel4, Texel4);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel5, Texel5);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel6, Texel6);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTexel7, Texel7);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CInterp0, Interp0);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CInterp1, Interp1);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CInterp2, Interp2);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CInterp3, Interp3);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CInterp4, Interp4);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureFilter, TextureFilter);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureEnvColor, TextureEnvColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFogColor, FogColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFStart, FStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdFdx, dFdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdFdyDom, dFdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKsStart, KsStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsdx, dKsdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsdyDom, dKsdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKdStart, KdStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdStart, dKdStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKddyDom, dKddyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CRStart, RStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdRdx, dRdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdRdyDom, dRdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGStart, GStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdGdx, dGdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdGdyDom, dGdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CBStart, BStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdBdx, dBdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdBdyDom, dBdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CAStart, AStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdAdx, dAdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdAdyDom, dAdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CConstantColor, ConstantColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CChromaUpper, ChromaUpper);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CChromaLower, ChromaLower);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CChromaTestMode, ChromaTestMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CStencilData, StencilData);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGLINTStencil, GLINTStencil);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CZStartU, ZStartU);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CZStartL, ZStartL);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdZdxU, dZdxU);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdZdxL, dZdxL);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdZdyDomU, dZdyDomU);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdZdyDomL, dZdyDomL);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFastClearDepth, FastClearDepth);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CMinRegion, MinRegion);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CMaxRegion, MaxRegion);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKsRStart, KsRStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsRdx, dKsRdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsRdyDom, dKsRdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKsGStart, KsGStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsGdx, dKsGdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsGdyDom, dKsGdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKsBStart, KsBStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsBdx, dKsBdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKsBdyDom, dKsBdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKdRStart, KdRStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdRdx, dKdRdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdRdyDom, dKdRdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKdGStart, KdGStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdGdx, dKdGdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdGdyDom, dKdGdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CKdBStart, KdBStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdBdx, dKdBdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdKdBdyDom, dKdBdyDom);
+
+ if (pGlint->numMultiDevices == 2) {
+ GLINT_SLOW_WRITE_REG(2, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CSStart, SStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdSdx, dSdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdSdyDom, dSdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTStart, TStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdTdx, dTdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdTdyDom, dTdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CQStart, QStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdQdx, dQdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdQdyDom, dQdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLOD, LOD);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdSdy, dSdy);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdTdy, dTdy);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdQdy, dQdy);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureFormat, TextureFormat);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureCacheControl, TextureCacheControl);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGLINTBorderColor, GLINTBorderColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUTIndex, TexelLUTIndex);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUTData, TexelLUTData);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUTAddress, TexelLUTAddress);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUTTransfer, TexelLUTTransfer);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureFilterMode, TextureFilterMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureChromaUpper, TextureChromaUpper);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureChromaLower, TextureChromaLower);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr0, TxBaseAddr0);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr1, TxBaseAddr1);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr2, TxBaseAddr2);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr3, TxBaseAddr3);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr4, TxBaseAddr4);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr5, TxBaseAddr5);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr6, TxBaseAddr6);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr7, TxBaseAddr7);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr8, TxBaseAddr8);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr9, TxBaseAddr9);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr10, TxBaseAddr10);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTxBaseAddr11, TxBaseAddr11);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT0, TexelLUT0);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT1, TexelLUT1);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT2, TexelLUT2);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT3, TexelLUT3);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT4, TexelLUT4);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT5, TexelLUT5);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT6, TexelLUT6);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT7, TexelLUT7);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT8, TexelLUT8);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT9, TexelLUT9);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT10, TexelLUT10);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT11, TexelLUT11);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT12, TexelLUT12);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT13, TexelLUT13);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT14, TexelLUT14);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexelLUT15, TexelLUT15);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel0, Texel0);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel1, Texel1);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel2, Texel2);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel3, Texel3);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel4, Texel4);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel5, Texel5);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel6, Texel6);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTexel7, Texel7);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CInterp0, Interp0);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CInterp1, Interp1);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CInterp2, Interp2);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CInterp3, Interp3);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CInterp4, Interp4);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureFilter, TextureFilter);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureEnvColor, TextureEnvColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFogColor, FogColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFStart, FStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdFdx, dFdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdFdyDom, dFdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKsStart, KsStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsdx, dKsdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsdyDom, dKsdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKdStart, KdStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdStart, dKdStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKddyDom, dKddyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CRStart, RStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdRdx, dRdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdRdyDom, dRdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGStart, GStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdGdx, dGdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdGdyDom, dGdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CBStart, BStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdBdx, dBdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdBdyDom, dBdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CAStart, AStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdAdx, dAdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdAdyDom, dAdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CConstantColor, ConstantColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CChromaUpper, ChromaUpper);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CChromaLower, ChromaLower);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CChromaTestMode, ChromaTestMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CStencilData, StencilData);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGLINTStencil, GLINTStencil);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CZStartU, ZStartU);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CZStartL, ZStartL);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdZdxU, dZdxU);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdZdxL, dZdxL);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdZdyDomU, dZdyDomU);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdZdyDomL, dZdyDomL);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFastClearDepth, FastClearDepth);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CMinRegion, MinRegion);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CMaxRegion, MaxRegion);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKsRStart, KsRStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsRdx, dKsRdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsRdyDom, dKsRdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKsGStart, KsGStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsGdx, dKsGdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsGdyDom, dKsGdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKsBStart, KsBStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsBdx, dKsBdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKsBdyDom, dKsBdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKdRStart, KdRStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdRdx, dKdRdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdRdyDom, dKdRdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKdGStart, KdGStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdGdx, dKdGdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdGdyDom, dKdGdyDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CKdBStart, KdBStart);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdBdx, dKdBdx);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdKdBdyDom, dKdBdyDom);
+ }
+ }
+
+ /* restore the 2D portion of the new context */
+
+ /* Restore MX1's registers */
+ if (pGlint->numMultiDevices == 2)
+ GLINT_SLOW_WRITE_REG(1, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CStartXDom, StartXDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdXDom, dXDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CStartXSub, StartXSub);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdXSub, dXSub);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CStartY, StartY);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CdY, dY);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGLINTCount, GLINTCount);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CPointTable0, PointTable0);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CPointTable1, PointTable1);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CPointTable2, PointTable2);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CPointTable3, PointTable3);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CRasterizerMode, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CYLimits, YLimits);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CScanLineOwnership, ScanLineOwnership);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CPixelSize, PixelSize);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CScissorMode, ScissorMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CScissorMinXY, ScissorMinXY);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CScissorMaxXY, ScissorMaxXY);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CScreenSize, ScreenSize);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CAreaStippleMode, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLineStippleMode, LineStippleMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLoadLineStippleCounters, LoadLineStippleCounters);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CWindowOrigin, WindowOrigin);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CRouterMode, RouterMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureAddressMode, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureReadMode, TextureReadMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureColorMode, TextureColorMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFogMode, FogMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CColorDDAMode, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGLINTColor, GLINTColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CAlphaTestMode, AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CAntialiasMode, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CAlphaBlendMode, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CDitherMode, DitherMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBSoftwareWriteMask, FBSoftwareWriteMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLogicalOpMode, LogicalOpMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBWriteData, FBWriteData);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLBReadMode, LBReadMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLBSourceOffset, LBSourceOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLBWindowBase, LBWindowBase);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLBWriteMode, LBWriteMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CTextureDownloadOffset, TextureDownloadOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CLBWindowOffset, LBWindowOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGLINTWindow, GLINTWindow);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CStencilMode, StencilMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CDepthMode, DepthMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CGLINTDepth, GLINTDepth);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBReadMode, FBReadMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBSourceOffset, FBSourceOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBPixelOffset, FBPixelOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBWindowBase, FBWindowBase);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBWriteMode, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBHardwareWriteMask, FBHardwareWriteMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBBlockColor, FBBlockColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CPatternRamMode, PatternRamMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBBlockColorU, FBBlockColorU);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFBBlockColorL, FBBlockColorL);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CFilterMode, FilterMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CStatisticMode, StatisticMode);
+
+ /* Restore MX2's registers */
+ if (pGlint->numMultiDevices == 2) {
+ GLINT_SLOW_WRITE_REG(2, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CStartXDom, StartXDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdXDom, dXDom);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CStartXSub, StartXSub);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdXSub, dXSub);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CStartY, StartY);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CdY, dY);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGLINTCount, GLINTCount);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CPointTable0, PointTable0);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CPointTable1, PointTable1);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CPointTable2, PointTable2);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CPointTable3, PointTable3);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CRasterizerMode, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CYLimits, YLimits);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CScanLineOwnership, ScanLineOwnership);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CPixelSize, PixelSize);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CScissorMode, ScissorMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CScissorMinXY, ScissorMinXY);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CScissorMaxXY, ScissorMaxXY);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CScreenSize, ScreenSize);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CAreaStippleMode, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLineStippleMode, LineStippleMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLoadLineStippleCounters, LoadLineStippleCounters);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CWindowOrigin, WindowOrigin);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CRouterMode, RouterMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureAddressMode, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureReadMode, TextureReadMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureColorMode, TextureColorMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFogMode, FogMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CColorDDAMode, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGLINTColor, GLINTColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CAlphaTestMode, AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CAntialiasMode, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CAlphaBlendMode, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CDitherMode, DitherMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBSoftwareWriteMask, FBSoftwareWriteMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLogicalOpMode, LogicalOpMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBWriteData, FBWriteData);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLBReadMode, LBReadMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLBSourceOffset, LBSourceOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLBWindowBase, LBWindowBase);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLBWriteMode, LBWriteMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CTextureDownloadOffset, TextureDownloadOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CLBWindowOffset, LBWindowOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGLINTWindow, GLINTWindow);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CStencilMode, StencilMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CDepthMode, DepthMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CGLINTDepth, GLINTDepth);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBReadMode, FBReadMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBSourceOffset, FBSourceOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBPixelOffset, FBPixelOffset);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBWindowBase, FBWindowBase);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBWriteMode, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBHardwareWriteMask, FBHardwareWriteMask);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBBlockColor, FBBlockColor);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CPatternRamMode, PatternRamMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBBlockColorU, FBBlockColorU);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFBBlockColorL, FBBlockColorL);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CFilterMode, FilterMode);
+ GLINT_SLOW_WRITE_REG(pWC->MX2.CStatisticMode, StatisticMode);
+
+ /* Restore the "real" broadcast mask last */
+ GLINT_SLOW_WRITE_REG(pWC->MX1.CBroadcastMask, BroadcastMask);
+ }
+ /* Sync is needed here probabilistically */
+ if (pGlint->AccelInfoRec->Sync) {
+ (*pGlint->AccelInfoRec->Sync)(pGlint->AccelInfoRec->pScrn);
+ pGlint->AccelInfoRec->NeedToSync = FALSE;
+ }
+ }
+}
+
+void
+GLINTDRIInitBuffers(
+ WindowPtr pWin,
+ RegionPtr prgn,
+ CARD32 index)
+{
+ ScreenPtr pScreen = pWin->drawable.pScreen;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ BoxPtr pbox;
+ int nbox;
+
+ pbox = REGION_RECTS(prgn);
+ nbox = REGION_NUM_RECTS(prgn);
+
+ GLINT_WAIT(7);
+ /* Turn off writes the FB */
+ GLINT_WRITE_REG(0, FBWriteMode);
+ GLINT_WRITE_REG(0, LBWindowBase);
+ GLINT_WRITE_REG(1, LBWriteMode);
+ if (pGlint->numMultiDevices == 2) {
+ GLINT_WRITE_REG( pGlint->pprod |
+ LBRM_ScanlineInt2 , LBReadMode);
+ } else {
+ GLINT_WRITE_REG( pGlint->pprod , LBReadMode);
+ }
+ GLINT_WRITE_REG(0, LBDepth);
+ GLINT_WRITE_REG(0, LBStencil);
+ GLINT_WRITE_REG( GWIN_UnitEnable |
+ GWIN_ForceLBUpdate |
+ ((index & 0xf) << 5) |
+ GWIN_LBUpdateSourceREG |
+ GWIN_OverrideWriteFilter, GLINTWindow);
+
+ while (nbox--) {
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG((pbox->x2)<<16, StartXSub);
+ GLINT_WRITE_REG((pbox->x1)<<16, StartXDom);
+ GLINT_WRITE_REG((pbox->y1)<<16, StartY);
+ GLINT_WRITE_REG((pbox->y2 - pbox->y1), GLINTCount);
+ GLINT_WRITE_REG(0, dXDom);
+ GLINT_WRITE_REG(0x10000, dY);
+ /* Must also set dXSub, since 3D tris cause it to be != 0 */
+ GLINT_WRITE_REG(0, dXSub);
+ GLINT_WRITE_REG(PrimitiveTrapezoid, Render);
+ pbox++;
+ }
+
+ GLINT_WAIT(3);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWriteMode);
+ GLINT_SLOW_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTWindow);
+
+ /* Update XAA's NeedToSync flag */
+ pGlint->AccelInfoRec->NeedToSync = TRUE;
+}
+
+void
+GLINTDRIMoveBuffers(
+ WindowPtr pParent,
+ DDXPointRec ptOldOrg,
+ RegionPtr prgnSrc,
+ CARD32 index)
+{
+#if 0
+ ScreenPtr pScreen = pParent->drawable.pScreen;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+#endif
+ int dx, dy;
+ WindowPtr pChild;
+ RegionRec rgnSubWindow, rgnTranslateSrc;
+ CARD32 indexSubWindow;
+
+ /* NOT_DONE: For now, just init the buffer. We are not copying the depth
+ * and stencil, they just get redrawn for the next frame(s).
+ */
+
+ REGION_INIT(pScreen, &rgnSubWindow, NullBox, 0);
+ REGION_INIT(pScreen, &rgnTranslateSrc, NullBox, 0);
+ REGION_COPY(pScreen, &rgnTranslateSrc, prgnSrc);
+ dx = ptOldOrg.x - pParent->drawable.x;
+ dy = ptOldOrg.y - pParent->drawable.y;
+ REGION_TRANSLATE(pScreen, &rgnTranslateSrc, -dx, -dy);
+
+ pChild = pParent;
+ while (1) {
+ if (pChild->viewable) {
+ REGION_INTERSECT(pScreen, &rgnSubWindow,
+ &pChild->borderClip, &rgnTranslateSrc);
+ indexSubWindow = DRIGetDrawableIndex(pChild);
+ GLINTDRIInitBuffers( pChild, &rgnSubWindow, indexSubWindow);
+ if (pChild->firstChild) {
+ pChild = pChild->firstChild;
+ continue;
+ }
+ }
+ while (!pChild->nextSib && (pChild != pParent))
+ pChild = pChild->parent;
+ if (pChild == pParent)
+ break;
+ pChild = pChild->nextSib;
+ }
+}
diff --git a/src/glint_dri.h b/src/glint_dri.h
new file mode 100644
index 0000000..3952759
--- /dev/null
+++ b/src/glint_dri.h
@@ -0,0 +1,123 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_dri.h,v 1.7 2002/10/30 12:52:16 alanh Exp $ */
+/**************************************************************************
+
+Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
+All Rights Reserved.
+
+Permission is hereby granted, free of charge, to any person obtaining a
+copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sub license, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice (including the
+next paragraph) shall be included in all copies or substantial portions
+of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
+ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+
+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+**************************************************************************/
+
+/*
+ * Author:
+ * Jens Owen <jens@tungstengraphics.com>
+ *
+ */
+
+#ifndef _GLINT_DRI_H_
+#define _GLINT_DRI_H_
+
+#include "xf86drm.h"
+#include "glint_common.h"
+
+typedef struct {
+ unsigned int GDeltaMode;
+ unsigned int GDepthMode;
+ unsigned int GGeometryMode;
+ unsigned int GTransformMode;
+} GAMMAContextRegionRec, *GAMMAContextRegionPtr;
+
+typedef struct {
+ unsigned char next, prev; /* indices to form a circular LRU */
+ unsigned char in_use; /* owned by a client, or free? */
+ int age; /* tracked by clients to update local LRU's */
+} GAMMATextureRegionRec, *GAMMATextureRegionPtr;
+
+typedef struct {
+ GAMMAContextRegionRec context_state;
+
+ unsigned int dirty;
+
+ /* Maintain an LRU of contiguous regions of texture space. If
+ * you think you own a region of texture memory, and it has an
+ * age different to the one you set, then you are mistaken and
+ * it has been stolen by another client. If global texAge
+ * hasn't changed, there is no need to walk the list.
+ *
+ * These regions can be used as a proxy for the fine-grained
+ * texture information of other clients - by maintaining them
+ * in the same lru which is used to age their own textures,
+ * clients have an approximate lru for the whole of global
+ * texture space, and can make informed decisions as to which
+ * areas to kick out. There is no need to choose whether to
+ * kick out your own texture or someone else's - simply eject
+ * them all in LRU order.
+ */
+
+#define GAMMA_NR_TEX_REGIONS 64
+ GAMMATextureRegionRec texList[GAMMA_NR_TEX_REGIONS+1];
+ /* Last elt is sentinal */
+ int texAge; /* last time texture was uploaded */
+ int last_enqueue; /* last time a buffer was enqueued */
+ int last_dispatch; /* age of the most recently dispatched buffer */
+ int last_quiescent; /* */
+ int ctxOwner; /* last context to upload state */
+
+ int vertex_prim;
+} GLINTSAREADRIRec, *GLINTSAREADRIPtr;
+
+/*
+ * Glint specific record passed back to client driver
+ * via DRIGetDeviceInfo request
+ */
+typedef struct {
+ drmRegion registers0;
+ drmRegion registers1;
+ drmRegion registers2;
+ drmRegion registers3;
+ int numMultiDevices;
+ int pprod;
+ int cpp;
+ int frontOffset;
+ int frontPitch;
+ int backOffset;
+ int backPitch;
+ int backX;
+ int backY;
+ int depthOffset;
+ int depthPitch;
+ int textureSize;
+ int logTextureGranularity;
+} GLINTDRIRec, *GLINTDRIPtr;
+
+#define GLINT_DRI_BUF_COUNT 256
+#define GLINT_DRI_BUF_SIZE 4096
+
+#define GAMMA_NR_TEX_REGIONS 64
+
+#define DMA_WRITE(val,reg) \
+do { \
+ pGlint->buf2D++ = Glint##reg##Tag; \
+ pGlint->buf2D++ = val; \
+} while (0)
+
+#endif /* _GLINT_DRI_H_ */
diff --git a/src/glint_dripriv.h b/src/glint_dripriv.h
new file mode 100644
index 0000000..15d5e48
--- /dev/null
+++ b/src/glint_dripriv.h
@@ -0,0 +1,296 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_dripriv.h,v 1.6 2002/10/30 12:52:16 alanh Exp $ */
+/**************************************************************************
+
+Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
+All Rights Reserved.
+
+Permission is hereby granted, free of charge, to any person obtaining a
+copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sub license, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice (including the
+next paragraph) shall be included in all copies or substantial portions
+of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
+ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+
+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+**************************************************************************/
+
+/*
+ * Author:
+ * Jens Owen <jens@tungstengraphics.com>
+ *
+ */
+
+extern void GlxSetVisualConfigs(
+ int nconfigs,
+ __GLXvisualConfig *configs,
+ void **configprivs
+);
+
+extern Bool GLINTCreateContext(ScreenPtr pScreen,
+ VisualPtr visual,
+ drmContext hwContext,
+ void* pVisualConfigPriv,
+ DRIContextType contextStore);
+
+extern void GLINTDRISwapContext( ScreenPtr pScreen,
+ DRISyncType syncType,
+ DRIContextType readContextType,
+ void* readContextStore,
+ DRIContextType writeContextType,
+ void* writeContextStore);
+
+/* Macros to Setup Generic Kernel Device Driver to Handle DMA for gamma */
+
+/* WARNING!!! MAGIC NUMBER!!! The number of regions already added to the
+ kernel must be specified here. Currently, the number is 2. */
+#define DRM_REG(reg) \
+ (2 \
+ + ((reg < 0x1000) \
+ ? 0 \
+ : ((reg < 0x10000) ? 1 : ((reg < 0x11000) ? 2 : 3))))
+
+#define DRM_OFF(reg) \
+ ((reg < 0x1000) \
+ ? reg \
+ : ((reg < 0x10000) \
+ ? (reg - 0x1000) \
+ : ((reg < 0x11000) \
+ ? (reg - 0x10000) \
+ : (reg - 0x11000))))
+
+
+#define DRM_I_WRITE_R(reg,a,b,c,d) \
+ DRM_I_WRITE(DRM_REG(reg), DRM_OFF(reg), a, b, c, d)
+
+#define DRM_I_WRITE_IMM_R(reg,a) \
+ DRM_I_WRITE_IMM(DRM_REG(reg), DRM_OFF(reg), a)
+
+#define DRM_I_READ_R(reg) \
+ DRM_I_READ(DRM_REG(reg), DRM_OFF(reg))
+
+#define DRM_I_WHILE_IMM_R(reg,a,b) \
+ DRM_I_WHILE_IMM(DRM_REG(reg), DRM_OFF(reg), a, b)
+
+#define DRM_I_IF_IMM_R(reg,a,b,c) \
+ DRM_I_IF_IMM(DRM_REG(reg), DRM_OFF(reg), a, b, c)
+
+#define GLINTSync GlintSync
+#define GLINTSyncTag 0x188
+
+#define GLINT_MAX_DRAWABLES 15
+#define GLINT_GAMMA_CONTEXT_SIZE 964
+#define GLINT_GAMMA_CONTEXT_MASK 0x7ff
+
+typedef struct {
+ int index;
+} GLINTConfigPrivRec, *GLINTConfigPrivPtr;
+
+typedef struct {
+
+ /* 2D components */
+ CARD32 CStartXDom;
+ CARD32 CdXDom;
+ CARD32 CStartXSub;
+ CARD32 CdXSub;
+ CARD32 CStartY;
+ CARD32 CdY;
+ CARD32 CGLINTCount;
+ CARD32 CPointTable0;
+ CARD32 CPointTable1;
+ CARD32 CPointTable2;
+ CARD32 CPointTable3;
+ CARD32 CRasterizerMode;
+ CARD32 CYLimits;
+ CARD32 CScanLineOwnership;
+ CARD32 CPixelSize;
+ CARD32 CScissorMode;
+ CARD32 CScissorMinXY;
+ CARD32 CScissorMaxXY;
+ CARD32 CScreenSize;
+ CARD32 CAreaStippleMode;
+ CARD32 CLineStippleMode;
+ CARD32 CLoadLineStippleCounters;
+ CARD32 CWindowOrigin;
+ CARD32 CRouterMode;
+ CARD32 CTextureAddressMode;
+ CARD32 CTextureReadMode;
+ CARD32 CTextureColorMode;
+ CARD32 CFogMode;
+ CARD32 CColorDDAMode;
+ CARD32 CGLINTColor;
+ CARD32 CAlphaTestMode;
+ CARD32 CAntialiasMode;
+ CARD32 CAlphaBlendMode;
+ CARD32 CDitherMode;
+ CARD32 CFBSoftwareWriteMask;
+ CARD32 CLogicalOpMode;
+ CARD32 CFBWriteData;
+ CARD32 CLBReadMode;
+ CARD32 CLBSourceOffset;
+ CARD32 CLBWindowBase;
+ CARD32 CLBWriteMode;
+ CARD32 CTextureDownloadOffset;
+ CARD32 CLBWindowOffset;
+ CARD32 CGLINTWindow;
+ CARD32 CStencilMode;
+ CARD32 CDepthMode;
+ CARD32 CGLINTDepth;
+ CARD32 CFBReadMode;
+ CARD32 CFBSourceOffset;
+ CARD32 CFBPixelOffset;
+ CARD32 CFBWindowBase;
+ CARD32 CFBWriteMode;
+ CARD32 CFBHardwareWriteMask;
+ CARD32 CFBBlockColor;
+ CARD32 CPatternRamMode;
+ CARD32 CFBBlockColorU;
+ CARD32 CFBBlockColorL;
+ CARD32 CFilterMode;
+ CARD32 CStatisticMode;
+ CARD32 CBroadcastMask;
+
+ /* 3D components */
+ CARD32 CSStart;
+ CARD32 CdSdx;
+ CARD32 CdSdyDom;
+ CARD32 CTStart;
+ CARD32 CdTdx;
+ CARD32 CdTdyDom;
+ CARD32 CQStart;
+ CARD32 CdQdx;
+ CARD32 CdQdyDom;
+ CARD32 CLOD;
+ CARD32 CdSdy;
+ CARD32 CdTdy;
+ CARD32 CdQdy;
+ CARD32 CTex;
+ CARD32 CTextureFormat;
+ CARD32 CTextureCacheControl;
+ CARD32 CGLINTBorderColor;
+ CARD32 CTexelLUTIndex;
+ CARD32 CTexelLUTData;
+ CARD32 CTexelLUTAddress;
+ CARD32 CTexelLUTTransfer;
+ CARD32 CTextureFilterMode;
+ CARD32 CTextureChromaUpper;
+ CARD32 CTextureChromaLower;
+ CARD32 CTxBaseAddr0;
+ CARD32 CTxBaseAddr1;
+ CARD32 CTxBaseAddr2;
+ CARD32 CTxBaseAddr3;
+ CARD32 CTxBaseAddr4;
+ CARD32 CTxBaseAddr5;
+ CARD32 CTxBaseAddr6;
+ CARD32 CTxBaseAddr7;
+ CARD32 CTxBaseAddr8;
+ CARD32 CTxBaseAddr9;
+ CARD32 CTxBaseAddr10;
+ CARD32 CTxBaseAddr11;
+ CARD32 CTxBaseAddr12;
+ CARD32 CTexelLUT0;
+ CARD32 CTexelLUT1;
+ CARD32 CTexelLUT2;
+ CARD32 CTexelLUT3;
+ CARD32 CTexelLUT4;
+ CARD32 CTexelLUT5;
+ CARD32 CTexelLUT6;
+ CARD32 CTexelLUT7;
+ CARD32 CTexelLUT8;
+ CARD32 CTexelLUT9;
+ CARD32 CTexelLUT10;
+ CARD32 CTexelLUT11;
+ CARD32 CTexelLUT12;
+ CARD32 CTexelLUT13;
+ CARD32 CTexelLUT14;
+ CARD32 CTexelLUT15;
+ CARD32 CTexel0;
+ CARD32 CTexel1;
+ CARD32 CTexel2;
+ CARD32 CTexel3;
+ CARD32 CTexel4;
+ CARD32 CTexel5;
+ CARD32 CTexel6;
+ CARD32 CTexel7;
+ CARD32 CInterp0;
+ CARD32 CInterp1;
+ CARD32 CInterp2;
+ CARD32 CInterp3;
+ CARD32 CInterp4;
+ CARD32 CTextureFilter;
+ CARD32 CTextureEnvColor;
+ CARD32 CFogColor;
+ CARD32 CFStart;
+ CARD32 CdFdx;
+ CARD32 CdFdyDom;
+ CARD32 CKsStart;
+ CARD32 CdKsdx;
+ CARD32 CdKsdyDom;
+ CARD32 CKdStart;
+ CARD32 CdKdStart;
+ CARD32 CdKddyDom;
+ CARD32 CRStart;
+ CARD32 CdRdx;
+ CARD32 CdRdyDom;
+ CARD32 CGStart;
+ CARD32 CdGdx;
+ CARD32 CdGdyDom;
+ CARD32 CBStart;
+ CARD32 CdBdx;
+ CARD32 CdBdyDom;
+ CARD32 CAStart;
+ CARD32 CdAdx;
+ CARD32 CdAdyDom;
+ CARD32 CConstantColor;
+ CARD32 CChromaUpper;
+ CARD32 CChromaLower;
+ CARD32 CChromaTestMode;
+ CARD32 CStencilData;
+ CARD32 CGLINTStencil;
+ CARD32 CZStartU;
+ CARD32 CZStartL;
+ CARD32 CdZdxU;
+ CARD32 CdZdxL;
+ CARD32 CdZdyDomU;
+ CARD32 CdZdyDomL;
+ CARD32 CFastClearDepth;
+ CARD32 CMinRegion;
+ CARD32 CMaxRegion;
+ CARD32 CKsRStart;
+ CARD32 CdKsRdx;
+ CARD32 CdKsRdyDom;
+ CARD32 CKsGStart;
+ CARD32 CdKsGdx;
+ CARD32 CdKsGdyDom;
+ CARD32 CKsBStart;
+ CARD32 CdKsBdx;
+ CARD32 CdKsBdyDom;
+ CARD32 CKdRStart;
+ CARD32 CdKdRdx;
+ CARD32 CdKdRdyDom;
+ CARD32 CKdGStart;
+ CARD32 CdKdGdx;
+ CARD32 CdKdGdyDom;
+ CARD32 CKdBStart;
+ CARD32 CdKdBdx;
+ CARD32 CdKdBdyDom;
+
+} GLINTMXRec;
+
+typedef struct {
+ GLINTMXRec MX1;
+ GLINTMXRec MX2;
+ CARD32 Gamma[GLINT_GAMMA_CONTEXT_SIZE];
+} GLINTDRIContextRec, *GLINTDRIContextPtr;
diff --git a/src/glint_driver.c b/src/glint_driver.c
new file mode 100644
index 0000000..de0c992
--- /dev/null
+++ b/src/glint_driver.c
@@ -0,0 +1,3875 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Michel Dänzer, <michdaen@iiic.ethz.ch>
+ * Sven Luther, <luther@dpt-info.u-strasbg.fr>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen,
+ * Siemens Nixdorf Informationssysteme and Appian Graphics.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_driver.c,v 1.156 2003/02/17 16:08:28 dawes Exp $ */
+
+#include "fb.h"
+#include "cfb8_32.h"
+#include "micmap.h"
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+#include "xf86Version.h"
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+#include "xf86cmap.h"
+#include "shadowfb.h"
+#include "fbdevhw.h"
+#include "xf86RAC.h"
+#include "xf86Resources.h"
+#include "xf86int10.h"
+#include "dixstruct.h"
+#include "vbe.h"
+
+#include "compiler.h"
+#include "mipointer.h"
+
+#include "mibstore.h"
+
+#include "pm3_regs.h"
+#include "glint_regs.h"
+#include "IBM.h"
+#include "TI.h"
+#include "glint.h"
+
+#define _XF86DGA_SERVER_
+#include "extensions/xf86dgastr.h"
+
+#include "globals.h"
+#define DPMS_SERVER
+#include "extensions/dpms.h"
+
+#define DEBUG 0
+
+#if DEBUG
+# define TRACE_ENTER(str) ErrorF("glint: " str " %d\n",pScrn->scrnIndex)
+# define TRACE_EXIT(str) ErrorF("glint: " str " done\n")
+# define TRACE(str) ErrorF("glint trace: " str "\n")
+#else
+# define TRACE_ENTER(str)
+# define TRACE_EXIT(str)
+# define TRACE(str)
+#endif
+
+static const OptionInfoRec * GLINTAvailableOptions(int chipid, int busid);
+static void GLINTIdentify(int flags);
+static Bool GLINTProbe(DriverPtr drv, int flags);
+static Bool GLINTPreInit(ScrnInfoPtr pScrn, int flags);
+static Bool GLINTScreenInit(int Index, ScreenPtr pScreen, int argc,
+ char **argv);
+static Bool GLINTEnterVT(int scrnIndex, int flags);
+static void GLINTLeaveVT(int scrnIndex, int flags);
+static Bool GLINTCloseScreen(int scrnIndex, ScreenPtr pScreen);
+static Bool GLINTSaveScreen(ScreenPtr pScreen, int mode);
+
+/* Optional functions */
+static void GLINTFreeScreen(int scrnIndex, int flags);
+static int GLINTValidMode(int scrnIndex, DisplayModePtr mode, Bool verbose,
+ int flags);
+
+/* Internally used functions */
+static Bool GLINTMapMem(ScrnInfoPtr pScrn);
+static Bool GLINTUnmapMem(ScrnInfoPtr pScrn);
+static void GLINTSave(ScrnInfoPtr pScrn);
+static void GLINTRestore(ScrnInfoPtr pScrn);
+static Bool GLINTModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode);
+static void GLINTBlockHandler(int, pointer, pointer, pointer);
+
+/*
+ * This is intentionally screen-independent. It indicates the binding
+ * choice made in the first PreInit.
+ */
+static int GLINTEntityIndex = -1;
+static Bool FBDevProbed = FALSE;
+
+/*
+ * This contains the functions needed by the server after loading the driver
+ * module. It must be supplied, and gets passed back by the SetupProc
+ * function in the dynamic case. In the static case, a reference to this
+ * is compiled in, and this requires that the name of this DriverRec be
+ * an upper-case version of the driver name.
+ */
+
+DriverRec GLINT = {
+ VERSION,
+ GLINT_DRIVER_NAME,
+ GLINTIdentify,
+ GLINTProbe,
+ GLINTAvailableOptions,
+ NULL,
+ 0
+};
+
+static SymTabRec GLINTVGAChipsets[] = {
+ { PCI_VENDOR_TI_CHIP_PERMEDIA2, "ti_pm2" },
+ { PCI_VENDOR_TI_CHIP_PERMEDIA, "ti_pm" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA4, "pm4" },
+ { PCI_VENDOR_3DLABS_CHIP_R4, "r4" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA3, "pm3" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V, "pm2v" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2, "pm2" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA, "pm" },
+ {-1, NULL }
+};
+
+static PciChipsets GLINTVGAPciChipsets[] = {
+ { PCI_VENDOR_TI_CHIP_PERMEDIA2, PCI_VENDOR_TI_CHIP_PERMEDIA2, RES_SHARED_VGA },
+ { PCI_VENDOR_TI_CHIP_PERMEDIA, PCI_VENDOR_TI_CHIP_PERMEDIA, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA4, PCI_VENDOR_3DLABS_CHIP_PERMEDIA4, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_R4, PCI_VENDOR_3DLABS_CHIP_R4, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA3, PCI_VENDOR_3DLABS_CHIP_PERMEDIA3, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V, PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2, PCI_VENDOR_3DLABS_CHIP_PERMEDIA2, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA, PCI_VENDOR_3DLABS_CHIP_PERMEDIA, NULL },
+ { -1, -1, RES_UNDEFINED }
+};
+
+static SymTabRec GLINTChipsets[] = {
+ { PCI_VENDOR_3DLABS_CHIP_GAMMA, "gamma" },
+ { PCI_VENDOR_3DLABS_CHIP_GAMMA2, "gamma2" },
+ { PCI_VENDOR_TI_CHIP_PERMEDIA2, "ti_pm2" },
+ { PCI_VENDOR_TI_CHIP_PERMEDIA, "ti_pm" },
+ { PCI_VENDOR_3DLABS_CHIP_R4, "r4" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA4, "pm4" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA3, "pm3" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V, "pm2v" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2, "pm2" },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA, "pm" },
+ { PCI_VENDOR_3DLABS_CHIP_300SX, "300sx" },
+ { PCI_VENDOR_3DLABS_CHIP_500TX, "500tx" },
+ { PCI_VENDOR_3DLABS_CHIP_MX, "mx" },
+ { PCI_VENDOR_3DLABS_CHIP_DELTA, "delta" },
+ { -1, NULL }
+};
+
+static PciChipsets GLINTPciChipsets[] = {
+ { PCI_VENDOR_3DLABS_CHIP_GAMMA, PCI_VENDOR_3DLABS_CHIP_GAMMA, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_GAMMA2, PCI_VENDOR_3DLABS_CHIP_GAMMA2, NULL },
+ { PCI_VENDOR_TI_CHIP_PERMEDIA2, PCI_VENDOR_TI_CHIP_PERMEDIA2, RES_SHARED_VGA },
+ { PCI_VENDOR_TI_CHIP_PERMEDIA, PCI_VENDOR_TI_CHIP_PERMEDIA, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_R4, PCI_VENDOR_3DLABS_CHIP_R4, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA4, PCI_VENDOR_3DLABS_CHIP_PERMEDIA4, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA3, PCI_VENDOR_3DLABS_CHIP_PERMEDIA3, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V, PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA2, PCI_VENDOR_3DLABS_CHIP_PERMEDIA2, RES_SHARED_VGA },
+ { PCI_VENDOR_3DLABS_CHIP_PERMEDIA, PCI_VENDOR_3DLABS_CHIP_PERMEDIA, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_300SX, PCI_VENDOR_3DLABS_CHIP_300SX, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_500TX, PCI_VENDOR_3DLABS_CHIP_500TX, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_MX, PCI_VENDOR_3DLABS_CHIP_MX, NULL },
+ { PCI_VENDOR_3DLABS_CHIP_DELTA, PCI_VENDOR_3DLABS_CHIP_DELTA, NULL },
+ { -1, -1, RES_UNDEFINED }
+};
+
+typedef enum {
+ OPTION_SW_CURSOR,
+ OPTION_RGB_BITS,
+ OPTION_NOACCEL,
+ OPTION_BLOCK_WRITE,
+ OPTION_FIREGL3000,
+ OPTION_OVERLAY,
+ OPTION_SHADOW_FB,
+ OPTION_FBDEV,
+ OPTION_FLATPANEL,
+ OPTION_VIDEO_KEY
+} GLINTOpts;
+
+static const OptionInfoRec GLINTOptions[] = {
+ { OPTION_SW_CURSOR, "SWcursor", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_RGB_BITS, "RGBbits", OPTV_INTEGER, {0}, FALSE },
+ { OPTION_NOACCEL, "NoAccel", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_BLOCK_WRITE, "BlockWrite", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_FIREGL3000, "FireGL3000", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_OVERLAY, "Overlay", OPTV_ANYSTR, {0}, FALSE },
+ { OPTION_SHADOW_FB, "ShadowFB", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_FBDEV, "UseFBDev", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_FLATPANEL, "UseFlatPanel", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_VIDEO_KEY, "VideoKey", OPTV_BOOLEAN, {0}, FALSE },
+ { -1, NULL, OPTV_NONE, {0}, FALSE }
+};
+
+static RamDacSupportedInfoRec IBMRamdacs[] = {
+ { IBM526DB_RAMDAC },
+ { IBM526_RAMDAC },
+ { IBM640_RAMDAC },
+ { -1 }
+};
+
+static RamDacSupportedInfoRec TIRamdacs[] = {
+ { TI3030_RAMDAC },
+ { TI3026_RAMDAC },
+ { -1 }
+};
+
+static const char *xf8_32bppSymbols[] = {
+ "cfb8_32ScreenInit",
+ "xf86Overlay8Plus32Init",
+ NULL
+};
+
+static const char *xaaSymbols[] = {
+ "XAACreateInfoRec",
+ "XAADestroyInfoRec",
+ "XAAFillSolidRects",
+ "XAAInit",
+ "XAAPolyLines",
+ "XAAPolySegment",
+ "XAAScreenIndex",
+ NULL
+};
+
+static const char *fbSymbols[] = {
+ "fbBres",
+ "fbPictureInit",
+ "fbScreenInit",
+ NULL
+};
+
+static const char *ddcSymbols[] = {
+ "xf86PrintEDID",
+ "xf86DoEDID_DDC2",
+ "xf86SetDDCproperties",
+ NULL
+};
+
+static const char *i2cSymbols[] = {
+ "xf86CreateI2CBusRec",
+ "xf86DestroyI2CBusRec",
+ "xf86DestroyI2CDevRec",
+ "xf86I2CBusInit",
+ "xf86I2CDevInit",
+ "xf86I2CProbeAddress",
+ "xf86I2CWriteByte",
+ "xf86I2CWriteVec",
+ NULL
+};
+
+static const char *shadowSymbols[] = {
+ "ShadowFBInit",
+ NULL
+};
+
+#ifdef XFree86LOADER
+static const char *vbeSymbols[] = {
+ "VBEInit",
+ "vbeDoEDID",
+ "vbeFree",
+ NULL
+};
+#endif
+
+static const char *ramdacSymbols[] = {
+ "IBMramdac526CalculateMNPCForClock",
+ "IBMramdac640CalculateMNPCForClock",
+ "IBMramdacProbe",
+ "RamDacCreateInfoRec",
+ "RamDacDestroyInfoRec",
+ "RamDacFreeRec",
+ "RamDacGetHWIndex",
+ "RamDacHandleColormaps",
+ "RamDacInit",
+ "TIramdacCalculateMNPForClock",
+ "TIramdacLoadPalette",
+ "TIramdacProbe",
+ "xf86CreateCursorInfoRec",
+ "xf86DestroyCursorInfoRec",
+ "xf86InitCursor",
+ NULL
+};
+
+
+static const char *fbdevHWSymbols[] = {
+ "fbdevHWFreeRec",
+ "fbdevHWInit",
+ "fbdevHWProbe",
+ "fbdevHWUseBuildinMode",
+
+ "fbdevHWGetDepth",
+ "fbdevHWGetVidmem",
+
+ /* colormap */
+ "fbdevHWLoadPalette",
+
+ /* ScrnInfo hooks */
+ "fbdevHWAdjustFrame",
+ "fbdevHWEnterVT",
+ "fbdevHWLeaveVT",
+ "fbdevHWMapMMIO",
+ "fbdevHWMapVidmem",
+ "fbdevHWModeInit",
+ "fbdevHWRestore",
+ "fbdevHWSave",
+ "fbdevHWSwitchMode",
+ "fbdevHWUnmapMMIO",
+ "fbdevHWUnmapVidmem",
+ "fbdevHWValidMode",
+
+ NULL
+};
+
+const char *GLINTint10Symbols[] = {
+ "xf86FreeInt10",
+ "xf86InitInt10",
+ NULL
+};
+
+#ifdef XF86DRI
+static const char *drmSymbols[] = {
+ "drmAddBufs",
+ "drmAddMap",
+ "drmCommandWrite",
+ "drmCtlInstHandler",
+ "drmFreeVersion",
+ "drmGetInterruptFromBusID",
+ "drmGetLibVersion",
+ "drmGetVersion",
+ "drmMapBufs",
+ "drmUnmapBufs",
+ NULL
+};
+
+static const char *driSymbols[] = {
+ "DRICloseScreen",
+ "DRICreateInfoRec",
+ "DRIDestroyInfoRec",
+ "DRIFinishScreenInit",
+ "DRIGetDrawableIndex",
+ "DRIQueryVersion",
+ "DRIScreenInit",
+ "GlxSetVisualConfigs",
+ NULL
+};
+#endif
+
+#ifdef XFree86LOADER
+
+static MODULESETUPPROTO(glintSetup);
+
+static XF86ModuleVersionInfo glintVersRec =
+{
+ "glint",
+ MODULEVENDORSTRING,
+ MODINFOSTRING1,
+ MODINFOSTRING2,
+ XF86_VERSION_CURRENT,
+ GLINT_MAJOR_VERSION, GLINT_MINOR_VERSION, GLINT_PATCHLEVEL,
+ ABI_CLASS_VIDEODRV, /* This is a video driver */
+ ABI_VIDEODRV_VERSION,
+ MOD_CLASS_VIDEODRV,
+ {0,0,0,0}
+};
+
+XF86ModuleData glintModuleData = { &glintVersRec, glintSetup, NULL };
+
+pointer
+glintSetup(pointer module, pointer opts, int *errmaj, int *errmin)
+{
+ static Bool setupDone = FALSE;
+
+ if (!setupDone) {
+ setupDone = TRUE;
+ xf86AddDriver(&GLINT, module, 0);
+ LoaderRefSymLists(fbSymbols, ddcSymbols, i2cSymbols,
+ xaaSymbols, xf8_32bppSymbols,
+ shadowSymbols, fbdevHWSymbols, GLINTint10Symbols,
+ vbeSymbols, ramdacSymbols,
+#ifdef XF86DRI
+ drmSymbols, driSymbols,
+#endif
+ NULL);
+ return (pointer)TRUE;
+ }
+
+ if (errmaj) *errmaj = LDR_ONCEONLY;
+ return NULL;
+}
+
+#endif /* XFree86LOADER */
+
+#define PARTPROD(a,b,c) (((a)<<6) | ((b)<<3) | (c))
+
+static char bppand[4] = { 0x03, /* 8bpp */
+ 0x01, /* 16bpp */
+ 0x00, /* 24bpp */
+ 0x00 /* 32bpp */};
+
+static int partprod500TX[] = {
+ -1,
+ PARTPROD(0,0,1), PARTPROD(0,0,2), PARTPROD(0,1,2), PARTPROD(0,0,3),
+ PARTPROD(0,1,3), PARTPROD(0,2,3), PARTPROD(1,2,3), PARTPROD(0,0,4),
+ PARTPROD(0,1,4), PARTPROD(0,2,4), PARTPROD(1,2,4), PARTPROD(0,3,4),
+ PARTPROD(1,3,4), PARTPROD(2,3,4), -1, PARTPROD(0,0,5),
+ PARTPROD(0,1,5), PARTPROD(0,2,5), PARTPROD(1,2,5), PARTPROD(0,3,5),
+ PARTPROD(1,3,5), PARTPROD(2,3,5), -1, PARTPROD(0,4,5),
+ PARTPROD(1,4,5), PARTPROD(2,4,5), PARTPROD(3,4,5), -1,
+ -1, -1, -1, PARTPROD(0,0,6),
+ PARTPROD(0,1,6), PARTPROD(0,2,6), PARTPROD(1,2,6), PARTPROD(0,3,6),
+ PARTPROD(1,3,6), PARTPROD(2,3,6), -1, PARTPROD(0,4,6),
+ PARTPROD(1,4,6), PARTPROD(2,4,6), -1, PARTPROD(3,4,6),
+ -1, -1, -1, PARTPROD(0,5,6),
+ PARTPROD(1,5,6), PARTPROD(2,5,6), -1, PARTPROD(3,5,6),
+ -1, -1, -1, PARTPROD(4,5,6),
+ -1, -1, -1, -1,
+ -1, -1, -1, PARTPROD(0,0,7),
+ -1, PARTPROD(0,2,7), PARTPROD(1,2,7), PARTPROD(0,3,7),
+ PARTPROD(1,3,7), PARTPROD(2,3,7), -1, PARTPROD(0,4,7),
+ PARTPROD(1,4,7), PARTPROD(2,4,7), -1, PARTPROD(3,4,7),
+ -1, -1, -1, PARTPROD(0,5,7),
+ PARTPROD(1,5,7), PARTPROD(2,5,7), -1, PARTPROD(3,5,7),
+ -1, -1, -1, PARTPROD(4,5,7),
+ -1, -1, -1, -1,
+ -1, -1, -1, PARTPROD(0,6,7),
+ PARTPROD(1,6,7), PARTPROD(2,6,7), -1, PARTPROD(3,6,7),
+ -1, -1, -1, PARTPROD(4,6,7),
+ -1, -1, -1, -1,
+ -1, -1, -1, PARTPROD(5,6,7),
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, PARTPROD(0,7,7),
+ 0};
+
+int partprodPermedia[] = {
+ -1,
+ PARTPROD(0,0,1), PARTPROD(0,1,1), PARTPROD(1,1,1), PARTPROD(1,1,2),
+ PARTPROD(1,2,2), PARTPROD(2,2,2), PARTPROD(1,2,3), PARTPROD(2,2,3),
+ PARTPROD(1,3,3), PARTPROD(2,3,3), PARTPROD(1,2,4), PARTPROD(3,3,3),
+ PARTPROD(1,3,4), PARTPROD(2,3,4), -1, PARTPROD(3,3,4),
+ PARTPROD(1,4,4), PARTPROD(2,4,4), -1, PARTPROD(3,4,4),
+ -1, PARTPROD(2,3,5), -1, PARTPROD(4,4,4),
+ PARTPROD(1,4,5), PARTPROD(2,4,5), PARTPROD(3,4,5), -1,
+ -1, -1, -1, PARTPROD(4,4,5),
+ PARTPROD(1,5,5), PARTPROD(2,5,5), -1, PARTPROD(3,5,5),
+ -1, -1, -1, PARTPROD(4,5,5),
+ -1, -1, -1, PARTPROD(3,4,6),
+ -1, -1, -1, PARTPROD(5,5,5),
+ PARTPROD(1,5,6), PARTPROD(2,5,6), -1, PARTPROD(3,5,6),
+ -1, -1, -1, PARTPROD(4,5,6),
+ -1, -1, -1, -1,
+ -1, -1, -1, PARTPROD(5,5,6),
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ -1, -1, -1, -1,
+ 0};
+
+static void
+GLINTDisplayPowerManagementSet(ScrnInfoPtr pScrn, int PowerManagementMode,
+ int flags)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int videocontrol = 0, vtgpolarity = 0;
+
+ if((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_500TX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_300SX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_MX) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_300SX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_500TX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ) {
+ vtgpolarity = GLINT_READ_REG(VTGPolarity) & 0xFFFFFFF0;
+ } else {
+ videocontrol = GLINT_READ_REG(PMVideoControl) & 0xFFFFFFD6;
+ }
+
+ switch (PowerManagementMode) {
+ case DPMSModeOn:
+ /* Screen: On, HSync: On, VSync: On */
+ videocontrol |= 0x29;
+ vtgpolarity |= 0x05;
+ break;
+ case DPMSModeStandby:
+ /* Screen: Off, HSync: Off, VSync: On */
+ videocontrol |= 0x20;
+ vtgpolarity |= 0x04;
+ break;
+ case DPMSModeSuspend:
+ /* Screen: Off, HSync: On, VSync: Off */
+ videocontrol |= 0x08;
+ vtgpolarity |= 0x01;
+ break;
+ case DPMSModeOff:
+ /* Screen: Off, HSync: Off, VSync: Off */
+ videocontrol |= 0x00;
+ vtgpolarity |= 0x00;
+ break;
+ default:
+ return;
+ }
+
+ if((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_500TX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_300SX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_MX) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_300SX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_500TX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ) {
+ GLINT_SLOW_WRITE_REG(vtgpolarity, VTGPolarity);
+ } else {
+ GLINT_SLOW_WRITE_REG(videocontrol, PMVideoControl);
+ }
+}
+
+static Bool
+GLINTGetRec(ScrnInfoPtr pScrn)
+{
+ TRACE_ENTER("GLINTGetRec");
+ /*
+ * Allocate an GLINTRec, and hook it into pScrn->driverPrivate.
+ * pScrn->driverPrivate is initialised to NULL, so we can check if
+ * the allocation has already been done.
+ */
+ if (pScrn->driverPrivate != NULL)
+ return TRUE;
+
+ pScrn->driverPrivate = xnfcalloc(sizeof(GLINTRec), 1);
+ /* Initialise it */
+
+ TRACE_EXIT("GLINTGetRec");
+ return TRUE;
+}
+
+static void
+GLINTFreeRec(ScrnInfoPtr pScrn)
+{
+ TRACE_ENTER("GLINTFreeRec");
+ if (pScrn->driverPrivate == NULL)
+ return;
+ xfree(pScrn->driverPrivate);
+ pScrn->driverPrivate = NULL;
+ TRACE_EXIT("GLINTFreeRec");
+}
+
+
+/* Mandatory */
+static void
+GLINTIdentify(int flags)
+{
+ xf86PrintChipsets(GLINT_NAME, "driver for 3Dlabs chipsets", GLINTChipsets);
+}
+
+static const OptionInfoRec *
+GLINTAvailableOptions(int chipid, int busid)
+{
+ return GLINTOptions;
+}
+
+static void
+GLINTProbeDDC(ScrnInfoPtr pScrn, int index)
+{
+ vbeInfoPtr pVbe;
+ if (xf86LoadSubModule(pScrn, "vbe"))
+ {
+ pVbe = VBEInit(NULL,index);
+ vbeDoEDID(pVbe, NULL);
+ vbeFree(pVbe);
+ }
+}
+
+/* Mandatory */
+static Bool
+GLINTProbe(DriverPtr drv, int flags)
+{
+ int i;
+ pciVideoPtr pPci, *checkusedPci;
+ GDevPtr *devSections;
+ int numDevSections;
+ int numUsed,bus,device,func;
+ char *dev;
+ int *usedChips = NULL;
+ Bool foundScreen = FALSE;
+ char *name;
+
+ /*
+ TRACE_ENTER("GLINTProbe");
+ */
+ TRACE_EXIT("GLINTProbe (Enter)");
+
+
+ if ((numDevSections = xf86MatchDevice(GLINT_DRIVER_NAME,
+ &devSections)) <= 0) {
+ return FALSE;
+ }
+
+ checkusedPci = xf86GetPciVideoInfo();
+
+ if (checkusedPci == NULL && devSections /* for xf86DoProbe */) {
+ /*
+ * Changed the behaviour to try probing using the FBDev support
+ * when no PCI cards have been found. This is for systems without
+ * (proper) PCI support. (Michel)
+ */
+ if (!xf86LoadDrvSubModule(drv, "fbdevhw"))
+ return FALSE;
+
+ xf86LoaderReqSymLists(fbdevHWSymbols, NULL);
+
+ for (i = 0; i < numDevSections; i++) {
+ dev = xf86FindOptionValue(devSections[i]->options,"fbdev");
+ if (devSections[i]->busID) {
+ xf86ParsePciBusString(devSections[i]->busID,&bus,&device,&func);
+ if (!xf86CheckPciSlot(bus,device,func))
+ continue;
+ }
+ if (fbdevHWProbe(NULL,dev,&name)) {
+ ScrnInfoPtr pScrn;
+
+ /* Check for pm2fb */
+ if (strcmp(name,"Permedia2")) continue;
+ foundScreen = TRUE;
+ pScrn = NULL;
+
+ if (devSections[i]->busID) {
+ /* XXX what about when there's no busID set? */
+ int entity;
+ entity = xf86ClaimPciSlot(bus,device,func,drv,
+ 0,devSections[i],
+ TRUE);
+ pScrn = xf86ConfigPciEntity(pScrn,0,entity,
+ NULL,RES_SHARED_VGA,
+ NULL,NULL,NULL,NULL);
+ if (pScrn)
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG,
+ "claimed PCI slot %d:%d:%d\n",bus,device,func);
+ } else {
+ /* XXX This is a quick hack */
+ int entity;
+
+ entity = xf86ClaimIsaSlot(drv, 0,
+ devSections[i], TRUE);
+ pScrn = xf86ConfigIsaEntity(pScrn,0,entity,
+ NULL,RES_SHARED_VGA,
+ NULL,NULL,NULL,NULL);
+ }
+ if (pScrn) {
+ /* Fill in what we can of the ScrnInfoRec */
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "%s successfully probed\n", dev ? dev : "default framebuffer device");
+ pScrn->driverVersion = VERSION;
+ pScrn->driverName = GLINT_DRIVER_NAME;
+ pScrn->name = GLINT_NAME;
+ pScrn->Probe = GLINTProbe;
+ pScrn->PreInit = GLINTPreInit;
+ pScrn->ScreenInit = GLINTScreenInit;
+ pScrn->SwitchMode = GLINTSwitchMode;
+ pScrn->FreeScreen = GLINTFreeScreen;
+ pScrn->EnterVT = GLINTEnterVT;
+ }
+ }
+ }
+
+ xfree(devSections);
+
+ } else if (checkusedPci) {
+
+ if (flags & PROBE_DETECT) {
+ /* HACK, Currently when -configuring, we only return VGA
+ * based chips. Manual configuring is necessary to poke
+ * at the other chips */
+ numUsed = xf86MatchPciInstances(GLINT_NAME, 0,
+ GLINTVGAChipsets, GLINTVGAPciChipsets,
+ devSections,
+ numDevSections, drv, &usedChips);
+ } else {
+ numUsed = xf86MatchPciInstances(GLINT_NAME, 0,
+ GLINTChipsets, GLINTPciChipsets, devSections,
+ numDevSections, drv, &usedChips);
+ }
+
+ xfree(devSections);
+ if (numUsed <= 0)
+ return FALSE;
+ foundScreen = TRUE;
+
+ if (!(flags & PROBE_DETECT))
+ for (i = 0; i < numUsed; i++) {
+ ScrnInfoPtr pScrn = NULL;
+ GLINTEntPtr pGlintEnt = NULL;
+ DevUnion *pPriv;
+
+ pPci = xf86GetPciInfoForEntity(usedChips[i]);
+ /* Allocate a ScrnInfoRec and claim the slot */
+ if ((pScrn = xf86ConfigPciEntity(pScrn, 0, usedChips[i],
+ GLINTPciChipsets, NULL,
+ NULL, NULL, NULL, NULL))) {
+
+
+ /* Claim specifics, when we KNOW ! the board */
+
+ /* Appian Jeronimo J2000 */
+ if ((pPci->subsysVendor == 0x1097) &&
+ (pPci->subsysCard == 0x3d32)) {
+ int eIndex;
+ if (!xf86IsEntityShared(usedChips[i])) {
+ eIndex = xf86ClaimPciSlot(pPci->bus,
+ pPci->device,
+ 1,
+ drv, -1 /* XXX */,
+ NULL, FALSE);
+ xf86AddEntityToScreen(pScrn,eIndex);
+ } else {
+ eIndex = xf86ClaimPciSlot(pPci->bus,
+ pPci->device,
+ 2,
+ drv, -1 /* XXX */,
+ NULL, FALSE);
+ xf86AddEntityToScreen(pScrn,eIndex);
+ }
+ } else
+ /* Only claim other chips when GAMMA is used */
+ if ((pPci->chipType == PCI_CHIP_GAMMA) ||
+ (pPci->chipType == PCI_CHIP_GAMMA2) ||
+ (pPci->chipType == PCI_CHIP_DELTA)) {
+ while (*checkusedPci != NULL) {
+ int eIndex;
+ /* make sure we claim all but our source device */
+ if ((pPci->bus == (*checkusedPci)->bus &&
+ pPci->device == (*checkusedPci)->device) &&
+ pPci->func != (*checkusedPci)->func) {
+
+ /* Claim other entities on the same card */
+ eIndex = xf86ClaimPciSlot((*checkusedPci)->bus,
+ (*checkusedPci)->device,
+ (*checkusedPci)->func,
+ drv, -1 /* XXX */,
+ NULL, FALSE);
+
+ if (eIndex != -1) {
+ xf86AddEntityToScreen(pScrn,eIndex);
+ } else {
+ ErrorF("BusID %d:%d:%d already claimed\n",
+ (*checkusedPci)->bus,
+ (*checkusedPci)->device,
+ (*checkusedPci)->func);
+ xfree(usedChips);
+ return FALSE;
+ }
+ }
+ checkusedPci++;
+ }
+ }
+
+ /* Fill in what we can of the ScrnInfoRec */
+ pScrn->driverVersion = VERSION;
+ pScrn->driverName = GLINT_DRIVER_NAME;
+ pScrn->name = GLINT_NAME;
+ pScrn->Probe = GLINTProbe;
+ pScrn->PreInit = GLINTPreInit;
+ pScrn->ScreenInit = GLINTScreenInit;
+ pScrn->SwitchMode = GLINTSwitchMode;
+ pScrn->FreeScreen = GLINTFreeScreen;
+ pScrn->EnterVT = GLINTEnterVT;
+ }
+
+ /* Allow sharing if Appian J2000 detected */
+ /* (later Diamond FireGL3000 support too) */
+
+ if ((pPci->subsysVendor == 0x1097) &&
+ (pPci->subsysCard == 0x3d32)) {
+ xf86SetEntitySharable(usedChips[i]);
+ /* Allocate an entity private if necessary */
+ if (GLINTEntityIndex < 0)
+ GLINTEntityIndex = xf86AllocateEntityPrivateIndex();
+ pPriv = xf86GetEntityPrivate(pScrn->entityList[0],
+ GLINTEntityIndex);
+ if (!pPriv->ptr) {
+ pPriv->ptr = xnfcalloc(sizeof(GLINTEntRec), 1);
+ pGlintEnt = pPriv->ptr;
+ pGlintEnt->lastInstance = -1;
+ } else {
+ pGlintEnt = pPriv->ptr;
+ }
+
+ /*
+ * Set the entity instance for this instance of the driver.
+ * For dual head per card, instance 0 is the "master"
+ * instance, driving the primary head, and instance 1 is
+ * the "slave".
+ */
+ pGlintEnt->lastInstance++;
+ xf86SetEntityInstanceForScreen(pScrn,
+ pScrn->entityList[0], pGlintEnt->lastInstance);
+ }
+ }
+ }
+
+ xfree(usedChips);
+
+ TRACE_EXIT("GLINTProbe");
+ return foundScreen;
+}
+
+/*
+ * GetAccelPitchValues -
+ *
+ * This function returns a list of display width (pitch) values that can
+ * be used in accelerated mode.
+ */
+static int *
+GetAccelPitchValues(ScrnInfoPtr pScrn)
+{
+ int *linePitches = NULL;
+ int i, n = 0;
+ int *linep = NULL;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ linep = &partprodPermedia[0];
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ linep = &partprod500TX[0];
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ /* When GAMMA/DELTA in use, we always have MultiChip defined, even if
+ * only one chip is connected to GAMMA/DELTA as the entities > 1
+ */
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_MX:
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ linep = &partprod500TX[0];
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ linep = &partprodPermedia[0];
+ break;
+ }
+ break;
+ }
+
+ for (i = 0; linep[i] != 0; i++) {
+ if (linep[i] != -1) {
+ n++;
+ linePitches = xnfrealloc(linePitches, n * sizeof(int));
+ linePitches[n - 1] = i << 5;
+ }
+ }
+
+ /* Mark the end of the list */
+ if (n > 0) {
+ linePitches = xnfrealloc(linePitches, (n + 1) * sizeof(int));
+ linePitches[n] = 0;
+ }
+
+ return linePitches;
+}
+
+static void
+GLINTProbeTIramdac(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint;
+ CARD32 temp = 0;
+ pGlint = GLINTPTR(pScrn);
+
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = glintInTIIndReg;
+ pGlint->RamDacRec->WriteDAC = glintOutTIIndReg;
+ pGlint->RamDacRec->ReadAddress = glintTIReadAddress;
+ pGlint->RamDacRec->WriteAddress = glintTIWriteAddress;
+ pGlint->RamDacRec->ReadData = glintTIReadData;
+ pGlint->RamDacRec->WriteData = glintTIWriteData;
+ pGlint->RamDacRec->LoadPalette = TIramdacLoadPalette;
+
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return;
+ }
+ GLINTMapMem(pScrn);
+ if (pGlint->numMultiDevices == 2) {
+ temp = GLINT_READ_REG(GCSRAperture);
+ GLINT_SLOW_WRITE_REG(GCSRSecondaryGLINTMapEn, GCSRAperture);
+ }
+ pGlint->RamDac = TIramdacProbe(pScrn, TIRamdacs);
+ if (pGlint->numMultiDevices == 2) {
+ GLINT_SLOW_WRITE_REG(temp, GCSRAperture);
+ }
+ GLINTUnmapMem(pScrn);
+}
+
+static void
+GLINTProbeIBMramdac(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint;
+ pGlint = GLINTPTR(pScrn);
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = glintInIBMRGBIndReg;
+ pGlint->RamDacRec->WriteDAC = glintOutIBMRGBIndReg;
+ pGlint->RamDacRec->ReadAddress = glintIBMReadAddress;
+ pGlint->RamDacRec->WriteAddress = glintIBMWriteAddress;
+ pGlint->RamDacRec->ReadData = glintIBMReadData;
+ pGlint->RamDacRec->WriteData = glintIBMWriteData;
+ pGlint->RamDacRec->LoadPalette = NULL;
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return;
+ }
+ GLINTMapMem(pScrn);
+ pGlint->RamDac = IBMramdacProbe(pScrn, IBMRamdacs);
+ GLINTUnmapMem(pScrn);
+}
+
+/* Mandatory */
+static Bool
+GLINTPreInit(ScrnInfoPtr pScrn, int flags)
+{
+ GLINTPtr pGlint;
+ GLINTEntPtr pGlintEnt = NULL;
+ MessageType from;
+ int i;
+ Bool Overlay = FALSE;
+ int maxwidth = 0, maxheight = 0;
+ ClockRangePtr clockRanges;
+ char *mod = NULL;
+ const char *s;
+ const char **syms = NULL;
+
+ TRACE_ENTER("GLINTPreInit");
+
+ /*
+ * Note: This function is only called once at server startup, and
+ * not at the start of each server generation. This means that
+ * only things that are persistent across server generations can
+ * be initialised here. xf86Screens[] is (pScrn is a pointer to one
+ * of these). Privates allocated using xf86AllocateScrnInfoPrivateIndex()
+ * are too, and should be used for data that must persist across
+ * server generations.
+ *
+ * Per-generation data should be allocated with
+ * AllocateScreenPrivateIndex() from the ScreenInit() function.
+ */
+
+ /* Check the number of entities, and fail if it isn't one or more. */
+ if (pScrn->numEntities < 1)
+ return FALSE;
+
+ /* Allocate the GLINTRec driverPrivate */
+ if (!GLINTGetRec(pScrn)) {
+ return FALSE;
+ }
+ pGlint = GLINTPTR(pScrn);
+
+ /* Get the entities, and make sure they are PCI. */
+ pGlint->pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
+
+ /* Allocate an entity private if necessary */
+ if (xf86IsEntityShared(pScrn->entityList[0])) {
+ pGlintEnt = xf86GetEntityPrivate(pScrn->entityList[0],
+ GLINTEntityIndex)->ptr;
+ pGlint->entityPrivate = pGlintEnt;
+ }
+
+ if (pGlint->pEnt->location.type == BUS_PCI)
+ {
+ pGlint->PciInfo = xf86GetPciInfoForEntity(pGlint->pEnt->index);
+ pGlint->PciTag = pciTag(pGlint->PciInfo->bus, pGlint->PciInfo->device,
+ pGlint->PciInfo->func);
+ }
+
+ pGlint->InFifoSpace = 0; /* Force a Read of FIFO space on first run */
+ pGlint->numMultiDevices = 0;
+ pGlint->IOOffset = 0; /* Set IO Offset for Gamma */
+
+ if (pScrn->numEntities > 1) {
+ pciVideoPtr pPci;
+ EntityInfoPtr pEnt;
+
+ for (i = 1; i < pScrn->numEntities; i++) {
+ pEnt = xf86GetEntityInfo(pScrn->entityList[i]);
+ pPci = xf86GetPciInfoForEntity(pEnt->index);
+ if ( (pPci->chipType == PCI_CHIP_MX) ||
+ (pPci->chipType == PCI_CHIP_PERMEDIA) ||
+ (pPci->chipType == PCI_CHIP_TI_PERMEDIA) ||
+ (pPci->chipType == PCI_CHIP_500TX) ||
+ (pPci->chipType == PCI_CHIP_300SX) ||
+ (pPci->chipType == PCI_CHIP_R4) ||
+ (pPci->chipType == PCI_CHIP_PERMEDIA3) ) {
+ pGlint->MultiChip = pPci->chipType;
+ if (pGlint->numMultiDevices >= GLINT_MAX_MULTI_DEVICES) {
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
+ "%d multiple chips unsupported, aborting. (Max - 2)\n",
+ pGlint->numMultiDevices);
+ return FALSE;
+ } else {
+ pGlint->MultiPciInfo[pGlint->numMultiDevices] = pPci;
+ pGlint->numMultiDevices++;
+ }
+ }
+ }
+ }
+
+ {
+ EntityInfoPtr pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
+ pciVideoPtr pPci = xf86GetPciInfoForEntity(pEnt->index);
+
+ if ( ((pPci->chipType == PCI_CHIP_GAMMA) ||
+ (pPci->chipType == PCI_CHIP_GAMMA2) ||
+ (pPci->chipType == PCI_CHIP_DELTA)) &&
+ (pGlint->numMultiDevices == 0) ) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "Gamma/Delta with ZERO connected chips, aborting\n");
+ return FALSE;
+ }
+ }
+
+ if (flags & PROBE_DETECT) {
+ EntityInfoPtr pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
+ pciVideoPtr pPci = xf86GetPciInfoForEntity(pEnt->index);
+
+ if ((pPci->chipType != PCI_CHIP_GAMMA) &&
+ (pPci->chipType != PCI_CHIP_GAMMA2) &&
+ (pPci->chipType != PCI_CHIP_DELTA)) {
+ GLINTProbeDDC(pScrn, pGlint->pEnt->index);
+ return TRUE;
+ } else
+ return FALSE;
+ }
+
+ xf86SetOperatingState(resVga, pGlint->pEnt->index, ResDisableOpr);
+
+ /* Operations for which memory access is required. */
+ pScrn->racMemFlags = RAC_FB | RAC_COLORMAP | RAC_CURSOR | RAC_VIEWPORT;
+ pScrn->racIoFlags = RAC_FB | RAC_COLORMAP | RAC_CURSOR | RAC_VIEWPORT;
+
+ /* Set pScrn->monitor */
+ pScrn->monitor = pScrn->confScreen->monitor;
+ /*
+ * The first thing we should figure out is the depth, bpp, etc.
+ * Our default depth is 8, so pass it to the helper function.
+ * We support both 24bpp and 32bpp layouts, so indicate that.
+ */
+ if (FBDevProbed) {
+ int default_depth, fbbpp;
+
+ if (!fbdevHWInit(pScrn,NULL,xf86FindOptionValue(pGlint->pEnt->device->options,"fbdev"))) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "fbdevHWInit failed!\n");
+ return FALSE;
+ }
+ default_depth = fbdevHWGetDepth(pScrn,&fbbpp);
+ if (!xf86SetDepthBpp(pScrn, default_depth, default_depth, fbbpp,0))
+ return FALSE;
+ } else {
+ if (!xf86SetDepthBpp(pScrn, 8, 0, 0, Support24bppFb | Support32bppFb
+ /*| SupportConvert32to24 | PreferConvert32to24*/))
+ return FALSE;
+ }
+ /* Check that the returned depth is one we support */
+ switch (pScrn->depth) {
+ case 8:
+ case 15:
+ case 16:
+ case 24:
+ case 30:
+ /* OK */
+ break;
+ default:
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "Given depth (%d) is not supported by this driver\n",
+ pScrn->depth);
+ return FALSE;
+ }
+
+ xf86PrintDepthBpp(pScrn);
+
+ /*
+ * This must happen after pScrn->display has been set because
+ * xf86SetWeight references it.
+ */
+ if (pScrn->depth > 8) {
+ /* The defaults are OK for us */
+ rgb zeros = {0, 0, 0};
+
+ if (!xf86SetWeight(pScrn, zeros, zeros)) {
+ return FALSE;
+ } else {
+ /* XXX check that weight returned is supported */
+ ;
+ }
+ }
+
+ if (!xf86SetDefaultVisual(pScrn, -1)) {
+ return FALSE;
+ } else {
+ /* We don't currently support DirectColor at > 8bpp */
+ if (pScrn->depth > 8 && pScrn->defaultVisual != TrueColor) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Given default visual"
+ " (%s) is not supported at depth %d\n",
+ xf86GetVisualName(pScrn->defaultVisual), pScrn->depth);
+ return FALSE;
+ }
+ }
+
+ /*
+ * If the driver can do gamma correction, it should call xf86SetGamma()
+ * here.
+ */
+
+ {
+ Gamma zeros = {0.0, 0.0, 0.0};
+
+ if (!xf86SetGamma(pScrn, zeros)) {
+ return FALSE;
+ }
+ }
+
+ /* We use a programmable clock */
+ pScrn->progClock = TRUE;
+
+ /* Collect all of the relevant option flags (fill in pScrn->options) */
+ xf86CollectOptions(pScrn, NULL);
+
+ /* Process the options */
+ if (!(pGlint->Options = xalloc(sizeof(GLINTOptions))))
+ return FALSE;
+ memcpy(pGlint->Options, GLINTOptions, sizeof(GLINTOptions));
+ xf86ProcessOptions(pScrn->scrnIndex, pScrn->options, pGlint->Options);
+
+ /* Default to 8bits per RGB */
+ if (pScrn->depth == 30) pScrn->rgbBits = 10;
+ else pScrn->rgbBits = 8;
+ if (xf86GetOptValInteger(pGlint->Options, OPTION_RGB_BITS, &pScrn->rgbBits)) {
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Bits per RGB set to %d\n",
+ pScrn->rgbBits);
+ }
+
+ from = X_DEFAULT;
+ pGlint->HWCursor = TRUE; /* ON by default */
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_SW_CURSOR, FALSE)) {
+ from = X_CONFIG;
+ pGlint->HWCursor = FALSE;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, from, "Using %s cursor\n",
+ pGlint->HWCursor ? "HW" : "SW");
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_FLATPANEL, FALSE)) {
+ pGlint->UseFlatPanel = TRUE;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Using Flat Panel Interface\n");
+ }
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_NOACCEL, FALSE)) {
+ pGlint->NoAccel = TRUE;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Acceleration disabled\n");
+ }
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_SHADOW_FB, FALSE)) {
+ pGlint->ShadowFB = TRUE;
+ pGlint->NoAccel = TRUE;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG,
+ "Using \"Shadow Framebuffer\" - acceleration disabled\n");
+ }
+ if(xf86GetOptValInteger(pGlint->Options, OPTION_VIDEO_KEY,
+ &(pGlint->videoKey))) {
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "video key set to 0x%x\n",
+ pGlint->videoKey);
+ } else {
+ /* Needs 8bit values for all modes */
+ pGlint->videoKey = (1 << 16) |
+ (1 << 8) |
+ ((pScrn->mask.blue - 1) << 0);
+ }
+
+ /* Check whether to use the FBDev stuff and fill in the rest of pScrn */
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_FBDEV, FALSE)) {
+ if (!FBDevProbed && !xf86LoadSubModule(pScrn, "fbdevhw"))
+ {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "couldn't load fbdevHW module!\n");
+ return FALSE;
+ }
+
+ xf86LoaderReqSymLists(fbdevHWSymbols, NULL);
+
+ if (!fbdevHWInit(pScrn,NULL,xf86FindOptionValue(pGlint->pEnt->device->options,"fbdev")))
+ {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "fbdevHWInit failed!\n");
+ return FALSE;
+ }
+
+ pGlint->FBDev = TRUE;
+ from = X_CONFIG;
+
+ pScrn->AdjustFrame = fbdevHWAdjustFrame;
+ pScrn->LeaveVT = fbdevHWLeaveVT;
+ pScrn->ValidMode = fbdevHWValidMode;
+
+ } else {
+ /* Only use FBDev if requested */
+ pGlint->FBDev = FALSE;
+ from = X_PROBED;
+
+ pScrn->AdjustFrame = GLINTAdjustFrame;
+ pScrn->LeaveVT = GLINTLeaveVT;
+ pScrn->ValidMode = GLINTValidMode;
+
+ }
+ xf86DrvMsg(pScrn->scrnIndex, from, "%s Linux framebuffer device\n",
+ pGlint->FBDev ? "Using" : "Not using");
+
+ pScrn->overlayFlags = 0;
+ from = X_DEFAULT;
+ if ((s = xf86GetOptValString(pGlint->Options, OPTION_OVERLAY))) {
+ if (!*s || !xf86NameCmp(s, "8,24") || !xf86NameCmp(s, "24,8")) {
+ Overlay = TRUE;
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
+ "\"%s\" is not a valid value for Option \"Overlay\"\n", s);
+ }
+ }
+ if (Overlay) {
+ if ((pScrn->depth == 24) && (pScrn->bitsPerPixel == 32)) {
+ pScrn->colorKey = 255; /* we should let the user change this */
+ pScrn->overlayFlags = OVERLAY_8_32_PLANAR;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "24/8 overlay enabled\n");
+ }
+ }
+
+ pGlint->DoubleBuffer = FALSE;
+ pGlint->RamDac = NULL;
+ pGlint->STATE = FALSE;
+ /*
+ * Set the Chipset and ChipRev, allowing config file entries to
+ * override.
+ */
+ if (FBDevProbed) { /* pm2fb so far only supports the Permedia2 */
+ pScrn->chipset = "ti_pm2";
+ pGlint->Chipset = xf86StringToToken(GLINTChipsets, pScrn->chipset);
+ from = X_PROBED;
+ } else {
+ if (pGlint->pEnt->device->chipset && *pGlint->pEnt->device->chipset) {
+ pScrn->chipset = pGlint->pEnt->device->chipset;
+ pGlint->Chipset = xf86StringToToken(GLINTChipsets, pScrn->chipset);
+ from = X_CONFIG;
+ } else if (pGlint->pEnt->device->chipID >= 0) {
+ pGlint->Chipset = pGlint->pEnt->device->chipID;
+ pScrn->chipset = (char *)xf86TokenToString(GLINTChipsets,
+ pGlint->Chipset);
+
+ from = X_CONFIG;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "ChipID override: 0x%04X\n",
+ pGlint->Chipset);
+ } else {
+ from = X_PROBED;
+ pGlint->Chipset = pGlint->PciInfo->vendor << 16 |
+ pGlint->PciInfo->chipType;
+ pScrn->chipset = (char *)xf86TokenToString(GLINTChipsets,
+ pGlint->Chipset);
+ }
+ if (pGlint->pEnt->device->chipRev >= 0) {
+ pGlint->ChipRev = pGlint->pEnt->device->chipRev;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "ChipRev override: %d\n",
+ pGlint->ChipRev);
+ } else {
+ pGlint->ChipRev = pGlint->PciInfo->chipRev;
+ }
+ }
+
+ /*
+ * This shouldn't happen because such problems should be caught in
+ * GLINTProbe(), but check it just in case.
+ */
+ if (pScrn->chipset == NULL) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "ChipID 0x%04X is not recognised\n", pGlint->Chipset);
+ return FALSE;
+ }
+ if (pGlint->Chipset < 0) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "Chipset \"%s\" is not recognised\n", pScrn->chipset);
+ return FALSE;
+ }
+
+ xf86DrvMsg(pScrn->scrnIndex, from, "Chipset: \"%s\"\n", pScrn->chipset);
+
+ if ((pGlint->Chipset == PCI_VENDOR_TI_CHIP_PERMEDIA2) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2)) {
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_BLOCK_WRITE, FALSE)) {
+ pGlint->UseBlockWrite = TRUE;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Block Writes enabled\n");
+ }
+ }
+
+ if (xf86ReturnOptValBool(pGlint->Options, OPTION_FIREGL3000, FALSE)) {
+ /* Can't we detect a Fire GL 3000 ????? and remove this ? */
+ pGlint->UseFireGL3000 = TRUE;
+ xf86DrvMsg(pScrn->scrnIndex, X_CONFIG,
+ "Diamond FireGL3000 mode enabled\n");
+ }
+
+ if (!FBDevProbed) {
+ if (pGlint->pEnt->device->MemBase != 0) {
+ /*
+ * XXX Should check that the config file value matches one of the
+ * PCI base address values.
+ */
+ pGlint->FbAddress = pGlint->pEnt->device->MemBase;
+ from = X_CONFIG;
+ } else {
+ pGlint->FbAddress = pGlint->PciInfo->memBase[2] & 0xFF800000;
+ }
+
+ if (pGlint->FbAddress)
+ xf86DrvMsg(pScrn->scrnIndex, from, "Linear framebuffer at 0x%lX\n",
+ (unsigned long)pGlint->FbAddress);
+
+ /* Trap GAMMA & DELTA specification, with no linear address */
+ /* Find the first GLINT chip and use that address */
+ if (pGlint->FbAddress == 0) {
+ if (pGlint->MultiPciInfo[0]->memBase[2]) {
+ pGlint->FbAddress = pGlint->MultiPciInfo[0]->memBase[2];
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "FrameBuffer used from first rasterizer chip at 0x%x\n",
+ pGlint->MultiPciInfo[0]->memBase[2]);
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "No FrameBuffer memory - aborting\n");
+ return FALSE;
+ }
+ }
+
+ if (pGlint->pEnt->device->IOBase != 0) {
+ /*
+ * XXX Should check that the config file value matches one of the
+ * PCI base address values.
+ */
+ pGlint->IOAddress = pGlint->pEnt->device->IOBase;
+ from = X_CONFIG;
+ } else {
+ pGlint->IOAddress = pGlint->PciInfo->memBase[0] & 0xFFFFC000;
+ }
+
+ if ((IS_J2000) && (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)) {
+ /* We know which head is the primary on the J2000 board, need a more
+ * generix solution though.
+ */
+ if ((xf86IsEntityShared(pScrn->entityList[0])) &&
+ (xf86IsPrimInitDone(pScrn->entityList[0]))) {
+ pGlint->IOAddress += 0x10000;
+ pGlint->MultiIndex = 2;
+ } else {
+ xf86SetPrimInitDone(pScrn->entityList[0]);
+ pGlint->MultiIndex = 1;
+ }
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ GLINT_SLOW_WRITE_REG(
+ GLINT_READ_REG(GCSRAperture) | GCSRBitSwap
+ , GCSRAperture);
+ } else {
+ pGlint->IOAddress += 0x10000;
+#endif
+ }
+
+ xf86DrvMsg(pScrn->scrnIndex, from, "MMIO registers at 0x%lX\n",
+ (unsigned long)pGlint->IOAddress);
+
+ pGlint->irq = pGlint->pEnt->device->irq;
+
+ /* Register all entities */
+ for (i = 0; i < pScrn->numEntities; i++) {
+ EntityInfoPtr pEnt;
+ pEnt = xf86GetEntityInfo(pScrn->entityList[i]);
+ if (xf86RegisterResources(pEnt->index, NULL, ResExclusive)) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "xf86RegisterResources() found resource conflicts\n");
+ return FALSE;
+ }
+ }
+ }
+
+ /* Initialize the card through int10 interface if needed */
+ if (pGlint->Chipset != PCI_VENDOR_3DLABS_CHIP_GAMMA &&
+ pGlint->Chipset != PCI_VENDOR_3DLABS_CHIP_GAMMA2 &&
+ pGlint->Chipset != PCI_VENDOR_3DLABS_CHIP_DELTA &&
+ !xf86IsPrimaryPci(pGlint->PciInfo) && !pGlint->FBDev) {
+ if ( xf86LoadSubModule(pScrn, "int10")){
+ xf86Int10InfoPtr pInt;
+
+ xf86LoaderReqSymLists(GLINTint10Symbols, NULL);
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Initializing int10\n");
+ pInt = xf86InitInt10(pGlint->pEnt->index);
+ xf86FreeInt10(pInt);
+ }
+ }
+
+ pGlint->FbMapSize = 0;
+
+ {
+ /* We have to boot some multiple head type boards here */
+ GLINTMapMem(pScrn);
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ Permedia3PreInit(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VPreInit(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ Permedia2PreInit(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_PERMEDIA3:
+ Permedia3PreInit(pScrn);
+ break;
+ }
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ /* Delta has a bug, we need to fix it here */
+ {
+ int basecopro =
+ pGlint->MultiPciInfo[0]->memBase[0] & 0xFFFFC000;
+ int basedelta = pGlint->PciInfo->memBase[0] & 0xFFFFC000;
+ int glintdelta = pGlint->PciTag;
+ int glintcopro = pciTag(pGlint->MultiPciInfo[0]->bus,
+ pGlint->MultiPciInfo[0]->device,
+ pGlint->MultiPciInfo[0]->func);
+ int temp, base3copro, offset;
+
+ if( (basedelta & 0x20000) ^ (basecopro & 0x20000) ) {
+ if ((pGlint->MultiChip == PCI_CHIP_PERMEDIA) ||
+ (pGlint->MultiChip == PCI_CHIP_TI_PERMEDIA)) {
+ offset = 0x20; /* base4 */
+ } else {
+ offset = 0x1c; /* base3 */
+ }
+ base3copro = pciReadLong(glintcopro, offset);
+ if( (basecopro & 0x20000) ^ (base3copro & 0x20000) ) {
+ /*
+ * oops, still different; we know that base3
+ * is at least 16 MB, so we just take 128k
+ * offset into it.
+ */
+ base3copro += 0x20000;
+ }
+ /*
+ * and now for the magic.
+ * read old value
+ * write fffffffff
+ * read value
+ * write new value
+ */
+ temp = pciReadLong(glintdelta, 0x10);
+ pciWriteLong(glintdelta, 0x10, 0xffffffff);
+ temp = pciReadLong(glintdelta, 0x10);
+ pciWriteLong(glintdelta, 0x10, base3copro);
+
+ /*
+ * additionally,sometimes we see the baserom which might
+ * confuse the chip, so let's make sure that is disabled
+ */
+ temp = pciReadLong(glintcopro, 0x30);
+ pciWriteLong(glintcopro, 0x30, 0xffffffff);
+ temp = pciReadLong(glintcopro, 0x30);
+ pciWriteLong(glintcopro, 0x30, 0);
+
+ /*
+ * now update our internal structure accordingly
+ */
+ pGlint->IOAddress =
+ pGlint->PciInfo->memBase[0] = base3copro;
+ xf86DrvMsg(pScrn->scrnIndex, from,
+ "Delta Bug - Changing MMIO registers to 0x%lX\n",
+ (unsigned long)pGlint->IOAddress);
+ }
+ }
+ break;
+ default:
+ break;
+ }
+ GLINTUnmapMem(pScrn);
+ }
+
+ /* HW bpp matches reported bpp */
+ pGlint->HwBpp = pScrn->bitsPerPixel;
+
+ pGlint->FbBase = NULL;
+ if (!FBDevProbed) {
+ if (pGlint->pEnt->device->videoRam != 0) {
+ pScrn->videoRam = pGlint->pEnt->device->videoRam;
+ from = X_CONFIG;
+ } else {
+ /* Need to access MMIO to determine videoRam */
+ GLINTMapMem(pScrn);
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ pScrn->videoRam = (1 << ((GLINT_READ_REG(FBMemoryCtl) &
+ 0xE0000000)>>29)) * 1024;
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ pScrn->videoRam = (((GLINT_READ_REG(PMMemConfig) >> 29) &
+ 0x03) + 1) * 2048;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ pScrn->videoRam = Permedia3MemorySizeDetect(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Attached Rasterizer is GLINT Permedia\n");
+ pScrn->videoRam = (((GLINT_READ_REG(PMMemConfig)>>29) &
+ 0x03) + 1) * 2048;
+ break;
+ case PCI_CHIP_300SX:
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Attached Rasterizer is GLINT 300SX\n");
+ pScrn->videoRam = (1 << ((GLINT_READ_REG(FBMemoryCtl) &
+ 0xE0000000)>>29)) * 1024;
+ break;
+ case PCI_CHIP_500TX:
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Attached Rasterizer is GLINT 500TX\n");
+ pScrn->videoRam = (1 << ((GLINT_READ_REG(FBMemoryCtl) &
+ 0xE0000000)>>29)) * 1024;
+ break;
+ case PCI_CHIP_MX:
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Attached Rasterizer is GLINT MX\n");
+ pScrn->videoRam =
+ (1 << ((GLINT_READ_REG(FBMemoryCtl) &
+ 0xE0000000)>>29)) * 1024;
+ break;
+ case PCI_CHIP_PERMEDIA3:
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Attached Rasterizer is Permedia3\n");
+ pScrn->videoRam = Permedia3MemorySizeDetect(pScrn);
+ break;
+ case PCI_CHIP_R4:
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Attached Rasterizer is R4\n");
+ pScrn->videoRam = Permedia3MemorySizeDetect(pScrn);
+ break;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Number of Rasterizers attached is %d\n",
+ pGlint->numMultiDevices);
+ break;
+ }
+ GLINTUnmapMem(pScrn);
+ }
+ } else {
+ pScrn->videoRam = fbdevHWGetVidmem(pScrn)/1024;
+ }
+
+ pGlint->FbMapSize = pScrn->videoRam * 1024;
+
+ /* OVERRIDE videoRam/FbMapSize, for Multiply connected chips to GAMMA */
+ pGlint->MultiAperture = FALSE;
+ if ( ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA2)) &&
+ (pGlint->numMultiDevices == 2) ) {
+ CARD32 chipconfig;
+ CARD32 size = 0;
+ CARD32 temp;
+
+ GLINTMapMem(pScrn);
+
+ temp = GLINT_READ_REG(GCSRAperture);
+ GLINT_SLOW_WRITE_REG(GCSRSecondaryGLINTMapEn, GCSRAperture);
+
+ chipconfig = GLINT_READ_REG(GChipConfig);
+
+ GLINT_SLOW_WRITE_REG(GCSRSecondaryGLINTMapEn, GCSRAperture);
+
+ GLINTUnmapMem(pScrn);
+
+ switch (chipconfig & GChipMultiGLINTApMask) {
+ case GChipMultiGLINTAp_0M:
+ size = 0;
+ break;
+ case GChipMultiGLINTAp_16M:
+ size = 16 * 1024 * 1024;
+ break;
+ case GChipMultiGLINTAp_32M:
+ size = 32 * 1024 * 1024;
+ break;
+ case GChipMultiGLINTAp_64M:
+ size = 64 * 1024 * 1024;
+ break;
+ }
+
+ if (size == 0) {
+ xf86DrvMsg(pScrn->scrnIndex, from, "MultiAperture: disabled\n");
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, from, "MultiAperture: enabled\n");
+ pGlint->FbMapSize = size;
+ pGlint->MultiAperture = TRUE;
+ }
+ }
+
+ xf86DrvMsg(pScrn->scrnIndex, from, "VideoRAM: %d kByte\n",
+ pGlint->FbMapSize / 1024);
+
+ /* The ramdac module should be loaded here when needed */
+ if (!xf86LoadSubModule(pScrn, "ramdac"))
+ return FALSE;
+
+ xf86LoaderReqSymLists(ramdacSymbols, NULL);
+
+ /* Let's check what type of DAC we have and reject if necessary */
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ pGlint->FIFOSize = 256;
+ maxheight = 2048;
+ maxwidth = 2048;
+ pGlint->RefClock = 14318;
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = Permedia2InIndReg;
+ pGlint->RamDacRec->WriteDAC = Permedia2OutIndReg;
+ pGlint->RamDacRec->ReadAddress = Permedia2ReadAddress;
+ pGlint->RamDacRec->WriteAddress = Permedia2WriteAddress;
+ pGlint->RamDacRec->ReadData = Permedia2ReadData;
+ pGlint->RamDacRec->WriteData = Permedia2WriteData;
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return FALSE;
+ }
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ pGlint->FIFOSize = 256;
+ maxheight = 2048;
+ maxwidth = 2048;
+ pGlint->RefClock = 14318;
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = Permedia2vInIndReg;
+ pGlint->RamDacRec->WriteDAC = Permedia2vOutIndReg;
+ pGlint->RamDacRec->ReadAddress = Permedia2ReadAddress;
+ pGlint->RamDacRec->WriteAddress = Permedia2WriteAddress;
+ pGlint->RamDacRec->ReadData = Permedia2ReadData;
+ pGlint->RamDacRec->WriteData = Permedia2WriteData;
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return FALSE;
+ }
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ if (pScrn->bitsPerPixel == 24) {
+ xf86DrvMsg(pScrn->scrnIndex, from,
+ "-depth 24 -pixmap24 not supported by this chip.\n");
+ return FALSE;
+ }
+ pGlint->FIFOSize = 120;
+ maxheight = 4096;
+ maxwidth = 4096;
+ pGlint->RefClock = 14318;
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = Permedia2vInIndReg;
+ pGlint->RamDacRec->WriteDAC = Permedia2vOutIndReg;
+ pGlint->RamDacRec->ReadAddress = Permedia2ReadAddress;
+ pGlint->RamDacRec->WriteAddress = Permedia2WriteAddress;
+ pGlint->RamDacRec->ReadData = Permedia2ReadData;
+ pGlint->RamDacRec->WriteData = Permedia2WriteData;
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return FALSE;
+ }
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ pGlint->FIFOSize = 31;
+ maxheight = 1024;
+ maxwidth = 1536;
+ /* Test for an TI ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeTIramdac(pScrn);
+ if (pGlint->RamDac)
+ if (pGlint->RamDac->RamDacType == (TI3026_RAMDAC))
+ pGlint->RefClock = 14318;
+ }
+ /* Test for an IBM ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeIBMramdac(pScrn);
+ if (pGlint->RamDac) {
+ if (pGlint->RamDac->RamDacType == (IBM526DB_RAMDAC) ||
+ pGlint->RamDac->RamDacType == (IBM526_RAMDAC))
+ pGlint->RefClock = 14318;
+ }
+ }
+ if (!pGlint->RamDac)
+ return FALSE;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ pGlint->FIFOSize = 15;
+ if (pScrn->bitsPerPixel == 24) {
+ xf86DrvMsg(pScrn->scrnIndex, from,
+ "-depth 24 -pixmap24 not supported by this chip.\n");
+ return FALSE;
+ }
+ maxheight = 4096;
+ maxwidth = 4096;
+ /* Test for an TI ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeTIramdac(pScrn);
+ if (pGlint->RamDac)
+ if ( (pGlint->RamDac->RamDacType == (TI3026_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (TI3030_RAMDAC)) )
+ pGlint->RefClock = 14318;
+ }
+ /* Test for an IBM ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeIBMramdac(pScrn);
+ if (pGlint->RamDac) {
+ if (pGlint->RamDac->RamDacType == (IBM640_RAMDAC))
+ pGlint->RefClock = 28322;
+ else
+ if (pGlint->RamDac->RamDacType == (IBM526DB_RAMDAC) ||
+ pGlint->RamDac->RamDacType == (IBM526_RAMDAC))
+ pGlint->RefClock = 40000;
+ }
+ }
+ if (!pGlint->RamDac)
+ return FALSE;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ pGlint->FIFOSize = 15;
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ maxheight = 1024;
+ maxwidth = 1536;
+ /* Test for an TI ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeTIramdac(pScrn);
+ if (pGlint->RamDac)
+ if (pGlint->RamDac->RamDacType == (TI3026_RAMDAC))
+ pGlint->RefClock = 14318;
+ }
+ /* Test for an IBM ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeIBMramdac(pScrn);
+ if (pGlint->RamDac) {
+ if (pGlint->RamDac->RamDacType == (IBM526DB_RAMDAC) ||
+ pGlint->RamDac->RamDacType == (IBM526_RAMDAC))
+ pGlint->RefClock = 14318;
+ }
+ }
+ if (!pGlint->RamDac)
+ return FALSE;
+ break;
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ case PCI_CHIP_MX:
+ if (pScrn->bitsPerPixel == 24) {
+ xf86DrvMsg(pScrn->scrnIndex, from,
+ "-depth 24 -pixmap24 not supported by this chip.\n");
+ return FALSE;
+ }
+ maxheight = 4096;
+ maxwidth = 4096;
+ /* Test for an TI ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeTIramdac(pScrn);
+ if (pGlint->RamDac)
+ if ( (pGlint->RamDac->RamDacType == (TI3026_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (TI3030_RAMDAC)) )
+ pGlint->RefClock = 14318;
+ }
+ /* Test for an IBM ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeIBMramdac(pScrn);
+ if (pGlint->RamDac) {
+ if (pGlint->RamDac->RamDacType == (IBM640_RAMDAC) ||
+ pGlint->RamDac->RamDacType == (IBM526DB_RAMDAC) ||
+ pGlint->RamDac->RamDacType == (IBM526_RAMDAC))
+ pGlint->RefClock = 40000;
+ }
+ }
+ break;
+ }
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ pGlint->FIFOSize = 32;
+ if (pScrn->bitsPerPixel == 24) {
+ xf86DrvMsg(pScrn->scrnIndex, from,
+ "-depth 24 -pixmap24 not supported by this chip.\n");
+ return FALSE;
+ }
+ maxheight = 4096;
+ maxwidth = 4096;
+ /* Let's do board specific stuff first */
+ if (IS_J2000) {
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Appian Jeronimo 2000 board detected\n");
+ pGlint->RefClock = 14318;
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = Permedia2vInIndReg;
+ pGlint->RamDacRec->WriteDAC = Permedia2vOutIndReg;
+ pGlint->RamDacRec->ReadAddress = Permedia2ReadAddress;
+ pGlint->RamDacRec->WriteAddress = Permedia2WriteAddress;
+ pGlint->RamDacRec->ReadData = Permedia2ReadData;
+ pGlint->RamDacRec->WriteData = Permedia2WriteData;
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return FALSE;
+ }
+ break;
+ }
+ if (IS_GMX2000) {
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "3DLabs GMX2000 board detected\n");
+ /* We need to wrap these after detection as the second MX
+ * is the only chip that can write to the TI3030 dac */
+ ACCESSCHIP2();
+ GLINTProbeTIramdac(pScrn);
+ ACCESSCHIP1();
+ pGlint->RamDacRec->ReadDAC = GMX2000InIndReg;
+ pGlint->RamDacRec->WriteDAC = GMX2000OutIndReg;
+ pGlint->RamDacRec->ReadAddress = GMX2000ReadAddress;
+ pGlint->RamDacRec->WriteAddress = GMX2000WriteAddress;
+ pGlint->RamDacRec->ReadData = GMX2000ReadData;
+ pGlint->RamDacRec->WriteData = GMX2000WriteData;
+ pGlint->RefClock = 14318;
+ break;
+ }
+ /* Test for an TI ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeTIramdac(pScrn);
+ if (pGlint->RamDac)
+ if ( (pGlint->RamDac->RamDacType == (TI3026_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (TI3030_RAMDAC)) )
+ pGlint->RefClock = 14318;
+ }
+ /* Test for an IBM ramdac */
+ if (!pGlint->RamDac) {
+ GLINTProbeIBMramdac(pScrn);
+ if (pGlint->RamDac) {
+ if (pGlint->RamDac->RamDacType == (IBM640_RAMDAC))
+ pGlint->RefClock = 28322;
+ else
+ if (pGlint->RamDac->RamDacType == (IBM526DB_RAMDAC) ||
+ pGlint->RamDac->RamDacType == (IBM526_RAMDAC))
+ pGlint->RefClock = 40000;
+ }
+ }
+ if (!pGlint->RamDac) {
+ if ((pGlint->MultiChip == PCI_CHIP_PERMEDIA3) ||
+ (pGlint->MultiChip == PCI_CHIP_R4)) {
+ pGlint->RefClock = 14318;
+ pGlint->RamDacRec = RamDacCreateInfoRec();
+ pGlint->RamDacRec->ReadDAC = Permedia2vInIndReg;
+ pGlint->RamDacRec->WriteDAC = Permedia2vOutIndReg;
+ pGlint->RamDacRec->ReadAddress = Permedia2ReadAddress;
+ pGlint->RamDacRec->WriteAddress = Permedia2WriteAddress;
+ pGlint->RamDacRec->ReadData = Permedia2ReadData;
+ pGlint->RamDacRec->WriteData = Permedia2WriteData;
+ }
+ if(!RamDacInit(pScrn, pGlint->RamDacRec)) {
+ RamDacDestroyInfoRec(pGlint->RamDacRec);
+ return FALSE;
+ }
+ } else
+ if (!pGlint->RamDac)
+ return FALSE;
+ break;
+ }
+
+ if ( pGlint->RamDac &&
+ (pGlint->RamDac->RamDacType != (IBM640_RAMDAC)) &&
+ (pScrn->depth == 30) )
+ {
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
+ "Depth 30 not supported for this chip\n");
+ return FALSE;
+ }
+
+ if (pGlint->FIFOSize)
+ xf86DrvMsg(pScrn->scrnIndex, X_PROBED, "FIFO Size is %d DWORDS\n",
+ pGlint->FIFOSize);
+
+ /* Set the min pixel clock */
+ pGlint->MinClock = 16250; /* XXX Guess, need to check this */
+ xf86DrvMsg(pScrn->scrnIndex, X_DEFAULT, "Min pixel clock is %d MHz\n",
+ pGlint->MinClock / 1000);
+
+ /*
+ * If the user has specified ramdac speed in the XF86Config
+ * file, we respect that setting.
+ */
+ if (pGlint->pEnt->device->dacSpeeds[0]) {
+ int speed = 0;
+
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ speed = pGlint->pEnt->device->dacSpeeds[DAC_BPP8];
+ break;
+ case 16:
+ speed = pGlint->pEnt->device->dacSpeeds[DAC_BPP16];
+ break;
+ case 24:
+ speed = pGlint->pEnt->device->dacSpeeds[DAC_BPP24];
+ break;
+ case 32:
+ speed = pGlint->pEnt->device->dacSpeeds[DAC_BPP32];
+ break;
+ }
+ if (speed == 0)
+ pGlint->MaxClock = pGlint->pEnt->device->dacSpeeds[0];
+ else
+ pGlint->MaxClock = speed;
+ from = X_CONFIG;
+ } else {
+ if((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_500TX)||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_300SX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_MX) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_300SX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_500TX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) )
+ pGlint->MaxClock = 220000;
+ if ( (pGlint->Chipset == PCI_VENDOR_TI_CHIP_PERMEDIA) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ ((pGlint->MultiChip == PCI_CHIP_PERMEDIA) ||
+ (pGlint->MultiChip == PCI_CHIP_TI_PERMEDIA))) ) {
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ pGlint->MaxClock = 200000;
+ break;
+ case 16:
+ pGlint->MaxClock = 100000;
+ break;
+ case 24:
+ pGlint->MaxClock = 50000;
+ break;
+ case 32:
+ pGlint->MaxClock = 50000;
+ break;
+ }
+ }
+ if ( (pGlint->Chipset == PCI_VENDOR_TI_CHIP_PERMEDIA2) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V) ) {
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ pGlint->MaxClock = 230000;
+ break;
+ case 16:
+ pGlint->MaxClock = 230000;
+ break;
+ case 24:
+ pGlint->MaxClock = 150000;
+ break;
+ case 32:
+ pGlint->MaxClock = 110000;
+ break;
+ }
+ }
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA3) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA4) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_R4) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA2) &&
+ (pGlint->MultiChip == PCI_CHIP_R4)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_PERMEDIA3)) )
+ pGlint->MaxClock = 300000;
+ }
+ xf86DrvMsg(pScrn->scrnIndex, from, "Max pixel clock is %d MHz\n",
+ pGlint->MaxClock / 1000);
+
+ /*
+ * Setup the ClockRanges, which describe what clock ranges are available,
+ * and what sort of modes they can be used for.
+ */
+ clockRanges = xnfcalloc(sizeof(ClockRange), 1);
+ clockRanges->next = NULL;
+ clockRanges->minClock = pGlint->MinClock;
+ clockRanges->maxClock = pGlint->MaxClock;
+ clockRanges->clockIndex = -1; /* programmable */
+ clockRanges->interlaceAllowed = FALSE; /* XXX check this */
+ clockRanges->doubleScanAllowed = FALSE; /* XXX check this */
+
+ /*
+ * xf86ValidateModes will check that the mode HTotal and VTotal values
+ * don't exceed the chipset's limit if pScrn->maxHValue and
+ * pScrn->maxVValue are set. Since our GLINTValidMode() already takes
+ * care of this, we don't worry about setting them here.
+ */
+
+ /* Select valid modes from those available */
+ if ((pGlint->NoAccel) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA3) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA4) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_R4) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA2) &&
+ (pGlint->MultiChip == PCI_CHIP_R4)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_PERMEDIA3)) ) {
+ /*
+ * XXX Assuming min pitch 256, max <maxwidth>
+ * XXX Assuming min height 128, max <maxheight>
+ */
+ i = xf86ValidateModes(pScrn, pScrn->monitor->Modes,
+ pScrn->display->modes, clockRanges,
+ NULL, 256, maxwidth,
+ pScrn->bitsPerPixel, 128, maxheight,
+ pScrn->display->virtualX,
+ pScrn->display->virtualY,
+ pGlint->FbMapSize,
+ LOOKUP_BEST_REFRESH);
+ } else {
+ /*
+ * Minimum width 32, Maximum width <maxwidth>
+ * Minimum height 128, Maximum height <maxheight>
+ */
+ i = xf86ValidateModes(pScrn, pScrn->monitor->Modes,
+ pScrn->display->modes, clockRanges,
+ GetAccelPitchValues(pScrn), 32, maxwidth,
+ pScrn->bitsPerPixel, 128, maxheight,
+ pScrn->display->virtualX,
+ pScrn->display->virtualY,
+ pGlint->FbMapSize,
+ LOOKUP_BEST_REFRESH);
+ }
+
+ if (i < 1 && pGlint->FBDev) {
+ fbdevHWUseBuildinMode(pScrn);
+ i = 1;
+ }
+
+ if (i == -1) {
+ GLINTFreeRec(pScrn);
+ return FALSE;
+ }
+
+ if (i == 0 || pScrn->modes == NULL) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "No valid modes found\n");
+ GLINTFreeRec(pScrn);
+ return FALSE;
+ }
+
+ if (pGlint->FBDev) {
+ /* shift horizontal timings for 64bit VRAM's or 32bit SGRAMs */
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ pGlint->BppShift = 2;
+ break;
+ case 16:
+ if (pGlint->DoubleBuffer) {
+ pGlint->BppShift = 0;
+ } else {
+ pGlint->BppShift = 1;
+ }
+ break;
+ case 24:
+ pGlint->BppShift = 2;
+ break;
+ case 32:
+ pGlint->BppShift = 0;
+ break;
+ }
+
+ pScrn->displayWidth = pScrn->virtualX;
+
+ /* Ensure vsync and hsync are high when using HW cursor */
+ if (pGlint->HWCursor) {
+ DisplayModePtr mode, first = mode = pScrn->modes;
+
+ do { /* We know there is at least the built-in mode */
+ mode->Flags |= V_PHSYNC | V_PVSYNC;
+ mode->Flags &= ~V_NHSYNC | ~V_NVSYNC;
+ mode = mode->next;
+ } while (mode != NULL && mode != first);
+ }
+ }
+
+ /* Prune the modes marked as invalid */
+ xf86PruneDriverModes(pScrn);
+
+ /* Only allow a single mode for MX and TX chipsets */
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_500TX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_300SX) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_MX) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_300SX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_500TX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_MX)) ) {
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
+ "This GLINT chip only supports one modeline, using first\n");
+ pScrn->modes->next = NULL;
+ pScrn->virtualX = pScrn->modes->HDisplay;
+ pScrn->virtualY = pScrn->modes->VDisplay;
+ pScrn->displayWidth = pScrn->virtualX;
+ if (partprod500TX[pScrn->displayWidth >> 5] == -1) {
+ i = -1;
+ do {
+ pScrn->displayWidth += 32;
+ i = partprod500TX[pScrn->displayWidth >> 5];
+ } while (i == -1);
+ }
+ }
+
+ /* Check Virtual resolution */
+ if (pScrn->virtualX > maxwidth) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "GLINTModeInit: virtual width (%d) too big for hardware\n",
+ pScrn->virtualX);
+ return FALSE;
+ }
+ if (pScrn->virtualY > maxheight) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "GLINTModeInit: virtual height (%d) too big for hardware\n",
+ pScrn->virtualY);
+ return FALSE;
+ }
+
+ switch (pGlint->Chipset)
+ { /* Now we know displaywidth, so set linepitch data */
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ pGlint->pprod = partprodPermedia[pScrn->displayWidth >> 5];
+ pGlint->bppalign = bppand[(pScrn->bitsPerPixel>>3)-1];
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ pGlint->pprod = partprod500TX[pScrn->displayWidth >> 5];
+ pGlint->bppalign = 0;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_MX:
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ pGlint->pprod = partprod500TX[pScrn->displayWidth >> 5];
+ pGlint->bppalign = 0;
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ pGlint->pprod = partprodPermedia[pScrn->displayWidth >> 5];
+ pGlint->bppalign = bppand[(pScrn->bitsPerPixel>>3)-1];
+ break;
+ }
+ break;
+ }
+
+ if ( ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA2)) &&
+ (pGlint->numMultiDevices == 2) ) {
+ int bytesPerPixel, realWidthBytes, inputXSpanBytes;
+ CARD32 postMultiply, productEnable, use16xProduct, inputXSpan;
+ CARD32 binaryEval, glintApSize;
+
+ /* setup multi glint framebuffer aperture */
+ bytesPerPixel = (pScrn->bitsPerPixel >> 3);
+ realWidthBytes = pScrn->displayWidth * bytesPerPixel;
+
+ /* compute Input X Span field */
+ binaryEval = ((realWidthBytes << 1) - 1);
+ if (binaryEval & (8 << 10)) { /* 8K */
+ inputXSpan = 3;
+ inputXSpanBytes = 8 * 1024;
+ }
+ else if (binaryEval & (4 << 10)) { /* 4K */
+ inputXSpan = 2;
+ inputXSpanBytes = 4 * 1024;
+ }
+ else if (binaryEval & (2 << 10)) { /* 2K */
+ inputXSpan = 1;
+ inputXSpanBytes = 2 * 1024;
+ }
+ else { /* 1K */
+ inputXSpan = 0;
+ inputXSpanBytes = 1024;
+ }
+
+ /* compute post multiply */
+ binaryEval = realWidthBytes >> 3;
+ postMultiply = 0;
+ while ((postMultiply < 5) && !(binaryEval & 1)) {
+ postMultiply++;
+ binaryEval >>= 1;
+ }
+ postMultiply <<= 7;
+
+ /* compute product enable fields */
+ if (binaryEval & ~0x1f) { /* too big */
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "GLINTModeInit: width (%d) too big\n",
+ pScrn->displayWidth);
+ return FALSE;
+ }
+ if ((binaryEval & 0x12) == 0x12) { /* clash between x2 and x16 */
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+ "GLINTModeInit: width (%d) is mult 18, not supported\n",
+ pScrn->displayWidth);
+ return FALSE;
+ }
+ if (binaryEval & 0x10) {
+ productEnable = (((binaryEval & 0xf) | 0x2) << 3);
+ use16xProduct = (1 << 2);
+ }
+ else {
+ productEnable = ((binaryEval & 0xf) << 3);
+ use16xProduct = 0;
+ }
+
+ /* compute GLINT Aperture Size field */
+ binaryEval = ((pScrn->videoRam << 11) - 1);
+ if (binaryEval & (32 << 20)) { /* 32M */
+ glintApSize = 3 << 10;
+ }
+ else if (binaryEval & (16 << 20)) { /* 16M */
+ glintApSize = 2 << 10;
+ }
+ else if (binaryEval & (8 << 20)) { /* 8M */
+ glintApSize = 1 << 10;
+ }
+ else { /* 4M */
+ glintApSize = 0 << 10;
+ }
+
+ pGlint->realWidth = ( glintApSize |
+ postMultiply |
+ productEnable |
+ use16xProduct |
+ inputXSpan );
+
+ /* set the MULTI width for software rendering */
+ pScrn->displayWidth = inputXSpanBytes / bytesPerPixel;
+ }
+
+ /* Set the current mode to the first in the list */
+ pScrn->currentMode = pScrn->modes;
+
+ xf86SetCrtcForModes(pScrn, INTERLACE_HALVE_V);
+
+ /* Print the list of modes being used */
+ xf86PrintModes(pScrn);
+
+ /* Set display resolution */
+ xf86SetDpi(pScrn, 0, 0);
+
+ /* Load bpp-specific modules */
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ case 16:
+ case 24:
+ mod = "fb";
+ syms = fbSymbols;
+ break;
+ case 32:
+ if (pScrn->overlayFlags & OVERLAY_8_32_PLANAR) {
+ mod = "xf8_32bpp";
+ syms = xf8_32bppSymbols;
+ } else {
+ mod = "fb";
+ syms = fbSymbols;
+ }
+ break;
+ }
+ if (mod && xf86LoadSubModule(pScrn, mod) == NULL) {
+ GLINTFreeRec(pScrn);
+ return FALSE;
+ }
+ if (mod && syms) {
+ xf86LoaderReqSymLists(syms, NULL);
+ }
+
+ /* Load XAA if needed */
+ if (!pGlint->NoAccel) {
+ if (!xf86LoadSubModule(pScrn, "xaa")) {
+ GLINTFreeRec(pScrn);
+ return FALSE;
+ }
+ xf86LoaderReqSymLists(xaaSymbols, NULL);
+ }
+
+ /* Load shadowfb if needed */
+ if (pGlint->ShadowFB) {
+ if (!xf86LoadSubModule(pScrn, "shadowfb")) {
+ GLINTFreeRec(pScrn);
+ return FALSE;
+ }
+ xf86LoaderReqSymLists(shadowSymbols, NULL);
+ }
+
+ /* Load DDC */
+ if (!xf86LoadSubModule(pScrn, "ddc")) {
+ GLINTFreeRec(pScrn);
+ return FALSE;
+ }
+ xf86LoaderReqSymLists(ddcSymbols, NULL);
+ /* Load I2C if needed */
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA3) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA4) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_R4) ||
+ (pGlint->Chipset == PCI_VENDOR_TI_CHIP_PERMEDIA2)) {
+ if (xf86LoadSubModule(pScrn, "i2c")) {
+ I2CBusPtr pBus;
+
+ xf86LoaderReqSymLists(i2cSymbols, NULL);
+ if ((pBus = xf86CreateI2CBusRec())) {
+ pBus->BusName = "DDC";
+ pBus->scrnIndex = pScrn->scrnIndex;
+ pBus->I2CUDelay = Permedia2I2CUDelay;
+ pBus->I2CPutBits = Permedia2I2CPutBits;
+ pBus->I2CGetBits = Permedia2I2CGetBits;
+ pBus->DriverPrivate.ptr = pGlint;
+ if (!xf86I2CBusInit(pBus)) {
+ xf86DestroyI2CBusRec(pBus, TRUE, TRUE);
+ } else
+ pGlint->DDCBus = pBus;
+ }
+
+ if ((pBus = xf86CreateI2CBusRec())) {
+ pBus->BusName = "Video";
+ pBus->scrnIndex = pScrn->scrnIndex;
+ pBus->I2CUDelay = Permedia2I2CUDelay;
+ pBus->I2CPutBits = Permedia2I2CPutBits;
+ pBus->I2CGetBits = Permedia2I2CGetBits;
+ pBus->DriverPrivate.ptr = pGlint;
+ if (!xf86I2CBusInit(pBus)) {
+ xf86DestroyI2CBusRec(pBus, TRUE, TRUE);
+ } else
+ pGlint->VSBus = pBus;
+ }
+ }
+ }
+
+ TRACE_EXIT("GLINTPreInit");
+ return TRUE;
+}
+
+
+/*
+ * Map the framebuffer and MMIO memory.
+ */
+
+static Bool
+GLINTMapMem(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint;
+
+ pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("GLINTMapMem");
+ if (pGlint->FBDev) {
+ pGlint->FbBase = fbdevHWMapVidmem(pScrn);
+ if (pGlint->FbBase == NULL)
+ return FALSE;
+
+ pGlint->IOBase = fbdevHWMapMMIO(pScrn);
+ if (pGlint->IOBase == NULL)
+ return FALSE;
+
+ TRACE_EXIT("GLINTMapMem");
+ return TRUE;
+ }
+
+ /*
+ * Map IO registers to virtual address space
+ * We always map VGA IO registers - even if we don't need them
+ */
+ pGlint->IOBase = xf86MapPciMem(pScrn->scrnIndex, VIDMEM_MMIO_32BIT,
+ pGlint->PciTag, pGlint->IOAddress, 0x20000);
+
+ if (pGlint->IOBase == NULL)
+ return FALSE;
+
+ if (pGlint->FbMapSize != 0) {
+ pGlint->FbBase = xf86MapPciMem(pScrn->scrnIndex, VIDMEM_FRAMEBUFFER,
+ pGlint->PciTag,
+ pGlint->FbAddress,
+ pGlint->FbMapSize);
+ if (pGlint->FbBase == NULL)
+ return FALSE;
+ }
+
+ TRACE_EXIT("GLINTMapMem");
+ return TRUE;
+}
+
+
+/*
+ * Unmap the framebuffer and MMIO memory.
+ */
+
+static Bool
+GLINTUnmapMem(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint;
+
+ pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("GLINTUnmapMem");
+ if (pGlint->FBDev) {
+ fbdevHWUnmapVidmem(pScrn);
+ pGlint->FbBase = NULL;
+ fbdevHWUnmapMMIO(pScrn);
+ pGlint->IOBase = NULL;
+
+ TRACE_EXIT("GLINTUnmapMem");
+ return TRUE;
+ }
+
+ /*
+ * Unmap IO registers to virtual address space
+ */
+ xf86UnMapVidMem(pScrn->scrnIndex, (pointer)pGlint->IOBase, 0x20000);
+ pGlint->IOBase = NULL;
+
+ if (pGlint->FbBase != NULL)
+ xf86UnMapVidMem(pScrn->scrnIndex, (pointer)pGlint->FbBase, pGlint->FbMapSize);
+ pGlint->FbBase = NULL;
+
+ TRACE_EXIT("GLINTUnmapMem");
+ return TRUE;
+}
+
+/*
+ * This function saves the video state.
+ */
+static void
+GLINTSave(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint;
+ GLINTRegPtr glintReg;
+ GLINTRegPtr glintReg2;
+ RamDacHWRecPtr pRAMDAC;
+ RamDacRegRecPtr RAMDACreg;
+
+ pGlint = GLINTPTR(pScrn);
+ pRAMDAC = RAMDACHWPTR(pScrn);
+ glintReg = &pGlint->SavedReg[0];
+ glintReg2 = &pGlint->SavedReg[1];
+ RAMDACreg = &pRAMDAC->SavedReg;
+ TRACE_ENTER("GLINTSave");
+
+ switch (pGlint->Chipset)
+ {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ Permedia2Save(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VSave(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3Save(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ PermediaSave(pScrn, glintReg);
+ (*pGlint->RamDac->Save)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ TXSave(pScrn, glintReg);
+ (*pGlint->RamDac->Save)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ case PCI_CHIP_MX:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2()
+ TXSave(pScrn, glintReg2);
+#if 0
+ (*pGlint->RamDac->Save)(pScrn, pGlint->RamDacRec, RAMDACreg2);
+#endif
+ ACCESSCHIP1();
+ }
+ TXSave(pScrn, glintReg);
+ (*pGlint->RamDac->Save)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ PermediaSave(pScrn, glintReg);
+ (*pGlint->RamDac->Save)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ Permedia3Save(pScrn, glintReg2);
+ ACCESSCHIP1();
+ }
+ Permedia3Save(pScrn, glintReg);
+ break;
+ }
+ break;
+ }
+ TRACE_EXIT("GLINTSave");
+}
+
+
+/*
+ * Initialise a new mode. This is currently still using the old
+ * "initialise struct, restore/write struct to HW" model. That could
+ * be changed.
+ */
+
+static Bool
+GLINTModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode)
+{
+ int ret = -1;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ RamDacHWRecPtr pRAMDAC = RAMDACHWPTR(pScrn);
+ RamDacRegRecPtr RAMDACreg;
+ GLINTRegPtr glintReg = &pGlint->ModeReg[0];
+ GLINTRegPtr glintReg2 = &pGlint->ModeReg[1];
+
+ pScrn->vtSema = TRUE;
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ ret = Permedia2Init(pScrn, mode);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ ret = Permedia2VInit(pScrn, mode);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ ret = Permedia3Init(pScrn, mode, glintReg);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ ret = PermediaInit(pScrn, mode);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ ret = TXInit(pScrn, mode, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_MX:
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ ret = TXInit(pScrn, mode, glintReg2);
+ ACCESSCHIP1();
+ }
+ ret = TXInit(pScrn, mode, glintReg);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ ret = PermediaInit(pScrn, mode);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ ret = Permedia3Init(pScrn, mode, glintReg2);
+ ACCESSCHIP1();
+ }
+ ret = Permedia3Init(pScrn, mode, glintReg);
+ break;
+ }
+ break;
+ }
+
+ if (!ret)
+ return FALSE;
+
+ glintReg = &pGlint->ModeReg[0];
+ glintReg2 = &pGlint->ModeReg[1];
+ RAMDACreg = &pRAMDAC->ModeReg;
+
+ pGlint->STATE = FALSE;
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ Permedia2Restore(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VRestore(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3Restore(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ PermediaRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ TXRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ case PCI_CHIP_MX:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ TXRestore(pScrn, glintReg2);
+#if 0
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec,RAMDACreg2);
+#endif
+ ACCESSCHIP1();
+ }
+ TXRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ PermediaRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ Permedia3Restore(pScrn, glintReg2);
+ ACCESSCHIP1();
+ }
+ Permedia3Restore(pScrn, glintReg);
+ break;
+ }
+ break;
+ }
+
+ if (xf86IsPc98())
+ outb(0xfac, 0x01);
+
+ return TRUE;
+}
+
+/*
+ * Restore the initial (text) mode.
+ */
+static void
+GLINTRestore(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint;
+ GLINTRegPtr glintReg;
+ GLINTRegPtr glintReg2;
+ RamDacHWRecPtr pRAMDAC;
+ RamDacRegRecPtr RAMDACreg;
+
+ pGlint = GLINTPTR(pScrn);
+ pRAMDAC = RAMDACHWPTR(pScrn);
+ glintReg = &pGlint->SavedReg[0];
+ glintReg2 = &pGlint->SavedReg[1];
+ RAMDACreg = &pRAMDAC->SavedReg;
+
+ TRACE_ENTER("GLINTRestore");
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ Permedia2VideoLeaveVT(pScrn);
+ Permedia2Restore(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VideoLeaveVT(pScrn);
+ Permedia2VRestore(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3Restore(pScrn, glintReg);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ PermediaRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ TXRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_MX:
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ TXRestore(pScrn, glintReg2);
+#if 0
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec,RAMDACreg2);
+#endif
+ ACCESSCHIP1();
+ }
+ TXRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ PermediaRestore(pScrn, glintReg);
+ (*pGlint->RamDac->Restore)(pScrn, pGlint->RamDacRec, RAMDACreg);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ if (pGlint->numMultiDevices == 2) {
+ ACCESSCHIP2();
+ Permedia3Restore(pScrn, glintReg2);
+ ACCESSCHIP1();
+ }
+ Permedia3Restore(pScrn, glintReg);
+ break;
+ }
+ break;
+ }
+
+ TRACE_EXIT("GLINTRestore");
+}
+
+
+/* Mandatory */
+
+/* This gets called at the start of each server generation */
+
+static Bool
+GLINTScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int ret, displayWidth;
+ int init_picture = 0;
+ unsigned char *FBStart;
+ VisualPtr visual;
+
+ TRACE_ENTER("GLINTScreenInit");
+ /* Map the GLINT memory and MMIO areas */
+ if (!GLINTMapMem(pScrn))
+ return FALSE;
+
+ if (pGlint->FBDev) {
+ fbdevHWSave(pScrn);
+ if (!fbdevHWModeInit(pScrn, pScrn->currentMode)) {
+ xf86DrvMsg(scrnIndex, X_ERROR,
+ "Internal error: invalid mode\n");
+ return FALSE;
+ }
+ } else
+ /* Save the current state */
+ GLINTSave(pScrn);
+
+ /* DDC */
+ {
+ xf86MonPtr pMon = NULL;
+
+ if (pGlint->DDCBus)
+ pMon = xf86DoEDID_DDC2(pScrn->scrnIndex, pGlint->DDCBus);
+
+ if (!pMon)
+ /* Try DDC1 */;
+
+ xf86SetDDCproperties(pScrn,xf86PrintEDID(pMon));
+ }
+
+ /* Initialise the first mode */
+ if ( (!pGlint->FBDev) && !(GLINTModeInit(pScrn, pScrn->currentMode))) {
+ xf86DrvMsg(scrnIndex, X_ERROR,
+ "Internal error: invalid mode\n");
+ return FALSE;
+ }
+
+ /* Darken the screen for aesthetic reasons and set the viewport */
+ GLINTSaveScreen(pScreen, SCREEN_SAVER_ON);
+ GLINTAdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0);
+
+ /*
+ * The next step is to setup the screen's visuals, and initialise the
+ * framebuffer code. In cases where the framebuffer's default
+ * choices for things like visual layouts and bits per RGB are OK,
+ * this may be as simple as calling the framebuffer's ScreenInit()
+ * function. If not, the visuals will need to be setup before calling
+ * a fb ScreenInit() function and fixed up after.
+ *
+ * For most PC hardware at depths >= 8, the defaults that cfb uses
+ * are not appropriate. In this driver, we fixup the visuals after.
+ */
+
+ /*
+ * Reset visual list.
+ */
+ miClearVisualTypes();
+
+ /* Setup the visuals we support. */
+
+ /*
+ * For bpp > 8, the default visuals are not acceptable because we only
+ * support TrueColor and not DirectColor. To deal with this, call
+ * miSetVisualTypes for each visual supported.
+ */
+
+ if((pScrn->overlayFlags & OVERLAY_8_32_PLANAR) &&
+ (pScrn->bitsPerPixel == 32)) {
+ if (!miSetVisualTypes(8, PseudoColorMask | GrayScaleMask,
+ pScrn->rgbBits, PseudoColor))
+ return FALSE;
+ if (!miSetVisualTypes(24, TrueColorMask, pScrn->rgbBits, TrueColor))
+ return FALSE;
+ } else {
+ if (!miSetVisualTypes(pScrn->depth,
+ miGetDefaultVisualMask(pScrn->depth),
+ pScrn->rgbBits, pScrn->defaultVisual))
+ return FALSE;
+ if (!miSetPixmapDepths())
+ return FALSE;
+ }
+
+#ifdef XF86DRI
+ /*
+ * Setup DRI after visuals have been established, but before fbScreenInit
+ * is called. fbScreenInit will eventually call into the drivers
+ * InitGLXVisuals call back.
+ */
+ if (!pGlint->NoAccel && pGlint->HWCursor) {
+ pGlint->directRenderingEnabled = GLINTDRIScreenInit(pScreen);
+ } else {
+ pGlint->directRenderingEnabled = FALSE;
+ }
+#endif
+
+ /*
+ * Call the framebuffer layer's ScreenInit function, and fill in other
+ * pScreen fields.
+ */
+
+ if(pGlint->ShadowFB) {
+ pGlint->ShadowPitch = BitmapBytePad(pScrn->bitsPerPixel * pScrn->virtualX);
+ pGlint->ShadowPtr = xalloc(pGlint->ShadowPitch * pScrn->virtualY);
+ displayWidth = pGlint->ShadowPitch / (pScrn->bitsPerPixel >> 3);
+ FBStart = pGlint->ShadowPtr;
+ } else {
+ pGlint->ShadowPtr = NULL;
+ displayWidth = pScrn->displayWidth;
+ FBStart = pGlint->FbBase;
+ }
+
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ case 16:
+ case 24:
+ ret = fbScreenInit(pScreen, FBStart,
+ pScrn->virtualX, pScrn->virtualY,
+ pScrn->xDpi, pScrn->yDpi,
+ displayWidth, pScrn->bitsPerPixel);
+ init_picture = 1;
+ break;
+ case 32:
+ if(pScrn->overlayFlags & OVERLAY_8_32_PLANAR)
+ ret = cfb8_32ScreenInit(pScreen, FBStart,
+ pScrn->virtualX, pScrn->virtualY,
+ pScrn->xDpi, pScrn->yDpi,
+ displayWidth);
+ else {
+ ret = fbScreenInit(pScreen, FBStart,
+ pScrn->virtualX, pScrn->virtualY,
+ pScrn->xDpi, pScrn->yDpi,
+ displayWidth, pScrn->bitsPerPixel);
+ init_picture = 1;
+ }
+ break;
+ default:
+ xf86DrvMsg(scrnIndex, X_ERROR,
+ "Internal error: invalid bpp (%d) in GLINTScrnInit\n",
+ pScrn->bitsPerPixel);
+ ret = FALSE;
+ break;
+ }
+ if (!ret)
+ return FALSE;
+
+ xf86SetBlackWhitePixels(pScreen);
+
+ pGlint->BlockHandler = pScreen->BlockHandler;
+ pScreen->BlockHandler = GLINTBlockHandler;
+
+#if !defined(__sparc__)
+ if (!pGlint->ShadowFB)
+ GLINTDGAInit(pScreen);
+#endif
+
+ if (pScrn->bitsPerPixel > 8) {
+ /* Fixup RGB ordering */
+ visual = pScreen->visuals + pScreen->numVisuals;
+ while (--visual >= pScreen->visuals) {
+ if ((visual->class | DynamicClass) == DirectColor) {
+ visual->offsetRed = pScrn->offset.red;
+ visual->offsetGreen = pScrn->offset.green;
+ visual->offsetBlue = pScrn->offset.blue;
+ visual->redMask = pScrn->mask.red;
+ visual->greenMask = pScrn->mask.green;
+ visual->blueMask = pScrn->mask.blue;
+ }
+ }
+ }
+
+ /* must be after RGB ordering fixed */
+ if (init_picture)
+ fbPictureInit(pScreen, 0, 0);
+ if (!pGlint->NoAccel) {
+ switch (pGlint->Chipset)
+ {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2AccelInit(pScreen);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3AccelInit(pScreen);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ PermediaAccelInit(pScreen);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ TXAccelInit(pScreen);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_MX:
+ TXAccelInit(pScreen);
+ break;
+ case PCI_CHIP_300SX:
+ SXAccelInit(pScreen);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ PermediaAccelInit(pScreen);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ Permedia3AccelInit(pScreen);
+ break;
+ }
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ SXAccelInit(pScreen);
+ break;
+ }
+ }
+
+ miInitializeBackingStore(pScreen);
+ xf86SetBackingStore(pScreen);
+ xf86SetSilkenMouse(pScreen);
+
+ miDCInitialize(pScreen, xf86GetPointerScreenFuncs());
+
+ /* Initialise cursor functions */
+ if (pGlint->HWCursor) {
+ /* Handle VGA chipsets first */
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2) ||
+ (pGlint->Chipset == PCI_VENDOR_TI_CHIP_PERMEDIA2))
+ Permedia2HWCursorInit(pScreen);
+ else
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA3) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA4) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_R4) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA2) &&
+ (pGlint->MultiChip == PCI_CHIP_R4)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_PERMEDIA3)) )
+ Permedia2vHWCursorInit(pScreen);
+ else
+ /* If we get here pGlint->Ramdac should have been set */
+ if ( ((pGlint->RamDac->RamDacType == (IBM526DB_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (IBM526_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (IBM640_RAMDAC))) )
+ glintIBMHWCursorInit(pScreen);
+ else
+ if ( (pGlint->RamDac->RamDacType == (TI3030_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (TI3026_RAMDAC)) )
+ glintTIHWCursorInit(pScreen);
+ }
+
+ /* Initialise default colourmap */
+ if (!miCreateDefColormap(pScreen))
+ return FALSE;
+
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA3) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA4) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_R4) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA2) &&
+ (pGlint->MultiChip == PCI_CHIP_R4)) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_PERMEDIA3)) ) {
+ if (!xf86HandleColormaps(pScreen, 256, pScrn->rgbBits,
+ (pGlint->FBDev) ? fbdevHWLoadPalette :
+ ((pScrn->depth == 16) ? Permedia3LoadPalette16:Permedia3LoadPalette),
+ NULL,
+ CMAP_RELOAD_ON_MODE_SWITCH |
+ ((pScrn->overlayFlags & OVERLAY_8_32_PLANAR)
+ ? 0 : CMAP_PALETTED_TRUECOLOR)))
+ return FALSE;
+ } else
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V) ||
+ (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2) ||
+ (pGlint->Chipset == PCI_VENDOR_TI_CHIP_PERMEDIA2)) {
+ if (!xf86HandleColormaps(pScreen, 256, pScrn->rgbBits,
+ (pGlint->FBDev) ? fbdevHWLoadPalette :
+ ((pScrn->depth == 16) ? Permedia2LoadPalette16:Permedia2LoadPalette),
+ NULL,
+ CMAP_RELOAD_ON_MODE_SWITCH |
+ ((pScrn->overlayFlags & OVERLAY_8_32_PLANAR)
+ ? 0 : CMAP_PALETTED_TRUECOLOR)))
+ return FALSE;
+ } else {
+ if (pScrn->rgbBits == 10) {
+ if (!RamDacHandleColormaps(pScreen, 1024, pScrn->rgbBits,
+ CMAP_RELOAD_ON_MODE_SWITCH | CMAP_PALETTED_TRUECOLOR))
+ return FALSE;
+ } else {
+ if (!RamDacHandleColormaps(pScreen, 256, pScrn->rgbBits,
+ CMAP_RELOAD_ON_MODE_SWITCH |
+ ((pScrn->overlayFlags & OVERLAY_8_32_PLANAR)
+ ? 0 : CMAP_PALETTED_TRUECOLOR)))
+ return FALSE;
+ }
+ }
+
+ if((pScrn->overlayFlags & OVERLAY_8_32_PLANAR) &&
+ (pScrn->bitsPerPixel == 32)) {
+ if(!xf86Overlay8Plus32Init(pScreen))
+ return FALSE;
+ }
+
+ if(pGlint->ShadowFB)
+ ShadowFBInit(pScreen, GLINTRefreshArea);
+
+ xf86DPMSInit(pScreen, (DPMSSetProcPtr)GLINTDisplayPowerManagementSet, 0);
+
+#ifdef XF86DRI
+ if (pGlint->directRenderingEnabled) {
+ /* Now that mi, cfb, drm and others have done their thing,
+ * complete the DRI setup.
+ */
+ pGlint->directRenderingEnabled = GLINTDRIFinishScreenInit(pScreen);
+ }
+ if (pGlint->directRenderingEnabled) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "direct rendering enabled\n");
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "direct rendering disabled\n");
+ }
+#endif
+
+ pScrn->memPhysBase = pGlint->FbAddress;
+ pScrn->fbOffset = 0;
+
+ pGlint->CloseScreen = pScreen->CloseScreen;
+ pScreen->CloseScreen = GLINTCloseScreen;
+ pScreen->SaveScreen = GLINTSaveScreen;
+
+ /* Report any unused options (only for the first generation) */
+ if (serverGeneration == 1) {
+ xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options);
+ }
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VideoInit(pScreen);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3InitVideo(pScreen);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ Permedia3InitVideo(pScreen);
+ }
+ }
+
+#if 0
+ /* Enable the screen */
+ GLINTSaveScreen(pScreen, SCREEN_SAVER_OFF);
+#endif
+
+ /* Done */
+ TRACE_EXIT("GLINTScreenInit");
+ return TRUE;
+}
+
+/* Usually mandatory */
+Bool
+GLINTSwitchMode(int scrnIndex, DisplayModePtr mode, int flags)
+{
+ ScrnInfoPtr pScrn;
+ GLINTPtr pGlint;
+
+ pScrn = xf86Screens[scrnIndex];
+ pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("GLINTSwitchMode");
+
+ if (pGlint->FBDev) {
+ Bool ret = fbdevHWSwitchMode(scrnIndex, mode, flags);
+
+ if (!pGlint->NoAccel) {
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2InitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3InitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ PermediaInitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ TXInitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ SXInitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_MX:
+ TXInitializeEngine(pScrn);
+ break;
+ case PCI_CHIP_300SX:
+ SXInitializeEngine(pScrn);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ PermediaInitializeEngine(pScrn);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ Permedia3InitializeEngine(pScrn);
+ break;
+ }
+ break;
+ }
+ }
+
+ TRACE_EXIT("GLINTSwitchMode (fbdev ?)");
+ return ret;
+ }
+
+ TRACE_EXIT("GLINTSwitchMode (normal)");
+ return GLINTModeInit(xf86Screens[scrnIndex], mode);
+}
+
+
+/*
+ * This function is used to initialize the Start Address - the first
+ * displayed location in the video memory.
+ */
+/* Usually mandatory */
+void
+GLINTAdjustFrame(int scrnIndex, int x, int y, int flags)
+{
+ ScrnInfoPtr pScrn;
+ CARD32 base;
+ GLINTPtr pGlint;
+
+ pScrn = xf86Screens[scrnIndex];
+ pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("GLINTAdjustFrame");
+
+ if (pGlint->FBDev) {
+ fbdevHWAdjustFrame(scrnIndex, x, y, flags);
+ TRACE_EXIT("GLINTAdjustFrame (fbdev)");
+ return;
+ }
+
+ base = ((y * pScrn->displayWidth + x) >> 1) >> pGlint->BppShift;
+ if (pScrn->bitsPerPixel == 24) base *= 3;
+
+ switch (pGlint->Chipset)
+ {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ GLINT_SLOW_WRITE_REG(base, PMScreenBase);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ base = (y * pScrn->displayWidth + x) >> pGlint->BppShift;
+ GLINT_SLOW_WRITE_REG(base, PMScreenBase);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ base = (y * pScrn->displayWidth + x) >> pGlint->BppShift;
+ GLINT_SLOW_WRITE_REG(base, PMScreenBase);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ GLINT_SLOW_WRITE_REG(base, PMScreenBase);
+ break;
+ }
+ break;
+ }
+ TRACE_EXIT("GLINTAdjustFrame (normal)");
+}
+
+
+/*
+ * This is called when VT switching back to the X server. Its job is
+ * to reinitialise the video mode.
+ *
+ * We may wish to unmap video/MMIO memory too.
+ */
+
+/* Mandatory */
+static Bool
+GLINTEnterVT(int scrnIndex, int flags)
+{
+ ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("GLINTEnterVT");
+
+ if (pGlint->FBDev)
+ fbdevHWEnterVT(scrnIndex, flags);
+ else
+ /* Should we re-save the text mode on each VT enter? */
+ if (!GLINTModeInit(pScrn, pScrn->currentMode))
+ return FALSE;
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VideoEnterVT(pScrn);
+ break;
+ }
+
+ if (!pGlint->NoAccel) {
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2InitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ Permedia3InitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ PermediaInitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ TXInitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ SXInitializeEngine(pScrn);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_MX:
+ TXInitializeEngine(pScrn);
+ break;
+ case PCI_CHIP_300SX:
+ SXInitializeEngine(pScrn);
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ PermediaInitializeEngine(pScrn);
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ Permedia3InitializeEngine(pScrn);
+ break;
+ }
+ break;
+ }
+ }
+
+ TRACE_EXIT("GLINTEnterVTFBDev");
+ return TRUE;
+}
+
+
+/*
+ * This is called when VT switching away from the X server. Its job is
+ * to restore the previous (text) mode.
+ *
+ * We may wish to remap video/MMIO memory too.
+ */
+
+/* Mandatory */
+static void
+GLINTLeaveVT(int scrnIndex, int flags)
+{
+ ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("GLINTLeaveVT");
+ pGlint->STATE = TRUE;
+ GLINTRestore(pScrn);
+
+ if (xf86IsPc98())
+ outb(0xfac, 0x00);
+
+ TRACE_EXIT("GLINTLeaveVT");
+}
+
+
+/*
+ * This is called at the end of each server generation. It restores the
+ * original (text) mode. It should really also unmap the video memory too.
+ */
+
+/* Mandatory */
+static Bool
+GLINTCloseScreen(int scrnIndex, ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("GLINTCloseScreen");
+#ifdef XF86DRI
+ if (pGlint->directRenderingEnabled) {
+ GLINTDRICloseScreen(pScreen);
+ }
+#endif
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ Permedia2VideoUninit(pScrn);
+ break;
+ }
+
+ if (pScrn->vtSema) {
+ if(pGlint->CursorInfoRec)
+ pGlint->CursorInfoRec->HideCursor(pScrn);
+ if (pGlint->FBDev)
+ fbdevHWRestore(pScrn);
+ else {
+ pGlint->STATE = TRUE;
+ GLINTRestore(pScrn);
+ }
+ GLINTUnmapMem(pScrn);
+ }
+ if(pGlint->AccelInfoRec)
+ XAADestroyInfoRec(pGlint->AccelInfoRec);
+ if(pGlint->CursorInfoRec)
+ xf86DestroyCursorInfoRec(pGlint->CursorInfoRec);
+ if (pGlint->ShadowPtr)
+ xfree(pGlint->ShadowPtr);
+ if (pGlint->DGAModes)
+ xfree(pGlint->DGAModes);
+ if (pGlint->ScratchBuffer)
+ xfree(pGlint->ScratchBuffer);
+ pScrn->vtSema = FALSE;
+
+ if (xf86IsPc98())
+ outb(0xfac, 0x00);
+
+ if(pGlint->BlockHandler)
+ pScreen->BlockHandler = pGlint->BlockHandler;
+
+ pScreen->CloseScreen = pGlint->CloseScreen;
+ TRACE_EXIT("GLINTCloseScreen");
+ return (*pScreen->CloseScreen)(scrnIndex, pScreen);
+}
+
+
+/* Free up any per-generation data structures */
+
+/* Optional */
+static void
+GLINTFreeScreen(int scrnIndex, int flags)
+{
+#if DEBUG
+ ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
+#endif
+ TRACE_ENTER("GLINTFreeScreen");
+ if (xf86LoaderCheckSymbol("fbdevHWFreeRec"))
+ fbdevHWFreeRec(xf86Screens[scrnIndex]);
+ if (xf86LoaderCheckSymbol("RamDacFreeRec"))
+ RamDacFreeRec(xf86Screens[scrnIndex]);
+ GLINTFreeRec(xf86Screens[scrnIndex]);
+ TRACE_EXIT("GLINTFreeScreen");
+}
+
+
+/* Checks if a mode is suitable for the selected chipset. */
+
+/* Optional */
+static int
+GLINTValidMode(int scrnIndex, DisplayModePtr mode, Bool verbose, int flags)
+{
+ ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (mode->Flags & V_INTERLACE)
+ return(MODE_NO_INTERLACE);
+
+ if (pScrn->bitsPerPixel == 24) {
+ /* A restriction on the PM2 where a black strip on the left hand
+ * side appears if not aligned properly */
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ if (mode->HDisplay % 8) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "HDisplay %d not divisible by 8, fixing...\n", mode->HDisplay);
+ mode->HDisplay -= (mode->HDisplay % 8);
+ mode->CrtcHDisplay = mode->CrtcHBlankStart = mode->HDisplay;
+ }
+
+ if (mode->HSyncStart % 8) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "HSyncStart %d not divisible by 8, fixing...\n", mode->HSyncStart);
+ mode->HSyncStart -= (mode->HSyncStart % 8);
+ mode->CrtcHSyncStart = mode->HSyncStart;
+ }
+
+ if (mode->HSyncEnd % 8) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "HSyncEnd %d not divisible by 8, fixing...\n", mode->HSyncEnd);
+ mode->HSyncEnd -= (mode->HSyncEnd % 8);
+ mode->CrtcHSyncEnd = mode->HSyncEnd;
+ }
+
+ if (mode->HTotal % 8) {
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "HTotal %d not divisible by 8, fixing...\n", mode->HTotal);
+ mode->HTotal -= (mode->HTotal % 8);
+ mode->CrtcHBlankEnd = mode->CrtcHTotal = mode->HTotal;
+ }
+ break;
+ }
+ }
+
+ return(MODE_OK);
+}
+
+/* Do screen blanking */
+
+/* Mandatory */
+static Bool
+GLINTSaveScreen(ScreenPtr pScreen, int mode)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 temp;
+ Bool unblank;
+
+ TRACE_ENTER("GLINTSaveScreen");
+
+ unblank = xf86IsUnblank(mode);
+
+ if (unblank)
+ SetTimeSinceLastInputEvent();
+
+ if ((pScrn != NULL ) && pScrn->vtSema) {
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ temp = GLINT_READ_REG(PMVideoControl);
+ if (unblank) temp |= 1;
+ else temp &= 0xFFFFFFFE;
+ GLINT_SLOW_WRITE_REG(temp, PMVideoControl);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ temp = GLINT_READ_REG(PMVideoControl);
+ if (unblank) temp |= 1;
+ else temp &= 0xFFFFFFFE;
+ GLINT_SLOW_WRITE_REG(temp, PMVideoControl);
+ break;
+ }
+ break;
+ }
+ }
+
+ TRACE_EXIT("GLINTSaveScreen");
+ return TRUE;
+}
+
+static void
+GLINTBlockHandler (
+ int i,
+ pointer blockData,
+ pointer pTimeout,
+ pointer pReadmask
+){
+ ScreenPtr pScreen = screenInfo.screens[i];
+ ScrnInfoPtr pScrn = xf86Screens[i];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int sigstate = xf86BlockSIGIO();
+
+ if(pGlint->CursorColorCallback)
+ (*pGlint->CursorColorCallback)(pScrn);
+
+ if(pGlint->LoadCursorCallback)
+ (*pGlint->LoadCursorCallback)(pScrn);
+
+ xf86UnblockSIGIO(sigstate);
+
+ pScreen->BlockHandler = pGlint->BlockHandler;
+ (*pScreen->BlockHandler) (i, blockData, pTimeout, pReadmask);
+ pScreen->BlockHandler = GLINTBlockHandler;
+
+ if(pGlint->VideoTimerCallback) {
+ UpdateCurrentTime();
+ (*pGlint->VideoTimerCallback)(pScrn, currentTime.milliseconds);
+ }
+}
+
+#ifdef DEBUG
+void
+GLINT_VERB_WRITE_REG(GLINTPtr pGlint, CARD32 v, int r, char *file, int line)
+{
+ if (xf86GetVerbosity() > 2)
+ ErrorF("[0x%04x] <- 0x%08x (%s, %d)\n", r, v, file, line);
+ *(volatile CARD32 *)((char *) pGlint->IOBase + pGlint->IOOffset + r) = v;
+}
+
+CARD32
+GLINT_VERB_READ_REG(GLINTPtr pGlint, CARD32 r, char *file, int line)
+{
+ CARD32 v =
+ *(volatile CARD32 *)((char *) pGlint->IOBase + pGlint->IOOffset + r);
+
+ if (xf86GetVerbosity() > 2)
+ ErrorF("[0x%04x] -> 0x%08x (%s, %d)\n", r, v, file, line);
+ return v;
+}
+#endif
+
+void GLINT_MoveBYTE(
+ register CARD32* dest,
+ register unsigned char* src,
+ register int dwords)
+{
+#ifdef __alpha__
+ write_mem_barrier();
+#endif
+ while(dwords) {
+ *dest = *src;
+ src += 1;
+ dest += 1;
+ dwords -= 1;
+ }
+}
+
+void GLINT_MoveWORDS(
+ register CARD32* dest,
+ register unsigned short* src,
+ register int dwords)
+{
+#ifdef __alpha__
+ write_mem_barrier();
+#endif
+ while(dwords & ~0x01) {
+ *dest = *src;
+ *(dest + 1) = *(src + 1);
+ src += 2;
+ dest += 2;
+ dwords -= 2;
+ }
+ if (dwords)
+ *dest = *src;
+}
+
+void GLINT_MoveDWORDS(
+ register CARD32* dest,
+ register CARD32* src,
+ register int dwords)
+{
+#ifdef __alpha__
+ write_mem_barrier();
+#endif
+ if ((unsigned long)src & 0x3UL) {
+ unsigned char *pchar;
+ while (dwords & ~0x03) {
+ pchar = (unsigned char *)(src + 0);
+ *(dest + 0) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ pchar = (unsigned char *)(src + 1);
+ *(dest + 1) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ pchar = (unsigned char *)(src + 2);
+ *(dest + 2) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ pchar = (unsigned char *)(src + 3);
+ *(dest + 3) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ src += 4;
+ dest += 4;
+ dwords -= 4;
+ }
+ if (!dwords)
+ return;
+ pchar = (unsigned char *)(src + 0);
+ *(dest + 0) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ if (dwords == 1)
+ return;
+ pchar = (unsigned char *)(src + 1);
+ *(dest + 1) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ if (dwords == 2)
+ return;
+ pchar = (unsigned char *)(src + 2);
+ *(dest + 2) = (((CARD32)pchar[0] << 24) |
+ ((CARD32)pchar[1] << 16) |
+ ((CARD32)pchar[2] << 8) |
+ ((CARD32)pchar[3] << 0));
+ } else {
+ while (dwords & ~0x03) {
+ *dest = *src;
+ *(dest + 1) = *(src + 1);
+ *(dest + 2) = *(src + 2);
+ *(dest + 3) = *(src + 3);
+ src += 4;
+ dest += 4;
+ dwords -= 4;
+ }
+ if (!dwords)
+ return;
+ *dest = *src;
+ if (dwords == 1)
+ return;
+ *(dest + 1) = *(src + 1);
+ if (dwords == 2)
+ return;
+ *(dest + 2) = *(src + 2);
+ }
+}
+
+int
+Shiftbpp(ScrnInfoPtr pScrn, int value)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int logbytesperaccess = 2; /* default */
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA:
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ logbytesperaccess = 2;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ logbytesperaccess = 4;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_300SX:
+ case PCI_VENDOR_3DLABS_CHIP_500TX:
+ case PCI_VENDOR_3DLABS_CHIP_MX:
+ if ( (pGlint->RamDac->RamDacType == (IBM640_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (TI3030_RAMDAC)) )
+ logbytesperaccess = 4;
+ else
+ logbytesperaccess = 3;
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA2:
+ case PCI_VENDOR_3DLABS_CHIP_DELTA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_500TX:
+ case PCI_CHIP_300SX:
+ case PCI_CHIP_MX:
+ if ( (pGlint->RamDac->RamDacType == (IBM640_RAMDAC)) ||
+ (pGlint->RamDac->RamDacType == (TI3030_RAMDAC)) )
+ logbytesperaccess = 4;
+ else
+ logbytesperaccess = 3;
+ break;
+ case PCI_CHIP_PERMEDIA:
+ case PCI_CHIP_TI_PERMEDIA:
+ logbytesperaccess = 2;
+ break;
+ case PCI_CHIP_R4:
+ case PCI_CHIP_PERMEDIA3:
+ logbytesperaccess = 4;
+ break;
+ }
+ }
+
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ value >>= logbytesperaccess;
+ pGlint->BppShift = logbytesperaccess;
+ break;
+ case 16:
+ if (pGlint->DoubleBuffer) {
+ value >>= (logbytesperaccess-2);
+ pGlint->BppShift = logbytesperaccess-2;
+ } else {
+ value >>= (logbytesperaccess-1);
+ pGlint->BppShift = logbytesperaccess-1;
+ }
+ break;
+ case 24:
+ value *= 3;
+ value >>= logbytesperaccess;
+ pGlint->BppShift = logbytesperaccess;
+ break;
+ case 32:
+ value >>= (logbytesperaccess-2);
+ pGlint->BppShift = logbytesperaccess-2;
+ break;
+ }
+ return (value);
+}
diff --git a/src/glint_regs.h b/src/glint_regs.h
new file mode 100644
index 0000000..122832d
--- /dev/null
+++ b/src/glint_regs.h
@@ -0,0 +1,1361 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_regs.h,v 1.36 2003/01/12 03:55:47 tsi Exp $ */
+
+/*
+ * glint register file
+ *
+ * Copyright by Stefan Dirsch, Dirk Hohndel, Alan Hourihane
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Simon P., <sim@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ *
+ */
+
+#ifndef _GLINTREG_H_
+#define _GLINTREG_H_
+
+#include "compiler.h"
+
+/* The chips we know */
+#define PCI_CHIP_3DLABS_300SX 0x01
+#define PCI_CHIP_3DLABS_500TX 0x02
+#define PCI_CHIP_3DLABS_DELTA 0x03
+#define PCI_CHIP_3DLABS_PERMEDIA 0x04
+#define PCI_CHIP_3DLABS_MX 0x06
+#define PCI_CHIP_3DLABS_PERMEDIA2 0x07
+#define PCI_CHIP_3DLABS_GAMMA 0x08
+#define PCI_CHIP_3DLABS_PERMEDIA2V 0x09
+#define PCI_CHIP_3DLABS_PERMEDIA3 0x0A
+#define PCI_CHIP_3DLABS_PERMEDIA4 0x0C
+#define PCI_CHIP_3DLABS_R4 0x0D
+#define PCI_CHIP_3DLABS_GAMMA2 0x0E
+
+/* The boards we know */
+#define IS_GLORIAXXL ((pGlint->PciInfo->subsysVendor == 0x1048) && \
+ (pGlint->PciInfo->subsysCard == 0x0a42))
+
+#define IS_GLORIASYNERGY ((pGlint->PciInfo->subsysVendor == 0x1048) && \
+ (pGlint->PciInfo->subsysCard == 0x0a32))
+
+#define IS_GMX2000 ((pGlint->PciInfo->subsysVendor == 0x3d3d) && \
+ (pGlint->PciInfo->subsysCard == 0x0106))
+
+#define IS_J2000 ((pGlint->PciInfo->subsysVendor == 0x1097) && \
+ (pGlint->PciInfo->subsysCard == 0x3d32))
+
+#define IS_JPRO ((pGlint->PciInfo->subsysVendor == 0x1097) && \
+ (pGlint->PciInfo->subsysCard == 0x3db3))
+
+/* COMPAQ OEM VX1 PCI
+ * subsys == 0x0121 if VGA is enabled
+ * subsys == 0x000a if VGA has never been enabled
+ */
+#define IS_PCI_QVX1 (pGlint->PciInfo->subsysVendor == 0x3d3d && \
+ ((pGlint->PciInfo->subsysCard == 0x0121) || \
+ (pGlint->PciInfo->subsysCard == 0x000a)))
+
+/* COMPAQ OEM VX1 AGP
+ * subsys == 0x0144 if VGA is enabled
+ * subsys == 0x000c if VGA has never been enabled
+ */
+#define IS_AGP_QVX1 (pGlint->PciInfo->subsysVendor == 0x3d3d && \
+ ((pGlint->PciInfo->subsysCard == 0x0144) || \
+ (pGlint->PciInfo->subsysCard == 0x000c)))
+
+#define IS_QVX1 (IS_PCI_QVX1 || IS_AGP_QVX1)
+
+#define IS_ELSA_SYNERGY ((pGlint->PciInfo->subsysVendor == 0x1048) && \
+ (pGlint->PciInfo->subsysCard == 0x0a32))
+
+/* COMPAQ OEM Permedia 2V with VGA disable jumper - 0x13e9 ? */
+#define IS_QPM2V ((pGlint->PciInfo->subsysVendor == 0x13e9) && \
+ ((pGlint->PciInfo->subsysCard == 0x0100) || \
+ (pGlint->PciInfo->subsysCard == 0x0002)))
+
+/**********************************************
+* GLINT 500TX Configuration Region Registers *
+***********************************************/
+
+/* Device Identification */
+#define CFGVendorId 0x0000
+#define PCI_VENDOR_3DLABS 0x3D3D
+#define PCI_VENDOR_TI 0x104C
+#define CFGDeviceId 0x0002
+
+#define CFGRevisionId 0x08
+#define CFGClassCode 0x09
+#define CFGHeaderType 0x0E
+
+/* Device Control/Status */
+#define CFGCommand 0x04
+#define CFGStatus 0x06
+
+/* Miscellaneous Functions */
+#define CFGBist 0x0f
+#define CFGLatTimer 0x0d
+#define CFGCacheLine 0x0c
+#define CFGMaxLat 0x3f
+#define CFGMinGrant 0x3e
+#define CFGIntPin 0x3d
+#define CFGIntLine 0x3c
+
+/* Base Adresses */
+#define CFGBaseAddr0 0x10
+#define CFGBaseAddr1 0x14
+#define CFGBaseAddr2 0x18
+#define CFGBaseAddr3 0x1C
+#define CFGBaseAddr4 0x20
+#define CFGRomAddr 0x30
+
+
+
+/**********************************
+ * GLINT 500TX Region 0 Registers *
+ **********************************/
+
+/* Control Status Registers */
+#define ResetStatus 0x0000
+#define IntEnable 0x0008
+#define IntFlags 0x0010
+#define InFIFOSpace 0x0018
+#define OutFIFOWords 0x0020
+#define DMAAddress 0x0028
+#define DMACount 0x0030
+#define ErrorFlags 0x0038
+#define VClkCtl 0x0040
+#define TestRegister 0x0048
+#define Aperture0 0x0050
+#define Aperture1 0x0058
+#define DMAControl 0x0060
+#define FIFODis 0x0068
+
+/* GLINT PerMedia Region 0 additional Registers */
+#define ChipConfig 0x0070
+#define SCLK_SEL_MASK (3 << 10)
+#define SCLK_SEL_MCLK_HALF (3 << 10)
+#define ByDMAControl 0x00D8
+
+/* GLINT 500TX LocalBuffer Registers */
+#define LBMemoryCtl 0x1000
+#define LBNumBanksMask 0x00000001
+#define LBNumBanks1 (0)
+#define LBNumBanks2 (1)
+#define LBPageSizeMask 0x00000006
+#define LBPageSize256 (0<<1)
+#define LBPageSize512 (1<<1)
+#define LBPageSize1024 (2<<1)
+#define LBPageSize2048 (3<<1)
+#define LBRASCASLowMask 0x00000018
+#define LBRASCASLow2 (0<<3)
+#define LBRASCASLow3 (1<<3)
+#define LBRASCASLow4 (2<<3)
+#define LBRASCASLow5 (3<<3)
+#define LBRASPrechargeMask 0x00000060
+#define LBRASPrecharge2 (0<<5)
+#define LBRASPrecharge3 (1<<5)
+#define LBRASPrecharge4 (2<<5)
+#define LBRASPrecharge5 (3<<5)
+#define LBCASLowMask 0x00000180
+#define LBCASLow1 (0<<7)
+#define LBCASLow2 (1<<7)
+#define LBCASLow3 (2<<7)
+#define LBCASLow4 (3<<7)
+#define LBPageModeMask 0x00000200
+#define LBPageModeEnabled (0<<9)
+#define LBPageModeDisabled (1<<9)
+#define LBRefreshCountMask 0x0003fc00
+#define LBRefreshCountShift 10
+
+#define LBMemoryEDO 0x1008
+#define LBEDOMask 0x00000001
+#define LBEDODisabled (0)
+#define LBEDOEnabled (1)
+#define LBEDOBankSizeMask 0x0000000e
+#define LBEDOBankSizeDiabled (0<<1)
+#define LBEDOBankSize256K (1<<1)
+#define LBEDOBankSize512K (2<<1)
+#define LBEDOBankSize1M (3<<1)
+#define LBEDOBankSize2M (4<<1)
+#define LBEDOBankSize4M (5<<1)
+#define LBEDOBankSize8M (6<<1)
+#define LBEDOBankSize16M (7<<1)
+#define LBTwoPageDetectorMask 0x00000010
+#define LBSinglePageDetector (0<<4)
+#define LBTwoPageDetector (1<<4)
+
+/* GLINT PerMedia Memory Control Registers */
+#define PMReboot 0x1000
+#define PMRomControl 0x1040
+#define PMBootAddress 0x1080
+#define PMMemConfig 0x10C0
+# define RowCharge8 1 << 10
+# define TimeRCD8 1 << 7
+# define TimeRC8 0x6 << 3
+# define TimeRP8 1
+# define CAS3Latency8 0 << 16
+# define BootAdress8 0x10
+# define NumberBanks8 0x3 << 29
+# define RefreshCount8 0x41 << 21
+# define TimeRASMin8 1 << 13
+# define DeadCycle8 1 << 17
+# define BankDelay8 0 << 18
+# define Burst1Cycle8 1 << 31
+# define SDRAM8 0 << 4
+
+# define RowCharge6 1 << 10
+# define TimeRCD6 1 << 7
+# define TimeRC6 0x6 << 3
+# define TimeRP6 0x2
+# define CAS3Latency6 1 << 16
+# define BootAdress6 0x60
+# define NumberBanks6 0x2 << 29
+# define RefreshCount6 0x41 << 21
+# define TimeRASMin6 1 << 13
+# define DeadCycle6 1 << 17
+# define BankDelay6 0 << 18
+# define Burst1Cycle6 1 << 31
+# define SDRAM6 0 << 4
+
+# define RowCharge4 0 << 10
+# define TimeRCD4 0 << 7
+# define TimeRC4 0x4 << 3
+# define TimeRP4 1
+# define CAS3Latency4 0 << 16
+# define BootAdress4 0x10
+# define NumberBanks4 1 << 29
+# define RefreshCount4 0x30 << 21
+# define TimeRASMin4 1 << 13
+# define DeadCycle4 0 << 17
+# define BankDelay4 0 << 18
+# define Burst1Cycle4 1 << 31
+# define SDRAM4 0 << 4
+
+/* Permedia 2 Control */
+#define MemControl 0x1040
+
+#define PMBypassWriteMask 0x1100
+#define PMFramebufferWriteMask 0x1140
+#define PMCount 0x1180
+
+/* Framebuffer Registers */
+#define FBMemoryCtl 0x1800
+#define FBModeSel 0x1808
+#define FBGCWrMask 0x1810
+#define FBGCColorLower 0x1818
+#define FBTXMemCtl 0x1820
+#define FBWrMaskk 0x1830
+#define FBGCColorUpper 0x1838
+
+/* Core FIFO */
+#define OutputFIFO 0x2000
+
+/* 500TX Internal Video Registers */
+#define VTGHLimit 0x3000
+#define VTGHSyncStart 0x3008
+#define VTGHSyncEnd 0x3010
+#define VTGHBlankEnd 0x3018
+#define VTGVLimit 0x3020
+#define VTGVSyncStart 0x3028
+#define VTGVSyncEnd 0x3030
+#define VTGVBlankEnd 0x3038
+#define VTGHGateStart 0x3040
+#define VTGHGateEnd 0x3048
+#define VTGVGateStart 0x3050
+#define VTGVGateEnd 0x3058
+#define VTGPolarity 0x3060
+#define VTGFrameRowAddr 0x3068
+#define VTGVLineNumber 0x3070
+#define VTGSerialClk 0x3078
+#define VTGModeCtl 0x3080
+
+/* Permedia Video Control Registers */
+#define PMScreenBase 0x3000
+#define PMScreenStride 0x3008
+#define PMHTotal 0x3010
+#define PMHgEnd 0x3018
+#define PMHbEnd 0x3020
+#define PMHsStart 0x3028
+#define PMHsEnd 0x3030
+#define PMVTotal 0x3038
+#define PMVbEnd 0x3040
+#define PMVsStart 0x3048
+#define PMVsEnd 0x3050
+#define PMVideoControl 0x3058
+#define PMInterruptLine 0x3060
+#define PMDDCData 0x3068
+#define DataIn (1<<0)
+#define ClkIn (1<<1)
+#define DataOut (1<<2)
+#define ClkOut (1<<3)
+#define PMLineCount 0x3070
+#define PMFifoControl 0x3078
+
+/* Permedia 2 RAMDAC Registers */
+#define PM2DACWriteAddress 0x4000
+#define PM2DACIndexReg 0x4000
+#define PM2DACData 0x4008
+#define PM2DACReadMask 0x4010
+#define PM2DACReadAddress 0x4018
+#define PM2DACCursorColorAddress 0x4020
+#define PM2DACCursorColorData 0x4028
+#define PM2DACIndexData 0x4050
+#define PM2DACCursorData 0x4058
+#define PM2DACCursorXLsb 0x4060
+#define PM2DACCursorXMsb 0x4068
+#define PM2DACCursorYLsb 0x4070
+#define PM2DACCursorYMsb 0x4078
+#define PM2DACCursorControl 0x06
+#define PM2DACIndexCMR 0x18
+#define PM2DAC_TRUECOLOR 0x80
+#define PM2DAC_RGB 0x20
+#define PM2DAC_GRAPHICS 0x10
+#define PM2DAC_PACKED 0x09
+#define PM2DAC_8888 0x08
+#define PM2DAC_565 0x06
+#define PM2DAC_4444 0x05
+#define PM2DAC_5551 0x04
+#define PM2DAC_2321 0x03
+#define PM2DAC_2320 0x02
+#define PM2DAC_332 0x01
+#define PM2DAC_CI8 0x00
+#define PM2DACIndexMDCR 0x19
+#define PM2DACIndexPalettePage 0x1c
+#define PM2DACIndexMCR 0x1e
+#define PM2DACIndexClockAM 0x20
+#define PM2DACIndexClockAN 0x21
+#define PM2DACIndexClockAP 0x22
+#define PM2DACIndexClockBM 0x23
+#define PM2DACIndexClockBN 0x24
+#define PM2DACIndexClockBP 0x25
+#define PM2DACIndexClockCM 0x26
+#define PM2DACIndexClockCN 0x27
+#define PM2DACIndexClockCP 0x28
+#define PM2DACIndexClockStatus 0x29
+#define PM2DACIndexMemClockM 0x30
+#define PM2DACIndexMemClockN 0x31
+#define PM2DACIndexMemClockP 0x32
+#define PM2DACIndexMemClockStatus 0x33
+#define PM2DACIndexColorKeyControl 0x40
+#define PM2DACIndexColorKeyOverlay 0x41
+#define PM2DACIndexColorKeyRed 0x42
+#define PM2DACIndexColorKeyGreen 0x43
+#define PM2DACIndexColorKeyBlue 0x44
+
+/* Permedia 2V extensions */
+#define PM2VDACRDMiscControl 0x000
+#define PM2VDACRDSyncControl 0x001
+#define PM2VDACRDDACControl 0x002
+#define PM2VDACRDPixelSize 0x003
+#define PM2VDACRDColorFormat 0x004
+#define PM2VDACRDCursorMode 0x005
+#define PM2VDACRDCursorXLow 0x007
+#define PM2VDACRDCursorXHigh 0x008
+#define PM2VDACRDCursorYLow 0x009
+#define PM2VDACRDCursorYHigh 0x00A
+#define PM2VDACRDCursorHotSpotX 0x00B
+#define PM2VDACRDCursorHotSpotY 0x00C
+#define PM2VDACRDOverlayKey 0x00D
+#define PM2VDACRDPan 0x00E
+#define PM2VDACRDSense 0x00F
+#define PM2VDACRDCheckControl 0x018
+#define PM2VDACIndexClockControl 0x200
+#define PM2VDACRDDClk0PreScale 0x201
+#define PM2VDACRDDClk0FeedbackScale 0x202
+#define PM2VDACRDDClk0PostScale 0x203
+#define PM2VDACRDDClk1PreScale 0x204
+#define PM2VDACRDDClk1FeedbackScale 0x205
+#define PM2VDACRDDClk1PostScale 0x206
+#define PM2VDACRDMClkControl 0x20D
+#define PM2VDACRDMClkPreScale 0x20E
+#define PM2VDACRDMClkFeedbackScale 0x20F
+#define PM2VDACRDMClkPostScale 0x210
+#define PM2VDACRDCursorPalette 0x303
+#define PM2VDACRDCursorPattern 0x400
+#define PM2VDACIndexRegLow 0x4020
+#define PM2VDACIndexRegHigh 0x4028
+#define PM2VDACIndexData 0x4030
+#define PM2VDACRDIndexControl 0x4038
+
+/* Permedia 2 Video Streams Unit Registers */
+#define VSBIntFlag (1<<8)
+#define VSAIntFlag (1<<9)
+
+#define VSConfiguration 0x5800
+#define VS_UnitMode_ROM 0
+#define VS_UnitMode_AB8 3
+#define VS_UnitMode_Mask 7
+#define VS_GPBusMode_A (1<<3)
+#define VS_HRefPolarityA (1<<9)
+#define VS_VRefPolarityA (1<<10)
+#define VS_VActivePolarityA (1<<11)
+#define VS_UseFieldA (1<<12)
+#define VS_FieldPolarityA (1<<13)
+#define VS_FieldEdgeA (1<<14)
+#define VS_VActiveVBIA (1<<15)
+#define VS_InterlaceA (1<<16)
+#define VS_ReverseDataA (1<<17)
+#define VS_HRefPolarityB (1<<18)
+#define VS_VRefPolarityB (1<<19)
+#define VS_VActivePolarityB (1<<20)
+#define VS_UseFieldB (1<<21)
+#define VS_FieldPolarityB (1<<22)
+#define VS_FieldEdgeB (1<<23)
+#define VS_VActiveVBIB (1<<24)
+#define VS_InterlaceB (1<<25)
+#define VS_ColorSpaceB_RGB (1<<26)
+#define VS_ReverseDataB (1<<27)
+#define VS_DoubleEdgeB (1<<28)
+
+#define VSStatus 0x5808
+#define VS_FieldOne0A (1<<9)
+#define VS_FieldOne1A (1<<10)
+#define VS_FieldOne2A (1<<11)
+#define VS_InvalidInterlaceA (1<<12)
+#define VS_FieldOne0B (1<<17)
+#define VS_FieldOne1B (1<<18)
+#define VS_FieldOne2B (1<<19)
+#define VS_InvalidInterlaceB (1<<20)
+
+#define VSSerialBusControl 0x5810
+
+#define VSABase 0x5900
+#define VSA_Video (1<<0)
+#define VSA_VBI (1<<1)
+#define VSA_BufferCtl (1<<2)
+#define VSA_MirrorX (1<<7)
+#define VSA_MirrorY (1<<8)
+#define VSA_Discard_None (0<<9)
+#define VSA_Discard_FieldOne (1<<9)
+#define VSA_Discard_FieldTwo (2<<9)
+#define VSA_CombineFields (1<<11)
+#define VSA_LockToStreamB (1<<12)
+#define VSBBase 0x5A00
+#define VSB_Video (1<<0)
+#define VSB_VBI (1<<1)
+#define VSB_BufferCtl (1<<2)
+#define VSB_CombineFields (1<<3)
+#define VSB_RGBOrder (1<<11)
+#define VSB_GammaCorrect (1<<12)
+#define VSB_LockToStreamA (1<<13)
+
+#define VSControl 0x0000
+#define VSInterrupt 0x0008
+#define VSCurrentLine 0x0010
+#define VSVideoAddressHost 0x0018
+#define VSVideoAddressIndex 0x0020
+#define VSVideoAddress0 0x0028
+#define VSVideoAddress1 0x0030
+#define VSVideoAddress2 0x0038
+#define VSVideoStride 0x0040
+#define VSVideoStartLine 0x0048
+#define VSVideoEndLine 0x0050
+#define VSVideoStartData 0x0058
+#define VSVideoEndData 0x0060
+#define VSVBIAddressHost 0x0068
+#define VSVBIAddressIndex 0x0070
+#define VSVBIAddress0 0x0078
+#define VSVBIAddress1 0x0080
+#define VSVBIAddress2 0x0088
+#define VSVBIStride 0x0090
+#define VSVBIStartLine 0x0098
+#define VSVBIEndLine 0x00A0
+#define VSVBIStartData 0x00A8
+#define VSVBIEndData 0x00B0
+#define VSFifoControl 0x00B8
+
+/**********************************
+ * GLINT Delta Region 0 Registers *
+ **********************************/
+
+/* Control Status Registers */
+#define DResetStatus 0x0800
+#define DIntEnable 0x0808
+#define DIntFlags 0x0810
+#define DErrorFlags 0x0838
+#define DTestRegister 0x0848
+#define DFIFODis 0x0868
+
+
+
+/**********************************
+ * GLINT Gamma Region 0 Registers *
+ **********************************/
+
+/* Control Status Registers */
+#define GInFIFOSpace 0x0018
+#define GDMAAddress 0x0028
+#define GDMACount 0x0030
+#define GDMAControl 0x0060
+#define GOutDMA 0x0080
+#define GOutDMACount 0x0088
+#define GResetStatus 0x0800
+#define GIntEnable 0x0808
+#define GIntFlags 0x0810
+#define GErrorFlags 0x0838
+#define GTestRegister 0x0848
+#define GFIFODis 0x0868
+
+#define GChipConfig 0x0870
+#define GChipAGPCapable 1 << 0
+#define GChipAGPSideband 1 << 1
+#define GChipMultiGLINTApMask 3 << 19
+#define GChipMultiGLINTAp_0M 0 << 19
+#define GChipMultiGLINTAp_16M 1 << 19
+#define GChipMultiGLINTAp_32M 2 << 19
+#define GChipMultiGLINTAp_64M 3 << 19
+
+#define GCSRAperture 0x0878
+#define GCSRSecondaryGLINTMapEn 1 << 0
+#define GCSRBitSwap 1 << 1
+
+#define GPageTableAddr 0x0c00
+#define GPageTableLength 0x0c08
+#define GDelayTimer 0x0c38
+#define GCommandMode 0x0c40
+#define GCommandIntEnable 0x0c48
+#define GCommandIntFlags 0x0c50
+#define GCommandErrorFlags 0x0c58
+#define GCommandStatus 0x0c60
+#define GCommandFaultingAddr 0x0c68
+#define GVertexFaultingAddr 0x0c70
+#define GWriteFaultingAddr 0x0c88
+#define GFeedbackSelectCount 0x0c98
+#define GGammaProcessorMode 0x0cb8
+#define GVGAShadow 0x0d00
+#define GMultGLINTAperture 0x0d08
+#define GMultGLINT1 0x0d10
+#define GMultGLINT2 0x0d18
+
+/************************
+ * GLINT Core Registers *
+ ************************/
+
+#define GLINT_TAG(major,offset) (((major) << 7) | ((offset) << 3))
+#define GLINT_TAG_ADDR(major,offset) (0x8000 | GLINT_TAG((major),(offset)))
+
+#define UNIT_DISABLE 0
+#define UNIT_ENABLE 1
+
+#define StartXDom GLINT_TAG_ADDR(0x00,0x00)
+#define dXDom GLINT_TAG_ADDR(0x00,0x01)
+#define StartXSub GLINT_TAG_ADDR(0x00,0x02)
+#define dXSub GLINT_TAG_ADDR(0x00,0x03)
+#define StartY GLINT_TAG_ADDR(0x00,0x04)
+#define dY GLINT_TAG_ADDR(0x00,0x05)
+#define GLINTCount GLINT_TAG_ADDR(0x00,0x06)
+#define Render GLINT_TAG_ADDR(0x00,0x07)
+# define AreaStippleEnable 0x00001
+# define LineStippleEnable 0x00002
+# define ResetLineStipple 0x00004
+# define FastFillEnable 0x00008
+# define PrimitiveLine 0
+# define PrimitiveTrapezoid 0x00040
+# define PrimitivePoint 0x00080
+# define PrimitiveRectangle 0x000C0
+# define AntialiasEnable 0x00100
+# define AntialiasingQuality 0x00200
+# define UsePointTable 0x00400
+# define SyncOnBitMask 0x00800
+# define SyncOnHostData 0x01000
+# define TextureEnable 0x02000
+# define FogEnable 0x04000
+# define CoverageEnable 0x08000
+# define SubPixelCorrectionEnable 0x10000
+# define SpanOperation 0x40000
+# define XPositive 1<<21
+# define YPositive 1<<22
+
+
+#define ContinueNewLine GLINT_TAG_ADDR(0x00,0x08)
+#define ContinueNewDom GLINT_TAG_ADDR(0x00,0x09)
+#define ContinueNewSub GLINT_TAG_ADDR(0x00,0x0a)
+#define Continue GLINT_TAG_ADDR(0x00,0x0b)
+#define FlushSpan GLINT_TAG_ADDR(0x00,0x0c)
+#define BitMaskPattern GLINT_TAG_ADDR(0x00,0x0d)
+
+#define PointTable0 GLINT_TAG_ADDR(0x01,0x00)
+#define PointTable1 GLINT_TAG_ADDR(0x01,0x01)
+#define PointTable2 GLINT_TAG_ADDR(0x01,0x02)
+#define PointTable3 GLINT_TAG_ADDR(0x01,0x03)
+#define RasterizerMode GLINT_TAG_ADDR(0x01,0x04)
+#define RMMultiGLINT 1<<17
+#define BitMaskPackingEachScanline 1<<9
+#define ForceBackgroundColor 1<<6
+#define InvertBitMask 1<<1
+#define YLimits GLINT_TAG_ADDR(0x01,0x05)
+#define ScanLineOwnership GLINT_TAG_ADDR(0x01,0x06)
+#define WaitForCompletion GLINT_TAG_ADDR(0x01,0x07)
+#define PixelSize GLINT_TAG_ADDR(0x01,0x08)
+#define XLimits GLINT_TAG_ADDR(0x01,0x09) /* PM only */
+
+#define RectangleOrigin GLINT_TAG_ADDR(0x01,0x0A) /* PM2 only */
+#define RectangleSize GLINT_TAG_ADDR(0x01,0x0B) /* PM2 only */
+
+#define PackedDataLimits GLINT_TAG_ADDR(0x02,0x0a) /* PM only */
+
+#define ScissorMode GLINT_TAG_ADDR(0x03,0x00)
+# define SCI_USER 0x01
+# define SCI_SCREEN 0x02
+# define SCI_USERANDSCREEN 0x03
+
+#define ScissorMinXY GLINT_TAG_ADDR(0x03,0x01)
+#define ScissorMaxXY GLINT_TAG_ADDR(0x03,0x02)
+#define ScreenSize GLINT_TAG_ADDR(0x03,0x03)
+#define AreaStippleMode GLINT_TAG_ADDR(0x03,0x04)
+ /* 0: */
+ /* NoMirrorY */
+ /* NoMirrorX */
+ /* NoInvertPattern */
+ /* YAddress_1bit */
+ /* XAddress_1bit */
+ /* UNIT_DISABLE */
+
+# define ASM_XAddress_2bit 1 << 1
+# define ASM_XAddress_3bit 2 << 1
+# define ASM_XAddress_4bit 3 << 1
+# define ASM_XAddress_5bit 4 << 1
+# define ASM_YAddress_2bit 1 << 4
+# define ASM_YAddress_3bit 2 << 4
+# define ASM_YAddress_4bit 3 << 4
+# define ASM_YAddress_5bit 4 << 4
+# define ASM_InvertPattern 1 << 17
+# define ASM_MirrorX 1 << 18
+# define ASM_MirrorY 1 << 19
+
+#define LineStippleMode GLINT_TAG_ADDR(0x03,0x05)
+#define LoadLineStippleCounters GLINT_TAG_ADDR(0x03,0x06)
+#define UpdateLineStippleCounters GLINT_TAG_ADDR(0x03,0x07)
+#define SaveLineStippleState GLINT_TAG_ADDR(0x03,0x08)
+#define WindowOrigin GLINT_TAG_ADDR(0x03,0x09)
+
+#define AreaStipplePattern0 GLINT_TAG_ADDR(0x04,0x00)
+#define AreaStipplePattern1 GLINT_TAG_ADDR(0x04,0x01)
+#define AreaStipplePattern2 GLINT_TAG_ADDR(0x04,0x02)
+#define AreaStipplePattern3 GLINT_TAG_ADDR(0x04,0x03)
+#define AreaStipplePattern4 GLINT_TAG_ADDR(0x04,0x04)
+#define AreaStipplePattern5 GLINT_TAG_ADDR(0x04,0x05)
+#define AreaStipplePattern6 GLINT_TAG_ADDR(0x04,0x06)
+#define AreaStipplePattern7 GLINT_TAG_ADDR(0x04,0x07)
+
+#define TextureAddressMode GLINT_TAG_ADDR(0x07,0x00)
+#define SStart GLINT_TAG_ADDR(0x07,0x01)
+#define dSdx GLINT_TAG_ADDR(0x07,0x02)
+#define dSdyDom GLINT_TAG_ADDR(0x07,0x03)
+#define TStart GLINT_TAG_ADDR(0x07,0x04)
+#define dTdx GLINT_TAG_ADDR(0x07,0x05)
+#define dTdyDom GLINT_TAG_ADDR(0x07,0x06)
+#define QStart GLINT_TAG_ADDR(0x07,0x07)
+#define dQdx GLINT_TAG_ADDR(0x07,0x08)
+#define dQdyDom GLINT_TAG_ADDR(0x07,0x09)
+#define LOD GLINT_TAG_ADDR(0x07,0x0A)
+#define dSdy GLINT_TAG_ADDR(0x07,0x0B)
+#define dTdy GLINT_TAG_ADDR(0x07,0x0C)
+#define dQdy GLINT_TAG_ADDR(0x07,0x0D)
+
+#define TextureReadMode GLINT_TAG_ADDR(0x09,0x00)
+#define TextureFormat GLINT_TAG_ADDR(0x09,0x01)
+# define Texture_4_Components 3 << 3
+# define Texture_Texel 0
+
+#define TextureCacheControl GLINT_TAG_ADDR(0x09,0x02)
+# define TextureCacheControlEnable 2
+# define TextureCacheControlInvalidate 1
+
+#define GLINTBorderColor GLINT_TAG_ADDR(0x09,0x05)
+
+#define TexelLUTIndex GLINT_TAG_ADDR(0x09,0x08)
+#define TexelLUTData GLINT_TAG_ADDR(0x09,0x09)
+#define TexelLUTAddress GLINT_TAG_ADDR(0x09,0x0A)
+#define TexelLUTTransfer GLINT_TAG_ADDR(0x09,0x0B)
+#define TextureFilterMode GLINT_TAG_ADDR(0x09,0x0C)
+#define TextureChromaUpper GLINT_TAG_ADDR(0x09,0x0D)
+#define TextureChromaLower GLINT_TAG_ADDR(0x09,0x0E)
+
+#define TxBaseAddr0 GLINT_TAG_ADDR(0x0A,0x00)
+#define TxBaseAddr1 GLINT_TAG_ADDR(0x0A,0x01)
+#define TxBaseAddr2 GLINT_TAG_ADDR(0x0A,0x02)
+#define TxBaseAddr3 GLINT_TAG_ADDR(0x0A,0x03)
+#define TxBaseAddr4 GLINT_TAG_ADDR(0x0A,0x04)
+#define TxBaseAddr5 GLINT_TAG_ADDR(0x0A,0x05)
+#define TxBaseAddr6 GLINT_TAG_ADDR(0x0A,0x06)
+#define TxBaseAddr7 GLINT_TAG_ADDR(0x0A,0x07)
+#define TxBaseAddr8 GLINT_TAG_ADDR(0x0A,0x08)
+#define TxBaseAddr9 GLINT_TAG_ADDR(0x0A,0x09)
+#define TxBaseAddr10 GLINT_TAG_ADDR(0x0A,0x0A)
+#define TxBaseAddr11 GLINT_TAG_ADDR(0x0A,0x0B)
+
+#define PMTextureBaseAddress GLINT_TAG_ADDR(0x0b,0x00)
+#define PMTextureMapFormat GLINT_TAG_ADDR(0x0b,0x01)
+#define PMTextureDataFormat GLINT_TAG_ADDR(0x0b,0x02)
+
+#define Texel0 GLINT_TAG_ADDR(0x0c,0x00)
+#define Texel1 GLINT_TAG_ADDR(0x0c,0x01)
+#define Texel2 GLINT_TAG_ADDR(0x0c,0x02)
+#define Texel3 GLINT_TAG_ADDR(0x0c,0x03)
+#define Texel4 GLINT_TAG_ADDR(0x0c,0x04)
+#define Texel5 GLINT_TAG_ADDR(0x0c,0x05)
+#define Texel6 GLINT_TAG_ADDR(0x0c,0x06)
+#define Texel7 GLINT_TAG_ADDR(0x0c,0x07)
+#define Interp0 GLINT_TAG_ADDR(0x0c,0x08)
+#define Interp1 GLINT_TAG_ADDR(0x0c,0x09)
+#define Interp2 GLINT_TAG_ADDR(0x0c,0x0a)
+#define Interp3 GLINT_TAG_ADDR(0x0c,0x0b)
+#define Interp4 GLINT_TAG_ADDR(0x0c,0x0c)
+#define TextureFilter GLINT_TAG_ADDR(0x0c,0x0d)
+#define PMTextureReadMode GLINT_TAG_ADDR(0x0c,0x0e)
+#define TexelLUTMode GLINT_TAG_ADDR(0x0c,0x0f)
+
+#define TextureColorMode GLINT_TAG_ADDR(0x0d,0x00)
+# define TextureTypeOpenGL 0
+# define TextureTypeApple 1 << 4
+# define TextureKsDDA 1 << 5 /* only Apple-Mode */
+# define TextureKdDDA 1 << 6 /* only Apple-Mode */
+
+#define TextureEnvColor GLINT_TAG_ADDR(0x0d,0x01)
+#define FogMode GLINT_TAG_ADDR(0x0d,0x02)
+ /* 0: */
+ /* FOG RGBA */
+ /* UNIT_DISABLE */
+
+# define FOG_CI 0x0002
+
+#define FogColor GLINT_TAG_ADDR(0x0d,0x03)
+#define FStart GLINT_TAG_ADDR(0x0d,0x04)
+#define dFdx GLINT_TAG_ADDR(0x0d,0x05)
+#define dFdyDom GLINT_TAG_ADDR(0x0d,0x06)
+#define KsStart GLINT_TAG_ADDR(0x0d,0x09)
+#define dKsdx GLINT_TAG_ADDR(0x0d,0x0a)
+#define dKsdyDom GLINT_TAG_ADDR(0x0d,0x0b)
+#define KdStart GLINT_TAG_ADDR(0x0d,0x0c)
+#define dKdStart GLINT_TAG_ADDR(0x0d,0x0d)
+#define dKddyDom GLINT_TAG_ADDR(0x0d,0x0e)
+
+#define RStart GLINT_TAG_ADDR(0x0f,0x00)
+#define dRdx GLINT_TAG_ADDR(0x0f,0x01)
+#define dRdyDom GLINT_TAG_ADDR(0x0f,0x02)
+#define GStart GLINT_TAG_ADDR(0x0f,0x03)
+#define dGdx GLINT_TAG_ADDR(0x0f,0x04)
+#define dGdyDom GLINT_TAG_ADDR(0x0f,0x05)
+#define BStart GLINT_TAG_ADDR(0x0f,0x06)
+#define dBdx GLINT_TAG_ADDR(0x0f,0x07)
+#define dBdyDom GLINT_TAG_ADDR(0x0f,0x08)
+#define AStart GLINT_TAG_ADDR(0x0f,0x09)
+#define dAdx GLINT_TAG_ADDR(0x0f,0x0a)
+#define dAdyDom GLINT_TAG_ADDR(0x0f,0x0b)
+#define ColorDDAMode GLINT_TAG_ADDR(0x0f,0x0c)
+ /* 0: */
+# define CDDA_FlatShading 0
+ /* UNIT_DISABLE */
+# define CDDA_GouraudShading 0x0002
+
+
+#define ConstantColor GLINT_TAG_ADDR(0x0f,0x0d)
+#define GLINTColor GLINT_TAG_ADDR(0x0f,0x0e)
+#define AlphaTestMode GLINT_TAG_ADDR(0x10,0x00)
+#define AntialiasMode GLINT_TAG_ADDR(0x10,0x01)
+#define AlphaBlendMode GLINT_TAG_ADDR(0x10,0x02)
+ /* 0: */
+ /* SrcZERO */
+ /* DstZERO */
+ /* ColorFormat8888 */
+ /* AlphaBuffer present */
+ /* ColorOrderBGR */
+ /* TypeOpenGL */
+ /* DstFBData */
+ /* UNIT_DISABLE */
+
+# define ABM_SrcONE 1 << 1
+# define ABM_SrcDST_COLOR 2 << 1
+# define ABM_SrcONE_MINUS_DST_COLOR 3 << 1
+# define ABM_SrcSRC_ALPHA 4 << 1
+# define ABM_SrcONE_MINUS_SRC_ALPHA 5 << 1
+# define ABM_SrcDST_ALPHA 6 << 1
+# define ABM_SrcONE_MINUS_DST_ALPHA 7 << 1
+# define ABM_SrcSRC_ALPHA_SATURATE 8 << 1
+# define ABM_DstONE 1 << 5
+# define ABM_DstSRC_COLOR 2 << 5
+# define ABM_DstONE_MINUS_SRC_COLOR 3 << 5
+# define ABM_DstSRC_ALPHA 4 << 5
+# define ABM_DstONE_MINUS_SRC_ALPHA 5 << 5
+# define ABM_DstDST_ALPHA 6 << 5
+# define ABM_DstONE_MINUS_DST_ALPHA 7 << 5
+# define ABM_ColorFormat5555 1 << 8
+# define ABM_ColorFormat4444 2 << 8
+# define ABM_ColorFormat4444_Front 3 << 8
+# define ABM_ColorFormat4444_Back 4 << 8
+# define ABM_ColorFormat332_Front 5 << 8
+# define ABM_ColorFormat332_Back 6 << 8
+# define ABM_ColorFormat121_Front 7 << 8
+# define ABM_ColorFormat121_Back 8 << 8
+# define ABM_ColorFormat555_Back 13 << 8
+# define ABM_ColorFormat_CI8 14 << 8
+# define ABM_ColorFormat_CI4 15 << 8
+# define ABM_NoAlphaBuffer 0x1000
+# define ABM_ColorOrderRGB 0x2000
+# define ABM_TypeQuickDraw3D 0x4000
+# define ABM_DstFBSourceData 0x8000
+
+#define DitherMode GLINT_TAG_ADDR(0x10,0x03)
+ /* 0: */
+ /* ColorOrder BGR */
+ /* AlphaDitherDefault */
+ /* ColorFormat8888 */
+ /* TruncateMode */
+ /* DitherDisable */
+ /* UNIT_DISABLE */
+
+# define DTM_DitherEnable 1 << 1
+# define DTM_ColorFormat5555 1 << 2
+# define DTM_ColorFormat4444 2 << 2
+# define DTM_ColorFormat4444_Front 3 << 2
+# define DTM_ColorFormat4444_Back 4 << 2
+# define DTM_ColorFormat332_Front 5 << 2
+# define DTM_ColorFormat332_Back 6 << 2
+# define DTM_ColorFormat121_Front 7 << 2
+# define DTM_ColorFormat121_Back 8 << 2
+# define DTM_ColorFormat555_Back 13 << 2
+# define DTM_ColorFormat_CI8 14 << 2
+# define DTM_ColorFormat_CI4 15 << 2
+# define DTM_ColorOrderRGB 1 << 10
+# define DTM_NoAlphaDither 1 << 14
+# define DTM_RoundMode 1 << 15
+
+#define FBSoftwareWriteMask GLINT_TAG_ADDR(0x10,0x04)
+#define LogicalOpMode GLINT_TAG_ADDR(0x10,0x05)
+# define Use_ConstantFBWriteData 0x40
+
+
+#define FBWriteData GLINT_TAG_ADDR(0x10,0x06)
+#define RouterMode GLINT_TAG_ADDR(0x10,0x08)
+# define ROUTER_Depth_Texture 1
+# define ROUTER_Texture_Depth 0
+
+
+#define LBReadMode GLINT_TAG_ADDR(0x11,0x00)
+ /* 0: */
+ /* SrcNoRead */
+ /* DstNoRead */
+ /* DataLBDefault */
+ /* WinTopLeft */
+ /* NoPatch */
+ /* ScanlineInterval1 */
+
+# define LBRM_SrcEnable 1 << 9
+# define LBRM_DstEnable 1 << 10
+# define LBRM_DataLBStencil 1 << 16
+# define LBRM_DataLBDepth 2 << 16
+# define LBRM_WinBottomLeft 1 << 18
+# define LBRM_DoPatch 1 << 19
+
+# define LBRM_ScanlineInt2 1 << 20
+# define LBRM_ScanlineInt4 2 << 20
+# define LBRM_ScanlineInt8 3 << 20
+
+
+#define LBReadFormat GLINT_TAG_ADDR(0x11,0x01)
+# define LBRF_DepthWidth15 0x03 /* only permedia */
+# define LBRF_DepthWidth16 0x00
+# define LBRF_DepthWidth24 0x01
+# define LBRF_DepthWidth32 0x02
+
+# define LBRF_StencilWidth0 (0 << 2)
+# define LBRF_StencilWidth4 (1 << 2)
+# define LBRF_StencilWidth8 (2 << 2)
+
+# define LBRF_StencilPos16 (0 << 4)
+# define LBRF_StencilPos20 (1 << 4)
+# define LBRF_StencilPos24 (2 << 4)
+# define LBRF_StencilPos28 (3 << 4)
+# define LBRF_StencilPos32 (4 << 4)
+
+# define LBRF_FrameCount0 (0 << 7)
+# define LBRF_FrameCount4 (1 << 7)
+# define LBRF_FrameCount8 (2 << 7)
+
+# define LBRF_FrameCountPos16 (0 << 9)
+# define LBRF_FrameCountPos20 (1 << 9)
+# define LBRF_FrameCountPos24 (2 << 9)
+# define LBRF_FrameCountPos28 (3 << 9)
+# define LBRF_FrameCountPos32 (4 << 9)
+# define LBRF_FrameCountPos36 (5 << 9)
+# define LBRF_FrameCountPos40 (6 << 9)
+
+# define LBRF_GIDWidth0 (0 << 12)
+# define LBRF_GIDWidth4 (1 << 12)
+
+# define LBRF_GIDPos16 (0 << 13)
+# define LBRF_GIDPos20 (1 << 13)
+# define LBRF_GIDPos24 (2 << 13)
+# define LBRF_GIDPos28 (3 << 13)
+# define LBRF_GIDPos32 (4 << 13)
+# define LBRF_GIDPos36 (5 << 13)
+# define LBRF_GIDPos40 (6 << 13)
+# define LBRF_GIDPos44 (7 << 13)
+# define LBRF_GIDPos48 (8 << 13)
+
+# define LBRF_Compact32 (1 << 17)
+
+
+
+#define LBSourceOffset GLINT_TAG_ADDR(0x11,0x02)
+#define LBStencil GLINT_TAG_ADDR(0x11,0x05)
+#define LBDepth GLINT_TAG_ADDR(0x11,0x06)
+#define LBWindowBase GLINT_TAG_ADDR(0x11,0x07)
+#define LBWriteMode GLINT_TAG_ADDR(0x11,0x08)
+# define LBWM_WriteEnable 0x1
+# define LBWM_UpLoad_LBDepth 0x2
+# define LBWM_UpLoad_LBStencil 0x4
+
+#define LBWriteFormat GLINT_TAG_ADDR(0x11,0x09)
+
+
+#define TextureData GLINT_TAG_ADDR(0x11,0x0d)
+#define TextureDownloadOffset GLINT_TAG_ADDR(0x11,0x0e)
+#define LBWindowOffset GLINT_TAG_ADDR(0x11,0x0f)
+
+#define GLINTWindow GLINT_TAG_ADDR(0x13,0x00)
+# define GWIN_UnitEnable (1 << 0)
+# define GWIN_ForceLBUpdate (1 << 3)
+# define GWIN_LBUpdateSourceREG (1 << 4)
+# define GWIN_LBUpdateSourceLB (0 << 4)
+# define GWIN_StencilFCP (1 << 17)
+# define GWIN_DepthFCP (1 << 18)
+# define GWIN_OverrideWriteFilter (1 << 19)
+
+ /* ??? is this needed, set by permedia (2) modules */
+# define GWIN_DisableLBUpdate 0x40000
+
+#define StencilMode GLINT_TAG_ADDR(0x13,0x01)
+#define StencilData GLINT_TAG_ADDR(0x13,0x02)
+#define GLINTStencil GLINT_TAG_ADDR(0x13,0x03)
+#define DepthMode GLINT_TAG_ADDR(0x13,0x04)
+ /* 0: */
+ /* WriteDisable */
+ /* SrcCompFragment */
+ /* CompFuncNEVER */
+ /* UNIT_DISABLE */
+
+# define DPM_WriteEnable 1 << 1
+# define DPM_SrcCompLBData 1 << 2
+# define DPM_SrcCompDregister 2 << 2
+# define DPM_SrcCompLBSourceData 3 << 2
+# define DPM_CompFuncLESS 1 << 4
+# define DPM_CompFuncEQUAL 2 << 4
+# define DPM_CompFuncLESS_OR_EQ 3 << 4
+# define DPM_CompFuncGREATER 4 << 4
+# define DPM_CompFuncNOT_EQ 5 << 4
+# define DPM_CompFuncGREATER_OR_EQ 6 << 4
+# define DPM_CompFuncALWAYS 7 << 4
+
+#define GLINTDepth GLINT_TAG_ADDR(0x13,0x05)
+#define ZStartU GLINT_TAG_ADDR(0x13,0x06)
+#define ZStartL GLINT_TAG_ADDR(0x13,0x07)
+#define dZdxU GLINT_TAG_ADDR(0x13,0x08)
+#define dZdxL GLINT_TAG_ADDR(0x13,0x09)
+#define dZdyDomU GLINT_TAG_ADDR(0x13,0x0a)
+#define dZdyDomL GLINT_TAG_ADDR(0x13,0x0b)
+#define FastClearDepth GLINT_TAG_ADDR(0x13,0x0c)
+
+#define FBReadMode GLINT_TAG_ADDR(0x15,0x00)
+ /* 0: */
+ /* SrcNoRead */
+ /* DstNoRead */
+ /* DataFBDefault */
+ /* WinTopLeft */
+ /* ScanlineInterval1 */
+
+# define FBRM_SrcEnable 1 << 9
+# define FBRM_DstEnable 1 << 10
+# define FBRM_DataFBColor 1 << 15
+# define FBRM_WinBottomLeft 1 << 16
+# define FBRM_Packed 1 << 19
+# define FBRM_ScanlineInt2 1 << 23
+# define FBRM_ScanlineInt4 2 << 23
+# define FBRM_ScanlineInt8 3 << 23
+
+
+#define FBSourceOffset GLINT_TAG_ADDR(0x15,0x01)
+#define FBPixelOffset GLINT_TAG_ADDR(0x15,0x02)
+#define FBColor GLINT_TAG_ADDR(0x15,0x03)
+#define FBData GLINT_TAG_ADDR(0x15,0x04)
+#define FBSourceData GLINT_TAG_ADDR(0x15,0x05)
+
+#define FBWindowBase GLINT_TAG_ADDR(0x15,0x06)
+#define FBWriteMode GLINT_TAG_ADDR(0x15,0x07)
+ /* 0: */
+ /* FBWM_NoColorUpload */
+ /* FBWM_WriteDisable */
+# define FBWM_WriteEnable 1
+# define FBWM_UploadColor 1 << 3
+/* Permedia3 extensions */
+# define FBWM_Enable0 1 << 12
+
+#define FBHardwareWriteMask GLINT_TAG_ADDR(0x15,0x08)
+#define FBBlockColor GLINT_TAG_ADDR(0x15,0x09)
+#define FBReadPixel GLINT_TAG_ADDR(0x15,0x0a) /* PM */
+#define PatternRamMode GLINT_TAG_ADDR(0x15,0x0f)
+
+#define PatternRamData0 GLINT_TAG_ADDR(0x16,0x00)
+#define PatternRamData1 GLINT_TAG_ADDR(0x16,0x01)
+#define PatternRamData2 GLINT_TAG_ADDR(0x16,0x02)
+#define PatternRamData3 GLINT_TAG_ADDR(0x16,0x03)
+#define PatternRamData4 GLINT_TAG_ADDR(0x16,0x04)
+#define PatternRamData5 GLINT_TAG_ADDR(0x16,0x05)
+#define PatternRamData6 GLINT_TAG_ADDR(0x16,0x06)
+#define PatternRamData7 GLINT_TAG_ADDR(0x16,0x07)
+
+#define FilterMode GLINT_TAG_ADDR(0x18,0x00)
+ /* 0: */
+ /* CullDepthTags */
+ /* CullDepthData */
+ /* CullStencilTags */
+ /* CullStencilData */
+ /* CullColorTag */
+ /* CullColorData */
+ /* CullSyncTag */
+ /* CullSyncData */
+ /* CullStatisticTag */
+ /* CullStatisticData */
+
+# define FM_PassDepthTags 0x0010
+# define FM_PassDepthData 0x0020
+# define FM_PassStencilTags 0x0040
+# define FM_PassStencilData 0x0080
+# define FM_PassColorTag 0x0100
+# define FM_PassColorData 0x0200
+# define FM_PassSyncTag 0x0400
+# define FM_PassSyncData 0x0800
+# define FM_PassStatisticTag 0x1000
+# define FM_PassStatisticData 0x2000
+
+#define Sync_tag 0x0188
+
+#define StatisticMode GLINT_TAG_ADDR(0x18,0x01)
+#define MinRegion GLINT_TAG_ADDR(0x18,0x02)
+#define MaxRegion GLINT_TAG_ADDR(0x18,0x03)
+#define ResetPickResult GLINT_TAG_ADDR(0x18,0x04)
+#define MitHitRegion GLINT_TAG_ADDR(0x18,0x05)
+#define MaxHitRegion GLINT_TAG_ADDR(0x18,0x06)
+#define PickResult GLINT_TAG_ADDR(0x18,0x07)
+#define GlintSync GLINT_TAG_ADDR(0x18,0x08)
+
+#define FBBlockColorU GLINT_TAG_ADDR(0x18,0x0d)
+#define FBBlockColorL GLINT_TAG_ADDR(0x18,0x0e)
+#define SuspendUntilFrameBlank GLINT_TAG_ADDR(0x18,0x0f)
+
+#define KsRStart GLINT_TAG_ADDR(0x19,0x00)
+#define dKsRdx GLINT_TAG_ADDR(0x19,0x01)
+#define dKsRdyDom GLINT_TAG_ADDR(0x19,0x02)
+#define KsGStart GLINT_TAG_ADDR(0x19,0x03)
+#define dKsGdx GLINT_TAG_ADDR(0x19,0x04)
+#define dKsGdyDom GLINT_TAG_ADDR(0x19,0x05)
+#define KsBStart GLINT_TAG_ADDR(0x19,0x06)
+#define dKsBdx GLINT_TAG_ADDR(0x19,0x07)
+#define dKsBdyDom GLINT_TAG_ADDR(0x19,0x08)
+
+#define KdRStart GLINT_TAG_ADDR(0x1A,0x00)
+#define dKdRdx GLINT_TAG_ADDR(0x1A,0x01)
+#define dKdRdyDom GLINT_TAG_ADDR(0x1A,0x02)
+#define KdGStart GLINT_TAG_ADDR(0x1A,0x03)
+#define dKdGdx GLINT_TAG_ADDR(0x1A,0x04)
+#define dKdGdyDom GLINT_TAG_ADDR(0x1A,0x05)
+#define KdBStart GLINT_TAG_ADDR(0x1A,0x06)
+#define dKdBdx GLINT_TAG_ADDR(0x1A,0x07)
+#define dKdBdyDom GLINT_TAG_ADDR(0x1A,0x08)
+
+#define FBSourceBase GLINT_TAG_ADDR(0x1B,0x00)
+#define FBSourceDelta GLINT_TAG_ADDR(0x1B,0x01)
+#define Config GLINT_TAG_ADDR(0x1B,0x02)
+#define CFBRM_SrcEnable 1<<0
+#define CFBRM_DstEnable 1<<1
+#define CFBRM_Packed 1<<2
+#define CWM_Enable 1<<3
+#define CCDDA_Enable 1<<4
+#define CLogOp_Enable 1<<5
+#define ContextDump GLINT_TAG_ADDR(0x1B,0x08)
+#define ContextRestore GLINT_TAG_ADDR(0x1B,0x09)
+#define ContextData GLINT_TAG_ADDR(0x1B,0x0a)
+
+#define TexelLUT0 GLINT_TAG_ADDR(0x1D,0x00)
+#define TexelLUT1 GLINT_TAG_ADDR(0x1D,0x01)
+#define TexelLUT2 GLINT_TAG_ADDR(0x1D,0x02)
+#define TexelLUT3 GLINT_TAG_ADDR(0x1D,0x03)
+#define TexelLUT4 GLINT_TAG_ADDR(0x1D,0x04)
+#define TexelLUT5 GLINT_TAG_ADDR(0x1D,0x05)
+#define TexelLUT6 GLINT_TAG_ADDR(0x1D,0x06)
+#define TexelLUT7 GLINT_TAG_ADDR(0x1D,0x07)
+#define TexelLUT8 GLINT_TAG_ADDR(0x1D,0x08)
+#define TexelLUT9 GLINT_TAG_ADDR(0x1D,0x09)
+#define TexelLUT10 GLINT_TAG_ADDR(0x1D,0x0A)
+#define TexelLUT11 GLINT_TAG_ADDR(0x1D,0x0B)
+#define TexelLUT12 GLINT_TAG_ADDR(0x1D,0x0C)
+#define TexelLUT13 GLINT_TAG_ADDR(0x1D,0x0D)
+#define TexelLUT14 GLINT_TAG_ADDR(0x1D,0x0E)
+#define TexelLUT15 GLINT_TAG_ADDR(0x1D,0x0F)
+
+#define YUVMode GLINT_TAG_ADDR(0x1E,0x00)
+#define ChromaUpper GLINT_TAG_ADDR(0x1E,0x01)
+#define ChromaLower GLINT_TAG_ADDR(0x1E,0x02)
+#define ChromaTestMode GLINT_TAG_ADDR(0x1E,0x03)
+
+
+/******************************
+ * GLINT Delta Core Registers *
+ ******************************/
+
+#define V0FixedTag GLINT_TAG_ADDR(0x20,0x00)
+#define V1FixedTag GLINT_TAG_ADDR(0x21,0x00)
+#define V2FixedTag GLINT_TAG_ADDR(0x22,0x00)
+#define V0FloatTag GLINT_TAG_ADDR(0x23,0x00)
+#define V1FloatTag GLINT_TAG_ADDR(0x24,0x00)
+#define V2FloatTag GLINT_TAG_ADDR(0x25,0x00)
+
+#define VPAR_s 0x00
+#define VPAR_t 0x08
+#define VPAR_q 0x10
+#define VPAR_Ks 0x18
+#define VPAR_Kd 0x20
+
+/* have changed colors in ramdac !
+#define VPAR_R 0x28
+#define VPAR_G 0x30
+#define VPAR_B 0x38
+#define VPAR_A 0x40
+*/
+#define VPAR_B 0x28
+#define VPAR_G 0x30
+#define VPAR_R 0x38
+#define VPAR_A 0x40
+
+#define VPAR_f 0x48
+
+#define VPAR_x 0x50
+#define VPAR_y 0x58
+#define VPAR_z 0x60
+
+#define DeltaModeTag GLINT_TAG_ADDR(0x26,0x00)
+ /* 0: */
+ /* GLINT_300SX */
+
+ /* DeltaMode Register Bit Field Assignments */
+# define DM_GLINT_300SX 0x0000
+# define DM_GLINT_500TX 0x0001
+# define DM_PERMEDIA 0x0002
+# define DM_Depth_16BPP (1 << 2)
+# define DM_Depth_24BPP (2 << 2)
+# define DM_Depth_32BPP (3 << 2)
+# define DM_FogEnable 0x0010
+# define DM_TextureEnable 0x0020
+# define DM_SmoothShadingEnable 0x0040
+# define DM_DepthEnable 0x0080
+# define DM_SpecularTextureEnable 0x0100
+# define DM_DiffuseTextureEnable 0x0200
+# define DM_SubPixelCorrectionEnable 0x0400
+# define DM_DiamondExit 0x0800
+# define DM_NoDraw 0x1000
+# define DM_ClampEnable 0x2000
+# define DM_ClampedTexParMode 0x4000
+# define DM_NormalizedTexParMode 0xC000
+
+
+# define DDCMD_AreaStrippleEnable 0x0001
+# define DDCMD_LineStrippleEnable 0x0002
+# define DDCMD_ResetLineStripple 1 << 2
+# define DDCMD_FastFillEnable 1 << 3
+ /* 2 Bits reserved */
+# define DDCMD_PrimitiveType_Point 2 << 6
+# define DDCMD_PrimitiveType_Line 0 << 6
+# define DDCMD_PrimitiveType_Trapezoid 1 << 6
+# define DDCMD_AntialiasEnable 1 << 8
+# define DDCMD_AntialiasingQuality 1 << 9
+# define DDCMD_UsePointTable 1 << 10
+# define DDCMD_SyncOnBitMask 1 << 11
+# define DDCMD_SyncOnHostDate 1 << 12
+# define DDCMD_TextureEnable 1 << 13
+# define DDCMD_FogEnable 1 << 14
+# define DDCMD_CoverageEnable 1 << 15
+# define DDCMD_SubPixelCorrectionEnable 1 << 16
+
+
+
+#define DrawTriangle GLINT_TAG_ADDR(0x26,0x01)
+#define RepeatTriangle GLINT_TAG_ADDR(0x26,0x02)
+#define DrawLine01 GLINT_TAG_ADDR(0x26,0x03)
+#define DrawLine10 GLINT_TAG_ADDR(0x26,0x04)
+#define RepeatLine GLINT_TAG_ADDR(0x26,0x05)
+#define BroadcastMask GLINT_TAG_ADDR(0x26,0x0F)
+
+/* Permedia 3 - Accelerator Extensions */
+#define FillRectanglePosition 0x8348
+#define FillRender2D 0x8350
+#define FBDstReadBufAddr0 0xAE80
+#define FBDstReadBufOffset0 0xAEA0
+#define FBDstReadBufWidth0 0xAEC0
+#define FBDstReadMode 0xAEE0
+#define FBDRM_Enable0 1<<8
+#define FBDRM_Blocking 1<<24
+#define FBDstReadEnables 0xAEE8
+#define FBSrcReadMode 0xAF00
+#define FBSRM_Blocking 1<<11
+#define FBSrcReadBufAddr 0xAF08
+#define FBSrcReadBufOffset0 0xAF10
+#define FBSrcReadBufWidth 0xAF18
+#define FBWriteBufAddr0 0xB000
+#define FBWriteBufOffset0 0xB020
+#define FBWriteBufWidth0 0xB040
+#define FBBlockColorBack 0xB0A0
+#define ForegroundColor 0xB0C0
+#define BackgroundColor 0xB0C8
+#define RectanglePosition 0xB600
+#define Render2D 0xB640
+
+/* Colorformats */
+#define BGR555 1
+#define BGR565 16
+#define CI8 14
+#define CI4 15
+
+#ifdef DEBUG
+#define GLINT_WRITE_REG(v,r) \
+ GLINT_VERB_WRITE_REG(pGlint,v,r,__FILE__,__LINE__)
+#define GLINT_READ_REG(r) \
+ GLINT_VERB_READ_REG(pGlint,r,__FILE__,__LINE__)
+#else
+
+#define GLINT_WRITE_REG(v,r) \
+ MMIO_OUT32(pGlint->IOBase + pGlint->IOOffset,(unsigned long)(r), (v))
+#define GLINT_READ_REG(r) \
+ MMIO_IN32(pGlint->IOBase + pGlint->IOOffset,(unsigned long)(r))
+
+#endif /* DEBUG */
+
+#define GLINT_WAIT(n) \
+do{ \
+ if (pGlint->InFifoSpace>=(n)) \
+ pGlint->InFifoSpace -= (n); \
+ else { \
+ int tmp; \
+ while((tmp=GLINT_READ_REG(InFIFOSpace))<(n)); \
+ /* Clamp value due to bugs in PM3 */ \
+ if (tmp > pGlint->FIFOSize) \
+ tmp = pGlint->FIFOSize; \
+ pGlint->InFifoSpace = tmp - (n); \
+ } \
+}while(0)
+
+#define GLINTDACDelay(x) do { \
+ int delay = x; \
+ unsigned char tmp; \
+ while(delay--){tmp = GLINT_READ_REG(InFIFOSpace);}; \
+ } while(0)
+
+#define GLINT_MASK_WRITE_REG(v,m,r) \
+ GLINT_WRITE_REG((GLINT_READ_REG(r)&(m))|(v),r)
+
+#define GLINT_SLOW_WRITE_REG(v,r) \
+do{ \
+ mem_barrier(); \
+ GLINT_WAIT(pGlint->FIFOSize); \
+ mem_barrier(); \
+ GLINT_WRITE_REG(v,r); \
+}while(0)
+
+#define GLINT_SET_INDEX(index) \
+do{ \
+ GLINT_SLOW_WRITE_REG(((index)>>8)&0xff,PM2VDACIndexRegHigh); \
+ GLINT_SLOW_WRITE_REG((index)&0xff,PM2VDACIndexRegLow); \
+} while(0)
+
+#define REPLICATE(r) \
+{ \
+ if (pScrn->bitsPerPixel == 16) { \
+ r &= 0xFFFF; \
+ r |= (r<<16); \
+ } else \
+ if (pScrn->bitsPerPixel == 8) { \
+ r &= 0xFF; \
+ r |= (r<<8); \
+ r |= (r<<16); \
+ } \
+}
+
+#ifndef XF86DRI
+#define LOADROP(rop) \
+{ \
+ if (pGlint->ROP != rop) { \
+ GLINT_WRITE_REG(rop<<1|UNIT_ENABLE, LogicalOpMode); \
+ pGlint->ROP = rop; \
+ } \
+}
+#else
+#define LOADROP(rop) \
+ { \
+ GLINT_WRITE_REG(rop<<1|UNIT_ENABLE, LogicalOpMode); \
+ pGlint->ROP = rop; \
+ }
+#endif
+
+#define CHECKCLIPPING \
+{ \
+ if (pGlint->ClippingOn) { \
+ pGlint->ClippingOn = FALSE; \
+ GLINT_WAIT(1); \
+ GLINT_WRITE_REG(0, ScissorMode); \
+ } \
+}
+
+#ifndef XF86DRI
+#define DO_PLANEMASK(planemask) \
+{ \
+ if (planemask != pGlint->planemask) { \
+ pGlint->planemask = planemask; \
+ REPLICATE(planemask); \
+ GLINT_WRITE_REG(planemask, FBHardwareWriteMask);\
+ } \
+}
+#else
+#define DO_PLANEMASK(planemask) \
+ { \
+ pGlint->planemask = planemask; \
+ REPLICATE(planemask); \
+ GLINT_WRITE_REG(planemask, FBHardwareWriteMask);\
+ }
+#endif
+
+/* Permedia Save/Restore functions */
+
+#define STOREREG(address,value) \
+ pReg->glintRegs[address >> 3] = value;
+
+#define SAVEREG(address) \
+ pReg->glintRegs[address >> 3] = GLINT_READ_REG(address);
+
+#define RESTOREREG(address) \
+ GLINT_SLOW_WRITE_REG(pReg->glintRegs[address >> 3], address);
+
+#define STOREDAC(address,value) \
+ pReg->DacRegs[address] = value;
+
+#define P2VOUT(address) \
+ Permedia2vOutIndReg(pScrn, address, 0x00, pReg->DacRegs[address]);
+
+#define P2VIN(address) \
+ pReg->DacRegs[address] = Permedia2vInIndReg(pScrn, address);
+
+/* RamDac Save/Restore functions, used by external DAC's */
+
+#define STORERAMDAC(address,value) \
+ ramdacReg->DacRegs[address] = value;
+
+/* Multi Chip access */
+
+#define ACCESSCHIP1() \
+ pGlint->IOOffset = 0;
+
+#define ACCESSCHIP2() \
+ pGlint->IOOffset = 0x10000;
+
+#endif
diff --git a/src/glint_shadow.c b/src/glint_shadow.c
new file mode 100644
index 0000000..2dfcef8
--- /dev/null
+++ b/src/glint_shadow.c
@@ -0,0 +1,46 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/glint_shadow.c,v 1.1 1999/11/19 13:54:32 hohndel Exp $ */
+
+/*
+ Copyright (c) 1999, The XFree86 Project Inc.
+ Code adapted from mga/mga_shadow.c (Mark Vojkovich <markv@valinux.com>)
+ by Michel Dänzer <michdaen@iiic.ethz.ch>
+*/
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86Resources.h"
+#include "xf86_ansic.h"
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+#include "glint.h"
+#include "shadowfb.h"
+#include "servermd.h"
+
+
+
+void
+GLINTRefreshArea(ScrnInfoPtr pScrn, int num, BoxPtr pbox)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int width, height, Bpp, FBPitch;
+ unsigned char *src, *dst;
+
+ Bpp = pScrn->bitsPerPixel >> 3;
+ FBPitch = BitmapBytePad(pScrn->displayWidth * pScrn->bitsPerPixel);
+
+ while(num--) {
+ width = (pbox->x2 - pbox->x1) * Bpp;
+ height = pbox->y2 - pbox->y1;
+ src = pGlint->ShadowPtr + (pbox->y1 * pGlint->ShadowPitch) +
+ (pbox->x1 * Bpp);
+ dst = pGlint->FbBase + (pbox->y1 * FBPitch) + (pbox->x1 * Bpp);
+
+ while(height--) {
+ memcpy(dst, src, width);
+ dst += FBPitch;
+ src += pGlint->ShadowPitch;
+ }
+
+ pbox++;
+ }
+}
diff --git a/src/pm2_accel.c b/src/pm2_accel.c
new file mode 100644
index 0000000..583fbc1
--- /dev/null
+++ b/src/pm2_accel.c
@@ -0,0 +1,1487 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Mark Vojkovich, <mvojkovi@ucsd.edu>
+ * Michel Dänzer, <michdaen@iiic.ethz.ch>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ *
+ * Permedia 2 accelerated options.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm2_accel.c,v 1.31 2001/10/28 03:33:30 tsi Exp $ */
+
+#include "Xarch.h"
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "miline.h"
+
+#include "fb.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+#include "xaalocal.h" /* For replacements */
+
+#define DEBUG 0
+
+#if DEBUG
+# define TRACE_ENTER(str) ErrorF("pm2_accel: " str " %d\n",pScrn->scrnIndex)
+# define TRACE_EXIT(str) ErrorF("pm2_accel: " str " done\n")
+# define TRACE(str) ErrorF("pm2_accel trace: " str "\n")
+#else
+# define TRACE_ENTER(str)
+# define TRACE_EXIT(str)
+# define TRACE(str)
+#endif
+
+static void Permedia2SetupForFillRectSolid(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask);
+static void Permedia2SubsequentFillRectSolid(ScrnInfoPtr pScrn, int x,
+ int y, int w, int h);
+static void Permedia2SetupForFillRectSolid24bpp(ScrnInfoPtr pScrn,int color,
+ int rop, unsigned int planemask);
+static void Permedia2SubsequentFillRectSolid24bpp(ScrnInfoPtr pScrn, int x,
+ int y, int w, int h);
+static void Permedia2SubsequentScreenToScreenCopy(ScrnInfoPtr pScrn,
+ int x1, int y1, int x2,
+ int y2, int w, int h);
+static void Permedia2SetupForScreenToScreenCopy(ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask,
+ int transparency_color);
+static void Permedia2SubsequentScreenToScreenCopy2432bpp(ScrnInfoPtr pScrn,
+ int x1, int y1, int x2, int y2, int w, int h);
+static void Permedia2SetupForScreenToScreenCopy2432bpp(ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask,
+ int transparency_color);
+static void Permedia2SetClippingRectangle(ScrnInfoPtr pScrn, int x, int y,
+ int w, int h);
+static void Permedia2DisableClipping(ScrnInfoPtr pScrn);
+static void Permedia2SetupForSolidLine(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask);
+static void Permedia2SubsequentHorVertLine(ScrnInfoPtr pScrn, int x, int y,
+ int len, int dir);
+static void Permedia2SubsequentSolidBresenhamLine(ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e,
+ int len, int octant);
+static void Permedia2WriteBitmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth, int skipleft,
+ int fg, int bg, int rop,unsigned int planemask);
+static void Permedia2SetupForMono8x8PatternFill(ScrnInfoPtr pScrn,
+ int patternx, int patterny, int fg, int bg,
+ int rop, unsigned int planemask);
+static void Permedia2SubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn,
+ int patternx, int patterny, int x, int y,
+ int w, int h);
+static void Permedia2SetupForMono8x8PatternFill24bpp(ScrnInfoPtr pScrn,
+ int patternx, int patterny, int fg, int bg,
+ int rop, unsigned int planemask);
+static void Permedia2SubsequentMono8x8PatternFillRect24bpp(ScrnInfoPtr pScrn,
+ int patternx, int patterny, int x, int y,
+ int w, int h);
+static void Permedia2WritePixmap8bpp(ScrnInfoPtr pScrn, int x, int y, int w,
+ int h, unsigned char *src, int srcwidth,
+ int rop, unsigned int planemask,
+ int transparency_color, int bpp, int depth);
+static void Permedia2WritePixmap16bpp(ScrnInfoPtr pScrn, int x, int y, int w,
+ int h, unsigned char *src, int srcwidth,
+ int rop, unsigned int planemask,
+ int transparency_color, int bpp, int depth);
+static void Permedia2WritePixmap32bpp(ScrnInfoPtr pScrn, int x, int y, int w,
+ int h, unsigned char *src, int srcwidth,
+ int rop, unsigned int planemask,
+ int transparency_color, int bpp, int depth);
+static void Permedia2SetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg, int rop,
+ unsigned int planemask);
+static void Permedia2SubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn, int x,
+ int y, int w, int h, int skipleft);
+static void Permedia2SubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno);
+static void Permedia2LoadCoord(ScrnInfoPtr pScrn, int x, int y, int w, int h);
+static void Permedia2PolylinesThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int mode, int npt, DDXPointPtr pPts);
+static void Permedia2PolySegmentThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int nseg, xSegment *pSeg);
+
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+# define STIPPLE_SWAP 1<<18 /* Mirror stipple pattern horizontally */
+#else
+# define STIPPLE_SWAP 0
+#endif
+
+void
+Permedia2InitializeEngine(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /* Initialize the Accelerator Engine to defaults */
+
+ TRACE_ENTER("Permedia2InitializeEngine");
+
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(0, dXSub);
+ GLINT_SLOW_WRITE_REG(GWIN_DisableLBUpdate, GLINTWindow);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DitherMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PMTextureReadMode);
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, LBReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TexelLUTMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, YUVMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FogMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
+ GLINT_SLOW_WRITE_REG(0x400, FilterMode);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBHardwareWriteMask);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBSoftwareWriteMask);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTDepth);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBPixelOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, WindowOrigin);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBWindowBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWindowBase);
+
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ pGlint->RasterizerSwap = 1;
+#else
+ pGlint->RasterizerSwap = 0;
+#endif
+
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ pGlint->PixelWidth = 0x0; /* 8 Bits */
+ pGlint->TexMapFormat = pGlint->pprod;
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ pGlint->RasterizerSwap |= 3<<15; /* Swap host data */
+#endif
+ break;
+ case 16:
+ pGlint->PixelWidth = 0x1; /* 16 Bits */
+ pGlint->TexMapFormat = pGlint->pprod | 1<<19;
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ pGlint->RasterizerSwap |= 2<<15; /* Swap host data */
+#endif
+ break;
+ case 24:
+ pGlint->PixelWidth = 0x4; /* 24 Bits */
+ pGlint->TexMapFormat = pGlint->pprod | 2<<19;
+ break;
+ case 32:
+ pGlint->PixelWidth = 0x2; /* 32 Bits */
+ pGlint->TexMapFormat = pGlint->pprod | 2<<19;
+ break;
+ }
+ pGlint->ClippingOn = FALSE;
+ pGlint->startxdom = 0;
+ pGlint->startxsub = 0;
+ pGlint->starty = 0;
+ pGlint->count = 0;
+ pGlint->dy = 1<<16;
+ pGlint->dxdom = 0;
+ pGlint->x = 0;
+ pGlint->y = 0;
+ pGlint->h = 0;
+ pGlint->w = 0;
+ pGlint->ROP = 0xFF;
+ GLINT_SLOW_WRITE_REG(pGlint->PixelWidth, FBReadPixel);
+ GLINT_SLOW_WRITE_REG(pGlint->TexMapFormat, PMTextureMapFormat);
+ GLINT_SLOW_WRITE_REG(0, RectangleSize);
+ GLINT_SLOW_WRITE_REG(0, RectangleOrigin);
+ GLINT_SLOW_WRITE_REG(0, dXDom);
+ GLINT_SLOW_WRITE_REG(1<<16, dY);
+ GLINT_SLOW_WRITE_REG(0, StartXDom);
+ GLINT_SLOW_WRITE_REG(0, StartXSub);
+ GLINT_SLOW_WRITE_REG(0, StartY);
+ GLINT_SLOW_WRITE_REG(0, GLINTCount);
+
+ TRACE_EXIT("Permedia2InitializeEngine");
+}
+
+Bool
+Permedia2AccelInit(ScreenPtr pScreen)
+{
+ XAAInfoRecPtr infoPtr;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ BoxRec AvailFBArea;
+
+ pGlint->AccelInfoRec = infoPtr = XAACreateInfoRec();
+ if (!infoPtr) return FALSE;
+
+ Permedia2InitializeEngine(pScrn);
+
+ infoPtr->Flags = PIXMAP_CACHE |
+ OFFSCREEN_PIXMAPS |
+ LINEAR_FRAMEBUFFER;
+
+ infoPtr->Sync = Permedia2Sync;
+
+ infoPtr->SetClippingRectangle = Permedia2SetClippingRectangle;
+ infoPtr->DisableClipping = Permedia2DisableClipping;
+ infoPtr->ClippingFlags = HARDWARE_CLIP_MONO_8x8_FILL;
+
+ infoPtr->SolidFillFlags = 0;
+ infoPtr->ScreenToScreenCopyFlags = NO_TRANSPARENCY;
+ infoPtr->WriteBitmapFlags = 0;
+ if (pScrn->bitsPerPixel == 24) {
+ infoPtr->SetupForSolidFill =
+ Permedia2SetupForFillRectSolid24bpp;
+ infoPtr->SubsequentSolidFillRect =
+ Permedia2SubsequentFillRectSolid24bpp;
+ } else {
+ infoPtr->SolidLineFlags = 0;
+ infoPtr->PolySegmentThinSolidFlags = 0;
+ infoPtr->PolylinesThinSolidFlags = 0;
+ infoPtr->SetupForSolidLine = Permedia2SetupForSolidLine;
+ infoPtr->SubsequentSolidHorVertLine = Permedia2SubsequentHorVertLine;
+ if (!(pScrn->overlayFlags & OVERLAY_8_32_PLANAR))
+ {
+ infoPtr->SubsequentSolidBresenhamLine =
+ Permedia2SubsequentSolidBresenhamLine;
+ }
+ infoPtr->PolySegmentThinSolid = Permedia2PolySegmentThinSolidWrapper;
+ infoPtr->PolylinesThinSolid = Permedia2PolylinesThinSolidWrapper;
+ infoPtr->SetupForSolidFill = Permedia2SetupForFillRectSolid;
+ infoPtr->SubsequentSolidFillRect = Permedia2SubsequentFillRectSolid;
+ }
+
+ if (pScrn->bitsPerPixel >= 24) {
+ infoPtr->SetupForScreenToScreenCopy =
+ Permedia2SetupForScreenToScreenCopy2432bpp;
+ infoPtr->SubsequentScreenToScreenCopy =
+ Permedia2SubsequentScreenToScreenCopy2432bpp;
+ } else {
+ infoPtr->SetupForScreenToScreenCopy =
+ Permedia2SetupForScreenToScreenCopy;
+ infoPtr->SubsequentScreenToScreenCopy =
+ Permedia2SubsequentScreenToScreenCopy;
+ }
+
+ infoPtr->Mono8x8PatternFillFlags =
+ HARDWARE_PATTERN_PROGRAMMED_ORIGIN |
+ HARDWARE_PATTERN_PROGRAMMED_BITS |
+ HARDWARE_PATTERN_SCREEN_ORIGIN;
+
+ if (pScrn->bitsPerPixel == 24) {
+ infoPtr->SetupForMono8x8PatternFill =
+ Permedia2SetupForMono8x8PatternFill24bpp;
+ infoPtr->SubsequentMono8x8PatternFillRect =
+ Permedia2SubsequentMono8x8PatternFillRect24bpp;
+ } else {
+ infoPtr->SetupForMono8x8PatternFill =
+ Permedia2SetupForMono8x8PatternFill;
+ infoPtr->SubsequentMono8x8PatternFillRect =
+ Permedia2SubsequentMono8x8PatternFillRect;
+ }
+
+ infoPtr->ScanlineCPUToScreenColorExpandFillFlags =
+ BIT_ORDER_IN_BYTE_LSBFIRST;
+
+ infoPtr->NumScanlineColorExpandBuffers = 1;
+ infoPtr->ScanlineColorExpandBuffers =
+ pGlint->XAAScanlineColorExpandBuffers;
+ pGlint->XAAScanlineColorExpandBuffers[0] =
+ pGlint->IOBase + OutputFIFO + 4;
+
+ infoPtr->SetupForScanlineCPUToScreenColorExpandFill =
+ Permedia2SetupForScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentScanlineCPUToScreenColorExpandFill =
+ Permedia2SubsequentScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentColorExpandScanline =
+ Permedia2SubsequentColorExpandScanline;
+
+ infoPtr->WriteBitmap = Permedia2WriteBitmap;
+
+ if (pScrn->bitsPerPixel == 8) {
+ infoPtr->WritePixmap = Permedia2WritePixmap8bpp;
+ infoPtr->WritePixmapFlags = NO_GXCOPY;
+ } else
+ if (pScrn->bitsPerPixel == 16) {
+ infoPtr->WritePixmap = Permedia2WritePixmap16bpp;
+ infoPtr->WritePixmapFlags = NO_GXCOPY;
+ } else
+ if (pScrn->bitsPerPixel == 32)
+ infoPtr->WritePixmap = Permedia2WritePixmap32bpp;
+
+ /* Now fixup if we are 24bpp */
+ if (pScrn->bitsPerPixel == 24) {
+ infoPtr->SolidFillFlags |= NO_PLANEMASK;
+ infoPtr->ScreenToScreenCopyFlags |= NO_PLANEMASK;
+ infoPtr->WriteBitmapFlags |= NO_PLANEMASK;
+ infoPtr->ScanlineCPUToScreenColorExpandFillFlags |= NO_PLANEMASK;
+ infoPtr->Mono8x8PatternFillFlags |= NO_PLANEMASK;
+ }
+
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = 0;
+ AvailFBArea.x2 = pScrn->displayWidth;
+ AvailFBArea.y2 = pGlint->FbMapSize / (pScrn->displayWidth *
+ pScrn->bitsPerPixel / 8);
+
+ if (AvailFBArea.y2 > 2047) AvailFBArea.y2 = 2047;
+
+ xf86InitFBManager(pScreen, &AvailFBArea);
+
+ return(XAAInit(pScreen, infoPtr));
+}
+
+static void Permedia2LoadCoord(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if ((h != pGlint->h) || (w != pGlint->w)) {
+ pGlint->w = w;
+ pGlint->h = h;
+ GLINT_WRITE_REG(((h&0x0FFF)<<16)|(w&0x0FFF), RectangleSize);
+ }
+ if ((y != pGlint->y) || (x != pGlint->x)) {
+ pGlint->x = x;
+ pGlint->y = y;
+ GLINT_WRITE_REG(((y&0x0FFF)<<16)|(x&0x0FFF), RectangleOrigin);
+ }
+}
+
+
+void
+Permedia2Sync(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ } while (GLINT_READ_REG(OutputFIFO) != Sync_tag);
+}
+
+static void
+Permedia2SetClippingRectangle(ScrnInfoPtr pScrn, int x1, int y1, int x2, int y2)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(((y1&0x0fff)<<16)|(x1&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG(((y2&0x0fff)<<16)|(x2&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(1, ScissorMode);
+ pGlint->ClippingOn = TRUE;
+}
+
+static void
+Permedia2DisableClipping(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CHECKCLIPPING;
+}
+
+static void
+Permedia2SetupForScreenToScreenCopy2432bpp(ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask, int transparency_color)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->BltScanDirection = 0;
+ if (xdir == 1) pGlint->BltScanDirection |= XPositive;
+ if (ydir == 1) pGlint->BltScanDirection |= YPositive;
+
+ if (pScrn->bitsPerPixel == 24) {
+ GLINT_WAIT(4);
+ } else {
+ GLINT_WAIT(5);
+ DO_PLANEMASK(planemask);
+ }
+
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ if ((rop == GXset) || (rop == GXclear)) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ if ((rop == GXcopy) || (rop == GXcopyInverted)) {
+ GLINT_WRITE_REG(pGlint->pprod|FBRM_SrcEnable, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod|FBRM_SrcEnable|FBRM_DstEnable,
+ FBReadMode);
+ }
+ }
+ LOADROP(rop);
+}
+
+static void
+Permedia2SubsequentScreenToScreenCopy2432bpp(ScrnInfoPtr pScrn, int x1,
+ int y1, int x2, int y2, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(4);
+ Permedia2LoadCoord(pScrn, x2, y2, w, h);
+ GLINT_WRITE_REG(((y1-y2)&0x0FFF)<<16 | ((x1-x2)&0x0FFF), FBSourceDelta);
+ GLINT_WRITE_REG(PrimitiveRectangle | pGlint->BltScanDirection, Render);
+}
+
+static void
+Permedia2SetupForScreenToScreenCopy(ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask, int transparency_color)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia2SetupForScreenToScreenCopy");
+
+ pGlint->BltScanDirection = 0;
+ if (xdir == 1) pGlint->BltScanDirection |= XPositive;
+ if (ydir == 1) pGlint->BltScanDirection |= YPositive;
+
+ GLINT_WAIT(4);
+ DO_PLANEMASK(planemask);
+
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ if ((rop == GXset) || (rop == GXclear)) {
+ pGlint->FrameBufferReadMode = pGlint->pprod;
+ } else
+ if ((rop == GXcopy) || (rop == GXcopyInverted)) {
+ pGlint->FrameBufferReadMode = pGlint->pprod |FBRM_SrcEnable;
+ } else {
+ pGlint->FrameBufferReadMode = pGlint->pprod | FBRM_SrcEnable |
+ FBRM_DstEnable;
+ }
+ LOADROP(rop);
+ TRACE_EXIT("Permedia2SetupForScreenToScreenCopy");
+}
+
+static void
+Permedia2SubsequentScreenToScreenCopy(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2, int y2, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ char align;
+
+ TRACE_ENTER("Permedia2SubsequentScreenToScreenCopy");
+ /* We can only use GXcopy for Packed modes */
+ if (pGlint->ROP != GXcopy) {
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(pGlint->FrameBufferReadMode, FBReadMode);
+ Permedia2LoadCoord(pScrn, x2, y2, w, h);
+ GLINT_WRITE_REG(((y1-y2)&0x0FFF)<<16 | ((x1-x2)&0x0FFF), FBSourceDelta);
+ } else {
+ align = (x2 & pGlint->bppalign) - (x1 & pGlint->bppalign);
+ GLINT_WAIT(6);
+ GLINT_WRITE_REG(pGlint->FrameBufferReadMode|FBRM_Packed, FBReadMode);
+ Permedia2LoadCoord(pScrn, x2>>pGlint->BppShift, y2,
+ (w+7)>>pGlint->BppShift, h);
+ GLINT_WRITE_REG(align<<29|x2<<16|(x2+w), PackedDataLimits);
+ GLINT_WRITE_REG(((y1-y2)&0x0FFF)<<16 | (((x1 & ~pGlint->bppalign)-(x2 & ~pGlint->bppalign))&0x0FFF), FBSourceDelta);
+ }
+
+ GLINT_WRITE_REG(PrimitiveRectangle | pGlint->BltScanDirection, Render);
+ TRACE_EXIT("Permedia2SubsequentScreenToScreenCopy");
+}
+
+
+
+static void
+Permedia2PolylinesThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int mode,
+ int npt,
+ DDXPointPtr pPts
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolyLines(pDraw, pGC, mode, npt, pPts);
+}
+
+static void
+Permedia2PolySegmentThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int nseg,
+ xSegment *pSeg
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolySegment(pDraw, pGC, nseg, pSeg);
+}
+
+static void
+Permedia2SetupForSolidLine(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, GLINTColor);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+Permedia2SubsequentHorVertLine(ScrnInfoPtr pScrn,int x,int y,int len,int dir)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(6);
+ GLINT_WRITE_REG(x<<16, StartXDom);
+ GLINT_WRITE_REG(y<<16, StartY);
+ if (dir == DEGREES_0) {
+ GLINT_WRITE_REG(1<<16, dXDom);
+ GLINT_WRITE_REG(0<<16, dY);
+ } else {
+ GLINT_WRITE_REG(0<<16, dXDom);
+ GLINT_WRITE_REG(1<<16, dY);
+ }
+
+ GLINT_WRITE_REG(len, GLINTCount);
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+}
+
+static void
+Permedia2SubsequentSolidBresenhamLine( ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e, int len, int octant)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if(dmaj == dmin) {
+ GLINT_WAIT(6);
+ if(octant & YDECREASING) {
+ GLINT_WRITE_REG(-1<<16, dY);
+ } else {
+ GLINT_WRITE_REG(1<<16, dY);
+ }
+
+ if(octant & XDECREASING) {
+ GLINT_WRITE_REG(-1<<16, dXDom);
+ } else {
+ GLINT_WRITE_REG(1<<16, dXDom);
+ }
+
+ GLINT_WRITE_REG(x<<16, StartXDom);
+ GLINT_WRITE_REG(y<<16, StartY);
+ GLINT_WRITE_REG(len,GLINTCount);
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+ return;
+ }
+
+ fbBres(pGlint->CurrentDrawable, pGlint->CurrentGC, 0,
+ (octant & XDECREASING) ? -1 : 1,
+ (octant & YDECREASING) ? -1 : 1,
+ (octant & YMAJOR) ? Y_AXIS : X_AXIS,
+ x, y, dmin + e, dmin, -dmaj, len);
+}
+
+static void
+Permedia2SetupForFillRectSolid24bpp(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ pGlint->ForeGroundColor = color;
+
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, ConstantColor);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+Permedia2SetupForFillRectSolid(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia2SetupForFillRectSolid");
+
+ REPLICATE(color);
+
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(color, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, ConstantColor);
+ /* We can use Packed mode for filling solid non-GXcopy rasters */
+ GLINT_WRITE_REG(pGlint->pprod|FBRM_DstEnable|FBRM_Packed, FBReadMode);
+ }
+ LOADROP(rop);
+ TRACE_EXIT("Permedia2SetupForFillRectSolid");
+}
+
+static void
+Permedia2SubsequentFillRectSolid24bpp(ScrnInfoPtr pScrn, int x, int y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINT_WAIT(3);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive, Render);
+}
+
+static void
+Permedia2SubsequentFillRectSolid(ScrnInfoPtr pScrn, int x, int y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int speed = 0;
+ TRACE_ENTER("Permedia2SubsequentFillRectSolid");
+
+ if (pGlint->ROP == GXcopy) {
+ GLINT_WAIT(3);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+ speed = FastFillEnable;
+ } else {
+ GLINT_WAIT(4);
+ Permedia2LoadCoord(pScrn, x>>pGlint->BppShift, y,
+ (w+7)>>pGlint->BppShift, h);
+ GLINT_WRITE_REG(x<<16|(x+w), PackedDataLimits);
+ speed = 0;
+ }
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive | speed, Render);
+ TRACE_EXIT("Permedia2SubsequentFillRectSolid");
+}
+
+static void
+Permedia2SetupForMono8x8PatternFill24bpp(ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (bg == -1) pGlint->FrameBufferReadMode = -1;
+ else pGlint->FrameBufferReadMode = 0;
+
+ pGlint->ForeGroundColor = fg;
+ pGlint->BackGroundColor = bg;
+ REPLICATE(pGlint->ForeGroundColor);
+ REPLICATE(pGlint->BackGroundColor);
+
+ GLINT_WAIT(12);
+ GLINT_WRITE_REG((patternx & 0xFF), AreaStipplePattern0);
+ GLINT_WRITE_REG((patternx & 0xFF00) >> 8, AreaStipplePattern1);
+ GLINT_WRITE_REG((patternx & 0xFF0000) >> 16, AreaStipplePattern2);
+ GLINT_WRITE_REG((patternx & 0xFF000000) >> 24, AreaStipplePattern3);
+ GLINT_WRITE_REG((patterny & 0xFF), AreaStipplePattern4);
+ GLINT_WRITE_REG((patterny & 0xFF00) >> 8, AreaStipplePattern5);
+ GLINT_WRITE_REG((patterny & 0xFF0000) >> 16, AreaStipplePattern6);
+ GLINT_WRITE_REG((patterny & 0xFF000000) >> 24, AreaStipplePattern7);
+
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+Permedia2SetupForMono8x8PatternFill(ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia2SetupForMono8x8PatternFill");
+
+ if (bg == -1) pGlint->FrameBufferReadMode = -1;
+ else pGlint->FrameBufferReadMode = 0;
+
+ pGlint->ForeGroundColor = fg;
+ pGlint->BackGroundColor = bg;
+ REPLICATE(pGlint->ForeGroundColor);
+ REPLICATE(pGlint->BackGroundColor);
+
+#if DEBUG
+ ErrorF("patternx: %x patterny: %x\n", patternx, patterny);
+#endif
+
+ GLINT_WAIT(13);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG((patternx & 0xFF), AreaStipplePattern0);
+ GLINT_WRITE_REG((patternx & 0xFF00) >> 8, AreaStipplePattern1);
+ GLINT_WRITE_REG((patternx & 0xFF0000) >> 16, AreaStipplePattern2);
+ GLINT_WRITE_REG((patternx & 0xFF000000) >> 24, AreaStipplePattern3);
+ GLINT_WRITE_REG((patterny & 0xFF), AreaStipplePattern4);
+ GLINT_WRITE_REG((patterny & 0xFF00) >> 8, AreaStipplePattern5);
+ GLINT_WRITE_REG((patterny & 0xFF0000) >> 16, AreaStipplePattern6);
+ GLINT_WRITE_REG((patterny & 0xFF000000) >> 24, AreaStipplePattern7);
+
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+ TRACE_EXIT("Permedia2SetupForMono8x8PatternFill");
+}
+
+static void
+Permedia2SubsequentMono8x8PatternFillRect24bpp(ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int x, int y,
+ int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(8);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+
+ if (pGlint->FrameBufferReadMode != -1) {
+ GLINT_WRITE_REG(pGlint->BackGroundColor, ConstantColor);
+ GLINT_WRITE_REG(patternx<<7|patterny<<12| ASM_InvertPattern |
+ STIPPLE_SWAP | UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | XPositive |
+ YPositive | PrimitiveRectangle, Render);
+ }
+
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, ConstantColor);
+ GLINT_WRITE_REG(patternx<<7|patterny<<12|UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | XPositive | YPositive |
+ PrimitiveRectangle, Render);
+}
+
+static void
+Permedia2SubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int x, int y,
+ int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("Permedia2SubsequentMono8x8PatternFillRect()");
+
+ GLINT_WAIT(9);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+
+ if (pGlint->FrameBufferReadMode != -1) {
+ if (pGlint->ROP == GXcopy) {
+ GLINT_WRITE_REG(pGlint->BackGroundColor, FBBlockColor);
+ GLINT_WRITE_REG(ASM_InvertPattern|patternx<<7|patterny<<12|
+ STIPPLE_SWAP | UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | FastFillEnable |
+ XPositive | YPositive | PrimitiveRectangle, Render);
+ } else {
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, ConstantColor);
+ GLINT_WRITE_REG(pGlint->BackGroundColor, Texel0);
+ GLINT_WRITE_REG(patternx<<7|patterny<<12|
+ STIPPLE_SWAP | UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | XPositive | TextureEnable |
+ YPositive | PrimitiveRectangle, Render);
+ return;
+ }
+ }
+
+ if (pGlint->ROP == GXcopy) {
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, FBBlockColor);
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ } else {
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, ConstantColor);
+ pGlint->FrameBufferReadMode = 0;
+ }
+ GLINT_WRITE_REG(patternx<<7|patterny<<12|STIPPLE_SWAP|UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | pGlint->FrameBufferReadMode |
+ XPositive | YPositive | PrimitiveRectangle, Render);
+
+ TRACE_EXIT("Permedia2SubsequentMono8x8PatternFillRect()");
+}
+
+static void
+Permedia2SetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int dobackground = 0;
+
+ TRACE_ENTER("Permedia2SetupForScanlineCPUToScreenColorExpandFill");
+ if (bg != -1) dobackground |= ForceBackgroundColor;
+ pGlint->BackGroundColor = bg;
+ pGlint->ForeGroundColor = fg;
+ REPLICATE(fg);
+ REPLICATE(bg);
+ GLINT_WAIT(7);
+ DO_PLANEMASK(planemask);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod|FBRM_DstEnable, FBReadMode);
+ }
+ if ((rop == GXcopy) && (pGlint->BackGroundColor == -1)) {
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ GLINT_WRITE_REG(pGlint->RasterizerSwap,RasterizerMode);
+ } else {
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(fg, ConstantColor);
+ GLINT_WRITE_REG(BitMaskPackingEachScanline|dobackground|
+ pGlint->RasterizerSwap,RasterizerMode);
+ if (dobackground) {
+ GLINT_WRITE_REG(bg, Texel0);
+ pGlint->FrameBufferReadMode = TextureEnable;
+ } else {
+ pGlint->FrameBufferReadMode = 0;
+ }
+ }
+ LOADROP(rop);
+ TRACE_EXIT("Permedia2SetupForScanlineCPUToScreenColorExpandFill");
+}
+
+static void
+Permedia2SubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ int skipleft
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("Permedia2SubsequentScanlineCPUToScreenColorExpandFill");
+
+ pGlint->dwords = ((w + 31) >> 5); /* dwords per scanline */
+
+ pGlint->cpucount = h;
+
+ GLINT_WAIT(6);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive | pGlint->FrameBufferReadMode | SyncOnBitMask, Render);
+ GLINT_WRITE_REG(((pGlint->dwords*h)-1)<<16 | 0x0D, OutputFIFO);
+ GLINT_WAIT(pGlint->dwords);
+ pGlint->cpucount--;
+ TRACE_EXIT("Permedia2SubsequentScanlineCPUToScreenColorExpandFill");
+}
+
+static void
+Permedia2SubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (pGlint->cpucount--)
+ GLINT_WAIT(pGlint->dwords);
+}
+
+
+static void
+Permedia2WriteBitmap(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int skipleft,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char *srcpntr;
+ int dwords, height, mode;
+ Bool SecondPass = FALSE;
+
+ TRACE_ENTER("Permedia2WriteBitmap");
+
+ w += skipleft;
+ x -= skipleft;
+ dwords = (w + 31) >> 5;
+
+ Permedia2SetClippingRectangle(pScrn,x+skipleft,y,x+w,y+h);
+
+ if (pScrn->bitsPerPixel == 24) {
+ GLINT_WAIT(10);
+ } else {
+ GLINT_WAIT(11);
+ DO_PLANEMASK(planemask);
+ }
+ LOADROP(rop);
+ Permedia2LoadCoord(pScrn, x&0xFFFF, y, w, h);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ if ((pScrn->bitsPerPixel != 24) && (rop == GXcopy)) {
+ mode = FastFillEnable;
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->RasterizerSwap,RasterizerMode);
+ } else {
+ mode = 0;
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(BitMaskPackingEachScanline|
+ pGlint->RasterizerSwap,RasterizerMode);
+ }
+
+ if(bg == -1) {
+ REPLICATE(fg);
+ if ((pScrn->bitsPerPixel != 24) && (rop == GXcopy)) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, ConstantColor);
+ }
+ } else if((rop == GXcopy) && (pScrn->bitsPerPixel != 24)) {
+ REPLICATE(bg);
+ GLINT_WRITE_REG(bg, FBBlockColor);
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive |YPositive |mode,Render);
+ REPLICATE(fg);
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ SecondPass = TRUE;
+ REPLICATE(fg);
+ if ((pScrn->bitsPerPixel != 24) && (rop == GXcopy)) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, ConstantColor);
+ }
+ }
+
+SECOND_PASS:
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive | mode | SyncOnBitMask, Render);
+
+ height = h;
+ srcpntr = src;
+ while(height--) {
+ GLINT_WAIT(dwords + 1);
+ /* 0x0D is the TAG value for BitMaskPattern */
+ GLINT_WRITE_REG(((dwords - 1) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS((CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32 *)srcpntr, dwords);
+ srcpntr += srcwidth;
+ }
+
+ if(SecondPass) {
+ SecondPass = FALSE;
+ REPLICATE(bg);
+ GLINT_WAIT(3);
+ if ((pScrn->bitsPerPixel != 24) && (rop == GXcopy)) {
+ GLINT_WRITE_REG(InvertBitMask|pGlint->RasterizerSwap,RasterizerMode);
+ GLINT_WRITE_REG(bg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(InvertBitMask|BitMaskPackingEachScanline|
+ pGlint->RasterizerSwap, RasterizerMode);
+ GLINT_WRITE_REG(bg, ConstantColor);
+ }
+ goto SECOND_PASS;
+ }
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(pGlint->RasterizerSwap, RasterizerMode);
+ Permedia2DisableClipping(pScrn);
+ SET_SYNC_FLAG(infoRec);
+ TRACE_EXIT("Permedia2WriteBitmap");
+}
+
+
+static void
+Permedia2WritePixmap8bpp(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int transparency_color,
+ int bpp, int depth
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int skipleft, dwords, count;
+ CARD32* srcp;
+ unsigned char *srcpbyte;
+ Bool FastTexLoad = FALSE;
+
+ GLINT_WAIT(3);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->RasterizerSwap,RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_Packed, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+
+ dwords = (w + 3) >> 2;
+#if X_BYTE_ORDER == X_LITTLE_ENDIAN
+ if((!(x&3)) && (!(w&3))) FastTexLoad = TRUE;
+#endif
+ if((rop != GXcopy) || (planemask != ~0))
+ FastTexLoad = FALSE;
+
+ if (rop == GXcopy) {
+ skipleft = 0;
+ } else {
+ if((skipleft = (long)src & 0x03)) {
+ skipleft /= (bpp>>3);
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03);
+ }
+ }
+
+
+ if(FastTexLoad) {
+ int address;
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_DISABLE, FBWriteMode);
+ Permedia2Sync(pScrn); /* we are not using the rasterizer */
+ while(h--) {
+ count = dwords;
+ address = ((y * pScrn->displayWidth) + x) >> 2;
+ srcp = (CARD32*)src;
+ GLINT_WAIT(1); /*??*/
+ GLINT_WRITE_REG(address, TextureDownloadOffset);
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x11 << 4) |
+ 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ address += pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x11 << 4) | 0x0D,
+ OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ y++;
+ }
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ } else {
+ char align = (x & pGlint->bppalign);
+
+
+ GLINT_WAIT(1); /*??*/
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ if (rop == GXcopy) {
+ GLINT_WAIT(6);
+ Permedia2LoadCoord(pScrn, x>>pGlint->BppShift, y,
+ (w+pGlint->bppalign)>>pGlint->BppShift, h);
+ GLINT_WRITE_REG(align<<29|x<<16|(x+w), PackedDataLimits);
+ } else {
+ Permedia2SetClippingRectangle(pScrn,x+skipleft,y,x+w,y+h);
+ GLINT_WAIT(5);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+ }
+ LOADROP(rop);
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive |
+ SyncOnHostData, Render);
+
+ if (rop == GXcopy) {
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+ } else {
+ while(h--) {
+ count = w;
+ srcpbyte = (unsigned char *)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveBYTE(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned char *)srcpbyte, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcpbyte += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveBYTE(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned char *)srcpbyte, count);
+ }
+ src += srcwidth;
+ }
+ }
+ }
+
+ Permedia2DisableClipping(pScrn);
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+Permedia2WritePixmap16bpp(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int transparency_color,
+ int bpp, int depth
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int skipleft, dwords, count;
+ CARD32* srcp;
+ unsigned short* srcpword;
+ Bool FastTexLoad;
+
+ TRACE_ENTER("Permedia2WritePixmap16bpp");
+ GLINT_WAIT(3);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->RasterizerSwap,RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_Packed, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+
+ FastTexLoad = FALSE;
+ dwords = (w + 1) >> 1;
+#if X_BYTE_ORDER == X_LITTLE_ENDIAN
+ if((!(x&1)) && (!(w&1))) FastTexLoad = TRUE;
+#endif
+ if((rop != GXcopy) || (planemask != ~0))
+ FastTexLoad = FALSE;
+
+ if (rop == GXcopy) {
+ skipleft = 0;
+ } else {
+ if((skipleft = (long)src & 0x03L)) {
+ skipleft /= (bpp>>3);
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+ }
+
+ if(FastTexLoad) {
+ int address;
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_DISABLE, FBWriteMode);
+ Permedia2Sync(pScrn); /* we are not using the rasterizer */
+ while(h--) {
+ count = dwords;
+ address = ((y * pScrn->displayWidth) + x) >> 1;
+ srcp = (CARD32*)src;
+ GLINT_WAIT(1); /*??*/
+ GLINT_WRITE_REG(address, TextureDownloadOffset);
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x11 << 4) |
+ 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ address += pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x11 << 4) | 0x0D,
+ OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ y++;
+ }
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ } else {
+ char align = (x & pGlint->bppalign);
+
+
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ if (rop == GXcopy) {
+ GLINT_WAIT(6);
+ Permedia2LoadCoord(pScrn, x>>pGlint->BppShift, y,
+ (w+pGlint->bppalign)>>pGlint->BppShift, h);
+ GLINT_WRITE_REG(align<<29|x<<16|(x+w), PackedDataLimits);
+ } else {
+ Permedia2SetClippingRectangle(pScrn,x+skipleft,y,x+w,y+h);
+ GLINT_WAIT(5);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+ }
+ LOADROP(rop);
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive |
+ SyncOnHostData, Render);
+
+ if (rop == GXcopy) {
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+ } else {
+ while(h--) {
+ count = w;
+ srcpword = (unsigned short *)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned short *)srcpword, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcpword += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned short *)srcpword, count);
+ }
+ src += srcwidth;
+ }
+ }
+ }
+
+ Permedia2DisableClipping(pScrn);
+ SET_SYNC_FLAG(infoRec);
+ TRACE_EXIT("Permedia2WritePixmap16bpp");
+}
+
+static void
+Permedia2WritePixmap32bpp(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int transparency_color,
+ int bpp, int depth
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int skipleft, dwords, count;
+ CARD32* srcp;
+
+ GLINT_WAIT(3);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->RasterizerSwap,RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+
+ dwords = w;
+
+ if((rop == GXcopy) && (planemask == ~0)) {
+ int address;
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_DISABLE, FBWriteMode);
+ Permedia2Sync(pScrn); /* we are not using the rasterizer */
+ while(h--) {
+ count = dwords;
+ address = (y * pScrn->displayWidth) + x;
+ srcp = (CARD32*)src;
+ GLINT_WAIT(1); /*??*/
+ GLINT_WRITE_REG(address, TextureDownloadOffset);
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x11 << 4) |
+ 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ address += pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x11 << 4) | 0x0D,
+ OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ y++;
+ }
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ } else {
+ if((skipleft = (long)src & 0x03L)) {
+ skipleft /= (bpp>>3);
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+
+ Permedia2SetClippingRectangle(pScrn,x+skipleft,y,x+w,y+h);
+
+ GLINT_WAIT(6);
+ Permedia2LoadCoord(pScrn, x, y, w, h);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ LOADROP(rop);
+ GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive |
+ SyncOnHostData, Render);
+
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+ }
+
+ Permedia2DisableClipping(pScrn);
+ SET_SYNC_FLAG(infoRec);
+}
diff --git a/src/pm2_dac.c b/src/pm2_dac.c
new file mode 100644
index 0000000..6df6e08
--- /dev/null
+++ b/src/pm2_dac.c
@@ -0,0 +1,506 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane <alanh@fairlite.demon.co.uk>
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Helmut Fahrion, <hf@suse.de>
+ * Michel Dänzer, <michdaen@iiic.ethz.ch>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm2_dac.c,v 1.26 2001/12/06 15:16:40 tsi Exp $ */
+
+#include "Xarch.h"
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+#define INITIALFREQERR 100000
+#define MINCLK 110000 /* VCO frequency range */
+#define MAXCLK 250000
+
+static unsigned long
+PM2DAC_CalculateMNPCForClock
+(
+ unsigned long reqclock, /* In kHz units */
+ unsigned long refclock, /* In kHz units */
+ unsigned char *rm, /* M Out */
+ unsigned char *rn, /* N Out */
+ unsigned char *rp /* P Out */
+ )
+{
+ unsigned char m, n, p;
+ unsigned long f;
+ long freqerr, lowestfreqerr = INITIALFREQERR;
+ unsigned long clock,actualclock = 0;
+
+ for (n = 2; n <= 14; n++) {
+ for (m = 2; m != 0; m++) { /* this is a char, so this counts to 255 */
+ f = refclock * m / n;
+ if ( (f < MINCLK) || (f > MAXCLK) )
+ continue;
+ for (p = 0; p <= 4; p++) {
+ clock = f >> p;
+ freqerr = reqclock - clock;
+ if (freqerr < 0)
+ freqerr = -freqerr;
+ if (freqerr < lowestfreqerr) {
+ *rn = n;
+ *rm = m;
+ *rp = p;
+ lowestfreqerr = freqerr;
+ actualclock = clock;
+#ifdef DEBUG
+ ErrorF("Best %ld diff %ld\n",actualclock,freqerr);
+#endif
+ }
+ }
+ }
+ }
+
+ return(actualclock);
+}
+
+Bool
+Permedia2Init(ScrnInfoPtr pScrn, DisplayModePtr mode)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTRegPtr pReg = &pGlint->ModeReg[0];
+ CARD32 temp1, temp2, temp3, temp4;
+
+ pReg->glintRegs[Aperture0 >> 3] = 0;
+ pReg->glintRegs[Aperture1 >> 3] = 0;
+ pReg->glintRegs[PMFramebufferWriteMask >> 3] = 0xFFFFFFFF;
+ pReg->glintRegs[PMBypassWriteMask >> 3] = 0xFFFFFFFF;
+
+ pReg->glintRegs[DFIFODis >> 3] = 0;
+ pReg->glintRegs[FIFODis >> 3] = 1;
+
+ if (pGlint->UseBlockWrite)
+ pReg->glintRegs[PMMemConfig >> 3] = GLINT_READ_REG(PMMemConfig) | 1<<21;
+
+
+ temp1 = mode->CrtcHSyncStart - mode->CrtcHDisplay;
+ temp2 = mode->CrtcVSyncStart - mode->CrtcVDisplay;
+ temp3 = mode->CrtcHSyncEnd - mode->CrtcHSyncStart;
+ temp4 = mode->CrtcVSyncEnd - mode->CrtcVSyncStart;
+
+ pReg->glintRegs[PMHTotal >> 3] = Shiftbpp(pScrn,mode->CrtcHTotal);
+ pReg->glintRegs[PMHsEnd >> 3] = Shiftbpp(pScrn, temp1 + temp3);
+ pReg->glintRegs[PMHsStart >> 3] = Shiftbpp(pScrn, temp1);
+ pReg->glintRegs[PMHbEnd >> 3] =
+ Shiftbpp(pScrn,mode->CrtcHTotal-mode->CrtcHDisplay);
+ pReg->glintRegs[PMScreenStride >> 3] =
+ Shiftbpp(pScrn,pScrn->displayWidth>>1);
+
+ pReg->glintRegs[PMVTotal >> 3] = mode->CrtcVTotal;
+ pReg->glintRegs[PMVsEnd >> 3] = temp2 + temp4;
+ pReg->glintRegs[PMVsStart >> 3] = temp2;
+ pReg->glintRegs[PMVbEnd >> 3] = mode->CrtcVTotal - mode->CrtcVDisplay;
+
+ /* The hw cursor needs /VSYNC to recognize vert retrace. We'll stick
+ both sync lines to active high here and if needed invert them
+ using the RAMDAC's MCR below. */
+ pReg->glintRegs[PMVideoControl >> 3] =
+ (1 << 5) | (1 << 3) | 1;
+
+ if (pScrn->bitsPerPixel > 8) {
+ /* When != 8bpp then we stick the RAMDAC into 64bit mode */
+ /* And reduce the horizontal timings by half */
+ pReg->glintRegs[PMVideoControl >> 3] |= 1<<16;
+ pReg->glintRegs[PMHTotal >> 3] >>= 1;
+ pReg->glintRegs[PMHsEnd >> 3] >>= 1;
+ pReg->glintRegs[PMHsStart >> 3] >>= 1;
+ pReg->glintRegs[PMHbEnd >> 3] >>= 1;
+ }
+
+ pReg->glintRegs[VClkCtl >> 3] = (GLINT_READ_REG(VClkCtl) & 0xFFFFFFFC);
+ pReg->glintRegs[PMScreenBase >> 3] = 0;
+ pReg->glintRegs[PMHTotal >> 3] -= 1;
+ pReg->glintRegs[PMHsStart >> 3] -= 1;
+ pReg->glintRegs[PMVTotal >> 3] -= 1;
+
+ pReg->glintRegs[ChipConfig >> 3] = GLINT_READ_REG(ChipConfig) & 0xFFFFFFDD;
+
+ pReg->DacRegs[PM2DACIndexMDCR] = 0x00; /* Disable Overlay */
+
+ {
+ /* Get the programmable clock values */
+ unsigned char m,n,p;
+ unsigned long clockused;
+
+ clockused = PM2DAC_CalculateMNPCForClock(mode->Clock,pGlint->RefClock,
+ &m,&n,&p);
+ pReg->DacRegs[PM2DACIndexClockAM] = m;
+ pReg->DacRegs[PM2DACIndexClockAN] = n;
+ pReg->DacRegs[PM2DACIndexClockAP] = p|0x08;
+ }
+
+ if (pScrn->rgbBits == 8)
+ pReg->DacRegs[PM2DACIndexMCR] = 0x02; /* 8bit DAC */
+ else
+ pReg->DacRegs[PM2DACIndexMCR] = 0x00; /* 6bit DAC */
+
+ if (!(mode->Flags & V_PHSYNC))
+ pReg->DacRegs[PM2DACIndexMCR] |= 0x04; /* invert hsync */
+ if (!(mode->Flags & V_PVSYNC))
+ pReg->DacRegs[PM2DACIndexMCR] |= 0x08; /* invert vsync */
+
+ switch (pScrn->bitsPerPixel)
+ {
+ case 8:
+ pReg->DacRegs[PM2DACIndexCMR] = PM2DAC_RGB | PM2DAC_GRAPHICS |
+ PM2DAC_CI8;
+ break;
+ case 16:
+ if (pScrn->depth == 15) {
+ pReg->DacRegs[PM2DACIndexCMR] = PM2DAC_RGB | PM2DAC_TRUECOLOR|
+ PM2DAC_GRAPHICS | PM2DAC_5551;
+ } else {
+ pReg->DacRegs[PM2DACIndexCMR] = PM2DAC_RGB | PM2DAC_TRUECOLOR|
+ PM2DAC_GRAPHICS | PM2DAC_565;
+ }
+ break;
+ case 24:
+ pReg->DacRegs[PM2DACIndexCMR] = PM2DAC_RGB | PM2DAC_TRUECOLOR|
+ PM2DAC_GRAPHICS | PM2DAC_PACKED;
+ break;
+ case 32:
+ pReg->DacRegs[PM2DACIndexCMR] = PM2DAC_RGB |
+ PM2DAC_GRAPHICS | PM2DAC_8888;
+ if (pScrn->overlayFlags & OVERLAY_8_32_PLANAR) {
+ pReg->DacRegs[PM2DACIndexColorKeyControl] = 0x11;
+ pReg->DacRegs[PM2DACIndexColorKeyOverlay] = pScrn->colorKey;
+ } else
+ pReg->DacRegs[PM2DACIndexCMR] |= PM2DAC_TRUECOLOR;
+ break;
+ }
+
+ return(TRUE);
+}
+
+void
+Permedia2Save(ScrnInfoPtr pScrn, GLINTRegPtr glintReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information using the slow routines */
+ xf86SlowBcopy((CARD8*)pGlint->FbBase, (CARD8*)pGlint->VGAdata, 65536);
+
+ glintReg->glintRegs[Aperture0 >> 3] = GLINT_READ_REG(Aperture0);
+ glintReg->glintRegs[Aperture1 >> 3] = GLINT_READ_REG(Aperture1);
+ glintReg->glintRegs[PMFramebufferWriteMask >> 3] =
+ GLINT_READ_REG(PMFramebufferWriteMask);
+ glintReg->glintRegs[PMBypassWriteMask >> 3] = GLINT_READ_REG(PMBypassWriteMask);
+ glintReg->glintRegs[DFIFODis >> 3] = GLINT_READ_REG(DFIFODis);
+ glintReg->glintRegs[FIFODis >> 3] = GLINT_READ_REG(FIFODis);
+ /* We only muck about with PMMemConfig, if user wants to */
+ if (pGlint->UseBlockWrite)
+ glintReg->glintRegs[PMMemConfig >> 3] = GLINT_READ_REG(PMMemConfig);
+ glintReg->glintRegs[PMHTotal >> 3] = GLINT_READ_REG(PMHTotal);
+ glintReg->glintRegs[PMHbEnd >> 3] = GLINT_READ_REG(PMHbEnd);
+ glintReg->glintRegs[PMHbEnd >> 3] = GLINT_READ_REG(PMHgEnd);
+ glintReg->glintRegs[PMScreenStride >> 3] = GLINT_READ_REG(PMScreenStride);
+ glintReg->glintRegs[PMHsStart >> 3] = GLINT_READ_REG(PMHsStart);
+ glintReg->glintRegs[PMHsEnd >> 3] = GLINT_READ_REG(PMHsEnd);
+ glintReg->glintRegs[PMVTotal >> 3] = GLINT_READ_REG(PMVTotal);
+ glintReg->glintRegs[PMVbEnd >> 3] = GLINT_READ_REG(PMVbEnd);
+ glintReg->glintRegs[PMVsStart >> 3] = GLINT_READ_REG(PMVsStart);
+ glintReg->glintRegs[PMVsEnd >> 3] = GLINT_READ_REG(PMVsEnd);
+ glintReg->glintRegs[PMScreenBase >> 3] = GLINT_READ_REG(PMScreenBase);
+ glintReg->glintRegs[PMVideoControl >> 3] = GLINT_READ_REG(PMVideoControl);
+ glintReg->glintRegs[VClkCtl >> 3] = GLINT_READ_REG(VClkCtl);
+ glintReg->glintRegs[ChipConfig >> 3] = GLINT_READ_REG(ChipConfig);
+
+ for (i=0;i<768;i++) {
+ Permedia2ReadAddress(pScrn, i);
+ glintReg->cmap[i] = Permedia2ReadData(pScrn);
+ }
+
+ glintReg->DacRegs[PM2DACIndexColorKeyOverlay] =
+ Permedia2InIndReg(pScrn, PM2DACIndexColorKeyOverlay);
+ glintReg->DacRegs[PM2DACIndexColorKeyControl] =
+ Permedia2InIndReg(pScrn, PM2DACIndexColorKeyControl);
+ glintReg->DacRegs[PM2DACIndexMCR] =
+ Permedia2InIndReg(pScrn, PM2DACIndexMCR);
+ glintReg->DacRegs[PM2DACIndexMDCR] =
+ Permedia2InIndReg(pScrn, PM2DACIndexMDCR);
+ glintReg->DacRegs[PM2DACIndexCMR] =
+ Permedia2InIndReg(pScrn, PM2DACIndexCMR);
+
+ glintReg->DacRegs[PM2DACIndexClockAM] =
+ Permedia2InIndReg(pScrn, PM2DACIndexClockAM);
+ glintReg->DacRegs[PM2DACIndexClockAN] =
+ Permedia2InIndReg(pScrn, PM2DACIndexClockAN);
+ glintReg->DacRegs[PM2DACIndexClockAP] =
+ Permedia2InIndReg(pScrn, PM2DACIndexClockAP);
+}
+
+void
+Permedia2Restore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information using the slow routines */
+ if (pGlint->STATE)
+ xf86SlowBcopy((CARD8*)pGlint->VGAdata, (CARD8*)pGlint->FbBase, 65536);
+
+#if 0
+ GLINT_SLOW_WRITE_REG(0, ResetStatus);
+ while(GLINT_READ_REG(ResetStatus) != 0) {
+ xf86MsgVerb(X_INFO, 2, "Resetting Engine - Please Wait.\n");
+ };
+#endif
+
+ GLINT_SLOW_WRITE_REG(0xFF, PM2DACReadMask);
+
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[Aperture0 >> 3], Aperture0);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[Aperture1 >> 3], Aperture1);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMFramebufferWriteMask >> 3],
+ PMFramebufferWriteMask);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMBypassWriteMask >> 3],
+ PMBypassWriteMask);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[DFIFODis >> 3], DFIFODis);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[FIFODis >> 3], FIFODis);
+ /* We only muck about with PMMemConfig, if user wants to */
+ if (pGlint->UseBlockWrite)
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMMemConfig >> 3],PMMemConfig);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVideoControl >> 3],
+ PMVideoControl);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHbEnd >> 3], PMHgEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMScreenBase >> 3], PMScreenBase);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[VClkCtl >> 3], VClkCtl);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMScreenStride >> 3],
+ PMScreenStride);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHTotal >> 3], PMHTotal);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHbEnd >> 3], PMHbEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHsStart >> 3], PMHsStart);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHsEnd >> 3], PMHsEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVTotal >> 3], PMVTotal);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVbEnd >> 3], PMVbEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVsStart >> 3], PMVsStart);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVsEnd >> 3], PMVsEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[ChipConfig >> 3], ChipConfig);
+
+ Permedia2OutIndReg(pScrn, PM2DACIndexColorKeyOverlay, 0x00,
+ glintReg->DacRegs[PM2DACIndexColorKeyOverlay]);
+ Permedia2OutIndReg(pScrn, PM2DACIndexColorKeyControl, 0x00,
+ glintReg->DacRegs[PM2DACIndexColorKeyControl]);
+ Permedia2OutIndReg(pScrn, PM2DACIndexMCR, 0x00,
+ glintReg->DacRegs[PM2DACIndexMCR]);
+ Permedia2OutIndReg(pScrn, PM2DACIndexMDCR, 0x00,
+ glintReg->DacRegs[PM2DACIndexMDCR]);
+ Permedia2OutIndReg(pScrn, PM2DACIndexCMR, 0x00,
+ glintReg->DacRegs[PM2DACIndexCMR]);
+
+ Permedia2OutIndReg(pScrn, PM2DACIndexClockAM, 0x00,
+ glintReg->DacRegs[PM2DACIndexClockAM]);
+ Permedia2OutIndReg(pScrn, PM2DACIndexClockAN, 0x00,
+ glintReg->DacRegs[PM2DACIndexClockAN]);
+ Permedia2OutIndReg(pScrn, PM2DACIndexClockAP, 0x00,
+ glintReg->DacRegs[PM2DACIndexClockAP]);
+
+ for (i=0;i<768;i++) {
+ Permedia2WriteAddress(pScrn, i);
+ Permedia2WriteData(pScrn, glintReg->cmap[i]);
+ }
+}
+
+static void
+Permedia2ShowCursor(ScrnInfoPtr pScrn)
+{
+ /* Enable cursor - X11 mode */
+ Permedia2OutIndReg(pScrn, PM2DACCursorControl, 0x00, 0x43);
+}
+
+static void
+Permedia2HideCursor(ScrnInfoPtr pScrn)
+{
+ /* Disable cursor */
+ Permedia2OutIndReg(pScrn, PM2DACCursorControl, 0x00, 0x00);
+}
+
+static void
+Permedia2LoadCursorImage(
+ ScrnInfoPtr pScrn,
+ unsigned char *src
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ GLINT_SLOW_WRITE_REG(0x00, PM2DACWriteAddress);
+ for (i=0; i<1024; i++) {
+ GLINT_SLOW_WRITE_REG(*(src++), PM2DACCursorData);
+ }
+}
+
+static void
+Permedia2SetCursorPosition(
+ ScrnInfoPtr pScrn,
+ int x, int y
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ x += 64;
+ y += 64;
+
+ /* Output position - "only" 11 bits of location documented */
+
+ GLINT_WRITE_REG(x & 0xFF, PM2DACCursorXLsb);
+ GLINT_WRITE_REG((x>>8) & 0x07, PM2DACCursorXMsb);
+ GLINT_WRITE_REG(y & 0xFF, PM2DACCursorYLsb);
+ GLINT_WRITE_REG((y>>8) & 0x07, PM2DACCursorYMsb);
+}
+
+static void
+Permedia2SetCursorColors(
+ ScrnInfoPtr pScrn,
+ int bg, int fg
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ /* The Permedia2 cursor is always 8 bits so shift 8, not 10 */
+
+ GLINT_SLOW_WRITE_REG(1, PM2DACCursorColorAddress);
+ /* Background color */
+ GLINT_SLOW_WRITE_REG(bg >> 0, PM2DACCursorColorData);
+ GLINT_SLOW_WRITE_REG(bg >> 8, PM2DACCursorColorData);
+ GLINT_SLOW_WRITE_REG(bg >> 16, PM2DACCursorColorData);
+
+ /* Foreground color */
+ GLINT_SLOW_WRITE_REG(fg >> 0, PM2DACCursorColorData);
+ GLINT_SLOW_WRITE_REG(fg >> 8, PM2DACCursorColorData);
+ GLINT_SLOW_WRITE_REG(fg >> 16, PM2DACCursorColorData);
+}
+
+static Bool
+Permedia2UseHWCursor(ScreenPtr pScr, CursorPtr pCurs)
+{
+ return TRUE;
+}
+
+Bool
+Permedia2HWCursorInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ xf86CursorInfoPtr infoPtr;
+
+ infoPtr = xf86CreateCursorInfoRec();
+ if(!infoPtr) return FALSE;
+
+ pGlint->CursorInfoRec = infoPtr;
+
+ infoPtr->MaxWidth = 64;
+ infoPtr->MaxHeight = 64;
+ infoPtr->Flags = HARDWARE_CURSOR_TRUECOLOR_AT_8BPP |
+#if X_BYTE_ORDER == X_LITTLE_ENDIAN
+ HARDWARE_CURSOR_BIT_ORDER_MSBFIRST |
+#endif
+ HARDWARE_CURSOR_SOURCE_MASK_NOT_INTERLEAVED;
+ infoPtr->SetCursorColors = Permedia2SetCursorColors;
+ infoPtr->SetCursorPosition = Permedia2SetCursorPosition;
+ infoPtr->LoadCursorImage = Permedia2LoadCursorImage;
+ infoPtr->HideCursor = Permedia2HideCursor;
+ infoPtr->ShowCursor = Permedia2ShowCursor;
+ infoPtr->UseHWCursor = Permedia2UseHWCursor;
+
+ return(xf86InitCursor(pScreen, infoPtr));
+}
+
+/* I2C Functions */
+
+void
+Permedia2I2CUDelay(I2CBusPtr b, int usec)
+{
+ GLINTPtr pGlint = (GLINTPtr) b->DriverPrivate.ptr;
+ CARD32 ct1 = GLINT_READ_REG(PMCount);
+ CARD32 ct2 = usec * 100;
+
+ if (GLINT_READ_REG(PMCount) != ct1)
+ while ((GLINT_READ_REG(PMCount) - ct1) < ct2);
+}
+
+void
+Permedia2I2CPutBits(I2CBusPtr b, int scl, int sda)
+{
+ GLINTPtr pGlint = (GLINTPtr) b->DriverPrivate.ptr;
+ int r = (pGlint->DDCBus == b) ? PMDDCData : VSSerialBusControl;
+ CARD32 v = GLINT_READ_REG(r) & ~(ClkOut | DataOut);
+
+ if (scl > 0) v |= ClkOut;
+ if (sda > 0) v |= DataOut;
+
+ GLINT_WRITE_REG(v, r);
+}
+
+void
+Permedia2I2CGetBits(I2CBusPtr b, int *scl, int *sda)
+{
+ GLINTPtr pGlint = (GLINTPtr) b->DriverPrivate.ptr;
+ CARD32 v = GLINT_READ_REG((pGlint->DDCBus == b) ?
+ PMDDCData : VSSerialBusControl);
+
+ *scl = (v & ClkIn) > 0;
+ *sda = (v & DataIn) > 0;
+}
+
+void
+Permedia2PreInit(ScrnInfoPtr pScrn)
+{
+#if defined(__alpha__)
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /*
+ * On Alpha, we have to init secondary PM2 cards, since
+ * int10 cannot be run on the OEMed cards with VGA disable
+ * jumpers.
+ */
+ if (!xf86IsPrimaryPci(pGlint->PciInfo)) {
+ if ( IS_GLORIASYNERGY ) {
+
+ /* PM2DAC_CalculateMNPCForClock(80000, 14318, &m, &n, &p); */
+ Permedia2OutIndReg(pScrn, PM2DACIndexMemClockM, 0x00, 0x7b);
+ Permedia2OutIndReg(pScrn, PM2DACIndexMemClockN, 0x00, 0x0b);
+ Permedia2OutIndReg(pScrn, PM2DACIndexMemClockP, 0x00, 0x09);
+
+ GLINT_SLOW_WRITE_REG( 0x20, PMBootAddress);
+ GLINT_SLOW_WRITE_REG( 0xe6002021, PMMemConfig);
+ }
+ }
+#endif /* __alpha__ */
+}
diff --git a/src/pm2_video.c b/src/pm2_video.c
new file mode 100644
index 0000000..869906e
--- /dev/null
+++ b/src/pm2_video.c
@@ -0,0 +1,3204 @@
+/*
+ * Permedia 2 Xv Driver
+ *
+ * Copyright (C) 1998-2000 Michael H. Schimek <m.schimek@netway.at>
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ */
+
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm2_video.c,v 1.23 2002/12/02 22:52:30 tsi Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+#include "xf86Pci.h"
+#include "xf86PciInfo.h"
+#include "xf86fbman.h"
+#include "xf86i2c.h"
+#include "xf86xv.h"
+#include "Xv.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+#ifndef XvExtension
+
+void Permedia2VideoInit(ScreenPtr pScreen) {}
+void Permedia2VideoUninit(ScrnInfoPtr pScrn) {}
+void Permedia2VideoEnterVT(ScrnInfoPtr pScrn) {}
+void Permedia2VideoLeaveVT(ScrnInfoPtr pScrn) {}
+
+#else
+
+#undef MIN
+#undef ABS
+#undef CLAMP
+#undef ENTRIES
+
+#define MIN(a, b) (((a) < (b)) ? (a) : (b))
+#define ABS(n) (((n) < 0) ? -(n) : (n))
+#define CLAMP(v, min, max) (((v) < (min)) ? (min) : MIN(v, max))
+#define ENTRIES(array) (sizeof(array) / sizeof((array)[0]))
+
+#define ADAPTORS 3
+#define PORTS 6
+
+#define PCI_SUBSYSTEM_ID_WINNER_2000_P2C 0x0a311048
+#define PCI_SUBSYSTEM_ID_GLORIA_SYNERGY_P2C 0x0a321048
+#define PCI_SUBSYSTEM_ID_GLORIA_SYNERGY_P2A 0x0a351048
+#define PCI_SUBSYSTEM_ID_WINNER_2000_P2A 0x0a441048
+
+/*
+ * Proprietary kernel backbone interface
+ */
+
+#define XVIPC_MAGIC 0x6A5D70E6
+#define XVIPC_VERSION 1
+#define VIDIOC_PM2_XVIPC 0x00007F7F
+
+typedef enum {
+ OP_ATTR = 0,
+ OP_RESET = 8, /* unused */
+ OP_START,
+ OP_STOP,
+ OP_PLUG,
+ OP_VIDEOSTD,
+ OP_WINDOW, /* unused */
+ OP_CONNECT,
+ OP_EVENT,
+ OP_ALLOC,
+ OP_FREE,
+ OP_UPDATE,
+ OP_NOP, /* ignored */
+ OP_ENTER,
+ OP_LEAVE,
+ OP_DISCONNECT
+} xvipc_op;
+
+typedef struct _pm2_xvipc {
+ int magic;
+ void *pm2p, *pAPriv;
+ int port, op, time, block;
+ int a, b, c, d, e, f;
+} pm2_xvipc;
+
+static pm2_xvipc xvipc;
+static int xvipc_fd = -1;
+
+
+#define MAX_BUFFERS 2
+
+typedef struct {
+ CARD32 xy, wh; /* 16.0 16.0 */
+ INT32 s, t; /* 12.20 fp */
+ short y1, y2;
+} CookieRec, *CookiePtr;
+
+typedef struct _PortPrivRec {
+ struct _AdaptorPrivRec * pAdaptor;
+ I2CDevRec I2CDev;
+
+ INT32 Attribute[8]; /* Brig, Con, Sat, Hue, Int, Filt, BkgCol, Alpha */
+
+ int BuffersRequested;
+ int BuffersAllocated;
+ FBAreaPtr pFBArea[MAX_BUFFERS];
+ CARD32 BufferBase[MAX_BUFFERS]; /* FB byte offset */
+ CARD32 BufferStride; /* bytes */
+ CARD32 BufferPProd; /* PProd(BufferStride in buffer pixels) */
+
+ INT32 vx, vy, vw, vh; /* 12.10 fp */
+ int dx, dy, dw, dh;
+ int fw, fh;
+
+ CookiePtr pCookies;
+ int nCookies;
+ INT32 dS, dT; /* 12.20 fp */
+
+ int Id, Bpp; /* Scaler */
+
+ int Plug;
+ int BkgCol; /* RGB 5:6:5; 5:6:5 */
+ Bool StreamOn; /* buffer <-> hardware */
+ int VideoOn; /* buffer <-> screen */
+ int VideoStdReq;
+
+ int StopDelay;
+
+ int FramesPerSec, FrameAcc;
+
+} PortPrivRec, *PortPrivPtr;
+
+enum { VIDEO_OFF, VIDEO_ONE_SHOT, VIDEO_ON };
+
+typedef struct _LFBAreaRec {
+ struct _LFBAreaRec * Next;
+ int Linear;
+ FBAreaPtr pFBArea;
+} LFBAreaRec, *LFBAreaPtr;
+
+typedef struct _AdaptorPrivRec {
+ struct _AdaptorPrivRec * Next;
+ ScrnInfoPtr pScrn;
+
+ void * pm2p;
+ LFBAreaPtr LFBList;
+
+ CARD32 dFifoControl;
+ CARD32 dDitherMode;
+ CARD32 dAlphaBlendMode;
+ CARD32 dTextureDataFormat;
+
+ OsTimerPtr Timer;
+ int TimerUsers;
+ int Delay, Instant;
+
+ int FramesPerSec;
+ int FrameLines;
+ int IntLine; /* Frame, not field */
+ int LinePer; /* nsec */
+
+ Bool VideoIO;
+ int VideoStd;
+
+ PortPrivRec Port[PORTS];
+
+} AdaptorPrivRec, *AdaptorPrivPtr;
+
+static AdaptorPrivPtr AdaptorPrivList = NULL;
+
+#define FreeCookies(pPPriv) \
+do { \
+ if ((pPPriv)->pCookies) { \
+ xfree((pPPriv)->pCookies); \
+ (pPPriv)->pCookies = NULL; \
+ } \
+} while (0)
+
+#define PORTNUM(p) ((int)((p) - &pAPriv->Port[0]))
+#define BPPSHIFT(g) (2 - (g)->BppShift) /* Bytes per pixel = 1 << BPPSHIFT(pGlint) */
+
+#define DEBUG(x)
+
+static const Bool ColorBars = FALSE;
+
+
+/*
+ * XF86Config VideoAdaptor options
+ */
+
+typedef enum {
+ OPTION_DEVICE,
+ OPTION_FPS,
+ OPTION_BUFFERS,
+ OPTION_ENCODING,
+ OPTION_EXPOSE /* obsolete, ignored */
+} OptToken;
+
+/* XXX These should be made const, and per-screen/adaptor copies processed. */
+static OptionInfoRec AdaptorOptions[] = {
+ { OPTION_DEVICE, "Device", OPTV_STRING, {0}, FALSE },
+ { -1, NULL, OPTV_NONE, {0}, FALSE }
+};
+static OptionInfoRec InputOptions[] = {
+ { OPTION_BUFFERS, "Buffers", OPTV_INTEGER, {0}, FALSE },
+ { OPTION_FPS, "FramesPerSec", OPTV_INTEGER, {0}, FALSE },
+ { OPTION_ENCODING, "Encoding", OPTV_STRING, {0}, FALSE },
+ { -1, NULL, OPTV_NONE, {0}, FALSE }
+};
+static OptionInfoRec OutputOptions[] = {
+ { OPTION_BUFFERS, "Buffers", OPTV_INTEGER, {0}, FALSE },
+ { OPTION_EXPOSE, "Expose", OPTV_BOOLEAN, {0}, FALSE },
+ { OPTION_FPS, "FramesPerSec", OPTV_INTEGER, {0}, FALSE },
+ { OPTION_ENCODING, "Encoding", OPTV_STRING, {0}, FALSE },
+ { -1, NULL, OPTV_NONE, {0}, FALSE }
+};
+
+
+/*
+ * Attributes
+ */
+
+#define XV_ENCODING "XV_ENCODING"
+#define XV_BRIGHTNESS "XV_BRIGHTNESS"
+#define XV_CONTRAST "XV_CONTRAST"
+#define XV_SATURATION "XV_SATURATION"
+#define XV_HUE "XV_HUE"
+
+/* Proprietary */
+
+#define XV_INTERLACE "XV_INTERLACE" /* Interlaced (bool) */
+#define XV_FILTER "XV_FILTER" /* Bilinear filter (bool) */
+#define XV_BKGCOLOR "XV_BKGCOLOR" /* Output background (0x00RRGGBB) */
+#define XV_ALPHA "XV_ALPHA" /* Scaler alpha channel (bool) */
+
+#define MAKE_ATOM(a) MakeAtom(a, sizeof(a) - 1, TRUE)
+
+static Atom xvEncoding, xvBrightness, xvContrast, xvSaturation, xvHue;
+static Atom xvInterlace, xvFilter, xvBkgColor, xvAlpha;
+
+/* Input */
+
+static XF86VideoEncodingRec
+InputVideoEncodings[] =
+{
+ { 0, "pal-composite", 704, 576, { 1, 50 }},
+ { 1, "pal-composite_adaptor", 704, 576, { 1, 50 }},
+ { 2, "pal-svideo", 704, 576, { 1, 50 }},
+ { 3, "ntsc-composite", 704, 480, { 1001, 60000 }},
+ { 4, "ntsc-composite_adaptor", 704, 480, { 1001, 60000 }},
+ { 5, "ntsc-svideo", 704, 480, { 1001, 60000 }},
+ { 6, "secam-composite", 704, 576, { 1, 50 }},
+ { 7, "secam-composite_adaptor", 704, 576, { 1, 50 }},
+ { 8, "secam-svideo", 704, 576, { 1, 50 }},
+};
+
+static XF86AttributeRec
+InputVideoAttributes[] =
+{
+ { XvSettable | XvGettable, -1000, +1000, XV_BRIGHTNESS },
+ { XvSettable | XvGettable, -3000, +1000, XV_CONTRAST },
+ { XvSettable | XvGettable, -3000, +1000, XV_SATURATION },
+ { XvSettable | XvGettable, -1000, +1000, XV_HUE },
+ { XvSettable | XvGettable, 0, 2, XV_INTERLACE },
+ { XvSettable | XvGettable, 0, 1, XV_FILTER },
+};
+
+static XF86VideoFormatRec
+InputVideoFormats[] =
+{
+ { 8, TrueColor }, /* Dithered */
+ { 15, TrueColor },
+ { 16, TrueColor },
+ { 24, TrueColor },
+};
+
+/* Output */
+
+static XF86VideoEncodingRec
+OutputVideoEncodings[] =
+{
+ { 0, "pal-composite_adaptor", 704, 576, { 1, 50 }},
+ { 1, "pal-svideo", 704, 576, { 1, 50 }},
+ { 2, "ntsc-composite_adaptor", 704, 480, { 1001, 60000 }},
+ { 3, "ntsc-svideo", 704, 480, { 1001, 60000 }},
+};
+
+static XF86AttributeRec
+OutputVideoAttributes[] =
+{
+ { XvSettable | XvGettable, 0, 2, XV_INTERLACE },
+ { XvSettable | XvGettable, 0, 1, XV_FILTER },
+ { XvSettable | XvGettable, 0x000000, 0xFFFFFF, XV_BKGCOLOR },
+};
+
+static XF86VideoFormatRec
+OutputVideoFormats[] =
+{
+ { 8, TrueColor },
+ { 8, PseudoColor }, /* Using .. */
+ { 8, StaticColor },
+ { 8, GrayScale },
+ { 8, StaticGray }, /* .. TexelLUT */
+ { 15, TrueColor },
+ { 16, TrueColor },
+ { 24, TrueColor },
+};
+
+/* Scaler */
+
+static XF86VideoEncodingRec
+ScalerEncodings[] =
+{
+ { 0, "XV_IMAGE", 2047, 2047, { 1, 1 }},
+};
+
+static XF86AttributeRec
+ScalerAttributes[] =
+{
+ { XvSettable | XvGettable, 0, 1, XV_FILTER },
+ { XvSettable | XvGettable, 0, 1, XV_ALPHA },
+};
+
+#define ScalerVideoFormats InputVideoFormats
+
+/*
+ * FOURCC from http://www.webartz.com/fourcc
+ * Generic GUID for legacy FOURCC XXXXXXXX-0000-0010-8000-00AA00389B71
+ */
+#define LE4CC(a,b,c,d) (((CARD32)(a)&0xFF)|(((CARD32)(b)&0xFF)<<8)|(((CARD32)(c)&0xFF)<<16)|(((CARD32)(d)&0xFF)<<24))
+#define GUID4CC(a,b,c,d) { a,b,c,d,0,0,0,0x10,0x80,0,0,0xAA,0,0x38,0x9B,0x71 }
+
+#define NoOrder LSBFirst
+
+static XF86ImageRec
+ScalerImages[] =
+{
+ /* Planar YVU 4:2:0 (emulated) */
+ { LE4CC('Y','V','1','2'), XvYUV, NoOrder, GUID4CC('Y','V','1','2'),
+ 12, XvPlanar, 3, 0, 0, 0, 0,
+ 8, 8, 8, 1, 2, 2, 1, 2, 2, "YVU", XvTopToBottom },
+
+ /* Packed YUYV 4:2:2 */
+ { LE4CC('Y','U','Y','2'), XvYUV, NoOrder, GUID4CC('Y','U','Y','2'),
+ 16, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 2, 2, 1, 1, 1, "YUYV", XvTopToBottom },
+
+ /* Packed UYVY 4:2:2 */
+ { LE4CC('U','Y','V','Y'), XvYUV, NoOrder, GUID4CC('U','Y','V','Y'),
+ 16, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 2, 2, 1, 1, 1, "UYVY", XvTopToBottom },
+
+ /* Packed YUVA 4:4:4 */
+ { LE4CC('Y','U','V','A') /* XXX not registered */, XvYUV, LSBFirst, { 0 },
+ 32, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 1, 1, 1, 1, 1, "YUVA", XvTopToBottom },
+
+ /* Packed VUYA 4:4:4 */
+ { LE4CC('V','U','Y','A') /* XXX not registered */, XvYUV, LSBFirst, { 0 },
+ 32, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 1, 1, 1, 1, 1, "VUYA", XvTopToBottom },
+
+ /* RGBA 8:8:8:8 */
+ { 0x41, XvRGB, LSBFirst, { 0 },
+ 32, XvPacked, 1, 24, 0x0000FF, 0x00FF00, 0xFF0000,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGB 5:6:5 */
+ { 0x42, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 16, 0x001F, 0x07E0, 0xF800,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGB", XvTopToBottom },
+
+ /* RGBA 5:5:5:1 */
+ { 0x43, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 15, 0x001F, 0x03E0, 0x7C00,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGBA 4:4:4:4 */
+ { 0x44, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 12, 0x000F, 0x00F0, 0x0F00,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGBA 2:3:2:1 */
+ { 0x45, XvRGB, NoOrder, { 0 },
+ 8, XvPacked, 1, 7, 0x03, 0x1C, 0x60,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGB 3:3:2 */
+ { 0x46, XvRGB, NoOrder, { 0 },
+ 8, XvPacked, 1, 8, 0x07, 0x38, 0xC0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGB", XvTopToBottom },
+
+ /* BGRA 8:8:8:8 */
+ { 0x47, XvRGB, LSBFirst, { 0 },
+ 32, XvPacked, 1, 24, 0xFF0000, 0x00FF00, 0x0000FF,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGR 5:6:5 */
+ { 0x48, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 16, 0xF800, 0x07E0, 0x001F,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGR", XvTopToBottom },
+
+ /* BGRA 5:5:5:1 */
+ { 0x49, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 15, 0x7C00, 0x03E0, 0x001F,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGRA 4:4:4:4 */
+ { 0x4A, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 12, 0x0F00, 0x00F0, 0x000F,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGRA 2:3:2:1 */
+ { 0x4B, XvRGB, NoOrder, { 0 },
+ 8, XvPacked, 1, 7, 0x60, 0x1C, 0x03,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGR 2:3:3 */
+ { 0x4C, XvRGB, NoOrder, { 0 },
+ 8, XvPacked, 1, 8, 0xC0, 0x38, 0x07,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGR", XvTopToBottom },
+};
+
+
+/*
+ * Video codec tables
+ */
+
+#define SAA7111_SLAVE_ADDRESS 0x48
+#define SAA7125_SLAVE_ADDRESS 0x88
+
+static I2CByte
+DecInitVec[] =
+{
+ 0x11, 0x00,
+ 0x02, 0xC1, 0x03, 0x00, 0x04, 0x00, 0x05, 0x00,
+ 0x06, 0x00, 0x07, 0x00, 0x08, 0x00, 0x09, 0x4A,
+ 0x0A, 0x80, 0x0B, 0x40, 0x0C, 0x40, 0x0D, 0x00,
+ 0x0E, 0x01, 0x10, 0xC8, 0x12, 0x20,
+ 0x13, 0x00, 0x15, 0x00, 0x16, 0x00, 0x17, 0x00,
+};
+
+static I2CByte
+EncInitVec[] =
+{
+ 0x3A, 0x83, 0x61, 0xC2,
+ 0x5A, 119, 0x5B, 0x7D,
+ 0x5C, 0xAF, 0x5D, 0x3C, 0x5E, 0x3F, 0x5F, 0x3F,
+ 0x60, 0x70, 0x62, 0x4B, 0x67, 0x00,
+ 0x68, 0x00, 0x69, 0x00, 0x6A, 0x00, 0x6B, 0x20,
+ 0x6C, 0x03, 0x6D, 0x30, 0x6E, 0xA0, 0x6F, 0x00,
+ 0x70, 0x80, 0x71, 0xE8, 0x72, 0x10,
+ 0x7A, 0x13, 0x7B, 0xFB, 0x7C, 0x00, 0x7D, 0x00,
+};
+
+static I2CByte Dec02[3] = { 0xC1, 0xC0, 0xC4 };
+static I2CByte Dec09[3] = { 0x4A, 0x4A, 0xCA };
+static I2CByte Enc3A[3] = { 0x03, 0x03, 0x23 };
+static I2CByte Enc61[3] = { 0x06, 0x01, 0xC2 };
+
+static I2CByte
+DecVS[3][8] =
+{
+ { 0x06, 108, 0x07, 108, 0x08, 0x09, 0x0E, 0x01 },
+ { 0x06, 107, 0x07, 107, 0x08, 0x49, 0x0E, 0x01 },
+ { 0x06, 108, 0x07, 108, 0x08, 0x01, 0x0E, 0x51 }
+};
+
+#define FSC(n) ((CARD32)((n) / 27e6 * 4294967296.0 + .5))
+#define SUBCARRIER_FREQ_PAL (4.433619e6)
+#define SUBCARRIER_FREQ_NTSC (3.579545e6)
+
+static I2CByte
+EncVS[2][14] =
+{
+ { 0x62, 0x4B, 0x6B, 0x28, 0x6E, 0xA0,
+ 0x63, (I2CByte)(FSC(SUBCARRIER_FREQ_PAL) >> 0),
+ 0x64, (I2CByte)(FSC(SUBCARRIER_FREQ_PAL) >> 8),
+ 0x65, (I2CByte)(FSC(SUBCARRIER_FREQ_PAL) >> 16),
+ 0x66, (I2CByte)(FSC(SUBCARRIER_FREQ_PAL) >> 24) },
+ { 0x62, 0x6A, 0x6B, 0x20, 0x6E, 0x20,
+ 0x63, (I2CByte)(FSC(SUBCARRIER_FREQ_NTSC) >> 0),
+ 0x64, (I2CByte)(FSC(SUBCARRIER_FREQ_NTSC) >> 8),
+ 0x65, (I2CByte)(FSC(SUBCARRIER_FREQ_NTSC) >> 16),
+ 0x66, (I2CByte)(FSC(SUBCARRIER_FREQ_NTSC) >> 24) }
+};
+
+/* Forward */
+static void StopVideoStream(PortPrivPtr pPPriv, Bool shutdown);
+static void RestoreVideoStd(AdaptorPrivPtr pAPriv);
+static Bool xvipcHandshake(PortPrivPtr pPPriv, int op, Bool block);
+
+
+/*
+ * Video codec controls
+ */
+
+static int
+SetAttr(PortPrivPtr pPPriv, int i, int value)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int v;
+
+ if (value < InputVideoAttributes[i].min_value)
+ value = InputVideoAttributes[i].min_value;
+ else
+ if (value > InputVideoAttributes[i].max_value)
+ value = InputVideoAttributes[i].max_value;
+
+ switch (i) {
+ case 0:
+ v = 128 + (MIN(value, 999) * 128) / 1000;
+ break;
+
+ case 1:
+ case 2:
+ v = 64 + (MIN(value, 999) * 64) / 1000;
+ break;
+
+ default:
+ v = (MIN(value, 999) * 128) / 1000;
+ break;
+ }
+
+ if (pAPriv->pm2p) {
+ xvipc.a = v << 8;
+
+ if (!xvipcHandshake(pPPriv, OP_ATTR + i, TRUE))
+ return XvBadAlloc;
+ } else
+ if (!xf86I2CWriteByte(&pPPriv->I2CDev, 0x0A + i, v))
+ return XvBadAlloc;
+
+ pPPriv->Attribute[i] = value;
+
+ return Success;
+}
+
+static int
+SetPlug(PortPrivPtr pPPriv, int Plug)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+
+ if (pAPriv->pm2p) {
+ xvipc.a = Plug - (pPPriv == &pAPriv->Port[1]);
+
+ if (!xvipcHandshake(pPPriv, OP_PLUG, TRUE))
+ return XvBadAlloc;
+ } else {
+ if (pPPriv == &pAPriv->Port[0]) {
+ if (!xf86I2CWriteByte(&pPPriv->I2CDev, 0x02, Dec02[Plug]) ||
+ !xf86I2CWriteByte(&pPPriv->I2CDev, 0x09, Dec09[Plug]))
+ return XvBadAlloc;
+ } else {
+ if (pPPriv->StreamOn) {
+ if (!xf86I2CWriteByte(&pPPriv->I2CDev, 0x3A, Enc3A[Plug]))
+ return XvBadAlloc;
+ } else
+ if (ColorBars)
+ xf86I2CWriteByte(&pPPriv->I2CDev, 0x3A, 0x83);
+ }
+ }
+
+ pPPriv->Plug = Plug;
+
+ return Success;
+}
+
+enum { PAL, NTSC, SECAM };
+
+static int
+SetVideoStd(PortPrivPtr pPPriv, int VideoStd)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int r = Success;
+
+ if (pAPriv->pm2p) {
+ xvipc.a = VideoStd;
+
+ if (!xvipcHandshake(&pAPriv->Port[0], OP_VIDEOSTD, TRUE))
+ return XvBadAlloc;
+
+ VideoStd = xvipc.a; /* Actual */
+ } else {
+ if (VideoStd == SECAM)
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x61, 0xC2);
+ /* Disable output, SECAM not supported */
+
+ if (!xf86I2CWriteVec(&pAPriv->Port[0].I2CDev, &DecVS[VideoStd][0], 4)) {
+ pAPriv->VideoStd = -1;
+ return XvBadAlloc;
+ }
+
+ if (VideoStd != SECAM)
+ if (!xf86I2CWriteVec(&pAPriv->Port[1].I2CDev, &EncVS[VideoStd][0], 7)) {
+ pAPriv->VideoStd = -1;
+ return XvBadAlloc;
+ }
+ }
+
+ pAPriv->VideoStd = VideoStd;
+ pPPriv->VideoStdReq = VideoStd;
+
+ if (VideoStd == NTSC) {
+ pAPriv->FramesPerSec = 30;
+ pAPriv->FrameLines = 525;
+ pAPriv->IntLine = 513;
+ pAPriv->LinePer = 63555;
+ } else {
+ pAPriv->FramesPerSec = 25;
+ pAPriv->FrameLines = 625;
+ pAPriv->IntLine = 613;
+ pAPriv->LinePer = 64000;
+ }
+
+#if 0 /* XF86Config option */
+
+ pAPriv->Port[0].FramesPerSec = pAPriv->FramesPerSec;
+ pAPriv->Port[1].FramesPerSec = pAPriv->FramesPerSec;
+
+#endif
+
+ return r;
+}
+
+
+/*
+ * Buffer management
+ */
+
+static void
+RemoveAreaCallback(FBAreaPtr pFBArea)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) pFBArea->devPrivate.ptr;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ DEBUG(ScrnInfoPtr pScrn = pAPriv->pScrn;)
+ int i;
+
+ for (i = 0; i < MAX_BUFFERS && pPPriv->pFBArea[i] != pFBArea; i++);
+
+ if (i >= MAX_BUFFERS)
+ return;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 4,
+ "RemoveAreaCallback port #%d, buffer #%d, pFB=%p, off=0x%08x\n",
+ PORTNUM(pPPriv), i, pPPriv->pFBArea[i], pPPriv->BufferBase[i]));
+
+ if (pAPriv->VideoIO && PORTNUM(pPPriv) < 2) {
+ StopVideoStream(pPPriv, FALSE);
+ }
+
+ for (; i < MAX_BUFFERS - 1; i++)
+ pPPriv->pFBArea[i] = pPPriv->pFBArea[i + 1];
+
+ pPPriv->pFBArea[MAX_BUFFERS - 1] = NULL;
+
+ pPPriv->BuffersAllocated--;
+}
+
+static void
+RemoveableBuffers(PortPrivPtr pPPriv, Bool remove)
+{
+ int i;
+
+ for (i = 0; i < MAX_BUFFERS; i++)
+ if (pPPriv->pFBArea[i])
+ pPPriv->pFBArea[i]->RemoveAreaCallback =
+ remove ? RemoveAreaCallback : NULL;
+}
+
+static void
+FreeBuffers(PortPrivPtr pPPriv)
+{
+ DEBUG(AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;)
+ DEBUG(ScrnInfoPtr pScrn = pAPriv->pScrn;)
+ int i;
+
+ RemoveableBuffers(pPPriv, FALSE);
+
+ for (i = MAX_BUFFERS - 1; i >= 0; i--)
+ if (pPPriv->pFBArea[i]) {
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 4,
+ "FreeBuffers port #%d, buffer #%d, pFB=%p, off=0x%08x\n",
+ PORTNUM(pPPriv), i, pPPriv->pFBArea[i], pPPriv->BufferBase[i]));
+
+ xf86FreeOffscreenArea(pPPriv->pFBArea[i]);
+
+ pPPriv->pFBArea[i] = NULL;
+ }
+
+ pPPriv->BuffersAllocated = 0;
+}
+
+enum { FORCE_LINEAR = 1, FORCE_RECT };
+
+static int
+AllocateBuffers(PortPrivPtr pPPriv,
+ int w, int h, int bytespp,
+ int num, int force)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ ScrnInfoPtr pScrn = pAPriv->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ Bool linear = (force != FORCE_RECT);
+ int i, j, retry = 0;
+
+ FreeBuffers(pPPriv);
+
+ for (i = 0; i < num; i++) {
+ if (linear) {
+ for (j = (w + 31) >> 5; partprodPermedia[j] < 0; j++);
+
+ pPPriv->BufferStride = j * bytespp * 32;
+ pPPriv->BufferPProd = partprodPermedia[j];
+
+ pPPriv->pFBArea[i] = xf86AllocateLinearOffscreenArea(pScrn->pScreen,
+ (pPPriv->BufferStride * h + (1 << BPPSHIFT(pGlint)) - 1) >> BPPSHIFT(pGlint),
+ 8 >> BPPSHIFT(pGlint), NULL, NULL, (pointer) pPPriv);
+
+ if (pPPriv->pFBArea[i])
+ /* pPPriv->BufferBase[i] = pPPriv->pFBArea[i].linear; */
+ pPPriv->BufferBase[i] =
+ ((pPPriv->pFBArea[i]->box.y1 * pScrn->displayWidth) +
+ pPPriv->pFBArea[i]->box.x1) << BPPSHIFT(pGlint);
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 4,
+ "New linear buffer %dx%d, rec %dx%d -> pFB=%p, off=0x%08x\n",
+ w, h, pPPriv->BufferStride, h, pPPriv->pFBArea[i], pPPriv->BufferBase[i]));
+ } else {
+ pPPriv->BufferStride = pScrn->displayWidth << BPPSHIFT(pGlint);
+
+ j = pPPriv->BufferStride / bytespp;
+
+ if (j <= w && j <= 2048 && (j & 31) == 0 &&
+ (pPPriv->BufferPProd = partprodPermedia[j >> 5]) >= 0)
+ {
+ pPPriv->pFBArea[i] = xf86AllocateOffscreenArea(pScrn->pScreen,
+ w, h, 8 >> BPPSHIFT(pGlint), NULL, NULL, (pointer) pPPriv);
+
+ if (pPPriv->pFBArea[i])
+ pPPriv->BufferBase[i] =
+ ((pPPriv->pFBArea[i]->box.y1 * pScrn->displayWidth) +
+ pPPriv->pFBArea[i]->box.x1) << BPPSHIFT(pGlint);
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 4,
+ "New rect buffer %dx%d, stride %d, %d -> pFB=%p, off=0x%08x\n",
+ w, h, pPPriv->BufferStride, j, pPPriv->pFBArea[i], pPPriv->BufferBase[i]));
+ }
+ }
+
+ if (pPPriv->pFBArea[i])
+ continue;
+
+ if (!force && i == 0 && retry++ < 1) {
+ linear ^= TRUE;
+ i = -1;
+ } else
+ break;
+ }
+
+ return pPPriv->BuffersAllocated = i;
+}
+
+
+/*
+ * Blitter
+ */
+
+static Bool
+RemakePutCookies(PortPrivPtr pPPriv, RegionPtr pRegion)
+{
+ BoxPtr pBox;
+ CookiePtr pCookie;
+ int nBox;
+
+ if (!pRegion) {
+ pBox = (BoxPtr) NULL;
+ nBox = pPPriv->nCookies;
+ } else {
+ pBox = REGION_RECTS(pRegion);
+ nBox = REGION_NUM_RECTS(pRegion);
+
+ if (!pPPriv->pCookies || pPPriv->nCookies < nBox) {
+ if (!(pCookie = (CookiePtr) xrealloc(pPPriv->pCookies, nBox * sizeof(CookieRec))))
+ return FALSE;
+
+ pPPriv->pCookies = pCookie;
+ }
+ }
+
+ pPPriv->dS = (pPPriv->vw << 10) / pPPriv->dw;
+ pPPriv->dT = (pPPriv->vh << 10) / pPPriv->dh;
+
+ for (pCookie = pPPriv->pCookies; nBox--; pCookie++, pBox++) {
+ if (pRegion) {
+ pCookie->y1 = pBox->y1;
+ pCookie->y2 = pBox->x1;
+ pCookie->xy = (pBox->y1 << 16) | pBox->x1;
+ pCookie->wh = ((pBox->y2 - pBox->y1) << 16) |
+ (pBox->x2 - pBox->x1);
+ }
+
+ pCookie->s = (pPPriv->vx << 10) + (pCookie->y2 - pPPriv->dx) * pPPriv->dS;
+ pCookie->t = (pPPriv->vy << 10) + (pCookie->y1 - pPPriv->dy) * pPPriv->dT;
+ }
+
+ pPPriv->nCookies = pCookie - pPPriv->pCookies;
+
+ return TRUE;
+}
+
+#define FORMAT_YUYV ((0 << 5) + (1 << 4) + ((19 & 0x10) << 2) + ((19 & 0x0F) << 0))
+#define FORMAT_UYVY ((1 << 5) + (1 << 4) + ((19 & 0x10) << 2) + ((19 & 0x0F) << 0))
+#define FORMAT_YUVA ((0 << 5) + ((18 & 0x10) << 2) + ((18 & 0x0F) << 0))
+#define FORMAT_VUYA ((1 << 5) + ((18 & 0x10) << 2) + ((18 & 0x0F) << 0))
+
+static void
+PutYUV(PortPrivPtr pPPriv, int BufferBase,
+ int format, int bptshift, int alpha)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ ScrnInfoPtr pScrn = pAPriv->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CookiePtr pCookie = pPPriv->pCookies;
+ int nCookies = pPPriv->nCookies;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "PutYUV %08x %08x\n",
+ BufferBase, format));
+
+ if (!nCookies || (GLINT_READ_REG(InFIFOSpace) < 200))
+ return; /* Denial of service fix, N/A for scaler */
+
+ CHECKCLIPPING;
+
+ GLINT_WRITE_REG(1 << 16, dY);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, TextureAddressMode);
+ GLINT_WRITE_REG(pPPriv->dS, dSdx);
+ GLINT_WRITE_REG(0, dSdyDom);
+ GLINT_WRITE_REG(0, dTdx);
+ GLINT_WRITE_REG(pPPriv->dT, dTdyDom);
+ GLINT_WRITE_REG(BufferBase >> bptshift, PMTextureBaseAddress);
+ GLINT_WRITE_REG((bptshift << 19) | pPPriv->BufferPProd, PMTextureMapFormat);
+ GLINT_WRITE_REG(format, PMTextureDataFormat);
+ GLINT_WRITE_REG((pPPriv->Attribute[5] << 17) | /* FilterMode */
+ (11 << 13) | (11 << 9) | /* TextureSize log2 */
+ UNIT_ENABLE, PMTextureReadMode);
+ GLINT_WRITE_REG((0 << 4) /* RGB */ |
+ (3 << 1) /* Copy */ |
+ UNIT_ENABLE, TextureColorMode);
+ if (alpha)
+ GLINT_WRITE_REG(pAPriv->dAlphaBlendMode, AlphaBlendMode);
+ GLINT_WRITE_REG(pAPriv->dDitherMode, DitherMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_WRITE_REG((alpha << 10) | /* ReadDestination */
+ pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(0xFFFFFFFF, FBHardwareWriteMask);
+ GLINT_WRITE_REG(UNIT_ENABLE, YUVMode);
+
+ for (; nCookies--; pCookie++) {
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(pCookie->xy, RectangleOrigin);
+ GLINT_WRITE_REG(pCookie->wh, RectangleSize);
+ GLINT_WRITE_REG(pCookie->s, SStart);
+ GLINT_WRITE_REG(pCookie->t, TStart);
+ GLINT_WRITE_REG(PrimitiveRectangle |
+ XPositive |
+ YPositive |
+ TextureEnable, Render);
+ }
+
+ pGlint->x = pGlint->y = -1; /* Force reload */
+ pGlint->w = pGlint->h = -1;
+ pGlint->ROP = 0xFF;
+ pGlint->planemask = 0xFFFFFFFF;
+
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_WRITE_REG(pGlint->TexMapFormat, PMTextureMapFormat);
+ GLINT_WRITE_REG(UNIT_DISABLE, PMTextureReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, DitherMode);
+ if (alpha) {
+ GLINT_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ }
+ GLINT_WRITE_REG(UNIT_DISABLE, YUVMode);
+}
+
+#define FORMAT_RGB8888 ((0 << 5) + (0 << 4) + ((0 & 0x10) << 2) + ((0 & 0x0F) << 0))
+#define FORMAT_RGB565 ((0 << 5) + (1 << 4) + ((16 & 0x10) << 2) + ((16 & 0x0F) << 0))
+#define FORMAT_RGB5551 ((0 << 5) + (0 << 4) + ((1 & 0x10) << 2) + ((1 & 0x0F) << 0))
+#define FORMAT_RGB4444 ((0 << 5) + (0 << 4) + ((2 & 0x10) << 2) + ((2 & 0x0F) << 0))
+#define FORMAT_RGB332 ((0 << 5) + (1 << 4) + ((5 & 0x10) << 2) + ((5 & 0x0F) << 0))
+#define FORMAT_RGB2321 ((0 << 5) + (0 << 4) + ((9 & 0x10) << 2) + ((9 & 0x0F) << 0))
+#define FORMAT_BGR8888 ((1 << 5) + (0 << 4) + ((0 & 0x10) << 2) + ((0 & 0x0F) << 0))
+#define FORMAT_BGR565 ((1 << 5) + (1 << 4) + ((16 & 0x10) << 2) + ((16 & 0x0F) << 0))
+#define FORMAT_BGR5551 ((1 << 5) + (0 << 4) + ((1 & 0x10) << 2) + ((1 & 0x0F) << 0))
+#define FORMAT_BGR4444 ((1 << 5) + (0 << 4) + ((2 & 0x10) << 2) + ((2 & 0x0F) << 0))
+#define FORMAT_BGR332 ((1 << 5) + (1 << 4) + ((5 & 0x10) << 2) + ((5 & 0x0F) << 0))
+#define FORMAT_BGR2321 ((1 << 5) + (0 << 4) + ((9 & 0x10) << 2) + ((9 & 0x0F) << 0))
+
+static void
+PutRGB(PortPrivPtr pPPriv, int BufferBase, int format, int bptshift, int alpha)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ ScrnInfoPtr pScrn = pAPriv->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CookiePtr pCookie = pPPriv->pCookies;
+ int nCookies = pPPriv->nCookies;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "PutRGB %08x %08x\n",
+ BufferBase, format));
+
+ if (!nCookies)
+ return;
+
+ CHECKCLIPPING;
+
+ GLINT_WRITE_REG(1 << 16, dY);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, TextureAddressMode);
+ GLINT_WRITE_REG(pPPriv->dS, dSdx);
+ GLINT_WRITE_REG(0, dSdyDom);
+ GLINT_WRITE_REG(0, dTdx);
+ GLINT_WRITE_REG(pPPriv->dT, dTdyDom);
+ GLINT_WRITE_REG(BufferBase >> bptshift, PMTextureBaseAddress);
+ GLINT_WRITE_REG((bptshift << 19) | pPPriv->BufferPProd, PMTextureMapFormat);
+ GLINT_WRITE_REG(format, PMTextureDataFormat);
+ GLINT_WRITE_REG((pPPriv->Attribute[5] << 17) | /* FilterMode */
+ (11 << 13) | (11 << 9) | /* TextureSize log2 */
+ UNIT_ENABLE, PMTextureReadMode);
+ GLINT_WRITE_REG((0 << 4) /* RGB */ |
+ (3 << 1) /* Copy */ |
+ UNIT_ENABLE, TextureColorMode);
+ if (alpha)
+ GLINT_WRITE_REG(pAPriv->dAlphaBlendMode, AlphaBlendMode);
+ GLINT_WRITE_REG(pAPriv->dDitherMode, DitherMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_WRITE_REG((alpha << 10) | /* ReadDestination */
+ pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(0xFFFFFFFF, FBHardwareWriteMask);
+
+ for (; nCookies--; pCookie++) {
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(pCookie->xy, RectangleOrigin);
+ GLINT_WRITE_REG(pCookie->wh, RectangleSize);
+ GLINT_WRITE_REG(pCookie->s, SStart);
+ GLINT_WRITE_REG(pCookie->t, TStart);
+ GLINT_WRITE_REG(PrimitiveRectangle |
+ XPositive |
+ YPositive |
+ TextureEnable, Render);
+ }
+
+ pGlint->x = pGlint->y = -1; /* Force reload */
+ pGlint->w = pGlint->h = -1;
+ pGlint->ROP = 0xFF;
+ pGlint->planemask = 0xFFFFFFFF;
+
+ GLINT_WAIT(7);
+ GLINT_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_WRITE_REG(pGlint->TexMapFormat, PMTextureMapFormat);
+ GLINT_WRITE_REG(UNIT_DISABLE, PMTextureReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, DitherMode);
+ if (alpha) {
+ GLINT_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ }
+}
+
+static void
+BlackOut(PortPrivPtr pPPriv, RegionPtr pRegion)
+{
+ ScrnInfoPtr pScrn = pPPriv->pAdaptor->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ RegionRec DRegion;
+ BoxRec DBox;
+ BoxPtr pBox;
+ int nBox;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5,
+ "BlackOut %d,%d,%d,%d -- %d,%d,%d,%d\n",
+ pPPriv->vx, pPPriv->vy, pPPriv->vw, pPPriv->vh,
+ pPPriv->dx, pPPriv->dy, pPPriv->dw, pPPriv->dh));
+
+ DBox.x1 = pPPriv->dx - (pPPriv->vx * pPPriv->dw) / pPPriv->vw;
+ DBox.y1 = pPPriv->dy - (pPPriv->vy * pPPriv->dh) / pPPriv->vh;
+ DBox.x2 = DBox.x1 + (pPPriv->fw * pPPriv->dw) / pPPriv->vw;
+ DBox.y2 = DBox.y1 + (pPPriv->fh * pPPriv->dh) / pPPriv->vh;
+
+ REGION_INIT(pScreen, &DRegion, &DBox, 1);
+
+ if (pRegion)
+ REGION_SUBTRACT(pScreen, &DRegion, &DRegion, pRegion);
+
+ nBox = REGION_NUM_RECTS(&DRegion);
+ pBox = REGION_RECTS(&DRegion);
+
+ GLINT_WAIT(15);
+ CHECKCLIPPING;
+
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pPPriv->BufferPProd, FBReadMode);
+ GLINT_WRITE_REG(0x1, FBReadPixel); /* 16 */
+ GLINT_WRITE_REG(pPPriv->BkgCol, FBBlockColor);
+ GLINT_WRITE_REG(pPPriv->BufferBase[0] >> 1 /* 16 */, FBWindowBase);
+ GLINT_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+
+ for (; nBox--; pBox++) {
+ int w = ((pBox->x2 - pBox->x1) * pPPriv->vw + pPPriv->dw) / pPPriv->dw + 1;
+ int h = ((pBox->y2 - pBox->y1) * pPPriv->vh + pPPriv->dh) / pPPriv->dh + 1;
+ int x = ((pBox->x1 - DBox.x1) * pPPriv->vw + (pPPriv->dw >> 1)) / pPPriv->dw;
+ int y = ((pBox->y1 - DBox.y1) * pPPriv->vh + (pPPriv->dh >> 1)) / pPPriv->dh;
+
+ if ((x + w) > pPPriv->fw)
+ w = pPPriv->fw - x;
+ if ((y + h) > pPPriv->fh)
+ h = pPPriv->fh - y;
+
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG((y << 16) | x, RectangleOrigin);
+ GLINT_WRITE_REG((h << 16) | w, RectangleSize);
+ GLINT_WRITE_REG(PrimitiveRectangle |
+ XPositive | YPositive | FastFillEnable, Render);
+ }
+
+ REGION_UNINIT(pScreen, &DRegion);
+
+ pGlint->x = pGlint->y = -1; /* Force reload */
+ pGlint->w = pGlint->h = -1;
+ pGlint->ROP = 0xFF;
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(0, FBWindowBase);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(pGlint->PixelWidth, FBReadPixel);
+}
+
+static Bool
+RemakeGetCookies(PortPrivPtr pPPriv, RegionPtr pRegion)
+{
+ BoxPtr pBox;
+ CookiePtr pCookie;
+ int nBox;
+ int dw1 = pPPriv->dw - 1;
+ int dh1 = pPPriv->dh - 1;
+
+ if (!pRegion) {
+ pBox = (BoxPtr) NULL;
+ nBox = pPPriv->nCookies;
+ } else {
+ pBox = REGION_RECTS(pRegion);
+ nBox = REGION_NUM_RECTS(pRegion);
+
+ if (!pPPriv->pCookies || pPPriv->nCookies < nBox) {
+ if (!(pCookie = (CookiePtr) xrealloc(pPPriv->pCookies, nBox * sizeof(CookieRec))))
+ return FALSE;
+
+ pPPriv->pCookies = pCookie;
+ }
+ }
+
+ pPPriv->dS = (pPPriv->dw << 20) / pPPriv->vw;
+ pPPriv->dT = (pPPriv->dh << 20) / pPPriv->vh;
+
+ for (pCookie = pPPriv->pCookies; nBox--; pBox++) {
+ int n1, n2;
+
+ if (pRegion) {
+ n1 = ((pBox->x1 - pPPriv->dx) * pPPriv->vw + dw1) / pPPriv->dw;
+ n2 = ((pBox->x2 - pPPriv->dx) * pPPriv->vw - 1) / pPPriv->dw;
+
+ if (n1 > n2)
+ continue; /* Clip is subpixel */
+
+ pCookie->xy = n1 + pPPriv->vx;
+ pCookie->wh = n2 - n1 + 1;
+ pCookie->s = n1 * pPPriv->dS + (pPPriv->dx << 20);
+ pCookie->y1 = pBox->y1;
+ pCookie->y2 = pBox->y2;
+ }
+
+ n1 = ((pCookie->y1 - pPPriv->dy) * pPPriv->vh + dh1) / pPPriv->dh;
+ n2 = ((pCookie->y2 - pPPriv->dy) * pPPriv->vh - 1) / pPPriv->dh;
+ pCookie->xy = (pCookie->xy & 0xFFFF) | ((n1 + pPPriv->vy) << 16);
+ pCookie->wh = (pCookie->wh & 0xFFFF) | ((n2 - n1 + 1) << 16);
+ pCookie->t = n1 * pPPriv->dT + (pPPriv->dy << 20);
+ if (n1 > n2) pCookie->t = -1;
+
+ pCookie++;
+ }
+
+ pPPriv->nCookies = pCookie - pPPriv->pCookies;
+ return TRUE;
+}
+
+static void
+GetYUV(PortPrivPtr pPPriv)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ ScrnInfoPtr pScrn = pAPriv->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CookiePtr pCookie = pPPriv->pCookies;
+ int nCookies = pPPriv->nCookies;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "GetYUV\n"));
+
+ if (!nCookies || (GLINT_READ_REG(InFIFOSpace) < 200))
+ return;
+
+ GLINT_WAIT(25);
+ CHECKCLIPPING;
+
+ GLINT_WRITE_REG(1 << 16, dY);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, TextureAddressMode);
+ GLINT_WRITE_REG(pPPriv->dS, dSdx);
+ GLINT_WRITE_REG(0, dSdyDom);
+ GLINT_WRITE_REG(0, dTdx);
+ GLINT_WRITE_REG(pPPriv->dT, dTdyDom);
+ GLINT_WRITE_REG(0, PMTextureBaseAddress);
+ GLINT_WRITE_REG(pAPriv->dTextureDataFormat, PMTextureDataFormat);
+ GLINT_WRITE_REG((pPPriv->Attribute[5] << 17) | /* FilterMode */
+ (11 << 13) | (11 << 9) | /* TextureSize log2 */
+ UNIT_ENABLE, PMTextureReadMode);
+ if (pScrn->depth == 8)
+ GLINT_WRITE_REG(UNIT_ENABLE, TexelLUTMode);
+ GLINT_WRITE_REG((0 << 4) /* RGB */ |
+ (3 << 1) /* Copy */ |
+ UNIT_ENABLE, TextureColorMode);
+ GLINT_WRITE_REG((1 << 10) | /* RGB */
+ ((16 & 0x10) << 12) |
+ ((16 & 0x0F) << 2) | /* 5:6:5f */
+ UNIT_ENABLE, DitherMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_WRITE_REG(pPPriv->BufferPProd, FBReadMode);
+ GLINT_WRITE_REG(pPPriv->BufferBase[0] >> 1 /* 16 */, FBWindowBase);
+ GLINT_WRITE_REG(0x1, FBReadPixel); /* 16 */
+ GLINT_WRITE_REG(UNIT_DISABLE, YUVMode);
+
+ for (; nCookies--; pCookie++)
+ if (pCookie->t >= 0) {
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(pCookie->xy, RectangleOrigin);
+ GLINT_WRITE_REG(pCookie->wh, RectangleSize);
+ GLINT_WRITE_REG(pCookie->s, SStart);
+ GLINT_WRITE_REG(pCookie->t, TStart);
+ GLINT_WRITE_REG(PrimitiveRectangle |
+ XPositive |
+ YPositive |
+ TextureEnable, Render);
+ }
+
+ pGlint->x = pGlint->y = -1; /* Force reload */
+ pGlint->w = pGlint->h = -1;
+ pGlint->ROP = 0xFF;
+
+ GLINT_WAIT(9);
+ GLINT_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, DitherMode);
+ if (pScrn->depth == 8)
+ GLINT_WRITE_REG(UNIT_DISABLE, TexelLUTMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, PMTextureReadMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(0, FBWindowBase);
+ GLINT_WRITE_REG(pGlint->PixelWidth, FBReadPixel);
+ GLINT_WRITE_REG(UNIT_DISABLE, YUVMode);
+}
+
+static int
+SetBkgCol(PortPrivPtr pPPriv, int value)
+{
+ pPPriv->Attribute[6] = value;
+
+ pPPriv->BkgCol = ((value & 0xF80000) >> 8) |
+ ((value & 0x00FC00) >> 5) |
+ ((value & 0x0000F8) >> 3);
+
+ pPPriv->BkgCol += pPPriv->BkgCol << 16;
+
+ if (pPPriv->VideoOn) {
+ BlackOut(pPPriv, NULL);
+ GetYUV(pPPriv);
+ }
+
+ return Success;
+}
+
+/* os/WaitFor.c */
+
+static CARD32
+TimerCallback(OsTimerPtr pTim, CARD32 now, pointer p)
+{
+ AdaptorPrivPtr pAPriv = (AdaptorPrivPtr) p;
+ GLINTPtr pGlint = GLINTPTR(pAPriv->pScrn);
+ PortPrivPtr pPPriv;
+ int i, delay;
+
+ if (!pAPriv->pm2p) {
+ pPPriv = &pAPriv->Port[0];
+
+ if (pPPriv->VideoOn > VIDEO_OFF) {
+ pPPriv->FrameAcc += pPPriv->FramesPerSec;
+
+ if (pPPriv->FrameAcc >= pAPriv->FramesPerSec) {
+ pPPriv->FrameAcc -= pAPriv->FramesPerSec;
+
+ PutYUV(pPPriv, (!pPPriv->pFBArea[1]) ?
+ pPPriv->BufferBase[0] : pPPriv->BufferBase[1 -
+ GLINT_READ_REG(VSABase + VSVideoAddressIndex)], FORMAT_YUYV, 1, 0);
+ }
+ } else
+ if (pPPriv->StopDelay >= 0 && !(pPPriv->StopDelay--)) {
+ StopVideoStream(pPPriv, TRUE);
+ RestoreVideoStd(pAPriv);
+ }
+
+ pPPriv = &pAPriv->Port[1];
+
+ if (pPPriv->VideoOn > VIDEO_OFF) {
+ pPPriv->FrameAcc += pPPriv->FramesPerSec;
+
+ if (pPPriv->FrameAcc >= pAPriv->FramesPerSec) {
+ pPPriv->FrameAcc -= pAPriv->FramesPerSec;
+
+ GetYUV(pPPriv);
+ }
+ } else
+ if (pPPriv->StopDelay >= 0 && !(pPPriv->StopDelay--)) {
+ StopVideoStream(pPPriv, TRUE);
+ RestoreVideoStd(pAPriv);
+ }
+ }
+
+ for (i = 2; i <= 5; i++) {
+ if (pAPriv->Port[i].StopDelay >= 0) {
+ if (!(pAPriv->Port[i].StopDelay--)) {
+ FreeBuffers(&pAPriv->Port[i]);
+ FreeCookies(&pAPriv->Port[i]);
+ pAPriv->TimerUsers &= ~(1 << i);
+ }
+ }
+ }
+
+ if (!pAPriv->pm2p) {
+ if (pAPriv->Port[0].StreamOn) {
+ delay = GLINT_READ_REG(VSABase + VSCurrentLine);
+
+ if (!(GLINT_READ_REG(VSStatus) & VS_FieldOne0A))
+ delay += pAPriv->FrameLines >> 1;
+
+ if (delay > (pAPriv->IntLine - 16))
+ delay -= pAPriv->FrameLines;
+
+ return (((pAPriv->IntLine - delay) * pAPriv->LinePer) + 999999) / 1000000;
+ } else if (pAPriv->Port[1].StreamOn) {
+ delay = GLINT_READ_REG(VSBBase + VSCurrentLine);
+
+ if (!(GLINT_READ_REG(VSStatus) & VS_FieldOne0B))
+ delay += pAPriv->FrameLines >> 1;
+
+ if (delay > (pAPriv->IntLine - 16))
+ delay -= pAPriv->FrameLines;
+
+ return (((pAPriv->IntLine - delay) * pAPriv->LinePer) + 999999) / 1000000;
+ }
+ }
+
+ if (pAPriv->TimerUsers)
+ return pAPriv->Instant;
+
+ return 0; /* Cancel */
+}
+
+
+/*
+ * Video stream (bounce buffer <-> hardware)
+ */
+
+static void
+StopVideoStream(PortPrivPtr pPPriv, Bool shutdown)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ GLINTPtr pGlint = GLINTPTR(pAPriv->pScrn);
+ int VideoOn;
+
+ pPPriv->StopDelay = -1;
+
+ VideoOn = pPPriv->VideoOn;
+ pPPriv->VideoOn = VIDEO_OFF;
+
+ if (!pPPriv->StreamOn)
+ return;
+
+ if (pAPriv->pm2p) {
+ xvipcHandshake(pPPriv, OP_STOP, TRUE);
+
+ pPPriv->StreamOn = FALSE;
+
+ if (shutdown)
+ FreeCookies(pPPriv);
+
+ if (VideoOn > VIDEO_OFF && pGlint->NoAccel)
+ Permedia2Sync(pAPriv->pScrn);
+
+ return;
+ }
+
+ if (pPPriv == &pAPriv->Port[0]) {
+ int line, eeek = 0;
+
+ do {
+ if (eeek++ > 1000000) break;
+ line = GLINT_READ_REG(VSABase + VSCurrentLine);
+ } while (line > 15);
+
+ GLINT_WRITE_REG(0, VSABase + VSControl);
+
+ pAPriv->Port[0].StreamOn = FALSE;
+
+ usleep(80000);
+ } else {
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x3A, 0x83);
+ if (!ColorBars)
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x61, 0xC2);
+
+ GLINT_WRITE_REG(0, VSBBase + VSControl);
+
+ pAPriv->Port[1].StreamOn = FALSE;
+ }
+
+ if (!pAPriv->Port[0].StreamOn && !pAPriv->Port[1].StreamOn) {
+ if (shutdown)
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x61, 0xC2);
+ xf86I2CWriteByte(&pAPriv->Port[0].I2CDev, 0x11, 0x00);
+ }
+
+ if (shutdown) {
+ FreeBuffers(pPPriv);
+ FreeCookies(pPPriv);
+
+ if (pAPriv->TimerUsers) {
+ pAPriv->TimerUsers &= ~PORTNUM(pPPriv);
+ if (!pAPriv->TimerUsers)
+ TimerCancel(pAPriv->Timer);
+ }
+
+ if (VideoOn > VIDEO_OFF && pGlint->NoAccel)
+ Permedia2Sync(pAPriv->pScrn);
+ }
+}
+
+static Bool
+StartVideoStream(PortPrivPtr pPPriv, RegionPtr pRegion)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ GLINTPtr pGlint = GLINTPTR(pAPriv->pScrn);
+
+ if (pAPriv->VideoStd < 0)
+ return FALSE;
+
+ pPPriv->StopDelay = -1;
+
+ if (pAPriv->pm2p) {
+ if (pPPriv == &pAPriv->Port[0]) {
+ if (!RemakePutCookies(pPPriv, pRegion))
+ return FALSE;
+ if (pPPriv->StreamOn)
+ return TRUE;
+ } else {
+ if (!RemakeGetCookies(pPPriv, pRegion))
+ return FALSE;
+ if (pPPriv->StreamOn) {
+ BlackOut(pPPriv, pRegion);
+ return TRUE;
+ }
+ }
+
+ xvipc.a = pPPriv->BuffersRequested;
+ xvipc.b = !pPPriv->Attribute[4];
+ xvipc.c = 1 + (pPPriv->Attribute[4] & 2);
+
+ if (!xvipcHandshake(pPPriv, OP_START, TRUE))
+ return FALSE;
+
+ if (pPPriv == &pAPriv->Port[1]) {
+ pPPriv->BufferBase[0] = xvipc.d;
+ BlackOut(pPPriv, pRegion);
+ }
+
+ return pPPriv->StreamOn = TRUE;
+ } else {
+ CARD32 Base = (pPPriv == &pAPriv->Port[0]) ? VSABase : VSBBase;
+
+ if (pPPriv->BuffersAllocated < pPPriv->BuffersRequested) {
+ int height = ((pAPriv->VideoStd == NTSC) ? 512 : 608) >> (!pPPriv->Attribute[4]);
+
+ if (!AllocateBuffers(pPPriv, 704, height, 2, pPPriv->BuffersRequested, 0))
+ return FALSE;
+
+ pPPriv->fw = 704;
+ pPPriv->fh = InputVideoEncodings[pAPriv->VideoStd * 3].height >>
+ (!pPPriv->Attribute[4]);
+ }
+
+ if (pPPriv == &pAPriv->Port[0]) {
+ if (!RemakePutCookies(pPPriv, pRegion))
+ return FALSE;
+ } else {
+ if (!RemakeGetCookies(pPPriv, pRegion))
+ return FALSE;
+
+ BlackOut(pPPriv, pRegion);
+ }
+
+ if (pPPriv->StreamOn)
+ return TRUE;
+
+ GLINT_WRITE_REG(pPPriv->BufferBase[0] / 8, Base + VSVideoAddress0);
+ if (pPPriv->pFBArea[1])
+ GLINT_WRITE_REG(pPPriv->BufferBase[1] / 8, Base + VSVideoAddress1);
+ else
+ GLINT_WRITE_REG(pPPriv->BufferBase[0] / 8, Base + VSVideoAddress1);
+ GLINT_WRITE_REG(pPPriv->BufferStride / 8, Base + VSVideoStride);
+
+ GLINT_WRITE_REG(0, Base + VSCurrentLine);
+
+ if (pAPriv->VideoStd == NTSC) {
+ GLINT_WRITE_REG(16, Base + VSVideoStartLine);
+ GLINT_WRITE_REG(16 + 240, Base + VSVideoEndLine);
+ GLINT_WRITE_REG(288 + (8 & ~3) * 2, Base + VSVideoStartData);
+ GLINT_WRITE_REG(288 + ((8 & ~3) + 704) * 2, Base + VSVideoEndData);
+ } else {
+ GLINT_WRITE_REG(16, Base + VSVideoStartLine);
+ GLINT_WRITE_REG(16 + 288, Base + VSVideoEndLine);
+ GLINT_WRITE_REG(288 + (8 & ~3) * 2, Base + VSVideoStartData);
+ GLINT_WRITE_REG(288 + ((8 & ~3) + 704) * 2, Base + VSVideoEndData);
+ }
+
+ GLINT_WRITE_REG(2, Base + VSVideoAddressHost);
+ GLINT_WRITE_REG(0, Base + VSVideoAddressIndex);
+
+ if (pPPriv == &pAPriv->Port[0]) {
+ int line, eeek = 0;
+
+ xf86I2CWriteByte(&pAPriv->Port[0].I2CDev, 0x11, 0x0D);
+
+ do {
+ if (eeek++ > 1000000) break;
+ line = GLINT_READ_REG(VSABase + VSCurrentLine);
+ } while (line > 15);
+
+ GLINT_WRITE_REG(VSA_Video |
+ (pPPriv->Attribute[4] ?
+ VSA_CombineFields : VSA_Discard_FieldTwo),
+ VSABase + VSControl);
+ if (ColorBars)
+ if (!pAPriv->Port[1].StreamOn) {
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x3A, 0x83);
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x61, Enc61[pAPriv->VideoStd]);
+ }
+ } else {
+ GLINT_WRITE_REG(VSB_Video |
+ (pPPriv->Attribute[4] ? VSB_CombineFields : 0) |
+ /* VSB_GammaCorrect | */
+ (16 << 4) | /* 5:6:5 */
+ (1 << 9) | /* 16 */
+ VSB_RGBOrder, VSBBase + VSControl);
+ xf86I2CWriteByte(&pAPriv->Port[0].I2CDev, 0x11, 0x0D);
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x3A, Enc3A[pPPriv->Plug]);
+ xf86I2CWriteByte(&pAPriv->Port[1].I2CDev, 0x61, Enc61[pAPriv->VideoStd]);
+ }
+
+ pAPriv->TimerUsers |= 1 << PORTNUM(pPPriv);
+ TimerSet(pAPriv->Timer, 0, 80, TimerCallback, pAPriv);
+
+ return pPPriv->StreamOn = TRUE;
+ }
+
+ return FALSE;
+}
+
+
+/*
+ * Xv interface
+ */
+
+static int
+Permedia2PutVideo(ScrnInfoPtr pScrn,
+ short vid_x, short vid_y, short drw_x, short drw_y,
+ short vid_w, short vid_h, short drw_w, short drw_h,
+ RegionPtr clipBoxes, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int sw, sh;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "PutVideo %d,%d,%d,%d -> %d,%d,%d,%d\n",
+ vid_x, vid_y, vid_w, vid_h, drw_x, drw_y, drw_w, drw_h));
+
+ sw = InputVideoEncodings[pAPriv->VideoStd * 3].width;
+ sh = InputVideoEncodings[pAPriv->VideoStd * 3].height;
+
+ if ((vid_x + vid_w) > sw ||
+ (vid_y + vid_h) > sh)
+ return BadValue;
+
+ pPPriv->VideoOn = VIDEO_OFF;
+
+ pPPriv->vx = ((vid_x << 10) * pPPriv->fw) / sw;
+ pPPriv->vy = ((vid_y << 10) * pPPriv->fh) / sh;
+ pPPriv->vw = ((vid_w << 10) * pPPriv->fw) / sw;
+ pPPriv->vh = ((vid_h << 10) * pPPriv->fh) / sh;
+
+ pPPriv->dx = drw_x;
+ pPPriv->dy = drw_y;
+ pPPriv->dw = drw_w;
+ pPPriv->dh = drw_h;
+
+ pPPriv->FrameAcc = pAPriv->FramesPerSec;
+
+ if (!StartVideoStream(pPPriv, clipBoxes))
+ return XvBadAlloc;
+
+ pPPriv->VideoOn = VIDEO_ON;
+
+ return Success;
+}
+
+static int
+Permedia2PutStill(ScrnInfoPtr pScrn,
+ short vid_x, short vid_y, short drw_x, short drw_y,
+ short vid_w, short vid_h, short drw_w, short drw_h,
+ RegionPtr clipBoxes, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int sw, sh, r = Success;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "PutStill %d,%d,%d,%d -> %d,%d,%d,%d\n",
+ vid_x, vid_y, vid_w, vid_h, drw_x, drw_y, drw_w, drw_h));
+
+ sw = InputVideoEncodings[pAPriv->VideoStd * 3].width;
+ sh = InputVideoEncodings[pAPriv->VideoStd * 3].height;
+
+ if ((vid_x + vid_w) > sw ||
+ (vid_y + vid_h) > sh)
+ return BadValue;
+
+ pPPriv->VideoOn = VIDEO_OFF;
+
+ pPPriv->vx = ((vid_x << 10) * pPPriv->fw) / sw;
+ pPPriv->vy = ((vid_y << 10) * pPPriv->fh) / sh;
+ pPPriv->vw = ((vid_w << 10) * pPPriv->fw) / sw;
+ pPPriv->vh = ((vid_h << 10) * pPPriv->fh) / sh;
+
+ pPPriv->dx = drw_x;
+ pPPriv->dy = drw_y;
+ pPPriv->dw = drw_w;
+ pPPriv->dh = drw_h;
+
+ pPPriv->FrameAcc = pAPriv->FramesPerSec;
+
+ if (!StartVideoStream(pPPriv, clipBoxes))
+ return XvBadAlloc;
+
+ if (pAPriv->pm2p) {
+ /* Sleep, not busy wait, until the very next frame is ready.
+ Accept memory requests and other window's update events
+ in the meantime. */
+ for (pPPriv->VideoOn = VIDEO_ONE_SHOT; pPPriv->VideoOn;)
+ if (!xvipcHandshake(pPPriv, OP_UPDATE, TRUE)) {
+ r = FALSE;
+ break;
+ }
+ } else {
+ usleep(80000);
+
+ PutYUV(pPPriv, (!pPPriv->pFBArea[1]) ?
+ pPPriv->BufferBase[0] : pPPriv->BufferBase[1 -
+ GLINT_READ_REG(VSABase + VSVideoAddressIndex)], FORMAT_YUYV, 1, 0);
+ }
+
+ pPPriv->StopDelay = 125;
+
+ return r;
+}
+
+static int
+Permedia2GetVideo(ScrnInfoPtr pScrn,
+ short vid_x, short vid_y, short drw_x, short drw_y,
+ short vid_w, short vid_h, short drw_w, short drw_h,
+ RegionPtr clipBoxes, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int sw, sh;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "GetVideo %d,%d,%d,%d <- %d,%d,%d,%d\n",
+ vid_x, vid_y, vid_w, vid_h, drw_x, drw_y, drw_w, drw_h));
+
+ sw = InputVideoEncodings[pAPriv->VideoStd * 3].width;
+ sh = InputVideoEncodings[pAPriv->VideoStd * 3].height;
+
+ if ((vid_x + vid_w) > sw ||
+ (vid_y + vid_h) > sh) {
+ return BadValue;
+ }
+
+ pPPriv->VideoOn = VIDEO_OFF;
+
+ pPPriv->vx = (vid_x * pPPriv->fw) / sw;
+ pPPriv->vy = (vid_y * pPPriv->fh) / sh;
+ pPPriv->vw = (vid_w * pPPriv->fw) / sw;
+ pPPriv->vh = (vid_h * pPPriv->fh) / sh;
+
+ pPPriv->dx = drw_x;
+ pPPriv->dy = drw_y;
+ pPPriv->dw = drw_w;
+ pPPriv->dh = drw_h;
+
+ pPPriv->FrameAcc = pAPriv->FramesPerSec;
+
+ if (!StartVideoStream(pPPriv, clipBoxes)) {
+ return XvBadAlloc;
+ }
+
+ GetYUV(pPPriv);
+
+ pPPriv->VideoOn = VIDEO_ON;
+
+ return Success;
+}
+
+static int
+Permedia2GetStill(ScrnInfoPtr pScrn,
+ short vid_x, short vid_y, short drw_x, short drw_y,
+ short vid_w, short vid_h, short drw_w, short drw_h,
+ RegionPtr clipBoxes, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int sw, sh;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "GetStill %d,%d,%d,%d <- %d,%d,%d,%d\n",
+ vid_x, vid_y, vid_w, vid_h, drw_x, drw_y, drw_w, drw_h));
+
+ sw = InputVideoEncodings[pAPriv->VideoStd * 3].width;
+ sh = InputVideoEncodings[pAPriv->VideoStd * 3].height;
+
+ if ((vid_x + vid_w) > sw ||
+ (vid_y + vid_h) > sh)
+ return BadValue;
+
+ pPPriv->VideoOn = VIDEO_OFF;
+
+ pPPriv->vx = (vid_x * pPPriv->fw) / sw;
+ pPPriv->vy = (vid_y * pPPriv->fh) / sh;
+ pPPriv->vw = (vid_w * pPPriv->fw) / sw;
+ pPPriv->vh = (vid_h * pPPriv->fh) / sh;
+
+ pPPriv->dx = drw_x;
+ pPPriv->dy = drw_y;
+ pPPriv->dw = drw_w;
+ pPPriv->dh = drw_h;
+
+ pPPriv->FrameAcc = pAPriv->FramesPerSec;
+
+ if (!StartVideoStream(pPPriv, clipBoxes))
+ return XvBadAlloc;
+
+ GetYUV(pPPriv);
+
+ return Success;
+}
+
+static void
+CopyYV12LE(CARD8 *Y, CARD32 *dst, int width, int height, int pitch)
+{
+ int Y_size = width * height;
+ CARD8 *V = Y + Y_size;
+ CARD8 *U = V + (Y_size >> 2);
+ int pad = (pitch >> 2) - (width >> 1);
+ int x;
+
+ width >>= 1;
+
+ for (height >>= 1; height > 0; height--) {
+ for (x = 0; x < width; Y += 2, x++)
+ *dst++ = Y[0] + (U[x] << 8) + (Y[1] << 16) + (V[x] << 24);
+ dst += pad;
+ for (x = 0; x < width; Y += 2, x++)
+ *dst++ = Y[0] + (U[x] << 8) + (Y[1] << 16) + (V[x] << 24);
+ dst += pad;
+ U += width;
+ V += width;
+ }
+}
+
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+
+static void
+CopyYV12BE(CARD8 *Y, CARD32 *dst, int width, int height, int pitch)
+{
+ int Y_size = width * height;
+ CARD8 *V = Y + Y_size;
+ CARD8 *U = V + (Y_size >> 2);
+ int pad = (pitch >> 2) - (width >> 1);
+ int x;
+
+ width >>= 1;
+
+ for (height >>= 1; height > 0; height--) {
+ for (x = 0; x < width; Y += 2, x++)
+ *dst++ = V[x] + (Y[1] << 8) + (U[x] << 16) + (Y[0] << 24);
+ dst += pad;
+ for (x = 0; x < width; Y += 2, x++)
+ *dst++ = V[x] + (Y[1] << 8) + (U[x] << 16) + (Y[0] << 24);
+ dst += pad;
+ U += width;
+ V += width;
+ }
+}
+
+#endif /* X_BYTE_ORDER == X_BIG_ENDIAN */
+
+static void
+CopyFlat(CARD8 *src, CARD8 *dst, int width, int height, int pitch)
+{
+ if (width == pitch) {
+ memcpy(dst, src, width * height);
+ return;
+ }
+
+ while (height > 0) {
+ memcpy(dst, src, width);
+ dst += pitch;
+ src += width;
+ height--;
+ }
+}
+
+static int
+Permedia2PutImage(ScrnInfoPtr pScrn,
+ short src_x, short src_y, short drw_x, short drw_y,
+ short src_w, short src_h, short drw_w, short drw_h,
+ int id, unsigned char *buf, short width, short height,
+ Bool sync, RegionPtr clipBoxes, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "PutImage %d,%d,%d,%d -> %d,%d,%d,%d id=0x%08x buf=%p w=%d h=%d sync=%d\n",
+ src_x, src_y, src_w, src_h, drw_x, drw_y, drw_w, drw_h,
+ id, buf, width, height, sync));
+
+ if ((src_x + src_w) > width ||
+ (src_y + src_h) > height)
+ return BadValue;
+
+ pPPriv->vx = src_x << 10;
+ pPPriv->vy = src_y << 10;
+ pPPriv->vw = src_w << 10;
+ pPPriv->vh = src_h << 10;
+
+ pPPriv->dx = drw_x;
+ pPPriv->dy = drw_y;
+ pPPriv->dw = drw_w;
+ pPPriv->dh = drw_h;
+
+ if (!RemakePutCookies(pPPriv, clipBoxes))
+ return XvBadAlloc;
+
+ if (pPPriv->BuffersAllocated <= 0 ||
+ id != pPPriv->Id || /* same bpp */
+ width != pPPriv->fw ||
+ height != pPPriv->fh)
+ {
+ for (i = 0; i < ENTRIES(ScalerImages); i++)
+ if (id == ScalerImages[i].id)
+ break;
+
+ if (i >= ENTRIES(ScalerImages))
+ return XvBadAlloc;
+#if 0
+ if (pPPriv->BuffersAllocated <= 0 ||
+ pPPriv->Bpp != ScalerImages[i].bits_per_pixel ||
+ width > pPPriv->fw || height > pPPriv->fw ||
+ pPPriv->fw * pPPriv->fh > width * height * 2)
+#else
+ if (1)
+#endif
+ {
+ Permedia2Sync(pScrn);
+
+ if (!AllocateBuffers(pPPriv, width, height,
+ (ScalerImages[i].bits_per_pixel + 7) >> 3, 1, 0)) {
+ pPPriv->Id = 0;
+ pPPriv->Bpp = 0;
+ pPPriv->fw = 0;
+ pPPriv->fh = 0;
+
+ return XvBadAlloc;
+ }
+
+ pPPriv->Id = id;
+ pPPriv->Bpp = ScalerImages[i].bits_per_pixel;
+ pPPriv->fw = width;
+ pPPriv->fh = height;
+
+ RemoveableBuffers(pPPriv, TRUE);
+ } else
+ Permedia2Sync(pScrn);
+ } else
+ Permedia2Sync(pScrn);
+
+ switch (id) {
+ case LE4CC('Y','V','1','2'):
+#if X_BYTE_ORDER == X_LITTLE_ENDIAN
+ CopyYV12LE(buf, (CARD32 *)((CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0]),
+ width, height, pPPriv->BufferStride);
+#else
+ if (pGlint->FBDev)
+ CopyYV12LE(buf, (CARD32 *)((CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0]),
+ width, height, pPPriv->BufferStride);
+ else
+ CopyYV12BE(buf, (CARD32 *)((CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0]),
+ width, height, pPPriv->BufferStride);
+#endif
+ PutYUV(pPPriv, pPPriv->BufferBase[0], FORMAT_YUYV, 1, 0);
+ break;
+
+ case LE4CC('Y','U','Y','2'):
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutYUV(pPPriv, pPPriv->BufferBase[0], FORMAT_YUYV, 1, 0);
+ break;
+
+ case LE4CC('U','Y','V','Y'):
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutYUV(pPPriv, pPPriv->BufferBase[0], FORMAT_UYVY, 1, 0);
+ break;
+
+ case LE4CC('Y','U','V','A'):
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 2, height, pPPriv->BufferStride);
+ PutYUV(pPPriv, pPPriv->BufferBase[0], FORMAT_YUVA, 2, pPPriv->Attribute[7]);
+ break;
+
+ case LE4CC('V','U','Y','A'):
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 2, height, pPPriv->BufferStride);
+ PutYUV(pPPriv, pPPriv->BufferBase[0], FORMAT_VUYA, 2, pPPriv->Attribute[7]);
+ break;
+
+ case 0x41: /* RGBA 8:8:8:8 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 2, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_RGB8888, 2, pPPriv->Attribute[7]);
+ break;
+
+ case 0x42: /* RGB 5:6:5 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_RGB565, 1, 0);
+ break;
+
+ case 0x43: /* RGB 1:5:5:5 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_RGB5551, 1, pPPriv->Attribute[7]);
+ break;
+
+ case 0x44: /* RGB 4:4:4:4 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_RGB4444, 1, pPPriv->Attribute[7]);
+ break;
+
+ case 0x45: /* RGB 1:2:3:2 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_RGB2321, 0, pPPriv->Attribute[7]);
+ break;
+
+ case 0x46: /* RGB 2:3:3 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_RGB332, 0, 0);
+ break;
+
+ case 0x47: /* BGRA 8:8:8:8 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 2, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_BGR8888, 2, pPPriv->Attribute[7]);
+ break;
+
+ case 0x48: /* BGR 5:6:5 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_BGR565, 1, 0);
+ break;
+
+ case 0x49: /* BGR 1:5:5:5 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_BGR5551, 1, pPPriv->Attribute[7]);
+ break;
+
+ case 0x4A: /* BGR 4:4:4:4 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 1, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_BGR4444, 1, pPPriv->Attribute[7]);
+ break;
+
+ case 0x4B: /* BGR 1:2:3:2 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 0, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_BGR2321, 0, pPPriv->Attribute[7]);
+ break;
+
+ case 0x4C: /* BGR 2:3:3 */
+ CopyFlat(buf, (CARD8 *) pGlint->FbBase + pPPriv->BufferBase[0],
+ width << 0, height, pPPriv->BufferStride);
+ PutRGB(pPPriv, pPPriv->BufferBase[0], FORMAT_BGR332, 0, 0);
+ break;
+
+ default:
+ return XvBadAlloc;
+ }
+
+ pPPriv->StopDelay = pAPriv->Delay;
+
+ if (!pAPriv->TimerUsers) {
+ pAPriv->TimerUsers |= 1 << PORTNUM(pPPriv);
+ TimerSet(pAPriv->Timer, 0, 80, TimerCallback, pAPriv);
+ }
+
+ if (sync) /* sched_yield? */
+ Permedia2Sync(pScrn);
+
+ return Success;
+}
+
+static void
+Permedia2StopVideo(ScrnInfoPtr pScrn, pointer data, Bool shutdown)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "StopVideo port=%d, shutdown=%d\n", PORTNUM(pPPriv), shutdown));
+
+ if (shutdown) {
+ if (PORTNUM(pPPriv) < 2) {
+ StopVideoStream(pPPriv, TRUE);
+ RestoreVideoStd(pAPriv);
+ } else {
+ FreeBuffers(pPPriv);
+ FreeCookies(pPPriv);
+ if (pAPriv->TimerUsers) {
+ pAPriv->TimerUsers &= ~PORTNUM(pPPriv);
+ if (!pAPriv->TimerUsers)
+ TimerCancel(pAPriv->Timer);
+ }
+ }
+ } else {
+ pPPriv->VideoOn = VIDEO_OFF;
+ pPPriv->StopDelay = 750; /* appx. 30 sec */
+
+ if (pGlint->NoAccel)
+ Permedia2Sync(pScrn);
+ }
+}
+
+static void
+RestartVideo(PortPrivPtr pPPriv, int old_VideoOn)
+{
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int new_fh;
+
+ if (pPPriv->VideoOn > VIDEO_OFF ||
+ pAPriv->VideoStd < 0 /* invalid */)
+ return;
+
+ new_fh = InputVideoEncodings[pAPriv->VideoStd * 3].height >>
+ (1 - (pPPriv->Attribute[4] & 1));
+
+ if (new_fh != pPPriv->fh) {
+ pPPriv->vy = (pPPriv->vy * new_fh) / pPPriv->fh;
+ pPPriv->vh = (pPPriv->vh * new_fh) / pPPriv->fh;
+
+ pPPriv->fh = new_fh;
+ }
+
+ if (old_VideoOn) {
+ if (StartVideoStream(pPPriv, NULL)) {
+ pPPriv->VideoOn = old_VideoOn;
+
+ if (pPPriv == &pAPriv->Port[1])
+ GetYUV(pPPriv);
+ } else {
+ DEBUG(xf86DrvMsgVerb(pAPriv->pScrn->scrnIndex, X_INFO, 4,
+ "RestartVideo port=%d suspend\n", PORTNUM(pPPriv)));
+ pPPriv->VideoOn = -old_VideoOn; /* suspend (not off) */
+ }
+ }
+}
+
+static int
+Permedia2SetPortAttribute(ScrnInfoPtr pScrn,
+ Atom attribute, INT32 value, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+ int old_VideoStd, old_Plug;
+ int VideoStd = -1, Plug = 0;
+ int r;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "SPA attr=%d val=%d port=%d\n",
+ attribute, value, PORTNUM(pPPriv)));
+
+ if (attribute == xvFilter) {
+ pPPriv->Attribute[5] = !!value;
+ return Success;
+ } else if (attribute == xvAlpha) {
+ pPPriv->Attribute[7] = !!value;
+ return Success;
+ }
+
+ if (PORTNUM(pPPriv) >= 2)
+ return BadMatch;
+
+ if (attribute == xvInterlace) {
+ int old_value = pPPriv->Attribute[4];
+
+ value %= 3;
+
+ if (value != old_value) {
+ int old_VideoOn = ABS(pPPriv->VideoOn);
+#if 0
+ if (old_VideoOn)
+ return XvBadAlloc;
+#endif
+ StopVideoStream(pPPriv, FALSE);
+ FreeBuffers(pPPriv);
+ pPPriv->Attribute[4] = value;
+ RestartVideo(pPPriv, old_VideoOn);
+
+ if (pPPriv->VideoOn < 0 /* suspended */) {
+ pPPriv->Attribute[4] = old_value;
+ RestartVideo(pPPriv, old_VideoOn);
+ return XvBadAlloc;
+ }
+ }
+
+ return Success;
+ }
+
+ if (pPPriv == &pAPriv->Port[0]) {
+ /*
+ * Input
+ */
+ if (attribute == xvEncoding) {
+ if (value < 0 || value > ENTRIES(InputVideoEncodings))
+ return XvBadEncoding;
+
+ VideoStd = value / 3;
+ Plug = value % 3;
+
+ /* Fall through */
+
+ } else if (attribute == xvBrightness)
+ return SetAttr(&pAPriv->Port[0], 0, value);
+ else if (attribute == xvContrast)
+ return SetAttr(&pAPriv->Port[0], 1, value);
+ else if (attribute == xvSaturation)
+ return SetAttr(&pAPriv->Port[0], 2, value);
+ else if (attribute == xvHue)
+ return SetAttr(&pAPriv->Port[0], 3, value);
+ } else {
+ /*
+ * Output
+ */
+ if (attribute == xvEncoding) {
+ if (value < 0 || value > ENTRIES(OutputVideoEncodings))
+ return XvBadEncoding;
+
+ VideoStd = value / 2;
+ Plug = (value % 2) + 1;
+
+ /* Fall through */
+
+ } else if (attribute == xvBkgColor)
+ return SetBkgCol(pPPriv, value);
+#if 1
+ else if (attribute == xvBrightness ||
+ attribute == xvContrast ||
+ attribute == xvSaturation ||
+ attribute == xvHue)
+ return Success;
+#endif
+ }
+
+ if (attribute != xvEncoding)
+ return BadMatch;
+
+ old_VideoStd = pAPriv->VideoStd;
+ old_Plug = pPPriv->Plug;
+
+#if 0
+ if (pAPriv->Port[0].VideoOn ||
+ pAPriv->Port[1].VideoOn)
+ return XvBadAlloc;
+#endif
+
+ if (Plug != old_Plug)
+ if ((r = SetPlug(pPPriv, Plug)) != Success)
+ return r;
+
+ if (VideoStd != old_VideoStd) {
+ int old_VideoOn0 = ABS(pAPriv->Port[0].VideoOn);
+ int old_VideoOn1 = ABS(pAPriv->Port[1].VideoOn);
+
+ StopVideoStream(&pAPriv->Port[0], FALSE);
+ StopVideoStream(&pAPriv->Port[1], FALSE);
+
+ if (VideoStd == NTSC || pAPriv->VideoStd == NTSC) {
+ FreeBuffers(&pAPriv->Port[0]);
+ FreeBuffers(&pAPriv->Port[1]);
+ }
+
+ if (SetVideoStd(pPPriv, VideoStd) == Success) {
+ RestartVideo(&pAPriv->Port[0], old_VideoOn0);
+ RestartVideo(&pAPriv->Port[1], old_VideoOn1);
+ }
+
+ if (pAPriv->Port[0].VideoOn < 0 ||
+ pAPriv->Port[1].VideoOn < 0 ||
+ VideoStd != pAPriv->VideoStd) {
+ if (SetVideoStd(pPPriv, old_VideoStd) == Success) {
+ RestartVideo(&pAPriv->Port[0], old_VideoOn0);
+ RestartVideo(&pAPriv->Port[1], old_VideoOn1);
+ }
+
+ if (Plug != old_Plug)
+ SetPlug(pPPriv, old_Plug);
+
+ return XvBadAlloc;
+ }
+ }
+
+ return Success;
+}
+
+static void
+RestoreVideoStd(AdaptorPrivPtr pAPriv)
+{
+ if (pAPriv->Port[0].VideoOn && !pAPriv->Port[1].VideoOn &&
+ pAPriv->Port[0].VideoStdReq != pAPriv->VideoStd)
+ Permedia2SetPortAttribute(pAPriv->pScrn, xvEncoding,
+ pAPriv->Port[0].VideoStdReq * 3 + pAPriv->Port[0].Plug,
+ (pointer) &pAPriv->Port[0]);
+ else
+ if (pAPriv->Port[1].VideoOn && !pAPriv->Port[0].VideoOn &&
+ pAPriv->Port[1].VideoStdReq != pAPriv->VideoStd)
+ Permedia2SetPortAttribute(pAPriv->pScrn, xvEncoding,
+ pAPriv->Port[2].VideoStdReq * 2 + pAPriv->Port[1].Plug - 1,
+ (pointer) &pAPriv->Port[1]);
+}
+
+static int
+Permedia2GetPortAttribute(ScrnInfoPtr pScrn,
+ Atom attribute, INT32 *value, pointer data)
+{
+ PortPrivPtr pPPriv = (PortPrivPtr) data;
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+
+ if (PORTNUM(pPPriv) >= 2 &&
+ attribute != xvFilter &&
+ attribute != xvAlpha)
+ return BadMatch;
+
+ if (attribute == xvEncoding) {
+ if (pAPriv->VideoStd < 0)
+ return XvBadAlloc;
+ else
+ if (pPPriv == &pAPriv->Port[0])
+ *value = pAPriv->VideoStd * 3 + pPPriv->Plug;
+ else
+ *value = pAPriv->VideoStd * 2 + pPPriv->Plug - 1;
+ } else if (attribute == xvBrightness)
+ *value = pPPriv->Attribute[0];
+ else if (attribute == xvContrast)
+ *value = pPPriv->Attribute[1];
+ else if (attribute == xvSaturation)
+ *value = pPPriv->Attribute[2];
+ else if (attribute == xvHue)
+ *value = pPPriv->Attribute[3];
+ else if (attribute == xvInterlace)
+ *value = pPPriv->Attribute[4];
+ else if (attribute == xvFilter)
+ *value = pPPriv->Attribute[5];
+ else if (attribute == xvBkgColor)
+ *value = pPPriv->Attribute[6];
+ else if (attribute == xvAlpha)
+ *value = pPPriv->Attribute[7];
+ else
+ return BadMatch;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3,
+ "GPA attr=%d val=%d port=%d\n",
+ attribute, *value, PORTNUM(pPPriv)));
+
+ return Success;
+}
+
+static void
+Permedia2QueryBestSize(ScrnInfoPtr pScrn, Bool motion,
+ short vid_w, short vid_h, short drw_w, short drw_h,
+ unsigned int *p_w, unsigned int *p_h, pointer data)
+{
+ *p_w = drw_w;
+ *p_h = drw_h;
+}
+
+static int
+Permedia2QueryImageAttributes(ScrnInfoPtr pScrn,
+ int id, unsigned short *width, unsigned short *height,
+ int *pitches, int *offsets)
+{
+ int i, pitch;
+
+ *width = CLAMP(*width, 1, 2047);
+ *height = CLAMP(*height, 1, 2047);
+
+ if (offsets)
+ offsets[0] = 0;
+
+ switch (id) {
+ case LE4CC('Y','V','1','2'): /* Planar YVU 4:2:0 (emulated) */
+ *width = CLAMP((*width + 1) & ~1, 2, 2046);
+ *height = CLAMP((*height + 1) & ~1, 2, 2046);
+
+ pitch = *width; /* luma component */
+
+ if (offsets) {
+ offsets[1] = pitch * *height;
+ offsets[2] = offsets[1] + (offsets[1] >> 2);
+ }
+
+ if (pitches) {
+ pitches[0] = pitch;
+ pitches[1] = pitches[2] = pitch >> 1;
+ }
+
+ return pitch * *height * 3 / 2;
+
+ case LE4CC('Y','U','Y','2'): /* Packed YUYV 4:2:2 */
+ case LE4CC('U','Y','V','Y'): /* Packed UYVY 4:2:2 */
+ *width = CLAMP((*width + 1) & ~1, 2, 2046);
+
+ pitch = *width * 2;
+
+ if (pitches)
+ pitches[0] = pitch;
+
+ return pitch * *height;
+
+ default:
+ for (i = 0; i < ENTRIES(ScalerImages); i++)
+ if (ScalerImages[i].id == id)
+ break;
+
+ if (i >= ENTRIES(ScalerImages))
+ break;
+
+ pitch = *width * (ScalerImages[i].bits_per_pixel >> 3);
+
+ if (pitches)
+ pitches[0] = pitch;
+
+ return pitch * *height;
+ }
+
+ return 0;
+}
+
+static void
+RestoreVideo(AdaptorPrivPtr pAPriv)
+{
+ GLINTPtr pGlint = GLINTPTR(pAPriv->pScrn);
+
+ GLINT_WRITE_REG(pAPriv->dFifoControl, PMFifoControl);
+ GLINT_WRITE_REG(0, VSABase + VSControl);
+ GLINT_WRITE_REG(0, VSBBase + VSControl);
+ usleep(160000);
+ GLINT_MASK_WRITE_REG(VS_UnitMode_ROM, ~VS_UnitMode_Mask, VSConfiguration);
+}
+
+static void
+InitializeVideo(AdaptorPrivPtr pAPriv)
+{
+ GLINTPtr pGlint = GLINTPTR(pAPriv->pScrn);
+ int i;
+
+ GLINT_WRITE_REG(0, VSABase + VSControl);
+ GLINT_WRITE_REG(0, VSBBase + VSControl);
+
+#if 0
+ GLINT_MASK_WRITE_REG(0, ~(VSAIntFlag | VSBIntFlag), IntEnable);
+ GLINT_WRITE_REG(VSAIntFlag | VSBIntFlag, IntFlags); /* Reset */
+#endif
+
+ for (i = 0x0018; i <= 0x00B0; i += 8) {
+ GLINT_WRITE_REG(0, VSABase + i);
+ GLINT_WRITE_REG(0, VSBBase + i);
+ }
+
+ GLINT_WRITE_REG((0 << 8) | (132 << 0), VSABase + VSFifoControl);
+ GLINT_WRITE_REG((0 << 8) | (132 << 0), VSBBase + VSFifoControl);
+
+ GLINT_MASK_WRITE_REG(
+ VS_UnitMode_AB8 |
+ VS_GPBusMode_A |
+ /* VS_HRefPolarityA | */
+ VS_VRefPolarityA |
+ VS_VActivePolarityA |
+ /* VS_UseFieldA | */
+ VS_FieldPolarityA |
+ /* VS_FieldEdgeA | */
+ /* VS_VActiveVBIA | */
+ VS_InterlaceA |
+ VS_ReverseDataA |
+
+ /* VS_HRefPolarityB | */
+ VS_VRefPolarityB |
+ VS_VActivePolarityB |
+ /* VS_UseFieldB | */
+ VS_FieldPolarityB |
+ /* VS_FieldEdgeB | */
+ /* VS_VActiveVBIB | */
+ VS_InterlaceB |
+ /* VS_ColorSpaceB_RGB | */
+ /* VS_ReverseDataB | */
+ /* VS_DoubleEdgeB | */
+ 0, ~0x1FFFFE0F, VSConfiguration);
+
+ pAPriv->dFifoControl = GLINT_READ_REG(PMFifoControl);
+ GLINT_WRITE_REG((12 << 8) | 8, PMFifoControl);
+}
+
+static Bool
+xvipcHandshake(PortPrivPtr pPPriv, int op, Bool block)
+{
+ int r;
+ int brake = 150;
+
+ xvipc.magic = XVIPC_MAGIC;
+ xvipc.op = op;
+ xvipc.block = block;
+
+ if (pPPriv) {
+ AdaptorPrivPtr pAPriv = pPPriv->pAdaptor;
+
+ xvipc.pm2p = pAPriv->pm2p;
+ xvipc.pAPriv = pAPriv;
+ xvipc.port = PORTNUM(pPPriv);
+ } else {
+ xvipc.pm2p = (void *) -1;
+ xvipc.pAPriv = NULL;
+ xvipc.port = -1;
+ }
+
+ for (;;) {
+ if (brake-- <= 0)
+ return FALSE; /* I brake for bugs. */
+
+ DEBUG(xf86MsgVerb(X_INFO, 4,
+ "PM2 XVIPC send op=%d bl=%d po=%d a=%d b=%d c=%d\n",
+ xvipc.op, xvipc.block, xvipc.port, xvipc.a, xvipc.b, xvipc.c));
+
+ r = ioctl(xvipc_fd, VIDIOC_PM2_XVIPC, (void *) &xvipc);
+
+ DEBUG(xf86MsgVerb(X_INFO, 4,
+ "PM2 XVIPC recv op=%d bl=%d po=%d a=%d b=%d c=%d err=%d/%d\n",
+ xvipc.op, xvipc.block, xvipc.port, xvipc.a, xvipc.b, xvipc.c, r, errno));
+
+ switch (xvipc.op) {
+ case OP_ALLOC:
+ {
+ AdaptorPrivPtr pAPriv = xvipc.pAPriv;
+ ScrnInfoPtr pScrn = pAPriv->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ FBAreaPtr pFBArea = NULL;
+ LFBAreaPtr pLFBArea;
+
+ xvipc.a = -1;
+
+ pLFBArea = xalloc(sizeof(LFBAreaRec));
+
+ if (pLFBArea) {
+ pLFBArea->pFBArea = pFBArea =
+ xf86AllocateLinearOffscreenArea(pScrn->pScreen,
+ xvipc.b >> BPPSHIFT(pGlint), 2, NULL, NULL, NULL);
+
+ if (pFBArea) {
+ /* xvipc.a = pFBArea->linear; */
+ pLFBArea->Linear = xvipc.a =
+ ((pFBArea->box.y1 * pScrn->displayWidth) +
+ pFBArea->box.x1) << BPPSHIFT(pGlint);
+ } else
+ xfree(pLFBArea);
+ }
+
+ /* Report results */
+
+ if (ioctl(xvipc_fd, VIDIOC_PM2_XVIPC, (void *) &xvipc) != 0)
+ if (pFBArea) {
+ xf86FreeOffscreenArea(pFBArea);
+ xfree(pLFBArea);
+ pFBArea = NULL;
+ }
+
+ if (pFBArea) {
+ pLFBArea->Next = pAPriv->LFBList;
+ pAPriv->LFBList = pLFBArea;
+ }
+
+ DEBUG(xf86MsgVerb(X_INFO, 3, "PM2 XVIPC alloc addr=%d=0x%08x pFB=%p\n",
+ xvipc.a, xvipc.a, pFBArea));
+
+ goto event;
+ }
+
+ case OP_FREE:
+ {
+ AdaptorPrivPtr pAPriv = xvipc.pAPriv;
+ LFBAreaPtr pLFBArea, *ppLFBArea;
+
+ for (ppLFBArea = &pAPriv->LFBList; (pLFBArea = *ppLFBArea);
+ ppLFBArea = &pLFBArea->Next)
+ if (pLFBArea->Linear == xvipc.a)
+ break;
+
+ if (!pLFBArea)
+ xvipc.a = -1;
+
+ DEBUG(xf86MsgVerb(X_INFO, 3, "PM2 XVIPC free addr=%d=0x%08x pFB=%p\n",
+ xvipc.a, xvipc.a, pLFBArea ? pLFBArea->pFBArea : NULL));
+
+ if (ioctl(xvipc_fd, VIDIOC_PM2_XVIPC, (void *) &xvipc) == 0 && pLFBArea) {
+ xf86FreeOffscreenArea(pLFBArea->pFBArea);
+ *ppLFBArea = pLFBArea->Next;
+ xfree(pLFBArea);
+ }
+
+ goto event;
+ }
+
+ case OP_UPDATE:
+ {
+ AdaptorPrivPtr pAPriv = xvipc.pAPriv;
+ PortPrivPtr pPPriv;
+
+ pPPriv = &pAPriv->Port[0];
+
+ if (pPPriv->VideoOn > VIDEO_OFF && xvipc.a > 0) {
+ pPPriv->FrameAcc += pPPriv->FramesPerSec;
+ if (pPPriv->FrameAcc >= pAPriv->FramesPerSec) {
+ pPPriv->FrameAcc -= pAPriv->FramesPerSec;
+
+ /* Asynchronous resizing caused by kernel app */
+
+ if (xvipc.c != pPPriv->fw ||
+ xvipc.d != pPPriv->fh) {
+ pPPriv->vx = (pPPriv->vx * xvipc.c) / pPPriv->fw;
+ pPPriv->vw = (pPPriv->vw * xvipc.c) / pPPriv->fw;
+ pPPriv->vy = (pPPriv->vy * xvipc.d) / pPPriv->fh;
+ pPPriv->vh = (pPPriv->vh * xvipc.d) / pPPriv->fh;
+
+ pPPriv->fw = xvipc.c;
+ pPPriv->fh = xvipc.d;
+ pPPriv->BufferPProd = xvipc.e;
+
+ RemakePutCookies(pPPriv, NULL);
+ }
+
+ PutYUV(pPPriv, xvipc.a, FORMAT_YUYV, 1, 0);
+
+ if (pPPriv->VideoOn == VIDEO_ONE_SHOT)
+ pPPriv->VideoOn = VIDEO_OFF;
+ }
+ } else
+ if (pPPriv->StopDelay >= 0 && !(pPPriv->StopDelay--)) {
+ StopVideoStream(pPPriv, TRUE);
+ RestoreVideoStd(pAPriv);
+ }
+
+ pPPriv = &pAPriv->Port[1];
+
+ if (pPPriv->VideoOn > VIDEO_OFF && xvipc.b > 0) {
+ pPPriv->FrameAcc += pPPriv->FramesPerSec;
+ if (pPPriv->FrameAcc >= pAPriv->FramesPerSec) {
+ pPPriv->FrameAcc -= pAPriv->FramesPerSec;
+
+ pPPriv->BufferBase[0] = xvipc.b;
+
+ /* Output is always exclusive, no async resizing */
+
+ GetYUV(pPPriv);
+
+ if (pPPriv->VideoOn == VIDEO_ONE_SHOT)
+ pPPriv->VideoOn = VIDEO_OFF;
+ }
+ } else
+ if (pPPriv->StopDelay >= 0 && !(pPPriv->StopDelay--)) {
+ StopVideoStream(pPPriv, TRUE);
+ RestoreVideoStd(pAPriv);
+ }
+
+ /* Fall through */
+ }
+
+ default:
+ event:
+ if (xvipc.op == op)
+ return r == 0;
+
+ xvipc.op = OP_EVENT;
+ xvipc.block = block;
+ }
+ }
+
+ return TRUE;
+}
+
+static void
+Permedia2ReadInput(int fd, pointer unused)
+{
+ xvipcHandshake(NULL, OP_EVENT, FALSE);
+}
+
+static Bool
+xvipcOpen(char *name, ScrnInfoPtr pScrn)
+{
+ const char *osname;
+
+ if (xvipc_fd >= 0)
+ return TRUE;
+
+ xf86GetOS(&osname, NULL, NULL, NULL);
+
+ if (!osname || strcmp(osname, "linux"))
+ return FALSE;
+
+ for (;;) {
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 2,
+ "XVIPC probing device %s\n", name));
+
+ if ((xvipc_fd = open(name, O_RDWR /* | O_TRUNC */, 0)) < 0)
+ break;
+
+ xvipc.magic = XVIPC_MAGIC;
+ xvipc.pm2p = (void *) -1;
+ xvipc.pAPriv = NULL;
+ xvipc.op = OP_CONNECT;
+ xvipc.a = 0;
+ xvipc.b = 0;
+ xvipc.c = 0;
+ xvipc.d = 0;
+
+ if (ioctl(xvipc_fd, VIDIOC_PM2_XVIPC, (void *) &xvipc) < 0 || xvipc.pm2p)
+ break;
+
+ if (xvipc.c != XVIPC_VERSION) {
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
+ "Your Permedia 2 kernel driver %d.%d uses XVIPC protocol "
+ "V.%d while this Xv driver expects V.%d. Please update.\n",
+ xvipc.a, xvipc.b, xvipc.c, XVIPC_VERSION);
+ break;
+ }
+
+ xf86AddInputHandler(xvipc_fd, Permedia2ReadInput, NULL);
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Xv driver opened %s\n", name);
+
+ return TRUE;
+ }
+
+ if (xvipc_fd >= 0)
+ close(xvipc_fd);
+
+ xvipc_fd = -1;
+
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Cannot find Permedia 2 kernel driver.\n");
+
+ return FALSE;
+}
+
+static void
+DeleteAdaptorPriv(AdaptorPrivPtr pAPriv)
+{
+ int i;
+
+ if (pAPriv->VideoIO) {
+ StopVideoStream(&pAPriv->Port[0], TRUE);
+ StopVideoStream(&pAPriv->Port[1], TRUE);
+ }
+
+ for (i = 0; i < 6; i++) {
+ FreeBuffers(&pAPriv->Port[i]);
+ FreeCookies(&pAPriv->Port[i]);
+ }
+
+ TimerFree(pAPriv->Timer);
+
+ if (pAPriv->VideoIO) {
+ if (pAPriv->pm2p)
+ xvipcHandshake(&pAPriv->Port[0], OP_DISCONNECT, TRUE);
+ else {
+ xf86DestroyI2CDevRec(&pAPriv->Port[0].I2CDev, FALSE);
+ xf86DestroyI2CDevRec(&pAPriv->Port[1].I2CDev, FALSE);
+
+ RestoreVideo(pAPriv);
+ }
+ }
+
+ xfree(pAPriv);
+}
+
+static AdaptorPrivPtr
+NewAdaptorPriv(ScrnInfoPtr pScrn, Bool VideoIO)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ AdaptorPrivPtr pAPriv = (AdaptorPrivPtr) xcalloc(1, sizeof(AdaptorPrivRec));
+ int i;
+
+ if (!pAPriv)
+ return NULL;
+
+ pAPriv->pScrn = pScrn;
+
+ for (i = 0; i < PORTS; i++)
+ pAPriv->Port[i].pAdaptor = pAPriv;
+
+ switch (pScrn->depth) {
+ case 8:
+ pAPriv->dDitherMode =
+ (0 << 10) | /* BGR */
+ (1 << 1) | /* Dither */
+ ((5 & 0x10) << 12) |
+ ((5 & 0x0F) << 2) | /* 3:3:2f */
+ UNIT_ENABLE;
+ pAPriv->dAlphaBlendMode =
+ (0 << 13) |
+ ((5 & 0x10) << 12) |
+ ((5 & 0x0F) << 8) |
+ (84 << 1) | /* Blend (decal) RGB */
+ UNIT_ENABLE;
+ pAPriv->dTextureDataFormat =
+ (1 << 4) | /* No alpha */
+ ((14 & 0x10) << 2) |
+ ((14 & 0x0F) << 0); /* CI8 */
+ break;
+
+ case 15:
+ pAPriv->dDitherMode =
+ (1 << 10) | /* RGB */
+ ((1 & 0x10) << 12) |
+ ((1 & 0x0F) << 2) | /* 5:5:5:1f */
+ UNIT_ENABLE;
+ pAPriv->dAlphaBlendMode =
+ (1 << 13) |
+ ((1 & 0x10) << 12) |
+ ((1 & 0x0F) << 8) |
+ (84 << 1) |
+ UNIT_ENABLE;
+ pAPriv->dTextureDataFormat =
+ (1 << 5) | /* RGB */
+ (1 << 4) |
+ ((1 & 0x10) << 2) |
+ ((1 & 0x0F) << 0);
+ break;
+
+ case 16:
+ pAPriv->dDitherMode =
+ (1 << 10) | /* RGB */
+ ((16 & 0x10) << 12) |
+ ((16 & 0x0F) << 2) | /* 5:6:5f */
+ UNIT_ENABLE;
+ pAPriv->dAlphaBlendMode =
+ (1 << 13) |
+ ((16 & 0x10) << 12) |
+ ((16 & 0x0F) << 8) |
+ (84 << 1) |
+ UNIT_ENABLE;
+ pAPriv->dTextureDataFormat =
+ (1 << 5) |
+ (1 << 4) |
+ ((16 & 0x10) << 2) |
+ ((16 & 0x0F) << 0);
+ break;
+
+ case 24:
+ pAPriv->dDitherMode =
+ (1 << 10) | /* RGB */
+ ((0 & 0x10) << 12) |
+ ((0 & 0x0F) << 2) | /* 8:8:8:8 */
+ UNIT_ENABLE;
+ pAPriv->dAlphaBlendMode =
+ (1 << 13) |
+ ((0 & 0x10) << 12) |
+ ((0 & 0x0F) << 8) |
+ (84 << 1) |
+ UNIT_ENABLE;
+ pAPriv->dTextureDataFormat =
+ (1 << 5) |
+ (1 << 4) |
+ ((0 & 0x10) << 2) |
+ ((0 & 0x0F) << 0);
+ break;
+
+ default:
+ xfree(pAPriv);
+ return NULL;
+ }
+
+ pAPriv->VideoIO = VideoIO;
+
+ if (VideoIO) {
+ if (xvipc_fd >= 0) {
+ /* Initial handshake, take over control of this head */
+
+ xvipc.magic = XVIPC_MAGIC;
+ xvipc.pm2p = (void *) -1; /* Kernel head ID */
+ xvipc.pAPriv = pAPriv; /* Server head ID */
+ xvipc.op = OP_CONNECT;
+
+ xvipc.a = pGlint->PciInfo->bus;
+ xvipc.b = pGlint->PciInfo->device;
+ xvipc.c = pGlint->PciInfo->func;
+
+ xvipc.d = pScrn->videoRam << 10; /* XF86Config overrides probing */
+
+ if (ioctl(xvipc_fd, VIDIOC_PM2_XVIPC, (void *) &xvipc) < 0) {
+ if (errno == EBUSY)
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
+ "Another application already opened the Permedia 2 "
+ "kernel driver for this board. To enable "
+ "shared access please start the server first.\n");
+ else
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
+ "Failed to initialize kernel backbone "
+ "due to error %d: %s.\n", errno, strerror(errno));
+ goto failed;
+ }
+
+ pAPriv->pm2p = xvipc.pm2p;
+ } else {
+ InitializeVideo(pAPriv);
+
+ if (!xf86I2CProbeAddress(pGlint->VSBus, SAA7111_SLAVE_ADDRESS))
+ goto failed;
+
+ pAPriv->Port[0].I2CDev.DevName = "Decoder SAA 7111A";
+ pAPriv->Port[0].I2CDev.SlaveAddr = SAA7111_SLAVE_ADDRESS;
+ pAPriv->Port[0].I2CDev.pI2CBus = pGlint->VSBus;
+
+ if (!xf86I2CDevInit(&pAPriv->Port[0].I2CDev))
+ goto failed;
+
+ if (!xf86I2CWriteVec(&pAPriv->Port[0].I2CDev, DecInitVec, ENTRIES(DecInitVec) / 2))
+ goto failed;
+
+ if (!xf86I2CProbeAddress(pGlint->VSBus, SAA7125_SLAVE_ADDRESS))
+ goto failed;
+
+ pAPriv->Port[1].I2CDev.DevName = "Encoder SAA 7125";
+ pAPriv->Port[1].I2CDev.SlaveAddr = SAA7125_SLAVE_ADDRESS;
+ pAPriv->Port[1].I2CDev.pI2CBus = pGlint->VSBus;
+
+ if (!xf86I2CDevInit(&pAPriv->Port[1].I2CDev))
+ goto failed;
+
+ if (!xf86I2CWriteVec(&pAPriv->Port[1].I2CDev, EncInitVec, ENTRIES(EncInitVec) / 2))
+ goto failed;
+ }
+
+ if (SetVideoStd(&pAPriv->Port[0], PAL) != Success ||
+ SetPlug(&pAPriv->Port[0], 0) != Success || /* composite */
+ SetPlug(&pAPriv->Port[1], 1) != Success) /* composite-adaptor */
+ goto failed;
+
+ pAPriv->Port[1].VideoStdReq = pAPriv->Port[0].VideoStdReq;
+
+ pAPriv->Port[0].BuffersRequested = 2;
+ pAPriv->Port[1].BuffersRequested = 1;
+
+ for (i = 0; i < 2; i++) {
+ pAPriv->Port[i].fw = 704;
+ pAPriv->Port[i].fh = 576;
+ pAPriv->Port[i].FramesPerSec = 30;
+ pAPriv->Port[i].BufferPProd = partprodPermedia[704 >> 5];
+ }
+
+ SetAttr(&pAPriv->Port[0], 0, 0); /* Brightness (-1000..+1000) */
+ SetAttr(&pAPriv->Port[0], 1, 0); /* Contrast (-3000..+1000) */
+ SetAttr(&pAPriv->Port[0], 2, 0); /* Color saturation (-3000..+1000) */
+ SetAttr(&pAPriv->Port[0], 3, 0); /* Hue (-1000..+1000) */
+
+ pAPriv->Port[0].Attribute[4] = 1; /* Interlaced (0 = not, 1 = yes,
+ 2 = double scan 50/60 Hz) */
+ pAPriv->Port[0].Attribute[5] = 0; /* Bilinear Filter (Bool) */
+
+ pAPriv->Port[1].Attribute[4] = 1; /* Interlaced (Bool) */
+ pAPriv->Port[1].Attribute[5] = 0; /* Bilinear Filter (Bool) */
+
+ SetBkgCol(&pAPriv->Port[1], 0x000000); /* BkgColor 0x00RRGGBB */
+ } /* VideoIO */
+
+ if (!(pAPriv->Timer = TimerSet(NULL, 0, 0, TimerCallback, pAPriv)))
+ goto failed;
+
+ for (i = 0; i < PORTS; i++)
+ pAPriv->Port[i].StopDelay = -1;
+
+ /* Frontend scaler */
+
+ for (i = 2; i < 6; i++) {
+ pAPriv->Port[i].fw = 0;
+ pAPriv->Port[i].fh = 0;
+ pAPriv->Port[i].BuffersRequested = 1;
+ pAPriv->Delay = 125;
+ pAPriv->Instant = 1000 / 25;
+
+ if (!VideoIO || pAPriv->pm2p) {
+ pAPriv->Delay = 5;
+ pAPriv->Instant = 1000;
+ }
+
+ pAPriv->Port[i].Attribute[5] = 0; /* Bilinear Filter (Bool) */
+ pAPriv->Port[i].Attribute[7] = 0; /* Alpha Enable (Bool) */
+ }
+
+ return pAPriv;
+
+failed:
+
+ DeleteAdaptorPriv(pAPriv);
+
+ return NULL;
+}
+
+
+/*
+ * Glint interface
+ */
+
+void
+Permedia2VideoEnterVT(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ AdaptorPrivPtr pAPriv;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 2, "Xv enter VT\n"));
+
+ for (pAPriv = AdaptorPrivList; pAPriv != NULL; pAPriv = pAPriv->Next)
+ if (pAPriv->pScrn == pScrn) {
+ if (pAPriv->VideoIO) {
+ if (pAPriv->pm2p)
+ xvipcHandshake(&pAPriv->Port[0], OP_ENTER, TRUE);
+ else {
+ InitializeVideo(pAPriv);
+
+ xf86I2CWriteVec(&pAPriv->Port[1].I2CDev, EncInitVec, ENTRIES(EncInitVec) / 2);
+ }
+
+ SetVideoStd(&pAPriv->Port[0], pAPriv->VideoStd);
+ SetPlug(&pAPriv->Port[0], pAPriv->Port[0].Plug);
+ SetPlug(&pAPriv->Port[1], pAPriv->Port[1].Plug);
+ }
+
+ if (pGlint->NoAccel)
+ Permedia2InitializeEngine(pScrn);
+
+ break;
+ }
+}
+
+void
+Permedia2VideoLeaveVT(ScrnInfoPtr pScrn)
+{
+ AdaptorPrivPtr pAPriv;
+
+ for (pAPriv = AdaptorPrivList; pAPriv != NULL; pAPriv = pAPriv->Next)
+ if (pAPriv->pScrn == pScrn) {
+ if (pAPriv->VideoIO) {
+ StopVideoStream(&pAPriv->Port[0], TRUE);
+ StopVideoStream(&pAPriv->Port[1], TRUE);
+
+ if (pAPriv->pm2p)
+ xvipcHandshake(&pAPriv->Port[0], OP_LEAVE, TRUE);
+ else
+ RestoreVideo(pAPriv);
+ }
+ break;
+ }
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 2, "Elvis left the building\n"));
+}
+
+void
+Permedia2VideoUninit(ScrnInfoPtr pScrn)
+{
+ AdaptorPrivPtr pAPriv, *ppAPriv;
+
+ for (ppAPriv = &AdaptorPrivList; (pAPriv = *ppAPriv); ppAPriv = &(pAPriv->Next))
+ if (pAPriv->pScrn == pScrn) {
+ *ppAPriv = pAPriv->Next;
+ DeleteAdaptorPriv(pAPriv);
+ break;
+ }
+
+ if (xvipc_fd >= 0) {
+ close(xvipc_fd);
+ xvipc_fd = -1;
+ }
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 2, "Xv cleanup\n"));
+}
+
+void
+Permedia2VideoInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ AdaptorPrivPtr pAPriv;
+ pointer options[3];
+ DevUnion Private[PORTS];
+ XF86VideoAdaptorRec VAR[ADAPTORS];
+ XF86VideoAdaptorPtr VARPtrs[ADAPTORS];
+ Bool VideoIO = TRUE;
+ int i;
+
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_TI_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2:
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V:
+ break;
+
+ default:
+ return;
+ }
+
+ options[0] = NULL; /* VideoAdaptor "input" subsection options */
+ options[1] = NULL; /* VideoAdaptor "output" subsection options */
+ options[2] = NULL; /* VideoAdaptor options */
+
+ for (i = 0;; i++) {
+ char *adaptor; /* receives VideoAdaptor section identifier */
+
+ if (!options[0])
+ options[0] = xf86FindXvOptions(pScreen->myNum, i, "input", &adaptor, options[2] ? NULL : &options[2]);
+
+ if (!options[1])
+ options[1] = xf86FindXvOptions(pScreen->myNum, i, "output", &adaptor, options[2] ? NULL : &options[2]);
+
+ if (!adaptor) {
+ if (!i) /* VideoAdaptor reference enables Xv vio driver */
+ VideoIO = FALSE;
+ break;
+ } else if (options[0] && options[1])
+ break;
+ }
+
+ if (VideoIO)
+ switch (pciReadLong(pGlint->PciTag, PCI_SUBSYSTEM_ID_REG)) {
+ case PCI_SUBSYSTEM_ID_WINNER_2000_P2A:
+ case PCI_SUBSYSTEM_ID_WINNER_2000_P2C:
+ case PCI_SUBSYSTEM_ID_GLORIA_SYNERGY_P2A:
+ case PCI_SUBSYSTEM_ID_GLORIA_SYNERGY_P2C:
+ break;
+
+ default:
+ xf86DrvMsgVerb(pScrn->scrnIndex, X_PROBED, 1, "No Xv vio support for this board\n");
+ VideoIO = FALSE;
+ }
+
+ if (pGlint->NoAccel && !VideoIO)
+ return;
+
+ xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 1, "Initializing Xv driver rev. 4\n");
+
+ if (VideoIO) {
+ for (i = 0; i <= 2; i++) {
+ xf86ProcessOptions(pScrn->scrnIndex, options[i],
+ (i == 0) ? InputOptions :
+ (i == 1) ? OutputOptions :
+ AdaptorOptions);
+
+ xf86ShowUnusedOptions(pScrn->scrnIndex, options[i]);
+ }
+
+ if (xf86IsOptionSet(AdaptorOptions, OPTION_DEVICE)) {
+ if (!xvipcOpen(xf86GetOptValString(AdaptorOptions, OPTION_DEVICE), pScrn))
+ VideoIO = FALSE;
+ }
+ }
+
+ if (!(pAPriv = NewAdaptorPriv(pScrn, VideoIO))) {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Xv driver initialization failed\n");
+ return;
+ }
+
+ if (VideoIO) {
+ int n;
+
+ if (xf86GetOptValInteger(InputOptions, OPTION_BUFFERS, &n))
+ pAPriv->Port[0].BuffersRequested = CLAMP(n, 1, 2);
+ if (xf86GetOptValInteger(InputOptions, OPTION_FPS, &n))
+ pAPriv->Port[0].FramesPerSec = CLAMP(n, 1, 30);
+
+ if (xf86GetOptValInteger(OutputOptions, OPTION_BUFFERS, &n))
+ pAPriv->Port[1].BuffersRequested = 1;
+ if (xf86GetOptValInteger(OutputOptions, OPTION_FPS, &n))
+ pAPriv->Port[1].FramesPerSec = CLAMP(n, 1, 30);
+ }
+
+ if (pGlint->NoAccel) {
+ BoxRec AvailFBArea;
+
+ xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Xv driver overrides NoAccel option\n");
+
+ Permedia2InitializeEngine(pScrn);
+
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = 0;
+ AvailFBArea.x2 = pScrn->displayWidth;
+ AvailFBArea.y2 = pGlint->FbMapSize /
+ (pScrn->displayWidth * pScrn->bitsPerPixel / 8);
+
+ xf86InitFBManager(pScreen, &AvailFBArea);
+ }
+
+#if defined(XFree86LOADER) && 0
+ if (xf86LoaderCheckSymbol("xf86InitLinearFBManagerRegion")) {
+ int last = pGlint->FbMapSize / (pScrn->bitsPerPixel / 8) - 1;
+ BoxRec AvailFBArea;
+ RegionPtr Region;
+
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = pScrn->virtualY;
+ AvailFBArea.x2 = last % pScrn->displayWidth + 1;
+ AvailFBArea.y2 = last / pScrn->displayWidth + 1;
+
+ DEBUG(xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 2,
+ "Using linear FB %d,%d-%d,%d pitch %d (%dk)\n",
+ AvailFBArea.x1, AvailFBArea.y1, AvailFBArea.x2, AvailFBArea.y2,
+ pScrn->displayWidth, (((AvailFBArea.y2 - AvailFBArea.y1)
+ * pScrn->displayWidth) << BPPSHIFT(pGlint)) / 1024));
+
+ Region = xf86LinearFBRegion(pScreen, &AvailFBArea, pScrn->displayWidth);
+ xf86InitLinearFBManagerRegion(pScreen, Region);
+ REGION_DESTROY(pScreen, Region);
+ }
+#endif
+
+ memset(VAR, 0, sizeof(VAR));
+
+ for (i = 0; i < PORTS; i++)
+ Private[i].ptr = (pointer) &pAPriv->Port[i];
+
+ for (i = 0; i < ADAPTORS; i++) {
+ VARPtrs[i] = &VAR[i];
+ switch (i) {
+ case 0:
+ VAR[i].name = "Permedia 2 Video Input";
+ VAR[i].type = XvInputMask | XvWindowMask | XvVideoMask | XvStillMask;
+ VAR[i].nPorts = 1;
+ VAR[i].pPortPrivates = &Private[0];
+ VAR[i].nAttributes = ENTRIES(InputVideoAttributes);
+ VAR[i].pAttributes = InputVideoAttributes;
+ VAR[i].nEncodings = ENTRIES(InputVideoEncodings);
+ VAR[i].pEncodings = InputVideoEncodings;
+ VAR[i].nFormats = ENTRIES(InputVideoFormats);
+ VAR[i].pFormats = InputVideoFormats;
+ break;
+
+ case 1:
+ VAR[i].name = "Permedia 2 Video Output";
+ VAR[i].type = XvOutputMask | XvWindowMask | XvVideoMask | XvStillMask;
+ VAR[i].nPorts = 1;
+ VAR[i].pPortPrivates = &Private[1];
+ VAR[i].nAttributes = ENTRIES(OutputVideoAttributes);
+ VAR[i].pAttributes = OutputVideoAttributes;
+ VAR[i].nEncodings = ENTRIES(OutputVideoEncodings);
+ VAR[i].pEncodings = OutputVideoEncodings;
+ VAR[i].nFormats = ENTRIES(OutputVideoFormats);
+ VAR[i].pFormats = OutputVideoFormats;
+ break;
+
+ case 2:
+ VAR[i].name = "Permedia 2 Frontend Scaler";
+ VAR[i].type = XvInputMask | XvWindowMask | XvImageMask;
+ VAR[i].nPorts = 3;
+ VAR[i].pPortPrivates = &Private[2];
+ VAR[i].nAttributes = ENTRIES(ScalerAttributes);
+ VAR[i].pAttributes = ScalerAttributes;
+ VAR[i].nEncodings = ENTRIES(ScalerEncodings);
+ VAR[i].pEncodings = ScalerEncodings;
+ VAR[i].nFormats = ENTRIES(ScalerVideoFormats);
+ VAR[i].pFormats = ScalerVideoFormats;
+ VAR[i].nImages = ENTRIES(ScalerImages);
+ VAR[i].pImages = ScalerImages;
+ break;
+ }
+
+ VAR[i].PutVideo = Permedia2PutVideo;
+ VAR[i].PutStill = Permedia2PutStill;
+ VAR[i].GetVideo = Permedia2GetVideo;
+ VAR[i].GetStill = Permedia2GetStill;
+ VAR[i].StopVideo = Permedia2StopVideo;
+ VAR[i].SetPortAttribute = Permedia2SetPortAttribute;
+ VAR[i].GetPortAttribute = Permedia2GetPortAttribute;
+ VAR[i].QueryBestSize = Permedia2QueryBestSize;
+ VAR[i].PutImage = Permedia2PutImage;
+ VAR[i].QueryImageAttributes = Permedia2QueryImageAttributes;
+ }
+
+ if (VideoIO ? xf86XVScreenInit(pScreen, &VARPtrs[0], 3) :
+ xf86XVScreenInit(pScreen, &VARPtrs[2], 1)) {
+ char *s;
+
+ xvEncoding = MAKE_ATOM(XV_ENCODING);
+ xvHue = MAKE_ATOM(XV_HUE);
+ xvSaturation = MAKE_ATOM(XV_SATURATION);
+ xvBrightness = MAKE_ATOM(XV_BRIGHTNESS);
+ xvContrast = MAKE_ATOM(XV_CONTRAST);
+ xvInterlace = MAKE_ATOM(XV_INTERLACE);
+ xvFilter = MAKE_ATOM(XV_FILTER);
+ xvBkgColor = MAKE_ATOM(XV_BKGCOLOR);
+ xvAlpha = MAKE_ATOM(XV_ALPHA);
+
+ pAPriv->Next = AdaptorPrivList;
+ AdaptorPrivList = pAPriv;
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Xv frontend scaler enabled\n");
+
+ if (VideoIO) {
+ if ((s = xf86GetOptValString(InputOptions, OPTION_ENCODING)))
+ for (i = 0; i < ENTRIES(InputVideoEncodings); i++)
+ if (!strncmp(s, InputVideoEncodings[i].name, strlen(s))) {
+ Permedia2SetPortAttribute(pScrn, xvEncoding, i, (pointer) &pAPriv->Port[0]);
+ break;
+ }
+
+ if ((s = xf86GetOptValString(OutputOptions, OPTION_ENCODING)))
+ for (i = 0; i < ENTRIES(OutputVideoEncodings); i++)
+ if (!strncmp(s, OutputVideoEncodings[i].name, strlen(s))) {
+ Permedia2SetPortAttribute(pScrn, xvEncoding, i, (pointer) &pAPriv->Port[1]);
+ break;
+ }
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Xv vio driver %senabled\n",
+ pAPriv->pm2p ? "with kernel backbone " : "");
+ }
+ } else {
+ xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Xv initialization failed\n");
+ DeleteAdaptorPriv(pAPriv);
+ }
+}
+
+#endif /* XvExtension */
diff --git a/src/pm2ramdac.c b/src/pm2ramdac.c
new file mode 100644
index 0000000..dddfcaa
--- /dev/null
+++ b/src/pm2ramdac.c
@@ -0,0 +1,165 @@
+/*
+ * Copyright 1998 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ *
+ * Permedia2OutIndReg() and Permedia2InIndReg() are used to access
+ * the indirect Permedia2 RAMDAC registers only.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm2ramdac.c,v 1.11 2000/12/22 10:39:24 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+void
+Permedia2OutIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char tmp = 0x00;
+
+ GLINT_SLOW_WRITE_REG (reg, PM2DACIndexReg);
+
+ if (mask != 0x00)
+ tmp = GLINT_READ_REG (PM2DACIndexData) & mask;
+
+ GLINT_SLOW_WRITE_REG (tmp | data, PM2DACIndexData);
+}
+
+unsigned char
+Permedia2InIndReg (ScrnInfoPtr pScrn, CARD32 reg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char ret;
+
+ GLINT_SLOW_WRITE_REG (reg, PM2DACIndexReg);
+ ret = GLINT_READ_REG (PM2DACIndexData);
+
+ return (ret);
+}
+
+void
+Permedia2WriteAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(index, PM2DACWriteAddress);
+}
+
+void
+Permedia2WriteData (ScrnInfoPtr pScrn, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(data, PM2DACData);
+}
+
+void
+Permedia2ReadAddress (ScrnInfoPtr pScrn, CARD32 index)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_SLOW_WRITE_REG(0xFF, PM2DACReadMask);
+ GLINT_SLOW_WRITE_REG(index, PM2DACReadAddress);
+}
+
+unsigned char
+Permedia2ReadData (ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTDACDelay(5);
+ return(GLINT_READ_REG(PM2DACData));
+}
+
+void Permedia2LoadPalette(
+ ScrnInfoPtr pScrn,
+ int numColors,
+ int *indices,
+ LOCO *colors,
+ VisualPtr pVisual
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i, index, shift = 0, j, repeat = 1;
+
+ if (pScrn->depth == 15) {
+ repeat = 8;
+ shift = 3;
+ }
+
+ for(i = 0; i < numColors; i++) {
+ index = indices[i];
+ for (j = 0; j < repeat; j++) {
+ Permedia2WriteAddress(pScrn, (index << shift)+j);
+ Permedia2WriteData(pScrn, colors[index].red);
+ Permedia2WriteData(pScrn, colors[index].green);
+ Permedia2WriteData(pScrn, colors[index].blue);
+ }
+ /* for video i/o */
+ GLINT_SLOW_WRITE_REG(index, TexelLUTIndex);
+ GLINT_SLOW_WRITE_REG((colors[index].red & 0xFF) |
+ ((colors[index].green & 0xFF) << 8) |
+ ((colors[index].blue & 0xFF) << 16),
+ TexelLUTData);
+ }
+}
+
+/* special one for 565 mode */
+void Permedia2LoadPalette16(
+ ScrnInfoPtr pScrn,
+ int numColors,
+ int *indices,
+ LOCO *colors,
+ VisualPtr pVisual
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i, index, j;
+
+ for(i = 0; i < numColors; i++) {
+ index = indices[i];
+ for (j = 0; j < 4; j++) {
+ Permedia2WriteAddress(pScrn, (index << 2)+j);
+ Permedia2WriteData(pScrn, colors[index >> 1].red);
+ Permedia2WriteData(pScrn, colors[index].green);
+ Permedia2WriteData(pScrn, colors[index >> 1].blue);
+ }
+ GLINT_SLOW_WRITE_REG(index, TexelLUTIndex);
+ GLINT_SLOW_WRITE_REG((colors[index].red & 0xFF) |
+ ((colors[index].green & 0xFF) << 8) |
+ ((colors[index].blue & 0xFF) << 16),
+ TexelLUTData);
+
+ if(index <= 31) {
+ for (j = 0; j < 4; j++) {
+ Permedia2WriteAddress(pScrn, (index << 3)+j);
+ Permedia2WriteData(pScrn, colors[index].red);
+ Permedia2WriteData(pScrn, colors[(index << 1) + 1].green);
+ Permedia2WriteData(pScrn, colors[index].blue);
+ }
+ }
+ }
+}
diff --git a/src/pm2v_dac.c b/src/pm2v_dac.c
new file mode 100644
index 0000000..0fd10ca
--- /dev/null
+++ b/src/pm2v_dac.c
@@ -0,0 +1,567 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane <alanh@fairlite.demon.co.uk>
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Helmut Fahrion, <hf@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm2v_dac.c,v 1.29 2002/05/07 23:15:59 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+static unsigned long
+PM2VDAC_CalculateClock
+(
+ unsigned long reqclock, /* In kHz units */
+ unsigned long refclock, /* In kHz units */
+ unsigned char *prescale, /* ClkPreScale */
+ unsigned char *feedback, /* ClkFeedBackScale */
+ unsigned char *postscale /* ClkPostScale */
+ )
+{
+ int f, pre, post;
+ unsigned long freq;
+ long freqerr = 1000;
+ unsigned long actualclock = 0;
+ unsigned char divide[5] = { 1, 2, 4, 8, 16 };
+
+ for (f=1;f<256;f++) {
+ for (pre=1;pre<256;pre++) {
+ for (post=0;post<2;post++) {
+ freq = ((refclock * f) / (pre * (1 << divide[post])));
+ if ((reqclock > freq - freqerr)&&(reqclock < freq + freqerr)){
+ freqerr = (reqclock > freq) ?
+ reqclock - freq : freq - reqclock;
+ *feedback = f;
+ *prescale = pre;
+ *postscale = post;
+ actualclock = freq;
+ }
+ }
+ }
+ }
+
+ return(actualclock);
+}
+
+static void
+Permedia2VPreInitSecondary(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /* disable MCLK */
+ Permedia2vOutIndReg(pScrn, PM2VDACRDMClkControl, 0x00, 0);
+
+ /* boot new mclk values */
+ Permedia2vOutIndReg(pScrn, PM2VDACRDMClkPreScale, 0x00, 0x09);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDMClkFeedbackScale, 0x00, 0x58);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDMClkPostScale, 0x00, 0x01);
+
+ /* re-enable MCLK */
+ Permedia2vOutIndReg(pScrn, PM2VDACRDMClkControl, 0x00, 1);
+
+ /* spin until locked MCLK */
+ while ( (Permedia2vInIndReg(pScrn, PM2VDACRDMClkControl) & 0x2) == 0);
+
+ /* Now re-boot the SGRAM's */
+ GLINT_SLOW_WRITE_REG(0xe6002021,PMMemConfig);
+ GLINT_SLOW_WRITE_REG(0x00000020,PMBootAddress);
+}
+
+void
+Permedia2VPreInit(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (IS_JPRO) {
+ /* Appian Jeronimo Pro 4x8mb (pm2v version) */
+ /* BIOS doesn't initialize the secondary heads, so we need to */
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "Appian Jeronimo Pro 4x8mb board detected and initialized.\n");
+
+ Permedia2VPreInitSecondary(pScrn);
+ }
+
+#if defined(__alpha__)
+ /*
+ * On Alpha, we have to init secondary PM2V cards, since
+ * int10 cannot be run on the OEMed cards with VGA disable
+ * jumpers.
+ */
+ if (!xf86IsPrimaryPci(pGlint->PciInfo)) {
+ if ( IS_QPM2V ) {
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "PM2V secondary: initializing\n");
+ Permedia2VPreInitSecondary(pScrn);
+ }
+ }
+#endif /* __alpha__ */
+}
+
+Bool
+Permedia2VInit(ScrnInfoPtr pScrn, DisplayModePtr mode)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTRegPtr pReg = &pGlint->ModeReg[0];
+ CARD32 temp1, temp2, temp3, temp4;
+
+ temp1 = 0;
+ temp2 = 0;
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ switch (pGlint->HwBpp) {
+ case 8:
+ case 24:
+ temp1 = 0x00;
+ temp2 = 0x00;
+ break;
+
+ case 15:
+ case 16:
+ temp1 = 0x02;
+ temp2 = 0x02;
+ break;
+
+ case 32:
+ temp1 = 0x01;
+ temp2 = 0x01;
+ break;
+ default:
+ break;
+ };
+#endif /* BIG_ENDIAN */
+
+ pReg->glintRegs[Aperture0 >> 3] = temp1;
+ pReg->glintRegs[Aperture1 >> 3] = temp2;
+
+ pReg->glintRegs[PMFramebufferWriteMask >> 3] = 0xFFFFFFFF;
+ pReg->glintRegs[PMBypassWriteMask >> 3] = 0xFFFFFFFF;
+
+ pReg->glintRegs[DFIFODis >> 3] = 0;
+ pReg->glintRegs[FIFODis >> 3] = 1;
+
+ if (pGlint->UseBlockWrite)
+ pReg->glintRegs[PMMemConfig >> 3] = GLINT_READ_REG(PMMemConfig) | 1<<21;
+
+ temp1 = mode->CrtcHSyncStart - mode->CrtcHDisplay;
+ temp2 = mode->CrtcVSyncStart - mode->CrtcVDisplay;
+ temp3 = mode->CrtcHSyncEnd - mode->CrtcHSyncStart;
+ temp4 = mode->CrtcVSyncEnd - mode->CrtcVSyncStart;
+
+ pReg->glintRegs[PMHTotal >> 3] = Shiftbpp(pScrn,mode->CrtcHTotal);
+ pReg->glintRegs[PMHsEnd >> 3] = Shiftbpp(pScrn, temp1 + temp3);
+ pReg->glintRegs[PMHsStart >> 3] = Shiftbpp(pScrn, temp1);
+ pReg->glintRegs[PMHbEnd >> 3] =
+ Shiftbpp(pScrn,mode->CrtcHTotal-mode->CrtcHDisplay);
+ pReg->glintRegs[PMScreenStride >> 3] =
+ Shiftbpp(pScrn,pScrn->displayWidth>>1);
+
+ pReg->glintRegs[PMVTotal >> 3] = mode->CrtcVTotal;
+ pReg->glintRegs[PMVsEnd >> 3] = temp2 + temp4;
+ pReg->glintRegs[PMVsStart >> 3] = temp2;
+ pReg->glintRegs[PMVbEnd >> 3] = mode->CrtcVTotal - mode->CrtcVDisplay;
+
+ /* The hw cursor needs /VSYNC to recognize vert retrace. We'll stick
+ both sync lines to active low here and if needed invert them
+ using the RAMDAC's RDSyncControl below. */
+ pReg->glintRegs[PMVideoControl >> 3] =
+ (1 << 5) | (1 << 3) | 1;
+
+ /* We stick the RAMDAC into 64bit mode */
+ /* And reduce the horizontal timings and clock by half */
+ pReg->glintRegs[PMVideoControl >> 3] |= 1<<16;
+ pReg->glintRegs[PMHTotal >> 3] >>= 1;
+ pReg->glintRegs[PMHsEnd >> 3] >>= 1;
+ pReg->glintRegs[PMHsStart >> 3] >>= 1;
+ pReg->glintRegs[PMHbEnd >> 3] >>= 1;
+
+ pReg->glintRegs[VClkCtl >> 3] = (GLINT_READ_REG(VClkCtl) & 0xFFFFFFFC);
+ pReg->glintRegs[PMScreenBase >> 3] = 0;
+ pReg->glintRegs[PMHTotal >> 3] -= 1;
+ pReg->glintRegs[PMHsStart >> 3] -= 1; /* PMHsStart */
+ pReg->glintRegs[PMVTotal >> 3] -= 1; /* PMVTotal */
+
+ pReg->glintRegs[ChipConfig >> 3] = GLINT_READ_REG(ChipConfig) & 0xFFFFFFDD;
+ pReg->DacRegs[PM2VDACRDDACControl] = 0x00;
+
+ {
+ /* Get the programmable clock values */
+ unsigned char m,n,p;
+ unsigned long clockused;
+
+ clockused = PM2VDAC_CalculateClock(mode->Clock/2,pGlint->RefClock,
+ &m,&n,&p);
+ pReg->DacRegs[PM2VDACRDDClk0PreScale] = m;
+ pReg->DacRegs[PM2VDACRDDClk0FeedbackScale] = n;
+ pReg->DacRegs[PM2VDACRDDClk0PostScale] = p;
+ }
+
+ pReg->glintRegs[PM2VDACRDIndexControl >> 3] = 0x00;
+
+ if (pScrn->rgbBits == 8)
+ pReg->DacRegs[PM2VDACRDMiscControl] = 0x01; /* 8bit DAC */
+ else
+ pReg->DacRegs[PM2VDACRDMiscControl] = 0x00; /* 6bit DAC */
+
+ pReg->DacRegs[PM2VDACRDSyncControl] = 0x00;
+ if (mode->Flags & V_PHSYNC)
+ pReg->DacRegs[PM2VDACRDSyncControl] |= 0x01; /* invert hsync */
+ if (mode->Flags & V_PVSYNC)
+ pReg->DacRegs[PM2VDACRDSyncControl] |= 0x08; /* invert vsync */
+
+ switch (pScrn->bitsPerPixel)
+ {
+ case 8:
+ pReg->DacRegs[PM2VDACRDPixelSize] = 0x00;
+ pReg->DacRegs[PM2VDACRDColorFormat] = 0x2E;
+ break;
+ case 16:
+ pReg->DacRegs[PM2VDACRDMiscControl] |= 0x08;
+ pReg->DacRegs[PM2VDACRDPixelSize] = 0x01;
+ if (pScrn->depth == 15)
+ pReg->DacRegs[PM2VDACRDColorFormat] = 0x61;
+ else
+ pReg->DacRegs[PM2VDACRDColorFormat] = 0x70;
+ break;
+ case 24:
+ pReg->DacRegs[PM2VDACRDMiscControl] |= 0x08;
+ pReg->DacRegs[PM2VDACRDPixelSize] = 0x04;
+ pReg->DacRegs[PM2VDACRDColorFormat] = 0x60;
+ break;
+ case 32:
+ pReg->DacRegs[PM2VDACRDMiscControl] |= 0x08;
+ pReg->DacRegs[PM2VDACRDPixelSize] = 0x02;
+ pReg->DacRegs[PM2VDACRDColorFormat] = 0x20;
+ if (pScrn->overlayFlags & OVERLAY_8_32_PLANAR) {
+ pReg->DacRegs[PM2VDACRDMiscControl] |= 0x18;
+ pReg->DacRegs[PM2VDACRDOverlayKey] = pScrn->colorKey;
+ }
+ break;
+ }
+
+ return(TRUE);
+}
+
+void
+Permedia2VSave(ScrnInfoPtr pScrn, GLINTRegPtr glintReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information */
+ memcpy((CARD8*)pGlint->VGAdata,(CARD8*)pGlint->FbBase, 65536);
+
+ glintReg->glintRegs[ChipConfig >> 3] = GLINT_READ_REG(ChipConfig);
+ glintReg->glintRegs[Aperture0 >> 3] = GLINT_READ_REG(Aperture0);
+ glintReg->glintRegs[Aperture1 >> 3] = GLINT_READ_REG(Aperture1);
+ glintReg->glintRegs[PMFramebufferWriteMask >> 3] =
+ GLINT_READ_REG(PMFramebufferWriteMask);
+ glintReg->glintRegs[PMBypassWriteMask >> 3] =
+ GLINT_READ_REG(PMBypassWriteMask);
+ glintReg->glintRegs[DFIFODis >> 3] = GLINT_READ_REG(DFIFODis);
+ glintReg->glintRegs[FIFODis >> 3] = GLINT_READ_REG(FIFODis);
+ /* We only muck about with PMMemConfig, if user wants to */
+ if (pGlint->UseBlockWrite)
+ glintReg->glintRegs[PMMemConfig >> 3] = GLINT_READ_REG(PMMemConfig);
+ glintReg->glintRegs[PMHTotal >> 3] = GLINT_READ_REG(PMHTotal);
+ glintReg->glintRegs[PMHbEnd >> 3] = GLINT_READ_REG(PMHbEnd);
+ glintReg->glintRegs[PMHbEnd >> 3] = GLINT_READ_REG(PMHgEnd);
+ glintReg->glintRegs[PMScreenStride >> 3] = GLINT_READ_REG(PMScreenStride);
+ glintReg->glintRegs[PMHsStart >> 3] = GLINT_READ_REG(PMHsStart);
+ glintReg->glintRegs[PMHsEnd >> 3] = GLINT_READ_REG(PMHsEnd);
+ glintReg->glintRegs[PMVTotal >> 3] = GLINT_READ_REG(PMVTotal);
+ glintReg->glintRegs[PMVbEnd >> 3] = GLINT_READ_REG(PMVbEnd);
+ glintReg->glintRegs[PMVsStart >> 3] = GLINT_READ_REG(PMVsStart);
+ glintReg->glintRegs[PMVsEnd >> 3] = GLINT_READ_REG(PMVsEnd);
+ glintReg->glintRegs[PMScreenBase >> 3] = GLINT_READ_REG(PMScreenBase);
+ glintReg->glintRegs[PMVideoControl >> 3] = GLINT_READ_REG(PMVideoControl);
+ glintReg->glintRegs[VClkCtl >> 3] = GLINT_READ_REG(VClkCtl);
+
+ for (i=0;i<768;i++) {
+ Permedia2ReadAddress(pScrn, i);
+ glintReg->cmap[i] = Permedia2ReadData(pScrn);
+ }
+
+ glintReg->glintRegs[PM2VDACRDIndexControl >> 3] =
+ GLINT_READ_REG(PM2VDACRDIndexControl);
+ glintReg->DacRegs[PM2VDACRDOverlayKey] =
+ Permedia2vInIndReg(pScrn, PM2VDACRDOverlayKey);
+ glintReg->DacRegs[PM2VDACRDSyncControl] =
+ Permedia2vInIndReg(pScrn, PM2VDACRDSyncControl);
+ glintReg->DacRegs[PM2VDACRDMiscControl] =
+ Permedia2vInIndReg(pScrn, PM2VDACRDMiscControl);
+ glintReg->DacRegs[PM2VDACRDDACControl] =
+ Permedia2vInIndReg(pScrn, PM2VDACRDDACControl);
+ glintReg->DacRegs[PM2VDACRDPixelSize] =
+ Permedia2vInIndReg(pScrn, PM2VDACRDPixelSize);
+ glintReg->DacRegs[PM2VDACRDColorFormat] =
+ Permedia2vInIndReg(pScrn, PM2VDACRDColorFormat);
+
+ glintReg->DacRegs[PM2VDACRDDClk0PreScale] = Permedia2vInIndReg(pScrn, PM2VDACRDDClk0PreScale);
+ glintReg->DacRegs[PM2VDACRDDClk0FeedbackScale] = Permedia2vInIndReg(pScrn, PM2VDACRDDClk0FeedbackScale);
+ glintReg->DacRegs[PM2VDACRDDClk0PostScale] = Permedia2vInIndReg(pScrn, PM2VDACRDDClk0PostScale);
+}
+
+void
+Permedia2VRestore(ScrnInfoPtr pScrn, GLINTRegPtr glintReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 temp;
+ int i;
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information */
+ if (pGlint->STATE)
+ memcpy((CARD8*)pGlint->FbBase,(CARD8*)pGlint->VGAdata, 65536);
+
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[ChipConfig >> 3], ChipConfig);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[Aperture0 >> 3], Aperture0);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[Aperture1 >> 3], Aperture1);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMFramebufferWriteMask >> 3],
+ PMFramebufferWriteMask);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMBypassWriteMask >> 3],
+ PMBypassWriteMask);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[DFIFODis >> 3], DFIFODis);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[FIFODis >> 3], FIFODis);
+ /* We only muck about with PMMemConfig, if user wants to */
+ if (pGlint->UseBlockWrite)
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMMemConfig >> 3],PMMemConfig);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVideoControl >> 3],
+ PMVideoControl);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHbEnd >> 3], PMHgEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMScreenBase >> 3], PMScreenBase);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[VClkCtl >> 3], VClkCtl);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMScreenStride >> 3],
+ PMScreenStride);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHTotal >> 3], PMHTotal);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHbEnd >> 3], PMHbEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHsStart >> 3], PMHsStart);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMHsEnd >> 3], PMHsEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVTotal >> 3], PMVTotal);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVbEnd >> 3], PMVbEnd);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVsStart >> 3], PMVsStart);
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PMVsEnd >> 3], PMVsEnd);
+
+ GLINT_SLOW_WRITE_REG(glintReg->glintRegs[PM2VDACRDIndexControl >> 3],
+ PM2VDACRDIndexControl);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDOverlayKey, 0x00,
+ glintReg->DacRegs[PM2VDACRDOverlayKey]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDSyncControl, 0x00,
+ glintReg->DacRegs[PM2VDACRDSyncControl]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDMiscControl, 0x00,
+ glintReg->DacRegs[PM2VDACRDMiscControl]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDDACControl, 0x00,
+ glintReg->DacRegs[PM2VDACRDDACControl]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDPixelSize, 0x00,
+ glintReg->DacRegs[PM2VDACRDPixelSize]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDColorFormat, 0x00,
+ glintReg->DacRegs[PM2VDACRDColorFormat]);
+
+ for (i=0;i<768;i++) {
+ Permedia2WriteAddress(pScrn, i);
+ Permedia2WriteData(pScrn, glintReg->cmap[i]);
+ }
+
+ temp = Permedia2vInIndReg(pScrn, PM2VDACIndexClockControl) & 0xFC;
+ Permedia2vOutIndReg(pScrn, PM2VDACRDDClk0PreScale, 0x00,
+ glintReg->DacRegs[PM2VDACRDDClk0PreScale]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDDClk0FeedbackScale, 0x00,
+ glintReg->DacRegs[PM2VDACRDDClk0FeedbackScale]);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDDClk0PostScale, 0x00,
+ glintReg->DacRegs[PM2VDACRDDClk0PostScale]);
+ Permedia2vOutIndReg(pScrn, PM2VDACIndexClockControl, 0x00, temp|0x03);
+}
+
+static void
+Permedia2vShowCursor(ScrnInfoPtr pScrn)
+{
+ /* Enable cursor - X11 mode */
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorMode, 0x00, 0x11);
+}
+
+static void Permedia2vLoadCursorCallback(ScrnInfoPtr pScrn);
+
+static void
+Permedia2vHideCursor(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /* Disable cursor - X11 mode */
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorMode, 0x00, 0x10);
+
+ /*
+ * For some reason, we need to clear the image as well as disable
+ * the cursor on PM2V, but not on PM3. The problem is noticeable
+ * only when running multi-head, as you can see the cursor get
+ * "left behind" on the screen it is leaving...
+ */
+ if (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA2V) {
+ memset(pGlint->HardwareCursorPattern, 0, 1024);
+ pGlint->LoadCursorCallback = Permedia2vLoadCursorCallback;
+ }
+}
+
+static void
+Permedia2vLoadCursorCallback(
+ ScrnInfoPtr pScrn
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ for (i=0; i<1024; i++)
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPattern+i, 0x00,
+ pGlint->HardwareCursorPattern[i]);
+
+ pGlint->LoadCursorCallback = NULL;
+}
+
+static void
+Permedia2vLoadCursorImage(
+ ScrnInfoPtr pScrn,
+ unsigned char *src
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ for (i=0; i<1024; i++)
+ pGlint->HardwareCursorPattern[i] = *(src++);
+
+ pGlint->LoadCursorCallback = Permedia2vLoadCursorCallback;
+}
+
+static void
+Permedia2vSetCursorPosition(
+ ScrnInfoPtr pScrn,
+ int x, int y
+)
+{
+ x += 64;
+ y += 64;
+ /* Output position - "only" 11 bits of location documented */
+
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorHotSpotX, 0x00, 0x3f);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorHotSpotY, 0x00, 0x3f);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorXLow, 0x00, x & 0xFF);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorXHigh, 0x00, (x>>8) & 0x0F);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorYLow, 0x00, y & 0xFF);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorYHigh, 0x00, (y>>8) & 0x0F);
+ Permedia2vOutIndReg(pScrn, PM2DACCursorControl, 0x00, 0x00);
+}
+
+static void
+Permedia2vCursorColorCallback(
+ ScrnInfoPtr pScrn
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int fg = pGlint->FGCursor;
+ int bg = pGlint->BGCursor;
+
+ if ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_PERMEDIA3) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA) &&
+ (pGlint->MultiChip == PCI_CHIP_PERMEDIA3)) ) {
+ /* PM3 uses last 2 indexes into hardware cursor palette fg first...*/
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+39, 0x00, (fg>>16)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+40, 0x00, (fg>>8)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+41, 0x00, fg & 0xff);
+
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+42, 0x00, (bg>>16)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+43, 0x00, (bg>>8)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+44, 0x00, bg & 0xff);
+ } else {
+ /* PM2v uses first 2 indexes into hardware cursor palette bg first...*/
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+0, 0x00, (bg>>16)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+1, 0x00, (bg>>8)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+2, 0x00, bg & 0xff);
+
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+3, 0x00, (fg>>16)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+4, 0x00, (fg>>8)&0xff);
+ Permedia2vOutIndReg(pScrn, PM2VDACRDCursorPalette+5, 0x00, fg & 0xff);
+ }
+ pGlint->CursorColorCallback = NULL;
+}
+
+static void
+Permedia2vSetCursorColors(
+ ScrnInfoPtr pScrn,
+ int bg, int fg
+)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->FGCursor = fg;
+ pGlint->BGCursor = bg;
+
+ pGlint->CursorColorCallback = Permedia2vCursorColorCallback;
+}
+
+static Bool
+Permedia2vUseHWCursor(ScreenPtr pScr, CursorPtr pCurs)
+{
+ return TRUE;
+}
+
+Bool
+Permedia2vHWCursorInit(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ xf86CursorInfoPtr infoPtr;
+
+ infoPtr = xf86CreateCursorInfoRec();
+ if(!infoPtr) return FALSE;
+
+ pGlint->CursorInfoRec = infoPtr;
+
+ infoPtr->MaxWidth = 64;
+ infoPtr->MaxHeight = 64;
+ infoPtr->Flags = HARDWARE_CURSOR_TRUECOLOR_AT_8BPP |
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ HARDWARE_CURSOR_BIT_ORDER_MSBFIRST |
+#endif
+ HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_1;
+ infoPtr->SetCursorColors = Permedia2vSetCursorColors;
+ infoPtr->SetCursorPosition = Permedia2vSetCursorPosition;
+ infoPtr->LoadCursorImage = Permedia2vLoadCursorImage;
+ infoPtr->HideCursor = Permedia2vHideCursor;
+ infoPtr->ShowCursor = Permedia2vShowCursor;
+ infoPtr->UseHWCursor = Permedia2vUseHWCursor;
+
+ return(xf86InitCursor(pScreen, infoPtr));
+}
diff --git a/src/pm2vramdac.c b/src/pm2vramdac.c
new file mode 100644
index 0000000..ae5b1d0
--- /dev/null
+++ b/src/pm2vramdac.c
@@ -0,0 +1,64 @@
+/*
+ * Copyright 1998 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ *
+ * Permedia2vOutIndReg() and Permedia2vInIndReg() are used to access
+ * the indirect Permedia2v RAMDAC registers only.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm2vramdac.c,v 1.6 2001/01/31 16:15:00 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+void
+Permedia2vOutIndReg(ScrnInfoPtr pScrn,
+ CARD32 reg, unsigned char mask, unsigned char data)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char tmp = 0x00;
+
+ GLINT_SET_INDEX(reg);
+
+ if (mask != 0x00)
+ tmp = GLINT_READ_REG (PM2VDACIndexData) & mask;
+
+ GLINT_WRITE_REG (tmp | data, PM2VDACIndexData);
+}
+
+unsigned char
+Permedia2vInIndReg (ScrnInfoPtr pScrn, CARD32 reg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char ret;
+
+ GLINT_SET_INDEX(reg);
+ ret = GLINT_READ_REG (PM2VDACIndexData);
+
+ return (ret);
+}
diff --git a/src/pm3_accel.c b/src/pm3_accel.c
new file mode 100644
index 0000000..9599590
--- /dev/null
+++ b/src/pm3_accel.c
@@ -0,0 +1,1223 @@
+/*
+ * Copyright 2000-2001 by Sven Luther <luther@dpt-info.u-strasbg.fr>.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Sven Luther not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Sven Luther makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * SVEN LUTHER DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL SVEN LUTHER BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Sven Luther, <luther@dpt-info.u-strasbg.fr>
+ * Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ *
+ * this work is sponsored by Appian Graphics.
+ *
+ * Permedia 3 accelerated options.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm3_accel.c,v 1.31 2003/01/06 00:04:54 alanh Exp $ */
+
+#include "Xarch.h"
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "miline.h"
+
+#include "fb.h"
+
+#include "glint_regs.h"
+#include "pm3_regs.h"
+#include "glint.h"
+
+#include "xaalocal.h" /* For replacements */
+
+#define DEBUG 0
+
+#if DEBUG
+# define TRACE_ENTER(str) ErrorF("pm3_accel: " str " %d\n",pScrn->scrnIndex)
+# define TRACE_EXIT(str) ErrorF("pm3_accel: " str " done\n")
+# define TRACE(str) ErrorF("pm3_accel trace: " str "\n")
+#else
+# define TRACE_ENTER(str)
+# define TRACE_EXIT(str)
+# define TRACE(str)
+#endif
+
+#define PM3_WRITEMASK \
+ (pGlint->PM3_UsingSGRAM ? PM3FBHardwareWriteMask : PM3FBSoftwareWriteMask )
+#define PM3_OTHERWRITEMASK \
+ (pGlint->PM3_UsingSGRAM ? PM3FBSoftwareWriteMask : PM3FBHardwareWriteMask )
+
+#ifndef XF86DRI
+#define PM3_PLANEMASK(planemask) \
+{ \
+ if (planemask != pGlint->planemask) { \
+ pGlint->planemask = planemask; \
+ REPLICATE(planemask); \
+ GLINT_WRITE_REG(planemask, PM3_WRITEMASK); \
+ } \
+}
+#else
+#define PM3_PLANEMASK(planemask) \
+ { \
+ pGlint->planemask = planemask; \
+ REPLICATE(planemask); \
+ GLINT_WRITE_REG(planemask, PM3_WRITEMASK); \
+ }
+#endif
+
+/* Clipping */
+static void Permedia3SetClippingRectangle(ScrnInfoPtr pScrn, int x, int y,
+ int w, int h);
+static void Permedia3DisableClipping(ScrnInfoPtr pScrn);
+/* ScreenToScreenCopy */
+static void Permedia3SubsequentScreenToScreenCopy(ScrnInfoPtr pScrn,
+ int x1, int y1, int x2,
+ int y2, int w, int h);
+static void Permedia3SetupForScreenToScreenCopy(ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask,
+ int transparency_color);
+/* SolidFill */
+static void Permedia3SetupForFillRectSolid(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask);
+static void Permedia3SubsequentFillRectSolid(ScrnInfoPtr pScrn, int x,
+ int y, int w, int h);
+static void Permedia3SubsequentFillRectSolid32bpp(ScrnInfoPtr pScrn, int x,
+ int y, int w, int h);
+/* 8x8 Mono Pattern Fills */
+static void Permedia3SetupForMono8x8PatternFill(ScrnInfoPtr pScrn,
+ int patternx, int patterny, int fg, int bg,
+ int rop, unsigned int planemask);
+static void Permedia3SubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn,
+ int x_offset, int y_offset, int x, int y,
+ int w, int h);
+static void Permedia3SetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg, int rop,
+ unsigned int planemask);
+static void Permedia3SubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn, int x,
+ int y, int w, int h, int skipleft);
+static void Permedia3SubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno);
+static void Permedia3SetupForScanlineImageWrite(ScrnInfoPtr pScrn, int rop,
+ unsigned int planemask, int trans_color,
+ int bpp, int depth);
+static void Permedia3SubsequentScanlineImageWriteRect(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h, int skipleft);
+static void Permedia3SubsequentImageWriteScanline(ScrnInfoPtr pScrn, int bufno);
+static void Permedia3RestoreAccelState(ScrnInfoPtr pScrn);
+static void Permedia3WritePixmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth, int rop,
+ unsigned int planemask, int transparency_color,
+ int bpp, int depth);
+static void Permedia3WriteBitmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth, int skipleft,
+ int fg, int bg, int rop,unsigned int planemask);
+
+void
+Permedia3InitializeEngine(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int colorformat = 0;
+
+ /* Initialize the Accelerator Engine to defaults */
+ TRACE_ENTER("Permedia3InitializeEngine");
+
+ if ((IS_J2000) && (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)) {
+ GLINT_SLOW_WRITE_REG(pGlint->MultiIndex, BroadcastMask);
+ }
+ if (pGlint->MultiAperture) {
+ ErrorF("pm3_accel: SVEN : multiAperture set\n");
+ /* Only write the following register to the first PM3 */
+ GLINT_SLOW_WRITE_REG(1, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(0x00000001, ScanLineOwnership);
+
+ /* Only write the following register to the second PM3 */
+ GLINT_SLOW_WRITE_REG(2, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(0x00000005, ScanLineOwnership);
+
+ /* Make sure the rest of the register writes go to both PM3's */
+ GLINT_SLOW_WRITE_REG(3, BroadcastMask);
+ }
+
+ /* Disable LocalBuffer. Fixes stripes problems when
+ * doing screen-to-screen copies */
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3LBDestReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3LBDestReadEnables);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3LBSourceReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3LBWriteMode);
+
+ /* Host out PreInit */
+ /* Set filter mode to enable sync tag & data output */
+ GLINT_SLOW_WRITE_REG(0x400, FilterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3DeltaMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LineStippleMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3GIDMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3TextureCoordMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3TextureIndexMode0);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3TextureIndexMode1);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3LUTMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureFilterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3TextureCompositeMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3TextureApplicationMode);
+ GLINT_SLOW_WRITE_REG(0, PM3TextureCompositeColorMode1);
+ GLINT_SLOW_WRITE_REG(0, PM3TextureCompositeAlphaMode1);
+ GLINT_SLOW_WRITE_REG(0, PM3TextureCompositeColorMode0);
+ GLINT_SLOW_WRITE_REG(0, PM3TextureCompositeAlphaMode0);
+
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FogMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ChromaTestMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaTestMode);
+ /* Not done in P3Lib ??? */
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, YUVMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3AlphaBlendColorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3AlphaBlendAlphaMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DitherMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PM3Window);
+
+ GLINT_SLOW_WRITE_REG(0, PM3Config2D);
+
+ GLINT_SLOW_WRITE_REG(0xffffffff, PM3SpanColorMask);
+
+ GLINT_SLOW_WRITE_REG(0, PM3XBias);
+ GLINT_SLOW_WRITE_REG(0, PM3YBias);
+
+ GLINT_SLOW_WRITE_REG(0, PM3DeltaControl);
+
+ GLINT_SLOW_WRITE_REG(0xffffffff, BitMaskPattern);
+
+ /* ScissorStippleUnit Initialization (is it needed ?) */
+ pGlint->ClippingOn = FALSE;
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
+ /* We never use Screen Scissor ...
+ GLINT_SLOW_WRITE_REG(
+ (pScrn->virtualX&0xffff)|((pScrn->virtualY&0xffff)<<16),
+ ScreenSize);
+ GLINT_SLOW_WRITE_REG(
+ (0&0xffff)|((0&0xffff)<<16),
+ WindowOrigin);
+ */
+
+ /* StencilDepthUnit Initialization */
+ GLINT_SLOW_WRITE_REG(0, PM3Window);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
+ GLINT_SLOW_WRITE_REG(0, StencilData);
+
+ /* FBReadUnit Initialization */
+ TRACE("Permedia3InitializeEngine : only syncs upto now");
+ GLINT_SLOW_WRITE_REG(
+ PM3FBDestReadEnables_E(0xff) |
+ PM3FBDestReadEnables_R(0xff) |
+ PM3FBDestReadEnables_ReferenceAlpha(0xff),
+ PM3FBDestReadEnables);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferAddr0);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferOffset0);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBDestReadBufferWidth_Width(pScrn->displayWidth),
+ PM3FBDestReadBufferWidth0);
+ /*
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferAddr1);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferOffset1);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBDestReadBufferWidth_Width(pScrn->displayWidth),
+ PM3FBDestReadBufferWidth1);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferAddr2);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferOffset2);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBDestReadBufferWidth_Width(pScrn->displayWidth),
+ PM3FBDestReadBufferWidth2);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferAddr3);
+ GLINT_SLOW_WRITE_REG(0, PM3FBDestReadBufferOffset3);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBDestReadBufferWidth_Width(pScrn->displayWidth),
+ PM3FBDestReadBufferWidth3);
+ */
+ GLINT_SLOW_WRITE_REG(
+ PM3FBDestReadMode_ReadEnable |
+ /* Not needed, since FBDestRead is the same as FBWrite.
+ PM3FBDestReadMode_Blocking |
+ */
+ PM3FBDestReadMode_Enable0,
+ PM3FBDestReadMode);
+ TRACE("Permedia3InitializeEngine : DestRead");
+ GLINT_SLOW_WRITE_REG(0, PM3FBSourceReadBufferAddr);
+ GLINT_SLOW_WRITE_REG(0, PM3FBSourceReadBufferOffset);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBSourceReadBufferWidth_Width(pScrn->displayWidth),
+ PM3FBSourceReadBufferWidth);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBSourceReadMode_Blocking |
+ PM3FBSourceReadMode_ReadEnable,
+ PM3FBSourceReadMode);
+ TRACE("Permedia3InitializeEngine : SourceRead");
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ pGlint->PM3_PixelSize = 2;
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ pGlint->RasterizerSwap = 3<<15; /* Swap host data */
+#endif
+ break;
+ case 16:
+ pGlint->PM3_PixelSize = 1;
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ pGlint->RasterizerSwap = 2<<15; /* Swap host data */
+#endif
+ break;
+ case 32:
+ pGlint->PM3_PixelSize = 0;
+ break;
+ }
+ GLINT_SLOW_WRITE_REG(pGlint->PM3_PixelSize, PixelSize);
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ GLINT_SLOW_WRITE_REG(1 | pGlint->RasterizerSwap, RasterizerMode);
+#endif
+ TRACE("Permedia3InitializeEngine : PixelSize");
+
+ /* LogicalOpUnit Initialization */
+ GLINT_SLOW_WRITE_REG(0xffffffff, PM3_OTHERWRITEMASK);
+
+ /* FBWriteUnit Initialization */
+ GLINT_SLOW_WRITE_REG(
+ PM3FBWriteMode_WriteEnable|
+ PM3FBWriteMode_OpaqueSpan|
+ PM3FBWriteMode_Enable0,
+ PM3FBWriteMode);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferAddr0);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferOffset0);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBWriteBufferWidth_Width(pScrn->displayWidth),
+ PM3FBWriteBufferWidth0);
+ /*
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferAddr1);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferOffset1);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBWriteBufferWidth_Width(pScrn->displayWidth),
+ PM3FBWriteBufferWidth1);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferAddr2);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferOffset2);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBWriteBufferWidth_Width(pScrn->displayWidth),
+ PM3FBWriteBufferWidth2);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferAddr3);
+ GLINT_SLOW_WRITE_REG(0, PM3FBWriteBufferOffset3);
+ GLINT_SLOW_WRITE_REG(
+ PM3FBWriteBufferWidth_Width(pScrn->displayWidth),
+ PM3FBWriteBufferWidth3);
+ */
+ TRACE("Permedia3InitializeEngine : FBWrite");
+ /* SizeOfframebuffer */
+ GLINT_SLOW_WRITE_REG(
+ pScrn->displayWidth *
+ (8 * pGlint->FbMapSize / (pScrn->bitsPerPixel * pScrn->displayWidth)
+ >4095?4095: 8 * pGlint->FbMapSize /
+ (pScrn->bitsPerPixel * pScrn->displayWidth)),
+ PM3SizeOfFramebuffer);
+ GLINT_SLOW_WRITE_REG(0xffffffff, PM3_WRITEMASK);
+ TRACE("Permedia3InitializeEngine : FBHardwareWriteMask & SizeOfFramebuffer");
+ /* Color Format */
+ switch (pScrn->depth) {
+ case 8:
+ colorformat = 4;
+ break;
+ case 15:
+ colorformat = 2;
+ break;
+ case 16:
+ colorformat = 3;
+ break;
+ case 24:
+ case 32:
+ colorformat = 0;
+ break;
+ }
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE|
+ ((colorformat&0xf)<<2)|(1<<10),
+ DitherMode);
+
+ /* Other stuff */
+ pGlint->startxdom = 0;
+ pGlint->startxsub = 0;
+ pGlint->starty = 0;
+ pGlint->count = 0;
+ pGlint->dy = 1<<16;
+ pGlint->dxdom = 0;
+ pGlint->x = 0;
+ pGlint->y = 0;
+ pGlint->h = 0;
+ pGlint->w = 0;
+ pGlint->ROP = 0xFF;
+ GLINT_SLOW_WRITE_REG(0, dXDom);
+ GLINT_SLOW_WRITE_REG(0, dXSub);
+ GLINT_SLOW_WRITE_REG(1<<16, dY);
+ GLINT_SLOW_WRITE_REG(0, StartXDom);
+ GLINT_SLOW_WRITE_REG(0, StartXSub);
+ GLINT_SLOW_WRITE_REG(0, StartY);
+ GLINT_SLOW_WRITE_REG(0, GLINTCount);
+ if (*pGlint->AccelInfoRec->Sync)
+ (*pGlint->AccelInfoRec->Sync)(pScrn);
+ TRACE_EXIT("Permedia3InitializeEngine");
+}
+
+Bool
+Permedia3AccelInit(ScreenPtr pScreen)
+{
+ XAAInfoRecPtr infoPtr;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->AccelInfoRec = infoPtr = XAACreateInfoRec();
+ if (!infoPtr) return FALSE;
+
+ /* Generic accel engine flags */
+ infoPtr->Flags = PIXMAP_CACHE |
+ OFFSCREEN_PIXMAPS |
+ LINEAR_FRAMEBUFFER;
+
+ /* Synchronization of the accel engine */
+ if (pGlint->MultiAperture)
+ infoPtr->Sync = DualPermedia3Sync;
+ else
+ infoPtr->Sync = Permedia3Sync;
+
+ Permedia3InitializeEngine(pScrn);
+
+ /* Clipping Setup */
+ infoPtr->ClippingFlags = 0;
+ infoPtr->SetClippingRectangle = Permedia3SetClippingRectangle;
+ infoPtr->DisableClipping = Permedia3DisableClipping;
+
+ /* ScreenToScreenCopy */
+ infoPtr->ScreenToScreenCopyFlags = NO_TRANSPARENCY;
+ infoPtr->SetupForScreenToScreenCopy =
+ Permedia3SetupForScreenToScreenCopy;
+ infoPtr->SubsequentScreenToScreenCopy =
+ Permedia3SubsequentScreenToScreenCopy;
+
+ /* SolidFill */
+ infoPtr->SolidFillFlags = 0;
+ infoPtr->SetupForSolidFill = Permedia3SetupForFillRectSolid;
+ infoPtr->SubsequentSolidFillRect = Permedia3SubsequentFillRectSolid;
+
+ /* 8x8 Mono Pattern Fills */
+ infoPtr->Mono8x8PatternFillFlags = HARDWARE_PATTERN_PROGRAMMED_BITS |
+ HARDWARE_PATTERN_PROGRAMMED_ORIGIN |
+ HARDWARE_PATTERN_SCREEN_ORIGIN |
+ BIT_ORDER_IN_BYTE_LSBFIRST;
+ infoPtr->SetupForMono8x8PatternFill =
+ Permedia3SetupForMono8x8PatternFill;
+ infoPtr->SubsequentMono8x8PatternFillRect =
+ Permedia3SubsequentMono8x8PatternFillRect;
+
+ infoPtr->ScanlineCPUToScreenColorExpandFillFlags =
+ LEFT_EDGE_CLIPPING |
+ LEFT_EDGE_CLIPPING_NEGATIVE_X |
+ BIT_ORDER_IN_BYTE_LSBFIRST |
+ CPU_TRANSFER_PAD_DWORD;
+
+ infoPtr->NumScanlineColorExpandBuffers = 1;
+ pGlint->ScratchBuffer = xalloc(((pScrn->virtualX+62)/32*4)
+ + (pScrn->virtualX
+ * pScrn->bitsPerPixel / 8));
+ infoPtr->ScanlineColorExpandBuffers =
+ pGlint->XAAScanlineColorExpandBuffers;
+ pGlint->XAAScanlineColorExpandBuffers[0] =
+ pGlint->IOBase + OutputFIFO + 4;
+
+ infoPtr->SetupForScanlineCPUToScreenColorExpandFill =
+ Permedia3SetupForScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentScanlineCPUToScreenColorExpandFill =
+ Permedia3SubsequentScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentColorExpandScanline =
+ Permedia3SubsequentColorExpandScanline;
+
+ infoPtr->ScanlineImageWriteFlags = NO_GXCOPY |
+ LEFT_EDGE_CLIPPING |
+ LEFT_EDGE_CLIPPING_NEGATIVE_X |
+ BIT_ORDER_IN_BYTE_LSBFIRST |
+ CPU_TRANSFER_PAD_DWORD;
+ infoPtr->NumScanlineImageWriteBuffers = 1;
+ infoPtr->ScanlineImageWriteBuffers =
+ pGlint->XAAScanlineColorExpandBuffers;
+ infoPtr->SetupForScanlineImageWrite =
+ Permedia3SetupForScanlineImageWrite;
+ infoPtr->SubsequentScanlineImageWriteRect =
+ Permedia3SubsequentScanlineImageWriteRect;
+ infoPtr->SubsequentImageWriteScanline =
+ Permedia3SubsequentImageWriteScanline;
+
+ infoPtr->WriteBitmap = Permedia3WriteBitmap;
+ infoPtr->WriteBitmapFlags = 0;
+
+ infoPtr->WritePixmap = Permedia3WritePixmap;
+ infoPtr->WritePixmapFlags = 0;
+
+ {
+ Bool shared_accel = FALSE;
+ int i;
+
+ for(i = 0; i < pScrn->numEntities; i++) {
+ if(xf86IsEntityShared(pScrn->entityList[i]))
+ shared_accel = TRUE;
+ }
+ if(shared_accel == TRUE)
+ infoPtr->RestoreAccelState = Permedia3RestoreAccelState;
+ }
+
+ Permedia3EnableOffscreen(pScreen);
+
+ return(XAAInit(pScreen, infoPtr));
+}
+
+void
+Permedia3EnableOffscreen (ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ BoxRec AvailFBArea;
+
+ /* Available Framebuffer Area for XAA. */
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = 0;
+ AvailFBArea.x2 = pScrn->displayWidth;
+ /* X coords are short's so we have to do this to make sure we dont wrap*/
+ AvailFBArea.y2 = ((pGlint->FbMapSize > 16384*1024) ? 16384*1024 :
+ pGlint->FbMapSize) / (pScrn->displayWidth *
+ pScrn->bitsPerPixel / 8);
+
+ /* Permedia3 has a maximum 4096x4096 framebuffer */
+ if (AvailFBArea.y2 > 4095) AvailFBArea.y2 = 4095;
+
+ xf86InitFBManager(pScreen, &AvailFBArea);
+}
+#define CHECKCLIPPING \
+{ \
+ if (pGlint->ClippingOn) { \
+ pGlint->ClippingOn = FALSE; \
+ GLINT_WAIT(1); \
+ GLINT_WRITE_REG(0, ScissorMode); \
+ } \
+}
+
+void
+Permedia3Sync(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ } while (GLINT_READ_REG(OutputFIFO) != Sync_tag);
+}
+
+void
+DualPermedia3Sync(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(3, BroadcastMask); /* hack! this shouldn't need to be reloaded */
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+
+ /* Read 1st PM3 until Sync Tag shows */
+ ACCESSCHIP1();
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ } while (GLINT_READ_REG(OutputFIFO) != Sync_tag);
+
+ ACCESSCHIP2();
+ /* Read 2nd PM3 until Sync Tag shows */
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ } while (GLINT_READ_REG(OutputFIFO) != Sync_tag);
+
+ ACCESSCHIP1();
+}
+
+static void
+Permedia3SetClippingRectangle(ScrnInfoPtr pScrn, int x1, int y1, int x2, int y2)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(((y1&0x0fff)<<16)|(x1&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG(((y2&0x0fff)<<16)|(x2&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(1, ScissorMode);
+ pGlint->ClippingOn = TRUE;
+}
+static void
+Permedia3DisableClipping(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CHECKCLIPPING;
+}
+
+/* ScreenToScreenCopy definition */
+static void
+Permedia3SetupForScreenToScreenCopy(ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask, int transparency_color)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SetupForScreenToScreenCopy");
+
+ pGlint->PM3_Render2D =
+ PM3Render2D_SpanOperation |
+ PM3Render2D_Operation_Normal;
+
+ pGlint->ClippingOn = TRUE;
+
+ pGlint->PM3_Config2D =
+ PM3Config2D_UserScissorEnable |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+
+ if (xdir == 1) pGlint->PM3_Render2D |= PM3Render2D_XPositive;
+ if (ydir == 1) pGlint->PM3_Render2D |= PM3Render2D_YPositive;
+
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXnoop)&&(rop!=GXinvert)) {
+ pGlint->PM3_Render2D |= PM3Render2D_FBSourceReadEnable;
+ pGlint->PM3_Config2D |= PM3Config2D_Blocking;
+ }
+
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+
+ GLINT_WAIT(2);
+ PM3_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+
+ TRACE_EXIT("Permedia3SetupForScreenToScreenCopy");
+}
+static void
+Permedia3SubsequentScreenToScreenCopy(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2, int y2, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ /* Spans needs to be 32 bit aligned. */
+ int x_align = x1 & 0x1f;
+ TRACE_ENTER("Permedia3SubsequentScreenToScreenCopy");
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(((y2&0x0fff)<<16)|(x2&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG((((y2+h)&0x0fff)<<16)|((x2+w)&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x2-x_align) |
+ PM3RectanglePosition_YOffset(y2),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(
+ PM3FBSourceReadBufferOffset_XOffset(x1-x2)|
+ PM3FBSourceReadBufferOffset_YOffset(y1-y2),
+ PM3FBSourceReadBufferOffset);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w+x_align)|
+ PM3Render2D_Height(h),
+ PM3Render2D);
+ TRACE_EXIT("Permedia3SubsequentScreenToScreenCopy");
+}
+
+/* Solid Fills */
+static void
+Permedia3SetupForFillRectSolid(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SetupForFillRectSolid");
+ /* Prepare Common Render2D & Config2D data */
+ pGlint->PM3_Render2D =
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_Normal;
+ pGlint->PM3_Config2D =
+ PM3Config2D_UseConstantSource |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+ GLINT_WAIT(3);
+ REPLICATE(color);
+ /* We can't do block fills properly at 32bpp, so we can stick the chip
+ * into 16bpp and double the width and xcoord, but it seems that at
+ * extremely high resolutions (above 1600) it doesn't fill.
+ * so, we fall back to the slower span filling method.
+ */
+ if ((rop == GXcopy) && (pScrn->bitsPerPixel == 32) &&
+ (pScrn->displayWidth <= 1600)) {
+ pGlint->AccelInfoRec->SubsequentSolidFillRect =
+ Permedia3SubsequentFillRectSolid32bpp;
+ if (pGlint->PM3_UsingSGRAM) {
+ GLINT_WRITE_REG(color, PM3FBBlockColor);
+ } else {
+ pGlint->PM3_Render2D |= PM3Render2D_SpanOperation;
+ GLINT_WRITE_REG(color, PM3ForegroundColor);
+ }
+ } else {
+ pGlint->AccelInfoRec->SubsequentSolidFillRect =
+ Permedia3SubsequentFillRectSolid;
+ /* Can't do block fills at 8bpp either */
+ if ((rop == GXcopy) && (pScrn->bitsPerPixel == 16)) {
+ if (pGlint->PM3_UsingSGRAM) {
+ GLINT_WRITE_REG(color, PM3FBBlockColor);
+ } else {
+ pGlint->PM3_Render2D |= PM3Render2D_SpanOperation;
+ GLINT_WRITE_REG(color, PM3ForegroundColor);
+ }
+ } else {
+ pGlint->PM3_Render2D |= PM3Render2D_SpanOperation;
+ GLINT_WRITE_REG(color, PM3ForegroundColor);
+ }
+ }
+ PM3_PLANEMASK(planemask);
+ if (((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ || ((planemask != 0xffffffff) && !(pGlint->PM3_UsingSGRAM)))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+ TRACE_EXIT("Permedia3SetupForFillRectSolid");
+}
+
+static void
+Permedia3SubsequentFillRectSolid(ScrnInfoPtr pScrn, int x, int y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SubsequentFillRectSolid");
+
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+
+ TRACE_EXIT("Permedia3SubsequentFillRectSolid");
+}
+
+static void
+Permedia3SubsequentFillRectSolid32bpp(ScrnInfoPtr pScrn, int x, int y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SubsequentFillRectSolid32bpp");
+
+ GLINT_WAIT(6);
+
+ /* Put the chip into 16bpp mode */
+ GLINT_WRITE_REG(1, PixelSize);
+ /* Now double the displayWidth */
+ GLINT_WRITE_REG(
+ PM3FBWriteBufferWidth_Width(pScrn->displayWidth<<1),
+ PM3FBWriteBufferWidth0);
+
+ /* and double the x,w coords */
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x<<1) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w<<1) | PM3Render2D_Height(h),
+ PM3Render2D);
+
+ /* Now fixup */
+ GLINT_WRITE_REG(
+ PM3FBWriteBufferWidth_Width(pScrn->displayWidth),
+ PM3FBWriteBufferWidth0);
+ GLINT_WRITE_REG(0, PixelSize);
+ TRACE_EXIT("Permedia3SubsequentFillRectSolid32bpp");
+}
+
+/* 8x8 Mono Pattern Fills */
+static void
+Permedia3SetupForMono8x8PatternFill(ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SetupForMono8x8PatternFill");
+ REPLICATE(fg);
+ pGlint->PM3_Render2D =
+ PM3Render2D_AreaStippleEnable |
+ PM3Render2D_SpanOperation |
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_Normal;
+ pGlint->PM3_Config2D =
+ PM3Config2D_UseConstantSource |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+ pGlint->PM3_AreaStippleMode = 1;
+/* Mirror stipple pattern horizontally */
+#if X_BYTE_ORDER == X_BIG_ENDIAN
+ pGlint->PM3_AreaStippleMode |= (1<<18);
+#endif
+ pGlint->PM3_AreaStippleMode |= (2<<1);
+ pGlint->PM3_AreaStippleMode |= (2<<4);
+ if (bg != -1) {
+ REPLICATE(bg);
+ pGlint->PM3_Config2D |= PM3Config2D_OpaqueSpan;
+ pGlint->PM3_AreaStippleMode |= 1<<20;
+ GLINT_WAIT(12);
+ GLINT_WRITE_REG(bg, BackgroundColor);
+ }
+ else GLINT_WAIT(11);
+ GLINT_WRITE_REG((patternx & 0xFF), AreaStipplePattern0);
+ GLINT_WRITE_REG((patternx & 0xFF00) >> 8, AreaStipplePattern1);
+ GLINT_WRITE_REG((patternx & 0xFF0000) >> 16, AreaStipplePattern2);
+ GLINT_WRITE_REG((patternx & 0xFF000000) >> 24, AreaStipplePattern3);
+ GLINT_WRITE_REG((patterny & 0xFF), AreaStipplePattern4);
+ GLINT_WRITE_REG((patterny & 0xFF00) >> 8, AreaStipplePattern5);
+ GLINT_WRITE_REG((patterny & 0xFF0000) >> 16, AreaStipplePattern6);
+ GLINT_WRITE_REG((patterny & 0xFF000000) >> 24, AreaStipplePattern7);
+ GLINT_WRITE_REG(fg, PM3ForegroundColor);
+ PM3_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+ TRACE_EXIT("Permedia3SetupForMono8x8PatternFill");
+}
+static void
+Permedia3SubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn,
+ int x_offset, int y_offset,
+ int x, int y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SubsequentMono8x8PatternFillRect");
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(
+ (x_offset&0x7)<<7 | (y_offset&0x7)<<12 |
+ pGlint->PM3_AreaStippleMode,
+ AreaStippleMode);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+ TRACE_EXIT("Permedia3SubsequentMono8x8PatternFillRect");
+}
+
+static void
+Permedia3SetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ REPLICATE(fg);
+ pGlint->PM3_Render2D =
+ PM3Render2D_SpanOperation |
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_SyncOnBitMask;
+ pGlint->PM3_Config2D =
+ PM3Config2D_UserScissorEnable |
+ PM3Config2D_UseConstantSource |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+ if (bg != -1) {
+ REPLICATE(bg);
+ pGlint->PM3_Config2D |= PM3Config2D_OpaqueSpan;
+ GLINT_WAIT(4);
+ GLINT_WRITE_REG(bg, BackgroundColor);
+ }
+ else GLINT_WAIT(3);
+ GLINT_WRITE_REG(fg, PM3ForegroundColor);
+ PM3_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+}
+
+static void
+Permedia3SubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ int skipleft
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ TRACE_ENTER("Permedia2SubsequentScanlineCPUToScreenColorExpandFill");
+
+ pGlint->dwords = ((w + 31) >> 5); /* dwords per scanline */
+
+ pGlint->cpucount = h;
+
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(((y&0x0fff)<<16)|((x+skipleft)&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG((((y+h)&0x0fff)<<16)|((x+w)&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+
+#if defined(__alpha__)
+ if (0) /* force Alpha to use indirect always */
+#else
+ if ((pGlint->dwords*h) < pGlint->FIFOSize)
+#endif
+ {
+ /* Turn on direct for less than 120 dword colour expansion */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->IOBase+OutputFIFO+4;
+ pGlint->ScanlineDirect = 1;
+ GLINT_WRITE_REG(((pGlint->dwords*h)-1)<<16 | 0x0D, OutputFIFO);
+ GLINT_WAIT(pGlint->dwords*h);
+ } else {
+ /* Use indirect for anything else */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->ScratchBuffer;
+ pGlint->ScanlineDirect = 0;
+ }
+
+ pGlint->cpucount--;
+}
+
+static void
+Permedia3SubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 *srcp = (CARD32*)pGlint->XAAScanlineColorExpandBuffers[bufno];
+ int dwords = pGlint->dwords;
+
+ if (!pGlint->ScanlineDirect) {
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ dwords -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords - 1) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, dwords);
+ }
+ }
+}
+
+/* Images Writes */
+static void Permedia3SetupForScanlineImageWrite(ScrnInfoPtr pScrn, int rop,
+ unsigned int planemask, int trans_color, int bpp, int depth)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SetupForScanlineImageWrite");
+ pGlint->PM3_Render2D =
+ PM3Render2D_SpanOperation |
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_SyncOnHostData;
+ pGlint->PM3_Config2D =
+ PM3Config2D_UserScissorEnable |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+ GLINT_WAIT(2);
+ PM3_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+ TRACE_EXIT("Permedia3SetupForScanlineImageWrite");
+}
+
+static void Permedia3SubsequentScanlineImageWriteRect(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h, int skipleft)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3SubsequentScanlineImageWrite");
+ pGlint->dwords = (((w * pScrn->bitsPerPixel) + 3) >> 2); /* per scanline */
+
+ pGlint->cpucount = h;
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG(((y&0x0fff)<<16)|((x+skipleft)&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG((((y+h)&0x0fff)<<16)|((x+w)&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+
+#if defined(__alpha__)
+ if (0) /* force Alpha to use indirect always */
+#else
+ if (pGlint->dwords < pGlint->FIFOSize)
+#endif
+ {
+ /* Turn on direct for less than 120 dword colour expansion */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->IOBase+OutputFIFO+4;
+ pGlint->ScanlineDirect = 1;
+ GLINT_WRITE_REG(((pGlint->dwords*h)-1)<<16 | (0x15<<4) | 0x05,
+ OutputFIFO);
+ GLINT_WAIT(pGlint->dwords);
+ } else {
+ /* Use indirect for anything else */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->ScratchBuffer;
+ pGlint->ScanlineDirect = 0;
+ }
+
+ pGlint->cpucount--;
+ TRACE_EXIT("Permedia3SubsequentScanlineImageWrite");
+}
+
+static void
+Permedia3SubsequentImageWriteScanline(ScrnInfoPtr pScrn, int bufno)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int dwords = pGlint->dwords;
+
+ if (pGlint->ScanlineDirect) {
+ if (pGlint->cpucount--)
+ GLINT_WAIT(dwords);
+ return;
+ } else {
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)pGlint->XAAScanlineColorExpandBuffers[bufno],
+ pGlint->FIFOSize - 1);
+ dwords -= pGlint->FIFOSize - 1;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)pGlint->XAAScanlineColorExpandBuffers[bufno],
+ dwords);
+ }
+ }
+}
+
+static void
+Permedia3RestoreAccelState(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ if ((IS_J2000) && (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)) {
+ GLINT_SLOW_WRITE_REG(pGlint->MultiIndex, BroadcastMask);
+ }
+ Permedia3Sync(pScrn);
+}
+
+static void
+Permedia3WritePixmap(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int trans,
+ int bpp, int depth
+)
+{
+ int dwords;
+ int count;
+ int skipleft = (long)src & 0x03L;
+ int Bpp = bpp >> 3;
+ CARD32 *srcp;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ TRACE_ENTER("Permedia3WritePixmap");
+
+ if (skipleft) {
+ /* Skipleft is either
+ * - 0, 1, 2 or 3 in 8 bpp
+ * - 0 or 1 in 16 bpp
+ * - 0 in 32 bpp
+ */
+ skipleft /= Bpp;
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+
+ pGlint->PM3_Render2D =
+ PM3Render2D_SpanOperation |
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_SyncOnHostData;
+ pGlint->PM3_Config2D =
+ PM3Config2D_UserScissorEnable |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+ GLINT_WAIT(6);
+ PM3_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+ GLINT_WRITE_REG(((y&0x0fff)<<16)|((x+skipleft)&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG((((y+h)&0x0fff)<<16)|((x+w)&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+ /* width of the stuff to copy in 32 bit words */
+ dwords = ((w * Bpp) + 3) >> 2;
+
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+
+ Permedia3DisableClipping(pScrn);
+ Permedia3Sync(pScrn);
+}
+
+static void
+Permedia3WriteBitmap(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth, int skipleft,
+ int fg, int bg, int rop,
+ unsigned int planemask
+)
+{
+ int dwords;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int count;
+ CARD32 *srcp;
+ TRACE_ENTER("Permedia3WriteBitmap");
+
+ w += skipleft;
+ x -= skipleft;
+ dwords = (w + 31) >>5;
+
+ REPLICATE(fg);
+ pGlint->PM3_Render2D =
+ PM3Render2D_SpanOperation |
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_SyncOnBitMask;
+ pGlint->PM3_Config2D =
+ PM3Config2D_UserScissorEnable |
+ PM3Config2D_UseConstantSource |
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(rop) |
+ PM3Config2D_FBWriteEnable;
+ if ((rop!=GXclear)&&(rop!=GXset)&&(rop!=GXcopy)&&(rop!=GXcopyInverted))
+ pGlint->PM3_Config2D |= PM3Config2D_FBDestReadEnable;
+ if (bg != -1) {
+ REPLICATE(bg);
+ pGlint->PM3_Config2D |= PM3Config2D_OpaqueSpan;
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG(bg, BackgroundColor);
+ }
+ else GLINT_WAIT(7);
+ GLINT_WRITE_REG(fg, PM3ForegroundColor);
+ PM3_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->PM3_Config2D, PM3Config2D);
+ GLINT_WRITE_REG(((y&0x0fff)<<16)|((x+skipleft)&0x0fff), ScissorMinXY);
+ GLINT_WRITE_REG((((y+h)&0x0fff)<<16)|((x+w)&0x0fff), ScissorMaxXY);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(pGlint->PM3_Render2D |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) |
+ 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ count -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ GLINT_WRITE_REG(((count - 1) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+
+ Permedia3DisableClipping(pScrn);
+ Permedia3Sync(pScrn);
+}
diff --git a/src/pm3_dac.c b/src/pm3_dac.c
new file mode 100644
index 0000000..f848094
--- /dev/null
+++ b/src/pm3_dac.c
@@ -0,0 +1,842 @@
+/*
+ * Copyright 2000,2001 by Sven Luther <luther@dpt-info.u-strasbg.fr>.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Sven Luther not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Sven Luther makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * SVEN LUTHER DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL SVEN LUTHER BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Sven Luther, <luther@dpt-info.u-strasbg.fr>
+ * Thomas Witzel, <twitzel@nmr.mgh.harvard.edu>
+ * Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ *
+ * this work is sponsored by Appian Graphics.
+ *
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm3_dac.c,v 1.33 2002/07/19 15:33:45 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+#include "xf86int10.h"
+
+#include "glint_regs.h"
+#include "pm3_regs.h"
+#include "glint.h"
+
+#define DEBUG 0
+
+#if DEBUG
+# define TRACE_ENTER(str) ErrorF("glint: " str " %d\n",pScrn->scrnIndex)
+# define TRACE_EXIT(str) ErrorF("glint: " str " done\n")
+# define TRACE(str) ErrorF("glint trace: " str "\n")
+#else
+# define TRACE_ENTER(str)
+# define TRACE_EXIT(str)
+# define TRACE(str)
+#endif
+
+int
+Permedia3MemorySizeDetect(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR (pScrn);
+ CARD32 size = 0, temp, temp1, temp2, i;
+
+ /* We can map 64MB, as that's the size of the Permedia3 aperture
+ * regardless of memory configuration */
+ pGlint->FbMapSize = 64*1024*1024;
+
+ /* Mark as VIDMEM_MMIO to avoid write-combining while detecting memory */
+ pGlint->FbBase = xf86MapPciMem(pScrn->scrnIndex, VIDMEM_MMIO,
+ pGlint->PciTag, pGlint->FbAddress, pGlint->FbMapSize);
+
+ if (pGlint->FbBase == NULL)
+ return 0;
+
+ temp = GLINT_READ_REG(PM3MemBypassWriteMask);
+ GLINT_SLOW_WRITE_REG(0xffffffff, PM3MemBypassWriteMask);
+
+ /* The Permedia3 splits up memory, and even replicates it. Grrr.
+ * So that each 32MB appears at offset 0, and offset 32, unless
+ * there's really 64MB attached to the chip.
+ * So, 16MB appears at offset 0, nothing between 16-32, then it re-appears
+ * at offset 32.
+ * This below is to detect the cases of memory combinations
+ */
+
+ /* Test first 32MB */
+ for(i=0;i<32;i++) {
+ /* write test pattern */
+ MMIO_OUT32(pGlint->FbBase, i*1024*1024, i*0x00345678);
+ mem_barrier();
+ temp1 = MMIO_IN32(pGlint->FbBase, i*1024*1024);
+ /* Let's check for wrapover, write will fail at 16MB boundary */
+ if (temp1 == (i*0x00345678))
+ size = i;
+ else
+ break;
+ }
+
+ /* Ok, we're satisfied we've got 32MB, let's test the second lot */
+ if ((size + 1) == i) {
+ for(i=0;i<32;i++) {
+ /* Clear first 32MB */
+ MMIO_OUT32(pGlint->FbBase, i*1024*1024, 0);
+ mem_barrier();
+ }
+ for(i=32;i<64;i++) {
+ /* write test pattern */
+ MMIO_OUT32(pGlint->FbBase, i*1024*1024, i*0x00345678);
+ mem_barrier();
+ temp1 = MMIO_IN32(pGlint->FbBase, i*1024*1024);
+ temp2 = MMIO_IN32(pGlint->FbBase, (i-32)*1024*1024);
+ /* Let's check for wrapover */
+ if ( (temp1 == (i*0x00345678)) && (temp2 == 0) )
+ size = i;
+ else
+ break;
+ }
+ }
+
+ GLINT_SLOW_WRITE_REG(temp, PM3MemBypassWriteMask);
+
+ xf86UnMapVidMem(pScrn->scrnIndex, (pointer)pGlint->FbBase,
+ pGlint->FbMapSize);
+
+ pGlint->FbBase = NULL;
+ pGlint->FbMapSize = 0;
+
+ return ( (size+1) * 1024 );
+}
+
+static unsigned long
+PM3DAC_CalculateClock
+(
+ unsigned long ReqClock, /* In kHz units */
+ unsigned long RefClock, /* In kHz units */
+ unsigned char *prescale, /* ClkPreScale */
+ unsigned char *feedback, /* ClkFeedBackScale */
+ unsigned char *postscale /* ClkPostScale */
+ )
+{
+ unsigned long fMinVCO = 2000000; /* min fVCO is 200MHz (in 100Hz units) */
+ unsigned long fMaxVCO = 6220000; /* max fVCO is 622MHz (in 100Hz units) */
+ unsigned long fMinINTREF = 10000;/* min fINTREF is 1MHz (in 100Hz units) */
+ unsigned long fMaxINTREF = 20000;/* max fINTREF is 2MHz (in 100Hz units) */
+ unsigned long M, N, P; /* M=feedback, N=prescale, P=postscale */
+ unsigned long fINTREF;
+ unsigned long fVCO;
+ unsigned long ActualClock;
+ long Error;
+ unsigned long LowestError = 1000000;
+ unsigned int bFoundFreq = FALSE;
+ int cInnerLoopIterations = 0;
+ int LoopCount;
+ unsigned long ClosestClock = 0;
+
+ ReqClock*=10; /* convert into 100Hz units */
+ RefClock*=10; /* convert into 100Hz units */
+
+ for(P = 0; P <= 5; ++P)
+ {
+ unsigned long fVCOLowest, fVCOHighest;
+
+ /* it is pointless going through the main loop if all values of
+ N produce an fVCO outside the acceptable range */
+ N = 1;
+ M = (N * (1UL << P) * ReqClock) / (2 * RefClock);
+ fVCOLowest = (2 * RefClock * M) / N;
+ N = 255;
+ M = (N * (1UL << P) * ReqClock) / (2 * RefClock);
+ fVCOHighest = (2 * RefClock * M) / N;
+
+ if(fVCOHighest < fMinVCO || fVCOLowest > fMaxVCO)
+ {
+ continue;
+ }
+
+ for(N = 1; N <= 255; ++N, ++cInnerLoopIterations)
+ {
+ fINTREF = RefClock / N;
+ if(fINTREF < fMinINTREF || fINTREF > fMaxINTREF)
+ {
+ if(fINTREF > fMaxINTREF)
+ {
+ /* hopefully we will get into range as the prescale
+ value increases */
+ continue;
+ }
+ else
+ {
+ /* already below minimum and it will only get worse:
+ move to the next postscale value */
+ break;
+ }
+ }
+
+ M = (N * (1UL << P) * ReqClock) / (2 * RefClock);
+ if(M > 255)
+ {
+ /* M, N & P registers are only 8 bits wide */
+ break;
+ }
+
+ /* we can expect rounding errors in calculating M, which
+ will always be rounded down. So we will checkout our
+ calculated value of M along with (M+1) */
+ for(LoopCount = (M == 255) ? 1 : 2; --LoopCount >= 0; ++M)
+ {
+ fVCO = (2 * RefClock * M) / N;
+ if(fVCO >= fMinVCO && fVCO <= fMaxVCO)
+ {
+ ActualClock = fVCO / (1UL << P);
+ Error = ActualClock - ReqClock;
+ if(Error < 0)
+ Error = -Error;
+ if(Error < LowestError)
+ {
+ bFoundFreq = TRUE;
+ LowestError = Error;
+ ClosestClock = ActualClock;
+ *prescale = N;
+ *feedback = M;
+ *postscale = P;
+ if(Error == 0)
+ goto Done;
+ }
+ }
+ }
+ }
+ }
+
+Done:
+
+ if(bFoundFreq)
+ ActualClock = ClosestClock;
+ else
+ ActualClock = 0;
+
+#if 0
+ ErrorF("PM3DAC_CalculateClock: Got prescale=%d, feedback=%d, postscale=%d, WantedClock = %d00 ActualClock = %d00 (Error %d00)\n",
+ *prescale, *feedback, *postscale, ReqClock, ActualClock, LowestError);
+#endif
+
+ return(ActualClock);
+}
+
+static unsigned long
+PM4DAC_CalculateClock
+(
+ unsigned long req_clock, /* In kHz units */
+ unsigned long ref_clock, /* In kHz units */
+ unsigned char *param_m, /* ClkPreScale */
+ unsigned char *param_n, /* ClkFeedBackScale */
+ unsigned char *param_p /* ClkPostScale */
+ )
+{
+#define INITIALFREQERR 10000
+
+ long fMinVCO = 200000; /* min fVCO is 200MHz (in 10000Hz units) */
+ long fMaxVCO = 400000; /* max fVCO is 400MHz (in 10000Hz units) */
+ unsigned long int M, N, P;
+ unsigned long int fVCO;
+ unsigned long int ActualClock;
+ int Error;
+ int LowestError = INITIALFREQERR;
+ short bFoundFreq = FALSE;
+ int cInnerLoopIterations = 0;
+ int LoopCount;
+
+ /*
+ * Actual Equations:
+ * fVCO = (ref_clock * M)/(N+1)
+ * PIXELCLOCK = fVCO/(1<<p)
+ * 200 <= fVCO <= 400
+ * 24 <= N <= 80
+ * 1 <= M <= 15
+ * 0 <= P <= 3
+ * 1Mhz < ref_clock/(N+1) <= 2Mhz - not used
+ * For refclk == 14.318 we have the tighter equations:
+ * 32 <= N <= 80
+ * 3 <= M <= 12
+ * Notes:
+ * The spec says that the PLLs will only do 260Mhz, but I have assumed 300Mhz 'cos
+ * 260Mhz is a crap limit.
+ */
+
+#define P4RD_PLL_MIN_P 0
+#define P4RD_PLL_MAX_P 3
+#define P4RD_PLL_MIN_M 1
+#define P4RD_PLL_MAX_M 12
+#define P4RD_PLL_MIN_N 24
+#define P4RD_PLL_MAX_N 80
+
+ for(P = P4RD_PLL_MIN_P; P <= P4RD_PLL_MAX_P; ++P) {
+ unsigned long int fVCOLowest, fVCOHighest;
+
+ /* it's pointless going through the main loop if all values of
+ * N produce an fVCO outside the acceptable range */
+
+ M = P4RD_PLL_MIN_M;
+ N = ((M + 1) * (1 << P) * req_clock) / ref_clock;
+
+ fVCOLowest = (ref_clock * N) / (M + 1);
+
+ M = P4RD_PLL_MAX_M;
+ N = ((M + 1) * (1 << P) * req_clock) / ref_clock;
+
+ fVCOHighest = (ref_clock * N) / (M + 1);
+
+ if(fVCOHighest < fMinVCO || fVCOLowest > fMaxVCO)
+ continue;
+
+ for(M = P4RD_PLL_MIN_M; M <= P4RD_PLL_MAX_M; ++M, ++cInnerLoopIterations)
+ {
+ N = ((M + 1) * (1 << P) * req_clock) / ref_clock;
+
+ if(N > P4RD_PLL_MAX_N || N < P4RD_PLL_MIN_N)
+ continue;
+
+ /* we can expect rounding errors in calculating M, which will always be rounded down. */
+ /* So we'll checkout our calculated value of M along with (M+1) */
+
+ for(LoopCount = (N == P4RD_PLL_MAX_N) ? 1 : 2; --LoopCount >= 0; ++N)
+ {
+ fVCO = (ref_clock * N) / (M + 1);
+
+ if( (fVCO >= fMinVCO) && (fVCO <= fMaxVCO) )
+ {
+ ActualClock = (fVCO / (1 << P));
+
+ Error = ActualClock - req_clock;
+
+ if(Error < 0)
+ Error = -Error;
+
+ /* It is desirable that we use the lowest value of M if the*/
+ /* frequencies are the same.*/
+ if(Error < LowestError || (Error == LowestError && M < *param_m))
+ {
+ bFoundFreq = TRUE;
+ LowestError = Error;
+ *param_m = M;
+ *param_n = N;
+ *param_p = P;
+ if(Error == 0)
+ goto Done;
+ }
+ }
+ }
+ }
+ }
+
+Done:
+ if(bFoundFreq)
+ ActualClock = (ref_clock * (*param_n)) / (((*param_m) + 1) * (1 << (*param_p)));
+ else
+ ActualClock = 0;
+
+ return(ActualClock);
+}
+
+void
+Permedia3PreInit(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 LocalMemCaps;
+
+ TRACE_ENTER("Permedia3PreInit");
+
+ if (IS_J2000) {
+ unsigned char m,n,p;
+ unsigned long clockused;
+
+ if (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)
+ GLINT_SLOW_WRITE_REG(GCSRSecondaryGLINTMapEn, GCSRAperture);
+
+ /* Memory timings for the Appian J2000 board.
+ * This is needed for the second head which is left un-initialized
+ * by the bios, thus freezing the machine. */
+ GLINT_SLOW_WRITE_REG(0x02e311B8, PM3LocalMemCaps);
+ GLINT_SLOW_WRITE_REG(0x07424905, PM3LocalMemTimings);
+ GLINT_SLOW_WRITE_REG(0x0c000003, PM3LocalMemControl);
+ GLINT_SLOW_WRITE_REG(0x00000061, PM3LocalMemRefresh);
+ GLINT_SLOW_WRITE_REG(0x00000000, PM3LocalMemPowerDown);
+
+ /* Let's program the K, M and S Clocks to the same values as the bios
+ * does for first head :
+ * - KClk and MClk are 105Mhz.
+ * - S Clock is set to PClk.
+ * Note 1 : pGlint->RefClock is not set yet, so use 14318 instead.
+ * Note 2 : KClk gets internally halved, so we need to double it.
+ */
+ clockused = PM3DAC_CalculateClock(2*105000, 14318, &m,&n,&p);
+ Permedia2vOutIndReg(pScrn, PM3RD_KClkPreScale, 0x00, m);
+ Permedia2vOutIndReg(pScrn, PM3RD_KClkFeedbackScale, 0x00, n);
+ Permedia2vOutIndReg(pScrn, PM3RD_KClkPostScale, 0x00, p);
+ Permedia2vOutIndReg(pScrn, PM3RD_KClkControl, 0x00,
+ PM3RD_KClkControl_STATE_RUN |
+ PM3RD_KClkControl_SOURCE_PLL |
+ PM3RD_KClkControl_ENABLE);
+ Permedia2vOutIndReg(pScrn, PM3RD_MClkControl, 0x00,
+ PM3RD_MClkControl_STATE_RUN |
+ PM3RD_MClkControl_SOURCE_KCLK |
+ PM3RD_MClkControl_ENABLE);
+ Permedia2vOutIndReg(pScrn, PM3RD_SClkControl, 0x00,
+ PM3RD_SClkControl_STATE_RUN |
+ PM3RD_SClkControl_SOURCE_PCLK |
+ PM3RD_SClkControl_ENABLE);
+ }
+
+#if defined(__alpha__)
+ /*
+ * On Alpha, we have to "int10" secondary VX1 cards early;
+ * otherwise, some information taken from registers, like
+ * memory size, is incorrect.
+ */
+ if (!xf86IsPrimaryPci(pGlint->PciInfo)) {
+ if ( IS_QVX1 ) {
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "VX1 secondary enabling VGA before int10\n");
+
+ /* Enable VGA on the current card. */
+ pciWriteByte( pGlint->PciTag, 0xf8, 0 );
+ pciWriteByte( pGlint->PciTag, 0xf4, 0 );
+ pciWriteByte( pGlint->PciTag, 0xfc, 0 );
+
+ /* The card we are on should be VGA-enabled now, so run int10. */
+ if (xf86LoadSubModule(pScrn, "int10")) {
+ xf86Int10InfoPtr pInt;
+
+ xf86LoaderReqSymLists(GLINTint10Symbols, NULL);
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Initializing int10\n");
+ pInt = xf86InitInt10(pGlint->pEnt->index);
+ xf86FreeInt10(pInt);
+ }
+
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO,
+ "VX1 secondary disabling VGA after int10\n");
+
+ /* Finally, disable VGA on the current card. */
+ pciWriteByte( pGlint->PciTag, 0xf8, 0x70 );
+ pciWriteByte( pGlint->PciTag, 0xf4, 0x01 );
+ pciWriteByte( pGlint->PciTag, 0xfc, 0x00 );
+ }
+ }
+#endif /* __alpha__ */
+
+ /* If we have SDRAM instead of SGRAM, we have to do some things
+ differently in the FillRectSolid code. */
+ LocalMemCaps = GLINT_READ_REG(PM3LocalMemCaps);
+ pGlint->PM3_UsingSGRAM = !(LocalMemCaps & PM3LocalMemCaps_NoWriteMask);
+ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Using %s memory\n",
+ pGlint->PM3_UsingSGRAM ? "SGRAM" : "SDRAM");
+
+ TRACE_EXIT("Permedia3PreInit");
+}
+
+Bool
+Permedia3Init(ScrnInfoPtr pScrn, DisplayModePtr mode, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 temp1, temp2, temp3, temp4;
+
+ if ((pGlint->numMultiDevices == 2) || (IS_J2000)) {
+ STOREREG(GCSRAperture, GCSRSecondaryGLINTMapEn);
+ }
+
+ if (pGlint->MultiAperture) {
+ STOREREG(GMultGLINTAperture, pGlint->realWidth);
+ STOREREG(GMultGLINT1,
+ pGlint->MultiPciInfo[0]->memBase[2] & 0xFF800000);
+ STOREREG(GMultGLINT2,
+ pGlint->MultiPciInfo[1]->memBase[2] & 0xFF800000);
+ }
+
+ STOREREG(PM3MemBypassWriteMask, 0xffffffff);
+ STOREREG(Aperture0, 0x00000000);
+ STOREREG(Aperture1, 0x00000000);
+
+ if (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)
+ STOREREG(DFIFODis, 0x00000001);
+
+ STOREREG(FIFODis, 0x00000007);
+
+ temp1 = mode->CrtcHSyncStart - mode->CrtcHDisplay;
+ temp2 = mode->CrtcVSyncStart - mode->CrtcVDisplay;
+ temp3 = mode->CrtcHSyncEnd - mode->CrtcHSyncStart;
+ temp4 = mode->CrtcVSyncEnd - mode->CrtcVSyncStart;
+
+ STOREREG(PMHTotal, Shiftbpp(pScrn, mode->CrtcHTotal - 1));
+ STOREREG(PMHsEnd, Shiftbpp(pScrn, temp1 + temp3));
+ STOREREG(PMHsStart, Shiftbpp(pScrn, temp1));
+ STOREREG(PMHbEnd, Shiftbpp(pScrn, mode->CrtcHTotal - mode->CrtcHDisplay));
+ STOREREG(PMHgEnd, Shiftbpp(pScrn, mode->CrtcHTotal - mode->CrtcHDisplay));
+ STOREREG(PMScreenStride, Shiftbpp(pScrn, pScrn->displayWidth));
+
+ STOREREG(PMVTotal, mode->CrtcVTotal - 1);
+ STOREREG(PMVsEnd, temp2 + temp4 - 1);
+ STOREREG(PMVsStart, temp2 - 1);
+ STOREREG(PMVbEnd, mode->CrtcVTotal - mode->CrtcVDisplay);
+
+ switch (pScrn->bitsPerPixel)
+ {
+ case 8:
+ STOREREG(PM3ByAperture1Mode, PM3ByApertureMode_PIXELSIZE_8BIT);
+ STOREREG(PM3ByAperture2Mode, PM3ByApertureMode_PIXELSIZE_8BIT);
+ STOREREG(PMVideoControl, 1 | (1 << 3) | (1 << 5) | (0 << 19));
+ break;
+ case 16:
+#if X_BYTE_ORDER != X_BIG_ENDIAN
+ STOREREG(PM3ByAperture1Mode, PM3ByApertureMode_PIXELSIZE_16BIT);
+ STOREREG(PM3ByAperture2Mode, PM3ByApertureMode_PIXELSIZE_16BIT);
+#else
+ STOREREG(PM3ByAperture1Mode, PM3ByApertureMode_PIXELSIZE_16BIT |
+ PM3ByApertureMode_BYTESWAP_BADC);
+ STOREREG(PM3ByAperture2Mode, PM3ByApertureMode_PIXELSIZE_16BIT |
+ PM3ByApertureMode_BYTESWAP_BADC);
+#endif
+ STOREREG(PMVideoControl, 1 | (1 << 3) | (1 << 5) | (1 << 19));
+ break;
+ case 32:
+#if X_BYTE_ORDER != X_BIG_ENDIAN
+ STOREREG(PM3ByAperture1Mode, PM3ByApertureMode_PIXELSIZE_32BIT);
+ STOREREG(PM3ByAperture2Mode, PM3ByApertureMode_PIXELSIZE_32BIT);
+#else
+ STOREREG(PM3ByAperture1Mode, PM3ByApertureMode_PIXELSIZE_32BIT |
+ PM3ByApertureMode_BYTESWAP_DCBA);
+ STOREREG(PM3ByAperture2Mode, PM3ByApertureMode_PIXELSIZE_32BIT |
+ PM3ByApertureMode_BYTESWAP_DCBA);
+#endif
+ STOREREG(PMVideoControl, 1 | (1 << 3) | (1 << 5) | (2 << 19));
+ break;
+ }
+
+ STOREREG(VClkCtl, GLINT_READ_REG(VClkCtl) & 0xFFFFFFFC);
+ STOREREG(PMScreenBase, 0x00000000);
+ STOREREG(ChipConfig, GLINT_READ_REG(ChipConfig) & 0xFFFFFFFD);
+
+ {
+ /* Get the programmable clock values */
+ unsigned char m,n,p;
+ unsigned long clockused;
+
+ /* Let's program the dot clock */
+ switch (pGlint->Chipset) {
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA4:
+ case PCI_VENDOR_3DLABS_CHIP_R4:
+ clockused = PM4DAC_CalculateClock(mode->Clock,
+ pGlint->RefClock, &m,&n,&p);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_PERMEDIA3:
+ clockused = PM3DAC_CalculateClock(mode->Clock,
+ pGlint->RefClock, &m,&n,&p);
+ break;
+ case PCI_VENDOR_3DLABS_CHIP_GAMMA:
+ switch (pGlint->MultiChip) {
+ case PCI_CHIP_PERMEDIA3:
+ clockused = PM3DAC_CalculateClock(mode->Clock,
+ pGlint->RefClock, &m,&n,&p);
+ break;
+ case PCI_CHIP_R4:
+ clockused = PM4DAC_CalculateClock(mode->Clock,
+ pGlint->RefClock, &m,&n,&p);
+ break;
+ }
+ break;
+ }
+ STOREDAC(PM3RD_DClk0PreScale, m);
+ STOREDAC(PM3RD_DClk0FeedbackScale, n);
+ STOREDAC(PM3RD_DClk0PostScale, p);
+ }
+
+ temp1 = 0;
+ temp2 = 0;
+ temp3 = 0;
+
+ if (pGlint->UseFlatPanel) {
+ temp2 |= PM3RD_DACControl_BLANK_PEDESTAL_ENABLE;
+ temp3 |= PM3RD_MiscControl_VSB_OUTPUT_ENABLE;
+ STOREREG(VSConfiguration, 0x06);
+ STOREREG(VSBBase, 1<<14);
+ }
+
+ if (mode->Flags & V_PHSYNC) temp1 |= PM3RD_SyncControl_HSYNC_ACTIVE_HIGH;
+ if (mode->Flags & V_PVSYNC) temp1 |= PM3RD_SyncControl_VSYNC_ACTIVE_HIGH;
+
+ STOREREG(PM2VDACRDIndexControl, 0x00);
+ STOREDAC(PM2VDACRDSyncControl, temp1);
+ STOREDAC(PM2VDACRDDACControl, temp2);
+
+ if (pScrn->rgbBits == 8)
+ temp3 |= 0x01; /* 8bit DAC */
+
+ switch (pScrn->bitsPerPixel)
+ {
+ case 8:
+ STOREDAC(PM2VDACRDPixelSize, 0x00);
+ STOREDAC(PM2VDACRDColorFormat, 0x2E);
+ break;
+ case 16:
+ temp3 |= PM3RD_MiscControl_DIRECTCOLOR_ENABLE;
+ STOREDAC(PM2VDACRDPixelSize, 0x01);
+ if (pScrn->depth == 15) {
+ STOREDAC(PM2VDACRDColorFormat, 0x61);
+ } else {
+ STOREDAC(PM2VDACRDColorFormat, 0x70);
+ }
+ break;
+ case 24:
+ temp3 |= PM3RD_MiscControl_DIRECTCOLOR_ENABLE;
+ STOREDAC(PM2VDACRDPixelSize, 0x04);
+ STOREDAC(PM2VDACRDColorFormat, 0x20);
+ break;
+ case 32:
+ temp3 |= PM3RD_MiscControl_DIRECTCOLOR_ENABLE;
+ if (pScrn->overlayFlags & OVERLAY_8_32_PLANAR) {
+ temp3 |= 0x18;
+ STOREDAC(PM2VDACRDOverlayKey, pScrn->colorKey);
+ }
+ STOREDAC(PM2VDACRDPixelSize, 0x02);
+ STOREDAC(PM2VDACRDColorFormat, 0x20);
+ break;
+ }
+ STOREDAC(PM2VDACRDMiscControl, temp3);
+
+ STOREREG(PM3FifoControl, 0x905); /* Lower the default fifo threshold */
+
+ return(TRUE);
+}
+
+void
+Permedia3Save(ScrnInfoPtr pScrn, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int i;
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information using the slow routines */
+ xf86SlowBcopy((CARD8*)pGlint->FbBase, (CARD8*)pGlint->VGAdata, 65536);
+
+ if ((pGlint->numMultiDevices == 2) || (IS_J2000)) {
+ SAVEREG(GCSRAperture);
+ }
+
+ if (pGlint->MultiAperture) {
+ SAVEREG(GMultGLINTAperture);
+ SAVEREG(GMultGLINT1);
+ SAVEREG(GMultGLINT2);
+ }
+
+ /* Permedia 3 memory Timings */
+ SAVEREG(PM3MemBypassWriteMask);
+ SAVEREG(PM3ByAperture1Mode);
+ SAVEREG(PM3ByAperture2Mode);
+ SAVEREG(ChipConfig);
+ SAVEREG(Aperture0);
+ SAVEREG(Aperture1);
+ SAVEREG(PM3FifoControl);
+
+ if (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)
+ SAVEREG(DFIFODis);
+ SAVEREG(FIFODis);
+ SAVEREG(PMHTotal);
+ SAVEREG(PMHbEnd);
+ SAVEREG(PMHgEnd);
+ SAVEREG(PMScreenStride);
+ SAVEREG(PMHsStart);
+ SAVEREG(PMHsEnd);
+ SAVEREG(PMVTotal);
+ SAVEREG(PMVbEnd);
+ SAVEREG(PMVsStart);
+ SAVEREG(PMVsEnd);
+ SAVEREG(PMScreenBase);
+ SAVEREG(PMVideoControl);
+ SAVEREG(VClkCtl);
+ if (pGlint->UseFlatPanel) {
+ SAVEREG(VSConfiguration);
+ SAVEREG(VSBBase);
+ }
+
+ for (i=0;i<768;i++) {
+ Permedia2ReadAddress(pScrn, i);
+ pReg->cmap[i] = Permedia2ReadData(pScrn);
+ }
+
+ SAVEREG(PM2VDACRDIndexControl);
+ P2VIN(PM2VDACRDOverlayKey);
+ P2VIN(PM2VDACRDSyncControl);
+ P2VIN(PM2VDACRDMiscControl);
+ P2VIN(PM2VDACRDDACControl);
+ P2VIN(PM2VDACRDPixelSize);
+ P2VIN(PM2VDACRDColorFormat);
+ P2VIN(PM2VDACRDDClk0PreScale);
+ P2VIN(PM2VDACRDDClk0FeedbackScale);
+ P2VIN(PM2VDACRDDClk0PostScale);
+}
+
+void
+Permedia3Restore(ScrnInfoPtr pScrn, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 temp;
+ int i;
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information using the slow routines */
+ if (pGlint->STATE)
+ xf86SlowBcopy((CARD8*)pGlint->VGAdata, (CARD8*)pGlint->FbBase, 65536);
+
+ if ((pGlint->numMultiDevices == 2) || (IS_J2000)) {
+ RESTOREREG(GCSRAperture);
+ }
+
+ if (pGlint->MultiAperture) {
+ RESTOREREG(GMultGLINTAperture);
+ RESTOREREG(GMultGLINT1);
+ RESTOREREG(GMultGLINT2);
+ }
+
+ /* Permedia 3 memory Timings */
+ RESTOREREG(PM3MemBypassWriteMask);
+ RESTOREREG(PM3ByAperture1Mode);
+ RESTOREREG(PM3ByAperture2Mode);
+ RESTOREREG(ChipConfig);
+ RESTOREREG(Aperture0);
+ RESTOREREG(Aperture1);
+ RESTOREREG(PM3FifoControl);
+ if (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_GAMMA)
+ RESTOREREG(DFIFODis);
+ RESTOREREG(FIFODis);
+ RESTOREREG(PMVideoControl);
+ RESTOREREG(PMHbEnd);
+ RESTOREREG(PMHgEnd);
+ RESTOREREG(PMScreenBase);
+ RESTOREREG(VClkCtl);
+ RESTOREREG(PMScreenStride);
+ RESTOREREG(PMHTotal);
+ RESTOREREG(PMHsStart);
+ RESTOREREG(PMHsEnd);
+ RESTOREREG(PMVTotal);
+ RESTOREREG(PMVbEnd);
+ RESTOREREG(PMVsStart);
+ RESTOREREG(PMVsEnd);
+
+ if (pGlint->UseFlatPanel) {
+ RESTOREREG(VSConfiguration);
+ RESTOREREG(VSBBase);
+ }
+
+ RESTOREREG(PM2VDACRDIndexControl);
+ P2VOUT(PM2VDACRDOverlayKey);
+ P2VOUT(PM2VDACRDSyncControl);
+ P2VOUT(PM2VDACRDMiscControl);
+ P2VOUT(PM2VDACRDDACControl);
+ P2VOUT(PM2VDACRDPixelSize);
+ P2VOUT(PM2VDACRDColorFormat);
+
+ for (i=0;i<768;i++) {
+ Permedia2WriteAddress(pScrn, i);
+ Permedia2WriteData(pScrn, pReg->cmap[i]);
+ }
+
+ temp = Permedia2vInIndReg(pScrn, PM2VDACIndexClockControl) & 0xFC;
+ P2VOUT(PM2VDACRDDClk0PreScale);
+ P2VOUT(PM2VDACRDDClk0FeedbackScale);
+ P2VOUT(PM2VDACRDDClk0PostScale);
+ Permedia2vOutIndReg(pScrn, PM2VDACIndexClockControl, 0x00, temp|0x03);
+}
+
+void Permedia3LoadPalette(
+ ScrnInfoPtr pScrn,
+ int numColors,
+ int *indices,
+ LOCO *colors,
+ VisualPtr pVisual
+){
+#if 0
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+#endif
+ int i, index, shift = 0, j, repeat = 1;
+
+ if (pScrn->depth == 15) {
+ repeat = 8;
+ shift = 3;
+ }
+
+ for(i = 0; i < numColors; i++) {
+ index = indices[i];
+ for (j = 0; j < repeat; j++) {
+ Permedia2WriteAddress(pScrn, (index << shift)+j);
+ Permedia2WriteData(pScrn, colors[index].red);
+ Permedia2WriteData(pScrn, colors[index].green);
+ Permedia2WriteData(pScrn, colors[index].blue);
+ }
+#if 0
+ GLINT_SLOW_WRITE_REG(index, PM3LUTIndex);
+ GLINT_SLOW_WRITE_REG((colors[index].red & 0xFF) |
+ ((colors[index].green & 0xFF) << 8) |
+ ((colors[index].blue & 0xFF) << 16),
+ PM3LUTData);
+#endif
+ }
+}
+
+/* special one for 565 mode */
+void Permedia3LoadPalette16(
+ ScrnInfoPtr pScrn,
+ int numColors,
+ int *indices,
+ LOCO *colors,
+ VisualPtr pVisual
+){
+#if 0
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+#endif
+ int i, index, j;
+
+ for(i = 0; i < numColors; i++) {
+ index = indices[i];
+ for (j = 0; j < 4; j++) {
+ Permedia2WriteAddress(pScrn, (index << 2)+j);
+ Permedia2WriteData(pScrn, colors[index >> 1].red);
+ Permedia2WriteData(pScrn, colors[index].green);
+ Permedia2WriteData(pScrn, colors[index >> 1].blue);
+ }
+#if 0
+ GLINT_SLOW_WRITE_REG(index, PM3LUTIndex);
+ GLINT_SLOW_WRITE_REG((colors[index].red & 0xFF) |
+ ((colors[index].green & 0xFF) << 8) |
+ ((colors[index].blue & 0xFF) << 16),
+ PM3LUTData);
+#endif
+
+ if(index <= 31) {
+ for (j = 0; j < 4; j++) {
+ Permedia2WriteAddress(pScrn, (index << 3)+j);
+ Permedia2WriteData(pScrn, colors[index].red);
+ Permedia2WriteData(pScrn, colors[(index << 1) + 1].green);
+ Permedia2WriteData(pScrn, colors[index].blue);
+ }
+ }
+ }
+}
diff --git a/src/pm3_regs.h b/src/pm3_regs.h
new file mode 100644
index 0000000..be9fc51
--- /dev/null
+++ b/src/pm3_regs.h
@@ -0,0 +1,1111 @@
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm3_regs.h,v 1.10 2003/01/12 03:55:47 tsi Exp $ */
+
+/*
+ * glint register file
+ *
+ * Copyright by Sven Luther
+ * Authors: Sven Luther, <luther@dpt-info.u-strasbg.fr>
+ * Thomas Witzel, <twitzel@nmr.mgh.harvard.edu>
+ *
+ * this work is sponsored by Appian Graphics.
+ *
+ */
+
+#ifndef _PM3_REG_H_
+#define _PM3_REG_H_
+
+/**********************************************
+* GLINT Permedia3 Control Status registers *
+***********************************************/
+/* Control Status Registers */
+#define PM3ResetStatus 0x0000
+#define PM3IntEnable 0x0008
+#define PM3IntFlags 0x0010
+#define PM3InFIFOSpace 0x0018
+#define PM3OutFIFOWords 0x0020
+#define PM3DMAAddress 0x0028
+#define PM3DMACount 0x0030
+#define PM3ErrorFlags 0x0038
+#define PM3VClkCtl 0x0040
+#define PM3TestRegister 0x0048
+#define PM3Aperture0 0x0050
+#define PM3Aperture1 0x0058
+#define PM3DMAControl 0x0060
+#define PM3FIFODis 0x0068
+#define PM3ChipConfig 0x0070
+#define PM3AGPControl 0x0078
+
+#define PM3GPOutDMAAddress 0x0080
+#define PM3PCIFeedbackCount 0x0088
+#define PM3PCIAbortStatus 0x0090
+#define PM3PCIAbortAddress 0x0098
+
+#define PM3PCIPLLStatus 0x00f0
+
+#define PM3HostTextureAddress 0x0100
+#define PM3TextureDownloadControl 0x0108
+#define PM3TextureOperation 0x0110
+#define PM3LogicalTexturePage 0x0118
+#define PM3TexDMAAddress 0x0120
+#define PM3TexFIFOSpace 0x0128
+
+/**********************************************
+* GLINT Permedia3 Region 0 Bypass Controls *
+***********************************************/
+#define PM3ByAperture1Mode 0x0300
+# define PM3ByApertureMode_BYTESWAP_ABCD (0<<0)
+# define PM3ByApertureMode_BYTESWAP_BADC (1<<0)
+# define PM3ByApertureMode_BYTESWAP_CDAB (2<<0)
+# define PM3ByApertureMode_BYTESWAP_DCBA (3<<0)
+# define PM3ByApertureMode_PATCH_DISABLE (0<<2)
+# define PM3ByApertureMode_PATCH_ENABLE (1<<2)
+# define PM3ByApertureMode_FORMAT_RAW (0<<3)
+# define PM3ByApertureMode_FORMAT_YUYV (1<<3)
+# define PM3ByApertureMode_FORMAT_UYVY (2<<3)
+# define PM3ByApertureMode_PIXELSIZE_8BIT (0<<5)
+# define PM3ByApertureMode_PIXELSIZE_16BIT (1<<5)
+# define PM3ByApertureMode_PIXELSIZE_32BIT (2<<5)
+# define PM3ByApertureMode_EFFECTIVE_STRIDE_1024 (0<<7)
+# define PM3ByApertureMode_EFFECTIVE_STRIDE_2048 (1<<7)
+# define PM3ByApertureMode_EFFECTIVE_STRIDE_4096 (2<<7)
+# define PM3ByApertureMode_EFFECTIVE_STRIDE_8192 (3<<7)
+# define PM3ByApertureMode_PATCH_OFFSET_X(off) (((off)&7f)<<9)
+# define PM3ByApertureMode_PATCH_OFFSET_Y(off) (((off)&7f)<<16)
+# define PM3ByApertureMode_FRAMEBUFFER (0<<21)
+# define PM3ByApertureMode_LOCALBUFFER (1<<21)
+# define PM3ByApertureMode_DOUBLE_WRITE_OFF (0<<22)
+# define PM3ByApertureMode_DOUBLE_WRITE_1MB (1<<22)
+# define PM3ByApertureMode_DOUBLE_WRITE_2MB (2<<22)
+# define PM3ByApertureMode_DOUBLE_WRITE_4MB (3<<22)
+# define PM3ByApertureMode_DOUBLE_WRITE_8MB (4<<22)
+# define PM3ByApertureMode_DOUBLE_WRITE_16MB (5<<22)
+# define PM3ByApertureMode_DOUBLE_WRITE_32MB (6<<22)
+
+#define PM3ByAperture2Mode 0x0328
+
+/**********************************************
+* GLINT Permedia3 Memory Control (0x1000) *
+***********************************************/
+#define PM3MemCounter 0x1000
+#define PM3MemBypassWriteMask 0x1008
+#define PM3MemScratch 0x1010
+#define PM3LocalMemCaps 0x1018
+# define PM3LocalMemCaps_NoWriteMask (1<<28)
+#define PM3LocalMemTimings 0x1020
+#define PM3LocalMemControl 0x1028
+#define PM3LocalMemRefresh 0x1030
+#define PM3LocalMemPowerDown 0x1038
+#define PM3RemoteMemControl 0x1100
+
+/**********************************************
+* GLINT Permedia3 Video Control (0x3000) *
+***********************************************/
+
+#define PM3ScreenBase 0x3000
+#define PM3ScreenStride 0x3008
+#define PM3HTotal 0x3010
+#define PM3HgEnd 0x3018
+#define PM3HbEnd 0x3020
+#define PM3HsStart 0x3028
+#define PM3HsEnd 0x3030
+#define PM3VTotal 0x3038
+#define PM3VbEnd 0x3040
+#define PM3VsStart 0x3048
+#define PM3VsEnd 0x3050
+#define PM3VideoControl 0x3058
+# define PM3VideoControl_DISABLE (0<<0)
+# define PM3VideoControl_ENABLE (1<<0)
+# define PM3VideoControl_BLANK_ACTIVE_HIGH (0<<1)
+# define PM3VideoControl_BLANK_ACTIVE_LOW (1<<1)
+# define PM3VideoControl_LINE_DOUBLE_OFF (0<<2)
+# define PM3VideoControl_LINE_DOUBLE_ON (1<<2)
+# define PM3VideoControl_HSYNC_FORCE_HIGH (0<<3)
+# define PM3VideoControl_HSYNC_ACTIVE_HIGH (1<<3)
+# define PM3VideoControl_HSYNC_FORCE_LOW (2<<3)
+# define PM3VideoControl_HSYNC_ACTIVE_LOW (3<<3)
+# define PM3VideoControl_VSYNC_FORCE_HIGH (0<<5)
+# define PM3VideoControl_VSYNC_ACTIVE_HIGH (1<<5)
+# define PM3VideoControl_VSYNC_FORCE_LOW (2<<5)
+# define PM3VideoControl_VSYNC_ACTIVE_LOW (3<<5)
+# define PM3VideoControl_BYTE_DOUBLE_OFF (0<<7)
+# define PM3VideoControl_BYTE_DOUBLE_ON (1<<7)
+# define PM3VideoControl_BUFFER_SWAP_SYNCON_FRAMEBLANK (0<<9)
+# define PM3VideoControl_BUFFER_SWAP_FREE_RUNNING (1<<9)
+# define PM3VideoControl_BUFFER_SWAP_LIMITETO_FRAMERATE (2<<9)
+# define PM3VideoControl_STEREO_DISABLE (0<<11)
+# define PM3VideoControl_STEREO_ENABLE (1<<11)
+# define PM3VideoControl_RIGHT_EYE_ACTIVE_HIGH (0<<12)
+# define PM3VideoControl_RIGHT_EYE_ACTIVE_LOW (1<<12)
+# define PM3VideoControl_VIDEO_EXT_LOW (0<<14)
+# define PM3VideoControl_VIDEO_EXT_HIGH (1<<14)
+# define PM3VideoControl_SYNC_MODE_INDEPENDENT (0<<16)
+# define PM3VideoControl_SYNC_MODE_SYNCTO_VSA (1<<16)
+# define PM3VideoControl_SYNC_MODE_SYNCTO_VSB (2<<16)
+# define PM3VideoControl_PATCH_DISABLE (0<<18)
+# define PM3VideoControl_PATCH_ENABLE (1<<18)
+# define PM3VideoControl_PIXELSIZE_8BIT (0<<19)
+# define PM3VideoControl_PIXELSIZE_16BIT (1<<19)
+# define PM3VideoControl_PIXELSIZE_32BIT (2<<19)
+# define PM3VideoControl_DISPLAY_DISABLE (0<<21)
+# define PM3VideoControl_DISPLAY_ENABLE (1<<21)
+# define PM3VideoControl_PATCH_OFFSET_X(off) (((off)&0x3f)<<22)
+# define PM3VideoControl_PATCH_OFFSET_Y(off) (((off)&0x3f)<<28)
+#define PM3InterruptLine 0x3060
+#define PM3DisplayData 0x3068
+#define PM3VerticalLineCount 0x3070
+#define PM3FifoControl 0x3078
+#define PM3ScreenBaseRight 0x3080
+#define PM3MiscControl 0x3088
+
+#define PM3VideoOverlayUpdate 0x3100
+# define PM3VideoOverlayUpdate_DISABLE (0<<0)
+# define PM3VideoOverlayUpdate_ENABLE (1<<0)
+#define PM3VideoOverlayMode 0x3108
+# define PM3VideoOverlayMode_DISABLE (0<<0)
+# define PM3VideoOverlayMode_ENABLE (1<<0)
+# define PM3VideoOverlayMode_BUFFERSYNC_MANUAL (0<<1)
+# define PM3VideoOverlayMode_BUFFERSYNC_VIDEOSTREAMA (1<<1)
+# define PM3VideoOverlayMode_BUFFERSYNC_VIDEOSTREAMB (2<<1)
+# define PM3VideoOverlayMode_FIELDPOLARITY_NORMAL (0<<4)
+# define PM3VideoOverlayMode_FIELDPOLARITY_INVERT (1<<4)
+# define PM3VideoOverlayMode_PIXELSIZE_8BIT (0<<5)
+# define PM3VideoOverlayMode_PIXELSIZE_16BIT (1<<5)
+# define PM3VideoOverlayMode_PIXELSIZE_32BIT (2<<5)
+# define PM3VideoOverlayMode_COLORFORMAT_RGB8888 ((0<<7)|(1<<12)|(2<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_RGB4444 ((1<<7)|(1<<12)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_RGB5551 ((2<<7)|(1<<12)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_RGB565 ((3<<7)|(1<<12)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_RGB332 ((4<<7)|(1<<12)|(0<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_BGR8888 ((0<<7)|(2<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_BGR4444 ((1<<7)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_BGR5551 ((2<<7)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_BGR565 ((3<<7)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_BGR332 ((4<<7)|(0<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_CI8 ((5<<7)|(1<<12)|(0<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_VUY444 ((2<<10)|(1<<12)|(2<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_YUV444 ((2<<10)|(2<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_VUY422 ((1<<10)|(1<<12)|(1<<5))
+# define PM3VideoOverlayMode_COLORFORMAT_YUV422 ((1<<10)|(1<<5))
+# define PM3VideoOverlayMode_COLORORDER_BGR (0<<12)
+# define PM3VideoOverlayMode_COLORORDER_RGB (1<<12)
+# define PM3VideoOverlayMode_LINEARCOLOREXT_OFF (0<<13)
+# define PM3VideoOverlayMode_LINEARCOLOREXT_ON (1<<13)
+# define PM3VideoOverlayMode_FILTER_MASK (3<<14)
+# define PM3VideoOverlayMode_FILTER_OFF (0<<14)
+# define PM3VideoOverlayMode_FILTER_FULL (1<<14)
+# define PM3VideoOverlayMode_FILTER_PARTIAL (2<<14)
+# define PM3VideoOverlayMode_DEINTERLACE_OFF (0<<16)
+# define PM3VideoOverlayMode_DEINTERLACE_BOB (1<<16)
+# define PM3VideoOverlayMode_PATCHMODE_OFF (0<<18)
+# define PM3VideoOverlayMode_PATCHMODE_ON (1<<18)
+# define PM3VideoOverlayMode_FLIP_VIDEO (0<<20)
+# define PM3VideoOverlayMode_FLIP_VIDEOSTREAMA (1<<20)
+# define PM3VideoOverlayMode_FLIP_VIDEOSTREAMB (2<<20)
+# define PM3VideoOverlayMode_MIRROR_MASK (3<<23)
+# define PM3VideoOverlayMode_MIRRORX_OFF (0<<23)
+# define PM3VideoOverlayMode_MIRRORX_ON (1<<23)
+# define PM3VideoOverlayMode_MIRRORY_OFF (0<<24)
+# define PM3VideoOverlayMode_MIRRORY_ON (1<<24)
+#define PM3VideoOverlayFifoControl 0x3110
+#define PM3VideoOverlayIndex 0x3118
+#define PM3VideoOverlayBase 0x3120
+#define PM3VideoOverlayBase0 0x3120
+#define PM3VideoOverlayBase1 0x3128
+#define PM3VideoOverlayBase2 0x3130
+#define PM3VideoOverlayStride 0x3138
+# define PM3VideoOverlayStride_STRIDE(s) (((s)&0xfff)<<0)
+#define PM3VideoOverlayWidth 0x3140
+# define PM3VideoOverlayWidth_WIDTH(w) (((w)&0xfff)<<0)
+#define PM3VideoOverlayHeight 0x3148
+# define PM3VideoOverlayHeight_HEIGHT(h) (((h)&0xfff)<<0)
+#define PM3VideoOverlayOrigin 0x3150
+# define PM3VideoOverlayOrigin_XORIGIN(x) (((x)&0xfff)<<0)
+# define PM3VideoOverlayOrigin_YORIGIN(y) (((y)&0xfff)<<16)
+#define PM3VideoOverlayShrinkXDelta 0x3158
+# define PM3VideoOverlayShrinkXDelta_NONE (1<<16)
+# define PM3VideoOverlayShrinkXDelta_DELTA(s,d) \
+ ((((s)<<16)/(d))&0x0ffffff0)
+#define PM3VideoOverlayZoomXDelta 0x3160
+# define PM3VideoOverlayZoomXDelta_NONE (1<<16)
+# define PM3VideoOverlayZoomXDelta_DELTA(s,d) \
+ ((((s)<<16)/(d))&0x0001fff0)
+#define PM3VideoOverlayYDelta 0x3168
+# define PM3VideoOverlayYDelta_NONE (1<<16)
+# define PM3VideoOverlayYDelta_DELTA(s,d) \
+ ((((s)<<16)/(d))&0x0ffffff0)
+#define PM3VideoOverlayFieldOffset 0x3170
+#define PM3VideoOverlayStatus 0x3178
+
+/**********************************************
+* GLINT Permedia3 RAMDAC Registers (0x4000) *
+***********************************************/
+/* Direct Registers */
+#define PM3RD_PaletteWriteAddress 0x4000
+#define PM3RD_PaletteData 0x4008
+#define PM3RD_PixelMask 0x4010
+#define PM3RD_PaletteReadAddress 0x4018
+
+#define PM3RD_IndexLow 0x4020
+#define PM3RD_IndexHigh 0x4028
+#define PM3RD_IndexedData 0x4030
+#define PM3RD_IndexControl 0x4038
+# define PM3RD_IndexControl_AUTOINCREMENT_ENABLE (1<<0)
+# define PM3RD_IndexControl_AUTOINCREMENT_DISABLE (0<<0)
+
+/* Indirect Registers */
+#define PM3RD_MiscControl 0x000
+# define PM3RD_MiscControl_HIGHCOLOR_RES_DISABLE (0<<0)
+# define PM3RD_MiscControl_HIGHCOLOR_RES_ENABLE (1<<0)
+# define PM3RD_MiscControl_PIXELDOUBLE_DISABLE (0<<1)
+# define PM3RD_MiscControl_PIXELDOUBLE_ENABLE (1<<1)
+# define PM3RD_MiscControl_LASTREAD_ADDR_DISABLE (0<<2)
+# define PM3RD_MiscControl_LASTREAD_ADDR_ENABLE (1<<2)
+# define PM3RD_MiscControl_DIRECTCOLOR_DISABLE (0<<3)
+# define PM3RD_MiscControl_DIRECTCOLOR_ENABLE (1<<3)
+# define PM3RD_MiscControl_OVERLAY_DISABLE (0<<4)
+# define PM3RD_MiscControl_OVERLAY_ENABLE (1<<4)
+# define PM3RD_MiscControl_PIXELDOUBLE_BUFFER_DISABLE (0<<5)
+# define PM3RD_MiscControl_PIXELDOUBLE_BUFFER_ENABLE (1<<5)
+# define PM3RD_MiscControl_VSB_OUTPUT_DISABLE (0<<6)
+# define PM3RD_MiscControl_VSB_OUTPUT_ENABLE (1<<6)
+# define PM3RD_MiscControl_STEREODOUBLE_BUFFER_DISABLE (0<<7)
+# define PM3RD_MiscControl_STEREODOUBLE_BUFFER_ENABLE (1<<7)
+#define PM3RD_SyncControl 0x001
+# define PM3RD_SyncControl_HSYNC_ACTIVE_LOW (0<<0)
+# define PM3RD_SyncControl_HSYNC_ACTIVE_HIGH (1<<0)
+# define PM3RD_SyncControl_HSYNC_FORCE_ACTIVE (3<<0)
+# define PM3RD_SyncControl_HSYNC_FORCE_INACTIVE (4<<0)
+# define PM3RD_SyncControl_HSYNC_TRI_STATE (2<<0)
+# define PM3RD_SyncControl_VSYNC_ACTIVE_LOW (0<<3)
+# define PM3RD_SyncControl_VSYNC_ACTIVE_HIGH (1<<3)
+# define PM3RD_SyncControl_VSYNC_TRI_STATE (2<<3)
+# define PM3RD_SyncControl_VSYNC_FORCE_ACTIVE (3<<3)
+# define PM3RD_SyncControl_VSYNC_FORCE_INACTIVE (4<<3)
+# define PM3RD_SyncControl_HSYNC_OVERRIDE_SETBY_HSYNC (0<<6)
+# define PM3RD_SyncControl_HSYNC_OVERRIDE_FORCE_HIGH (1<<6)
+# define PM3RD_SyncControl_VSYNC_OVERRIDE_SETBY_VSYNC (0<<7)
+# define PM3RD_SyncControl_VSYNC_OVERRIDE_FORCE_HIGH (1<<7)
+#define PM3RD_DACControl 0x002
+# define PM3RD_DACControl_DAC_POWER_ON (0<<0)
+# define PM3RD_DACControl_DAC_POWER_OFF (1<<0)
+# define PM3RD_DACControl_SYNC_ON_GREEN_DISABLE (0<<3)
+# define PM3RD_DACControl_SYNC_ON_GREEN_ENABLE (1<<3)
+# define PM3RD_DACControl_BLANK_RED_DAC_DISABLE (0<<4)
+# define PM3RD_DACControl_BLANK_RED_DAC_ENABLE (1<<4)
+# define PM3RD_DACControl_BLANK_GREEN_DAC_DISABLE (0<<5)
+# define PM3RD_DACControl_BLANK_GREEN_DAC_ENABLE (1<<5)
+# define PM3RD_DACControl_BLANK_BLUE_DAC_DISABLE (0<<6)
+# define PM3RD_DACControl_BLANK_BLUE_DAC_ENABLE (1<<6)
+# define PM3RD_DACControl_BLANK_PEDESTAL_DISABLE (0<<7)
+# define PM3RD_DACControl_BLANK_PEDESTAL_ENABLE (1<<7)
+#define PM3RD_PixelSize 0x003
+# define PM3RD_PixelSize_24_BIT_PIXELS (4<<0)
+# define PM3RD_PixelSize_32_BIT_PIXELS (2<<0)
+# define PM3RD_PixelSize_16_BIT_PIXELS (1<<0)
+# define PM3RD_PixelSize_8_BIT_PIXELS (0<<0)
+#define PM3RD_ColorFormat 0x004
+# define PM3RD_ColorFormat_LINEAR_COLOR_EXT_ENABLE (1<<6)
+# define PM3RD_ColorFormat_LINEAR_COLOR_EXT_DISABLE (0<<6)
+# define PM3RD_ColorFormat_COLOR_ORDER_BLUE_LOW (1<<5)
+# define PM3RD_ColorFormat_COLOR_ORDER_RED_LOW (0<<5)
+# define PM3RD_ColorFormat_COLOR_FORMAT_MASK (0x1f<<0)
+# define PM3RD_ColorFormat_8888_COLOR (0<<0)
+# define PM3RD_ColorFormat_5551_FRONT_COLOR (1<<0)
+# define PM3RD_ColorFormat_4444_COLOR (2<<0)
+# define PM3RD_ColorFormat_332_FRONT_COLOR (5<<0)
+# define PM3RD_ColorFormat_332_BACK_COLOR (6<<0)
+# define PM3RD_ColorFormat_2321_FRONT_COLOR (9<<0)
+# define PM3RD_ColorFormat_2321_BACK_COLOR (10<<0)
+# define PM3RD_ColorFormat_232_FRONTOFF_COLOR (11<<0)
+# define PM3RD_ColorFormat_232_BACKOFF_COLOR (12<<0)
+# define PM3RD_ColorFormat_5551_BACK_COLOR (13<<0)
+# define PM3RD_ColorFormat_CI8_COLOR (14<<0)
+# define PM3RD_ColorFormat_565_FRONT_COLOR (16<<0)
+# define PM3RD_ColorFormat_565_BACK_COLOR (17<<0)
+#define PM3RD_CursorMode 0x005
+# define PM3RD_CursorMode_CURSOR_DISABLE (0<<0)
+# define PM3RD_CursorMode_CURSOR_ENABLE (1<<0)
+# define PM3RD_CursorMode_FORMAT_64x64_2BPE_P0123 (0<<2)
+# define PM3RD_CursorMode_FORMAT_32x32_2BPE_P0 (1<<2)
+# define PM3RD_CursorMode_FORMAT_32x32_2BPE_P1 (2<<2)
+# define PM3RD_CursorMode_FORMAT_32x32_2BPE_P2 (3<<2)
+# define PM3RD_CursorMode_FORMAT_32x32_2BPE_P3 (4<<2)
+# define PM3RD_CursorMode_FORMAT_32x32_4BPE_P01 (5<<2)
+# define PM3RD_CursorMode_FORMAT_32x32_4BPE_P23 (6<<2)
+# define PM3RD_CursorMode_TYPE_MS (0<<4)
+# define PM3RD_CursorMode_TYPE_X (1<<4)
+# define PM3RD_CursorMode_REVERSE_PIXEL_ORDER_DISABLE (0<<6)
+# define PM3RD_CursorMode_REVERSE_PIXEL_ORDER_ENABLE (1<<6)
+# define PM3RD_CursorMode_REVERSE_PIXEL_ORDER_3_COLOR (2<<6)
+# define PM3RD_CursorMode_REVERSE_PIXEL_ORDER_15_COLOR (3<<6)
+#define PM3RD_CursorControl 0x006
+# define PM3RD_CursorControl_DOUBLE_X_DISABLED (0<<0)
+# define PM3RD_CursorControl_DOUBLE_X_ENABLED (1<<0)
+# define PM3RD_CursorControl_DOUBLE_Y_DISABLED (0<<1)
+# define PM3RD_CursorControl_DOUBLE_Y_ENABLED (1<<1)
+# define PM3RD_CursorControl_READBACK_POS_DISABLED (0<<2)
+# define PM3RD_CursorControl_READBACK_POS_ENABLED (1<<2)
+
+#define PM3RD_CursorXLow 0x007
+#define PM3RD_CursorXHigh 0x008
+#define PM3RD_CursorYLow 0x009
+#define PM3RD_CursorYHigh 0x00a
+#define PM3RD_CursorHotSpotX 0x00b
+#define PM3RD_CursorHotSpotY 0x00c
+#define PM3RD_OverlayKey 0x00d
+#define PM3RD_Pan 0x00e
+# define PM3RD_Pan_DISABLE (0<<0)
+# define PM3RD_Pan_ENABLE (1<<0)
+# define PM3RD_Pan_GATE_DISABLE (0<<1)
+# define PM3RD_Pan_GATE_ENABLE (1<<1)
+#define PM3RD_Sense 0x00f
+
+#define PM3RD_CheckControl 0x018
+# define PM3RD_CheckControl_PIXEL_DISABLED (0<<0)
+# define PM3RD_CheckControl_PIXEL_ENABLED (1<<0)
+# define PM3RD_CheckControl_LUT_DISABLED (0<<1)
+# define PM3RD_CheckControl_LUT_ENABLED (1<<1)
+#define PM3RD_CheckPixelRed 0x019
+#define PM3RD_CheckPixelGreen 0x01a
+#define PM3RD_CheckPixelBlue 0x01b
+#define PM3RD_CheckLUTRed 0x01c
+#define PM3RD_CheckLUTGreen 0x01d
+#define PM3RD_CheckLUTBlue 0x01e
+#define PM3RD_Scratch 0x01f
+
+#define PM3RD_VideoOverlayControl 0x020
+# define PM3RD_VideoOverlayControl_DISABLE (0<<0)
+# define PM3RD_VideoOverlayControl_ENABLE (1<<0)
+# define PM3RD_VideoOverlayControl_MODE_MASK (3<<1)
+# define PM3RD_VideoOverlayControl_MODE_MAINKEY (0<<1)
+# define PM3RD_VideoOverlayControl_MODE_OVERLAYKEY (1<<1)
+# define PM3RD_VideoOverlayControl_MODE_ALWAYS (2<<1)
+# define PM3RD_VideoOverlayControl_MODE_BLEND (3<<1)
+# define PM3RD_VideoOverlayControl_DIRECTCOLOR_DISABLED (0<<3)
+# define PM3RD_VideoOverlayControl_DIRECTCOLOR_ENABLED (1<<3)
+# define PM3RD_VideoOverlayControl_BLENDSRC_MAIN (0<<4)
+# define PM3RD_VideoOverlayControl_BLENDSRC_REGISTER (1<<4)
+# define PM3RD_VideoOverlayControl_KEY_COLOR (0<<5)
+# define PM3RD_VideoOverlayControl_KEY_ALPHA (1<<5)
+#define PM3RD_VideoOverlayXStartLow 0x021
+#define PM3RD_VideoOverlayXStartHigh 0x022
+#define PM3RD_VideoOverlayYStartLow 0x023
+#define PM3RD_VideoOverlayYStartHigh 0x024
+#define PM3RD_VideoOverlayXEndLow 0x025
+#define PM3RD_VideoOverlayXEndHigh 0x026
+#define PM3RD_VideoOverlayYEndLow 0x027
+#define PM3RD_VideoOverlayYEndHigh 0x028
+#define PM3RD_VideoOverlayKeyR 0x029
+#define PM3RD_VideoOverlayKeyG 0x02a
+#define PM3RD_VideoOverlayKeyB 0x02b
+#define PM3RD_VideoOverlayBlend 0x02c
+# define PM3RD_VideoOverlayBlend_FACTOR_0_PERCENT (0<<6)
+# define PM3RD_VideoOverlayBlend_FACTOR_25_PERCENT (1<<6)
+# define PM3RD_VideoOverlayBlend_FACTOR_75_PERCENT (2<<6)
+# define PM3RD_VideoOverlayBlend_FACTOR_100_PERCENT (3<<6)
+
+#define PM3RD_DClkSetup1 0x1f0
+#define PM3RD_DClkSetup2 0x1f1
+#define PM3RD_KClkSetup1 0x1f2
+#define PM3RD_KClkSetup2 0x1f3
+
+#define PM3RD_DClkControl 0x200
+# define PM3RD_DClkControl_SOURCE_PLL (0<<4)
+# define PM3RD_DClkControl_SOURCE_VSA (1<<4)
+# define PM3RD_DClkControl_SOURCE_VSB (2<<4)
+# define PM3RD_DClkControl_SOURCE_EXT (3<<4)
+# define PM3RD_DClkControl_STATE_RUN (2<<2)
+# define PM3RD_DClkControl_STATE_HIGH (1<<2)
+# define PM3RD_DClkControl_STATE_LOW (0<<2)
+# define PM3RD_DClkControl_LOCKED (1<<1)
+# define PM3RD_DClkControl_NOT_LOCKED (0<<1)
+# define PM3RD_DClkControl_ENABLE (1<<0)
+# define PM3RD_DClkControl_DISABLE (0<<0)
+#define PM3RD_DClk0PreScale 0x201
+#define PM3RD_DClk0FeedbackScale 0x202
+#define PM3RD_DClk0PostScale 0x203
+#define PM3RD_DClk1PreScale 0x204
+#define PM3RD_DClk1FeedbackScale 0x205
+#define PM3RD_DClk1PostScale 0x206
+#define PM3RD_DClk2PreScale 0x207
+#define PM3RD_DClk2FeedbackScale 0x208
+#define PM3RD_DClk2PostScale 0x209
+#define PM3RD_DClk3PreScale 0x20a
+#define PM3RD_DClk3FeedbackScale 0x20b
+#define PM3RD_DClk3PostScale 0x20c
+#define PM3RD_KClkControl 0x20d
+# define PM3RD_KClkControl_DISABLE (0<<0)
+# define PM3RD_KClkControl_ENABLE (1<<0)
+# define PM3RD_KClkControl_NOT_LOCKED (0<<1)
+# define PM3RD_KClkControl_LOCKED (1<<1)
+# define PM3RD_KClkControl_STATE_LOW (0<<2)
+# define PM3RD_KClkControl_STATE_HIGH (1<<2)
+# define PM3RD_KClkControl_STATE_RUN (2<<2)
+# define PM3RD_KClkControl_STATE_LOW_POWER (3<<2)
+# define PM3RD_KClkControl_SOURCE_PCLK (0<<4)
+# define PM3RD_KClkControl_SOURCE_HALF_PCLK (1<<4)
+# define PM3RD_KClkControl_SOURCE_PLL (2<<4)
+#define PM3RD_KClkPreScale 0x20e
+#define PM3RD_KClkFeedbackScale 0x20f
+#define PM3RD_KClkPostScale 0x210
+#define PM3RD_MClkControl 0x211
+# define PM3RD_MClkControl_DISABLE (0<<0)
+# define PM3RD_MClkControl_ENABLE (1<<0)
+# define PM3RD_MClkControl_NOT_LOCKED (0<<1)
+# define PM3RD_MClkControl_LOCKED (1<<1)
+# define PM3RD_MClkControl_STATE_LOW (0<<2)
+# define PM3RD_MClkControl_STATE_HIGH (1<<2)
+# define PM3RD_MClkControl_STATE_RUN (2<<2)
+# define PM3RD_MClkControl_STATE_LOW_POWER (3<<2)
+# define PM3RD_MClkControl_SOURCE_PCLK (0<<4)
+# define PM3RD_MClkControl_SOURCE_HALF_PCLK (1<<4)
+# define PM3RD_MClkControl_SOURCE_HALF_EXT (3<<4)
+# define PM3RD_MClkControl_SOURCE_EXT (4<<4)
+# define PM3RD_MClkControl_SOURCE_HALF_KCLK (5<<4)
+# define PM3RD_MClkControl_SOURCE_KCLK (6<<4)
+#define PM3RD_MClkPreScale 0x212
+#define PM3RD_MClkFeedbackScale 0x213
+#define PM3RD_MClkPostScale 0x214
+#define PM3RD_SClkControl 0x215
+# define PM3RD_SClkControl_DISABLE (0<<0)
+# define PM3RD_SClkControl_ENABLE (1<<0)
+# define PM3RD_SClkControl_NOT_LOCKED (0<<1)
+# define PM3RD_SClkControl_LOCKED (1<<1)
+# define PM3RD_SClkControl_STATE_LOW (0<<2)
+# define PM3RD_SClkControl_STATE_HIGH (1<<2)
+# define PM3RD_SClkControl_STATE_RUN (2<<2)
+# define PM3RD_SClkControl_STATE_LOW_POWER (3<<2)
+# define PM3RD_SClkControl_SOURCE_PCLK (0<<4)
+# define PM3RD_SClkControl_SOURCE_HALF_PCLK (1<<4)
+# define PM3RD_SClkControl_SOURCE_HALF_EXT (3<<4)
+# define PM3RD_SClkControl_SOURCE_EXT (4<<4)
+# define PM3RD_SClkControl_SOURCE_HALF_KCLK (5<<4)
+# define PM3RD_SClkControl_SOURCE_KCLK (6<<4)
+#define PM3RD_SClkPreScale 0x216
+#define PM3RD_SClkFeedbackScale 0x217
+#define PM3RD_SClkPostScale 0x218
+
+#define PM3RD_CursorPalette(p) (0x303+(p))
+#define PM3RD_CursorPattern(p) (0x400+(p))
+/******************************************************
+* GLINT Permedia3 Video Streaming Registers (0x5000) *
+*******************************************************/
+
+#define PM3VSConfiguration 0x5800
+
+/**********************************************
+* GLINT Permedia3 Core Registers (0x8000+) *
+***********************************************/
+#define PM3AALineWidth 0x94c0
+#define PM3AAPointsize 0x94a0
+#define PM3AlphaBlendAlphaMode 0xafa8
+#define PM3AlphaBlendAlphaModeAnd 0xad30
+#define PM3AlphaBlendAlphaModeOr 0xad38
+#define PM3AlphaBlendColorMode 0xafa0
+#define PM3AlphaBlendColorModeAnd 0xacb0
+#define PM3AlphaBlendColorModeOr 0xacb8
+#define PM3AlphaDestColor 0xaf88
+#define PM3AlphaSourceColor 0xaf80
+#define PM3AlphaTestMode 0x8800
+#define PM3AlphaTestModeAnd 0xabf0
+#define PM3AlphaTestModeOr 0xabf8
+#define PM3AntialiasMode 0x8808
+#define PM3AntialiasModeAnd 0xac00
+#define PM3AntialiasModeOr 0xac08
+/* ... */
+#define PM3BackgroundColor 0xb0c8
+/* ... */
+#define PM3ColorDDAMode 0x87e0
+#define PM3ColorDDAModeAnd 0xabe0
+#define PM3ColorDDAModeOr 0xabe8
+#define PM3CommandInterrupt 0xa990
+#define PM3ConstantColorDDA 0xafb0
+# define PM3ConstantColorDDA_R(r) ((r)&0xff)
+# define PM3ConstantColorDDA_G(g) (((g)&0xff)<<8)
+# define PM3ConstantColorDDA_B(b) (((b)&0xff)<<16)
+# define PM3ConstantColorDDA_A(a) (((a)&0xff)<<24)
+#define PM3ContextData 0x8dd0
+#define PM3ContextDump 0x8dc0
+#define PM3ContextRestore 0x8dc8
+#define PM3Continue 0x8058
+#define PM3ContinueNewDom 0x8048
+#define PM3ContinueNewLine 0x8040
+#define PM3ContinueNewSub 0x8050
+#define PM3Count 0x8030
+/* ... */
+#define PM3DeltaControl 0x9350
+#define PM3DeltaControlAnd 0xab20
+#define PM3DeltaControlOr 0xab28
+#define PM3DeltaMode 0x9300
+#define PM3DeltaModeAnd 0xaad0
+#define PM3DeltaModeOr 0xaad8
+/* ... */
+#define PM3DitherMode 0x8818
+#define PM3DitherModeAnd 0xacd0
+#define PM3DitherModeOr 0xacd8
+/* ... */
+#define PM3dXDom 0x8008
+#define PM3dXSub 0x8018
+#define PM3dY 0x8028
+/* ... */
+#define PM3FBBlockColor 0x8ac8
+#define PM3FBBlockColor0 0xb060
+#define PM3FBBlockColor1 0xb068
+#define PM3FBBlockColor2 0xb070
+#define PM3FBBlockColor3 0xb078
+#define PM3FBBlockColorBack 0xb0a0
+#define PM3FBBlockColorBack0 0xb080
+#define PM3FBBlockColorBack1 0xb088
+#define PM3FBBlockColorBack2 0xb090
+#define PM3FBBlockColorBack3 0xb098
+#define PM3FBColor 0x8a98
+#define PM3FBDestReadBufferAddr0 0xae80
+#define PM3FBDestReadBufferAddr1 0xae88
+#define PM3FBDestReadBufferAddr2 0xae90
+#define PM3FBDestReadBufferAddr3 0xae98
+#define PM3FBDestReadBufferOffset0 0xaea0
+#define PM3FBDestReadBufferOffset1 0xaea8
+#define PM3FBDestReadBufferOffset2 0xaeb0
+#define PM3FBDestReadBufferOffset3 0xaeb8
+# define PM3FBDestReadBufferOffset_XOffset(x) ((x)&0xffff)
+# define PM3FBDestReadBufferOffset_YOffset(y) (((y)&0xffff)<<16)
+#define PM3FBDestReadBufferWidth0 0xaec0
+#define PM3FBDestReadBufferWidth1 0xaec8
+#define PM3FBDestReadBufferWidth2 0xaed0
+#define PM3FBDestReadBufferWidth3 0xaed8
+# define PM3FBDestReadBufferWidth_Width(w) ((w)&0x0fff)
+
+#define PM3FBDestReadEnables 0xaee8
+#define PM3FBDestReadEnablesAnd 0xad20
+#define PM3FBDestReadEnablesOr 0xad28
+# define PM3FBDestReadEnables_E(e) ((e)&0xff)
+# define PM3FBDestReadEnables_E0 1<<0
+# define PM3FBDestReadEnables_E1 1<<1
+# define PM3FBDestReadEnables_E2 1<<2
+# define PM3FBDestReadEnables_E3 1<<3
+# define PM3FBDestReadEnables_E4 1<<4
+# define PM3FBDestReadEnables_E5 1<<5
+# define PM3FBDestReadEnables_E6 1<<6
+# define PM3FBDestReadEnables_E7 1<<7
+# define PM3FBDestReadEnables_R(r) (((r)&0xff)<<8)
+# define PM3FBDestReadEnables_R0 1<<8
+# define PM3FBDestReadEnables_R1 1<<9
+# define PM3FBDestReadEnables_R2 1<<10
+# define PM3FBDestReadEnables_R3 1<<11
+# define PM3FBDestReadEnables_R4 1<<12
+# define PM3FBDestReadEnables_R5 1<<13
+# define PM3FBDestReadEnables_R6 1<<14
+# define PM3FBDestReadEnables_R7 1<<15
+# define PM3FBDestReadEnables_ReferenceAlpha(a) (((a)&0xff)<<24)
+
+#define PM3FBDestReadMode 0xaee0
+#define PM3FBDestReadModeAnd 0xac90
+#define PM3FBDestReadModeOr 0xac98
+# define PM3FBDestReadMode_ReadDisable 0<<0
+# define PM3FBDestReadMode_ReadEnable 1<<0
+# define PM3FBDestReadMode_StripePitch(sp) (((sp)&0x7)<<2
+# define PM3FBDestReadMode_StripeHeight(sh) (((sh)&0x7)<<7
+# define PM3FBDestReadMode_Enable0 1<<8
+# define PM3FBDestReadMode_Enable1 1<<9
+# define PM3FBDestReadMode_Enable2 1<<10
+# define PM3FBDestReadMode_Enable3 1<<11
+# define PM3FBDestReadMode_Layout0(l) (((l)&0x3)<<12
+# define PM3FBDestReadMode_Layout1(l) (((l)&0x3)<<14
+# define PM3FBDestReadMode_Layout2(l) (((l)&0x3)<<16
+# define PM3FBDestReadMode_Layout3(l) (((l)&0x3)<<18
+# define PM3FBDestReadMode_Origin0 1<<20
+# define PM3FBDestReadMode_Origin1 1<<21
+# define PM3FBDestReadMode_Origin2 1<<22
+# define PM3FBDestReadMode_Origin3 1<<23
+# define PM3FBDestReadMode_Blocking 1<<24
+# define PM3FBDestReadMode_UseReadEnabled 1<<26
+# define PM3FBDestReadMode_AlphaFiltering 1<<27
+
+#define PM3FBHardwareWriteMask 0x8ac0
+#define PM3FBSoftwareWriteMask 0x8820
+#define PM3FBData 0x8aa0
+#define PM3FBSourceData 0x8aa8
+#define PM3FBSourceReadBufferAddr 0xaf08
+#define PM3FBSourceReadBufferOffset 0xaf10
+# define PM3FBSourceReadBufferOffset_XOffset(x) ((x)&0xffff)
+# define PM3FBSourceReadBufferOffset_YOffset(y) (((y)&0xffff)<<16)
+#define PM3FBSourceReadBufferWidth 0xaf18
+# define PM3FBSourceReadBufferWidth_Width(w) ((w)&0x0fff)
+#define PM3FBSourceReadMode 0xaf00
+#define PM3FBSourceReadModeAnd 0xaca0
+#define PM3FBSourceReadModeOr 0xaca8
+# define PM3FBSourceReadMode_ReadDisable (0<<0)
+# define PM3FBSourceReadMode_ReadEnable (1<<0)
+# define PM3FBSourceReadMode_StripePitch(sp) (((sp)&0x7)<<2
+# define PM3FBSourceReadMode_StripeHeight(sh) (((sh)&0x7)<<7
+# define PM3FBSourceReadMode_Layout(l) (((l)&0x3)<<8
+# define PM3FBSourceReadMode_Origin 1<<10
+# define PM3FBSourceReadMode_Blocking 1<<11
+# define PM3FBSourceReadMode_UserTexelCoord 1<<13
+# define PM3FBSourceReadMode_WrapXEnable 1<<14
+# define PM3FBSourceReadMode_WrapYEnable 1<<15
+# define PM3FBSourceReadMode_WrapX(w) (((w)&0xf)<<16
+# define PM3FBSourceReadMode_WrapY(w) (((w)&0xf)<<20
+# define PM3FBSourceReadMode_ExternalSourceData 1<<24
+#define PM3FBWriteBufferAddr0 0xb000
+#define PM3FBWriteBufferAddr1 0xb008
+#define PM3FBWriteBufferAddr2 0xb010
+#define PM3FBWriteBufferAddr3 0xb018
+
+#define PM3FBWriteBufferOffset0 0xb020
+#define PM3FBWriteBufferOffset1 0xb028
+#define PM3FBWriteBufferOffset2 0xb030
+#define PM3FBWriteBufferOffset3 0xb038
+# define PM3FBWriteBufferOffset_XOffset(x) ((x)&0xffff)
+# define PM3FBWriteBufferOffset_YOffset(y) (((y)&0xffff)<<16)
+
+#define PM3FBWriteBufferWidth0 0xb040
+#define PM3FBWriteBufferWidth1 0xb048
+#define PM3FBWriteBufferWidth2 0xb050
+#define PM3FBWriteBufferWidth3 0xb058
+# define PM3FBWriteBufferWidth_Width(w) ((w)&0x0fff)
+
+#define PM3FBWriteMode 0x8ab8
+#define PM3FBWriteModeAnd 0xacf0
+#define PM3FBWriteModeOr 0xacf8
+# define PM3FBWriteMode_WriteDisable 0<<0
+# define PM3FBWriteMode_WriteEnable 1<<0
+# define PM3FBWriteMode_Replicate 1<<4
+# define PM3FBWriteMode_OpaqueSpan 1<<5
+# define PM3FBWriteMode_StripePitch(p) (((p)&0x7)<<6)
+# define PM3FBWriteMode_StripeHeight(h) (((h)&0x7)<<9)
+# define PM3FBWriteMode_Enable0 1<<12
+# define PM3FBWriteMode_Enable1 1<<13
+# define PM3FBWriteMode_Enable2 1<<14
+# define PM3FBWriteMode_Enable3 1<<15
+# define PM3FBWriteMode_Layout0(l) (((l)&0x3)<<16)
+# define PM3FBWriteMode_Layout1(l) (((l)&0x3)<<18)
+# define PM3FBWriteMode_Layout2(l) (((l)&0x3)<<20)
+# define PM3FBWriteMode_Layout3(l) (((l)&0x3)<<22)
+# define PM3FBWriteMode_Origin0 1<<24
+# define PM3FBWriteMode_Origin1 1<<25
+# define PM3FBWriteMode_Origin2 1<<26
+# define PM3FBWriteMode_Origin3 1<<27
+#define PM3ForegroundColor 0xb0c0
+/* ... */
+#define PM3GIDMode 0xb538
+#define PM3GIDModeAnd 0xb5b0
+#define PM3GIDModeOr 0xb5b8
+/* ... */
+#define PM3LBDestReadBufferAddr 0xb510
+#define PM3LBDestReadBufferOffset 0xb518
+#define PM3LBDestReadEnables 0xb508
+#define PM3LBDestReadEnablesAnd 0xb590
+#define PM3LBDestReadEnablesOr 0xb598
+#define PM3LBDestReadMode 0xb500
+#define PM3LBDestReadModeAnd 0xb580
+#define PM3LBDestReadModeOr 0xb588
+# define PM3LBDestReadMode_Disable 0<<0
+# define PM3LBDestReadMode_Enable 1<<0
+# define PM3LBDestReadMode_StripePitch(p) (((p)&0x7)<<2)
+# define PM3LBDestReadMode_StripeHeight(h) (((h)&0x7)<<5)
+# define PM3LBDestReadMode_Layout 1<<8
+# define PM3LBDestReadMode_Origin 1<<9
+# define PM3LBDestReadMode_UserReadEnables 1<<10
+# define PM3LBDestReadMode_Packed16 1<<11
+# define PM3LBDestReadMode_Width(w) (((w)&0xfff)<<12)
+#define PM3LBReadFormat 0x8888
+# define PM3LBReadFormat_DepthWidth(w) (((w)&0x3)<<0)
+# define PM3LBReadFormat_StencilWidth(w) (((w)&0xf)<<2)
+# define PM3LBReadFormat_StencilPosition(p) (((p)&0x1f)<<6)
+# define PM3LBReadFormat_FCPWidth(w) (((w)&0xf)<<11)
+# define PM3LBReadFormat_FCPPosition(p) (((p)&0x1f)<<15)
+# define PM3LBReadFormat_GIDWidth(w) (((w)&0x7)<<20)
+# define PM3LBReadFormat_GIDPosition(p) (((p)&0x1f)<<23)
+#define PM3LBSourceReadBufferAddr 0xb528
+#define PM3LBSourceReadBufferOffset 0xb530
+#define PM3LBSourceReadMode 0xb520
+#define PM3LBSourceReadModeAnd 0xb5a0
+#define PM3LBSourceReadModeOr 0xb5a8
+# define PM3LBSourceReadMode_Enable 1<<0
+# define PM3LBSourceReadMode_StripePitch(p) (((p)&0x7)<<2)
+# define PM3LBSourceReadMode_StripeHeight(h) (((h)&0x7)<<5)
+# define PM3LBSourceReadMode_Layout 1<<8
+# define PM3LBSourceReadMode_Origin 1<<9
+# define PM3LBSourceReadMode_Packed16 1<<10
+# define PM3LBSourceReadMode_Width(w) (((w)&0xfff)<<11)
+#define PM3LBStencil 0x88a8
+#define PM3LBWriteBufferAddr 0xb540
+#define PM3LBWriteBufferOffset 0xb548
+#define PM3LBWriteFormat 0x88c8
+# define PM3LBWriteFormat_DepthWidth(w) (((w)&0x3)<<0)
+# define PM3LBWriteFormat_StencilWidth(w) (((w)&0xf)<<2)
+# define PM3LBWriteFormat_StencilPosition(p) (((p)&0x1f)<<6)
+# define PM3LBWriteFormat_GIDWidth(w) (((w)&0x7)<<20)
+# define PM3LBWriteFormat_GIDPosition(p) (((p)&0x1f)<<23)
+#define PM3LBWriteMode 0x88c0
+#define PM3LBWriteModeAnd 0xac80
+#define PM3LBWriteModeOr 0xac88
+# define PM3LBWriteMode_WriteDisable 0<<0
+# define PM3LBWriteMode_WriteEnable 1<<0
+# define PM3LBWriteMode_StripePitch(p) (((p)&0x7)<<3)
+# define PM3LBWriteMode_StripeHeight(h) (((h)&0x7)<<6)
+# define PM3LBWriteMode_Layout 1<<9
+# define PM3LBWriteMode_Origin 1<<10
+# define PM3LBWriteMode_Packed16 1<<11
+# define PM3LBWriteMode_Width(w) (((w)&0xfff)<<12)
+/* ... */
+#define PM3LineStippleMode 0x81a8
+#define PM3LineStippleModeAnd 0xabc0
+#define PM3LineStippleModeOr 0xabc8
+#define PM3LoadLineStippleCounters 0x81b0
+/* ... */
+#define PM3LogicalOpMode 0x8828
+#define PM3LogicalOpModeAnd 0xace0
+#define PM3LogicalOpModeOr 0xace8
+# define PM3LogicalOpMode_Disable (0<<0)
+# define PM3LogicalOpMode_Enable (1<<0)
+# define PM3LogicalOpMode_LogicOp(op) (((op)&0xf)<<1)
+# define PM3LogicalOpMode_UseConstantWriteData_Disable (0<<5)
+# define PM3LogicalOpMode_UseConstantWriteData_Enable (1<<5)
+# define PM3LogicalOpMode_Background_Disable (0<<6)
+# define PM3LogicalOpMode_Background_Enable (1<<6)
+# define PM3LogicalOpMode_Background_LogicOp(op) (((op)&0xf)<<7)
+# define PM3LogicalOpMode_UseConstantSource_Disable (0<<11)
+# define PM3LogicalOpMode_UseConstantSource_Enable (1<<11)
+
+/* ... */
+#define PM3LUT 0x8e80
+/* ... */
+#define PM3LUT 0x8e80
+#define PM3LUTAddress 0x84d0
+#define PM3LUTData 0x84c8
+#define PM3LUTIndex 0x84c0
+#define PM3LUTMode 0xb378
+#define PM3LUTModeAnd 0xad70
+#define PM3LUTModeOr 0xad78
+#define PM3LUTTransfer 0x84d8
+/* ... */
+#define PM3PixelSize 0x80c0
+# define PM3PixelSize_GLOBAL_32BIT (0<<0)
+# define PM3PixelSize_GLOBAL_16BIT (1<<0)
+# define PM3PixelSize_GLOBAL_8BIT (2<<0)
+# define PM3PixelSize_RASTERIZER_32BIT (0<<2)
+# define PM3PixelSize_RASTERIZER_16BIT (1<<2)
+# define PM3PixelSize_RASTERIZER_8BIT (2<<2)
+# define PM3PixelSize_SCISSOR_AND_STIPPLE_32BIT (0<<4)
+# define PM3PixelSize_SCISSOR_AND_STIPPLE_16BIT (1<<4)
+# define PM3PixelSize_SCISSOR_AND_STIPPLE_8BIT (2<<4)
+# define PM3PixelSize_TEXTURE_32BIT (0<<6)
+# define PM3PixelSize_TEXTURE_16BIT (1<<6)
+# define PM3PixelSize_TEXTURE_8BIT (2<<6)
+# define PM3PixelSize_LUT_32BIT (0<<8)
+# define PM3PixelSize_LUT_16BIT (1<<8)
+# define PM3PixelSize_LUT_8BIT (2<<8)
+# define PM3PixelSize_FRAMEBUFFER_32BIT (0<<10)
+# define PM3PixelSize_FRAMEBUFFER_16BIT (1<<10)
+# define PM3PixelSize_FRAMEBUFFER_8BIT (2<<10)
+# define PM3PixelSize_LOGICAL_OP_32BIT (0<<12)
+# define PM3PixelSize_LOGICAL_OP_16BIT (1<<12)
+# define PM3PixelSize_LOGICAL_OP_8BIT (2<<12)
+# define PM3PixelSize_LOCALBUFFER_32BIT (0<<14)
+# define PM3PixelSize_LOCALBUFFER_16BIT (1<<14)
+# define PM3PixelSize_LOCALBUFFER_8BIT (2<<14)
+# define PM3PixelSize_SETUP_32BIT (0<<16)
+# define PM3PixelSize_SETUP_16BIT (1<<16)
+# define PM3PixelSize_SETUP_8BIT (2<<16)
+# define PM3PixelSize_GLOBAL (0<<31)
+# define PM3PixelSize_INDIVIDUAL (1<<31)
+/* ... */
+#define PM3Render 0x8038
+# define PM3Render_AreaStipple_Disable (0<<0)
+# define PM3Render_AreaStipple_Enable (1<<0)
+# define PM3Render_LineStipple_Disable (0<<1)
+# define PM3Render_LineStipple_Enable (1<<1)
+# define PM3Render_ResetLine_Disable (0<<2)
+# define PM3Render_ResetLine_Enable (1<<2)
+# define PM3Render_FastFill_Disable (0<<3)
+# define PM3Render_FastFill_Enable (1<<3)
+# define PM3Render_Primitive_Line (0<<6)
+# define PM3Render_Primitive_Trapezoid (1<<6)
+# define PM3Render_Primitive_Point (2<<6)
+# define PM3Render_Antialias_Disable (0<<8)
+# define PM3Render_Antialias_Enable (1<<8)
+# define PM3Render_Antialias_SubPixelRes_4x4 (0<<9)
+# define PM3Render_Antialias_SubPixelRes_8x8 (1<<9)
+# define PM3Render_UsePointTable_Disable (0<<10)
+# define PM3Render_UsePointTable_Enable (1<<10)
+# define PM3Render_SyncOnbitMask_Disable (0<<11)
+# define PM3Render_SyncOnBitMask_Enable (1<<11)
+# define PM3Render_SyncOnHostData_Disable (0<<12)
+# define PM3Render_SyncOnHostData_Enable (1<<12)
+# define PM3Render_Texture_Disable (0<<13)
+# define PM3Render_Texture_Enable (1<<13)
+# define PM3Render_Fog_Disable (0<<14)
+# define PM3Render_Fog_Enable (1<<14)
+# define PM3Render_Coverage_Disable (0<<15)
+# define PM3Render_Coverage_Enable (1<<15)
+# define PM3Render_SubPixelCorrection_Disable (0<<16)
+# define PM3Render_SubPixelCorrection_Enable (1<<16)
+# define PM3Render_SpanOperation_Disable (0<<18)
+# define PM3Render_SpanOperation_Enable (1<<18)
+# define PM3Render_FBSourceRead_Disable (0<<27)
+# define PM3Render_FBSourceRead_Enable (1<<27)
+#define PM3RasterizerMode 0x80a0
+#define PM3RasterizerModeAnd 0xaba0
+#define PM3RasterizerModeOr 0xabb8
+#define PM3RectangleHeight 0x94e0
+#define PM3Render 0x8038
+#define PM3RepeatLine 0x9328
+#define PM3ResetPickResult 0x8c20
+#define PM3RLEMask 0x8c48
+#define PM3RouterMode 0x8840
+#define PM3RStart 0x8780
+#define PM3S1Start 0x8400
+#define PM3aveLineStippleCounters 0x81c0
+#define PM3ScissorMaxXY 0x8190
+#define PM3ScissorMinXY 0x8188
+#define PM3ScissorMode 0x8180
+#define PM3ScissorModeAnd 0xabb0
+#define PM3ScissorModeOr 0xabb8
+#define PM3ScreenSize 0x8198
+#define PM3Security 0x8908
+#define PM3SetLogicalTexturePage 0xb360
+#define PM3SizeOfFramebuffer 0xb0a8
+#define PM3SStart 0x8388
+#define PM3StartXDom 0x8000
+#define PM3StartXSub 0x8010
+#define PM3StartY 0x8020
+/* ... */
+#define PM3SpanColorMask 0x8168
+/* ... */
+#define PM3TextureApplicationMode 0x8680
+#define PM3TextureApplicationModeAnd 0xac50
+#define PM3TextureApplicationModeOr 0xac58
+#define PM3TextureBaseAddr 0x8500
+#define PM3TextureCacheControl 0x8490
+#define PM3TextureChromaLower0 0x84f0
+#define PM3TextureChromaLower1 0x8608
+#define PM3TextureChromaUpper0 0x84e8
+#define PM3TextureChromaUpper1 0x8600
+#define PM3TextureCompositeAlphaMode0 0xb310
+#define PM3TextureCompositeAlphaMode0And 0xb390
+#define PM3TextureCompositeAlphaMode0Or 0xb398
+#define PM3TextureCompositeAlphaMode1 0xb320
+#define PM3TextureCompositeAlphaMode1And 0xb3b0
+#define PM3TextureCompositeAlphaMode1Or 0xb3b8
+#define PM3TextureCompositeColorMode0 0xb308
+#define PM3TextureCompositeColorMode0And 0xb380
+#define PM3TextureCompositeColorMode0Or 0xb388
+#define PM3TextureCompositeColorMode1 0xb318
+#define PM3TextureCompositeColorMode1And 0xb3a0
+#define PM3TextureCompositeColorMode1Or 0xb3a8
+#define PM3TextureCompositeFactor0 0xb328
+#define PM3TextureCompositeFactor1 0xb330
+#define PM3TextureCompositeMode 0xb300
+#define PM3TextureCoordMode 0x8380
+#define PM3TextureCoordModeAnd 0xac20
+#define PM3TextureCoordModeOr 0xac28
+#define PM3TextureData 0x88e8
+/*
+#define PM3TextureDownloadControl 0x0108
+*/
+#define PM3TextureDownloadOffset 0x88f0
+#define PM3TextureEnvColor 0x8688
+#define PM3TextureFilterMode 0x84e0
+#define PM3TextureFilterModeAnd 0xad50
+#define PM3TextureFilterModeOr 0xad58
+#define PM3TextureIndexMode0 0xb338
+#define PM3TextureIndexMode0And 0xb3c0
+#define PM3TextureIndexMode0Or 0xb3c8
+#define PM3TextureIndexMode1 0xb340
+#define PM3TextureIndexMode1And 0xb3d0
+#define PM3TextureIndexMode1Or 0xb3d8
+#define PM3TextureLODBiasS 0x8450
+#define PM3TextureLODBiasT 0x8458
+/* ... */
+#define PM3TextureMapSize 0xb428
+#define PM3TextureMapWidth0 0x8580
+#define PM3TextureMapWidth1 0x8588
+# define PM3TextureMapWidth_Width(w) ((w&0xfff)<<0)
+# define PM3TextureMapWidth_BorderLayout (1<<12)
+# define PM3TextureMapWidth_Layout_Linear (0<<13)
+# define PM3TextureMapWidth_Layout_Patch64 (1<<13)
+# define PM3TextureMapWidth_Layout_Patch32_2 (2<<13)
+# define PM3TextureMapWidth_Layout_Patch2 (3<<13)
+# define PM3TextureMapWidth_HostTexture (1<<15)
+#define PM3TextureReadMode0 0xb400
+#define PM3TextureReadMode0And 0xac30
+#define PM3TextureReadMode0Or 0xac38
+#define PM3TextureReadMode1 0xb408
+#define PM3TextureReadMode1And 0xad40
+#define PM3TextureReadMode1Or 0xad48
+/* ... */
+#define PM3WaitForCompletion 0x80b8
+#define PM3Window 0x8980
+# define PM3Window_ForceLBUpdate 1<<3
+# define PM3Window_LBUpdateSource 1<<4
+# define PM3Window_FrameCount(c) (((c)&0xff)<<9
+# define PM3Window_StencilFCP 1<<17
+# define PM3Window_DepthFCP 1<<18
+# define PM3Window_OverrideWriteFiltering 1<<19
+#define PM3WindowAnd 0xab80
+#define PM3WindowOr 0xab88
+#define PM3WindowOrigin 0x81c8
+#define PM3XBias 0x9480
+#define PM3YBias 0x9488
+#define PM3YLimits 0x80a8
+#define PM3UVMode 0x8f00
+#define PM3ZFogBias 0x86b8
+#define PM3ZStart 0xadd8
+#define PM3ZStartL 0x89b8
+#define PM3ZStartU 0x89b0
+
+
+/**********************************************
+* GLINT Permedia3 2D setup Unit *
+***********************************************/
+#define PM3Config2D 0xb618
+# define PM3Config2D_OpaqueSpan 1<<0
+# define PM3Config2D_MultiRXBlit 1<<1
+# define PM3Config2D_UserScissorEnable 1<<2
+# define PM3Config2D_FBDestReadEnable 1<<3
+# define PM3Config2D_AlphaBlendEnable 1<<4
+# define PM3Config2D_DitherEnable 1<<5
+# define PM3Config2D_ForegroundROPEnable 1<<6
+# define PM3Config2D_ForegroundROP(rop) (((rop)&0xf)<<7)
+# define PM3Config2D_BackgroundROPEnable 1<<11
+# define PM3Config2D_BackgroundROP(rop) (((rop)&0xf)<<12)
+# define PM3Config2D_UseConstantSource 1<<16
+# define PM3Config2D_FBWriteEnable 1<<17
+# define PM3Config2D_Blocking 1<<18
+# define PM3Config2D_ExternalSourceData 1<<19
+# define PM3Config2D_LUTModeEnable 1<<20
+#define PM3DownloadGlyphwidth 0xb658
+# define PM3DownloadGlyphwidth_GlyphWidth(gw) ((gw)&0xffff)
+#define PM3DownloadTarget 0xb650
+# define PM3DownloadTarget_TagName(tag) ((tag)&0x1fff)
+#define PM3GlyphData 0xb660
+#define PM3GlyphPosition 0xb608
+# define PM3GlyphPosition_XOffset(x) ((x)&0xffff)
+# define PM3GlyphPosition_YOffset(y) (((y)&0xffff)<<16)
+#define PM3Packed4Pixels 0xb668
+#define PM3Packed8Pixels 0xb630
+#define PM3Packed16Pixels 0xb638
+#define PM3RectanglePosition 0xb600
+# define PM3RectanglePosition_XOffset(x) ((x)&0xffff)
+# define PM3RectanglePosition_YOffset(y) (((y)&0xffff)<<16)
+#define PM3Render2D 0xb640
+# define PM3Render2D_Width(w) ((w)&0x0fff)
+# define PM3Render2D_Operation_Normal 0<<12
+# define PM3Render2D_Operation_SyncOnHostData 1<<12
+# define PM3Render2D_Operation_SyncOnBitMask 2<<12
+# define PM3Render2D_Operation_PatchOrderRendering 3<<12
+# define PM3Render2D_FBSourceReadEnable 1<<14
+# define PM3Render2D_SpanOperation 1<<15
+# define PM3Render2D_Height(h) (((h)&0x0fff)<<16)
+# define PM3Render2D_XPositive 1<<28
+# define PM3Render2D_YPositive 1<<29
+# define PM3Render2D_AreaStippleEnable 1<<30
+# define PM3Render2D_TextureEnable 1<<31
+#define PM3Render2DGlyph 0xb648
+# define PM3Render2DGlyph_Width(w) ((w)&0x7f)
+# define PM3Render2DGlyph_Height(h) (((h)&0x7f)<<7)
+# define PM3Render2DGlyph_XOffset(x) (((x)&0x1ff)<<14)
+# define PM3Render2DGlyph_YOffset(y) (((y)&0x1ff)<<23)
+#define PM3RenderPatchOffset 0xb610
+# define PM3RenderPatchOffset_XOffset(x) ((x)&0xffff)
+# define PM3RenderPatchOffset_YOffset(y) (((y)&0xffff)<<16)
+#define PM3RLCount 0xb678
+# define PM3RLCount_Count(c) ((c)&0x0fff)
+#define PM3RLData 0xb670
+
+/**********************************************
+* GLINT Permedia3 Alias Register *
+***********************************************/
+#define PM3FillBackgroundColor 0x8330
+#define PM3FillConfig2D0 0x8338
+#define PM3FillConfig2D1 0x8360
+# define PM3FillConfig2D_OpaqueSpan 1<<0
+# define PM3FillConfig2D_MultiRXBlit 1<<1
+# define PM3FillConfig2D_UserScissorEnable 1<<2
+# define PM3FillConfig2D_FBDestReadEnable 1<<3
+# define PM3FillConfig2D_AlphaBlendEnable 1<<4
+# define PM3FillConfig2D_DitherEnable 1<<5
+# define PM3FillConfig2D_ForegroundROPEnable 1<<6
+# define PM3FillConfig2D_ForegroundROP(rop) (((rop)&0xf)<<7)
+# define PM3FillConfig2D_BackgroundROPEnable 1<<11
+# define PM3FillConfig2D_BackgroundROP(rop) (((rop)&0xf)<<12)
+# define PM3FillConfig2D_UseConstantSource 1<<16
+# define PM3FillConfig2D_FBWriteEnable 1<<17
+# define PM3FillConfig2D_Blocking 1<<18
+# define PM3FillConfig2D_ExternalSourceData 1<<19
+# define PM3FillConfig2D_LUTModeEnable 1<<20
+#define PM3FillFBDestReadBufferAddr 0x8310
+#define PM3FillFBSourceReadBufferAddr 0x8308
+#define PM3FillFBSourceReadBufferOffset 0x8340
+# define PM3FillFBSourceReadBufferOffset_XOffset(x) ((x)&0xffff)
+# define PM3FillFBSourceReadBufferOffset_YOffset(y) (((y)&0xffff)<<16)
+#define PM3FillFBWriteBufferAddr 0x8300
+#define PM3FillForegroundColor0 0x8328
+#define PM3FillForegroundColor1 0x8358
+#define PM3FillGlyphPosition 0x8368
+# define PM3FillGlyphPosition_XOffset(x) ((x)&0xffff)
+# define PM3FillGlyphPosition_YOffset(y) (((y)&0xffff)<<16)
+#define PM3FillRectanglePosition 0x8348
+# define PM3FillRectanglePosition_XOffset(x) ((x)&0xffff)
+# define PM3FillRectanglePosition_YOffset(y) (((y)&0xffff)<<16)
+
+#if 0
+
+/**********************************************
+* GLINT Permedia3 Macros *
+***********************************************/
+
+#define WRITE_REG(base,offset,val) \
+ *(volatile unsigned long *)(((unsigned char *)(base)) + offset) = (val)
+
+#define READ_REG(base,offset) \
+ *(volatile unsigned long *)(((unsigned char *)(base)) + offset)
+
+#define UPDATE_SET_REG(base,offset,val) \
+ { \
+ unsigned long temp; \
+ temp = READ_REG(base,offset); \
+ WRITE_REG(base,offset,temp|(val)); \
+ }
+
+#define UPDATE_CLEAR_REG(base,offset,val) \
+ { \
+ unsigned long temp; \
+ temp = READ_REG(base,offset); \
+ WRITE_REG(base,offset,temp&(~(val))); \
+ }
+
+#define RAMDAC_DELAY(b,x) do { \
+ int delay = x; \
+ unsigned char tmp; \
+ while(delay--){tmp = READ_REG(b,PM3InFIFOSpace);}; \
+} while(0)
+
+#define SLOW_WRITE_REG(b,v,r) \
+do{ \
+ RAMDAC_DELAY(b,5); \
+ WRITE_REG(b,v,r); \
+ RAMDAC_DELAY(b,5); \
+}while(0)
+
+#define RAMDAC_SET_INDEX(b, index) \
+{ \
+ SLOW_WRITE_REG (b,PM3RD_IndexHigh,(index>>8)&0xff); \
+ SLOW_WRITE_REG (b,PM3RD_IndexLow,index&0xff); \
+}
+
+#define RAMDAC_SET_REG(b, index, data) \
+{ \
+ RAMDAC_SET_INDEX(b, index); \
+ SLOW_WRITE_REG(b, PM3RD_IndexedData, data); \
+}
+
+#define RAMDAC_GET_REG(b, index, temp) \
+{ \
+ RAMDAC_SET_INDEX(b, index); \
+ temp = READ_REG(b, PM3RD_IndexedData); \
+}
+#endif
+#endif /* _PM3_REG_H_ */
diff --git a/src/pm3_video.c b/src/pm3_video.c
new file mode 100644
index 0000000..0a42417
--- /dev/null
+++ b/src/pm3_video.c
@@ -0,0 +1,1322 @@
+/*
+ * Copyright 2001 by Alan Hourihane, Sychdyn, North Wales.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, alanh@fairlite.demon.co.uk
+ * Sven Luther <luther@dpt-info.u-strasbg.fr>
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm3_video.c,v 1.11.2.1 2003/05/09 02:10:18 dawes Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86Resources.h"
+#include "xf86_ansic.h"
+#include "compiler.h"
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+#include "xf86fbman.h"
+#include "regionstr.h"
+
+#include "glint.h"
+#include "glint_regs.h"
+#include "pm3_regs.h"
+#include "Xv.h"
+#include "xaa.h"
+#include "xaalocal.h"
+#include "dixstruct.h"
+#include "fourcc.h"
+
+#define OFF_DELAY 200 /* milliseconds */
+#define FREE_DELAY 60000
+
+#define OFF_TIMER 0x01
+#define FREE_TIMER 0x02
+#define CLIENT_VIDEO_ON 0x04
+
+#define TIMER_MASK (OFF_TIMER | FREE_TIMER)
+
+#ifndef XvExtension
+void Permedia3InitVideo(ScreenPtr pScreen) {}
+void Permedia3ResetVideo(ScrnInfoPtr pScrn) {}
+#else
+
+static XF86VideoAdaptorPtr Permedia3SetupImageVideo(ScreenPtr);
+static void Permedia3InitOffscreenImages(ScreenPtr);
+static void Permedia3StopVideo(ScrnInfoPtr, pointer, Bool);
+static int Permedia3SetPortAttribute(ScrnInfoPtr, Atom, INT32, pointer);
+static int Permedia3GetPortAttribute(ScrnInfoPtr, Atom ,INT32 *, pointer);
+static void Permedia3QueryBestSize(ScrnInfoPtr, Bool,
+ short, short, short, short, unsigned int *, unsigned int *, pointer);
+static int Permedia3PutImage( ScrnInfoPtr,
+ short, short, short, short, short, short, short, short,
+ int, unsigned char*, short, short, Bool, RegionPtr, pointer);
+static int Permedia3QueryImageAttributes(ScrnInfoPtr,
+ int, unsigned short *, unsigned short *, int *, int *);
+static void Permedia3VideoTimerCallback(ScrnInfoPtr pScrn, Time time);
+
+#define MAKE_ATOM(a) MakeAtom(a, sizeof(a) - 1, TRUE)
+
+static Atom xvColorKey, xvDoubleBuffer, xvAutopaintColorKey, xvFilter;
+
+void Permedia3InitVideo(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ XF86VideoAdaptorPtr *adaptors, *newAdaptors = NULL;
+ XF86VideoAdaptorPtr newAdaptor = NULL;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int num_adaptors;
+
+ /* Because of bugs in the PM3 when uploading images via the
+ * bypass to the framebuffer, we always have to use the accelerator.
+ */
+ if (pGlint->NoAccel)
+ return;
+
+ newAdaptor = Permedia3SetupImageVideo(pScreen);
+ Permedia3InitOffscreenImages(pScreen);
+
+ num_adaptors = xf86XVListGenericAdaptors(pScrn, &adaptors);
+
+ if(newAdaptor) {
+ if(!num_adaptors) {
+ num_adaptors = 1;
+ adaptors = &newAdaptor;
+ } else {
+ newAdaptors = /* need to free this someplace */
+ xalloc((num_adaptors + 1) * sizeof(XF86VideoAdaptorPtr*));
+ if(newAdaptors) {
+ memcpy(newAdaptors, adaptors, num_adaptors *
+ sizeof(XF86VideoAdaptorPtr));
+ newAdaptors[num_adaptors] = newAdaptor;
+ adaptors = newAdaptors;
+ num_adaptors++;
+ }
+ }
+ }
+
+ if(num_adaptors)
+ xf86XVScreenInit(pScreen, adaptors, num_adaptors);
+
+ if(newAdaptors)
+ xfree(newAdaptors);
+}
+
+/* client libraries expect an encoding */
+static XF86VideoEncodingRec DummyEncoding[1] =
+{
+ {
+ 0,
+ "XV_IMAGE",
+ 2047, 2047,
+ {1, 1}
+ }
+};
+
+#define NUM_FORMATS 4
+
+static XF86VideoFormatRec Formats[NUM_FORMATS] =
+{
+ {8, PseudoColor}, {15, TrueColor}, {16, TrueColor}, {24, TrueColor}
+};
+
+#define NUM_ATTRIBUTES 4
+
+static XF86AttributeRec Attributes[NUM_ATTRIBUTES] =
+{
+ {XvSettable | XvGettable, 0, 1, "XV_DOUBLE_BUFFER"},
+ {XvSettable | XvGettable, 0, (1 << 24) - 1, "XV_COLORKEY"},
+ {XvSettable | XvGettable, 0, 1, "XV_AUTOPAINT_COLORKEY"},
+ {XvSettable | XvGettable, 0, 2, "XV_FILTER"},
+};
+
+/*
+ * FOURCC from http://www.webartz.com/fourcc
+ * Generic GUID for legacy FOURCC XXXXXXXX-0000-0010-8000-00AA00389B71
+ */
+#define LE4CC(a,b,c,d) (((CARD32)(a)&0xFF)|(((CARD32)(b)&0xFF)<<8)|(((CARD32)(c)&0xFF)<<16)|(((CARD32)(d)&0xFF)<<24))
+#define GUID4CC(a,b,c,d) { a,b,c,d,0,0,0,0x10,0x80,0,0,0xAA,0,0x38,0x9B,0x71 }
+
+#define NoOrder LSBFirst
+
+#define NUM_IMAGES 15
+
+static XF86ImageRec Images[NUM_IMAGES] =
+{
+ /* Planar YVU 4:2:0 (emulated) */
+ { LE4CC('Y','V','1','2'), XvYUV, NoOrder, GUID4CC('Y','V','1','2'),
+ 12, XvPlanar, 3, 0, 0, 0, 0,
+ 8, 8, 8, 1, 2, 2, 1, 2, 2, "YVU", XvTopToBottom },
+
+ /* Packed YUYV 4:2:2 */
+ { LE4CC('Y','U','Y','2'), XvYUV, NoOrder, GUID4CC('Y','U','Y','2'),
+ 16, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 2, 2, 1, 1, 1, "YUYV", XvTopToBottom },
+
+ /* Packed UYVY 4:2:2 */
+ { LE4CC('U','Y','V','Y'), XvYUV, NoOrder, GUID4CC('U','Y','V','Y'),
+ 16, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 2, 2, 1, 1, 1, "UYVY", XvTopToBottom },
+
+ /* Packed YUVA 4:4:4 */
+ { LE4CC('Y','U','V','A') /* XXX not registered */, XvYUV, LSBFirst, { 0 },
+ 32, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 1, 1, 1, 1, 1, "YUVA", XvTopToBottom },
+
+ /* Packed VUYA 4:4:4 */
+ { LE4CC('V','U','Y','A') /* XXX not registered */, XvYUV, LSBFirst, { 0 },
+ 32, XvPacked, 1, 0, 0, 0, 0,
+ 8, 8, 8, 1, 1, 1, 1, 1, 1, "VUYA", XvTopToBottom },
+
+ /* RGBA 8:8:8:8 */
+ { 0x41, XvRGB, LSBFirst, { 0 },
+ 32, XvPacked, 1, 24, 0x0000FF, 0x00FF00, 0xFF0000,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGB 5:6:5 */
+ { 0x42, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 16, 0x001F, 0x07E0, 0xF800,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGB", XvTopToBottom },
+
+ /* RGBA 5:5:5:1 */
+ { 0x43, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 15, 0x001F, 0x03E0, 0x7C00,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGBA 4:4:4:4 */
+ { 0x44, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 12, 0x000F, 0x00F0, 0x0F00,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGBA", XvTopToBottom },
+
+ /* RGB 3:3:2 */
+ { 0x46, XvRGB, NoOrder, { 0 },
+ 8, XvPacked, 1, 8, 0x07, 0x38, 0xC0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "RGB", XvTopToBottom },
+
+ /* BGRA 8:8:8:8 */
+ { 0x47, XvRGB, LSBFirst, { 0 },
+ 32, XvPacked, 1, 24, 0xFF0000, 0x00FF00, 0x0000FF,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGR 5:6:5 */
+ { 0x48, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 16, 0xF800, 0x07E0, 0x001F,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGR", XvTopToBottom },
+
+ /* BGRA 5:5:5:1 */
+ { 0x49, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 15, 0x7C00, 0x03E0, 0x001F,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGRA 4:4:4:4 */
+ { 0x4A, XvRGB, LSBFirst, { 0 },
+ 16, XvPacked, 1, 12, 0x0F00, 0x00F0, 0x000F,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGRA", XvTopToBottom },
+
+ /* BGR 2:3:3 */
+ { 0x4C, XvRGB, NoOrder, { 0 },
+ 8, XvPacked, 1, 8, 0xC0, 0x38, 0x07,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, "BGR", XvTopToBottom },
+};
+
+#define MAX_BUFFERS 2
+
+typedef struct {
+ FBAreaPtr area[MAX_BUFFERS];
+ RegionRec clip;
+ CARD32 colorKey;
+ CARD32 videoStatus;
+ Time offTime;
+ Time freeTime;
+ int Video_Shift;
+ int Format;
+ Bool ramdacOn;
+ Bool doubleBuffer;
+ Bool autopaintColorKey;
+ int Filter;
+ int sx, sy;
+ int offset[MAX_BUFFERS];
+ int buffer;
+} GLINTPortPrivRec, *GLINTPortPrivPtr;
+
+#define GET_PORT_PRIVATE(pScrn) \
+ (GLINTPortPrivPtr)((GLINTPTR(pScrn))->adaptor->pPortPrivates[0].ptr)
+
+#define RAMDAC_WRITE(data,index) \
+do{ \
+ GLINT_WRITE_REG(((index)>>8)&0xff, PM3RD_IndexHigh); \
+ GLINT_WRITE_REG((index)&0xff, PM3RD_IndexLow); \
+ GLINT_WRITE_REG(data, PM3RD_IndexedData); \
+}while(0)
+
+void Permedia3ResetVideo(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTPortPrivPtr pPriv = pGlint->adaptor->pPortPrivates[0].ptr;
+
+ GLINT_WAIT(15);
+ GLINT_WRITE_REG(0xfff0|(0xffff<<16), PM3VideoOverlayFifoControl);
+ GLINT_WRITE_REG(PM3VideoOverlayMode_DISABLE, PM3VideoOverlayMode);
+ pPriv->ramdacOn = FALSE;
+ RAMDAC_WRITE(PM3RD_VideoOverlayControl_DISABLE, PM3RD_VideoOverlayControl);
+ RAMDAC_WRITE((pPriv->colorKey&0xff0000)>>16, PM3RD_VideoOverlayKeyR);
+ RAMDAC_WRITE((pPriv->colorKey&0x00ff00)>>8, PM3RD_VideoOverlayKeyG);
+ RAMDAC_WRITE(pPriv->colorKey&0x0000ff, PM3RD_VideoOverlayKeyB);
+ GLINT_WRITE_REG(PM3VideoOverlayUpdate_ENABLE, PM3VideoOverlayUpdate);
+}
+
+
+static XF86VideoAdaptorPtr
+Permedia3SetupImageVideo(ScreenPtr pScreen)
+{
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ XF86VideoAdaptorPtr adapt;
+ GLINTPortPrivPtr pPriv;
+
+ if(!(adapt = xcalloc(1, sizeof(XF86VideoAdaptorRec) +
+ sizeof(GLINTPortPrivRec) +
+ sizeof(DevUnion))))
+ return NULL;
+
+ adapt->type = XvWindowMask | XvInputMask | XvImageMask;
+ adapt->flags = VIDEO_OVERLAID_IMAGES | VIDEO_CLIP_TO_VIEWPORT;
+ adapt->name = "Permedia3 Backend Scaler";
+ adapt->nEncodings = 1;
+ adapt->pEncodings = DummyEncoding;
+ adapt->nFormats = NUM_FORMATS;
+ adapt->pFormats = Formats;
+ adapt->nPorts = 1;
+ adapt->pPortPrivates = (DevUnion*)(&adapt[1]);
+ pPriv = (GLINTPortPrivPtr)(&adapt->pPortPrivates[1]);
+ adapt->pPortPrivates[0].ptr = (pointer)(pPriv);
+ adapt->pAttributes = Attributes;
+ adapt->nImages = NUM_IMAGES;
+ adapt->nAttributes = NUM_ATTRIBUTES;
+ adapt->pImages = Images;
+ adapt->PutVideo = NULL;
+ adapt->PutStill = NULL;
+ adapt->GetVideo = NULL;
+ adapt->GetStill = NULL;
+ adapt->StopVideo = Permedia3StopVideo;
+ adapt->SetPortAttribute = Permedia3SetPortAttribute;
+ adapt->GetPortAttribute = Permedia3GetPortAttribute;
+ adapt->QueryBestSize = Permedia3QueryBestSize;
+ adapt->PutImage = Permedia3PutImage;
+ adapt->QueryImageAttributes = Permedia3QueryImageAttributes;
+
+ /* FIXME : depth 15 and 16 doesn't work here */
+ pPriv->colorKey = pGlint->videoKey;
+ pPriv->videoStatus = 0;
+ pPriv->buffer = 0; /* double buffer (or maybe triple later) */
+ pPriv->doubleBuffer = TRUE;
+ pPriv->autopaintColorKey = TRUE;
+ pPriv->Filter = PM3VideoOverlayMode_FILTER_FULL;
+
+ /* gotta uninit this someplace */
+ REGION_INIT(pScreen, &pPriv->clip, NullBox, 0);
+
+ pGlint->adaptor = adapt;
+
+ xvDoubleBuffer = MAKE_ATOM("XV_DOUBLE_BUFFER");
+ xvColorKey = MAKE_ATOM("XV_COLORKEY");
+ xvAutopaintColorKey = MAKE_ATOM("XV_AUTOPAINT_COLORKEY");
+ xvFilter = MAKE_ATOM("XV_FILTER");
+
+ Permedia3ResetVideo(pScrn);
+
+ return adapt;
+}
+
+
+static Bool
+RegionsEqual(RegionPtr A, RegionPtr B)
+{
+ int *dataA, *dataB;
+ int num;
+
+ num = REGION_NUM_RECTS(A);
+ if(num != REGION_NUM_RECTS(B))
+ return FALSE;
+
+ if((A->extents.x1 != B->extents.x1) ||
+ (A->extents.x2 != B->extents.x2) ||
+ (A->extents.y1 != B->extents.y1) ||
+ (A->extents.y2 != B->extents.y2))
+ return FALSE;
+
+ dataA = (int*)REGION_RECTS(A);
+ dataB = (int*)REGION_RECTS(B);
+
+ while(num--) {
+ if((dataA[0] != dataB[0]) || (dataA[1] != dataB[1]))
+ return FALSE;
+ dataA += 2;
+ dataB += 2;
+ }
+
+ return TRUE;
+}
+
+static void
+Permedia3StopVideo(ScrnInfoPtr pScrn, pointer data, Bool shutdown)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTPortPrivPtr pPriv = (GLINTPortPrivPtr)data;
+ int i;
+
+ REGION_EMPTY(pScrn->pScreen, &pPriv->clip);
+
+ if(shutdown) {
+ if(pPriv->videoStatus & CLIENT_VIDEO_ON) {
+ pPriv->ramdacOn = FALSE;
+ GLINT_WAIT(4);
+ RAMDAC_WRITE(PM3RD_VideoOverlayControl_DISABLE,
+ PM3RD_VideoOverlayControl);
+ GLINT_WRITE_REG(PM3VideoOverlayMode_DISABLE,
+ PM3VideoOverlayMode);
+ }
+ for (i = 0; i < (pPriv->doubleBuffer ? 2 : 1); i++) {
+ if(pPriv->area[i]) {
+ xf86FreeOffscreenArea(pPriv->area[i]);
+ pPriv->area[i] = NULL;
+ }
+ }
+ pPriv->videoStatus = 0;
+ } else {
+ if(pPriv->videoStatus & CLIENT_VIDEO_ON) {
+ pPriv->videoStatus |= OFF_TIMER;
+ pPriv->offTime = currentTime.milliseconds + OFF_DELAY;
+ }
+ }
+}
+
+static int
+Permedia3SetPortAttribute(
+ ScrnInfoPtr pScrn,
+ Atom attribute,
+ INT32 value,
+ pointer data
+){
+ GLINTPortPrivPtr pPriv = (GLINTPortPrivPtr)data;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (attribute == xvDoubleBuffer)
+ {
+ if ((value < 0) || (value > 1))
+ return BadValue;
+ pPriv->doubleBuffer = value;
+ }
+ else if (attribute == xvColorKey)
+ {
+ pPriv->colorKey = value;
+ GLINT_WAIT(9);
+ RAMDAC_WRITE((value & 0xff0000)>>16, PM3RD_VideoOverlayKeyR);
+ RAMDAC_WRITE((value & 0x00ff00)>>8, PM3RD_VideoOverlayKeyG);
+ RAMDAC_WRITE((value & 0x0000ff), PM3RD_VideoOverlayKeyB);
+ REGION_EMPTY(pScrn->pScreen, &pPriv->clip);
+ }
+ else if (attribute == xvAutopaintColorKey)
+ {
+ if ((value < 0) || (value > 1))
+ return BadValue;
+ pPriv->autopaintColorKey = value;
+ }
+ else if (attribute == xvFilter)
+ {
+ if ((value < 0) || (value > 2))
+ return BadValue;
+ switch (value) {
+ case 0:
+ pPriv->Filter = PM3VideoOverlayMode_FILTER_OFF;
+ break;
+ case 1:
+ pPriv->Filter = PM3VideoOverlayMode_FILTER_FULL;
+ break;
+ case 2:
+ pPriv->Filter = PM3VideoOverlayMode_FILTER_PARTIAL;
+ break;
+ }
+ }
+ else
+ return BadMatch;
+
+ return Success;
+}
+
+static int
+Permedia3GetPortAttribute(
+ ScrnInfoPtr pScrn,
+ Atom attribute,
+ INT32 *value,
+ pointer data
+){
+ GLINTPortPrivPtr pPriv = (GLINTPortPrivPtr)data;
+
+ if (attribute == xvDoubleBuffer)
+ *value = (pPriv->doubleBuffer) ? 1 : 0;
+ else if (attribute == xvColorKey)
+ *value = pPriv->colorKey;
+ else if (attribute == xvAutopaintColorKey)
+ *value = (pPriv->autopaintColorKey) ? 1 : 0;
+ else if (attribute == xvFilter)
+ *value = pPriv->Filter >> 14;
+ else
+ return BadMatch;
+
+ return Success;
+}
+
+static void
+Permedia3QueryBestSize(
+ ScrnInfoPtr pScrn,
+ Bool motion,
+ short vid_w, short vid_h,
+ short drw_w, short drw_h,
+ unsigned int *p_w, unsigned int *p_h,
+ pointer data
+){
+ if(vid_w > (drw_w << 3))
+ drw_w = vid_w >> 3;
+ if(vid_h > (drw_h << 3))
+ drw_h = vid_h >> 3;
+
+ *p_w = drw_w;
+ *p_h = drw_h;
+}
+
+static void
+HWCopySetup(ScrnInfoPtr pScrn, int x, int y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(4);
+ GLINT_WRITE_REG(0xffffffff, FBHardwareWriteMask);
+ GLINT_WRITE_REG(
+ PM3Config2D_ForegroundROPEnable |
+ PM3Config2D_ForegroundROP(GXcopy) |
+ PM3Config2D_FBWriteEnable,
+ PM3Config2D);
+ GLINT_WRITE_REG(
+ PM3RectanglePosition_XOffset(x) |
+ PM3RectanglePosition_YOffset(y),
+ PM3RectanglePosition);
+ GLINT_WRITE_REG(
+ PM3Render2D_SpanOperation |
+ PM3Render2D_XPositive |
+ PM3Render2D_YPositive |
+ PM3Render2D_Operation_SyncOnHostData |
+ PM3Render2D_Width(w) | PM3Render2D_Height(h),
+ PM3Render2D);
+}
+
+static void
+HWCopyYV12(ScrnInfoPtr pScrn, CARD8 *Y, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int size = w * h;
+ CARD8 *V = Y + size;
+ CARD8 *U = V + (size >> 2);
+ CARD32 *dst;
+ int pass2 = 0;
+ int dwords, i, x = 0;
+
+ dwords = size >> 1;
+
+ w >>= 1;
+
+ while (dwords >= pGlint->FIFOSize) {
+ dst = (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4);
+ GLINT_WAIT(pGlint->FIFOSize);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ for (i = pGlint->FIFOSize - 1; i; i--, Y += 2, x++) {
+ if (x == w) {
+ x = 0;
+ if (pass2 == 0)
+ pass2 = 1;
+ else
+ if (pass2 == 1) {
+ pass2 = 0;
+ U += w;
+ V += w;
+ }
+ }
+ *dst++ = Y[0] + (U[x] << 8) + (Y[1] << 16) + (V[x] << 24);
+ }
+ dwords -= pGlint->FIFOSize - 1;
+ }
+ if (dwords) {
+ dst = (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4);
+ GLINT_WAIT(dwords + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((dwords - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ for (i = dwords; i; i--, Y += 2, x++) {
+ if (x == w) {
+ x = 0;
+ if (pass2 == 0)
+ pass2 = 1;
+ else
+ if (pass2 == 1) {
+ pass2 = 0;
+ U += w;
+ V += w;
+ }
+ }
+ *dst++ = Y[0] + (U[x] << 8) + (Y[1] << 16) + (V[x] << 24);
+ }
+ }
+}
+
+static void
+HWCopyFlat(ScrnInfoPtr pScrn, CARD8 *src, int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTPortPrivPtr pPriv = pGlint->adaptor->pPortPrivates[0].ptr;
+ int pitch = pScrn->displayWidth;
+ CARD8 *tmp_src;
+ int dwords;
+
+ if (w == pitch) {
+ dwords = (w * h) >> (2 - pPriv->Video_Shift);
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)src, pGlint->FIFOSize - 1);
+ dwords -= (pGlint->FIFOSize - 1);
+ src += (pGlint->FIFOSize << 2) - 4;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords - 1) << 16)|(0x15 << 4) |0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)src, dwords);
+ }
+ } else {
+ while (h--) {
+ tmp_src = src;
+ dwords = w >> (2 - pPriv->Video_Shift);
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)src, pGlint->FIFOSize - 1);
+ dwords -= (pGlint->FIFOSize - 1);
+ src += (pGlint->FIFOSize << 2) - 4;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords-1)<<16)|(0x15<<4) | 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)src, dwords);
+ }
+ src = tmp_src + (w << pPriv->Video_Shift);
+ }
+ }
+}
+
+static FBAreaPtr
+Permedia3AllocateMemory(ScrnInfoPtr pScrn, FBAreaPtr area, int width, int height)
+{
+ ScreenPtr pScreen;
+ FBAreaPtr new_area;
+
+ if (area) {
+ if ((area->box.x2 - area->box.x1 >= width) &&
+ (area->box.y2 - area->box.y1 >= height))
+ return area;
+
+ if (xf86ResizeOffscreenArea(area, width, height))
+ return area;
+
+ xf86FreeOffscreenArea(area);
+ }
+
+ pScreen = screenInfo.screens[pScrn->scrnIndex];
+
+ new_area = xf86AllocateOffscreenArea(pScreen, width, height, pScrn->bitsPerPixel / 8, NULL, NULL, NULL);
+
+ if (!new_area) {
+ int max_width, max_height;
+
+ xf86QueryLargestOffscreenArea(pScreen, &max_width, &max_height, pScrn->bitsPerPixel / 8, 0, PRIORITY_EXTREME);
+
+ if (max_width < width || max_height < height)
+ return NULL;
+
+ xf86PurgeUnlockedOffscreenAreas(pScreen);
+ new_area = xf86AllocateOffscreenArea(pScreen, width, height, pScrn->bitsPerPixel / 8, NULL, NULL, NULL);
+ }
+
+ return new_area;
+}
+
+#define FORMAT_RGB8888 PM3VideoOverlayMode_COLORFORMAT_RGB8888
+#define FORMAT_RGB4444 PM3VideoOverlayMode_COLORFORMAT_RGB4444
+#define FORMAT_RGB5551 PM3VideoOverlayMode_COLORFORMAT_RGB5551
+#define FORMAT_RGB565 PM3VideoOverlayMode_COLORFORMAT_RGB565
+#define FORMAT_RGB332 PM3VideoOverlayMode_COLORFORMAT_RGB332
+#define FORMAT_BGR8888 PM3VideoOverlayMode_COLORFORMAT_BGR8888
+#define FORMAT_BGR4444 PM3VideoOverlayMode_COLORFORMAT_BGR4444
+#define FORMAT_BGR5551 PM3VideoOverlayMode_COLORFORMAT_BGR5551
+#define FORMAT_BGR565 PM3VideoOverlayMode_COLORFORMAT_BGR565
+#define FORMAT_BGR332 PM3VideoOverlayMode_COLORFORMAT_BGR332
+#define FORMAT_CI8 PM3VideoOverlayMode_COLORFORMAT_CI8
+#define FORMAT_VUY444 PM3VideoOverlayMode_COLORFORMAT_VUY444
+#define FORMAT_YUV444 PM3VideoOverlayMode_COLORFORMAT_YUV444
+#define FORMAT_VUY422 PM3VideoOverlayMode_COLORFORMAT_VUY422
+#define FORMAT_YUV422 PM3VideoOverlayMode_COLORFORMAT_YUV422
+
+/* Notice, have to check that we dont overflow the deltas here ... */
+static void
+compute_scale_factor(
+ short* src_w, short* dst_w,
+ unsigned int* shrink_delta, unsigned int* zoom_delta)
+{
+ /* NOTE: If we don't return reasonable values here then the video
+ * unit can potential shut off and won't display an image until re-enabled.
+ * Seems as though the zoom_delta is o.k, and I've not had the problem.
+ * The 'shrink_delta' is prone to this the most - FIXME ! */
+
+ if (*src_w >= *dst_w) {
+ *src_w &= ~0x3;
+ *dst_w &= ~0x3;
+ *shrink_delta = (((*src_w << 16) / *dst_w) + 0x0f) & 0x0ffffff0;
+ *zoom_delta = 1<<16;
+ if ( ((*shrink_delta * *dst_w) >> 16) & 0x03 )
+ *shrink_delta += 0x10;
+ } else {
+ *src_w &= ~0x3;
+ *dst_w &= ~0x3;
+ *zoom_delta = (((*src_w << 16) / *dst_w) + 0x0f) & 0x0001fff0;
+ *shrink_delta = 1<<16;
+ if ( ((*zoom_delta * *dst_w) >> 16) & 0x03 )
+ *zoom_delta += 0x10;
+ }
+}
+
+static void
+Permedia3DisplayVideo(
+ ScrnInfoPtr pScrn,
+ int id,
+ int offset,
+ short width, short height,
+ int x1, int y1, int x2, int y2,
+ BoxPtr dstBox,
+ short src_w, short src_h,
+ short drw_w, short drw_h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTPortPrivPtr portPriv = pGlint->adaptor->pPortPrivates[0].ptr;
+ unsigned int shrink, zoom;
+ unsigned int newx1, newx2;
+
+ /* Let's overlay only to visible parts of the screen */
+ if (dstBox->x1 == 0) {
+ x1 = drw_w - dstBox->x2;
+ drw_w = dstBox->x2;
+ }
+ if (dstBox->x2 == pScrn->frameX1) {
+ x2 = drw_w - (dstBox->x2 - dstBox->x1);
+ drw_w = (dstBox->x2 - dstBox->x1);
+ }
+
+ /* Avoid divide by zero in compute_scale_factor. */
+ if (drw_w < 8)
+ return;
+
+ /* Let's adjust the width of source and dest to be compliant with
+ * the Permedia3 overlay unit requirement, and compute the X deltas. */
+ newx1 = src_w; newx2 = drw_w;
+ compute_scale_factor(&src_w, &drw_w, &shrink, &zoom);
+ dstBox->x2 -= (newx2 - drw_w);
+
+ /* We do a long wait here - for everything that needs to be written */
+ GLINT_WAIT(39);
+ GLINT_WRITE_REG(offset>>portPriv->Video_Shift,
+ portPriv->buffer ? PM3VideoOverlayBase1 : PM3VideoOverlayBase0);
+ /* Let's set the source pitch. */
+ GLINT_WRITE_REG(PM3VideoOverlayStride_STRIDE(pScrn->displayWidth<<
+ (pScrn->bitsPerPixel>>4) >>portPriv->Video_Shift),
+ PM3VideoOverlayStride);
+ /* Let's set the position and size of the visible part of the source. */
+ GLINT_WRITE_REG(PM3VideoOverlayWidth_WIDTH(src_w),
+ PM3VideoOverlayWidth);
+ GLINT_WRITE_REG(PM3VideoOverlayHeight_HEIGHT(src_h),
+ PM3VideoOverlayHeight);
+ GLINT_WRITE_REG(
+ PM3VideoOverlayOrigin_XORIGIN(x1) |
+ PM3VideoOverlayOrigin_YORIGIN(y1),
+ PM3VideoOverlayOrigin);
+ /* Scale the source to the destinationsize */
+ if (src_h == drw_h) {
+ GLINT_WRITE_REG(
+ PM3VideoOverlayYDelta_NONE,
+ PM3VideoOverlayYDelta);
+ } else {
+ GLINT_WRITE_REG(
+ PM3VideoOverlayYDelta_DELTA(src_h,drw_h),
+ PM3VideoOverlayYDelta);
+ }
+ if (src_w == drw_w) {
+ GLINT_WRITE_REG(1<<16, PM3VideoOverlayShrinkXDelta);
+ GLINT_WRITE_REG(1<<16, PM3VideoOverlayZoomXDelta);
+ } else {
+ GLINT_WRITE_REG(shrink, PM3VideoOverlayShrinkXDelta);
+ GLINT_WRITE_REG(zoom, PM3VideoOverlayZoomXDelta);
+ }
+ GLINT_WRITE_REG(portPriv->buffer, PM3VideoOverlayIndex);
+
+ /* Now set the ramdac video overlay region and mode */
+ RAMDAC_WRITE((dstBox->x1&0xff), PM3RD_VideoOverlayXStartLow);
+ RAMDAC_WRITE((dstBox->x1&0xf00)>>8, PM3RD_VideoOverlayXStartHigh);
+ RAMDAC_WRITE((dstBox->x2&0xff), PM3RD_VideoOverlayXEndLow);
+ RAMDAC_WRITE((dstBox->x2&0xf00)>>8,PM3RD_VideoOverlayXEndHigh);
+ RAMDAC_WRITE((dstBox->y1&0xff), PM3RD_VideoOverlayYStartLow);
+ RAMDAC_WRITE((dstBox->y1&0xf00)>>8, PM3RD_VideoOverlayYStartHigh);
+ RAMDAC_WRITE((dstBox->y2&0xff), PM3RD_VideoOverlayYEndLow);
+ RAMDAC_WRITE((dstBox->y2&0xf00)>>8,PM3RD_VideoOverlayYEndHigh);
+
+ GLINT_WRITE_REG(portPriv->Video_Shift << 5 |
+ portPriv->Format |
+ portPriv->Filter |
+ PM3VideoOverlayMode_BUFFERSYNC_MANUAL |
+ PM3VideoOverlayMode_FLIP_VIDEO |
+ PM3VideoOverlayMode_ENABLE,
+ PM3VideoOverlayMode);
+
+ if (!portPriv->ramdacOn) {
+ RAMDAC_WRITE(PM3RD_VideoOverlayControl_ENABLE |
+ PM3RD_VideoOverlayControl_KEY_COLOR |
+ PM3RD_VideoOverlayControl_MODE_MAINKEY |
+ PM3RD_VideoOverlayControl_DIRECTCOLOR_ENABLED,
+ PM3RD_VideoOverlayControl);
+ portPriv->ramdacOn = TRUE;
+ }
+ GLINT_WRITE_REG(PM3VideoOverlayUpdate_ENABLE,
+ PM3VideoOverlayUpdate);
+}
+
+static int
+Permedia3PutImage(
+ ScrnInfoPtr pScrn,
+ short src_x, short src_y,
+ short drw_x, short drw_y,
+ short src_w, short src_h,
+ short drw_w, short drw_h,
+ int id, unsigned char* buf,
+ short width, short height,
+ Bool sync,
+ RegionPtr clipBoxes, pointer data
+){
+#if 0
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+#endif
+ GLINTPortPrivPtr pPriv = (GLINTPortPrivPtr)data;
+ INT32 x1, x2, y1, y2;
+ int pitch;
+ int i;
+ int w_bpp, bpp;
+ Bool copy_flat = TRUE;
+ BoxRec dstBox;
+
+ /* Let's find the image format and Video_Shift values */
+ switch (id) {
+ case LE4CC('Y','V','1','2'):
+ pPriv->Format = FORMAT_YUV422;
+ pPriv->Video_Shift = 1;
+ copy_flat = FALSE;
+ break;
+ case LE4CC('Y','U','Y','2'):
+ pPriv->Format = FORMAT_YUV422;
+ pPriv->Video_Shift = 1;
+ break;
+ case LE4CC('U','Y','V','Y'):
+ pPriv->Format = FORMAT_VUY422;
+ pPriv->Video_Shift = 1;
+ break;
+ case LE4CC('Y','U','V','A'):
+ pPriv->Format = FORMAT_YUV444;
+ pPriv->Video_Shift = 2;
+ break;
+ case LE4CC('V','U','Y','A'):
+ pPriv->Format = FORMAT_VUY444;
+ pPriv->Video_Shift = 2;
+ break;
+ case 0x41: /* RGBA 8:8:8:8 */
+ pPriv->Format = FORMAT_RGB8888;
+ pPriv->Video_Shift = 2;
+ break;
+ case 0x42: /* RGB 5:6:5 */
+ pPriv->Format = FORMAT_RGB565;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x43: /* RGB 1:5:5:5 */
+ pPriv->Format = FORMAT_RGB5551;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x44: /* RGB 4:4:4:4 */
+ pPriv->Format = FORMAT_RGB4444;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x46: /* RGB 2:3:3 */
+ pPriv->Format = FORMAT_RGB332;
+ pPriv->Video_Shift = 0;
+ break;
+ case 0x47: /* BGRA 8:8:8:8 */
+ pPriv->Format = FORMAT_BGR8888;
+ pPriv->Video_Shift = 2;
+ break;
+ case 0x48: /* BGR 5:6:5 */
+ pPriv->Format = FORMAT_BGR565;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x49: /* BGR 1:5:5:5 */
+ pPriv->Format = FORMAT_BGR5551;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x4A: /* BGR 4:4:4:4 */
+ pPriv->Format = FORMAT_BGR4444;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x4C: /* BGR 2:3:3 */
+ pPriv->Format = FORMAT_BGR332;
+ pPriv->Video_Shift = 0;
+ break;
+ default:
+ return XvBadAlloc;
+ }
+
+ /* Clip */
+ x1 = src_x;
+ x2 = src_x + src_w;
+ y1 = src_y;
+ y2 = src_y + src_h;
+
+ dstBox.x1 = drw_x;
+ dstBox.x2 = drw_x + drw_w;
+ dstBox.y1 = drw_y;
+ dstBox.y2 = drw_y + drw_h;
+
+ if(!xf86XVClipVideoHelper(&dstBox, &x1, &x2, &y1, &y2, clipBoxes,
+ width, height))
+ return Success;
+
+ dstBox.x1 -= pScrn->frameX0;
+ dstBox.x2 -= pScrn->frameX0;
+ dstBox.y1 -= pScrn->frameY0;
+ dstBox.y2 -= pScrn->frameY0;
+
+ bpp = pScrn->bitsPerPixel >> 3;
+ pitch = bpp * pScrn->displayWidth;
+
+ w_bpp = (width << pPriv->Video_Shift) >> (pScrn->bitsPerPixel >> 4);
+
+ for (i = 0; i < (pPriv->doubleBuffer ? 2 : 1); i++) {
+ if (!(pPriv->area[i] =
+ Permedia3AllocateMemory(pScrn,pPriv->area[i],w_bpp,src_h)))
+ return BadAlloc;
+
+ pPriv->offset[i] = (pPriv->area[i]->box.x1 * bpp) +
+ (pPriv->area[i]->box.y1 * pitch);
+ }
+
+ HWCopySetup(pScrn, pPriv->area[pPriv->buffer]->box.x1,
+ pPriv->area[pPriv->buffer]->box.y1, w_bpp, height);
+
+ if (copy_flat)
+ HWCopyFlat(pScrn, buf, width, height);
+ else
+ HWCopyYV12(pScrn, buf, width, height);
+
+ /* paint the color key */
+ if(pPriv->autopaintColorKey && !RegionsEqual(&pPriv->clip, clipBoxes)) {
+ /* update cliplist */
+ REGION_COPY(pScrn->pScreen, &pPriv->clip, clipBoxes);
+#if 0
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(PM3VideoOverlayMode_DISABLE,
+ PM3VideoOverlayMode);
+ pPriv->ramdacOn = FALSE;
+#endif
+ xf86XVFillKeyHelper(pScrn->pScreen, pPriv->colorKey, clipBoxes);
+ }
+
+ Permedia3Sync(pScrn);
+
+ Permedia3DisplayVideo(pScrn, id, pPriv->offset[pPriv->buffer], width,height,
+ x1, y1, x2, y2, &dstBox, src_w, src_h, drw_w, drw_h);
+
+ /* Switch buffer on next run - double buffer */
+ if (pPriv->doubleBuffer) {
+ if (!pPriv->buffer)
+ pPriv->buffer = 1;
+ else
+ pPriv->buffer = 0;
+ }
+
+ pPriv->videoStatus = CLIENT_VIDEO_ON;
+
+ return Success;
+}
+
+static int
+Permedia3QueryImageAttributes(
+ ScrnInfoPtr pScrn,
+ int id,
+ unsigned short *w, unsigned short *h,
+ int *pitches, int *offsets
+){
+ int size, tmp;
+
+ if(*w > 2047) *w = 2047;
+ if(*h > 2047) *h = 2047;
+
+ *w = (*w + 1) & ~1;
+ if(offsets) offsets[0] = 0;
+
+ switch(id) {
+ case FOURCC_YV12: /* YV12 */
+ *h = (*h + 1) & ~1;
+ size = (*w + 3) & ~3;
+ if(pitches) pitches[0] = size;
+ size *= *h;
+ if(offsets) offsets[1] = size;
+ tmp = ((*w >> 1) + 3) & ~3;
+ if(pitches) pitches[1] = pitches[2] = tmp;
+ tmp *= (*h >> 1);
+ size += tmp;
+ if(offsets) offsets[2] = size;
+ size += tmp;
+ break;
+ default: /* RGB15, RGB16, YUY2 */
+ size = *w << 1;
+ if(pitches) pitches[0] = size;
+ size *= *h;
+ break;
+ }
+
+ return size;
+}
+
+/****************** Offscreen stuff ***************/
+
+typedef struct {
+ FBAreaPtr area;
+ Bool isOn;
+ int Video_Shift;
+ int Format;
+ Bool ramdacOn;
+} OffscreenPrivRec, * OffscreenPrivPtr;
+
+static int
+Permedia3AllocateSurface(
+ ScrnInfoPtr pScrn,
+ int id,
+ unsigned short w,
+ unsigned short h,
+ XF86SurfacePtr surface
+){
+ FBAreaPtr area;
+ int fbpitch, bpp;
+ OffscreenPrivPtr pPriv;
+
+ if((w > 2047) || (h > 2047))
+ return BadAlloc;
+
+ w = (w + 1) & ~1;
+ bpp = pScrn->bitsPerPixel >> 3;
+ fbpitch = bpp * pScrn->displayWidth;
+
+ if(!(area = Permedia3AllocateMemory(pScrn, NULL, w, h)))
+ return BadAlloc;
+
+ surface->width = w;
+ surface->height = h;
+
+ if(!(surface->offsets = xalloc(sizeof(int)))) {
+ xf86FreeOffscreenArea(area);
+ return BadAlloc;
+ }
+ if(!(pPriv = xalloc(sizeof(OffscreenPrivRec)))) {
+ xfree(surface->offsets);
+ xf86FreeOffscreenArea(area);
+ return BadAlloc;
+ }
+
+ pPriv->area = area;
+ pPriv->isOn = FALSE;
+
+ surface->pScrn = pScrn;
+ surface->id = id;
+ surface->offsets[0] = (area->box.x1 * bpp) + (area->box.y1 * fbpitch);
+ surface->devPrivate.ptr = (pointer)pPriv;
+
+ return Success;
+}
+
+static int
+Permedia3StopSurface(
+ XF86SurfacePtr surface
+){
+ OffscreenPrivPtr pPriv = (OffscreenPrivPtr)surface->devPrivate.ptr;
+
+ if(pPriv->isOn) {
+ GLINTPtr pGlint = GLINTPTR(surface->pScrn);
+ pPriv->ramdacOn = FALSE;
+ GLINT_WAIT(4);
+ RAMDAC_WRITE(PM3RD_VideoOverlayControl_DISABLE,
+ PM3RD_VideoOverlayControl);
+ GLINT_WRITE_REG(PM3VideoOverlayMode_DISABLE,
+ PM3VideoOverlayMode);
+ pPriv->isOn = FALSE;
+ }
+
+ return Success;
+}
+
+static int
+Permedia3FreeSurface(
+ XF86SurfacePtr surface
+){
+ OffscreenPrivPtr pPriv = (OffscreenPrivPtr)surface->devPrivate.ptr;
+
+ if(pPriv->isOn)
+ Permedia3StopSurface(surface);
+ xf86FreeOffscreenArea(pPriv->area);
+ xfree(surface->pitches);
+ xfree(surface->offsets);
+ xfree(surface->devPrivate.ptr);
+
+ return Success;
+}
+
+static int
+Permedia3GetSurfaceAttribute(
+ ScrnInfoPtr pScrn,
+ Atom attribute,
+ INT32 *value
+){
+ return Permedia3GetPortAttribute(pScrn, attribute, value,
+ (pointer)(GET_PORT_PRIVATE(pScrn)));
+}
+
+static int
+Permedia3SetSurfaceAttribute(
+ ScrnInfoPtr pScrn,
+ Atom attribute,
+ INT32 value
+){
+ return Permedia3SetPortAttribute(pScrn, attribute, value,
+ (pointer)(GET_PORT_PRIVATE(pScrn)));
+}
+
+static int
+Permedia3DisplaySurface(
+ XF86SurfacePtr surface,
+ short src_x, short src_y,
+ short drw_x, short drw_y,
+ short src_w, short src_h,
+ short drw_w, short drw_h,
+ RegionPtr clipBoxes
+){
+ OffscreenPrivPtr pPriv = (OffscreenPrivPtr)surface->devPrivate.ptr;
+ ScrnInfoPtr pScrn = surface->pScrn;
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTPortPrivPtr portPriv = pGlint->adaptor->pPortPrivates[0].ptr;
+ INT32 x1, y1, x2, y2;
+ BoxRec dstBox;
+
+ x1 = src_x;
+ x2 = src_x + src_w;
+ y1 = src_y;
+ y2 = src_y + src_h;
+
+ dstBox.x1 = drw_x;
+ dstBox.x2 = drw_x + drw_w;
+ dstBox.y1 = drw_y;
+ dstBox.y2 = drw_y + drw_h;
+
+ if(!xf86XVClipVideoHelper(&dstBox, &x1, &x2, &y1, &y2, clipBoxes,
+ surface->width, surface->height))
+ {
+ return Success;
+ }
+
+ dstBox.x1 -= pScrn->frameX0;
+ dstBox.x2 -= pScrn->frameX0;
+ dstBox.y1 -= pScrn->frameY0;
+ dstBox.y2 -= pScrn->frameY0;
+
+ /* Let's find the image format and Video_Shift values */
+ switch (surface->id) {
+ case LE4CC('Y','V','1','2'):
+ pPriv->Format = FORMAT_YUV422;
+ pPriv->Video_Shift = 1;
+ break;
+ case LE4CC('Y','U','Y','2'):
+ pPriv->Format = FORMAT_YUV422;
+ pPriv->Video_Shift = 1;
+ break;
+ case LE4CC('U','Y','V','Y'):
+ pPriv->Format = FORMAT_VUY422;
+ pPriv->Video_Shift = 1;
+ break;
+ case LE4CC('Y','U','V','A'):
+ pPriv->Format = FORMAT_YUV444;
+ pPriv->Video_Shift = 2;
+ break;
+ case LE4CC('V','U','Y','A'):
+ pPriv->Format = FORMAT_VUY444;
+ pPriv->Video_Shift = 2;
+ break;
+ case 0x41: /* RGBA 8:8:8:8 */
+ pPriv->Format = FORMAT_RGB8888;
+ pPriv->Video_Shift = 2;
+ break;
+ case 0x42: /* RGB 5:6:5 */
+ pPriv->Format = FORMAT_RGB565;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x43: /* RGB 1:5:5:5 */
+ pPriv->Format = FORMAT_RGB5551;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x44: /* RGB 4:4:4:4 */
+ pPriv->Format = FORMAT_RGB4444;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x46: /* RGB 2:3:3 */
+ pPriv->Format = FORMAT_RGB332;
+ pPriv->Video_Shift = 0;
+ break;
+ case 0x47: /* BGRA 8:8:8:8 */
+ pPriv->Format = FORMAT_BGR8888;
+ pPriv->Video_Shift = 2;
+ break;
+ case 0x48: /* BGR 5:6:5 */
+ pPriv->Format = FORMAT_BGR565;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x49: /* BGR 1:5:5:5 */
+ pPriv->Format = FORMAT_BGR5551;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x4A: /* BGR 4:4:4:4 */
+ pPriv->Format = FORMAT_BGR4444;
+ pPriv->Video_Shift = 1;
+ break;
+ case 0x4C: /* BGR 2:3:3 */
+ pPriv->Format = FORMAT_BGR332;
+ pPriv->Video_Shift = 0;
+ break;
+ default:
+ return XvBadAlloc;
+ }
+
+ Permedia3DisplayVideo(pScrn, surface->id, surface->offsets[0],
+ surface->width, surface->height,
+ x1, y1, x2, y2, &dstBox, src_w, src_h, drw_w, drw_h);
+
+ xf86XVFillKeyHelper(pScrn->pScreen, portPriv->colorKey, clipBoxes);
+
+ pPriv->isOn = TRUE;
+ /* we've prempted the XvImage stream so set its free timer */
+ if(portPriv->videoStatus & CLIENT_VIDEO_ON) {
+ REGION_EMPTY(pScrn->pScreen, &portPriv->clip);
+ UpdateCurrentTime();
+ portPriv->videoStatus = FREE_TIMER;
+ portPriv->freeTime = currentTime.milliseconds + FREE_DELAY;
+ pGlint->VideoTimerCallback = Permedia3VideoTimerCallback;
+ }
+
+ return Success;
+}
+
+static void
+Permedia3InitOffscreenImages(ScreenPtr pScreen)
+{
+ XF86OffscreenImagePtr offscreenImages;
+
+ /* need to free this someplace */
+ if(!(offscreenImages = xalloc(sizeof(XF86OffscreenImageRec))))
+ return;
+
+ offscreenImages[0].image = &Images[0];
+ offscreenImages[0].flags = VIDEO_OVERLAID_IMAGES |
+ VIDEO_CLIP_TO_VIEWPORT;
+ offscreenImages[0].alloc_surface = Permedia3AllocateSurface;
+ offscreenImages[0].free_surface = Permedia3FreeSurface;
+ offscreenImages[0].display = Permedia3DisplaySurface;
+ offscreenImages[0].stop = Permedia3StopSurface;
+ offscreenImages[0].setAttribute = Permedia3SetSurfaceAttribute;
+ offscreenImages[0].getAttribute = Permedia3GetSurfaceAttribute;
+ offscreenImages[0].max_width = 2047;
+ offscreenImages[0].max_height = 2047;
+ offscreenImages[0].num_attributes = NUM_ATTRIBUTES;
+ offscreenImages[0].attributes = Attributes;
+
+ xf86XVRegisterOffscreenImages(pScreen, offscreenImages, 1);
+}
+
+static void
+Permedia3VideoTimerCallback(ScrnInfoPtr pScrn, Time time)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTPortPrivPtr pPriv = pGlint->adaptor->pPortPrivates[0].ptr;
+ int i;
+
+ if(pPriv->videoStatus & TIMER_MASK) {
+ if(pPriv->videoStatus & OFF_TIMER) {
+ if(pPriv->offTime < time) {
+ pPriv->ramdacOn = FALSE;
+ GLINT_WAIT(4);
+ RAMDAC_WRITE(PM3RD_VideoOverlayControl_DISABLE,
+ PM3RD_VideoOverlayControl);
+ GLINT_WRITE_REG(PM3VideoOverlayMode_DISABLE,
+ PM3VideoOverlayMode);
+ pPriv->videoStatus = FREE_TIMER;
+ pPriv->freeTime = time + FREE_DELAY;
+ }
+ } else { /* FREE_TIMER */
+ if(pPriv->freeTime < time) {
+ for (i = 0; i < (pPriv->doubleBuffer ? 2 : 1); i++) {
+ if(pPriv->area[i]) {
+ xf86FreeOffscreenArea(pPriv->area[i]);
+ pPriv->area[i] = NULL;
+ }
+ }
+ pPriv->videoStatus = 0;
+ pGlint->VideoTimerCallback = NULL;
+ }
+ }
+ } else /* shouldn't get here */
+ pGlint->VideoTimerCallback = NULL;
+}
+
+#endif /* !XvExtension */
diff --git a/src/pm_accel.c b/src/pm_accel.c
new file mode 100644
index 0000000..f999006
--- /dev/null
+++ b/src/pm_accel.c
@@ -0,0 +1,1199 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ *
+ * Permedia accelerated options.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm_accel.c,v 1.23 2001/05/29 11:23:38 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "fb.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+#include "miline.h" /* for octants */
+#include "xaalocal.h" /* For replacements */
+
+static void PermediaSync(ScrnInfoPtr pScrn);
+static void PermediaSetupForFillRectSolid(ScrnInfoPtr pScrn, int color, int rop,
+ unsigned int planemask);
+static void PermediaSubsequentFillRectSolid(ScrnInfoPtr pScrn, int x, int y,
+ int w, int h);
+static void PermediaSetupForSolidLine(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask);
+static void PermediaSubsequentHorVertLine(ScrnInfoPtr pScrn, int x, int y,
+ int len, int dir);
+static void PermediaSubsequentSolidBresenhamLine(ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e,
+ int len, int octant);
+static void PermediaSubsequentScreenToScreenCopy(ScrnInfoPtr pScrn, int x1,
+ int y1, int x2, int y2, int w, int h);
+static void PermediaSetupForScreenToScreenCopy(ScrnInfoPtr pScrn, int xdir,
+ int ydir, int rop, unsigned int planemask,
+ int transparency_color);
+static void PermediaSetClippingRectangle(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2, int y2);
+static void PermediaDisableClipping(ScrnInfoPtr pScrn);
+static void PermediaSetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg, int rop,
+ unsigned int planemask);
+static void PermediaSubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn, int x,
+ int y, int w, int h, int skipleft);
+static void PermediaSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno);
+static void PermediaWriteBitmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth, int skipleft,
+ int fg, int bg, int rop,unsigned int planemask);
+static void PermediaWritePixmap8bpp(ScrnInfoPtr pScrn, int x, int y, int w,
+ int h, unsigned char *src, int srcwidth,
+ int rop, unsigned int planemask,
+ int transparency_color, int bpp, int depth);
+static void PermediaWritePixmap16bpp(ScrnInfoPtr pScrn, int x, int y, int w,
+ int h, unsigned char *src, int srcwidth,
+ int rop, unsigned int planemask,
+ int transparency_color, int bpp, int depth);
+static void PermediaWritePixmap32bpp(ScrnInfoPtr pScrn, int x, int y, int w,
+ int h, unsigned char *src, int srcwidth,
+ int rop, unsigned int planemask,
+ int transparency_color, int bpp, int depth);
+static void PermediaSetupForMono8x8PatternFill(ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned planemask);
+static void PermediaSubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn,
+ int patternx, int patterny, int x, int y,
+ int w, int h);
+static void PermediaLoadCoord(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ int a, int d);
+static void PermediaPolylinesThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int mode, int npt, DDXPointPtr pPts);
+static void PermediaPolySegmentThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int nseg, xSegment *pSeg);
+
+void
+PermediaInitializeEngine(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /* Initialize the Accelerator Engine to defaults */
+
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(0, dXSub);
+ GLINT_SLOW_WRITE_REG(GWIN_DisableLBUpdate, GLINTWindow);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DitherMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PMTextureReadMode);
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, LBReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TexelLUTMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, YUVMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FogMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
+ GLINT_SLOW_WRITE_REG(0x400, FilterMode);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBHardwareWriteMask);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBSoftwareWriteMask);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTDepth);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBPixelOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, WindowOrigin);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBWindowBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWindowBase);
+
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ GLINT_SLOW_WRITE_REG(0x0, FBReadPixel); /* 8 Bits */
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, PMTextureMapFormat);
+ break;
+ case 16:
+ GLINT_SLOW_WRITE_REG(0x1, FBReadPixel); /* 16 Bits */
+ GLINT_SLOW_WRITE_REG(pGlint->pprod | 1<<19, PMTextureMapFormat);
+ break;
+ case 32:
+ GLINT_SLOW_WRITE_REG(0x2, FBReadPixel); /* 32 Bits */
+ GLINT_SLOW_WRITE_REG(pGlint->pprod | 2<<19, PMTextureMapFormat);
+ break;
+ }
+ pGlint->ROP = 0xFF;
+ pGlint->ClippingOn = FALSE;
+ pGlint->startxsub = 0;
+ pGlint->startxdom = 0;
+ pGlint->starty = 0;
+ pGlint->count = 0;
+ pGlint->dxdom = 0;
+ pGlint->dy = 1<<16;
+ GLINT_WAIT(6);
+ GLINT_WRITE_REG(0, StartXSub);
+ GLINT_WRITE_REG(0,StartXDom);
+ GLINT_WRITE_REG(0,StartY);
+ GLINT_WRITE_REG(0,GLINTCount);
+ GLINT_WRITE_REG(0,dXDom);
+ GLINT_WRITE_REG(1<<16,dY);
+}
+
+Bool
+PermediaAccelInit(ScreenPtr pScreen)
+{
+ XAAInfoRecPtr infoPtr;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ BoxRec AvailFBArea;
+
+ pGlint->AccelInfoRec = infoPtr = XAACreateInfoRec();
+ if (!infoPtr) return FALSE;
+
+ PermediaInitializeEngine(pScrn);
+
+ infoPtr->Flags = PIXMAP_CACHE |
+ LINEAR_FRAMEBUFFER |
+ OFFSCREEN_PIXMAPS;
+
+ infoPtr->Sync = PermediaSync;
+
+ infoPtr->SetClippingRectangle = PermediaSetClippingRectangle;
+ infoPtr->DisableClipping = PermediaDisableClipping;
+ infoPtr->ClippingFlags = HARDWARE_CLIP_MONO_8x8_FILL;
+
+ infoPtr->SolidFillFlags = 0;
+ infoPtr->SetupForSolidFill = PermediaSetupForFillRectSolid;
+ infoPtr->SubsequentSolidFillRect = PermediaSubsequentFillRectSolid;
+ infoPtr->SolidLineFlags = 0;
+ infoPtr->PolySegmentThinSolidFlags = 0;
+ infoPtr->PolylinesThinSolidFlags = 0;
+ infoPtr->SetupForSolidLine = PermediaSetupForSolidLine;
+ infoPtr->SubsequentSolidHorVertLine = PermediaSubsequentHorVertLine;
+ if (!(pScrn->overlayFlags & OVERLAY_8_32_PLANAR))
+ {
+ infoPtr->SubsequentSolidBresenhamLine =
+ PermediaSubsequentSolidBresenhamLine;
+ }
+ infoPtr->PolySegmentThinSolid = PermediaPolySegmentThinSolidWrapper;
+ infoPtr->PolylinesThinSolid = PermediaPolylinesThinSolidWrapper;
+
+ infoPtr->ScreenToScreenCopyFlags = NO_TRANSPARENCY;
+
+ infoPtr->SetupForScreenToScreenCopy = PermediaSetupForScreenToScreenCopy;
+ infoPtr->SubsequentScreenToScreenCopy = PermediaSubsequentScreenToScreenCopy;
+
+ infoPtr->Mono8x8PatternFillFlags =
+ HARDWARE_PATTERN_PROGRAMMED_ORIGIN |
+ HARDWARE_PATTERN_PROGRAMMED_BITS |
+ HARDWARE_PATTERN_SCREEN_ORIGIN;
+
+ infoPtr->SetupForMono8x8PatternFill =
+ PermediaSetupForMono8x8PatternFill;
+ infoPtr->SubsequentMono8x8PatternFillRect =
+ PermediaSubsequentMono8x8PatternFillRect;
+
+ infoPtr->ScanlineCPUToScreenColorExpandFillFlags =
+#if 0
+ LEFT_EDGE_CLIPPING |
+ LEFT_EDGE_CLIPPING_NEGATIVE_X |
+#endif
+ BIT_ORDER_IN_BYTE_LSBFIRST;
+
+ infoPtr->NumScanlineColorExpandBuffers = 1;
+ pGlint->ScratchBuffer = xalloc(((pScrn->virtualX+62)/32*4)
+ + (pScrn->virtualX
+ * pScrn->bitsPerPixel / 8));
+ infoPtr->ScanlineColorExpandBuffers =
+ pGlint->XAAScanlineColorExpandBuffers;
+ pGlint->XAAScanlineColorExpandBuffers[0] =
+ pGlint->IOBase + OutputFIFO + 4;
+
+ infoPtr->SetupForScanlineCPUToScreenColorExpandFill =
+ PermediaSetupForScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentScanlineCPUToScreenColorExpandFill =
+ PermediaSubsequentScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentColorExpandScanline =
+ PermediaSubsequentColorExpandScanline;
+
+ infoPtr->ColorExpandRange = pGlint->FIFOSize;
+
+ infoPtr->WriteBitmap = PermediaWriteBitmap;
+
+ if (pScrn->bitsPerPixel == 8)
+ infoPtr->WritePixmap = PermediaWritePixmap8bpp;
+ else
+ if (pScrn->bitsPerPixel == 16)
+ infoPtr->WritePixmap = PermediaWritePixmap16bpp;
+ else
+ if (pScrn->bitsPerPixel == 32)
+ infoPtr->WritePixmap = PermediaWritePixmap32bpp;
+
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = 0;
+ AvailFBArea.x2 = pScrn->displayWidth;
+ AvailFBArea.y2 = pGlint->FbMapSize / (pScrn->displayWidth *
+ pScrn->bitsPerPixel / 8);
+
+ if (AvailFBArea.y2 > 1023) AvailFBArea.y2 = 1023;
+
+ xf86InitFBManager(pScreen, &AvailFBArea);
+
+ return (XAAInit(pScreen, infoPtr));
+}
+
+static void PermediaLoadCoord(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h,
+ int a, int d
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (w != pGlint->startxsub) {
+ GLINT_WRITE_REG(w, StartXSub);
+ pGlint->startxsub = w;
+ }
+ if (x != pGlint->startxdom) {
+ GLINT_WRITE_REG(x,StartXDom);
+ pGlint->startxdom = x;
+ }
+ if (y != pGlint->starty) {
+ GLINT_WRITE_REG(y,StartY);
+ pGlint->starty = y;
+ }
+ if (h != pGlint->count) {
+ GLINT_WRITE_REG(h,GLINTCount);
+ pGlint->count = h;
+ }
+ if (a != pGlint->dxdom) {
+ GLINT_WRITE_REG(a,dXDom);
+ pGlint->dxdom = a;
+ }
+ if (d != pGlint->dy) {
+ GLINT_WRITE_REG(d,dY);
+ pGlint->dy = d;
+ }
+}
+
+static void
+PermediaSync(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ } while (GLINT_READ_REG(OutputFIFO) != Sync_tag);
+}
+
+static void
+PermediaSetClippingRectangle(
+ ScrnInfoPtr pScrn,
+ int x1, int y1,
+ int x2, int y2
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG (((y1&0x0FFF) << 16) | (x1&0x0FFF), ScissorMinXY);
+ GLINT_WRITE_REG (((y2&0x0FFF) << 16) | (x2&0x0FFF), ScissorMaxXY);
+ GLINT_WRITE_REG (1, ScissorMode);
+ pGlint->ClippingOn = TRUE;
+}
+
+static void
+PermediaDisableClipping(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CHECKCLIPPING;
+}
+
+static void
+PermediaSetupForScreenToScreenCopy(
+ ScrnInfoPtr pScrn,
+ int xdir, int ydir, int rop,
+ unsigned int planemask, int transparency_color
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->BltScanDirection = 0;
+ if (ydir == 1) pGlint->BltScanDirection |= YPositive;
+
+ GLINT_WAIT(4);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+
+ if ((rop == GXset) || (rop == GXclear)) {
+ pGlint->FrameBufferReadMode = pGlint->pprod;
+ } else
+ if ((rop == GXcopy) || (rop == GXcopyInverted)) {
+ pGlint->FrameBufferReadMode = pGlint->pprod | FBRM_SrcEnable;
+ } else {
+ pGlint->FrameBufferReadMode = pGlint->pprod | FBRM_SrcEnable |
+ FBRM_DstEnable;
+ }
+ LOADROP(rop);
+}
+
+static void
+PermediaSubsequentScreenToScreenCopy(
+ ScrnInfoPtr pScrn,
+ int x1, int y1,
+ int x2, int y2,
+ int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int srcaddr;
+ int dstaddr;
+ char align;
+ int direction;
+
+ if (!(pGlint->BltScanDirection & YPositive)) {
+ y1 = y1 + h - 1;
+ y2 = y2 + h - 1;
+ direction = -1<<16;
+ } else {
+ direction = 1<<16;
+ }
+
+ /* We can only use GXcopy for Packed modes, and less than 32 width
+ * gives us speed for small blits. */
+ if ((w < 32) || (pGlint->ROP != GXcopy)) {
+ GLINT_WAIT(9);
+ PermediaLoadCoord(pScrn, x2<<16, y2<<16, (x2+w)<<16, h, 0, direction);
+ srcaddr = x1;
+ dstaddr = x2;
+ GLINT_WRITE_REG(pGlint->FrameBufferReadMode, FBReadMode);
+ } else {
+ GLINT_WAIT(10);
+ PermediaLoadCoord(pScrn, (x2>>pGlint->BppShift)<<16, y2<<16,
+ ((x2+w+7)>>pGlint->BppShift)<<16, h, 0,
+ direction);
+ srcaddr = (x1 & ~pGlint->bppalign);
+ dstaddr = (x2 & ~pGlint->bppalign);
+ align = (x2 & pGlint->bppalign) - (x1 & pGlint->bppalign);
+ GLINT_WRITE_REG(pGlint->FrameBufferReadMode | FBRM_Packed |
+ (align&7)<<20, FBReadMode);
+ GLINT_WRITE_REG(x2<<16|(x2+w), PackedDataLimits);
+ }
+ srcaddr += y1 * pScrn->displayWidth;
+ dstaddr += y2 * pScrn->displayWidth;
+ GLINT_WRITE_REG(srcaddr - dstaddr, FBSourceOffset);
+ GLINT_WRITE_REG(PrimitiveTrapezoid, Render);
+}
+
+static void
+PermediaSetupForFillRectSolid(
+ ScrnInfoPtr pScrn,
+ int color, int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ REPLICATE(color);
+
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, ConstantColor);
+ }
+ LOADROP(rop);
+}
+
+static void
+PermediaSubsequentFillRectSolid(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int speed = 0;
+ if (pGlint->ROP == GXcopy) {
+ GLINT_WAIT(7);
+ PermediaLoadCoord(pScrn, x<<16, y<<16, (x+w)<<16, h, 0, 1<<16);
+ speed = FastFillEnable;
+ } else {
+ GLINT_WAIT(9);
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_Packed | FBRM_DstEnable, FBReadMode);
+ PermediaLoadCoord(pScrn, (x>>pGlint->BppShift)<<16, y<<16,
+ ((x+w+7)>>pGlint->BppShift)<<16, h, 0, 1<<16);
+ GLINT_WRITE_REG(x<<16|(x+w), PackedDataLimits);
+ }
+ GLINT_WRITE_REG(PrimitiveTrapezoid | speed, Render);
+}
+
+static void
+PermediaSetupForMono8x8PatternFill(
+ ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ if (bg == -1) pGlint->FrameBufferReadMode = -1;
+ else pGlint->FrameBufferReadMode = 0;
+ pGlint->ForeGroundColor = fg;
+ pGlint->BackGroundColor = bg;
+ REPLICATE(pGlint->ForeGroundColor);
+ REPLICATE(pGlint->BackGroundColor);
+
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG ((patternx & 0x000000ff), AreaStipplePattern0);
+ GLINT_WRITE_REG ((patternx & 0x0000ff00) >> 8, AreaStipplePattern1);
+ GLINT_WRITE_REG ((patternx & 0x00ff0000) >> 16, AreaStipplePattern2);
+ GLINT_WRITE_REG ((patternx & 0xff000000) >> 24, AreaStipplePattern3);
+ GLINT_WRITE_REG ((patterny & 0x000000ff), AreaStipplePattern4);
+ GLINT_WRITE_REG ((patterny & 0x0000ff00) >> 8, AreaStipplePattern5);
+ GLINT_WRITE_REG ((patterny & 0x00ff0000) >> 16, AreaStipplePattern6);
+ GLINT_WRITE_REG ((patterny & 0xff000000) >> 24, AreaStipplePattern7);
+
+ GLINT_WAIT(7);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, ConstantColor);
+ GLINT_WRITE_REG(pGlint->BackGroundColor, Texel0);
+ LOADROP(rop);
+}
+
+static void
+PermediaSubsequentMono8x8PatternFillRect(
+ ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int x, int y,
+ int w, int h)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINT_WAIT(8);
+ PermediaLoadCoord(pScrn, x<<16, y<<16, (x+w)<<16, h, 0, 1<<16);
+ if (pGlint->FrameBufferReadMode != -1) {
+ GLINT_WRITE_REG(1<<20|patternx<<7|patterny<<12|UNIT_ENABLE,
+ AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | TextureEnable | PrimitiveTrapezoid,
+ Render);
+ } else {
+ GLINT_WRITE_REG(patternx<<7|patterny<<12|UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | PrimitiveTrapezoid, Render);
+ }
+}
+
+static void
+PermediaWriteBitmap(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int skipleft,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char *srcpntr;
+ int dwords, height;
+ register int count;
+ register CARD32* pattern;
+ int dobackground = 0;
+
+ w += skipleft;
+ x -= skipleft;
+ dwords = (w + 31) >> 5;
+
+ PermediaSetClippingRectangle(pScrn, x+skipleft, y, x+w, y+h);
+
+ GLINT_WAIT(14);
+ DO_PLANEMASK(planemask);
+ LOADROP(rop);
+ if (bg != -1) dobackground = ForceBackgroundColor;
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ pGlint->BackGroundColor = bg;
+ pGlint->ForeGroundColor = fg;
+ REPLICATE(fg);
+ REPLICATE(bg);
+ if ((rop == GXcopy) && (pGlint->BackGroundColor == -1)) {
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ GLINT_WRITE_REG(0, RasterizerMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(BitMaskPackingEachScanline|dobackground,RasterizerMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(fg, ConstantColor);
+ if (dobackground) {
+ GLINT_WRITE_REG(bg, Texel0);
+ pGlint->FrameBufferReadMode = TextureEnable;
+ } else {
+ pGlint->FrameBufferReadMode = 0;
+ }
+ }
+ PermediaLoadCoord(pScrn, x<<16, y<<16, (x+w)<<16, h, 0, 1<<16);
+
+ GLINT_WRITE_REG(PrimitiveTrapezoid | pGlint->FrameBufferReadMode | SyncOnBitMask, Render);
+
+ height = h;
+ srcpntr = src;
+ while(height--) {
+ count = dwords >> 3;
+ pattern = (CARD32*)srcpntr;
+ while(count--) {
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG(*(pattern), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+1), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+2), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+3), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+4), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+5), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+6), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+7), BitMaskPattern);
+ pattern+=8;
+ }
+ count = dwords & 0x07;
+ GLINT_WAIT(count);
+ while (count--)
+ GLINT_WRITE_REG(*(pattern++), BitMaskPattern);
+ srcpntr += srcwidth;
+ }
+
+ PermediaDisableClipping(pScrn);
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+PermediaSetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int dobackground = 0;
+
+ if (bg != -1) dobackground |= ForceBackgroundColor;
+ pGlint->BackGroundColor = bg;
+ pGlint->ForeGroundColor = fg;
+ REPLICATE(fg);
+ REPLICATE(bg);
+ GLINT_WAIT(7);
+ DO_PLANEMASK(planemask);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod|FBRM_DstEnable, FBReadMode);
+ }
+ if ((rop == GXcopy) && (pGlint->BackGroundColor == -1)) {
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ GLINT_WRITE_REG(0,RasterizerMode);
+ } else {
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(fg, ConstantColor);
+ GLINT_WRITE_REG(BitMaskPackingEachScanline|dobackground,RasterizerMode);
+ if (dobackground) {
+ GLINT_WRITE_REG(bg, Texel0);
+ pGlint->FrameBufferReadMode = TextureEnable;
+ } else {
+ pGlint->FrameBufferReadMode = 0;
+ }
+ }
+ LOADROP(rop);
+}
+
+static void
+PermediaSubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ int skipleft
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->dwords = ((w + 31) >> 5); /* dwords per scanline */
+
+#if 0
+ PermediaSetClippingRectangle(pScrn, x+skipleft, y, x+w, y+h);
+#endif
+
+ pGlint->cpucount = h;
+
+ GLINT_WAIT(8);
+ PermediaLoadCoord(pScrn, x<<16, y<<16, (x+w)<<16, h, 0, 1<<16);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | pGlint->FrameBufferReadMode | SyncOnBitMask,
+ Render);
+#if defined(__alpha__)
+ if (0) /* force Alpha to use indirect always */
+#else
+ if ((pGlint->dwords*h) < pGlint->FIFOSize)
+#endif
+ {
+ /* Turn on direct for less than FIFOSize dword colour expansion */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->IOBase+OutputFIFO+4;
+ pGlint->ScanlineDirect = 1;
+ GLINT_WRITE_REG(((pGlint->dwords*h)-1)<<16 | 0x0D, OutputFIFO);
+ GLINT_WAIT(pGlint->dwords*h);
+ } else {
+ /* Use indirect for anything else */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->ScratchBuffer;
+ pGlint->ScanlineDirect = 0;
+ }
+
+ pGlint->cpucount--;
+}
+
+static void
+PermediaSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 *srcp = (CARD32*)pGlint->XAAScanlineColorExpandBuffers[bufno];
+ int dwords = pGlint->dwords;
+
+ if (!pGlint->ScanlineDirect) {
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ dwords -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords - 1) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, dwords);
+ }
+ }
+}
+
+
+static void
+PermediaWritePixmap8bpp(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int transparency_color,
+ int bpp, int depth
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int skipleft, dwords, count;
+ CARD32* srcp;
+ unsigned char *srcpbyte;
+ Bool FastTexLoad = FALSE;
+
+ GLINT_WAIT(2);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+
+ dwords = (w + 3) >> 2;
+ if((!(x&3)) && (!(w&3))) FastTexLoad = TRUE;
+ if((rop != GXcopy) || (planemask != ~0))
+ FastTexLoad = FALSE;
+
+#if 0
+ if (rop == GXcopy) {
+ skipleft = 0;
+ } else {
+ if((skipleft = (long)src & 0x03)) {
+ skipleft /= (bpp>>3);
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03);
+ }
+ }
+#endif
+ skipleft = 0;
+
+ if(FastTexLoad) {
+ int address;
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_DISABLE, FBWriteMode);
+ PermediaSync(pScrn); /* we are not using the rasterizer */
+ while(h--) {
+ count = dwords;
+ address = ((y * pScrn->displayWidth) + x) >> 2;
+ srcp = (CARD32*)src;
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(address, TextureDownloadOffset);
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16)
+ | (0x11 << 4) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, infoRec->ColorExpandRange - 1);
+ count -= infoRec->ColorExpandRange - 1;
+ address += infoRec->ColorExpandRange - 1;
+ srcp += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x11 << 4) | 0x0D,
+ OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ y++;
+ }
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ } else {
+ GLINT_WAIT(10);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ PermediaLoadCoord(pScrn, x<<16, y<<16, (x+w)<<16, h, 0, 1<<16);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ LOADROP(rop);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | SyncOnHostData, Render);
+
+ {
+ while(h--) {
+ count = w;
+ srcpbyte = (unsigned char *)src;
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) |
+ (0x15 << 4) | 0x05, OutputFIFO);
+ GLINT_MoveBYTE(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned char *)srcpbyte, infoRec->ColorExpandRange-1);
+ count -= infoRec->ColorExpandRange - 1;
+ srcpbyte += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveBYTE(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned char *)srcpbyte, count);
+ }
+ src += srcwidth;
+ }
+ }
+ }
+
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+PermediaWritePixmap16bpp(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int transparency_color,
+ int bpp, int depth
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int skipleft, dwords, count;
+ CARD32* srcp;
+ unsigned short* srcpword;
+ Bool FastTexLoad;
+
+ GLINT_WAIT(2);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+
+ FastTexLoad = FALSE;
+ dwords = (w + 1) >> 1;
+ if((!(x&1)) && (!(w&1))) FastTexLoad = TRUE;
+ if((rop != GXcopy) || (planemask != ~0))
+ FastTexLoad = FALSE;
+
+#if 0
+ if (rop == GXcopy) {
+ skipleft = 0;
+ } else {
+ if((skipleft = (long)src & 0x03L)) {
+ skipleft /= (bpp>>3);
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+ }
+#endif
+ skipleft = 0;
+
+ if(FastTexLoad) {
+ int address;
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_DISABLE, FBWriteMode);
+ PermediaSync(pScrn); /* we are not using the rasterizer */
+ while(h--) {
+ count = dwords;
+ address = ((y * pScrn->displayWidth) + x) >> 1;
+ srcp = (CARD32*)src;
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(address, TextureDownloadOffset);
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) |
+ (0x11 << 4) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, infoRec->ColorExpandRange - 1);
+ count -= infoRec->ColorExpandRange - 1;
+ address += infoRec->ColorExpandRange - 1;
+ srcp += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x11 << 4) | 0x0D,
+ OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ y++;
+ }
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ } else {
+ GLINT_WAIT(10);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ PermediaLoadCoord(pScrn, x<<16, y<<16, (x+w)<<16, h, 0, 1<<16);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ LOADROP(rop);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | SyncOnHostData, Render);
+
+ {
+ while(h--) {
+ count = w;
+ srcpword = (unsigned short *)src;
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) |
+ (0x15 << 4) | 0x05, OutputFIFO);
+ GLINT_MoveWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned short *)srcpword,infoRec->ColorExpandRange-1);
+ count -= infoRec->ColorExpandRange - 1;
+ srcpword += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (unsigned short *)srcpword, count);
+ }
+ src += srcwidth;
+ }
+ }
+ }
+
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+PermediaWritePixmap32bpp(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int rop,
+ unsigned int planemask,
+ int transparency_color,
+ int bpp, int depth
+)
+{
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int skipleft, dwords, count;
+ CARD32* srcp;
+ Bool FastTexLoad;
+
+ GLINT_WAIT(3);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+
+ FastTexLoad = TRUE;
+ dwords = w;
+ if((rop != GXcopy) || (planemask != ~0))
+ FastTexLoad = FALSE;
+
+#if 0
+ if (!FastTexLoad) {
+ if((skipleft = (long)src & 0x03L)) {
+ skipleft /= (bpp>>3);
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+ }
+#endif
+ skipleft = 0;
+
+ if(FastTexLoad) {
+ int address;
+
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_DISABLE, FBWriteMode);
+ PermediaSync(pScrn); /* we are not using the rasterizer */
+ while(h--) {
+ count = dwords;
+ address = (y * pScrn->displayWidth) + x;
+ srcp = (CARD32*)src;
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(address, TextureDownloadOffset);
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) |
+ (0x11 << 4) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, infoRec->ColorExpandRange - 1);
+ count -= infoRec->ColorExpandRange - 1;
+ address += infoRec->ColorExpandRange - 1;
+ srcp += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x11 << 4) | 0x0D is the TAG for TextureData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x11 << 4) | 0x0D,
+ OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ y++;
+ }
+ GLINT_WAIT(1);
+ GLINT_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ } else {
+ GLINT_WAIT(9);
+ PermediaLoadCoord(pScrn, (x&0xFFFF)<<16, y<<16, ((x&0xFFFF)+w)<<16, h, 0, 1<<16);
+ LOADROP(rop);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | SyncOnHostData, Render);
+
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) |
+ (0x15 << 4) | 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, infoRec->ColorExpandRange - 1);
+ count -= infoRec->ColorExpandRange - 1;
+ srcp += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count + 1);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+ }
+
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+PermediaPolylinesThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int mode,
+ int npt,
+ DDXPointPtr pPts
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolyLines(pDraw, pGC, mode, npt, pPts);
+}
+
+static void
+PermediaPolySegmentThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int nseg,
+ xSegment *pSeg
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolySegment(pDraw, pGC, nseg, pSeg);
+}
+
+static void
+PermediaSetupForSolidLine(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, GLINTColor);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+PermediaSubsequentHorVertLine(ScrnInfoPtr pScrn,int x,int y,int len,int dir)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(7);
+ if (dir == DEGREES_0) {
+ PermediaLoadCoord(pScrn, x<<16, y<<16, 0, len, 1<<16, 0);
+ } else {
+ PermediaLoadCoord(pScrn, x<<16, y<<16, 0, len, 0, 1<<16);
+ }
+
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+}
+
+static void
+PermediaSubsequentSolidBresenhamLine( ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e, int len, int octant)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int dxdom, dy;
+
+ if(dmaj == dmin) {
+ GLINT_WAIT(7);
+ if(octant & YDECREASING) {
+ dy = -1<<16;
+ } else {
+ dy = 1<<16;
+ }
+
+ if(octant & XDECREASING) {
+ dxdom = -1<<16;
+ } else {
+ dxdom = 1<<16;
+ }
+
+ PermediaLoadCoord(pScrn, x<<16, y<<16, 0, len, dxdom, dy);
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+ return;
+ }
+
+ fbBres(pGlint->CurrentDrawable, pGlint->CurrentGC, 0,
+ (octant & XDECREASING) ? -1 : 1,
+ (octant & YDECREASING) ? -1 : 1,
+ (octant & YMAJOR) ? Y_AXIS : X_AXIS,
+ x, y, dmin + e, dmin, -dmaj, len);
+}
diff --git a/src/pm_dac.c b/src/pm_dac.c
new file mode 100644
index 0000000..fed0c38
--- /dev/null
+++ b/src/pm_dac.c
@@ -0,0 +1,251 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane <alanh@fairlite.demon.co.uk>
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Helmut Fahrion, <hf@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/pm_dac.c,v 1.11 2002/02/27 18:41:04 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "IBM.h"
+#include "TI.h"
+#include "glint_regs.h"
+#include "glint.h"
+
+Bool
+PermediaInit(ScrnInfoPtr pScrn, DisplayModePtr mode)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ GLINTRegPtr pReg = &pGlint->ModeReg[0];
+ RamDacHWRecPtr pIBM = RAMDACHWPTR(pScrn);
+ RamDacRegRecPtr ramdacReg = &pIBM->ModeReg;
+ CARD32 temp1, temp2, temp3, temp4;
+
+ STOREREG(Aperture0, 0x00000000);
+ STOREREG(Aperture1, 0x00000000);
+
+ pReg->glintRegs[PMFramebufferWriteMask >> 3] = 0xFFFFFFFF;
+ pReg->glintRegs[PMBypassWriteMask >> 3] = 0xFFFFFFFF;
+
+ pReg->glintRegs[DFIFODis >> 3] = 1;
+ pReg->glintRegs[FIFODis >> 3] = 3;
+
+ temp1 = mode->CrtcHSyncStart - mode->CrtcHDisplay;
+ temp2 = mode->CrtcVSyncStart - mode->CrtcVDisplay;
+ temp3 = mode->CrtcHSyncEnd - mode->CrtcHSyncStart;
+ temp4 = mode->CrtcVSyncEnd - mode->CrtcVSyncStart;
+
+ pReg->glintRegs[PMHTotal >> 3] = Shiftbpp(pScrn,mode->CrtcHTotal);
+ pReg->glintRegs[PMHsEnd >> 3] = Shiftbpp(pScrn, temp1 + temp3);
+ pReg->glintRegs[PMHsStart >> 3] = Shiftbpp(pScrn, temp1);
+ pReg->glintRegs[PMHbEnd >> 3] = Shiftbpp(pScrn, mode->CrtcHTotal -
+ mode->CrtcHDisplay);
+ pReg->glintRegs[PMHgEnd >> 3] = Shiftbpp(pScrn, mode->CrtcHTotal -
+ mode->CrtcHDisplay);
+ pReg->glintRegs[PMScreenStride >> 3] =
+ Shiftbpp(pScrn,pScrn->displayWidth>>1);
+
+ pReg->glintRegs[PMVTotal >> 3] = mode->CrtcVTotal;
+ pReg->glintRegs[PMVsEnd >> 3] = temp2 + temp4;
+ pReg->glintRegs[PMVsStart >> 3] = temp2;
+ pReg->glintRegs[PMVbEnd >> 3] = mode->CrtcVTotal - mode->CrtcVDisplay;
+
+ pReg->glintRegs[PMVideoControl >> 3] =
+ (((mode->Flags & V_PHSYNC) ? 0x1 : 0x3) << 3) |
+ (((mode->Flags & V_PVSYNC) ? 0x1 : 0x3) << 5) | 1;
+
+ pReg->glintRegs[VClkCtl >> 3] = 3;
+ pReg->glintRegs[PMScreenBase >> 3] = 0;
+ pReg->glintRegs[PMHTotal >> 3] -= 1; /* PMHTotal */
+ pReg->glintRegs[PMHsStart >> 3] -= 1; /* PMHsStart */
+ pReg->glintRegs[PMVTotal >> 3] -= 1; /* PMVTotal */
+ pReg->glintRegs[ChipConfig >> 3] = GLINT_READ_REG(ChipConfig) & 0xFFFFFFFD;
+
+ switch(pGlint->RamDac->RamDacType) {
+ case IBM526_RAMDAC:
+ case IBM526DB_RAMDAC:
+ {
+ /* Get the programmable clock values */
+ unsigned long m=0,n=0,p=0,c=0;
+ unsigned long clock;
+
+ clock = IBMramdac526CalculateMNPCForClock(pGlint->RefClock, mode->Clock,
+ 1, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p, &c);
+
+ ramdacReg->DacRegs[IBMRGB_m0] = m;
+ ramdacReg->DacRegs[IBMRGB_n0] = n;
+ ramdacReg->DacRegs[IBMRGB_p0] = p;
+ ramdacReg->DacRegs[IBMRGB_c0] = c;
+
+ ramdacReg->DacRegs[IBMRGB_pll_ctrl1] = 0x05;
+ ramdacReg->DacRegs[IBMRGB_pll_ctrl2] = 0x00;
+
+ p = 1;
+ clock = IBMramdac526CalculateMNPCForClock(pGlint->RefClock, mode->Clock,
+ 0, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p, &c);
+
+ ramdacReg->DacRegs[IBMRGB_sysclk] = 0x05;
+ ramdacReg->DacRegs[IBMRGB_sysclk_m] = m;
+ ramdacReg->DacRegs[IBMRGB_sysclk_n] = n;
+ ramdacReg->DacRegs[IBMRGB_sysclk_p] = p;
+ ramdacReg->DacRegs[IBMRGB_sysclk_c] = c;
+ }
+ ramdacReg->DacRegs[IBMRGB_misc1] = SENS_DSAB_DISABLE | VRAM_SIZE_32;
+ ramdacReg->DacRegs[IBMRGB_misc2] = COL_RES_8BIT | PORT_SEL_VRAM;
+ if (pScrn->depth >= 24)
+ ramdacReg->DacRegs[IBMRGB_misc2] |= PCLK_SEL_LCLK;
+ else
+ ramdacReg->DacRegs[IBMRGB_misc2] |= PCLK_SEL_PLL;
+ ramdacReg->DacRegs[IBMRGB_misc3] = 0;
+ ramdacReg->DacRegs[IBMRGB_misc_clock] = 1;
+ ramdacReg->DacRegs[IBMRGB_sync] = 0;
+ ramdacReg->DacRegs[IBMRGB_hsync_pos] = 0;
+ ramdacReg->DacRegs[IBMRGB_pwr_mgmt] = 0;
+ ramdacReg->DacRegs[IBMRGB_dac_op] = 0;
+ ramdacReg->DacRegs[IBMRGB_pal_ctrl] = 0;
+ break;
+ case TI3026_RAMDAC:
+ {
+ /* Get the programmable clock values */
+ unsigned long m=0,n=0,p=0;
+ unsigned long clock;
+ unsigned long q, VCO = 0;
+
+ clock = TIramdacCalculateMNPForClock(pGlint->RefClock,
+ mode->Clock, 1, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p);
+
+ STORERAMDAC(TIDAC_PIXEL_N, ((n & 0x3f) | 0xC0));
+ STORERAMDAC(TIDAC_PIXEL_M, (m & 0x3f));
+ STORERAMDAC(TIDAC_PIXEL_P, ((p & 0x03) | 0xbc));
+ STORERAMDAC(TIDAC_PIXEL_VALID, TRUE);
+
+ if (pGlint->RamDac->RamDacType == (TI3026_RAMDAC))
+ n = 65 - ((32 << 2) / pScrn->bitsPerPixel);
+ else
+ n = 65 - ((128 << 2) / pScrn->bitsPerPixel);
+ m = 61;
+ p = 0;
+ for (q = 0; q < 8; q++) {
+ if (q > 0) p = 3;
+ for ( ; p < 4; p++) {
+ VCO = ((clock * (q + 1) * (65 - m)) / (65 - n)) << (p + 1);
+ if (VCO >= 110000) { break; }
+ }
+ if (VCO >= 110000) { break; }
+ }
+ STORERAMDAC(TIDAC_clock_ctrl, (q | 0x38));
+
+ STORERAMDAC(TIDAC_LOOP_N, ((n & 0x3f) | 0xC0));
+ STORERAMDAC(TIDAC_LOOP_M, (m & 0x3f));
+ STORERAMDAC(TIDAC_LOOP_P, ((p & 0x03) | 0xF0));
+ STORERAMDAC(TIDAC_LOOP_VALID, TRUE);
+ break;
+ }
+ }
+
+ (*pGlint->RamDac->SetBpp)(pScrn, ramdacReg);
+
+ /* The permedia uses a 32bit data path, the TI ramdac code
+ * defaults to 64bit. So we knock it down to 32bit here */
+ if (pGlint->RamDac->RamDacType == (TI3026_RAMDAC))
+ ramdacReg->DacRegs[TIDAC_multiplex_ctrl] -= 1;
+
+ return(TRUE);
+}
+
+void
+PermediaSave(ScrnInfoPtr pScrn, GLINTRegPtr glintReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information using the slow routines */
+ xf86SlowBcopy((CARD8*)pGlint->FbBase, (CARD8*)pGlint->VGAdata, 65536);
+
+ glintReg->glintRegs[Aperture0 >> 3] = GLINT_READ_REG(Aperture0);
+ glintReg->glintRegs[Aperture1 >> 3] = GLINT_READ_REG(Aperture1);
+ glintReg->glintRegs[PMFramebufferWriteMask] =
+ GLINT_READ_REG(PMFramebufferWriteMask);
+ glintReg->glintRegs[PMBypassWriteMask >> 3] =
+ GLINT_READ_REG(PMBypassWriteMask);
+ glintReg->glintRegs[DFIFODis >> 3] = GLINT_READ_REG(DFIFODis);
+ glintReg->glintRegs[FIFODis >> 3] = GLINT_READ_REG(FIFODis);
+
+ glintReg->glintRegs[PMHTotal >> 3] = GLINT_READ_REG(PMHTotal);
+ glintReg->glintRegs[PMHbEnd >> 3] = GLINT_READ_REG(PMHbEnd);
+ glintReg->glintRegs[PMHgEnd >> 3] = GLINT_READ_REG(PMHgEnd);
+ glintReg->glintRegs[PMScreenStride >> 3] = GLINT_READ_REG(PMScreenStride);
+ glintReg->glintRegs[PMHsStart >> 3] = GLINT_READ_REG(PMHsStart);
+ glintReg->glintRegs[PMHsEnd >> 3] = GLINT_READ_REG(PMHsEnd);
+ glintReg->glintRegs[PMVTotal >> 3] = GLINT_READ_REG(PMVTotal);
+ glintReg->glintRegs[PMVbEnd >> 3] = GLINT_READ_REG(PMVbEnd);
+ glintReg->glintRegs[PMVsStart >> 3] = GLINT_READ_REG(PMVsStart);
+ glintReg->glintRegs[PMVsEnd >> 3] = GLINT_READ_REG(PMVsEnd);
+ glintReg->glintRegs[PMScreenBase >> 3] = GLINT_READ_REG(PMScreenBase);
+ glintReg->glintRegs[PMVideoControl >> 3] = GLINT_READ_REG(PMVideoControl);
+ glintReg->glintRegs[VClkCtl >> 3] = GLINT_READ_REG(VClkCtl);
+ glintReg->glintRegs[ChipConfig >> 3] = GLINT_READ_REG(ChipConfig);
+}
+
+void
+PermediaRestore(ScrnInfoPtr pScrn, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ /* We can't rely on the vgahw layer copying the font information
+ * back properly, due to problems with MMIO access to VGA space
+ * so we memcpy the information using the slow routines */
+ if (pGlint->STATE)
+ xf86SlowBcopy((CARD8*)pGlint->VGAdata, (CARD8*)pGlint->FbBase, 65536);
+
+ RESTOREREG(ChipConfig);
+ RESTOREREG(DFIFODis);
+ RESTOREREG(FIFODis);
+ RESTOREREG(Aperture0);
+ RESTOREREG(Aperture1);
+ RESTOREREG(PMFramebufferWriteMask);
+ RESTOREREG(PMBypassWriteMask);
+ RESTOREREG(PMVideoControl);
+ RESTOREREG(PMHgEnd);
+ RESTOREREG(VClkCtl);
+ RESTOREREG(PMHTotal);
+ RESTOREREG(PMHbEnd);
+ RESTOREREG(PMHsStart);
+ RESTOREREG(PMHsEnd);
+ RESTOREREG(PMVTotal);
+ RESTOREREG(PMVbEnd);
+ RESTOREREG(PMVsStart);
+ RESTOREREG(PMVsEnd);
+ RESTOREREG(PMScreenBase);
+ RESTOREREG(PMScreenStride);
+}
diff --git a/src/sx_accel.c b/src/sx_accel.c
new file mode 100644
index 0000000..36ecd4b
--- /dev/null
+++ b/src/sx_accel.c
@@ -0,0 +1,872 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ *
+ * GLINT 300SX accelerated options.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/sx_accel.c,v 1.8 2001/10/28 03:33:30 tsi Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "fb.h"
+
+#include "miline.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+#include "xaalocal.h" /* For replacements */
+
+static void SXSync(ScrnInfoPtr pScrn);
+static void SXSetupForFillRectSolid(ScrnInfoPtr pScrn, int color, int rop,
+ unsigned int planemask);
+static void SXSubsequentFillRectSolid(ScrnInfoPtr pScrn, int x, int y,
+ int w, int h);
+static void SXSetupForMono8x8PatternFill(ScrnInfoPtr pScrn, int patternx,
+ int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask);
+static void SXSubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn, int patternx,
+ int patterny, int x, int y,
+ int w, int h);
+static void SXSetupForScreenToScreenCopy(ScrnInfoPtr pScrn, int xdir, int ydir,
+ int rop, unsigned int planemask,
+ int transparency_color);
+static void SXSubsequentScreenToScreenCopy(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2, int y2, int w, int h);
+#if 0
+static void SXWriteBitmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth,
+ int skipleft, int fg, int bg, int rop,
+ unsigned int planemask);
+static void SXWritePixmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth, int rop,
+ unsigned int planemask, int trans,
+ int bpp, int depth);
+static void SXSetupForScanlineCPUToScreenColorExpandFill(ScrnInfoPtr pScrn, int fg,
+ int bg, int rop, unsigned int planemask);
+static void SXSubsequentScanlineCPUToScreenColorExpandFill(ScrnInfoPtr pScrn, int x,
+ int y, int w, int h, int skipleft);
+static void SXSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno);
+#endif
+static void SXSetClippingRectangle(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2,int y2);
+static void SXDisableClipping(ScrnInfoPtr pScrn);
+static void SXLoadCoord(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ int a, int d);
+static void SXSetupForSolidLine(ScrnInfoPtr pScrn, int color, int rop,
+ unsigned int planemask);
+static void SXSubsequentHorVertLine(ScrnInfoPtr pScrn, int x1, int y1,
+ int len, int dir);
+static void SXSubsequentSolidBresenhamLine(ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e,
+ int len, int octant);
+static void SXPolylinesThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int mode, int npt, DDXPointPtr pPts);
+static void SXPolySegmentThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int nseg, xSegment *pSeg);
+
+#define MAX_FIFO_ENTRIES 15
+
+void
+SXInitializeEngine(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ /* Initialize the Accelerator Engine to defaults */
+
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DitherMode);
+ GLINT_SLOW_WRITE_REG(0x400, FilterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, LBReadMode);
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWriteMode);
+ GLINT_SLOW_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTWindow);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FogMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LineStippleMode);
+ GLINT_SLOW_WRITE_REG(0, UpdateLineStippleCounters);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBHardwareWriteMask);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBSoftwareWriteMask);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTDepth);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBPixelOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, WindowOrigin);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBWindowBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWindowBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+
+ pGlint->ROP = 0xFF;
+ pGlint->ClippingOn = FALSE;
+ pGlint->startxsub = 0;
+ pGlint->startxdom = 0;
+ pGlint->starty = 0;
+ pGlint->count = 0;
+ pGlint->dxdom = 0;
+ pGlint->dy = 1;
+ pGlint->planemask = 0;
+ GLINT_SLOW_WRITE_REG(0, StartXSub);
+ GLINT_SLOW_WRITE_REG(0, StartXDom);
+ GLINT_SLOW_WRITE_REG(0, StartY);
+ GLINT_SLOW_WRITE_REG(0, GLINTCount);
+ GLINT_SLOW_WRITE_REG(0, dXDom);
+ GLINT_SLOW_WRITE_REG(0, dXSub);
+ GLINT_SLOW_WRITE_REG(1<<16, dY);
+}
+
+Bool
+SXAccelInit(ScreenPtr pScreen)
+{
+ XAAInfoRecPtr infoPtr;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ long memory = pGlint->FbMapSize;
+ BoxRec AvailFBArea;
+
+ pGlint->AccelInfoRec = infoPtr = XAACreateInfoRec();
+ if (!infoPtr) return FALSE;
+
+ SXInitializeEngine(pScrn);
+
+ infoPtr->Flags = PIXMAP_CACHE |
+ LINEAR_FRAMEBUFFER |
+ OFFSCREEN_PIXMAPS;
+
+ infoPtr->Sync = SXSync;
+
+ infoPtr->SetClippingRectangle = SXSetClippingRectangle;
+ infoPtr->DisableClipping = SXDisableClipping;
+ infoPtr->ClippingFlags = HARDWARE_CLIP_MONO_8x8_FILL |
+ HARDWARE_CLIP_SCREEN_TO_SCREEN_COPY |
+ HARDWARE_CLIP_SOLID_FILL;
+
+ infoPtr->SolidFillFlags = 0;
+ infoPtr->SetupForSolidFill = SXSetupForFillRectSolid;
+ infoPtr->SubsequentSolidFillRect = SXSubsequentFillRectSolid;
+
+ infoPtr->SolidLineFlags = 0;
+ infoPtr->PolySegmentThinSolidFlags = 0;
+ infoPtr->PolylinesThinSolidFlags = 0;
+ infoPtr->SetupForSolidLine = SXSetupForSolidLine;
+ infoPtr->SubsequentSolidHorVertLine = SXSubsequentHorVertLine;
+ infoPtr->SubsequentSolidBresenhamLine =
+ SXSubsequentSolidBresenhamLine;
+ infoPtr->PolySegmentThinSolid = SXPolySegmentThinSolidWrapper;
+ infoPtr->PolylinesThinSolid = SXPolylinesThinSolidWrapper;
+
+ infoPtr->ScreenToScreenCopyFlags = NO_TRANSPARENCY |
+ ONLY_LEFT_TO_RIGHT_BITBLT;
+ infoPtr->SetupForScreenToScreenCopy = SXSetupForScreenToScreenCopy;
+ infoPtr->SubsequentScreenToScreenCopy = SXSubsequentScreenToScreenCopy;
+
+ infoPtr->Mono8x8PatternFillFlags = HARDWARE_PATTERN_PROGRAMMED_ORIGIN |
+ HARDWARE_PATTERN_SCREEN_ORIGIN |
+ HARDWARE_PATTERN_PROGRAMMED_BITS;
+ infoPtr->SetupForMono8x8PatternFill = SXSetupForMono8x8PatternFill;
+ infoPtr->SubsequentMono8x8PatternFillRect =
+ SXSubsequentMono8x8PatternFillRect;
+
+#if 0
+ infoPtr->ScanlineCPUToScreenColorExpandFillFlags =
+ TRANSPARENCY_ONLY |
+ BIT_ORDER_IN_BYTE_LSBFIRST;
+
+ infoPtr->NumScanlineColorExpandBuffers = 1;
+ pGlint->ScratchBuffer = xalloc(((pScrn->virtualX+62)/32*4)
+ + (pScrn->virtualX
+ * pScrn->bitsPerPixel / 8));
+ infoPtr->ScanlineColorExpandBuffers =
+ pGlint->XAAScanlineColorExpandBuffers;
+ pGlint->XAAScanlineColorExpandBuffers[0] =
+ pGlint->IOBase + OutputFIFO + 4;
+
+ infoPtr->SetupForScanlineCPUToScreenColorExpandFill =
+ SXSetupForScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentScanlineCPUToScreenColorExpandFill =
+ SXSubsequentScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentColorExpandScanline =
+ SXSubsequentColorExpandScanline;
+
+ infoPtr->WriteBitmap = SXWriteBitmap;
+ infoPtr->ColorExpandRange = MAX_FIFO_ENTRIES;
+
+ infoPtr->WritePixmap = SXWritePixmap;
+#endif
+
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = 0;
+ AvailFBArea.x2 = pScrn->displayWidth;
+ if (memory > (16383*1024)) memory = 16383*1024;
+ AvailFBArea.y2 = memory / (pScrn->displayWidth *
+ pScrn->bitsPerPixel / 8);
+
+ if (AvailFBArea.y2 > 2047) AvailFBArea.y2 = 2047;
+
+ xf86InitFBManager(pScreen, &AvailFBArea);
+
+ return (XAAInit(pScreen, infoPtr));
+}
+
+static void SXLoadCoord(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h,
+ int a, int d
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (w != pGlint->startxsub) {
+ GLINT_WRITE_REG(w<<16, StartXSub);
+ pGlint->startxsub = w;
+ }
+ if (x != pGlint->startxdom) {
+ GLINT_WRITE_REG(x<<16,StartXDom);
+ pGlint->startxdom = x;
+ }
+ if (y != pGlint->starty) {
+ GLINT_WRITE_REG(y<<16,StartY);
+ pGlint->starty = y;
+ }
+ if (h != pGlint->count) {
+ GLINT_WRITE_REG(h,GLINTCount);
+ pGlint->count = h;
+ }
+ if (a != pGlint->dxdom) {
+ GLINT_WRITE_REG(a<<16,dXDom);
+ pGlint->dxdom = a;
+ }
+ if (d != pGlint->dy) {
+ GLINT_WRITE_REG(d<<16,dY);
+ pGlint->dy = d;
+ }
+}
+
+static void
+SXSync(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 readValue;
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+ } while (readValue != Sync_tag);
+}
+
+static void
+SXSetupForFillRectSolid(
+ ScrnInfoPtr pScrn,
+ int color, int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ pGlint->ForeGroundColor = color;
+
+ GLINT_WAIT(6);
+ REPLICATE(color);
+ DO_PLANEMASK(planemask);
+ if (pScrn->bitsPerPixel >= 24) {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, ConstantColor);
+ pGlint->FrameBufferReadMode = 0;
+ } else
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, FBBlockColor);
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(color, ConstantColor);
+ pGlint->FrameBufferReadMode = 0;
+ }
+ LOADROP(rop);
+}
+
+static void
+SXSubsequentFillRectSolid(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(8);
+ SXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | pGlint->FrameBufferReadMode,Render);
+}
+
+static void
+SXSetClippingRectangle(
+ ScrnInfoPtr pScrn,
+ int x1, int y1,
+ int x2, int y2
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(5);
+ GLINT_WRITE_REG((y1&0xFFFF)<<16|(x1&0xFFFF), ScissorMinXY);
+ GLINT_WRITE_REG((y2&0xFFFF)<<16|(x2&0xFFFF), ScissorMaxXY);
+ GLINT_WRITE_REG(1, ScissorMode); /* Enable Scissor Mode */
+ pGlint->ClippingOn = TRUE;
+}
+
+static void
+SXDisableClipping(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CHECKCLIPPING;
+}
+
+static void
+SXSetupForScreenToScreenCopy(
+ ScrnInfoPtr pScrn,
+ int xdir, int ydir,
+ int rop,
+ unsigned int planemask,
+ int transparency_color
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->BltScanDirection = ydir;
+
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_SrcEnable, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_SrcEnable | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+SXSubsequentScreenToScreenCopy(
+ ScrnInfoPtr pScrn,
+ int x1, int y1,
+ int x2, int y2,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int srcaddr, dstaddr;
+
+ GLINT_WAIT(10);
+
+ srcaddr = y1 * pScrn->displayWidth + x1;
+ dstaddr = y2 * pScrn->displayWidth + x2;
+ GLINT_WRITE_REG(srcaddr - dstaddr, FBSourceOffset);
+
+ if (pGlint->BltScanDirection != 1) {
+ y1 += h - 1;
+ y2 += h - 1;
+ SXLoadCoord(pScrn, x2, y2, x2+w, h, 0, -1);
+ } else {
+ SXLoadCoord(pScrn, x2, y2, x2+w, h, 0, 1);
+ }
+
+ GLINT_WRITE_REG(PrimitiveTrapezoid, Render);
+}
+
+#if 0
+static void
+SXSetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ REPLICATE(fg);
+ REPLICATE(bg);
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, PatternRamMode);
+ pGlint->FrameBufferReadMode = FastFillEnable | SpanOperation;
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ LOADROP(rop);
+}
+
+static void
+SXSubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ int skipleft
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->dwords = ((w + 31) >> 5); /* dwords per scanline */
+
+ pGlint->cpucount = h;
+
+ GLINT_WAIT(8);
+ SXLoadCoord(pScrn, x, y, x+w, 1, 0, 1);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | pGlint->FrameBufferReadMode | SyncOnBitMask,
+ Render);
+#if defined(__alpha__)
+ if (0) /* force Alpha to use indirect always */
+#else
+ if ((pGlint->dwords*h) < pGlint->FIFOSize)
+#endif
+ {
+ /* Turn on direct for less than FIFOSize dword colour expansion */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->IOBase+OutputFIFO+4;
+ pGlint->ScanlineDirect = 1;
+ GLINT_WRITE_REG(((pGlint->dwords*h)-1)<<16 | 0x0D, OutputFIFO);
+ GLINT_WAIT(pGlint->dwords*h);
+ } else {
+ /* Use indirect for anything else */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->ScratchBuffer;
+ pGlint->ScanlineDirect = 0;
+ }
+
+ pGlint->cpucount--;
+}
+
+static void
+SXSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 *srcp = (CARD32*)pGlint->XAAScanlineColorExpandBuffers[bufno];
+ int dwords = pGlint->dwords;
+
+ if (!pGlint->ScanlineDirect) {
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ dwords -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords - 1) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, dwords);
+ }
+ }
+}
+#endif
+
+void SXSetupForMono8x8PatternFill(
+ ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (bg == -1) pGlint->FrameBufferReadMode = -1;
+ else pGlint->FrameBufferReadMode = 0;
+ pGlint->ForeGroundColor = fg;
+ pGlint->BackGroundColor = bg;
+ REPLICATE(pGlint->ForeGroundColor);
+ REPLICATE(pGlint->BackGroundColor);
+
+ GLINT_WAIT(13);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG((patternx & 0x000000FF), AreaStipplePattern0);
+ GLINT_WRITE_REG((patternx & 0x0000FF00) >> 8, AreaStipplePattern1);
+ GLINT_WRITE_REG((patternx & 0x00FF0000) >> 16, AreaStipplePattern2);
+ GLINT_WRITE_REG((patternx & 0xFF000000) >> 24, AreaStipplePattern3);
+ GLINT_WRITE_REG((patterny & 0x000000FF), AreaStipplePattern4);
+ GLINT_WRITE_REG((patterny & 0x0000FF00) >> 8, AreaStipplePattern5);
+ GLINT_WRITE_REG((patterny & 0x00FF0000) >> 16, AreaStipplePattern6);
+ GLINT_WRITE_REG((patterny & 0xFF000000) >> 24, AreaStipplePattern7);
+
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ if (rop == GXcopy)
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ else
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ LOADROP(rop);
+}
+
+static void
+SXSubsequentMono8x8PatternFillRect(
+ ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int x, int y,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(12);
+ SXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+
+ if (pGlint->FrameBufferReadMode != -1) {
+ GLINT_WRITE_REG(pGlint->BackGroundColor, ConstantColor);
+ GLINT_WRITE_REG(2<<1|2<<4|patternx<<7|patterny<<12|ASM_InvertPattern |
+ UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | PrimitiveTrapezoid, Render);
+ }
+
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, ConstantColor);
+ GLINT_WRITE_REG(2<<1|2<<4|patternx<<7|patterny<<12|
+ UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | PrimitiveTrapezoid, Render);
+}
+
+#if 0
+static void
+SXWriteBitmap(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int skipleft,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char *srcpntr;
+ int dwords, height, mode;
+ Bool SecondPass = FALSE;
+ register int count;
+ register CARD32* pattern;
+
+ w += skipleft;
+ x -= skipleft;
+ dwords = (w + 31) >> 5;
+
+ SXSetClippingRectangle(pScrn,x+skipleft, y, x+w, y+h);
+
+ GLINT_WAIT(11);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ LOADROP(rop);
+ if (rop == GXcopy) {
+ mode = FastFillEnable;
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ mode = 0;
+ GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ SXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+
+ if(bg == -1) {
+ REPLICATE(fg);
+ GLINT_WAIT(3);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ } else if(rop == GXcopy) {
+ REPLICATE(bg);
+ GLINT_WAIT(5);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(bg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(bg, PatternRamData0);
+ }
+ GLINT_WRITE_REG(PrimitiveTrapezoid |mode|FastFillEnable,Render);
+ REPLICATE(fg);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ } else {
+ SecondPass = TRUE;
+ REPLICATE(fg);
+ GLINT_WAIT(3);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ }
+
+SECOND_PASS:
+ GLINT_WRITE_REG(PrimitiveTrapezoid | FastFillEnable | mode | SyncOnBitMask, Render);
+
+ height = h;
+ srcpntr = src;
+ while(height--) {
+ count = dwords >> 3;
+ pattern = (CARD32*)srcpntr;
+ while(count--) {
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG(*(pattern), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+1), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+2), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+3), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+4), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+5), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+6), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+7), BitMaskPattern);
+ pattern+=8;
+ }
+ count = dwords & 0x07;
+ GLINT_WAIT(count);
+ while (count--)
+ GLINT_WRITE_REG(*(pattern++), BitMaskPattern);
+ srcpntr += srcwidth;
+ }
+
+ if(SecondPass) {
+ SecondPass = FALSE;
+ REPLICATE(bg);
+ GLINT_WAIT(4);
+ GLINT_WRITE_REG(InvertBitMask, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(bg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(bg, PatternRamData0);
+ }
+ goto SECOND_PASS;
+ }
+
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(0, RasterizerMode);
+ CHECKCLIPPING;
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+SXWritePixmap(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth, /* bytes */
+ int rop,
+ unsigned int planemask,
+ int trans,
+ int bpp, int depth
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 *srcp;
+ int count,dwords, skipleft, Bpp = bpp >> 3;
+
+ if((skipleft = (long)src & 0x03L)) {
+ skipleft /= Bpp;
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+
+ switch(Bpp) {
+ case 1: dwords = (w + 3) >> 2;
+ break;
+ case 2: dwords = (w + 1) >> 1;
+ break;
+ case 4: dwords = w;
+ break;
+ default: return;
+ }
+
+ SXSetClippingRectangle(pScrn,x+skipleft, y, x+w, y+h);
+
+ GLINT_WAIT(12);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+ SXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | SyncOnHostData, Render);
+
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x0f << 4) | 0x0e is the TAG for GLINTColor */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) | (0x0F << 4) |
+ 0x0E, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, infoRec->ColorExpandRange - 1);
+ count -= infoRec->ColorExpandRange - 1;
+ srcp += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count);
+ /* (0x0F << 4) | 0x0E is the TAG for GLINTColor */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x0f << 4) |
+ 0x0e, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+ CHECKCLIPPING;
+ SET_SYNC_FLAG(infoRec);
+}
+#endif
+
+static void
+SXPolylinesThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int mode,
+ int npt,
+ DDXPointPtr pPts
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolyLines(pDraw, pGC, mode, npt, pPts);
+}
+
+static void
+SXPolySegmentThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int nseg,
+ xSegment *pSeg
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolySegment(pDraw, pGC, nseg, pSeg);
+}
+
+static void
+SXSetupForSolidLine(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(7);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(color, GLINTColor);
+ GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+SXSubsequentHorVertLine(ScrnInfoPtr pScrn,int x,int y,int len,int dir)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(9);
+ if (dir == DEGREES_0) {
+ SXLoadCoord(pScrn, x, y, 0, len, 1, 0);
+ } else {
+ SXLoadCoord(pScrn, x, y, 0, len, 0, 1);
+ }
+
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+}
+
+static void
+SXSubsequentSolidBresenhamLine( ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e, int len, int octant)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int dxdom, dy;
+
+ if(dmaj == dmin) {
+ GLINT_WAIT(9);
+ if(octant & YDECREASING) {
+ dy = -1;
+ } else {
+ dy = 1;
+ }
+
+ if(octant & XDECREASING) {
+ dxdom = -1;
+ } else {
+ dxdom = 1;
+ }
+
+ SXLoadCoord(pScrn, x, y, 0, len, dxdom, dy);
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+ return;
+ }
+
+ fbBres(pGlint->CurrentDrawable, pGlint->CurrentGC, 0,
+ (octant & XDECREASING) ? -1 : 1,
+ (octant & YDECREASING) ? -1 : 1,
+ (octant & YMAJOR) ? Y_AXIS : X_AXIS,
+ x, y, dmin + e, dmin, -dmaj, len);
+}
diff --git a/src/tx_accel.c b/src/tx_accel.c
new file mode 100644
index 0000000..9e30ec3
--- /dev/null
+++ b/src/tx_accel.c
@@ -0,0 +1,961 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane, Wigan, England.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ *
+ * GLINT 500TX / MX accelerated options.
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/tx_accel.c,v 1.28 2001/05/30 10:07:56 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "fb.h"
+
+#include "miline.h"
+
+#include "glint_regs.h"
+#include "glint.h"
+
+#include "xaalocal.h" /* For replacements */
+
+static void TXSync(ScrnInfoPtr pScrn);
+static void DualTXSync(ScrnInfoPtr pScrn);
+static void TXSetupForFillRectSolid(ScrnInfoPtr pScrn, int color, int rop,
+ unsigned int planemask);
+static void TXSubsequentFillRectSolid(ScrnInfoPtr pScrn, int x, int y,
+ int w, int h);
+static void TXSetupForMono8x8PatternFill(ScrnInfoPtr pScrn, int patternx,
+ int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask);
+static void TXSubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn, int patternx,
+ int patterny, int x, int y,
+ int w, int h);
+static void TXSetupForScreenToScreenCopy(ScrnInfoPtr pScrn, int xdir, int ydir,
+ int rop, unsigned int planemask,
+ int transparency_color);
+static void TXSubsequentScreenToScreenCopy(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2, int y2, int w, int h);
+static void TXWriteBitmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth,
+ int skipleft, int fg, int bg, int rop,
+ unsigned int planemask);
+static void TXSetClippingRectangle(ScrnInfoPtr pScrn, int x1, int y1,
+ int x2,int y2);
+static void TXDisableClipping(ScrnInfoPtr pScrn);
+static void TXWritePixmap(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ unsigned char *src, int srcwidth, int rop,
+ unsigned int planemask, int trans,
+ int bpp, int depth);
+static void TXSetupForScanlineCPUToScreenColorExpandFill(ScrnInfoPtr pScrn, int fg,
+ int bg, int rop, unsigned int planemask);
+static void TXSubsequentScanlineCPUToScreenColorExpandFill(ScrnInfoPtr pScrn, int x,
+ int y, int w, int h, int skipleft);
+static void TXSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno);
+static void TXLoadCoord(ScrnInfoPtr pScrn, int x, int y, int w, int h,
+ int a, int d);
+static void TXSetupForSolidLine(ScrnInfoPtr pScrn, int color, int rop,
+ unsigned int planemask);
+static void TXSubsequentHorVertLine(ScrnInfoPtr pScrn, int x1, int y1,
+ int len, int dir);
+static void TXSubsequentSolidBresenhamLine(ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e,
+ int len, int octant);
+static void TXPolylinesThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int mode, int npt, DDXPointPtr pPts);
+static void TXPolySegmentThinSolidWrapper(DrawablePtr pDraw, GCPtr pGC,
+ int nseg, xSegment *pSeg);
+
+void
+TXInitializeEngine(ScrnInfoPtr pScrn)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ /* Initialize the Accelerator Engine to defaults */
+ pGlint->rasterizerMode = UNIT_DISABLE;
+
+ if (pGlint->MultiAperture) {
+ pGlint->rasterizerMode = RMMultiGLINT;
+
+ /* Only write the following register to the first chip */
+ GLINT_SLOW_WRITE_REG(1, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(0x00000001, ScanLineOwnership);
+
+ /* Only write the following register to the second chip */
+ GLINT_SLOW_WRITE_REG(2, BroadcastMask);
+ GLINT_SLOW_WRITE_REG(0x00000005, ScanLineOwnership);
+
+ /* Make sure the rest of the register writes go to both chip's */
+ GLINT_SLOW_WRITE_REG(3, BroadcastMask);
+
+ pGlint->pprod |= FBRM_ScanlineInt2;
+ }
+
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, LBReadMode);
+ GLINT_SLOW_WRITE_REG(pGlint->rasterizerMode, RasterizerMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
+ GLINT_SLOW_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_SLOW_WRITE_REG(0, dXSub);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWriteMode);
+ GLINT_SLOW_WRITE_REG(UNIT_ENABLE, FBWriteMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DitherMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureColorMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureReadMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTWindow);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FogMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AntialiasMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaTestMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LineStippleMode);
+ GLINT_SLOW_WRITE_REG(0, UpdateLineStippleCounters);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
+ GLINT_SLOW_WRITE_REG(0x400, FilterMode);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBHardwareWriteMask);
+ GLINT_SLOW_WRITE_REG(0xffffffff, FBSoftwareWriteMask);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTDepth);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBPixelOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBSourceOffset);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, WindowOrigin);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBWindowBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWindowBase);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
+ GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ GLINT_SLOW_WRITE_REG(0x2, PixelSize);
+ break;
+ case 16:
+ GLINT_SLOW_WRITE_REG(0x1, PixelSize);
+ break;
+ case 32:
+ GLINT_SLOW_WRITE_REG(0x0, PixelSize);
+ break;
+ }
+ pGlint->ROP = 0xFF;
+ pGlint->ClippingOn = FALSE;
+ pGlint->startxsub = 0;
+ pGlint->startxdom = 0;
+ pGlint->starty = 0;
+ pGlint->count = 0;
+ pGlint->dxdom = 0;
+ pGlint->dy = 1;
+ pGlint->planemask = 0;
+ GLINT_SLOW_WRITE_REG(0, StartXSub);
+ GLINT_SLOW_WRITE_REG(0, StartXDom);
+ GLINT_SLOW_WRITE_REG(0, StartY);
+ GLINT_SLOW_WRITE_REG(0, GLINTCount);
+ GLINT_SLOW_WRITE_REG(0, dXDom);
+ GLINT_SLOW_WRITE_REG(1<<16, dY);
+}
+
+Bool
+TXAccelInit(ScreenPtr pScreen)
+{
+ XAAInfoRecPtr infoPtr;
+ ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ long memory = pGlint->FbMapSize;
+ BoxRec AvailFBArea;
+
+ pGlint->AccelInfoRec = infoPtr = XAACreateInfoRec();
+ if (!infoPtr) return FALSE;
+
+ TXInitializeEngine(pScrn);
+
+ infoPtr->Flags = PIXMAP_CACHE |
+ LINEAR_FRAMEBUFFER |
+ OFFSCREEN_PIXMAPS;
+
+ if (pGlint->MultiAperture)
+ infoPtr->Sync = DualTXSync;
+ else
+ infoPtr->Sync = TXSync;
+
+ infoPtr->SetClippingRectangle = TXSetClippingRectangle;
+ infoPtr->DisableClipping = TXDisableClipping;
+ infoPtr->ClippingFlags = HARDWARE_CLIP_MONO_8x8_FILL |
+ HARDWARE_CLIP_SCREEN_TO_SCREEN_COPY |
+ HARDWARE_CLIP_SOLID_FILL;
+
+ infoPtr->SolidFillFlags = 0;
+ infoPtr->SetupForSolidFill = TXSetupForFillRectSolid;
+ infoPtr->SubsequentSolidFillRect = TXSubsequentFillRectSolid;
+
+ infoPtr->SolidLineFlags = 0;
+ infoPtr->PolySegmentThinSolidFlags = 0;
+ infoPtr->PolylinesThinSolidFlags = 0;
+ infoPtr->SetupForSolidLine = TXSetupForSolidLine;
+ infoPtr->SubsequentSolidHorVertLine = TXSubsequentHorVertLine;
+ if (!(pScrn->overlayFlags & OVERLAY_8_32_PLANAR))
+ {
+ infoPtr->SubsequentSolidBresenhamLine =
+ TXSubsequentSolidBresenhamLine;
+ }
+ infoPtr->PolySegmentThinSolid = TXPolySegmentThinSolidWrapper;
+ infoPtr->PolylinesThinSolid = TXPolylinesThinSolidWrapper;
+
+ if (!pGlint->MultiAperture) {
+ infoPtr->ScreenToScreenCopyFlags = NO_TRANSPARENCY |
+ ONLY_LEFT_TO_RIGHT_BITBLT;
+ infoPtr->SetupForScreenToScreenCopy = TXSetupForScreenToScreenCopy;
+ infoPtr->SubsequentScreenToScreenCopy = TXSubsequentScreenToScreenCopy;
+ }
+
+ infoPtr->Mono8x8PatternFillFlags = HARDWARE_PATTERN_PROGRAMMED_ORIGIN |
+ HARDWARE_PATTERN_SCREEN_ORIGIN |
+ HARDWARE_PATTERN_PROGRAMMED_BITS;
+ infoPtr->SetupForMono8x8PatternFill = TXSetupForMono8x8PatternFill;
+ infoPtr->SubsequentMono8x8PatternFillRect = TXSubsequentMono8x8PatternFillRect;
+
+ infoPtr->ScanlineCPUToScreenColorExpandFillFlags =
+ TRANSPARENCY_ONLY |
+ BIT_ORDER_IN_BYTE_LSBFIRST;
+
+ infoPtr->NumScanlineColorExpandBuffers = 1;
+ pGlint->ScratchBuffer = xalloc(((pScrn->virtualX+62)/32*4)
+ + (pScrn->virtualX
+ * pScrn->bitsPerPixel / 8));
+ infoPtr->ScanlineColorExpandBuffers =
+ pGlint->XAAScanlineColorExpandBuffers;
+ pGlint->XAAScanlineColorExpandBuffers[0] =
+ pGlint->IOBase + OutputFIFO + 4;
+
+ infoPtr->SetupForScanlineCPUToScreenColorExpandFill =
+ TXSetupForScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentScanlineCPUToScreenColorExpandFill =
+ TXSubsequentScanlineCPUToScreenColorExpandFill;
+ infoPtr->SubsequentColorExpandScanline =
+ TXSubsequentColorExpandScanline;
+
+ infoPtr->ColorExpandRange = pGlint->FIFOSize;
+
+ infoPtr->WriteBitmap = TXWriteBitmap;
+ infoPtr->WritePixmap = TXWritePixmap;
+
+ AvailFBArea.x1 = 0;
+ AvailFBArea.y1 = 0;
+ AvailFBArea.x2 = pScrn->displayWidth;
+ if (memory > (16383*1024)) memory = 16383*1024;
+ AvailFBArea.y2 = memory / (pScrn->displayWidth *
+ pScrn->bitsPerPixel / 8);
+
+ if (AvailFBArea.y2 > 4095) AvailFBArea.y2 = 4095;
+
+ xf86InitFBManager(pScreen, &AvailFBArea);
+
+ return (XAAInit(pScreen, infoPtr));
+}
+
+static void TXLoadCoord(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h,
+ int a, int d
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+#ifndef XF86DRI
+ if (w != pGlint->startxsub) {
+ GLINT_WRITE_REG(w<<16, StartXSub);
+ pGlint->startxsub = w;
+ }
+ if (x != pGlint->startxdom) {
+ GLINT_WRITE_REG(x<<16,StartXDom);
+ pGlint->startxdom = x;
+ }
+ if (y != pGlint->starty) {
+ GLINT_WRITE_REG(y<<16,StartY);
+ pGlint->starty = y;
+ }
+ if (h != pGlint->count) {
+ GLINT_WRITE_REG(h,GLINTCount);
+ pGlint->count = h;
+ }
+ if (a != pGlint->dxdom) {
+ GLINT_WRITE_REG(a<<16,dXDom);
+ pGlint->dxdom = a;
+ }
+ if (d != pGlint->dy) {
+ GLINT_WRITE_REG(d<<16,dY);
+ pGlint->dy = d;
+ }
+#else
+ GLINT_WRITE_REG(w<<16, StartXSub);
+ GLINT_WRITE_REG(x<<16,StartXDom);
+ GLINT_WRITE_REG(y<<16,StartY);
+ GLINT_WRITE_REG(h,GLINTCount);
+ GLINT_WRITE_REG(a<<16,dXDom);
+ GLINT_WRITE_REG(d<<16,dY);
+ pGlint->startxsub = w;
+ pGlint->startxdom = x;
+ pGlint->starty = y;
+ pGlint->count = h;
+ pGlint->dxdom = a;
+ pGlint->dy = d;
+#endif
+}
+
+static void
+TXSync(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 readValue;
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+ } while (readValue != Sync_tag);
+}
+
+static void
+DualTXSync(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned long readValue;
+
+ CHECKCLIPPING;
+
+ while (GLINT_READ_REG(DMACount) != 0);
+ GLINT_WAIT(3);
+
+ /* hack! this shouldn't need to be reloaded */
+ GLINT_WRITE_REG(3, BroadcastMask);
+ GLINT_WRITE_REG(0x400, FilterMode);
+ GLINT_WRITE_REG(0, GlintSync);
+
+ /* Read 1st MX until Sync Tag shows */
+ ACCESSCHIP1();
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+ } while (readValue != Sync_tag);
+
+ ACCESSCHIP2();
+ /* Read 2nd MX until Sync Tag shows */
+ do {
+ while(GLINT_READ_REG(OutFIFOWords) == 0);
+ readValue = GLINT_READ_REG(OutputFIFO);
+ } while (readValue != Sync_tag);
+
+ ACCESSCHIP1();
+}
+
+
+static void
+TXSetupForFillRectSolid(
+ ScrnInfoPtr pScrn,
+ int color, int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ pGlint->ForeGroundColor = color;
+
+ GLINT_WAIT(5);
+ REPLICATE(color);
+ DO_PLANEMASK(planemask);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+ GLINT_WRITE_REG(color, FBBlockColor);
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, PatternRamMode);
+ GLINT_WRITE_REG(color, PatternRamData0);
+ pGlint->FrameBufferReadMode = FastFillEnable | SpanOperation;
+ }
+ LOADROP(rop);
+}
+
+static void
+TXSubsequentFillRectSolid(
+ ScrnInfoPtr pScrn,
+ int x, int y,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(7);
+ TXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | pGlint->FrameBufferReadMode,Render);
+}
+
+static void
+TXSetClippingRectangle(
+ ScrnInfoPtr pScrn,
+ int x1, int y1,
+ int x2, int y2
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(3);
+ GLINT_WRITE_REG((y1&0xFFFF)<<16|(x1&0xFFFF), ScissorMinXY);
+ GLINT_WRITE_REG((y2&0xFFFF)<<16|(x2&0xFFFF), ScissorMaxXY);
+ GLINT_WRITE_REG(1, ScissorMode); /* Enable Scissor Mode */
+ pGlint->ClippingOn = TRUE;
+}
+
+static void
+TXDisableClipping(
+ ScrnInfoPtr pScrn
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CHECKCLIPPING;
+}
+
+static void
+TXSetupForScreenToScreenCopy(
+ ScrnInfoPtr pScrn,
+ int xdir, int ydir,
+ int rop,
+ unsigned int planemask,
+ int transparency_color
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->BltScanDirection = ydir;
+
+ GLINT_WAIT(5);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_SrcEnable, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_SrcEnable | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+TXSubsequentScreenToScreenCopy(
+ ScrnInfoPtr pScrn,
+ int x1, int y1,
+ int x2, int y2,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int srcaddr, dstaddr;
+
+ GLINT_WAIT(8);
+ if (pGlint->BltScanDirection != 1) {
+ y1 += h - 1;
+ y2 += h - 1;
+ TXLoadCoord(pScrn, x2, y2, x2+w, h, 0, -1);
+ } else {
+ TXLoadCoord(pScrn, x2, y2, x2+w, h, 0, 1);
+ }
+
+ srcaddr = y1 * pScrn->displayWidth + x1;
+ dstaddr = y2 * pScrn->displayWidth + x2;
+
+ GLINT_WRITE_REG(srcaddr - dstaddr, FBSourceOffset);
+ GLINT_WRITE_REG(PrimitiveTrapezoid| FastFillEnable | SpanOperation, Render);
+}
+
+static void
+TXSetupForScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ REPLICATE(fg);
+ REPLICATE(bg);
+ GLINT_WAIT(6);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->rasterizerMode, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ GLINT_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+ pGlint->FrameBufferReadMode = FastFillEnable;
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ GLINT_WRITE_REG(UNIT_ENABLE, PatternRamMode);
+ pGlint->FrameBufferReadMode = FastFillEnable | SpanOperation;
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ LOADROP(rop);
+}
+
+static void
+TXSubsequentScanlineCPUToScreenColorExpandFill(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ int skipleft
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ pGlint->dwords = ((w + 31) >> 5); /* dwords per scanline */
+
+ pGlint->cpucount = h;
+
+ GLINT_WAIT(8);
+ TXLoadCoord(pScrn, x, y, (x+w), h, 0, 1);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | pGlint->FrameBufferReadMode | SyncOnBitMask,
+ Render);
+#if defined(__alpha__)
+ if (0) /* force Alpha to use indirect always */
+#else
+ if ((pGlint->dwords*h) < pGlint->FIFOSize)
+#endif
+ {
+ /* Turn on direct for less than FIFOSize dword colour expansion */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->IOBase+OutputFIFO+4;
+ pGlint->ScanlineDirect = 1;
+ GLINT_WRITE_REG(((pGlint->dwords*h)-1)<<16 | 0x0D, OutputFIFO);
+ GLINT_WAIT(pGlint->dwords*h);
+ } else {
+ /* Use indirect for anything else */
+ pGlint->XAAScanlineColorExpandBuffers[0] = pGlint->ScratchBuffer;
+ pGlint->ScanlineDirect = 0;
+ }
+
+ pGlint->cpucount--;
+}
+
+static void
+TXSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 *srcp = (CARD32*)pGlint->XAAScanlineColorExpandBuffers[bufno];
+ int dwords = pGlint->dwords;
+
+ if (!pGlint->ScanlineDirect) {
+ while(dwords >= pGlint->FIFOSize) {
+ GLINT_WAIT(pGlint->FIFOSize);
+ GLINT_WRITE_REG(((pGlint->FIFOSize - 2) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, pGlint->FIFOSize - 1);
+ dwords -= pGlint->FIFOSize - 1;
+ srcp += pGlint->FIFOSize - 1;
+ }
+ if(dwords) {
+ GLINT_WAIT(dwords + 1);
+ GLINT_WRITE_REG(((dwords - 1) << 16) | 0x0D, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, dwords);
+ }
+ }
+}
+
+void TXSetupForMono8x8PatternFill(
+ ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int fg, int bg, int rop,
+ unsigned int planemask
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (bg == -1) pGlint->FrameBufferReadMode = -1;
+ else pGlint->FrameBufferReadMode = 0;
+ pGlint->ForeGroundColor = fg;
+ pGlint->BackGroundColor = bg;
+ REPLICATE(pGlint->ForeGroundColor);
+ REPLICATE(pGlint->BackGroundColor);
+
+ GLINT_WAIT(13);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG((patternx & 0x000000FF), AreaStipplePattern0);
+ GLINT_WRITE_REG((patternx & 0x0000FF00) >> 8, AreaStipplePattern1);
+ GLINT_WRITE_REG((patternx & 0x00FF0000) >> 16, AreaStipplePattern2);
+ GLINT_WRITE_REG((patternx & 0xFF000000) >> 24, AreaStipplePattern3);
+ GLINT_WRITE_REG((patterny & 0x000000FF), AreaStipplePattern4);
+ GLINT_WRITE_REG((patterny & 0x0000FF00) >> 8, AreaStipplePattern5);
+ GLINT_WRITE_REG((patterny & 0x00FF0000) >> 16, AreaStipplePattern6);
+ GLINT_WRITE_REG((patterny & 0xFF000000) >> 24, AreaStipplePattern7);
+
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(UNIT_ENABLE, PatternRamMode);
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+TXSubsequentMono8x8PatternFillRect(
+ ScrnInfoPtr pScrn,
+ int patternx, int patterny,
+ int x, int y,
+ int w, int h
+){
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int span = 0;
+
+ GLINT_WAIT(12);
+ TXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+
+ if (pGlint->FrameBufferReadMode != -1) {
+ if (pGlint->ROP == GXcopy) {
+ GLINT_WRITE_REG(pGlint->BackGroundColor, FBBlockColor);
+ span = 0;
+ } else {
+ GLINT_WRITE_REG(pGlint->BackGroundColor, PatternRamData0);
+ span = SpanOperation;
+ }
+ GLINT_WRITE_REG(2<<1|2<<4|patternx<<7|patterny<<12|ASM_InvertPattern |
+ UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | span | FastFillEnable |
+ PrimitiveTrapezoid, Render);
+ }
+
+ if (pGlint->ROP == GXcopy) {
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, FBBlockColor);
+ span = 0;
+ } else {
+ GLINT_WRITE_REG(pGlint->ForeGroundColor, PatternRamData0);
+ span = SpanOperation;
+ }
+ GLINT_WRITE_REG(2<<1|2<<4|patternx<<7|patterny<<12|
+ UNIT_ENABLE, AreaStippleMode);
+ GLINT_WRITE_REG(AreaStippleEnable | span | FastFillEnable |
+ PrimitiveTrapezoid, Render);
+}
+
+static void
+TXWriteBitmap(ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth,
+ int skipleft,
+ int fg, int bg,
+ int rop,
+ unsigned int planemask
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ unsigned char *srcpntr;
+ int dwords, height, mode;
+ Bool SecondPass = FALSE;
+ register int count;
+ register CARD32* pattern;
+
+ w += skipleft;
+ x -= skipleft;
+ dwords = (w + 31) >> 5;
+
+ TXSetClippingRectangle(pScrn,x+skipleft, y, x+w, y+h);
+
+ GLINT_WAIT(11);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(pGlint->rasterizerMode, RasterizerMode);
+ LOADROP(rop);
+ if (rop == GXcopy) {
+ mode = 0;
+ GLINT_WRITE_REG(UNIT_DISABLE, PatternRamMode);
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ mode = SpanOperation;
+ GLINT_WRITE_REG(UNIT_ENABLE, PatternRamMode);
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ TXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+
+ if(bg == -1) {
+ REPLICATE(fg);
+ GLINT_WAIT(3);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ } else if(rop == GXcopy) {
+ REPLICATE(bg);
+ GLINT_WAIT(5);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(bg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(bg, PatternRamData0);
+ }
+ GLINT_WRITE_REG(PrimitiveTrapezoid |mode|FastFillEnable,Render);
+ REPLICATE(fg);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ } else {
+ SecondPass = TRUE;
+ REPLICATE(fg);
+ GLINT_WAIT(3);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(fg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(fg, PatternRamData0);
+ }
+ }
+
+SECOND_PASS:
+ GLINT_WRITE_REG(PrimitiveTrapezoid | FastFillEnable | mode | SyncOnBitMask, Render);
+
+ height = h;
+ srcpntr = src;
+ while(height--) {
+ count = dwords >> 3;
+ pattern = (CARD32*)srcpntr;
+ while(count--) {
+ GLINT_WAIT(8);
+ GLINT_WRITE_REG(*(pattern), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+1), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+2), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+3), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+4), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+5), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+6), BitMaskPattern);
+ GLINT_WRITE_REG(*(pattern+7), BitMaskPattern);
+ pattern+=8;
+ }
+ count = dwords & 0x07;
+ GLINT_WAIT(count);
+ while (count--)
+ GLINT_WRITE_REG(*(pattern++), BitMaskPattern);
+ srcpntr += srcwidth;
+ }
+
+ if(SecondPass) {
+ SecondPass = FALSE;
+ REPLICATE(bg);
+ GLINT_WAIT(4);
+ GLINT_WRITE_REG(InvertBitMask | pGlint->rasterizerMode, RasterizerMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(bg, FBBlockColor);
+ } else {
+ GLINT_WRITE_REG(bg, PatternRamData0);
+ }
+ goto SECOND_PASS;
+ }
+
+ GLINT_WAIT(2);
+ GLINT_WRITE_REG(pGlint->rasterizerMode, RasterizerMode);
+ CHECKCLIPPING;
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+TXWritePixmap(
+ ScrnInfoPtr pScrn,
+ int x, int y, int w, int h,
+ unsigned char *src,
+ int srcwidth, /* bytes */
+ int rop,
+ unsigned int planemask,
+ int trans,
+ int bpp, int depth
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_SCRNINFOPTR(pScrn);
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ CARD32 *srcp;
+ int count,dwords, skipleft, Bpp = bpp >> 3;
+
+ if((skipleft = (long)src & 0x03L)) {
+ skipleft /= Bpp;
+
+ x -= skipleft;
+ w += skipleft;
+
+ src = (unsigned char*)((long)src & ~0x03L);
+ }
+
+ switch(Bpp) {
+ case 1: dwords = (w + 3) >> 2;
+ break;
+ case 2: dwords = (w + 1) >> 1;
+ break;
+ case 4: dwords = w;
+ break;
+ default: return;
+ }
+
+ TXSetClippingRectangle(pScrn,x+skipleft, y, x+w, y+h);
+
+ GLINT_WAIT(12);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(0, PatternRamMode);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+ TXLoadCoord(pScrn, x, y, x+w, h, 0, 1);
+ GLINT_WRITE_REG(PrimitiveTrapezoid | FastFillEnable | SpanOperation |
+ SyncOnHostData, Render);
+
+ while(h--) {
+ count = dwords;
+ srcp = (CARD32*)src;
+ while(count >= infoRec->ColorExpandRange) {
+ GLINT_WAIT(infoRec->ColorExpandRange);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((infoRec->ColorExpandRange - 2) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, infoRec->ColorExpandRange - 1);
+ count -= infoRec->ColorExpandRange - 1;
+ srcp += infoRec->ColorExpandRange - 1;
+ }
+ if(count) {
+ GLINT_WAIT(count);
+ /* (0x15 << 4) | 0x05 is the TAG for FBSourceData */
+ GLINT_WRITE_REG(((count - 1) << 16) | (0x15 << 4) |
+ 0x05, OutputFIFO);
+ GLINT_MoveDWORDS(
+ (CARD32*)((char*)pGlint->IOBase + OutputFIFO + 4),
+ (CARD32*)srcp, count);
+ }
+ src += srcwidth;
+ }
+ CHECKCLIPPING;
+ SET_SYNC_FLAG(infoRec);
+}
+
+static void
+TXPolylinesThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int mode,
+ int npt,
+ DDXPointPtr pPts
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolyLines(pDraw, pGC, mode, npt, pPts);
+}
+
+static void
+TXPolySegmentThinSolidWrapper(
+ DrawablePtr pDraw,
+ GCPtr pGC,
+ int nseg,
+ xSegment *pSeg
+){
+ XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
+ GLINTPtr pGlint = GLINTPTR(infoRec->pScrn);
+ pGlint->CurrentGC = pGC;
+ pGlint->CurrentDrawable = pDraw;
+ if(infoRec->NeedToSync) (*infoRec->Sync)(infoRec->pScrn);
+ XAAPolySegment(pDraw, pGC, nseg, pSeg);
+}
+
+static void
+TXSetupForSolidLine(ScrnInfoPtr pScrn, int color,
+ int rop, unsigned int planemask)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(5);
+ DO_PLANEMASK(planemask);
+ GLINT_WRITE_REG(color, GLINTColor);
+ if (rop == GXcopy) {
+ GLINT_WRITE_REG(pGlint->pprod, FBReadMode);
+ } else {
+ GLINT_WRITE_REG(pGlint->pprod | FBRM_DstEnable, FBReadMode);
+ }
+ LOADROP(rop);
+}
+
+static void
+TXSubsequentHorVertLine(ScrnInfoPtr pScrn,int x,int y,int len,int dir)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ GLINT_WAIT(7);
+ if (dir == DEGREES_0) {
+ TXLoadCoord(pScrn, x, y, 0, len, 1, 0);
+ } else {
+ TXLoadCoord(pScrn, x, y, 0, len, 0, 1);
+ }
+
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+}
+
+static void
+TXSubsequentSolidBresenhamLine( ScrnInfoPtr pScrn,
+ int x, int y, int dmaj, int dmin, int e, int len, int octant)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ int dxdom, dy;
+
+ if(dmaj == dmin) {
+ GLINT_WAIT(7);
+ if(octant & YDECREASING) {
+ dy = -1;
+ } else {
+ dy = 1;
+ }
+
+ if(octant & XDECREASING) {
+ dxdom = -1;
+ } else {
+ dxdom = 1;
+ }
+
+ TXLoadCoord(pScrn, x, y, 0, len, dxdom, dy);
+ GLINT_WRITE_REG(PrimitiveLine, Render);
+ return;
+ }
+
+ fbBres(pGlint->CurrentDrawable, pGlint->CurrentGC, 0,
+ (octant & XDECREASING) ? -1 : 1,
+ (octant & YDECREASING) ? -1 : 1,
+ (octant & YMAJOR) ? Y_AXIS : X_AXIS,
+ x, y, dmin + e, dmin, -dmaj, len);
+}
diff --git a/src/tx_dac.c b/src/tx_dac.c
new file mode 100644
index 0000000..8924e96
--- /dev/null
+++ b/src/tx_dac.c
@@ -0,0 +1,397 @@
+/*
+ * Copyright 1997-2001 by Alan Hourihane <alanh@fairlite.demon.co.uk>
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of Alan Hourihane not be used in
+ * advertising or publicity pertaining to distribution of the software without
+ * specific, written prior permission. Alan Hourihane makes no representations
+ * about the suitability of this software for any purpose. It is provided
+ * "as is" without express or implied warranty.
+ *
+ * ALAN HOURIHANE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL ALAN HOURIHANE BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Alan Hourihane, <alanh@fairlite.demon.co.uk>
+ * Dirk Hohndel, <hohndel@suse.de>
+ * Stefan Dirsch, <sndirsch@suse.de>
+ * Helmut Fahrion, <hf@suse.de>
+ *
+ * this work is sponsored by S.u.S.E. GmbH, Fuerth, Elsa GmbH, Aachen and
+ * Siemens Nixdorf Informationssysteme
+ */
+/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/glint/tx_dac.c,v 1.15 2001/05/29 11:23:38 alanh Exp $ */
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86_ansic.h"
+
+#include "xf86PciInfo.h"
+#include "xf86Pci.h"
+
+#include "IBM.h"
+#include "TI.h"
+#include "glint_regs.h"
+#include "glint.h"
+
+Bool
+TXInit(ScrnInfoPtr pScrn, DisplayModePtr mode, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+ RamDacHWRecPtr pRamDac = RAMDACHWPTR(pScrn);
+ RamDacRegRecPtr ramdacReg = &pRamDac->ModeReg;
+ CARD32 temp1, temp2, temp3, temp4;
+
+ if (pGlint->numMultiDevices == 2) {
+ STOREREG(GCSRAperture, GCSRSecondaryGLINTMapEn);
+ }
+
+ if (pGlint->MultiAperture) {
+ /*
+ * Setup HW
+ *
+ * Note: The order of discovery for the MX devices is dependent
+ * on which way the resource allocation code decides to scan the
+ * bus. This setup assumes the first MX found owns the even
+ * scanlines. Should the implementation change an scan the bus
+ * in the opposite direction, then simple invert the indices for
+ * MultiPciInfo below. If this is setup wrong, the bug will appear
+ * as incorrect scanline interleaving when software rendering.
+ */
+ STOREREG(GMultGLINTAperture, pGlint->realWidth);
+ STOREREG(GMultGLINT1,
+ pGlint->MultiPciInfo[0]->memBase[2] & 0xFF800000);
+ STOREREG(GMultGLINT2,
+ pGlint->MultiPciInfo[1]->memBase[2] & 0xFF800000);
+ }
+
+ if (IS_GMX2000 || IS_GLORIAXXL) {
+ pReg->glintRegs[LBMemoryEDO >> 3] = GLINT_READ_REG(LBMemoryEDO);
+ pReg->glintRegs[LBMemoryEDO >> 3] &= ~(LBEDOMask |
+ LBEDOBankSizeMask |
+ LBTwoPageDetectorMask);
+ pReg->glintRegs[LBMemoryEDO >> 3] |= (LBEDOEnabled |
+ LBEDOBankSize4M |
+ LBTwoPageDetector);
+ pReg->glintRegs[LBMemoryCtl >> 3] = GLINT_READ_REG(LBMemoryCtl);
+ pReg->glintRegs[LBMemoryCtl >> 3] &= ~(LBNumBanksMask |
+ LBPageSizeMask |
+ LBRASCASLowMask |
+ LBRASPrechargeMask |
+ LBCASLowMask |
+ LBPageModeMask |
+ LBRefreshCountMask);
+ pReg->glintRegs[LBMemoryCtl >> 3] |= (LBNumBanks2 |
+ LBPageSize1024 |
+ LBRASCASLow2 |
+ LBRASPrecharge2 |
+ LBCASLow1 |
+ LBPageModeEnabled |
+ (0x20 << LBRefreshCountShift));
+ }
+
+ STOREREG(Aperture0, 0);
+ STOREREG(Aperture1, 0);
+
+ STOREREG(DFIFODis, GLINT_READ_REG(DFIFODis) & 0xFFFFFFFE);
+ STOREREG(FIFODis, GLINT_READ_REG(FIFODis) | 0x01);
+
+ temp1 = mode->CrtcHSyncStart - mode->CrtcHDisplay;
+ temp2 = mode->CrtcVSyncStart - mode->CrtcVDisplay;
+ temp3 = mode->CrtcHSyncEnd - mode->CrtcHSyncStart;
+ temp4 = mode->CrtcVSyncEnd - mode->CrtcVSyncStart;
+
+ STOREREG(VTGHLimit, Shiftbpp(pScrn, mode->CrtcHTotal));
+ STOREREG(VTGHSyncEnd, Shiftbpp(pScrn, temp1 + temp3));
+ STOREREG(VTGHSyncStart, Shiftbpp(pScrn, temp1));
+ STOREREG(VTGHBlankEnd,
+ Shiftbpp(pScrn, mode->CrtcHTotal - mode->CrtcHDisplay));
+
+ STOREREG(VTGVLimit, mode->CrtcVTotal);
+ STOREREG(VTGVSyncEnd, temp2 + temp4);
+ STOREREG(VTGVSyncStart, temp2);
+ STOREREG(VTGVBlankEnd, mode->CrtcVTotal - mode->CrtcVDisplay);
+
+ if (IS_GMX2000) {
+ STOREREG(VTGPolarity, 0xba);
+ } else {
+ STOREREG(VTGPolarity, (((mode->Flags & V_PHSYNC ? 0:2)<<2) |
+ ((mode->Flags & V_PVSYNC) ? 0 : 2) | (0xb0)));
+ }
+
+ STOREREG(VClkCtl, 0);
+ STOREREG(VTGVGateStart, mode->CrtcVTotal - mode->CrtcVDisplay - 1);
+ STOREREG(VTGVGateEnd, mode->CrtcVTotal - mode->CrtcVDisplay);
+
+ /* This is ugly */
+ if (pGlint->UseFireGL3000) {
+ STOREREG(VTGSerialClk, 0x05);
+ STOREREG(VTGHGateStart,
+ Shiftbpp(pScrn, mode->CrtcHTotal - mode->CrtcHDisplay - 1));
+ STOREREG(VTGHGateEnd, Shiftbpp(pScrn, mode->CrtcHTotal) - 1);
+ STOREREG(FBModeSel, 0x907);
+ STOREREG(VTGModeCtl, 0x00);
+ } else
+ if (IS_GMX2000) {
+ STOREREG(VTGSerialClk, 0x02);
+ STOREREG(VTGHGateStart,
+ Shiftbpp(pScrn, mode->CrtcHTotal - mode->CrtcHDisplay - 1));
+ STOREREG(VTGHGateEnd, Shiftbpp(pScrn, mode->CrtcHTotal) - 1);
+ STOREREG(FBModeSel, 0x907);
+ STOREREG(VTGModeCtl, 0x04);
+ } else {
+ STOREREG(VTGSerialClk, 0x05);
+ STOREREG(VTGHGateStart,
+ Shiftbpp(pScrn, mode->CrtcHTotal - mode->CrtcHDisplay) - 2);
+ STOREREG(VTGHGateEnd, Shiftbpp(pScrn, mode->CrtcHTotal) - 2);
+ STOREREG(FBModeSel, 0x0A07);
+ STOREREG(VTGModeCtl, 0x44);
+ }
+
+ if (IS_GMX2000 || IS_GLORIAXXL) {
+ STOREREG(FBMemoryCtl, 0x800); /* Optimum memory timings */
+ } else {
+ STOREREG(FBMemoryCtl, GLINT_READ_REG(FBMemoryCtl));
+ }
+
+ /* Override FBModeSel for 300SX chip */
+ if ( (pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_300SX) ||
+ ((pGlint->Chipset == PCI_VENDOR_3DLABS_CHIP_DELTA) &&
+ (pGlint->MultiChip == PCI_CHIP_300SX)) ) {
+ switch (pScrn->bitsPerPixel) {
+ case 8:
+ STOREREG(FBModeSel, 0x905);
+ break;
+ case 16:
+ STOREREG(FBModeSel, 0x903);
+ break;
+ case 32:
+ STOREREG(FBModeSel, 0x901);
+ break;
+ }
+ }
+
+ switch (pGlint->RamDac->RamDacType) {
+ case IBM526DB_RAMDAC:
+ case IBM526_RAMDAC:
+ {
+ /* Get the programmable clock values */
+ unsigned long m=0,n=0,p=0,c=0;
+ unsigned long clock;
+
+ clock = IBMramdac526CalculateMNPCForClock(pGlint->RefClock, mode->Clock,
+ 1, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p, &c);
+
+ STORERAMDAC(IBMRGB_m0, m);
+ STORERAMDAC(IBMRGB_n0, n);
+ STORERAMDAC(IBMRGB_p0, p);
+ STORERAMDAC(IBMRGB_c0, c);
+
+ STORERAMDAC(IBMRGB_pll_ctrl1, 0x05);
+ STORERAMDAC(IBMRGB_pll_ctrl2, 0x00);
+
+ p = 1;
+ clock = IBMramdac526CalculateMNPCForClock(pGlint->RefClock, mode->Clock,
+ 0, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p, &c);
+
+ STORERAMDAC(IBMRGB_sysclk, 0x05);
+ STORERAMDAC(IBMRGB_sysclk_m, m);
+ STORERAMDAC(IBMRGB_sysclk_n, n);
+ STORERAMDAC(IBMRGB_sysclk_p, p);
+ STORERAMDAC(IBMRGB_sysclk_c, c);
+ }
+ STORERAMDAC(IBMRGB_misc1, SENS_DSAB_DISABLE | VRAM_SIZE_64);
+ STORERAMDAC(IBMRGB_misc2, COL_RES_8BIT | PORT_SEL_VRAM | PCLK_SEL_PLL);
+ STORERAMDAC(IBMRGB_misc3, 0);
+ STORERAMDAC(IBMRGB_misc_clock, 1);
+ STORERAMDAC(IBMRGB_sync, 0);
+ STORERAMDAC(IBMRGB_hsync_pos, 0);
+ STORERAMDAC(IBMRGB_pwr_mgmt, 0);
+ STORERAMDAC(IBMRGB_dac_op, 0);
+ STORERAMDAC(IBMRGB_pal_ctrl, 0);
+
+ break;
+ case IBM640_RAMDAC:
+ {
+ /* Get the programmable clock values */
+ unsigned long m=0,n=0,p=0,c=0;
+ unsigned long clock;
+
+ clock = IBMramdac640CalculateMNPCForClock(pGlint->RefClock, mode->Clock,
+ 1, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p, &c);
+
+ STORERAMDAC(RGB640_PLL_N, n);
+ STORERAMDAC(RGB640_PLL_M, m);
+ STORERAMDAC(RGB640_PLL_P, p<<1);
+ STORERAMDAC(RGB640_PLL_CTL, c | IBM640_PLL_EN);
+ STORERAMDAC(RGB640_AUX_PLL_CTL, 0); /* Disable AUX PLL */
+ }
+ STORERAMDAC(RGB640_PIXEL_INTERLEAVE, 0x00);
+
+ temp1 = IBM640_RDBK | IBM640_VRAM;
+ if (pScrn->rgbBits == 8)
+ temp1 |= IBM640_PSIZE8;
+ STORERAMDAC(RGB640_VGA_CONTROL, temp1);
+
+ STORERAMDAC(RGB640_DAC_CONTROL, IBM640_DACENBL | IBM640_SHUNT);
+ STORERAMDAC(RGB640_OUTPUT_CONTROL, IBM640_RDAI | IBM640_WATCTL);
+ STORERAMDAC(RGB640_SYNC_CONTROL, 0x00);
+ STORERAMDAC(RGB640_VRAM_MASK0, 0xFF);
+ STORERAMDAC(RGB640_VRAM_MASK1, 0xFF);
+ STORERAMDAC(RGB640_VRAM_MASK2, 0x0F);
+
+ STOREREG(VTGModeCtl, 0x04);
+ break;
+
+ case TI3026_RAMDAC:
+ case TI3030_RAMDAC:
+ {
+ /* Get the programmable clock values */
+ unsigned long m=0,n=0,p=0;
+ unsigned long clock;
+ unsigned long q, VCO = 0;
+
+ clock = TIramdacCalculateMNPForClock(pGlint->RefClock,
+ mode->Clock, 1, pGlint->MinClock, pGlint->MaxClock, &m, &n, &p);
+
+ STORERAMDAC(TIDAC_PIXEL_N, ((n & 0x3f) | 0xC0));
+ STORERAMDAC(TIDAC_PIXEL_M, (m & 0x3f));
+ STORERAMDAC(TIDAC_PIXEL_P, ((p & 0x03) | 0xbc));
+ STORERAMDAC(TIDAC_PIXEL_VALID, TRUE);
+
+ if (pGlint->RamDac->RamDacType == (TI3026_RAMDAC))
+ n = 65 - ((64 << 2) / pScrn->bitsPerPixel);
+ else
+ n = 65 - ((128 << 2) / pScrn->bitsPerPixel);
+ m = 61;
+ p = 0;
+ for (q = 0; q < 8; q++) {
+ if (q > 0) p = 3;
+ for ( ; p < 4; p++) {
+ VCO = ((clock * (q + 1) * (65 - m)) / (65 - n)) << (p + 1);
+ if (VCO >= 110000) { break; }
+ }
+ if (VCO >= 110000) { break; }
+ }
+ STORERAMDAC(TIDAC_clock_ctrl, (q | 0x38));
+
+ STORERAMDAC(TIDAC_LOOP_N, ((n & 0x3f) | 0xC0));
+ STORERAMDAC(TIDAC_LOOP_M, (m & 0x3f));
+ STORERAMDAC(TIDAC_LOOP_P, ((p & 0x03) | 0xF0));
+ STORERAMDAC(TIDAC_LOOP_VALID, TRUE);
+ }
+ if (pGlint->RamDac->RamDacType == (TI3030_RAMDAC))
+ STOREREG(VTGModeCtl, 0x04);
+ break;
+ }
+
+ /* Now use helper routines to setup bpp for this driver */
+ (*pGlint->RamDac->SetBpp)(pScrn, ramdacReg);
+
+ return(TRUE);
+}
+
+void
+TXSave(ScrnInfoPtr pScrn, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (pGlint->numMultiDevices == 2) {
+ SAVEREG(GCSRAperture);
+ }
+
+ if (pGlint->MultiAperture) {
+ SAVEREG(GMultGLINTAperture);
+ SAVEREG(GMultGLINT1);
+ SAVEREG(GMultGLINT2);
+ }
+
+ SAVEREG(Aperture0);
+ SAVEREG(Aperture1);
+
+ SAVEREG(DFIFODis);
+
+ if (pGlint->Chipset != PCI_VENDOR_3DLABS_CHIP_300SX) {
+ SAVEREG(FIFODis);
+ SAVEREG(VTGModeCtl);
+ }
+
+ SAVEREG(VClkCtl);
+ SAVEREG(VTGPolarity);
+ SAVEREG(VTGHLimit);
+ SAVEREG(VTGHBlankEnd);
+ SAVEREG(VTGHSyncStart);
+ SAVEREG(VTGHSyncEnd);
+ SAVEREG(VTGVLimit);
+ SAVEREG(VTGVBlankEnd);
+ SAVEREG(VTGVSyncStart);
+ SAVEREG(VTGVSyncEnd);
+ SAVEREG(VTGVGateStart);
+ SAVEREG(VTGVGateEnd);
+ SAVEREG(VTGSerialClk);
+ SAVEREG(FBModeSel);
+ SAVEREG(VTGHGateStart);
+ SAVEREG(VTGHGateEnd);
+ SAVEREG(FBMemoryCtl);
+
+ if (IS_GMX2000 || IS_GLORIAXXL) {
+ SAVEREG(LBMemoryEDO);
+ SAVEREG(LBMemoryCtl);
+ }
+}
+
+void
+TXRestore(ScrnInfoPtr pScrn, GLINTRegPtr pReg)
+{
+ GLINTPtr pGlint = GLINTPTR(pScrn);
+
+ if (pGlint->numMultiDevices == 2) {
+ RESTOREREG(GCSRAperture);
+ }
+
+ if (pGlint->MultiAperture) {
+ RESTOREREG(GMultGLINTAperture);
+ RESTOREREG(GMultGLINT1);
+ RESTOREREG(GMultGLINT2);
+ }
+
+ RESTOREREG(Aperture0);
+ RESTOREREG(Aperture1);
+
+ RESTOREREG(DFIFODis);
+
+ if (pGlint->Chipset != PCI_VENDOR_3DLABS_CHIP_300SX) {
+ RESTOREREG(FIFODis);
+ RESTOREREG(VTGModeCtl);
+ }
+
+ RESTOREREG(VTGPolarity);
+ RESTOREREG(VClkCtl);
+ RESTOREREG(VTGSerialClk);
+ RESTOREREG(VTGHLimit);
+ RESTOREREG(VTGHSyncStart);
+ RESTOREREG(VTGHSyncEnd);
+ RESTOREREG(VTGHBlankEnd);
+ RESTOREREG(VTGVLimit);
+ RESTOREREG(VTGVSyncStart);
+ RESTOREREG(VTGVSyncEnd);
+ RESTOREREG(VTGVBlankEnd);
+ RESTOREREG(VTGVGateStart);
+ RESTOREREG(VTGVGateEnd);
+ RESTOREREG(FBModeSel);
+ RESTOREREG(VTGHGateStart);
+ RESTOREREG(VTGHGateEnd);
+ RESTOREREG(FBMemoryCtl);
+
+ if (IS_GMX2000 || IS_GLORIAXXL) {
+ RESTOREREG(LBMemoryEDO);
+ RESTOREREG(LBMemoryCtl);
+ }
+}