Advertisement
Guest User

Untitled

a guest
Oct 23rd, 2019
81
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.79 KB | None | 0 0
  1. `include "defines.vh"
  2. module decode_unit #(
  3. parameter INSTR_WIDTH = 16, // instructions are 16 bits in width
  4. parameter R_ADDR_WIDTH = 5
  5.  
  6. )(
  7. input wire [INSTR_WIDTH-1:0] instruction,
  8. output reg [`OPCODE_COUNT-1:0] opcode_type,
  9. output wire [`GROUP_COUNT-1:0] opcode_group,
  10. output reg [R_ADDR_WIDTH-1:0] opcode_rd,
  11. output reg [R_ADDR_WIDTH-1:0] opcode_rr,
  12. output reg [11:0] opcode_imd,
  13. output reg [2:0] opcode_bit
  14. );
  15.  
  16. /*Fiindca register file-ul procesorului nostru (ATtiny20)
  17. are doar 16 registre, putem ignora bitii Rr si Rd de pe pozitiile 9 si 8
  18. (Atmel garanteaza ca, din motive de compatibilitate, vor fi mereu setati
  19. pe 1, sau, echivalent, vor fi folosite numai registrele R16 ? R31).
  20. Deci opcode = 000111rdxxxxxxxx devifne 00011111xxxxxxxx. (Btw, that's ADD)
  21. */
  22.  
  23. always @* begin
  24. casez (instruction)
  25. 16'b0000_11??_????_????: begin
  26. opcode_type = `TYPE_ADD;
  27. opcode_rd = instruction[8:4];
  28. opcode_rr = {instruction[9], instruction[3:0]};
  29. end
  30. 16'b0001_11??_????_????: begin
  31. opcode_type = `TYPE_ADC;
  32. opcode_rd = instruction[8:4];
  33. opcode_rr = {instruction[9], instruction[3:0]};
  34. end
  35. 16'b0010_00??_????_????: begin
  36. opcode_type = `TYPE_AND;
  37. opcode_rd = instruction[8:4];
  38. opcode_rr = {instruction[9], instruction[3:0]};
  39. end
  40. 16'b0010_01??_????_????: begin
  41. opcode_type = `TYPE_EOR;
  42. opcode_rd = instruction[8:4];
  43. opcode_rr = {instruction[9], instruction[3:0]};
  44. end
  45. /* TODO 5: LD_Y */
  46. 16'b1000_000?_????_1000: begin
  47. opcode_type = `TYPE_LD_Y;
  48. opcode_rd = instruction[8:4];
  49. opcode_rr = {R_ADDR_WIDTH{1'bx}};
  50. end
  51. /* TODO 3: LDI */
  52. 16'b1110_????_????_????: begin
  53. opcode_type = `TYPE_LDI;
  54. opcode_rd = instruction[7:4];
  55. opcode_imd = {instruction[11:8], instruction[3:0]};
  56. end
  57. /* TODO 6,7: instructions */
  58. 16'b1010_0???_????_????: begin
  59. opcode_type = `TYPE_LDS;
  60. opcode_rd = instruction[7:4];
  61. opcode_imd = {instruction[10:8], instruction[3:0]};
  62. end
  63. 16'b1001_010?_????_0001: begin
  64. opcode_type = `TYPE_NEG;
  65. opcode_rd = instruction[8:4];
  66. opcode_rr = {R_ADDR_WIDTH{1'bx}};
  67. end
  68. 16'b0000_0000_0000_0000: begin
  69. opcode_type = `TYPE_NOP;
  70. opcode_rd = {R_ADDR_WIDTH{1'bx}};
  71. opcode_rr = {R_ADDR_WIDTH{1'bx}};
  72. end
  73. 16'b0010_10??_????_????: begin
  74. opcode_type = `TYPE_OR;
  75. opcode_rd = instruction[8:4];
  76. opcode_rr = {instruction[9], instruction[3:0]};
  77. end
  78. 16'b0001_10??_????_????: begin
  79. opcode_type = `TYPE_SUB;
  80. opcode_rd = instruction[8:4];
  81. opcode_rr = {instruction[9], instruction[3:0]};
  82. end
  83. /*TODO 4: STS */
  84. /* TODO : De codificat instructiunile din laborator. */
  85. 16'b1010_1???_????_????: begin
  86. opcode_type = `TYPE_STS;
  87. opcode_rr = instruction[7:4];
  88. opcode_imd = {instruction[10:8], instruction[3:0]};
  89. end
  90. 16'b0010_11??_????_????: begin
  91. opcode_type = `TYPE_MOV;
  92. opcode_rd = instruction[8:4];
  93. opcode_rr = {instruction[9], instruction[3:0]};
  94. end
  95.  
  96. default: begin
  97. opcode_type = `TYPE_UNKNOWN;
  98. opcode_rd = {R_ADDR_WIDTH{1'bx}};
  99. opcode_rr = {R_ADDR_WIDTH{1'bx}};
  100. end
  101. /*TODO : completati cu opcodes ale voastre.
  102. Where can I find such opcodes? Make them up or read the lab and see
  103. they're at http://www.atmel.com/images/Atmel-0856-AVR-Instruction-Set-Manual.pdf */
  104. /* Cand gasiti o instructiune de UAL, setati opcode_type la valoarea corecta */
  105. /* instruction seamana cu un ADD? -> opcode_type = `TYPE_ADD; */
  106. endcase
  107. end
  108.  
  109. assign opcode_group[`GROUP_ALU_ONE_OP] =
  110. (opcode_type == `TYPE_NEG);
  111. assign opcode_group[`GROUP_ALU_TWO_OP] =
  112. (opcode_type == `TYPE_ADD) ||
  113. (opcode_type == `TYPE_ADC) ||
  114. (opcode_type == `TYPE_SUB) ||
  115. (opcode_type == `TYPE_AND) ||
  116. (opcode_type == `TYPE_EOR) ||
  117. (opcode_type == `TYPE_OR);
  118. assign opcode_group[`GROUP_ALU] =
  119. opcode_group[`GROUP_ALU_ONE_OP] ||
  120. opcode_group[`GROUP_ALU_TWO_OP];
  121.  
  122. assign opcode_group[`GROUP_LOAD_DIRECT] =
  123. (opcode_type == `TYPE_LDI) ||
  124. (opcode_type == `TYPE_LDS);
  125. assign opcode_group[`GROUP_LOAD_INDIRECT] =
  126. (opcode_type == `TYPE_LD_Y);
  127.  
  128. assign opcode_group[`GROUP_STORE_DIRECT] =
  129. (opcode_type == `TYPE_STS);
  130. assign opcode_group[`GROUP_STORE_INDIRECT] =
  131. 0;
  132.  
  133. assign opcode_group[`GROUP_REGISTER] =
  134. /* TODO 3: LDI */
  135. (opcode_type == `TYPE_MOV);
  136.  
  137. assign opcode_group[`GROUP_LOAD] =
  138. opcode_group[`GROUP_LOAD_DIRECT] ||
  139. opcode_group[`GROUP_LOAD_INDIRECT];
  140. assign opcode_group[`GROUP_STORE] =
  141. opcode_group[`GROUP_STORE_DIRECT] ||
  142. opcode_group[`GROUP_STORE_INDIRECT];
  143. assign opcode_group[`GROUP_MEMORY] =
  144. (opcode_group[`GROUP_LOAD] ||
  145. opcode_group[`GROUP_STORE]);
  146. endmodule
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement