8.3 intersci

Il existe dans Scilab un utilitaire appelé intersci qui permet de générer un fichier d'interface à partir d'un fichier de description de la fonction à interfacer. intersci ne permet pas toute la souplesse d'une interface écrite à la main en C mais peut être utilisé pour certaines interfaces simples ou comme base de départ. Dans une version récente intersci génère du code compatible avec celui que nous avons décrit dans les paragraphes précédent.

La documentation complète de intersci se trouve dans le répertoire doc de Scilab et de nombreux exemples sont décrits dans le répertoire

SCI/examples/intersci-examples-so.

Nous nous limitons ici à un exemple simple, interfacer la fonction ext1c :


#include "machine.h"

int F2C(ext1c)(n, a, b, c)
     int *n;
     double *a, *b, *c;
{   
  int k;
  for (k = 0; k < *n; ++k) 
      c[k] = a[k] + b[k];
  return(0);
}

On notera que cette fonction n'a que des arguments de type pointeurs et que le nom de la fonction est encapsulé dans un appel de macros C2F(ext1c) (c'est une limitation de intersci qui doit interfacer à la fois des fonctions C et Fortran). Pour interfacer cette fonction il faut écrire un fichier de description disons ex01fi.desc (le suffixe .desc est imposé) :


ext1c	a b 
a 	vector	m
b 	vector	m
c	vector  m 

ext1c   m a b c 
m	integer 
a	double 
b	double 
c	double 

out	sequence	c
***********************

Le texte écrit dans le fichier indique que l'on va créer une fonction Scilab [c]=ext1c(a,b) où a,b et c sont trois vecteurs de même taille. La première ligne décrit les arguments d'entrée et la dernière les arguments de sortie. La fonction ext1c pour s'exécuter doit appeler la fonction C ou Fortran C2F(ext1c) avec quatre arguments : un pointeur d'entier qui contiendra la taille des vecteurs et trois pointeurs de ``double'' qui permettrons d'accéder aux valeurs contenues dans les vecteurs Scilab a,b et c. La place nécessaire pour stocker c est réservée dans l'interface avant l'appel de la fonction C C2F(ext1c).

En exécutant intersci au moyen de la commande :

 
bin/intersci-n ex01fi
on va générer l'interface ex01fi.c et un fichier de type ``builder'' (comme au paragraphe 8.2) ex01fi_builder.sce.


#include "stack-c.h"
/******************************************
 * SCILAB function : ext1c, fin = 1
 ******************************************/

int intsext1c(fname)
   char *fname;
{
 int m1,n1,l1,mn1,m2,n2,l2,mn2,un=1,mn3,l3;
 CheckRhs(2,2);
 CheckLhs(1,1);
 /*  checking variable a */
 GetRhsVar(1,"d",&m1,&n1,&l1);
 CheckVector(1,m1,n1);
 mn1=m1*n1;
 /*  checking variable b */
 GetRhsVar(2,"d",&m2,&n2,&l2);
 CheckVector(2,m2,n2);
 mn2=m2*n2;
 /* cross variable size checking */
 CheckDimProp(1,2,m1*n1 != m2*n2);
 CreateVar(3,"d",(un=1,&un),(mn3=n1,&mn3),&l3);
 C2F(ext1c)(&mn1,stk(l1),stk(l2),stk(l3));
 LhsVar(1)= 3;
 return 0;
}

On se reportera au répertoire

SCI/examples/intersci-examples-so

où le même exemple est repris de façon plus complète. L'ensemble des opérations à effectuer étant récapitulées dans le fichier ex01.sce :


// appel de intersci-n au moyen d'un Makefile
G_make('ex01fi.c','ex01fi.c');
// execution du builder cr\'ee par intersci-n
files = ['ex01fi.o' , 'ex01c.o'];
libs  = [] ;
exec('ex01fi_builder.sce');
// execution du loader 
exec loader.sce 
// test de la fonction 
a=[1,2,3];b=[4,5,6];
c=ext1c(a,b);
if norm(c-(a+b)) > %eps then pause,end