~ubuntu-branches/ubuntu/trusty/sflphone/trusty

« back to all changes in this revision

Viewing changes to daemon/libs/pjproject-2.1.0/third_party/BaseClasses/mtype.cpp

  • Committer: Package Import Robot
  • Author(s): Mark Purcell
  • Date: 2014-01-28 18:23:36 UTC
  • mfrom: (4.3.4 sid)
  • Revision ID: package-import@ubuntu.com-20140128182336-jrsv0k9u6cawc068
Tags: 1.3.0-1
* New upstream release 
  - Fixes "New Upstream Release" (Closes: #735846)
  - Fixes "Ringtone does not stop" (Closes: #727164)
  - Fixes "[sflphone-kde] crash on startup" (Closes: #718178)
  - Fixes "sflphone GUI crashes when call is hung up" (Closes: #736583)
* Build-Depends: ensure GnuTLS 2.6
  - libucommon-dev (>= 6.0.7-1.1), libccrtp-dev (>= 2.0.6-3)
  - Fixes "FTBFS Build-Depends libgnutls{26,28}-dev" (Closes: #722040)
* Fix "boost 1.49 is going away" unversioned Build-Depends: (Closes: #736746)
* Add Build-Depends: libsndfile-dev, nepomuk-core-dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
//------------------------------------------------------------------------------
 
2
// File: MType.cpp
 
3
//
 
4
// Desc: DirectShow base classes - implements a class that holds and 
 
5
//       manages media type information.
 
6
//
 
7
// Copyright (c) 1992-2001 Microsoft Corporation.  All rights reserved.
 
8
//------------------------------------------------------------------------------
 
9
 
 
10
#include <pjmedia-videodev/config.h>
 
11
 
 
12
#if defined(PJMEDIA_VIDEO_DEV_HAS_DSHOW) && PJMEDIA_VIDEO_DEV_HAS_DSHOW != 0
 
13
 
 
14
// helper class that derived pin objects can use to compare media
 
15
// types etc. Has same data members as the struct AM_MEDIA_TYPE defined
 
16
// in the streams IDL file, but also has (non-virtual) functions
 
17
 
 
18
#include <streams.h>
 
19
#include <mmreg.h>
 
20
 
 
21
CMediaType::~CMediaType(){
 
22
    FreeMediaType(*this);
 
23
}
 
24
 
 
25
 
 
26
CMediaType::CMediaType()
 
27
{
 
28
    InitMediaType();
 
29
}
 
30
 
 
31
 
 
32
CMediaType::CMediaType(const GUID * type)
 
33
{
 
34
    InitMediaType();
 
35
    majortype = *type;
 
36
}
 
37
 
 
38
 
 
39
// copy constructor does a deep copy of the format block
 
40
 
 
41
CMediaType::CMediaType(const AM_MEDIA_TYPE& rt, __out_opt HRESULT* phr)
 
42
{
 
43
    HRESULT hr = CopyMediaType(this, &rt);
 
44
    if (FAILED(hr) && (NULL != phr)) {
 
45
        *phr = hr;
 
46
    }
 
47
}
 
48
 
 
49
 
 
50
CMediaType::CMediaType(const CMediaType& rt, __out_opt HRESULT* phr)
 
51
{
 
52
    HRESULT hr = CopyMediaType(this, &rt);
 
53
    if (FAILED(hr) && (NULL != phr)) {
 
54
        *phr = hr;
 
55
    }
 
56
}
 
57
 
 
58
 
 
59
// this class inherits publicly from AM_MEDIA_TYPE so the compiler could generate
 
60
// the following assignment operator itself, however it could introduce some
 
61
// memory conflicts and leaks in the process because the structure contains
 
62
// a dynamically allocated block (pbFormat) which it will not copy correctly
 
63
 
 
64
CMediaType&
 
65
CMediaType::operator=(const AM_MEDIA_TYPE& rt)
 
66
{
 
67
    Set(rt);
 
68
    return *this;
 
69
}
 
70
 
 
71
CMediaType&
 
72
CMediaType::operator=(const CMediaType& rt)
 
73
{
 
74
    *this = (AM_MEDIA_TYPE &) rt;
 
75
    return *this;
 
76
}
 
77
 
 
78
BOOL
 
79
CMediaType::operator == (const CMediaType& rt) const
 
80
{
 
81
    // I don't believe we need to check sample size or
 
82
    // temporal compression flags, since I think these must
 
83
    // be represented in the type, subtype and format somehow. They
 
84
    // are pulled out as separate flags so that people who don't understand
 
85
    // the particular format representation can still see them, but
 
86
    // they should duplicate information in the format block.
 
87
 
 
88
    return ((IsEqualGUID(majortype,rt.majortype) == TRUE) &&
 
89
        (IsEqualGUID(subtype,rt.subtype) == TRUE) &&
 
90
        (IsEqualGUID(formattype,rt.formattype) == TRUE) &&
 
91
        (cbFormat == rt.cbFormat) &&
 
92
        ( (cbFormat == 0) ||
 
93
          pbFormat != NULL && rt.pbFormat != NULL &&
 
94
          (memcmp(pbFormat, rt.pbFormat, cbFormat) == 0)));
 
95
}
 
96
 
 
97
 
 
98
BOOL
 
99
CMediaType::operator != (const CMediaType& rt) const
 
100
{
 
101
    /* Check to see if they are equal */
 
102
 
 
103
    if (*this == rt) {
 
104
        return FALSE;
 
105
    }
 
106
    return TRUE;
 
107
}
 
108
 
 
109
 
 
110
HRESULT
 
111
CMediaType::Set(const CMediaType& rt)
 
112
{
 
113
    return Set((AM_MEDIA_TYPE &) rt);
 
114
}
 
115
 
 
116
 
 
117
HRESULT
 
118
CMediaType::Set(const AM_MEDIA_TYPE& rt)
 
119
{
 
120
    if (&rt != this) {
 
121
        FreeMediaType(*this);
 
122
        HRESULT hr = CopyMediaType(this, &rt);
 
123
        if (FAILED(hr)) {
 
124
            return E_OUTOFMEMORY;
 
125
        }
 
126
    }
 
127
 
 
128
    return S_OK;    
 
129
}
 
130
 
 
131
 
 
132
BOOL
 
133
CMediaType::IsValid() const
 
134
{
 
135
    return (!IsEqualGUID(majortype,GUID_NULL));
 
136
}
 
137
 
 
138
 
 
139
void
 
140
CMediaType::SetType(const GUID* ptype)
 
141
{
 
142
    majortype = *ptype;
 
143
}
 
144
 
 
145
 
 
146
void
 
147
CMediaType::SetSubtype(const GUID* ptype)
 
148
{
 
149
    subtype = *ptype;
 
150
}
 
151
 
 
152
 
 
153
ULONG
 
154
CMediaType::GetSampleSize() const {
 
155
    if (IsFixedSize()) {
 
156
        return lSampleSize;
 
157
    } else {
 
158
        return 0;
 
159
    }
 
160
}
 
161
 
 
162
 
 
163
void
 
164
CMediaType::SetSampleSize(ULONG sz) {
 
165
    if (sz == 0) {
 
166
        SetVariableSize();
 
167
    } else {
 
168
        bFixedSizeSamples = TRUE;
 
169
        lSampleSize = sz;
 
170
    }
 
171
}
 
172
 
 
173
 
 
174
void
 
175
CMediaType::SetVariableSize() {
 
176
    bFixedSizeSamples = FALSE;
 
177
}
 
178
 
 
179
 
 
180
void
 
181
CMediaType::SetTemporalCompression(BOOL bCompressed) {
 
182
    bTemporalCompression = bCompressed;
 
183
}
 
184
 
 
185
BOOL
 
186
CMediaType::SetFormat(__in_bcount(cb) BYTE * pformat, ULONG cb)
 
187
{
 
188
    if (NULL == AllocFormatBuffer(cb))
 
189
        return(FALSE);
 
190
 
 
191
    ASSERT(pbFormat);
 
192
    memcpy(pbFormat, pformat, cb);
 
193
    return(TRUE);
 
194
}
 
195
 
 
196
 
 
197
// set the type of the media type format block, this type defines what you
 
198
// will actually find in the format pointer. For example FORMAT_VideoInfo or
 
199
// FORMAT_WaveFormatEx. In the future this may be an interface pointer to a
 
200
// property set. Before sending out media types this should be filled in.
 
201
 
 
202
void
 
203
CMediaType::SetFormatType(const GUID *pformattype)
 
204
{
 
205
    formattype = *pformattype;
 
206
}
 
207
 
 
208
 
 
209
// reset the format buffer
 
210
 
 
211
void CMediaType::ResetFormatBuffer()
 
212
{
 
213
    if (cbFormat) {
 
214
        CoTaskMemFree((PVOID)pbFormat);
 
215
    }
 
216
    cbFormat = 0;
 
217
    pbFormat = NULL;
 
218
}
 
219
 
 
220
 
 
221
// allocate length bytes for the format and return a read/write pointer
 
222
// If we cannot allocate the new block of memory we return NULL leaving
 
223
// the original block of memory untouched (as does ReallocFormatBuffer)
 
224
 
 
225
BYTE*
 
226
CMediaType::AllocFormatBuffer(ULONG length)
 
227
{
 
228
    ASSERT(length);
 
229
 
 
230
    // do the types have the same buffer size
 
231
 
 
232
    if (cbFormat == length) {
 
233
        return pbFormat;
 
234
    }
 
235
 
 
236
    // allocate the new format buffer
 
237
 
 
238
    BYTE *pNewFormat = (PBYTE)CoTaskMemAlloc(length);
 
239
    if (pNewFormat == NULL) {
 
240
        if (length <= cbFormat) return pbFormat; //reuse the old block anyway.
 
241
        return NULL;
 
242
    }
 
243
 
 
244
    // delete the old format
 
245
 
 
246
    if (cbFormat != 0) {
 
247
        ASSERT(pbFormat);
 
248
        CoTaskMemFree((PVOID)pbFormat);
 
249
    }
 
250
 
 
251
    cbFormat = length;
 
252
    pbFormat = pNewFormat;
 
253
    return pbFormat;
 
254
}
 
255
 
 
256
 
 
257
// reallocate length bytes for the format and return a read/write pointer
 
258
// to it. We keep as much information as we can given the new buffer size
 
259
// if this fails the original format buffer is left untouched. The caller
 
260
// is responsible for ensuring the size of memory required is non zero
 
261
 
 
262
BYTE*
 
263
CMediaType::ReallocFormatBuffer(ULONG length)
 
264
{
 
265
    ASSERT(length);
 
266
 
 
267
    // do the types have the same buffer size
 
268
 
 
269
    if (cbFormat == length) {
 
270
        return pbFormat;
 
271
    }
 
272
 
 
273
    // allocate the new format buffer
 
274
 
 
275
    BYTE *pNewFormat = (PBYTE)CoTaskMemAlloc(length);
 
276
    if (pNewFormat == NULL) {
 
277
        if (length <= cbFormat) return pbFormat; //reuse the old block anyway.
 
278
        return NULL;
 
279
    }
 
280
 
 
281
    // copy any previous format (or part of if new is smaller)
 
282
    // delete the old format and replace with the new one
 
283
 
 
284
    if (cbFormat != 0) {
 
285
        ASSERT(pbFormat);
 
286
        memcpy(pNewFormat,pbFormat,min(length,cbFormat));
 
287
        CoTaskMemFree((PVOID)pbFormat);
 
288
    }
 
289
 
 
290
    cbFormat = length;
 
291
    pbFormat = pNewFormat;
 
292
    return pNewFormat;
 
293
}
 
294
 
 
295
// initialise a media type structure
 
296
 
 
297
void CMediaType::InitMediaType()
 
298
{
 
299
    ZeroMemory((PVOID)this, sizeof(*this));
 
300
    lSampleSize = 1;
 
301
    bFixedSizeSamples = TRUE;
 
302
}
 
303
 
 
304
 
 
305
// a partially specified media type can be passed to IPin::Connect
 
306
// as a constraint on the media type used in the connection.
 
307
// the type, subtype or format type can be null.
 
308
BOOL
 
309
CMediaType::IsPartiallySpecified(void) const
 
310
{
 
311
    if ((majortype == GUID_NULL) ||
 
312
        (formattype == GUID_NULL)) {
 
313
            return TRUE;
 
314
    } else {
 
315
        return FALSE;
 
316
    }
 
317
}
 
318
 
 
319
BOOL
 
320
CMediaType::MatchesPartial(const CMediaType* ppartial) const
 
321
{
 
322
    if ((ppartial->majortype != GUID_NULL) &&
 
323
        (majortype != ppartial->majortype)) {
 
324
            return FALSE;
 
325
    }
 
326
    if ((ppartial->subtype != GUID_NULL) &&
 
327
        (subtype != ppartial->subtype)) {
 
328
            return FALSE;
 
329
    }
 
330
 
 
331
    if (ppartial->formattype != GUID_NULL) {
 
332
        // if the format block is specified then it must match exactly
 
333
        if (formattype != ppartial->formattype) {
 
334
            return FALSE;
 
335
        }
 
336
        if (cbFormat != ppartial->cbFormat) {
 
337
            return FALSE;
 
338
        }
 
339
        if ((cbFormat != 0) &&
 
340
            (memcmp(pbFormat, ppartial->pbFormat, cbFormat) != 0)) {
 
341
                return FALSE;
 
342
        }
 
343
    }
 
344
 
 
345
    return TRUE;
 
346
 
 
347
}
 
348
 
 
349
 
 
350
 
 
351
// general purpose function to delete a heap allocated AM_MEDIA_TYPE structure
 
352
// which is useful when calling IEnumMediaTypes::Next as the interface
 
353
// implementation allocates the structures which you must later delete
 
354
// the format block may also be a pointer to an interface to release
 
355
 
 
356
void WINAPI DeleteMediaType(__inout_opt AM_MEDIA_TYPE *pmt)
 
357
{
 
358
    // allow NULL pointers for coding simplicity
 
359
 
 
360
    if (pmt == NULL) {
 
361
        return;
 
362
    }
 
363
 
 
364
    FreeMediaType(*pmt);
 
365
    CoTaskMemFree((PVOID)pmt);
 
366
}
 
367
 
 
368
 
 
369
// this also comes in useful when using the IEnumMediaTypes interface so
 
370
// that you can copy a media type, you can do nearly the same by creating
 
371
// a CMediaType object but as soon as it goes out of scope the destructor
 
372
// will delete the memory it allocated (this takes a copy of the memory)
 
373
 
 
374
AM_MEDIA_TYPE * WINAPI CreateMediaType(AM_MEDIA_TYPE const *pSrc)
 
375
{
 
376
    ASSERT(pSrc);
 
377
 
 
378
    // Allocate a block of memory for the media type
 
379
 
 
380
    AM_MEDIA_TYPE *pMediaType =
 
381
        (AM_MEDIA_TYPE *)CoTaskMemAlloc(sizeof(AM_MEDIA_TYPE));
 
382
 
 
383
    if (pMediaType == NULL) {
 
384
        return NULL;
 
385
    }
 
386
    // Copy the variable length format block
 
387
 
 
388
    HRESULT hr = CopyMediaType(pMediaType,pSrc);
 
389
    if (FAILED(hr)) {
 
390
        CoTaskMemFree((PVOID)pMediaType);
 
391
        return NULL;
 
392
    }
 
393
 
 
394
    return pMediaType;
 
395
}
 
396
 
 
397
 
 
398
//  Copy 1 media type to another
 
399
 
 
400
HRESULT WINAPI CopyMediaType(__out AM_MEDIA_TYPE *pmtTarget, const AM_MEDIA_TYPE *pmtSource)
 
401
{
 
402
    //  We'll leak if we copy onto one that already exists - there's one
 
403
    //  case we can check like that - copying to itself.
 
404
    ASSERT(pmtSource != pmtTarget);
 
405
    *pmtTarget = *pmtSource;
 
406
    if (pmtSource->cbFormat != 0) {
 
407
        ASSERT(pmtSource->pbFormat != NULL);
 
408
        pmtTarget->pbFormat = (PBYTE)CoTaskMemAlloc(pmtSource->cbFormat);
 
409
        if (pmtTarget->pbFormat == NULL) {
 
410
            pmtTarget->cbFormat = 0;
 
411
            return E_OUTOFMEMORY;
 
412
        } else {
 
413
            CopyMemory((PVOID)pmtTarget->pbFormat, (PVOID)pmtSource->pbFormat,
 
414
                       pmtTarget->cbFormat);
 
415
        }
 
416
    }
 
417
    if (pmtTarget->pUnk != NULL) {
 
418
        pmtTarget->pUnk->AddRef();
 
419
    }
 
420
 
 
421
    return S_OK;
 
422
}
 
423
 
 
424
//  Free an existing media type (ie free resources it holds)
 
425
 
 
426
void WINAPI FreeMediaType(__inout AM_MEDIA_TYPE& mt)
 
427
{
 
428
    if (mt.cbFormat != 0) {
 
429
        CoTaskMemFree((PVOID)mt.pbFormat);
 
430
 
 
431
        // Strictly unnecessary but tidier
 
432
        mt.cbFormat = 0;
 
433
        mt.pbFormat = NULL;
 
434
    }
 
435
    if (mt.pUnk != NULL) {
 
436
        mt.pUnk->Release();
 
437
        mt.pUnk = NULL;
 
438
    }
 
439
}
 
440
 
 
441
//  Initialize a media type from a WAVEFORMATEX
 
442
 
 
443
STDAPI CreateAudioMediaType(
 
444
    const WAVEFORMATEX *pwfx,
 
445
    __out AM_MEDIA_TYPE *pmt,
 
446
    BOOL bSetFormat
 
447
)
 
448
{
 
449
    pmt->majortype            = MEDIATYPE_Audio;
 
450
    if (pwfx->wFormatTag == WAVE_FORMAT_EXTENSIBLE) {
 
451
        pmt->subtype = ((PWAVEFORMATEXTENSIBLE)pwfx)->SubFormat;
 
452
    } else {
 
453
        pmt->subtype              = FOURCCMap(pwfx->wFormatTag);
 
454
    }
 
455
    pmt->formattype           = FORMAT_WaveFormatEx;
 
456
    pmt->bFixedSizeSamples    = TRUE;
 
457
    pmt->bTemporalCompression = FALSE;
 
458
    pmt->lSampleSize          = pwfx->nBlockAlign;
 
459
    pmt->pUnk                 = NULL;
 
460
    if (bSetFormat) {
 
461
        if (pwfx->wFormatTag == WAVE_FORMAT_PCM) {
 
462
            pmt->cbFormat         = sizeof(WAVEFORMATEX);
 
463
        } else {
 
464
            pmt->cbFormat         = sizeof(WAVEFORMATEX) + pwfx->cbSize;
 
465
        }
 
466
        pmt->pbFormat             = (PBYTE)CoTaskMemAlloc(pmt->cbFormat);
 
467
        if (pmt->pbFormat == NULL) {
 
468
            return E_OUTOFMEMORY;
 
469
        }
 
470
        if (pwfx->wFormatTag == WAVE_FORMAT_PCM) {
 
471
            CopyMemory(pmt->pbFormat, pwfx, sizeof(PCMWAVEFORMAT));
 
472
            ((WAVEFORMATEX *)pmt->pbFormat)->cbSize = 0;
 
473
        } else {
 
474
            CopyMemory(pmt->pbFormat, pwfx, pmt->cbFormat);
 
475
        }
 
476
    }
 
477
    return S_OK;
 
478
}
 
479
 
 
480
// eliminate very many spurious warnings from MS compiler
 
481
#pragma warning(disable:4514)
 
482
 
 
483
#endif /* PJMEDIA_VIDEO_DEV_HAS_DSHOW */