Thread: Avisynth+
View Single Post
Old 7th July 2019, 11:42   #4796  |  Link
Groucho2004
 
Join Date: Mar 2006
Location: Barcelona
Posts: 5,034
Quote:
Originally Posted by pinterf View Post
Sounds interesting. I don't want (= there are other things in my queue) to touch that section right now, but yes, your idea can work.
For your reference, below is the latest "GetPluginType()". Every plugin I have thrown at it is correctly detected.
Code:
BOOL GetPluginType(std::string sPlugin)
{
 BOOL PROCESS_64 = (sizeof(void*) == 8) ? TRUE : FALSE;
 BOOL bIs64BitDLL = FALSE;

 //The MapAndLoad function maps an image and preloads data from the mapped file.
 LOADED_IMAGE li;
 BOOL bLoaded = MapAndLoad((LPSTR)sPlugin.c_str(), NULL, &li, TRUE, TRUE);

 if (!bLoaded)
 {
  //error handling, check GetLastError() why the DLL could not be loaded
  return FALSE;
 }

 if (li.FileHeader->FileHeader.Machine != IMAGE_FILE_MACHINE_I386) //check the PE header for bitness
 {
  bIs64BitDLL = TRUE; //it's a 64 bit DLL
  if (!PROCESS_64) //if running a 32 bit process, throw error and return
  {
   //"Trying to load 64 bit DLL in 32 bit Avisynth"
   UnMapAndLoad(&li);
   return FALSE;
  }
 }
 else //it's a 32 bit DLL
 {
  if (PROCESS_64) //if running a 64 bit process, throw error and return
  {
   //"Trying to load 32 bit DLL in 64 bit Avisynth"
   UnMapAndLoad(&li);
   return FALSE;
  }
 }

 DWORD expVA = li.FileHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress;
 if (expVA == 0)
 {
  //error handling -> "Cannot retrieve PE header data"
  UnMapAndLoad(&li);
  return FALSE;
 }

 PIMAGE_EXPORT_DIRECTORY pExp = (PIMAGE_EXPORT_DIRECTORY)ImageRvaToVa(li.FileHeader, li.MappedAddress, expVA, NULL);
 if (pExp == 0)
 {
  //error handling -> "Cannot retrieve PE header data", check GetLastError()
  UnMapAndLoad(&li);
  return FALSE;
 }

 DWORD rvaNames = pExp->AddressOfNames;
 DWORD *prvaNames = (DWORD*)ImageRvaToVa(li.FileHeader, li.MappedAddress, rvaNames, NULL);
 if (prvaNames == 0)
 {
  //error handling -> "Cannot retrieve PE header data", check GetLastError()
  UnMapAndLoad(&li);
  return FALSE;
 }


 //enumerate DLL exports 
 DWORD dwName = 0;
 std::string sPluginType = "";
 for (dwName = 0; dwName < pExp->NumberOfNames; ++dwName)
 {
  DWORD rvaName = prvaNames[dwName];
  std::string sExportFunc((char *)ImageRvaToVa(li.FileHeader, li.MappedAddress, rvaName, NULL));
  std::transform(sExportFunc.begin(), sExportFunc.end(), sExportFunc.begin(), ::tolower); //convert to lower case for comparison

  if (sExportFunc.find("avisynthplugininit3") != string::npos) //CPP 2.6, 32 or 64 bit
  {
   sPluginType = "AVSCPP26";
   break;
  }

  if (sExportFunc.find("avisynthplugininit2") != string::npos) //CPP 2.5, 32 or 64 bit
  {
   sPluginType = "AVSCPP25";
   break;
  }

  if ((sExportFunc.find("avisynthplugininit") != string::npos) && !bIs64BitDLL) //CPP 2.0 (these are 32 bit only)
   sPluginType = "AVSCPP20"; //don't break here, keep looping

  if ((sExportFunc.find("avisynth_c_plugin_init@4") != string::npos) && !bIs64BitDLL) //32 bit C 2.5
  {
   sPluginType = "AVSC25";
   break;
  }

  if ((sExportFunc.find("avisynth_c_plugin_init") != string::npos) && bIs64BitDLL) //64 bit C 2.5
  {
   sPluginType = "AVSC25";
   break;
  }

  if ((sExportFunc == "avisynth_c_plugin_init") && !bIs64BitDLL) //C 2.0 (these are 32 bit only)
   sPluginType = "AVSC20"; //don't break here, keep looping
 }

 UnMapAndLoad(&li);

 return TRUE;
}
__________________
Groucho's Avisynth Stuff

Last edited by Groucho2004; 7th July 2019 at 17:37.
Groucho2004 is offline