# Pointer verändern



## Schnicker (4 März 2010)

Hallo,
ich bin blutiger CodeSys-Anfänger und kämpfe mit folgendem Problem:
Ich habe einen DINT-Wert auf den ich mit einem POINTER TO WORD zeige um das erste wort dieses Wertes zu lesen. Das funktioniert soweit.
Wie aber muss ich den Pointer verändern um auf das zweite Wort zu zeigen? Wenn ich diesen Pointer um 1 erhöhe sollte dieser doch auf das zweite Wort zeigen, da der Pointer doch Wort-gross ist - oder liege ich da falsch?

```
pt:POINTER TO WORD;
wert:DINT;
wort1:WORD;
wort2:WORD;
 
pt := ADR(wert);
wort1:= pt^;
(* was muss da hin? *)
wort2:= pt^;
```
Gruss und Danke


----------



## Cerberus (4 März 2010)

Ich bin mir nicht sicher, aber versuchs mal wie folgt:


```
pt := pt + SIZEOF(WORD);
```


----------



## Mr.Spok (4 März 2010)

Versuchs mal so:



```
pt :=( ADR(wert)+2);
```
 
mfG Jan


----------



## Schnicker (4 März 2010)

Dankeschön erstmal!
Ich habs jetzt so gemacht:

```
pt := pt + SIZEOF(wort1);
```
...wie Mr.Spok vorgeschlagen funktioniert aber auch!


----------



## RobiHerb (4 März 2010)

*Pointer*

Die IEC Norm definiert Pointer aber keine Arithmetik dazu.

Wenn Pointer also nicht als const gesehen werden, ist jede Manipulation abhängig von der Implementation.

In den mir bekannten CoDeSys Implementationen ist die Bedeutung der Incrementation um 1 identisch mit der Erhöhung um eine Byte Adresse. Das ist somit identisch mit der Sprache PLM von Intel. Das ist aber nicht garantiert und könnte sich sogar in einer neuen Version ändern, wenn man z.B. irgendwann mal bei schnellen 32 Implementationen immer 4 Byte weise zugreift. 

Deshalb Prüfungen bei Anlauf des PRG einbauen, Z.B. ein Array von 2 Items anlegen und den Abstand zwischen den Pointern auf diese Items auswerten. 

Immer funktioniert das Prüfen eines Pointers auf NULL und das ist auch der Hauptgrund, wieso es in der Norm Pointer gibt.

In C und Verwandten ist die Erhöhung um 1 identisch mit der Erhöhung um Sizeof Itemtyp, der bei der Declaration des Pointer angegeben wurde.

In C# geht man den sicheren Weg, Pointer sind nicht total tabu, werden aber ausdrücklich als unsave behandelt. Man verwendet Referenzen, was man in CoDeSys mit INOUT Datentypen vergleichen könnte.


----------



## Thomas_v2.1 (4 März 2010)

RobiHerb schrieb:


> Die IEC Norm definiert Pointer aber keine Arithmetik dazu.
> 
> Wenn Pointer also nicht als const gesehen werden, ist jede Manipulation abhängig von der Implementation.
> 
> ...



Zumindest die TwinCAT Hilfe sagt dazu:


> Bitte beachten: Ein Pointer wird byte-weise hochgezählt! Über die Anweisung p=p+SIZEOF(p^); kann ein Hochzählen wie im C-Compiler erreicht werden.
> 
> Achtung:
> Wenn Online Change angewendet wird, können sich Inhalte von Adressen verschieben. Beachten Sie dies bei der Verwendung von Pointern auf Adressen.



In C sieht ein Inkrementieren mit einem ptr++ schöner aus, denn der Compiler kennt eh den Typ auf den der Pointer zeigt und weiß um wieviele Bytes er den Zeiger weitersetzen muss.

Dass so etwas in einer Norm nicht festgelegt wurde ist nicht so schön, denn dann wären solche Bausteine wieder nur Platformabhängig. In der Oscat-Lib habe ich aber auch schon etwas mit Pointerarithmetik gesehen, und das läuft zumindest nicht nur unter Codesys. Siemens SCL muss man wieder außenvor lassen, denn da gibt es keine Pointer sondern nur die AT-Sicht.

Gibt es die komplette Norm 61131 eigentlich irgendwo zu Download?


----------



## ybbs (4 März 2010)

Thomas_v2.1 schrieb:


> Gibt es die komplette Norm 61131 eigentlich irgendwo zu Download?



Guckst du http://www.iec-normen.de/shop/product.php?artikelnr=210408


----------



## RobiHerb (5 März 2010)

*IEC Norm*

Es ist schon sonderbar in unseren Zeiten, wo es Wiki und alles direkt im Net gibt, dass diese Norm von seinen Hütern mit einer "Schutzgebühr" von über 190 Euro der breiten Öffentlichkeit vorenthalten wird.


----------



## Werner29 (5 März 2010)

RobiHerb schrieb:


> In den mir bekannten CoDeSys Implementationen ist die Bedeutung der Incrementation um 1 identisch mit der Erhöhung um eine Byte Adresse. Das ist somit identisch mit der Sprache PLM von Intel. Das ist aber nicht garantiert und könnte sich sogar in einer neuen Version ändern, wenn man z.B. irgendwann mal bei schnellen 32 Implementationen immer 4 Byte weise zugreift.



Ja, schön wäre es, wenn wir sowas noch ändern könnten. Nein, dieses Verhalten wurde (leider) sogar in die V3 Welt gerettet. Was in V3 aber geht, ist der Zugriff mit Index auf einen Pointer:
p[12]. Dieser Zugriff funktioniert dann genauso wie man es von C her kennt und ist identisch zu folgendem Code
(p + 12*SIZEOF(basistyp))^

Pointer sind in der 1131 im übrigen überhaupt nicht vorgesehen.


----------

