public bool abort(IdTransaction tid) { bool rValue; rValue = true; ISet<string> serversURL; Monitor.Enter(this); bool transactionFound = activeTransactions.TryGetValue(tid, out serversURL); if (!transactionFound) { Monitor.Exit(this); throw new TxException("Commit: Not in a transaction. " + tid.Timestamp); } foreach (string s in serversURL) { ServerInformation serverInfo; bool infoFound = serversMap.TryGetValue(s, out serverInfo); if (infoFound) { Monitor.Exit(this); Thread t = new Thread(delegate() { rValue = rValue && serverInfo.server.abort(tid); }); t.Start(); Monitor.Enter(this); } } activeTransactions.Remove(tid); Monitor.Exit(this); return rValue; }
public bool tryReadValue(IdTransaction tid, out int val) { Monitor.Enter(log); bool canRead = log.canRead(tid); if (canRead) { //Use only when a transactions reads its writes before commiting if (log.hasTentative(tid) && (log.lastPreparedWriteTs == tid.Timestamp)) { log.lastPrepareRead = tid; val = log.lastPreparedWriteValue; } else { log.lastRead = tid; val = value; } } else val = -1; Monitor.Exit(log); return canRead; }
public static bool TxBegin() { if (InTransaction) { throw new TxException("Already in transaction"); } currTransaction = master.createTransation(); if (InTransaction) { return true; } return false; }
public void addServerToTransaction(String urlServer, IdTransaction tId) { Monitor.Enter(this); activeTransactions[tId].Add(urlServer); Monitor.Exit(this); }
/* * Transactions-related operations */ public IdTransaction createTransation() { Monitor.Enter(this); IdTransaction t = new IdTransaction(nextTId); nextTId += 1; activeTransactions.Add(t, new HashSet<string>()); Monitor.Exit(this); return t; }
public bool hasPadInt(int id, IdTransaction tId) { if (failed) { throw new NetworkException(this.serverURL, "is not responding."); } else { checkFreezed(); //check if PadInt exists ServerPadInt padInt; Monitor.Enter(this); bool foundPadInt = padIntsMap.TryGetValue(id, out padInt); Monitor.Exit(this); if (!foundPadInt) { return false; } //add PadInt to tid transaction seen PadInts addTransactionIfNotPresent(tId); insertPadintInTransaction(tId, id); Monitor.Enter(this); pingData.addNewTransaction(tId, id); allPingData.addNewTransaction(tId, id); Monitor.Exit(this); return true; } }
public bool write(IdTransaction tid, int id, int value) { ServerPadInt padInt; if (failed) { throw new NetworkException(this.serverURL, "is not responding."); } checkFreezed(); addTransactionIfNotPresent(tid); insertPadintInTransaction(tid, id); Monitor.Enter(this); pingData.addNewTransaction(tid, id); allPingData.addNewTransaction(tid, id); if (padIntsMap.TryGetValue(id, out padInt)) { Monitor.Exit(this); bool couldWrite = padInt.tryWriteValue(tid, value); Monitor.Enter(this); pingData.addModifiedPadInt(id, generatePadIntData(padInt)); allPingData.addModifiedPadInt(id, generatePadIntData(padInt)); Monitor.Exit(this); return couldWrite; } Monitor.Exit(this); throw new NetworkException(this.serverURL, "Error writing '" + value + "' to PadInt " + id + ". Not present."); }
public bool canWrite(IdTransaction tid) { bool validWrite; bool geLRead, geLWrite; if (!tentative || lTentative == tid) { geLRead = lRead == null || tid.Timestamp >= lRead.Timestamp; geLWrite = lWrite == null || tid.Timestamp >= lWrite.Timestamp; validWrite = geLWrite && geLRead; return validWrite; } return false; }
public bool commitWrite(IdTransaction tid, out int value) { if (hasTentative(tid)) { lWrite = lTentative; lTentative = null; value = lTentativeVal; if (lastPrepareRead != null && lastPrepareRead.Timestamp == tid.Timestamp) { if (lRead == null || lRead.Timestamp < lTentativeRead.Timestamp) { lRead = lTentativeRead; } lTentativeRead = null; } return true; } value = -1; return false; }
public void abortWrite(IdTransaction tid) { lTentative = null; lTentativeRead = null; }
public bool canRead(IdTransaction tid) { bool validRead; if (!tentative) { validRead = lWrite == null || tid.Timestamp >= lWrite.Timestamp; return validRead; } if (lTentative.Timestamp == tid.Timestamp) { return true; } return false; }
//Response to commit public bool voteCommit(IdTransaction tid) { bool result; Monitor.Enter(log); if (log.tentative) { result = log.hasTentative(tid); Monitor.Exit(log); return result; } Monitor.Exit(log); return true; }
public bool tryWriteValue(IdTransaction tid, int val) { Monitor.Enter(log); bool canWrite = log.canWrite(tid); if (canWrite) { log.writeTentative(tid, val); } Monitor.Exit(log); return canWrite; }
private IdTransaction lWrite; //última escrita #endregion Fields #region Constructors public LogInformation() { lRead = null; lWrite = null; lTentative = null; }
public bool commit(IdTransaction tid) { if (failed) { throw new NetworkException(this.serverURL, "is not responding."); } checkFreezed(); ISet<int> padIntIds; bool result = true; ServerPadInt padInt; Monitor.Enter(this); bool tidExists = tIdPadIntMap.TryGetValue(tid, out padIntIds); if (!tidExists) { Monitor.Exit(this); throw new TxException(this.serverURL + " This server has no transaction with id " + tid.Id + "."); } foreach (int i in padIntIds) { if (padIntsMap.TryGetValue(i, out padInt)) { Monitor.Exit(this); bool couldCommitPad = padInt.tryCommit(tid); result = result && couldCommitPad; Monitor.Enter(this); } else if (createdPadIntsMap.TryGetValue(i, out padInt)) { padIntsMap.Add(i, padInt); createdPadIntsMap.Remove(i); pingData.addCommitedPadInt(i, generatePadIntData(padInt)); allPingData.addCommitedPadInt(i, generatePadIntData(padInt)); } else { result = false; } pingData.addModifiedPadInt(i, generatePadIntData(padInt)); allPingData.addModifiedPadInt(i, generatePadIntData(padInt)); } tIdPadIntMap.Remove(tid); pingData.removeTransaction(tid); allPingData.removeTransaction(tid); int actualOccupation = padIntsMap.Count; int actualNumberTransactions = tIdPadIntMap.Count; Monitor.Exit(this); Thread t = new Thread(delegate() { sendData(); }); t.Start(); if (!t.Join(TimeSpan.FromSeconds(Constants.TIMEOUT))) { t.Abort(); onSecundaryServerFailure(); } //FIXME what happens when 2 transactions try to create the same PadInt master.updateChargeServer(serverURL, actualOccupation, actualNumberTransactions); master.updatePadIntsMap(padIntIds, serverURL); return result; }
public bool hasTentative(IdTransaction tid) { return (lTentative != null && lTentative.Id == tid.Id && lTentative.Timestamp == tid.Timestamp); }
public bool createPadInt(int id, IdTransaction tId) { if (failed) { throw new NetworkException(this.serverURL, "is not responding."); } checkFreezed(); //if padInt already exists Monitor.Enter(this); if (padIntsMap.ContainsKey(id) || createdPadIntsMap.ContainsKey(id)) { Monitor.Exit(this); return false; } Monitor.Exit(this); //add PadInt to tid transaction seen PadInts addTransactionIfNotPresent(tId); insertPadintInTransaction(tId, id); Monitor.Enter(this); pingData.addNewTransaction(tId, id); allPingData.addNewTransaction(tId, id); //create PadInt object ServerPadInt padInt = new ServerPadInt(id); createdPadIntsMap.Add(id, padInt); pingData.createdPadInt(id, generatePadIntData(padInt)); allPingData.createdPadInt(id, generatePadIntData(padInt)); Monitor.Exit(this); return true; }
public void setReadData(IdTransaction read) { lRead = read; }
public bool prepare(IdTransaction tid) { if (failed) { throw new NetworkException(this.serverURL, "is not responding."); } checkFreezed(); bool result = true; ServerPadInt padInt; ISet<int> padIntIds; Monitor.Enter(this); bool tidExists = tIdPadIntMap.TryGetValue(tid, out padIntIds); if (!tidExists) { Monitor.Exit(this); throw new TxException(this.serverURL + " This server has no transaction with id " + tid.Id + "."); } foreach (int i in padIntIds) { if (createdPadIntsMap.TryGetValue(i, out padInt)) { //DO nothing... } else if (padIntsMap.TryGetValue(i, out padInt)) { Monitor.Exit(this); bool couldPrepPad = padInt.voteCommit(tid); result = result && couldPrepPad; Monitor.Enter(this); } else { result = false; } } Monitor.Exit(this); Thread t = new Thread(delegate() { sendData(); }); t.Start(); if (!t.Join(TimeSpan.FromSeconds(Constants.TIMEOUT))) { t.Abort(); onSecundaryServerFailure(); } return result; }
public void setTentativeData(IdTransaction tentative) { lTentative = tentative; }
private void addTransactionIfNotPresent(IdTransaction tId) { Monitor.Enter(this); if (!tIdPadIntMap.ContainsKey(tId)) { tIdPadIntMap.Add(tId, new HashSet<int>()); Monitor.Exit(this); master.addServerToTransaction(serverURL, tId); } else { Monitor.Exit(this); } }
public void setTentativeReadData(IdTransaction tentativeRead) { lTentativeRead = tentativeRead; }
public bool commit(IdTransaction tid) { bool allPrepared = true; ISet<string> serversURL; Monitor.Enter(this); bool transactionFound = activeTransactions.TryGetValue(tid, out serversURL); if (!transactionFound) { Monitor.Exit(this); throw new TxException("Commit: Not in a transaction. "+ tid.Timestamp); } foreach (string s in serversURL) { ServerInformation info; bool serverExists = serversMap.TryGetValue(s, out info); if (!serverExists) { Monitor.Exit(this); throw new NetworkException("masterURL", "Commit: Participant server not found. Please stop using this service. :P"); } Console.WriteLine("Starting 2PC for transaction " + tid.Timestamp); Monitor.Exit(this); Thread t = new Thread(delegate() { try { allPrepared = allPrepared && info.server.prepare(tid); } catch (SocketException e) { Console.WriteLine("Exception while preparing. " + e.Message); Thread.Sleep(TimeSpan.FromSeconds(Constants.TIMEOUT)); } }); t.Start(); if (!t.Join(TimeSpan.FromSeconds(Constants.TIMEOUT))) { t.Abort(); allPrepared = false; Console.WriteLine("master: " + "Commit prepare timed out for server " + s); } Monitor.Enter(this); } //commit if (allPrepared) { Console.WriteLine("Starting Commit"); foreach (string s in serversURL) { ServerInformation info; bool infoFound = serversMap.TryGetValue(s, out info); if (infoFound) { Monitor.Exit(this); Thread t = new Thread(delegate() { info.server.commit(tid); }); t.Start(); Monitor.Enter(this); } } activeTransactions.Remove(tid); Console.WriteLine("Commited transaction " + tid.Timestamp); Monitor.Exit(this); return true; } //abort Console.WriteLine("Starting Abort"); foreach (string s in serversURL) { ServerInformation info; bool infoFound = serversMap.TryGetValue(s, out info); if (infoFound) { Monitor.Exit(this); Thread t = new Thread(delegate() { info.server.abort(tid); }); t.Start(); Monitor.Enter(this); } } activeTransactions.Remove(tid); Console.WriteLine("Aborted transaction " + tid.Timestamp); Monitor.Exit(this); return false; }
public void setWriteData(IdTransaction write) { lWrite = write; }
//loadBalancing choice. Returns URL of server less charged. public string getServerLessCharged(IdTransaction tId) { float minLoad; float tmpLoad; if (serversMap.Count == 0) { Thread.Sleep(1000); if (serversMap.Count == 0) { throw new NetworkException("Master", "Service not available: No servers online"); } } Monitor.Enter(this); ServerInformation serverInfo = serversMap.Values.ElementAt(0); String serverURL = serversMap.Keys.ElementAt(0); minLoad = Single.MaxValue; foreach (KeyValuePair<string, ServerInformation> entry in serversMap) { serverInfo = entry.Value; if (serverInfo.Status.Equals(Constants.STATUS_PRIMARY) && (tmpLoad = 0.5f * serverInfo.Ocupation + 0.5f * serverInfo.Transactions) < minLoad) { minLoad = tmpLoad; serverURL = entry.Key; } } activeTransactions[tId].Add(serverURL); Monitor.Exit(this); return serverURL; }
public void writeTentative(IdTransaction tid, int val) { lTentative = tid; lTentativeVal = val; }
public static bool Init() { masterURL = "tcp://localhost:"+Constants.MASTER_PORT+"/"+Constants.MASTER_NAME; master = (iMaster)Activator.GetObject(typeof(iMaster), masterURL); currTransaction = null; KnownPadInts = new Dictionary<int, iServer>(); padIntsMap = new Dictionary<int, PadInt>(); temporaryPadInts = new Dictionary<int, PadInt>(); server = null; return true; }
public bool abort(IdTransaction tid) { if (failed) { throw new NetworkException(this.serverURL, "is not responding."); } checkFreezed(); ISet<int> padIntTids; bool result = true; ServerPadInt padInt; Monitor.Enter(this); bool tidExists = tIdPadIntMap.TryGetValue(tid, out padIntTids); if (!tidExists) { Monitor.Exit(this); throw new TxException(this.serverURL + " This server has no transaction with id " + tid.Id + "."); } foreach (int i in padIntTids) { //check if padInts were created and remove them if (createdPadIntsMap.TryGetValue(i, out padInt)) { createdPadIntsMap.Remove(i); pingData.removeCreatedPadInt(i); allPingData.removeCreatedPadInt(i); } else if (padIntsMap.TryGetValue(i, out padInt)) { Monitor.Exit(this); bool couldAbortPad = padInt.tryAbort(tid); Monitor.Enter(this); result = result && couldAbortPad; pingData.addModifiedPadInt(i, generatePadIntData(padInt)); allPingData.addModifiedPadInt(i, generatePadIntData(padInt)); } else { result = false; } } tIdPadIntMap.Remove(tid); pingData.removeTransaction(tid); allPingData.removeTransaction(tid); Monitor.Exit(this); Thread t = new Thread(delegate() { sendData(); }); t.Start(); if (!t.Join(TimeSpan.FromSeconds(Constants.TIMEOUT))) { t.Abort(); onSecundaryServerFailure(); } return result; }
private static void unsetInTransaction() { currTransaction = null; }
public bool tryCommit(IdTransaction tid) { Monitor.Enter(log); bool hasTentative = log.hasTentative(tid); if (hasTentative) { int tvalue; if (log.commitWrite(tid, out tvalue)) { value = tvalue; Monitor.Exit(log); return true; } Monitor.Exit(log); return false; } Monitor.Exit(log); return true; }