Commit 1ddaea61 authored by whesse@chromium.org's avatar whesse@chromium.org

Stop inlining of list reallocation in virtual frames.

Review URL: http://codereview.chromium.org/100253

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@1835 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent 7fa09c0a
// Copyright 2006-2008 the V8 project authors. All rights reserved.
// Copyright 2006-2009 the V8 project authors. All rights reserved.
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
......@@ -38,21 +38,36 @@ void List<T, P>::Add(const T& element) {
if (length_ < capacity_) {
data_[length_++] = element;
} else {
// Grow the list capacity by 50%, but make sure to let it grow
// even when the capacity is zero (possible initial case).
int new_capacity = 1 + capacity_ + (capacity_ >> 1);
T* new_data = NewData(new_capacity);
memcpy(new_data, data_, capacity_ * sizeof(T));
// Since the element reference could be an element of the list,
// assign it to the new backing store before deleting the old.
new_data[length_++] = element;
DeleteData(data_);
data_ = new_data;
capacity_ = new_capacity;
List<T, P>::ResizeAdd(element);
}
}
// Use two layers of inlining so that the non-inlined function can
// use the same implementation as the inlined version.
template<typename T, class P>
void List<T, P>::ResizeAdd(const T& element) {
ResizeAddInternal(element);
}
template<typename T, class P>
void List<T, P>::ResizeAddInternal(const T& element) {
ASSERT(length_ >= capacity_);
// Grow the list capacity by 50%, but make sure to let it grow
// even when the capacity is zero (possible initial case).
int new_capacity = 1 + capacity_ + (capacity_ >> 1);
T* new_data = List<T, P>::NewData(new_capacity);
memcpy(new_data, data_, capacity_ * sizeof(T));
// Since the element reference could be an element of the list,
// assign it to the new backing store before deleting the old.
new_data[length_++] = element;
List<T, P>::DeleteData(data_);
data_ = new_data;
capacity_ = new_capacity;
}
template<typename T, class P>
Vector<T> List<T, P>::AddBlock(T value, int count) {
int start = length_;
......
......@@ -118,9 +118,24 @@ class List {
INLINE(T* NewData(int n)) { return static_cast<T*>(P::New(n * sizeof(T))); }
INLINE(void DeleteData(T* data)) { P::Delete(data); }
// Increase the capacity of a full list, and add an element.
// List must be full already.
void ResizeAdd(const T& element);
// Inlined implementation of ResizeAdd, shared by inlined and
// non-inlined versions of ResizeAdd.
void ResizeAddInternal(const T& element);
DISALLOW_COPY_AND_ASSIGN(List);
};
class FrameElement;
// Add() is inlined, ResizeAdd() called by Add() is inlined except for
// Lists of FrameElements, and ResizeAddInternal() is inlined in ResizeAdd().
template <>
void List<FrameElement,
FreeStoreAllocationPolicy>::ResizeAdd(const FrameElement& element);
} } // namespace v8::internal
......
......@@ -507,4 +507,14 @@ bool VirtualFrame::Equals(VirtualFrame* other) {
return true;
}
// Specialization of List::ResizeAdd to non-inlined version for FrameElements.
// The function ResizeAdd becomes a real function, whose implementation is the
// inlined ResizeAddInternal.
template <>
void List<FrameElement,
FreeStoreAllocationPolicy>::ResizeAdd(const FrameElement& element) {
ResizeAddInternal(element);
}
} } // namespace v8::internal
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment