CString PathString::TunnelIntoCString(const mpt::PathString &path) //---------------------------------------------------------------- { #ifdef UNICODE return path.ToWide().c_str(); #else return path.ToUTF8().c_str(); #endif }
// Add a plugin to the list of known plugins. VSTPluginLib *CVstPluginManager::AddPlugin(const mpt::PathString &dllPath, bool fromCache, const bool checkFileExistence, std::wstring *const errStr) //--------------------------------------------------------------------------------------------------------------------------------------------------- { const mpt::PathString fileName = dllPath.GetFileName(); if(checkFileExistence && (PathFileExistsW(dllPath.AsNative().c_str()) == FALSE)) { if(errStr) { *errStr += L"\nUnable to find "; *errStr += dllPath.ToWide(); } } // Check if this is already a known plugin. for(const_iterator dupePlug = begin(); dupePlug != end(); dupePlug++) { if(!dllPath.CompareNoCase(dllPath, (**dupePlug).dllPath)) return *dupePlug; } // Look if the plugin info is stored in the PluginCache if(fromCache) { SettingsContainer & cacheFile = theApp.GetPluginCache(); const std::string IDs = cacheFile.Read<std::string>(cacheSectionW, fileName.ToWide(), ""); if(IDs.length() >= 16) { // Get path from cache file mpt::PathString realPath = cacheFile.Read<mpt::PathString>(cacheSection, IDs, MPT_PATHSTRING("")); realPath = theApp.RelativePathToAbsolute(realPath); if(!realPath.empty() && !dllPath.CompareNoCase(realPath, dllPath)) { VSTPluginLib *plug = new (std::nothrow) VSTPluginLib(dllPath, fileName); if(plug == nullptr) { return nullptr; } pluginList.push_back(plug); // Extract plugin IDs for (int i = 0; i < 16; i++) { VstInt32 n = IDs[i] - '0'; if (n > 9) n = IDs[i] + 10 - 'A'; n &= 0x0f; if (i < 8) { plug->pluginId1 = (plug->pluginId1 << 4) | n; } else { plug->pluginId2 = (plug->pluginId2 << 4) | n; } } const std::string flagKey = IDs + ".Flags"; plug->DecodeCacheFlags(cacheFile.Read<int32>(cacheSection, flagKey, 0)); #ifdef VST_LOG Log("Plugin \"%s\" found in PluginCache\n", plug->libraryName.ToLocale().c_str()); #endif // VST_LOG return plug; } else { #ifdef VST_LOG Log("Plugin \"%s\" mismatch in PluginCache: \"%s\" [%s]=\"%s\"\n", s, dllPath, (LPCTSTR)IDs, (LPCTSTR)strFullPath); #endif // VST_LOG } } } // If this key contains a file name on program launch, a plugin previously crashed OpenMPT. theApp.GetSettings().Write<mpt::PathString>("VST Plugins", "FailedPlugin", dllPath); AEffect *pEffect; HINSTANCE hLib; bool validPlug = false; VSTPluginLib *plug = new (std::nothrow) VSTPluginLib(dllPath, fileName); if(plug == nullptr) { return nullptr; } try { pEffect = LoadPlugin(dllPath, hLib); if(pEffect != nullptr && pEffect->magic == kEffectMagic && pEffect->dispatcher != nullptr) { pEffect->dispatcher(pEffect, effOpen, 0, 0, 0, 0); plug->pluginId1 = pEffect->magic; plug->pluginId2 = pEffect->uniqueID; GetPluginInformation(pEffect, *plug); #ifdef VST_LOG int nver = pEffect->dispatcher(pEffect, effGetVstVersion, 0,0, nullptr, 0); if (!nver) nver = pEffect->version; Log("%-20s: v%d.0, %d in, %d out, %2d programs, %2d params, flags=0x%04X realQ=%d offQ=%d\n", plug->libraryName.ToLocale().c_str(), nver, pEffect->numInputs, pEffect->numOutputs, pEffect->numPrograms, pEffect->numParams, pEffect->flags, pEffect->realQualities, pEffect->offQualities); #endif // VST_LOG pEffect->dispatcher(pEffect, effClose, 0, 0, 0, 0); validPlug = true; } FreeLibrary(hLib); } catch(...) { CVstPluginManager::ReportPlugException(mpt::String::PrintW(L"Exception while trying to load plugin \"%1\"!\n", plug->libraryName)); } // Now it should be safe to assume that this plugin loaded properly. :) theApp.GetSettings().Remove("VST Plugins", "FailedPlugin"); // If OK, write the information in PluginCache if(validPlug) { pluginList.push_back(plug); WriteToCache(*plug); } else { delete plug; } return (validPlug ? plug : nullptr); }