# libnodave und AS511



## Ralle (19 Februar 2007)

*AS511 und libnodave*

Hat jemand schon einmal mit libnodave und AS511 auf eine S95U zugegriffen?
Was bedeuteten die Fehlermeldungen im Bild?


----------



## Zottel (19 Februar 2007)

Ohne es sicher zu wissen: Mir scheint, da kommt gar keine Antwort von der SPS. Probe: Stecker von der CPU abziehen, da sollte sich nichts ändern.
Gegenprobe: RS232/TTY-Adapter vom PC abziehen, PIN 2+3 der Schnittstelle verbinden, nun sollte das Testprogramm sein eigenes Zeichen 0x02 zurückbekommen, oder die Schnittstelle hat ein Problem.


----------



## Zottel (19 Februar 2007)

Ralle schrieb:


> Hat jemand schon einmal mit libnodave und AS511 auf eine S95U zugegriffen?
> Was bedeuteten die Fehlermeldungen im Bild?


BTW: Schau dir mal deine Kommandozeile an: Deine Schnitstelle sollte doch wohl COM1 und nicht 1 heißen?????


----------



## Ralle (19 Februar 2007)

@zottel

Hm, klar, ich dachte die Nummer reicht schon mit 'com1' gehts sofort.
Kleine Ursache, große (oder besser Keine) Wirkung.

Muß ich nut noch mal rausbekommen, warum das mit meiner Win-Software nicht will, sicher was Ahnliches:

Danke Zottel!


----------



## Ralle (19 Februar 2007)

Hm, weder mit der Komponente von afk (sein Demoprogramm), noch mit meinem Programm funktioniert das, obwohl beide mit MPI Daten lesen und schreiben.
In der Delphi-Demo von afk (arbeitet mit dem Buffer von von libnodave) werden zwar im Debugmodus von der DLL die richtigen Werte gelesen, aber im Buffer steht dann nur Schrott. (Irgendwo aus dem Arbeitsspeicher, uninitialisiert). Ich stelle den Buffer bereit (alles Null), da stehen nur Nullen drin, offensichtlich wird auch hier nichts in den Buffer geschrieben von ReadBytes.


----------



## Zottel (19 Februar 2007)

Ralle schrieb:


> Hm, weder mit der Komponente von afk (sein Demoprogramm), noch mit meinem Programm funktioniert das, obwohl beide mit MPI Daten lesen und schreiben.
> In der Delphi-Demo von afk (arbeitet mit dem Buffer von von libnodave) werden zwar im Debugmodus von der DLL die richtigen Werte gelesen, aber im Buffer steht dann nur Schrott. (Irgendwo aus dem Arbeitsspeicher, uninitialisiert). Ich stelle den Buffer bereit (alles Null), da stehen nur Nullen drin, offensichtlich wird auch hier nichts in den Buffer geschrieben von ReadBytes.


Das ist richtig. Wo du es sagst, fehlt in daveReadBytes das Kopieren in einen Puffer, den das Anwendungsprogramm zur Verfügung stellt. Im Moment bleibt dir da nur folgendes:
1. Die Daten "Stück für Stück" mittels der Funktionen daveGetXX() aus dem internen Puffer zu holen.
2. Das Kopieren selbst nachbilden. C-Code:

statt:
daveReadBytes(...,...,len,  buffer)

schreibst du:

daveReadBytes(...,...,len, null)
memcpy(buffer, dc->resultPointer, len);


----------



## Ralle (19 Februar 2007)

@Zottel

Danke für deinen Hinweis, das sehe ich mir mal an. 
Eine Frage noch zum Verständnis. Heißt das, daß je nachdem, ob ich s7 (TCP/IP, MPI, s7Online) oder s5 (AS511) einsetze wird die Funktion daveReadBytes innerhalb der libnodavedll anders abgearbeitet? Einmal kann ich einen Pointer auf den Buffer übergeben und bekomme auch Wert da hinein (s7) und bei S5 wird geht das so nicht?


----------



## Zottel (20 Februar 2007)

Ralle schrieb:


> @Zottel
> 
> Danke für deinen Hinweis, das sehe ich mir mal an.
> Eine Frage noch zum Verständnis. Heißt das, daß je nachdem, ob ich s7 (TCP/IP, MPI, s7Online) oder s5 (AS511) einsetze wird die Funktion daveReadBytes innerhalb der libnodavedll anders abgearbeitet? Einmal kann ich einen Pointer auf den Buffer übergeben und bekomme auch Wert da hinein (s7) und bei S5 wird geht das so nicht?


Bei allen S7-Protokollen wird die gleiche Funktion abgearbeitet. Nur wenn das Protokoll AS511 ist, wird zu einer anderen Funktion verzweigt:
Der (vereinfachte*) Code:
{code]
int daveReadBytes(daveConnection * dc,int area, int DBnum, int start,int len, void * buffer){
    PDU p1,p2;
    int res;
    if (protocol==daveProtoAS511) {	    
	return daveReadS5Bytes(dc, area, DBnum, start, len/*, buffer*/);
    }
    /* Hier ist der Fehler, daß unmittelbar nach Aufruf von
     daveReadS5Bytes()
     ein return erfolgt. Deswegen wird der Code zum Kopieren des Puffers
     nie erreicht.
  */
 ...   
    davePrepareReadRequest(dc, &p1);
    daveAddVarToReadRequest(&p1, area, DBnum, start, len);
    res=_daveExchange(dc, &p1);
    res=_daveSetupReceivedPDU(dc, &p2);
    res,daveStrerror(res));
    res=_daveTestReadResult(&p2);
    res,daveStrerror(res));
/*
    copy to user buffer and setup internal buffer pointers:
*/    
    if (buffer!=NULL) memcpy(buffer,p2.udata,p2.udlen);
{/code]
* ohne Debug-Ausgabe und Fehlerbehandlung

Bei den verschiedenen (Transport)-Protokollen der S7-Kommunikation wird halt immer dieselbe PDU erzeugt und dann über den Funktionszeiger
_daveExchange auf verschiedene Weise gegen eine Antwort "eingetauscht".
Die  S5-Kommunikation ist völlig anders. Sie ist halt per if-Entscheidung eingebunden, den Unterschied für den Benuzer zu "verbergen". 
Richtig wäre (nicht getestet):
{code]
    if (protocol==daveProtoAS511) {	    
	res=daveReadS5Bytes(dc, area, DBnum, start, len/*, buffer*/);
        if (buffer!=NULL) memcpy(buffer, dc->msgIn+5,len);
        return res;
    }
{/code]


----------



## Ralle (20 Februar 2007)

Alles klar soweit, danke Zottel


----------

