Error 21

Hi. First of all i am a newbie in the matter of Linux.
Today I installed Suse 11.1 on my external USB-Harddrive. On my laptop is WindowsXP Pro running. In my BIOS is now selected: “boot from (internal) Harddrive”. And as long as my external USB-Harddrive is connected I get every time the selection menu from where I like to boot, I can either select Suse or WinXP and everything is running fine. But when my external is disconnected I get the “Error 21” !
I was already looking through the Web how I can fix that problem, as it seems I could use my WinXP installation CD, but the problem is thats at home (~10.000km far away) and so I can’t use it! Are there anytoher possibilities to fix this problem?
It would be great if anyone could help me.
Thanks a lot!
ciao Sebastian

Error 21 means, “can’t find the disk.” Boot loaders like Grub and LILO only install a little runt loader on the bootable drive. That contains a pointer to the next stage. In your case, it sounds like the next stage was written onto the external hard drive.

Reconnect the external hard drive and boot into Opensuse normally. Run Yast (System Configuration), enter your root password, then select System -> Boot Loader. See what your “boot loader installation” currently shows and post it here. In fact, if you don’t mind, go ahead post what it shows for menu entries. The more info, the better.

The good news is, this can be fixed. Despair not! :slight_smile:

It sounds like the GRUB code is in the MBR of the internal drive, and it knows that it’s installed on the 2nd disk, which of course is the external one which you’ve switched off.

If you can boot off external drive directly, I’d make that the preferred boot drive, with internal 2nd in BIOS. GRUB installed there (including the multi-disk Windows boot entry covered in past threads). Then on internal drive, use generic boot code, so it boots the active Windows partition, when the external disk is absent.

Boot Loader Installation:
Bootloader: GRUB
Bootloader location:
the only thing what is selected is: “Boot from Master Boot Record”

When clicking on Bootloader Installation Details, The DiskOrder is like that my internal HDD is first and second my USB HDD.

Thanks a lot man!

One other question: you have only one internal hard drive, right? And Windows is on it?

If so, open a terminal. If you’ve never done that, it’s under System -> Terminal -> Konsole (one of the others will work, but that’s usually the first listed).

Enter “su,” then enter your root password. Now enter:

fdisk -l

(That’s a lowercase L after the dash.) This will list all of your partitions. The disks will have names like “hda,” “hdb” or “sda,” “sdb,” and so on. These are the complete drives. The partitions on these drives are numbered: ex., “hda1,” “hda2,” and so on.

Look for the “hd?” or “sd?” that has an NTFS or FAT partition on it. That’s the drive with Windows. Once you’re sure you have the right drive, enter this:

grub-install /dev/hd?


grub-install /dev/sd?

… where “/dev/hd?” is actually “dev/sda,” or “dev/hda,” or whichever drive actually has the Windows stuff on it. (Use only one of these commands; the “OR” there is instructive, and isn’t intended to be typed in!) Don’t put a number after the three-letter drive name.

See if that works. Of course, you won’t be able to boot into Opensuse if that USB drive is removed!! :slight_smile:

That info confirms it.

So to boot the active windows partition, on the internal disk, where there’s no Linux partition you’ld need generic boot code there.

As is, GRUB knows to get later stage from the 2nd disk, which is why it fails, when that’s not connected. Because you’re now relying on GRUB to boot windows you need the Linux disk at moment.

If you can’t try to boot from external disk, and fall back to internal, then a suitable setup, would be to have a small boot partition for GRUB and kernel files on the internal disk, using it’s menu to start windows.

Another alternative, would be to use another boot manager, that provides a way to usually boot windows, off internal disk, but has flexibility to boot the 2nd disk.

So what are the options? Does the BIOS let you boot directly from the USB disk?

Just to add a bit to @robopensuse’s post . . . there are several lengthy threads in this sub-forum dealing with an installation and boot with a USB external disk. As already mentioned, you have grub’s stage1 in the internal disk’s MBR pointing to grub stage2 on the USB drive; when that drive is not connected (or powered on) then stage1 cannot find stage2 and the boot fails.

The key to your final solution is what the bios permits; you need to decide how you will configure it and set up the boot accordingly. Some bios’s allow changing the boot disk on-the-fly, i.e., a menu for boot device selection without entering bios setup. Other bios’s do not support booting from USB at all. And some bios’s that allow booting from USB will not fall back to the internal drive if the USB is not present, while other bios’s will. So it just depends on your particular bios.

If the bios supports on-the-fly changing of the boot device, you will need to configure openSUSE to treat the USB disk as the first boot disk, in grub language that is (hd0). With your current setup, the USB is the second disk, named (hd1). Forcing grub to install to the MBR of the USB or installing “generic” boot code to the USB MBR plus grub to the SuSE root partition (the latter would be best), requires manual work from the command line. If this is what you want to do, we can give you instructions. You will also need to take this approach if you can set the bios to boot from USB with the bios falling back to the internal drive if the USB is not connected; if the bios will not fall back, this is probably not a solution for you.

Often, the best method is as @robopensuse already mentioned, creating a small partition on the internal disk for the linux boot files; the grub stage2 there can call the XP boot loader for booting Windows. It would be preferable for this small partition to be a “primary” (but not an “extended” primary). If a primary is not available, grub stage1 can be installed in the internal’s MBR pointing to stage2 in a logical partition created within an extended primary.

You may not be familiar with this terminology - no problem, we can explain what is needed and how to get it done. But everything is determined by what your bios supports and how you want to set it up; that is the starting point.

You’ve gotten some good advice from everyone here. Do note that my suggestion was based on an assumption: that you were concerned that, when the USB is removed, you can’t boot at all. I addressed that with one possible solution.

Consider the other advice here as well.

ok thanks for all your help.
i tried first the version of smpool7. but unfortunaltelly this didn’t work. my windows disk is sda and my linux is sdb. (so i typed in sda).
so ithink i will try this one:

If the bios supports on-the-fly changing of the boot device, you will need to configure openSUSE to treat the USB disk as the first boot disk, in grub language that is (hd0). With your current setup, the USB is the second disk, named (hd1). Forcing grub to install to the MBR of the USB or installing “generic” boot code to the USB MBR plus grub to the SuSE root partition (the latter would be best), requires manual work from the command line. If this is what you want to do, we can give you instructions. You will also need to take this approach if you can set the bios to boot from USB with the bios falling back to the internal drive if the USB is not connected; if the bios will not fall back, this is probably not a solution for you.

My BIOS (Dell Inspiron 1525 ; Version A11)supports booting from USB and I think it also supports on-the-fly changing, since I can currently select which OS I wanna run. The thing is I have never heard of ‘generic boot’. So it would be great if you can describe how can I do that.
I don’t wanna make a new partition on the internal harddrive, because I first have no tool for that and second I dont wanna risk to loose everything.

What rob and mingus are saying is valid. The bios needs to boot the correct drive before you can get what you want. I’ll tell you what I was trying to accomplish, and now that I’ve had time to think about it, I realize I probably just had you redo what Opensuse did during the installation. In other words, it didn’t change anything. :slight_smile:

I was trying to get ALL of grub on your hard drive, with nothing on the USB. That way, even if the USB was unplugged, you’d still have a functional grub. If you tried to boot Suse without the USB stick, you’d get an error. If you tried to boot Windows, it would chain load normally and you’d boot Windows.

I realized, though, that unless you specifically tell grub-install to put the grub images on the hard drive, they’re still on the USB! So my instructions didn’t really change anything.

The problem with depending on the bios, is that it’s only going to boot the first sector/MBR of the chosen “disk” (or disk-like device). If what’s in there isn’t correct, you’re still not going to boot up. (Back when I was doing security work under DOS, we used to point out that if you put a program in the first sector that displayed a dancing chicken, that’s what you’d get. The BIOS loader doesn’t check what’s there, it just loads it and lets it rip – which is why boot viruses were a big problem back then.)

The answer is to get the additional grub “stages” onto that hard drive and off of the USB stick. That’s what I originally thought I was doing, but I realize now that I wasn’t. That way, you’d get what I intended: if you boot without the USB, you can select “Windows” from the menu and continue into that OS. If the USB is plugged in, you can do either Windows or Opensuse.

Someone want to pitch in? If the hard drive is formatted NTFS for Windows, Grub’s gonna have a problem reading the next stage from that hard drive. It’s my understanding that Grub doesn’t like NTFS (but please correct me if I’m wrong).

It seems to me that the solution is for the original poster to resize the NTFS partition to create a small linux partition that Grub can easily use and recognize. Then, when you run grub-install, you’d say

grub-install --root-directory=/dev/hd?/new_partition /dev/hda

… where "/dev/hd?/new_partition is the new 'nix style partition that was created from the space freed up from the NTFS partition.

It would tickle me weedless if someone could give the original poster an easier and more reliable way to do it. That way, I’d learn something, too. :slight_smile:

OK, I don’t like not understanding something, so now I know more about Grub than I ever thought I would. :slight_smile:

What I said above is correct. To rob and mingus, I thought that bergen was complaining that he couldn’t boot at all without the USB stick. Some people (and I assume he/she is one of them) don’t want to depend on a USB stick. What if it gets lost? What about when it wears out (they’ll only do a limited number of write-cycles)?

Just changing the BIOS settings won’t address that problem. In fact, if Suse didn’t install the grub stub to the front of the USB stick, selecting “USB boot” in the BIOS won’t work at all. If bergen had the Windows DVD handy, he/she could reinstall the MBR, then install Grub to the first sector of the USB stick (assuming the USB stick supports that, not all of them do – something that the how-to’s on line apparently overlook, by the way). That way, the BIOS selection would work just fine.

To give bergen a complete walkthrough of my suggestion above, based on the information provided:

  1. Your linux disk is the USB, which is /dev/sdb. Windows is on /dev/sda.

  2. Resize the Windows partition to get about 500 meg of space. Be warned that this has risks, so I’d backup anything important on that Windows drive first!

Go into Yast -> System -> Partitioner. Click on the Windows partition (it should be obvious) and select “resize.”

  1. Once you get that free space, create a new partition with it. Click on the free space and create a new partition. You can set the mount point to something like “grubboot” (just type that name in).

  2. Note the /dev/ name of the new partition: something like, “/dev/sda2” (change the “2” to the actual number).

  3. Now use grub-install as described above, with this syntax:

grub-install --root-directory=/dev/sda2/grubboot /dev/sda

Now THAT should work. But that’s pretty advanced stuff. If you’re not comfortable with it (and I don’t blame you if you’re not!!!), just resign yourself to booting with the USB stick until you can get back to your Windows install DVD.

First, there are some details here that are important to clarify. The “grub-install” script in openSUSE is not the same as it is in other distros. The vanilla “grub-install” script comes with the grub package, and there are definite caveats with using it, one of which is that it is less reliable than directly using the shell (the script passes arguments to the install command in the shell). This script exists in openSUSE as “grub-install.unsupported”. The openSUSE version of grub-install runs the grub shell and feeds it the scriptlet at /etc/grub.conf which is created by YaST; this is because YaST’s Boot Loader module has code which attempts to more reliably determine the boot disk order (all grub can do is guess, since the bios does not provide this data), and additionally evaluates the current disk setup to suggest the best grub install configuration.

It is also absolutely critical that the be set up correctly; the relevance of this is that if you are booting from the USB either as configured in bios setup or on-the-fly, then the USB is the first boot disk and hence needs to think that sdb is (hd0).

Usually the pivot point for deciding how to do this is (a) does the bios supporting boot from USB, and if so (b) will the bios fall back to the next boot device in the event the USB device is not found. Unfortunately, determining if (b) is true can only be done by testing an actual setup (short of reading the code). In fact, I have found that some bios’s will fall back if the USB device is an external hard disk drive but will not do so if the device is a stick. OP is using a drive, which is a plus. Now, what can work around this is if the bios supports on-the-fly boot device choice; in that case, there is no need for fallback (although the user should not be surprised that, if the USB is chosen from that menu and it is not available, the bios may not loop back to the menu but may lock up, requiring a machine restart).

If you checked the other threads here I ref’d earlier, you would see more than one method of getting this to work, as (again) machines and desired setups vary. Having tried it virtually every way, let me suggest this: We install generic (DOS) boot code to the USB’s MBR (actually, copying the Windows boot code from the internal would work, too), and install grub to the root partition on the USB. Then restore the Windows MBR to the internal disk, and the bios on-the-fly method should work well.

To do this, I need to know the partition layout on the USB and grub’s install configuration. So boot into openSUSE, open a terminal, and do:

sudo fdisk -lu
cat /boot/grub/
cat /etc/grub.conf

And post back the output here. Once I have this info I can give you the commands you need. (Do not try to use YaST’s option to install generic code to the MBR; if you do, it will put that code in the internal’s MBR, not the USB’s.)

Also, did you install from the DVD or LiveCD?

ok these commands brought me to the following outputs:

sudo fdisk -lu

Program 'fdisk' is present in package 'util-linux', which is installed on your system.

Absolute path to 'fdisk' is '/sbin/fdisk', so it might be intended to be run only by user with superuser privileges (eg. root).

bash: fdisk: command not found

cat /boot/grub/

(hd1)   /dev/disk/by-id/usb-WD_2500BEV_External_57442D575848593038333135353137-0:0
(fd0)   /dev/fd0
(hd0)   /dev/disk/by-id/ata-WDC_WD2500BEVS-75UST0_WD-WXE408KM2301

cat /etc/grub.conf

setup --stage2=/boot/grub/stage2 --force-lba (hd0) (hd1,1)

I installed Suse from DVD.

Sorry about the fdisk command not working - I didn’t realize that sudo would cause a path problem. But I think we may have enough to do the job without it. So, boot into openSUSE, open a terminal, and do:

su -
fdisk -lu

You should see the partition tables for both disks, with the internal listed as sda1, sda2, etc. and the USB as sdb1, sdb2, sdb3, etc. If you do not see that, post back the output here. But if (as I expect) that is what you see, then continue with the following (please be very careful, a typo could be bad):

root (hd1,1)
setup (hd1,1) (hd1,1)

dd if=/usr/lib/boot/master-boot-code of=/dev/sdb bs=440 count=1

sfdisk -A2 /dev/sdb

fdisk -lu /dev/sdb

In this second listing of the sdb partition table, you should see an asterisk in the “boot” column next to sdb2. Now reboot. At your bios boot menu choose USB. Report back.

Thank you. But unfortunatelly this didnt work either. here is my log during the commands:


    GNU GRUB  version 0.97  (640K lower / 3072K upper memory)

  Minimal BASH-like line editing is supported.  For the first word, TAB
   lists possible command completions.  Anywhere else TAB lists the possible
   completions of a device/filename. ]                                      
grub> root (hd1,1)                                                          
root (hd1,1)                                                                
 Filesystem type is ext2fs, partition type 0x83                             
grub> setup (hd1,1) (hd1,1)                                                 
setup (hd1,1) (hd1,1)                                                       
 Checking if "/boot/grub/stage1" exists... yes                              
 Checking if "/boot/grub/stage2" exists... yes
 Checking if "/boot/grub/e2fs_stage1_5" exists... yes
 Running "embed /boot/grub/e2fs_stage1_5 (hd1,1)"... failed (this is not fatal)
 Running "embed /boot/grub/e2fs_stage1_5 (hd1,1)"... failed (this is not fatal)
 Running "install /boot/grub/stage1 (hd1,1) /boot/grub/stage2 p /boot/grub/menu.lst "... succeeded
grub> quit
linux-2omp:/home/sebastian # dd if=/usr/lib/boot/master-boot-code of=/dev/sdb bs=440 count=1
1+0 records in
1+0 records out
440 bytes (440 B) copied, 0.0564098 s, 7.8 kB/s
linux-2omp:/home/sebastian # sfdisk -A2 /dev/sdb

linux-2omp:/home/sebastian # fdisk -lu /dev/sdb

Disk /dev/sdb: 250.0 GB, 250059350016 bytes
255 heads, 63 sectors/track, 30401 cylinders, total 488397168 sectors
Units = sectors of 1 * 512 = 512 bytes
Disk identifier: 0x44fdfe06

   Device Boot      Start         End      Blocks   Id  System
/dev/sdb1              63     4209029     2104483+  82  Linux swap / Solaris
/dev/sdb2   *     4209030    46154744    20972857+  83  Linux
/dev/sdb3        46154745   488392064   221118660   83  Linux

When I select booting from harddrive first I have the same constallation than before. But when I select booting from USB first I can’t boot anything.
The first message which displays is:
“Grub LoadingStage2
(hd1,1)boot message: file not found”
This last for maybe 3seconds. Then it comes to like a boot-selection menue but from my laptop. Where you can select Linux or Windows.
When I select Linux:
“Error17 can not mount selected partition
Press any key” (and a lot of additional text, if you like to know what just tell me, but it was a lot)
(What brings you back to the menue)
When I select Windows:
Invalid Systemdisk
Replace the disk and press any key”

I hope you still can help me.
Thanks so much in advance!

I did NOT know that. Thanks for sharing that!

I’m going to dip out of this one. Too many cooks will spoil the soup … :slight_smile:

bergen1785- due to my great ability to make dumb errors will only tell you the problem not how to fix.

The is wrong when you boot directly to the external hdd. Right now (hd0) points to the internal hdd and (hd1) points to the external hdd, they need to be reversed.

You will also need to write a XP (XP’s recovery console and run fixmbr) or generic boot code to the MBR of internal hdd to remove grub, only after is fixed.

@bergen1785 -

As @LostFarmer indicated, we may need to modify (which is what we have done in the past). But from the error you got, it may be that we only need to modify the grub menu file named menu.lst to get everything working. We need to take additional care here with your setup, or we might make openSUSE unbootable from the internal drive and that would create a problem booting Windows. So before making permanent changes, let’s do this . . .

Boot from the bios menu to the USB drive. You will get the “(hd1,1)boot message: file not found” error message; that is expected (we will fix it later). Then you get a white text on black background version of the menu that you get when booting from the internal, that is, same selections but just in text. At this point, hit the ‘c’ key (not Enter!). You will be dropped from that menu into the grub shell. Then try:

kernel (hd0,1)/boot/vmlinuz root=/dev/sdb2
initrd (hd0,1)/boot/initrd

After you type the kernel line grub should return a message like: [Linux-bzImage …] and after the initrd line grub should return: [Linux-initrd …]. And typing “boot” and hitting Enter, the boot should proceed with a lot of unformatted text and then your gui should start up as normal. I will need to see your menu.lst file to tell you how to edit it. You need to do this as root, so you can press Alt-F2 and type (in KDE):

kdesu kwrite /boot/grub/menu.lst

or in Gnome

gnomesu gedit /boot/grub/menu.lst

Or in a terminal you can do:

sudo cat /boot/grub/menu.lst

Copy the file’s text and post it back here.

Those commands doesn’t work :frowning:
I got the Error27: Unrecognized Command when I typped in the first two commands. And then logically I got Error8 for the boot coomand.
I dunno, either my system is weird or I’m dumb :X
But thanks a lot for your patient!

You should not have gotten Error 27. Please try again. After you hit the ‘c’ key you should leave the menu and the screen should at the top say “GNU Grub version …” followed by several lines of text, and below that there should be a grub prompt like this:


At the end of each line you enter, of course you hit Enter to go to the next line. This time, we’ll try it with different syntax:

grub> root (hd0,1)
grub> kernel /boot/vmlinuz root=/dev/sdb2
grub> initrd /boot/initrd
grub> boot

Report back.