From ad53f4c24af841f2c533bef49d81d20bbf2fd24f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jean-Pierre=20Andr=C3=A9?= Date: Tue, 1 Mar 2011 12:04:43 +0100 Subject: [PATCH] Enabled getting the sector size from an ioctl on FreeBSD and MacOSX (Erik Larsson) The sector size is needed for formatting a volume unless forced through an option or using the traditional sector size. --- configure.ac | 8 +++---- libntfs-3g/device.c | 55 +++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 59 insertions(+), 4 deletions(-) diff --git a/configure.ac b/configure.ac index 128340ad..c8853192 100644 --- a/configure.ac +++ b/configure.ac @@ -367,10 +367,10 @@ AC_HEADER_STDC AC_CHECK_HEADERS([ctype.h fcntl.h libgen.h libintl.h limits.h locale.h \ mntent.h stddef.h stdint.h stdlib.h stdio.h stdarg.h string.h \ strings.h errno.h time.h unistd.h utime.h wchar.h getopt.h features.h \ - endian.h byteswap.h sys/byteorder.h sys/endian.h sys/param.h \ - sys/ioctl.h sys/mkdev.h sys/mount.h sys/stat.h sys/types.h sys/vfs.h \ - sys/statvfs.h sys/sysmacros.h linux/major.h linux/fd.h linux/hdreg.h \ - machine/endian.h windows.h syslog.h pwd.h]) + endian.h byteswap.h sys/byteorder.h sys/disk.h sys/endian.h \ + sys/param.h sys/ioctl.h sys/mkdev.h sys/mount.h sys/stat.h sys/types.h \ + sys/vfs.h sys/statvfs.h sys/sysmacros.h linux/major.h linux/fd.h \ + linux/hdreg.h machine/endian.h windows.h syslog.h pwd.h]) # Checks for typedefs, structures, and compiler characteristics. AC_HEADER_STDBOOL diff --git a/libntfs-3g/device.c b/libntfs-3g/device.c index db840108..274abacb 100644 --- a/libntfs-3g/device.c +++ b/libntfs-3g/device.c @@ -58,6 +58,9 @@ #ifdef HAVE_SYS_MOUNT_H #include #endif +#ifdef HAVE_SYS_DISK_H +#include +#endif #ifdef HAVE_LINUX_FD_H #include #endif @@ -556,6 +559,36 @@ s64 ntfs_device_size_get(struct ntfs_device *dev, int block_size) return (s64)this_floppy.size * 512 / block_size; } } +#endif +#ifdef DIOCGMEDIASIZE + { + /* FreeBSD */ + off_t size; + + if (dev->d_ops->ioctl(dev, DIOCGMEDIASIZE, &size) >= 0) { + ntfs_log_debug("DIOCGMEDIASIZE nr bytes = %llu (0x%llx)\n", + (unsigned long long)size, + (unsigned long long)size); + return (s64)size / block_size; + } + } +#endif +#ifdef DKIOCGETBLOCKCOUNT + { + /* Mac OS X */ + uint64_t blocks; + int sector_size; + + sector_size = ntfs_device_sector_size_get(dev); + if (sector_size >= 0 && dev->d_ops->ioctl(dev, + DKIOCGETBLOCKCOUNT, &blocks) >= 0) + { + ntfs_log_debug("DKIOCGETBLOCKCOUNT nr blocks = %llu (0x%llx)\n", + (unsigned long long) blocks, + (unsigned long long) blocks); + return blocks * sector_size / block_size; + } + } #endif /* * We couldn't figure it out by using a specialized ioctl, @@ -705,6 +738,28 @@ int ntfs_device_sector_size_get(struct ntfs_device *dev) return sect_size; } } +#elif defined(DIOCGSECTORSIZE) + { + /* FreeBSD */ + size_t sect_size = 0; + + if (!dev->d_ops->ioctl(dev, DIOCGSECTORSIZE, §_size)) { + ntfs_log_debug("DIOCGSECTORSIZE sector size = %d bytes\n", + (int) sect_size); + return sect_size; + } + } +#elif defined(DKIOCGETBLOCKSIZE) + { + /* Mac OS X */ + uint32_t sect_size = 0; + + if (!dev->d_ops->ioctl(dev, DKIOCGETBLOCKSIZE, §_size)) { + ntfs_log_debug("DKIOCGETBLOCKSIZE sector size = %d bytes\n", + (int) sect_size); + return sect_size; + } + } #else errno = EOPNOTSUPP; #endif