Langages de type Basic, pour utiliser les pilotes Mensura
Ils sont très nombreux !
DecimalBasic, FreeBasic, Gambas, BBCBasic, FNXBasic, LibertyBasic, OxygenBasic, Panoramic, PowerBasic, PureBasic, QB64, RapidQ, ThinBasic, VisualBasic.
Decimal Basic (Windows et Linux)
Ce logiciel pédagogique d'origine japonaise existe pour les trois principaux systèmes d'exploitation, Linux, Mac et Windows (http://hp.vector.co.jp/authors/VA008683/english/)
Il peut exploiter les bibliothèques dynamiques. Sous Windows, ce sont des fonctions stdcall, alors que sous Linux, ce sont des fonctions cdecl.
Sous Linux, la vieille version 6.5.12 réalisée en Kylix peut bien utiliser les bibliothèques dynamiques, ainsi que la nouvelle version 0.6.2.4 réalisée en Lazarus, mais non les versions antérieures en Lazarus.
Par défaut, on suppose que les fonctions travaillent avec des entiers (32 bits). Si on veut que le résultat soit une chaîne de caractères (pointeur de chaîne à zéro terminal), il faut que le nom de la fonction soit terminé par un signe $, qui est la marque classique des chaînes de caractères en Basic. Si on veut que la fonction ait des paramètres d'entrée et/ou un résultat de type réel (double 32 bits), il faut terminer la ligne de définition par ",FPU".
Le chargement des bibliothèques dynamiques est très simple.
FUNCTION detail$
assign "bibdyn_syst.dll","stddetail"
END FUNCTION
FUNCTION ea(n)
assign "bibdyn_syst.dll","stdea"
END FUNCTION
FUNCTION nea$(n)
assign "bibdyn_syst.dll","stdnea"
END FUNCTION
FUNCTION sb(n,valeur)
assign "bibdyn_syst.dll","stdsb"
END FUNCTION
FUNCTION nsb$(n)
assign "bibdyn_syst.dll","stdnsb"
END FUNCTION
FUNCTION eadstr$(n$)
assign "bibdyn_syst.dll","stdeadstr"
END FUNCTION
FUNCTION ead(n)
assign "bibdyn_syst.dll","stdead",FPU
END FUNCTION
FUNCTION nead$(n)
assign "bibdyn_syst.dll","stdnead"
END FUNCTION
FUNCTION eadouble(n)
assign "bibdyn_syst.dll","stdeadouble",FPU
END FUNCTION
FOR i=0 TO 10
PRINT i,nead$(i),ead(i)
NEXT i
SET WINDOW 0,100,0,100
SET POINT STYLE 6
SET LINE COLOR 4
PLOT LINES: 0,0;
FOR i=1 TO 20
PLOT LINES: i,ead(0);
WAIT DELAY 0.5
NEXT i
PRINT sb(0,1)
PRINT "Fini !"
END
FreeBasic (logiciel libre, Windows et Linux)
dim z as integer
Dim library As any ptr
Dim stdea As function (byval n As integer) As integer
Dim stdnea As function (byval n As integer) As zstring pointer
Dim stdead As function (byval n As integer) As double
Dim stdnead As function(byval n As integer) As zstring pointer
Dim stddetail As function () As zstring pointer
library = dylibload( "bibdyn" )rem pour charger la bibliothèque bibdyn.dll
If( library = 0 ) then
print "bibliothèque inchargeable !"
End If
stdea=dylibsymbol(library,"stdea")
If (stdea=0) then
print "la fonction stdea n'est pas utilisable"
End If
stdnea=dylibsymbol(library,"stdnea")
stdead = dylibsymbol(library,"stdead")
stdnead=dylibsymbol(library,"stdnead")
stddetail=dylibsymbol(library,"stddetail")
print *stddetail()
print *stdnea(1);stdea(1)
print *stdnead(1);stdead(1)
input "",z
dylibfree library
Gambas (logiciel libre pour Linux)
C'est un langage Basic pour Linux, disponible en http://gambas.sourceforge.net/fr/main.html.
Il peut appeler les bibliothèques dynamiques du système Mensurasoft.
Exemple :
' Gambas module file
EXTERN cdetail() AS Pointer IN "./libbib_expeyes_USB0"
EXTERN cead(n AS Integer) AS Float IN "./libbib_expeyes_USB0"
EXTERN cnead(n AS Integer) AS Pointer IN "./libbib_expeyes_USB0"
EXTERN csad(n AS Integer, valeur AS Float) AS Float IN "./libbib_expeyes_USB0"
PUBLIC x AS Integer
PUBLIC y AS String
PUBLIC SUB Main()
PRINT StrPtr(cdetail())
PRINT "entrez le numéro de l'entrée analogique à lire"
INPUT x
PRINT "vous avez entré :"
PRINT x
REPEAT
PRINT cead(x)
PRINT StrPtr(cnead(x))
PRINT "entrez la valeur à fixer pour la sortie analogique 2"
INPUT y
csad(2, y)
UNTIL Val(y) > 100
END
BBC Basic pour Windows
BBC Basic (http://www.bbcbasic.co.uk/bbcbasic.html) est un logiciel commercial, mais la version de démonstration est fonctionnelle, y compris pour l'emploi des bibliothèques dynamiques. Ce logiciel existe pour divers systèmes d'exploitation, plus ou moins anciens, y compris Windows, mais pas Linux (sauf avec utilisation de Wine et de la version pour Windows).
On peut utiliser les pilotes Mensurasoft sans difficultés :
PRINT "bonjour"
SYS "LoadLibrary", "bibdyn_syst_pb_mouse.dll" TO adr_bibdyn%
IF adr_bibdyn% = 0 ERROR 100, "chargement impossible du pilote"
PRINT "par la fonction :"+FN_nea$(0)
PRINT "la fonction ea : ",FN_ea(0)
INPUT a$
*BYE
END rem fin de la partie principale
DEF FN_nea$(n)
resultat$=STRING$(255," ")
SYS "GetProcAddress", adr_bibdyn%, "stdnea" TO stdnea
SYS stdnea,1 TO !^resultat$
r2$=LEFT$(resultat$,INSTR(resultat$,CHR$(0))-1)
=r2$
DEF FN_ea(n)
SYS "GetProcAddress", adr_bibdyn%, "stdea" TO stdea
SYS stdea,0 TO resultat%
=resultat%
FNXBasic (Windows)
Ce logiciel léger (http://www.fnxbasic.com/index.html) peut appeler les bibliothèques dynamiques dont les paramètres d'entrée ou de sortie sont des entiers ou des chaînes de caractères (pas de nombres réels de type "double" !). Il lui faut apparemment des fonctions déclarées stdcall. Pour utiliser les fonctions ayant des paramètres de type "double", il faudrait faire une bibliothèque dynamique adaptatrice.
Il réalise un programme exécutable assez volumineux, mais qui fonctionne sans l'environnement de développement.
declare stddetail as "stddetail" of "bibdyn.dll"
result as string:end declare
function f_stddetail as string
stddetail.execute : result=stddetail.result : end function
declare stdea as "stdea" of "bibdyn.dll"
n as integer :result as integer:end declare
function f_stdea (n as integer) as integer
stdea.n=n : stdea.execute : result=stdea.result : end function
declare stdnea as "stdnea" of "bibdyn.dll"
n as integer :result as string :end declare
function f_stdnea (n as integer) as string
stdnea.n=n : stdnea.execute: result=stdnea.result :end function
declare stdeadstr as "stdeadstr" of "bibdyn.dll"
n as string :result as string:end declare
function f_stdeadstr (n as string) as string
stdeadstr.n=n : stdeadstr.execute : result=stdeadstr.result
end function
dim i as integer
print f_stddetail()
print f_stdnea(0)
for i=1 to 10
print f_stdea(0)
sleep(500)
next i
for i=1 to 10
print val(f_stdeadstr(str$(0)))/i
next i
print "frappez une touche pour finir";
while inkey$="":wend
Liberty Basic (logiciel commercial pour Windows)
Il est téléchargeable sur http://www.libertybasic.com/.
La version simplement téléchargée, non enregistrée, peut utiliser les bibliothèques dynamiques, mais ne peut pas créer d'exécutable (et elle a quelques messages invitant à l'achat d'une version enregistrée). La version JustBasic ne permet pas d'utiliser les bibliothèques dynamiques.
print "bonjour"
open "bibdyn_syst.dll" for dll as #u
print detail$()
print titre$()
print ea(0)
print nea$(0)
print ead(0)
print nead$(0)
print sb(0,1)
print nsb$(0)
close #u
print "fini"
end
function nea$(m)
calldll #u,"stdnea",m as long, result as ulong
nea$=winstring(result)
end function
function ea(n)
calldll #u , "stdea", n as long, result as long
ea=result
end function
function ead(n)
calldll #u,"stdead",n as long, result as double
ead=result
end function
function nead$(n)
calldll #u,"stdnead",m as long, result as ulong
nead$=winstring(result)
end function
function sb(n,valeur)
calldll #u,"stdsb",n as long,valeur as long, result as long
sb=result
end function
function nsb$(n)
calldll #u,"stdnsb",m as long, result as ulong
nsb$=winstring(result)
end function
function detail$()
calldll #u, "stddetail", a as ulong
detail$= winstring(a)
end function
function titre$()
calldll #u,"stdtitre", a as ulong
titre$=winstring(a)
end function
OxygenBasic (pour Windows)
'essai de programme OxygenBasic pour lire les bibliothèques dynamiques
#File "essai_lecture_bibdyn_o2bas.exe" 'nom du fichier .exe souhaité
extern stdcall lib "bibdyn_syst_pb.dll"
declare function stdead(byval n as dword) as double
declare function stddetail as zstring
declare function stdeadouble(byval n as double) as double
declare function stdsb(byval n as dword,byval valeur as dword)
declare function stdnead (byval n as dword) as zstring
declare function stdneadouble(byval n as double) as zstring
end extern
extern cdecl lib "bibdyn_syst_pb_ANSI.dll"
declare function cead(byval n as dword) as double
declare function cdetail as zstring
declare function ceadouble(byval n as double) as double
declare function cneadouble(byval n as double) as zstring
end extern
print stdnead(0)
print stddetail
print stdneadouble(1)
print stdeadouble(1)
print cneadouble(1)
print ceadouble (1)
print stdead(0)
print stdsb(0,1);
Le programme résultant est très petit (5 ko), mais il a besoin de la bibliothèque oxygen.dll.
Panoramic (logiciel gratuit mais non libre pour Windows)
C'est un langage Basic pour Windows (http://panoramic-language.pagesperso-orange.fr/), peu puissant sur le plan de la programmation, car il ne permet pas de déclarer des fonctions, mais seulement des sous-programmes (avec les instructions label, gosub et return, ou sub et end_sub), mais il permet assez facilement d'utiliser les ressources de Windows, ainsi que les bibliothèques dynamiques. Il peut utiliser les bibliothèques dynamiques, mais uniquement avec des paramètres entiers. Il peut gérer directement les fonctions stdea, stdeb, stdsa, stdsb, et indirectement les fonctions renvoyant des chaînes de caractères. .
Lorsque le programme est au point, on peut le sauvegarder dans un fichier .exe (qui est l'interpréteur plus le programme-source).
dim i%,j% ,a% , detail$,titre$,calibration$,ea$,ead$,nead$
dll_on "bibdynsyst_delphi2016b.dll"
for j%=0 to 5 : rem affiche les entrées analogiques ea
a%=dll_call1("stdnea",j%)
ea$="":i%=0:while peek(a%+i%)>0:ea$=ea$+chr$(peek(a%+i%)):i%=i%+1:end_while
print ea$,":",dll_call1("stdea",j%)
next j%
a%=dll_call0("stddetail") : rem affiche le détail du nom
detail$="" :i%=0
while peek(a%+i%)>0:detail$=detail$+chr$(peek(a%+i%)):i%=i%+1:end_while
print detail$
a%=dll_call0("stdtitre") : rem affiche le titre
titre$="" :i%=0
while peek(a%+i%)>0:titre$=titre$+chr$(peek(a%+i%)):i%=i%+1:end_while
print titre$
a%=dll_call1("stdcalibration",a%) : rem affiche la calibration
calibration$="" :i%=0
while peek(a%+i%)>0:calibration$=calibration$+chr$(peek(a%+i%)):i%=i%+1:end_while
print calibration$
for j%=0 to 5
a%=dll_call1("stdnead",j%) :rem affiche les noms des entrées analogiques nead
nead$="" :i%=0
while peek(a%+i%)>0 :nead$=nead$+chr$(peek(a%+i%)) :i%=i%+1 :end_while
print nead$
next j%
for j%=0 to 5 : rem affiche les entrées analogiques ead
a%=dll_call1("stdeadintstr",j%)
ead$="" :i%=0
while peek(a%+i%)>0 :ead$=ead$+chr$(peek(a%+i%)) :i%=i%+1 :end_while
print str$(val(ead$))
next j%
rem a%=dll_call2("stdsb",3,1) rem commande la sortie binaire
print "fin du programme"
dll_off
end
PowerBasic (Windows)
Les deux versions Classic PowerBASIC for Windows et Classic PowerBASIC Console Compiler permettent d'utiliser les bibliothèques dynamiques, mais il faut qu'elles aient une fonction ou procédure pour l'entrée dans la DLL.
Le code ci-dessous est pour la version « Console Compiler » :
#COMPILE EXE
MACRO nomdll2="bibdynsyst_delphi_dllmain.dll"
DECLARE FUNCTION stdead SDECL LIB nomdll2 ALIAS "stdead" (BYVAL param1 AS INTEGER) AS DOUBLE
DECLARE FUNCTION cead CDECL LIB nomdll2 ALIAS "cead" (BYVAL param1 AS INTEGER) AS DOUBLE
DECLARE FUNCTION stdnead SDECL LIB nomdll2 ALIAS "stdnead" (BYVAL param1 AS INTEGER) AS DWORD
DECLARE FUNCTION cnead CDECL LIB nomdll2 ALIAS "cnead" (BYVAL param1 AS INTEGER) AS DWORD
DECLARE FUNCTION stddetail SDECL LIB nomdll2 ALIAS "stddetail" AS DWORD
DECLARE FUNCTION cdetail CDECL LIB nomdll2 ALIAS "cdetail" AS DWORD
FUNCTION PBMAIN () AS LONG
GLOBAL adressechaine AS ASCIIZ PTR
adressechaine=stdnead(0):PRINT "stdnead(0) : "+@adressechaine+" -> "+STR$(stdead(0))
adressechaine=cnead(0):PRINT "cnead(0) : "+@adressechaine+" -> "+STR$(cead(0))
STDIN LINE ch$
END FUNCTION
PureBasic (logiciel non libre, Windows et Linux)
Comme pour beaucoup de langages, il faut d’abord ouvrir la bibliothèque par OpenLibrary.
Ensuite, on peut tester l’existence d’une fonction dans la bibliothèque par GetFunction, mais ce n’est pas obligatoire.
Lorsqu’on veut utiliser une fonction de type stdcall (nom commençant par std), on l’appelle par CallFunction (Windows). Lorsqu'on utilise une fonction de type cdecl (nom commençant par c), on l'appelle par CallCFunction.
Les fonctions qui renvoient un nombre entier sont utilisables sans difficultés car CallFunction renvoie directement la valeur numérique correspondante.
L’utilisation des fonctions qui renvoient une chaîne est un peu plus délicate. L’appel de CallFunction renvoie l’adresse de la chaîne en question, et il faut aller lire cette adresse par la fonction PeekS, qui renvoie la valeur de la chaîne se trouvant à l’endroit indiqué.
Les nombres réels ont aussi besoin d'instructions particulières, avec l'emploi de "prototypes". Si la fonction doit renvoyer un nombre réel, on commence par déclarer un "prototype" d'une telle fonction, puis on déclare une variable d'un tel type. Ensuite, on affecte à cette variable la fonction de la DLL par l'instruction getfunction.
A la fin, en principe, on ferme la bibliothèque par CloseLibrary.
nomdll$="bibdyn.dll"
Global string .s
Procedure .s nead(n .c)
string=PeekS(CallFunction(0,"stdnead",n))
ProcedureReturn(string)
EndProcedure
Prototype.d protoead(n.l)
Global eadbis .protoead
Procedure .d ead(n.l)
eadbis=GetFunction(0,"stdead")
ProcedureReturn(eadbis(n))
EndProcedure
OpenConsole()
If OpenLibrary(0,nomdll$)
Print(nead(1)+" "+StrD(ead(1),2))
PrintN("")
CloseLibrary(0)
Else
Print("problème !")
EndIf
Input()
CloseConsole()
Pour connaître la liste des fonctions d'une bibliothèque dynamique, on peut teste le programme suivant :
oFichier$ = OpenFileRequester("Choisissez une bibliothèque dynamique à examiner", "", "bibdyn *.dll|*.dll", 0)
OpenConsole()
PrintN("nom du fichier : "+oFichier$)
numbib=OpenLibrary(#PB_Any ,oFichier$)
PrintN("numéro de la bibliothèque : "+Str(numbib))
If numbib<>0
PrintN("la bibliothèque est ouverte")
PrintN(Str(CountLibraryFunctions(numbib)))
ExamineLibraryFunctions(numbib)
While NextLibraryFunction()<>0
Print(LibraryFunctionName())
Print(" // "):PrintN(Str(LibraryFunctionAddress()))
Wend
Else
PrintN("la bibliothèque n'est pas ouverte")
EndIf
CloseLibrary(numbib)
Input()
QB64 (logiciel libre pour Windows et Linux)
(Adresse de téléchargement : http://www.qb64.net/)
PRINT "bonjour"
DECLARE DYNAMIC LIBRARY "bibdyn_syst_pb_ANSI"
FUNCTION stdead# ALIAS stdead (BYVAL n AS LONG)
FUNCTION stdnead$ ALIAS stdnead (BYVAL n AS LONG)
FUNCTION stdsb& ALIAS stdsb (BYVAL n AS LONG, BYVAL valeur AS LONG)
FUNCTION stdnsb$ ALIAS stdnsb (BYVAL n AS LONG)
FUNCTION stddetail$ ALIAS stddetail ()
FUNCTION cead# ALIAS cead (BYVAL n AS LONG)
END DECLARE
PRINT stdnead(0)
PRINT stdead(0)
PRINT stdnsb(0)
PRINT stdsb(0, 1)
PRINT stddetail
PRINT cead(0)
Contrairement à d'autres langages Basic, il ne faut pas déclarer le type du résultat de la fonction à la fin de la ligne, mais à la suite du nom de la fonction, sous forme d'un caractère indiquant le type de ce résultat ($ pour une chaîne de caractères, & pour un entier, # pour un double)
RapidQ (Windows et Linux)
Site de téléchargement : http://www.telefonica.net/web2/rq/WiYu/Download.htm
C'est un langage Basic semi compilé datant de 2000 (et qui n'est plus mis à jour) : il fait un fichier exécutable contenant le source et son interpréteur. Le programme ci-dessous fait un exécutable d'environ 300 ko.
print "bonjour"
DECLARE FUNCTION stdead LIB "bibdyn_syst_pb_ANSI.dll" ALIAS "stdead" (n AS LONG) AS double
declare function stdnead lib "bibdyn_syst_pb_ANSI.dll" alias "stdnead" (n as long) as string
declare function stddetail lib "bibdyn_syst_pb_ANSI.dll" alias "stddetail" () as string
print stddetail()
print stdead(0)
print stdnead(0)
INPUT "Appuyez sur entrée ", a
Il peut faire des programmes en mode console, comme ci-dessus, mais aussi des programmes en mode graphique, avec un éditeur visuel assez simple qui permet de faire des programmes avec fenêtres et boutons (comme Delphi, Lazarus, C++Builder, etc).
C'est donc un logiciel pratique pour faire de petits programmes sans prétention.
ThinBasic (Windows)
C'est un langage interprété, fonctionnant uniquement sous Windows, qui permet d'appeler assez simplement les bibliothèques dynamiques.
Bien qu'étant un langage interprété, il permet de faire des fichiers exécutables, car il peut empaqueter le programme-source, l'interpréteur, et les diverses bibliothèques dynamiques nécessaires à son fonctionnement dans un seul fichier exécutable.
Uses "Console"
Declare Function stddetail Lib "bibdyn_syst_pb_ANSI.DLL" Alias "stddetail" () As DWord
Declare Function stdead Lib "bibdyn_syst_pb_ANSI.dll" Alias "stdead" (ByVal n As Integer) As Double
Declare Function stdnead Lib "bibdyn_syst_pb_ANSI.dll" Alias "stdnead" (ByVal n As Integer) As DWord
Function mondetail () As Asciiz
Function=Peek$(Asciiz,stddetail())
End Function
Function monnead(ByVal n As Integer) As Asciiz
Function = Peek$(Asciiz,stdnead(n))
End Function
PrintL "bonjour, "
PrintL stdead(0)
Sleep(2000)
PrintL stdead(0)
PrintL mondetail()
PrintL monnead(0)
PrintL "appuyez sur q"
Do
Loop Until Console_InKey ="q"
VisualBasic (logiciel Microsoft, pour Windows
Le langage de programmation « VisualBasic » existe depuis 1991, et a évolué en même temps que les systèmes d'exploitation Microsoft. Les indications ci-dessous ont été testées sur Microsoft VisualBasic 10 Express.
Declare Function stdtitre Lib "bibdynsyst.dll" () As String
Declare Function stddetail Lib "bibdynsyst.dll" () As String
Declare Function stdead Lib "bibdynsyst.dll" (ByVal n As Int32) As Double
Declare Function stdnead Lib "bibdynsyst.dll" (ByVal n As Int32) As String
Declare Function stdsad Lib "bibdynsyst.dll" (ByVal n As Int32, ByVal valeur As Double) As Double
Declare Function stdnsad Lib "bibdynsyst.dll" (ByVal n As Int32) As String
Declare Function stdeb Lib "bibdynsyst.dll" (ByVal n As Int32) As Int32
Declare Function stdneb Lib "bibdynsyst.dll" (ByVal n As Int32) As String
Declare Function stdsb Lib "bibdynsyst.dll" (ByVal n As Int32, ByVal valeur As Int32) As Int32
Declare Function stdnsb Lib "bibdynsyst.dll" (ByVal n As Int32) As String
Sub Main()
Console.WriteLine("début du programme")
Console.WriteLine(stdtitre())
Console.WriteLine(stddetail())
For i = 0 To 10
If Len(stdnead(i)) > 0 Then
Console.WriteLine("nead(" & Str(i) & ")-->" & stdnead(i) & " = " & Str(stdead(i)))
End If
Next
For i = 0 To 10
If Len(stdnsad(i)) > 0 Then
Console.WriteLine("nsad(" & Str(i) & ")-->" & stdnsad(i))
End If
Next
For i = 0 To 10
If Len(stdneb(i)) > 0 Then
Console.WriteLine("neb(" & Str(i) & ")-->" & stdneb(i) & " = " & Str(stdeb(i)))
End If
Next
For i = 0 To 10
If Len(stdnsb(i)) > 0 Then
Console.WriteLine("nsb(" & Str(i) & ")-->" & stdnsb(i))
End If
Next
stdsb(3, 1) : Sleep(1000) : stdsb(3, 0)
Console.WriteLine(" fin du programme")
Console.ReadLine()
End Sub
Dernière modification le 10/03/2018