diff --git a/compiler-rt/lib/profile/InstrProfiling.h b/compiler-rt/lib/profile/InstrProfiling.h --- a/compiler-rt/lib/profile/InstrProfiling.h +++ b/compiler-rt/lib/profile/InstrProfiling.h @@ -218,6 +218,9 @@ /*! \brief Initialize file handling. */ void __llvm_profile_initialize_file(void); +/*! \brief Initialize the profile runtime. */ +void __llvm_profile_initialize(void); + /*! * \brief Return path prefix (excluding the base filename) of the profile data. * This is useful for users using \c -fprofile-generate=./path_prefix who do diff --git a/compiler-rt/lib/profile/InstrProfilingBuffer.c b/compiler-rt/lib/profile/InstrProfilingBuffer.c --- a/compiler-rt/lib/profile/InstrProfilingBuffer.c +++ b/compiler-rt/lib/profile/InstrProfilingBuffer.c @@ -10,9 +10,6 @@ #include "InstrProfilingInternal.h" #include "InstrProfilingPort.h" -/* When counters are being relocated at runtime, this parameter is set to 1. */ -COMPILER_RT_VISIBILITY int RuntimeCounterRelocation = 0; - /* When continuous mode is enabled (%c), this parameter is set to 1. * * This parameter is defined here in InstrProfilingBuffer.o, instead of in @@ -66,7 +63,7 @@ uint64_t *PaddingBytesBeforeCounters, uint64_t *PaddingBytesAfterCounters, uint64_t *PaddingBytesAfterNames) { if (!__llvm_profile_is_continuous_mode_enabled() || - RuntimeCounterRelocation) { + lprofRuntimeCounterRelocation()) { *PaddingBytesBeforeCounters = 0; *PaddingBytesAfterCounters = 0; *PaddingBytesAfterNames = __llvm_profile_get_num_padding_bytes(NamesSize); diff --git a/compiler-rt/lib/profile/InstrProfilingFile.c b/compiler-rt/lib/profile/InstrProfilingFile.c --- a/compiler-rt/lib/profile/InstrProfilingFile.c +++ b/compiler-rt/lib/profile/InstrProfilingFile.c @@ -35,6 +35,16 @@ #include "InstrProfilingPort.h" #include "InstrProfilingUtil.h" +static int RuntimeCounterRelocation = 0; + +COMPILER_RT_VISIBILITY unsigned lprofRuntimeCounterRelocation(void) { + return RuntimeCounterRelocation; +} + +COMPILER_RT_VISIBILITY void lprofSetRuntimeCounterRelocation(void) { + RuntimeCounterRelocation = 1; +} + /* From where is profile name specified. * The order the enumerators define their * precedence. Re-order them may lead to @@ -477,7 +487,8 @@ } static void relocateCounters(void) { - if (!__llvm_profile_is_continuous_mode_enabled() || !RuntimeCounterRelocation) + if (!__llvm_profile_is_continuous_mode_enabled() || + !lprofRuntimeCounterRelocation()) return; /* Get the sizes of various profile data sections. Taken from @@ -808,7 +819,7 @@ truncateCurrentFile(); if (__llvm_profile_is_continuous_mode_enabled()) { - if (RuntimeCounterRelocation) + if (lprofRuntimeCounterRelocation()) relocateCounters(); else initializeProfileForContinuousMode(); @@ -951,10 +962,10 @@ return FilenameBuf; } -/* This method is invoked by the runtime initialization hook - * InstrProfilingRuntime.o if it is linked in. Both user specified +/* This API initializes the file handling, both user specified * profile path via -fprofile-instr-generate= and LLVM_PROFILE_FILE - * environment variable can override this default value. */ + * environment variable can override this default value. + */ COMPILER_RT_VISIBILITY void __llvm_profile_initialize_file(void) { const char *EnvFilenamePat; @@ -963,7 +974,7 @@ int hasCommandLineOverrider = (INSTR_PROF_PROFILE_NAME_VAR[0] != 0); if (__llvm_profile_counter_bias != -1) - RuntimeCounterRelocation = 1; + lprofSetRuntimeCounterRelocation(); EnvFilenamePat = getFilenamePatFromEnv(); if (EnvFilenamePat) { @@ -982,6 +993,16 @@ parseAndSetFilename(SelectedPat, PNS, 0); } +/* This method is invoked by the runtime initialization hook + * InstrProfilingRuntime.o if it is linked in. + */ +COMPILER_RT_VISIBILITY +void __llvm_profile_initialize(void) { + __llvm_profile_initialize_file(); + if (!__llvm_profile_is_continuous_mode_enabled()) + __llvm_profile_register_write_file_atexit(); +} + /* This API is directly called by the user application code. It has the * highest precedence compared with LLVM_PROFILE_FILE environment variable * and command line option -fprofile-instr-generate=. diff --git a/compiler-rt/lib/profile/InstrProfilingInternal.h b/compiler-rt/lib/profile/InstrProfilingInternal.h --- a/compiler-rt/lib/profile/InstrProfilingInternal.h +++ b/compiler-rt/lib/profile/InstrProfilingInternal.h @@ -184,7 +184,10 @@ unsigned lprofProfileDumped(); void lprofSetProfileDumped(); -COMPILER_RT_VISIBILITY extern int RuntimeCounterRelocation; +/* Return non zero value if counters are being relocated at runtime. */ +unsigned lprofRuntimeCounterRelocation(void); +void lprofSetRuntimeCounterRelocation(void); + COMPILER_RT_VISIBILITY extern void (*FreeHook)(void *); COMPILER_RT_VISIBILITY extern uint8_t *DynamicBufferIOBuffer; COMPILER_RT_VISIBILITY extern uint32_t VPBufferSize; diff --git a/compiler-rt/lib/profile/InstrProfilingPlatformFuchsia.c b/compiler-rt/lib/profile/InstrProfilingPlatformFuchsia.c --- a/compiler-rt/lib/profile/InstrProfilingPlatformFuchsia.c +++ b/compiler-rt/lib/profile/InstrProfilingPlatformFuchsia.c @@ -34,7 +34,11 @@ #include "InstrProfilingInternal.h" #include "InstrProfilingUtil.h" -/* VMO that contains the coverage data shared across all modules. */ +COMPILER_RT_VISIBILITY unsigned lprofRuntimeCounterRelocation(void) { + return 1; +} + +/* VMO that contains the profile data for this module. */ static zx_handle_t __llvm_profile_vmo; /* Current offset within the VMO where data should be written next. */ static uint64_t __llvm_profile_offset; @@ -92,43 +96,23 @@ This->WriterCtx = NULL; } -static int dump(void) { - if (lprofProfileDumped()) { - lprofWrite("LLVM Profile: data not published: already written.\n"); - return 0; - } - - /* Check if there is llvm/runtime version mismatch. */ - if (GET_VERSION(__llvm_profile_get_version()) != INSTR_PROF_RAW_VERSION) { - lprofWrite("LLVM Profile: runtime and instrumentation version mismatch: " - "expected %d, but got %d\n", - INSTR_PROF_RAW_VERSION, - (int)GET_VERSION(__llvm_profile_get_version())); - return -1; - } - - /* Write the profile data into the mapped region. */ - ProfDataWriter VMOWriter; - initVMOWriter(&VMOWriter); - if (lprofWriteData(&VMOWriter, lprofGetVPDataReader(), 0) != 0) - return -1; - - return 0; -} - +/* This method is invoked by the runtime initialization hook + * InstrProfilingRuntime.o if it is linked in. */ COMPILER_RT_VISIBILITY -int __llvm_profile_dump(void) { - int rc = dump(); - lprofSetProfileDumped(); - return rc; -} - -static void dumpWithoutReturn(void) { dump(); } +void __llvm_profile_initialize(void) { + /* This symbol is defined as weak and initialized to -1 by the runtimer, but + * compiler will generate a strong definition initialized to 0 when runtime + * counter relocation is used. */ + if (__llvm_profile_counter_bias == -1) { + lprofWrite("LLVM Profile: counter relocation at runtime is required\n"); + return; + } -static void createVMO(void) { /* Don't create VMO if it has been alread created. */ - if (__llvm_profile_vmo != ZX_HANDLE_INVALID) + if (__llvm_profile_vmo != ZX_HANDLE_INVALID) { + lprofWrite("LLVM Profile: VMO has already been created\n"); return; + } const __llvm_profile_data *DataBegin = __llvm_profile_begin_data(); const __llvm_profile_data *DataEnd = __llvm_profile_end_data(); @@ -211,23 +195,4 @@ (uintptr_t)__llvm_profile_begin_counters() + CountersOffset; } -/* This method is invoked by the runtime initialization hook - * InstrProfilingRuntime.o if it is linked in. - */ -COMPILER_RT_VISIBILITY -void __llvm_profile_initialize_file(void) { createVMO(); } - -COMPILER_RT_VISIBILITY -int __llvm_profile_register_write_file_atexit(void) { - static bool HasBeenRegistered = false; - - if (HasBeenRegistered) - return 0; - - lprofSetupValueProfiler(); - - HasBeenRegistered = true; - return atexit(dumpWithoutReturn); -} - #endif diff --git a/compiler-rt/lib/profile/InstrProfilingRuntime.cpp b/compiler-rt/lib/profile/InstrProfilingRuntime.cpp --- a/compiler-rt/lib/profile/InstrProfilingRuntime.cpp +++ b/compiler-rt/lib/profile/InstrProfilingRuntime.cpp @@ -19,9 +19,7 @@ class RegisterRuntime { public: RegisterRuntime() { - __llvm_profile_initialize_file(); - if (!__llvm_profile_is_continuous_mode_enabled()) - __llvm_profile_register_write_file_atexit(); + __llvm_profile_initialize(); } };