Der Aufbau und die Verarbeitung von Makros im X-Ray-Programm

m_steerg.h/cpp im Detail betrachtet

Kay Schützler
v09Sep99


Grundlegendes

Makros stellen Folgen von Befehlen dar, die durch die Klasse TSteering in entsprechende Motor- und Detektorsteueranweisungen umgesetzt werden. Damit besteht die Möglichkeit der Automatisierung der Steuerung durch entsprechende Makrodefinitionen in sogenannten Makrodateien (*.mak). Makros bzw. Makrobefehle werden auch programmintern benutzt, so zum Beispiel bei der Mehrfachbelichtung und bei der automatischen Nachregelung der Intensität.


Syntax der Makrodateien

Makrodatei = {Makro "\n"}+.

Makro = CommonBlock "\n" Befehlsblock.

Commonblock = "[Common]" "\n" Namensdef "\n" Längendef.

Namensdef = "Name" Trennzeichen Makroname.

Längendef = "Length" Trennzeichen Zahl.

Makroname = "InquireHwb" | "BatchMacro" |
"MiddleOfValley" | "SearchReflection"| "Test" | "AzimutalJustify" | 
"SetupTopography" | "ScanJob" | "AreaScanJob".

Zahl = 1...n.

Befehlsblock = "[Commands]" "\n" Befehlsfolge "[End]".
Befehlsfolge = {Befehl {Trennzeichen Parameter}* "\n"}+. Trennzeichen = " " | "=" | "\t" | "\r" | "\n". Befehl = "GotoPeak" | "GotoIntensity" | "ChooseAxis" | "GetHWB" | "SetWidth" | "AreaScan" | "Scan" | "ControlFlank" | "ShowHWB" | "SaveData" | "ChooseDevice" | "Calculate" | "LoadPoint" | "ShowValue" | "MoveToPoint" | "SetFileName" | "Inquire" | "GotoLine" | "Stop" | "SetupScan" | "SetupAreaScan". Parameter = "LargeSide" | "SmallSide" | "ToSmallerAngle" | "ToLargerAngle" | "Equidistant" | "Interpolation" | "Reflection" | "LastGoal" | "Standard" | "DecreaseWidth" | "ThisDFPos" | "BackMove" | "MaximizeTilt" | "MaximizeCollimator" | "MaximizeGradient" | "DynamicWidth" | "Result" | "StaticStepWidth" | "IncreasePeak" | "Relative" | "AreaScanResult" | "AbsorberUsed" | "Hwb" | "Difference" | "ScanResult" | "Middle" | "Array" | "Start" | "Peak" | "Min" | "Max" | "List" | "Argument" | "Opposite" | "ForAreaScan" | "ForScan".

Verarbeitung von Makros

1. Makros laden

Die Funktion LoadMacro( LPSTR makname, LPSTR filename ) versucht, das mit makname bezeichnete Makro in der mit filename bezeichneten Datei aufzufinden. Bei Vorhandensein (die Zeile "Name=makname" wird gefunden) wird in der Makroliste Steering.aMacroList ein Eintrag angelegt und die Befehlsfolge nach Steering.aMacroList.CmdList gespeichert.

Sollte ein Makro gleichen Namens bereits geladen gewesen sein, so wird die vorhandene Befehlsfolge durch die neu eingelesene ersetzt.

Die ebenfalls vorhandene Funktion LoadMacroByUser() ruft LoadMacro( makname, ".\scan.mak" ) fuer makname == "ScanJob" und makname == "AreaScanJob" auf. Vermutlich war hier urpsrünglich eine Erweiterung der Liste der vorgegebenen Makros um benutzereigene geplant.

2. Makros ausführen

Die Funktion StartMacroExecution( TMacroTag* Macro, HWND ) setzt Steering.TheMacro auf Macro und die (aktuelle) Befehlsliste Steering.TheCmdList auf Macro.CmdList und ruft daraufhin StartCmdExecution( TheCmdList[nCmdIdx] ) mit nCmdIdx == 0 auf.

StartCmdExecution( TCmdTag Cmd ) löscht TheCmd und setzt danach TheCmd auf ein neu erstelltes Objekt einer TCmd-Ableitung. Der konkrete Typ ergibt sich aus dem Wert von Cmd.Id.

Die jeweiligen Befehlsobjekte arbeiten asynchron zur Steuerung. Die timer-getriggerte Funktion Steering.WakeUp() löst jeweils ein TheCmd->WakeUp() aus. Der jeweilige Befehl kann darauf mit CMeasure (Messung (Detektor) gewünscht), CRecall (Motorbewegung noch nicht fertig, eine Runde aussetzen) oder CReady antworten. Bei CReady wird Steering.ReadyReaction() gerufen, die ihrerseits bei Vorliegen eines gültigen TheMacro-Zeigers ExecuteNextCmd() aufruft.

ExecuteNextCmd() erhöht den Zähler Steering.nCmdIdx um Eins. Stop und GotoLine werden von ExecuteNextCmd() selbst behandelt. Alle anderen Befehle werden durch einen Funktionsaufruf von StartCmdExecution( TheCmdList[nCmdIndex] ) angestossen.


Amerkungen

Die Arbeit mit m_steerg.h und m_steerg.cpp hat gezeigt, dass die Steuerung eine zentrale Komponente des X-Ray-Programms darstellt. Das Objekt Steering wird in m_topo.cpp (Topographie-Komponente), m_scan.cpp und m_arscan.cpp (Diffraktometrie-Komponenten) zur Motor-/Detektorsteuerung verwendet.

Der Quelltext enthält zahlreiche Stellen, die am besten mit "Hier war noch was geplant..." beschrieben werden können. Über die Bedeutung eines Großteils dieser Implementationsansätze kann nur spekuliert werden. Ein Teil dieser "Artefakte" kann jedoch bei näherem Studium sicher beseitigt werden.


Kay Schützler
Last modified: Thu Sep 9 20:56:19 CEST 1999