Revision: 3153 http://jnode.svn.sourceforge.net/jnode/?rev=3153&view=rev Author: lsantha Date: 2007-04-03 13:21:40 -0700 (Tue, 03 Apr 2007)
Log Message: ----------- GRUB installer inplementation in progress, by Tango. I've applied some refactorings on it. Added Paths: ----------- trunk/fs/src/fs/org/jnode/fs/jfat/command/ trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatBootSector.java trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatFormatter.java trunk/fs/src/fs/org/jnode/fs/jfat/command/JGrubInstallCommand.java Added: trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatBootSector.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatBootSector.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatBootSector.java 2007-04-03 20:21:40 UTC (rev 3153) @@ -0,0 +1,47 @@ +package org.jnode.fs.jfat.command; + +import org.jnode.fs.jfat.BootSector; + +/** + * + * @author Tango Devian + * + */ +/** + * This file will contain the differetn value se + * + */ + + +class GrubJFatBootSector extends BootSector{ + + public GrubJFatBootSector(byte[] sector) { + super(sector); + } + /** + * Constructor for GrubBootSector. + * @param size + */ + public GrubJFatBootSector(int size) { + super(size); + } + /** + * Gets the first sector of stage1_5 + * @return long + */ + public long getStage1_5Sector() { + return get32(0x44); + } + + /** + * Sets the first sector of stage1_5 + */ + public void setStage1_5Sector(long v) { + set32(0x44, v); + } + + + + + +} Added: trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatFormatter.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatFormatter.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/jfat/command/GrubJFatFormatter.java 2007-04-03 20:21:40 UTC (rev 3153) @@ -0,0 +1,267 @@ +package org.jnode.fs.jfat.command; + + +import java.io.*; +import java.nio.ByteBuffer; +import java.util.zip.CRC32; +import org.apache.log4j.Logger; +import org.jnode.driver.ApiNotFoundException; +import org.jnode.driver.Device; +import org.jnode.driver.block.BlockDeviceAPI; +import org.jnode.fs.FileSystemException; +import org.jnode.fs.jfat.BootSector; +import org.jnode.util.FileUtils; +import org.jnode.util.LittleEndian; + +/** + * File :GrubFatFormatter.java + * <p/> + * The very important file for the Grub Installation. Here the methods for write + * to the MBR and the setting the Stage2 are kept. + * + * @author Tango Devian + */ +class GrubJFatFormatter { + private static final Logger log = Logger.getLogger(GrubJFatFormatter.class); + + // The variables parameters declaration + byte[] stage1; + + byte[] stage1_5; + /** + * The Source path for the Grub in CD://devices/sg0/boot/grub/STAGE1. + * Because the grub can installed from the Live Boot CD. + */ + final String stageResourceName1 = "//devices/sg0/BOOT/GRUB/STAGE1."; + + final String stageResourceName1_5 = "//devices/sg0/BOOT/GRUB/FAT1_5."; + + private static int installPartition = 0xFFFFFFFF; + + private String configFile; + + private int bootSectorOffset; + private static boolean clock = true; + private static boolean verify = true; + + /** + * Create the actual bootsector. + */ + private BootSector createBootSector(String stage1Name, String stage1_5Name, + BlockDeviceAPI devApi) throws Exception { + System.out.println("The createbootsector entered."); + if (stage1Name == null) { + System.out.println("hi i am in createbotsector...."); + stage1Name = "//devices/sg0/BOOT/GRUB/STAGE1."; + } + if (stage1_5Name == null) { + stage1_5Name = "//devices/sg0/BOOT/GRUB/FAT1_5."; + } + try { + stage1 = getStage1(stage1Name); + stage1_5 = getStage1_5(stage1_5Name); + return new GrubJFatBootSector(getStage1(stageResourceName1)); + } catch (IOException ex) { + throw new RuntimeException(ex); + } + + } + + /** + * Reading the Grub stages from the device + * + * @param stage1ResourceName + * @return + * @throws IOException + */ + public byte[] getStage1(String stage1ResourceName) throws IOException { + if (stage1 == null) { + File file = new File(stage1ResourceName); + InputStream is = new FileInputStream(file); + byte[] buf = new byte[512]; + FileUtils.copy(is, buf); + is.close(); + stage1 = buf; + } + return stage1; + } + + public byte[] getStage1_5(String stage1_5ResourceName) throws IOException { + if (stage1_5 == null) { + File file = new File(stage1_5ResourceName); + InputStream in = new FileInputStream(file); + byte[] buf = new byte[(int) file.length()]; + FileUtils.copy(in, buf); + in.close(); + stage1_5 = buf; + } + return stage1_5; + + } + + /** + * The method that will write the stage1.5 for the fat specific to the + * Boot-sector to the block device. + */ + public final static void writeStage1_5(long stage1_5_start, byte[] stage1_5, + BlockDeviceAPI devApi) { + try { + devApi.write(stage1_5_start, ByteBuffer.wrap(stage1_5)); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + + /** + * @throws FileSystemException + * @throws FileSystemException + * @throws FileSystemException + * @throws IOException + * @throws IOException + * @see org.jnode.fs.fat.FatFormatter#format(BlockDeviceAPI) + */ + public final void format(Device device, String path) throws FileSystemException, IOException { + + System.out.println("The format(device) entered."); + BlockDeviceAPI devApi; + try { + + devApi = device.getAPI(BlockDeviceAPI.class); + System.out.println("The devAPI initialization successfully...."); + } catch (ApiNotFoundException e) { + throw new FileSystemException("Device is not a partition!", e); + } + System.out.println("The GrubJFatBootSector starting now......"); + try { + GrubJFatBootSector bs = (GrubJFatBootSector) createBootSector( + stageResourceName1, stageResourceName1_5, devApi); + + try { + bs.write(devApi); + // write the GRUB's stage1 to the MBR + // Writing Stage1 + devApi.flush(); + + System.out.println("The stage1 is written successfully..."); + + stage1_5 = getStage1_5(stageResourceName1_5); + + System.out.println("The stage1_5 buffer is created successfully...."); + // writting the stage1.5;Here it is FatStage1_5 + LittleEndian.setInt32(stage1_5, 512 - 8, bootSectorOffset + 2); + /* Fixup the install partition */ + LittleEndian.setInt32(stage1_5, 512 + 0x08, installPartition); + + setConfigFile("/boot/grub/menu.lst"); + /* Fixup the config file */ + if (configFile != null) { + int ofs = 512 + 0x12; + while (stage1_5[ofs] != 0) { + ofs++; + } + ofs++; /* Skip '\0' */ + for (int i = 0; i < configFile.length(); i++) { + stage1_5[ofs++] = (byte) configFile.charAt(i); + } + stage1_5[ofs] = 0; + } + System.out.println("grub version ["); + int i; + for (i = 512 + 0x12; stage1_5[i] != 0; i++) { + System.out.print((char) stage1_5[i]); + } + System.out.println("[ config ]"); + i++; + for (; stage1_5[i] != 0; i++) { + System.out.println((char) stage1_5[i]); + } + // writting the stage1.5 + System.out.println("the stage1_5 is writing now...pls wait..."); + + writeStage1_5(bs.getBytesPerSector(), stage1_5, devApi); + } catch (IOException e) { + System.out.println("The Bootsector Failed...."); + } + } catch (Exception e) { + System.out.println("The exception at format()"); + } + + System.out.println("Thanks...The stage1_5 is written successfully....."); + + // writting of the stage2 and menu.LST + System.out.println("The Stage2 is now writing...."); + copyFAT("//devices/sg0/BOOT/GRUB/STAGE2_E.", path + "/boot/grub/"); + System.out.println("The Menu.LSt is now writting...."); + copyFAT("//devices/sg0/BOOT/GRUB/MENU.LST", path + "/boot/grub/"); + System.out.println("The Stage2 is successfully created...."); + } + + public String getConfigFile() { + return configFile; + } + + private void setConfigFile(String configFile) { + this.configFile = configFile; + } + + public int getInstallPartition() { + return installPartition; + } + + public static void setInstallPartition(int installPartition1) { + installPartition = installPartition1; + } + + public static Long copyFile(File srcFile, File destFile) throws IOException { + + InputStream in = new FileInputStream(srcFile); + OutputStream out = new FileOutputStream(destFile); + long millis = System.currentTimeMillis(); + CRC32 checksum = null; + if (verify) { + checksum = new CRC32(); + checksum.reset(); + } + byte[] buffer = new byte[1024]; + int bytesRead; + while ((bytesRead = in.read(buffer)) >= 0) { + if (verify) { + checksum.update(buffer, 0, bytesRead); + } + out.write(buffer, 0, bytesRead); + } + out.close(); + in.close(); + if (clock) { + millis = System.currentTimeMillis() - millis; + System.out.println("Second(s): " + (millis / 1000L)); + } + if (verify) { + return new Long(checksum.getValue()); + } else { + return null; + } + } + + public static void copyFAT(String srcFileCopy, String destFileCopy) throws IOException { + + // make sure the source file is indeed a readable file + File srcFile = new File(srcFileCopy); + if (!srcFile.isFile() || !srcFile.canRead()) { + System.err.println("Not a readable file: " + srcFile.getName()); + System.exit(1); + } + // make sure the second argument is a directory + File destDir = new File(destFileCopy); + if (!destDir.exists()) { + destDir.mkdirs(); + System.out.println("The BOOT/GRUB/ Directory is created..."); + } + // create File object for destination file + File destFile = new File(destDir, srcFile.getName()); + + // copy file, optionally creating a checksum + Long checksumSrc = copyFile(srcFile, destFile); + } +} Added: trunk/fs/src/fs/org/jnode/fs/jfat/command/JGrubInstallCommand.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/jfat/command/JGrubInstallCommand.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/jfat/command/JGrubInstallCommand.java 2007-04-03 20:21:40 UTC (rev 3153) @@ -0,0 +1,105 @@ +package org.jnode.fs.jfat.command; + +import java.io.File; +import java.io.InputStream; +import java.io.PrintStream; +import java.io.IOException; +import java.io.FileNotFoundException; + +import javax.naming.NameNotFoundException; + +import org.jnode.driver.Device; +import org.jnode.driver.DeviceManager; +import org.jnode.driver.DeviceNotFoundException; +import org.jnode.driver.DriverException; +import org.jnode.naming.InitialNaming; +import org.jnode.shell.Command; +import org.jnode.shell.CommandLine; +import org.jnode.shell.help.Help; +import org.jnode.shell.help.Parameter; +import org.jnode.shell.help.ParsedArguments; +import org.jnode.shell.help.argument.DeviceArgument; +import org.jnode.shell.help.argument.FileArgument; + +/** + * The Grub Installer command for the JNODE. + * jnode/>jgrub HDA_TARGET + * HDA_TARGET /dev/hda0 or /dev/fd0 + * + * @author Tango Devian + */ +public class JGrubInstallCommand implements Command { + + static final DeviceArgument ARG_DEVICE = new DeviceArgument("device", "device to where the Grub will install"); + + static final FileArgument ARG_DIR = new FileArgument("directory", "the directory where you set the Stage2 and Menu.Lst"); + + static final Help.Info HELP_INFO = new Help.Info("grub", "Install the grub to the specified location.", new Parameter[]{ + new Parameter(ARG_DEVICE, Parameter.MANDATORY), + new Parameter(ARG_DIR, Parameter.MANDATORY)}); + + //static final Parameter PARAM_DEVICE = new Parameter(ARG_DEVICE, + //Parameter.MANDATORY); + /** + * @param args + * @throws Exception + */ + public static void main(String[] args) throws Exception { + new JGrubInstallCommand().execute(new CommandLine(args), System.in, System.out, System.err); + } + + /** + * + */ + public void execute(CommandLine commandLine, InputStream in, PrintStream out, PrintStream err) throws Exception { + try { + ParsedArguments cmdLine = HELP_INFO.parse(commandLine.toStringArray()); + String device = ARG_DEVICE.getValue(cmdLine); + //i am not sure yet + File destDir = ARG_DIR.getFile(cmdLine); + + out.println("grub The dm is now initialized."); + DeviceManager dm = InitialNaming.lookup(DeviceManager.NAME); + + out.println("The getdevice() method invoking now."); + Device dev = dm.getDevice(device); + + out.println("The device is successfully initialized."); + out.println("The Grub Installer is started......wait"); + try { + try { + new GrubJFatFormatter().format(dev, destDir.getAbsolutePath()); + } catch (FileNotFoundException e) { + err.println("The ERROR at GRUB FAT FORMAT method."); + } + } catch (IOException e) { + err.println("The ERROR at the FAT FORMAT method..."); + } + //restart the device + dm.stop(dev); + out.println("The device is stopped...."); + dm.start(dev); + out.println("The Grub successflly installed."); + } catch (NameNotFoundException e) { + out.println("The NameNotFoundException occured..."); + } catch (DeviceNotFoundException e) { + err.println("The Device Not Found..."); + } catch (DriverException e) { + out.println("The DriverException Occuered......"); + } + } +} + + + + + + + + + + + + + + This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. ------------------------------------------------------------------------- Take Surveys. Earn Cash. Influence the Future of IT Join SourceForge.net's Techsay panel and you'll get the chance to share your opinions on IT & business topics through brief surveys-and earn cash http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV _______________________________________________ Jnode-svn-commits mailing list Jnode-svn-commits@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/jnode-svn-commits