Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 13 additions & 2 deletions src/edu/temple/cis/c3238/banksim/Account.java
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ public class Account {

private volatile int balance;
private final int id;
private final Bank myBank;
private Bank myBank;

public Account(Bank myBank, int id, int initialBalance) {
this.myBank = myBank;
Expand Down Expand Up @@ -38,10 +38,21 @@ public synchronized void deposit(int amount) {
// Thread.yield(); // Try to force collision
int newBalance = currentBalance + amount;
balance = newBalance;
//notifyAll();
}

@Override
public synchronized String toString() {
return String.format("Account[%d] balance %d", id, balance);
}

public synchronized void waitForSufficientFunds(int amount) {
while (myBank.isOpen() && amount >= balance) {
try {
wait();
} catch (InterruptedException ex) {
/*ignore*/ }
}
}

}
100 changes: 57 additions & 43 deletions src/edu/temple/cis/c3238/banksim/Bank.java
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,14 @@ public class Bank {

public static final int NTEST = 10;
private final Account[] accounts;
private long ntransacts = 0;
private long ntransacts;
private final int initialBalance;
private final int numAccounts;

private boolean waitForTest = false;
//private int threadsPutToSleep = 0;
private int threadsSleeping = 0;
private int threadsAwake = 10;

private boolean open = true;

public Bank(int numAccounts, int initialBalance) {
this.initialBalance = initialBalance;
Expand All @@ -29,28 +28,42 @@ public Bank(int numAccounts, int initialBalance) {
ntransacts = 0;
}

synchronized boolean isOpen() {
return open;
}

void closeBank() {
synchronized (this) {
open = false;
}
for (Account account : accounts) {
synchronized (account) {
account.notifyAll();
}
}
}

public void transfer(int from, int to, int amount) {
// accounts[from].waitForAvailableFunds(amount);
//accounts[from].waitForSufficientFunds(amount);
if (accounts[from].withdraw(amount)) {
accounts[to].deposit(amount);
System.out.println("trasnfer has occured");
}
//System.out.println("transfer has occured");

if (shouldTest()) {
waitForTest = true;
System.out.println("ntransacts " + ntransacts);
}

if (waitForTest) {
// If test() needs to be ran (waitForTest set to true) this method will
// put each thread to sleep and track threadsPutToSleep/Awake
sleepTransferThread();
}

}

public synchronized void test() {
public void test() {
int sum = 0;
System.out.println("Test Start");
for (Account account : accounts) {
System.out.printf("%s %s%n",
Thread.currentThread().toString(), account.toString());
Expand All @@ -66,69 +79,70 @@ public synchronized void test() {
System.out.println(Thread.currentThread().toString()
+ " The bank is in balance");
}

//Reset the signal for threads to sleep back to false
waitForTest = false;
this.setThreadsSleeping(0);
//Test is complete, wake up all threads
notifyAll();
}

public int size() {
return accounts.length;
}

public boolean shouldTest() {
return ++ntransacts % NTEST == 0;
}

public synchronized void sleepTransferThread() {

//Threads are put to sleep upon completion of last transfer
this.incrThreadsSleeping();

//long threadId = Thread.currentThread().getId();
//System.out.println("thread " + threadId/*this.getThreadsSleeping()*/ + " put to sleep");
System.out.println("thread " + this.getThreadsSleeping() + " put to sleep");
System.out.println("thread " + this.getThreadsAwake() + " still awake");
System.out.println("ntransactions = " + this.ntransacts);

//Last thread to sleep creates new thread to run test
if (this.getThreadsAwake() == 1 /* this.threadsSleeping == NTEST*/) {
System.out.println("Inside Test Condition");
Thread t = new Thread(new Sum(this));
t.start();
//System.out.println("threads awake " + this.getThreadsAwake());
//Last thread to wait creates new thread to run test
if (this.getThreadsAwake() == 1) {
Sum sum = new Sum(this);
sum.start();
}

//Thread is about to wait, adjust count
this.incrThreadsSleeping();

while (waitForTest) {
try {
wait();
this.wait();
} catch (InterruptedException ex) {
}
}

//Thread has resumed running, adjust count
this.decrThreadsSleeping();
}

public synchronized int getThreadsSleeping() {

//Pretty sure I didn't need any of these but to afraid to take them out
public int getThreadsSleeping() {
return threadsSleeping;
}

public synchronized int getThreadsAwake() {
public int getThreadsAwake() {
return threadsAwake;
}

public synchronized void setThreadsSleeping(int i) {
public void setThreadsSleeping(int i) {
this.threadsSleeping = i;
this.threadsAwake = NTEST - 0;
}

public synchronized void incrThreadsSleeping() {
public void incrThreadsSleeping() {
this.threadsSleeping++;
this.threadsAwake--;
}

public synchronized void decrThreadsSleeping() {
public void decrThreadsSleeping() {
this.threadsSleeping--;
this.threadsAwake++;
}

public long incrNtransacts() {
this.ntransacts++;
return ntransacts;
}

public int size() {
return accounts.length;
}

public void setFlagFalse() {
this.waitForTest = false;
}

public boolean shouldTest() {
return incrNtransacts() % NTEST == 0;
}

}
6 changes: 5 additions & 1 deletion src/edu/temple/cis/c3238/banksim/Sum.java
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,12 @@ public Sum(Bank b) {
}

@Override
public synchronized void run() {
public void run() {
synchronized(bank){
bank.test();
bank.setFlagFalse();
bank.notifyAll();
}
}

}
7 changes: 5 additions & 2 deletions src/edu/temple/cis/c3238/banksim/TransferThread.java
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,15 @@ public TransferThread(Bank b, int from, int max) {

@Override
public void run() {
for (int i = 0; i < 1000; i++) {///////////////////////////////change 1000 back to 10000
for (int i = 0; i < 10000; i++) {
int toAccount = (int) (bank.size() * Math.random());
int amount = (int) (maxAmount * Math.random());
bank.transfer(fromAccount, toAccount, amount);

//System.out.println(i);
//System.out.println(Thread.currentThread().toString() + " i = " + i);
if(i == 9999)
System.out.println("For loop complete!");
}
//bank.closeBank();
}
}