Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(19)

Side by Side Diff: src/v8threads.cc

Issue 2715004: [Isolates]... (Closed) Base URL: http://v8.googlecode.com/svn/branches/experimental/isolates/
Patch Set: Address comments/make StackGuard::ThreadLocal::Initialize/Clear side-effects visible Created 10 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright 2008 the V8 project authors. All rights reserved. 1 // Copyright 2008 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
43 43
44 44
45 // Track whether this V8 instance has ever called v8::Locker. This allows the 45 // Track whether this V8 instance has ever called v8::Locker. This allows the
46 // API code to verify that the lock is always held when V8 is being entered. 46 // API code to verify that the lock is always held when V8 is being entered.
47 bool Locker::active_ = false; 47 bool Locker::active_ = false;
48 48
49 49
50 // Constructor for the Locker object. Once the Locker is constructed the 50 // Constructor for the Locker object. Once the Locker is constructed the
51 // current thread will be guaranteed to have the big V8 lock. 51 // current thread will be guaranteed to have the big V8 lock.
52 Locker::Locker() : has_lock_(false), top_level_(true) { 52 Locker::Locker() : has_lock_(false), top_level_(true) {
53 internal::Isolate* isolate = internal::Isolate::Current();
53 // Record that the Locker has been used at least once. 54 // Record that the Locker has been used at least once.
54 active_ = true; 55 active_ = true;
55 // Get the big lock if necessary. 56 // Get the big lock if necessary.
56 if (!internal::ThreadManager::IsLockedByCurrentThread()) { 57 if (!internal::ThreadManager::IsLockedByCurrentThread()) {
57 internal::ThreadManager::Lock(); 58 internal::ThreadManager::Lock();
58 has_lock_ = true; 59 has_lock_ = true;
59 // Make sure that V8 is initialized. Archiving of threads interferes 60 // Make sure that V8 is initialized. Archiving of threads interferes
60 // with deserialization by adding additional root pointers, so we must 61 // with deserialization by adding additional root pointers, so we must
61 // initialize here, before anyone can call ~Locker() or Unlocker(). 62 // initialize here, before anyone can call ~Locker() or Unlocker().
62 if (!internal::V8::IsRunning()) { 63 if (!internal::V8::IsRunning()) {
63 V8::Initialize(); 64 V8::Initialize();
64 } 65 }
65 // This may be a locker within an unlocker in which case we have to 66 // This may be a locker within an unlocker in which case we have to
66 // get the saved state for this thread and restore it. 67 // get the saved state for this thread and restore it.
67 if (internal::ThreadManager::RestoreThread()) { 68 if (internal::ThreadManager::RestoreThread()) {
68 top_level_ = false; 69 top_level_ = false;
69 } else { 70 } else {
70 internal::ExecutionAccess access; 71 internal::ExecutionAccess access;
71 internal::StackGuard::ClearThread(access); 72 isolate->stack_guard()->ClearThread(access);
72 internal::StackGuard::InitThread(access); 73 isolate->stack_guard()->InitThread(access);
73 } 74 }
74 } 75 }
75 ASSERT(internal::ThreadManager::IsLockedByCurrentThread()); 76 ASSERT(internal::ThreadManager::IsLockedByCurrentThread());
76 77
77 // Make sure this thread is assigned a thread id. 78 // Make sure this thread is assigned a thread id.
78 internal::ThreadManager::AssignId(); 79 internal::ThreadManager::AssignId();
79 } 80 }
80 81
81 82
82 bool Locker::IsLocked() { 83 bool Locker::IsLocked() {
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
118 119
119 void Locker::StopPreemption() { 120 void Locker::StopPreemption() {
120 v8::internal::ContextSwitcher::StopPreemption(); 121 v8::internal::ContextSwitcher::StopPreemption();
121 } 122 }
122 123
123 124
124 namespace internal { 125 namespace internal {
125 126
126 127
127 bool ThreadManager::RestoreThread() { 128 bool ThreadManager::RestoreThread() {
129 Isolate* isolate = Isolate::Current();
128 // First check whether the current thread has been 'lazily archived', ie 130 // First check whether the current thread has been 'lazily archived', ie
129 // not archived at all. If that is the case we put the state storage we 131 // not archived at all. If that is the case we put the state storage we
130 // had prepared back in the free list, since we didn't need it after all. 132 // had prepared back in the free list, since we didn't need it after all.
131 if (lazily_archived_thread_.IsSelf()) { 133 if (lazily_archived_thread_.IsSelf()) {
132 lazily_archived_thread_.Initialize(ThreadHandle::INVALID); 134 lazily_archived_thread_.Initialize(ThreadHandle::INVALID);
133 ASSERT(Thread::GetThreadLocal(thread_state_key) == 135 ASSERT(Thread::GetThreadLocal(thread_state_key) ==
134 lazily_archived_thread_state_); 136 lazily_archived_thread_state_);
135 lazily_archived_thread_state_->set_id(kInvalidId); 137 lazily_archived_thread_state_->set_id(kInvalidId);
136 lazily_archived_thread_state_->LinkInto(ThreadState::FREE_LIST); 138 lazily_archived_thread_state_->LinkInto(ThreadState::FREE_LIST);
137 lazily_archived_thread_state_ = NULL; 139 lazily_archived_thread_state_ = NULL;
138 Thread::SetThreadLocal(thread_state_key, NULL); 140 Thread::SetThreadLocal(thread_state_key, NULL);
139 return true; 141 return true;
140 } 142 }
141 143
142 // Make sure that the preemption thread cannot modify the thread state while 144 // Make sure that the preemption thread cannot modify the thread state while
143 // it is being archived or restored. 145 // it is being archived or restored.
144 ExecutionAccess access; 146 ExecutionAccess access;
145 147
146 // If there is another thread that was lazily archived then we have to really 148 // If there is another thread that was lazily archived then we have to really
147 // archive it now. 149 // archive it now.
148 if (lazily_archived_thread_.IsValid()) { 150 if (lazily_archived_thread_.IsValid()) {
149 EagerlyArchiveThread(); 151 EagerlyArchiveThread();
150 } 152 }
151 ThreadState* state = 153 ThreadState* state =
152 reinterpret_cast<ThreadState*>(Thread::GetThreadLocal(thread_state_key)); 154 reinterpret_cast<ThreadState*>(Thread::GetThreadLocal(thread_state_key));
153 if (state == NULL) { 155 if (state == NULL) {
154 // This is a new thread. 156 // This is a new thread.
155 StackGuard::InitThread(access); 157 isolate->stack_guard()->InitThread(access);
156 return false; 158 return false;
157 } 159 }
158 Isolate* isolate = Isolate::Current();
159 char* from = state->data(); 160 char* from = state->data();
160 from = isolate->handle_scope_implementer()->RestoreThread(from); 161 from = isolate->handle_scope_implementer()->RestoreThread(from);
161 from = Top::RestoreThread(from); 162 from = Top::RestoreThread(from);
162 from = Relocatable::RestoreState(from); 163 from = Relocatable::RestoreState(from);
163 #ifdef ENABLE_DEBUGGER_SUPPORT 164 #ifdef ENABLE_DEBUGGER_SUPPORT
164 from = Debug::RestoreDebug(from); 165 from = Debug::RestoreDebug(from);
165 #endif 166 #endif
166 from = StackGuard::RestoreStackGuard(from); 167 from = isolate->stack_guard()->RestoreStackGuard(from);
167 from = RegExpStack::RestoreStack(from); 168 from = RegExpStack::RestoreStack(from);
168 from = isolate->bootstrapper()->RestoreState(from); 169 from = isolate->bootstrapper()->RestoreState(from);
169 Thread::SetThreadLocal(thread_state_key, NULL); 170 Thread::SetThreadLocal(thread_state_key, NULL);
170 if (state->terminate_on_restore()) { 171 if (state->terminate_on_restore()) {
171 StackGuard::TerminateExecution(); 172 isolate->stack_guard()->TerminateExecution();
172 state->set_terminate_on_restore(false); 173 state->set_terminate_on_restore(false);
173 } 174 }
174 state->set_id(kInvalidId); 175 state->set_id(kInvalidId);
175 state->Unlink(); 176 state->Unlink();
176 state->LinkInto(ThreadState::FREE_LIST); 177 state->LinkInto(ThreadState::FREE_LIST);
177 return true; 178 return true;
178 } 179 }
179 180
180 181
181 void ThreadManager::Lock() { 182 void ThreadManager::Lock() {
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
276 Thread::SetThreadLocal(thread_state_key, reinterpret_cast<void*>(state)); 277 Thread::SetThreadLocal(thread_state_key, reinterpret_cast<void*>(state));
277 lazily_archived_thread_.Initialize(ThreadHandle::SELF); 278 lazily_archived_thread_.Initialize(ThreadHandle::SELF);
278 lazily_archived_thread_state_ = state; 279 lazily_archived_thread_state_ = state;
279 ASSERT(state->id() == kInvalidId); 280 ASSERT(state->id() == kInvalidId);
280 state->set_id(CurrentId()); 281 state->set_id(CurrentId());
281 ASSERT(state->id() != kInvalidId); 282 ASSERT(state->id() != kInvalidId);
282 } 283 }
283 284
284 285
285 void ThreadManager::EagerlyArchiveThread() { 286 void ThreadManager::EagerlyArchiveThread() {
287 Isolate* isolate = Isolate::Current();
286 ThreadState* state = lazily_archived_thread_state_; 288 ThreadState* state = lazily_archived_thread_state_;
287 state->LinkInto(ThreadState::IN_USE_LIST); 289 state->LinkInto(ThreadState::IN_USE_LIST);
288 Isolate* isolate = Isolate::Current();
289 char* to = state->data(); 290 char* to = state->data();
290 // Ensure that data containing GC roots are archived first, and handle them 291 // Ensure that data containing GC roots are archived first, and handle them
291 // in ThreadManager::Iterate(ObjectVisitor*). 292 // in ThreadManager::Iterate(ObjectVisitor*).
292 to = isolate->handle_scope_implementer()->ArchiveThread(to); 293 to = isolate->handle_scope_implementer()->ArchiveThread(to);
293 to = Top::ArchiveThread(to); 294 to = Top::ArchiveThread(to);
294 to = Relocatable::ArchiveState(to); 295 to = Relocatable::ArchiveState(to);
295 #ifdef ENABLE_DEBUGGER_SUPPORT 296 #ifdef ENABLE_DEBUGGER_SUPPORT
296 to = Debug::ArchiveDebug(to); 297 to = Debug::ArchiveDebug(to);
297 #endif 298 #endif
298 to = StackGuard::ArchiveStackGuard(to); 299 to = isolate->stack_guard()->ArchiveStackGuard(to);
299 to = RegExpStack::ArchiveStack(to); 300 to = RegExpStack::ArchiveStack(to);
300 to = isolate->bootstrapper()->ArchiveState(to); 301 to = isolate->bootstrapper()->ArchiveState(to);
301 lazily_archived_thread_.Initialize(ThreadHandle::INVALID); 302 lazily_archived_thread_.Initialize(ThreadHandle::INVALID);
302 lazily_archived_thread_state_ = NULL; 303 lazily_archived_thread_state_ = NULL;
303 } 304 }
304 305
305 306
306 void ThreadManager::FreeThreadResources() { 307 void ThreadManager::FreeThreadResources() {
307 Isolate* isolate = Isolate::Current(); 308 Isolate* isolate = Isolate::Current();
308 isolate->handle_scope_implementer()->FreeThreadResources(); 309 isolate->handle_scope_implementer()->FreeThreadResources();
309 Top::FreeThreadResources(); 310 Top::FreeThreadResources();
310 #ifdef ENABLE_DEBUGGER_SUPPORT 311 #ifdef ENABLE_DEBUGGER_SUPPORT
311 Debug::FreeThreadResources(); 312 Debug::FreeThreadResources();
312 #endif 313 #endif
313 StackGuard::FreeThreadResources(); 314 isolate->stack_guard()->FreeThreadResources();
314 RegExpStack::FreeThreadResources(); 315 RegExpStack::FreeThreadResources();
315 isolate->bootstrapper()->FreeThreadResources(); 316 isolate->bootstrapper()->FreeThreadResources();
316 } 317 }
317 318
318 319
319 bool ThreadManager::IsArchived() { 320 bool ThreadManager::IsArchived() {
320 return Thread::HasThreadLocal(thread_state_key); 321 return Thread::HasThreadLocal(thread_state_key);
321 } 322 }
322 323
323 324
(...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after
440 singleton_ = NULL; 441 singleton_ = NULL;
441 } 442 }
442 } 443 }
443 444
444 445
445 // Main loop of the ContextSwitcher thread: Preempt the currently running V8 446 // Main loop of the ContextSwitcher thread: Preempt the currently running V8
446 // thread at regular intervals. 447 // thread at regular intervals.
447 void ContextSwitcher::Run() { 448 void ContextSwitcher::Run() {
448 while (keep_going_) { 449 while (keep_going_) {
449 OS::Sleep(sleep_ms_); 450 OS::Sleep(sleep_ms_);
450 StackGuard::Preempt(); 451 Isolate::Current()->stack_guard()->Preempt();
451 } 452 }
452 } 453 }
453 454
454 455
455 // Acknowledge the preemption by the receiving thread. 456 // Acknowledge the preemption by the receiving thread.
456 void ContextSwitcher::PreemptionReceived() { 457 void ContextSwitcher::PreemptionReceived() {
457 ASSERT(Locker::IsLocked()); 458 ASSERT(Locker::IsLocked());
458 // There is currently no accounting being done for this. But could be in the 459 // There is currently no accounting being done for this. But could be in the
459 // future, which is why we leave this in. 460 // future, which is why we leave this in.
460 } 461 }
461 462
462 463
463 } // namespace internal 464 } // namespace internal
464 } // namespace v8 465 } // namespace v8
OLDNEW
« src/execution.cc ('K') | « src/v8.cc ('k') | src/x64/regexp-macro-assembler-x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698