Memory.java 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181
  1. /*
  2. * To change this license header, choose License Headers in Project Properties.
  3. * To change this template file, choose Tools | Templates
  4. * and open the template in the editor.
  5. */
  6. package tools.mips;
  7. import API.Utils;
  8. import java.util.TreeMap;
  9. /**
  10. *
  11. * @author EUGENIO CARVALHO
  12. */
  13. public class Memory {
  14. public Integer WORD_BYTES_COUNT = 4;
  15. protected String EMPTY_BYTE = "00000000";
  16. protected boolean writable;
  17. protected String file;
  18. protected Long size = 0L, localAddress = 0L;
  19. protected TreeMap<Long, String> data = new TreeMap<>();
  20. protected MemoryImportExportInterface io;
  21. public Memory ReadOnly() {
  22. this.writable = false;
  23. return this;
  24. }
  25. public int WordBitSize() {
  26. return WORD_BYTES_COUNT * 8;
  27. }
  28. public Memory Writable() {
  29. this.writable = true;
  30. return this;
  31. }
  32. public void Reset() {
  33. data.entrySet().forEach((entry) -> {
  34. entry.setValue(EMPTY_BYTE);
  35. });
  36. }
  37. public Memory(long size) {
  38. this.size = size;
  39. }
  40. public Memory(String filename, long size) throws Exception {
  41. if (filename.equals("")) {
  42. throw new Exception("Empty file not allowed.");
  43. }
  44. this.file = filename;
  45. this.size = size;
  46. }
  47. public TreeMap<Long, String> Data() {
  48. return data;
  49. }
  50. @Override
  51. public String toString() {
  52. try {
  53. return Dump();
  54. } catch (Exception ex) {
  55. return ex.getMessage();
  56. }
  57. }
  58. protected void CheckIOSet() throws Exception {
  59. if (io == null) {
  60. throw new Exception("Interface de IO da memória não definida.");
  61. }
  62. }
  63. public String Dump() throws Exception {
  64. CheckIOSet();
  65. return io.DumpFile(this);
  66. }
  67. protected void ReadFile() throws Exception {
  68. CheckIOSet();
  69. io.FromFile(this);
  70. }
  71. public Long ReadLong(long address, int rsize) throws Exception {
  72. // System.out.println("R(address, rsize):" + Utils.padPreserveSignal(64, R(address, rsize)));
  73. return Long.parseUnsignedLong(Utils.padPreserveSignal(64, R(address, rsize)), 2);
  74. }
  75. public String R(long address, int rsize) throws Exception {
  76. valid(address);
  77. String buffer = "";
  78. for (int i = 0; i < rsize; i++) {
  79. buffer += RB(address + i);
  80. }
  81. return buffer;
  82. // return Utils.Pad(buffer, "0", Utils.PAD_LEFT, 32);
  83. // System.out.println("R:" + buffer);
  84. // return Utils.padPreserveSignal(32, buffer);
  85. }
  86. public String RB(long address) throws Exception {
  87. valid(address);
  88. address = (address + size) % size;
  89. if (!data.containsKey(address)) {
  90. data.put(address, EMPTY_BYTE);
  91. }
  92. return data.get(address);
  93. }
  94. protected void valid(long address) throws Exception {
  95. if (Math.abs(address) > size) {
  96. throw new Exception("Address '" + address + "' out of range limit " + size + "!");
  97. }
  98. }
  99. public void WB(String sbyte) throws Exception {
  100. WB(localAddress++, sbyte);
  101. }
  102. public void WB(Long address, String sbyte) throws Exception {
  103. valid(address);
  104. int len = sbyte.length();
  105. if (len > 8) {
  106. sbyte = sbyte.substring(sbyte.length() - 8);
  107. } else if (len < 8) {
  108. sbyte = Utils.Pad(sbyte, "0", Utils.PAD_LEFT, 8);
  109. }
  110. data.put((address + size) % size, sbyte);
  111. }
  112. public void W(long address, long value, int wsize) throws Exception {
  113. W(address, Long.toBinaryString(value), wsize);
  114. }
  115. public void W(long address, String bin, int wsize) throws Exception {
  116. valid(address);
  117. int bpos = 4 - wsize;
  118. bin = Utils.Pad(bin, "0", Utils.PAD_LEFT, 32);
  119. String[] bytes = Utils.SplitEach(bin, 8);
  120. //Fix to 16 bytes of negative value binary
  121. // System.out.println("W(" + address + ")" + Arrays.asList(bytes));
  122. if (bytes.length > 4) {
  123. bpos += 4;
  124. }
  125. for (int i = 0; i < wsize; i++) {
  126. WB(address + i, bytes[bpos + i]);
  127. }
  128. }
  129. public Memory Save() throws Exception {
  130. return Save(file);
  131. }
  132. public Memory Save(String filename) throws Exception {
  133. // Grava o conteudo no arquivo
  134. Utils.WriteFile(filename, Dump());
  135. return this;
  136. }
  137. public void SetIO(MemoryImportExportInterface memoryInitializationFile) {
  138. io = memoryInitializationFile;
  139. }
  140. public String File() {
  141. return file;
  142. }
  143. public long Size() {
  144. return size;
  145. }
  146. }