001 /* 002 * This file is part of the Jikes RVM project (http://jikesrvm.org). 003 * 004 * This file is licensed to You under the Eclipse Public License (EPL); 005 * You may not use this file except in compliance with the License. You 006 * may obtain a copy of the License at 007 * 008 * http://www.opensource.org/licenses/eclipse-1.0.php 009 * 010 * See the COPYRIGHT.txt file distributed with this work for information 011 * regarding copyright ownership. 012 */ 013 package org.jikesrvm.util; 014 015 import java.io.InputStream; 016 import java.io.IOException; 017 import org.vmmagic.unboxed.Address; 018 import org.vmmagic.unboxed.Offset; 019 020 /** 021 * Access raw memory region as an input stream. 022 */ 023 public final class AddressInputStream extends InputStream { 024 /** Address of memory region to be read */ 025 private final Address location; 026 /** Length of the memory region */ 027 private final Offset length; 028 /** Offset to be read */ 029 private Offset offset; 030 /** Mark offset */ 031 private Offset markOffset; 032 033 /** Constructor */ 034 public AddressInputStream(Address location, Offset length) { 035 this.location = location; 036 this.length = length; 037 offset = Offset.zero(); 038 markOffset = Offset.zero(); 039 } 040 041 /** @return number of bytes that can be read */ 042 @Override 043 public int available() { 044 return length.minus(offset).toInt(); 045 } 046 /** Mark location */ 047 @Override 048 public void mark(int readLimit) { 049 markOffset = offset; 050 } 051 /** Is mark/reset supported */ 052 @Override 053 public boolean markSupported() { 054 return true; 055 } 056 /** Read a byte */ 057 @Override 058 public int read() throws IOException { 059 if (offset.sGE(length)) { 060 throw new IOException("Read beyond end of memory region"); 061 } 062 byte result = location.loadByte(offset); 063 offset = offset.plus(1); 064 return result & 0xFF; 065 } 066 /** Reset to mark */ 067 @Override 068 public void reset() { 069 offset = markOffset; 070 } 071 /** Skip bytes */ 072 @Override 073 public long skip(long n) { 074 offset = offset.plus((int)n); 075 return ((int)n); 076 } 077 }