1076 lines
51 KiB
Plaintext
1076 lines
51 KiB
Plaintext
|
|
|||
|
EINF<EFBFBD>HRUNG
|
|||
|
===========
|
|||
|
|
|||
|
LDmicro erzeugt einen systemspezifischen Code f<>r einige Microchip PIC16
|
|||
|
und Atmel AVR Mikroprozessoren. <20>blicherweise wird die Software f<>r diese
|
|||
|
Prozessoren in Programmsprachen, wie Assembler, C oder BASIC geschrieben.
|
|||
|
Ein Programm, welches in einer dieser Sprachen abgefasst ist, enth<74>lt
|
|||
|
eine Anweisungsliste. Auch sind die diese Sprachen sehr leistungsf<73>hig
|
|||
|
und besonders gut geeignet f<>r die Architektur dieser Prozessoren,
|
|||
|
welche diese Anweisungsliste intern abarbeiten.
|
|||
|
|
|||
|
Programme f<>r speicherprogrammierbare Steuerungen (SPS) andererseits,
|
|||
|
werden oftmals im Kontaktplan (KOP = ladder logic) geschrieben.
|
|||
|
Ein einfaches Programm, k<>nnte wie folgt aussehen:
|
|||
|
|
|||
|
|| ||
|
|||
|
|| Xbutton1 Tdon Rchatter Yred ||
|
|||
|
1 ||-------]/[---------[TON 1.000 s]-+-------]/[--------------( )-------||
|
|||
|
|| | ||
|
|||
|
|| Xbutton2 Tdof | ||
|
|||
|
||-------]/[---------[TOF 2.000 s]-+ ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| Rchatter Ton Tneu Rchatter ||
|
|||
|
2 ||-------]/[---------[TON 1.000 s]----[TOF 1.000 s]---------( )-------||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
||------[END]---------------------------------------------------------||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|
|||
|
(TON ist eine Anzugsverz<72>gerung, TOF eine Abfallverz<72>gerung.
|
|||
|
Die --] [-- Anweisungen bedeuten Eing<6E>nge, die sich <20>hnlich, wie Relais-
|
|||
|
kontakte verhalten. Die --( )-- Anweisungen bedeuten Ausg<73>nge, die sich
|
|||
|
<20>hnlich, wie Relaisspulen verhalten. Viele gute Bezugsquellen werden f<>r
|
|||
|
KOP im Internet oder sonst wo angeboten; Einzelheiten zu dieser speziellen
|
|||
|
Ausf<73>hrung werden weiter unten angegeben.)
|
|||
|
|
|||
|
Einige Unterschiede sind jedoch offensichtlich:
|
|||
|
|
|||
|
* Das Programm wird in einem grafischen Format dargestellt
|
|||
|
und nicht mit einer aus Anweisungen bestehenden Textliste. Viele
|
|||
|
Anwender werden dies zun<75>chst als besser verst<73>ndlich auffassen.
|
|||
|
|
|||
|
* Diese Programme erscheinen wie einfachste Schaltpl<70>ne, mit
|
|||
|
Relaiskontakten (Eing<6E>ngen) and Spulen (Ausg<73>ngen). Dies ist recht
|
|||
|
intuitiv f<>r Programmierer, die <20>ber Kenntnisse der Theorie von
|
|||
|
Elektroschaltpl<70>nen verf<72>gen.
|
|||
|
|
|||
|
* Der <20>ladder logic compiler<65> <20>bernimmt was wo berechnet wird.
|
|||
|
Es ist nicht notwendig einen Code zu schreiben, um zu errechnen, wann
|
|||
|
der Status (Zustand) der Ausg<73>nge neu bestimmt werden muss, z.B. auf
|
|||
|
Grund einer <20>nderung eines Eingangs oder Timers. Auch braucht man die
|
|||
|
Reihenfolge der Berechnungen nicht anzugeben; die SPS-Hilfsprogramme
|
|||
|
<20>bernehmen dies.
|
|||
|
|
|||
|
LDmicro kompiliert <20>ladder logic<69> (KOP) in PIC16- oder AVR-Code.
|
|||
|
Die folgenden Prozessoren werden unterst<73>tzt:
|
|||
|
|
|||
|
* PIC16F877
|
|||
|
* PIC16F628
|
|||
|
* PIC16F876 (ungetestet)
|
|||
|
* PIC16F88 (ungetestet)
|
|||
|
* PIC16F819 (ungetestet)
|
|||
|
* PIC16F887 (ungetestet)
|
|||
|
* PIC16F886 (ungetestet)
|
|||
|
* ATmega8 (ungetestet)
|
|||
|
* ATmega16 (ungetestet)
|
|||
|
* ATmega32 (ungetestet)
|
|||
|
* ATmega128
|
|||
|
* ATmega64
|
|||
|
* ATmega162 (ungetestet)
|
|||
|
|
|||
|
Es w<>re einfach noch weitere AVR- oder PIC16-Prozessoren zu unterst<73>tzen,
|
|||
|
aber ich habe keine M<>glichkeit diese zu testen. Falls Sie einen
|
|||
|
bestimmten ben<65>tigen, so nehmen Sie Kontakt mit mir auf und ich werde
|
|||
|
sehen, was ich tun kann.
|
|||
|
|
|||
|
Mit LDmicro k<>nnen Sie ein Kontaktplan-Programm zeichnen bzw. entwickeln.
|
|||
|
Auch k<>nnen Sie dies in Realzeit mit Ihrem Computer simulieren. Wenn
|
|||
|
Sie dann <20>berzeugt sind, dass Ihr Programm korrekt ist, so k<>nnen
|
|||
|
Sie die Pins, entsprechend dem Programm als Ein- oder Ausg<73>nge, dem
|
|||
|
Mikroprozessor zuweisen. Nach der Zuweisung der Pins k<>nnen Sie den PIC-
|
|||
|
oder AVR-Code f<>r Ihr Programm kompilieren. Der Compiler erzeugt eine
|
|||
|
Hex-Datei, mit dem Sie dann Ihren Mikroprozessor programmieren. Dies
|
|||
|
ist mit jedem PIC/AVR-Programmer m<>glich.
|
|||
|
|
|||
|
LDmicro wurde entworfen, um in etwa mit den meisten kommerziellen
|
|||
|
SPS-Systemen <20>hnlich zu sein. Es gibt einige Ausnahmen und viele Dinge
|
|||
|
sind ohnehin kein Standard in der Industrie. Lesen Sie aufmerksam die
|
|||
|
Beschreibung jeder Anweisung, auch wenn Ihnen diese vertraut erscheint.
|
|||
|
Dieses Dokument setzt ein Grundwissen an Kontaktplan-Programmierung
|
|||
|
und der Struktur von SPS-Software voraus (wie: der Ausf<73>hrungszyklus,
|
|||
|
Eing<EFBFBD>nge lesen, rechnen und Ausg<73>nge setzen).
|
|||
|
|
|||
|
|
|||
|
WEITERE ZIELE
|
|||
|
=============
|
|||
|
|
|||
|
Es ist auch m<>glich einen ANSI C - Code zu erzeugen. Diesen k<>nnen
|
|||
|
Sie dann f<>r jeden Prozessor verwenden, f<>r den Sie einen C-Compiler
|
|||
|
besitzen. Sie sind dann aber selbst verantwortlich, den Ablauf zu
|
|||
|
bestimmen. Das hei<65>t, LDmicro erzeugt nur ein Stammprogramm f<>r einen
|
|||
|
Funktions- SPS-Zyklus. Sie m<>ssen den SPS-Zyklus bei jedem Durchlauf
|
|||
|
aufrufen und auch die Ausf<73>hrung (Implementierung) der E/A-Funktionen,
|
|||
|
die der SPS-Zyklus abruft (wie: lesen/schreiben, digitaler Eingang usw.).
|
|||
|
F<EFBFBD>r mehr Einzelheiten: Siehe die Kommentare in dem erzeugten Quellcode.
|
|||
|
|
|||
|
Ganz zuletzt kann LDmicro auch f<>r eine virtuelle Maschine einen
|
|||
|
prozessor-unabh<62>ngigen Byte-Code erzeugen, welche mit der KOP-Kodierung
|
|||
|
(ladder logic) laufen soll. Ich habe eine Beispiel-Anwendung des
|
|||
|
VM/Interpreters vorgesehen, in ziemlich gutem C geschrieben. Dieses
|
|||
|
Anwendungsziel wird halbwegs auf jeder Plattform funktionieren, so lange
|
|||
|
Sie Ihre eigene VM vorsehen. Dies k<>nnte f<>r solche Anwendungen n<>tzlich
|
|||
|
sein, f<>r die Sie KOP (ladder logic) als Datentransfer-Sprache verwenden
|
|||
|
m<EFBFBD>chten, um ein gr<67><72>eres Programm anzupassen. F<>r weitere Einzelheiten:
|
|||
|
Siehe die Kommentare in dem Beispiel-Interpreter.
|
|||
|
|
|||
|
|
|||
|
OPTIONEN DER BEFEHLSZEILEN
|
|||
|
==========================
|
|||
|
|
|||
|
ldmicro.exe l<>uft normalerweise ohne eine Befehlszeilen-Option.
|
|||
|
Das hei<65>t, dass Sie nur ein Tastenk<6E>rzel zu dem Programm ben<65>tigen
|
|||
|
oder es auf dem Desktop abspeichern und dann auf das Symbol (die Ikone)
|
|||
|
doppelklicken, um es laufen zu lassen. Danach k<>nnen Sie alles ausf<73>hren,
|
|||
|
was das GUI (Graphical User Interface) zul<75>sst.
|
|||
|
|
|||
|
Wenn man an LDmicro einen alleinstehenden Dateinamen in der Befehlszeile
|
|||
|
vergeben hat (z. B. <20>ldmicro.exe asd.ld<6C>), wird LDmicro versuchen <20>asd.ld<6C>
|
|||
|
zu <20>ffnen, falls diese existiert. Dies bedeutet, dass man ldmicro.exe
|
|||
|
mit .ld Dateien verbinden kann, sodass dies automatisch abl<62>uft, wenn
|
|||
|
man auf eine .ld Datei doppelklickt.
|
|||
|
|
|||
|
Wenn man an LDmicro das Argument in der Befehlszeile in folgender Form
|
|||
|
vergeben hat: <20>ldmicro.exe /c src.ld dest.hex<65>, so wird es versuchen
|
|||
|
<EFBFBD>src.ld<6C> zu kompilieren und unter <20>dest.hex<65> abzuspeichern. LDmicro endet
|
|||
|
nach dem Kompilieren, unabh<62>ngig davon, ob die Kompilierung erfolgreich
|
|||
|
war oder nicht. Alle Meldungen werden auf der Konsole ausgegeben. Dieser
|
|||
|
Modus ist hilfreich, wenn man LDmicro von der Befehlszeile laufen
|
|||
|
aus l<>sst.
|
|||
|
|
|||
|
|
|||
|
GRUNDLAGEN
|
|||
|
==========
|
|||
|
|
|||
|
Wenn Sie LDmicro ohne Argumente aufrufen, so beginnt es als ein leeres
|
|||
|
Programm. Wenn Sie LDmicro mit dem Namen eines <20>ladder<65> (KOP)-Programms
|
|||
|
(z.B. xxx.ld) in der Befehlszeile <20>ffnen, dann wird es versuchen dieses
|
|||
|
Programm am Anfang zu laden.
|
|||
|
|
|||
|
LDmicro verwendet sein eigenes internes Format f<>r das Programm und
|
|||
|
man kann kein logisches Zeichen aus einem anderen (Fremd-)Programm
|
|||
|
importieren.
|
|||
|
|
|||
|
Falls Sie nicht ein schon vorhandenes Programm laden, dann wird Ihnen
|
|||
|
ein Programm mit einem leeren Netzwerk geliefert. In dieses k<>nnen Sie
|
|||
|
einen Befehl einf<6E>gen; z. B. k<>nnten Sie auch eine Reihe von Kontakten
|
|||
|
einf<EFBFBD>gen (Anweisung -> Kontakte Einf<6E>gen), die zun<75>chst mit <20>Xneu<65>
|
|||
|
bezeichnet werden. <20>X<EFBFBD> bedeutet, dass der Kontakt auf einen Eingang
|
|||
|
des Mikroprozessors festgelegt ist. Diesen Pin k<>nnen Sie sp<73>ter zuweisen,
|
|||
|
nachdem Sie den Mikroprozessor gew<65>hlt haben und die Kontakte
|
|||
|
umbenannt haben. Der erste Buchstabe zeigt an, um welche Art Objekt es
|
|||
|
sich handelt. Zum Beispiel:
|
|||
|
|
|||
|
* XName -- Auf einen Eingang des Mikroprozessors festgelegt
|
|||
|
* YName -- Auf einen Ausgang des Mikroprozessors festgelegt
|
|||
|
* RName -- Merker: Ein Bit im Speicher (Internes Relais)
|
|||
|
* TName -- Ein Timer; Anzugs- oder Abfallverz<72>gerung
|
|||
|
* CName -- Ein Z<>hler, Aufw<66>rts- oder Abw<62>rtsz<73>hler
|
|||
|
* AName -- Eine Ganzzahl, von einem A/D-Wandler eingelesen
|
|||
|
* Name -- Eine Allzweck-Variable als Ganzzahl
|
|||
|
|
|||
|
W<EFBFBD>hlen Sie den Rest des Namens, sodass dieser beschreibt, was das Objekt
|
|||
|
bewirkt und das dieser auch einmalig im Programm ist. Der gleiche Name
|
|||
|
bezieht sich immer auf das gleiche Objekt im Programm. Es w<>re zum
|
|||
|
Beispiel falsch eine Anzugsverz<72>gerung (TON) <20>TVerz<72>g<EFBFBD> zu nennen und im
|
|||
|
selben Programm eine Abfallverz<72>gerung <20>TVerz<72>g<EFBFBD> (TOF), weil jeder Z<>hler
|
|||
|
(oder Timer) seinen eigenen Speicher ben<65>tigt. Andererseits w<>re es
|
|||
|
korrekt einen <20>Speichernden Timer<65> (RTO) <20>TVerz<72>g<EFBFBD> zu nennen und eine
|
|||
|
entsprechende R<>cksetz-Anweisung (RES) = <20>TVerz<72>g<EFBFBD>, weil in diesem
|
|||
|
Fall beide Befehle dem gleichen Timer gelten.
|
|||
|
|
|||
|
Die Namen von Variablen k<>nnen aus Buchstaben, Zahlen und Unter-
|
|||
|
strichen (_) bestehen. Der Name einer Variablen darf nicht mit einer
|
|||
|
Nummer beginnen. Die Namen von Variablen sind fallabh<62>ngig.
|
|||
|
|
|||
|
Ein Befehl f<>r eine gew<65>hnliche Variable (MOV, ADD, EQU, usw.), kann
|
|||
|
mit Variablen mit jedem Namen arbeiten. Das bedeutet, dass diese Zugang
|
|||
|
zu den Timer- und Z<>hler-Akkumulatoren haben. Das kann manchmal recht
|
|||
|
hilfreich sein; zum Beispiel kann man damit pr<70>fen, ob die Z<>hlung eines
|
|||
|
Timers in einem bestimmten Bereich liegt.
|
|||
|
|
|||
|
Die Variablen sind immer 16-Bit Ganzzahlen. Das hei<65>t sie k<>nnen von
|
|||
|
-32768 bis 32767 reichen. Die Variablen werden immer als vorzeichen-
|
|||
|
behaftet behandelt. Sie k<>nnen auch Buchstaben als Dezimalzahlen festlegen
|
|||
|
(0, 1234, -56). Auch k<>nnen Sie ASCII-Zeichenwerte (<28>A<EFBFBD>, <20>z<EFBFBD>) festlegen,
|
|||
|
indem Sie die Zeichen in <20>Auslassungszeichen<65> einf<6E>gen. Sie k<>nnen
|
|||
|
ein ASCII-Zeichen an den meisten Stellen verwenden, an denen Sie eine
|
|||
|
Dezimalzahl verwenden k<>nnen.
|
|||
|
|
|||
|
Am unteren Ende der Maske (Bildanzeige) sehen Sie eine Liste aller
|
|||
|
Objekte (Anweisungen, Befehle) des Programms. Diese Liste wird vom
|
|||
|
Programm automatisch erzeugt; es besteht somit keine Notwendigkeit diese
|
|||
|
von Hand auf dem Laufenden zu halten. Die meisten Objekte ben<65>tigen
|
|||
|
keine Konfiguration. <20>XName<6D>, <20>YName<6D>, und <20>AName<6D> Objekte allerdings,
|
|||
|
m<EFBFBD>ssen einem Pin des Mikroprozessors zugeordnet werden. W<>hlen Sie zuerst
|
|||
|
welcher Prozessor verwendet wird (Voreinstellungen -> Prozessor). Danach
|
|||
|
legen Sie Ihre E/A Pins fest, indem Sie in der Liste auf diese jeweils
|
|||
|
doppelklicken.
|
|||
|
|
|||
|
Sie k<>nnen das Programm ver<65>ndern, indem Sie Anweisungen (Befehle)
|
|||
|
einf<EFBFBD>gen oder l<>schen. Die Schreibmarke (cursor)im Programm blinkt,
|
|||
|
um die momentan gew<65>hlte Anweisung und den Einf<6E>gungspunkt anzuzeigen.
|
|||
|
Falls diese nicht blinkt, so dr<64>cken Sie den <Tabulator> oder klicken
|
|||
|
Sie auf eine Anweisung. Jetzt k<>nnen Sie die momentane Anweisung l<>schen
|
|||
|
oder eine neue Anweisung einf<6E>gen; links oder rechts (in Reihenschaltung)
|
|||
|
oder <20>ber oder unter (in Parallelschaltung) mit der gew<65>hlten Anweisung.
|
|||
|
Einige Handhabungen sind nicht erlaubt, so zum Beispiel weitere
|
|||
|
Anweisungen rechts von einer Spule.
|
|||
|
|
|||
|
Das Programm beginnt mit nur einem Netzwerk. Sie k<>nnen mehr Netzwerke
|
|||
|
hinzuf<EFBFBD>gen, indem Sie <20>Netzwerk Einf<6E>gen Davor/Danach<63> im Programm-Men<65>
|
|||
|
w<EFBFBD>hlen. Den gleichen Effekt k<>nnten Sie erzielen, indem Sie viele
|
|||
|
komplizierte parallele Unterschaltungen in einem einzigen Netzwerk
|
|||
|
unterbringen. Es ist aber <20>bersichtlicher, mehrere Netzwerke zu verwenden.
|
|||
|
|
|||
|
Wenn Sie Ihr Programm fertig geschrieben haben, so k<>nnen Sie dieses
|
|||
|
mit der Simulation testen. Danach k<>nnen Sie es in eine Hex-Datei f<>r
|
|||
|
den zugedachten Mikroprozessor kompilieren.
|
|||
|
|
|||
|
|
|||
|
SIMULATION
|
|||
|
==========
|
|||
|
|
|||
|
Um den Simulationsbetrieb einzugeben, w<>hlen Sie <20>Simulieren ->
|
|||
|
Simulationsbetrieb<EFBFBD> oder dr<64>cken Sie <Strg+M>. Das Programm wird
|
|||
|
im Simulationsbetrieb unterschiedlich dargestellt. Es gibt keine
|
|||
|
Schreibmarke (cursor) mehr. Die <20>erregten<65> Anweisungen erscheinen hellrot,
|
|||
|
die <20>nicht erregten<65> erscheinen grau. Dr<44>cken Sie die Leertaste, um das
|
|||
|
SPS-Programm nur einen einzelnen Zyklus durchlaufen zu lassen. W<>hlen
|
|||
|
Sie f<>r einen kontinuierlichen Umlauf in Echtzeit <20>Simulieren -> Start
|
|||
|
Echtzeit-Simulation<6F> oder dr<64>cken Sie <Strg+R>. Die Maske (Bildanzeige)
|
|||
|
des Programms wird jetzt in Echtzeit, entsprechend der <20>nderungen des
|
|||
|
Status (des Zustands) des Programms aktualisiert.
|
|||
|
|
|||
|
Sie k<>nnen den Status (Zustand) eines Eingangs im Programm einstellen,
|
|||
|
indem Sie auf den jeweiligen auf der Liste am unteren Ende der
|
|||
|
Maske (Bildanzeige) doppelklicken oder auf die jeweilige <20>XName<6D>
|
|||
|
Kontakt-Anweisung im Programm. Wenn Sie den Status (Zustand) eines
|
|||
|
Eingangs-Pins <20>ndern, so wird diese <20>nderung nicht unmittelbar in
|
|||
|
der Maske (Bildanzeige) wiedergegeben, sondern erst wenn sich die
|
|||
|
SPS im zyklischen Umlauf befindet. Das geschieht automatisch wenn das
|
|||
|
SPS-Programm in Echtzeit-Simulation l<>uft, oder wenn Sie die Leertaste
|
|||
|
dr<EFBFBD>cken.
|
|||
|
|
|||
|
|
|||
|
KOMPILIEREN ZUM SYSTEMSPEZIFISCHEN CODE
|
|||
|
=======================================
|
|||
|
|
|||
|
Letztlich ist es dann nur sinnvoll eine .hex Datei zu erzeugen, mit
|
|||
|
der Sie Ihren Mikroprozessor programmieren k<>nnen. Zun<75>chst m<>ssen
|
|||
|
Sie die Teilenummer des Mikroprozessors im Men<65> <20>Voreinstellungen ->
|
|||
|
Prozessor<EFBFBD> w<>hlen. Danach m<>ssen jedem <20>XName<6D> oder <20>YName<6D> Objekt
|
|||
|
einen E/A-Pin zuweisen. Tun Sie dies, indem auf den Namen des Objekts
|
|||
|
doppelklicken, welcher sich in der Liste ganz unten in der Maske
|
|||
|
(Bildanzeige) befindet. Ein Dialogfenster wird dann erscheinen und Sie
|
|||
|
k<EFBFBD>nnen daraufhin einen noch nicht vergebenen Pin von der Liste aussuchen.
|
|||
|
|
|||
|
Als n<>chstes m<>ssen Sie die Zykluszeit w<>hlen, mit der Sie das
|
|||
|
Programm laufen lassen wollen, auch m<>ssen Sie dem Compiler mitteilen
|
|||
|
mit welcher Taktgeschwindigkeit der Prozessor arbeiten soll. Diese
|
|||
|
Einstellungen werden im Men<65> <20>Voreinstellungen -> Prozessor Parameter...<2E>
|
|||
|
vorgenommen. <20>blicherweise sollten Sie die Zykluszeit nicht <20>ndern,
|
|||
|
denn diese ist auf 10ms voreingestellt, dies ist ein guter Wert f<>r
|
|||
|
die meisten Anwendungen. Tippen Sie die Frequenz des Quarzes (oder des
|
|||
|
Keramik-Resonators) ein, mit der Sie den Prozessor betreiben wollen und
|
|||
|
klicken auf Okay.
|
|||
|
|
|||
|
Jetzt k<>nnen Sie einen Code von Ihrem Programm erzeugen. W<>hlen Sie
|
|||
|
<EFBFBD>Kompilieren -> Kompilieren<65> oder <20>Kompilieren -> Kompilieren unter...<2E>,
|
|||
|
falls Sie vorher Ihr Programm schon kompiliert haben und einen neuen Namen
|
|||
|
f<EFBFBD>r die Ausgangsdatei vergeben wollen. Wenn Ihr Programm fehlerfrei ist,
|
|||
|
wird LDmicro eine Intel IHEX Datei erzeugen, mit der sich Ihr Prozessor
|
|||
|
programmieren l<>sst.
|
|||
|
|
|||
|
Verwenden Sie hierzu irgendeine Programmier Soft- und Hardware, die Sie
|
|||
|
besitzen, um die Hex-Datei in den Mikroprozessor zu laden. Beachten Sie
|
|||
|
die Einstellungen f<>r die Konfigurationsbits (fuses)! Bei den PIC16
|
|||
|
Prozessoren sind diese Konfigurationsbits bereits in der Hex-Datei
|
|||
|
enthalten. Die meisten Programmiersoftwares schauen automatisch nach
|
|||
|
diesen. F<>r die AVR-Prozessoren m<>ssen Sie die Konfigurationsbits von
|
|||
|
Hand einstellen.
|
|||
|
|
|||
|
|
|||
|
ANWEISUNGS-VERZEICHNIS
|
|||
|
======================
|
|||
|
|
|||
|
> KONTAKT, SCHLIESSER XName RName YName
|
|||
|
----] [---- ----] [---- ----] [----
|
|||
|
|
|||
|
Wenn ein <20>unwahres<65> Signal diese Anweisung erreicht, so ist das
|
|||
|
Ausgangssignal <20>unwahr<68>. Wenn ein <20>wahres<65> Signal diese Anweisung
|
|||
|
erreicht, so ist das Ausgangssignal <20>wahr<68>. Dies nur, falls der
|
|||
|
vorliegende Eingangspin, Ausgangspin oder eines Merkers (Hilfsrelais)
|
|||
|
<EFBFBD>wahr<EFBFBD> ist, anderenfalls ist es unwahr. Diese Anweisung fragt den Status
|
|||
|
(Zustand) eines Eingangspins, Ausgangspins oder Merkers (Hilfsrelais) ab.
|
|||
|
|
|||
|
|
|||
|
> KONTAKT, <20>FFNER XName RName YName
|
|||
|
----]/[---- ----]/[---- ----]/[----
|
|||
|
|
|||
|
Wenn ein <20>unwahres<65> Signal diese Anweisung erreicht, so ist das
|
|||
|
Ausgangssignal <20>unwahr<68>. Wenn ein <20>wahres<65> Signal diese Anweisung
|
|||
|
erreicht, so ist das Ausgangssignal <20>wahr<68>. Dies nur, falls der
|
|||
|
vorliegende Eingangspin, Ausgangspin oder der Merker (= internes
|
|||
|
Hilfsrelais) <20>unwahr<68> ist, anderenfalls ist es <20>unwahr<68>. Diese Anweisung
|
|||
|
fragt den Status (Zustand) eines Eingangspins, Ausgangspins oder Merkers
|
|||
|
(Hilfsrelais) ab. Dies ist das Gegenteil eines Schlie<69>ers.
|
|||
|
|
|||
|
|
|||
|
> SPULE, NORMAL (MERKER,AUSGANG) RName YName
|
|||
|
----( )---- ----( )----
|
|||
|
|
|||
|
Wenn ein <20>unwahres<65> Signal diese Anweisung erreicht, so wird der
|
|||
|
vorliegende Merker (Hilfsrelais) oder Ausgangspin nicht angesteuert. Wenn
|
|||
|
ein <20>wahres<65> Signal diese Anweisung erreicht, so wird der vorliegende
|
|||
|
Merker (Hilfsrelais) oder Ausgangspin angesteuert. Es ist nicht sinnvoll
|
|||
|
dieser Spule eine Eingangsvariable zuzuweisen. Diese Anweisung muss
|
|||
|
ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> SPULE, NEGIERT (MERKER,AUSGANG) RName YName
|
|||
|
----(/)---- ----(/)----
|
|||
|
|
|||
|
Wenn ein <20>wahres<65> Signal diese Anweisung erreicht, so wird der vorliegende
|
|||
|
Merker (Hilfsrelais)oder Ausgangspin nicht angesteuert. Wenn ein
|
|||
|
<EFBFBD>unwahres<EFBFBD> Signal diese Anweisung erreicht, so wird der vorliegende Merker
|
|||
|
(Hilfsrelais) oder Ausgangspin angesteuert. Es ist nicht sinnvoll dieser
|
|||
|
Spule eine Eingangsvariable zuzuweisen. Dies ist das Gegenteil einer
|
|||
|
normalen Spule. Diese Anweisung muss im Netzwerk ganz rechts stehen.
|
|||
|
|
|||
|
|
|||
|
> SPULE, SETZEN RName YName
|
|||
|
----(S)---- ----(S)----
|
|||
|
|
|||
|
Wenn ein <20>wahres<65> Signal diese Anweisung erreicht, so wird der vorliegende
|
|||
|
Merker (Hilfsrelais)oder Ausgangspin auf <20>wahr<68> gesetzt. Anderenfalls
|
|||
|
bleibt der Status (Zustand) des Merkers (Hilfsrelais) oder Ausgangspins
|
|||
|
unver<EFBFBD>ndert. Diese Anweisung kann nur den Status (Zustand) einer Spule
|
|||
|
von <20>unwahr<68> nach <20>wahr<68> ver<65>ndern, insofern wird diese <20>blicherweise in
|
|||
|
einer Kombination mit einer R<>cksetz-Anweisung f<>r eine Spule verwendet.
|
|||
|
Diese Anweisung muss ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> SPULE, R<>CKSETZEN RName YName
|
|||
|
----(R)---- ----(R)----
|
|||
|
|
|||
|
Wenn ein <20>wahres<65> Signal diese Anweisung erreicht, so wird der vorliegende
|
|||
|
Merker (Hilfsrelais) oder Ausgangspin r<>ckgesetzt. Anderenfalls bleibt der
|
|||
|
Status (Zustand) des Merkers (Hilfsrelais) oder Ausgangspins unver<65>ndert.
|
|||
|
Diese Anweisung kann nur den Status (Zustand) einer Spule von <20>wahr<68> nach
|
|||
|
<EFBFBD>unwahr<EFBFBD> ver<65>ndern, insofern wird diese <20>blicherweise in einer Kombination
|
|||
|
mit einer Setz-Anweisung f<>r eine Spule verwendet. Diese Anweisung muss
|
|||
|
ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> ANZUGSVERZ<52>GERUNG Tdon
|
|||
|
-[TON 1.000 s]-
|
|||
|
|
|||
|
Wenn ein Signal diese Anweisung erreicht, welches seinen Status
|
|||
|
(Zustand) von <20>unwahr<68> nach <20>wahr<68> <20>ndert, so bleibt das Ausgangssignal
|
|||
|
f<EFBFBD>r 1,000 s <20>unwahr<68>, dann wird es <20>wahr<68>. Wenn ein Signal diese
|
|||
|
Anweisung erreicht, welches seinen Status (Zustand) von <20>wahr<68> nach
|
|||
|
<EFBFBD>unwahr<EFBFBD> <20>ndert, so wird das Ausgangssignal sofort <20>unwahr<68>. Der Timer
|
|||
|
wird jedes Mal r<>ckgesetzt (bzw. auf Null gesetzt), wenn der Eingang
|
|||
|
<EFBFBD>unwahr<EFBFBD> wird. Der Eingang muss f<>r 1000 aufeinanderfolgende Millisekunden
|
|||
|
<EFBFBD>wahr<EFBFBD> bleiben, bevor auch der Ausgang <20>wahr<68> wird. Die Verz<72>gerung
|
|||
|
ist konfigurierbar.
|
|||
|
|
|||
|
Die <20>TName<6D> Variable z<>hlt, in der Einheit der jeweiligen Zykluszeit,
|
|||
|
von Null ab hoch. Der Ausgang der TON-Anweisung wird wahr, wenn die
|
|||
|
Z<EFBFBD>hlervariable gr<67><72>er oder gleich der vorliegenden Verz<72>gerung ist.
|
|||
|
Es m<>glich die Z<>hlervariable an einer anderen Stelle im Programm zu
|
|||
|
bearbeiten, zum Beispiel mit einer TRANSFER-Anweisung (MOV).
|
|||
|
|
|||
|
|
|||
|
> ABFALLVERZ<52>GERUNG Tdoff
|
|||
|
-[TOF 1.000 s]-
|
|||
|
|
|||
|
Wenn ein Signal diese Anweisung erreicht, welches seinen Status
|
|||
|
(Zustand) von <20>wahr<68> nach <20>unwahr<68> <20>ndert, so bleibt das Ausgangssignal
|
|||
|
f<EFBFBD>r 1,000 s <20>wahr<68>, dann wird es <20>unwahr<68>. Wenn ein Signal diese
|
|||
|
Anweisung erreicht, welches seinen Status (Zustand) von <20>unwahr<68> nach
|
|||
|
<EFBFBD>wahr<EFBFBD> <20>ndert, so wird das Ausgangssignal sofort <20>wahr<68>. Der Timer wird
|
|||
|
jedes Mal r<>ckgesetzt (bzw. auf Null gesetzt), wenn der Eingang <20>unwahr<68>
|
|||
|
wird. Der Eingang muss f<>r 1000 aufeinanderfolgende Millisekunden <20>unwahr<68>
|
|||
|
bleiben, bevor auch der Ausgang <20>unwahr<68> wird. Die Verz<72>gerung ist
|
|||
|
konfigurierbar.
|
|||
|
|
|||
|
Die <20>TName<6D> Variable z<>hlt, in der Einheit der jeweiligen Zykluszeit,
|
|||
|
von Null ab hoch. Der Ausgang der TOF Anweisung wird wahr, wenn die
|
|||
|
Z<EFBFBD>hlervariable gr<67><72>er oder gleich der vorliegenden Verz<72>gerung ist.
|
|||
|
Es m<>glich die Z<>hlervariable an einer anderen Stelle im Programm zu
|
|||
|
bearbeiten, zum Beispiel mit einer TRANSFER-Anweisung (MOV).
|
|||
|
|
|||
|
|
|||
|
> SPEICHERNDER TIMER Trto
|
|||
|
-[RTO 1.000 s]-
|
|||
|
|
|||
|
Diese Anweisung zeichnet auf, wie lange sein Eingang <20>wahr<68> gewesen
|
|||
|
ist. Wenn der Eingang f<>r mindestens 1.000 s <20>wahr<68> gewesen ist, dann
|
|||
|
wird der Ausgang <20>wahr<68>. Andernfalls ist er <20>unwahr<68>. Der Eingang muss
|
|||
|
f<EFBFBD>r 1000 aufeinanderfolgende Millisekunden <20>wahr<68> gewesen sein; wenn
|
|||
|
der Eingang f<>r 0,6 s <20>wahr<68> war, dann <20>unwahr<68> f<>r 2,0 s und danach f<>r
|
|||
|
0,4 s wieder <20>wahr<68>, so wird sein Ausgang <20>wahr<68>. Nachdem der Ausgang
|
|||
|
<EFBFBD>wahr<EFBFBD> wurde, so bleibt er <20>wahr<68>, selbst wenn der Eingang <20>unwahr<68>
|
|||
|
wird, so lange der Eingang f<>r l<>nger als 1.000 s <20>wahr<68> gewesen ist.
|
|||
|
Der Timer muss deshalb von Hand mit Hilfe der R<>cksetz-Anweisung
|
|||
|
r<EFBFBD>ckgesetzt (auf Null gesetzt) werden.
|
|||
|
|
|||
|
Die <20>TName<6D> Variable z<>hlt, in der Einheit der jeweiligen Zykluszeit,
|
|||
|
von Null ab hoch. Der Ausgang der RTO-Anweisung wird wahr, wenn die
|
|||
|
Z<EFBFBD>hlervariable gr<67><72>er oder gleich der vorliegenden Verz<72>gerung ist.
|
|||
|
Es m<>glich die Z<>hlervariable an einer anderen Stelle im Programm zu
|
|||
|
bearbeiten, zum Beispiel mit einer TRANSFER-Anweisung (MOV).
|
|||
|
|
|||
|
|
|||
|
> R<>CKSETZEN Trto Citems
|
|||
|
----{RES}---- ----{RES}----
|
|||
|
|
|||
|
Diese Anweisung r<>cksetzt einen Timer oder Z<>hler. TON oder TOF Timer
|
|||
|
werden automatisch r<>ckgesetzt, wenn ihr Eingang <20>wahr<68> oder <20>unwahr<68>
|
|||
|
wird, somit ist die RES-Anweisung f<>r diese Timer nicht erforderlich. RTO
|
|||
|
Timer und CTU/CTD Z<>hler werden nicht automatisch r<>ckgesetzt, somit
|
|||
|
m<EFBFBD>ssen diese von Hand mit Hilfe der RES-Anweisung r<>ckgesetzt (auf Null)
|
|||
|
werden. Wenn der Eingang <20>wahr<68> ist, so wird der Timer oder Z<>hler
|
|||
|
r<EFBFBD>ckgesetzt; wenn der Eingang <20>unwahr<68> ist, so erfolgt keine Aktion.
|
|||
|
Diese Anweisung muss ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
_
|
|||
|
> ONE-SHOT RISING, STEIGENDE FLANKE --[OSR_/ ]--
|
|||
|
|
|||
|
Diese Anweisung wird normalerweise <20>unwahr<68> ausgewiesen. Wenn der Eingang
|
|||
|
der Anweisung w<>hrend des momentanen Zyklus <20>wahr<68> ist und w<>hrend des
|
|||
|
vorgehenden <20>unwahr<68> war, so wird der Ausgang <20>wahr<68>. Daher erzeugt diese
|
|||
|
Anweisung bei jeder steigenden Flanke einen Impuls f<>r einen Zyklus.
|
|||
|
Diese Anweisung ist hilfreich, wenn Sie Ereignisse an der steigenden
|
|||
|
Flanke eines Signals ausl<73>sen wollen.
|
|||
|
|
|||
|
_
|
|||
|
> ONE-SHOT FALLING, FALLENDE FLANKE --[OSF \_ ]--
|
|||
|
|
|||
|
Diese Anweisung wird normalerweise <20>unwahr<68> ausgewiesen. Wenn der Eingang
|
|||
|
der Anweisung w<>hrend des momentanen Zyklus <20>unwahr<68> ist und w<>hrend des
|
|||
|
vorgehenden <20>wahr<68> war, so wird der Ausgang <20>wahr<68>. Daher erzeugt diese
|
|||
|
Anweisung bei jeder fallenden Flanke einen Impuls f<>r einen Zyklus.
|
|||
|
Diese Anweisung ist hilfreich, wenn Sie Ereignisse an der fallenden
|
|||
|
Flanke eines Signals ausl<73>sen wollen.
|
|||
|
|
|||
|
|
|||
|
> BR<42>CKE, <20>FFNUNG ----+----+---- ----+ +----
|
|||
|
|
|||
|
Der Eingangszustand einer Br<42>cke ist immer gleich seinem Ausgangszustand.
|
|||
|
Der Ausgangszustands einer <20>ffnung ist immer <20>unwahr<68>. Diese Anweisungen
|
|||
|
sind bei der Fehlerbehebung (debugging) besonders hilfreich.
|
|||
|
|
|||
|
|
|||
|
> MASTER CONTROL RELAIS -{MASTER RLY}-
|
|||
|
|
|||
|
|
|||
|
Im Normalfall ist der Anfang (die linke Stromschiene) von jedem Netzwerk
|
|||
|
<EFBFBD>wahr<EFBFBD>. Wenn eine <20>Master Control Relais<69> Anweisung ausgef<65>hrt wird dessen
|
|||
|
Eingang <20>unwahr<68> ist, so werden die Anf<6E>nge (die linke Stromschiene)
|
|||
|
aller folgenden Netzwerke <20>unwahr<68>. Das setzt sich fort bis die n<>chste
|
|||
|
<EFBFBD>Master Control Relais<69> Anweisung erreicht wird (unabh<62>ngig von dem
|
|||
|
Anfangszustand dieser Anweisung). Diese Anweisungen m<>ssen daher als Paar
|
|||
|
verwendet werden: Eine (vielleicht abh<62>ngige), um den <20>gegebenenfalls
|
|||
|
gesperrten<EFBFBD> Abschnitt zu starten und eine weitere, um diesen zu beenden.
|
|||
|
|
|||
|
|
|||
|
> TRANSFER, MOV {destvar := } {Tret := }
|
|||
|
-{ 123 MOV}- -{ srcvar MOV}-
|
|||
|
|
|||
|
Wenn der Eingang dieser Anweisung <20>wahr<68> ist, so setzt diese die
|
|||
|
vorliegende Zielvariable gleich der vorliegenden Quellvariablen
|
|||
|
oder Konstanten. Wenn der Eingang dieser Anweisung <20>unwahr<68> ist, so
|
|||
|
geschieht nichts. Mit der TRANSFER-Anweisung (MOV) k<>nnen Sie jede
|
|||
|
Variable zuweisen; dies schlie<69>t Timer und Z<>hler Statusvariablen ein,
|
|||
|
welche mit einem vorgestellten <20>T<EFBFBD> oder <20>C<EFBFBD> unterschieden werden. Eine
|
|||
|
Anweisung zum Beispiel, die eine <20>0<EFBFBD> in einen <20>TBewahrend<6E> transferiert,
|
|||
|
ist <20>quivalent mit einer RES-Anweisung f<>r diesen Timer. Diese Anweisung
|
|||
|
muss ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> ARITHMETISCHE OPERATIONEN {ADD kay :=} {SUB Ccnt :=}
|
|||
|
-{ 'a' + 10 }- -{ Ccnt - 10 }-
|
|||
|
|
|||
|
> {MUL dest :=} {DIV dv := }
|
|||
|
-{ var * -990 }- -{ dv / -10000}-
|
|||
|
|
|||
|
Wenn der Eingang einer dieser Anweisungen <20>wahr<68> ist, so setzt diese
|
|||
|
die vorliegende Zielvariable gleich dem vorliegenden arithmetischem
|
|||
|
Ausdruck. Die Operanden k<>nnen entweder Variabelen (einschlie<69>lich Timer-
|
|||
|
und Z<>hlervariabelen) oder Konstanten sein. Diese Anweisungen verwenden
|
|||
|
16-Bitzeichen Mathematik. Beachten Sie, dass das Ergebnis jeden Zyklus
|
|||
|
ausgewertet wird, wenn der Eingangszustand <20>wahr<68> ist. Falls Sie eine
|
|||
|
Variable inkrementieren oder dekrementieren (d.h., wenn die Zielvariable
|
|||
|
ebenfalls einer der Operanden ist), dann wollen Sie dies vermutlich
|
|||
|
nicht; normalerweise w<>rden Sie einen Impuls (one-shot) verwenden,
|
|||
|
sodass die Variable nur bei einer steigenden oder fallenden Flanke des
|
|||
|
Eingangszustands ausgewertet wird. Dividieren k<>rzt: D.h. 8 / 3 = 2.
|
|||
|
Diese Anweisungen m<>ssen ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> VERGLEICHEN [var ==] [var >] [1 >=]
|
|||
|
-[ var2 ]- -[ 1 ]- -[ Ton]-
|
|||
|
|
|||
|
> [var /=] [-4 < ] [1 <=]
|
|||
|
-[ var2 ]- -[ vartwo]- -[ Cup]-
|
|||
|
|
|||
|
Wenn der Eingang dieser Anweisung <20>unwahr<68> ist, so ist der Ausgang
|
|||
|
auch <20>unwahr<68>. Wenn der Eingang dieser Anweisung <20>wahr<68> ist, dann ist
|
|||
|
Ausgang <20>wahr<68>; dies aber nur, wenn die vorliegende Bedingung <20>wahr<68>
|
|||
|
ist. Diese Anweisungen k<>nnen zum Vergleichen verwendet werden, wie:
|
|||
|
Auf gleich, auf gr<67><72>er als, auf gr<67><72>er als oder gleich, auf ungleich,
|
|||
|
auf kleiner als, auf kleiner als oder gleich, eine Variable mit einer
|
|||
|
Variablen oder eine Variable mit einer 16-Bitzeichen-Konstanten.
|
|||
|
|
|||
|
|
|||
|
> Z<>HLER CName CName
|
|||
|
--[CTU >=5]-- --[CTD >=5]<5D>
|
|||
|
|
|||
|
Ein Z<>hler inkrementiert (CTU, aufw<66>rtsz<73>hlen) oder dekrementiert
|
|||
|
(CTD, abw<62>rtsz<73>hlen) die bezogene Z<>hlung bei jeder steigenden Flanke
|
|||
|
des Eingangszustands des Netzwerks (d.h. der Eingangszustand des
|
|||
|
Netzwerks geht von <20>unwahr<68> auf <20>wahr<68> <20>ber). Der Ausgangszustand des
|
|||
|
Z<EFBFBD>hlers ist <20>wahr<68>, wenn die Z<>hler- variable ist gr<67><72>er oder gleich 5
|
|||
|
und andernfalls <20>unwahr<68>. Der Ausgangszustand des Netzwerks kann <20>wahr<68>
|
|||
|
sein, selbst wenn der Eingangszustand <20>unwahr<68> ist; das h<>ngt lediglich
|
|||
|
von Z<>hlervariablen ab. Sie k<>nnen einer CTU- und CTD-Anweisung den
|
|||
|
gleichen Namen zuteilen, um den gleichen Z<>hler zu inkrementieren und
|
|||
|
dekrementieren. Die RES-Anweisung kann einen Z<>hler r<>cksetzen oder auch
|
|||
|
eine gew<65>hnliche Variablen-Operation mit der Z<>hlervariablen ausf<73>hren.
|
|||
|
|
|||
|
|
|||
|
> ZIRKULIERENDER Z<>HLER CName
|
|||
|
--{CTC 0:7}--
|
|||
|
|
|||
|
Ein zirkulierender Z<>hler arbeitet wie ein normaler CTU-Z<>hler, au<61>er
|
|||
|
nach der Erreichung seiner Obergrenze, r<>cksetzt er seine Z<>hlervariable
|
|||
|
auf Null. Zum Beispiel w<>rde der oben gezeigte Z<>hler, wie folgt z<>hlen:
|
|||
|
0, 1, 2, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2,.... Dies ist
|
|||
|
hilfreich in Kombination mit bedingten Anweisungen der Variablen<65>CName<6D>;
|
|||
|
Sie k<>nnen dies als eine Folgeschaltung verwenden. CTC-Z<>hler takten
|
|||
|
mit der aufsteigenden Flanke der Eingangsbedingung des Netzwerks.
|
|||
|
Diese Anweisung muss ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> SCHIEBEREGISTER {SHIFT REG }
|
|||
|
-{ reg0..3 }-
|
|||
|
|
|||
|
Ein Schieberegister besteht aus einer Reihe von Variablen. So best<73>nde
|
|||
|
zum Beispiel ein Schieberegister aus den Variablen <20>reg0<67>, <20>reg1<67>,
|
|||
|
<EFBFBD>reg2<EFBFBD>, and <20>reg3<67>. Der Eingang des Schieberegisters ist <20>reg0<67>. Bei
|
|||
|
jeder steigenden Flanke der Eingansbedingung des Netzwerks, schiebt das
|
|||
|
Schieberegister nach rechts. Dies bedeutet es wie folgt zuweist: <20>reg3<67>
|
|||
|
nach <20>reg2<67>, <20>reg2<67> nach <20>reg1<67> und <20>reg1<67> nach <20>reg0<67>. <20>reg0<67> bleibt
|
|||
|
unver<EFBFBD>ndert. Ein gro<72>es Schieberegister kann leicht viel Speicherplatz
|
|||
|
belegen. Diese Anweisung muss ganz rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> NACHSCHLAG-TABELLE {dest := }
|
|||
|
-{ LUT[i] }-
|
|||
|
|
|||
|
Eine Nachschlag-Tabelle ist eine Anordnung von n Werten. Wenn die
|
|||
|
Eingangsbedingung des Netzwerks <20>wahr<68> ist, so wird die Ganzzahl-Variable
|
|||
|
<EFBFBD>dest<EFBFBD> mit dem Eintrag in der Nachschlag-Tabelle gleichgesetzt, der der
|
|||
|
Ganzzahl-Variablen <20>i<EFBFBD> entspricht. Das Verzeichnis beginnt bei Null,
|
|||
|
insofern muss sich <20>i<EFBFBD> zwischen 0 und (n-1) befinden. Das Verhalten
|
|||
|
dieser Anweisung ist undefiniert, wenn sich die Werte des Verzeichnisses
|
|||
|
au<EFBFBD>erhalb dieses Bereichs befinden.
|
|||
|
|
|||
|
|
|||
|
> N<>HERUNGS-LINEAR-TABELLE {yvar :=}
|
|||
|
-{PWL[xvar] }-
|
|||
|
|
|||
|
Dies ist eine gute Methode f<>r die N<>herungsl<73>sung einer komplizierten
|
|||
|
Funktion oder Kurve. Sie k<>nnte zum Beispiel hilfreich sein, wenn Sie
|
|||
|
versuchen eine Eichkurve zu verwenden, um die rohe Ausgangsspannung
|
|||
|
eines F<>hlers in g<>nstigere Einheiten zu wandeln.
|
|||
|
|
|||
|
Angenommen Sie versuchen eine N<>herungsl<73>sung f<>r eine Funktion zu finden,
|
|||
|
die eine Eingangs-Ganzzahlvariable <20>x<EFBFBD> in Ausgangs-Ganzzahlvariable <20>y<EFBFBD>
|
|||
|
wandelt. Einige Punkte der Funktion sind Ihnen bekannt; so w<>rden Sie
|
|||
|
z.B. die folgenden kennen:
|
|||
|
|
|||
|
f(0) = 2
|
|||
|
f(5) = 10
|
|||
|
f(10) = 50
|
|||
|
f(100) = 100
|
|||
|
|
|||
|
Dies bedeutet, dass sich die Punkte
|
|||
|
|
|||
|
(x0, y0) = ( 0, 2)
|
|||
|
(x1, y1) = ( 5, 10)
|
|||
|
(x2, y2) = ( 10, 50)
|
|||
|
(x3, y3) = (100, 100)
|
|||
|
|
|||
|
in dieser Kurve befinden. Diese 4 Punkte k<>nnen Sie in die Tabelle der
|
|||
|
<EFBFBD>N<EFBFBD>herungs-Linear<61>-Anweisung eintragen. Die <20>N<EFBFBD>herungs-Linear<61>-Anweisung
|
|||
|
wird dann auf den Wert von <20>xvar<61> schauen und legt den Wert von <20>yvar<61>
|
|||
|
fest. Sie stellt <20>yvar<61> so ein, dass die <20>N<EFBFBD>herungs-Linear<61>-Kurve sich
|
|||
|
durch alle Punkte bewegt, die Sie vorgegeben haben. Wenn Sie z.B. f<>r
|
|||
|
<EFBFBD>xvar<EFBFBD> = 10 vorgegeben haben, dann stellt die Anweisung <20>yvar<61> auf gleich
|
|||
|
50 ein.
|
|||
|
|
|||
|
Falls Sie dieser Anweisung einen Wert <20>xvar<61> zuweisen, der zwischen zwei
|
|||
|
Werten von <20>x<EFBFBD> liegt, denen Sie Punkte zugeordnet haben, dann stellt die
|
|||
|
Anweisung <20>yvar<61> so ein, dass (<28>xvar<61>, <20>yvar<61>) in der geraden Linie liegt;
|
|||
|
diejenige die, die zwei Punkte in der Tabelle verbindet. Z.B. erzeugt
|
|||
|
<EFBFBD>xvar<EFBFBD> = 55 bei <20>yvar<61> = 75. Die beiden Punkte in der Tabelle sind (10,
|
|||
|
50) und (100, 100). 55 liegt auf halbem Weg zwischen 10 und 100 und 75
|
|||
|
liegt auf halbem Weg zwischen 50 und 100, somit liegt (55, 75) auf der
|
|||
|
Linie, die diese zwei Punkte verbindet.
|
|||
|
|
|||
|
Die Punkte m<>ssen in aufsteigender Reihenfolge der x-Koordinaten
|
|||
|
angegeben werden. Einige mathematische Operationen, erforderlich f<>r
|
|||
|
bestimmte Nachschlag-Tabellen mit 16-Bit-Mathematik, kann man ggf. nicht
|
|||
|
ausf<EFBFBD>hren. In diesem Falle gibt LDmicro eine Warnmeldung aus. So w<>rde
|
|||
|
z.B. die folgende Nachschlag-Tabelle eine Fehlermeldung hervorrufen:
|
|||
|
|
|||
|
(x0, y0) = ( 0, 0)
|
|||
|
(x1, y1) = (300, 300)
|
|||
|
|
|||
|
Sie k<>nnen diesen Fehler beheben, indem sie den Abstand zwischen den
|
|||
|
Punkten kleiner machen. So ist zum Beispiel die n<>chste Tabelle <20>quivalent
|
|||
|
zur vorhergehenden, ruft aber keine Fehlermeldung hervor.
|
|||
|
|
|||
|
(x0, y0) = ( 0, 2)
|
|||
|
(x1, y1) = (150, 150)
|
|||
|
(x2, y2) = (300, 300)
|
|||
|
|
|||
|
Es wird kaum einmal notwendig sein, mehr als f<>nf oder sechs Punkte
|
|||
|
zu verwenden. Falls Sie mehr Punkte hinzuf<75>gen, so vergr<67><72>ert dies
|
|||
|
Ihren Code und verlangsamt die Ausf<73>hrung. Falls Sie f<>r <20>xvar<61> einen
|
|||
|
Wert vergeben, der gr<67><72>er ist, als die gr<67><72>te x-Koordinate der Tabelle
|
|||
|
oder kleiner, als die kleinste x-Koordinate in der Tabelle, so ist das
|
|||
|
Verhalten der Anweisung undefiniert. Diese Anweisung muss ganz rechts
|
|||
|
im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> A/D-WANDLER EINLESEN AName
|
|||
|
--{READ ADC}--
|
|||
|
|
|||
|
LDmicro kann einen Code erzeugen, der erm<72>glicht, die A/D-Wandler
|
|||
|
zu verwenden, die in manchen Mikroprozessoren vorgesehen sind.
|
|||
|
Wenn der Eingangszustand dieser Anweisung <20>wahr<68> ist, dann wird eine
|
|||
|
Einzellesung von dem A/D-Wandler entnommen und in der Variablen <20>AName<6D>
|
|||
|
gespeichert. Diese Variable kann anschlie<69>end mit einer gew<65>hnlichen
|
|||
|
Ganzzahlvariablen bearbeitet werden (wie: Kleiner als, gr<67><72>er als,
|
|||
|
arithmetisch usw.). Weisen Sie <20>Axxx<78> in der gleichen Weise einen Pin
|
|||
|
zu, wie Sie einen Pin f<>r einen digitalen Ein- oder Ausgang vergeben
|
|||
|
w<EFBFBD>rden, indem auf diesen in der Liste unten in der Maske (Bildanzeige)
|
|||
|
doppelklicken. Wenn der Eingangszustand dieses Netzwerks <20>unwahr<68> ist,
|
|||
|
so wird die Variable <20>AName<6D> unver<65>ndert belassen.
|
|||
|
|
|||
|
F<EFBFBD>r alle derzeitig unterst<73>tzten Prozessoren gilt: Eine 0 Volt Lesung
|
|||
|
am Eingang des A/D-Wandlers entspricht 0. Eine Lesung gleich der
|
|||
|
Versorgungsspannung (bzw. Referenzspannung) entspricht 1023. Falls Sie
|
|||
|
AVR-Prozessoren verwenden, so verbinden Sie AREF mit Vdd. (Siehe Atmel
|
|||
|
Datenblatt, dort wird eine Induktivit<69>t von 100<30>H empfohlen). Sie k<>nnen
|
|||
|
arithmetische Operationen verwenden, um einen g<>nstigeren Ma<4D>stabfaktor
|
|||
|
festzulegen, aber beachten Sie, dass das Programm nur Ganzzahl-Arithmetik
|
|||
|
vorsieht. Allgemein sind nicht alle Pins als A/D-Wandler verwendbar. Die
|
|||
|
Software gestattet Ihnen nicht, einen Pin zuzuweisen, der kein A/D
|
|||
|
bzw. analoger Eingang ist. Diese Anweisung muss ganz rechts im Netzwerk
|
|||
|
stehen.
|
|||
|
|
|||
|
|
|||
|
> PULSWEITEN MODULATIONSZYKLUS FESTLEGEN duty_cycle
|
|||
|
-{PWM 32.8 kHz}-
|
|||
|
|
|||
|
LDmicro kann einen Code erzeugen, der erm<72>glicht, die PWM-Peripherie
|
|||
|
zu verwenden, die in manchen Mikroprozessoren vorgesehen ist. Wenn die
|
|||
|
Eingangsbedingung dieser Anweisung <20>wahr<68> ist, so wird der Zyklus der
|
|||
|
PWM-Peripherie mit dem Wert der Variablen <20>duty cycle<6C> gleichgesetzt. Der
|
|||
|
<EFBFBD>duty cycle<6C> muss eine Zahl zwischen 0 und 100 sein. 0 entspricht immer
|
|||
|
<EFBFBD>low<EFBFBD> und 100 entsprechend immer <20>high<67>. (Wenn Sie damit vertraut sind,
|
|||
|
wie die PWM-Peripherie funktioniert, so bemerken Sie, dass dies bedeutet,
|
|||
|
dass LDmicro die <20>duty cycle<6C>-Variable automatisch prozentual zu den
|
|||
|
PWM-Taktintervallen skaliert [= den Ma<4D>stabfaktor festlegt].)
|
|||
|
|
|||
|
Sie k<>nnen die PWM-Zielfrequenz in Hz definieren. Es kann vorkommen, dass
|
|||
|
die angegebene Frequenz nicht genau erreicht wird, das h<>ngt davon ab,
|
|||
|
wie sich diese innerhalb der Taktfrequenz des Prozessors einteilt. LDmicro
|
|||
|
w<EFBFBD>hlt dann die n<>chst erreichbare Frequenz; falls der Fehler zu gro<72> ist,
|
|||
|
so wird eine Warnung ausgegeben. H<>here Geschwindigkeiten k<>nnen die
|
|||
|
Aufl<EFBFBD>sung beeintr<74>chtigen.
|
|||
|
|
|||
|
Diese Anweisung muss ganz rechts im Netzwerk stehen. Die <20>ladder
|
|||
|
logic<EFBFBD>-Laufzeit verbraucht (schon) einen Timer, um die Zykluszeit
|
|||
|
zu messen. Dies bedeutet, dass die PWM nur bei den Mikroprozessoren
|
|||
|
verf<EFBFBD>gbar ist, bei denen mindestens zwei geeignete Timer vorhanden sind.
|
|||
|
PWM verwendet den PIN CCP2 (nicht CCP1) bei den PIC16-Prozessoren und
|
|||
|
OC2 (nicht OC1A) bei den AVR-Prozessoren.
|
|||
|
|
|||
|
|
|||
|
> REMANENT MACHEN saved_var
|
|||
|
--{PERSIST}--
|
|||
|
|
|||
|
Wenn der Eingangszustand dieser Anweisung <20>wahr<68> ist, so bewirkt
|
|||
|
dies, dass eine angegebene Ganzzahl-Variable automatisch im EEPROM
|
|||
|
gespeichert wird. Dies bedeutet, dass ihr Wert bestehen bleiben wird,
|
|||
|
auch wenn der Prozessor seine Versorgungsspannung verliert. Es ist
|
|||
|
nicht notwendig, die Variable an klarer Stelle im EEPROM zu speichern,
|
|||
|
dies geschieht automatisch, so oft sich der Wert der Variablen
|
|||
|
<EFBFBD>ndert. Bei Spannungswiederkehr wird die Variable automatisch vom
|
|||
|
EEPROM zur<75>ckgespeichert. Falls eine Variable, die h<>ufig ihren Wert
|
|||
|
<EFBFBD>ndert, remanent (dauerhaft) gemacht wird, so k<>nnte Ihr Prozessor sehr
|
|||
|
rasch verschlei<65>en, weil dieser lediglich f<>r eine begrenzte Anzahl von
|
|||
|
Schreibbefehlen konstruiert ist (~100 000). Wenn der Eingangszustand des
|
|||
|
Netzwerks <20>unwahr<68> ist, so geschieht nichts. Diese Anweisung muss ganz
|
|||
|
rechts im Netzwerk stehen.
|
|||
|
|
|||
|
|
|||
|
> UART (SERIELL) EMPFANGEN var
|
|||
|
--{UART RECV}--
|
|||
|
|
|||
|
LDmicro kann einen Code erzeugen, der erm<72>glicht UART zu verwenden,
|
|||
|
welcher in manchen Mikroprozessoren vorgesehen ist.
|
|||
|
Bei AVR-Prozessoren mir mehrfachem UART, wird nur UART1 (nicht UART0)
|
|||
|
unterst<EFBFBD>tzt. Konfigurieren Sie die Baudrate, indem Sie <20>Voreinstellungen
|
|||
|
-> Prozessor-Parameter<65> verwenden. Bestimmte Baudraten werden mit
|
|||
|
bestimmten Quarzfrequenzen nicht erreichbar sein. In diesem Fall gibt
|
|||
|
LDmicro eine Warnmeldung.
|
|||
|
|
|||
|
Wenn der Eingangszustand dieser Anweisung <20>unwahr<68> ist, so geschieht
|
|||
|
nichts. Wenn der Eingangszustand <20>wahr<68> ist, so versucht diese Anweisung
|
|||
|
ein einzelnes Schriftzeichen vom UART-Eingang zu empfangen. Wenn
|
|||
|
kein Schriftzeichen eingelesen wird, dann ist der Ausgangszustand
|
|||
|
<EFBFBD>unwahr<EFBFBD>. Wenn ein ASCII-Zeichen eingelesen wird, so wird sein Wert in
|
|||
|
<EFBFBD>var<EFBFBD> abgespeichert und der Ausgangszustand wird f<>r einen einzelnen
|
|||
|
Zyklus <20>wahr<68>.
|
|||
|
|
|||
|
|
|||
|
> UART (SERIELL) SENDEN var
|
|||
|
--{UART SEND}--
|
|||
|
|
|||
|
LDmicro kann einen Code erzeugen, der erm<72>glicht UART zu verwenden,
|
|||
|
welcher in manchen Mikroprozessoren vorgesehen ist.
|
|||
|
Bei AVR-Prozessoren mir mehrfachem UART, wird nur UART1 (nicht UART0)
|
|||
|
unterst<EFBFBD>tzt. Konfigurieren Sie die Baudrate, indem Sie <20>Voreinstellungen
|
|||
|
-> Prozessor-Parameter<65> verwenden. Bestimmte Baudraten werden mit
|
|||
|
bestimmten Quarzfrequenzen nicht erreichbar sein. In diesem Fall gibt
|
|||
|
LDmicro eine Warnmeldung.
|
|||
|
|
|||
|
Wenn der Eingangszustand dieser Anweisung <20>unwahr<68> ist, so geschieht
|
|||
|
nichts. Wenn der Eingangszustand <20>wahr<68> ist, so schreibt diese
|
|||
|
Anweisung ein einzelnes Schriftzeichen zum UART. Der ASCII-Wert des
|
|||
|
Schriftzeichens, welches gesendet werden soll, muss vorher in <20>var<61>
|
|||
|
abgespeichert worden sein. Der Ausgangszustand dieses Netzwerks ist
|
|||
|
<EFBFBD>wahr<EFBFBD>, wenn UART besch<63>ftigt ist (gerade dabei ein Schriftzeichen zu
|
|||
|
<EFBFBD>bermitteln) und andernfalls <20>unwahr<68>.
|
|||
|
|
|||
|
Denken Sie daran, dass einige Zeit zum Senden von Schriftzeichen
|
|||
|
beansprucht wird. <20>berpr<70>fen Sie den Ausgangszustand dieser Anweisung,
|
|||
|
sodass das erste Schriftzeichen bereits <20>bermittelt wurde, bevor Sie
|
|||
|
versuchen ein zweites Schriftzeichen zu <20>bermitteln. Oder verwenden Sie
|
|||
|
einen Timer, um eine Verz<72>gerung zwischen die Schriftzeichen f<>gen. Sie
|
|||
|
d<EFBFBD>rfen den Eingangszustand dieser Anweisung nur dann auf <20>wahr<68> setzen
|
|||
|
(bzw. ein Schriftzeichen <20>bermitteln), wenn der Ausgangszustand <20>unwahr<68>
|
|||
|
ist (bzw. UART unbesch<63>ftigt ist).
|
|||
|
|
|||
|
Untersuchen Sie die <20>Formatierte Zeichenfolge<67>-Anweisung, bevor Sie
|
|||
|
diese Anweisung verwenden. Die <20>Formatierte Zeichenfolge<67>- Anweisung
|
|||
|
ist viel einfacher in der Anwendung und fast sicher f<>hig, das zu tun,
|
|||
|
was Sie beabsichtigen.
|
|||
|
|
|||
|
|
|||
|
> FORMATIERTE ZEICHENFOLGE <20>BER UART var
|
|||
|
-{"Druck: \3\r\n"}-
|
|||
|
|
|||
|
LDmicro kann einen Code erzeugen, der erm<72>glicht UART zu verwenden,
|
|||
|
welcher in manchen Mikroprozessoren vorgesehen ist.
|
|||
|
Bei AVR-Prozessoren mir mehrfachem UART, wird nur UART1 (nicht UART0)
|
|||
|
unterst<EFBFBD>tzt. Konfigurieren Sie die Baudrate, indem Sie <20>Voreinstellungen
|
|||
|
-> Prozessor-Parameter<65> verwenden. Bestimmte Baudraten werden mit
|
|||
|
bestimmten Quarzfrequenzen nicht erreichbar sein. In diesem Fall gibt
|
|||
|
LDmicro eine Warnmeldung.
|
|||
|
|
|||
|
Wenn der Eingangszustand des Netzwerks f<>r diese Anweisung von <20>unwahr<68>
|
|||
|
auf <20>wahr<68> <20>bergeht, so beginnt diese eine vollst<73>ndige Zeichenfolge
|
|||
|
<EFBFBD>ber den seriellen Anschluss zu senden. Wenn die Zeichenfolge die
|
|||
|
besondere Reihenfolge <20>\3<> enth<74>lt, dann wird diese Folge durch den Wert
|
|||
|
von <20>var<61> ersetzt, welcher automatisch in eine Zeichenfolge gewandelt
|
|||
|
wird. Die Variable wird formatiert, sodass diese exakt 3 Schriftzeichen
|
|||
|
<EFBFBD>bernimmt. Falls die Variable zum Beispiel gleich 35 ist, dann wird die
|
|||
|
exakte ausgegebene Zeichenfolge, wie folgt aussehen: <20>Druck: 35\r\n<>
|
|||
|
(beachten Sie das zus<75>tzliche Freizeichen). Wenn stattdessen die Variable
|
|||
|
gleich 1432 ist, so w<>re das Verhalten der Anweisung undefiniert,
|
|||
|
weil 1432 mehr als drei Stellen hat. In diesem Fall w<>re es notwendig
|
|||
|
stattdessen <20>\4<> zu verwenden.
|
|||
|
|
|||
|
Falls die Variable negativ ist, so verwenden Sie stattdessen <20>\-3d<33>
|
|||
|
(oder <20>\-4d<34>). LDmicro wird hierdurch veranlasst eine vorgestellte
|
|||
|
Freistelle f<>r positive Zahlen und ein vorgestelltes Minuszeichen f<>r
|
|||
|
negative Zahlen auszugeben.
|
|||
|
|
|||
|
Falls mehrere <20>Formatierte Zeichenfolge<67>-Anweisungen zugleich ausgegeben
|
|||
|
werden (oder wenn eine neue Zeichenfolge ausgegeben wird bevor die
|
|||
|
vorherige vollendet ist), oder auch wenn diese mit UART TX Anweisungen
|
|||
|
vermischt, so ist das Verhalten undefiniert.
|
|||
|
|
|||
|
Es ist auch m<>glich diese Anweisung f<>r eine feste Zeichenfolge zu
|
|||
|
verwenden, die <20>ber den seriellen Anschluss gesendet wird, ohne den Wert
|
|||
|
einer Ganzzahlvariablen in den Text zu interpolieren. In diesem Fall
|
|||
|
f<EFBFBD>gen Sie einfach diese spezielle Steuerungsfolge nicht ein.
|
|||
|
|
|||
|
Verwenden Sie <20>\\<5C> f<>r einen zeichengetreuen verkehrten Schr<68>gstrich.
|
|||
|
Zus<EFBFBD>tzlich zur Steuerungsfolge f<>r die Interpolierung einer Ganzzahl-
|
|||
|
Variablen, sind die folgenden Steuerungszeichen erh<72>ltlich:
|
|||
|
|
|||
|
* \r -- carriage return Zeilenschaltung
|
|||
|
* \n -- new line Zeilenwechsel
|
|||
|
* \f -- form feed Formularvorschub
|
|||
|
* \b -- backspace R<>cksetzen
|
|||
|
* \xAB -- character with ASCII value 0xAB (hex)
|
|||
|
-- Schriftzeichen mit ASCII-Wert 0xAB (hex)
|
|||
|
|
|||
|
Der Ausgangszustand des Netzwerks dieser Anweisung ist <20>wahr<68>, w<>hrend
|
|||
|
diese Daten <20>bertr<74>gt, ansonsten <20>unwahr<68>. Diese Anweisung ben<65>tigt eine
|
|||
|
gro<EFBFBD>e Menge des Programmspeichers, insofern sollte sie sparsam verwendet
|
|||
|
werden. Die gegenw<6E>rtige Umsetzung ist nicht besonders effizient, aber
|
|||
|
eine bessere w<>rde <20>nderungen an s<>mtlichen Ausl<73>ufern des Programms
|
|||
|
ben<EFBFBD>tigen.
|
|||
|
|
|||
|
|
|||
|
EIN HINWEIS ZUR VERWENDUNG DER MATHEMATIK
|
|||
|
=========================================
|
|||
|
|
|||
|
Denken Sie daran, dass LDmicro nur 16-Bit mathematische Operationen
|
|||
|
ausf<EFBFBD>hrt. Dies bedeutet, dass das Endresultat jeder Berechnung,
|
|||
|
die Sie vornehmen, eine Ganzzahl zwischen -32768 und 32767 sein muss.
|
|||
|
Dies bedeutet auch, dass die Zwischenergebnisse Ihrer Berechnungen alle
|
|||
|
in diesem Bereich liegen m<>ssen.
|
|||
|
|
|||
|
Wollen wir zum Beispiel annehmen, dass Sie folgendes berechnen m<>chten
|
|||
|
y = (1/x) * 1200, in der x zwischen 1 und 20 liegt.
|
|||
|
Dann liegt y zwischen 1200 und 60, was in eine 16-Bit Ganzzahl passt,
|
|||
|
so w<>re es zumindest theoretisch m<>glich diese Berechnung auszuf<75>hren.
|
|||
|
Es gibt zwei M<>glichkeiten, wie Sie dies codieren k<>nnten: Sie k<>nnen
|
|||
|
die Reziproke (Kehrwert) ausf<73>hren and dann multiplizieren:
|
|||
|
|
|||
|
|| {DIV temp :=} ||
|
|||
|
||---------{ 1 / x }----------||
|
|||
|
|| ||
|
|||
|
|| {MUL y := } ||
|
|||
|
||----------{ temp * 1200}----------||
|
|||
|
|| ||
|
|||
|
|
|||
|
Oder Sie k<>nnten einfach die Division in einem Schritt direkt vornehmen.
|
|||
|
|
|||
|
|| {DIV y :=} ||
|
|||
|
||-----------{ 1200 / x }-----------||
|
|||
|
|
|||
|
|
|||
|
Mathematisch sind die zwei <20>quivalent; aber wenn Sie diese ausprobieren,
|
|||
|
so werden Sie herausfinden, dass die erste ein falsches Ergebnis von
|
|||
|
y = 0 liefert. Dies geschieht, weil die Variable einen Unterlauf
|
|||
|
[= resultatabh<62>ngige Kommaverschiebung] ergibt. So sei zum Beispiel x = 3,
|
|||
|
(1 / x) = 0.333, dies ist aber keine Ganzzahl; die Divisionsoperation
|
|||
|
n<EFBFBD>hert dies, als 'temp = 0'. Dann ist y = temp * 1200 = 0. Im zweiten
|
|||
|
Fall gibt es kein Zwischenergebnis, welches einen Unterlauf [= resultats-
|
|||
|
abh<EFBFBD>ngige Kommaverschiebung] ergibt, somit funktioniert dann alles.
|
|||
|
|
|||
|
Falls Sie Probleme bei Ihren mathematischen Operationen erkennen,
|
|||
|
dann <20>berpr<70>fen Sie die Zwischenergebnisse auf Unterlauf [eine
|
|||
|
resultatabh<EFBFBD>ngige Kommaverschiebung] (oder auch auf <20>berlauf, der dann
|
|||
|
im Programm in Umlauf kommt; wie zum Beispiel 32767 + 1 = -32768).
|
|||
|
Wann immer m<>glich, w<>hlen Sie Einheiten, deren Werte in einem Bereich
|
|||
|
von -100 bis 100 liegen.
|
|||
|
|
|||
|
Falls Sie eine Variable um einen bestimmten Faktor vergr<67><72>ern m<>ssen, tun
|
|||
|
Sie dies, indem Sie eine Multiplikation und eine Division verwenden. Um
|
|||
|
zum Beispiel y = 1.8 * x zu vergr<67><72>ern, berechnen Sie y = (9/5) * x,
|
|||
|
(was dasselbe ist, weil 1,8 = 9/5 ist), und codieren Sie dies als
|
|||
|
y = (9 * x)/5, indem Sie die Multiplikation zuerst ausf<73>hren.
|
|||
|
|
|||
|
|| {MUL temp :=} ||
|
|||
|
||---------{ x * 9 }----------||
|
|||
|
|| ||
|
|||
|
|| {DIV y :=} ||
|
|||
|
||-----------{ temp / 5 }-----------||
|
|||
|
|
|||
|
|
|||
|
Dies funktioniert mit allen x < (32767 / 9), oder x < 3640. Bei h<>heren
|
|||
|
Werten w<>rde die Variable <20>temp<6D> <20>berflie<69>en. F<>r x gibt es eine
|
|||
|
<EFBFBD>hnliche Untergrenze.
|
|||
|
|
|||
|
|
|||
|
KODIER-STIL
|
|||
|
===========
|
|||
|
|
|||
|
Ich gestatte mehrere Spulen in Parallelschaltung in einem einzigen
|
|||
|
Netzwerk unterzubringen. Das bedeutet, sie k<>nnen ein Netzwerk, wie
|
|||
|
folgt schreiben:
|
|||
|
|
|||
|
|| Xa Ya ||
|
|||
|
1 ||-------] [--------------( )-------||
|
|||
|
|| ||
|
|||
|
|| Xb Yb ||
|
|||
|
||-------] [------+-------( )-------||
|
|||
|
|| | ||
|
|||
|
|| | Yc ||
|
|||
|
|| +-------( )-------||
|
|||
|
|| ||
|
|||
|
|
|||
|
Anstatt diesem:
|
|||
|
|
|||
|
|| Xa Ya ||
|
|||
|
1 ||-------] [--------------( )-------||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| Xb Yb ||
|
|||
|
2 ||-------] [--------------( )-------||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| Xb Yc ||
|
|||
|
3 ||-------] [--------------( )-------||
|
|||
|
|| ||
|
|||
|
|
|||
|
Rein theoretisch bedeutet das, dass Sie irgendein Programm, als ein
|
|||
|
gigantisches Netzwerk, schreiben k<>nnten. Und es best<73>nde <20>berhaupt
|
|||
|
keine Notwendigkeit mehrere Netzwerke zu verwenden. In der Praxis ist
|
|||
|
dies aber eine schlechte Idee, denn wenn Netzwerke komplexer werden, so
|
|||
|
werden sie auch schwieriger zu editieren, ohne L<>schen und neu Schreiben
|
|||
|
von Anweisungen.
|
|||
|
|
|||
|
Jedoch, ist es manchmal ein guter Einfall, verwandte Logik in einem
|
|||
|
einzelnen Netzwerk zusammenzufassen. Dies erzeugt einen beinahe
|
|||
|
identischen Code, als ob sie getrennte Netzwerke entworfen h<>tten, es
|
|||
|
zeigt aber, dass diese Anweisungen (Logik) verwandt ist, wenn man diese
|
|||
|
im Netzwerk-Diagramm betrachtet.
|
|||
|
|
|||
|
* * *
|
|||
|
|
|||
|
Im Allgemeinen h<>lt man es f<>r eine schlechte Form, den Code in einer
|
|||
|
solchen Weise zu schreiben, dass sein Ergebnis von einer Folge von
|
|||
|
Netzwerken abh<62>ngt. So zum Beispiel ist der folgende Code nicht besonders
|
|||
|
gut, falls <20>xa<78> und <20>xb<78> jemals <20>wahr<68> w<>rden.
|
|||
|
|
|||
|
|| Xa {v := } ||
|
|||
|
1 ||-------] [--------{ 12 MOV}--||
|
|||
|
|| ||
|
|||
|
|| Xb {v := } ||
|
|||
|
||-------] [--------{ 23 MOV}--||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| ||
|
|||
|
|| [v >] Yc ||
|
|||
|
2 ||------[ 15]-------------( )-------||
|
|||
|
|| ||
|
|||
|
|
|||
|
Ich werde diese Regel brechen und indem ich dies so mache, entwerfe ich
|
|||
|
einen Code-Abschnitt, der erheblich kompakter ist. Hier zum Beispiel,
|
|||
|
zeige ich auf, wie ich eine 4-Bit bin<69>re Gr<47><72>e von <20>xb3:0<> in eine
|
|||
|
Ganzzahl wandeln w<>rde.
|
|||
|
|
|||
|
|| {v := } ||
|
|||
|
3 ||-----------------------------------{ 0 MOV}--||
|
|||
|
|| ||
|
|||
|
|| Xb0 {ADD v :=} ||
|
|||
|
||-------] [------------------{ v + 1 }-----------||
|
|||
|
|| ||
|
|||
|
|| Xb1 {ADD v :=} ||
|
|||
|
||-------] [------------------{ v + 2 }-----------||
|
|||
|
|| ||
|
|||
|
|| Xb2 {ADD v :=} ||
|
|||
|
||-------] [------------------{ v + 4 }-----------||
|
|||
|
|| ||
|
|||
|
|| Xb3 {ADD v :=} ||
|
|||
|
||-------] [------------------{ v + 8 }-----------||
|
|||
|
|| ||
|
|||
|
|
|||
|
Falls die TRANSFER-Anweisung (MOV) an das untere Ende des Netzwerks
|
|||
|
gebracht w<>rde, anstatt auf das obere, so w<>rde der Wert von <20>v<EFBFBD>, an
|
|||
|
anderer Stelle im Programm gelesen, gleich Null sein. Das Ergebnis dieses
|
|||
|
Codes h<>ngt daher von der Reihenfolge ab, in welcher die Anweisungen
|
|||
|
ausgewertet werden. Im Hinblick darauf, wie hinderlich es w<>re, diesen
|
|||
|
Code auf eine andere Weise zu schreiben, nehme ich dies so hin.
|
|||
|
|
|||
|
|
|||
|
BUGS
|
|||
|
====
|
|||
|
|
|||
|
LDmicro erzeugt keinen sehr effizienten Code; es ist langsam in der
|
|||
|
Ausf<EFBFBD>hrung und geht verschwenderisch mit dem Flash- und RAM-Speicher
|
|||
|
um. Trotzdem kann ein mittelgro<72>er PIC- oder AVR-Prozessor alles, was
|
|||
|
eine kleine SPS kann, somit st<73>rt dies mich nicht besonders.
|
|||
|
|
|||
|
Die maximale L<>nge der Variabelen-Bezeichnungen (-Namen) ist sehr
|
|||
|
begrenzt. Dies ist so, weil diese so gut in das KOP-Programm (ladder)
|
|||
|
passen. Somit sehe ich keine gute L<>sung f<>r diese Angelegenheit.
|
|||
|
|
|||
|
Falls Ihr Programm zu gro<72> f<>r die Zeit-, Programmspeicher- oder
|
|||
|
Datenspeicher-Beschr<68>nkungen des Prozessors ist, den Sie gew<65>hlt haben,
|
|||
|
so erhalten Sie keine Fehlermeldung. Es wird einfach irgendwo anders alles
|
|||
|
vermasseln. (Anmerkung: Das AVR STK500 gibt hierzu Fehlermeldungen aus.)
|
|||
|
|
|||
|
Unsorgf<EFBFBD>ltiges Programmieren bei den Datei <20>ffnen/Abspeichern-Routinen
|
|||
|
f<EFBFBD>hren wahrscheinlich zu der M<>glichkeit eines Absturzes oder es wird
|
|||
|
ein willk<6C>rlicher Code erzeugt, der eine besch<63>digte oder b<>sartige .ld
|
|||
|
Datei ergibt.
|
|||
|
|
|||
|
Bitte berichten Sie zus<75>tzliche Bugs oder richten Sie Anfragen f<>r neue
|
|||
|
Programm-Bestandteile an den Autor (in Englisch).
|
|||
|
|
|||
|
Thanks to:
|
|||
|
* Marcelo Solano, for reporting a UI bug under Win98
|
|||
|
* Serge V. Polubarjev, for not only noticing that RA3:0 on the
|
|||
|
PIC16F628 didn't work but also telling me how to fix it
|
|||
|
* Maxim Ibragimov, for reporting and diagnosing major problems
|
|||
|
with the till-then-untested ATmega16 and ATmega162 targets
|
|||
|
* Bill Kishonti, for reporting that the simulator crashed when the
|
|||
|
ladder logic program divided by zero
|
|||
|
* Mohamed Tayae, for reporting that persistent variables were broken
|
|||
|
on the PIC16F628
|
|||
|
* David Rothwell, for reporting several user interface bugs and a
|
|||
|
problem with the "Export as Text" function
|
|||
|
|
|||
|
Particular thanks to Heinz Ullrich Noell, for this translation (of both
|
|||
|
the manual and the program's user interface) into German.
|
|||
|
|
|||
|
|
|||
|
COPYING, AND DISCLAIMER
|
|||
|
=======================
|
|||
|
|
|||
|
DO NOT USE CODE GENERATED BY LDMICRO IN APPLICATIONS WHERE SOFTWARE
|
|||
|
FAILURE COULD RESULT IN DANGER TO HUMAN LIFE OR DAMAGE TO PROPERTY. THE
|
|||
|
AUTHOR ASSUMES NO LIABILITY FOR ANY DAMAGES RESULTING FROM THE OPERATION
|
|||
|
OF LDMICRO OR CODE GENERATED BY LDMICRO.
|
|||
|
|
|||
|
This program is free software: you can redistribute it and/or modify it
|
|||
|
under the terms of the GNU General Public License as published by the
|
|||
|
Free Software Foundation, either version 3 of the License, or (at your
|
|||
|
option) any later version.
|
|||
|
|
|||
|
This program is distributed in the hope that it will be useful, but
|
|||
|
WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
|||
|
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|||
|
for more details.
|
|||
|
|
|||
|
You should have received a copy of the GNU General Public License along
|
|||
|
with this program. If not, see <http://www.gnu.org/licenses/>.
|
|||
|
|
|||
|
|
|||
|
Jonathan Westhues
|
|||
|
|
|||
|
Rijswijk -- Dec 2004
|
|||
|
Waterloo ON -- Jun, Jul 2005
|
|||
|
Cambridge MA -- Sep, Dec 2005
|
|||
|
Feb, Mar 2006
|
|||
|
|
|||
|
Email: user jwesthues, at host cq.cx
|
|||
|
|
|||
|
|