зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1125202 - SpiderMonkey: Replace AssemblerBuffer's internals with mozilla::Vector r=sstangl
This commit is contained in:
Родитель
69618e3989
Коммит
2742e5d193
|
@ -91,7 +91,7 @@ AssemblerX86Shared::trace(JSTracer *trc)
|
|||
}
|
||||
if (dataRelocations_.length()) {
|
||||
CompactBufferReader reader(dataRelocations_);
|
||||
::TraceDataRelocations(trc, masm.buffer(), reader);
|
||||
::TraceDataRelocations(trc, masm.data(), reader);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -75,96 +75,78 @@ namespace js {
|
|||
namespace jit {
|
||||
|
||||
class AssemblerBuffer {
|
||||
static const size_t inlineCapacity = 256;
|
||||
public:
|
||||
AssemblerBuffer()
|
||||
: m_buffer(m_inlineBuffer)
|
||||
, m_capacity(inlineCapacity)
|
||||
, m_size(0)
|
||||
, m_allocSize(0)
|
||||
, m_oom(false)
|
||||
: m_oom(false)
|
||||
{
|
||||
}
|
||||
|
||||
~AssemblerBuffer()
|
||||
{
|
||||
if (m_buffer != m_inlineBuffer)
|
||||
js_free(m_buffer);
|
||||
}
|
||||
|
||||
void ensureSpace(size_t space)
|
||||
{
|
||||
if (m_size > m_capacity - space)
|
||||
grow();
|
||||
if (MOZ_UNLIKELY(!m_buffer.reserve(m_buffer.length() + space)))
|
||||
oomDetected();
|
||||
}
|
||||
|
||||
bool isAligned(size_t alignment) const
|
||||
{
|
||||
return !(m_size & (alignment - 1));
|
||||
return !(m_buffer.length() & (alignment - 1));
|
||||
}
|
||||
|
||||
void putByteUnchecked(int value)
|
||||
{
|
||||
MOZ_ASSERT(!(m_size > m_capacity - 4));
|
||||
m_buffer[m_size] = char(value);
|
||||
m_size++;
|
||||
m_buffer.infallibleAppend(char(value));
|
||||
}
|
||||
|
||||
void putByte(int value)
|
||||
{
|
||||
if (m_size > m_capacity - 4)
|
||||
grow();
|
||||
putByteUnchecked(value);
|
||||
if (MOZ_UNLIKELY(!m_buffer.append(char(value))))
|
||||
oomDetected();
|
||||
}
|
||||
|
||||
void putShortUnchecked(int value)
|
||||
{
|
||||
MOZ_ASSERT(!(m_size > m_capacity - 4));
|
||||
*reinterpret_cast<short*>(&m_buffer[m_size]) = short(value);
|
||||
m_size += 2;
|
||||
m_buffer.infallibleGrowByUninitialized(2);
|
||||
memcpy(m_buffer.end() - 2, &value, 2);
|
||||
}
|
||||
|
||||
void putShort(int value)
|
||||
{
|
||||
if (m_size > m_capacity - 4)
|
||||
grow();
|
||||
putShortUnchecked(value);
|
||||
if (MOZ_UNLIKELY(!m_buffer.growByUninitialized(2))) {
|
||||
oomDetected();
|
||||
return;
|
||||
}
|
||||
memcpy(m_buffer.end() - 2, &value, 2);
|
||||
}
|
||||
|
||||
void putIntUnchecked(int value)
|
||||
{
|
||||
MOZ_ASSERT(!(m_size > m_capacity - 4));
|
||||
*reinterpret_cast<int*>(&m_buffer[m_size]) = value;
|
||||
m_size += 4;
|
||||
m_buffer.infallibleGrowByUninitialized(4);
|
||||
memcpy(m_buffer.end() - 4, &value, 4);
|
||||
}
|
||||
|
||||
void putInt64Unchecked(int64_t value)
|
||||
{
|
||||
MOZ_ASSERT(!(m_size > m_capacity - 8));
|
||||
*reinterpret_cast<int64_t*>(&m_buffer[m_size]) = value;
|
||||
m_size += 8;
|
||||
m_buffer.infallibleGrowByUninitialized(8);
|
||||
memcpy(m_buffer.end() - 8, &value, 8);
|
||||
}
|
||||
|
||||
void putInt(int value)
|
||||
{
|
||||
if (m_size > m_capacity - 4)
|
||||
grow();
|
||||
putIntUnchecked(value);
|
||||
if (MOZ_UNLIKELY(!m_buffer.growByUninitialized(4))) {
|
||||
oomDetected();
|
||||
return;
|
||||
}
|
||||
memcpy(m_buffer.end() - 4, &value, 4);
|
||||
}
|
||||
|
||||
void* data() const
|
||||
unsigned char *data()
|
||||
{
|
||||
return m_buffer;
|
||||
return m_buffer.begin();
|
||||
}
|
||||
|
||||
size_t size() const
|
||||
{
|
||||
return m_size;
|
||||
}
|
||||
|
||||
size_t allocSize() const
|
||||
{
|
||||
return m_allocSize;
|
||||
return m_buffer.length();
|
||||
}
|
||||
|
||||
bool oom() const
|
||||
|
@ -172,91 +154,32 @@ namespace jit {
|
|||
return m_oom;
|
||||
}
|
||||
|
||||
unsigned char *buffer() const {
|
||||
const unsigned char *buffer() const {
|
||||
MOZ_ASSERT(!m_oom);
|
||||
return reinterpret_cast<unsigned char *>(m_buffer);
|
||||
return m_buffer.begin();
|
||||
}
|
||||
|
||||
protected:
|
||||
void append(const char* data, size_t size)
|
||||
{
|
||||
if (m_size > m_capacity - size)
|
||||
grow(size);
|
||||
|
||||
// If we OOM and size > inlineCapacity, this would crash.
|
||||
if (m_oom)
|
||||
return;
|
||||
memcpy(m_buffer + m_size, data, size);
|
||||
m_size += size;
|
||||
}
|
||||
|
||||
/*
|
||||
* OOM handling: This class can OOM in the grow() method trying to
|
||||
* allocate a new buffer. In response to an OOM, we need to avoid
|
||||
* OOM handling: This class can OOM in the ensureSpace() method trying
|
||||
* to allocate a new buffer. In response to an OOM, we need to avoid
|
||||
* crashing and report the error. We also want to make it so that
|
||||
* users of this class need to check for OOM only at certain points
|
||||
* and not after every operation.
|
||||
*
|
||||
* Our strategy for handling an OOM is to set m_oom, and then set
|
||||
* m_size to 0, preserving the current buffer. This way, the user
|
||||
* Our strategy for handling an OOM is to set m_oom, and then clear (but
|
||||
* not free) m_buffer, preserving the current buffer. This way, the user
|
||||
* can continue assembling into the buffer, deferring OOM checking
|
||||
* until the user wants to read code out of the buffer.
|
||||
*
|
||||
* See also the |buffer| method.
|
||||
*/
|
||||
|
||||
void grow(size_t extraCapacity = 0)
|
||||
{
|
||||
char* newBuffer;
|
||||
|
||||
/*
|
||||
* If |extraCapacity| is zero (as it almost always is) this is an
|
||||
* allocator-friendly doubling growth strategy.
|
||||
*/
|
||||
size_t doubleCapacity = m_capacity + m_capacity;
|
||||
|
||||
// Check for overflow.
|
||||
if (doubleCapacity < m_capacity) {
|
||||
m_size = 0;
|
||||
m_oom = true;
|
||||
return;
|
||||
}
|
||||
|
||||
size_t newCapacity = doubleCapacity + extraCapacity;
|
||||
|
||||
// Check for overflow.
|
||||
if (newCapacity < doubleCapacity) {
|
||||
m_size = 0;
|
||||
m_oom = true;
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_buffer == m_inlineBuffer) {
|
||||
newBuffer = static_cast<char*>(js_malloc(newCapacity));
|
||||
if (!newBuffer) {
|
||||
m_size = 0;
|
||||
m_oom = true;
|
||||
return;
|
||||
}
|
||||
memcpy(newBuffer, m_buffer, m_size);
|
||||
} else {
|
||||
newBuffer = static_cast<char*>(js_realloc(m_buffer, newCapacity));
|
||||
if (!newBuffer) {
|
||||
m_size = 0;
|
||||
m_oom = true;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
m_buffer = newBuffer;
|
||||
m_capacity = newCapacity;
|
||||
void oomDetected() {
|
||||
m_oom = true;
|
||||
m_buffer.clear();
|
||||
}
|
||||
|
||||
char m_inlineBuffer[inlineCapacity];
|
||||
char* m_buffer;
|
||||
size_t m_capacity;
|
||||
size_t m_size;
|
||||
size_t m_allocSize;
|
||||
mozilla::Vector<unsigned char, 256, SystemAllocPolicy> m_buffer;
|
||||
bool m_oom;
|
||||
};
|
||||
|
||||
|
|
|
@ -627,8 +627,8 @@ public:
|
|||
};
|
||||
|
||||
size_t size() const { return m_formatter.size(); }
|
||||
size_t allocSize() const { return m_formatter.allocSize(); }
|
||||
unsigned char *buffer() const { return m_formatter.buffer(); }
|
||||
const unsigned char *buffer() const { return m_formatter.buffer(); }
|
||||
unsigned char *data() { return m_formatter.data(); }
|
||||
bool oom() const { return m_formatter.oom(); }
|
||||
|
||||
void nop()
|
||||
|
@ -5292,11 +5292,10 @@ private:
|
|||
// Administrative methods:
|
||||
|
||||
size_t size() const { return m_buffer.size(); }
|
||||
size_t allocSize() const { return m_buffer.allocSize(); }
|
||||
unsigned char *buffer() const { return m_buffer.buffer(); }
|
||||
const unsigned char *buffer() const { return m_buffer.buffer(); }
|
||||
bool oom() const { return m_buffer.oom(); }
|
||||
bool isAligned(int alignment) const { return m_buffer.isAligned(alignment); }
|
||||
void* data() const { return m_buffer.data(); }
|
||||
unsigned char *data() { return m_buffer.data(); }
|
||||
|
||||
private:
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче