alternative new version of the AppleUtility library
[ardour.git] / libs / appleutility / CoreAudio / AudioFile / AFPublic / DataSource.h
1 /*
2      File: DataSource.h
3  Abstract: Part of CoreAudio Utility Classes
4   Version: 1.1
5  
6  Disclaimer: IMPORTANT:  This Apple software is supplied to you by Apple
7  Inc. ("Apple") in consideration of your agreement to the following
8  terms, and your use, installation, modification or redistribution of
9  this Apple software constitutes acceptance of these terms.  If you do
10  not agree with these terms, please do not use, install, modify or
11  redistribute this Apple software.
12  
13  In consideration of your agreement to abide by the following terms, and
14  subject to these terms, Apple grants you a personal, non-exclusive
15  license, under Apple's copyrights in this original Apple software (the
16  "Apple Software"), to use, reproduce, modify and redistribute the Apple
17  Software, with or without modifications, in source and/or binary forms;
18  provided that if you redistribute the Apple Software in its entirety and
19  without modifications, you must retain this notice and the following
20  text and disclaimers in all such redistributions of the Apple Software.
21  Neither the name, trademarks, service marks or logos of Apple Inc. may
22  be used to endorse or promote products derived from the Apple Software
23  without specific prior written permission from Apple.  Except as
24  expressly stated in this notice, no other rights or licenses, express or
25  implied, are granted by Apple herein, including but not limited to any
26  patent rights that may be infringed by your derivative works or by other
27  works in which the Apple Software may be incorporated.
28  
29  The Apple Software is provided by Apple on an "AS IS" basis.  APPLE
30  MAKES NO WARRANTIES, EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION
31  THE IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY AND FITNESS
32  FOR A PARTICULAR PURPOSE, REGARDING THE APPLE SOFTWARE OR ITS USE AND
33  OPERATION ALONE OR IN COMBINATION WITH YOUR PRODUCTS.
34  
35  IN NO EVENT SHALL APPLE BE LIABLE FOR ANY SPECIAL, INDIRECT, INCIDENTAL
36  OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
37  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
38  INTERRUPTION) ARISING IN ANY WAY OUT OF THE USE, REPRODUCTION,
39  MODIFICATION AND/OR DISTRIBUTION OF THE APPLE SOFTWARE, HOWEVER CAUSED
40  AND WHETHER UNDER THEORY OF CONTRACT, TORT (INCLUDING NEGLIGENCE),
41  STRICT LIABILITY OR OTHERWISE, EVEN IF APPLE HAS BEEN ADVISED OF THE
42  POSSIBILITY OF SUCH DAMAGE.
43  
44  Copyright (C) 2014 Apple Inc. All Rights Reserved.
45  
46 */
47 #ifndef __DataSource_h__
48 #define __DataSource_h__
49
50 #if !defined(__COREAUDIO_USE_FLAT_INCLUDES__)
51         #include <AudioToolbox/AudioFile.h>
52 #else
53         #include <ConditionalMacros.h>
54         #include "AudioFile.h"
55 #endif
56 #include <stdlib.h>
57 #include <stdio.h>
58 #include <stdexcept>
59 #include "CAAutoDisposer.h"
60
61 //////////////////////////////////////////////////////////////////////////////////////////
62
63 class DataSource
64 {
65 public:
66         
67         DataSource(Boolean inCloseOnDelete);
68         virtual ~DataSource();
69                 
70         virtual OSStatus GetSize32(UInt32& outSize)
71         {
72                 SInt64 size64;
73                 OSStatus err = GetSize(size64);
74                 if (err) return err;
75                 if (size64 > 0x00000000FFFFffffLL) return kAudioFileDoesNotAllow64BitDataSizeError;
76                 outSize = (UInt32)size64;
77                 return noErr;
78         }
79         
80         virtual OSStatus GetSize(SInt64& outSize) =0;
81         
82         virtual OSStatus SetSize(SInt64 inSize)=0;
83         
84         virtual OSStatus GetPos(SInt64& outPos) const=0; 
85         
86         /* non seekable data sources should use fsAtMark for the positionMode (or SEEK_CUR with offset zero, 
87                 or SEEK_SET with offset equal to the current position in the stream, in other words no seeking from the 
88                 current position is allowed.)
89         */
90         
91         virtual OSStatus ReadBytes(     UInt16 positionMode, 
92                                                                 SInt64 positionOffset, 
93                                                                 UInt32 requestCount, 
94                                                                 void *buffer, 
95                                                                 UInt32* actualCount)=0;
96                                                 
97         virtual OSStatus WriteBytes(UInt16 positionMode, 
98                                                                 SInt64 positionOffset, 
99                                                                 UInt32 requestCount, 
100                                                                 const void *buffer, 
101                                                                 UInt32* actualCount)=0;
102         
103         virtual void SetCloseOnDelete(Boolean inFlag) { mCloseOnDelete = inFlag; }
104         
105         virtual Boolean CanSeek() const=0;
106         virtual Boolean CanGetSize() const=0;
107         virtual Boolean CanSetSize() const=0;
108         virtual Boolean CanRead() const=0;
109         virtual Boolean CanWrite() const=0;
110         
111 protected:
112         Boolean mCloseOnDelete;
113         
114         /* utility method */
115         SInt64 CalcOffset(      UInt16 positionMode, 
116                                                 SInt64 positionOffset,
117                                                 SInt64 currentOffset,
118                                                 SInt64 size);
119 };
120
121 //////////////////////////////////////////////////////////////////////////////////////////
122 //////////////////////////////////////////////////////////////////////////////////////////
123
124 /*
125         Initialize with a Macintosh file fork ref num as obtained from FSOpenFork.
126 */
127
128 #if 0
129
130 class MacFile_DataSource : public DataSource
131 {
132         FSIORefNum mFileNum;
133         SInt8 mPermissions;
134         
135 public:
136
137         MacFile_DataSource(     FSIORefNum inForkRefNum, SInt8 inPermissions, Boolean inCloseOnDelete);
138         virtual ~MacFile_DataSource();
139         
140         virtual OSStatus GetSize(SInt64& outSize);
141         virtual OSStatus GetPos(SInt64& outPos) const; 
142         
143         virtual OSStatus SetSize(SInt64 inSize);
144         
145         virtual OSStatus ReadBytes(     UInt16 positionMode, 
146                                                                 SInt64 positionOffset, 
147                                                                 UInt32 requestCount, 
148                                                                 void *buffer, 
149                                                                 UInt32* actualCount);
150                                                 
151         virtual OSStatus WriteBytes(UInt16 positionMode, 
152                                                                 SInt64 positionOffset, 
153                                                                 UInt32 requestCount, 
154                                                                 const void *buffer, 
155                                                                 UInt32* actualCount);
156         
157         virtual Boolean CanSeek() const { return true; }
158         virtual Boolean CanGetSize() const { return true; }
159         virtual Boolean CanSetSize() const { return true; }
160         
161         virtual Boolean CanRead() const { return mPermissions & kAudioFileReadPermission; }
162         virtual Boolean CanWrite() const { return mPermissions & kAudioFileWritePermission; }
163 };
164 #endif
165
166
167 class UnixFile_DataSource : public DataSource
168 {
169         int       mFileD;
170         SInt8 mPermissions;
171         UInt32 mNoCache;
172         SInt64 mCachedSize;
173         SInt64 mFilePointer;
174         
175 public:
176
177         UnixFile_DataSource( int inFD, SInt8 inPermissions, Boolean inCloseOnDelete);
178         virtual ~UnixFile_DataSource();
179         
180         virtual OSStatus GetSize(SInt64& outSize);
181         virtual OSStatus GetPos(SInt64& outPos) const; 
182         
183         virtual OSStatus SetSize(SInt64 inSize);
184         
185         virtual OSStatus ReadBytes(     UInt16 positionMode, 
186                                                                 SInt64 positionOffset, 
187                                                                 UInt32 requestCount, 
188                                                                 void *buffer, 
189                                                                 UInt32* actualCount);
190                                                 
191         virtual OSStatus WriteBytes(UInt16 positionMode, 
192                                                                 SInt64 positionOffset, 
193                                                                 UInt32 requestCount, 
194                                                                 const void *buffer, 
195                                                                 UInt32* actualCount);
196         
197         virtual Boolean CanSeek() const { return true; }
198         virtual Boolean CanGetSize() const { return true; }
199         virtual Boolean CanSetSize() const { return true; }
200         
201         virtual Boolean CanRead() const { return mPermissions & kAudioFileReadPermission; }
202         virtual Boolean CanWrite() const { return mPermissions & kAudioFileWritePermission; }
203
204 private:
205
206         SInt64  UFCurrentOffset (UInt16         positionMode, 
207                                                         SInt64          positionOffset);
208 };
209
210 //////////////////////////////////////////////////////////////////////////////////////////
211
212 //////////////////////////////////////////////////////////////////////////////////////////
213
214 /*
215         A wrapper that caches the wrapped source's header.
216 */
217 class Cached_DataSource : public DataSource
218 {
219         DataSource* mDataSource;
220         CAAutoFree<UInt8> mHeaderCache;
221         UInt32 mHeaderCacheSize;
222         CAAutoFree<UInt8> mBodyCache;
223         UInt32 mBodyCacheSize;
224         UInt32 mBodyCacheCurSize;
225         SInt64 mBodyCacheOffset;
226         SInt64 mOffset;
227         Boolean mOwnDataSource;
228         
229 public:
230
231         Cached_DataSource(DataSource* inDataSource, UInt32 inHeaderCacheSize = 4096, UInt32 inBodyCacheSize = 32768, Boolean inOwnDataSource = true)
232                                         : DataSource(false), 
233                                         mDataSource(inDataSource), mHeaderCacheSize(inHeaderCacheSize), 
234                                         mBodyCacheSize(inBodyCacheSize), mBodyCacheCurSize(0), mBodyCacheOffset(-1), 
235                                         mOffset(0),
236                                         mOwnDataSource(inOwnDataSource)
237                                 {
238                                 }
239                                 
240         virtual ~Cached_DataSource()
241                                 {
242                                         if (mOwnDataSource) delete mDataSource;
243                                 }
244
245         
246         virtual OSStatus GetSize(SInt64& outSize) { return mDataSource->GetSize(outSize); }
247         virtual OSStatus GetPos(SInt64& outPos) const { return mDataSource->GetPos(outPos); } 
248         
249         virtual OSStatus SetSize(SInt64 inSize) { return mDataSource->SetSize(inSize); }
250         
251         virtual OSStatus ReadBytes(             UInt16 positionMode, 
252                                                                         SInt64 positionOffset, 
253                                                                         UInt32 requestCount, 
254                                                                         void *buffer, 
255                                                                         UInt32* actualCount);
256                                                 
257         virtual OSStatus WriteBytes(    UInt16 positionMode, 
258                                                                         SInt64 positionOffset, 
259                                                                         UInt32 requestCount, 
260                                                                         const void *buffer, 
261                                                                         UInt32* actualCount);
262         
263         OSStatus ReadFromHeaderCache(   SInt64 offset, 
264                                                                         UInt32 requestCount,
265                                                                         void *buffer, 
266                                                                         UInt32* actualCount);
267         
268         virtual Boolean CanSeek() const { return mDataSource->CanSeek(); }
269         virtual Boolean CanGetSize() const { return mDataSource->CanGetSize(); }
270         virtual Boolean CanSetSize() const { return mDataSource->CanSetSize(); }
271         
272         virtual Boolean CanRead() const { return mDataSource->CanRead(); }
273         virtual Boolean CanWrite() const { return mDataSource->CanWrite(); }
274 };
275
276 //////////////////////////////////////////////////////////////////////////////////////////
277
278 //////////////////////////////////////////////////////////////////////////////////////////
279
280 //////////////////////////////////////////////////////////////////////////////////////////
281
282
283 /* This class calls user supplied routines on demand. */
284
285 class Seekable_DataSource : public DataSource
286 {
287         void * mClientData;
288         SInt64 mOffset;
289         
290         AudioFile_ReadProc mReadFunc;
291         AudioFile_WriteProc mWriteFunc;
292         AudioFile_GetSizeProc mSizeFunc;
293         AudioFile_SetSizeProc mSetSizeFunc;
294         
295 public:
296         Seekable_DataSource(    void *                                                          inClientData,
297                                                         AudioFile_ReadProc                                      inReadFunc, 
298                                                         AudioFile_WriteProc                                     inWriteFunc, 
299                                                         AudioFile_GetSizeProc                           inGetSizeFunc,
300                                                         AudioFile_SetSizeProc                           inSetSizeFunc
301                                         );
302         
303         virtual ~Seekable_DataSource();
304         
305         virtual OSStatus GetSize(SInt64& outSize);
306         virtual OSStatus GetPos(SInt64& outPos) const { outPos = mOffset; return noErr; }; 
307         
308         virtual OSStatus SetSize(SInt64 inSize);
309         
310         virtual OSStatus ReadBytes(     UInt16 positionMode, 
311                                                                 SInt64 positionOffset, 
312                                                                 UInt32 requestCount, 
313                                                                 void *buffer, 
314                                                                 UInt32* actualCount);
315                                                 
316         virtual OSStatus WriteBytes(UInt16 positionMode, 
317                                                                 SInt64 positionOffset, 
318                                                                 UInt32 requestCount, 
319                                                                 const void *buffer, 
320                                                                 UInt32* actualCount);
321
322         virtual Boolean CanSeek() const { return true; }
323         virtual Boolean CanGetSize() const { return mSizeFunc != 0; }
324         virtual Boolean CanSetSize() const { return mSetSizeFunc != 0; }
325         virtual Boolean CanRead() const { return mReadFunc != 0; }
326         virtual Boolean CanWrite() const { return mWriteFunc != 0; }
327 };
328
329 //////////////////////////////////////////////////////////////////////////////////////////
330
331 class Buffer_DataSource : public DataSource
332 {
333         UInt32 mDataByteSize;
334         const char * mData;
335
336         SInt64 mStartOffset;
337         SInt64 mOffset;
338 public:
339         Buffer_DataSource(      UInt32                  inDataByteSize,
340                                                 const void *    inData,
341                                                 SInt64                  inStartOffset = 0
342                                         ) : DataSource(false), mDataByteSize(inDataByteSize), mData((const char*)inData), mStartOffset(inStartOffset), mOffset(mStartOffset) {}
343         
344         virtual ~Buffer_DataSource() {}
345         
346         virtual OSStatus GetSize(SInt64& outSize) { outSize = mDataByteSize + mStartOffset; return noErr; }
347         virtual OSStatus GetPos(SInt64& outPos) const { outPos = mOffset; return noErr; }; 
348         
349         virtual OSStatus SetSize(SInt64 inSize) { throw std::runtime_error("not writable"); }
350         
351         virtual OSStatus ReadBytes(     UInt16 positionMode, 
352                                                                 SInt64 positionOffset, 
353                                                                 UInt32 requestCount, 
354                                                                 void *buffer, 
355                                                                 UInt32* actualCount);
356                                                 
357         virtual OSStatus WriteBytes(UInt16 positionMode, 
358                                                                 SInt64 positionOffset, 
359                                                                 UInt32 requestCount, 
360                                                                 const void *buffer, 
361                                                                 UInt32* actualCount) { throw std::runtime_error("not writable"); }
362
363         virtual Boolean CanSeek() const { return true; }
364         virtual Boolean CanGetSize() const { return true; }
365         virtual Boolean CanSetSize() const { return false; }
366         virtual Boolean CanRead() const { return true; }
367         virtual Boolean CanWrite() const { return false; }
368 };
369
370 //////////////////////////////////////////////////////////////////////////////////////////
371
372 #endif