Mercurial > mplayer.hg
annotate libao2/ao_plugin.c @ 3571:ceaccd11b8ec
VP30 added - report by Mark Janssen <maniac@maniac.nl>
author | arpi |
---|---|
date | Mon, 17 Dec 2001 22:09:56 +0000 |
parents | 9eaee0d257e1 |
children | 2cc5737ec923 |
rev | line source |
---|---|
3096 | 1 #include <stdio.h> |
2 #include <stdlib.h> | |
3 | |
4 #include "../config.h" | |
5 | |
3194
1648d11fc36c
commandline configuration of audio plugins now through struct, format conversion plugin added
anders
parents:
3107
diff
changeset
|
6 #include "afmt.h" |
3096 | 7 #include "audio_out.h" |
8 #include "audio_out_internal.h" | |
9 | |
10 #include "audio_plugin.h" | |
11 | |
12 static ao_info_t info = | |
13 { | |
14 "Plugin audio output", | |
15 "plugin", | |
16 "Anders", | |
17 "" | |
18 }; | |
19 | |
20 LIBAO_EXTERN(plugin) | |
21 | |
3107 | 22 #define plugin(i) (ao_plugin_local_data.plugins[i]) |
23 #define driver() (ao_plugin_local_data.driver) | |
3096 | 24 |
3107 | 25 // local data |
3096 | 26 typedef struct ao_plugin_local_data_s |
27 { | |
3107 | 28 ao_functions_t* driver; // Output driver set in mplayer.c |
29 ao_plugin_functions_t** plugins; // List of used plugins | |
3194
1648d11fc36c
commandline configuration of audio plugins now through struct, format conversion plugin added
anders
parents:
3107
diff
changeset
|
30 ao_plugin_functions_t* available_plugins[NPL]; // List of available plugins |
3096 | 31 } ao_plugin_local_data_t; |
32 | |
3308 | 33 static ao_plugin_local_data_t ao_plugin_local_data={NULL,NULL,AO_PLUGINS}; |
3096 | 34 |
3107 | 35 // gloabal data |
3308 | 36 volatile ao_plugin_data_t ao_plugin_data; // data used by the plugins |
37 volatile ao_plugin_cfg_t ao_plugin_cfg=CFG_DEFAULTS; // cfg data set in cfg-mplayer.h | |
3096 | 38 |
39 // to set/get/query special features/parameters | |
40 static int control(int cmd,int arg){ | |
3107 | 41 switch(cmd){ |
42 case AOCONTROL_SET_PLUGIN_DRIVER: | |
43 ao_plugin_local_data.driver=(ao_functions_t*)arg; | |
44 return CONTROL_OK; | |
45 default: | |
46 return driver()->control(cmd,arg); | |
47 } | |
48 return CONTROL_UNKNOWN; | |
49 } | |
50 | |
51 // Recursive function for adding plugins | |
52 // return 1 for success and 0 for error | |
53 int add_plugin(int i,char* cfg){ | |
54 int cnt=0; | |
55 // Find end of plugin name | |
56 while((cfg[cnt]!=',')&&(cfg[cnt]!='\0')&&(cnt<100)) cnt++; | |
57 if(cnt >= 100) | |
58 return 0; | |
59 | |
60 // Is this the last itteration or just another plugin | |
61 if(cfg[cnt]=='\0'){ | |
62 ao_plugin_local_data.plugins=malloc((i+1)*sizeof(ao_plugin_functions_t*)); | |
63 if(ao_plugin_local_data.plugins){ | |
64 ao_plugin_local_data.plugins[i+1]=NULL; | |
65 // Find the plugin matching the cfg string name | |
66 cnt=0; | |
67 while(ao_plugin_local_data.available_plugins[cnt] && cnt<20){ | |
68 if(0==strcmp(ao_plugin_local_data.available_plugins[cnt]->info->short_name,cfg)){ | |
69 ao_plugin_local_data.plugins[i]=ao_plugin_local_data.available_plugins[cnt]; | |
70 return 1; | |
71 } | |
72 cnt++; | |
73 } | |
74 printf("[plugin]: Invalid plugin: %s \n",cfg); | |
75 return 0; | |
76 } | |
77 else | |
78 return 0; | |
79 } else { | |
80 cfg[cnt]='\0'; | |
81 if(add_plugin(i+1,&cfg[cnt+1])){ | |
82 cnt=0; | |
83 // Find the plugin matching the cfg string name | |
84 while(ao_plugin_local_data.available_plugins[cnt] && cnt < 20){ | |
85 if(0==strcmp(ao_plugin_local_data.available_plugins[cnt]->info->short_name,cfg)){ | |
86 ao_plugin_local_data.plugins[i]=ao_plugin_local_data.available_plugins[cnt]; | |
87 return 1; | |
88 } | |
89 cnt++; | |
90 } | |
91 printf("[plugin]: Invalid plugin: %s \n",cfg); | |
92 return 0; | |
93 } | |
94 else | |
95 return 0; | |
96 } | |
97 return 0; // Will never happen... | |
3096 | 98 } |
99 | |
100 // open & setup audio device and plugins | |
101 // return: 1=success 0=fail | |
102 static int init(int rate,int channels,int format,int flags){ | |
103 int ok=1; | |
104 | |
3107 | 105 /* Create list of plugins from cfg option */ |
3096 | 106 int i=0; |
3194
1648d11fc36c
commandline configuration of audio plugins now through struct, format conversion plugin added
anders
parents:
3107
diff
changeset
|
107 if(ao_plugin_cfg.plugin_list){ |
1648d11fc36c
commandline configuration of audio plugins now through struct, format conversion plugin added
anders
parents:
3107
diff
changeset
|
108 if(!add_plugin(i,ao_plugin_cfg.plugin_list)) |
3107 | 109 return 0; |
110 } | |
3096 | 111 |
112 /* Set input parameters and itterate through plugins each plugin | |
113 changes the parameters according to its output */ | |
114 ao_plugin_data.rate=rate; | |
115 ao_plugin_data.channels=channels; | |
116 ao_plugin_data.format=format; | |
117 ao_plugin_data.sz_mult=1; | |
118 ao_plugin_data.sz_fix=0; | |
119 ao_plugin_data.delay_mult=1; | |
120 ao_plugin_data.delay_fix=0; | |
121 i=0; | |
122 while(plugin(i)&&ok) | |
123 ok=plugin(i++)->init(); | |
124 | |
125 if(!ok) return 0; | |
126 | |
3107 | 127 // This should never happen but check anyway |
128 if(NULL==ao_plugin_local_data.driver) | |
129 return 0; | |
130 | |
3096 | 131 ok = driver()->init(ao_plugin_data.rate, |
3107 | 132 ao_plugin_data.channels, |
133 ao_plugin_data.format, | |
134 flags); | |
3096 | 135 if(!ok) return 0; |
136 | |
137 /* Now that the driver is initialized we can calculate and set the | |
138 input and output buffers for each plugin */ | |
139 ao_plugin_data.len=driver()->get_space(); | |
3107 | 140 while((i>0) && ok) |
3194
1648d11fc36c
commandline configuration of audio plugins now through struct, format conversion plugin added
anders
parents:
3107
diff
changeset
|
141 ok=plugin(--i)->control(AOCONTROL_PLUGIN_SET_LEN,0); |
3107 | 142 |
143 if(!ok) return 0; | |
3096 | 144 |
145 return 1; | |
146 } | |
147 | |
148 // close audio device | |
149 static void uninit(){ | |
150 int i=0; | |
151 driver()->uninit(); | |
152 while(plugin(i)) | |
153 plugin(i++)->uninit(); | |
3107 | 154 if(ao_plugin_local_data.plugins) |
155 free(ao_plugin_local_data.plugins); | |
3096 | 156 } |
157 | |
158 // stop playing and empty buffers (for seeking/pause) | |
159 static void reset(){ | |
160 int i=0; | |
161 driver()->reset(); | |
162 while(plugin(i)) | |
163 plugin(i++)->reset(); | |
164 } | |
165 | |
166 // stop playing, keep buffers (for pause) | |
167 static void audio_pause(){ | |
168 driver()->pause(); | |
169 } | |
170 | |
171 // resume playing, after audio_pause() | |
172 static void audio_resume(){ | |
173 driver()->resume(); | |
174 } | |
175 | |
176 // return: how many bytes can be played without blocking | |
177 static int get_space(){ | |
178 double sz=(double)(driver()->get_space()); | |
179 sz*=ao_plugin_data.sz_mult; | |
180 sz+=ao_plugin_data.sz_fix; | |
181 return (int)(sz); | |
182 } | |
183 | |
184 // plays 'len' bytes of 'data' | |
185 // return: number of bytes played | |
186 static int play(void* data,int len,int flags){ | |
187 int i=0; | |
188 /* Due to constant buffer sizes in plugins limit length */ | |
189 int tmp = get_space(); | |
190 int ret_len =(tmp<len)?tmp:len; | |
191 /* Filter data */ | |
192 ao_plugin_data.len=ret_len; | |
193 ao_plugin_data.data=data; | |
194 while(plugin(i)) | |
195 plugin(i++)->play(); | |
196 /* Send data to output */ | |
3486 | 197 //fprintf(stderr, "ao_plugin: ret_len=%d, len=%d\n", ret_len, len); |
3096 | 198 len=driver()->play(ao_plugin_data.data,ao_plugin_data.len,flags); |
3486 | 199 //fprintf(stderr, "ao_plugin: returned len=%d\n", len); |
3096 | 200 |
201 if(len!=ao_plugin_data.len) | |
3486 | 202 fprintf(stderr,"[ao_plugin] Warning under or over flow in sound plugin\n"); |
3096 | 203 |
204 return ret_len; | |
205 } | |
206 | |
207 // return: delay in seconds between first and last sample in buffer | |
208 static float get_delay(){ | |
209 float delay=driver()->get_delay(); | |
210 delay*=ao_plugin_data.delay_mult; | |
211 delay+=ao_plugin_data.delay_fix; | |
212 return delay; | |
213 } | |
214 | |
215 | |
3279
d6ea11bed983
Commandline interface to ao_plugin updated according to mplayers complex parameter format and plugin pl_format finished (alpha code needs testing)
anders
parents:
3194
diff
changeset
|
216 |
d6ea11bed983
Commandline interface to ao_plugin updated according to mplayers complex parameter format and plugin pl_format finished (alpha code needs testing)
anders
parents:
3194
diff
changeset
|
217 |