ALU.v 1.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152
  1. /*
  2. * ALU
  3. */
  4. module ALU(
  5. input [31:0] a, b,
  6. input [3:0] opcode,
  7. output reg [31:0] y
  8. );
  9. // Opcodes
  10. localparam
  11. OP_OR = 4'b0000, // OR
  12. OP_AND = 4'b0001, // AND
  13. OP_XOR = 4'b0010, // XOR
  14. OP_ADD = 4'b0011, // Add
  15. OP_SUB = 4'b0100, // Substract
  16. OP_SHIFTL = 4'b0101, // Shift left
  17. OP_SHIFTR = 4'b0110, // Shift right
  18. OP_NOTA = 4'b0111, // ~A
  19. OP_MULTS = 4'b1000, // Multiplication signed
  20. OP_MULTU = 4'b1001, // Multiplication unsigned
  21. OP_SLT = 4'b1010, // Set on less than signed
  22. OP_SLTU = 4'b1011, // Set on less than unsigned
  23. OP_LOAD = 4'b1100, // Load input B ( y := b )
  24. OP_LOADHI = 4'b1101, // Loadhi input B ( y := {(b<<16), a} )
  25. OP_SHIFTRS = 4'b1110, // Shift right with sign extesion
  26. OP_U7 = 4'b1111; // Unimplemented
  27. always @ (*)
  28. begin
  29. case (opcode)
  30. OP_OR: y <= a | b;
  31. OP_AND: y <= a & b;
  32. OP_XOR: y <= a ^ b;
  33. OP_ADD: y <= a + b;
  34. OP_SUB: y <= a - b;
  35. OP_SHIFTL: y <= a << b;
  36. OP_SHIFTR: y <= a >> b;
  37. OP_NOTA: y <= ~a;
  38. OP_MULTS: y <= $signed(a) * $signed(b);
  39. OP_MULTU: y <= a * b;
  40. OP_SLT: y <= {{31{1'b0}}, ($signed(a) < $signed(b))};
  41. OP_SLTU: y <= {{31{1'b0}}, (a < b)};
  42. OP_LOAD: y <= b;
  43. OP_LOADHI: y <= {b[15:0], a[15:0]};
  44. OP_SHIFTRS: y <= $signed(a) >>> b;
  45. OP_U7: y <= 32'd0;
  46. endcase
  47. end
  48. endmodule