AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

COM Ports im System auslesen

Ein Thema von Moony · begonnen am 11. Aug 2008 · letzter Beitrag vom 12. Mär 2020
Antwort Antwort
Seite 1 von 4  1 23     Letzte »    
Moony

Registriert seit: 29. Jul 2003
Ort: Essen
454 Beiträge
 
Delphi 2010 Professional
 
#1

COM Ports im System auslesen

  Alt 11. Aug 2008, 11:31
Hallo zusammen,

ich möchte alle im System angemeldeten, seriellen Ports auslesen. Egal ob on Board, via PCI Karte oder USB-To-Serial.

Hoffe mir kann jemand helfen.

Danke & Gruß, Moony
Ich weiß, daß ich nichts weiß! Sokrates
  Mit Zitat antworten Zitat
Reinhard Kern

Registriert seit: 22. Okt 2006
772 Beiträge
 
#2

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 11:45
Zitat von Moony:
Hallo zusammen,

ich möchte alle im System angemeldeten, seriellen Ports auslesen. Egal ob on Board, via PCI Karte oder USB-To-Serial.

Hoffe mir kann jemand helfen.

Danke & Gruß, Moony
Hallo,

am einfachsten von COM1 bis COMx (256 sollte reichen) iterieren, dann ist man nicht von speziellen Registry-Inhalten abhängig. Öffnen lassen sich natürlich nur Schnittstellen, die vorhanden sind und nicht von einem anderen Programm verwendet werden. Bei den "besetzten" lässt sich nur die Existenz anzeigen.

Gruss Reinhard
  Mit Zitat antworten Zitat
Benutzerbild von christian.noeding
christian.noeding

Registriert seit: 26. Mai 2005
Ort: Knw.-Remsfeld
119 Beiträge
 
Delphi XE2 Professional
 
#3

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 12:50
Hi,


habe auch lange nach einer sauberen Methode gesucht. Diese hier erkennt alle COM-Ports und zeigt auch die Beschreibung an. Die COM-Ports werden bei meiner Funktion in die Combobox "portchange" eingefügt. Es wird die SetupAPI der Jedis benötigt:

Delphi-Quellcode:
procedure SearchSerialPorts;
const
  GUID_DEVINTERFACE_COMPORT: TGUID = '{86e0d1e0-8089-11d0-9ce4-08003e301f73}';
  GUID_DEVINTERFACE_SERENUM_BUS_ENUMERATOR: TGUID = '{4D36E978-E325-11CE-BFC1-08002BE10318}';
var
  PnPHandle: HDEVINFO;
  DevData: TSPDevInfoData;
  DeviceInterfaceData: TSPDeviceInterfaceData;
  FunctionClassDeviceData: PSPDeviceInterfaceDetailData;
  Success: LongBool;
  Devn: Integer;
  BytesReturned: DWORD;
  SerialGUID: TGUID;
  Inst: DEVINST;
  RegKey: HKEY;
  RegBuffer: array [0..1023] of Char;
  RegSize, RegType: DWORD;
  FriendlyName: string;
  PortName: string;
  DeviceDescription: string;
  Bus: string;
begin
  // these API conversions are loaded dynamically by default
  LoadSetupApi;
  LoadConfigManagerApi;

  // enumerate all serial devices (COM port devices)
    SerialGUID := GUID_DEVINTERFACE_COMPORT; // GUID_DEVINTERFACE_SERENUM_BUS_ENUMERATOR;

  PnPHandle := SetupDiGetClassDevs(@SerialGUID, nil, 0, DIGCF_PRESENT or DIGCF_DEVICEINTERFACE);
  if PnPHandle = Pointer(INVALID_HANDLE_VALUE) then
    Exit;

  // Combobox klarmachen
  portchange.Items.BeginUpdate;
  portchange.Items.Clear;

  Devn := 0;
  repeat
    DeviceInterfaceData.cbSize := SizeOf(TSPDeviceInterfaceData);
    Success := SetupDiEnumDeviceInterfaces(PnPHandle, nil, SerialGUID, Devn, DeviceInterfaceData);
    if Success then
    begin
      DevData.cbSize := SizeOf(DevData);
      BytesReturned := 0;
      // get size required for call
      SetupDiGetDeviceInterfaceDetail(PnPHandle, @DeviceInterfaceData, nil, 0, BytesReturned, @DevData);
      if (BytesReturned <> 0) and (GetLastError = ERROR_INSUFFICIENT_BUFFER) then
      begin
        // allocate buffer and initialize it for call
        FunctionClassDeviceData := AllocMem(BytesReturned);
        FunctionClassDeviceData.cbSize := SizeOf(TSPDeviceInterfaceDetailData);

        if SetupDiGetDeviceInterfaceDetail(PnPHandle, @DeviceInterfaceData,
          FunctionClassDeviceData, BytesReturned, BytesReturned, @DevData) then
        begin
          // gives the friendly name of the device as shown in Device Manager
          FriendlyName := GetRegistryPropertyString(PnPHandle, DevData, SPDRP_FRIENDLYNAME);
          // gives a device description
          DeviceDescription := GetRegistryPropertyString(PnPHandle, DevData, SPDRP_DEVICEDESC);
          // now try to get the assigned COM port name
          RegKey := SetupDiOpenDevRegKey(PnPHandle, DevData, DICS_FLAG_GLOBAL, 0, DIREG_DEV, KEY_READ);
          RegType := REG_SZ;
          RegSize := SizeOf(RegBuffer);
          RegQueryValueEx(RegKey, 'PortName', nil, @RegType, @RegBuffer[0], @RegSize);
          RegCloseKey(RegKey);
          PortName := RegBuffer;
          Inst := DevData.DevInst;
          CM_Get_Parent(Inst, Inst, 0);
          Bus := ExtractBus(GetDeviceID(Inst));
            
          // COM-Ports in Combobox eintragen
          portchange.Items.Add(PortName + ' (' + DeviceDescription + ', ' + Bus+')');
        end;
        FreeMem(FunctionClassDeviceData);
      end;
    end;
    Inc(Devn);
  until not Success;
  SetupDiDestroyDeviceInfoList(PnPHandle);

  // Combobox freigeben
  portchange.Items.EndUpdate;

  // unload API conversions
  UnloadSetupApi;
  UnloadConfigManagerApi;
end;

Das führt dann zu dem Ergebnis im Anhang.




eine alternative Suchmethode, die allerdings keine Beschreibung des COM-Ports anzeigt:

Delphi-Quellcode:
// COM-Ports von 1 bis 16 abklappern
  portchange.Clear;
  for i:=1 to 16 do
  begin
    TestHandle := CreateFile(PChar('\\.\COM'+IntToStr(i)),GENERIC_READ or GENERIC_WRITE,0,nil,OPEN_EXISTING,FILE_FLAG_OVERLAPPED,LongInt(0));
    if (TestHandle > 0) then
    begin
      portchange.Items.Add('COM'+inttostr(i));
      CloseHandle(TestHandle);
    end;
  end;

Viel Erfolg,
Christian
Miniaturansicht angehängter Grafiken
comport_213.png  
Christian Nöding
  Mit Zitat antworten Zitat
Moony

Registriert seit: 29. Jul 2003
Ort: Essen
454 Beiträge
 
Delphi 2010 Professional
 
#4

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 13:56
Danke für die fixe Antwort. Ich werde beide Routinen mal ausprobieren und dann bescheid geben.

Gruß, Moony


Aso, wo finde ich die SetupAPI ???
Ich weiß, daß ich nichts weiß! Sokrates
  Mit Zitat antworten Zitat
Benutzerbild von christian.noeding
christian.noeding

Registriert seit: 26. Mai 2005
Ort: Knw.-Remsfeld
119 Beiträge
 
Delphi XE2 Professional
 
#5

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 14:04
Da nimmste einfach den ersten Google-Eintrag bei der Suche "Jedi Setup API"


Jedi SetupAPI bei Sourceforge.NET


Deeplink zur Version 3.15



ciao,
Christian



PS: es müssen in deine Applikation dann folgende Dateien eingebunden werden:

Delphi-Quellcode:
uses
  JwaWinType,
  SetupApi, Cfg, CfgMgr32;
Christian Nöding
  Mit Zitat antworten Zitat
Moony

Registriert seit: 29. Jul 2003
Ort: Essen
454 Beiträge
 
Delphi 2010 Professional
 
#6

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 14:32
Also, die Alternativeroutine macht es falsch. Ich habe nur einen seriellen Port und dennoch fügt sie mir weitere Ports hinzu.

Die JEdi Geschichte bekomme ich irgendwie nicht angebunden. Habe es mir runtergeladen, das in mein Lib verzeichnis kopiert und in den Umgebungsoptionen das Verzeichnis für die jedis angegeben. Aber delphi erkennt diesen immer noch nicht...
Ich weiß, daß ich nichts weiß! Sokrates
  Mit Zitat antworten Zitat
Benutzerbild von christian.noeding
christian.noeding

Registriert seit: 26. Mai 2005
Ort: Knw.-Remsfeld
119 Beiträge
 
Delphi XE2 Professional
 
#7

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 14:38
Die "alternative" Methode öffnet jeden seriellen Comport von 1 bis 16 und prüft, ob man auf den Port schreiben kann. Wenn du jetzt natürlich irgendwelche Bluetoothgeräte oder andere Treiber für virtuelle Comports hast, werden die natürlich auch aufgelistet.


Bei der SetupAPI muss das Verzeichnis "..\jedi-api-lib\jwapi\trunk\SaCMAPI" (SetupAPI-Dateien) und das Verzeichnis "..\jedi-api-lib\jwapi\trunk\Win32API" (Win32-API-Dateien) mit in den Suchpfad rein, sonst geht es natürlich nicht.
Christian Nöding
  Mit Zitat antworten Zitat
Moony

Registriert seit: 29. Jul 2003
Ort: Essen
454 Beiträge
 
Delphi 2010 Professional
 
#8

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 14:57
Hab die beiden Verzeichnisse jetzt im Suchpfad des Projekts eingebunden. In der Uses sind alle Unit angegeben, die du mir gesagt hast. Beim Kompilieren kommt die Fehlermeldung, dass folgende Datei nicht gefunden wurde: jediapilib.inc
Ich weiß, daß ich nichts weiß! Sokrates
  Mit Zitat antworten Zitat
Benutzerbild von christian.noeding
christian.noeding

Registriert seit: 26. Mai 2005
Ort: Knw.-Remsfeld
119 Beiträge
 
Delphi XE2 Professional
 
#9

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 18:40
Sorry, war unterwegs...


dann musst du halt noch das Verzeichnis "..\jedi-api-lib\jwapi\trunk\Common" mit in den Uses-PFad einbinden. Dort ist nämlich diese inc-Datei drin.


ciao,
Chris
Christian Nöding
  Mit Zitat antworten Zitat
Benutzerbild von Chemiker
Chemiker

Registriert seit: 14. Aug 2005
1.859 Beiträge
 
Delphi 11 Alexandria
 
#10

Re: COM Ports im System auslesen

  Alt 11. Aug 2008, 21:49
Hallo Moony,

willst Du nur die Informationen welche COM-Ports im Rechner vorhanden sind, oder willst Du auch Daten senden/empfangen?

Bis bald Chemiker
wer gesund ist hat 1000 wünsche wer krank ist nur einen.
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 1 von 4  1 23     Letzte »    


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 12:57 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz