## mars.mips.hardware
Class Memory

    java.lang.Object
      java.util.Observable
          mars.mips.hardware.Memory

    public class Memory

extends Observable

Represents MIPS memory. Different segments are represented by different data structs.

Author:
  Pete Sanderson

Field Summary
`static boolean` `BIG_ENDIAN` Constant representing byte order of each memory word.
`static int` `dataBaseAddress` base address for storage of non-global static data in data segment: 0x10010000 (from SPIM)
`static int` `dataSegmentBaseAddress` base address for (user) data segment: 0x10000000
`static int` `dataSegmentLimitAddress`
`static int` `exceptionHandlerAddress` starting address for exception handlers: 0x80000180
`static int` `externBaseAddress` base address for .extern directive: 0x10000000
`static int` `globalPointer` base address for storing globals
`static int` `heapAddress`
`static int` `heapBaseAddress` base address for heap: 0x10040000 (I think from SPIM not MIPS)
`static int` `kernelBaseAddress` kernel boundary.
`static int` `kernelDataBaseAddress` base address for kernel data segment: 0x90000000
`static int` `kernelDataSegmentLimitAddress`
`static int` `kernelHighAddress` highest address acessible in kernel mode.
`static int` `kernelTextBaseAddress` base address for kernel text segment: 0x80000000
`static int` `kernelTextLimitAddress`
`static boolean` `LITTLE_ENDIAN` Constant representing byte order of each memory word.
`static int` `memoryMapBaseAddress` starting address for memory mapped I/O: 0xffff0000 (-65536)
`static int` `memoryMapLimitAddress`
`static int` `stackBaseAddress` base address for stack: 0x7ffffffc (this is mine - start of highest word below kernel space)
`static int` `stackLimitAddress`
`static int` `stackPointer` starting address for stack: 0x7fffeffc (this is from SPIM not MIPS)
`static int` `textBaseAddress` base address for (user) text segment: 0x00400000
`static int` `textLimitAddress`
`static int` `userHighAddress` highest address accessible in user (not kernel) mode.
`static int` `WORD_LENGTH_BYTES` MIPS word length in bytes.

Method Summary
`void` `addObserver(Observer obs)` Method to accept registration from observer for any memory address.
`void` `addObserver(Observer obs, int addr)` Method to accept registration from observer for specific address.
`void` `addObserver(Observer obs, int startAddr, int endAddr)` Method to accept registration from observer for specific address range.
`static int` `alignToWordBoundary(int address)` Utility method to align given address to next full word boundary, if not already aligned.
`int` `allocateBytesFromHeap(int numBytes)` Returns the next available word-aligned heap address.
`void` `clear()` Explicitly clear the contents of memory.
`int` `countObservers()` Return number of observers
`void` `deleteObserver(Observer obs)` Remove specified memory observers
`void` `deleteObservers()` Remove all memory observers
`static boolean` `doublewordAligned(int address)` Utility to determine if given address is doubleword-aligned.
`int` `get(int address, int length)` Starting at the given word address, read the given number of bytes (max 4).
`int` `getAddressOfFirstNull(int baseAddress, int limitAddress)` Look for first "null" memory value in an address range.
`int` `getByte(int address)` Reads specified Memory byte into low order 8 bits of int.
`boolean` `getByteOrder()` Retrieve memory byte order.
`int` `getHalf(int address)` Starting at the given word address, read a 2 byte word into lower 16 bits of int.
`static Memory` `getInstance()` Returns the unique Memory instance, which becomes in essence global.
`int` `getRawWord(int address)` Starting at the given word address, read a 4 byte word as an int.
`Integer` `getRawWordOrNull(int address)` Starting at the given word address, read a 4 byte word as an int and return Integer.
`ProgramStatement` `getStatement(int address)` Gets ProgramStatement from Text Segment.
`ProgramStatement` `getStatementNoNotify(int address)` Gets ProgramStatement from Text Segment without notifying observers.
`int` `getWord(int address)` Starting at the given word address, read a 4 byte word as an int.
`int` `getWordNoNotify(int address)` Starting at the given word address, read a 4 byte word as an int.
`static boolean` `inDataSegment(int address)` Handy little utility to find out if given address is in MARS data segment (starts at Memory.dataSegmentBaseAddress).
`static boolean` `inKernelDataSegment(int address)` Handy little utility to find out if given address is in MARS kernel data segment (starts at Memory.kernelDataSegmentBaseAddress).
`static boolean` `inKernelTextSegment(int address)` Handy little utility to find out if given address is in MARS kernel text segment (starts at Memory.kernelTextBaseAddress).
`static boolean` `inMemoryMapSegment(int address)` Handy little utility to find out if given address is in the Memory Map area starts at Memory.memoryMapBaseAddress, range 0xffff0000 to 0xffffffff.
`static boolean` `inTextSegment(int address)` Handy little utility to find out if given address is in MARS text segment (starts at Memory.textBaseAddress).
`void` `notifyObservers()` Overridden to be unavailable.
`void` `notifyObservers(Object obj)` Overridden to be unavailable.
`int` `set(int address, int value, int length)` Starting at the given address, write the given value over the given number of bytes.
`int` `setByte(int address, int value)` Writes low order 8 bits of given value into specified Memory byte.
`void` `setByteOrder(boolean order)` Set byte order to either LITTLE_ENDIAN or BIG_ENDIAN.
`static void` `setConfiguration()` Sets current memory configuration for simulated MIPS.
`double` `setDouble(int address, double value)` Writes 64 bit double value starting at specified Memory address.
`int` `setHalf(int address, int value)` Starting at the given halfword address, write the lower 16 bits of given value into 2 bytes (a halfword).
`int` `setRawWord(int address, int value)` Starting at the given word address, write the given value over 4 bytes (a word).
`void` `setStatement(int address, ProgramStatement statement)` Stores ProgramStatement in Text Segment.
`int` `setWord(int address, int value)` Starting at the given word address, write the given value over 4 bytes (a word).
`boolean` `usingCompactMemoryConfiguration()` Determine whether the current memory configuration has a maximum address that can be stored in 16 bits.
`static boolean` `wordAligned(int address)` Utility to determine if given address is word-aligned.

Methods inherited from class java.util.Observable
`clearChanged, hasChanged, setChanged`

Methods inherited from class java.lang.Object
`clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait`

Field Detail

### textBaseAddress

    public static int textBaseAddress

  base address for (user) text segment: 0x00400000

### dataSegmentBaseAddress

    public static int dataSegmentBaseAddress

  base address for (user) data segment: 0x10000000

### externBaseAddress

    public static int externBaseAddress

  base address for .extern directive: 0x10000000

### globalPointer

    public static int globalPointer

  base address for storing globals

### dataBaseAddress

    public static int dataBaseAddress

  base address for storage of non-global static data in data segment: 0x10010000 (from SPIM)

### heapBaseAddress

    public static int heapBaseAddress

  base address for heap: 0x10040000 (I think from SPIM not MIPS)

### stackPointer

    public static int stackPointer

  starting address for stack: 0x7fffeffc (this is from SPIM not MIPS)

### stackBaseAddress

    public static int stackBaseAddress

  base address for stack: 0x7ffffffc (this is mine - start of highest word below kernel space)

### userHighAddress

    public static int userHighAddress

  highest address accessible in user (not kernel) mode.

### kernelBaseAddress

    public static int kernelBaseAddress

  kernel boundary. Only OS can access this or higher address

### kernelTextBaseAddress

    public static int kernelTextBaseAddress

  base address for kernel text segment: 0x80000000

### exceptionHandlerAddress

    public static int exceptionHandlerAddress

  starting address for exception handlers: 0x80000180

### kernelDataBaseAddress

    public static int kernelDataBaseAddress

  base address for kernel data segment: 0x90000000

### memoryMapBaseAddress

    public static int memoryMapBaseAddress

  starting address for memory mapped I/O: 0xffff0000 (-65536)

### kernelHighAddress

    public static int kernelHighAddress

  highest address acessible in kernel mode.

### WORD_LENGTH_BYTES

    public static final int WORD_LENGTH_BYTES

  MIPS word length in bytes.

  See Also:
    Constant Field Values

### LITTLE_ENDIAN

    public static final boolean LITTLE_ENDIAN

  Constant representing byte order of each memory word. Little-endian means lowest numbered byte is right most [3][2][1][0].

  See Also:
    Constant Field Values

### BIG_ENDIAN

    public static final boolean BIG_ENDIAN

  Constant representing byte order of each memory word. Big-endian means lowest numbered byte is left most [0][1][2][3].

  See Also:
    Constant Field Values

### heapAddress

    public static int heapAddress

### dataSegmentLimitAddress

    public static int dataSegmentLimitAddress

### textLimitAddress

    public static int textLimitAddress

### kernelDataSegmentLimitAddress

    public static int kernelDataSegmentLimitAddress

### kernelTextLimitAddress

    public static int kernelTextLimitAddress

### stackLimitAddress

    public static int stackLimitAddress

### memoryMapLimitAddress

    public static int memoryMapLimitAddress

Method Detail

### getInstance

    public static Memory getInstance()

  Returns the unique Memory instance, which becomes in essence global.

### clear

    public void clear()

  Explicitly clear the contents of memory. Typically done at start of assembly.

### setConfiguration

    public static void setConfiguration()

  Sets current memory configuration for simulated MIPS. Configuration is collection of memory segment addresses. e.g. text segment starting at address 0x00400000. Configuration can be modified starting with MARS 3.7.

### usingCompactMemoryConfiguration

    public boolean usingCompactMemoryConfiguration()

  Determine whether the current memory configuration has a maximum address that can be stored in 16 bits.

  Returns:
    true if maximum address can be stored in 16 bits or less, false otherwise

### allocateBytesFromHeap

    public int allocateBytesFromHeap(int numBytes)
                              throws IllegalArgumentException

  Returns the next available word-aligned heap address. There is no recycling and no heap management! There is however nearly 4MB of heap space available in Mars.

  Parameters:
    `numBytes` - Number of bytes requested. Should be multiple of 4, otherwise next higher multiple of 4 allocated.
  Returns:
    address of allocated heap storage.
  Throws:
    `IllegalArgumentException` - if number of requested bytes is negative or exceeds available heap storage

### setByteOrder

    public void setByteOrder(boolean order)

  Set byte order to either LITTLE_ENDIAN or BIG_ENDIAN. Default is LITTLE_ENDIAN.

  Parameters:
    `order` - either LITTLE_ENDIAN or BIG_ENDIAN

### getByteOrder

    public boolean getByteOrder()

  Retrieve memory byte order. Default is LITTLE_ENDIAN (like PCs).

  Returns:
    either LITTLE_ENDIAN or BIG_ENDIAN

### set

    public int set(int address,
                   int value,
                   int length)
            throws AddressErrorException

  Starting at the given address, write the given value over the given number of bytes. This one does not check for word boundaries, and copies one byte at a time. If length == 1, takes value from low order byte. If 2, takes from low order half-word.

  Parameters:
    `address` - Starting address of Memory address to be set.
    `value` - Value to be stored starting at that address.
    `length` - Number of bytes to be written.
  Returns:
    old value that was replaced by the set operation
  Throws:
    `AddressErrorException`

### setRawWord

    public int setRawWord(int address,
                          int value)
                   throws AddressErrorException

  Starting at the given word address, write the given value over 4 bytes (a word). It must be written as is, without adjusting for byte order (little vs big endian). Address must be word-aligned.

  Parameters:
    `address` - Starting address of Memory address to be set.
    `value` - Value to be stored starting at that address.
  Returns:
    old value that was replaced by the set operation.
  Throws:
    `AddressErrorException` - If address is not on word boundary.

### setWord

    public int setWord(int address,
                       int value)
                throws AddressErrorException

  Starting at the given word address, write the given value over 4 bytes (a word). The address must be word-aligned.

  Parameters:
    `address` - Starting address of Memory address to be set.
    `value` - Value to be stored starting at that address.
  Returns:
    old value that was replaced by setWord operation.
  Throws:
    `AddressErrorException` - If address is not on word boundary.

### setHalf

    public int setHalf(int address,
                       int value)
                throws AddressErrorException

  Starting at the given halfword address, write the lower 16 bits of given value into 2 bytes (a halfword).

  Parameters:
    `address` - Starting address of Memory address to be set.
    `value` - Value to be stored starting at that address. Only low order 16 bits used.
  Returns:
    old value that was replaced by setHalf operation.
  Throws:
    `AddressErrorException` - If address is not on halfword boundary.

### setByte

    public int setByte(int address,
                       int value)
                throws AddressErrorException

  Writes low order 8 bits of given value into specified Memory byte.

  Parameters:
    `address` - Address of Memory byte to be set.
    `value` - Value to be stored at that address. Only low order 8 bits used.
  Returns:
    old value that was replaced by setByte operation.
  Throws:
    `AddressErrorException`

### setDouble

    public double setDouble(int address,
                            double value)
                     throws AddressErrorException

  Writes 64 bit double value starting at specified Memory address. Note that high-order 32 bits are stored in higher (second) memory word regardless of "endianness".

  Parameters:
    `address` - Starting address of Memory address to be set.
    `value` - Value to be stored at that address.
  Returns:
    old value that was replaced by setDouble operation.
  Throws:
    `AddressErrorException`

### setStatement

    public void setStatement(int address,
                             ProgramStatement statement)
                      throws AddressErrorException

  Stores ProgramStatement in Text Segment.

  Parameters:
    `address` - Starting address of Memory address to be set. Must be word boundary.
    `statement` - Machine code to be stored starting at that address -- for simulation purposes, actually stores reference to ProgramStatement instead of 32-bit machine code.
  Throws:
    `AddressErrorException` - If address is not on word boundary or is outside Text Segment.
  See Also:
    `ProgramStatement`

### get

    public int get(int address,
                   int length)
            throws AddressErrorException

  Starting at the given word address, read the given number of bytes (max 4). This one does not check for word boundaries, and copies one byte at a time. If length == 1, puts value in low order byte. If 2, puts into low order half-word.

  Parameters:
    `address` - Starting address of Memory address to be read.
    `length` - Number of bytes to be read.
  Returns:
    Value stored starting at that address.
  Throws:
    `AddressErrorException`

### getRawWord

    public int getRawWord(int address)
                   throws AddressErrorException

  Starting at the given word address, read a 4 byte word as an int. It transfers the 32 bit value "raw" as stored in memory, and does not adjust for byte order (big or little endian). Address must be word-aligned.

  Parameters:
    `address` - Starting address of word to be read.
  Returns:
    Word (4-byte value) stored starting at that address.
  Throws:
    `AddressErrorException` - If address is not on word boundary.

### getRawWordOrNull

    public Integer getRawWordOrNull(int address)
                             throws AddressErrorException

  Starting at the given word address, read a 4 byte word as an int and return Integer. It transfers the 32 bit value "raw" as stored in memory, and does not adjust for byte order (big or little endian). Address must be word-aligned. Returns null if reading from text segment and there is no instruction at the requested address. Returns null if reading from data segment and this is the first reference to the MARS 4K memory allocation block (i.e., an array to hold the memory has not been allocated). This method was developed by Greg Giberling of UC Berkeley to support the memory dump feature that he implemented in Fall 2007.

  Parameters:
    `address` - Starting address of word to be read.
  Returns:
    Word (4-byte value) stored starting at that address as an Integer. Conditions that cause return value null are described above.
  Throws:
    `AddressErrorException` - If address is not on word boundary.

### getAddressOfFirstNull

    public int getAddressOfFirstNull(int baseAddress,
                                     int limitAddress)
                              throws AddressErrorException

  Look for first "null" memory value in an address range. For text segment (binary code), this represents a word that does not contain an instruction. Normally use this to find the end of the program. For data segment, this represents the first block of simulated memory (block length currently 4K words) that has not been referenced by an assembled/executing program.

  Parameters:
    `baseAddress` - lowest MIPS address to be searched; the starting point
    `limitAddress` - highest MIPS address to be searched
  Returns:
    lowest address within specified range that contains "null" value as described above.
  Throws:
    `AddressErrorException` - if the base address is not on a word boundary

### getWord

    public int getWord(int address)
                throws AddressErrorException

  Starting at the given word address, read a 4 byte word as an int. Does not use "get()"; we can do it faster here knowing we're working only with full words.

  Parameters:
    `address` - Starting address of word to be read.
  Returns:
    Word (4-byte value) stored starting at that address.
  Throws:
    `AddressErrorException` - If address is not on word boundary.

### getWordNoNotify

    public int getWordNoNotify(int address)
                        throws AddressErrorException

  Starting at the given word address, read a 4 byte word as an int. Does not use "get()"; we can do it faster here knowing we're working only with full words. Observers are NOT notified.

  Parameters:
    `address` - Starting address of word to be read.
  Returns:
    Word (4-byte value) stored starting at that address.
  Throws:
    `AddressErrorException` - If address is not on word boundary.

### getHalf

    public int getHalf(int address)
                throws AddressErrorException

  Starting at the given word address, read a 2 byte word into lower 16 bits of int.

  Parameters:
    `address` - Starting address of word to be read.
  Returns:
    Halfword (2-byte value) stored starting at that address, stored in lower 16 bits.
  Throws:
    `AddressErrorException` - If address is not on halfword boundary.

### getByte

    public int getByte(int address)
                throws AddressErrorException

  Reads specified Memory byte into low order 8 bits of int.

  Parameters:
    `address` - Address of Memory byte to be read.
  Returns:
    Value stored at that address. Only low order 8 bits used.
  Throws:
    `AddressErrorException`

### getStatement

    public ProgramStatement getStatement(int address)
                                  throws AddressErrorException

  Gets ProgramStatement from Text Segment.

  Parameters:
    `address` - Starting address of Memory address to be read. Must be word boundary.
  Returns:
    reference to ProgramStatement object associated with that address, or null if none.
  Throws:
    `AddressErrorException` - If address is not on word boundary or is outside Text Segment.
  See Also:
    `ProgramStatement`

### getStatementNoNotify

    public ProgramStatement getStatementNoNotify(int address)
                                          throws AddressErrorException

  Gets ProgramStatement from Text Segment without notifying observers.

  Parameters:
    `address` - Starting address of Memory address to be read. Must be word boundary.
  Returns:
    reference to ProgramStatement object associated with that address, or null if none.
  Throws:
    `AddressErrorException` - If address is not on word boundary or is outside Text Segment.
  See Also:
    `ProgramStatement`

### wordAligned

    public static boolean wordAligned(int address)

  Utility to determine if given address is word-aligned.

  Parameters:
    `address` - the address to check
  Returns:
    true if address is word-aligned, false otherwise

### doublewordAligned

    public static boolean doublewordAligned(int address)

  Utility to determine if given address is doubleword-aligned.

  Parameters:
    `address` - the address to check
  Returns:
    true if address is doubleword-aligned, false otherwise

### alignToWordBoundary

    public static int alignToWordBoundary(int address)

  Utility method to align given address to next full word boundary, if not already aligned.

  Parameters:
    `address` - a memory address (any int value is potentially valid)
  Returns:
    address aligned to next word boundary (divisible by 4)

### inTextSegment

    public static boolean inTextSegment(int address)

  Handy little utility to find out if given address is in MARS text segment (starts at Memory.textBaseAddress). Note that MARS does not implement the entire MIPS text segment space, but it does implement enough for hundreds of thousands of lines of code.

  Parameters:
    `address` - integer memory address
  Returns:
    true if that address is within MARS-defined text segment, false otherwise.

### inKernelTextSegment

    public static boolean inKernelTextSegment(int address)

  Handy little utility to find out if given address is in MARS kernel text segment (starts at Memory.kernelTextBaseAddress).

  Parameters:
    `address` - integer memory address
  Returns:
    true if that address is within MARS-defined kernel text segment, false otherwise.

### inDataSegment

    public static boolean inDataSegment(int address)

  Handy little utility to find out if given address is in MARS data segment (starts at Memory.dataSegmentBaseAddress). Note that MARS does not implement the entire MIPS data segment space, but it does support at least 4MB.

  Parameters:
    `address` - integer memory address
  Returns:
    true if that address is within MARS-defined data segment, false otherwise.

### inKernelDataSegment

    public static boolean inKernelDataSegment(int address)

  Handy little utility to find out if given address is in MARS kernel data segment (starts at Memory.kernelDataSegmentBaseAddress).

  Parameters:
    `address` - integer memory address
  Returns:
    true if that address is within MARS-defined kernel data segment, false otherwise.

### inMemoryMapSegment

    public static boolean inMemoryMapSegment(int address)

  Handy little utility to find out if given address is in the Memory Map area starts at Memory.memoryMapBaseAddress, range 0xffff0000 to 0xffffffff.

  Parameters:
    `address` - integer memory address
  Returns:
    true if that address is within MARS-defined memory map (MMIO) area, false otherwise.

### addObserver

    public void addObserver(Observer obs)

  Method to accept registration from observer for any memory address. Overrides inherited method. Note to observers: this class delegates Observable operations so notices will come from the delegate, not the memory object.

  Overrides:
    `addObserver` in class `Observable`
  Parameters:
    `obs` - the observer

### addObserver

    public void addObserver(Observer obs,
                            int addr)
                     throws AddressErrorException

  Method to accept registration from observer for specific address. This includes the memory word starting at the given address. Note to observers: this class delegates Observable operations so notices will come from the delegate, not the memory object.

  Parameters:
    `obs` - the observer
    `addr` - the memory address which must be on word boundary
  Throws:
    `AddressErrorException`

### addObserver

    public void addObserver(Observer obs,
                            int startAddr,
                            int endAddr)
                     throws AddressErrorException

  Method to accept registration from observer for specific address range. The last byte included in the address range is the last byte of the word specified by the ending address. Note to observers: this class delegates Observable operations so notices will come from the delegate, not the memory object.

  Parameters:
    `obs` - the observer
    `startAddr` - the low end of memory address range, must be on word boundary
    `endAddr` - the high end of memory address range, must be on word boundary
  Throws:
    `AddressErrorException`

### countObservers

    public int countObservers()

  Return number of observers

  Overrides:
    `countObservers` in class `Observable`

### deleteObserver

    public void deleteObserver(Observer obs)

  Remove specified memory observers

  Overrides:
    `deleteObserver` in class `Observable`
  Parameters:
    `obs` - Observer to be removed

### deleteObservers

    public void deleteObservers()

  Remove all memory observers

  Overrides:
    `deleteObservers` in class `Observable`

### notifyObservers

    public void notifyObservers()

  Overridden to be unavailable. The notice that an Observer receives does not come from the memory object itself, but instead from a delegate.

  Overrides:
    `notifyObservers` in class `Observable`
  Throws:
    `UnsupportedOperationException`

### notifyObservers

    public void notifyObservers(Object obj)

  Overridden to be unavailable. The notice that an Observer receives does not come from the memory object itself, but instead from a delegate.

  Overrides:
    `notifyObservers` in class `Observable`
  Throws:
    `UnsupportedOperationException`