// Notify the given JIT whenever this method is recompiled or initially compiled. // The callback_data pointer will be passed back to the JIT during the callback. // The JIT's callback function is JIT_recompiled_method_callback. void Method::register_jit_recompiled_method_callback(JIT *jit_to_be_notified, Method* caller, void *callback_data) { // Don't insert the same entry repeatedly on the _notify_recompiled_records list. Method_Change_Notification_Record *nr = _notify_recompiled_records; while (nr != NULL) { if (nr->equals(jit_to_be_notified, callback_data)) { return; } nr = nr->next; } // Insert a new notification record. Method_Change_Notification_Record *new_nr = (Method_Change_Notification_Record *)STD_MALLOC(sizeof(Method_Change_Notification_Record)); new_nr->caller = caller; new_nr->jit = jit_to_be_notified; new_nr->callback_data = callback_data; new_nr->next = _notify_recompiled_records; _notify_recompiled_records = new_nr; // Record a callback in the caller method to let it unregister itself if unloaded. ClassLoader* this_loader = get_class()->get_class_loader(); ClassLoader* caller_loader = caller->get_class()->get_class_loader(); if (this_loader == caller_loader || caller_loader->IsBootstrap()) return; MethodSet *vec = caller->_recompilation_callbacks; if (vec == NULL) { vec = caller->_recompilation_callbacks = new MethodSet(); } vec->push_back(this); } //Method::register_jit_recompiled_method_callback
void Options::setIsAltJit() { // Initial state is that we are not an alternative jit until proven otherwise; IsAltJit = false; // NDEBUG is !Debug #if !defined(NDEBUG) // DEBUG case // Get/reuse method set that contains the altjit method value. MethodSet *AltJit = nullptr; if (Context->Flags & CORJIT_FLG_PREJIT) { wchar_t *NgenStr = Context->JitInfo->getStringConfigValue(L"AltJitNgen"); std::unique_ptr<std::string> NgenUtf8 = Convert::wideToUtf8(NgenStr); AltJitNgenMethodSet.init(std::move(NgenUtf8)); Context->JitInfo->freeStringConfigValue(NgenStr); AltJit = &AltJitNgenMethodSet; } else { wchar_t *JitStr = Context->JitInfo->getStringConfigValue(L"AltJit"); // Move this to the UTIL code and ifdef it for platform std::unique_ptr<std::string> JitUtf8 = Convert::wideToUtf8(JitStr); AltJitMethodSet.init(std::move(JitUtf8)); Context->JitInfo->freeStringConfigValue(JitStr); AltJit = &AltJitMethodSet; } #ifdef ALT_JIT if (AltJit->contains(Context->MethodName.data(), nullptr, Context->MethodInfo->args.pSig)) { IsAltJit = true; } #endif // ALT_JIT #else if (Context->Flags & CORJIT_FLG_PREJIT) { wchar_t *NgenStr = Context->JitInfo->getStringConfigValue(L"AltJitNgen"); std::unique_ptr<std::string> NgenUtf8 = Convert::wideToUtf8(NgenStr); if (NgenUtf8->compare("*") == 0) { IsAltJit = true; } } else { wchar_t *JitStr = Context->JitInfo->getStringConfigValue(L"AltJit"); std::unique_ptr<std::string> JitUtf8 = Convert::wideToUtf8(JitStr); if (JitUtf8->compare("*") == 0) { IsAltJit = true; } } #endif }
bool JitOptions::queryMethodSet(LLILCJitContext &JitContext, MethodSet &TheSet, const char16_t *Name) { if (!TheSet.isInitialized()) { char16_t *ConfigStr = getStringConfigValue(JitContext.JitInfo, Name); bool NeedFree = true; if (ConfigStr == nullptr) { ConfigStr = (char16_t *)UTF16(""); NeedFree = false; } std::unique_ptr<std::string> ConfigUtf8 = Convert::utf16ToUtf8(ConfigStr); TheSet.init(std::move(ConfigUtf8)); if (NeedFree) { freeStringConfigValue(JitContext.JitInfo, ConfigStr); } } const char *ClassName = nullptr; const char *MethodName = nullptr; MethodName = JitContext.JitInfo->getMethodName(JitContext.MethodInfo->ftn, &ClassName); bool IsInMethodSet = TheSet.contains(MethodName, ClassName, JitContext.MethodInfo->args.pSig); return IsInMethodSet; }
bool JitOptions::queryIsAltJit(LLILCJitContext &Context) { // Initial state is that we are not an alternative jit until proven otherwise; bool IsAlternateJit = false; // NDEBUG is !Debug #if !defined(NDEBUG) // DEBUG case // Get/reuse method set that contains the altjit method value. MethodSet *AltJit = nullptr; if (Context.Flags & CORJIT_FLG_PREJIT) { if (!AltJitNgenMethodSet.isInitialized()) { char16_t *NgenStr = getStringConfigValue(Context.JitInfo, UTF16("AltJitNgen")); std::unique_ptr<std::string> NgenUtf8 = Convert::utf16ToUtf8(NgenStr); AltJitNgenMethodSet.init(std::move(NgenUtf8)); freeStringConfigValue(Context.JitInfo, NgenStr); } // Set up AltJitNgen set to be used for AltJit test. AltJit = &AltJitNgenMethodSet; } else { if (!AltJitMethodSet.isInitialized()) { char16_t *JitStr = getStringConfigValue(Context.JitInfo, UTF16("AltJit")); // Move this to the UTIL code and ifdef it for platform std::unique_ptr<std::string> JitUtf8 = Convert::utf16ToUtf8(JitStr); AltJitMethodSet.init(std::move(JitUtf8)); freeStringConfigValue(Context.JitInfo, JitStr); } // Set up AltJit set to be use for AltJit test. AltJit = &AltJitMethodSet; } #ifdef ALT_JIT const char *ClassName = nullptr; const char *MethodName = nullptr; MethodName = Context.JitInfo->getMethodName(Context.MethodInfo->ftn, &ClassName); IsAlternateJit = AltJit->contains(MethodName, ClassName, Context.MethodInfo->args.pSig); #endif // ALT_JIT #else if (Context.Flags & CORJIT_FLG_PREJIT) { char16_t *NgenStr = getStringConfigValue(Context.JitInfo, UTF16("AltJitNgen")); std::unique_ptr<std::string> NgenUtf8 = Convert::utf16ToUtf8(NgenStr); if (NgenUtf8->compare("*") == 0) { IsAlternateJit = true; } } else { char16_t *JitStr = getStringConfigValue(Context.JitInfo, UTF16("AltJit")); std::unique_ptr<std::string> JitUtf8 = Convert::utf16ToUtf8(JitStr); if (JitUtf8->compare("*") == 0) { IsAlternateJit = true; } } #endif return IsAlternateJit; }