Example #1
0
static int extension_load_plugins(rdpExtension* extension)
{
	int i;
	void* han;
	char path[256];
	rdpSettings* settings;
	PFREERDP_EXTENSION_ENTRY entry;
	FREERDP_EXTENSION_ENTRY_POINTS entryPoints;

	settings = extension->instance->settings;

	entryPoints.ext = extension;
	entryPoints.pRegisterExtension = extension_register_plugin;
	entryPoints.pRegisterPreConnectHook = extension_register_pre_connect_hook;
	entryPoints.pRegisterPostConnectHook = extension_register_post_connect_hook;

	for (i = 0; settings->extensions[i].name[0]; i++)
	{
		if (strchr(settings->extensions[i].name, PATH_SEPARATOR) == NULL)
			sprintf_s(path, sizeof(path), EXT_PATH "/%s." PLUGIN_EXT, settings->extensions[i].name);
		else
			sprintf_s(path, sizeof(path), "%s", settings->extensions[i].name);

		han = DLOPEN(path);
		fprintf(stderr, "extension_load_plugins: %s\n", path);

		if (han == NULL)
		{
			fprintf(stderr, "extension_load_plugins: failed to load %s\n", path);
			continue;
		}

		entry = (PFREERDP_EXTENSION_ENTRY) DLSYM(han, FREERDP_EXT_EXPORT_FUNC_NAME);
		if (entry == NULL)
		{
			DLCLOSE(han);
			fprintf(stderr, "extension_load_plugins: failed to find export function in %s\n", path);
			continue;
		}

		entryPoints.data = extension->instance->settings->extensions[i].data;
		if (entry(&entryPoints) != 0)
		{
			DLCLOSE(han);
			fprintf(stderr, "extension_load_plugins: %s entry returns error.\n", path);
			continue;
		}
	}

	return 0;
}
Example #2
0
File: ext.c Project: DrTusk/FreeRDP
static int
ext_load_plugins(rdpExt * ext)
{
	FREERDP_EXTENSION_ENTRY_POINTS entryPoints;
	int i;
	char path[256];
	void * han;
	PFREERDP_EXTENSION_ENTRY entry;

	entryPoints.ext = ext;
	entryPoints.pRegisterExtension = ext_register_extension;
	entryPoints.pRegisterPreConnectHook = ext_register_pre_connect_hook;
	entryPoints.pRegisterPostConnectHook = ext_register_post_connect_hook;

	for (i = 0; ext->inst->settings->extensions[i].name[0]; i++)
	{
		if (strchr(ext->inst->settings->extensions[i].name, PATH_SEPARATOR) == NULL)
		{
			snprintf(path, sizeof(path), EXT_PATH "/%s." PLUGIN_EXT, ext->inst->settings->extensions[i].name);
		}
		else
		{
			snprintf(path, sizeof(path), "%s", ext->inst->settings->extensions[i].name);
		}
		han = DLOPEN(path);
		printf("ext_load_plugins: %s\n", path);
		if (han == NULL)
		{
			printf("ext_load_plugins: failed to load %s\n", path);
			continue;
		}

		entry = (PFREERDP_EXTENSION_ENTRY) DLSYM(han, RDPEXT_EXPORT_FUNC_NAME);
		if (entry == NULL)
		{
			DLCLOSE(han);
			printf("ext_load_plugins: failed to find export function in %s\n", path);
			continue;
		}

		entryPoints.data = ext->inst->settings->extensions[i].data;
		if (entry(&entryPoints) != 0)
		{
			DLCLOSE(han);
			printf("ext_load_plugins: %s entry returns error.\n", path);
			continue;
		}
	}
	return 0;
}
Example #3
0
static ITSMFDecoder *
tsmf_load_decoder_by_name(const char * name, TS_AM_MEDIA_TYPE * media_type)
{
	ITSMFDecoder * decoder;
	char path[256];
	void * han;
	TSMF_DECODER_ENTRY entry;

	if (strchr(name, PATH_SEPARATOR) == NULL)
	{
		snprintf(path, sizeof(path), PLUGIN_PATH "/tsmf_%s." PLUGIN_EXT, name);
	}
	else
	{
		snprintf(path, sizeof(path), "%s", name);
	}
	han = DLOPEN(path);
	LLOGLN(0, ("tsmf_load_decoder_by_name: %s", path));
	if (han == NULL)
	{
		LLOGLN(0, ("tsmf_load_decoder_by_name: failed to load %s", path));
		return NULL;
	}
	entry = (TSMF_DECODER_ENTRY) DLSYM(han, TSMF_DECODER_EXPORT_FUNC_NAME);
	if (entry == NULL)
	{
		DLCLOSE(han);
		LLOGLN(0, ("tsmf_load_decoder_by_name: failed to find export function in %s", path));
		return NULL;
	}
	decoder = entry();
	if (decoder == NULL)
	{
		DLCLOSE(han);
		LLOGLN(0, ("tsmf_load_decoder_by_name: failed to call export function in %s", path));
		return NULL;
	}
	if (decoder->SetFormat(decoder, media_type) != 0)
	{
		decoder->Free(decoder);
		decoder = NULL;
	}
	return decoder;
}
Example #4
0
static int
rdpsnd_load_device_plugin(rdpsndPlugin * plugin, const char * name, RD_PLUGIN_DATA * data)
{
	FREERDP_RDPSND_DEVICE_ENTRY_POINTS entryPoints;
	char path[256];
	void * han;
	PFREERDP_RDPSND_DEVICE_ENTRY entry;

	if (strchr(name, PATH_SEPARATOR) == NULL)
	{
		snprintf(path, sizeof(path), PLUGIN_PATH "/rdpsnd_%s." PLUGIN_EXT, name);
	}
	else
	{
		snprintf(path, sizeof(path), "%s", name);
	}
	han = DLOPEN(path);
	LLOGLN(0, ("rdpsnd_load_device_plugin: %s", path));
	if (han == NULL)
	{
		LLOGLN(0, ("rdpsnd_load_device_plugin: failed to load %s", path));
		return 1;
	}
	entry = (PFREERDP_RDPSND_DEVICE_ENTRY) DLSYM(han, RDPSND_DEVICE_EXPORT_FUNC_NAME);
	if (entry == NULL)
	{
		DLCLOSE(han);
		LLOGLN(0, ("rdpsnd_load_device_plugin: failed to find export function in %s", path));
		return 1;
	}

	entryPoints.plugin = plugin;
	entryPoints.pRegisterRdpsndDevice = rdpsnd_register_device_plugin;
	entryPoints.pResample = rdpsnd_dsp_resample;
	entryPoints.pDecodeImaAdpcm = rdpsnd_dsp_decode_ima_adpcm;
	entryPoints.data = data;
	if (entry(&entryPoints) != 0)
	{
		DLCLOSE(han);
		LLOGLN(0, ("rdpsnd_load_device_plugin: %s entry returns error.", path));
		return 1;
	}
	return 0;
}
Example #5
0
/*
 * Callback for removing a module from stp_module_list.
 */
static void
module_list_freefunc(void *item /* module to remove */)
{
  stp_module_t *module = (stp_module_t *) item;
  if (module && module->fini) /* Call the module exit function */
    module->fini();
#if defined(USE_LTDL) || defined(USE_DLOPEN)
  DLCLOSE(module->handle); /* Close the module if it's not static */
#endif
}
Example #6
0
void
FeatureExtractionPluginFactory::pluginDeleted(Vamp::Plugin *plugin)
{
    void *handle = m_handleMap[plugin];
    if (handle) {
//        std::cerr << "unloading library " << handle << " for plugin " << plugin << std::endl;
        DLCLOSE(handle);
    }
    m_handleMap.erase(plugin);
}
Example #7
0
// play selected opponent
static void
opponentsloop (gameinfo * gi)
{
	char command[64];
	char reply[1024];
	CBengine engine;

	if (!loadlib (gi, &engine))
		return;

	// use DL_CALL_FCT macro
	// to enable profiling of shared object with sprof

	// engine info
	strcpy (command, "about");
	//DL_CALL_FCT (engine.command, (command, reply));
	(engine.command)(command,reply);
	printf ("\n%s\n\n", reply);

	// gametype
	strcpy (command, "get gametype");
	//DL_CALL_FCT (engine.command, (command, reply));
	(engine.command)(command,reply);
	gi->gametype = strtol (reply, (char **) NULL, 10);

	// start gamesloop
	switch (gi->gametype)
	{
	case ENGLISH:
		printf ("Playing english rules.\n");
		gamesloop (&engine, gi);
		break;
	case ITALIAN:
		printf ("Playing italian rules.\n");
		gamesloop (&engine, gi);
		break;
	case MAFIERZ:
		printf ("Playing italian rules on english board.\n");
		gamesloop (&engine, gi);
		break;
	case RUSSIAN:
		printf ("Playing russian rules.\n");
		gamesloop (&engine, gi);
		break;
	default:
		printf ("Unknown rules.\n");
		strcpy (gi->opponent, "part");
	}
#if 0
	DLCLOSE (engine.handle);
#endif
	printf ("\nOpponent left.\n");
}
Example #8
0
/**
 * UNUSED
 * This function closes a library handle that was previously opened by freerdp_open_library().
 * It is a wrapper over dlclose(), but provides logs in case of error.
 *
 * @see freerdp_open_library
 * @see freerdp_get_library_symbol
 *
 * @return true if the close succeeded. false otherwise.
 */
boolean freerdp_close_library(void* library)
{
	int status;

	status = DLCLOSE(library);

#ifdef _WIN32
	if (status != 0)
#else
	if (status == 0)
#endif
	{
		printf("freerdp_free_library: failed to close: %s\n", DLERROR());
		return false;
	}

	return true;
}
Example #9
0
bool CTAPI_closeCTAPI()
{
    char logmsg[300];
    
    // closing CTAPI lib
    signed char err=(*closefunc)(ctnum);
    if (err!=0) {
        sprintf(logmsg,"CT_close: %i (%s)",err,CTAPI_getErrorString(err));
        CTAPI_log(logmsg);
        return false;
    }
    
    CTAPI_log("closing CTAPI ok");

    // unloading CTAPI library
    if (DLCLOSE(handle)!=0) {
        sprintf(logmsg,"dlclose: %s",DLERROR());
        CTAPI_log(logmsg);
        return false;
    }
    
    return true;
}
Example #10
0
static int
loadlib (gameinfo * gi, CBengine * engine)
{
	char enginepath[512];

#if 0
#ifdef WIN32

	strcpy (enginepath, gi->opponent);
	strcat (enginepath, ".dll");

	engine->handle = LoadLibrary (enginepath);
	if (!engine->handle)
	{
		printf ("\nNo such opponent.\n");
		fprintf (stderr, "DLL not found: %s.\n", enginepath);
		strcpy (gi->opponent, "part");
		return 0;
	}

#else // not WIN32

	const char *error;

	// try system location
	strcpy (enginepath, LIB_DIR);
	strcat (enginepath, gi->opponent);
	strcat (enginepath, ".so");
	engine->handle = dlopen (enginepath, RTLD_LAZY);

	// try cwd
	if (!engine->handle)
	{
		strcpy (enginepath, "./");
		strcat (enginepath, gi->opponent);
		strcat (enginepath, ".so");
		engine->handle = dlopen (enginepath, RTLD_LAZY);
	}

	if (!engine->handle)
	{
		printf ("\nNo such opponent.\n");
		fprintf (stderr, "%s", dlerror ());
		printf ("\nAdditional search path: %s\n", LIB_DIR);
		strcpy (gi->opponent, "part");
		return 0;
	}

#endif // WIN32

	// mandatory library functions
	engine->command = (E_COMMAND) DLSYM (engine->handle, "enginecommand");
	engine->islegal = (E_ISLEGAL) DLSYM (engine->handle, "islegal");
	engine->getmove = (E_GETMOVE) DLSYM (engine->handle, "getmove");
#endif

	engine->command = enginecommand;
	engine->islegal = islegal;
	engine->getmove = getmove;

#if 0
#ifdef WIN32
	if (engine->command == NULL
		|| engine->islegal == NULL || engine->getmove == NULL)
	{
		fprintf (stderr, "Invalid engine.\n");
		strcpy (gi->opponent, "part");
		DLCLOSE (engine->handle);
		return 0;
	}
#else // not WIN32
	if (engine->command == NULL
		|| engine->islegal == NULL || engine->getmove == NULL)
	{
		fprintf (stderr, "Invalid engine: ");
		if ((error = dlerror ()) != NULL)
			fprintf (stderr, "%s\n", error);
		strcpy (gi->opponent, "part");
		DLCLOSE (engine->handle);
		return 0;
	}
#endif
#endif

	return 1;
}
Example #11
0
/* this is called when processing the command line parameters
   called only from main thread */
int
freerdp_chanman_load_plugin(rdpChanMan * chan_man, rdpSet * settings,
	const char * filename, void * data)
{
	struct lib_data * lib;
	CHANNEL_ENTRY_POINTS_EX ep;
	int ok;
	CHR path[255];

	DEBUG_CHANMAN("input filename %s", filename);
	if (chan_man->num_libs + 1 >= CHANNEL_MAX_COUNT)
	{
		DEBUG_CHANMAN("freerdp_chanman_load_plugin: too many channels");
		return 1;
	}
	lib = chan_man->libs + chan_man->num_libs;
	if (strchr(filename, PATH_SEPARATOR) == NULL)
	{
#ifdef _WIN32
		swprintf(path, sizeof(path), L"./%S." PLUGIN_EXT, filename);
#else
		snprintf(path, sizeof(path), PLUGIN_PATH "/%s." PLUGIN_EXT, filename);
#endif
	}
	else
	{
#ifdef _WIN32
		swprintf(path, sizeof(path), L"%S", filename);
#else
		strncpy(path, filename, sizeof(path));
#endif
	}
	DEBUG_CHANMAN("freerdp_chanman_load_plugin %s: %s", filename, path);
	lib->han = DLOPEN(path);
	if (lib->han == 0)
	{
		DEBUG_CHANMAN("freerdp_chanman_load_plugin: failed to load library");
		return 1;
	}
	lib->entry = (PVIRTUALCHANNELENTRY)
		DLSYM(lib->han, CHANNEL_EXPORT_FUNC_NAME);
	if (lib->entry == 0)
	{
		DEBUG_CHANMAN("freerdp_chanman_load_plugin: failed to find export function");
		DLCLOSE(lib->han);
		return 1;
	}
	ep.cbSize = sizeof(ep);
	ep.protocolVersion = VIRTUAL_CHANNEL_VERSION_WIN2000;
	ep.pVirtualChannelInit = MyVirtualChannelInit;
	ep.pVirtualChannelOpen = MyVirtualChannelOpen;
	ep.pVirtualChannelClose = MyVirtualChannelClose;
	ep.pVirtualChannelWrite = MyVirtualChannelWrite;
	ep.pExtendedData = data;
	ep.pVirtualChannelEventPush = MyVirtualChannelEventPush;

	/* enable MyVirtualChannelInit */
	chan_man->can_call_init = 1;
	chan_man->settings = settings;

	MUTEX_LOCK(g_mutex_init);
	g_init_chan_man = chan_man;
	ok = lib->entry((PCHANNEL_ENTRY_POINTS)&ep);
	g_init_chan_man = NULL;
	MUTEX_UNLOCK(g_mutex_init);

	/* disable MyVirtualChannelInit */
	chan_man->settings = 0;
	chan_man->can_call_init = 0;
	if (!ok)
	{
		DEBUG_CHANMAN("freerdp_chanman_load_plugin: export function call failed");
		DLCLOSE(lib->han);
		return 1;
	}
	return 0;
}
Example #12
0
int main(int argc, char **argv)
{
   HANDLE indigoHandle;
   HANDLE indigoInChIHandle;
   HANDLE indigoRendererHandle;
   HANDLE bingoHandle;

   STR_RET_VOID indigoVersion;
   INT_RET_STR indigoLoadMoleculeFromString;
   INT_RET_STR_STR indigoSetOption;
   INT_RET indigoWriteBuffer;
   INT_RET_INT_INT indigoRender;
   STR_RET_INT indigoInchiGetInchi;
   INT_RET_STR_STR_STR bingoCreateDatabaseFile;
   INT_RET_INT bingoCloseDatabase;
   STR_RET_VOID bingoVersion;


   int indigoTest = 0;
   int indigoInChITest = 0;
   int indigoRendererTest = 0;
   int bingoTest = 0;

   const char *indigoLibraryPath;
   const char *indigoInChILibraryPath;
   const char *indigoRendererLibraryPath;
   const char *bingoLibraryPath;

   int i = 0;

   /* Parse arguments and set variables*/
   for (i = 0; i < argc; i++)
   {
      if (strstr(argv[i], "indigo."))
      {
         indigoTest = 1;
         indigoLibraryPath = argv[i];
      }
      if (strstr(argv[i], "indigo-inchi"))
      {
         indigoInChITest = 1;
         indigoInChILibraryPath = argv[i];
      }
      if (strstr(argv[i], "indigo-renderer"))
      {
         indigoRendererTest = 1;
         indigoRendererLibraryPath = argv[i];
      }
      if (strstr(argv[i], "bingo"))
      {
         bingoTest = 1;
         bingoLibraryPath = argv[i];
      }
   }
   /* Tests */
   if (indigoTest)
   {
      /* Load Indigo */
      indigoHandle = dlOpenWithCheck(indigoLibraryPath);
      if (!indigoHandle)
      {
         printf("Cannot load %s\n", indigoLibraryPath);
         return 1;
      }
      printf("Indigo instance: %lu\n", (unsigned long)indigoHandle);
      /* Execute Indigo function */
      indigoVersion = (STR_RET_VOID)DLSYM(indigoHandle, "indigoVersion");
      printf("Indigo version: %s\n", indigoVersion());
   }
   if (indigoInChITest)
   {
      int m;
      /* Load IndigoInChI */
      indigoInChIHandle = dlOpenWithCheck(indigoInChILibraryPath);
      if (!indigoInChIHandle)
      {
         printf("Cannot load %s\n", indigoInChILibraryPath);
         return 1;
      }
      printf("IndigoInChI address: %lu\n", (unsigned long)indigoInChIHandle);
      indigoInchiGetInchi = (STR_RET_INT)DLSYM(indigoInChIHandle, "indigoInchiGetInchi");
      indigoLoadMoleculeFromString = (INT_RET_STR)DLSYM(indigoHandle, "indigoLoadMoleculeFromString");
      m = indigoLoadMoleculeFromString("C");
      printf("indigoInChI InChI: %s\n", indigoInchiGetInchi(m));
   }
   if (indigoRendererTest)
   {
      int m, buf, res;
      /* Load IndigoRenderer */
      indigoRendererHandle = dlOpenWithCheck(indigoRendererLibraryPath);
      if (!indigoRendererHandle)
      {
         printf("Cannot load %s\n", indigoRendererLibraryPath);
         return 1;
      }
      printf("IndigoRenderer address: %lu\n", (unsigned long)indigoRendererHandle);
      indigoLoadMoleculeFromString = (INT_RET_STR)DLSYM(indigoHandle, "indigoLoadMoleculeFromString");
      indigoWriteBuffer = (INT_RET)DLSYM(indigoHandle, "indigoWriteBuffer");
      indigoRender = (INT_RET_INT_INT)DLSYM(indigoRendererHandle, "indigoRender");
      indigoSetOption = (INT_RET_STR_STR)DLSYM(indigoHandle, "indigoSetOption");
      indigoSetOption("render-output-format", "png");
      m = indigoLoadMoleculeFromString("C");
      buf = indigoWriteBuffer();
      res = indigoRender(m, buf);
      printf("indigoRender result: %d\n", res);
   }
   if (bingoTest)
   {
      int db;
      /* Load Bingo */
      bingoHandle = dlOpenWithCheck(bingoLibraryPath);
      if (!bingoHandle)
      {
         printf("Cannot load %s\n", bingoLibraryPath);
         return 1;
      }
      printf("Bingo address: %lu\n", (unsigned long)bingoHandle);
      bingoVersion = (STR_RET_VOID)DLSYM(bingoHandle, "bingoVersion");
      printf("Bingo version: %s\n", bingoVersion());
      bingoCreateDatabaseFile = (INT_RET_STR_STR_STR)DLSYM(bingoHandle, "bingoCreateDatabaseFile");
      bingoCloseDatabase = (INT_RET_INT)DLSYM(bingoHandle, "bingoCloseDatabase");
      db = bingoCreateDatabaseFile("test.db", "molecule", "");
      printf("Bingo database ID: %d\n", db);
      printf("Bingo close database status: %d\n", bingoCloseDatabase(db));
   }
   /* Close libraries */
   if (bingoTest)
   {
      DLCLOSE(bingoHandle);
   }
   if (indigoRendererTest)
   {
      DLCLOSE(indigoRendererHandle);
   }
   if (indigoInChITest)
   {
      DLCLOSE(indigoInChIHandle);
   }
   if (indigoTest)
   {
      DLCLOSE(indigoHandle);
   }
   return 0;
}
Example #13
0
Vamp::Plugin *
FeatureExtractionPluginFactory::instantiatePlugin(QString identifier,
						  float inputSampleRate)
{
    Profiler profiler("FeatureExtractionPluginFactory::instantiatePlugin");

    Vamp::Plugin *rv = 0;
    Vamp::PluginHostAdapter *plugin = 0;

    const VampPluginDescriptor *descriptor = 0;
    int index = 0;

    QString type, soname, label;
    PluginIdentifier::parseIdentifier(identifier, type, soname, label);
    if (type != "vamp") {
	std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Wrong factory for plugin type " << type.toStdString() << std::endl;
	return 0;
    }

    QString found = findPluginFile(soname);

    if (found == "") {
        std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Failed to find library file " << soname.toStdString() << std::endl;
        return 0;
    } else if (found != soname) {

#ifdef DEBUG_PLUGIN_SCAN_AND_INSTANTIATE
        std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Given library name was " << soname.toStdString() << ", found at " << found.toStdString() << std::endl;
        std::cerr << soname.toStdString() << " -> " << found.toStdString() << std::endl;
#endif

    }        

    soname = found;

    void *libraryHandle = DLOPEN(soname, RTLD_LAZY | RTLD_LOCAL);
            
    if (!libraryHandle) {
        std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Failed to load library " << soname.toStdString() << ": " << DLERROR() << std::endl;
        return 0;
    }

    VampGetPluginDescriptorFunction fn = (VampGetPluginDescriptorFunction)
        DLSYM(libraryHandle, "vampGetPluginDescriptor");
    
    if (!fn) {
        std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: No descriptor function in " << soname.toStdString() << std::endl;
        goto done;
    }

    while ((descriptor = fn(VAMP_API_VERSION, index))) {
        if (label == descriptor->identifier) break;
        ++index;
    }

    if (!descriptor) {
        std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Failed to find plugin \"" << label.toStdString() << "\" in library " << soname.toStdString() << std::endl;
        goto done;
    }

    plugin = new Vamp::PluginHostAdapter(descriptor, inputSampleRate);

    if (plugin) {
        m_handleMap[plugin] = libraryHandle;
        rv = new PluginDeletionNotifyAdapter(plugin, this);
    }

//    std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Constructed Vamp plugin, rv is " << rv << std::endl;

    //!!! need to dlclose() when plugins from a given library are unloaded

done:
    if (!rv) {
        if (DLCLOSE(libraryHandle) != 0) {
            std::cerr << "WARNING: FeatureExtractionPluginFactory::instantiatePlugin: Failed to unload library " << soname.toStdString() << std::endl;
        }
    }

//    std::cerr << "FeatureExtractionPluginFactory::instantiatePlugin: Instantiated plugin " << label.toStdString() << " from library " << soname.toStdString() << ": descriptor " << descriptor << ", rv "<< rv << ", label " << rv->getName() << ", outputs " << rv->getOutputDescriptors().size() << std::endl;
    
    return rv;
}
Example #14
0
std::vector<QString>
FeatureExtractionPluginFactory::getPluginIdentifiers()
{
    Profiler profiler("FeatureExtractionPluginFactory::getPluginIdentifiers");

    std::vector<QString> rv;
    std::vector<QString> path = getPluginPath();
    
    for (std::vector<QString>::iterator i = path.begin(); i != path.end(); ++i) {

#ifdef DEBUG_PLUGIN_SCAN_AND_INSTANTIATE
        std::cerr << "FeatureExtractionPluginFactory::getPluginIdentifiers: scanning directory " << i->toStdString() << std::endl;
#endif

	QDir pluginDir(*i, PLUGIN_GLOB,
                       QDir::Name | QDir::IgnoreCase,
                       QDir::Files | QDir::Readable);

	for (unsigned int j = 0; j < pluginDir.count(); ++j) {

            QString soname = pluginDir.filePath(pluginDir[j]);

#ifdef DEBUG_PLUGIN_SCAN_AND_INSTANTIATE
            std::cerr << "FeatureExtractionPluginFactory::getPluginIdentifiers: trying potential library " << soname.toStdString() << std::endl;
#endif

            void *libraryHandle = DLOPEN(soname, RTLD_LAZY | RTLD_LOCAL);
            
            if (!libraryHandle) {
                std::cerr << "WARNING: FeatureExtractionPluginFactory::getPluginIdentifiers: Failed to load library " << soname.toStdString() << ": " << DLERROR() << std::endl;
                continue;
            }

#ifdef DEBUG_PLUGIN_SCAN_AND_INSTANTIATE
            std::cerr << "FeatureExtractionPluginFactory::getPluginIdentifiers: It's a library all right, checking for descriptor" << std::endl;
#endif

            VampGetPluginDescriptorFunction fn = (VampGetPluginDescriptorFunction)
                DLSYM(libraryHandle, "vampGetPluginDescriptor");

            if (!fn) {
                std::cerr << "WARNING: FeatureExtractionPluginFactory::getPluginIdentifiers: No descriptor function in " << soname.toStdString() << std::endl;
                if (DLCLOSE(libraryHandle) != 0) {
                    std::cerr << "WARNING: FeatureExtractionPluginFactory::getPluginIdentifiers: Failed to unload library " << soname.toStdString() << std::endl;
                }
                continue;
            }

#ifdef DEBUG_PLUGIN_SCAN_AND_INSTANTIATE
            std::cerr << "FeatureExtractionPluginFactory::getPluginIdentifiers: Vamp descriptor found" << std::endl;
#endif

            const VampPluginDescriptor *descriptor = 0;
            int index = 0;

            std::map<std::string, int> known;
            bool ok = true;

            while ((descriptor = fn(VAMP_API_VERSION, index))) {

                if (known.find(descriptor->identifier) != known.end()) {
                    std::cerr << "WARNING: FeatureExtractionPluginFactory::getPluginIdentifiers: Plugin library "
                              << soname.toStdString()
                              << " returns the same plugin identifier \""
                              << descriptor->identifier << "\" at indices "
                              << known[descriptor->identifier] << " and "
                              << index << std::endl;
                    std::cerr << "FeatureExtractionPluginFactory::getPluginIdentifiers: Avoiding this library (obsolete API?)" << std::endl;
                    ok = false;
                    break;
                } else {
                    known[descriptor->identifier] = index;
                }

                ++index;
            }

            if (ok) {

                index = 0;

                while ((descriptor = fn(VAMP_API_VERSION, index))) {

                    QString id = PluginIdentifier::createIdentifier
                        ("vamp", soname, descriptor->identifier);
                    rv.push_back(id);
#ifdef DEBUG_PLUGIN_SCAN_AND_INSTANTIATE
                    std::cerr << "FeatureExtractionPluginFactory::getPluginIdentifiers: Found plugin id " << id.toStdString() << " at index " << index << std::endl;
#endif
                    ++index;
                }
            }
            
            if (DLCLOSE(libraryHandle) != 0) {
                std::cerr << "WARNING: FeatureExtractionPluginFactory::getPluginIdentifiers: Failed to unload library " << soname.toStdString() << std::endl;
            }
	}
    }

    generateTaxonomy();

    return rv;
}