84 // Note: Currently StubQueues are never destroyed so nothing needs to be done here.
85 // If we want to implement the destructor, we need to release the BufferBlob
86 // allocated in the constructor (i.e., we need to keep it around or look it
87 // up via CodeCache::find_blob(...).
88 Unimplemented();
89 }
90
91
92 Stub* StubQueue::stub_containing(address pc) const {
93 if (contains(pc)) {
94 for (Stub* s = first(); s != NULL; s = next(s)) {
95 if (stub_contains(s, pc)) return s;
96 }
97 }
98 return NULL;
99 }
100
101
102 Stub* StubQueue::request_committed(int code_size) {
103 Stub* s = request(code_size);
104 CodeComments comments;
105 if (s != NULL) commit(code_size, comments);
106 return s;
107 }
108
109
110 Stub* StubQueue::request(int requested_code_size) {
111 assert(requested_code_size > 0, "requested_code_size must be > 0");
112 if (_mutex != NULL) _mutex->lock();
113 Stub* s = current_stub();
114 int requested_size = round_to(stub_code_size_to_size(requested_code_size), CodeEntryAlignment);
115 if (requested_size <= available_space()) {
116 if (is_contiguous()) {
117 // Queue: |...|XXXXXXX|.............|
118 // ^0 ^begin ^end ^size = limit
119 assert(_buffer_limit == _buffer_size, "buffer must be fully usable");
120 if (_queue_end + requested_size <= _buffer_size) {
121 // code fits in at the end => nothing to do
122 CodeComments comments;
123 stub_initialize(s, requested_size, comments);
124 return s;
125 } else {
126 // stub doesn't fit in at the queue end
127 // => reduce buffer limit & wrap around
128 assert(!is_empty(), "just checkin'");
129 _buffer_limit = _queue_end;
130 _queue_end = 0;
131 }
132 }
133 }
134 if (requested_size <= available_space()) {
135 assert(!is_contiguous(), "just checkin'");
136 assert(_buffer_limit <= _buffer_size, "queue invariant broken");
137 // Queue: |XXX|.......|XXXXXXX|.......|
138 // ^0 ^end ^begin ^limit ^size
139 s = current_stub();
140 CodeComments comments;
141 stub_initialize(s, requested_size, comments);
142 return s;
143 }
144 // Not enough space left
145 if (_mutex != NULL) _mutex->unlock();
146 return NULL;
147 }
148
149
150 void StubQueue::commit(int committed_code_size, CodeComments& comments) {
151 assert(committed_code_size > 0, "committed_code_size must be > 0");
152 int committed_size = round_to(stub_code_size_to_size(committed_code_size), CodeEntryAlignment);
153 Stub* s = current_stub();
154 assert(committed_size <= stub_size(s), "committed size must not exceed requested size");
155 stub_initialize(s, committed_size, comments);
156 _queue_end += committed_size;
157 _number_of_stubs++;
158 if (_mutex != NULL) _mutex->unlock();
159 debug_only(stub_verify(s);)
160 }
161
162
163 void StubQueue::remove_first() {
164 if (number_of_stubs() == 0) return;
165 Stub* s = first();
166 debug_only(stub_verify(s);)
167 stub_finalize(s);
168 _queue_begin += stub_size(s);
169 assert(_queue_begin <= _buffer_limit, "sanity check");
170 if (_queue_begin == _queue_end) {
171 // buffer empty
172 // => reset queue indices
173 _queue_begin = 0;
174 _queue_end = 0;
175 _buffer_limit = _buffer_size;
|
84 // Note: Currently StubQueues are never destroyed so nothing needs to be done here.
85 // If we want to implement the destructor, we need to release the BufferBlob
86 // allocated in the constructor (i.e., we need to keep it around or look it
87 // up via CodeCache::find_blob(...).
88 Unimplemented();
89 }
90
91
92 Stub* StubQueue::stub_containing(address pc) const {
93 if (contains(pc)) {
94 for (Stub* s = first(); s != NULL; s = next(s)) {
95 if (stub_contains(s, pc)) return s;
96 }
97 }
98 return NULL;
99 }
100
101
102 Stub* StubQueue::request_committed(int code_size) {
103 Stub* s = request(code_size);
104 CodeStrings strings;
105 if (s != NULL) commit(code_size, strings);
106 return s;
107 }
108
109
110 Stub* StubQueue::request(int requested_code_size) {
111 assert(requested_code_size > 0, "requested_code_size must be > 0");
112 if (_mutex != NULL) _mutex->lock();
113 Stub* s = current_stub();
114 int requested_size = round_to(stub_code_size_to_size(requested_code_size), CodeEntryAlignment);
115 if (requested_size <= available_space()) {
116 if (is_contiguous()) {
117 // Queue: |...|XXXXXXX|.............|
118 // ^0 ^begin ^end ^size = limit
119 assert(_buffer_limit == _buffer_size, "buffer must be fully usable");
120 if (_queue_end + requested_size <= _buffer_size) {
121 // code fits in at the end => nothing to do
122 CodeStrings strings;
123 stub_initialize(s, requested_size, strings);
124 return s;
125 } else {
126 // stub doesn't fit in at the queue end
127 // => reduce buffer limit & wrap around
128 assert(!is_empty(), "just checkin'");
129 _buffer_limit = _queue_end;
130 _queue_end = 0;
131 }
132 }
133 }
134 if (requested_size <= available_space()) {
135 assert(!is_contiguous(), "just checkin'");
136 assert(_buffer_limit <= _buffer_size, "queue invariant broken");
137 // Queue: |XXX|.......|XXXXXXX|.......|
138 // ^0 ^end ^begin ^limit ^size
139 s = current_stub();
140 CodeStrings strings;
141 stub_initialize(s, requested_size, strings);
142 return s;
143 }
144 // Not enough space left
145 if (_mutex != NULL) _mutex->unlock();
146 return NULL;
147 }
148
149
150 void StubQueue::commit(int committed_code_size, CodeStrings& strings) {
151 assert(committed_code_size > 0, "committed_code_size must be > 0");
152 int committed_size = round_to(stub_code_size_to_size(committed_code_size), CodeEntryAlignment);
153 Stub* s = current_stub();
154 assert(committed_size <= stub_size(s), "committed size must not exceed requested size");
155 stub_initialize(s, committed_size, strings);
156 _queue_end += committed_size;
157 _number_of_stubs++;
158 if (_mutex != NULL) _mutex->unlock();
159 debug_only(stub_verify(s);)
160 }
161
162
163 void StubQueue::remove_first() {
164 if (number_of_stubs() == 0) return;
165 Stub* s = first();
166 debug_only(stub_verify(s);)
167 stub_finalize(s);
168 _queue_begin += stub_size(s);
169 assert(_queue_begin <= _buffer_limit, "sanity check");
170 if (_queue_begin == _queue_end) {
171 // buffer empty
172 // => reset queue indices
173 _queue_begin = 0;
174 _queue_end = 0;
175 _buffer_limit = _buffer_size;
|