Repository navigation
Expand file tree
/
Copy pathVMParser.java
More file actions
66 lines (55 loc) · 2.1 KB
/
Copy pathVMParser.java
File metadata and controls
66 lines (55 loc) · 2.1 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
package com.daniyaldianati.vmtranslator;
import java.util.Scanner;
public class VMParser {
private Scanner scanner;
private String current;
public VMParser(Scanner s) {
scanner = s;
}
public boolean hasNextCommand() {
return scanner.hasNextLine();
}
public void parseNextLine() {
// Keep reading until a valid, non-empty, non-comment line is found
do {
if (!scanner.hasNextLine()) {
current = null;
return;
}
current = scanner.nextLine().split("//")[0].trim(); // Strip comments & whitespace
} while (current.isEmpty());
}
public CommandType commandType() {
if (current == null || current.isEmpty()) {
throw new IllegalStateException("No current command to analyze");
}
String cmd = current.split(" ")[0];
switch (cmd) {
case "push": return CommandType.C_PUSH;
case "pop": return CommandType.C_POP;
case "label": return CommandType.C_LABEL;
case "goto": return CommandType.C_GOTO;
case "if-goto": return CommandType.C_IF;
case "function": return CommandType.C_FUNCTION;
case "call": return CommandType.C_CALL;
case "return": return CommandType.C_RETURN;
default: return CommandType.C_ARITHMETIC;
}
}
public String arg1() {
if (commandType() == CommandType.C_RETURN) {
throw new IllegalStateException("arg1() should not be called on return command");
}
String[] parts = current.split(" ");
return (commandType() == CommandType.C_ARITHMETIC) ? parts[0] : parts[1];
}
public int arg2() {
if (!(commandType() == CommandType.C_PUSH ||
commandType() == CommandType.C_POP ||
commandType() == CommandType.C_FUNCTION ||
commandType() == CommandType.C_CALL)) {
throw new IllegalStateException("arg2() should only be called on push/pop/function/call");
}
return Integer.parseInt(current.split(" ")[2]);
}
}