root/trunk/ACPublic/ACBaseCodec.cpp

Revision 1, 16.3 kB (checked in by gbooker, 3 years ago)

Initial Import

Line 
1 /*      Copyright:      © Copyright 2004 Apple Computer, Inc. All rights reserved.
2
3         Disclaimer:     IMPORTANT:  This Apple software is supplied to you by Apple Computer, Inc.
4                         ("Apple") in consideration of your agreement to the following terms, and your
5                         use, installation, modification or redistribution of this Apple software
6                         constitutes acceptance of these terms.  If you do not agree with these terms,
7                         please do not use, install, modify or redistribute this Apple software.
8
9                         In consideration of your agreement to abide by the following terms, and subject
10                         to these terms, Apple grants you a personal, non-exclusive license, under AppleÕs
11                         copyrights in this original Apple software (the "Apple Software"), to use,
12                         reproduce, modify and redistribute the Apple Software, with or without
13                         modifications, in source and/or binary forms; provided that if you redistribute
14                         the Apple Software in its entirety and without modifications, you must retain
15                         this notice and the following text and disclaimers in all such redistributions of
16                         the Apple Software.  Neither the name, trademarks, service marks or logos of
17                         Apple Computer, Inc. may be used to endorse or promote products derived from the
18                         Apple Software without specific prior written permission from Apple.  Except as
19                         expressly stated in this notice, no other rights or licenses, express or implied,
20                         are granted by Apple herein, including but not limited to any patent rights that
21                         may be infringed by your derivative works or by other works in which the Apple
22                         Software may be incorporated.
23
24                         The Apple Software is provided by Apple on an "AS IS" basis.  APPLE MAKES NO
25                         WARRANTIES, EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION THE IMPLIED
26                         WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
27                         PURPOSE, REGARDING THE APPLE SOFTWARE OR ITS USE AND OPERATION ALONE OR IN
28                         COMBINATION WITH YOUR PRODUCTS.
29
30                         IN NO EVENT SHALL APPLE BE LIABLE FOR ANY SPECIAL, INDIRECT, INCIDENTAL OR
31                         CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
32                         GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33                         ARISING IN ANY WAY OUT OF THE USE, REPRODUCTION, MODIFICATION AND/OR DISTRIBUTION
34                         OF THE APPLE SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF CONTRACT, TORT
35                         (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF APPLE HAS BEEN
36                         ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
37 */
38 /*=============================================================================
39         ACBaseCodec.cpp
40
41 =============================================================================*/
42
43 //=============================================================================
44 //      Includes
45 //=============================================================================
46
47 #include "ACBaseCodec.h"
48 #include <algorithm>
49
50 //=============================================================================
51 //      ACBaseCodec
52 //=============================================================================
53
54 ACBaseCodec::ACBaseCodec()
55 :
56         ACCodec(),
57         mIsInitialized(false),
58         mInputFormatList(),
59         mInputFormat(),
60         mOutputFormatList(),
61         mOutputFormat()
62 {
63 }
64
65 ACBaseCodec::~ACBaseCodec()
66 {
67 }
68
69 void    ACBaseCodec::GetPropertyInfo(AudioCodecPropertyID inPropertyID, UInt32& outPropertyDataSize, bool& outWritable)
70 {
71         switch(inPropertyID)
72         {
73                 case kAudioCodecPropertyNameCFString:
74                         outPropertyDataSize = sizeof(CFStringRef);
75                         outWritable = false;
76                         break;
77                 case kAudioCodecPropertyManufacturerCFString:
78                         outPropertyDataSize = sizeof(CFStringRef);
79                         outWritable = false;
80                         break;
81                 case kAudioCodecPropertyMinimumNumberInputPackets :
82                         outPropertyDataSize = sizeof(UInt32);
83                         outWritable = false;
84                         break;
85                 case kAudioCodecPropertyMinimumNumberOutputPackets :
86                         outPropertyDataSize = sizeof(UInt32);
87                         outWritable = false;
88                         break;
89                 case kAudioCodecPropertyInputChannelLayout :
90                 case kAudioCodecPropertyOutputChannelLayout :
91                         // by default a codec doesn't support channel layouts.
92                         CODEC_THROW(kAudioCodecIllegalOperationError);
93                         break;
94                 case kAudioCodecPropertyAvailableInputChannelLayouts :
95                 case kAudioCodecPropertyAvailableOutputChannelLayouts :
96                         // by default a codec doesn't support channel layouts.
97                         CODEC_THROW(kAudioCodecIllegalOperationError);
98                         break;
99
100                 case kAudioCodecPropertyCurrentInputFormat:
101                         outPropertyDataSize = sizeof(AudioStreamBasicDescription);
102                         outWritable = !mIsInitialized;
103                         break;
104                        
105                 case kAudioCodecPropertySupportedInputFormats:
106                         outPropertyDataSize = GetNumberSupportedInputFormats() * sizeof(AudioStreamBasicDescription);
107                         outWritable = false;
108                         break;
109                        
110                 case kAudioCodecPropertyCurrentOutputFormat:
111                         outPropertyDataSize = sizeof(AudioStreamBasicDescription);
112                         outWritable = !mIsInitialized;
113                         break;
114                        
115                 case kAudioCodecPropertySupportedOutputFormats:
116                         outPropertyDataSize = GetNumberSupportedOutputFormats() * sizeof(AudioStreamBasicDescription);
117                         outWritable = false;
118                         break;
119                        
120                 case kAudioCodecPropertyMagicCookie:
121                         outPropertyDataSize = GetMagicCookieByteSize();
122                         outWritable = !mIsInitialized;
123                         break;
124                        
125                 case kAudioCodecPropertyInputBufferSize:
126                         outPropertyDataSize = sizeof(UInt32);
127                         outWritable = true;
128                         break;
129                        
130                 case kAudioCodecPropertyUsedInputBufferSize:
131                         outPropertyDataSize = sizeof(UInt32);
132                         outWritable = false;
133                         break;
134                
135                 case kAudioCodecPropertyIsInitialized:
136                         outPropertyDataSize = sizeof(UInt32);
137                         outWritable = false;
138                         break;
139
140                 case kAudioCodecPropertyAvailableNumberChannels:
141                         outPropertyDataSize = sizeof(UInt32) * 2; // Mono, stereo
142                         outWritable = false;
143                         break;
144                        
145                 case kAudioCodecPropertyPrimeMethod:
146                         outPropertyDataSize = sizeof(UInt32);
147                         outWritable = false;
148                         break;
149
150                 case kAudioCodecPropertyPrimeInfo:
151                         outPropertyDataSize = sizeof(AudioCodecPrimeInfo);
152                         outWritable = false;
153                         break;
154                        
155                 default:
156                         CODEC_THROW(kAudioCodecUnknownPropertyError);
157                         break;
158                        
159         };
160 }
161
162 void    ACBaseCodec::GetProperty(AudioCodecPropertyID inPropertyID, UInt32& ioPropertyDataSize, void* outPropertyData)
163 {
164         UInt32 thePacketsToGet;
165        
166         switch(inPropertyID)
167         {
168                 case kAudioCodecPropertyNameCFString:
169                 {
170                         if (ioPropertyDataSize != sizeof(CFStringRef)) CODEC_THROW(kAudioCodecBadPropertySizeError);
171                        
172                         CFStringRef name = CFCopyLocalizedStringFromTableInBundle(CFSTR("unknown codec"), CFSTR("CodecNames"), GetCodecBundle(), CFSTR(""));
173                         *(CFStringRef*)outPropertyData = name;
174                         break;
175                 }
176                 case kAudioCodecPropertyManufacturerCFString:
177                 {
178                         if (ioPropertyDataSize != sizeof(CFStringRef)) CODEC_THROW(kAudioCodecBadPropertySizeError);
179                        
180                         CFStringRef name = CFCopyLocalizedStringFromTableInBundle(CFSTR("Apple Computer, Inc."), CFSTR("CodecNames"), GetCodecBundle(), CFSTR(""));
181                         *(CFStringRef*)outPropertyData = name;
182                         break;
183                 }
184                 case kAudioCodecPropertyMinimumNumberInputPackets :
185                         if(ioPropertyDataSize != sizeof(UInt32)) CODEC_THROW(kAudioCodecBadPropertySizeError);
186                         *(UInt32*)outPropertyData = 1;
187                         break;
188                 case kAudioCodecPropertyMinimumNumberOutputPackets :
189                         if(ioPropertyDataSize != sizeof(UInt32)) CODEC_THROW(kAudioCodecBadPropertySizeError);
190                         *(UInt32*)outPropertyData = 1;
191                         break;
192                        
193                 case kAudioCodecPropertyInputChannelLayout :
194                 case kAudioCodecPropertyOutputChannelLayout :
195                         // by default a codec doesn't support channel layouts.
196                         CODEC_THROW(kAudioCodecIllegalOperationError);
197                         break;
198                 case kAudioCodecPropertyAvailableInputChannelLayouts :
199                 case kAudioCodecPropertyAvailableOutputChannelLayouts :
200                         // by default a codec doesn't support channel layouts.
201                         CODEC_THROW(kAudioCodecIllegalOperationError);
202                         break;
203                        
204                 case kAudioCodecPropertyCurrentInputFormat:
205                         if(ioPropertyDataSize == sizeof(AudioStreamBasicDescription))
206                         {
207                                 GetCurrentInputFormat(*reinterpret_cast<AudioStreamBasicDescription*>(outPropertyData));
208                         }
209                         else
210                         {
211                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
212                         }
213                         break;
214                        
215                 case kAudioCodecPropertySupportedInputFormats:
216                         thePacketsToGet = ioPropertyDataSize / sizeof(AudioStreamBasicDescription);
217                         GetSupportedInputFormats(reinterpret_cast<AudioStreamBasicDescription*>(outPropertyData), thePacketsToGet);
218                         ioPropertyDataSize = thePacketsToGet * sizeof(AudioStreamBasicDescription);
219                         break;
220                        
221                 case kAudioCodecPropertyCurrentOutputFormat:
222                         if(ioPropertyDataSize == sizeof(AudioStreamBasicDescription))
223                         {
224                                 GetCurrentOutputFormat(*reinterpret_cast<AudioStreamBasicDescription*>(outPropertyData));
225                         }
226                         else
227                         {
228                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
229                         }
230                         break;
231                        
232                 case kAudioCodecPropertySupportedOutputFormats:
233                         thePacketsToGet = ioPropertyDataSize / sizeof(AudioStreamBasicDescription);
234                         GetSupportedOutputFormats(reinterpret_cast<AudioStreamBasicDescription*>(outPropertyData), thePacketsToGet);
235                         ioPropertyDataSize = thePacketsToGet * sizeof(AudioStreamBasicDescription);
236                         break;
237                        
238                 case kAudioCodecPropertyMagicCookie:
239                         if(ioPropertyDataSize >= GetMagicCookieByteSize())
240                         {
241                                 GetMagicCookie(outPropertyData, ioPropertyDataSize);
242                         }
243                         else
244                         {
245                                 CODEC_THROW(kAudioCodecIllegalOperationError);
246                         }
247                         break;
248                        
249                 case kAudioCodecPropertyInputBufferSize:
250                         if(ioPropertyDataSize == sizeof(UInt32))
251                         {
252                                 *reinterpret_cast<UInt32*>(outPropertyData) = GetInputBufferByteSize();
253                         }
254                         else
255                         {
256                                 CODEC_THROW(kAudioCodecIllegalOperationError);
257                         }
258                         break;
259                        
260                 case kAudioCodecPropertyUsedInputBufferSize:
261                         if(ioPropertyDataSize == sizeof(UInt32))
262                         {
263                                 *reinterpret_cast<UInt32*>(outPropertyData) = GetUsedInputBufferByteSize();
264                         }
265                         else
266                         {
267                                 CODEC_THROW(kAudioCodecIllegalOperationError);
268                         }
269                         break;
270                        
271                 case kAudioCodecPropertyIsInitialized:
272                         if(ioPropertyDataSize == sizeof(UInt32))
273                         {
274                                 *reinterpret_cast<UInt32*>(outPropertyData) = IsInitialized() ? 1 : 0;
275                         }
276                         else
277                         {
278                                 CODEC_THROW(kAudioCodecIllegalOperationError);
279                         }
280                         break;
281                        
282         case kAudioCodecPropertyAvailableNumberChannels:
283                         if(ioPropertyDataSize == sizeof(UInt32) * 2)
284                         {
285                                 (reinterpret_cast<UInt32*>(outPropertyData))[0] = 1;
286                                 (reinterpret_cast<UInt32*>(outPropertyData))[1] = 2;
287                         }
288                         else
289                         {
290                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
291                         }
292                         break;
293
294         case kAudioCodecPropertyPrimeMethod:
295                         if(ioPropertyDataSize == sizeof(UInt32))
296                         {
297                                 *reinterpret_cast<UInt32*>(outPropertyData) = (UInt32)kAudioCodecPrimeMethod_None;
298                         }
299                         else
300                         {
301                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
302                         }
303                         break;
304
305                 case kAudioCodecPropertyPrimeInfo:
306                         if(ioPropertyDataSize == sizeof(AudioCodecPrimeInfo) )
307                         {
308                                 (reinterpret_cast<AudioCodecPrimeInfo*>(outPropertyData))->leadingFrames = 0;
309                                 (reinterpret_cast<AudioCodecPrimeInfo*>(outPropertyData))->trailingFrames = 0;
310                         }
311                         else
312                         {
313                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
314                         }
315                         break;
316
317                 default:
318                         CODEC_THROW(kAudioCodecUnknownPropertyError);
319                         break;
320                        
321         };
322 }
323
324 void    ACBaseCodec::SetProperty(AudioCodecPropertyID inPropertyID, UInt32 inPropertyDataSize, const void* inPropertyData)
325 {
326         switch(inPropertyID)
327         {
328                 case kAudioCodecPropertyMinimumNumberInputPackets :
329                         CODEC_THROW(kAudioCodecIllegalOperationError);
330                         break;
331                 case kAudioCodecPropertyMinimumNumberOutputPackets :
332                         CODEC_THROW(kAudioCodecIllegalOperationError);
333                         break;
334
335                 case kAudioCodecPropertyInputChannelLayout :
336                 case kAudioCodecPropertyOutputChannelLayout :
337                         // by default a codec doesn't support channel layouts.
338                         CODEC_THROW(kAudioCodecIllegalOperationError);
339                         break;
340
341                 case kAudioCodecPropertyAvailableInputChannelLayouts :
342                 case kAudioCodecPropertyAvailableOutputChannelLayouts :
343                         // by default a codec doesn't support channel layouts.
344                         CODEC_THROW(kAudioCodecIllegalOperationError);
345                         break;
346
347                 case kAudioCodecPropertyCurrentInputFormat:
348                         if(inPropertyDataSize == sizeof(AudioStreamBasicDescription))
349                         {
350                                 SetCurrentInputFormat(*reinterpret_cast<const AudioStreamBasicDescription*>(inPropertyData));
351                         }
352                         else
353                         {
354                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
355                         }
356                         break;
357                        
358                 case kAudioCodecPropertyCurrentOutputFormat:
359                         if(inPropertyDataSize == sizeof(AudioStreamBasicDescription))
360                         {
361                                 SetCurrentOutputFormat(*reinterpret_cast<const AudioStreamBasicDescription*>(inPropertyData));
362                         }
363                         else
364                         {
365                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
366                         }
367                         break;
368                        
369                 case kAudioCodecPropertyMagicCookie:
370                         SetMagicCookie(inPropertyData, inPropertyDataSize);
371                         break;
372                        
373                 case kAudioCodecPropertyInputBufferSize:
374                         if(inPropertyDataSize == sizeof(UInt32))
375                         {
376                                 ReallocateInputBuffer(*reinterpret_cast<const UInt32*>(inPropertyData));
377                         }
378                         else
379                         {
380                                 CODEC_THROW(kAudioCodecBadPropertySizeError);
381                         }
382                         break;
383                        
384                 case kAudioCodecPropertySupportedInputFormats:
385                 case kAudioCodecPropertySupportedOutputFormats:
386                 case kAudioCodecPropertyUsedInputBufferSize:
387                 case kAudioCodecPropertyIsInitialized:
388                 case kAudioCodecPropertyAvailableNumberChannels:
389                 case kAudioCodecPropertyPrimeMethod:
390                 case kAudioCodecPropertyPrimeInfo:
391                         CODEC_THROW(kAudioCodecIllegalOperationError);
392                         break;
393                        
394                 default:
395                         CODEC_THROW(kAudioCodecUnknownPropertyError);
396                         break;
397                        
398         };
399 }
400
401 void    ACBaseCodec::Initialize(const AudioStreamBasicDescription* inInputFormat, const AudioStreamBasicDescription* inOutputFormat, const void* inMagicCookie, UInt32 inMagicCookieByteSize)
402 {
403         mIsInitialized = true;
404 }
405
406 void    ACBaseCodec::Uninitialize()
407 {
408         mIsInitialized = false;
409 }
410
411 void    ACBaseCodec::Reset()
412 {
413 }
414
415 UInt32  ACBaseCodec::GetNumberSupportedInputFormats() const
416 {
417         return mInputFormatList.size();
418 }
419
420 void    ACBaseCodec::GetSupportedInputFormats(AudioStreamBasicDescription* outInputFormats, UInt32& ioNumberInputFormats) const
421 {
422         UInt32 theNumberFormats = mInputFormatList.size();
423         ioNumberInputFormats = (theNumberFormats < ioNumberInputFormats) ? theNumberFormats : ioNumberInputFormats;
424        
425         FormatList::const_iterator theIterator = mInputFormatList.begin();
426         theNumberFormats = ioNumberInputFormats;
427         while((theNumberFormats > 0) && (theIterator != mInputFormatList.end()))
428         {
429                 *outInputFormats = *theIterator;
430                
431                 ++outInputFormats;
432                 --theNumberFormats;
433                 std::advance(theIterator, 1);
434         }
435 }
436
437 void    ACBaseCodec::GetCurrentInputFormat(AudioStreamBasicDescription& outInputFormat)
438 {
439         outInputFormat = mInputFormat;
440 }
441
442 void    ACBaseCodec::SetCurrentInputFormat(const AudioStreamBasicDescription& inInputFormat)
443 {
444         if(!mIsInitialized)
445         {
446                 mInputFormat = inInputFormat;
447         }
448         else
449         {
450                 CODEC_THROW(kAudioCodecStateError);
451         }
452 }
453
454 UInt32  ACBaseCodec::GetNumberSupportedOutputFormats() const
455 {
456         return mOutputFormatList.size();
457 }
458
459 void    ACBaseCodec::GetSupportedOutputFormats(AudioStreamBasicDescription* outOutputFormats, UInt32& ioNumberOutputFormats) const
460 {
461         UInt32 theNumberFormats = mOutputFormatList.size();
462         ioNumberOutputFormats = (theNumberFormats < ioNumberOutputFormats) ? theNumberFormats : ioNumberOutputFormats;
463        
464         FormatList::const_iterator theIterator = mOutputFormatList.begin();
465         theNumberFormats = ioNumberOutputFormats;
466         while((theNumberFormats > 0) && (theIterator != mOutputFormatList.end()))
467         {
468                 *outOutputFormats = *theIterator;
469                
470                 ++outOutputFormats;
471                 --theNumberFormats;
472                 std::advance(theIterator, 1);
473         }
474 }
475
476 void    ACBaseCodec::GetCurrentOutputFormat(AudioStreamBasicDescription& outOutputFormat)
477 {
478         outOutputFormat = mOutputFormat;
479 }
480
481 void    ACBaseCodec::SetCurrentOutputFormat(const AudioStreamBasicDescription& inOutputFormat)
482 {
483         if(!mIsInitialized)
484         {
485                 mOutputFormat = inOutputFormat;
486         }
487         else
488         {
489                 CODEC_THROW(kAudioCodecStateError);
490         }
491 }
492
493 UInt32  ACBaseCodec::GetMagicCookieByteSize() const
494 {
495         return 0;
496 }
497
498 void    ACBaseCodec::GetMagicCookie(void* outMagicCookieData, UInt32& ioMagicCookieDataByteSize) const
499 {
500 }
501
502 void    ACBaseCodec::SetMagicCookie(const void* outMagicCookieData, UInt32 inMagicCookieDataByteSize)
503 {
504         if(mIsInitialized)
505         {
506                 CODEC_THROW(kAudioCodecStateError);
507         }
508 }
509
510 void    ACBaseCodec::AddInputFormat(const AudioStreamBasicDescription& inInputFormat)
511 {
512         FormatList::iterator theIterator = std::find(mInputFormatList.begin(), mInputFormatList.end(), inInputFormat);
513         if(theIterator == mInputFormatList.end())
514         {
515                 theIterator = std::lower_bound(mInputFormatList.begin(), mInputFormatList.end(), inInputFormat);
516                 mInputFormatList.insert(theIterator, inInputFormat);
517         }
518 }
519
520 void    ACBaseCodec::AddOutputFormat(const AudioStreamBasicDescription& inOutputFormat)
521 {
522         FormatList::iterator theIterator = std::find(mOutputFormatList.begin(), mOutputFormatList.end(), inOutputFormat);
523         if(theIterator == mOutputFormatList.end())
524         {
525                 theIterator = std::lower_bound(mOutputFormatList.begin(), mOutputFormatList.end(), inOutputFormat);
526                 mOutputFormatList.insert(theIterator, inOutputFormat);
527         }
528 }
Note: See TracBrowser for help on using the browser.