wgl: Rewrite ChoosePixelFormat.
[wine] / dlls / dmusic / instrument.c
1 /* IDirectMusicInstrument Implementation
2  *
3  * Copyright (C) 2003-2004 Rok Mandeljc
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this program; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
18  */
19
20 #include "dmusic_private.h"
21
22 WINE_DEFAULT_DEBUG_CHANNEL(dmusic);
23 WINE_DECLARE_DEBUG_CHANNEL(dmfile);
24
25 static const GUID IID_IDirectMusicInstrumentPRIVATE = {0xbcb20080,0xa40c,0x11d1,{0x86,0xbc,0x00,0xc0,0x4f,0xbf,0x8f,0xef}};
26
27 static ULONG WINAPI IDirectMusicInstrumentImpl_IUnknown_AddRef (LPUNKNOWN iface);
28 static ULONG WINAPI IDirectMusicInstrumentImpl_IDirectMusicInstrument_AddRef (LPDIRECTMUSICINSTRUMENT iface);
29
30 /* IDirectMusicInstrument IUnknown part: */
31 static HRESULT WINAPI IDirectMusicInstrumentImpl_IUnknown_QueryInterface (LPUNKNOWN iface, REFIID riid, LPVOID *ppobj) {
32         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, UnknownVtbl, iface);
33         TRACE("(%p, %s, %p)\n", This, debugstr_dmguid(riid), ppobj);
34         
35         if (IsEqualIID (riid, &IID_IUnknown)) {
36                 *ppobj = (LPVOID)&This->UnknownVtbl;
37                 IDirectMusicInstrumentImpl_IUnknown_AddRef ((LPUNKNOWN)&This->UnknownVtbl);
38                 return S_OK;    
39         } else if (IsEqualIID (riid, &IID_IDirectMusicInstrument)) {
40                 *ppobj = (LPVOID)&This->InstrumentVtbl;
41                 IDirectMusicInstrumentImpl_IDirectMusicInstrument_AddRef ((LPDIRECTMUSICINSTRUMENT)&This->InstrumentVtbl);
42                 return S_OK;
43         } else if (IsEqualIID (riid, &IID_IDirectMusicInstrumentPRIVATE)) {     
44                 /* it seems to me that this interface is only basic IUnknown, without any
45                         other inherited functions... *sigh* this is the worst scenario, since it means 
46                         that whoever calls it knows the layout of original implementation table and therefore
47                         tries to get data by direct access... expect crashes */
48                 FIXME("*sigh*... requested private/unspecified interface\n");
49                 *ppobj = (LPVOID)&This->UnknownVtbl;
50                 IDirectMusicInstrumentImpl_IUnknown_AddRef ((LPUNKNOWN)&This->UnknownVtbl);
51                 return S_OK;    
52         }
53         
54         WARN("(%p, %s, %p): not found\n", This, debugstr_dmguid(riid), ppobj);
55         return E_NOINTERFACE;
56 }
57
58 static ULONG WINAPI IDirectMusicInstrumentImpl_IUnknown_AddRef (LPUNKNOWN iface) {
59         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, UnknownVtbl, iface);
60         ULONG refCount = InterlockedIncrement(&This->ref);
61
62         TRACE("(%p)->(ref before=%u)\n", This, refCount - 1);
63
64         DMUSIC_LockModule();
65
66         return refCount;
67 }
68
69 static ULONG WINAPI IDirectMusicInstrumentImpl_IUnknown_Release (LPUNKNOWN iface) {
70         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, UnknownVtbl, iface);
71         ULONG refCount = InterlockedDecrement(&This->ref);
72
73         TRACE("(%p)->(ref before=%u)\n", This, refCount + 1);
74
75         if (!refCount) {
76                 HeapFree(GetProcessHeap(), 0, This);
77         }
78
79         DMUSIC_UnlockModule();
80         
81         return refCount;
82 }
83
84 static const IUnknownVtbl DirectMusicInstrument_Unknown_Vtbl = {
85         IDirectMusicInstrumentImpl_IUnknown_QueryInterface,
86         IDirectMusicInstrumentImpl_IUnknown_AddRef,
87         IDirectMusicInstrumentImpl_IUnknown_Release
88 };
89
90 /* IDirectMusicInstrumentImpl IDirectMusicInstrument part: */
91 static HRESULT WINAPI IDirectMusicInstrumentImpl_IDirectMusicInstrument_QueryInterface (LPDIRECTMUSICINSTRUMENT iface, REFIID riid, LPVOID *ppobj) {
92         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, InstrumentVtbl, iface);
93         return IDirectMusicInstrumentImpl_IUnknown_QueryInterface ((LPUNKNOWN)&This->UnknownVtbl, riid, ppobj);
94 }
95
96 static ULONG WINAPI IDirectMusicInstrumentImpl_IDirectMusicInstrument_AddRef (LPDIRECTMUSICINSTRUMENT iface) {
97         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, InstrumentVtbl, iface);
98         return IDirectMusicInstrumentImpl_IUnknown_AddRef ((LPUNKNOWN)&This->UnknownVtbl);
99 }
100
101 static ULONG WINAPI IDirectMusicInstrumentImpl_IDirectMusicInstrument_Release (LPDIRECTMUSICINSTRUMENT iface) {
102         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, InstrumentVtbl, iface);
103         return IDirectMusicInstrumentImpl_IUnknown_Release ((LPUNKNOWN)&This->UnknownVtbl);
104 }
105
106 static HRESULT WINAPI IDirectMusicInstrumentImpl_IDirectMusicInstrument_GetPatch (LPDIRECTMUSICINSTRUMENT iface, DWORD* pdwPatch) {
107         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, InstrumentVtbl, iface);
108         TRACE("(%p, %p)\n", This, pdwPatch);    
109         *pdwPatch = MIDILOCALE2Patch(&This->pHeader->Locale);
110         return S_OK;
111 }
112
113 static HRESULT WINAPI IDirectMusicInstrumentImpl_IDirectMusicInstrument_SetPatch (LPDIRECTMUSICINSTRUMENT iface, DWORD dwPatch) {
114         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, InstrumentVtbl, iface);
115         TRACE("(%p, %d): stub\n", This, dwPatch);
116         Patch2MIDILOCALE(dwPatch, &This->pHeader->Locale);
117         return S_OK;
118 }
119
120 static const IDirectMusicInstrumentVtbl DirectMusicInstrument_Instrument_Vtbl = {
121         IDirectMusicInstrumentImpl_IDirectMusicInstrument_QueryInterface,
122         IDirectMusicInstrumentImpl_IDirectMusicInstrument_AddRef,
123         IDirectMusicInstrumentImpl_IDirectMusicInstrument_Release,
124         IDirectMusicInstrumentImpl_IDirectMusicInstrument_GetPatch,
125         IDirectMusicInstrumentImpl_IDirectMusicInstrument_SetPatch
126 };
127
128 /* for ClassFactory */
129 HRESULT WINAPI DMUSIC_CreateDirectMusicInstrumentImpl (LPCGUID lpcGUID, LPVOID* ppobj, LPUNKNOWN pUnkOuter) {
130         IDirectMusicInstrumentImpl* dminst;
131         
132         dminst = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IDirectMusicInstrumentImpl));
133         if (NULL == dminst) {
134                 *ppobj = NULL;
135                 return E_OUTOFMEMORY;
136         }
137         dminst->UnknownVtbl = &DirectMusicInstrument_Unknown_Vtbl;
138         dminst->InstrumentVtbl = &DirectMusicInstrument_Instrument_Vtbl;
139         dminst->ref = 0; /* will be inited by QueryInterface */
140         
141         return IDirectMusicInstrumentImpl_IUnknown_QueryInterface ((LPUNKNOWN)&dminst->UnknownVtbl, lpcGUID, ppobj);
142 }
143
144 /* aux. function that completely loads instrument; my tests indicate that it's 
145    called somewhere around IDirectMusicCollection_GetInstrument */
146 HRESULT WINAPI IDirectMusicInstrumentImpl_Custom_Load (LPDIRECTMUSICINSTRUMENT iface, LPSTREAM pStm) {
147         ICOM_THIS_MULTI(IDirectMusicInstrumentImpl, InstrumentVtbl, iface);
148         
149         DMUS_PRIVATE_CHUNK Chunk;
150         DWORD ListSize[4], ListCount[4];
151         LARGE_INTEGER liMove; /* used when skipping chunks */
152         
153         TRACE("(%p, %p, offset = 0x%04llx)\n", This, pStm, This->liInstrumentPosition.QuadPart);
154
155         /* goto the beginning of chunk */
156         IStream_Seek (pStm, This->liInstrumentPosition, STREAM_SEEK_SET, NULL);
157         
158         IStream_Read (pStm, &Chunk, sizeof(FOURCC)+sizeof(DWORD), NULL);
159         TRACE_(dmfile)(": %s chunk (size = 0x%04x)", debugstr_fourcc (Chunk.fccID), Chunk.dwSize);
160         switch (Chunk.fccID) {
161                 case FOURCC_LIST: {
162                         IStream_Read (pStm, &Chunk.fccID, sizeof(FOURCC), NULL);                                
163                         TRACE_(dmfile)(": LIST chunk of type %s", debugstr_fourcc(Chunk.fccID));
164                         ListSize[0] = Chunk.dwSize - sizeof(FOURCC);
165                         ListCount[0] = 0;
166                         switch (Chunk.fccID) {
167                                 case FOURCC_INS: {
168                                         TRACE_(dmfile)(": instrument list\n");
169                                         do {
170                                                 IStream_Read (pStm, &Chunk, sizeof(FOURCC)+sizeof(DWORD), NULL);
171                                                 ListCount[0] += sizeof(FOURCC) + sizeof(DWORD) + Chunk.dwSize;
172                                                 TRACE_(dmfile)(": %s chunk (size = 0x%04x)", debugstr_fourcc (Chunk.fccID), Chunk.dwSize);
173                                                 switch (Chunk.fccID) {
174                                                         case FOURCC_INSH: {
175                                                                 TRACE_(dmfile)(": instrument header chunk\n");
176                                                                 /* should be already initialised */
177                                                                 IStream_Read (pStm, This->pHeader, Chunk.dwSize, NULL);
178                                                                 break;  
179                                                         }
180                                                         case FOURCC_DLID: {
181                                                                 TRACE_(dmfile)(": DLID (GUID) chunk\n");
182                                                                 /* should be already initialised */
183                                                                 IStream_Read (pStm, This->pInstrumentID, Chunk.dwSize, NULL);
184                                                                 break;
185                                                         }
186                                                         case FOURCC_LIST: {
187                                                                 IStream_Read (pStm, &Chunk.fccID, sizeof(FOURCC), NULL);                                
188                                                                 TRACE_(dmfile)(": LIST chunk of type %s", debugstr_fourcc(Chunk.fccID));
189                                                                 ListSize[1] = Chunk.dwSize - sizeof(FOURCC);
190                                                                 ListCount[1] = 0;
191                                                                 switch (Chunk.fccID) {
192                                                                         case FOURCC_LRGN: {
193                                                                                 TRACE_(dmfile)(": regions list\n");
194                                                                                 do {
195                                                                                         IStream_Read (pStm, &Chunk, sizeof(FOURCC)+sizeof(DWORD), NULL);
196                                                                                         ListCount[1] += sizeof(FOURCC) + sizeof(DWORD) + Chunk.dwSize;
197                                                                                         TRACE_(dmfile)(": %s chunk (size = 0x%04x)", debugstr_fourcc (Chunk.fccID), Chunk.dwSize);
198                                                                                         switch (Chunk.fccID) {
199                                                                                                 case FOURCC_LIST: {
200                                                                                                         IStream_Read (pStm, &Chunk.fccID, sizeof(FOURCC), NULL);                                
201                                                                                                         TRACE_(dmfile)(": LIST chunk of type %s", debugstr_fourcc(Chunk.fccID));
202                                                                                                         ListSize[2] = Chunk.dwSize - sizeof(FOURCC);
203                                                                                                         ListCount[2] = 0;
204                                                                                                         switch (Chunk.fccID) {
205                                                                                                                 case FOURCC_RGN: {                                                                                                                              
206                                                                                                                         /* temporary structures */
207                                                                                                                         RGNHEADER tmpRegionHeader;
208                                                                                                                         WSMPL tmpWaveSample;
209                                                                                                                         WLOOP tmpWaveLoop;
210                                                                                                                         WAVELINK tmpWaveLink;
211                                                                                                                         
212                                                                                                                         TRACE_(dmfile)(": region list\n");
213                                                                                                                         do {
214                                                                                                                                 IStream_Read (pStm, &Chunk, sizeof(FOURCC)+sizeof(DWORD), NULL);
215                                                                                                                                 ListCount[2] += sizeof(FOURCC) + sizeof(DWORD) + Chunk.dwSize;
216                                                                                                                                 TRACE_(dmfile)(": %s chunk (size = 0x%04x)", debugstr_fourcc (Chunk.fccID), Chunk.dwSize);
217                                                                                                                                 switch (Chunk.fccID) {
218                                                                                                                                         case FOURCC_RGNH: {
219                                                                                                                                                 TRACE_(dmfile)(": region header chunk\n");
220                                                                                                                                                 memset (&tmpRegionHeader, 0, sizeof(RGNHEADER)); /* reset */
221                                                                                                                                                 IStream_Read (pStm, &tmpRegionHeader, Chunk.dwSize, NULL);
222                                                                                                                                                 break;
223                                                                                                                                         }
224                                                                                                                                         case FOURCC_WSMP: {
225                                                                                                                                                 TRACE_(dmfile)(": wave sample chunk\n");
226                                                                                                                                                 memset (&tmpWaveSample, 0, sizeof(WSMPL)); /* reset */
227                                                                                                                                                 memset (&tmpWaveLoop, 0, sizeof(WLOOP)); /* reset */
228                                                                                                                                                 if (Chunk.dwSize != (sizeof(WSMPL) + sizeof(WLOOP))) ERR(": incorrect chunk size\n");
229                                                                                                                                                 IStream_Read (pStm, &tmpWaveSample, sizeof(WSMPL), NULL);
230                                                                                                                                                 IStream_Read (pStm, &tmpWaveLoop, sizeof(WLOOP), NULL);
231                                                                                                                                                 break;
232                                                                                                                                         }
233                                                                                                                                         case FOURCC_WLNK: {
234                                                                                                                                                 TRACE_(dmfile)(": wave link chunk\n");
235                                                                                                                                                 memset (&tmpWaveLink, 0, sizeof(WAVELINK)); /* reset */
236                                                                                                                                                 IStream_Read (pStm, &tmpWaveLink, Chunk.dwSize, NULL);
237                                                                                                                                                 break;
238                                                                                                                                         }
239                                                                                                                                         default: {
240                                                                                                                                                 TRACE_(dmfile)(": unknown (skipping)\n");
241                                                                                                                                                 liMove.QuadPart = Chunk.dwSize - sizeof(FOURCC);
242                                                                                                                                                 IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
243                                                                                                                                                 break;                                          
244                                                                                                                                         }
245                                                                                                                                 }
246                                                                                                                                 TRACE_(dmfile)(": ListCount[2] = %d < ListSize[2] = %d\n", ListCount[2], ListSize[2]);
247                                                                                                                         } while (ListCount[2] < ListSize[2]);
248                                                                                                                         FIXME(": need to write temporary data to instrument data\n");
249                                                                                                                         break;
250                                                                                                                 }
251                                                                                                                 default: {
252                                                                                                                         TRACE_(dmfile)(": unknown (skipping)\n");
253                                                                                                                         liMove.QuadPart = Chunk.dwSize - sizeof(FOURCC);
254                                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
255                                                                                                                         break;                                          
256                                                                                                                 }
257                                                                                                         }
258                                                                                                         break;
259                                                                                                 }                               
260                                                                                                 default: {
261                                                                                                         TRACE_(dmfile)(": unknown chunk (irrevelant & skipping)\n");
262                                                                                                         liMove.QuadPart = Chunk.dwSize;
263                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
264                                                                                                         break;                                          
265                                                                                                 }
266                                                                                         }
267                                                                                         TRACE_(dmfile)(": ListCount[1] = %d < ListSize[1] = %d\n", ListCount[1], ListSize[1]);
268                                                                                 } while (ListCount[1] < ListSize[1]);
269                                                                                 break;
270                                                                         }
271                                                                         case FOURCC_LART: {
272                                                                                 TRACE_(dmfile)(": articulators list\n");
273                                                                                 do {
274                                                                                         IStream_Read (pStm, &Chunk, sizeof(FOURCC)+sizeof(DWORD), NULL);
275                                                                                         ListCount[1] += sizeof(FOURCC) + sizeof(DWORD) + Chunk.dwSize;
276                                                                                         TRACE_(dmfile)(": %s chunk (size = 0x%04x)", debugstr_fourcc (Chunk.fccID), Chunk.dwSize);
277                                                                                         switch (Chunk.fccID) {
278                                                                                                 case FOURCC_ART1: {
279                                                                                                         /* temporary structures */
280                                                                                                         CONNECTIONLIST tmpConnectionList;
281                                                                                                         LPCONNECTION tmpConnections;
282                                                                                                         
283                                                                                                         TRACE_(dmfile)(": level 1 articulator chunk\n");
284                                                                                                         memset (&tmpConnectionList, 0, sizeof(CONNECTIONLIST)); /* reset */
285                                                                                                         tmpConnections = HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, sizeof(CONNECTION)*tmpConnectionList.cConnections);
286                                                                                                         if (Chunk.dwSize != (sizeof(CONNECTIONLIST) + sizeof(CONNECTION)*tmpConnectionList.cConnections)) ERR(": incorrect chunk size\n");
287                                                                                                         IStream_Read (pStm, &tmpConnectionList, sizeof(CONNECTIONLIST), NULL);
288                                                                                                         IStream_Read (pStm, tmpConnections, sizeof(CONNECTION)*tmpConnectionList.cConnections, NULL);
289                                                                                                         break;
290                                                                                                 }
291                                                                                                 default: {
292                                                                                                         TRACE_(dmfile)(": unknown chunk (irrevelant & skipping)\n");
293                                                                                                         liMove.QuadPart = Chunk.dwSize;
294                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
295                                                                                                         break;                                          
296                                                                                                 }
297                                                                                         }
298                                                                                         TRACE_(dmfile)(": ListCount[1] = %d < ListSize[1] = %d\n", ListCount[1], ListSize[1]);
299                                                                                 } while (ListCount[1] < ListSize[1]);
300                                                                                 break;
301                                                                         }
302                                                                         case mmioFOURCC('I','N','F','O'): {
303                                                                                 TRACE_(dmfile)(": INFO list\n");
304                                                                                 do {
305                                                                                         IStream_Read (pStm, &Chunk, sizeof(FOURCC)+sizeof(DWORD), NULL);
306                                                                                         ListCount[1] += sizeof(FOURCC) + sizeof(DWORD) + Chunk.dwSize;
307                                                                                         TRACE_(dmfile)(": %s chunk (size = 0x%04x)", debugstr_fourcc (Chunk.fccID), Chunk.dwSize);
308                                                                                         switch (Chunk.fccID) {
309                                                                                                 case mmioFOURCC('I','N','A','M'): {
310                                                                                                         TRACE_(dmfile)(": name chunk (ignored)\n");
311                                                                                                         if (even_or_odd(Chunk.dwSize)) {
312                                                                                                                 ListCount[1] ++;
313                                                                                                                 Chunk.dwSize++;
314                                                                                                         }
315                                                                                                         liMove.QuadPart = Chunk.dwSize;
316                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
317                                                                                                         break;
318                                                                                                 }
319                                                                                                 case mmioFOURCC('I','A','R','T'): {
320                                                                                                         TRACE_(dmfile)(": artist chunk (ignored)\n");
321                                                                                                         if (even_or_odd(Chunk.dwSize)) {
322                                                                                                                 ListCount[1] ++;
323                                                                                                                 Chunk.dwSize++;
324                                                                                                         }
325                                                                                                         liMove.QuadPart = Chunk.dwSize;
326                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
327                                                                                                         break;
328                                                                                                 }
329                                                                                                 case mmioFOURCC('I','C','O','P'): {
330                                                                                                         /* temporary structures */
331                                                                                                         CHAR tmpCopyright[DMUS_MAX_NAME];
332                                                                                                         
333                                                                                                         TRACE_(dmfile)(": copyright chunk\n");
334                                                                                                         IStream_Read (pStm, tmpCopyright, Chunk.dwSize, NULL);
335                                                                                                         if (even_or_odd(Chunk.dwSize)) {
336                                                                                                                 ListCount[1] ++;
337                                                                                                                 liMove.QuadPart = 1;
338                                                                                                                 IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
339                                                                                                         }
340                                                                                                         break;
341                                                                                                 }
342                                                                                                 case mmioFOURCC('I','S','B','J'): {
343                                                                                                         TRACE_(dmfile)(": subject chunk (ignored)\n");
344                                                                                                         if (even_or_odd(Chunk.dwSize)) {
345                                                                                                                 ListCount[1] ++;
346                                                                                                                 Chunk.dwSize++;
347                                                                                                         }
348                                                                                                         liMove.QuadPart = Chunk.dwSize;
349                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
350                                                                                                         break;
351                                                                                                 }
352                                                                                                 case mmioFOURCC('I','C','M','T'): {
353                                                                                                         TRACE_(dmfile)(": comment chunk (ignored)\n");
354                                                                                                         if (even_or_odd(Chunk.dwSize)) {
355                                                                                                                 ListCount[1] ++;
356                                                                                                                 Chunk.dwSize++;
357                                                                                                         }
358                                                                                                         liMove.QuadPart = Chunk.dwSize;
359                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
360                                                                                                         break;
361                                                                                                 }
362                                                                                                 default: {
363                                                                                                         TRACE_(dmfile)(": unknown chunk (irrevelant & skipping)\n");
364                                                                                                         if (even_or_odd(Chunk.dwSize)) {
365                                                                                                                 ListCount[1] ++;
366                                                                                                                 Chunk.dwSize++;
367                                                                                                         }
368                                                                                                         liMove.QuadPart = Chunk.dwSize;
369                                                                                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
370                                                                                                         break;                                          
371                                                                                                 }
372                                                                                         }
373                                                                                         TRACE_(dmfile)(": ListCount[1] = %d < ListSize[1] = %d\n", ListCount[1], ListSize[1]);
374                                                                                 } while (ListCount[1] < ListSize[1]);
375                                                                                 break;
376                                                                         }                                                                       
377                                                                         
378                                                                         default: {
379                                                                                 TRACE_(dmfile)(": unknown (skipping)\n");
380                                                                                 liMove.QuadPart = Chunk.dwSize - sizeof(FOURCC);
381                                                                                 IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
382                                                                                 break;                                          
383                                                                         }
384                                                                 }
385                                                                 break;
386                                                         }                               
387                                                         default: {
388                                                                 TRACE_(dmfile)(": unknown chunk (irrevelant & skipping)\n");
389                                                                 liMove.QuadPart = Chunk.dwSize;
390                                                                 IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
391                                                                 break;                                          
392                                                         }
393                                                 }
394                                                 TRACE_(dmfile)(": ListCount[0] = %d < ListSize[0] = %d\n", ListCount[0], ListSize[0]);
395                                         } while (ListCount[0] < ListSize[0]);
396                                         break;
397                                 }
398                                 default: {
399                                         TRACE_(dmfile)(": unknown chunk (irrevelant & skipping)\n");
400                                         liMove.QuadPart = Chunk.dwSize;
401                                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL);
402                                         break;                                          
403                                 }
404                         }
405                         break;
406                 }
407                 default: {
408                         TRACE_(dmfile)(": unexpected chunk; loading failed)\n");
409                         liMove.QuadPart = Chunk.dwSize;
410                         IStream_Seek (pStm, liMove, STREAM_SEEK_CUR, NULL); /* skip the rest of the chunk */
411                         return E_FAIL;
412                 }
413         }
414         /* DEBUG: dumps whole instrument object tree: */
415 /*      if (TRACE_ON(dmusic)) {         
416                 TRACE("*** IDirectMusicInstrument (%p) ***\n", This);
417                 if (This->pInstrumentID)
418                         TRACE(" - GUID = %s\n", debugstr_dmguid(This->pInstrumentID));
419                 
420                 TRACE(" - Instrument header:\n");
421                 TRACE("    - cRegions: %ld\n", This->pHeader->cRegions);
422                 TRACE("    - Locale:\n");
423                 TRACE("       - ulBank: %ld\n", This->pHeader->Locale.ulBank);
424                 TRACE("       - ulInstrument: %ld\n", This->pHeader->Locale.ulInstrument);
425                 TRACE("       => dwPatch: %ld\n", MIDILOCALE2Patch(&This->pHeader->Locale));            
426         }*/
427
428         return S_OK;
429 }