容量について

解決


プリン  2005-08-25 02:29:37  No: 17248

フォルダないにあるファイルの合計容量を表示したいのですが

FindFirst を使って Size を合計するとファイルのサイズは取得
できたのですが、 ディスク上のサイズがわかりません。
HDD・OS・機種?によって値が変わるのですが
どうやって求めればよいのでしょうか?

昔は  1024で割って、切り上げて 1024 倍すると
サイズがでてきたと思いますが・・・・


見習  2005-08-25 07:16:00  No: 17249

ディスク上のサイズはHDDの1クラスタの容量によって変わるのではないかと思うのですが、
GetDiskFreeSpaceで1クラスタの容量を取得し、取得バイト数で割って切り上げて(以下略

// RootPathName に 'C:'や'C:\'のようにドライブを指定。
function GetBytePerCluster(RootPathName: String): Cardinal;
var
  SectorsPerCluster,
  BytesPerSector,
  FreeClusterCount,
  ClusterCount: Cardinal;
begin
  GetDiskFreeSpace(PAnsiChar(RootPathName),
          SectorsPerCluster,
          BytesPerSector,
          FreeClusterCount,
          ClusterCount);

  // 1クラスタの容量 = 1セクタのバイト数 * 1クラスタのセクタ数
  Result := BytesPerSector * SectorsPerCluster;
end;

見習いなのでこれが限度です(ーー;
ちなみにWin2000+NTFSではきちんと動作しました。


プリン  2005-09-03 03:45:04  No: 17250

どうもです。
がんばります。


Basser  2005-09-06 20:14:15  No: 17251

9x系でファイルシステムがFAT32の場合、
GetDiskFreeSpaceは間違った値を返すので処理をわける必要があります。
9x系 FAT32クラスタサイズ取得方法は下記のようにします。

const
  CARRY_FLAG = $00000001;
  VWIN32_DIOC_DOS_DRIVEINFO = 6;

type
  // DIOCレジスタ構造体
  TDIOC_REGISTERS = record
    reg_EBX  : DWORD;
    reg_EDX  : DWORD;
    reg_ECX  : DWORD;
    reg_EAX  : DWORD;
    reg_EDI  : DWORD;
    reg_ESI  : DWORD;
    reg_Flags: DWORD;
  end;

// -----------------------------------------------------------------
// 9x系 FAT32クラスタサイズ取得関数 ※取得失敗時は -1 を返す
//   Drive ドライブ番号 1 が A ドライブ,2 が B ドライブと続きます。
// -----------------------------------------------------------------
function GetClusterSizeFAT32(Drive: Byte): Integer;
type
  // FAT32 拡張DPB(Device Parameter Block)構造体
  TExtDPB = packed record
    dpb_drive          : Byte;
    dpb_unit           : Byte;
    dpb_sector_size    : Word; // セクタサイズ
    dpb_cluster_mask   : Byte; // クラスタ当りのセクタ数 - 1
    dpb_cluster_shift  : Byte;
    dpb_first_fat      : Word;
    dpb_fat_count      : Byte;
    dpb_root_entries   : Word;
    dpb_first_sector   : Word;
    dpb_max_cluster    : Word;
    dpb_fat_size       : Word;
    dpb_dir_sector     : Word;
    dpb_reserved2      : DWORD;
    dpb_media          : Byte;
    dpb_first_access   : Byte;
    dpb_reserved3      : DWORD;
    dpb_next_free      : Word;
    dpb_free_cnt       : Word;
    extdpb_free_cnt_hi : Word;
    extdpb_flags       : Word;
    extdpb_FSInfoSec   : Word;
    extdpb_BkUpBootSec : Word;
    extdpb_first_sector: DWORD;
    extdpb_max_cluster : DWORD;
    extdpb_fat_size    : DWORD;
    extdpb_root_clus   : DWORD;
    extdpb_next_free   : DWORD;
  end;

  // Int 21h Function 7302hの戻り値を格納する構造体
  TDPBResult = packed record
    wSize: Word;
    DPB  : TExtDPB;
  end;

var
  Reg          : TDIOC_REGISTERS;
  DPBResult    : TDPBResult;
  hDevice      : THandle;
  bResult      : Boolean;
  BytesReturned: DWORD;
begin

  Result:= -1;

  FillChar(DPBResult, SizeOf(TDPBResult), 0);
  FillChar(Reg, SizeOf(TDIOC_REGISTERS), 0);
  Reg.reg_EDX  := Drive;              // 対象のドライブ番号をDLレジスタに読込
  Reg.reg_EAX  := $7302;              // Int 21h Function 7302h: Get_ExtDPB(FAT32)
  Reg.reg_EDI  := DWORD(@DPBResult);  // 戻り値を受け取る構造体のアドレス。 DeviceIoControlによって、ES:DIに分割される
  Reg.reg_ECX  := SizeOf(TDPBResult); // 戻り値を受け取る構造体のサイズ
  Reg.reg_Flags:= CARRY_FLAG;         // エラーを仮定したキャリーフラグ

  // 仮想ドライバ Vwin32を開く
  hDevice:= CreateFile('\\.\vwin32', 0, 0, nil, 0, FILE_FLAG_DELETE_ON_CLOSE, 0);
  if (hDevice <> INVALID_HANDLE_VALUE) then
  begin

    // Int 21h Function 7302hの呼出
    try
      bResult:=
        DeviceIoControl(
          hDevice, VWIN32_DIOC_DOS_DRIVEINFO, @Reg, SizeOf(TDIOCRegisters),
          @Reg, SizeOf(TDIOCRegisters), BytesReturned, nil
        );
    finally
      CloseHandle(hDevice);
    end;

    // reg_FlagsのLSBはcarry flagであり、エラーならセットされる
    if bResult and (Reg.reg_Flags and CARRY_FLAG = 0) then
      with DPBResult.DPB do Result:= (dpb_cluster_mask + 1) * dpb_sector_size;

  end;

end;

この他にも setupapi.dll の API関数を使った方法もあります。
使用関数は
  SetupCreateDiskSpaceList
  SetupDestroyDiskSpaceList
  SetupAddToDiskSpaceList
  SetupQuerySpaceRequiredOnDrive
です。

こちらはクラスタギャップを考慮したディスクサイズを返してくれます。
よかったら調べてみて下さい。


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加