Step 7 Verständnissfrage Any Pointer, AR1

stalmoro

Level-2
Beiträge
17
Reaktionspunkte
1
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo liebe Community,
zu der Frage Any Pointer habe ich sämtliche Foren durchgewühlt und sämtliche Infos angeschaut. Ich kann die Zusammensetzung schon nachvollziehen, jedoch konkret bei uns, verstehe ich nicht wie die Werte bezogen werden. Es ist mir bekannt, dass der Wert im Wort 0 den Wert 1002 beinhalten soll. h10 als S7 ID und 02 für Datentype. Jedoch verstehe ich nicht, wo dieser Wert bezogen wird. Der Any Zeiger "LinieProd" wird im FC Kopf als Input deklariert und von Außen beschaltet

ImPrg.png
Hier wird einfach ein Wort geladen L W [AR1, P#0.0] und nach AR2 transferiert. Dabei verstehe ich nicht, welches Wort das ist, ein Merkerwort oder DB Bereich..

Die Beschaltung von Außen zeigt auf Anfang eines Bereiches in DB
.
Zuweisung.png
Im DB hat die entsprechende Zeile nichts mit dem Wer 1002 zu tun.
inDB.png
In allen Beispielen die ich im Internet gefunden habe, wird der Wert ja direkt in AR1 geladen:
L B#16#10 //10h für s7
T LB 0

Ich wäre sehr dankbar, wenn mir einer auf die Sprünge helfen könnte, auf welche Art und weise das bei uns geschieht, weil der Programmierer (oder die Programmierer) die das Programm erstellt haben, nicht mehr im Betrieb sind.

Vielen Dank im Voraus!
 
Code:
L    P##LineProd
LAR1
LAR2    P##zgrLinieProd
L W [AR1, P#0.0]
T W [AR2, P#0.0]
L W [AR1, P#2.0]
T W [AR2, P#2.0]
L W [AR1, P#4.0]
T W [AR2, P#4.0]
L W [AR1, P#6.0]
T W [AR2, P#6.0]

"P##LineProd" ist ein Zeiger, welcher auf die Stelle DB500.DBX18.0 zeigt.

In deinem Programm lädst du Worte von DB500.DBW18 nach der Stelle wohin der Zeiger P##zgrLinieProd hin zeigt.
Mit dem Offset "P#X.0" in deinen Lade/Transferiere-Befehlen gibst du immer die nächste Stelle an.
Somit ist im folgenden Lade/Transferiere-Befehl DB500.DBW20 nach P##zgrLinieProd + Offset P#2.0.

Code:
L P##LineProd
bedeutet Lade P#DB500.DBX18.0 aus dem In des Bausteins
Code:
LAR1
Code:
Bedeutet: AR1
= Der Pointer mit der Info "DB500.DBX18.0" wird ins AR1 geladen

Code:
L W [AR1, P#0.0]
bedeutet L W P#DB500.DBW18
Code:
L W [AR1, P#2.0]
bedeutet L W P#DB500.DBW20
Code:
L W [AR1, P#4.0]
bedeutet L W P#DB500.DBW22
Code:
L W [AR1, P#6.0]
bedeutet L W P#DB500.DBW24

Und so weiter..

Ich hoffe es ist einigermaßen verständlich, was ich geschrieben habe :D
 
Zuletzt bearbeitet:
Zuviel Werbung?
-> Hier kostenlos registrieren
Hier wird einfach ein Wort geladen L W [AR1, P#0.0] und nach AR2 transferiert. Dabei verstehe ich nicht, welches Wort das ist, ein Merkerwort oder DB Bereich..
Der Code kopiert den ANY-Pointer (10 Bytes) vom Input #LineProd (wo AR1 hinzeigt) in die ANY-Variable #zgrLinieProd (wo AR2 hinzeigt).
Am Input LineProd muss beim Baustein-Aufruf eine Adresse aus einem DB angegeben sein.

Der Code ist in einem FC oder einem FB?
 
Man hätte auch SFC20 BLKMOV verwenden können, doch dann hätte man noch eine zusätzliche Variable für den RET_VAL vom BLKMOV gebraucht... vielleicht zu viel Arbeit oder zu leicht verständlich? ;)
Ich glaube, wenn man dieses kopieren in SCL in Step7 classic programmiert (zgrLinieProd := LineProd;), dann verwendet der SCL-Compiler auch nicht BLKMOV, sondern erzeugt auch ungefähr 10 L/T-AWL-Anweisungen.

PS: Korrektur: man kann keinen FC-Input-Parameter direkt am BLKMOV verschalten, deshalb muss der Wert des Input-Parameters auf eine TEMP-Variable umkopiert werden. Dafür kann man nicht BLKMOV verwenden, sondern muss L/T-Anweisungen verwenden.
 
Zuletzt bearbeitet:
Aber generell kann man String arrays nicht übertragen mit SFC 20?
Aus der SFC20 Hilfe:,
Zulässige Quellbereiche sind:

· Teile von Datenbausteinen
· Merker
· Prozeßabbild der Eingänge
· Prozeßabbild der Ausgänge
Wenn Sie für die Parameter SRCBLK und DSTBLK Variablen vom Datentyp STRING verwenden, interpretiert STEP 7 diese Variablen als ARRAY of BYTE (einschließlich den beiden Verwaltungsbytes mit maximaler und aktueller Länge). Das führt dazu, dass die SFC 20 byteweise kopiert: Kopiert werden also das Byte mit maximaler Länge, das Byte mit aktueller Länge und der eigentliche String.

Wenn bei einem der Parameter SRCBLK oder DSTBLK oder bei beiden der Datentyp STRING zur Anwendung kommen soll, müssen Sie die zugehörigen ANY-Pointer selbst aufbauen. Ist die Quelle ein String, werden maximal nur die aktuell im String enthaltenen Zeichen kopiert. Sind Quelle und Ziel jeweils ein String, wird die aktuelle Länge des Ziels auf die Anzahl der kopierten Zeichen gesetzt.
 
Hallo zusammen, vielen Dank für Eure Antworten!
Code:
L W [AR1, P#0.0]
bedeutet L W P#DB500.DBW18
Das ist genau das, was ich nicht nachvollziehen kann. Wenn W P#DB500.DBW18 geladen wird, dann wird ja erwartet, dass der Inhalt des Feldes DB500.DBW18 geladen wird. Und das ist aktuell 1
18.png
Wenn man aber tatsächlich geladenen Wert sieht, ist es 1002 (wie es auch sein soll). Es ist aber nicht das was im DB500.DBW18 ist. Daher verstehe ich leider nicht, wo der Wert 1002 bezogen wird...
1002.png
Der Code ist in einem FC oder einem FB?
das ist tatsächlich eine FC, ohne Instanz DB. Sonst hätte ich auch vermutet, dass der Wert irgendwo aus eigener Instanz kommt.

Man hätte auch SFC20 BLKMOV verwenden können
im nächsten Schritt wird BLKMOV sogar verwendet um den Zeiger als Temp zu speichern...
blkmove.png
 
Wenn man aber tatsächlich geladenen Wert sieht, ist es 1002 (wie es auch sein soll). Es ist aber nicht das was im DB500.DBW18 ist.
Es wird ja auch nicht das kopiert, was ab DB500.DBB18 steht, sondern der übergebene Wert des ANY-Pointer (P#DB500.DBX18.0 BYTE ...) aus dem Input-Parameter LineProd. Das eigentliche Kopieren aus DB500 macht der BLKMOV
 
Es wird ja auch nicht das kopiert, was ab DB500.DBB18 steht, sondern der übergebene Wert des ANY-Pointer (P#DB500.DBX18.0 BYTE ...) aus dem Input-Parameter LineProd. Das eigentliche Kopieren aus DB500 macht der BLKMOV
verstehe ich richtig, dass der Wert für die unteren Bytes (hier 1002) in einem Any-Zeiger schon von vordefiniert ist, wenn man Any Zeiger erstellt? Weil ich kann sonst nirgends finden, wo das zugewiesen ist. Wenn ich mir die Beispiele aus dem Internet ansehe, wird die S7 ID und Datentype immer explizit angegeben. z.B.
L B#16#10 //10h für s7
T LB 0
L B#16#02 //Typ BYTE
T LB 1

in unserem Programm finde ich eine solche Zuweisung nicht. Da ist nur:
L W [AR1, P#0.0]
T W [AR2, P#0.0]
L W [AR1, P#2.0]
T W [AR2, P#2.0]

Dabei werden ja schon die richtigen Werte angezeigt. Kann es sein, dass wenn man einen Any Zeiger erstellt, dass die unteren Bytes (also Byte 0 und Byte 1) von Anfang an schon mit den Werten 10 und 02 belegt sind? Das wäre jetzt für mich die einzige Erklärung, wie das zustande kommt.
 
Arbeien mit einem ANY_Zeiger

Der ANY_Zeiger ist 10 Byte lang und sihe wie folgt aus:
zB. P#DB1.DBX30.0 10 Byte, im temporären Bereich des FC1 wurde ein ANY_Zeiger definiert. Die temporären Variablen kann man mit LBx, LWx, LDx ansprechen.


ANY-Zeiger für Datenbausteine z.Beispiel P#DB1.DBX30.0 10 Byte
16# in HEX
2# dual
LB0 Byte n fest 16#10 16#10
LB1 Byte n+1 Type 16#02 (Byte)
LB2 Byte n+2 Anzahl (highbyte) 16#00
LB3 Byte n+3 Anzahl (lowbyte) 16#0A 10 Byte
LB4 Byte n+4 DB-NR (highbyte) 16#00
LB5 Byte n+5 DB-NR (lowbyte) 16#01 DB1
LB6 Byte n+6 Bereichszeiger 16#84 DBX
LB7 Byte n+7 " 16#00
LB8 Byte n+8 " 16#00
LB9 Byte n+9 " 2#11110000 30.0


im untenstehenden Beispiel arbeiten wir mit LW also Lokalwort.

UN "M 3.3" // Impuls auswerten M3.3
// der ANY-Zeiger wird nun mit Daten belegt
LAR1 P##ANY_Zeiger // Adressregister mit Anfangsadresse der temp.Variable laden Hier L0.0
L W#16#1002 // Type Byte
T LW [AR1,P#0.0] // in BYte n und n+1 laden
L 10 // Anzahl der Bytes
T LW [AR1,P#2.0] // in Byte n+2 und n+3 laden
L 1 // DB-Nr
T LW [AR1,P#4.0] // in BYte n+4 und n+5
L W#16#8400 // Operandenbereich hier DBX
T LW [AR1,P#6.0] // in Byte n+6 und n+7

/ wir laden hier eine Konstant zB 30 als Byteanfangsadresse, hier kann man über MWxx xbeliebige
// Werte laden. Die Byteadresse muss dreimal nach links geschoben werden, weil die unteren // drei Bits die Bitadresse beinhalten als 0 bis 7. Wir wollen 30.0 adressieren.
L 30 // Quellenanfang (Zeiger) wir woolen aus DB1.DBX30.0 anfangen
SLW 3 // dreimal nach links (im Akku 1)
T LW [AR1,P#8.0] // in Byte n+8 und n+9
// Der ANY_Zeiger sollte jetzt komplett vorbelegt sein, war doch einfach oder ?
www: NOP 0 // Sprungmarke mit Nulloperation, ist halt so !



1726815598262.png
 
verstehe ich richtig, dass der Wert für die unteren Bytes (hier 1002) in einem Any-Zeiger schon von vordefiniert ist, wenn man Any Zeiger erstellt?
Nein, das muss man schon selbst reinschreiben oder dafür sorgen, dass das reingeschrieben wird (z.B. von einem Compiler).

Weil ich kann sonst nirgends finden, wo das zugewiesen ist.
Das macht der AWL/FUP/KOP-Compiler beim Zuweisen des Aktualparameters (Konstante P#DB500.DBX....) an den Übergabeparameter. Weil der Übergabeparameter LineProd als ANY deklariert ist, weiß der Compiler, dass er einen ANY-Pointer basteln muss.

PS:
und weil der BLKMOV im FC keine FC-Input-Parameter direkt verarbeiten kann, muss der Wert des übergebenen ANY-Pointers zuerst in eine TEMP-Variable im FC umkopiert werden (was mit dem obigen Code mit AR1 und AR2 gemacht wird), und die TEMP-Variable kann dann am BLKMOV angeschaltet werden.
 
Arbeien mit einem ANY_Zeiger
(...)
Hier im Thema soll allerdings gar kein ANY-Pointer gebastelt werden, weil der existiert ja schon im FC-Input-Parameter (wurde schon vom AWL/FUP/KOP-Compiler automatisch erstellt). Der Wert des ANY muss nur aus dem FC-Input-Parameter in eine lokale TEMP-Variable umkopiert werden, damit er an BLKMOV verschaltet werden kann.
 
@TE @stalmoro
Man muss nicht alles glauben, was in einem Forum geantwortet wird. :cool: ;)

#2 die Erklärungen sind komplett falsch
#4,6,7 das Thema hier hat nichts mit String kopieren zu tun
#12 das Kopieren geht nicht mit BLKMOV
#14 dein Code von deiner Frage in #1 hat nichts mit ANY-Pointer basteln zu tun
 
Zurück
Oben