Externe Prozeduren unter Windows mit dem Freeware

Transcription

Externe Prozeduren unter Windows mit dem Freeware
Externe Prozeduren unter Windows
mit dem Freeware-Compiler MinGW
Autor: Jens-Uwe Petersen, Trivadis GmbH
DOAGNews Q1_2004
Dieses Werk ist urheberrechtlich geschützt. Die dadurch begründeten Rechte, insbesondere die der
Übersetzung, des Nachdrucks, des Vortrags, der Entnahme von Abbildungen und Tabellen, der Funksendung, der Mikroverfilmung oder der Vervielfältigung auf anderen Wegen und der Speicherung in
Datenverarbeitungsanlagen, bleiben, bei auch nur auszugsweiser Verwertung, vorbehalten. Eine Vervielfältigung dieses Werkes oder von Teilen dieses Werkes ist auch im Einzelfall nur in den Grenzen der
gesetzlichen Bestimmungen des Urheberrechtes der Bundesrepublik Deutschland vom 9. September
1965 in der jeweils geltenden Fassung zulässig. Sie ist grundsätzlich vergütungspflichtig. Zuwiderhandlungen unterliegen den Strafbestimmungen des Urheberrechtsgesetzes.
©2004
Einleitung
Es ist immer wieder ärgerlich, dass Microsoft seine Betriebssysteme im Gegensatz zu anderen
Herstellern ohne Compiler ausliefert. Das separat von Microsoft zu erwerbende VisualStudio ist
sicherlich ein sehr leistungsfähiges Produkt, aber auch sehr ressourcenintensiv (Preis,
Einarbeitung, Plattenplatz). Für jemanden, der nur gelegentlich (und „g’schwind“ wie man im
Schwäbischen sagt) ein paar Sourcen kompilieren möchte, ist das einfach zu aufwendig.
Ursprünglich hatte ich für diese Zwecke den Compiler LCC-Win32 verwendet, der aber seit
Anfang des Jahres nur noch für private Zwecke kostenlos ist. Auf der Suche nach einer
Alternative bin ich dann recht schnell auf MinGW ("Minimalistic GNU for Windows") gestossen.
MinGW basiert auf dem populären Gnu-Compiler GCC, erweitert um eine Reihe von Headerund Include-Dateien um native Windows-Applikationen erstellen zu können.
Die folgenden Beispiele gehen davon aus, dass MinGW im Verzeichnis c:\programme\MinGW
installiert wurde und ORACLE_HOME unter c:\oracle\9i liegt.
Erstes Beispiel
Als erstes versuchen wir, das mit der Datenbank mitgelieferte Beispiel im Verzeichnis
%ORACLE_HOME%\rdbms\extproc zum Laufen zu bekommen, das das Maximum zweier
Werte ermittelt.
Fügen Sie das MinGW\bin-Verzeichnis dem Suchpfad hinzu.
PATH=c:\programme\MinGW\bin;%PATH%
Um die Datei zu kompilieren auf DOS-Ebene in das Verzeichnis wechseln und den Compiler
starten. Durch den Parameter –shared wird gleich die DLL erzeugt.
cd %ORACLE_HOME%\rdbms\extproc
gcc -shared -o extern.dll extern.c
Nun muss datenbankseitig noch die dazugehörige Wrapper-Funktion „UseIt“ angelegt werden.
Dies geschieht mit dem Skript extern.sql aus dem gleichen Verzeichnis. Gleich nach dem
Anlegen wird „UseIt“ auch ausgeführt, sodass als Ausgabe in etwa folgendes erscheinen sollte:
©2004
sample@TVD9I> execute UseIt;
The maximum of 1 and 2 is 2
PL/SQL-Prozedur wurde erfolgreich abgeschlossen.
Unter Oracle9i Release 2 kann es zur Fehlermeldung ORA-28595 "Extproc agent: Invalid DLL
Path" kommen, da hier standardmäßig nur DLLs in %ORACLE_HOME%\bin (Windows) bzw.
%ORACLE_HOME%\lib (Unix) ausgeführt werden. In diesem Falle müssen Sie die
LISTENER.ORA entsprechend anpassen.
Für die Testumgebung mag es evntl. angehen die Verwendung aller DLLs erlauben:
(ENVS="EXTPROC_DLLS=ANY")
In Produktionsumgebungen sollte man aber aus Sicherheitsgründen unbedingt nur die wirklich
benötigten DLLs freigeben. Für unsere Beispiele wären dies:
(ENVS="EXTPROC_DLLS=
c:\oracle\9i\RDBMS\EXTPROC\extern.dll;c:\Programme\MinGW\Projects\callback")
Für weitere Informationen dazu siehe Metalink Note 198523.1.
Falls andere Fehler auftreten sollten, ist wahrscheinlich der Listener nicht richtig konfiguriert,
dann siehe beispielsweise Metalink Note 68061.1, das im Beispielverzeichnis enthaltene
Readme.doc oder Kapitel 10 im Application Developers Guide.
Zweites Beispiel
Als nächstes wollen wir uns einem etwas komplexeren Beispiel zuwenden, das die Callback
Möglichkeiten demonstrieren soll und unter %ORACLE_HOME%/rdbms/plsql/demo zu finden
ist. Die beiden Dateien, die uns hier interessieren, heißen extproc.sql und extproc.c
Um die Sourcen übersichtlich an einem Ort zu haben, erstellen wir im Projektverzeichnis von
MinGW ein neues Verzeichnis callback.
©2004
cd c:\programme\MinGW\projects\
mkdir callback
cd callback
copy %ORACLE_HOME%\plsql\demo\extproc.* .
Dieses Beispiel verwendet die Oracle-Library oci.dll. Da die Libraries von Microsoft nicht
kompatibel zu denen von MinGW sind, muss die Library erst konvertiert werden.
reimp c:\oracle\9i\oci\lib\msvc\oci.lib
Die erzeugte Textdatei OCI.def enthält eine Liste der enthaltenen Funktionen (und wird nicht
weiter benötigt), liboci.a ist die konvertierte Library, die am besten ins lib-Verzeichnis von
MinGW kopiert wird.
Jetzt noch schnell die DLL erzeugen:
gcc -shared -o extproc.dll extproc.c -L. -loci
-Ic:\oracle\9i\oci\include
Dann in der Datenbank die Objekte anlegen:
SQLPLUS SCOTT/TIGER
CREATE OR REPLACE LIBRARY demolib IS
'c:\programme\MinGW\projects\callback\extproc.dll';
/
@c:\programme\MinGW\projects\callback\extproc.sql
Und zu guter Letzt kann nun das Ergebnis validiert werden:
scott@TVD9I> set serveroutput on;
scott@TVD9I> execute demopack.demo_procedure;
ENAME
: ALLEN
JOB
: SALESMAN
SALARY
: 1600
COMMISSION : 300
Percent Commission : 18,75
ENAME
: MARTIN
JOB
: SALESMAN
©2004
SALARY
: 1250
COMMISSION : 1400
Percent Commission : 112
Return value from CheckEmpName : 0
old_ename value on return
: ANIL
ENAME
: 7369
HIREDATE
: 17.12.1980
Employee Experience Test Passed.
***************************************
Zusammenfassung
Es wurde gezeigt, dass es auch unter Windows ohne großen Aufwand möglich ist, DLLs zu erzeugen und als externe Prozeduren einzusetzen.
Was es für Schwierigkeiten mit windowseigenen Libraries wie z.B. kernel32.dll geben kann und
wie ‚Native Compilation’ mit MinGW eingesetzt wird, wird in weiteren Artikeln erklärt werden.
Und damit wünsche ich Ihnen fehlerfreie Kompilate und erfolgreiches „Outsourcen“ von Prozeduren....
Jens-Uwe Petersen
jens.petersen@trivadis.com
Trivadis GmbH
Max-Lang-Straße 56
70771 Leinfelden-Echterdingen
Tel: +49 711 903 63 230
Fax: +49 711 903 63 259
©2004