1// Copyright (c) 2012 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef BASE_MEMORY_REF_COUNTED_MEMORY_H_
6#define BASE_MEMORY_REF_COUNTED_MEMORY_H_
7
8#include <string>
9#include <vector>
10
11#include "base/base_export.h"
12#include "base/compiler_specific.h"
13#include "base/memory/ref_counted.h"
14
15namespace base {
16
17// A generic interface to memory. This object is reference counted because one
18// of its two subclasses own the data they carry, and we need to have
19// heterogeneous containers of these two types of memory.
20class BASE_EXPORT RefCountedMemory
21    : public base::RefCountedThreadSafe<RefCountedMemory> {
22 public:
23  // Retrieves a pointer to the beginning of the data we point to. If the data
24  // is empty, this will return NULL.
25  virtual const unsigned char* front() const = 0;
26
27  // Size of the memory pointed to.
28  virtual size_t size() const = 0;
29
30  // Returns true if |other| is byte for byte equal.
31  bool Equals(const scoped_refptr<RefCountedMemory>& other) const;
32
33  // Handy method to simplify calling front() with a reinterpret_cast.
34  template<typename T> const T* front_as() const {
35    return reinterpret_cast<const T*>(front());
36  }
37
38 protected:
39  friend class base::RefCountedThreadSafe<RefCountedMemory>;
40  RefCountedMemory();
41  virtual ~RefCountedMemory();
42};
43
44// An implementation of RefCountedMemory, where the ref counting does not
45// matter.
46class BASE_EXPORT RefCountedStaticMemory : public RefCountedMemory {
47 public:
48  RefCountedStaticMemory()
49      : data_(NULL), length_(0) {}
50  RefCountedStaticMemory(const void* data, size_t length)
51      : data_(static_cast<const unsigned char*>(length ? data : NULL)),
52        length_(length) {}
53
54  // Overridden from RefCountedMemory:
55  virtual const unsigned char* front() const OVERRIDE;
56  virtual size_t size() const OVERRIDE;
57
58 private:
59  virtual ~RefCountedStaticMemory();
60
61  const unsigned char* data_;
62  size_t length_;
63
64  DISALLOW_COPY_AND_ASSIGN(RefCountedStaticMemory);
65};
66
67// An implementation of RefCountedMemory, where we own the data in a vector.
68class BASE_EXPORT RefCountedBytes : public RefCountedMemory {
69 public:
70  RefCountedBytes();
71
72  // Constructs a RefCountedBytes object by _copying_ from |initializer|.
73  explicit RefCountedBytes(const std::vector<unsigned char>& initializer);
74
75  // Constructs a RefCountedBytes object by copying |size| bytes from |p|.
76  RefCountedBytes(const unsigned char* p, size_t size);
77
78  // Constructs a RefCountedBytes object by performing a swap. (To non
79  // destructively build a RefCountedBytes, use the constructor that takes a
80  // vector.)
81  static RefCountedBytes* TakeVector(std::vector<unsigned char>* to_destroy);
82
83  // Overridden from RefCountedMemory:
84  virtual const unsigned char* front() const OVERRIDE;
85  virtual size_t size() const OVERRIDE;
86
87  const std::vector<unsigned char>& data() const { return data_; }
88  std::vector<unsigned char>& data() { return data_; }
89
90 private:
91  virtual ~RefCountedBytes();
92
93  std::vector<unsigned char> data_;
94
95  DISALLOW_COPY_AND_ASSIGN(RefCountedBytes);
96};
97
98// An implementation of RefCountedMemory, where the bytes are stored in an STL
99// string. Use this if your data naturally arrives in that format.
100class BASE_EXPORT RefCountedString : public RefCountedMemory {
101 public:
102  RefCountedString();
103
104  // Constructs a RefCountedString object by performing a swap. (To non
105  // destructively build a RefCountedString, use the default constructor and
106  // copy into object->data()).
107  static RefCountedString* TakeString(std::string* to_destroy);
108
109  // Overridden from RefCountedMemory:
110  virtual const unsigned char* front() const OVERRIDE;
111  virtual size_t size() const OVERRIDE;
112
113  const std::string& data() const { return data_; }
114  std::string& data() { return data_; }
115
116 private:
117  virtual ~RefCountedString();
118
119  std::string data_;
120
121  DISALLOW_COPY_AND_ASSIGN(RefCountedString);
122};
123
124// An implementation of RefCountedMemory that holds a chunk of memory
125// previously allocated with malloc or calloc, and that therefore must be freed
126// using free().
127class BASE_EXPORT RefCountedMallocedMemory : public base::RefCountedMemory {
128 public:
129  RefCountedMallocedMemory(void* data, size_t length);
130
131  // Overridden from RefCountedMemory:
132  virtual const unsigned char* front() const OVERRIDE;
133  virtual size_t size() const OVERRIDE;
134
135 private:
136  virtual ~RefCountedMallocedMemory();
137
138  unsigned char* data_;
139  size_t length_;
140
141  DISALLOW_COPY_AND_ASSIGN(RefCountedMallocedMemory);
142};
143
144}  // namespace base
145
146#endif  // BASE_MEMORY_REF_COUNTED_MEMORY_H_
147