Prescaler, Watchdog, (Cycle-) Timer
This commit is contained in:
@ -201,7 +201,7 @@ public class Commands {
|
||||
switch (instruction){
|
||||
case 0b01100100:
|
||||
System.out.println("CLRWDT");
|
||||
//TODO
|
||||
WatchdogTimer.reset();
|
||||
return;
|
||||
case 0b1001:
|
||||
System.out.println("RETFIE");
|
||||
@ -249,6 +249,7 @@ public class Commands {
|
||||
|
||||
public static void addExecutionTime(int i) {
|
||||
totalExecutionTime += i;
|
||||
Timer.cycles(i);
|
||||
}
|
||||
|
||||
public static long getTotalExecutionTime() {
|
||||
@ -259,8 +260,7 @@ public class Commands {
|
||||
|
||||
public static void MOVWF(int file) {
|
||||
DataRegister.setRegister(file, wRegister);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
public static void CLRW() {
|
||||
wRegister = 0;
|
||||
@ -375,7 +375,6 @@ public class Commands {
|
||||
DataRegister.setRegister(file, content);
|
||||
}
|
||||
DataRegister.determineZeroFlag(content);
|
||||
addExecutionTime(1);
|
||||
}
|
||||
|
||||
public static void IORWF(int file, int destination) {
|
||||
|
||||
@ -110,7 +110,7 @@ public class Controller_Frontend {
|
||||
e.printStackTrace();
|
||||
}
|
||||
});
|
||||
Thread.sleep(200); //Verzögerungszeit in Millisekunden
|
||||
Thread.sleep(50); //Verzögerungszeit in Millisekunden
|
||||
}
|
||||
} catch (InterruptedException e) {
|
||||
e.printStackTrace();
|
||||
@ -159,12 +159,12 @@ public class Controller_Frontend {
|
||||
// Befehle ausführen
|
||||
Commands.decode(prog[DataRegister.getPC()]);
|
||||
DataRegister.increasePC();
|
||||
WatchdogTimer.testAndTrigger();
|
||||
Table.refresh();
|
||||
Stage stage = (Stage) stepintoButton.getScene().getWindow();
|
||||
CreateWindow.refreshTable(stage);
|
||||
IOPorts.refreshUI(getTRISbuttons(), getPORTbuttons());
|
||||
//Total Execution Time
|
||||
totalExecutionTimeLabel.setText("Total Execution Time: " + Commands.getTotalExecutionTime() + " microsekunden");
|
||||
totalExecutionTimeLabel.setText("Total Execution Time: " + Commands.getTotalExecutionTime() + " µs");
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -93,6 +93,8 @@ public class DataRegister {
|
||||
setFlags();
|
||||
}
|
||||
}
|
||||
if (address == 1)
|
||||
PreScaler.resetFromRegister();
|
||||
}
|
||||
|
||||
public static int getBit(int fileAddress, int bit) {
|
||||
@ -124,6 +126,8 @@ public class DataRegister {
|
||||
}
|
||||
}
|
||||
}
|
||||
if (address == 1)
|
||||
PreScaler.resetFromRegister();
|
||||
}
|
||||
|
||||
public static void setBit(int fileAddress, int bit) {
|
||||
@ -146,6 +150,8 @@ public class DataRegister {
|
||||
}
|
||||
}
|
||||
}
|
||||
if (address == 1)
|
||||
PreScaler.resetFromRegister();
|
||||
}
|
||||
|
||||
public static void setDirectBit (int fileAddress, int bit, int value){
|
||||
@ -178,6 +184,10 @@ public class DataRegister {
|
||||
writeToPCL();
|
||||
}
|
||||
|
||||
public static void resetPC () {
|
||||
programCounter = 0;
|
||||
}
|
||||
|
||||
public static int getPC(){
|
||||
return programCounter;
|
||||
}
|
||||
|
||||
43
src/main/java/fabrik/simulator/pic16f84/PreScaler.java
Normal file
43
src/main/java/fabrik/simulator/pic16f84/PreScaler.java
Normal file
@ -0,0 +1,43 @@
|
||||
package fabrik.simulator.pic16f84;
|
||||
|
||||
public class PreScaler {
|
||||
private static final int PSA = 0x3;
|
||||
private static final int OPTION = 0x81;
|
||||
|
||||
private static int scaler = 0b111;
|
||||
|
||||
public static boolean isPrescalerOnTimer (){
|
||||
return DataRegister.getDirectBit(OPTION, PSA) == 0;
|
||||
}
|
||||
|
||||
public static int getFactor () {
|
||||
int scale = DataRegister.getDirectRegister(OPTION) & 0b111;
|
||||
int timer = isPrescalerOnTimer() ? 1 : 0;
|
||||
return (int) Math.pow (2, scale+timer);
|
||||
}
|
||||
|
||||
public static void reset (){
|
||||
DataRegister.setDirectBit(OPTION, 0, 0);
|
||||
DataRegister.setDirectBit(OPTION, 1, 0);
|
||||
DataRegister.setDirectBit(OPTION, 2, 0);
|
||||
}
|
||||
|
||||
public static void resetFromRegister() {
|
||||
scaler = getFactor();
|
||||
}
|
||||
|
||||
public static void decrement() {
|
||||
scaler--;
|
||||
if (scaler == 0) {
|
||||
scaler = getFactor();
|
||||
Timer.incrementFromInstructionCycle();
|
||||
}
|
||||
System.err.println("VT: " + scaler);
|
||||
}
|
||||
|
||||
public static void cycles(int i) {
|
||||
for (int j = 0; j < i; j++) {
|
||||
decrement();
|
||||
}
|
||||
}
|
||||
}
|
||||
40
src/main/java/fabrik/simulator/pic16f84/Timer.java
Normal file
40
src/main/java/fabrik/simulator/pic16f84/Timer.java
Normal file
@ -0,0 +1,40 @@
|
||||
package fabrik.simulator.pic16f84;
|
||||
|
||||
public class Timer {
|
||||
private static final int TIMERREG = 0x1;
|
||||
private static final int T0IF = 0x2;
|
||||
private static final int T0SE = 0x4;
|
||||
private static final int T0CS = 0x5;
|
||||
private static final int INTCON = 0x0B;
|
||||
private static final int OPTION = 0x81;
|
||||
|
||||
|
||||
public static void cycles(int cycles){
|
||||
if (DataRegister.getDirectBit(OPTION, T0CS) == 0){
|
||||
if (PreScaler.isPrescalerOnTimer()){
|
||||
for (int i = 0; i < cycles; i++){
|
||||
PreScaler.decrement();
|
||||
}
|
||||
} else {
|
||||
increment();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void incrementFromInstructionCycle(){
|
||||
if (DataRegister.getDirectBit(OPTION, T0CS) == 0){
|
||||
increment();
|
||||
}
|
||||
}
|
||||
|
||||
private static void increment() {
|
||||
int timer = DataRegister.getDirectRegister(TIMERREG);
|
||||
timer++;
|
||||
if (timer > 0xFF){
|
||||
DataRegister.setDirectRegister(TIMERREG, 0);
|
||||
DataRegister.setBit(INTCON, T0IF);
|
||||
} else {
|
||||
DataRegister.setDirectRegister(1, timer);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,93 +1,27 @@
|
||||
package fabrik.simulator.pic16f84;
|
||||
|
||||
import java.util.Timer;
|
||||
import java.util.TimerTask;
|
||||
|
||||
public class WatchdogTimer {
|
||||
private int prescaler;
|
||||
private int counter;
|
||||
private final int MAX_PRESCALER = 128;
|
||||
private static long watchdogTime;
|
||||
private static long lastReset = 0;
|
||||
|
||||
public WatchdogTimer(int prescaler) {
|
||||
|
||||
this.prescaler = Math.min(prescaler, MAX_PRESCALER);
|
||||
this.counter = 0;
|
||||
private static long getTimeFromRegister() {
|
||||
return (PreScaler.isPrescalerOnTimer()) ? 18L : PreScaler.getFactor() * 18L;
|
||||
}
|
||||
|
||||
public void start() {
|
||||
|
||||
activateWatchdog(prescaler);
|
||||
|
||||
int watchdogTime = 18 * prescaler; // Zeit in Millisekunden
|
||||
|
||||
|
||||
Timer timer = new Timer();
|
||||
timer.schedule(new TimerTask() {
|
||||
@Override
|
||||
public void run() {
|
||||
counter++;
|
||||
if (counter >= MAX_PRESCALER) {
|
||||
|
||||
reset();
|
||||
System.out.println("Watchdog Timeout!");
|
||||
|
||||
}
|
||||
}
|
||||
}, 0, watchdogTime);
|
||||
}
|
||||
|
||||
|
||||
public void reset() {
|
||||
counter = 0;
|
||||
}
|
||||
|
||||
|
||||
private void activateWatchdog(int prescaler) {
|
||||
// Teilerfaktor entsprechend einstellen durch zweierpotenz
|
||||
switch (prescaler) {
|
||||
case 1:
|
||||
|
||||
DataRegister.setBit(0x81, 0); // Setze PS2:0 auf 000
|
||||
DataRegister.setBit(0x81, 1); // Deaktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 2:
|
||||
|
||||
DataRegister.clearBit(0x81, 0); // Setze PS2:0 auf 001
|
||||
DataRegister.setBit(0x81, 1); // Deaktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 4:
|
||||
|
||||
DataRegister.setBit(0x81, 0); // Setze PS2:0 auf 010
|
||||
DataRegister.setBit(0x81, 1); // Deaktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 8:
|
||||
|
||||
DataRegister.setBit(0x81, 0); // Setze PS2:0 auf 011
|
||||
DataRegister.setBit(0x81, 1); // Deaktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 16:
|
||||
|
||||
DataRegister.clearBit(0x81, 0); // Setze PS2:0 auf 100
|
||||
DataRegister.clearBit(0x81, 1); // Aktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 32:
|
||||
|
||||
DataRegister.setBit(0x81, 0); // Setze PS2:0 auf 101
|
||||
DataRegister.clearBit(0x81, 1); // Aktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 64:
|
||||
|
||||
DataRegister.clearBit(0x81, 0); // Setze PS2:0 auf 110
|
||||
DataRegister.setBit(0x81, 1); // Aktiviere den Watchdog-Timer
|
||||
break;
|
||||
case 128:
|
||||
|
||||
DataRegister.setBit(0x81, 0); // Setze PS2:0 auf 111
|
||||
DataRegister.setBit(0x81, 1); // Aktiviere den Watchdog-Timer
|
||||
break;
|
||||
default:
|
||||
System.out.println("NÜCHTITTGGGGG für den Watchdog-Timer.");
|
||||
break;
|
||||
public static void testAndTrigger () {
|
||||
watchdogTime = getTimeFromRegister() * 1000;
|
||||
if (!PreScaler.isPrescalerOnTimer() && (Commands.getTotalExecutionTime() >= (watchdogTime + lastReset))){
|
||||
DataRegister.resetPC();
|
||||
System.err.println("Watchdog Timer triggered");
|
||||
DataRegister.clearBit(3, 4);
|
||||
lastReset = Commands.getTotalExecutionTime();
|
||||
}
|
||||
}
|
||||
|
||||
public static void reset (){
|
||||
lastReset = Commands.getTotalExecutionTime();
|
||||
PreScaler.reset();
|
||||
DataRegister.setBit(3, 3);
|
||||
DataRegister.setBit(3, 4);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user