Eine aufbereitete Darstellung der Quelle

 
     
 
 
Anforderungen  |   Konzepte  |   Entwurf  |   Entwicklung  |   Qualitätssicherung  |   Lebenszyklus  |   Steuerung
 
 
 
 

Benutzer

Quelle  WMFClearKeyUtils.h

  Sprache: C
 

/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */


#ifndef DOM_MEDIA_PLATFORM_WMF_CLEARKEY_WMFCLEARKEYCDMUTILS_H
#define DOM_MEDIA_PLATFORM_WMF_CLEARKEY_WMFCLEARKEYCDMUTILS_H

#include <initguid.h>
#include <mfidl.h>
#include <mutex>
#include <string>
#include <thread>
#include <windows.h>
#include <wrl.h>
#include <stdio.h>

#include "MFCDMExtra.h"
#include "mozilla/Assertions.h"
#include "mozilla/EndianUtils.h"

namespace mozilla {

inline constexpr WCHAR kCLEARKEY_SYSTEM_NAME[] = L"org.w3.clearkey";

#define WMF_CLEARKEY_DEBUG 0

#if WMF_CLEARKEY_DEBUG
#  define LOG(msg, ...)                                                   \
    printf(("[Thread %lu]: D/WMFClearKey " msg "\n"),                     \
           static_cast<unsigned long>(                                    \
               std::hash<std::thread::id>{}(std::this_thread::get_id())), \
           ##__VA_ARGS__)
#else
#  define LOG(msg, ...)
#endif

// Returns a trimmed pretty-function name as a std::string. Callers must
// bind the result to a named local before calling .c_str() on it, so the
// backing buffer outlives the pointer handed to printf.
inline std::string GetPrettyFunctionName(const char* aPrettyFunc) {
  std::string prettyFunction(aPrettyFunc);
  std::size_t pos1 = prettyFunction.find("::");
  std::size_t pos2 = prettyFunction.find("(", pos1);
  return prettyFunction.substr(0, pos2);
}

// We can't reuse the definition in the `MediaEngineUtils.h` due to the
// restriction of not being able to use XPCOM string in the external library.
#ifndef RETURN_IF_FAILED
#  define RETURN_IF_FAILED(x)               \
    do {                                    \
      HRESULT rv = x;                       \
      if (FAILED(rv)) {                     \
        LOG("(" #x ") failed, rv=%lx", rv); \
        return rv;                          \
      }                                     \
    } while (false)
#endif

#if WMF_CLEARKEY_DEBUG
#  define NOT_IMPLEMENTED()                                       \
    do {                                                          \
      const std::string prettyFunc =                              \
          mozilla::GetPrettyFunctionName(__PRETTY_FUNCTION__);    \
      LOG("WARNING : '%s' NOT IMPLEMENTED!", prettyFunc.c_str()); \
    } while (0)
#  define ENTRY_LOG(...)                                       \
    do {                                                       \
      const std::string prettyFunc =                           \
          mozilla::GetPrettyFunctionName(__PRETTY_FUNCTION__); \
      LOG("%s [%p]", prettyFunc.c_str(), this);                \
    } while (0)
#  define ENTRY_LOG_ARGS(fmt, ...)                                   \
    do {                                                             \
      const std::string prettyFunc =                                 \
          mozilla::GetPrettyFunctionName(__PRETTY_FUNCTION__);       \
      LOG("%s [%p]: " fmt, prettyFunc.c_str(), this, ##__VA_ARGS__); \
    } while (0)
#else
#  define NOT_IMPLEMENTED() ((void)0)
#  define ENTRY_LOG(...) ((void)0)
#  define ENTRY_LOG_ARGS(fmt, ...) \
    do {                           \
      (void)fmt;                   \
      (void)(0##__VA_ARGS__);    \
    } while (0)
#endif

// Convert a GUID (little-endian GUID byte order) to a 16-byte big-endian key
// ID. In Media Foundation, key IDs are GUIDs but the actual key ID bytes are
// big-endian. Data1/2/3 are stored little-endian in a GUID, so we swap them.
inline void GuidToKeyId(const GUID& aGuid, uint8_t aKeyId[16]) {
  GUID swapped = aGuid;
  swapped.Data1 = NativeEndian::swapToBigEndian(aGuid.Data1);
  swapped.Data2 = NativeEndian::swapToBigEndian(aGuid.Data2);
  swapped.Data3 = NativeEndian::swapToBigEndian(aGuid.Data3);
  // Data4 is already a byte array (big-endian), no swap needed.
  memcpy(aKeyId, &swapped, 16);
}

// TODO : should we use Microsoft's definition or Chromium's defintion?

// This is defined in Microsoft's sample code
// https://github.com/microsoft/media-foundation/blob/dc81175a3e893c7c58fcbf1a943ac342e39f172c/samples/storecdm/clearkeyStoreCDM/clearkeydll/guids.h#L17-L18C14
// DEFINE_GUID(CLEARKEY_GUID_CLEARKEY_PROTECTION_SYSTEM_ID, 0x9b0ff3ca, 0x1378,
//             0x4f28, 0x96, 0x65, 0x18, 0x9e, 0x15, 0x30, 0x2a, 0x71);

// Media Foundation Clear Key protection system ID from Chromium
// {E4E94971-696A-447E-96E4-93FDF3A57A7A}
// https://source.chromium.org/chromium/chromium/src/+/main:media/cdm/win/test/media_foundation_clear_key_guids.h;l=16-29?q=CLEARKEY_GUID_CLEARKEY_PROTECTION_SYSTEM_ID&ss=chromium%2Fchromium%2Fsrc
DEFINE_GUID(CLEARKEY_GUID_CLEARKEY_PROTECTION_SYSTEM_ID, 0xe4e94971, 0x696a,
            0x447e, 0x96, 0xe4, 0x93, 0xfd, 0xf3, 0xa5, 0x7a, 0x7a);

// Media Foundation Clear Key content enabler type
// {C262FD73-2F13-41C2-94E7-4CAF087AE1D1}
DEFINE_GUID(MEDIA_FOUNDATION_CLEARKEY_GUID_CONTENT_ENABLER_TYPE, 0xc262fd73,
            0x2f13, 0x41c2, 0x94, 0xe7, 0x4c, 0xaf, 0x8, 0x7a, 0xe1, 0xd1);

// https://source.chromium.org/chromium/chromium/src/+/refs/heads/main:media/cdm/win/test/media_foundation_clear_key_guids.h;l=46;drc=fcefb4563e8ea5b2036ecde882f4f228dd1e4338
#define PLAYREADY_GUID_MEDIA_PROTECTION_SYSTEM_ID_STRING \
  L"{F4637010-03C3-42CD-B932-B48ADF3A6A54}"

// A PROPVARIANT that is automatically initialized and cleared upon respective
// construction and destruction of this class.
class AutoPropVar final {
 public:
  AutoPropVar() { PropVariantInit(&mVar); }

  ~AutoPropVar() { Reset(); }

  AutoPropVar(const AutoPropVar&) = delete;
  AutoPropVar& operator=(const AutoPropVar&) = delete;
  bool operator==(const AutoPropVar&) const = delete;
  bool operator!=(const AutoPropVar&) const = delete;

  // Returns a pointer to the underlying PROPVARIANT for use as an out param
  // in a function call.
  PROPVARIANT* Receive() {
    MOZ_ASSERT(mVar.vt == VT_EMPTY);
    return &mVar;
  }

  // Clears the instance to prepare it for re-use (e.g., via Receive).
  void Reset() {
    if (mVar.vt != VT_EMPTY) {
      HRESULT hr = PropVariantClear(&mVar);
      MOZ_ASSERT(SUCCEEDED(hr));
      (void)hr;
    }
  }

  const PROPVARIANT& get() const { return mVar; }
  const PROPVARIANT* ptr() const { return &mVar; }

 private:
  PROPVARIANT mVar;
};

template <typename T>
class ScopedCoMem final {
 public:
  ScopedCoMem() : mPtr(nullptr) {}

  ~ScopedCoMem() { Reset(nullptr); }

  ScopedCoMem(const ScopedCoMem&) = delete;
  ScopedCoMem& operator=(const ScopedCoMem&) = delete;

  T** operator&() {               // NOLINT
    MOZ_ASSERT(mPtr == nullptr);  // To catch memory leaks.
    return &mPtr;
  }

  operator T*() { return mPtr; }

  T* operator->() {
    MOZ_ASSERT(mPtr != nullptr);
    return mPtr;
  }

  const T* operator->() const {
    MOZ_ASSERT(mPtr != nullptr);
    return mPtr;
  }

  explicit operator bool() const { return mPtr; }

  friend bool operator==(const ScopedCoMem& lhs, std::nullptr_t) {
    return lhs.Get() == nullptr;
  }

  friend bool operator==(std::nullptr_t, const ScopedCoMem& rhs) {
    return rhs.Get() == nullptr;
  }

  friend bool operator!=(const ScopedCoMem& lhs, std::nullptr_t) {
    return lhs.Get() != nullptr;
  }

  friend bool operator!=(std::nullptr_t, const ScopedCoMem& rhs) {
    return rhs.Get() != nullptr;
  }

  void Reset(T* ptr) {
    if (mPtr) {
      CoTaskMemFree(mPtr);
    }
    mPtr = ptr;
  }

  T* Get() const { return mPtr; }

 private:
  T* mPtr;
};

template <typename T>
class DataMutex final {
 public:
  DataMutex() = default;

  template <typename... Args>
  explicit DataMutex(Args&&... args) : mData(std::forward<Args>(args)...) {}

  class AutoLock {
   public:
    AutoLock(std::unique_lock<std::mutex>&& lock, DataMutex<T>* mutex)
        : mLock(std::move(lock)), mMutex(mutex) {}
    T& operator*() { return ref(); }
    T* operator->() { return &ref(); }
    T& ref() const& { return mMutex->mData; }
    operator T*() const& { return &ref(); }
    ~AutoLock() { mMutex = nullptr; }

   private:
    std::unique_lock<std::mutex> mLock;
    DataMutex<T>* mMutex;
  };

  AutoLock Lock() {
    return AutoLock(std::unique_lock<std::mutex>(mMutex), this);
  }

 private:
  std::mutex mMutex;
  T mData;
};

}  // namespace mozilla

#endif  // DOM_MEDIA_PLATFORM_WMF_CLEARKEY_WMFCLEARKEYCDMUTILS_H

Messung V0.5 in Prozent
C=90 H=99 G=94

¤ Dauer der Verarbeitung: 0.5 Sekunden  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

PVS Prover

Isabelle Prover

NIST Cobol Testsuite

Cephes Mathematical Library

Vienna Development Method

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.






                                                                                                                                                                                                                                                                                                                                                                                                     


Neuigkeiten

     Aktuelles
     Motto des Tages

Open Source Software

     Quellcodebibliothek
     Eigene Quellcodes
     Fremde Quellcodes
     Suchen

Jenseits des Üblichen ....
    

Besucherstatistik

Besucherstatistik

Statistik
#Sources=141584
#Domains=752002