Mercurial > mplayer.hg
annotate vidix/vidixlib.c @ 22033:a9b8e965de13
stray fflush spotted by Aurel
author | lu_zero |
---|---|
date | Sun, 28 Jan 2007 20:38:35 +0000 |
parents | fa99b3d31d13 |
children | 77def5093daf |
rev | line source |
---|---|
3991 | 1 /* |
2 * vidixlib.c | |
3 * VIDIXLib - Library for VIDeo Interface for *niX | |
4 * This interface is introduced as universal one to MPEG decoder, | |
5 * BES == Back End Scaler and YUV2RGB hw accelerators. | |
6 * In the future it may be expanded up to capturing and audio things. | |
7 * Main goal of this this interface imlpementation is providing DGA | |
8 * everywhere where it's possible (unlike X11 and other). | |
9 * Copyright 2002 Nick Kurshev | |
10 * Licence: GPL | |
11 * This interface is based on v4l2, fbvid.h, mga_vid.h projects | |
12 * and personally my ideas. | |
13 * NOTE: This interface is introduces as APP interface. | |
14 * Don't use it for driver. | |
15 * It provides multistreaming. This mean that APP can handle | |
16 * several streams simultaneously. (Example: Video capturing and video | |
17 * playback or capturing, video playback, audio encoding and so on). | |
18 */ | |
19 #include <stdlib.h> | |
20 #include <stdio.h> | |
21 #include <errno.h> | |
22 #include <string.h> | |
23 | |
10982 | 24 #ifndef WIN32 |
3991 | 25 #include <dlfcn.h> /* GLIBC specific. Exists under cygwin too! */ |
10982 | 26 #else |
27 #include <windows.h> | |
28 #define dlsym(h,s) GetProcAddress(h,s) | |
29 #define dlopen(h,s) LoadLibrary(h) | |
30 #define dlclose(h) FreeLibrary(h) | |
31 static char* dlerror(){ | |
32 char errormsg[10]; | |
33 sprintf(errormsg,"%i\n",GetLastError()); | |
34 return errormsg; | |
35 } | |
36 #endif | |
37 | |
38 | |
3991 | 39 #include <dirent.h> |
40 | |
6130
e9a309486f18
openbsd a.out needs underscore for dlsym - patch by Bj«Órn Sandell <biorn@dce.chalmers.se>
arpi
parents:
5872
diff
changeset
|
41 #if defined(__OpenBSD__) && !defined(__ELF__) |
e9a309486f18
openbsd a.out needs underscore for dlsym - patch by Bj«Órn Sandell <biorn@dce.chalmers.se>
arpi
parents:
5872
diff
changeset
|
42 #define dlsym(h,s) dlsym(h, "_" s) |
e9a309486f18
openbsd a.out needs underscore for dlsym - patch by Bj«Órn Sandell <biorn@dce.chalmers.se>
arpi
parents:
5872
diff
changeset
|
43 #endif |
e9a309486f18
openbsd a.out needs underscore for dlsym - patch by Bj«Órn Sandell <biorn@dce.chalmers.se>
arpi
parents:
5872
diff
changeset
|
44 |
3991 | 45 #include "vidixlib.h" |
21372 | 46 #include "../config.h" |
47 #include "../libavutil/common.h" | |
21507
fa99b3d31d13
Hack around libavutil/bswap.h compilation problems due to always_inline undefined.
reimar
parents:
21372
diff
changeset
|
48 #include "../mpbswap.h" |
3991 | 49 |
4011 | 50 static char drv_name[FILENAME_MAX]; |
3991 | 51 |
52 typedef struct vdl_stream_s | |
53 { | |
54 void * handle; | |
55 int (*get_caps)(vidix_capability_t *); | |
56 int (*query_fourcc)(vidix_fourcc_t *); | |
3995 | 57 int (*config_playback)(vidix_playback_t *); |
3991 | 58 int (*playback_on)( void ); |
59 int (*playback_off)( void ); | |
60 /* Functions below can be missed in driver ;) */ | |
61 int (*init)(void); | |
62 void (*destroy)(void); | |
63 int (*frame_sel)( unsigned frame_idx ); | |
64 int (*get_eq)( vidix_video_eq_t * ); | |
65 int (*set_eq)( const vidix_video_eq_t * ); | |
4191 | 66 int (*get_deint)( vidix_deinterlace_t * ); |
67 int (*set_deint)( const vidix_deinterlace_t * ); | |
3991 | 68 int (*copy_frame)( const vidix_dma_t * ); |
4070
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
69 int (*get_gkey)( vidix_grkey_t * ); |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
70 int (*set_gkey)( const vidix_grkey_t * ); |
4191 | 71 int (*get_num_fx)( unsigned * ); |
72 int (*get_fx)( vidix_oem_fx_t * ); | |
73 int (*set_fx)( const vidix_oem_fx_t * ); | |
3991 | 74 }vdl_stream_t; |
75 | |
76 #define t_vdl(p) (((vdl_stream_t *)p)) | |
77 | |
78 extern unsigned vdlGetVersion( void ) | |
79 { | |
80 return VIDIX_VERSION; | |
81 } | |
82 | |
83 static int vdl_fill_driver(VDL_HANDLE stream) | |
84 { | |
85 t_vdl(stream)->init = dlsym(t_vdl(stream)->handle,"vixInit"); | |
86 t_vdl(stream)->destroy = dlsym(t_vdl(stream)->handle,"vixDestroy"); | |
87 t_vdl(stream)->get_caps = dlsym(t_vdl(stream)->handle,"vixGetCapability"); | |
88 t_vdl(stream)->query_fourcc = dlsym(t_vdl(stream)->handle,"vixQueryFourcc"); | |
89 t_vdl(stream)->config_playback= dlsym(t_vdl(stream)->handle,"vixConfigPlayback"); | |
90 t_vdl(stream)->playback_on = dlsym(t_vdl(stream)->handle,"vixPlaybackOn"); | |
91 t_vdl(stream)->playback_off = dlsym(t_vdl(stream)->handle,"vixPlaybackOff"); | |
92 t_vdl(stream)->frame_sel = dlsym(t_vdl(stream)->handle,"vixPlaybackFrameSelect"); | |
93 t_vdl(stream)->get_eq = dlsym(t_vdl(stream)->handle,"vixPlaybackGetEq"); | |
94 t_vdl(stream)->set_eq = dlsym(t_vdl(stream)->handle,"vixPlaybackSetEq"); | |
4070
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
95 t_vdl(stream)->get_gkey = dlsym(t_vdl(stream)->handle,"vixGetGrKeys"); |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
96 t_vdl(stream)->set_gkey = dlsym(t_vdl(stream)->handle,"vixSetGrKeys"); |
4191 | 97 t_vdl(stream)->get_deint = dlsym(t_vdl(stream)->handle,"vixPlaybackGetDeint"); |
98 t_vdl(stream)->set_deint = dlsym(t_vdl(stream)->handle,"vixPlaybackSetDeint"); | |
3991 | 99 t_vdl(stream)->copy_frame = dlsym(t_vdl(stream)->handle,"vixPlaybackCopyFrame"); |
4191 | 100 t_vdl(stream)->get_num_fx = dlsym(t_vdl(stream)->handle,"vixQueryNumOemEffects"); |
101 t_vdl(stream)->get_fx = dlsym(t_vdl(stream)->handle,"vixGetOemEffect"); | |
102 t_vdl(stream)->set_fx = dlsym(t_vdl(stream)->handle,"vixSetOemEffect"); | |
3991 | 103 /* check driver viability */ |
3995 | 104 if(!( t_vdl(stream)->get_caps && t_vdl(stream)->query_fourcc && |
105 t_vdl(stream)->config_playback && t_vdl(stream)->playback_on && | |
106 t_vdl(stream)->playback_off)) | |
4011 | 107 { |
4509
90386125ec1f
using dlerror() instead strerror(), displays unresolved symbol messages
alex
parents:
4191
diff
changeset
|
108 printf("vidixlib: Incomplete driver: some of essential features are missed in it.\n"); |
4011 | 109 return 0; |
110 } | |
3991 | 111 return 1; |
112 } | |
113 | |
5872 | 114 #ifndef RTLD_GLOBAL |
115 #define RTLD_GLOBAL RTLD_LAZY | |
116 #endif | |
117 #ifndef RTLD_NOW | |
118 #define RTLD_NOW RTLD_LAZY | |
119 #endif | |
120 | |
3995 | 121 static int vdl_probe_driver(VDL_HANDLE stream,const char *path,const char *name,unsigned cap,int verbose) |
3991 | 122 { |
123 vidix_capability_t vid_cap; | |
124 unsigned (*_ver)(void); | |
4191 | 125 int (*_probe)(int,int); |
3991 | 126 int (*_cap)(vidix_capability_t*); |
12646 | 127 strlcpy(drv_name,path, sizeof( drv_name )); |
128 strlcat(drv_name,name, sizeof( drv_name )); | |
4008 | 129 if(verbose) printf("vidixlib: PROBING: %s\n",drv_name); |
4011 | 130 if(!(t_vdl(stream)->handle = dlopen(drv_name,RTLD_LAZY|RTLD_GLOBAL))) |
131 { | |
4509
90386125ec1f
using dlerror() instead strerror(), displays unresolved symbol messages
alex
parents:
4191
diff
changeset
|
132 if(verbose) printf("vidixlib: %s not driver: %s\n",drv_name,dlerror()); |
4011 | 133 return 0; |
134 } | |
3991 | 135 _ver = dlsym(t_vdl(stream)->handle,"vixGetVersion"); |
136 _probe = dlsym(t_vdl(stream)->handle,"vixProbe"); | |
137 _cap = dlsym(t_vdl(stream)->handle,"vixGetCapability"); | |
4008 | 138 if(_ver) |
139 { | |
140 if((*_ver)() != VIDIX_VERSION) | |
141 { | |
142 if(verbose) printf("vidixlib: %s has wrong version\n",drv_name); | |
143 err: | |
144 dlclose(t_vdl(stream)->handle); | |
145 t_vdl(stream)->handle = 0; | |
146 return 0; | |
147 } | |
148 } | |
149 else | |
150 { | |
151 fatal_err: | |
152 if(verbose) printf("vidixlib: %s has no function definition\n",drv_name); | |
153 goto err; | |
154 } | |
4191 | 155 if(_probe) { if((*_probe)(verbose,PROBE_NORMAL) != 0) goto err; } |
4008 | 156 else goto fatal_err; |
3991 | 157 if(_cap) { if((*_cap)(&vid_cap) != 0) goto err; } |
4008 | 158 else goto fatal_err; |
4011 | 159 if((vid_cap.type & cap) != cap) |
160 { | |
161 if(verbose) printf("vidixlib: Found %s but has no required capability\n",drv_name); | |
162 goto err; | |
163 } | |
4008 | 164 if(verbose) printf("vidixlib: %s probed o'k\n",drv_name); |
3991 | 165 return 1; |
166 } | |
167 | |
3995 | 168 static int vdl_find_driver(VDL_HANDLE stream,const char *path,unsigned cap,int verbose) |
3991 | 169 { |
170 DIR *dstream; | |
171 struct dirent *name; | |
172 int done = 0; | |
173 if(!(dstream = opendir(path))) return 0; | |
174 while(!done) | |
175 { | |
176 name = readdir(dstream); | |
4008 | 177 if(name) |
178 { | |
179 if(name->d_name[0] != '.') | |
180 if(vdl_probe_driver(stream,path,name->d_name,cap,verbose)) break; | |
181 } | |
3991 | 182 else done = 1; |
183 } | |
184 closedir(dstream); | |
185 return done?0:1; | |
186 } | |
187 | |
3995 | 188 VDL_HANDLE vdlOpen(const char *path,const char *name,unsigned cap,int verbose) |
3991 | 189 { |
190 vdl_stream_t *stream; | |
4011 | 191 int errcode; |
3991 | 192 if(!(stream = malloc(sizeof(vdl_stream_t)))) return NULL; |
193 memset(stream,0,sizeof(vdl_stream_t)); | |
194 if(name) | |
195 { | |
196 unsigned (*ver)(void); | |
4191 | 197 int (*probe)(int,int); |
3991 | 198 unsigned version = 0; |
12646 | 199 strlcpy(drv_name,path, sizeof( drv_name )); |
200 strlcat(drv_name,name, sizeof( drv_name )); | |
3991 | 201 if(!(t_vdl(stream)->handle = dlopen(drv_name,RTLD_NOW|RTLD_GLOBAL))) |
202 { | |
4509
90386125ec1f
using dlerror() instead strerror(), displays unresolved symbol messages
alex
parents:
4191
diff
changeset
|
203 if (verbose) |
90386125ec1f
using dlerror() instead strerror(), displays unresolved symbol messages
alex
parents:
4191
diff
changeset
|
204 printf("vidixlib: dlopen error: %s\n", dlerror()); |
3991 | 205 err: |
206 free(stream); | |
207 return NULL; | |
208 } | |
209 ver = dlsym(t_vdl(stream)->handle,"vixGetVersion"); | |
210 if(ver) version = (*ver)(); | |
211 if(version != VIDIX_VERSION) | |
212 { | |
213 drv_err: | |
214 if(t_vdl(stream)->handle) dlclose(t_vdl(stream)->handle); | |
215 goto err; | |
216 } | |
3995 | 217 probe = dlsym(t_vdl(stream)->handle,"vixProbe"); |
4191 | 218 if(probe) { if((*probe)(verbose,PROBE_FORCE)!=0) goto drv_err; } |
3995 | 219 else goto drv_err; |
3991 | 220 fill: |
221 if(!vdl_fill_driver(stream)) goto drv_err; | |
4011 | 222 goto ok; |
3991 | 223 } |
224 else | |
4011 | 225 if(vdl_find_driver(stream,path,cap,verbose)) |
226 { | |
227 if(verbose) printf("vidixlib: will use %s driver\n",drv_name); | |
228 goto fill; | |
229 } | |
230 else goto err; | |
231 ok: | |
232 if(t_vdl(stream)->init) | |
233 { | |
234 if(verbose) printf("vidixlib: Attempt to initialize driver at: %p\n",t_vdl(stream)->init); | |
235 if((errcode=t_vdl(stream)->init())!=0) | |
236 { | |
237 if(verbose) printf("vidixlib: Can't init driver: %s\n",strerror(errcode)); | |
238 goto drv_err; | |
239 } | |
240 } | |
241 if(verbose) printf("vidixlib: '%s'successfully loaded\n",drv_name); | |
3991 | 242 return stream; |
243 } | |
244 | |
245 void vdlClose(VDL_HANDLE stream) | |
246 { | |
247 if(t_vdl(stream)->destroy) t_vdl(stream)->destroy(); | |
248 dlclose(t_vdl(stream)->handle); | |
249 memset(stream,0,sizeof(vdl_stream_t)); /* <- it's not stupid */ | |
250 free(stream); | |
251 } | |
252 | |
253 int vdlGetCapability(VDL_HANDLE handle, vidix_capability_t *cap) | |
254 { | |
255 return t_vdl(handle)->get_caps(cap); | |
256 } | |
257 | |
4539 | 258 #define MPLAYER_IMGFMT_RGB (('R'<<24)|('G'<<16)|('B'<<8)) |
259 #define MPLAYER_IMGFMT_BGR (('B'<<24)|('G'<<16)|('R'<<8)) | |
260 #define MPLAYER_IMGFMT_RGB_MASK 0xFFFFFF00 | |
261 | |
4547 | 262 static uint32_t normalize_fourcc(uint32_t fourcc) |
4539 | 263 { |
264 if((fourcc & MPLAYER_IMGFMT_RGB_MASK) == (MPLAYER_IMGFMT_RGB|0) || | |
265 (fourcc & MPLAYER_IMGFMT_RGB_MASK) == (MPLAYER_IMGFMT_BGR|0)) | |
266 return bswap_32(fourcc); | |
267 else return fourcc; | |
268 } | |
269 | |
3991 | 270 int vdlQueryFourcc(VDL_HANDLE handle,vidix_fourcc_t *f) |
271 { | |
4547 | 272 f->fourcc = normalize_fourcc(f->fourcc); |
3991 | 273 return t_vdl(handle)->query_fourcc(f); |
274 } | |
275 | |
3995 | 276 int vdlConfigPlayback(VDL_HANDLE handle,vidix_playback_t *p) |
3991 | 277 { |
4547 | 278 p->fourcc = normalize_fourcc(p->fourcc); |
3991 | 279 return t_vdl(handle)->config_playback(p); |
280 } | |
281 | |
282 int vdlPlaybackOn(VDL_HANDLE handle) | |
283 { | |
284 return t_vdl(handle)->playback_on(); | |
285 } | |
286 | |
287 int vdlPlaybackOff(VDL_HANDLE handle) | |
288 { | |
289 return t_vdl(handle)->playback_off(); | |
290 } | |
291 | |
292 int vdlPlaybackFrameSelect(VDL_HANDLE handle, unsigned frame_idx ) | |
293 { | |
294 return t_vdl(handle)->frame_sel ? t_vdl(handle)->frame_sel(frame_idx) : ENOSYS; | |
295 } | |
296 | |
297 int vdlPlaybackGetEq(VDL_HANDLE handle, vidix_video_eq_t * e) | |
298 { | |
299 return t_vdl(handle)->get_eq ? t_vdl(handle)->get_eq(e) : ENOSYS; | |
300 } | |
301 | |
302 int vdlPlaybackSetEq(VDL_HANDLE handle, const vidix_video_eq_t * e) | |
303 { | |
304 return t_vdl(handle)->set_eq ? t_vdl(handle)->set_eq(e) : ENOSYS; | |
305 } | |
306 | |
307 int vdlPlaybackCopyFrame(VDL_HANDLE handle, const vidix_dma_t * f) | |
308 { | |
309 return t_vdl(handle)->copy_frame ? t_vdl(handle)->copy_frame(f) : ENOSYS; | |
310 } | |
4070
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
311 |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
312 int vdlGetGrKeys(VDL_HANDLE handle, vidix_grkey_t * k) |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
313 { |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
314 return t_vdl(handle)->get_gkey ? t_vdl(handle)->get_gkey(k) : ENOSYS; |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
315 } |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
316 |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
317 int vdlSetGrKeys(VDL_HANDLE handle, const vidix_grkey_t * k) |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
318 { |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
319 return t_vdl(handle)->set_gkey ? t_vdl(handle)->set_gkey(k) : ENOSYS; |
b61ba6c256dd
Minor interface changes: color and video keys are moved out from playback configuring
nick
parents:
4011
diff
changeset
|
320 } |
4191 | 321 |
322 int vdlPlaybackGetDeint(VDL_HANDLE handle, vidix_deinterlace_t * d) | |
323 { | |
324 return t_vdl(handle)->get_deint ? t_vdl(handle)->get_deint(d) : ENOSYS; | |
325 } | |
326 | |
327 int vdlPlaybackSetDeint(VDL_HANDLE handle, const vidix_deinterlace_t * d) | |
328 { | |
329 return t_vdl(handle)->set_deint ? t_vdl(handle)->set_deint(d) : ENOSYS; | |
330 } | |
331 | |
332 int vdlQueryNumOemEffects(VDL_HANDLE handle, unsigned * number ) | |
333 { | |
334 return t_vdl(handle)->get_num_fx ? t_vdl(handle)->get_num_fx(number) : ENOSYS; | |
335 } | |
336 | |
337 int vdlGetOemEffect(VDL_HANDLE handle, vidix_oem_fx_t * f) | |
338 { | |
339 return t_vdl(handle)->get_fx ? t_vdl(handle)->get_fx(f) : ENOSYS; | |
340 } | |
341 | |
342 int vdlSetOemEffect(VDL_HANDLE handle, const vidix_oem_fx_t * f) | |
343 { | |
344 return t_vdl(handle)->set_fx ? t_vdl(handle)->set_fx(f) : ENOSYS; | |
345 } |