AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren

DLL Schnitstelle

Ein Thema von hewy · begonnen am 10. Jul 2020 · letzter Beitrag vom 7. Aug 2020
Antwort Antwort
Seite 1 von 4  1 23     Letzte » 
hewy

Registriert seit: 2. Aug 2006
Ort: Arni (Region Zürich) Schweiz
61 Beiträge
 
Delphi XE5 Enterprise
 
#1

DLL Schnitstelle

  Alt 10. Jul 2020, 14:45
Hallo,

Seit mehreren Tagen brüte ich nun schon über folgendes:
Als nicht DLL und auch nicht C/C++ Spezi habe ich hier eine Frage zum Aufruf einer DLL Funktion aus Delphi.
Hier die ‘c’ Seite:

Code:
SE_API_IMPL(se_result_t, se_getCertificationId)(char **certificationId,   uint32_t *certificationIdLength)
Wie würde das Delphi Gegenstück dazu aussehen?

Die DLL function spreche ich in Delphi so an
function se_getCertificationId(var certificationId: PAnsiChar; certificationIdLength: Cardinal): Cardinal; cdecl; external 'se-api-c.dll'; Sicher ein Klacks komme aber hier nicht weiter und wäre daher sehr dankbar für eine Hint oder besser
Code:
In VB.Net sieht es so aus. Brauche aber das Delphi äquivalent.
        ' Get certification ID as assigned by BSI ("BSI-K-TR-0374-2019" for cryptovision TSE).
        ' @param[out] certificationId      Returned identifier string (Not null terminated) [REQUIRED]
        '                                  If successfully executed, the buffer has to freed by the function caller [@ref se_free()].
        ' @param[out] certificationIdLength length of the returned identifier string [REQUIRED]
        ' @return @ref ExecutionOk         execution of the function has been successful
        ' @return @ref ErrorSECommunicationFailed Secure Element communication failed
        ' @since v2.1
        ' se_result_t se_getCertificationId(char**certificationId, uint32_t*certificationIdLength);
        <DllImport("se-api-c.dll", EntryPoint:="se_getCertificationId", CharSet:=CharSet.Ansi)>
        Private Function GetCertificationIdSub(ByRef certificationId As IntPtr,
                                               ByRef certificationIdLength As Integer) As SeReturnCode
        End Function
        Public Structure GetCertificationIdReturn
            Public ReturnCode As SeReturnCode
            Public certificationId As String
        End Structure
        Public Function GetCertificationId()
            Dim ReturnStruct As GetCertificationIdReturn
            Dim certificationId As IntPtr
            Dim certificationIdLength As Integer
            ReturnStruct.ReturnCode = GetCertificationIdSub(certificationId, certificationIdLength)
            If SeReturnCode.ExecutionOk = ReturnStruct.ReturnCode Then
                ReturnStruct.certificationId = PtrToStringAnsiAndFree(certificationId, certificationIdLength)
            Else
                ReturnStruct.certificationId = String.Empty
            End If
            Return ReturnStruct
        End Function
Vielen Dank für jegliche Hilfe
Heiri
Heinrich Wyssen

Geändert von hewy (11. Jul 2020 um 10:33 Uhr)
  Mit Zitat antworten Zitat
TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
2.957 Beiträge
 
Delphi 10.4 Sydney
 
#2

AW: DLL Schnitstelle

  Alt 10. Jul 2020, 15:01
Code:
SE_API_IMPL(se_result_t, se_getCertificationId)(char **certificationId, uint32_t *certificationIdLength)
-> declare se_getCertificationId as function (pointer to pointer to char, pointer to uint32_t) returning se_result_t
Delphi-Quellcode:
type
  se_result_t = Cardinal; //? musst du in der Doku gucken was se_result_t sein soll
  PUInt32 = ^System.UInt32;
  PPByte = ^System.PByte;


function se_getCertificationId(var certificationId: PAnsiChar; certificationIdLength: PUInt32): se_result_t ; cdecl; external 'se-api-c.dll';
//oder
function se_getCertificationId(var certificationId: PAnsiChar; var certificationIdLength: UInt32): se_result_t ; cdecl; external 'se-api-c.dll';
// probiere auch mal so, wenn certificationID eh ne Zahl zwischen 0 und 255 laut Doku ist:
function se_getCertificationId(var certificationId: PByte; var certificationIdLength: UInt32): se_result_t ; cdecl; external 'se-api-c.dll';
// gerne auch
function se_getCertificationId(certificationId: PPByte; certificationIdLength: PUInt32): se_result_t ; cdecl; external 'se-api-c.dll';
  Mit Zitat antworten Zitat
hewy

Registriert seit: 2. Aug 2006
Ort: Arni (Region Zürich) Schweiz
61 Beiträge
 
Delphi XE5 Enterprise
 
#3

AW: DLL Schnitstelle

  Alt 10. Jul 2020, 15:30
Oh vielen Dank für deine Antwort.
- se_result_t enthält ein Fehler Code falls es nicht korrekt durch läuft 0. Bei mir kommt immer 'fehlender Parameter'
- var certificationId: PAnsiChar sollte die gesuchte ID zurückliefern bei der VB Version bekomme ich das hier 'BSI-K-TR-0000-2019' bei Delphi eben noch nicht! Humm
Heiri
Heinrich Wyssen
  Mit Zitat antworten Zitat
TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
2.957 Beiträge
 
Delphi 10.4 Sydney
 
#4

AW: DLL Schnitstelle

  Alt 10. Jul 2020, 15:46
Zeig doch mal deinen Quelltext, wo du die Funktion aufrufst.
Hast du alle beide PAnsiChar-Varianten mal durchprobiert?

EDIT: Ändere mal bei se_result_t von Cardinal zu einen Int32.
Da du nicht die Definition aus dem C-Header gepostet hast, nehme ich einfach mal an, dass da ggf. auch negative Werte rausfallen können?!
  Mit Zitat antworten Zitat
Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
40.034 Beiträge
 
Delphi 11 Alexandria
 
#5

AW: DLL Schnitstelle

  Alt 10. Jul 2020, 15:53
Sicher, dass es cdecl oder nicht vielleicht stdcall ist?

Wie sieht denn SE_API_IMPL aus?




[OT]
Hach, wie schön es bald mit 64 Bit wird ... da gibt's nur noch eine Convention (die fast wie bei unserem Pascal aussieht )
Garbage Collector ... Delphianer erzeugen keinen Müll, also brauchen sie auch keinen Müllsucher.
Delphi-Tage 2005-2014

Geändert von himitsu (10. Jul 2020 um 15:55 Uhr)
  Mit Zitat antworten Zitat
hewy

Registriert seit: 2. Aug 2006
Ort: Arni (Region Zürich) Schweiz
61 Beiträge
 
Delphi XE5 Enterprise
 
#6

AW: DLL Schnitstelle

  Alt 11. Jul 2020, 10:21
Vielen Dank für eure Hilfe versuche.

Jetzt habe ich auch begriffen wie man hier korrekt Code schnipsel einfügt!
Insgesammt sind es über 50 Funktionen, die meisten sind ok nur 'se_getCertificationId' will nicht so recht.
So sehen die Einbindungen der DLL Funktionen aus:
Delphi-Quellcode:
function se_getImplementationVersionString(): PAnsiChar; cdecl; external 'se-api-c.dll';
function se_getImplementationVersion(): PAnsiChar; cdecl; external 'se-api-c.dll';
function se_getUniqueId(): PAnsiChar; cdecl; external 'se-api-c.dll';

function se_getCertificationId(var certificationId: PAnsiChar; certificationIdLength: Cardinal): Cardinal; cdecl; external 'se-api-c.dll';

function se_getLifeCycleState(var lcs: Cardinal): Cardinal; cdecl; external 'se-api-c.dll';
function se_getMaxNumberOfClients(var maxNumberClients: Cardinal): Cardinal; cdecl; external 'se-api-c.dll';
Und hier die Aufrufe dazu:
Delphi-Quellcode:
function SeGetPinStatus(var PINState: Cardinal): TSeReturnCode;
function SeGetUniqueId: string;

function SeGetCertificationId(var CertificationId: string): TSeReturnCode;

function SeAuthenticateUser(UserId: string; PIN: array of Byte; var AuthenticationResult: TSeAuthenticationResult; var RemainingRetrie: ShortInt): TSeReturnCode;
function SeGetLifeCycleState(var lcs: TSeLifeCycleState): TSeReturnCode;
Und die Implementation dazu (Hier mache ich eiregend etwas falsch und komme nicht dahinter was wie gemacht werden muss.)

Delphi-Quellcode:
function SeGetCertificationId(var CertificationId: string): TSeReturnCode;
var
  PCertificationID: PAnsiChar;
  PCurrent: PAnsiChar;
  CertificationIDLength: Cardinal;
  i: Cardinal;
begin
  PCertificationID := nil;

  // VB übergibt PCertificationID = &H000000000 und CertificationIDLength = 0

  Result := TSeReturnCode(se_getCertificationID(PCertificationID, CertificationIDLength));

  // Zurück bekomme ich im VB Code BSI-K-TR-0000-2019 für PCertificationID und 18 für CertificationIDLength

  // Mit Delphi und der Zeile oben einen Fehlercode

  // Da werde ich die Parameter entsprechend übernehme sobalt
  // mir se_getCertificationID was brauchbares liefert.
  // Aktuell erhalte ich hier Access Violation oder der Result code sagt
  // etwas von 'missing parameter'

end;
Vielen Dank schon mal für die Auswertung meiner Angaben und etwelche wie was wo zu tun ist Hints!
Heinrich Wyssen

Geändert von hewy (11. Jul 2020 um 10:49 Uhr)
  Mit Zitat antworten Zitat
venice2

Registriert seit: 5. Dez 2019
Ort: Köln
1.032 Beiträge
 
Delphi 2010 Architect
 
#7

AW: DLL Schnitstelle

  Alt 11. Jul 2020, 10:46
Das.
function se_getCertificationId(certificationId: PPByte; certificationIdLength: PUInt32): se_result_t ; cdecl; external 'se-api-c.dll';

kann nur ins leere laufen denn ByRef ist immer var in Delphi ByVal ist einfach ein Parameter der übergeben wird.
Und dann was denn nun?

PCertificationID: PAnsiChar; oder CertificationId: string beides geht auf keinen Fall wenn schon dann PCertificationID: PAnsiChar; entfernen und Rückgabe ist CertificationId: string
Wenn CertificationId ein Pointer auf AnsiString ist (siehe PtrToStringAnsiAndFree) dann bitte CertificationID: PAnsiChar und nicht CertificationID: string .

Alles durcheinander geworfen sorry.
Siehe

function SeGetCertificationId(var CertificationId: string): TSeReturnCode;
und
function SeGetCertificationId(var CertificationId: PAnsiChar): TSeReturnCode;

Die Definition
PCertificationID: PAnsiChar;
ist dann unsinnig.

Korrekt wäre das ohne Gewähr.

Delphi-Quellcode:
function SeGetCertificationId(var CertificationId: PAnsiChar): TSeReturnCode;
var
  // PCertificationID: PAnsiChar; // Quatsch
  // PCurrent: PAnsiChar; wird nicht verwendet
  CertificationIDLength: Cardinal;
  // i: Cardinal; wird nicht verwendet
begin
  // PCertificationID := nil; Quatsch

  // VB übergibt PCertificationID = &H000000000 und CertificationIDLength = 0

  Result := TSeReturnCode(se_getCertificationID(CertificationID, CertificationIDLength));

  // Zurück bekomme ich im VB Code BSI-K-TR-0000-2019 für PCertificationID und 18 für CertificationIDLength

  // Mit Delphi und der Zeile oben einen Fehlercode

  // Da werde ich die Parameter entsprechend übernehme sobalt
  // mir se_getCertificationID was brauchbares liefert.
  // Aktuell erhalte ich hier Access Violation oder der Result code sagt
  // etwas von 'missing parameter'

end;
Nochmal var certificationId: PAnsiChar oder var certificationId: string entscheide dich einfach mal.

function se_getCertificationId(var certificationId: PAnsiChar; certificationIdLength: Cardinal): Cardinal; cdecl; external 'se-api-c.dll';

Geändert von venice2 (11. Jul 2020 um 11:22 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
40.034 Beiträge
 
Delphi 11 Alexandria
 
#8

AW: DLL Schnitstelle

  Alt 11. Jul 2020, 11:20
Das PAnsiChar <> String UnicodeString (seit Delphi 2009) wollte ich auch grade ansprechen.

Zitat:
Delphi-Quellcode:
function SeGetCertificationId(var CertificationId: string): TSeReturnCode;
var
  PCertificationID: PAnsiChar;
  PCurrent: PAnsiChar;
  CertificationIDLength: Cardinal;
  i: Cardinal;
begin
  PCertificationID := nil;

  // VB übergibt PCertificationID = &H000000000 und CertificationIDLength = 0

  Result := TSeReturnCode(se_getCertificationID(PCertificationID, CertificationIDLength));
  ...
Der Code ist so nichtmal kompilierbar.
Wieso ignoriert hier jemand die Compilerwarnungen?
Und wenn VB das macht, warum du nicht auch?

CertificationIDLength wurde nicht initialisiert
PCertificationID = string -> PAnsiChar

Und wenn VB das macht, dann vermutlich um erstmal im Result die nötige Länge abzufragen, welche für einen weiteren Aufruf benutzt wird.

Man kann alternativ auch blind den Speicher auf eine Länge festlegen, die "immer" ausreichend wäre,
und anschließend auf das zurück ändern, was wirklich benutzt wurde.

Probleme:
* falsche Typen (ANSI <> Unicode)
* falsche Benutzung (ungültige Parameter)

Entweder intern mit ANSI arbeiten und umkopieren oder die umgebende Funktion mit einem AnsiString bauen.
Garbage Collector ... Delphianer erzeugen keinen Müll, also brauchen sie auch keinen Müllsucher.
Delphi-Tage 2005-2014

Geändert von himitsu (11. Jul 2020 um 11:25 Uhr)
  Mit Zitat antworten Zitat
hewy

Registriert seit: 2. Aug 2006
Ort: Arni (Region Zürich) Schweiz
61 Beiträge
 
Delphi XE5 Enterprise
 
#9

AW: DLL Schnitstelle

  Alt 11. Jul 2020, 11:28
Vielen Dank venice2,

hilft mir schon mal weiter.
Delphi-Quellcode:
function SeGetCertificationId(var CertificationId: string): TSeReturnCode;
var
  PCertificationID: PAnsiChar;
  PCurrent: PAnsiChar;
  CertificationIDLength: Cardinal;
  i: Cardinal;
begin
  PCertificationID := nil;

  // VB übergibt PCertificationID = &H000000000 und CertificationIDLength = 0

  Result := TSeReturnCode(se_getCertificationID(PCertificationID, CertificationIDLength));

  // Zurück bekomme ich im VB Code BSI-K-TR-0000-2019 für PCertificationID und 18 für CertificationIDLength

  // Der var Parameter im Header der Funktion sollte für meine Zwecke schon [B]string[/B] sein

  // Dann müsste ich halt dies entsprechend konvertieren.
  // Zum Beispiel so
  CertificationId := String(AnsiString(PCertificationID)); // Oder sehe ich das falsch?

  // Nur eben die Funktion se_getCertificationID liefert nichts brauchbares in Delphi
  // Also müsste wohl PCertificationID: PAnsiChar; anders definiert sein oder anders
  // initialisiert werden, [B]da liegt offenbar mein Problem. [/B]

end;
Heinrich Wyssen
  Mit Zitat antworten Zitat
venice2

Registriert seit: 5. Dez 2019
Ort: Köln
1.032 Beiträge
 
Delphi 2010 Architect
 
#10

AW: DLL Schnitstelle

  Alt 11. Jul 2020, 11:32
Ich würde den Kram so umschreiben wenn für CertificationIDLength keine Rückgabe erforderlich ist.

Zitat:
CertificationIDLength wurde nicht initialisiert
PCertificationID = string -> PAnsiChar
function SeGetCertificationId(var CertificationId: PAnsiChar; CertificationIDLength: Cardinal): TSeReturnCode;
Delphi-Quellcode:
if SeGetCertificationId(CertificationId, 0) = ExecutionOk then
  bla, bla
EDIT:
CertificationId := String(AnsiString(PCertificationID)); // Oder sehe ich das falsch?
Ja. Du benötigst die Variable PCertificationID nicht!
Die Rückgabe ist ein Pointer auf Ansistring (PAnsiChar) siehe (PtrToStringAnsiAndFree) kein String!

Geändert von venice2 (11. Jul 2020 um 11:43 Uhr)
  Mit Zitat antworten Zitat
Themen-Optionen Thema durchsuchen
Thema durchsuchen:

Erweiterte Suche
Ansicht

Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 06:25 Uhr.
Powered by vBulletin® Copyright ©2000 - 2022, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2021 by Daniel R. Wolf