Home | History | Annotate | Download | only in libutils
      1 /*
      2  * Copyright (C) 2005 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 /*
     18  * DEPRECATED.  DO NOT USE FOR NEW CODE.
     19  */
     20 
     21 #ifndef ANDROID_SHARED_BUFFER_H
     22 #define ANDROID_SHARED_BUFFER_H
     23 
     24 #include <atomic>
     25 #include <stdint.h>
     26 #include <sys/types.h>
     27 
     28 // ---------------------------------------------------------------------------
     29 
     30 namespace android {
     31 
     32 class SharedBuffer
     33 {
     34 public:
     35 
     36     /* flags to use with release() */
     37     enum {
     38         eKeepStorage = 0x00000001
     39     };
     40 
     41     /*! allocate a buffer of size 'size' and acquire() it.
     42      *  call release() to free it.
     43      */
     44     static          SharedBuffer*           alloc(size_t size);
     45 
     46     /*! free the memory associated with the SharedBuffer.
     47      * Fails if there are any users associated with this SharedBuffer.
     48      * In other words, the buffer must have been release by all its
     49      * users.
     50      */
     51     static          void                    dealloc(const SharedBuffer* released);
     52 
     53     //! access the data for read
     54     inline          const void*             data() const;
     55 
     56     //! access the data for read/write
     57     inline          void*                   data();
     58 
     59     //! get size of the buffer
     60     inline          size_t                  size() const;
     61 
     62     //! get back a SharedBuffer object from its data
     63     static  inline  SharedBuffer*           bufferFromData(void* data);
     64 
     65     //! get back a SharedBuffer object from its data
     66     static  inline  const SharedBuffer*     bufferFromData(const void* data);
     67 
     68     //! get the size of a SharedBuffer object from its data
     69     static  inline  size_t                  sizeFromData(const void* data);
     70 
     71     //! edit the buffer (get a writtable, or non-const, version of it)
     72                     SharedBuffer*           edit() const;
     73 
     74     //! edit the buffer, resizing if needed
     75                     SharedBuffer*           editResize(size_t size) const;
     76 
     77     //! like edit() but fails if a copy is required
     78                     SharedBuffer*           attemptEdit() const;
     79 
     80     //! resize and edit the buffer, loose it's content.
     81                     SharedBuffer*           reset(size_t size) const;
     82 
     83     //! acquire/release a reference on this buffer
     84                     void                    acquire() const;
     85 
     86     /*! release a reference on this buffer, with the option of not
     87      * freeing the memory associated with it if it was the last reference
     88      * returns the previous reference count
     89      */
     90                     int32_t                 release(uint32_t flags = 0) const;
     91 
     92     //! returns wether or not we're the only owner
     93     inline          bool                    onlyOwner() const;
     94 
     95 
     96 private:
     97         inline SharedBuffer() { }
     98         inline ~SharedBuffer() { }
     99         SharedBuffer(const SharedBuffer&);
    100         SharedBuffer& operator = (const SharedBuffer&);
    101 
    102         // Must be sized to preserve correct alignment.
    103         mutable std::atomic<int32_t>        mRefs;
    104                 size_t                      mSize;
    105                 uint32_t                    mReserved[2];
    106 };
    107 
    108 static_assert(sizeof(SharedBuffer) % 8 == 0
    109         && (sizeof(size_t) > 4 || sizeof(SharedBuffer) == 16),
    110         "SharedBuffer has unexpected size");
    111 
    112 // ---------------------------------------------------------------------------
    113 
    114 const void* SharedBuffer::data() const {
    115     return this + 1;
    116 }
    117 
    118 void* SharedBuffer::data() {
    119     return this + 1;
    120 }
    121 
    122 size_t SharedBuffer::size() const {
    123     return mSize;
    124 }
    125 
    126 SharedBuffer* SharedBuffer::bufferFromData(void* data) {
    127     return data ? static_cast<SharedBuffer *>(data)-1 : 0;
    128 }
    129 
    130 const SharedBuffer* SharedBuffer::bufferFromData(const void* data) {
    131     return data ? static_cast<const SharedBuffer *>(data)-1 : 0;
    132 }
    133 
    134 size_t SharedBuffer::sizeFromData(const void* data) {
    135     return data ? bufferFromData(data)->mSize : 0;
    136 }
    137 
    138 bool SharedBuffer::onlyOwner() const {
    139     return (mRefs.load(std::memory_order_acquire) == 1);
    140 }
    141 
    142 }; // namespace android
    143 
    144 // ---------------------------------------------------------------------------
    145 
    146 #endif // ANDROID_VECTOR_H
    147