delorie.com/archives/browse.cgi   search  
Mail Archives: djgpp-workers/2000/12/30/01:57:17

X-Originating-IP: [200.42.4.138]
From: "Norberto Alfredo Bensa" <nbensa AT hotmail DOT com>
To: "Martin Stromberg" <eplmst AT lu DOT erisoft DOT se>
Cc: <djgpp-workers AT delorie DOT com>
References: <200012291357 DOT OAA08308 AT lws256 DOT lu DOT erisoft DOT se>
Subject: Re: Fw: Patch for statfs.c
Date: Sat, 30 Dec 2000 03:52:55 -0300
Organization: nBens@ Computers
X-Priority: 3
X-MSMail-Priority: Normal
X-Mailer: Microsoft Outlook Express 5.50.4522.1200
X-MimeOLE: Produced By Microsoft MimeOLE V5.50.4522.1200
Message-ID: <OE73pjE5aHaZVrDs9aA00002209@hotmail.com>
X-OriginalArrivalTime: 30 Dec 2000 06:56:26.0546 (UTC) FILETIME=[A0EE9920:01C0722D]
Reply-To: djgpp-workers AT delorie DOT com

Hi Martin! Hi everyone!

Ok, I think I got it... now with network drives support.

From: "Martin Stromberg" <eplmst AT lu DOT erisoft DOT se>
> > BTW, what does rescaling do? You're calling two services (2136 and
>
> It's been a while but I think it had something to do with me noticing
> that INT 21, AX=0x7302 wasn't quite accurate so I falled back to the

ahhhh... that's it!... 322197*4096/32768 isn't integer, i.e. 322197 is not a
power of 2!!!...

Can you please tell me if you remember at least one case where 217302
wasn't giving accurate info? I have "#if 0...#endif"the rescaling for
now, but it *must* be tested.

>
> Yes, but on the network drives...
>

I think I got it... test it please.


Best regards,
Norberto

Now the patch...

------CUT---------8<---------CUT------------
--- src/libc/compat/sys/vfs/statfs.c.~ Mon Jun 19 19:00:56 2000
+++ src/libc/compat/sys/vfs/statfs.c Sat Dec 30 02:41:26 2000
@@ -108,73 +108,116 @@

   if (!cdrom_calls_used)
   {
-    /* Get free space info from DOS.  */
-    regs.h.ah = 0x36;  /* DOS Get Free Disk Space call */
-    regs.h.dl = drive_number + 1;
-    __dpmi_int(0x21, &regs);
-
-    /* Check for errors */
-    if ((regs.x.ax & 0xffff) == 0xffff)
-    {
-      errno = ENODEV;
-      return -1;
-    }
-    bsize = regs.x.cx * regs.x.ax;
-    free = regs.x.bx;
-    blocks = regs.x.dx;
-#if 0
-    printf("First: bsize = %ld, free = %ld, blocks = %ld.\n"
-  , bsize
-  , free
-         , blocks
-    );
-#endif
-
     if( 7 <= (_get_dos_version(1) >> 8) /* Is FAT32 supported? */
+#if 0
      && _is_fat32(drive_number + 1) /* Is it a FAT32 drive? */
+#endif
        )
     {
-      /* 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, &regs);
+      /* 217303 - Win9x - Get Extended Free Drive Space:
+        Extended Drive Paramenter Block, seams to report the largest
+  block of free clusters when running under Windows (this info
+  is not confirmed), so I'm using this service here. BTW, it
+  expects a path on DS:DX and should be not an empty string or
+  the sevice will fail */
+      if (path && !*path)
+ _put_path ("/");
+      else
+ _put_path (path);

-      /* Errors? */
-      if( regs.x.flags & 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; /* Buffer lenght. Actually ~70 bytes would be enough */
+      __dpmi_int (0x21, &regs);
+
+      /* On plain DOS, 217303 fails (?), so here comes the old code.
+         Under DOS, ExtDPB returns "accurate" info (!?) */
+      if (regs.x.flags & 1)
       {
- errno = ENODEV;
- return( -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, &regs);
+
+       /* Errors? */
+       if( regs.x.flags & 1 )
+       {
+   errno = ENODEV;
+   return( -1 );
+       }

-      /* We trust previous int21 call more if free hasn't maxed out. */
-      if( free < blocks )
+#if 0
+       /* We trust previous int21 call more if free hasn't maxed out. */
+       if( free < blocks )
+       {
+   /* Previous bsize is a multiple of this bsize, so the multiplication
+      and division here is really a rescaling of the previous free
+      value. */
+   free *= bsize;
+   bsize = _farpeekw (_dos_ds, __tb + 0x2 + 0x2) *
+     ( _farpeekb (_dos_ds, __tb + 0x2 + 0x4) + 1 );
+   free /= bsize;
+       }
+       else
+#endif
+       {
+   free = _farpeekl (_dos_ds, __tb + 0x2 + 0x1f);
+   bsize = _farpeekw (_dos_ds, __tb + 0x2 + 0x2) *
+     ( _farpeekb (_dos_ds, __tb + 0x2 + 0x4) + 1 );
+       }
+
+ /* -1, because it was reporting 1 more cluster than CHKDSK,
+     again, this information is not confirmed */
+       blocks = _farpeekl( _dos_ds, __tb + 0x2 + 0x2d) - 1;
+#if 0
+       printf("217302: bsize = %ld, free = %ld, blocks = %ld.\n"
+       , bsize
+       , free
+       , blocks
+  );
+#endif
+      }
+      else /* Use information from service 217303 */
       {
- /* Previous bsize is a multiple of this bsize, so the multiplication
-    and division here is really a rescaling of the previous free
-    value. */
- free *= bsize;
- bsize = _farpeekw (_dos_ds, __tb + 0x2 + 0x2) *
-   ( _farpeekb (_dos_ds, __tb + 0x2 + 0x4) + 1 );
- free /= bsize;
+ free   = _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("217303: bsize = %ld, free = %ld, blocks = %ld.\n"
+       , bsize
+       , free
+       , blocks
+  );
+#endif
       }
-      else
+    }
+    else /* DOS version is < 7  */
+    {
+      /* Get free space info from DOS.  */
+      regs.h.ah = 0x36;  /* DOS Get Free Disk Space call */
+      regs.h.dl = drive_number + 1;
+      __dpmi_int(0x21, &regs);
+
+      /* Check for errors */
+      if ((regs.x.ax & 0xffff) == 0xffff)
       {
- free = _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 );
+ errno = ENODEV;
+ return -1;
       }
-
-      blocks = _farpeekl( _dos_ds, __tb + 0x2 + 0x2d);
+      bsize = regs.x.cx * regs.x.ax;
+      free = regs.x.bx;
+      blocks = regs.x.dx;
 #if 0
-      printf("Second: bsize = %ld, free = %ld, blocks = %ld.\n"
-    , bsize
-    , free
-          , blocks
-      );
+      printf("2136: bsize = %ld, free = %ld, blocks = %ld.\n"
+ , bsize
+ , free
+ , blocks
+   );
 #endif
     }
   }
------CUT---------8<---------CUT------------








- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019