* fhandler.h (class fhandler_dev_raw): Delete current_position and
eof_detected status flag. Delete is_eom and is_eof methods. Move drive_size, bytes_per_sector, eom_detected status flag, as well as the methods read_file, write_file, raw_read and raw_write to ... (class fhandler_dev_floppy): ... here. Remove is_eom and is_eof methods. Add dup method. * fhandler_floppy.cc (IS_EOM): New macro. (fhandler_dev_floppy::is_eom): Remove. (fhandler_dev_floppy::is_eof): Remove. (fhandler_dev_floppy::fhandler_dev_floppy): Initialize status flags. (fhandler_dev_floppy::get_drive_info): Only call EX functions on systems supporting them and stop suffering strange delays. (fhandler_dev_floppy::read_file): Move here, drop setting current_position. (fhandler_dev_floppy::write_file): Move here, drop setting current_position. (fhandler_dev_floppy::open): Rearrange comment. (fhandler_dev_floppy::dup): New method. (fhandler_dev_floppy::get_current_position): New inline method. Use instead of former current_position were appropriate. (fhandler_dev_floppy::raw_read): Move here. Drop EOF handling. (fhandler_dev_floppy::raw_write): Move here. Drop EOF handling. (fhandler_dev_floppy::lseek): Remove useless conditions. Convert sector_aligned_offset to LARGE_INTEGER to improve SetFilePointer call. (fhandler_dev_floppy::ioctl): Move blocksize check in RDSETBLK case to here. * fhandler_raw.cc (fhandler_dev_raw::is_eom): Remove. (fhandler_dev_raw::is_eof): Remove. (fhandler_dev_raw::write_file): Remove. (fhandler_dev_raw::read_file): Remove. (fhandler_dev_raw::raw_read): Remove. (fhandler_dev_raw::raw_write): Remove. (fhandler_dev_raw::dup): Drop copying removed members. (fhandler_dev_raw::ioctl): Drop blocksize testing. * wincap.h: Implement has_disk_ex_ioctls throughout. * wincap.cc: Ditto. (wincap_vista): Preliminary wincaps for Windows Vista/Longhorn. (wincapc::init): Add Vista/Longhorn handling.
This commit is contained in:
		| @@ -1,3 +1,44 @@ | |||||||
|  | 2005-09-28  Corinna Vinschen  <corinna@vinschen.de> | ||||||
|  |  | ||||||
|  | 	* fhandler.h (class fhandler_dev_raw): Delete current_position and | ||||||
|  | 	eof_detected status flag.  Delete is_eom and is_eof methods. | ||||||
|  | 	Move drive_size, bytes_per_sector, eom_detected status flag, as well | ||||||
|  | 	as the methods read_file, write_file, raw_read and raw_write to ... | ||||||
|  | 	(class fhandler_dev_floppy): ... here. Remove is_eom and is_eof | ||||||
|  | 	methods.  Add dup method. | ||||||
|  | 	* fhandler_floppy.cc (IS_EOM): New macro. | ||||||
|  | 	(fhandler_dev_floppy::is_eom): Remove. | ||||||
|  | 	(fhandler_dev_floppy::is_eof): Remove. | ||||||
|  | 	(fhandler_dev_floppy::fhandler_dev_floppy): Initialize status flags. | ||||||
|  | 	(fhandler_dev_floppy::get_drive_info): Only call EX functions on | ||||||
|  | 	systems supporting them and stop suffering strange delays. | ||||||
|  | 	(fhandler_dev_floppy::read_file): Move here, drop setting | ||||||
|  | 	current_position. | ||||||
|  | 	(fhandler_dev_floppy::write_file): Move here, drop setting | ||||||
|  | 	current_position. | ||||||
|  | 	(fhandler_dev_floppy::open): Rearrange comment. | ||||||
|  | 	(fhandler_dev_floppy::dup): New method. | ||||||
|  | 	(fhandler_dev_floppy::get_current_position): New inline method.  Use | ||||||
|  | 	instead of former current_position were appropriate. | ||||||
|  | 	(fhandler_dev_floppy::raw_read): Move here.  Drop EOF handling. | ||||||
|  | 	(fhandler_dev_floppy::raw_write): Move here.  Drop EOF handling. | ||||||
|  | 	(fhandler_dev_floppy::lseek): Remove useless conditions.  Convert | ||||||
|  | 	sector_aligned_offset to LARGE_INTEGER to improve SetFilePointer call. | ||||||
|  | 	(fhandler_dev_floppy::ioctl): Move blocksize check in RDSETBLK case | ||||||
|  | 	to here. | ||||||
|  | 	* fhandler_raw.cc (fhandler_dev_raw::is_eom): Remove. | ||||||
|  | 	(fhandler_dev_raw::is_eof): Remove. | ||||||
|  | 	(fhandler_dev_raw::write_file): Remove. | ||||||
|  | 	(fhandler_dev_raw::read_file): Remove. | ||||||
|  | 	(fhandler_dev_raw::raw_read): Remove. | ||||||
|  | 	(fhandler_dev_raw::raw_write): Remove. | ||||||
|  | 	(fhandler_dev_raw::dup): Drop copying removed members. | ||||||
|  | 	(fhandler_dev_raw::ioctl): Drop blocksize testing. | ||||||
|  | 	* wincap.h: Implement has_disk_ex_ioctls throughout. | ||||||
|  | 	* wincap.cc: Ditto. | ||||||
|  | 	(wincap_vista): Preliminary wincaps for Windows Vista/Longhorn. | ||||||
|  | 	(wincapc::init): Add Vista/Longhorn handling. | ||||||
|  |  | ||||||
| 2005-09-28  Christopher Faylor  <cgf@timesys.com> | 2005-09-28  Christopher Faylor  <cgf@timesys.com> | ||||||
|  |  | ||||||
| 	* dcrt0.cc (getstack): New function. | 	* dcrt0.cc (getstack): New function. | ||||||
|   | |||||||
| @@ -551,50 +551,29 @@ public: | |||||||
| class fhandler_dev_raw: public fhandler_base | class fhandler_dev_raw: public fhandler_base | ||||||
| { | { | ||||||
|  protected: |  protected: | ||||||
|   _off64_t drive_size; |  | ||||||
|   _off64_t current_position; |  | ||||||
|   unsigned long bytes_per_sector; |  | ||||||
|   char *devbuf; |   char *devbuf; | ||||||
|   size_t devbufsiz; |   size_t devbufsiz; | ||||||
|   size_t devbufstart; |   size_t devbufstart; | ||||||
|   size_t devbufend; |   size_t devbufend; | ||||||
|   struct status_flags |   struct status_flags | ||||||
|   { |   { | ||||||
|     unsigned eom_detected    : 1; |  | ||||||
|     unsigned eof_detected    : 1; |  | ||||||
|     unsigned lastblk_to_read : 1; |     unsigned lastblk_to_read : 1; | ||||||
|    public: |    public: | ||||||
|     status_flags () : |     status_flags () : lastblk_to_read (0) {} | ||||||
|       eom_detected (0), eof_detected (0), lastblk_to_read (0) |  | ||||||
|       {} |  | ||||||
|   } status; |   } status; | ||||||
|  |  | ||||||
|   IMPLEMENT_STATUS_FLAG (bool, eom_detected) |  | ||||||
|   IMPLEMENT_STATUS_FLAG (bool, eof_detected) |  | ||||||
|   IMPLEMENT_STATUS_FLAG (bool, lastblk_to_read) |   IMPLEMENT_STATUS_FLAG (bool, lastblk_to_read) | ||||||
|  |  | ||||||
|   virtual BOOL write_file (const void *buf, DWORD to_write, |  | ||||||
| 			   DWORD *written, int *err); |  | ||||||
|   virtual BOOL read_file (void *buf, DWORD to_read, DWORD *read, int *err); |  | ||||||
|  |  | ||||||
|   /* returns not null, if `win_error' determines an end of media condition */ |  | ||||||
|   virtual int is_eom(int win_error); |  | ||||||
|   /* returns not null, if `win_error' determines an end of file condition */ |  | ||||||
|   virtual int is_eof(int win_error); |  | ||||||
|  |  | ||||||
|   fhandler_dev_raw (); |   fhandler_dev_raw (); | ||||||
|  |  | ||||||
|  public: |  public: | ||||||
|   ~fhandler_dev_raw (); |   ~fhandler_dev_raw (); | ||||||
|  |  | ||||||
|   int open (int flags, mode_t mode = 0); |   int open (int flags, mode_t mode = 0); | ||||||
|   void raw_read (void *ptr, size_t& ulen); |  | ||||||
|   int raw_write (const void *ptr, size_t ulen); |  | ||||||
|  |  | ||||||
|   int __stdcall fstat (struct __stat64 *buf) __attribute__ ((regparm (2))); |   int __stdcall fstat (struct __stat64 *buf) __attribute__ ((regparm (2))); | ||||||
|  |  | ||||||
|   int dup (fhandler_base *child); |   int dup (fhandler_base *child); | ||||||
|  |  | ||||||
|   int ioctl (unsigned int cmd, void *buf); |   int ioctl (unsigned int cmd, void *buf); | ||||||
|  |  | ||||||
|   void fixup_after_fork (HANDLE); |   void fixup_after_fork (HANDLE); | ||||||
| @@ -604,20 +583,32 @@ class fhandler_dev_raw: public fhandler_base | |||||||
| class fhandler_dev_floppy: public fhandler_dev_raw | class fhandler_dev_floppy: public fhandler_dev_raw | ||||||
| { | { | ||||||
|  private: |  private: | ||||||
|  |   _off64_t drive_size; | ||||||
|  |   unsigned long bytes_per_sector; | ||||||
|  |   struct status_flags | ||||||
|  |   { | ||||||
|  |     unsigned eom_detected    : 1; | ||||||
|  |    public: | ||||||
|  |     status_flags () : eom_detected (0) {} | ||||||
|  |   } status; | ||||||
|  |  | ||||||
|  |   IMPLEMENT_STATUS_FLAG (bool, eom_detected) | ||||||
|  |  | ||||||
|  |   inline _off64_t get_current_position (); | ||||||
|   int fhandler_dev_floppy::get_drive_info (struct hd_geometry *geo); |   int fhandler_dev_floppy::get_drive_info (struct hd_geometry *geo); | ||||||
|  |  | ||||||
|  protected: |   BOOL write_file (const void *buf, DWORD to_write, DWORD *written, int *err); | ||||||
|   virtual int is_eom (int win_error); |   BOOL read_file (void *buf, DWORD to_read, DWORD *read, int *err); | ||||||
|   virtual int is_eof (int win_error); |  | ||||||
|  |  | ||||||
|  public: |  public: | ||||||
|   fhandler_dev_floppy (); |   fhandler_dev_floppy (); | ||||||
|  |  | ||||||
|   virtual int open (int flags, mode_t mode = 0); |   int open (int flags, mode_t mode = 0); | ||||||
|  |   int dup (fhandler_base *child); | ||||||
|   virtual _off64_t lseek (_off64_t offset, int whence); |   void raw_read (void *ptr, size_t& ulen); | ||||||
|  |   int raw_write (const void *ptr, size_t ulen); | ||||||
|   virtual int ioctl (unsigned int cmd, void *buf); |   _off64_t lseek (_off64_t offset, int whence); | ||||||
|  |   int ioctl (unsigned int cmd, void *buf); | ||||||
| }; | }; | ||||||
|  |  | ||||||
| class fhandler_dev_tape: public fhandler_dev_raw | class fhandler_dev_tape: public fhandler_dev_raw | ||||||
|   | |||||||
| @@ -14,6 +14,7 @@ details. */ | |||||||
| #include <unistd.h> | #include <unistd.h> | ||||||
| #include <winioctl.h> | #include <winioctl.h> | ||||||
| #include <asm/socket.h> | #include <asm/socket.h> | ||||||
|  | #include <cygwin/rdevio.h> | ||||||
| #include <cygwin/hdreg.h> | #include <cygwin/hdreg.h> | ||||||
| #include <cygwin/fs.h> | #include <cygwin/fs.h> | ||||||
| #include "cygerrno.h" | #include "cygerrno.h" | ||||||
| @@ -21,31 +22,15 @@ details. */ | |||||||
| #include "path.h" | #include "path.h" | ||||||
| #include "fhandler.h" | #include "fhandler.h" | ||||||
|  |  | ||||||
|  | #define IS_EOM(err)	((err) == ERROR_INVALID_PARAMETER \ | ||||||
|  | 			 || (err) == ERROR_SEEK \ | ||||||
|  | 			 || (err) == ERROR_SECTOR_NOT_FOUND) | ||||||
|  |  | ||||||
| /**********************************************************************/ | /**********************************************************************/ | ||||||
| /* fhandler_dev_floppy */ | /* fhandler_dev_floppy */ | ||||||
|  |  | ||||||
| int |  | ||||||
| fhandler_dev_floppy::is_eom (int win_error) |  | ||||||
| { |  | ||||||
|   int ret = (win_error == ERROR_INVALID_PARAMETER |  | ||||||
| 	     || win_error == ERROR_SEEK |  | ||||||
| 	     || win_error == ERROR_SECTOR_NOT_FOUND); |  | ||||||
|   if (ret) |  | ||||||
|     debug_printf ("end of medium"); |  | ||||||
|   return ret; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| fhandler_dev_floppy::is_eof (int) |  | ||||||
| { |  | ||||||
|   int ret = 0; |  | ||||||
|   if (ret) |  | ||||||
|     debug_printf ("end of file"); |  | ||||||
|   return ret; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| fhandler_dev_floppy::fhandler_dev_floppy () | fhandler_dev_floppy::fhandler_dev_floppy () | ||||||
|   : fhandler_dev_raw () |   : fhandler_dev_raw (), status () | ||||||
| { | { | ||||||
| } | } | ||||||
|  |  | ||||||
| @@ -62,9 +47,22 @@ fhandler_dev_floppy::get_drive_info (struct hd_geometry *geo) | |||||||
|  |  | ||||||
|   /* Always try using the new EX ioctls first (>= XP).  If not available, |   /* Always try using the new EX ioctls first (>= XP).  If not available, | ||||||
|      fall back to trying the old non-EX ioctls. */ |      fall back to trying the old non-EX ioctls. */ | ||||||
|   if (!DeviceIoControl (get_handle (), |   if (wincap.has_disk_ex_ioctls ()) | ||||||
| 			IOCTL_DISK_GET_DRIVE_GEOMETRY_EX, NULL, 0, |     { | ||||||
| 			dbuf, 256, &bytes_read, NULL)) |       if (!DeviceIoControl (get_handle (), | ||||||
|  | 			    IOCTL_DISK_GET_DRIVE_GEOMETRY_EX, NULL, 0, | ||||||
|  | 			    dbuf, 256, &bytes_read, NULL)) | ||||||
|  | 	{ | ||||||
|  | 	  __seterrno (); | ||||||
|  | 	  return -1; | ||||||
|  | 	} | ||||||
|  |       di = &((DISK_GEOMETRY_EX *) dbuf)->Geometry; | ||||||
|  |       if (DeviceIoControl (get_handle (), | ||||||
|  | 			   IOCTL_DISK_GET_PARTITION_INFO_EX, NULL, 0, | ||||||
|  | 			   pbuf, 256, &bytes_read, NULL)) | ||||||
|  | 	pix = (PARTITION_INFORMATION_EX *) pbuf; | ||||||
|  |     } | ||||||
|  |   else | ||||||
|     { |     { | ||||||
|       if (!DeviceIoControl (get_handle (), |       if (!DeviceIoControl (get_handle (), | ||||||
| 			    IOCTL_DISK_GET_DRIVE_GEOMETRY, NULL, 0, | 			    IOCTL_DISK_GET_DRIVE_GEOMETRY, NULL, 0, | ||||||
| @@ -74,18 +72,11 @@ fhandler_dev_floppy::get_drive_info (struct hd_geometry *geo) | |||||||
| 	  return -1; | 	  return -1; | ||||||
| 	} | 	} | ||||||
|       di = (DISK_GEOMETRY *) dbuf; |       di = (DISK_GEOMETRY *) dbuf; | ||||||
|  |       if (DeviceIoControl (get_handle (), | ||||||
|  | 			   IOCTL_DISK_GET_PARTITION_INFO, NULL, 0, | ||||||
|  | 			   pbuf, 256, &bytes_read, NULL)) | ||||||
|  | 	pi = (PARTITION_INFORMATION *) pbuf; | ||||||
|     } |     } | ||||||
|   else |  | ||||||
|     di = &((DISK_GEOMETRY_EX *) dbuf)->Geometry; |  | ||||||
|      |  | ||||||
|   if (DeviceIoControl (get_handle (), |  | ||||||
| 		       IOCTL_DISK_GET_PARTITION_INFO_EX, NULL, 0, |  | ||||||
| 		       pbuf, 256, &bytes_read, NULL)) |  | ||||||
|     pix = (PARTITION_INFORMATION_EX *) pbuf; |  | ||||||
|   else if (DeviceIoControl (get_handle (), |  | ||||||
| 			    IOCTL_DISK_GET_PARTITION_INFO, NULL, 0, |  | ||||||
| 			    pbuf, 256, &bytes_read, NULL)) |  | ||||||
|     pi = (PARTITION_INFORMATION *) pbuf; |  | ||||||
|  |  | ||||||
|   debug_printf ("disk geometry: (%ld cyl)*(%ld trk)*(%ld sec)*(%ld bps)", |   debug_printf ("disk geometry: (%ld cyl)*(%ld trk)*(%ld sec)*(%ld bps)", | ||||||
| 		 di->Cylinders.LowPart, | 		 di->Cylinders.LowPart, | ||||||
| @@ -132,22 +123,46 @@ fhandler_dev_floppy::get_drive_info (struct hd_geometry *geo) | |||||||
|   return 0; |   return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
|  | /* Wrapper functions for ReadFile and WriteFile to simplify error handling. */ | ||||||
|  | BOOL | ||||||
|  | fhandler_dev_floppy::read_file (void *buf, DWORD to_read, DWORD *read, int *err) | ||||||
|  | { | ||||||
|  |   BOOL ret; | ||||||
|  |  | ||||||
|  |   *err = 0; | ||||||
|  |   if (!(ret = ReadFile (get_handle (), buf, to_read, read, 0))) | ||||||
|  |     *err = GetLastError (); | ||||||
|  |   syscall_printf ("%d (err %d) = ReadFile (%d, %d, to_read %d, read %d, 0)", | ||||||
|  | 		  ret, *err, get_handle (), buf, to_read, *read); | ||||||
|  |   return ret; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | BOOL | ||||||
|  | fhandler_dev_floppy::write_file (const void *buf, DWORD to_write, | ||||||
|  | 				 DWORD *written, int *err) | ||||||
|  | { | ||||||
|  |   BOOL ret; | ||||||
|  |  | ||||||
|  |   *err = 0; | ||||||
|  |   if (!(ret = WriteFile (get_handle (), buf, to_write, written, 0))) | ||||||
|  |     *err = GetLastError (); | ||||||
|  |   syscall_printf ("%d (err %d) = WriteFile (%d, %d, write %d, written %d, 0)", | ||||||
|  | 		  ret, *err, get_handle (), buf, to_write, *written); | ||||||
|  |   return ret; | ||||||
|  | } | ||||||
|  |  | ||||||
| int | int | ||||||
| fhandler_dev_floppy::open (int flags, mode_t) | fhandler_dev_floppy::open (int flags, mode_t) | ||||||
| { | { | ||||||
|   /* The correct size of the buffer would be 512 bytes, |   /* The correct size of the buffer would be 512 bytes, which is the atomic | ||||||
|    * which is the atomic size, supported by WinNT. |      size, supported by WinNT.  Unfortunately, the performance is worse than | ||||||
|    * Unfortunately, the performance is worse than |      access to file system on same device!  Setting buffer size to a | ||||||
|    * access to file system on same device! |      relatively big value increases performance by means.  The new ioctl call | ||||||
|    * Setting buffer size to a relatively big value |      with 'rdevio.h' header file supports changing this value. | ||||||
|    * increases performance by means. |  | ||||||
|    * The new ioctl call with 'rdevio.h' header file |      Let's try to be smart: Let's take a multiple of typical tar and cpio | ||||||
|    * supports changing this value. |      buffer sizes by default. */ | ||||||
|    * |   devbufsiz = 61440L; | ||||||
|    * Let's be smart: Let's take a multiplier of typical tar |  | ||||||
|    * and cpio buffer sizes by default! |  | ||||||
|   */ |  | ||||||
|   devbufsiz = 61440L; /* 512L; */ |  | ||||||
|   int ret =  fhandler_dev_raw::open (flags); |   int ret =  fhandler_dev_raw::open (flags); | ||||||
|  |  | ||||||
|   if (ret && get_drive_info (NULL)) |   if (ret && get_drive_info (NULL)) | ||||||
| @@ -159,59 +174,244 @@ fhandler_dev_floppy::open (int flags, mode_t) | |||||||
|   return ret; |   return ret; | ||||||
| } | } | ||||||
|  |  | ||||||
|  | int | ||||||
|  | fhandler_dev_floppy::dup (fhandler_base *child) | ||||||
|  | { | ||||||
|  |   int ret = fhandler_dev_raw::dup (child); | ||||||
|  |  | ||||||
|  |   if (!ret) | ||||||
|  |     { | ||||||
|  |       fhandler_dev_floppy *fhc = (fhandler_dev_floppy *) child; | ||||||
|  |  | ||||||
|  |       fhc->drive_size = drive_size; | ||||||
|  |       fhc->bytes_per_sector = bytes_per_sector; | ||||||
|  |       fhc->eom_detected (eom_detected ()); | ||||||
|  |     } | ||||||
|  |   return ret; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | inline _off64_t | ||||||
|  | fhandler_dev_floppy::get_current_position () | ||||||
|  | { | ||||||
|  |   LARGE_INTEGER off = { QuadPart: 0LL }; | ||||||
|  |   off.LowPart = SetFilePointer (get_handle (), 0, &off.HighPart, FILE_CURRENT); | ||||||
|  |   return off.QuadPart; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | void | ||||||
|  | fhandler_dev_floppy::raw_read (void *ptr, size_t& ulen) | ||||||
|  | { | ||||||
|  |   DWORD bytes_read = 0; | ||||||
|  |   DWORD read2; | ||||||
|  |   DWORD bytes_to_read; | ||||||
|  |   int ret; | ||||||
|  |   size_t len = ulen; | ||||||
|  |   char *tgt; | ||||||
|  |   char *p = (char *) ptr; | ||||||
|  |  | ||||||
|  |   /* Checking a previous end of media */ | ||||||
|  |   if (eom_detected () && !lastblk_to_read ()) | ||||||
|  |     { | ||||||
|  |       set_errno (ENOSPC); | ||||||
|  |       goto err; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |   if (devbuf) | ||||||
|  |     { | ||||||
|  |       while (len > 0) | ||||||
|  | 	{ | ||||||
|  | 	  if (devbufstart < devbufend) | ||||||
|  | 	    { | ||||||
|  | 	      bytes_to_read = min (len, devbufend - devbufstart); | ||||||
|  | 	      debug_printf ("read %d bytes from buffer (rest %d)", | ||||||
|  | 			    bytes_to_read, | ||||||
|  | 			    devbufend - devbufstart - bytes_to_read); | ||||||
|  | 	      memcpy (p, devbuf + devbufstart, bytes_to_read); | ||||||
|  | 	      len -= bytes_to_read; | ||||||
|  | 	      p += bytes_to_read; | ||||||
|  | 	      bytes_read += bytes_to_read; | ||||||
|  | 	      devbufstart += bytes_to_read; | ||||||
|  |  | ||||||
|  | 	      if (lastblk_to_read ()) | ||||||
|  | 		{ | ||||||
|  | 		  lastblk_to_read (false); | ||||||
|  | 		  break; | ||||||
|  | 		} | ||||||
|  | 	    } | ||||||
|  | 	  if (len > 0) | ||||||
|  | 	    { | ||||||
|  | 	      if (len >= devbufsiz) | ||||||
|  | 		{ | ||||||
|  | 		  bytes_to_read = (len / bytes_per_sector) * bytes_per_sector; | ||||||
|  | 		  tgt = p; | ||||||
|  | 		} | ||||||
|  | 	      else | ||||||
|  | 		{ | ||||||
|  | 		  tgt = devbuf; | ||||||
|  | 		  bytes_to_read = devbufsiz; | ||||||
|  | 		} | ||||||
|  | 	      _off64_t current_position = get_current_position (); | ||||||
|  | 	      if (current_position + bytes_to_read >= drive_size) | ||||||
|  | 		bytes_to_read = drive_size - current_position; | ||||||
|  | 	      if (!bytes_to_read) | ||||||
|  | 		{ | ||||||
|  | 		  eom_detected (true); | ||||||
|  | 		  break; | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 	      debug_printf ("read %d bytes %s", bytes_to_read, | ||||||
|  | 			    len < devbufsiz ? "into buffer" : "directly"); | ||||||
|  | 	      if (!read_file (tgt, bytes_to_read, &read2, &ret)) | ||||||
|  | 		{ | ||||||
|  | 		  if (!IS_EOM (ret)) | ||||||
|  | 		    { | ||||||
|  | 		      __seterrno (); | ||||||
|  | 		      goto err; | ||||||
|  | 		    } | ||||||
|  |  | ||||||
|  | 		  eom_detected (true); | ||||||
|  |  | ||||||
|  | 		  if (!read2) | ||||||
|  | 		    { | ||||||
|  | 		      if (!bytes_read) | ||||||
|  | 			{ | ||||||
|  | 			  debug_printf ("return -1, set errno to ENOSPC"); | ||||||
|  | 			  set_errno (ENOSPC); | ||||||
|  | 			  goto err; | ||||||
|  | 			} | ||||||
|  | 		      break; | ||||||
|  | 		    } | ||||||
|  | 		  lastblk_to_read (true); | ||||||
|  | 		} | ||||||
|  | 	      if (!read2) | ||||||
|  | 	       break; | ||||||
|  | 	      if (tgt == devbuf) | ||||||
|  | 		{ | ||||||
|  | 		  devbufstart = 0; | ||||||
|  | 		  devbufend = read2; | ||||||
|  | 		} | ||||||
|  | 	      else | ||||||
|  | 		{ | ||||||
|  | 		  len -= read2; | ||||||
|  | 		  p += read2; | ||||||
|  | 		  bytes_read += read2; | ||||||
|  | 		} | ||||||
|  | 	    } | ||||||
|  | 	} | ||||||
|  |     } | ||||||
|  |   else if (!read_file (p, len, &bytes_read, &ret)) | ||||||
|  |     { | ||||||
|  |       if (!IS_EOM (ret)) | ||||||
|  | 	{ | ||||||
|  | 	  __seterrno (); | ||||||
|  | 	  goto err; | ||||||
|  | 	} | ||||||
|  |       if (bytes_read) | ||||||
|  | 	eom_detected (true); | ||||||
|  |       else | ||||||
|  | 	{ | ||||||
|  | 	  debug_printf ("return -1, set errno to ENOSPC"); | ||||||
|  | 	  set_errno (ENOSPC); | ||||||
|  | 	  goto err; | ||||||
|  | 	} | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |   ulen = (size_t) bytes_read; | ||||||
|  |   return; | ||||||
|  |  | ||||||
|  | err: | ||||||
|  |   ulen = (size_t) -1; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | int | ||||||
|  | fhandler_dev_floppy::raw_write (const void *ptr, size_t len) | ||||||
|  | { | ||||||
|  |   DWORD bytes_written = 0; | ||||||
|  |   char *p = (char *) ptr; | ||||||
|  |   int ret; | ||||||
|  |  | ||||||
|  |   /* Checking a previous end of media on tape */ | ||||||
|  |   if (eom_detected ()) | ||||||
|  |     { | ||||||
|  |       set_errno (ENOSPC); | ||||||
|  |       return -1; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |   /* Invalidate buffer. */ | ||||||
|  |   devbufstart = devbufend = 0; | ||||||
|  |  | ||||||
|  |   if (len > 0) | ||||||
|  |     { | ||||||
|  |       if (!write_file (p, len, &bytes_written, &ret)) | ||||||
|  | 	{ | ||||||
|  | 	  if (!IS_EOM (ret)) | ||||||
|  | 	    { | ||||||
|  | 	      __seterrno (); | ||||||
|  | 	      return -1; | ||||||
|  | 	    } | ||||||
|  | 	  eom_detected (true); | ||||||
|  | 	  if (!bytes_written) | ||||||
|  | 	    { | ||||||
|  | 	      set_errno (ENOSPC); | ||||||
|  | 	      return -1; | ||||||
|  | 	    } | ||||||
|  | 	} | ||||||
|  |     } | ||||||
|  |   return bytes_written; | ||||||
|  | } | ||||||
|  |  | ||||||
| _off64_t | _off64_t | ||||||
| fhandler_dev_floppy::lseek (_off64_t offset, int whence) | fhandler_dev_floppy::lseek (_off64_t offset, int whence) | ||||||
| { | { | ||||||
|   char buf[512]; |   char buf[512]; | ||||||
|   _off64_t lloffset = offset; |   _off64_t lloffset = offset; | ||||||
|   _off64_t sector_aligned_offset; |   LARGE_INTEGER sector_aligned_offset; | ||||||
|   _off64_t bytes_left; |   _off64_t bytes_left; | ||||||
|   DWORD low; |  | ||||||
|   LONG high = 0; |  | ||||||
|  |  | ||||||
|   if (whence == SEEK_END && drive_size > 0) |   if (whence == SEEK_END) | ||||||
|     { |     { | ||||||
|       lloffset = offset + drive_size; |       lloffset += drive_size; | ||||||
|  |       whence = SEEK_SET; | ||||||
|  |     } | ||||||
|  |   else if (whence == SEEK_CUR) | ||||||
|  |     { | ||||||
|  |       lloffset += get_current_position () - (devbufend - devbufstart); | ||||||
|       whence = SEEK_SET; |       whence = SEEK_SET; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|   if (whence == SEEK_CUR) |   if (whence != SEEK_SET || lloffset < 0 || lloffset >= drive_size) | ||||||
|     { |  | ||||||
|       lloffset += current_position - (devbufend - devbufstart); |  | ||||||
|       whence = SEEK_SET; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|   if (whence != SEEK_SET |  | ||||||
|       || lloffset < 0 |  | ||||||
|       || drive_size > 0 && lloffset >= drive_size) |  | ||||||
|     { |     { | ||||||
|       set_errno (EINVAL); |       set_errno (EINVAL); | ||||||
|       return -1; |       return -1; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|   sector_aligned_offset = (lloffset / bytes_per_sector) * bytes_per_sector; |   sector_aligned_offset.QuadPart = (lloffset / bytes_per_sector) | ||||||
|   bytes_left = lloffset - sector_aligned_offset; | 				   * bytes_per_sector; | ||||||
|  |   bytes_left = lloffset - sector_aligned_offset.QuadPart; | ||||||
|  |  | ||||||
|   /* Invalidate buffer. */ |   /* Invalidate buffer. */ | ||||||
|   devbufstart = devbufend = 0; |   devbufstart = devbufend = 0; | ||||||
|  |  | ||||||
|   low = sector_aligned_offset & UINT32_MAX; |   sector_aligned_offset.LowPart = | ||||||
|   high = sector_aligned_offset >> 32; | 			SetFilePointer (get_handle (), | ||||||
|   if (SetFilePointer (get_handle (), low, &high, FILE_BEGIN) | 					sector_aligned_offset.LowPart, | ||||||
|       == INVALID_SET_FILE_POINTER && GetLastError ()) | 					§or_aligned_offset.HighPart, | ||||||
|  | 					FILE_BEGIN); | ||||||
|  |   if (sector_aligned_offset.LowPart == INVALID_SET_FILE_POINTER | ||||||
|  |       && GetLastError ()) | ||||||
|     { |     { | ||||||
|       __seterrno (); |       __seterrno (); | ||||||
|       return -1; |       return -1; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|   eom_detected (false); |   eom_detected (false); | ||||||
|   current_position = sector_aligned_offset; |  | ||||||
|   if (bytes_left) |   if (bytes_left) | ||||||
|     { |     { | ||||||
|       size_t len = bytes_left; |       size_t len = bytes_left; | ||||||
|       raw_read (buf, len); |       raw_read (buf, len); | ||||||
|     } |     } | ||||||
|   return current_position + bytes_left; |   return sector_aligned_offset.QuadPart + bytes_left; | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| @@ -257,6 +457,18 @@ fhandler_dev_floppy::ioctl (unsigned int cmd, void *buf) | |||||||
| 	*(int *)buf = bytes_per_sector; | 	*(int *)buf = bytes_per_sector; | ||||||
| 	return 0; | 	return 0; | ||||||
|       } |       } | ||||||
|  |     case RDSETBLK: | ||||||
|  |       /* Just check the restriction that blocksize must be a multiple | ||||||
|  |          of the sector size of the underlying volume sector size, | ||||||
|  | 	 then fall through to fhandler_dev_raw::ioctl. */ | ||||||
|  |       struct rdop *op = (struct rdop *) buf; | ||||||
|  |       if (op->rd_parm % bytes_per_sector) | ||||||
|  | 	{ | ||||||
|  | 	  SetLastError (ERROR_INVALID_PARAMETER); | ||||||
|  | 	  __seterrno (); | ||||||
|  | 	  return -1; | ||||||
|  | 	} | ||||||
|  |       /*FALLTHRUGH*/ | ||||||
|     default: |     default: | ||||||
|       return fhandler_dev_raw::ioctl (cmd, buf); |       return fhandler_dev_raw::ioctl (cmd, buf); | ||||||
|     } |     } | ||||||
|   | |||||||
| @@ -27,52 +27,6 @@ | |||||||
| /**********************************************************************/ | /**********************************************************************/ | ||||||
| /* fhandler_dev_raw */ | /* fhandler_dev_raw */ | ||||||
|  |  | ||||||
| int |  | ||||||
| fhandler_dev_raw::is_eom (int win_error) |  | ||||||
| { |  | ||||||
|   return 0; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| fhandler_dev_raw::is_eof (int) |  | ||||||
| { |  | ||||||
|   return 0; |  | ||||||
| } |  | ||||||
|  |  | ||||||
|  |  | ||||||
| /* Wrapper functions to simplify error handling. */ |  | ||||||
|  |  | ||||||
| BOOL |  | ||||||
| fhandler_dev_raw::write_file (const void *buf, DWORD to_write, |  | ||||||
| 			      DWORD *written, int *err) |  | ||||||
| { |  | ||||||
|   BOOL ret; |  | ||||||
|  |  | ||||||
|   *err = 0; |  | ||||||
|   if (!(ret = WriteFile (get_handle (), buf, to_write, written, 0))) |  | ||||||
|     *err = GetLastError (); |  | ||||||
|   else |  | ||||||
|     current_position += *written; |  | ||||||
|   syscall_printf ("%d (err %d) = WriteFile (%d, %d, write %d, written %d, 0)", |  | ||||||
| 		  ret, *err, get_handle (), buf, to_write, *written); |  | ||||||
|   return ret; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| BOOL |  | ||||||
| fhandler_dev_raw::read_file (void *buf, DWORD to_read, DWORD *read, int *err) |  | ||||||
| { |  | ||||||
|   BOOL ret; |  | ||||||
|  |  | ||||||
|   *err = 0; |  | ||||||
|   if (!(ret = ReadFile (get_handle (), buf, to_read, read, 0))) |  | ||||||
|     *err = GetLastError (); |  | ||||||
|   else |  | ||||||
|     current_position += *read; |  | ||||||
|   syscall_printf ("%d (err %d) = ReadFile (%d, %d, to_read %d, read %d, 0)", |  | ||||||
| 		  ret, *err, get_handle (), buf, to_read, *read); |  | ||||||
|   return ret; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| fhandler_dev_raw::fhandler_dev_raw () | fhandler_dev_raw::fhandler_dev_raw () | ||||||
|   : fhandler_base (), status () |   : fhandler_base (), status () | ||||||
| { | { | ||||||
| @@ -140,205 +94,20 @@ fhandler_dev_raw::open (int flags, mode_t) | |||||||
|   return res; |   return res; | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| fhandler_dev_raw::raw_read (void *ptr, size_t& ulen) |  | ||||||
| { |  | ||||||
|   DWORD bytes_read = 0; |  | ||||||
|   DWORD read2; |  | ||||||
|   DWORD bytes_to_read; |  | ||||||
|   int ret; |  | ||||||
|   size_t len = ulen; |  | ||||||
|   char *tgt; |  | ||||||
|   char *p = (char *) ptr; |  | ||||||
|  |  | ||||||
|   /* Checking a previous end of file */ |  | ||||||
|   if (eof_detected () && !lastblk_to_read ()) |  | ||||||
|     { |  | ||||||
|       eof_detected (false); |  | ||||||
|       ulen = 0; |  | ||||||
|       return; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|   /* Checking a previous end of media */ |  | ||||||
|   if (eom_detected () && !lastblk_to_read ()) |  | ||||||
|     { |  | ||||||
|       set_errno (ENOSPC); |  | ||||||
|       goto err; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|   if (devbuf) |  | ||||||
|     { |  | ||||||
|       while (len > 0) |  | ||||||
| 	{ |  | ||||||
| 	  if (devbufstart < devbufend) |  | ||||||
| 	    { |  | ||||||
| 	      bytes_to_read = min (len, devbufend - devbufstart); |  | ||||||
| 	      debug_printf ("read %d bytes from buffer (rest %d)", |  | ||||||
| 			    bytes_to_read, |  | ||||||
| 			    devbufend - devbufstart - bytes_to_read); |  | ||||||
| 	      memcpy (p, devbuf + devbufstart, bytes_to_read); |  | ||||||
| 	      len -= bytes_to_read; |  | ||||||
| 	      p += bytes_to_read; |  | ||||||
| 	      bytes_read += bytes_to_read; |  | ||||||
| 	      devbufstart += bytes_to_read; |  | ||||||
|  |  | ||||||
| 	      if (lastblk_to_read ()) |  | ||||||
| 		{ |  | ||||||
| 		  lastblk_to_read (false); |  | ||||||
| 		  break; |  | ||||||
| 		} |  | ||||||
| 	    } |  | ||||||
| 	  if (len > 0) |  | ||||||
| 	    { |  | ||||||
| 	      if (len >= devbufsiz) |  | ||||||
| 		{ |  | ||||||
| 		  bytes_to_read = (len / bytes_per_sector) * bytes_per_sector; |  | ||||||
| 		  if (current_position + bytes_to_read >= drive_size) |  | ||||||
| 		    bytes_to_read = drive_size - current_position; |  | ||||||
| 		  tgt = p; |  | ||||||
| 		  debug_printf ("read %d bytes direct from file",bytes_to_read); |  | ||||||
| 		} |  | ||||||
| 	      else |  | ||||||
| 		{ |  | ||||||
| 		  tgt = devbuf; |  | ||||||
| 		  bytes_to_read = devbufsiz; |  | ||||||
| 		  if (current_position + bytes_to_read >= drive_size) |  | ||||||
| 		    bytes_to_read = drive_size - current_position; |  | ||||||
| 		  debug_printf ("read %d bytes from file into buffer", |  | ||||||
| 				bytes_to_read); |  | ||||||
| 		} |  | ||||||
| 	      if (!bytes_to_read) |  | ||||||
| 		{ |  | ||||||
| 		  eom_detected (true); |  | ||||||
| 		  break; |  | ||||||
| 		} |  | ||||||
|  |  | ||||||
| 	      if (!read_file (tgt, bytes_to_read, &read2, &ret)) |  | ||||||
| 		{ |  | ||||||
| 		  if (!is_eof (ret) && !is_eom (ret)) |  | ||||||
| 		    { |  | ||||||
| 		      __seterrno (); |  | ||||||
| 		      goto err; |  | ||||||
| 		    } |  | ||||||
|  |  | ||||||
| 		  if (is_eof (ret)) |  | ||||||
| 		    eof_detected (true); |  | ||||||
| 		  else |  | ||||||
| 		    eom_detected (true); |  | ||||||
|  |  | ||||||
| 		  if (!read2) |  | ||||||
| 		    { |  | ||||||
| 		      if (!bytes_read && is_eom (ret)) |  | ||||||
| 			{ |  | ||||||
| 			  debug_printf ("return -1, set errno to ENOSPC"); |  | ||||||
| 			  set_errno (ENOSPC); |  | ||||||
| 			  goto err; |  | ||||||
| 			} |  | ||||||
| 		      break; |  | ||||||
| 		    } |  | ||||||
| 		  lastblk_to_read (true); |  | ||||||
| 		} |  | ||||||
| 	      if (!read2) |  | ||||||
| 	       break; |  | ||||||
| 	      if (tgt == devbuf) |  | ||||||
| 		{ |  | ||||||
| 		  devbufstart = 0; |  | ||||||
| 		  devbufend = read2; |  | ||||||
| 		} |  | ||||||
| 	      else |  | ||||||
| 		{ |  | ||||||
| 		  len -= read2; |  | ||||||
| 		  p += read2; |  | ||||||
| 		  bytes_read += read2; |  | ||||||
| 		} |  | ||||||
| 	    } |  | ||||||
| 	} |  | ||||||
|     } |  | ||||||
|   else if (!read_file (p, len, &bytes_read, &ret)) |  | ||||||
|     { |  | ||||||
|       if (!is_eof (ret) && !is_eom (ret)) |  | ||||||
| 	{ |  | ||||||
| 	  __seterrno (); |  | ||||||
| 	  goto err; |  | ||||||
| 	} |  | ||||||
|       if (bytes_read) |  | ||||||
| 	{ |  | ||||||
| 	  if (is_eof (ret)) |  | ||||||
| 	    eof_detected (true); |  | ||||||
| 	  else |  | ||||||
| 	    eom_detected (true); |  | ||||||
| 	} |  | ||||||
|       else if (is_eom (ret)) |  | ||||||
| 	{ |  | ||||||
| 	  debug_printf ("return -1, set errno to ENOSPC"); |  | ||||||
| 	  set_errno (ENOSPC); |  | ||||||
| 	  goto err; |  | ||||||
| 	} |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|   ulen = (size_t) bytes_read; |  | ||||||
|   return; |  | ||||||
|  |  | ||||||
| err: |  | ||||||
|   ulen = (size_t) -1; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| fhandler_dev_raw::raw_write (const void *ptr, size_t len) |  | ||||||
| { |  | ||||||
|   DWORD bytes_written = 0; |  | ||||||
|   char *p = (char *) ptr; |  | ||||||
|   int ret; |  | ||||||
|  |  | ||||||
|   /* Checking a previous end of media on tape */ |  | ||||||
|   if (eom_detected ()) |  | ||||||
|     { |  | ||||||
|       set_errno (ENOSPC); |  | ||||||
|       return -1; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|   /* Invalidate buffer. */ |  | ||||||
|   devbufstart = devbufend = 0; |  | ||||||
|  |  | ||||||
|   if (len > 0) |  | ||||||
|     { |  | ||||||
|       if (!write_file (p, len, &bytes_written, &ret)) |  | ||||||
| 	{ |  | ||||||
| 	  if (!is_eom (ret)) |  | ||||||
| 	    { |  | ||||||
| 	      __seterrno (); |  | ||||||
| 	      return -1; |  | ||||||
| 	    } |  | ||||||
| 	  eom_detected (true); |  | ||||||
| 	  if (!bytes_written) |  | ||||||
| 	    { |  | ||||||
| 	      set_errno (ENOSPC); |  | ||||||
| 	      return -1; |  | ||||||
| 	    } |  | ||||||
| 	} |  | ||||||
|     } |  | ||||||
|   return bytes_written; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| fhandler_dev_raw::dup (fhandler_base *child) | fhandler_dev_raw::dup (fhandler_base *child) | ||||||
| { | { | ||||||
|   int ret = fhandler_base::dup (child); |   int ret = fhandler_base::dup (child); | ||||||
|  |  | ||||||
|   if (! ret) |   if (!ret) | ||||||
|     { |     { | ||||||
|       fhandler_dev_raw *fhc = (fhandler_dev_raw *) child; |       fhandler_dev_raw *fhc = (fhandler_dev_raw *) child; | ||||||
|  |  | ||||||
|       fhc->drive_size = drive_size; |  | ||||||
|       fhc->current_position = current_position; |  | ||||||
|       fhc->bytes_per_sector = bytes_per_sector; |  | ||||||
|       fhc->devbufsiz = devbufsiz; |       fhc->devbufsiz = devbufsiz; | ||||||
|       if (devbufsiz > 1L) |       if (devbufsiz > 1L) | ||||||
| 	fhc->devbuf = new char [devbufsiz]; | 	fhc->devbuf = new char [devbufsiz]; | ||||||
|       fhc->devbufstart = 0; |       fhc->devbufstart = 0; | ||||||
|       fhc->devbufend = 0; |       fhc->devbufend = 0; | ||||||
|       fhc->eom_detected (eom_detected ()); |  | ||||||
|       fhc->eof_detected (eof_detected ()); |  | ||||||
|       fhc->lastblk_to_read (false); |       fhc->lastblk_to_read (false); | ||||||
|     } |     } | ||||||
|   return ret; |   return ret; | ||||||
| @@ -385,8 +154,6 @@ fhandler_dev_raw::ioctl (unsigned int cmd, void *buf) | |||||||
| 		mop.mt_count = op->rd_parm; | 		mop.mt_count = op->rd_parm; | ||||||
| 		ret = ioctl (MTIOCTOP, &mop); | 		ret = ioctl (MTIOCTOP, &mop); | ||||||
| 	      } | 	      } | ||||||
| 	    else if (op->rd_parm % bytes_per_sector) |  | ||||||
| 	      ret = ERROR_INVALID_PARAMETER; |  | ||||||
| 	    else if (devbuf && op->rd_parm < devbufend - devbufstart) | 	    else if (devbuf && op->rd_parm < devbufend - devbufstart) | ||||||
| 	      ret = ERROR_INVALID_PARAMETER; | 	      ret = ERROR_INVALID_PARAMETER; | ||||||
| 	    else if (!devbuf || op->rd_parm != devbufsiz) | 	    else if (!devbuf || op->rd_parm != devbufsiz) | ||||||
|   | |||||||
| @@ -59,7 +59,8 @@ static NO_COPY wincaps wincap_unknown = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:true, |   detect_win16_exe:true, | ||||||
|   has_null_console_handler_routine:false |   has_null_console_handler_routine:false, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_95 = { | static NO_COPY wincaps wincap_95 = { | ||||||
| @@ -110,7 +111,8 @@ static NO_COPY wincaps wincap_95 = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:true, |   detect_win16_exe:true, | ||||||
|   has_null_console_handler_routine:false |   has_null_console_handler_routine:false, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_95osr2 = { | static NO_COPY wincaps wincap_95osr2 = { | ||||||
| @@ -161,7 +163,8 @@ static NO_COPY wincaps wincap_95osr2 = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:true, |   detect_win16_exe:true, | ||||||
|   has_null_console_handler_routine:false |   has_null_console_handler_routine:false, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_98 = { | static NO_COPY wincaps wincap_98 = { | ||||||
| @@ -212,7 +215,8 @@ static NO_COPY wincaps wincap_98 = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:true, |   detect_win16_exe:true, | ||||||
|   has_null_console_handler_routine:false |   has_null_console_handler_routine:false, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_98se = { | static NO_COPY wincaps wincap_98se = { | ||||||
| @@ -263,7 +267,8 @@ static NO_COPY wincaps wincap_98se = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:true, |   detect_win16_exe:true, | ||||||
|   has_null_console_handler_routine:false |   has_null_console_handler_routine:false, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_me = { | static NO_COPY wincaps wincap_me = { | ||||||
| @@ -314,7 +319,8 @@ static NO_COPY wincaps wincap_me = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:true, |   detect_win16_exe:true, | ||||||
|   has_null_console_handler_routine:false |   has_null_console_handler_routine:false, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_nt3 = { | static NO_COPY wincaps wincap_nt3 = { | ||||||
| @@ -365,7 +371,8 @@ static NO_COPY wincaps wincap_nt3 = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:false, |   detect_win16_exe:false, | ||||||
|   has_null_console_handler_routine:true |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_nt4 = { | static NO_COPY wincaps wincap_nt4 = { | ||||||
| @@ -416,7 +423,8 @@ static NO_COPY wincaps wincap_nt4 = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:false, |   detect_win16_exe:false, | ||||||
|   has_null_console_handler_routine:true |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_nt4sp4 = { | static NO_COPY wincaps wincap_nt4sp4 = { | ||||||
| @@ -467,7 +475,8 @@ static NO_COPY wincaps wincap_nt4sp4 = { | |||||||
|   has_extended_priority_class:false, |   has_extended_priority_class:false, | ||||||
|   has_guid_volumes:false, |   has_guid_volumes:false, | ||||||
|   detect_win16_exe:false, |   detect_win16_exe:false, | ||||||
|   has_null_console_handler_routine:true |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_2000 = { | static NO_COPY wincaps wincap_2000 = { | ||||||
| @@ -518,7 +527,8 @@ static NO_COPY wincaps wincap_2000 = { | |||||||
|   has_extended_priority_class:true, |   has_extended_priority_class:true, | ||||||
|   has_guid_volumes:true, |   has_guid_volumes:true, | ||||||
|   detect_win16_exe:false, |   detect_win16_exe:false, | ||||||
|   has_null_console_handler_routine:true |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:false | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_xp = { | static NO_COPY wincaps wincap_xp = { | ||||||
| @@ -569,7 +579,8 @@ static NO_COPY wincaps wincap_xp = { | |||||||
|   has_extended_priority_class:true, |   has_extended_priority_class:true, | ||||||
|   has_guid_volumes:true, |   has_guid_volumes:true, | ||||||
|   detect_win16_exe:false, |   detect_win16_exe:false, | ||||||
|   has_null_console_handler_routine:true |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:true | ||||||
| }; | }; | ||||||
|  |  | ||||||
| static NO_COPY wincaps wincap_2003 = { | static NO_COPY wincaps wincap_2003 = { | ||||||
| @@ -620,7 +631,60 @@ static NO_COPY wincaps wincap_2003 = { | |||||||
|   has_extended_priority_class:true, |   has_extended_priority_class:true, | ||||||
|   has_guid_volumes:true, |   has_guid_volumes:true, | ||||||
|   detect_win16_exe:false, |   detect_win16_exe:false, | ||||||
|   has_null_console_handler_routine:true |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:true | ||||||
|  | }; | ||||||
|  |  | ||||||
|  | static NO_COPY wincaps wincap_vista = { | ||||||
|  |   lock_file_highword:UINT32_MAX, | ||||||
|  |   chunksize:0, | ||||||
|  |   shared:FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE, | ||||||
|  |   is_winnt:true, | ||||||
|  |   is_server:true, | ||||||
|  |   access_denied_on_delete:false, | ||||||
|  |   has_delete_on_close:true, | ||||||
|  |   has_page_guard:true, | ||||||
|  |   has_security:true, | ||||||
|  |   has_security_descriptor_control:true, | ||||||
|  |   has_get_process_times:true, | ||||||
|  |   has_lseek_bug:false, | ||||||
|  |   has_lock_file_ex:true, | ||||||
|  |   has_signal_object_and_wait:true, | ||||||
|  |   has_eventlog:true, | ||||||
|  |   has_ip_helper_lib:true, | ||||||
|  |   has_set_handle_information:true, | ||||||
|  |   has_set_handle_information_on_console_handles:true, | ||||||
|  |   supports_smp:true, | ||||||
|  |   map_view_of_file_ex_sucks:false, | ||||||
|  |   altgr_is_ctrl_alt:true, | ||||||
|  |   has_physical_mem_access:true, | ||||||
|  |   has_working_copy_on_write:true, | ||||||
|  |   share_mmaps_only_by_name:false, | ||||||
|  |   virtual_protect_works_on_shared_pages:true, | ||||||
|  |   has_hard_links:true, | ||||||
|  |   can_open_directories:true, | ||||||
|  |   has_move_file_ex:true, | ||||||
|  |   has_negative_pids:false, | ||||||
|  |   has_unreliable_pipes:false, | ||||||
|  |   has_named_pipes:true, | ||||||
|  |   has_try_enter_critical_section:true, | ||||||
|  |   has_raw_devices:true, | ||||||
|  |   has_valid_processorlevel:true, | ||||||
|  |   has_64bit_file_access:true, | ||||||
|  |   has_process_io_counters:true, | ||||||
|  |   supports_reading_modem_output_lines:true, | ||||||
|  |   needs_memory_protection:true, | ||||||
|  |   pty_needs_alloc_console:true, | ||||||
|  |   has_terminal_services:true, | ||||||
|  |   has_switch_to_thread:true, | ||||||
|  |   cant_debug_dll_entry:false, | ||||||
|  |   has_ioctl_storage_get_media_types_ex:true, | ||||||
|  |   start_proc_suspended:false, | ||||||
|  |   has_extended_priority_class:true, | ||||||
|  |   has_guid_volumes:true, | ||||||
|  |   detect_win16_exe:false, | ||||||
|  |   has_null_console_handler_routine:true, | ||||||
|  |   has_disk_ex_ioctls:true | ||||||
| }; | }; | ||||||
|  |  | ||||||
| wincapc wincap; | wincapc wincap; | ||||||
| @@ -676,6 +740,11 @@ wincapc::init () | |||||||
| 		    caps = &wincap_2003; | 		    caps = &wincap_2003; | ||||||
| 		} | 		} | ||||||
| 	      break; | 	      break; | ||||||
|  | 	    case 6: | ||||||
|  | 	      os = "NT"; | ||||||
|  | 	      has_osversioninfoex = true; | ||||||
|  | 	      caps = &wincap_vista; | ||||||
|  | 	      break; | ||||||
| 	    default: | 	    default: | ||||||
| 	      os = "??"; | 	      os = "??"; | ||||||
| 	      caps = &wincap_unknown; | 	      caps = &wincap_unknown; | ||||||
|   | |||||||
| @@ -61,6 +61,7 @@ struct wincaps | |||||||
|   unsigned has_guid_volumes				: 1; |   unsigned has_guid_volumes				: 1; | ||||||
|   unsigned detect_win16_exe				: 1; |   unsigned detect_win16_exe				: 1; | ||||||
|   unsigned has_null_console_handler_routine		: 1; |   unsigned has_null_console_handler_routine		: 1; | ||||||
|  |   unsigned has_disk_ex_ioctls				: 1; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| class wincapc | class wincapc | ||||||
| @@ -126,6 +127,7 @@ public: | |||||||
|   bool	IMPLEMENT (has_guid_volumes) |   bool	IMPLEMENT (has_guid_volumes) | ||||||
|   bool	IMPLEMENT (detect_win16_exe) |   bool	IMPLEMENT (detect_win16_exe) | ||||||
|   bool	IMPLEMENT (has_null_console_handler_routine) |   bool	IMPLEMENT (has_null_console_handler_routine) | ||||||
|  |   bool	IMPLEMENT (has_disk_ex_ioctls) | ||||||
|  |  | ||||||
| #undef IMPLEMENT | #undef IMPLEMENT | ||||||
| }; | }; | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user