1/* 2 * Copyright (C) 2013 Apple Inc. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' 14 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, 15 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS 17 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 18 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 19 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 20 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 21 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 22 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF 23 * THE POSSIBILITY OF SUCH DAMAGE. 24 */ 25 26#include "config.h" 27#include "MockCDM.h" 28 29#if ENABLE(ENCRYPTED_MEDIA_V2) 30 31#include "CDM.h" 32#include "MediaKeyError.h" 33#include <wtf/Uint8Array.h> 34 35namespace WebCore { 36 37class MockCDMSession : public CDMSession { 38public: 39 static PassOwnPtr<MockCDMSession> create() { return adoptPtr(new MockCDMSession()); } 40 virtual ~MockCDMSession() { } 41 42 virtual const String& sessionId() const OVERRIDE { return m_sessionId; } 43 virtual PassRefPtr<Uint8Array> generateKeyRequest(const String& mimeType, Uint8Array* initData, String& destinationURL, unsigned short& errorCode, unsigned long& systemCode) OVERRIDE; 44 virtual void releaseKeys() OVERRIDE; 45 virtual bool update(Uint8Array*, RefPtr<Uint8Array>& nextMessage, unsigned short& errorCode, unsigned long& systemCode) OVERRIDE; 46 47protected: 48 MockCDMSession(); 49 50 String m_sessionId; 51}; 52 53bool MockCDM::supportsKeySystem(const String& keySystem) 54{ 55 return equalIgnoringCase(keySystem, "com.webcore.mock"); 56} 57 58bool MockCDM::supportsKeySystemAndMimeType(const String& keySystem, const String& mimeType) 59{ 60 if (!supportsKeySystem(keySystem)) 61 return false; 62 63 return equalIgnoringCase(mimeType, "video/mock"); 64} 65 66bool MockCDM::supportsMIMEType(const String& mimeType) 67{ 68 return equalIgnoringCase(mimeType, "video/mock"); 69} 70 71PassOwnPtr<CDMSession> MockCDM::createSession() 72{ 73 return MockCDMSession::create(); 74} 75 76static Uint8Array* initDataPrefix() 77{ 78 static const unsigned char prefixData[] = {'m', 'o', 'c', 'k'}; 79 DEFINE_STATIC_LOCAL(RefPtr<Uint8Array>, prefix, ()); 80 static bool initialized = false; 81 if (!initialized) { 82 initialized = true; 83 prefix = Uint8Array::create(prefixData, sizeof(prefixData) / sizeof(prefixData[0])); 84 } 85 return prefix.get(); 86} 87 88static Uint8Array* keyPrefix() 89{ 90 static const unsigned char prefixData[] = {'k', 'e', 'y'}; 91 DEFINE_STATIC_LOCAL(RefPtr<WTF::Uint8Array>, prefix, ()); 92 static bool initialized = false; 93 if (!initialized) { 94 initialized = true; 95 prefix = Uint8Array::create(prefixData, sizeof(prefixData) / sizeof(prefixData[0])); 96 } 97 return prefix.get(); 98} 99 100static Uint8Array* keyRequest() 101{ 102 static const unsigned char requestData[] = {'r', 'e', 'q', 'u', 'e', 's', 't'}; 103 DEFINE_STATIC_LOCAL(RefPtr<WTF::Uint8Array>, request, ()); 104 static bool initialized = false; 105 if (!initialized) { 106 initialized = true; 107 request = Uint8Array::create(requestData, sizeof(requestData) / sizeof(requestData[0])); 108 } 109 return request.get(); 110} 111 112static String generateSessionId() 113{ 114 static int monotonicallyIncreasingSessionId = 0; 115 return String::number(monotonicallyIncreasingSessionId++); 116} 117 118MockCDMSession::MockCDMSession() 119 : m_sessionId(generateSessionId()) 120{ 121} 122 123PassRefPtr<Uint8Array> MockCDMSession::generateKeyRequest(const String&, Uint8Array* initData, String&, unsigned short& errorCode, unsigned long&) 124{ 125 for (unsigned i = 0; i < initDataPrefix()->length(); ++i) { 126 if (!initData || i >= initData->length() || initData->item(i) != initDataPrefix()->item(i)) { 127 errorCode = MediaKeyError::MEDIA_KEYERR_UNKNOWN; 128 return 0; 129 } 130 } 131 return keyRequest(); 132} 133 134void MockCDMSession::releaseKeys() 135{ 136 // no-op 137} 138 139bool MockCDMSession::update(Uint8Array* key, RefPtr<Uint8Array>&, unsigned short& errorCode, unsigned long&) 140{ 141 for (unsigned i = 0; i < keyPrefix()->length(); ++i) { 142 if (i >= key->length() || key->item(i) != keyPrefix()->item(i)) { 143 errorCode = MediaKeyError::MEDIA_KEYERR_CLIENT; 144 return false; 145 } 146 } 147 return true; 148} 149 150} 151 152#endif // ENABLE(ENCRYPTED_MEDIA_V2) 153