2003/09/20 05:03:47
[org.ibex.core.git] / src / org / xwt / mips / ELF.java
index 50f7ab3..8f2c771 100644 (file)
@@ -2,7 +2,18 @@ package org.xwt.mips;
 import java.io.*;
 
 class ELF {
-    private MyRandomAccessFile fd;
+
+    private DataInput fd;
+    private Object image;
+    private void seek(long l) throws IOException {
+        if (image instanceof RandomAccessFile) {
+            ((RandomAccessFile)image).seek(l);
+        } else if (image instanceof byte[]) {
+            ByteArrayInputStream bais = new ByteArrayInputStream((byte[])image);
+            bais.skip(l);
+            fd = new DataInputStream(bais);
+        }
+    }
     
     public ELFHeader header;
     public PHeader[] pheaders;
@@ -10,6 +21,10 @@ class ELF {
     
     private boolean sectionReaderActive;
     
+    private static void skipFully(DataInput fd, int n) throws IOException {
+        while(n>0) n -= fd.skipBytes(n);
+    }
+
     public class ELFHeader {
         byte klass;
         byte data;
@@ -37,10 +52,10 @@ class ELF {
             if(fd.readInt() != ELF_MAGIC) throw new ELFException("Bad Magic (is: " );
             klass = fd.readByte();
             data = fd.readByte();
-            fd.skipFully(1); // version
+            skipFully(fd, 1); // version
             osabi = fd.readByte();
             abiversion = fd.readByte();
-            fd.skipFully(7);
+            skipFully(fd, 7);
             type = fd.readShort();
             machine = fd.readShort();
             version = fd.readInt();
@@ -127,21 +142,22 @@ class ELF {
         }
     }
     
-    public ELF(String file) throws IOException, ELFException {
-        fd = new MyRandomAccessFile(file,"r");
+    public ELF(Object img) throws IOException, ELFException {
+        image = img;
+        seek(0);
         header = new ELFHeader();
         pheaders = new PHeader[header.phnum];
         for(int i=0;i<header.phnum;i++) {
-            fd.seek(header.phoff+i*header.phentsize);
+            seek(header.phoff+i*header.phentsize);
             pheaders[i] = new PHeader();
         }
         sheaders = new SHeader[header.shnum];
         for(int i=0;i<header.shnum;i++) {
-            fd.seek(header.shoff+i*header.shentsize);
+            seek(header.shoff+i*header.shentsize);
             sheaders[i] = new SHeader();
         }
         if(header.shstrndx < 0 || header.shstrndx >= header.shnum) throw new ELFException("Bad shstrndx");
-        fd.seek(sheaders[header.shstrndx].offset);
+        seek(sheaders[header.shstrndx].offset);
         byte[] a = new byte[sheaders[header.shstrndx].size];
         fd.readFully(a);
         for(int i=0;i<header.shnum;i++) {
@@ -161,13 +177,6 @@ class ELF {
     
     public class ELFException extends IOException { ELFException(String s) { super(s); } }
     
-    private class MyRandomAccessFile extends RandomAccessFile  {
-        MyRandomAccessFile(String f,String m) throws IOException { super(f,m); }
-        public void skipFully(int n) throws IOException {
-            while(n>0) n-= skipBytes(n);
-        }
-    }
-
     private class SectionInputStream extends InputStream {
         private int pos;
         private int maxpos;
@@ -176,14 +185,24 @@ class ELF {
                 throw new IOException("Section reader already active");
             sectionReaderActive = true;
             pos = start;
-            fd.seek(pos);
+            seek(pos);
             maxpos = end;
         }
         
         private int bytesLeft() { return maxpos - pos; }
-        public int read() throws IOException { if(bytesLeft()==0) return -1; int b = fd.read(); if(b >= 0) pos++; return b; }
+        public int read() throws IOException {
+            if(bytesLeft()==0) return -1;
+            try {
+                byte b = fd.readByte();
+                pos++;
+                return b;
+            } catch (EOFException e) {
+                return -1;
+            }
+        }
         public int read(byte[] b, int off, int len) throws IOException {
-            int n = fd.read(b,off,Math.min(len,bytesLeft())); if(n > 0) pos += n; return n;
+            fd.readFully(b, off, len);
+            return len;
         }
         public void close() { sectionReaderActive = false; }
     }