Seite 1 von 1

DLL dezimal zu ascii

Verfasst: 23.03.2013 20:18
von twofel
Hallo,

brauche mal eure Hilfe. Eine Meßtechnik-Software benötigt eine DLL um gewisse Aktionen auszuführen.

Einige Prozeduren zur Übergabe der PArameter sind vorgegeben.

So z.B. diese hier: ( hier wird Wert an in1 nur an out1 übergeben)

Code: Alles auswählen

; check inputs and set outputs while running...

ProcedureDLL CCalculate(*PInput.sDLLParams, *POutput.sDLLParams, *PUser.sDLLParams)

  Protected in1.d, out1.d

  in1 = *PInput\DLLParam[0]
    
  out1 = in1
    
  *POutput\DLLParam[0] = out1
 

EndProcedure
in1 ist der Eingang eines Bauteils...hier lese ich den Inhalt eines 16 bit Registers ein.

An out1 ( der entsprechende Ausgang) soll aber der ASCII Wert von in1 erscheinen.

Also sind das 2 ASCII Strings. Allerdings muessen die auch noch in der richtigen Reihefolge erscheinen.
D.h. das LSB des Registerinhaltes muss als zweites Zeichen und das MSB als erstes Zeichen an "out2" erscheinen.


z.b. Inhalt Register = 20051 (dec) entspricht hex = 4E 53 also ASCII = N S und vertauscht dann ASCII = SN
Dieser ASCII Wert muss dann an "out2" stehen.

Da ich noch nicht so fit in PUREBASIC bin, ich aber diese DLL unbedingt in dieser Sprache programmieren möchte,
wäre ich fuer eure Hilfestellung dankbar.


Gruss

Tim

Re: DLL dezimal zu ascii

Verfasst: 23.03.2013 20:44
von NicTheQuick
Also einfach nur die zwei Bytes verdrehen?

Code: Alles auswählen

; check inputs and set outputs while running...

ProcedureDLL CCalculate(*PInput.sDLLParams, *POutput.sDLLParams, *PUser.sDLLParams)
	
	Protected in1.u, out1.u ;unsigned 16-Bit Werte anstatt Doubles!
	
	in1 = *PInput\DLLParam[0]
	
	out1 = ((in1 & $ff) << 8) | (in1 >> 8)
	
	*POutput\DLLParam[0] = out1
	
	
EndProcedure
//Edit: Danke, ts-soft.

Re: DLL dezimal zu ascii

Verfasst: 23.03.2013 20:46
von ts-soft
Funktioniert das denn mit den Doubles?

Re: DLL dezimal zu ascii

Verfasst: 23.03.2013 20:48
von NicTheQuick
Wohl eher nicht. Ist mir aber auch nicht aufgefallen. Hab das ganze nicht getestet. Jetzt ist es korrigiert.

Re: DLL dezimal zu ascii

Verfasst: 23.03.2013 21:03
von twofel
danke @ NicTheQuick und ts-soft.

Habs mal kurz getetstet....also die Bytes sind gedreht....funktioniert soweit.

Danke !!

Wie kriege ich jetzt den entspechenden ASCII -Wert der beiden bytes an den Ausgang "out1" ?

Muss ich eine neue Stringvariable noch hinzufügen ?



//Edit

Re: DLL dezimal zu ascii

Verfasst: 23.03.2013 22:19
von NicTheQuick
Ob da jetzt ein B oder 66 steht, macht doch keinen Unterschied. Ein B ist ja auch nur eine bestimmte Zahl nach dem ASCII-Code eben.

Also nach deiner Beschreibung musst du doch nicht mehr machen als die Bytes zu drehen, oder?

Also ich verstehe nicht, was du mit ASCII Wert meinst. out1 ist ja ein 16-Bit-Wert, kann aber auch als String mit zwei Zeichen interpretiert werden. Aber jeder Buchstabe in diesem String ist ja auch nichts anderes als eine Zahl. Das heißt wenn ich die beiden 8-Bit-Zahlen tausche, sind ja automatisch auch die Buchstaben vertauscht. Dann redest du noch von einem "out2", was ich aber nirgendwo sehe.

Weiterhin hab ich keine Ahnung, was sDLLParams für eine Struktur ist, kann also ab jetzt nur noch raten.

Re: DLL dezimal zu ascii

Verfasst: 24.03.2013 15:07
von twofel
Hallo NicTheQuick,

ja du hast Recht. Letztlich muss man nur den Digitalwert interpretieren, um die
entsprechenden ASCII Zeichen zu erhalten.

Was die Struktur betrifft, die sieht so aus.

Code: Alles auswählen

Structure sDLLParams
  DLLParam.d[100]
EndStructure
Ich glaube, ich habe auch die falsche Prozedur erwischt. Jedenfalls habe ich gesehen, dass der Hersteller der Meßtechniksoftware
auch eine andere Prozedur zur Verarbeitung von Zeichenketten zur Verfügung stellt. Die müsste halt in PureBasic umgeschrieben werden.

hier die Herstellervorgaben:

Delphi: Procedure CalculateEx(PInput,POutput,PUser: PDLLParams; PStrings: PStringParams);
C++: void _stdcall CCalculateEx(double *PInput, double *POutput, double *PUser; StringParam PStrings)
Diese Methode wurde eingeführt um zusätzlich die Verarbeitung von Zeichenketten durch eine DLL zu ermöglichen und kann bei Bedarf alternativ
zu CALCULATE verwendet werden. Die Zeichenketten werden mit dem Parameter PSTRINGS übergeben. Dabei handelt es sich um eine Zeigervariable, deren Delphi-Deklaration so aussieht:

type TStringParams = array[0..100] of PChar;
PStringParams = ^TStringParams;

Re: DLL dezimal zu ascii

Verfasst: 25.03.2013 13:28
von twofel
Hallo,

soo..nachdem ich die richtige Prozedur fand, habe ich folgenden Code unter Nutzung der Hilfestellung von NicTheQuick
geschrieben.

Code: Alles auswählen

ProcedureDLL CCalculateEx(*PInput.sDLLParams, *POutput.sDLLParams, *PUser.sDLLParams,*PStrings.sStringParams)
   
   Protected  in1.u;unsigned 16-Bit Werte anstatt Doubles!
   Protected  ausgang1.s, out1.s,i.i
   
   ; in1 erhält Inhalt eines 16 bit Registers
   in1 = *PInput\DLLParam[0]
   
   ; Vertauschen der Bytereihenfolge (Endianness)  und Umwandlung in 2 HEX-Ausdrücke
   ausgang1.s = Hex(((in1 & $ff) << 8) | (in1 >> 8))
   
 
   ;Umwandlung von Hex in 2 ASCII Zeichen
   For i = 1 To (Len(ausgang1)/2)+1 Step 2 
  
    out1.s = out1 + Chr(Val("$"+Mid(ausgang1, i, 2))) 
  Next i 
    
  ;Übergabe des ASCII Strings
   *PStrings\StringParam[0] = out1   
   
   
 EndProcedure 
 
Ziel sollte ja sein den übergebenen Wert eines 16bit Registers in einen ASCII-String umzuwandeln und diesen dann
wieder an einen "Ausgangsparameter" der DLL zu übergeben.

Könnt ihr mal bitte drübergucken, ob es programmiertechnisch so ok ist .
Für Verbesserungshinweise wäre ich dankbar.

PS:
Die DLL, in der diese Prozedur vorkommt konnte ich in der Meßtechniksoftware mit erfolg testen.

Re: DLL dezimal zu ascii

Verfasst: 25.03.2013 15:07
von NicTheQuick
Mir stellt sich immer noch die Frage, warum die DLLParams-Structure Doubles enthält. Soll da wirklich mit Doubles gearbeitet werden?

Ansonsten scheint deine Methode zu funktionieren, aber einfacher wäre diese hier:

Code: Alles auswählen

in1.i = ...

in1Inverse = ((in1 & $ff) << 8) | (in1 >> 8)

ausgabe1.s = PeekS(@in1, 2)
out1.s = PeekS(@in1Inverse, 2)

Debug in1
Debug in1Inverse

Debug ausgabe1
Debug out1

Re: DLL dezimal zu ascii

Verfasst: 25.03.2013 17:01
von twofel
@NicTheQuick

Man oh man....das ist aber extrem kurz. Für meine Zwecke muesste
dann folgender Code reichen. PeekS...ist aber ein schöner Befehl :mrgreen:

Code: Alles auswählen

in1.i = < dec-zahl>

out1.s = PeekS(@in1, 2)

Die DLLParams-Structur ist in Doubles von der Messtechniksoftware vorgegeben...da kann ich nichts ändern.

Es heisst dort:

Alle drei Pointer PINPUT, POUTPUT und PUSER zeigen jeweils auf einen Speicherbereich in dem 100 Variablen vom Typ
EXTENDED in einem Array abgelegt sind. Die Pointer sind vom Typ PDLLParams, dessen Deklaration in Delphi so aussieht:

type TDLLParams = array[0..100] of extended;
PDLLParams = ^TDLLParams;

In C++ wird dieser Speicherbereich z.B. als (double *PInput) übergeben. ................................