public void Write(int fileRegisterIndex, byte[] contents) { Console.WriteLine("WRITE FILE = " + fileRegisterIndex); try { // forces to get always the most recent file FileVersion latest = ReadVersion(fileRegisterIndex, Helper.Semantics.MONOTONIC).Version; latest.Increment(Client.id); FileData fileData = new FileData(latest, contents); string filename = fileRegister.FilenameAt(fileRegisterIndex); FileMetadata fileMetadata = fileRegister.FileMetadataAt(fileRegisterIndex); // data server id / bool write ConcurrentDictionary <string, bool> writes = new ConcurrentDictionary <string, bool>(); int requests = 0; bool quorumReached = false; //QUORUM while (true) { // voting WriteQuorum quorum = new WriteQuorum(fileMetadata.WriteQuorum); foreach (var entry in writes) { bool vote = entry.Value; quorum.AddVote(vote); if (quorum.CheckQuorum()) { quorumReached = true; break; } } // found the quorum file if (quorumReached) { break; } // if there are still pending requests // dont create new ones if (requests > 0) { continue; } // if all the votes arrived at the quorum // stops when all requests are counted (requests = 0) if (quorum.Count == (requests + quorum.Count)) { // get possible new fileMetadata locations // possible optimization // check if there are no dataa servers fileMetadata = OpenFileMetadata(filename); // broadcast to all dataServers that have that file foreach (var entry in fileMetadata.Locations) { string id = entry.Key; string location = entry.Value; string localFilename = fileMetadata.LocalFilenames[id]; // increment right away so it doesn't request untill its decremented Interlocked.Increment(ref requests); Thread request = new Thread(() => { IDataServerToClient dataServer = (IDataServerToClient)Activator.GetObject( typeof(IDataServerToClient), location); bool vote = false; try { dataServer.Write(localFilename, fileData); vote = true; } catch (ProcessFailedException) { } catch (ProcessFreezedException) { } finally { writes[id] = vote; Interlocked.Decrement(ref requests); } }); request.Start(); } } } // update file registers fileRegister.SetFileDataAt(fileRegisterIndex, fileData); } catch (FileDoesNotExistException e) { Console.WriteLine(e.Message); return; } }
public void Write(int fileRegisterIndex, byte[] contents) { Console.WriteLine("WRITE FILE = " + fileRegisterIndex); try { // forces to get always the most recent file FileVersion latest = ReadVersion(fileRegisterIndex, Helper.Semantics.MONOTONIC).Version; latest.Increment(Client.id); FileData fileData = new FileData(latest, contents); string filename = fileRegister.FilenameAt(fileRegisterIndex); FileMetadata fileMetadata = fileRegister.FileMetadataAt(fileRegisterIndex); // data server id / bool write ConcurrentDictionary<string, bool> writes = new ConcurrentDictionary<string, bool>(); int requests = 0; bool quorumReached = false; //QUORUM while (true) { // voting WriteQuorum quorum = new WriteQuorum(fileMetadata.WriteQuorum); foreach (var entry in writes) { bool vote = entry.Value; quorum.AddVote(vote); if (quorum.CheckQuorum()) { quorumReached = true; break; } } // found the quorum file if (quorumReached) break; // if there are still pending requests // dont create new ones if (requests > 0) continue; // if all the votes arrived at the quorum // stops when all requests are counted (requests = 0) if (quorum.Count == (requests + quorum.Count)) { // get possible new fileMetadata locations // possible optimization // check if there are no dataa servers fileMetadata = OpenFileMetadata(filename); // broadcast to all dataServers that have that file foreach (var entry in fileMetadata.Locations) { string id = entry.Key; string location = entry.Value; string localFilename = fileMetadata.LocalFilenames[id]; // increment right away so it doesn't request untill its decremented Interlocked.Increment(ref requests); Thread request = new Thread(() => { IDataServerToClient dataServer = (IDataServerToClient)Activator.GetObject( typeof(IDataServerToClient), location); bool vote = false; try { dataServer.Write(localFilename, fileData); vote = true; } catch (ProcessFailedException) { } catch (ProcessFreezedException) { } finally { writes[id] = vote; Interlocked.Decrement(ref requests); } }); request.Start(); } } } // update file registers fileRegister.SetFileDataAt(fileRegisterIndex, fileData); } catch (FileDoesNotExistException e) { Console.WriteLine(e.Message); return; } }