1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #ifndef mozilla_ArenaAllocatorExtensions_h
8 #define mozilla_ArenaAllocatorExtensions_h
10 #include "mozilla/ArenaAllocator.h"
11 #include "mozilla/CheckedInt.h"
12 #include "nsAString.h"
15 * Extensions to the ArenaAllocator class.
21 template <typename T
, size_t ArenaSize
, size_t Alignment
>
22 T
* DuplicateString(const T
* aSrc
, const CheckedInt
<size_t>& aLen
,
23 ArenaAllocator
<ArenaSize
, Alignment
>& aArena
);
28 * Makes an arena allocated null-terminated copy of the source string. The
29 * source string must be null-terminated.
31 * @param aSrc String to copy.
32 * @param aArena The arena to allocate the string copy out of.
33 * @return An arena allocated null-terminated string.
35 template <typename T
, size_t ArenaSize
, size_t Alignment
>
36 T
* ArenaStrdup(const T
* aStr
, ArenaAllocator
<ArenaSize
, Alignment
>& aArena
) {
37 return detail::DuplicateString(aStr
, nsCharTraits
<T
>::length(aStr
), aArena
);
41 * Makes an arena allocated null-terminated copy of the source string.
43 * @param aSrc String to copy.
44 * @param aArena The arena to allocate the string copy out of.
45 * @return An arena allocated null-terminated string.
47 template <typename T
, size_t ArenaSize
, size_t Alignment
>
48 T
* ArenaStrdup(const detail::nsTStringRepr
<T
>& aStr
,
49 ArenaAllocator
<ArenaSize
, Alignment
>& aArena
) {
50 return detail::DuplicateString(aStr
.BeginReading(), aStr
.Length(), aArena
);
54 * Copies the source string and adds a null terminator. Source string does not
55 * have to be null terminated.
57 template <typename T
, size_t ArenaSize
, size_t Alignment
>
58 T
* detail::DuplicateString(const T
* aSrc
, const CheckedInt
<size_t>& aLen
,
59 ArenaAllocator
<ArenaSize
, Alignment
>& aArena
) {
60 const auto byteLen
= (aLen
+ 1) * sizeof(T
);
61 if (!byteLen
.isValid()) {
65 T
* p
= static_cast<T
*>(aArena
.Allocate(byteLen
.value(), mozilla::fallible
));
67 memcpy(p
, aSrc
, byteLen
.value() - sizeof(T
));
68 p
[aLen
.value()] = T(0);
74 } // namespace mozilla
76 #endif // mozilla_ArenaAllocatorExtensions_h