Mail Archives: djgpp-workers/2001/01/05/13:45:40
While I'm very satisfied with your work, Norberto, yet another case
has dawned on me: DVD-drives.
WINDOZE 98 says "4 634 253 213 bytes 4,31GB" when I select
properies of my R: drive when it contains a DVD-ROM. Interestingly, if
I in EXPLORER select everything and right-click properties WINDOZE
says "Size: 4,31GB (4 634 200 064), 4 634 476 544
bytes". Meanwhile WINDOZE "dir /v" says
" Volume in drive R is FOURWEDDING
Volume Serial Number is 9688-FAFF
Directory of R:\
File Name Size Allocated Modified Accessed Attrib
AUDIO_TS <DIR> 00-08-09 15.56 00-08-09 R DA
AUDIO_TS
VIDEO_TS <DIR> 00-08-09 16.46 00-08-09 R DA
VIDEO_TS
0 file(s) 0 bytes
2 dir(s) 0.00 MB free
4 419.57 MB total disk space, 100% in use".
So we have several right values...
Alas df compiled with our latest (the one you have made) statfs.c says
"FOURWEDDINGS 2295300 2295300 0 100% r:/".
The one from fil316b.zip says
"FOURWEDDINGS 2295300 2295300 0 100% r:/" so there
has been no regression.
However if I try the INT21 AX=7303 on R: I get:
"r:/ -> 0, (0), bsize = 2048, blocks = 2262819, bfree = 0." which
evaluates to 4 634 253 312 which is in accordance with the first
WINDOZE value above. (Program source last in this message.)
It would be neat if we could make this work also.
In statfs.c there is this text:
/* For a CD-ROM drive, Int 21h/AX=3600h gives incorrect info.
Use CD-ROM-specific calls if they are available.
Int 2Fh/AX=1510h gives us a way of doing IOCTL with the
CD-ROM device driver without knowing the name of the
device (which is defined by the CONFIG.SYS line that
installs the driver and can therefore be arbitrary). */
So I ask the list on which platforms does Int 21h/AX=3600h give
incorrect info?
My testing seems to say that in (WINDOZE 98's) plain DOZE mode does
not support INT21 AX=7303/7302. So there we must fall back to the
earlier methods.
Right,
MartinS
#include <stdio.h>
#include <errno.h>
#include <sys/vfs.h>
#include <libc/farptrgs.h>
#include <libc/dosio.h>
#include <go32.h>
#include <dpmi.h>
int my_statfs( char * path, struct statfs *buf )
{
__dpmi_regs regs;
int drive_number;
long blocks = 0;
long freec = 0;
long bsize = 0;
/* First try 217303 as 217302 reports fake free space
(largest block of free clusters?) */
_put_path( path );
drive_number = (_farpeekb(_dos_ds, __tb) & 0x1f) - 1;
regs.x.ax = 0x7303;
regs.x.ds = regs.x.es = __tb_segment;
regs.x.dx = regs.x.di = __tb_offset;
regs.x.cx = 0x100; /* 256 bytes should be enough (RBIL says
0x3f). */
__dpmi_int (0x21, ®s);
/* Errors? (217303 seams to fail under plain DOS) */
if (regs.x.flags & 1)
{
/* Get free space info from Extended Drive Parameter Block. */
regs.x.ax = 0x7302;
regs.h.dl = drive_number + 1;
regs.x.es = __tb_segment;
regs.x.di = __tb_offset;
regs.x.cx = 0x100; /* 256 bytes should be enough (RBIL says
0x3f). */
__dpmi_int(0x21, ®s);
/* Errors? */
if( regs.x.flags & 1 )
{
errno = ENODEV;
return( -1 );
}
freec = _farpeekw (_dos_ds, __tb + 0x2 + 0x1f) +
65536 * _farpeekw (_dos_ds, __tb + 0x2 + 0x21);
bsize = _farpeekw (_dos_ds, __tb + 0x2 + 0x2) *
( _farpeekb (_dos_ds, __tb + 0x2 + 0x4) + 1 );
blocks = _farpeekl( _dos_ds, __tb + 0x2 + 0x2d) - 1;
#if 0
printf("Second: bsize = %ld, free = %ld, blocks = %ld.\n"
, bsize
, freec
, blocks
);
#endif
}
else
{
freec = _farpeekl (_dos_ds, __tb + 0x0c);
bsize = _farpeekl (_dos_ds, __tb + 0x08)
* _farpeekl (_dos_ds, __tb + 0x04);
blocks = _farpeekl (_dos_ds, __tb + 0x10);
#if 0
printf("Third: bsize = %ld, free = %ld, blocks = %ld.\n"
, bsize
, freec
, blocks
);
#endif
}
/* Fill in the structure */
buf->f_bavail = freec;
buf->f_bfree = freec;
buf->f_blocks = blocks;
buf->f_bsize = bsize;
buf->f_ffree = freec;
buf->f_files = blocks;
buf->f_type = 0;
buf->f_fsid[0] = drive_number;
buf->f_fsid[1] = MOUNT_UFS;
buf->f_magic = FS_MAGIC;
return( 0 );
}
int main(void)
{
int ret;
struct statfs s;
ret = my_statfs("c:/", &s);
printf("c:/ -> %d, (%d), bsize = %ld, blocks = %ld, bfree = %ld.\n",
ret, errno, s.f_bsize, s.f_blocks, s.f_bfree);
ret = my_statfs("d:/", &s);
printf("d:/ -> %d, (%d), bsize = %ld, blocks = %ld, bfree = %ld.\n",
ret, errno, s.f_bsize, s.f_blocks, s.f_bfree);
ret = my_statfs("f:/", &s);
printf("f:/ -> %d, (%d), bsize = %ld, blocks = %ld, bfree = %ld.\n",
ret, errno, s.f_bsize, s.f_blocks, s.f_bfree);
ret = my_statfs("g:/", &s);
printf("g:/ -> %d, (%d), bsize = %ld, blocks = %ld, bfree = %ld.\n",
ret, errno, s.f_bsize, s.f_blocks, s.f_bfree);
ret = my_statfs("r:/", &s);
printf("r:/ -> %d, (%d), bsize = %ld, blocks = %ld, bfree = %ld.\n",
ret, errno, s.f_bsize, s.f_blocks, s.f_bfree);
ret = my_statfs("u:/", &s);
printf("u:/ -> %d, (%d), bsize = %ld, blocks = %ld, bfree = %ld.\n",
ret, errno, s.f_bsize, s.f_blocks, s.f_bfree);
return(0);
}
- Raw text -