[comp.os.minix] Corrupting DOS partition

lyle@ogccse.ogc.edu (Lyle Cool) (10/09/89)

Last night I was making several boot disks with various hard disk drivers
when I typed the following line:
	build bootblok kernel mm fs init fsck /dev/hd0   instead of
	build bootblok kernel mm fs init fsck /dev/fd0

This one-letter-mistake basically trashed my hard disk, DOS partition and all.

It raises this issue: should Minix allow a fumble-fingered programmer
to corrupt another partition on the disk?

Lyle Cool (lyle@cse.ogc.edu)

rwberry@hubcap.clemson.edu (Robert W Berry) (10/09/89)

From article <5033@ogccse.ogc.edu>, by lyle@ogccse.ogc.edu (Lyle Cool):
> 
> ...  User built boot image to HD0 and trashed DOS partition ...
>

     The first thing I do when I set up Minix on a hard disk is get rid
of any /dev/hd?'s that Minix has no business writing to.  The only
problem with this can come when Minix has a legitimate reason to look at
that partition (i.e. DOSREAD, et al) so I just built a small
shell-script to create the necessary device and then remove it
immediately afterwards.

     However, there's little you can do if some out-of-control program
trashes your partition table.  This happened to me when I was trying to
optimize FS.  Ouch, good thing I believe in _REGULAR_ backups.

> 
> Lyle Cool (lyle@cse.ogc.edu)

Hope this helps, (tm)

Bob

-- 
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-=- Bob Berry -=- PC-Guru's Inc.         ! rwberry@hubcap.clemson.edu   -=-
-=- We are the science of modern motion. ! 803-654-7623 || 803-656-2635 -=-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-

cwr@pnet01.cts.com (Will Rose) (10/09/89)

  
             The MSDOS 3.3 hard disk partition table
             ======================================= 
 
                            Abstract
 
There has recently been some discussion in comp.minix about partitioning 
hard disks; by coincidence,a couple of days ago I wiped my Minix partition 
superblock and inodes with the MSDOS fdisk, and decided to rebuild the 
partition table.  An account of this may interest those with similar 
problems; the explanation will be at a strictly amateur level, so 
professionals can skip it.
 
                           Background
 
The hard disk I use is a Seagate ST-251 on a 10MHz XT clone running MSDOS 
3.3, with the first 20 MB used by MSDOS and the last 20MB by Minix.  The 
only partition used by MSDOS is the active partition, hd1; Minix uses hd2, 
hd3 and hd4.
 
The disk was first set up under MSDOS 3.3 and Minix 1.2, and the two fdisks 
proved incompatible.  Since MSDOS would not write more than two partitions, I 
set up hd1 as the 'active' partition and hd2 as an 'extended' partition.  I 
then assigned no drive letter to the extended partition, so that MSDOS would 
not write to it inadvertently.  However, Minix fdisk would not add to a 
partition table written by MSDOS; it gave an error message of the form 
'overlapping partitions' even when they were separated by several cylinders.  
For some time, while building 1.3, I ran with hd1 as 20 MB for MSDOS and hd2 
as 18 MB for Minix.  I then patched the partition table by hand (a process 
explained in detail below) to give an hd3 of 1MB, in order to auto-load the 
ramdisk.  (I only used 150KB of hd3, but allowed space for a future ramdisk 
in expanded memory.)
 
Finally I got a stand-alone fdisk working, by recompiling with the correct 
maximum head and sector numbers, and used it to add a 1MB hd4 partition 
which I mounted in /etc/rc as /tmp.  It should be noted that the partition 
sizes above are slightly less than the maximum partition sizes set by the 
partition table - for convenience I rounded down the values I gave mkfs.
 
                 Rebuilding the partition table
 
The system above worked well, until I destroyed it with injudicious use of 
the MSDOS fdisk.  After I had used the MINIX fdisk, both OS worked 
perfectly, but the MSDOS fdisk would not display any partition information, 
even for the MSDOS partition itself.  While switching between MSDOS and 
Minix to investigate this problem, I (almost certainly) hit the wrong key, 
and MSDOS fdisk tried to reinitialize hd2 as an extended MSDOS partition.  
This wiped the Minix superblock clean, and I believe most inodes as well; 
Minix no longer accepted hd2 as a valid file-system, and running mkfs on it 
cleared the inodes entirely.
 
I had a set of emergency boot disks with various relevant programs on them, 
including fdisk and the disk editor de, but I had stored the original 
version of fdisk which was unusable.  Of course, due to another set of 
problems all my backups were source code - I had no modified binaries!
 
I had wanted to change the layout of my disk partitions for some time, and 
this seemed like a good opportunity. However, putting together a system to 
compile fdisk in order to edit the partition table in order to put together 
a system.... seemed a waste of time.  I decided to edit all three Minix 
partitions by hand, reading and writing the table with df and editing it 
with de.  I used this procedure when first setting up hd3 (see above) except 
that I moved the 512 byte file produced by df across to MSDOS and patched it 
with debug, before moving it back to Minix and writing it to disk.  (I think 
Norton tools can edit the partition table, but I don't have a copy).
 
Before changing anything I backed up my MSDOS partition - such is the power 
of Murphy's law that this precaution proved quite unnecessary.  I also 
recovered my modification log from hd2, using de's search command to find 
the date strings in the various blocks of the file.  I then produced two 
files containing different new versions of the partition table; the first 
had only an unaltered hd1 (the MSDOS partition) and the second had hd1, a 1 
MB hd2, a 1MB hd3, and an 18 MB hd3.  These files were produced by reading 
the partition table with:
    dd if=/dev/hd0 of=/tmp/table1 count=1
 
I then edited table1 with the command de -w /dev/ram, looking through the 
blocks until I found something that looked like a partition table; the 
conclusive check is the value of 0x55aa written as bytes 510 and 511, which 
to MSDOS indicates a valid boot record.  For the first file, I simply zeroed 
out all the partition data other than that for hd1; for the second file, I 
entered the data which I calculated using the method shown in the appendix, 
again leaving hd1 unchanged.  I could have edited /dev/hd0 directly, but I 
wanted to double-check my work before writing it to disk.
 
I wrote the first table back to disk with:
    dd if=/tmp/table1 of=/dev/hd0 count=1
and rebooted to MSDOS.  The MSDOS fdisk showed one (MSDOS) partition of the 
right size; the previous clash (whatever it was) had gone away.  I then 
rebooted Minix, wrote the second table to disk, and rebooted again to MSDOS.  
Fdisk again worked, showing one MSDOS partition and three non-MSDOS 
partitions, all of the right sizes, and the original problem was solved.
 
I don't think the new partition sizes had anything to do with the solution.  
When I rewrote the partition table, I altered the type number which MSDOS 
uses to identify the partition, and I think this was what was confusing 
fdisk.  Originally the numbers for hd1 to 4 were 4, 5, 0, 0; 4 means MSDOS 
with a 16 bit FAT, 5 is an MSDOS extended partition, and 0 is undefined.  
The new partitions have the identities 4, 6, 6, 6; 6 is 'reserved', and 
certainly MSDOS 3.3 knows enough not to touch it.
 
The appendix has a description of the MSDOS 3.3 partition table, and a list 
of the values in the partition table for my final disk set up.  This list 
takes about 15 minutes to produce with a hex/binary calculator; using it 
with dd is probably easier than patching and recompiling fdisk on floppies.
 
                             Summary
 
The fdisk programs of Minix and MSDOS 3.3 are in some way incompatible, 
probably because the Minix version uses a partition type number of 0 which 
MSDOS does not understand.  Using a partition type of 6, which MSDOS 3.3 has 
reserved for future use, both allows MSDOS fdisk to function and prevents it 
writing to the Minix partitions.  It is possible that this type number is 
used by another OS, eg. XENIX.  Those mixing XENIX and Minix on the same 
drive should beware of this.
 
If an fdisk patched for a specific machine is not available, calculating the 
appropriate values (by the method given in the Appendix) and patching the 
partition table with df is quick and relatively straightforward.
 
                           References.
 
Hogan, T. (1988).  The Programmer's PC Sourcebook.  Redmond, Washington:
     Microsoft Press.
 
Appendix A - Disk Partition Table Layout.
 
  Ref. Offset Length Name              Contents
 
   A      0   Byte   Partition status  0=inactive.
                                       0x80=active, bootable.
   B      1   Byte   Starting head
   C      2   Word   Starting sec/cyl. See note 2 below.
   D      4   Byte   Partition type    1=DOS, 12 bit FAT.
                                       4=DOS, 16 bit FAT.
                                       5=Extended DOS.
                                       6=Reserved for future use.
                                       0xdb=Concurrent DOS.
   E      5   Byte   Ending head
   F      6   Word   Ending sec/cyl.   See note 2 below.
   G      8   2-word Starting sector   Absolute sector number.
                                       LSW first, words byte-swapped.
   H     12   2-word Number of sectors Sectors in this partition
                                       LSW first, words byte-swapped.
 
 Notes.
 
 1.  The partition tables begin at an offset of 0x1be in the boot record.
     The 16 bytes shown above repeat for partitions 1-4 in turn, with
     the final word of the boot record (510) being a signature, 0x55aa.
 
 2.  The cylinder number has ten bits, the low byte of the word with
     the two upper bits of the high byte.  The sector number is the 6
     low bits of the high byte.  Thus we have: ccss ssss  cccc cccc.
 
Appendix B - Worked example.
 
The Ref. headings are from Appendix A.  For boxes marked '*', see note 1.
 
Ref:      A  B     C    D  E     F      G      G      H      H
 
Ptn 1     01 80  00 01  05 04  8f 51  00 11  00 00  9f 4f  00 00  Dump (od -x)
Cyl 400   80 01  01 00  04 05  51 8f  11 00  00 00  4f 9f  00 00  Byte
reversed
Trk 2400           *            *     00 00  00 11  00 00  9f 4f  Decoded
Sec 40800     1   1  0   4  5  17 399           17         40783  Decimal
 
Ptn 2     00 00  90 41  05 06  a3 51  9f 60  00 00  07 f8  00 00  Dump (od -x)
Cyl 20    00 00  41 90  06 05  51 87  60 9f  00 00  f8 07  00 00  Byte
reversed
Trk 120            *            *     00 00  9f 60  00 00  07 f8  Decoded
Sec 2040   0  0   1 400  6  5  17 419        40800          2040  Decimal
Blk 1020
 
Ptn 3     00 00  a4 41  05 06  b7 51  a7 58  00 00  07 f8  00 00  Dump (od -x)
Cyl 20    00 00  41 a4  06 05  51 b7  58 a7  00 00  f8 07  00 00  Byte
reversed
Trk 120            *             *    00 00  a7 58  00 00  07 f8  Decoded
Sec 2040   0  0   1 420  6  5  17 439        42840          2040  Decimal
Blk 1020
 
Ptn 4     00 00  b8 41  05 06  33 d1  af 50  00 00  97 68  00 00  Dump (od -x)
Cyl 380   00 00  41 b8  06 05  d1 33  50 af  00 00  68 97  00 00  Byte
reversed
Trk 2280           *             *    00 00  af 50  00 00  97 68  Decoded
Sec 38760  0  0   1 440  6  5  17 819        44880         38760  Decimal
Blk 19380
 
Notes.
 
1.  Calculation of sector/cylinder words.
 
Partition 1: 0x0100 = 00(00 0001) 0000 0000 = 1, 0
             0x518f = 01(01 0001) 1000 1111 = 17, 399
Partition 2: 0x4190 = 01(00 0001) 1001 0000 = 1, 400
             0x51a3 = 01(01 0001) 1010 0011 = 17, 419
Partition 3: 0x41a4 = 01(00 0001) 1010 0100 = 1, 420
             0x51b7 = 01(01 0001) 1011 0111 = 17, 439
Partition 4: 0x41b8 = 01(00 0001) 1011 1000 = 1, 440
             0xd133 = 11(01 0001) 0011 0011 = 17, 819
 
2.  Use of the table.
 
If you develop the numbers for the first (MSDOS) partition from top
to bottom, it is then relatively easy to work backwards (from bottom
to top) in the subsequent calculations.  One gotcha is MSDOS' habit
of byte reversal.  Whenever you get a table dump, check the last word.
It is actually 0x55aa, and if it looks like aa55 then all the rest of
the data will need reversing.  Another gotcha is that the start point
of each 16 byte table is exactly not on a click boundary; the first
partition table starts at an offset of 0x1be in the boot record.
 
C W ROSE
 
San Diego, 9 Oct 89.

UUCP: {nosc ucsd hplabs!hp-sdd}!crash!pnet01!cwr
ARPA: crash!pnet01!cwr@nosc.mil
INET: cwr@pnet01.cts.com

ast@cs.vu.nl (Andy Tanenbaum) (10/09/89)

In article <5033@ogccse.ogc.edu> lyle@ogccse.UUCP (Lyle Cool) writes:
>Last night I was making several boot disks with various hard disk drivers
>when I typed the following line:
>	build bootblok kernel mm fs init fsck /dev/hd0   instead of
>	build bootblok kernel mm fs init fsck /dev/fd0
>
>This one-letter-mistake basically trashed my hard disk, DOS partition and all.

Sorry about that.  There are two remedies I can think of.  First of all,
keep /dev/hdx as owned by the root or bin and mode 600.  This prevents
mere mortals from causing trouble.  If you are superuser, you have to be
careful.

Second, I think it is a good idea to copy /dev/hd0 to a floppy.  Only
360K, 720K, 1.2M, or 1.44M will fit, depending on your
floppy, but restoring this, even it is old, helps a lot.  Fsck can
fix up the rest.

Andy Tanenbaum (ast@cs.vu.nl)

evans@ditsyda.oz (Bruce Evans) (10/10/89)

In article <5033@ogccse.ogc.edu> lyle@ogccse.UUCP (Lyle Cool) writes:
>	build bootblok kernel mm fs init fsck /dev/hd0   instead of
>...
>It raises this issue: should Minix allow a fumble-fingered programmer
>to corrupt another partition on the disk?

The system can easily protect against this if the file permissions are
set properly. I have all hard disk readable by everyone but writable
only by root and their owner (bin), and avoid working as root or bin.
Floppy disks are writable by all, so this particular problem is solved.

I still need to become root too much, mainly to run chown and move files
between users. Perhaps chown should be suid root on a single-user Minix
system. The 1.2 (?) version of mv had security holes which made it all-
powerful when suid root. Perhaps these should be put back. :-)
-- 
Bruce Evans		evans@ditsyda.oz.au

hcj@lzaz.ATT.COM (HC Johnson) (10/10/89)

In article <5033@ogccse.ogc.edu>, lyle@ogccse.ogc.edu (Lyle Cool) writes:
> Last night I was making several boot disks with various hard disk drivers
> when I typed the following line:
> 	build bootblok kernel mm fs init fsck /dev/hd0   instead of
> 	build bootblok kernel mm fs init fsck /dev/fd0
> 
> This one-letter-mistake basically trashed my hard disk, DOS partition and all.
> 
> It raises this issue: should Minix allow a fumble-fingered programmer
> to corrupt another partition on the disk?

This is how Minix most closely mimicks UNIX(r).  Any screw up as ROOT will
destroy the system.

Try mkfs on the root image on disk.  Very destructive.


Howard C. Johnson
ATT Bell Labs
att!lzaz!hcj
hcj@lzaz.att.com

powell@mva.cs.liv.ac.uk (10/11/89)

In article <2255@ditsyda.oz>, evans@ditsyda.oz (Bruce Evans) writes:
> In article <5033@ogccse.ogc.edu> lyle@ogccse.UUCP (Lyle Cool) writes:
>>	build bootblok kernel mm fs init fsck /dev/hd0   instead of
>>...
>>It raises this issue: should Minix allow a fumble-fingered programmer
>>to corrupt another partition on the disk?
> 
> The system can easily protect against this if the file permissions are
> set properly. I have all hard disk readable by everyone but writable
                                     ^^^^^^^^^^^^^^^^^^^^

   Surely, not every user should be able to read the hard disks. This 
rather makes redundant any attempt to stop a user from looking at your file
space. They can just do a "od /dev/hd5" (or whatever) to look at the entire
contents of the file system!


^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
"she wants me t' say what she wants t' say    - B. Dylan (Some other kinds
 she wants me t' say what she can understand"             of songs... #3)

Mark Powell

ARPA  usqb015%hp1.hp.liv.ac.uk@nsfnet-relay.ac.uk
JANET usqb015@uk.ac.liv.hp.hp1
UUCP  ...!mcvax!ukc!hp1.hp.liv.ac.uk!usqb015