AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Programmierung allgemein Win32/Win64 API (native code) Delphi Hilfe bei Übersetzung von C nach Delphi
Thema durchsuchen
Ansicht
Themen-Optionen

Hilfe bei Übersetzung von C nach Delphi

Ein Thema von c.wuensch · begonnen am 14. Jul 2008 · letzter Beitrag vom 16. Jul 2008
Antwort Antwort
c.wuensch

Registriert seit: 19. Dez 2004
Ort: Münster
96 Beiträge
 
#1

Hilfe bei Übersetzung von C nach Delphi

  Alt 14. Jul 2008, 21:11
Hi an alle,

Ich hab die Frage hier schonmal gestellt, aber mach jetzt nochmal einen neuen Thread damit der Titel besser passt.

Ich möchte den Power-Status (aktiv / Standby) einer Festplatte auslesen.

Folgender Delphi-Code bewirkt, dass die Platte in Standby versetzt wird (Dank an hathor):
Delphi-Quellcode:
Type
TIDERegs = packed record
    bFeaturesReg : Byte; // Used for specifying SMART "commands".
    bSectorCountReg : Byte; // IDE sector count register
    bSectorNumberReg : Byte; // IDE sector number register
    bCylLowReg : Byte; // IDE low order cylinder value
    bCylHighReg : Byte; // IDE high order cylinder value
    bDriveHeadReg : Byte; // IDE drive/head register
    bCommandReg : Byte; // Actual IDE command.
    bReserved : Byte; // reserved for future use. Must be zero.
  end;
  IDEREGS = TIDERegs;
  PIDERegs = ^TIDERegs;
 
const
  BufferSize = SizeOf(TIDERegs)+4;
  IOCTL_IDE_PASS_THROUGH = $0004d028;

 
implementation

 
{$R *.dfm}  

 
Function IdeRegPassThrough(Device: String; var ideregs: TIDERegs ): Boolean;
var
  ret:BOOL;
  hDevice : THandle;
  cbBytesReturned : DWORD;
  pInData : PIDERegs;
  pOutData : Pointer;
  Buffer : Array[0..BufferSize-1] of Byte;
begin
  Result := False;
  FillChar(Buffer,BufferSize,#0);

 
  hDevice := CreateFile( PChar(Device), GENERIC_READ or GENERIC_WRITE,
    FILE_SHARE_READ or FILE_SHARE_WRITE, nil, OPEN_EXISTING, 0, 0 );
  if hDevice=INVALID_HANDLE_VALUE then Exit;
  try
    pInData := @Buffer;
     pOutData := pInData;
    pInData^ := ideregs;
    ret := DeviceIoControl( hDevice, IOCTL_IDE_PASS_THROUGH, @Buffer, BufferSize, @Buffer, BufferSize, cbBytesReturned, nil );
    if not ret then begin
      Exit;
    end;
    ideregs := PIDERegs(pOutData)^;
  finally
    CloseHandle(hDevice);
  end;
  Result := True;
end;

function SendToSleep(Device: String): Boolean;
var
  ideregs : TIDERegs;
begin
  Result := False;
  with ideregs do
  begin
    bFeaturesReg := 0;
    bSectorCountReg := 0;
    bSectorNumberReg := 0;
    bCylLowReg := 0;
    bCylHighReg := 0;
    bDriveHeadReg := $A0;
    bCommandReg := $E6;
    bReserved := 0;
  end;
  if not IdeRegPassThrough(Device, ideregs ) then Exit else Result := True;
end;
 
//Label1.caption:= BoolToStr(SendToSleep('\\.\PhysicalDrive0'));

Folgender C-Code stammt aus dem Linux-Tool hdparm und bewirkt das Auslesen des Status:
Code:
  __u8 args[4] = {ATA_OP_CHECKPOWERMODE1,0,0,0};
  const char *state;
  if (do_drive_cmd(fd, args)
    && (args[0] = ATA_OP_CHECKPOWERMODE2) /* (single =) try again with 0x98 */ 
    && do_drive_cmd(fd, args)) { 
      err = errno;
      state = "unknown";
    } else { 
      state = (args[2] == 255) ? "active/idle" : "standby";
    } 
  printf(" drive state is: %s\n", state);
Hier sind die Flags dazu:
Code:
ATA_OP_CHECKPOWERMODE1   = 0xe5,
ATA_OP_CHECKPOWERMODE2   = 0x98,
ATA_OP_STANDBYNOW1      = 0xe0,
ATA_OP_SLEEPNOW1      = 0xe6, // das hier wird im Delphi-Code schonmal benutzt
ATA_OP_SLEEPNOW2      = 0x99,
ATA_OP_SETIDLE1      = 0xe3,
Und hier ist die Funktion do_drive_cmd, die dadurch aufgerufen wird:
Code:
int do_drive_cmd (int fd, unsigned char *args)
{
#ifdef SG_IO

   struct ata_tf tf;
   void *data = NULL;
   unsigned int data_bytes = 0;
   int rc;

   if (args == NULL)
      goto use_legacy_ioctl;
   /*
    * Reformat and try to issue via SG_IO:
    */
   if (args[3]) {
      data_bytes = args[3] * 512;
      data      = args + 4;
   }
   tf_init(&tf, args[0], 0, args[1]);
   tf.lob.feat = args[2];
   if (tf.command == ATA_OP_SMART) {
      tf.lob.nsect = args[3];
      tf.lob.lbal = args[1];
      tf.lob.lbam = 0x4f;
      tf.lob.lbah = 0xc2;
   }

   rc = sg16(fd, SG_READ, &tf, data, data_bytes, 0);
   if (rc) {
      if (rc == -1)
         goto use_legacy_ioctl;
      errno = rc;
      rc = -1;
   } else if (tf.status & (ATA_STAT_ERR | ATA_STAT_DRQ)) {
      if (verbose)
         fprintf(stderr, "I/O error, ata_op=0x%02x ata_status=0x%02x ata_error=0x%02x\n",
            tf.command, tf.status, tf.error);
      errno = EIO;
      rc = -1;
   }

   args[0] = tf.status;
   args[1] = tf.error;
   args[2] = tf.lob.nsect;
   return rc;

use_legacy_ioctl:
#endif /* SG_IO */
   if (verbose)
      fprintf(stderr, "Trying legacy HDIO_DRIVE_CMD\n");
   return ioctl(fd, HDIO_DRIVE_CMD, args); // das ist wohl die entscheidende Zeile!
}
So, und jetzt die Frage:
Wie kann man obigen Delphi-Code entsprechend abwandeln, so dass er den Status abfragt?

Freue mich über jede Antwort!
Cu, Chris
  Mit Zitat antworten Zitat
c.wuensch

Registriert seit: 19. Dez 2004
Ort: Münster
96 Beiträge
 
#2

Re: Hilfe bei Übersetzung von C nach Delphi

  Alt 16. Jul 2008, 14:25
Hmm, das war vielleicht etwas zu viel...
Kann mir denn vielleicht wenigstens jemand einen Tipp geben, wie ich bei diesem Aufruf den Rückgabewert verarbeiten kann?
    ret := DeviceIoControl( hDevice, IOCTL_IDE_PASS_THROUGH, @Buffer, BufferSize, @Buffer, BufferSize, cbBytesReturned, nil ); ret ist ja nur eine Boolean-Variable, also wird der Wert wohl in einem der Puffer zu finden sein. Aber mit diesen Pointern usw. kenn ich mich nicht aus. Wie kriege ich diesen Wert denn in einen normalen Datentyp, wie bsp. Integer oder String konvertiert?

Cu, Chris
  Mit Zitat antworten Zitat
Antwort Antwort


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 01:15 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