1/* 2 * Copyright 2004 The WebRTC Project Authors. All rights reserved. 3 * 4 * Use of this source code is governed by a BSD-style license 5 * that can be found in the LICENSE file in the root of the source 6 * tree. An additional intellectual property rights grant can be found 7 * in the file PATENTS. All contributing project authors may 8 * be found in the AUTHORS file in the root of the source tree. 9 */ 10 11// @file Contains utility classes that make it easier to use SecBuffers 12 13#ifndef WEBRTC_BASE_SEC_BUFFER_H__ 14#define WEBRTC_BASE_SEC_BUFFER_H__ 15 16namespace rtc { 17 18// A base class for CSecBuffer<T>. Contains 19// all implementation that does not require 20// template arguments. 21class CSecBufferBase : public SecBuffer { 22 public: 23 CSecBufferBase() { 24 Clear(); 25 } 26 27 // Uses the SSPI to free a pointer, must be 28 // used for buffers returned from SSPI APIs. 29 static void FreeSSPI(void *ptr) { 30 if ( ptr ) { 31 SECURITY_STATUS status; 32 status = ::FreeContextBuffer(ptr); 33 ASSERT(SEC_E_OK == status); // "Freeing context buffer" 34 } 35 } 36 37 // Deletes a buffer with operator delete 38 static void FreeDelete(void *ptr) { 39 delete [] reinterpret_cast<char*>(ptr); 40 } 41 42 // A noop delete, for buffers over other 43 // people's memory 44 static void FreeNone(void *ptr) { 45 } 46 47 protected: 48 // Clears the buffer to EMPTY & NULL 49 void Clear() { 50 this->BufferType = SECBUFFER_EMPTY; 51 this->cbBuffer = 0; 52 this->pvBuffer = NULL; 53 } 54}; 55 56// Wrapper class for SecBuffer to take care 57// of initialization and destruction. 58template <void (*pfnFreeBuffer)(void *ptr)> 59class CSecBuffer: public CSecBufferBase { 60 public: 61 // Initializes buffer to empty & NULL 62 CSecBuffer() { 63 } 64 65 // Frees any allocated memory 66 ~CSecBuffer() { 67 Release(); 68 } 69 70 // Frees the buffer appropriately, and re-nulls 71 void Release() { 72 pfnFreeBuffer(this->pvBuffer); 73 Clear(); 74 } 75 76 private: 77 // A placeholder function for compile-time asserts on the class 78 void CompileAsserts() { 79 // never invoked... 80 assert(false); // _T("Notreached") 81 82 // This class must not extend the size of SecBuffer, since 83 // we use arrays of CSecBuffer in CSecBufferBundle below 84 cassert(sizeof(CSecBuffer<SSPIFree> == sizeof(SecBuffer))); 85 } 86}; 87 88// Contains all generic implementation for the 89// SecBufferBundle class 90class SecBufferBundleBase { 91 public: 92}; 93 94// A template class that bundles a SecBufferDesc with 95// one or more SecBuffers for convenience. Can take 96// care of deallocating buffers appropriately, as indicated 97// by pfnFreeBuffer function. 98// By default does no deallocation. 99template <int num_buffers, 100 void (*pfnFreeBuffer)(void *ptr) = CSecBufferBase::FreeNone> 101class CSecBufferBundle : public SecBufferBundleBase { 102 public: 103 // Constructs a security buffer bundle with num_buffers 104 // buffers, all of which are empty and nulled. 105 CSecBufferBundle() { 106 desc_.ulVersion = SECBUFFER_VERSION; 107 desc_.cBuffers = num_buffers; 108 desc_.pBuffers = buffers_; 109 } 110 111 // Frees all currently used buffers. 112 ~CSecBufferBundle() { 113 Release(); 114 } 115 116 // Accessor for the descriptor 117 PSecBufferDesc desc() { 118 return &desc_; 119 } 120 121 // Accessor for the descriptor 122 const PSecBufferDesc desc() const { 123 return &desc_; 124 } 125 126 // returns the i-th security buffer 127 SecBuffer &operator[] (size_t num) { 128 ASSERT(num < num_buffers); // "Buffer index out of bounds" 129 return buffers_[num]; 130 } 131 132 // returns the i-th security buffer 133 const SecBuffer &operator[] (size_t num) const { 134 ASSERT(num < num_buffers); // "Buffer index out of bounds" 135 return buffers_[num]; 136 } 137 138 // Frees all non-NULL security buffers, 139 // using the deallocation function 140 void Release() { 141 for ( size_t i = 0; i < num_buffers; ++i ) { 142 buffers_[i].Release(); 143 } 144 } 145 146 private: 147 // Our descriptor 148 SecBufferDesc desc_; 149 // Our bundled buffers, each takes care of its own 150 // initialization and destruction 151 CSecBuffer<pfnFreeBuffer> buffers_[num_buffers]; 152}; 153 154} // namespace rtc 155 156#endif // WEBRTC_BASE_SEC_BUFFER_H__ 157