summaryrefslogtreecommitdiff
path: root/sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c
diff options
context:
space:
mode:
authorDaichi GOTO <daichi@FreeBSD.org>2003-06-24 08:03:36 +0000
committerDaichi GOTO <daichi@FreeBSD.org>2003-06-24 08:03:36 +0000
commit528d417f18c4c5f3350c037644a32bd58796fdf0 (patch)
tree1a73afc61fb82901c3fccf97dcc1659989aaf0b2 /sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c
parentUpdate to version 1.21. (diff)
Update port: sysutils/linuxfdisk
PR: 53666 Submitted by: Valentin Nechayev <netch@netch.kiev.ua> (maintainer)
Notes
Notes: svn path=/head/; revision=83517
Diffstat (limited to 'sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c')
-rw-r--r--sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c88
1 files changed, 64 insertions, 24 deletions
diff --git a/sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c b/sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c
index 22767ba366b7..fde86bc2bf21 100644
--- a/sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c
+++ b/sysutils/linuxfdisk/files/linuxfdisk-sys_bsd.c
@@ -2,6 +2,7 @@
#include <sys/disklabel.h>
#if __FreeBSD_version < 500000
#include <sys/diskslice.h>
+#include <sys/stat.h>
#else
#include <sys/disk.h>
#include <errno.h>
@@ -13,13 +14,23 @@ unsigned int
sys_bsd_sectorsize(int fd)
{
#ifdef DIOCGSECTORSIZE
- unsigned int d;
- if (ioctl(fd, DIOCGSECTORSIZE, &d) == 0)
- return d;
-#else
- struct disklabel dl;
- if (ioctl(fd, DIOCGDINFO, &dl) == 0)
- return dl.d_secsize;
+ ;{
+ unsigned int d;
+ if (ioctl(fd, DIOCGSECTORSIZE, &d) == 0)
+ return d;
+ }
+#endif
+ ;{
+ struct disklabel dl;
+ if (ioctl(fd, DIOCGDINFO, &dl) == 0)
+ return dl.d_secsize;
+ }
+#ifdef DIOCGSLICEINFO
+ ;{
+ struct diskslices dss;
+ if (ioctl(fd, DIOCGSLICEINFO, &dss) == 0)
+ return dss.dss_secsize;
+ }
#endif
return 0;
}
@@ -28,23 +39,48 @@ int
sys_bsd_getsectors(int fd, unsigned long *s)
{
/* XXX */
-#if defined(DIOCGMEDIASIZE) && defined(DIOCGSECTORSIZE)
- off_t fullsize;
- unsigned sectsize;
- if (ioctl(fd, DIOCGMEDIASIZE, &fullsize) ||
- ioctl(fd, DIOCGSECTORSIZE, &sectsize))
- return -1;
- *s = fullsize / sectsize;
- return 0;
-#else
struct disklabel dl;
- if (ioctl(fd, DIOCGDINFO, &dl) < 0)
- return -1;
- *s = (unsigned long) dl.d_ncylinders *
- (unsigned long) dl.d_ntracks *
- (unsigned long) dl.d_nsectors;
- return 0;
+#if defined(DIOCGMEDIASIZE) && defined(DIOCGSECTORSIZE)
+ ;{
+ off_t fullsize;
+ unsigned sectsize;
+ if (ioctl(fd, DIOCGMEDIASIZE, &fullsize) == 0 &&
+ ioctl(fd, DIOCGSECTORSIZE, &sectsize) == 0)
+ {
+ *s = fullsize / sectsize;
+ return 0;
+ }
+ }
+#endif
+#ifdef DIOCGSLICEINFO
+ /* XXX it is somehow ugly, but seems to work on 4.x. */
+ ;{
+ struct diskslices dss;
+ struct stat st;
+ if (ioctl(fd, DIOCGSLICEINFO, &dss) == 0 &&
+ fstat(fd, &st) == 0)
+ {
+ int slice = 31 & (st.st_rdev >> 16);
+ /* If it have disklabel, fall to disklabel case,
+ * because it shows more exact info.
+ */
+ if (slice != WHOLE_DISK_SLICE &&
+ dss.dss_slices[slice].ds_label != NULL &&
+ ioctl(fd, DIOCGDINFO, &dl) == 0) {
+ *s = (unsigned long) dl.d_secperunit;
+ return 0;
+ }
+ *s = dss.dss_slices[slice].ds_size;
+ return 0;
+ }
+ }
#endif
+ /* Fallback method. */
+ if (ioctl(fd, DIOCGDINFO, &dl) == 0) {
+ *s = (unsigned long) dl.d_secperunit;
+ return 0;
+ }
+ return -1;
}
int
@@ -53,8 +89,12 @@ sys_bsd_ptsync(int fd)
#ifdef DIOCSYNCSLICEINFO
return ioctl(fd, DIOCSYNCSLICEINFO, NULL);
#else
- errno = EINVAL;
- return -1;
+ /* XXX I suppose here GEOM systems which:
+ * 1) Don't allow writing to raw disk if it is mounted anywhere,
+ * 2) Automatically update GEOM structures after writing to disk.
+ * Hence, no explicit syncing is required.
+ */
+ return 0;
#endif
}