Dies ist eine alte Version des Dokuments!
Inhaltsverzeichnis
Tokiwa-Basic-Compiler
Der Tokiwa-Basic-Compiler (TBC) ist eigentlich nicht neu, stammt aber aus Japan und hatte lange Zeit nur eine japanische Dokumentation, so dass er außerhalb Japans relativ wenig Verbreitung fand.
Der Compiler wurde - vermutlich Anfang der 1990er Jahre - von Dr. Genji Okada entwickelt. Die bislang letzte Version (5.55e) stammt vom Dezember 2000 und bekam vom Autor eine, wenn auch sehr knappe, englischsprachige Beschreibung spendiert, was den Einsatz natürlich erleichtert, Neben der Freeware-Version, die man z.B. unter http://www.franksteinberg.de/psprach.htm#TokiwaBas herunterladen kann, gab es wohl noch eine kommerzielle Variante, die aber nirgends mehr auffindbar zu sein scheint.
Inzwischen existiert auch eine deutschsprachige Version des Handbuchs, die eine Übersetzung der englischen Version mit einer Reihe von Ergänzungen und erklärenden Anmerkungen darstellt. Sie ist HIER abrufbar.
Besonderheiten von Tokiwa-Basic
Tokiwa-Basic nimmt sich (so der Autor) Standard-Basic als Ausgangspunkt und erweitert es um nützliche Eigenschaften:
- keine Angabe von Zeilennummern notwendig
- explizit destlegbare Datentypen für Variablen (integer, real, character)
- erweiterte Arrays (mir DIMX definierbar)
- benutzerdefinierte benannte Unterprogramme und Funktionen mit formalen Parameterlisten
- lokale Variablen in Unterprogrammen und Funktionen
- integrierte Gleitpunkt-Arithmetik
- integrierter Assembler für maschinennahe Routinen
Der Tokiwa-Basic-Cpmpiler ist tatsächlich ein „echter“ Compiler. Es wird also direkt Maschinencode erzeugt und folglich kein Runtime-Modul benötigt. Der Overhead ist dabei recht klein - er liegt bei etwa 400 Bytes, die für die Initialisierung benötigt werden. Werden Real-Zahlen verwendet und somit die Gleitpunkt-Arithmetik benötigt, kommen noch einmal ca. 3 KB dazu, was im Vergleich zu den 20KB, die z.B. die Gleitpunkt-Emulation von Turbo-C braucht, sehr sparsam ist.
Der Compiler kann wahlweise Programme im EXE- oder COM-Format erzeugen, wobei sich beide Varianten in ihrem Aufbau praktisch nicht unterscheiden. Die EXE-Dateien verwenden initial das Tiny-Speichermodell und belegen, wie die COM-Dateien, den gesamten freien Speicher. Die Initialisierung der Segmentregister erfolgt in beiden Varianten auf gleiche Weise zur Laufzeit.
Tokiwa-Basic erlaubt das Anlegen von Bibliotheken (Quelltext), die in Programme per MERGE-Anweisung integriert werden können. Dies ermöglicht die einfache Wiederverwendung benutzerdefinierter Funktionen und Unterprogramme.
Tokiwa-Basic auf dem Portfolio
Der Compiler ist nur etwa 36KB groß und passt damit bequem auf eine CCM-Karte. Weder der Compiler noch die von ihm erzeugten Programme benötigen Funktionen, die auf dem Portfolio nicht verfügbar sind. Bei der Übersetzung werden außerdem keine temporären Dateien erzeugt, die bei wenig Platz zu Problemen führen könnten.
Allerdings gibt es ein anderes Problem, das den Einsatz des Compilers auf einem Standard-Pofo verhindert: Er gönnt sich zu seinem Code zwei Datensegmente von jeweils 64K sowie einen Stack von 18K und benötigt damit mindestens ca. 180K RAM, was also eine Speichererweiterung erfordert.
Auch die erzeugten Programme gehen - für Portfolio-Verhältnisse - recht großzügig mit dem Speicher um. Sie verlangen normalerweise mindestens 69K RAM, was darauf zurückzuführen ist, dass standardmäßig ein Datensegment von 64K und ein Stack von 4K angelegt werden. Mit Hilfe von Compiler-Optionen und einem kleinen Patch-Programm lässt sich der Bedarf aber bis auf etwa 10K reduzieren. Damit sind mit dem TBC erzeugte Programme dann bestens für den Einsatz auf dem Portfolio geeignet. Der integrierte Assembler ermöglicht sehr einfach den direkten Zugriff auf Systemfunktionen.
Für die Pofo-Programmierung mit Tokiwa-Basic gibt es HIER eine erweiterte Distribution des Compilers, die folgende zusätzliche Dateien enthält:
- tbc_de.pdf: die deutschprachige Dokumentation
- tbcptch.com: Binary des Patch-Programms
- tbcptch.bas: Quellcode des Patch-Programms (ja, in Tokiwa-Basic geschrieben
)
- mshrink.ltb: Bibliothek zur Verkleinerung des verwendeten Speicherblocks
- alloc.ltb: Bibliothek zur Verwaltung von dynamischen Speicherbereichen
- strings.ltb: Bibliothek mit zusätzlichen String-Funktionen
- files.ltb: Bibliothek mit erweiterten Funktionen zum Umgang mit Binärdateien
- dirs.ltb: Bibliothek mit Verzeichnisfunktionen
- test31.bas: Testprogramm für mshrink.ltb und alloc.ltb
- strings.bas: Testprogramm für strings.ltb
Verwenden von TBCPTCH
Der Zweck von TBCPTCH besteht darin, den beim Programmstart benötigten Speicherplatz eines mit TBC übersetzten Programms zu reduzieren. Voraussetzung dafür ist es, die Maximalgröße des Datenbereichs zu reduzieren. Dies erfolgt mit Hilfe der Compiler-Optionen /wl (Obergrenze des Offsets im Datensegment), /wp (Maximalwert des Stack-Pointers) und /ws (Stack-Größe in Bytes).
Dabei gelten folgende Standardeinstellungen: /wl=&fff8 /wp=&fffe /ws=4096
Allerdings kann man diese Werte nicht beliebig verkleinern - folgendes ist zu beachten:
Das Datensegment braucht eine Mindestgröße, die sich etwa wie folgt abschätzen lässt:
Anzahl aller globalen Integer-Variablen * 2 + Anzahl aller globalen Real-Variablen * 5 + Anzahl aller globalen String (Character)-Variablen * 2 + Summe der Längen aller globalen String-Variablen + Summe der Längen aller mit DIM definierten Felder Länge = Anzahl Elemente * Elementgröße) + Anzahl der mit DINX definierten Felder * 2 + Summe der Puffergrößen (Optionen /wt, /wi und /wb; Standard: 514 Bytes) + mindestens 1K für Stringoperationen und sonstigen Verwaltungs-Kleinkram = Minimalwert für /wl
Das Stacksegment liegt um die durch /ws gegebene Anzahl von Bytes oberhalb des Beginns des Datensegments. Damit sich Stack und Datenbereich nicht gegenseitig überschreiben können, darf der Wert von /wp nicht kleiner als der von /wl sein.
Die benötigte Stackgröße ergibt sich vor allem aus der Anzahl der in Unterprogrammen und Funktionen verwendeten Argumente und lokalen Variablen sowie der maximalen Tiefe rekursiver Aufrufe. Jedes Argument benötigt 2 Bytes auf dem Stäck, zusätzlich werden für jeden Unterprogramm-/Funktionsaufruf 2 Bytes für die Return-Adresse benötigt. Darüber hinaus fallen für jede lokale Integer-Variable 2 bytes an. Lokale Real- und String-Variablen werden dagegen im Datensegment angelegt und sind für dessen Größe zu berücksichtigen.
Für die Einstellung der Optionen bietet es sich an, in der ersten Zeile des Programm-Quelltextes die options-Anweisung zu verwenden.
z.B. options /wl=&1ff8 /wp=&1ffe /ws=1024
Nach dem Übersetzen mit TBC.COM kann nun TBCPTCH.COM mit folgender Syntax aufgerufen werden:
TBCPTCH file[.COM] [file2]
Dabei ist file der Name (ggf. mit Pfad) des zu patchenden Programms. Fehlt die Extension, so wird als Standard COM angenommen. Das optionale Argument file2 bezeichnet den Namen der Ausgabedatei. Ist das Argument angegeben, so wird eine Kopie von file angelegt und der Patch darauf ausgeführt; fehlt es, wird file selbst modifiziert. TBCPTCH erkennt den Dateityp an der Extension. Lautet sie „EXE“, wird eine EXE-Datei angenommen, andernfalls eine Datei im COM-Format.
Achtung: Der Patch bewirkt, dass man Programme auch bei weniger als 69K freiem Speicher starten kann.
Falls in einem Programm mit DIMX definierte (erweiterte) Arrays verwendet werden, ist dies allerdings
keine Garantie dafür, dass es auch läuft. Der Grund: Solche Felder werden oberhalb des Stacks angelegt
und bei der Prüfung des freien Speichers beim Programmstart nicht berücksichtigt. Auf der sicheren Seite
ist man also nur, wenn man keine DIMX-Felder verwendet oder weiß, dass der Speicher trotzdem reicht .
Speicherbereich zur Laufzeit verkleinern
Sowohl die EXE- als auch die COM-Versionen (die sowieso) der mit TBC erzeugten Programme belegen beim Start den größtmöglichen Speicherblock (was oft dem gesamten freien Speicher entspricht). Die Folge davon ist, dass man weder die Möglichkeit hat, vom System weiteren Speicher dynamisch anzufordern noch weitere Programme als Kindprozesse zu starten. Weil im Normalfall aber nicht der gesamte Speicher benötigt wird, kann man den Speicherblock des Programms zur Laufzeit verkleinern.
Dabei ist der Ablauf folgender:
- ermittle die Adresse des eigenen PSP (= Startadresse des Speicherblocks)
- ermittle die höchstmögliche verwendete Adresse (Ende des als letztes definierten DIMX-Feldes)
- rechne die Gesamtgröße in Paragraphen aus
- verkleinere den Speicherbereich mit der DOS-Funktion 4AH (Set Block)
Da die Größe von Arrays leider nirgends abfragbar ist, bietet es sich an, zum Bestimmen der Endadresse mit DIMX ein Dummy-Feld anzulegen, das hinter allen anderen Feldern definiert wird. Seine Startadresse entspricht damit der Adresse des ersten freien Segments hinter dem Programm und die Blockgröße in Paragraphen ist einfach diese Adresse, vermindert um die PSP-Segmentadresse.
Weil der beschriebene Ablauf eigentlich immer gleich ist, gibt es in der erweiterten Distribution eine kleine Bibliothek, die man einfach mit MERGE hinter der letzten Felddefinition ins Programm einfügt und die dann die Verkleinerung automatisch erledigt. Ein Beispiel für die Verwendung findet sich im schon erwähnten Testprogramm test31.bas.
Bibliotheken
Tokiwa-Basic unterstützt mit der MERGE-Anweisung das Einbinden von Quelltextbibliotheken in ein Programm. Das erlaubt es grundsätzlich, wiederverwendbare Programmteile (typischerweise Unterprogramme und Funktionen) zu erstellen und bei Bedarf darauf zurückzugreifen.
Mit Hilfe von Bibliotheken lassen sich vor allem auch wichtige Funktionen „nachrüsten“, für die keine Standardfunktionen vorhanden sind.
Eine wesentliche Einschränkung ergibt sich allerdings daraus, dass die MERGE-Anweisung keine verschachtelten Bibliotheken zulässt (MERGE darf nicht in einer Bibliothek verwendet werden), was es z.B. unmöglich macht, an zentraler Stelle Konstantendefinitionen zusammenzufassen. Wenn Bibliotheken voneinander abhängen, lässt sich dies nicht im Quellcode ausdrücken - vielmehr muss man es wissen bzw. entsprechend dokumentieren. Wenn - wie bei unserem Pofo - der Platz recht knapp ist, kann es außerdem ein Problem darstellen, dass mit dem Einbinden einer Bibliothek deren gesamter Inhalt mit ins Programm aufgenommen wird - auch wen man womöglich nur eine einzige Funktion aufruft. Deshalb kann es in manchen Fällen von Vorteil sein, nur einzelne Abschnitte aus einer Bibliothek direkt in Programm hinein zu kopieren, anstatt die Bibliothek mit MERGE einzubinden.
Nachfolgend wird - ohne Anspruch auf Vollständigkeit - der Inhalt der einzelnen Bibliotheken als Kurzreferenz dargestellt. Diese Referenz soll bei der Verwendung helfen, ist aber keine umfassende Dokumentation. Es empfiehlt sich also in jedem Fall, auch die Kommentare in den Bibliotheken selbst und ggf. deren Quellen zu lesen.
Weil bei Tokiwa-Basic benutzerdefinierte Funktionen, die einen Integer-Wert zurückliefern uber das Schlüsselwort SUBROUTINE beschrieben werden, ist die Unterscheidung zwischen Unterprogrammen und Funktionen etwas verwirrend. Nachfolgend wird die Unterscheidung so vorgenommen, dass Unterprogramme keinen Rückgabewert haben (entsprechend etwa Prozeduren in Pascal), während Funktionen einen Wert zurückgeben.
Bibliothek CONTIME.LIB
Diese Bibliothek gehört zur Original-Distribution von Tokiwa-Basic und beinhaltet eine etwas eigenartige Mischung von Funktionen zur Konsoleneingabe, Lesen von Datum und Uhrzeit sowie Zeichenkettenbehandlung.
Enthaltene Unterprogramme/Funktionen:
conin
Die Funktion liest ein einzelnes Zeichen von der Konsole. Ein Bildschirmecho erfolgt dabei nicht. Ist kein Zeichen im Tastaturpuffer, so wird auf die Eingabe eines Zeichens gewartet.
Argumente: keine
Rückgabewert: ASCII-Code des gelesenen Zeichens
up_conin
Fie Funktion verhält sich wie conin
, eingegebene Buchstaben werden jedoch in Großbuchstaben umgewandelt.
Argumente: keine
Rückgabewert: ASCII-Code des gelesenen Zeichens
to_upper(str)
Das Unterprogramm wandelt alle Kleinbuchstaben der übergebenen Zeichenkette in Großbuchstaben um.
Argument: zu modifizierende Zeichenkette
Rückgabewert: keiner
time
Das Unterprogramm trägt in die globale Variable time$ die aktuelle Uhrzeit in der Form hh:mm:ss
ein.
Argumente: keine
Rückgabewert: keiner
Nach dem Aufruf steht die Uhrzeit in der Variablen time$.
Achtung: Ein Programm, dass das Unterprogramm verwendet, sollte selbst keine Variable time$ zu einem anderen Zweck anlegen.
date
Das Unterprogramm trägt in die globale Variable date$ die aktuelle Uhrzeit in der Form yy-mm-dd
ein.
Argumente: keine
Rückgabewert: keiner
Nach dem Aufruf steht das Datum in der Variablen date$.
Achtung: Ein Programm, dass das Unterprogramm verwendet, sollte selbt keine Variable date$ zu einem anderen Zweck anlegen.
Bibliothek MSHRINK.LTB
Diese Bibliothek stellt keine Funktionen im eigentlichen Sinne bereit. Ihre Aufgabe besteht darin, den vom aktuellen Programm belegten Speicher auf die tatsächlich benötigte Größe zu beschränken, um so die dynamische Anforderung von Speicher zu ermöglichen.
Dazu muss MSHRINK.LTB hinter dem letzten mit dimx
definierten rweiterten Feld (oder am Programmstart, falls es kein solches Feld gibt, eingebunden werden.
Mit dem Einbinden von MSHRINK.LTB sind außerdem folgende globale Variablen definiert:
- integer psp__seg : Segmentadresse des eigenen PSP
- integer nxt__mcb : Segmentadresse des MCB für den nächsten Speicherbereich hinter dem Programm
- integer my__size : Größe des vom Programm belegten Speicherblocks in Paragraphen
Bibliothek ALLOC.LTB
Die Bibliothek stellt Funktionen zur dynamischen Speicheranforderung über DOS-Systemaufrufe bereit.
Da Tokiwa-Basic-Programme standardmäßig den gesamten verfügbaren Speicher belegen, ist die Verwendung dynamischen Speichers nur dann möglich, wenn der belegte Speicher vorher (mit Hilfe der Bibliothek MSHRING.LTB) redutiert wurde.
Alle Funktionen dieser Bibliothek legen im Falle eines Ausführungsfehlers den DOS-Fehlercode in der globalen (Integer-) Variablen ALLOC_ERROR
ab.
Darüber hinaus werden folgende Konstanten definiert:
- DOS-Funktionen
- _dos_malloc &48 (allocate memory block)
- _dos_mfree &49 (free memory block)
- _dos_mresize &4A (resize memory block)
- _dos_setmstrat &5801 (set memory strategy)
- _dos_getmstrat &5800 (get memory strategy)
- Strategie-Konstanten für _dos_setmstrat
- _mstrat_first 0 (allocate first block available)
- _mstrat_best 1 (allocate best sized menory block)
- _mstrat_last 2 (allocate last block available)
Enthaltene Unterprogramme/Funktionen:
allocMem(parSize)
Die Funktion fordert einen Speicherbereich der angegebenen Größe vom System an.
Argument: Größe des Speicherbereichs in Paragraphen
Rückgabewert: Segmentadresse des Bereichs bei Erfolg, sonst 0
Hinweis: Ein mit allocMem
angelegter Speicherbereich sollte stets mit freeMem
wieder freigegeben werden.
freeMem(handle)
Die Funktion gibt einen mit allocMem
angeforderten Speicherbereich wieder frei.
Argument: Handle (Segmentadresse) des freizugebenden Speicherbereichs
Rückgabewert: 0 bei Erfolg, sonst Fehlernummer
resizeMem(handle, parSize)
Die Funktion ändert die Größe eines mit allocMem
angelegten Speicherbereichs.
Argumente:
- handle: Handle (Segmentadresse) des Speicherbereichs
- parSize: neue Größe in Paragraphen
Rückgabewert: 0 bei Erfolg, sonst Fehlernummer
getMemAvail
Die Funktion ermittelt die Größe des größten noch freien Speicherbereichs.
Argumente: keine
Rückgabewert: Größe des größten freien Speicherblocks in Paragraphen
getAllocStrategy
Die Funktion gibt die aktuelle Einstellung für die Strategie der Speichervergabe zurück.
Argumente: keine
Rückgabewert: Speichervergabe-Strategie (_mstrat_first
, _mstrat_best
oder _mstrat_last
)
setAllocStrategy(strategy)
Das Unterprogramm legt die Einstellung für die Strategie der Speichervergabe fest.
Argument: Speichervergabe-Strategie (_mstrat_first
, _mstrat_best
oder _mstrat_last
)
Rückgabewert: keiner
Bibliothek STRINGS.LTB
Die Bibliothek enthält eine Reihe von Funktionen zur erweiterten und schnelleren Verarbeitung von Zeichenketten.
Enthaltene Unterprogramme/Funktionen:
getCmdLine(resloc)
Die Funktion speichert die Kommandozeile (Programmpfad mit übergebenen Argumenten) in einer String-Variablen.
Argument: Adresse der Puffervariablen, in der die Kommandozeile abgelegt werden soll.
Rückgabewert: Offset-Adresse des ersten Zeichens in der Puffervariablen
Hinweise:
- Der Ergebnispuffer (adressiert durch resloc) muss eine String-Variable im Datensegment sein, deren Adresse sich mit Hilfe der LOC-Funktion bestimmen lässt.
- Der Rückgabewert kann direkt an die
strTok
-Funktion als Argumentstr
übergeben werden.
memCpy(dest,src,nbytes)
Die Funktion kopiert einen Datenbereich im Speicher unter Nutzung von NEAR-Adressen.
Argumente:
- dest: Adresse des Zielpuffers
- osrc: Adresse der Datenquelle
- nbytes: Länge des zu kopierenden Speicherbereichs in Bytes
Rückgabewert: Adresse des Zielpuffers
Hinweise:
- Sowohl der Zielpuffer als auch die Datenquelle müssen vollständig im Datensegment liegen.
- Der Zielpuffer nuss mindestens eine kapazität von
nbytes
Bytes haben. - Ein Überlappen der Bereiche von Quelle und Zielpuffer ist zulässig, wenn die Zieladresse unterhalb der Quelladresse liegt - nicht umgekehrt!
- Das
nbytes
-Argument wird als vorzeichenloser Integer-Wert interpretiert. - Achtung: Es wird keine Überprüfung auf Offset-Überlauf durchgeführt!
memCpyFar(odest,sdest,osrc,ssrc,nbytes)
Die Funktion kopiert einen Datenbereich im Speicher unter Nutzung von FAR-Adressen.
Argumente:
- odest: Offset-Adresse des Zielpuffers
- sdest: Segment-Adresse des Zielpuffers
- osrc: Offset-Adresse der Datenquelle
- ssrc: Segment-Adresse der Datenquelle
- nbytes: Länge des zu kopierenden Speicherbereichs in Bytes
Rückgabewert: Offset-Adresse des Zielpuffers; die Segment-Adresse wird im Register DX abgelegt
Hinweise:
- Der Zielpuffer nuss mindestens eine kapazität von
nbytes
Bytes haben. - Ein Überlappen der Bereiche von Quelle und Zielpuffer ist zulässig, wenn die Zieladresse unterhalb der Quelladresse liegt - nicht umgekehrt!
- Das
nbytes
-Argument wird als vorzeichenloser Integer-Wert interpretiert, es können also theoretisch bis zu 64 KBytes auf einmal kopiert werden. - Achtung: Es wird weder eine Normalisierung der Zeiger noch eine Überprüfung auf Offset-Überlauf durchgeführt!
strChrPos(str, c)
Die Funktion ermittelt die Position eines Zeichens innerhalb einer Zeichenkette.
Argumente:
- str: Zeichenkette, in der nach einem Zeichen gesucht werden soll
- c: Zeichen, nach dem gesucht werden soll
Rückgabewert: Position des ersten Auftretens des Zeichens in str; -1, wenn das Zeichen nicht gefunden wurde
strCmp(str1,str2)
Die Funktion führt einen byteweisen Vergleich zweier Zeichenketten durch.
Argumente:
- str1: linker Operand
- str2: rechter Operand
Rückgabewert: -1 für str1 < str2
, 1 für str1 > str2
, 0 für str1 = str2
strDelete(str, pos, length)
Die Funktion löscht Zeichen aus einer Zeichenkette.
Argumente:
- str: Zeichenkette, aus der Zeichen gelöscht werden sollen
- pos: Indexposition des ersten zu löschenden Zeichens
- length: maximale Anzahl zu löschender Zeichen
Rückgabewert: Anzahl tatsächlich gelöschter Zeichen
Hinweise:
- Bei einem negativen Wert von
length
werden alle Zeichen abpos
bis zum Ende gelöscht. - Das Löschen erfolgt „in place“, d.h. es wird kein neuer String erzeugt, sondern die übergebene Zeichenkette selbst modifiziert.
strDeleteChr(str, chr, pos, length)
Die Funktion löscht alle Vorkommen des angegebenen Zeichens aus einer Zeichenkette oder Teilzeichenkette.
Argumente:
- str: Zeichenkette, aus der Zeichen gelöscht werden sollen
- chr: Zeichencode (integer) des Zeichens, das gelöscht werden soll
- pos: Start-Indexposition des Bereichs, in dem das Zeichen gelöscht werden soll
- length: Maximallänge des Bereichs, in dem das zeichen gelöscht werden soll
Rückgabewert: Anzahl tatsächlich gelöschter Zeichen
Hinweise:
- Bei einem negativen Wert von
length
recht der Löschbereich vonpos
bis zum Ende der Zichenkette. - Das Löschen erfolgt „in place“, d.h. es wird kein neuer String erzeugt, sondern die übergebene Zeichenkette selbst modifiziert.
strInsert(str,pos,insertion)
Die Funktion fügt eine Zeichenkette an der angegebenen Position in eine andere Zeichenkette ein.
Argumente:
- str: Adresse der String-Variablen, die als Ziel der Einfügeoperation dient
- pos: Indexposition, an der die Einfügung vorgenommen werden soll
- insertion: einzufügende Zeichenkette
Rückgabewert: Adresse des ersten Zeichens der Ziel-Zeichenkette nach dem Einfügen
Hinweise:
- Die Adresse der Ziel-Zeichenkette (Argument
str
) kann mit derLOC
-Funktion ermittelt werden. - Wenn der Wert von
pos
kleiner als Null ist oder die Länge vonstr
übersteigt, wirdinsertion
an das Ende vonstr
angehängt.
strLen(str)
Die Funktion bestimmt die Länge der übergebenen Zeichenkette.
Argument: Zeichenkette, deren Länge werden soll
Rückgabewert: Anzahl der Zeichen in str
Hinweis: Die Funktion verhält sich wie die Standardfunktion LEN, akzeptiert jedoch als Argument auch statt einer Stringvariablen oder -konstanten auch einen Integer-Wert, der den Offset des ersten Zeichens eines Strings im Datensegment angibt.
strLower(str)
Das Unterprogramm wandelt alle Großbuchstaben (A-Z) der übergebenen Zeichenkette in Kleinbuchstaben um.
Argument: Zeichenkette, die modifiziert werden soll.
Rückgabewert: keiner
Hinweis: Die Umwandlung erfolgt „in place“, d.h. es wird kein neuer String erzeugt, sondern die übergebene Zeichenkette selbst modifiziert.
strReplace(strloc,search,rep)
Die Funktion ersetzt alle Vorkommen einer Teilzeichenkette durch eine andere Zeichenkette.
Argumente:
- strloc: Adresse der String-Variablen, die als Ziel der Operation dient
- search: zu ersetzende Teilzeichenkette
- rep: Ersatzzeichenkette
Rückgabewert: Anzahl der durchgeführten Ersetzungen
Hinweise:
- Die Adresse der Ziel-Zeichenkette (Argument
strloc
) kann mit derLOC
-Funktion ermittelt werden. - Wenn die Länge von
rep
nicht größer ist als die vonsearch
, so wird die Ersetzung „in place“ durchgeführt.
strReplaceChr(str,search,rep)
Die Funktion ersetzt alle Vorkommen eines Zeichens innerhalb einer Zeichenkette durch ein anderes Zeichen.
Argumente:
- str: Zeichenkette, die modifiziert werden soll
- search: Zeichencode des zu ersetzenden Zeichens (integer)
- rep: Zeichencode des Ersatzzeichens (integer)
Rückgabewert: Anzahl der durchgeführten Ersetzungen
Hinweis: Das Ersetzen erfolgt „in place“, d.h. es wird kein neuer String erzeugt, sondern die übergebene Zeichenkette selbst modifiziert.
strStrPos(str, search)
Die Funktion sucht innerhalb einer Zeichenkette nach einer Teilzeichenkette.
Argumente:
- str: Zeichenkette, in der gesucht werden soll
- search: zu suchende Teilzeichenkette
Rückgabewert: Position von search
in str
bei Erfolg, sonst -1
strTok(str,resloc,delimit)
Die Funktion erlaubt das schrittweise Zerlegen einer Zeichenkette in Token. Dazu wird die Zeichenkette nach dem ersten Vorkommen eines Trennzeichens durchsucht. Enthält sie ein Trennzeichen, wird die Teilzeichenkezze vor dem Trennzeichen im Ergebnispuffer abgelegt; ist kein Trennzeichen enthalten, wird als Ergebnis die ganze Zeichenkette (als einzelnes Token gespeichert. Argumente:
- str: Zeichenkette, die zerlegt werden soll
- resloc: Adresse der Puffervariablen, in der das Ergebnis-Token abgelegt werden soll
- delimit: Liste der zum Zerlegen verwendeten Trennzeichen (als Zeichenkette)
Rückgabewert:
Startadresse des hinter dem gefundenen Trennzeichen verleibenden Restes der Zeichen, falls ein Trennzeichen gefunden
wurde; andernfalls 0.
Hinweise:
- Der Ergebnispuffer (adressiert durch resloc) muss eine String-Variable im Datensegment sein.
- Wenn der Rückgabewert der Funktion nicht 0 ist, so kann dieser Wert als Argument str für einen nachfolgenden Aufruf der Funktion verwendet werden um ein weiters Token abzuspalten.
Beispiel:
txt$ = "This text consists of multiple words." buf$ = "" delimit$ = " ." integer s, bloc bloc = loc(buf$); s = call_StrTok(txt$,bloc,delimit$) while s <> 0 print buf$ s = call_StrTok(s,bloc,delimit$) wend end
strUpper(str)
Das Unterprogramm wandelt alle Kleinbuchstaben (a-z) der übergebenen Zeichenkette in Großbuchstaben um.
Argument: Zeichenkette, die modifiziert werden soll.
Rückgabewert: keiner
Hinweis: Die Umwandlung erfolgt „in place“, d.h. es wird kein neuer String erzeugt, sondern die übergebene Zeichenkette selbst modifiziert.
Bibliothek FILES.LTB
Diese Bibliothek stellt zusätzliche Funktionen zum Umgang mit Binärdateien bereit, wobei Handle-basierte DOS-Aufrufe verwendet werden.
Alle Funktionen dieser Bibliothek legen im Falle eines Ausführungsfehlers den DOS-Fehlercode in der globalen (Integer-) Variablen FILE_ERROR ab.
Die Funktionen fseek und fseek_f belegen außerdem eine globale Variable seek_pos
mit der Dateiposition. Diese Position ist 32 Bit breit und wird auf ein zweielementiges Integer-Feld abgebildet. Dabei beinhaltet seek_pos(0)
den niederwertigen und seek_pos(1)
den höherwertigen Teil des Wertes.
Darüber hinaus werden folgende Konstanten definiert:
- Dateiattribute (Bitflags, OR-kombinierbar)
- _fattr_r 1 (read only)
- _fattr_h 2 (hidden)
- _fattr_s 4 (system)
- _fattr_l 8 (volume label)
- _fattr_a 16 (archive flag)
- Datei-Fehlercodes
- _fsuccess 0
- _ferr_invalid_func 1
- _ferr_no_file 2
- _ferr_no_path 3
- _ferr_no_handle 4
- _ferr_acc_denied 5
- _ferr_inv_handle 6
- Modi zum Öffnen einer Datei
- _fopen_r 0 (open for read)
- _fopen_w 1 (open for write)
- _fopen_rw 2 (open for read and write)
- _ fopen_a 3 (open for append)
- Modi für Seek-Funktionen
- _fseek_start 0 (seek from start)
- _fseek_rel 1 (seek relative to current position)
- _fseek_end 2 (seek from end)
- DOS-Funktionsnummern
- _dos_fcreate &3c (create file)
- _dos_fopen &3d (open file or device)
- _dos_fclose &3e (close file)
- _dos_fread &3f (read from file/device)
- _dos_fwrite &40 (write to file/device)
- _dos_fseek &42 (file seek)
Enthaltene Unterprogramme/Funktionen
fopen(fileName, mode)
Die Funktion öffnet eine Datei oder ein Gerät (Zeichentreiber).
Argumente:
- fileName: Name (ggf. mit Pfad) der zu öffnenden Datei
- mode: Modus, in dem die Datei geöffnet werden soll (_fopen_r, _fopen_rw, _fopen_w oder _fopen_a)
Rückgabewert: Bei Erfolg Datei-Handle (Kanalnummer), sonst -1.
Hinweis: Eine mit fopen
geöffnete Datei sollte stets mit fclose
explizit geschlossen werden.
fcreate(fileName, attributes)
Die Funktion legt eine neue Datei an oder schneidet eine bereits existierende auf die Länge Null ab.
Argumente:
- fileName: Name (ggf. mit Pfad) der anzulegenden Datei
- attributes: Bitmaske als OR-Verknüpfung der Dateiattribute (_fattr_?)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Die Funktion kann nicht mit dem Attribut _fattr_l (Volume Label) verwendet werden.
- Die Anwendung auf eine existierende schreibgeschützte Datei führt zu einem Fehler.
- Nach erfolgreicher Ausführung ist die angelegte Datei geschlossen und muss mit
fopen
für den Zugriff explizit geöffnet werden.
fclose(fhandle)
Die Funktion schließt eine zuvor mit fopen
geöffnete Datei.
Argument: Handle (Kanalnummer) der zu schließenden Datei.
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
fread_f(fhandle, nbytes, bufoffs, bufseg)
Die Funktion liest Daten aus einer geöffneten (Binär-)Datei in einen per FAR-Zeiger adressierten Puffer.
Argumente:
- fhandle: Handle (Kanalnummer) einer geöffneten Datei oder eines Geräts
- nbytes: maximale Anzahl der zu lesenden Bytes
- bufoffs: Offset-Adresse des Datenpuffers
- bufseg: Segment-Adresse des Datenpuffers
Rückgabewert: Anzahl der gelesenen Bytes (0 bei Fehler)
Hinweise:
nbytes
wird als vorzeichenloser Integer-Wert repräsentiert. Somit können theoretisch Datenblöcke bis zu 64 KBytes gelesen werden.- Auch der Rückgabewert ist streng genommen vorzeichenlos. Bei Blockgrößen über 32 KBytes sollte er deshalb nicht als negativer Wert fehlinterpretiert werden.
- Das aufrufende Programm ist dafür verantwortlich, einen hinreichend großen Datenpuffer bereitzustellen. Die Funktion selbst kann dessen tatsächliche Größe nicht überprüfen und überschreibt schlimmstenfalls andere Speicherbereiche.
- Die Funktion schließt die Datei nach Ausführung nicht, sondern verschiebt lediglich deren internen Datenzeiger um die Anzahl der gelesenen Bytes. Sie kann also mehrfach hintereinander aufgerufen werden, um den Inhalt einer Datei stückweise zu lesen. Das Dateiende ist erreicht (die Datei vollständig gelesen), wenn der Rückgabewert kleiner als
nbytes
ist.
fread(fhandle, nbytes, buf)
Die Funktion liest Daten aus einer geöffneten (Binär-)Datei in einen per NEAR-Zeiger adressierten Puffer innerhalb des Datensegments.
Argumente:
- fhandle: Handle (Kanalnummer) einer geöffneten Datei oder eines Geräts
- nbytes: maximale Anzahl der zu lesenden Bytes
- buf: Adresse des Datenpuffers
Rückgabewert: Anzahl der gelesenen Bytes (0 bei Fehler)
Hinweise:
nbytes
wird als vorzeichenloser Integer-Wert repräsentiert. Somit können theoretisch Datenblöcke von mehr als 32 KBytes gelesen werden.- Auch der Rückgabewert ist streng genommen vorzeichenlos. Bei Blockgrößen über 32 KBytes sollte er deshalb nicht als negativer Wert fehlinterpretiert werden.
- Das aufrufende Programm ist dafür verantwortlich, einen hinreichend großen Datenpuffer bereitzustellen. Die Funktion selbst kann dessen tatsächliche Größe nicht überprüfen und überschreibt schlimmstenfalls andere Speicherbereiche.
- Die Funktion schließt die Datei nach Ausführung nicht, sondern verschiebt lediglich deren internen Datenzeiger um die Anzahl der gelesenen Bytes. Sie kann also mehrfach hintereinander aufgerufen werden, um den Inhalt einer Datei stückweise zu lesen. Das Dateiende ist erreicht (die Datei vollständig gelesen), wenn der Rückgabewert kleiner als
nbytes
ist.
fwrite_f(fhandle,nbytes,bufoffs,bufseg)
Die Funktion schreibt Daten aus einem per FAR-Zeiger adressierten Puffer in eine geöffnete (Binär-)Datei.
Argumente:
- fhandle: Handle (Kanalnummer) einer geöffneten Datei oder eines Geräts
- nbytes: maximale Anzahl der zu schreibenden Bytes
- bufoffs: Offset-Adresse des Datenpuffers
- bufseg: Segment-Adresse des Datenpuffers
Rückgabewert: Anzahl der geschriebenen Bytes (0 bei Fehler)
Hinweise:
nbytes
wird als vorzeichenloser Integer-Wert repräsentiert. Somit können theoretisch Datenblöcke bis zu 64 KBytes geschriebenn werden.- Auch der Rückgabewert ist streng genommen vorzeichenlos. Bei Blockgrößen über 32 KBytes sollte er deshalb nicht als negativer Wert fehlinterpretiert werden.
- Die Funktion schließt die Datei nach Ausführung nicht, sondern verschiebt lediglich deren internen Datenzeiger um die Anzahl der geschriebenen Bytes. Sie kann also mehrfach hintereinander aufgerufen werden, um den Inhalt einer Datei stückweise zu schreiben.
fwrite(fhandle,nbytes,buf)
Die Funktion schreibt Daten aus einem per NEAR-Zeiger adressierten Puffer in eine geöffnete (Binär-)Datei.
Argumente:
- fhandle: Handle (Kanalnummer) einer geöffneten Datei oder eines Geräts
- nbytes: maximale Anzahl der zu schreibenden Bytes
- buf: Adresse des Datenpuffers (Offset im Datensegment)
Rückgabewert: Anzahl der geschriebenen Bytes (0 bei Fehler)
Hinweise:
nbytes
wird als vorzeichenloser Integer-Wert repräsentiert. Somit können theoretisch Datenblöcke von mehr als 32 KBytes geschriebenn werden.- Auch der Rückgabewert ist streng genommen vorzeichenlos. Bei Blockgrößen über 32 KBytes sollte er deshalb nicht als negativer Wert fehlinterpretiert werden.
- Die Funktion schließt die Datei nach Ausführung nicht, sondern verschiebt lediglich deren internen Datenzeiger um die Anzahl der geschriebenen Bytes. Sie kann also mehrfach hintereinander aufgerufen werden, um den Inhalt einer Datei stückweise zu schreiben.
fseek(fhandle,smode,offset)
Die Funktion ändert die Lese- bzw. Schreibposition in einer göffneten Datei.
Argumente:
- fhandle: Handle (Kanalnummer) einer geöffneten Datei
- smode: Modus
- _fseek_start - Positionierung relativ zum Dateianfang
- _fseek_rel - Positionierung relativ zur aktuellen Position
- _fseek_end - Positionierung relativ zum Dateiende
- offset: Anzahl von Bytes, um die die Position geändert werden soll
Rückgebewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der Wert von
offset
ist ein vorzeichenbehafteter Integer. Somit kann man die Position um maximal 32K ändern. - Im Modus
_fseek_end
wird die Position vom Dateiende umoffset
Bytes in Richtung Dateianfang verschoben. In den anderen Modi erfolgt die Verschiebung in Richtung Dateiende (bei einem positiven Offset, sonst umgekehrt). - Es erfolgt keine Prüfung, ob die Position über die Dateigrenze hinaus verschoben wird. Bei einer Verschiebung vor den Dateianfang können bei nachfolgenden Schreibzugriffen Fehler in der Dateistruktur entstehen. Bei einer Verschiebung hinter das Dateiende wird die Datei vergrößert und es entsteht ein Bereich, der mit zufälligem Inhalt gefüllt ist.
- Wird für
offset=0
angegeben, so bewirktsmode=_fseek_st
art eine Positionierung auf den Dateianfang,smode=_fseek_end
eine Positionierung auf das Dateiende undsmode=_fseek_rel
keine ositionsänderung.
- Bei erfolgreicher Ausführung wird die aktuelle Dateiposition in der globalen Variablen
seek_pos
abgelegt, wobeiseek_pos(0)
den niederwertigen undseek_pos(1)
den höherwertigen Teil enthält (die Dateiposition ist ein 32-Bit-Integer). Somit kann man die Angabe vonoffset=0
auch nutzen, um die aktuelle Position (mitsmode=_fseek_rel
) bzw. die Dateilänge (mitsmode=_fseek_end
) zu ermitteln.
fseek_f(fhandle,smode,offslow,offshigh)
Die Funktion ändert die Lese- bzw. Schreibposition in einer göffneten Datei, wobei ein 32-Bit-Offset verwendet wird.
Argumente:
- fhandle: Handle (Kanalnummer) einer geöffneten Datei
- smode: Modus
- _fseek_start - Positionierung relativ zum Dateianfang
- _fseek_rel - Positionierung relativ zur aktuellen Position
- _fseek_end - Positionierung relativ zum Dateiende
- offslow: Anzahl von Bytes, um die die Position geändert werden soll (niederwertiger Teil)
- offshigh: Anzahl von Bytes, um die die Position geändert werden soll (höherwertiger Teil)
Rückgebewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Die Offset-Wert ist ein vorzeichenbehafteter 32-Bit-Integer. Somit kann man die Positionsverschiebunf theoretisch maximal +/-2^31 betragen. Weil Tokiwa-Basic keinen integralen 32-Bit-Integer kennt, ist eine Aufteilung auf zwei Argumente nötig.
- Bis auf den größeren möglichen Offset entspricht das Verhalten der Funktion dem für
fseek
beschriebenen.
Bibliothek DIRS.LTB
Diese Bibliothek stellt Unterprogramme und Funktionen für DOS-basierte Dateisystem- und Verzeichnisoperationen zur Verfügung.
Für die Datei-Suchfunktionen wird eine globale Puffervariable dos_s_rec
von 44 Bytes Länge angelegt.
Außerdem definiert die Bibliothel folgende globale Konstanten:
- DOS-Funktionsnummern
- _dos_set_drive &e (set current drive)
- _dos_get_drive &19 (get current drive)
- _dos_set_dta &1a (set DTA address)
- _dos_get_dta &2f (get DTA address)
- _dos_mkdir &39 (make directory)
- _dos_rmdir &3a (remove directory)
- _dos_chdir &3b (change directory)
- _dos_del_file &41 (delete file)
- _dos_get_dir &47 (get current directory)
- _dos_find_first &4e (find first)
- _dos_find_next &4f (find next)
- _dos_get_attr &4300 (get file attributes)
- _dos_set_attr &4301 (set file attributes)
- _dos_rename_fd &56 (rename file or directory)
- Fehlercodes (als Rückgebewerte von Funktionen)
- _dsuccess 0 (kein Fehler)
- _derr_no_file 2
- _derr_no_path 3
- _derr_acc_denied 5
- _derr_inv_drive 15
- _derr_cant_delete 16
- _derr_cant_move 17
- _derr_no_entries 18
- Dateiattribute (Bitflags, OR-verknüpfbar)
- _dfattr_r 1 (read only)
- _dfattr_h 2 (hidden)
- _dfattr_s 4 (system)
- _dfattr_l 8 (volume label)
- _dfattr_a 16 (archive flag)
- Byte-Offsets der Elemente in
dos_s_rec
- _dos_srec_attr 21
- _dos_srec_time 22
- _dos_srec_date 24
- _dos_srec_sizelo 26
- _dos_srec_sizehi 28
- _dos_srec_name 30
- Dateiattribut-Flags zur Verwendung mit findFirst
- _sattr_hidden 2
- _sattr_system 4
- _sattr_vlabel 8
- _sattr_dir &10
- _sattr_all &3f
Unterprogramme und Funktionen
setCurrentDrive(drv)
Die Funktion legt das aktive Laufwerk fest.
Argument: Laufwerk, das aktiv gesetzt werden soll (angegeben als Index oder laufwerksbuchstabe)
Rückgabewert: aktives Laufwerk
Hinweise:
- Der Argumenrwert ist eine Zahl (Laufwerksindex, wobei 0 für Laufwerk A, 1 für B usw. steht) oder ein Groß- bzw. Kleinbuchstabe (Laufwerksbuchstabe)
- Der Rückgabewert ist eine Zahl, wenn als Argument ein Index (also ein Wert zwischen 0 und 25) angegeben wurde,oder ein Groß- bzw. Kleinbuchstabe, wenn das Argument als Buchstabe angegeben wurde.
- Der Aufrufer kann den Erfolg der Operation prüfen, indem er den Rückgabewert mit dem übergebenen Argumentwert vergleicht.
getCurrentDrive
Die Funktion ermittelt das aktuell aktive Laufwerk.
Argumente: keine
Rückgabewert: aktives Laufwerk (als Großbuchstabe)
mkDir(path)
Die Funktion legt ein Verzeichnis entsprechend dem angegebenen Pfad an.
Argument: Name des anzulegenden Verzeichnisses (relativer oder absoluter Pfad)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der als Argument übergebene Pfad kann absolut oder relativ zum aktuellen Verzeichnis angegeben werden.
- Eine absolute Pfadangebe kann eine Laufwerksangabe enthalten, die nicht mit dem aktuellen (aktiven) Laufwerk übereinstimmen muss.
- Es lässt sich (wie beim mkdir-Befehl von DOS) nur ein einzelnes Verzeichnis anlegen, d.h. alle übergeordneten Verzeichnisse müssen bereits existieren.
rmDir(path)
Die Funktion löscht ein (leeres) Verzeichnis.
Argument: Name des zu löschenden Verzeichnisses (relativer oder absoluter Pfad)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der als Argument übergebene Pfad kann absolut oder relativ zum aktuellen Verzeichnis angegeben werden.
- Eine absolute Pfadangebe kann eine Laufwerksangabe enthalten, die nicht mit dem aktuellen (aktiven) Laufwerk übereinstimmen muss.
- Die Funktion kann (wie der rmdir-Befehl von DOS) nur einzelne Verzeichnisse, keine vollständigen Pfade löschen.
- Das zu löschende Verzeichnis muss leer sein und darf nicht schreibgeschützt sein.
delFile(fpath)
Die Funktion löscht die angegebene Datei.
Argument: Name der zu löschenden Datei(relativer oder absoluter Pfad)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der als Argument übergebene Pfad kann absolut oder relativ zum aktuellen Verzeichnis angegeben werden.
- Eine absolute Pfadangebe kann eine Laufwerksangabe enthalten, die nicht mit dem aktuellen (aktiven) Laufwerk übereinstimmen muss.
- Im Unterschied zum DOS-Befehl del kann nur eine einzelne datei gelöscht wwrden; Wildchards (* oder ?) in der Pfadangabe sind nicht zulässig.
- Die zu löschende Datei darf nicht schreibgeschützt und nicht geöffnet sein.
setCwd(path)
Die Funktion setzt das aktuelle Arbeitsverzeichnis.
Argument: Name des Verzeichnisses, das als Arbeitsverzeichnis gesetzt werden soll (relativer oder absoluter Verzeichnispfad)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der als Argument übergebene Pfad kann absolut oder relativ zum aktuellen Verzeichnis angegeben werden.
- Falls der Verzeichnispfad eine Laufwerksangabe enthält, wird auch das aktive Laufwerk entsprechend gesetzt.
getCwd(pathloc)
Die Funktion bestimmt das aktuelle Arbeitsverzeichnis.
Argument: Adresse der Puffervariablen (String), in der das aktuelle Arbeitsverzeichnis abgelegt werden soll.
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Bei erfolgreicher Ausführung wird der vollständige Pfad des aktuellen Arbeitsverzeichnisses in der Puffervariablen abgelegt.
- Als Parameter muss die Adresse (bestimmbar mit der LOC-Funktion) des Puffers angegeben werden.
setDTA(offs, seg)
Das Unterprogramm verlegt das DTA auf die angegebene Adresse.
Argumente:
- offs: Offset-Adresse des DTA
- seg: Segment-Adresse des DTA
Rückgabewert: keiner
Hinweis:
Das DTA (Disk Transfer Area) ist ein Pufferbereich, der von den „altem“ (CP/M-kompatiblen) DOS-Dateifunktionen sowie
von den Suchfunktionen (find first / find next) verwendete wird. Standardmäßig befindet sich dieser Bereich ab Offset
80H im PSP und teilt sich damit den Speicherbereich mit den auf der Kommandozeile übergebenen Parametern. Das temporäre Verlegen
dieses Bereichs kann sinnvoll sein, um beim Verwenden der genannten Funktionen die Parameter nicht zu überschreiben.
Die Funktionen findFirst und findNext dieser Bibliothek verlegen das DTA
temporär und beeinträchtigen so die Kommandozeilenparameter nicht.
getDTA(locoffs, locseg)
Das Unterprogramm bestimmt die aktuell gesetzte DTA-Adresse.
Argumente:
- locoffs: Adresse der Puffervariablen (Integer) für die Offset-Adresse des DTA
- locseg: Adresse der Puffervariablen (Integer) für die Segment-Adresse des DTA
findFirst(pattern,attr,resloc)
Die Funktion sucht den ersten Verzeichniseintrag, der dem angegebenen Suchmuster entspricht.
Argumente:
- pattern: Suchmuster (Zeichenkette); das Suchmuster kann eine relative oder absolute Pfadangabe (ggf. auch mit
Laufwerk) sowie im Dateinamens- und Erweiterungsteil die unter DOS üblichen Wildcards (* byw. ?) enthalten.
- attr: Attribute für die Suche; OR-Kombination der
_sattr_xx
-Flags (siehe oben). Standardmäßig werden „normale“ Dateien gefunden, mit Hilfe der Flags lassen sich zusätzlich Verzeichnisse, Volume-Labels und versteckte Dateien in die Suche einbeziehen. - resloc: Adresse des Ergebnispuffers (Zeichenkettenvariable)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der Ergebnispuffer (
resloc
) muss im Datensegment liegen, die Adresse kann mit der LOC-Funktion bestimmt werden. - Bei Erfolg (Rückgabewert 0, d.h. ein passender Eintrag wurde gefunden) wird der Eintragsname mit ggf. vorhandener Erweiterung, jedoch ohne Verzeichnispfad, in der durch
resloc
adressierten Variablen abgelegt.
findNext(resloc)
Die Funktion sucht den nächsten Verzeichniseintrag, der dem beim vorangegangenen Aufruf von findFirst angegebenen Suchmuster entspricht.
Argument: Adresse des Ergebnispuffers (Zeichenkettenvariable)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Der Ergebnispuffer (
resloc
) muss im Datensegment liegen, die Adresse kann mit der LOC-Funktion bestimmt werden. - Bei Erfolg (Rückgabewert 0, d.h. ein passender Eintrag wurde gefunden) wird der Eintragsname mit ggf. vorhandener Erweiterung,
jedoch ohne Verzeichnispfad, in der durch resloc
adressierten Variablen abgelegt.
getFileSize
Die Funktion bestimmt die Größe der zuletzt mit findFirst
bzw findNext
gefundenen Datei.
Argumente: keine
Rückgabewert: Größe der Datei in Bytes
Hinweise:
- Die Dateigröße wird aus der Pseudo-Struktur
_dos_s_rec
ausgelesen. Deshalb muss vor dem Aufruf der Funktion ein Aufruf vonfindFirst
bzw.findNext
erfolgt sein. - Weil der Rückgabewert vom Real-Typ ist, kann er wegen der begrenzten Genauigkeit der Zahldarstellung mit einem Fehler behaftet sein, falls die Dateigröße 1 GB überschreitet.
getFileAttr(fname)
Die Funktion bestimmt die Attribute einer Datei oder eines anderen Verzeichniseintrags.
Argument:
Name der Datei- bzw. des Eintrags, für die/den die Attribute bestimmt werden sollen. Der
Name kann eine absolute oder relative Pfadangabe beinhalten.
Rückgabewert: Bitset der Attribute (OR-Kombination aus _sattr_xx
-Flags)
Hinweis:
Im Falle eines Fehlers (z.B. wenn die Datei nicht existiert) ist der Rückgabewert
größer als 255. Der um 256 verminderte Rückgabewert entspricht dann dem Fehlercode.
setFileAttr(fname,fattr)
Die Funktion legt die Attribute des angegebenen Verzeichniseintrags fest.
Argumente:
- fname: Name der Datei- bzw. des Eintrags, für die/den die Attribute festgelegt werden sollen. Der Name kann eine absolute oder relative Pfadangabe beinhalten.
- fattr: Bitset der Attribute (OR-Kombination aus
_sattr_xx
-Flags)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweise:
- Das Setzen von Attributen ist nicht beliebig möglich. Welche Attribute gesetzt werden können, ist vom Typ des Verzeichniseintrags abhängig.
- Vorsicht: Es ist mit dieser Funktion grundsätzlich möglich Dateieinträge in Vezeichniseinträge umzuwandeln (und umgekehrt). Ein Anwendungsprogramm sollte dies abfangen um Fehler im Dateisystem zu verhindern.
renDirEntry(name,newname)
Die Funktion benennt einen Verzeichniseintrag um.
Argumente:
- name: Bisheriger Name des Verzeichniseintrags (ggf. einschließlich Pfadangabe)
- newname: Neuer Name des Verzeichniseintrags (ggf. einschließlich Pfadangabe)
Rückgabewert: 0 bei Erfolg, sonst Fehlercode
Hinweis:
Die Funktion führt nur das Umbenennen eines Eintrags in der Verzeichnisstruktur durch, kein „echtes“
Kopieren oder Verschieben einer Datei. Deshalb dürfen name
und newname
nicht auf unterschiedliche Laufwerke verweisen.