1 /*
2  * ReactOS Generic Framebuffer display driver
3  *
4  * Copyright (C) 2004 Filip Navara
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License along
17  * with this program; if not, write to the Free Software Foundation, Inc.,
18  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19  */
20 
21 #include "framebuf.h"
22 
23 /*
24  * DrvEnableSurface
25  *
26  * Create engine bitmap around frame buffer and set the video mode requested
27  * when PDEV was initialized.
28  *
29  * Status
30  *    @implemented
31  */
32 
33 HSURF APIENTRY
34 DrvEnableSurface(
35    IN DHPDEV dhpdev)
36 {
37    PPDEV ppdev = (PPDEV)dhpdev;
38    HSURF hSurface;
39    ULONG BitmapType;
40    SIZEL ScreenSize;
41    VIDEO_MEMORY VideoMemory;
42    VIDEO_MEMORY_INFORMATION VideoMemoryInfo;
43    ULONG ulTemp;
44 
45    /*
46     * Set video mode of our adapter.
47     */
48 
49    if (EngDeviceIoControl(ppdev->hDriver, IOCTL_VIDEO_SET_CURRENT_MODE,
50                           &(ppdev->ModeIndex), sizeof(ULONG), NULL, 0,
51                           &ulTemp))
52    {
53       return FALSE;
54    }
55 
56    /*
57     * Map the framebuffer into our memory.
58     */
59 
60    VideoMemory.RequestedVirtualAddress = NULL;
61    if (EngDeviceIoControl(ppdev->hDriver, IOCTL_VIDEO_MAP_VIDEO_MEMORY,
62                           &VideoMemory, sizeof(VIDEO_MEMORY),
63                           &VideoMemoryInfo, sizeof(VIDEO_MEMORY_INFORMATION),
64                           &ulTemp))
65    {
66       return FALSE;
67    }
68 
69    ppdev->ScreenPtr = VideoMemoryInfo.FrameBufferBase;
70 
71    switch (ppdev->BitsPerPixel)
72    {
73       case 8:
74          IntSetPalette(dhpdev, ppdev->PaletteEntries, 0, 256);
75          BitmapType = BMF_8BPP;
76          break;
77 
78       case 16:
79          BitmapType = BMF_16BPP;
80          break;
81 
82       case 24:
83          BitmapType = BMF_24BPP;
84          break;
85 
86       case 32:
87          BitmapType = BMF_32BPP;
88          break;
89 
90       default:
91          return FALSE;
92    }
93 
94    ppdev->iDitherFormat = BitmapType;
95 
96    ScreenSize.cx = ppdev->ScreenWidth;
97    ScreenSize.cy = ppdev->ScreenHeight;
98 
99    hSurface = (HSURF)EngCreateBitmap(ScreenSize, ppdev->ScreenDelta, BitmapType,
100                                      (ppdev->ScreenDelta > 0) ? BMF_TOPDOWN : 0,
101                                      ppdev->ScreenPtr);
102    if (hSurface == NULL)
103    {
104       return FALSE;
105    }
106 
107    /*
108     * Associate the surface with our device.
109     */
110 
111    if (!EngAssociateSurface(hSurface, ppdev->hDevEng, 0))
112    {
113       EngDeleteSurface(hSurface);
114       return FALSE;
115    }
116 
117    ppdev->hSurfEng = hSurface;
118 
119    return hSurface;
120 }
121 
122 /*
123  * DrvDisableSurface
124  *
125  * Used by GDI to notify a driver that the surface created by DrvEnableSurface
126  * for the current device is no longer needed.
127  *
128  * Status
129  *    @implemented
130  */
131 
132 VOID APIENTRY
133 DrvDisableSurface(
134    IN DHPDEV dhpdev)
135 {
136    DWORD ulTemp;
137    VIDEO_MEMORY VideoMemory;
138    PPDEV ppdev = (PPDEV)dhpdev;
139 
140    EngDeleteSurface(ppdev->hSurfEng);
141    ppdev->hSurfEng = NULL;
142 
143 #ifdef EXPERIMENTAL_MOUSE_CURSOR_SUPPORT
144    /* Clear all mouse pointer surfaces. */
145    DrvSetPointerShape(NULL, NULL, NULL, NULL, 0, 0, 0, 0, NULL, 0);
146 #endif
147 
148    /*
149     * Unmap the framebuffer.
150     */
151 
152    VideoMemory.RequestedVirtualAddress = ((PPDEV)dhpdev)->ScreenPtr;
153    EngDeviceIoControl(((PPDEV)dhpdev)->hDriver, IOCTL_VIDEO_UNMAP_VIDEO_MEMORY,
154                       &VideoMemory, sizeof(VIDEO_MEMORY), NULL, 0, &ulTemp);
155 }
156 
157 /*
158  * DrvAssertMode
159  *
160  * Sets the mode of the specified physical device to either the mode specified
161  * when the PDEV was initialized or to the default mode of the hardware.
162  *
163  * Status
164  *    @implemented
165  */
166 
167 BOOL APIENTRY
168 DrvAssertMode(
169    IN DHPDEV dhpdev,
170    IN BOOL bEnable)
171 {
172    PPDEV ppdev = (PPDEV)dhpdev;
173    ULONG ulTemp;
174 
175    if (bEnable)
176    {
177       /*
178        * Reinitialize the device to a clean state.
179        */
180       if (EngDeviceIoControl(ppdev->hDriver, IOCTL_VIDEO_SET_CURRENT_MODE,
181                              &(ppdev->ModeIndex), sizeof(ULONG), NULL, 0,
182                              &ulTemp))
183       {
184           /* We failed, bail out */
185           return FALSE;
186       }
187       if (ppdev->BitsPerPixel == 8)
188       {
189 	     IntSetPalette(dhpdev, ppdev->PaletteEntries, 0, 256);
190       }
191 
192       return TRUE;
193    }
194    else
195    {
196       /*
197        * Call the miniport driver to reset the device to a known state.
198        */
199       return !EngDeviceIoControl(ppdev->hDriver, IOCTL_VIDEO_RESET_DEVICE,
200                                  NULL, 0, NULL, 0, &ulTemp);
201    }
202 }
203