GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Für alles, was in den übrigen Lazarusthemen keinen Platz, aber mit Lazarus zutun hat.
Antworten
thosch
Beiträge: 324
Registriert: Mo 10. Jul 2017, 20:32

GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von thosch »

Wie kann ich unter Linux unabhängig vom XServer die Windows API Funktion

function GetDiskFreeSpaceA(
lpRootPathName: LPCSTR;
lpSectorsPerCluster : LPDWORD;
lpBytesPerSector : LPDWORD;
lpNumberOfFreeClusters : LPDWORD;
lpTotalNumberOfClusters: LPDWORD
): BOOL;

nachbauen.

Dazu brauche ich eine Funktion, die mir die Anzahl der Sektoren pro Cluster, den Bytes pro Sektor, der Anzahl freier und der Anzahl der Cluster insgesamt liefert. Oder mehrere Funktionen, die das tun.

Nur, welche ist/sind das? Und in welcher Unit finde ich die?

Pascal selber kennt nur die Funktionen DiskFree() und DiskSize(), die aber nur die ANzahl Bytes liefern.

Benutzeravatar
Winni
Beiträge: 1577
Registriert: Mo 2. Mär 2009, 16:45
OS, Lazarus, FPC: Laz2.2.2, fpc 3.2.2
CPU-Target: 64Bit
Wohnort: Fast Dänemark

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von Winni »

Hallo!

Ich erinner mich nicht, dass ich derartiges schon in den Unix-units gefunden zu haben.

Aber das Rad ist schon erfunden.

Linux fdisk -l ausführen vom Lazarus Programm aus und den Output einlesen:

---------------------------------------------------------
fdisk -l
Disk /dev/sda: 232.91 GiB, 250059350016 bytes, 488397168 sectors
Disk model: CT250MX500SSD1
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 4096 bytes
I/O size (minimum/optimal): 4096 bytes / 4096 bytes
Disklabel type: gpt
Disk identifier: 04FBD09C-EAAF-4AB7-A59C-DBE004D99D08

Device Start End Sectors Size Type
/dev/sda1 2048 18431 16384 8M BIOS boot
/dev/sda2 18432 484202495 484184064 230.9G Linux filesystem
/dev/sda3 484202496 488397134 4194639 2G Linux swap


Disk /dev/sdb: 1.84 TiB, 2000398934016 bytes, 3907029168 sectors
Disk model: TOSHIBA DT01ACA2
Units: sectors of 1 * 512 = 512 bytes
.......
.......
---------------------------------------------------------------

Und Du solltest dich mal mit hdparm anfreunden.
Das erzählt dir ALLES über Deine Hardware, also auch über die Platten.

Zum Start:

hdparm /dev/sd*

Grüße
Winni

Ich934
Lazarusforum e. V.
Beiträge: 316
Registriert: So 5. Mai 2019, 16:52
OS, Lazarus, FPC: ArchLinux und Windows mit FPCUPdeluxe (L: 2.0.X, FPC 3.2.0)
CPU-Target: x86_64, i386
Wohnort: Bayreuth

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von Ich934 »

hdparm muss aber u.U. extra installiert werden und ist nicht auf jeden System vorhanden.
Tipp für PostgreSQL: www.pg-forum.de

Benutzeravatar
Winni
Beiträge: 1577
Registriert: Mo 2. Mär 2009, 16:45
OS, Lazarus, FPC: Laz2.2.2, fpc 3.2.2
CPU-Target: 64Bit
Wohnort: Fast Dänemark

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von Winni »

Ich934 hat geschrieben:
Di 10. Nov 2020, 20:31
hdparm muss aber u.U. extra installiert werden und ist nicht auf jeden System vorhanden.
Hi!

Also Suse Tumbleweed hat's per default installiert.
Und selbst mein minimalistisches Debian in der VirtualBox hat es parat.

Winni

Ich934
Lazarusforum e. V.
Beiträge: 316
Registriert: So 5. Mai 2019, 16:52
OS, Lazarus, FPC: ArchLinux und Windows mit FPCUPdeluxe (L: 2.0.X, FPC 3.2.0)
CPU-Target: x86_64, i386
Wohnort: Bayreuth

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von Ich934 »

ArchLinux hatte es früher nicht dabei. Aktuell bin ich mir nicht sicher. Meine Systeme laufen zu lange stabil. ;-)

Bei Serversystemen, vor allem im virtuellen Bereich, ist das nicht immer vorhanden. Auch bei Debian und Ubuntu. Installier dir einen Container auf Proxmox mit den offiziellen Debian Image von Proxmox und hdparm fehlt.
Tipp für PostgreSQL: www.pg-forum.de

marcov
Beiträge: 1100
Registriert: Di 5. Aug 2008, 09:37
OS, Lazarus, FPC: Windows ,Linux,FreeBSD,Dos (L trunk FPC trunk)
CPU-Target: 32/64,PPC(+64), ARM
Wohnort: Eindhoven (Niederlande)

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von marcov »

Sehe mal nach baseunix.fpstatfs() Ein Problem dabei ist auch filesystemen zu enumerieren.

Sektoren pro Cluster hat kein Bedeutung auf *nix while *nix Filesystemen mehrere Files pro Cluster speichern können. Das heisst "extents"

PascalDragon
Beiträge: 825
Registriert: Mi 3. Jun 2020, 07:18
OS, Lazarus, FPC: L 2.0.8, FPC Trunk, OS Win/Linux
CPU-Target: Aarch64 bis Z80 ;)
Wohnort: München

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von PascalDragon »

marcov hat geschrieben:
Mi 11. Nov 2020, 11:43
Sektoren pro Cluster hat kein Bedeutung auf *nix while *nix Filesystemen mehrere Files pro Cluster speichern können. Das heisst "extents"
Wobei das vom Dateisystem abhängt: FAT oder NTFS unter Linux brauchen sehr wohl „Sektoren pro Cluster”.
FPC Compiler Entwickler

thosch
Beiträge: 324
Registriert: Mo 10. Jul 2017, 20:32

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von thosch »

Hmmm, Danke zuerst für Eure Antworten. Da bevorzuge ich dann doch die Funktion fpStatFS in Zusammenarbeit mit der Funktion fplstat, die die Blockgröße in Byte liefert, wenn ich das richtig verstanden habe. fpstatFS liefert die Anzahl der Blöcke, die sich dann anstelle der Anzahl Sektoren oder der Cluster übergeben ließe.

So hier für ein Linux Dateisystem:

lpSectorsPerCluster : Anzahl verfügbarer Blöcke
lpBytesPerSector : Blockgröße
lpNumberOfFreeClusters : Anzahl der noch freien Blöcke
lpTotalNumberOfClusters: Gesamtanzahl der Blöcke

Ich musste lernen dass auch Linux das FATxx oder NTFS Dateisystem nutzen kann, dann müssen diese Werte äquivalent zu Windows interpretiert werden, daher möchte ich die aäquivalenten Parameter aus TStatFs an die Übergabevariablen übergeben, so dass der Anwender dann die Werte gemäß seinem Dateisystem so oder so interpretieren kann. Ist da die obige Zuordnung korrekt?

Daher einige Fragen zu den Datenstrukturen. Zuerst TStatFS

Code: Alles auswählen

type TStatfs = record

  fstype: clong;                        //File system type

  bsize: clong;                         //Block size

  blocks: culong;                     //Total number of blocks

  bfree: culong;                        //Number of free blocks

  bavail: culong;                      //Number of available blocks

  files: culong;                          //Number of files

  ffree: culong;

?

 fsid: array [0..1] of cint;

  

?

  namelen: clong;                        //Max name length for files.


  frsize: clong;                              //Optimal block transfer size


  spare: array [0..4] of clong;

  

Pad bytes. Do not use.

end;
Warum noch neben der Anzahl freier Blöcke die Anzahl verfügbarer Blöcke? Wo ist da der Unterschied?

Code: Alles auswählen

type Stat = packed record

  st_dev: QWord;                             //Device number

  __pad0_: array [0..3] of Byte;     //Alignment padding.

  __st_ino_: Cardinal;                    //Inode number

  st_mode: Cardinal;                        //File mode

  st_nlink: Cardinal;                          //Number of hard links

  st_uid: Cardinal;                             //File owner User ID

  st_gid: Cardinal;                             //File owner group ID

  st_rdev: QWord;                              //??

  __pad3_: array [0..3] of Byte;       //Alignment padding.

  st_size: QWord;                               //File size in bytes

  st_blksize: Cardinal;                       //Block size

  st_blocks: QWord;                           //Number of blocks

  st_atime: Cardinal;                         //Last file access time

  st_atime_nsec: Cardinal;               //Access time with nanosecond 
                                                            //precision

  st_mtime: Cardinal;                         //Last file modification time

  st_mtime_nsec: Cardinal;              //Modification time with nanosecond 
                                                            //precision

  st_ctime: Cardinal;                          //File creation time

  st_ctime_nsec: Cardinal;                //Create time with nanosecond 
                                                             //precision

  st_ino: QWord;                                  //Inode number

end;

Hier wäre schon mal die Blockgröße dabei und die Filetime. Letztere brauche ich wenn ich andere Funktionen unter linux nachbauen will.

Benutzeravatar
Winni
Beiträge: 1577
Registriert: Mo 2. Mär 2009, 16:45
OS, Lazarus, FPC: Laz2.2.2, fpc 3.2.2
CPU-Target: 64Bit
Wohnort: Fast Dänemark

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von Winni »

thosch hat geschrieben:
Mi 11. Nov 2020, 14:04

Code: Alles auswählen


Warum noch neben der Anzahl freier Blöcke die Anzahl verfügbarer Blöcke? Wo ist da der Unterschied?

[code]
type Stat = packed record

  st_dev: QWord;                             //Device number
......
  st_rdev: QWord;                              //??
....
end;

Hier wäre schon mal die Blockgröße dabei und die Filetime. Letztere brauche ich wenn ich andere Funktionen unter linux nachbauen will.

Hi!

st_dev ist die device number für alle Geräte, also nicht nur Platten sondern auch Terminals, serielle Leitungen etc.

st_rdev ist die device number des zugehörigen Massenspeichers.

Winni

thosch
Beiträge: 324
Registriert: Mo 10. Jul 2017, 20:32

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von thosch »

Ok, danke, da kann ich das also so verwenden. Und die Übergabe der Parameter mache ich dann so wie oben festgelegt.

Hier noch mal zur Erinnerung:

lpSectorsPerCluster : Anzahl verfügbarer Blöcke
lpBytesPerSector : Blockgröße
lpNumberOfFreeClusters : Anzahl der noch freien Blöcke
lpTotalNumberOfClusters: Gesamtanzahl der Blöcke

Im FATxx oder NTFS Dateisystem müssen die Werte dann gemäß der dortigen Bedeutung interpretiert werden. Im Linux Dateisysten dann wie oben.

thosch
Beiträge: 324
Registriert: Mo 10. Jul 2017, 20:32

Re: GetDiskFreeSpaceA aus WinAPI in Linux nachbauen

Beitrag von thosch »

Ist da st_dev bzw st_rdev als HANDLE zu verstehen?

Antworten