Chromium Code Reviews| Index: src/platform-linux.cc |
| diff --git a/src/platform-linux.cc b/src/platform-linux.cc |
| index ec48d6305e3de2ea4b51f0571a1c7a83bb0ae619..4217c11c2cfdf1d4e8e3bea9087778484a360402 100644 |
| --- a/src/platform-linux.cc |
| +++ b/src/platform-linux.cc |
| @@ -1022,62 +1022,6 @@ static int GetThreadID() { |
| } |
| -static void ProfilerSignalHandler(int signal, siginfo_t* info, void* context) { |
| - USE(info); |
| - if (signal != SIGPROF) return; |
| - Isolate* isolate = Isolate::UncheckedCurrent(); |
| - if (isolate == NULL || !isolate->IsInitialized() || !isolate->IsInUse()) { |
| - // We require a fully initialized and entered isolate. |
| - return; |
| - } |
| - if (v8::Locker::IsActive() && |
| - !isolate->thread_manager()->IsLockedByCurrentThread()) { |
| - return; |
| - } |
| - |
| - Sampler* sampler = isolate->logger()->sampler(); |
| - if (sampler == NULL || !sampler->IsActive()) return; |
| - |
| - TickSample sample_obj; |
| - TickSample* sample = CpuProfiler::TickSampleEvent(isolate); |
| - if (sample == NULL) sample = &sample_obj; |
| - |
| - // Extracting the sample from the context is extremely machine dependent. |
| - ucontext_t* ucontext = reinterpret_cast<ucontext_t*>(context); |
| - mcontext_t& mcontext = ucontext->uc_mcontext; |
| - sample->state = isolate->current_vm_state(); |
| -#if V8_HOST_ARCH_IA32 |
| - sample->pc = reinterpret_cast<Address>(mcontext.gregs[REG_EIP]); |
| - sample->sp = reinterpret_cast<Address>(mcontext.gregs[REG_ESP]); |
| - sample->fp = reinterpret_cast<Address>(mcontext.gregs[REG_EBP]); |
| -#elif V8_HOST_ARCH_X64 |
| - sample->pc = reinterpret_cast<Address>(mcontext.gregs[REG_RIP]); |
| - sample->sp = reinterpret_cast<Address>(mcontext.gregs[REG_RSP]); |
| - sample->fp = reinterpret_cast<Address>(mcontext.gregs[REG_RBP]); |
| -#elif V8_HOST_ARCH_ARM |
| -#if defined(__GLIBC__) && !defined(__UCLIBC__) && \ |
| - (__GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ <= 3)) |
| - // Old GLibc ARM versions used a gregs[] array to access the register |
| - // values from mcontext_t. |
| - sample->pc = reinterpret_cast<Address>(mcontext.gregs[R15]); |
| - sample->sp = reinterpret_cast<Address>(mcontext.gregs[R13]); |
| - sample->fp = reinterpret_cast<Address>(mcontext.gregs[R11]); |
| -#else |
| - sample->pc = reinterpret_cast<Address>(mcontext.arm_pc); |
| - sample->sp = reinterpret_cast<Address>(mcontext.arm_sp); |
| - sample->fp = reinterpret_cast<Address>(mcontext.arm_fp); |
| -#endif // defined(__GLIBC__) && !defined(__UCLIBC__) && |
| - // (__GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ <= 3)) |
| -#elif V8_HOST_ARCH_MIPS |
| - sample->pc = reinterpret_cast<Address>(mcontext.pc); |
| - sample->sp = reinterpret_cast<Address>(mcontext.gregs[29]); |
| - sample->fp = reinterpret_cast<Address>(mcontext.gregs[30]); |
| -#endif // V8_HOST_ARCH_* |
| - sampler->SampleStack(sample); |
| - sampler->Tick(sample); |
| -} |
| - |
| - |
| class Sampler::PlatformData : public Malloced { |
| public: |
| PlatformData() : vm_tid_(GetThreadID()) {} |
| @@ -1089,6 +1033,9 @@ class Sampler::PlatformData : public Malloced { |
| }; |
| +static void ProfilerSignalHandler(int signal, siginfo_t* info, void* context); |
| + |
| + |
| class SignalSender : public Thread { |
| public: |
| enum SleepInterval { |
| @@ -1122,6 +1069,11 @@ class SignalSender : public Thread { |
| } |
| } |
| + static void CallOldSignalHandler(int signal, siginfo_t* info, void* context) { |
| + if (signal_handler_installed_ && old_signal_handler_.sa_sigaction) |
|
willchan no longer on Chromium
2012/12/12 22:28:37
old_signal_handler_.sa_sigaction is 0x1 in the cra
danno
2012/12/13 00:00:19
Go ahead and re-open this one, since I'd like to m
willchan no longer on Chromium
2012/12/13 00:15:58
Don't worry, that's exactly why I added Markus to
|
| + old_signal_handler_.sa_sigaction(signal, info, context); |
|
Markus (顧孟勤)
2012/12/12 22:58:17
If you want to do this right, things get a lot mor
willchan no longer on Chromium
2012/12/13 00:15:58
Yeah, I'm going to skip almost all the corner case
|
| + } |
| + |
| static void AddActiveSampler(Sampler* sampler) { |
| ScopedLock lock(mutex_); |
| SamplerRegistry::AddActiveSampler(sampler); |
| @@ -1255,6 +1207,63 @@ struct sigaction SignalSender::old_signal_handler_; |
| bool SignalSender::signal_handler_installed_ = false; |
| +static void ProfilerSignalHandler(int signal, siginfo_t* info, void* context) { |
| + USE(info); |
| + if (signal != SIGPROF) return; |
|
Markus (顧孟勤)
2012/12/12 22:58:17
This seems somewhat bogus. That really should neve
|
| + SignalSender::CallOldSignalHandler(signal, info, context); |
| + Isolate* isolate = Isolate::UncheckedCurrent(); |
| + if (isolate == NULL || !isolate->IsInitialized() || !isolate->IsInUse()) { |
| + // We require a fully initialized and entered isolate. |
| + return; |
| + } |
| + if (v8::Locker::IsActive() && |
| + !isolate->thread_manager()->IsLockedByCurrentThread()) { |
| + return; |
| + } |
| + |
| + Sampler* sampler = isolate->logger()->sampler(); |
| + if (sampler == NULL || !sampler->IsActive()) return; |
| + |
| + TickSample sample_obj; |
| + TickSample* sample = CpuProfiler::TickSampleEvent(isolate); |
| + if (sample == NULL) sample = &sample_obj; |
| + |
| + // Extracting the sample from the context is extremely machine dependent. |
| + ucontext_t* ucontext = reinterpret_cast<ucontext_t*>(context); |
| + mcontext_t& mcontext = ucontext->uc_mcontext; |
| + sample->state = isolate->current_vm_state(); |
| +#if V8_HOST_ARCH_IA32 |
| + sample->pc = reinterpret_cast<Address>(mcontext.gregs[REG_EIP]); |
| + sample->sp = reinterpret_cast<Address>(mcontext.gregs[REG_ESP]); |
| + sample->fp = reinterpret_cast<Address>(mcontext.gregs[REG_EBP]); |
| +#elif V8_HOST_ARCH_X64 |
| + sample->pc = reinterpret_cast<Address>(mcontext.gregs[REG_RIP]); |
| + sample->sp = reinterpret_cast<Address>(mcontext.gregs[REG_RSP]); |
| + sample->fp = reinterpret_cast<Address>(mcontext.gregs[REG_RBP]); |
| +#elif V8_HOST_ARCH_ARM |
| +#if defined(__GLIBC__) && !defined(__UCLIBC__) && \ |
| + (__GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ <= 3)) |
| + // Old GLibc ARM versions used a gregs[] array to access the register |
| + // values from mcontext_t. |
| + sample->pc = reinterpret_cast<Address>(mcontext.gregs[R15]); |
| + sample->sp = reinterpret_cast<Address>(mcontext.gregs[R13]); |
| + sample->fp = reinterpret_cast<Address>(mcontext.gregs[R11]); |
| +#else |
| + sample->pc = reinterpret_cast<Address>(mcontext.arm_pc); |
| + sample->sp = reinterpret_cast<Address>(mcontext.arm_sp); |
| + sample->fp = reinterpret_cast<Address>(mcontext.arm_fp); |
| +#endif // defined(__GLIBC__) && !defined(__UCLIBC__) && |
| + // (__GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ <= 3)) |
| +#elif V8_HOST_ARCH_MIPS |
| + sample->pc = reinterpret_cast<Address>(mcontext.pc); |
| + sample->sp = reinterpret_cast<Address>(mcontext.gregs[29]); |
| + sample->fp = reinterpret_cast<Address>(mcontext.gregs[30]); |
| +#endif // V8_HOST_ARCH_* |
| + sampler->SampleStack(sample); |
| + sampler->Tick(sample); |
|
Markus (顧孟勤)
2012/12/12 22:58:17
I don't see any code here that preserves "errno".
|
| +} |
| + |
| + |
| void OS::SetUp() { |
| // Seed the random number generator. We preserve microsecond resolution. |
| uint64_t seed = Ticks() ^ (getpid() << 16); |