18 October 2010

Determining Partition Tables

This tip deals somewhat with Solaris, though moreso with FreeBSD.
On a Solaris host, to quickly determine how a hard disk may be carved up,
one can simply run prtvtoc against the device:
    sunbox [0] /usr/bin/uname -a
    SunOS sunbox 5.10 Generic_118855-14 i86pc i386 i86pc
    sunbox [0] /usr/sbin/prtvtoc /dev/dsk/c1t0d0s2
    * /dev/dsk/c1t0d0s2 partition map
    *
    * Dimensions:
    *     512 bytes/sector
    *      63 sectors/track
    *     255 tracks/cylinder
    *   16065 sectors/cylinder
    *    8921 cylinders
    *    8919 accessible cylinders
    *
    * Flags:
    *   1: unmountable
    *  10: read-only
    *
    *                          First     Sector    Last
    * Partition  Tag  Flags    Sector     Count    Sector  Mount Directory
           0      2    00   16803990   4192965  20996954   /
           1      3    01      16065   8401995   8418059
           2      5    00          0 143283735 143283734
           3      4    00   20996955  16787925  37784879   /usr
           4      7    00   12611025   4192965  16803989   /var
           5      8    00    8418060   4192965  12611024   /export/home
           6      0    00   37784880 105498855 143283734   /bitbucket
           8      1    01          0     16065     16064

As seen above, this was run on a Solaris x86 box, however the output
is nearly identical for sparc based hosts.  When used without any options,
prtvtoc will print out the VTOC (volume table of contents) with additional
header information.  To remove this information, printing only the VTOC,
supply option -h to prtvtoc.

In dealing with FreeBSD, unlike Solaris systems, a usable disk would both
contain slices and partitions.  Before proceeding, clarification between
slices and partitions are necessary.  A slice is a division of a disk
(4 potential slices), composed of contiguous sectors into which partitions
are created.  A partition is a logical division of a slice and used in
dealing with filesystems.  To determine the various slices of a device
residing at da0, one would use the fdisk command:

    bsdbox [0] /usr/bin/uname -a
    FreeBSD bsdbox 5.4-RELEASE FreeBSD 5.4-RELEASE #0: Mon May  8 11:23:06 EDT 2006
                     root@bsdbox:/usr/src/sys/i386/compile/SYSENG.  i386
    bsdbox [0] /sbin/fdisk /dev/da0
    ******* Working on device /dev/da0 *******
    parameters extracted from in-core disklabel are:
    cylinders=8924 heads=255 sectors/track=63 (16065 blks/cyl)

    Figures below won't work with BIOS for partitions not in cyl 1
    parameters to be used for BIOS calculations are:
    cylinders=8924 heads=255 sectors/track=63 (16065 blks/cyl)

    Media sector size is 512
    Warning: BIOS sector numbering starts with sector 1
    Information from DOS bootblock is:
    The data for partition 1 is:
    sysid 165 (0xa5),(FreeBSD/NetBSD/386BSD)
        start 63, size 143363997 (70001 Meg), flag 80 (active)
            beg: cyl 0/ head 1/ sector 1;
            end: cyl 1023/ head 254/ sector 63
    The data for partition 2 is:

    The data for partition 3 is:

    The data for partition 4 is:


In the above, device da0 is seen to have only a single configured slice
(weirdly identified as a partition), that being slice 1.  For a summarized
view of this information, once could pass -s to fdisk:

    bsdbox [0] /sbin/fdisk -s /dev/da0
    /dev/da0: 8924 cyl 255 hd 63 sec
    Part        Start        Size Type Flags
       1:          63   143363997 0xa5 0x80

Now that the configured slices are known, it is possible to determine
how those slices are carved up into partitions.  With the same example as
above, the partitions configured on device da0 slice 1 can be determined
with bsdlabel (or disklabel, which is hard linked to bsdlabel):

    bsdbox [0] /sbin/bsdlabel -A /dev/da0s1
    # /dev/da0s1:
    type: SCSI
    disk: da0s1
    label:
    flags:
    bytes/sector: 512
    sectors/track: 63
    tracks/cylinder: 255
    sectors/cylinder: 16065
    cylinders: 8924
    sectors/unit: 143374650
    rpm: 3600
    interleave: 1
    trackskew: 0
    cylinderskew: 0
    headswitch: 0           # milliseconds
    track-to-track seek: 0  # milliseconds
    drivedata: 0

    8 partitions:
    #        size   offset    fstype   [fsize bsize bps/cpg]
      a:  2097152        0    4.2BSD     2048 16384 28552
      b:  8388608  2097152      swap
      c: 143363997        0    unused        0     0         # "raw" part, don't edit
      d: 10485760 10485760    4.2BSD     2048 16384 28552
      e:  2097152 20971520    4.2BSD     2048 16384 28552
      f:  4194304 23068672    4.2BSD     2048 16384 28552
      g:  2097152 27262976    4.2BSD     2048 16384 28552
      h: 114003869 29360128    4.2BSD     2048 16384 28552

The output from bsdlabel is very similar to prtvtoc in the output it
gives, with the exception of identifying which partitions each device
was last mounted at.  With the -A option, bsdlabel prints out full
header information, similar to prtvtoc without any options.  To only
display how the device is partitioned, without the header information,
simply execute bsdlabel with the device being the only option.  Of note,
just as in Solaris where slice 2 is treated specially (as it is the
length of the entire disk), in FreeBSD, partition c is the same.