ReactOS 0.4.15-dev-7924-g5949c20
buffer.c
Go to the documentation of this file.
1/*
2 * IDirectMusicBuffer Implementation
3 *
4 * Copyright (C) 2003-2004 Rok Mandeljc
5 * Copyright (C) 2012 Christian Costa
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
16 *
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
20 */
21
22#include "dmusic_private.h"
23#include "initguid.h"
24#include "dmksctrl.h"
25
27
28static inline IDirectMusicBufferImpl *impl_from_IDirectMusicBuffer(IDirectMusicBuffer *iface)
29{
30 return CONTAINING_RECORD(iface, IDirectMusicBufferImpl, IDirectMusicBuffer_iface);
31}
32
33/* IDirectMusicBufferImpl IUnknown part: */
35{
36 TRACE("(%p)->(%s, %p)\n", iface, debugstr_dmguid(riid), ret_iface);
37
39 IsEqualIID(riid, &IID_IDirectMusicBuffer))
40 {
42 *ret_iface = iface;
43 return S_OK;
44 }
45
46 *ret_iface = NULL;
47
48 WARN("(%p)->(%s, %p): not found\n", iface, debugstr_dmguid(riid), ret_iface);
49
50 return E_NOINTERFACE;
51}
52
54{
57
58 TRACE("(%p)->(): new ref = %u\n", iface, ref);
59
60 return ref;
61}
62
64{
67
68 TRACE("(%p)->(): new ref = %u\n", iface, ref);
69
70 if (!ref) {
71 HeapFree(GetProcessHeap(), 0, This->data);
74 }
75
76 return ref;
77}
78
79/* IDirectMusicBufferImpl IDirectMusicBuffer part: */
81{
83
84 TRACE("(%p)->()\n", iface);
85
86 This->write_pos = 0;
87
88 return S_OK;
89}
90
92{
94
95 FIXME("(%p, %p): stub\n", This, prtTime);
96
97 return S_OK;
98}
99
101{
103 DWORD new_write_pos = This->write_pos + DMUS_EVENT_SIZE(sizeof(channel_message));
105
106 TRACE("(%p)->(0x%s, %u, 0x%x)\n", iface, wine_dbgstr_longlong(ref_time), channel_group, channel_message);
107
108 if (new_write_pos > This->size)
109 return DMUS_E_BUFFER_FULL;
110
111 /* Channel_message 0xZZYYXX (3 bytes) is a midi message where XX = status byte, YY = byte 1 and ZZ = byte 2 */
112
113 if (!(channel_message & 0x80))
114 {
115 /* Status byte MSB is always set */
117 }
118
119 if (!This->write_pos)
120 This->start_time = ref_time;
121
122 header = (DMUS_EVENTHEADER*)&This->data[This->write_pos];
123 header->cbEvent = 3; /* Midi message takes 4 bytes space but only 3 are relevant */
124 header->dwChannelGroup = channel_group;
125 header->rtDelta = ref_time - This->start_time;
126 header->dwFlags = DMUS_EVENT_STRUCTURED;
127
128 *(DWORD*)&header[1] = channel_message;
129 This->write_pos = new_write_pos;
130
131 return S_OK;
132}
133
135 REFERENCE_TIME ref_time, DWORD channel_group, DWORD len, BYTE *data)
136{
138 DWORD new_write_pos = This->write_pos + DMUS_EVENT_SIZE(len);
140
141 TRACE("(%p, 0x%s, %d, %d, %p)\n", This, wine_dbgstr_longlong(ref_time), channel_group, len, data);
142
143 if (new_write_pos > This->size)
144 return DMUS_E_BUFFER_FULL;
145
146 if (!This->write_pos)
147 This->start_time = ref_time;
148
149 header = (DMUS_EVENTHEADER*)&This->data[This->write_pos];
150 header->cbEvent = len;
151 header->dwChannelGroup = channel_group;
152 header->rtDelta = ref_time - This->start_time;
153 header->dwFlags = 0;
154
155 memcpy(&header[1], data, len);
156 This->write_pos = new_write_pos;
157
158 return S_OK;
159}
160
162{
164
165 FIXME("(%p): stub\n", This);
166
167 return S_OK;
168}
169
171{
173
174 FIXME("(%p, %p, %p, %p, %p): stub\n", This, prt, pdwChannelGroup, pdwLength, ppData);
175
176 return S_OK;
177}
178
180{
182
183 TRACE("(%p)->(%p)\n", iface, data);
184
185 if (!data)
186 return E_POINTER;
187
188 *data = This->data;
189
190 return S_OK;
191}
192
194{
196
197 TRACE("(%p)->(%p)\n", iface, ref_time);
198
199 if (!ref_time)
200 return E_POINTER;
201 if (!This->write_pos)
202 return DMUS_E_BUFFER_EMPTY;
203
204 *ref_time = This->start_time;
205
206 return S_OK;
207}
208
210{
212
213 TRACE("(%p)->(%p)\n", iface, used_bytes);
214
215 if (!used_bytes)
216 return E_POINTER;
217
218 *used_bytes = This->write_pos;
219
220 return S_OK;
221}
222
224{
226
227 TRACE("(%p)->(%p)\n", iface, max_bytes);
228
229 if (!max_bytes)
230 return E_POINTER;
231
232 *max_bytes = This->size;
233
234 return S_OK;
235}
236
238{
240
241 TRACE("(%p)->(%p)\n", iface, format);
242
243 if (!format)
244 return E_POINTER;
245
246 *format = This->format;
247 return S_OK;
248}
249
251{
253
254 TRACE("(%p)->(0x%s)\n", This, wine_dbgstr_longlong(ref_time));
255
256 This->start_time = ref_time;
257
258 return S_OK;
259}
260
262{
264
265 TRACE("(%p)->(%u)\n", iface, used_bytes);
266
267 if (used_bytes > This->size)
268 return DMUS_E_BUFFER_FULL;
269
270 This->write_pos = used_bytes;
271
272 return S_OK;
273}
274
275static const IDirectMusicBufferVtbl DirectMusicBuffer_Vtbl = {
292};
293
295{
296 IDirectMusicBufferImpl* dmbuffer;
297
298 TRACE("(%p, %p)\n", desc, ret_iface);
299
300 *ret_iface = NULL;
301
303 if (!dmbuffer)
304 return E_OUTOFMEMORY;
305
307 dmbuffer->ref = 1;
308
309 if (IsEqualGUID(&desc->guidBufferFormat, &GUID_NULL))
311 else
312 dmbuffer->format = desc->guidBufferFormat;
313 dmbuffer->size = (desc->cbBuffer + 3) & ~3; /* Buffer size must be multiple of 4 bytes */
314
315 dmbuffer->data = HeapAlloc(GetProcessHeap(), 0, dmbuffer->size);
316 if (!dmbuffer->data) {
317 HeapFree(GetProcessHeap(), 0, dmbuffer);
318 return E_OUTOFMEMORY;
319 }
320
322 *ret_iface = &dmbuffer->IDirectMusicBuffer_iface;
323
324 return S_OK;
325}
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
const GUID IID_IUnknown
#define FIXME(fmt,...)
Definition: debug.h:111
#define WARN(fmt,...)
Definition: debug.h:112
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define NULL
Definition: types.h:112
static HRESULT WINAPI IDirectMusicBufferImpl_PackUnstructured(IDirectMusicBuffer *iface, REFERENCE_TIME ref_time, DWORD channel_group, DWORD len, BYTE *data)
Definition: buffer.c:134
static HRESULT WINAPI IDirectMusicBufferImpl_GetNextEvent(LPDIRECTMUSICBUFFER iface, LPREFERENCE_TIME prt, LPDWORD pdwChannelGroup, LPDWORD pdwLength, LPBYTE *ppData)
Definition: buffer.c:170
static HRESULT WINAPI IDirectMusicBufferImpl_Flush(LPDIRECTMUSICBUFFER iface)
Definition: buffer.c:80
static HRESULT WINAPI IDirectMusicBufferImpl_SetUsedBytes(LPDIRECTMUSICBUFFER iface, DWORD used_bytes)
Definition: buffer.c:261
static ULONG WINAPI IDirectMusicBufferImpl_Release(LPDIRECTMUSICBUFFER iface)
Definition: buffer.c:63
HRESULT DMUSIC_CreateDirectMusicBufferImpl(LPDMUS_BUFFERDESC desc, LPVOID *ret_iface)
Definition: buffer.c:294
static HRESULT WINAPI IDirectMusicBufferImpl_GetUsedBytes(LPDIRECTMUSICBUFFER iface, LPDWORD used_bytes)
Definition: buffer.c:209
static HRESULT WINAPI IDirectMusicBufferImpl_QueryInterface(LPDIRECTMUSICBUFFER iface, REFIID riid, LPVOID *ret_iface)
Definition: buffer.c:34
static HRESULT WINAPI IDirectMusicBufferImpl_GetStartTime(LPDIRECTMUSICBUFFER iface, LPREFERENCE_TIME ref_time)
Definition: buffer.c:193
static HRESULT WINAPI IDirectMusicBufferImpl_SetStartTime(LPDIRECTMUSICBUFFER iface, REFERENCE_TIME ref_time)
Definition: buffer.c:250
static IDirectMusicBufferImpl * impl_from_IDirectMusicBuffer(IDirectMusicBuffer *iface)
Definition: buffer.c:28
static HRESULT WINAPI IDirectMusicBufferImpl_GetRawBufferPtr(LPDIRECTMUSICBUFFER iface, LPBYTE *data)
Definition: buffer.c:179
static ULONG WINAPI IDirectMusicBufferImpl_AddRef(LPDIRECTMUSICBUFFER iface)
Definition: buffer.c:53
static HRESULT WINAPI IDirectMusicBufferImpl_PackStructured(LPDIRECTMUSICBUFFER iface, REFERENCE_TIME ref_time, DWORD channel_group, DWORD channel_message)
Definition: buffer.c:100
static HRESULT WINAPI IDirectMusicBufferImpl_GetMaxBytes(LPDIRECTMUSICBUFFER iface, LPDWORD max_bytes)
Definition: buffer.c:223
static HRESULT WINAPI IDirectMusicBufferImpl_TotalTime(LPDIRECTMUSICBUFFER iface, LPREFERENCE_TIME prtTime)
Definition: buffer.c:91
static HRESULT WINAPI IDirectMusicBufferImpl_ResetReadPtr(LPDIRECTMUSICBUFFER iface)
Definition: buffer.c:161
static const IDirectMusicBufferVtbl DirectMusicBuffer_Vtbl
Definition: buffer.c:275
static HRESULT WINAPI IDirectMusicBufferImpl_GetBufferFormat(LPDIRECTMUSICBUFFER iface, LPGUID format)
Definition: buffer.c:237
#define GetProcessHeap()
Definition: compat.h:736
#define HeapAlloc
Definition: compat.h:733
static __inline const char * wine_dbgstr_longlong(ULONGLONG ll)
Definition: compat.h:49
#define HeapFree(x, y, z)
Definition: compat.h:735
#define HEAP_ZERO_MEMORY
Definition: compat.h:134
REFERENCE_TIME * LPREFERENCE_TIME
Definition: dmdls.h:21
#define DMUS_E_BUFFER_FULL
Definition: dmerror.h:91
#define DMUS_E_BUFFER_EMPTY
Definition: dmerror.h:90
#define DMUS_E_INVALID_EVENT
Definition: dmerror.h:100
#define DMUS_EVENT_STRUCTURED
Definition: dmusbuff.h:4
#define DMUS_EVENT_SIZE(cb)
Definition: dmusbuff.h:6
const char * debugstr_dmguid(const GUID *id)
Definition: dmusic_main.c:237
static void DMUSIC_UnlockModule(void)
static void DMUSIC_LockModule(void)
#define IDirectMusicBuffer_AddRef(p)
Definition: dmusicc.h:487
struct IDirectMusicBuffer * LPDIRECTMUSICBUFFER
Definition: dmusicc.h:97
LONGLONG REFERENCE_TIME
Definition: dmusicks.h:9
unsigned long DWORD
Definition: ntddk_ex.h:95
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
GLint GLint GLsizei GLsizei GLsizei GLint GLenum format
Definition: gl.h:1546
GLenum GLsizei len
Definition: glext.h:6722
REFIID riid
Definition: atlbase.h:39
#define S_OK
Definition: intsafe.h:52
#define GUID_NULL
Definition: ks.h:106
#define KSDATAFORMAT_SUBTYPE_MIDI
Definition: ksmedia.h:1016
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
PSDBQUERYRESULT_VISTA PVOID * ppData
Definition: env.c:56
static const WCHAR desc[]
Definition: protectdata.c:36
#define IsEqualGUID(rguid1, rguid2)
Definition: guiddef.h:147
#define IsEqualIID(riid1, riid2)
Definition: guiddef.h:95
#define REFIID
Definition: guiddef.h:118
#define TRACE(s)
Definition: solgame.cpp:4
IDirectMusicBuffer IDirectMusicBuffer_iface
Definition: send.c:48
unsigned char * LPBYTE
Definition: typedefs.h:53
uint32_t * LPDWORD
Definition: typedefs.h:59
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
#define WINAPI
Definition: msvc.h:6
#define E_NOINTERFACE
Definition: winerror.h:2364
#define E_POINTER
Definition: winerror.h:2365
unsigned char BYTE
Definition: xxhash.c:193