source: trunk/src/avifil32/iastream.c@ 6652

Last change on this file since 6652 was 6652, checked in by bird, 24 years ago

Added $Id:$ keyword.

File size: 12.0 KB
Line 
1/* $Id: iastream.c,v 1.2 2001-09-05 14:16:45 bird Exp $ */
2/*
3 * Copyright 2001 Hidenori TAKESHIMA <hidenori@a2.ctktv.ne.jp>
4 */
5
6#include <string.h>
7#include <stdio.h>
8#include <assert.h>
9
10#include "winbase.h"
11#include "winnls.h"
12#include "mmsystem.h"
13#include "winerror.h"
14#include "vfw.h"
15#include "debugtools.h"
16#include "avifile_private.h"
17
18DEFAULT_DEBUG_CHANNEL(avifile);
19
20static HRESULT WINAPI IAVIStream_fnQueryInterface(IAVIStream*iface,REFIID refiid,LPVOID *obj);
21static ULONG WINAPI IAVIStream_fnAddRef(IAVIStream*iface);
22static ULONG WINAPI IAVIStream_fnRelease(IAVIStream* iface);
23static HRESULT WINAPI IAVIStream_fnCreate(IAVIStream*iface,LPARAM lParam1,LPARAM lParam2);
24static HRESULT WINAPI IAVIStream_fnInfo(IAVIStream*iface,AVISTREAMINFOW *psi,LONG size);
25static LONG WINAPI IAVIStream_fnFindSample(IAVIStream*iface,LONG pos,LONG flags);
26static HRESULT WINAPI IAVIStream_fnReadFormat(IAVIStream*iface,LONG pos,LPVOID format,LONG *formatsize);
27static HRESULT WINAPI IAVIStream_fnSetFormat(IAVIStream*iface,LONG pos,LPVOID format,LONG formatsize);
28static HRESULT WINAPI IAVIStream_fnRead(IAVIStream*iface,LONG start,LONG samples,LPVOID buffer,LONG buffersize,LONG *bytesread,LONG *samplesread);
29static HRESULT WINAPI IAVIStream_fnWrite(IAVIStream*iface,LONG start,LONG samples,LPVOID buffer,LONG buffersize,DWORD flags,LONG *sampwritten,LONG *byteswritten);
30static HRESULT WINAPI IAVIStream_fnDelete(IAVIStream*iface,LONG start,LONG samples);
31static HRESULT WINAPI IAVIStream_fnReadData(IAVIStream*iface,DWORD fcc,LPVOID lp,LONG *lpread);
32static HRESULT WINAPI IAVIStream_fnWriteData(IAVIStream*iface,DWORD fcc,LPVOID lp,LONG size);
33static HRESULT WINAPI IAVIStream_fnSetInfo(IAVIStream*iface,AVISTREAMINFOW*info,LONG infolen);
34
35
36struct ICOM_VTABLE(IAVIStream) iavist = {
37 ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
38 IAVIStream_fnQueryInterface,
39 IAVIStream_fnAddRef,
40 IAVIStream_fnRelease,
41 IAVIStream_fnCreate,
42 IAVIStream_fnInfo,
43 IAVIStream_fnFindSample,
44 IAVIStream_fnReadFormat,
45 IAVIStream_fnSetFormat,
46 IAVIStream_fnRead,
47 IAVIStream_fnWrite,
48 IAVIStream_fnDelete,
49 IAVIStream_fnReadData,
50 IAVIStream_fnWriteData,
51 IAVIStream_fnSetInfo
52};
53
54
55
56typedef struct IAVIStreamImpl
57{
58 ICOM_VFIELD(IAVIStream);
59 /* IUnknown stuff */
60 DWORD ref;
61 /* IAVIStream stuff */
62 IAVIFile* paf;
63 WINE_AVISTREAM_DATA* pData;
64} IAVIStreamImpl;
65
66static HRESULT IAVIStream_Construct( IAVIStreamImpl* This );
67static void IAVIStream_Destruct( IAVIStreamImpl* This );
68
69HRESULT AVIFILE_CreateIAVIStream(void** ppobj)
70{
71 IAVIStreamImpl *This;
72 HRESULT hr;
73
74 *ppobj = NULL;
75 This = (IAVIStreamImpl*)HeapAlloc(AVIFILE_data.hHeap,HEAP_ZERO_MEMORY,
76 sizeof(IAVIStreamImpl));
77 This->ref = 1;
78 ICOM_VTBL(This) = &iavist;
79 hr = IAVIStream_Construct( This );
80 if ( hr != S_OK )
81 {
82 IAVIStream_Destruct( This );
83 return hr;
84 }
85
86 *ppobj = (LPVOID)This;
87
88 return S_OK;
89}
90
91
92/****************************************************************************
93 * IUnknown interface
94 */
95
96static HRESULT WINAPI IAVIStream_fnQueryInterface(IAVIStream*iface,REFIID refiid,LPVOID *obj) {
97 ICOM_THIS(IAVIStreamImpl,iface);
98
99 TRACE("(%p)->QueryInterface(%s,%p)\n",This,debugstr_guid(refiid),obj);
100 if ( IsEqualGUID(&IID_IUnknown,refiid) ||
101 IsEqualGUID(&IID_IAVIStream,refiid) )
102 {
103 IAVIStream_AddRef(iface);
104 *obj = iface;
105 return S_OK;
106 }
107 /* can return IGetFrame interface too */
108
109 return OLE_E_ENUM_NOMORE;
110}
111
112static ULONG WINAPI IAVIStream_fnAddRef(IAVIStream*iface) {
113 ICOM_THIS(IAVIStreamImpl,iface);
114
115 TRACE("(%p)->AddRef()\n",iface);
116 return ++(This->ref);
117}
118
119static ULONG WINAPI IAVIStream_fnRelease(IAVIStream* iface) {
120 ICOM_THIS(IAVIStreamImpl,iface);
121
122 TRACE("(%p)->Release()\n",iface);
123 if ((--(This->ref)) > 0 )
124 return This->ref;
125 IAVIStream_Destruct(This);
126
127 HeapFree(AVIFILE_data.hHeap,0,iface);
128 return 0;
129}
130
131/****************************************************************************
132 * IAVIStream interface
133 */
134
135static HRESULT IAVIStream_Construct( IAVIStreamImpl* This )
136{
137 This->paf = NULL;
138 This->pData = NULL;
139
140 AVIFILE_data.dwClassObjRef ++;
141
142 return S_OK;
143}
144
145static void IAVIStream_Destruct( IAVIStreamImpl* This )
146{
147 AVIFILE_data.dwClassObjRef --;
148}
149
150static HRESULT WINAPI IAVIStream_fnCreate(IAVIStream*iface,LPARAM lParam1,LPARAM lParam2)
151{
152 ICOM_THIS(IAVIStreamImpl,iface);
153
154 FIXME("(%p)->Create(%ld,%ld)\n",iface,lParam1,lParam2);
155
156 This->paf = (IAVIFile*)lParam1;
157 This->pData = (WINE_AVISTREAM_DATA*)lParam2;
158
159 return S_OK;
160}
161
162static HRESULT WINAPI IAVIStream_fnInfo(IAVIStream*iface,AVISTREAMINFOW *psi,LONG size)
163{
164 ICOM_THIS(IAVIStreamImpl,iface);
165 AVISTREAMINFOW siw;
166
167 FIXME("(%p)->Info(%p,%ld)\n",iface,psi,size);
168 if ( This->pData == NULL )
169 return E_UNEXPECTED;
170
171 memset( &siw, 0, sizeof(AVISTREAMINFOW) );
172 siw.fccType = This->pData->pstrhdr->fccType;
173 siw.fccHandler = This->pData->pstrhdr->fccHandler;
174 siw.dwFlags = This->pData->pstrhdr->dwFlags;
175 siw.dwCaps = 0; /* FIXME */
176 siw.wPriority = This->pData->pstrhdr->wPriority;
177 siw.wLanguage = This->pData->pstrhdr->wLanguage;
178 siw.dwScale = This->pData->pstrhdr->dwScale;
179 siw.dwRate = This->pData->pstrhdr->dwRate;
180 siw.dwStart = This->pData->pstrhdr->dwStart;
181 siw.dwLength = This->pData->pstrhdr->dwLength;
182 siw.dwInitialFrames = This->pData->pstrhdr->dwInitialFrames;
183 siw.dwSuggestedBufferSize = This->pData->pstrhdr->dwSuggestedBufferSize;
184 siw.dwQuality = This->pData->pstrhdr->dwQuality;
185 siw.dwSampleSize = This->pData->pstrhdr->dwSampleSize;
186 siw.rcFrame.left = This->pData->pstrhdr->rcFrame.left;
187 siw.rcFrame.top = This->pData->pstrhdr->rcFrame.top;
188 siw.rcFrame.right = This->pData->pstrhdr->rcFrame.right;
189 siw.rcFrame.bottom = This->pData->pstrhdr->rcFrame.bottom;
190 siw.dwEditCount = 0; /* FIXME */
191 siw.dwFormatChangeCount = 0; /* FIXME */
192 /* siw.szName[64] */
193
194 if ( size > sizeof(AVISTREAMINFOW) )
195 size = sizeof(AVISTREAMINFOW);
196 memcpy( psi, &siw, size );
197
198 return S_OK;
199}
200
201static LONG WINAPI IAVIStream_fnFindSample(IAVIStream*iface,LONG pos,LONG flags)
202{
203 ICOM_THIS(IAVIStreamImpl,iface);
204 HRESULT hr;
205 AVIINDEXENTRY* pIndexEntry;
206 DWORD dwCountOfIndexEntry;
207 LONG lCur, lAdd, lEnd;
208
209 FIXME("(%p)->FindSample(%ld,0x%08lx)\n",This,pos,flags);
210
211 hr = AVIFILE_IAVIFile_GetIndexTable(
212 This->paf, This->pData->dwStreamIndex,
213 &pIndexEntry, &dwCountOfIndexEntry );
214 if ( hr != S_OK )
215 return -1L;
216
217 if ( flags & (~(FIND_DIR|FIND_TYPE|FIND_RET)) )
218 {
219 FIXME( "unknown flag %08lx\n", flags );
220 return -1L;
221 }
222
223 switch ( flags & FIND_DIR )
224 {
225 case FIND_NEXT:
226 lCur = pos;
227 lAdd = 1;
228 lEnd = dwCountOfIndexEntry;
229 if ( lCur > dwCountOfIndexEntry )
230 return -1L;
231 break;
232 case FIND_PREV:
233 lCur = pos;
234 if ( lCur > dwCountOfIndexEntry )
235 lCur = dwCountOfIndexEntry;
236 lAdd = -1;
237 lEnd = 0;
238 break;
239 case FIND_FROM_START:
240 lCur = 0;
241 lAdd = 1;
242 lEnd = dwCountOfIndexEntry;
243 break;
244 default:
245 FIXME( "unknown direction flag %08lx\n", (flags & FIND_DIR) );
246 return -1L;
247 }
248
249 switch ( flags & FIND_TYPE )
250 {
251 case FIND_KEY:
252 while ( 1 )
253 {
254 if ( pIndexEntry[lCur].dwFlags & AVIIF_KEYFRAME )
255 break;
256 if ( lCur == lEnd )
257 return -1L;
258 lCur += lAdd;
259 }
260 break;
261 case FIND_ANY:
262 while ( 1 )
263 {
264 if ( !(pIndexEntry[lCur].dwFlags & AVIIF_NOTIME) )
265 break;
266 if ( lCur == lEnd )
267 return -1L;
268 lCur += lAdd;
269 }
270 break;
271 case FIND_FORMAT:
272 FIXME( "FIND_FORMAT is not implemented.\n" );
273 return -1L;
274 default:
275 FIXME( "unknown type flag %08lx\n", (flags & FIND_TYPE) );
276 return -1L;
277 }
278
279 switch ( flags & FIND_RET )
280 {
281 case FIND_POS:
282 return lCur;
283 case FIND_LENGTH:
284 FIXME( "FIND_LENGTH is not implemented.\n" );
285 return -1L;
286 case FIND_OFFSET:
287 return pIndexEntry[lCur].dwChunkOffset;
288 case FIND_SIZE:
289 return pIndexEntry[lCur].dwChunkLength;
290 case FIND_INDEX:
291 FIXME( "FIND_INDEX is not implemented.\n" );
292 return -1L;
293 default:
294 FIXME( "unknown return type flag %08lx\n", (flags & FIND_RET) );
295 break;
296 }
297
298 return -1L;
299}
300
301static HRESULT WINAPI IAVIStream_fnReadFormat(IAVIStream*iface,LONG pos,LPVOID format,LONG *formatsize) {
302 ICOM_THIS(IAVIStreamImpl,iface);
303
304 TRACE("(%p)->ReadFormat(%ld,%p,%p)\n",This,pos,format,formatsize);
305 if ( This->pData == NULL )
306 return E_UNEXPECTED;
307
308 /* FIXME - check pos. */
309 if ( format == NULL )
310 {
311 *formatsize = This->pData->dwFmtLen;
312 return S_OK;
313 }
314 if ( (*formatsize) < This->pData->dwFmtLen )
315 return AVIERR_BUFFERTOOSMALL;
316
317 memcpy( format, This->pData->pbFmt, This->pData->dwFmtLen );
318 *formatsize = This->pData->dwFmtLen;
319
320 return S_OK;
321}
322
323static HRESULT WINAPI IAVIStream_fnSetFormat(IAVIStream*iface,LONG pos,LPVOID format,LONG formatsize) {
324 ICOM_THIS(IAVIStreamImpl,iface);
325
326 FIXME("(%p)->SetFormat(%ld,%p,%ld)\n",This,pos,format,formatsize);
327 return E_FAIL;
328}
329
330static HRESULT WINAPI IAVIStream_fnRead(IAVIStream*iface,LONG start,LONG samples,LPVOID buffer,LONG buffersize,LONG *bytesread,LONG *samplesread) {
331 ICOM_THIS(IAVIStreamImpl,iface);
332 HRESULT hr;
333 AVIINDEXENTRY* pIndexEntry;
334 DWORD dwCountOfIndexEntry;
335 DWORD dwFrameLength;
336
337 FIXME("(%p)->Read(%ld,%ld,%p,%ld,%p,%p)\n",This,start,samples,buffer,buffersize,bytesread,samplesread);
338
339 *bytesread = 0;
340 *samplesread = 0;
341
342 hr = AVIFILE_IAVIFile_GetIndexTable(
343 This->paf, This->pData->dwStreamIndex,
344 &pIndexEntry, &dwCountOfIndexEntry );
345 if ( hr != S_OK )
346 return hr;
347 if ( start < 0 )
348 return E_FAIL;
349 if ( start >= dwCountOfIndexEntry || samples <= 0 )
350 {
351 FIXME("start %ld,samples %ld,total %ld\n",start,samples,dwCountOfIndexEntry);
352 return S_OK;
353 }
354
355 /* FIXME - is this data valid??? */
356 dwFrameLength = pIndexEntry[start].dwChunkLength + sizeof(DWORD)*2;
357
358 if ( buffer == NULL )
359 {
360 *bytesread = dwFrameLength;
361 *samplesread = 1;
362 return S_OK;
363 }
364 if ( buffersize < dwFrameLength )
365 {
366 FIXME( "buffer is too small!\n" );
367 return AVIERR_BUFFERTOOSMALL;
368 }
369
370 hr = AVIFILE_IAVIFile_ReadMovieData(
371 This->paf,
372 pIndexEntry[start].dwChunkOffset,
373 dwFrameLength, buffer );
374 if ( hr != S_OK )
375 {
376 FIXME( "ReadMovieData failed!\n");
377 return hr;
378 }
379 *bytesread = dwFrameLength;
380 *samplesread = 1;
381
382 return S_OK;
383}
384
385static HRESULT WINAPI IAVIStream_fnWrite(IAVIStream*iface,LONG start,LONG samples,LPVOID buffer,LONG buffersize,DWORD flags,LONG *sampwritten,LONG *byteswritten) {
386 ICOM_THIS(IAVIStreamImpl,iface);
387
388
389 FIXME("(%p)->Write(%ld,%ld,%p,%ld,0x%08lx,%p,%p)\n",This,start,samples,buffer,buffersize,flags,sampwritten,byteswritten);
390 return E_FAIL;
391}
392
393static HRESULT WINAPI IAVIStream_fnDelete(IAVIStream*iface,LONG start,LONG samples) {
394 ICOM_THIS(IAVIStreamImpl,iface);
395
396 FIXME("(%p)->Delete(%ld,%ld)\n",This,start,samples);
397 return E_FAIL;
398}
399static HRESULT WINAPI IAVIStream_fnReadData(IAVIStream*iface,DWORD fcc,LPVOID lp,LONG *lpread) {
400 ICOM_THIS(IAVIStreamImpl,iface);
401
402 FIXME("(%p)->ReadData(0x%08lx,%p,%p)\n",This,fcc,lp,lpread);
403 return E_FAIL;
404}
405
406static HRESULT WINAPI IAVIStream_fnWriteData(IAVIStream*iface,DWORD fcc,LPVOID lp,LONG size) {
407 ICOM_THIS(IAVIStreamImpl,iface);
408
409 FIXME("(%p)->WriteData(0x%08lx,%p,%ld)\n",This,fcc,lp,size);
410 return E_FAIL;
411}
412
413static HRESULT WINAPI IAVIStream_fnSetInfo(IAVIStream*iface,AVISTREAMINFOW*info,LONG infolen) {
414 ICOM_THIS(IAVIStreamImpl,iface);
415
416 FIXME("(%p)->SetInfo(%p,%ld)\n",This,info,infolen);
417
418 return E_FAIL;
419}
420
Note: See TracBrowser for help on using the repository browser.