Mercurial > mplayer.hg
annotate linux/vbelib.c @ 2293:638cd37032da
Better resolution detection
author | nick |
---|---|
date | Fri, 19 Oct 2001 15:09:40 +0000 |
parents | 6e5b548790c9 |
children | 9475a75dde9c |
rev | line source |
---|---|
2243 | 1 /* |
2 This file contains implementation of VESA library which is based on | |
3 LRMI (Linux real-mode interface). | |
4 So it's not an emulator - it calls real int 10h handler under Linux. | |
5 Note: VESA is available only on x86 systems. | |
6 You can redistribute this file under terms and conditions | |
7 GNU General Public licence v2. | |
8 Written by Nick Kurshev <nickols_k@mail.ru> | |
9 */ | |
10 #include "vbelib.h" | |
11 #include "lrmi.h" | |
12 #include <stdlib.h> | |
13 #include <string.h> | |
14 #include <stdio.h> | |
15 #include <sys/io.h> | |
16 | |
17 static struct VesaProtModeInterface vbe_pm_info; | |
18 | |
19 int vbeInit( void ) | |
20 { | |
21 if(!LRMI_init()) return VBE_VM86_FAIL; | |
22 /* | |
23 Allow read/write to ALL io ports | |
24 */ | |
25 ioperm(0, 1024, 1); | |
26 iopl(3); | |
27 memset(&vbe_pm_info,0,sizeof(struct VesaProtModeInterface)); | |
28 vbeGetProtModeInfo(&vbe_pm_info); | |
29 return VBE_OK; | |
30 } | |
31 | |
32 int vbeDestroy( void ) { return VBE_OK; } | |
33 | |
34 int vbeGetControllerInfo(struct VbeInfoBlock *data) | |
35 { | |
36 struct LRMI_regs r; | |
37 void *rm_space; | |
38 int retval; | |
39 if(!(rm_space = LRMI_alloc_real(sizeof(struct VbeInfoBlock)))) return VBE_OUT_OF_DOS_MEM; | |
40 memcpy(rm_space,data,sizeof(struct VbeInfoBlock)); | |
41 memset(&r,0,sizeof(struct LRMI_regs)); | |
42 r.eax = 0x4f00; | |
43 r.es = VirtToPhysSeg(rm_space); | |
44 r.edi = VirtToPhysOff(rm_space); | |
45 if(!LRMI_int(0x10,&r)) | |
46 { | |
47 LRMI_free_real(rm_space); | |
48 return VBE_VM86_FAIL; | |
49 } | |
50 retval = r.eax & 0xffff; | |
51 if(retval == 0x4f) | |
52 { | |
53 FarPtr fpdata; | |
54 retval = VBE_OK; | |
55 memcpy(data,rm_space,sizeof(struct VbeInfoBlock)); | |
56 fpdata.seg = (unsigned long)(data->OemStringPtr) >> 16; | |
57 fpdata.off = (unsigned long)(data->OemStringPtr) & 0xffff; | |
58 data->OemStringPtr = PhysToVirt(fpdata); | |
59 fpdata.seg = (unsigned long)(data->VideoModePtr) >> 16; | |
60 fpdata.off = (unsigned long)(data->VideoModePtr) & 0xffff; | |
61 data->VideoModePtr = PhysToVirt(fpdata); | |
62 fpdata.seg = (unsigned long)(data->OemVendorNamePtr) >> 16; | |
63 fpdata.off = (unsigned long)(data->OemVendorNamePtr) & 0xffff; | |
64 data->OemVendorNamePtr = PhysToVirt(fpdata); | |
65 fpdata.seg = (unsigned long)(data->OemProductNamePtr) >> 16; | |
66 fpdata.off = (unsigned long)(data->OemProductNamePtr) & 0xffff; | |
67 data->OemProductNamePtr = PhysToVirt(fpdata); | |
68 fpdata.seg = (unsigned long)(data->OemProductRevPtr) >> 16; | |
69 fpdata.off = (unsigned long)(data->OemProductRevPtr) & 0xffff; | |
70 data->OemProductRevPtr = PhysToVirt(fpdata); | |
71 } | |
72 return retval; | |
73 } | |
74 | |
75 int vbeGetModeInfo(unsigned mode,struct VesaModeInfoBlock *data) | |
76 { | |
77 struct LRMI_regs r; | |
78 void *rm_space; | |
79 int retval; | |
80 if(!(rm_space = LRMI_alloc_real(sizeof(struct VesaModeInfoBlock)))) return VBE_OUT_OF_DOS_MEM; | |
81 memset(&r,0,sizeof(struct LRMI_regs)); | |
82 r.eax = 0x4f01; | |
83 r.ecx = mode; | |
84 r.es = VirtToPhysSeg(rm_space); | |
85 r.edi = VirtToPhysOff(rm_space); | |
86 if(!LRMI_int(0x10,&r)) | |
87 { | |
88 LRMI_free_real(rm_space); | |
89 return VBE_VM86_FAIL; | |
90 } | |
91 retval = r.eax & 0xffff; | |
92 if(retval == 0x4f) | |
93 { | |
94 retval = VBE_OK; | |
95 memcpy(data,rm_space,sizeof(struct VesaModeInfoBlock)); | |
96 } | |
97 return retval; | |
98 } | |
99 | |
100 int vbeSetMode(unsigned mode,struct VesaCRTCInfoBlock *data) | |
101 { | |
102 struct LRMI_regs r; | |
103 void *rm_space = NULL; | |
104 int retval; | |
105 memset(&r,0,sizeof(struct LRMI_regs)); | |
106 if(data) | |
107 { | |
108 if(!(rm_space = LRMI_alloc_real(sizeof(struct VesaCRTCInfoBlock)))) return VBE_OUT_OF_DOS_MEM; | |
109 r.es = VirtToPhysSeg(rm_space); | |
110 r.edi = VirtToPhysOff(rm_space); | |
111 memcpy(rm_space,data,sizeof(struct VesaCRTCInfoBlock)); | |
112 } | |
113 r.eax = 0x4f02; | |
114 r.ebx = mode; | |
115 retval = LRMI_int(0x10,&r); | |
116 if(rm_space) LRMI_free_real(rm_space); | |
117 if(!retval) return VBE_VM86_FAIL; | |
118 retval = r.eax & 0xffff; | |
119 if(retval == 0x4f) retval = VBE_OK; | |
120 return retval; | |
121 } | |
122 | |
123 int vbeGetMode(unsigned *mode) | |
124 { | |
125 struct LRMI_regs r; | |
126 int retval; | |
127 memset(&r,0,sizeof(struct LRMI_regs)); | |
128 r.eax = 0x4f03; | |
129 if(!LRMI_int(0x10,&r)) return VBE_VM86_FAIL; | |
130 retval = r.eax & 0xffff; | |
131 if(retval == 0x4f) | |
132 { | |
133 *mode = r.ebx; | |
134 retval = VBE_OK; | |
135 } | |
136 return retval; | |
137 } | |
138 | |
139 int vbeSaveState(void **data) | |
140 { | |
141 struct LRMI_regs r; | |
142 int retval; | |
143 void *rm_space; | |
144 memset(&r,0,sizeof(struct LRMI_regs)); | |
145 r.eax = 0x4f04; | |
146 r.edx = 0x00; | |
147 r.ecx = 0x0f; | |
148 if(!LRMI_int(0x10,&r)) return VBE_VM86_FAIL; | |
149 retval = r.eax & 0xffff; | |
150 if(retval != 0x4f) return retval; | |
151 if(!(rm_space = LRMI_alloc_real((r.ebx & 0xffff)*64))) return VBE_OUT_OF_DOS_MEM; | |
152 r.eax = 0x4f04; | |
153 r.edx = 0x01; | |
154 r.ecx = 0x0f; | |
155 r.es = VirtToPhysSeg(rm_space); | |
2254
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
156 r.ebx = VirtToPhysOff(rm_space); |
2243 | 157 if(!LRMI_int(0x10,&r)) |
158 { | |
159 LRMI_free_real(rm_space); | |
160 return VBE_VM86_FAIL; | |
161 } | |
162 retval = r.eax & 0xffff; | |
163 if(retval != 0x4f) | |
164 { | |
165 LRMI_free_real(rm_space); | |
166 return retval; | |
167 } | |
168 *data = rm_space; | |
169 return VBE_OK; | |
170 } | |
171 | |
172 int vbeRestoreState(void *data) | |
173 { | |
174 struct LRMI_regs r; | |
175 int retval; | |
176 void *rm_space; | |
177 memset(&r,0,sizeof(struct LRMI_regs)); | |
178 r.eax = 0x4f04; | |
179 r.edx = 0x02; | |
180 r.ecx = 0x0f; | |
181 r.es = VirtToPhysSeg(data); | |
2254
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
182 r.ebx = VirtToPhysOff(data); |
2243 | 183 retval = LRMI_int(0x10,&r); |
184 LRMI_free_real(data); | |
185 if(!retval) return VBE_VM86_FAIL; | |
186 retval = r.eax & 0xffff; | |
187 if(retval == 0x4f) retval = VBE_OK; | |
188 return retval; | |
189 } | |
190 | |
191 int vbeGetWindow(unsigned *win_num) | |
192 { | |
193 struct LRMI_regs r; | |
194 int retval; | |
195 memset(&r,0,sizeof(struct LRMI_regs)); | |
196 r.eax = 0x4f05; | |
197 r.ebx = (*win_num & 0x0f) | 0x0100; | |
198 if(!LRMI_int(0x10,&r)) return VBE_VM86_FAIL; | |
199 retval = r.eax & 0xffff; | |
200 if(retval == 0x4f) | |
201 { | |
202 *win_num = r.edx & 0xffff; | |
203 retval = VBE_OK; | |
204 } | |
205 return retval; | |
206 } | |
207 | |
208 int vbeSetWindow(unsigned win_num,unsigned win_gran) | |
209 { | |
210 int retval; | |
211 if(vbe_pm_info.SetWindowCall) | |
212 { | |
213 /* 32-bit function call is much better of int 10h */ | |
214 __asm __volatile( | |
215 "pushl %%ebx\n" | |
216 "movl %1, %%ebx\n" | |
217 ::"a"(0x4f05),"S"(win_num & 0x0f),"d"(win_gran):"memory"); | |
218 (*vbe_pm_info.SetWindowCall)(); | |
2254
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
219 __asm __volatile("popl %%ebx":::"memory"); |
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
220 retval = VBE_OK; |
2243 | 221 } |
222 else | |
223 { | |
224 struct LRMI_regs r; | |
225 memset(&r,0,sizeof(struct LRMI_regs)); | |
226 r.eax = 0x4f05; | |
227 r.ebx = win_num & 0x0f; | |
228 r.edx = win_gran; | |
229 if(!LRMI_int(0x10,&r)) return VBE_VM86_FAIL; | |
230 retval = r.eax & 0xffff; | |
2254
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
231 if(retval == 0x4f) retval = VBE_OK; |
2243 | 232 } |
233 return retval; | |
234 } | |
235 | |
236 struct realVesaProtModeInterface | |
237 { | |
238 unsigned short SetWindowCall; | |
239 unsigned short SetDisplayStart; | |
240 unsigned short SetPaletteData; | |
241 unsigned short iopl_ports; | |
242 }__attribute__((packed)); | |
243 | |
244 int vbeGetProtModeInfo(struct VesaProtModeInterface *pm_info) | |
245 { | |
246 struct LRMI_regs r; | |
247 int retval; | |
2254
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
248 unsigned info_offset; |
2243 | 249 struct realVesaProtModeInterface *rm_info; |
250 memset(&r,0,sizeof(struct LRMI_regs)); | |
251 r.eax = 0x4f0a; | |
252 r.ebx = 0; | |
253 if(!LRMI_int(0x10,&r)) return VBE_VM86_FAIL; | |
254 retval = r.eax & 0xffff; | |
255 if(retval == 0x4f) | |
256 { | |
2254
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
257 info_offset = r.edi&0xffff; |
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
258 rm_info = PhysToVirtSO(r.es,info_offset); |
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
259 pm_info->SetWindowCall = PhysToVirtSO(r.es,info_offset+rm_info->SetWindowCall); |
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
260 pm_info->SetDisplayStart = PhysToVirtSO(r.es,info_offset+rm_info->SetDisplayStart); |
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
261 pm_info->SetPaletteData = PhysToVirtSO(r.es,info_offset+rm_info->SetPaletteData); |
6e5b548790c9
Fixed bug of 32-bit mode interface detection and save-restore mechanism
nick
parents:
2243
diff
changeset
|
262 pm_info->iopl_ports = PhysToVirtSO(r.es,info_offset+rm_info->iopl_ports); |
2243 | 263 retval = VBE_OK; |
264 } | |
265 return retval; | |
266 } |