The UNIX and Linux Forums  

Go Back   The UNIX and Linux Forums > Top Forums > UNIX for Dummies Questions & Answers > Answers to Frequently Asked Questions > Tips and Tutorials
Google UNIX.COM



View Single Post in UNIX Forums - Click on the Thread or Permalink to View Entire Thread -->
  #2 (permalink)  
Old 10-07-2006
Perderabo's Avatar
Perderabo Perderabo is online now
Unix Daemon
 

Join Date: Aug 2001
Location: Washington DC Area
Posts: 8,452
One of the secrets of success in a complex installation like this is to completely understand exactly where everything is on disk. Acronis disk director could list some of the info, but I needed more. I wrote a tool to take the info that Acronis displayed and produce a table for my notes...

Code:
   ===== Device Name ====                                     ========== Start ========== ========== End ============== ====== Length ========
P#   Grub   Linux FreeBSD      Description    Partition Type     LBA     Cyl--Head--Sectr    LBA     Cyl--Head--Sector   Sectors    MB    Cyls
-- -------- ----- ------- ------------------- --------------- ---------- ---------------- ---------- ------------------ --------- ------ -----
   (hd0)    hda           the whole disk                               0 (0---0---1)       195371568 (12161---81---1)     5371569   2622   334
                          first full cylinder                          0 (0---0---1)           16064 (0---254---63)         16065      7     1
                          usable space                                 0 (0---0---1)       195366464 (12160---254---63)   5366465   2620   334
                          unusable space                       195366465 (12161---0---1)   195371568 (12161---81---1)        5104      2
                          MBR                                          0 (0---0---1)               0 (0---0---1)                1
                          the hidden sectors                           1 (0---0---2)              62 (0---0---63)              62
1  (hd0,0)  hda1  ad0s1   XP                  NTFS       0x07         63 (0---1---1)        31519529 (1961---254---63)    1519467    741    94
                          EBR                                   31519530 (1962---0---1)     31519592 (1962---0---63)           63
5  (hd0,4)  hda5  ad0s4   driveE              FAT32      0x0B   31519593 (1962---1---1)     52500419 (3267---254---63)    0980827    478    61
                          EBR                                   52500420 (3268---0---1)     52500482 (3268---0---63)           63
6  (hd0,5)  hda6  ad0s5   /userdata           EXT3       0x83   52500483 (3268---1---1)     62990864 (3920---254---63)    0490382    239    30
                          EBR                                   62990865 (3921---0---1)     62990934 (3921---1---7)            70
7  (hd0,6)  hda7  ad0s7   /mastergrub         EXT3       0x83   62990935 (3921---1---8)     63263969 (3937---254---63)     273035    133    16
                          EBR                                   63263970 (3938---0---1)     63264032 (3938---0---63)           63
8  (hd0,7)  hda8  ad0s8                       Linux swap 0x82   63264033 (3938---1---1)     67472999 (4199---254---63)    4208967   2055   262
                          EBR                                   67473000 (4200---0---1)     67473062 (4200---0---63)           63
9  (hd0,8)  hda9  ad0s9   /tmp                EXT3       0x8E   67473063 (4200---1---1)     69577514 (4330---254---63)    2104452   1027   131
                          EBR                                   69577515 (4331---0---1)     69577577 (4331---0---63)           63
10 (hd0,9)  hda10 ad0s10  Redhat00            Linux LVM  0x8E   69577578 (4331---1---1)     77979509 (4853---254---63)    8401932   4102   523
                          EBR                                   77979510 (4854---0---1)     77979572 (4854---0---63)           63
11 (hd0,10) hda11 ad0s11  Fedora00            Linux LVM  0x8E   77979573 (4854---1---1)     88469954 (5506---254---63)    0490382    239    30
                          EBR                                   88469955 (5507---0---1)     88470017 (5507---0---63)           63
12 (hd0,11) hda12 ad0s12  SuSE00              Linux LVM  0x8E   88470018 (5507---1---1)    101064914 (6290---254---63)    2594897   1267   161
                          EBR                                  101064915 (6291---0---1)    101064977 (6291---0---63)           63
13 (hd0,12) hda13 ad0s13  Debian00            Linux LVM  0x8E  101064978 (6291---1---1)    117852839 (7335---254---63)    6787862   3314   422
                          EBR                                  117852840 (7336---0---1)    117852902 (7336---0---63)           63
14 (hd0,13) hda14 ad0s14  Scientific00        Linux LVM  0x8E  117852903 (7336---1---1)    130447799 (8119---254---63)    2594897   1267   161
                          EBR                                  130447800 (8120---0---1)    130447862 (8120---0---63)           63
15 (hd0,14) hda15 ad0s15  /backupgrub         EXT3       0x83  130447863 (8120---1---1)    130720904 (8136---254---63)     273042    133    17
                          EBR                                  130720905 (8137---0---1)    130720967 (8137---0---63)           63
16 (hd0,15) hda16 ad0s16  /testgrub           EXT3       0x83  130720968 (8137---1---1)    130994009 (8153---254---63)     273042    133    17
                          Free Space                           130994010 (8154---0---1)    158256314 (9850---254---63)    7262305   3546   452
2  (hd0,2)  hda2  ad0s2                       FreeBSD    0xA5  158256315 (9851---0---1)    172939724 (10764---254---63)   4683410   2286   291
3  (hd0,3)  hda3  ad0s3                       Solaris    0xBF  172939725 (10765---0---1)   195366464 (12160---254---63)   2426740   1184   151
Some notes on this...

MBR, the hidden sectors, and the EBR's
The Master Boot Record (MBR) is the first sector of the disk. It has the boot code and the partition table in it. The rest of the first track is called "the hidden sectors". In my case, Grub stage 1.5 is in the hidden sectors. The structure of this first track is duplicated for each logical partition. Each logical partition has a structure like a MBR as it first sector. Then the rest of the first track is ignored. This first track immediately precedes the logical partition that it describes. Microsoft uses the term "logical drive" which almost means the same thing as "logical partition". But looking carefully at the definitions it seems to me that "logical drive" = EBR + "wasted sectors" + "logical partition". In any case, you need the MBR and the EBR's to define the partition layout of a drive. I see programs to backup the MBR but they always ignore the EBR's. I will fix that by writing a utility to backup the MBR plus the EBR's. Strickly speaking the EBR is one sector and it is followed by some wasted sectors. In my chart I have cheated a little bit and redefined the EBR to be all overhead sectors between partitions. I feel that the chart is "busy enough" and would be even harder to read with two lines between each partition.


Cylinder Alignment
Notice how the partitions are generally aligned on cylinder boundaries. The exception is /mastergrub and this is due to a bug in Acronis Disk Director. I originally had /mastergrub at .5 MB which is too big. I shrunk it, but I made the free space appear before the partition rather then after it. (This let me shuffle the free space down and add it to my XP partition.) When I produced this chart, I noted that /mastergrub was not aligned properly. This wastes a few more cylinders, but it seems to have few consequences. The only potential problems that I can think of... Some programs try to guess the disk geometry....with amazing success. They might do this by looking at the alignment of the partitions. Some programs (like Acronis itself) can locate and restore deleted partitions. This might fail if the partition was misaligned to begin with. I notice that Acronis has a "fast" and "slow" search for deleted partitions (with the "slow" option being more robust) and this might push you into the "slow" option.

This encouraged me to experiment with partitions that were truly logical but also had an entry in the fourth MBR slot as a primary partition. My idea was to switch one of several logicals into the primary slot, install an OS, destroy the primary entry, and boot from the logical partition. This did not work very well. A smart bootloader could switch a partition from logical to primary and then boot it, but I did not want to write a bootloader.

I notice that each logical partition is wasting most of a full track. I am considering misaligning all of the partitions to recover that space. There is not a lot of space to be recovered and this may not be worth the effort. Also Acronis does not have enough control to allow me to try. I believe that qtparted can do this though.

Solaris Changed Types
Solaris 10 is using BF as its partition type and the Solasis 10 installer does not recognize partition with a type of 82 anymore.

I did not want to enter the starting and ending LBA's for the EBR's. The script should be able to calculate them from the preceding and following entries. This increased the complexity of the script but in the long run it saved effort. And here is the source code...
Code:
#! /usr/bin/ksh

typeset -L3 opartn
typeset -L9 ogrubdev
typeset -L6 olinuxdev
typeset -L8 ofbsddev
typeset -L20 odesc
typeset -L11 otype
typeset -L5 ohextype
typeset -R9 ofirst
typeset -L17 ofirstchs
typeset -R9 olast
typeset -L20 olastchs
typeset -R7 olong
typeset -R6 omegs
typeset -R5 ocyls
function chs
{
        ((s=$1%63))
        ((rest=$1/63))
        ((h=rest%255))
        ((c=rest/255))
        ((c=rest/255))
        ((s=s+1))
        echo "(${c}---${h}---${s})"
        return 0
}
some_data_left=1
saved_record=0

echo '   ===== Device Name ====                                     ========== Start ========== ========== End ============== ====== Length ========'
echo 'P#   Grub   Linux FreeBSD      Description    Partition Type     LBA     Cyl--Head--Sectr    LBA     Cyl--Head--Sector   Sectors    MB    Cyls'
echo '-- -------- ----- ------- ------------------- --------------- ---------- ---------------- ---------- ------------------ --------- ------ -----'

echo ';(hd0)   ;hda       ;            ;the whole disk     ;          ;    ;        0;195371568
      ;        ;          ;            ;first full cylinder;          ;    ;        0;    16064
      ;        ;          ;            ;usable space       ;          ;    ;        0;195366464
      ;        ;          ;            ;unusable space     ;          ;    ;195366465;195371568
      ;        ;          ;            ;MBR                ;          ;    ;        0;        0
      ;        ;          ;            ;the hidden sectors ;          ;    ;        1;       62
     1;(hd0,0) ;hda1      ;ad0s1       ;XP                 ;NTFS      ;0x07;       63; 31519529
      ;        ;          ;            ;EBR                ;          ;    ;         ;
     5;(hd0,4) ;hda5      ;ad0s4       ;driveE             ;FAT32     ;0x0B; 31519593; 52500419
      ;        ;          ;            ;EBR                ;          ;    ;         ;
     6;(hd0,5) ;hda6      ;ad0s5       ;/userdata          ;EXT3      ;0x83; 52500483; 62990864
      ;        ;          ;            ;EBR                ;          ;    ;         ;
     7;(hd0,6) ;hda7      ;ad0s7       ;/mastergrub        ;EXT3      ;0x83; 62990935; 63263969
      ;        ;          ;            ;EBR                ;          ;    ;         ;
     8;(hd0,7) ;hda8      ;ad0s8       ;                   ;Linux swap;0x82; 63264033; 67472999
      ;        ;          ;            ;EBR                ;          ;    ;         ;
     9;(hd0,8) ;hda9      ;ad0s9       ;/tmp               ;EXT3      ;0x8E; 67473063; 69577514
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    10;(hd0,9) ;hda10     ;ad0s10      ;Redhat00           ;Linux LVM ;0x8E; 69577578; 77979509
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    11;(hd0,10);hda11     ;ad0s11      ;Fedora00           ;Linux LVM ;0x8E; 77979573; 88469954
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    12;(hd0,11);hda12     ;ad0s12      ;SuSE00             ;Linux LVM ;0x8E; 88470018;101064914
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    13;(hd0,12);hda13     ;ad0s13      ;Debian00           ;Linux LVM ;0x8E;101064978;117852839
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    14;(hd0,13);hda14     ;ad0s14      ;Scientific00       ;Linux LVM ;0x8E;117852903;130447799
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    15;(hd0,14);hda15     ;ad0s15      ;/backupgrub        ;EXT3      ;0x83;130447863;130720904
      ;        ;          ;            ;EBR                ;          ;    ;         ;
    16;(hd0,15);hda16     ;ad0s16      ;/testgrub          ;EXT3      ;0x83;130720968;130994009
      ;        ;          ;            ;Free Space         ;          ;    ;130994010;158256314
     2;(hd0,2) ;hda2      ;ad0s2       ;                   ;FreeBSD   ;0xA5;158256315;172939724
     3;(hd0,3) ;hda3      ;ad0s3       ;                   ;Solaris   ;0xBF;172939725;195366464'|\
while ((some_data_left)) ; do
        if ((saved_record)) ; then
                saved_record=0
                partn=$saved_partn
                grubdev=$saved_grubdev
                linuxdev=$saved_linuxdev
                fbsddev=$saved_fbsddev
                desc=$saved_desc
                type=$saved_type
                hextype=$saved_hextype
                first=$saved_first
                last=$saved_last
        else
                if IFS=";" read partn grubdev linuxdev fbsddev desc type hextype first last ; then
                        if [[ "$desc" = EBR* ]] ; then
                                if IFS=";" read partn grubdev linuxdev fbsddev desc type hextype fir
                                        saved_record=1
                                        saved_partn=$partn
                                        saved_grubdev=$grubdev
                                        saved_linuxdev=$linuxdev
                                        saved_fbsddev=$fbsddev
                                        saved_desc=$desc
                                        saved_type=$type
                                        saved_hextype=$hextype
                                        saved_first=$first
                                        saved_last=$last
                                        partn=""
                                        grubdev=""
                                        linuxdev=""
                                        fbsddev=""
                                        type=""
                                        hextype=""
                                        desc="EBR"
                                        ((first=old_last+1))
                                        ((last=saved_first-1))
                                else
                                        echo error EBR is last record >&2
                                        exit 1
                                fi
                        fi
                else
                        some_data_left=0
                fi
        fi

        if ((some_data_left)) ; then
                opartn=$partn
                ogrubdev=$grubdev
                olinuxdev=$linuxdev
                ofbsddev=$fbsddev
                odesc=$desc
                otype=$type
                ohextype=$hextype
                ofirst=$first
                ofirstchs=$(chs $first)
                olast=$last
                olastchs=$(chs $last)
                ((olong=last-first+1))
                if ((olong>2048)) ; then
                        ((omegs=olong/2048))
                else
                        omegs=""
                fi
                if ((olong>16064)) ; then
                        ((ocyls=(olong+64)/16065))
                else
                        ocyls=""
                fi
                echo "${opartn}${ogrubdev}${olinuxdev}${ofbsddev}${odesc}${otype}${ohextype}" \
                        "${ofirst} ${ofirstchs} ${olast} ${olastchs} ${olong} ${omegs} ${ocyls}"

                old_partn=$partn
                old_grubdev=$grubdev
                old_linuxdev=$linuxdev
                old_fbsddev=$fbsddev
                old_desc=$desc
                old_type=$type
                old_hextype=$hextype
                old_first=$first
                old_last=$last
        fi
done
exit 0