[PD-cvs] externals/postlude/dssi/src jload.c, NONE, 1.1 jsearch.c, NONE, 1.1 jutils.h, NONE, 1.1 dssi~.c, 1.6, 1.7 dssi~.h, 1.4, 1.5

Jamie Bullock postlude at users.sourceforge.net
Sat Mar 11 21:32:53 CET 2006


Update of /cvsroot/pure-data/externals/postlude/dssi/src
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv3190/src

Modified Files:
	dssi~.c dssi~.h 
Added Files:
	jload.c jsearch.c jutils.h 
Log Message:
Added jutils for improved search and load facilities


--- NEW FILE: jsearch.c ---
/* search.c

   Free software by Richard W.E. Furse. Do with as you will. No
   warranty. */

/* patched by Jarno Seppänen, jams at cs.tut.fi, for plugin~ */

/* patched by Jamie Bullock, jamie at postlude.co.uk, for dssi~ */

/*****************************************************************************/

#include <dirent.h>
#include <dlfcn.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <unistd.h>

/*****************************************************************************/

#include "dssi.h"
#include "jutils.h"

/*****************************************************************************/

/* Search just the one directory. */
static void
LADSPADirectoryPluginSearch (const char * pcDirectory, 
			     LADSPAPluginSearchCallbackFunction fCallbackFunction,
			     void* user_data)
{
  char * pcFilename;
  DIR * psDirectory;
  DSSI_Descriptor_Function fDescriptorFunction;
  long lDirLength;
  long iNeedSlash;
  struct dirent * psDirectoryEntry;
  void * pvPluginHandle;
  int is_DSSI;

  lDirLength = strlen(pcDirectory);
  if (!lDirLength)
    return;
  if (pcDirectory[lDirLength - 1] == '/')
    iNeedSlash = 0;
  else
    iNeedSlash = 1;

  psDirectory = opendir(pcDirectory);
  if (!psDirectory)
    return;

  while (1) {

    psDirectoryEntry = readdir(psDirectory);
    if (!psDirectoryEntry) {
      closedir(psDirectory);
      return;
    }

    pcFilename = malloc(lDirLength
			+ strlen(psDirectoryEntry->d_name)
			+ 1 + iNeedSlash);
    strcpy(pcFilename, pcDirectory);
    if (iNeedSlash)
      strcat(pcFilename, "/");
    strcat(pcFilename, psDirectoryEntry->d_name);
    
    pvPluginHandle = dlopen(pcFilename, RTLD_LAZY);
    if (pvPluginHandle) {
      /* This is a file and the file is a shared library! */

      dlerror();
      if(fDescriptorFunction = (DSSI_Descriptor_Function)dlsym(pvPluginHandle,
					    "ladspa_descriptor"))
	      is_DSSI = 0;
      
      else if(fDescriptorFunction = (DSSI_Descriptor_Function)dlsym(pvPluginHandle,
					    "dssi_descriptor"))
	      is_DSSI = 1;
      
      if (dlerror() == NULL && fDescriptorFunction) {
	/* We've successfully found a ladspa_descriptor function. Pass
           it to the callback function. */
	fCallbackFunction(pcFilename,
			  pvPluginHandle,
			  fDescriptorFunction,
			  user_data,
			  is_DSSI);
	dlclose (pvPluginHandle);
      }
      else {
	/* It was a library, but not a LADSPA one. Unload it. */
	dlclose(pcFilename);
      }
    }
  }
}

/*****************************************************************************/

void 
LADSPAPluginSearch(LADSPAPluginSearchCallbackFunction fCallbackFunction,
		   void* user_data)
{

  char * pcBuffer;
  const char * pcEnd;
  const char * pcLADSPAPath;
  char *pluginPath;
  const char * pcStart;


  pcLADSPAPath = NULL;
  
  if(getenv("LADSPA_PATH") && getenv("DSSI_PATH")){ 
	pluginPath = malloc(sizeof(char) * 
			(strlen(getenv("LADSPA_PATH")) + 1) + 
			sizeof(char) * strlen(getenv("DSSI_PATH")));
  	sprintf(pluginPath, "%s:%s", 
			getenv("LADSPA_PATH"), getenv("DSSI_PATH"));
	pcLADSPAPath = pluginPath;
	free(pluginPath);
  }
  if (pcLADSPAPath == NULL) {
    fprintf(stderr, "Warning: no LADSPA_PATH and DSSI_PATH, assuming /usr/lib/ladspa:/usr/local/lib/ladspa:/usr/lib/dssi:/usr/local/lib/dssi\n");
    pcLADSPAPath = 
	"/usr/lib/ladspa:/usr/local/lib/ladspa:/usr/lib/dssi:/usr/local/lib/dssi";
  }
  
  pcStart = pcLADSPAPath;
  while (*pcStart != '\0') {
    pcEnd = pcStart;
    while (*pcEnd != ':' && *pcEnd != '\0')
      pcEnd++;
    
    pcBuffer = malloc(1 + pcEnd - pcStart);
    if (pcEnd > pcStart)
      strncpy(pcBuffer, pcStart, pcEnd - pcStart);
    pcBuffer[pcEnd - pcStart] = '\0';
    
    LADSPADirectoryPluginSearch(pcBuffer, fCallbackFunction, user_data);
    
    pcStart = pcEnd;
    if (*pcStart == ':')
      pcStart++;
  }
}


/*****************************************************************************/

/* EOF */

--- NEW FILE: jload.c ---
/* load.c

   Free software by Richard W.E. Furse. Do with as you will. No
   warranty. */

/* patched by Jarno Seppänen, jams at cs.tut.fi, for plugin~ */

/* patched by Jamie Bullock, jamie at postlude.co.uk, for dssi~ */

/*****************************************************************************/

#include <dlfcn.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

/*****************************************************************************/

#include "ladspa.h"
#include "jutils.h"

/*****************************************************************************/

/* This function provides a wrapping of dlopen(). When the filename is
   not an absolute path (i.e. does not begin with / character), this
   routine will search the LADSPA_PATH for the file. */
static void *
dlopenLADSPA(const char * pcFilename, int iFlag) {

  char * pcBuffer;
  const char * pcEnd;
  const char * pcLADSPAPath;
  const char * pcStart;
  int iEndsInSO;
  int iNeedSlash;
  size_t iFilenameLength;
  void * pvResult;
  char *pluginPath;


  iFilenameLength = strlen(pcFilename);
  pvResult = NULL;

  /* First we just try calling dlopen(). This works if the user knows
     about dlopen() and has placed the file on the LD_LIBRARY path or
     has used an absolute directory. */
  pvResult = dlopen(pcFilename, iFlag);
  if (pvResult != NULL)
    return pvResult;

  /* If the filename is not absolute then we wish to check along the
     LADSPA_PATH path to see if we can find the file there. */
  if (pcFilename[0] != '/') {

	  pcLADSPAPath = NULL;
	  
	  if(getenv("LADSPA_PATH") && getenv("DSSI_PATH")){ 
		pluginPath = malloc(sizeof(char) * 
				(strlen(getenv("LADSPA_PATH")) + 1) + 
				sizeof(char) * strlen(getenv("DSSI_PATH")));
		sprintf(pluginPath, "%s:%s", 
				getenv("LADSPA_PATH"), getenv("DSSI_PATH"));
		pcLADSPAPath = pluginPath;
		free(pluginPath);
	  }
	  if (pcLADSPAPath == NULL) {
	    fprintf(stderr, "Warning: no LADSPA_PATH and DSSI_PATH, assuming /usr/lib/ladspa:/usr/local/lib/ladspa:/usr/lib/dssi:/usr/local/lib/dssi\n");
	    pcLADSPAPath = 
		"/usr/lib/ladspa:/usr/local/lib/ladspa:/usr/lib/dssi:/usr/local/lib/dssi";
	  }

    if (pcLADSPAPath) {

      pcStart = pcLADSPAPath;
      while (*pcStart != '\0') {
	pcEnd = pcStart;
	while (*pcEnd != ':' && *pcEnd != '\0')
	  pcEnd++;
	
	pcBuffer = malloc(iFilenameLength + 2 + (pcEnd - pcStart));
	if (pcEnd > pcStart)
	  strncpy(pcBuffer, pcStart, pcEnd - pcStart);
	iNeedSlash = 0;
	if (pcEnd > pcStart)
	  if (*(pcEnd - 1) != '/') {
	    iNeedSlash = 1;
	    pcBuffer[pcEnd - pcStart] = '/';
	  }
	strcpy(pcBuffer + iNeedSlash + (pcEnd - pcStart), pcFilename);
	
	pvResult = dlopen(pcBuffer, iFlag);
	
	free (pcBuffer);
	if (pvResult != NULL){
		  return pvResult;
	}
	
	pcStart = pcEnd;
	if (*pcStart == ':')
	  pcStart++;
      }
    } else {
	fputs ("warning: You haven't specified the LADSPA_PATH environment variable and didn't specify an absolute path to the plug-in.\n"
	       "Please set the LADSPA_PATH variable to point to your LADSPA plug-in directories (eg. \"export LADSPA_PATH=/usr/local/lib/ladspa\").\n", stderr);
    }
  }

  /* As a last ditch effort, check if filename does not end with
     ".so". In this case, add this suffix and recurse. */
  iEndsInSO = 0;
  if (iFilenameLength > 3)
    iEndsInSO = (strcmp(pcFilename + iFilenameLength - 3, ".so") == 0);
  if (!iEndsInSO) {
    pcBuffer = malloc(iFilenameLength + 4);
    strcpy(pcBuffer, pcFilename);
    strcat(pcBuffer, ".so");
    pvResult = dlopenLADSPA(pcBuffer,  iFlag);
  }

  if (pvResult != NULL)
    return pvResult;

  /* If nothing has worked, then at least we can make sure we set the
     correct error message - and this should correspond to a call to
     dlopen() with the actual filename requested. The dlopen() manual
     page does not specify whether the first or last error message
     will be kept when multiple calls are made to dlopen(). We've
     covered the former case - now we can handle the latter by calling
     dlopen() again here. */
  return dlopen(pcFilename, iFlag);
}

/*****************************************************************************/

void *
loadLADSPAPluginLibrary(const char * pcPluginFilename) {

  void * pvPluginHandle;

  pvPluginHandle = dlopenLADSPA(pcPluginFilename, RTLD_NOW);
  if (!pvPluginHandle) {
    fprintf(stderr, 
	    "Failed to load plugin \"%s\": %s\n", 
	    pcPluginFilename,
	    dlerror());
#if 0
    exit(1);
#else
    return NULL;
#endif
  }

  return pvPluginHandle;
}

/*****************************************************************************/

void 
unloadLADSPAPluginLibrary(void * pvLADSPAPluginLibrary) {
  dlclose(pvLADSPAPluginLibrary);
}

/*****************************************************************************/

const LADSPA_Descriptor *
findLADSPAPluginDescriptor(void * pvLADSPAPluginLibrary,
			   const char * pcPluginLibraryFilename,
			   const char * pcPluginLabel) {

  const LADSPA_Descriptor * psDescriptor;
  LADSPA_Descriptor_Function pfDescriptorFunction;
  unsigned long lPluginIndex;

  dlerror();
  pfDescriptorFunction 
    = (LADSPA_Descriptor_Function)dlsym(pvLADSPAPluginLibrary,
					"ladspa_descriptor");
  if (!pfDescriptorFunction) {
    const char * pcError = dlerror();
    if (pcError) 
      fprintf(stderr,
	      "Unable to find ladspa_descriptor() function in plugin "
	      "library file \"%s\": %s.\n"
	      "Are you sure this is a LADSPA plugin file?\n", 
	      pcPluginLibraryFilename,
	      pcError);
#if 0
    exit(1);
#else
    return NULL;
#endif
  }

  for (lPluginIndex = 0;; lPluginIndex++) {
    psDescriptor = pfDescriptorFunction(lPluginIndex);
    if (psDescriptor == NULL) {
      fprintf(stderr,
	      "Unable to find label \"%s\" in plugin library file \"%s\".\n",
	      pcPluginLabel,
	      pcPluginLibraryFilename);
#if 0
      exit(1);
#else
      return NULL;
#endif
    }
    if (strcmp(psDescriptor->Label, pcPluginLabel) == 0)
      return psDescriptor;
  }
}

/*****************************************************************************/

/* EOF */

Index: dssi~.c
===================================================================
RCS file: /cvsroot/pure-data/externals/postlude/dssi/src/dssi~.c,v
retrieving revision 1.6
retrieving revision 1.7
diff -C2 -d -r1.6 -r1.7
*** dssi~.c	22 Feb 2006 12:34:12 -0000	1.6
--- dssi~.c	11 Mar 2006 20:32:51 -0000	1.7
***************
*** 9,12 ****
--- 9,14 ----
   * Hexter (GPL license): Copyright (C) 2004 Sean Bolton and others.
   * 
+  * plugin~ (GPL license): Copyright (C) 2000 Jarno Seppänen, remIXed 2005
+  * 
   *
   * This program is free software; you can redistribute it and/or
***************
*** 28,32 ****
  
[...1669 lines suppressed...]
! 	class_addmethod(dssi_tilde_class, (t_method)dssi_config, 
! 			gensym("config"), A_GIMME, 0);
    	class_sethelpsymbol(dssi_tilde_class, gensym("help-dssi"));
    CLASS_MAINSIGNALIN(dssi_tilde_class, t_dssi_tilde,f);
--- 2108,2122 ----
  void dssi_tilde_setup(void) {
  	
! 	dssi_tilde_class = class_new(gensym("dssi~"), (t_newmethod)dssi_tilde_new,(t_method)dssi_tilde_free, sizeof(t_dssi_tilde), 0, A_GIMME, 0);
! 	class_addlist(dssi_tilde_class, dssi_tilde_list);
  	class_addbang(dssi_tilde_class, dssi_bang);
! 	class_addmethod(dssi_tilde_class, 
! 			(t_method)dssi_tilde_dsp, gensym("dsp"), 0);
! 	class_addmethod(dssi_tilde_class, (t_method)dssi_tilde_dssi_methods, 
! 			gensym("dssi"), A_GIMME, 0);
! 	class_addmethod (dssi_tilde_class,(t_method)dssi_tilde_control, gensym ("control"),A_DEFSYM, A_DEFFLOAT, A_DEFFLOAT, 0);
! 	class_addmethod (dssi_tilde_class,(t_method)dssi_tilde_info,gensym ("info"),0);
! 	class_addmethod (dssi_tilde_class,(t_method)dssi_tilde_list_plugins,gensym ("listplugins"),0);
! 	class_addmethod (dssi_tilde_class,(t_method)dssi_tilde_reset,gensym ("reset"), A_DEFFLOAT, 0);
    	class_sethelpsymbol(dssi_tilde_class, gensym("help-dssi"));
    CLASS_MAINSIGNALIN(dssi_tilde_class, t_dssi_tilde,f);

Index: dssi~.h
===================================================================
RCS file: /cvsroot/pure-data/externals/postlude/dssi/src/dssi~.h,v
retrieving revision 1.4
retrieving revision 1.5
diff -C2 -d -r1.4 -r1.5
*** dssi~.h	22 Feb 2006 12:34:12 -0000	1.4
--- dssi~.h	11 Mar 2006 20:32:51 -0000	1.5
***************
*** 42,46 ****
  
  
! #define VERSION 0.83
  #define EVENT_BUFSIZE 1024
  #define OSC_BASE_MAX 1024
--- 42,46 ----
  
  
! #define VERSION 0.89
  #define EVENT_BUFSIZE 1024
  #define OSC_BASE_MAX 1024
***************
*** 53,58 ****
  
  #define LOADGUI 1 /* FIX: depracate this */
! #define DEBUG 0
  #ifdef DEBUG
  	#define CHECKSUM_PATCH_FILES_ON_LOAD 1
  #endif
--- 53,177 ----
  
  #define LOADGUI 1 /* FIX: depracate this */
! #define DEBUG 1
  #ifdef DEBUG
  	#define CHECKSUM_PATCH_FILES_ON_LOAD 1
  #endif
+ 
+ #ifndef MIN
+ #define MIN(a,b) ((a)<(b)?(a):(b))
+ #endif
+ 
+ 
+ /*From dx7_voice.h by Sean Bolton */
+ 
+ typedef struct _dx7_patch_t {
+ 	uint8_t data[128];
+ } dx7_patch_t;
+ 
+ typedef struct _dssi_instance {
+    
+    long             currentBank;
+    long             currentProgram;
+    int              pendingBankLSB;
+    int              pendingBankMSB;
+    int              pendingProgramChange;
+    
+    int plugin_ProgramCount;
+    DSSI_Program_Descriptor *pluginPrograms;
+ 
+    lo_address       uiTarget; /*osc stuff */
+    int              ui_hidden;
+    int              ui_show;
+    int              uiNeedsProgramUpdate;
+    char            *ui_osc_control_path;
+    char            *ui_osc_configure_path;
+    char            *ui_osc_program_path;
+    char            *ui_osc_show_path;
+    char            *ui_osc_hide_path;
+    char            *ui_osc_quit_path;
+    
+    int *plugin_PortControlInNumbers; /*not sure if this should go here?*/
+   
+    char *osc_url_path;
+    pid_t	gui_pid;
+    
+ } t_dssi_instance;
+ 
+ struct dssi_configure_pair {
+ 	t_int instance;
+ 	char *key,
+ 	     *value;
+ 	struct dssi_configure_pair *next;
+ }; 
+ 
+ typedef struct dssi_configure_pair t_dssi_configure_pair;
+ 
+ typedef struct _port_info {
+ 	t_atom type,
+ 	       data_type,
+ 	       name,
+ 	       lower_bound,
+ 	      upper_bound,
+ 	      p_default;
+ } t_port_info;
+ 
+ typedef struct _dssi_tilde {
+   t_object  x_obj;
+   t_int is_DSSI;
+   const char *dll_arg,  /*arg given by user - either path or dll name*/
+        	     *plugin_label;
+   char	     *dll_path; /*absolute path to plugin */
+   void *dll_handle;
+   char *dir; /* project dircetory */
+   LADSPA_Handle *instanceHandles; /*was handle*/
+   t_dssi_instance *instances; 
+   int n_instances;
+   unsigned long *instanceEventCounts;
+   snd_seq_event_t **instanceEventBuffers;
+ 
+ snd_seq_event_t midiEventBuf[EVENT_BUFSIZE];
+ /*static snd_seq_event_t **instanceEventBuffers;*/
+ int bufWriteIndex, bufReadIndex;
+ pthread_mutex_t midiEventBufferMutex;
+ /*static pthread_mutex_t listHandlerMutex = PTHREAD_MUTEX_INITIALIZER;*/
+    
+   DSSI_Descriptor_Function desc_func;
+   DSSI_Descriptor *descriptor;
+   
+   t_port_info *port_info;
+   
+   t_int	ports_in, ports_out, ports_controlIn, ports_controlOut;
+   t_int plugin_ins;/* total audio input ports for plugin*/
+   t_int plugin_outs;/* total audio output ports plugin*/
+   t_int plugin_controlIns;/* total control input ports*/
+   t_int plugin_controlOuts;/* total control output ports */
+ 
+   unsigned long *plugin_ControlInPortNumbers; /*Array of input port numbers for the plugin */
+ 
+   t_float **plugin_InputBuffers, **plugin_OutputBuffers; /* arrays of arrays for buffering audio for each audio port */
+   t_float *plugin_ControlDataInput, *plugin_ControlDataOutput; /*arrays for control data for each port (1 item per 'run')*/
+   lo_server_thread osc_thread;
+   char *osc_url_base;
+   char *dll_name;
+   
+   t_int time_ref; /*logical time reference */
+   t_int sr;
+   t_float sr_inv;
+   t_int blksize;
+   t_float f;
+   
+   t_float **outlets, **inlets;
+   t_outlet *control_outlet;
+ 
+   t_dssi_configure_pair *configure_buffer_head;
+   
+ } t_dssi_tilde;
+ 
+ static char *dssi_tilde_send_configure(t_dssi_tilde *x, char *key, 
+ 		char *value, t_int instance);
+ static int osc_message_handler(const char *path, const char *types, 
+ 		lo_arg **argv, int argc, void *data, void *user_data);
+ static LADSPA_Data get_port_default(t_dssi_tilde *x, int port);
+ static void MIDIbuf(int type, int chan, int param, int val, t_dssi_tilde *x);
+ 
+ 

--- NEW FILE: jutils.h ---
/* utils.h

   Free software by Richard W.E. Furse. Do with as you will. No
   warranty. */

/* patched by Jarno Seppänen, jams at cs.tut.fi, for plugin~ */

/* patched by Jamie Bullock, jamie at postlude.co.uk, for dssi~ */

#ifndef LADSPA_SDK_LOAD_PLUGIN_LIB
#define LADSPA_SDK_LOAD_PLUGIN_LIB

/*****************************************************************************/

#include "dssi.h"

/*****************************************************************************/

/* Functions in load.c: */

/* This function call takes a plugin library filename, searches for
   the library along the LADSPA_PATH, loads it with dlopen() and
   returns a plugin handle for use with findPluginDescriptor() or
   unloadLADSPAPluginLibrary(). Errors are handled by writing a
   message to stderr and calling exit(1). It is alright (although
   inefficient) to call this more than once for the same file. */
void * loadLADSPAPluginLibrary(const char * pcPluginFilename);

/* This function unloads a LADSPA plugin library. */
void unloadLADSPAPluginLibrary(void * pvLADSPAPluginLibrary);

/* This function locates a LADSPA plugin within a plugin library
   loaded with loadLADSPAPluginLibrary(). Errors are handled by
   writing a message to stderr and calling exit(1). Note that the
   plugin library filename is only included to help provide
   informative error messages. */
const LADSPA_Descriptor *
findLADSPAPluginDescriptor(void * pvLADSPAPluginLibrary,
			   const char * pcPluginLibraryFilename,
			   const char * pcPluginLabel);

/*****************************************************************************/

/* Functions in search.c: */

/* Callback function for use with LADSPAPluginSearch(). The callback
   function passes the filename (full path), a plugin handle (dlopen()
   style) and a LADSPA_DescriptorFunction (from which
   LADSPA_Descriptors can be acquired). */
typedef void LADSPAPluginSearchCallbackFunction
(const char * pcFullFilename, 
 void * pvPluginHandle,
 DSSI_Descriptor_Function fDescriptorFunction,
 void* user_data,
 int is_DSSI);

/* Search through the $(LADSPA_PATH) (or a default path) for any
   LADSPA plugin libraries. Each plugin library is tested using
   dlopen() and dlsym(,"ladspa_descriptor"). After loading each
   library, the callback function is called to process it. This
   function leaves items passed to the callback function open. */
void LADSPAPluginSearch(LADSPAPluginSearchCallbackFunction fCallbackFunction,
			void* user_data);

/*****************************************************************************/

#endif

/* EOF */





More information about the Pd-cvs mailing list