/// <summary> /// Writes the input letterset to the file. /// </summary> /// <param name="rotorCount">The new number of rotors to save.</param> /// <param name="lettersetFile">The letterset file to save the letters to.</param> private void SaveToFile(LetterSet letterSet, string lettersetFile) { Directory.CreateDirectory(Path.GetDirectoryName(File)); string text = string.Join(Environment.NewLine, letterSet.Select(c => EscapeLetter(c))); System.IO.File.WriteAllText(lettersetFile, text); }
/// <summary> /// Runs the plugboard randomizer. /// </summary> /// /// <exception cref="IOException"> /// The input save path is invalid. /// </exception> /// <exception cref="SaveFailedException"> /// Failed to save the new plugboard steckering. /// </exception> public void RandomizePlugboard(LetterSet letterSet, string input) { if (letterSet == null) { throw new LetterSetMissingException("Cannot configure Plugboard without a loaded letterset!"); } string file = input; try { Path.GetFullPath(file); string directory = Path.GetDirectoryName(file); if (!string.IsNullOrEmpty(directory) && !Directory.Exists(directory)) { Directory.CreateDirectory(directory); } } catch (Exception ex) { throw new IOException($"Input file \"{file}\" has an invalid path!\n" + ex.Message, ex); } try { Steckering newSteckering = letterSet.RandomizeSteckering(); SaveToFile(letterSet, newSteckering, file); Steckering = newSteckering; File = file; } catch (Exception ex) { throw new SaveFailedException(ex); } }
/// <summary> /// Runs the letterset configurer. /// </summary> /// /// <exception cref="FileNotFoundException"> /// The input file was not found. /// </exception> /// <exception cref="LoadFailedException"> /// An error occurred while loading the letterset. /// </exception> public void ConfigureLetterSet(string input) { string file = input; try { if (!System.IO.File.Exists(file)) { throw new FileNotFoundException($"Input file \"{file}\" does not exist!"); } } catch (Exception ex) { throw new FileNotFoundException($"Input file \"{file}\" does not exist!\n" + ex.Message, ex); } LetterSet oldLetterSet = LetterSet; try { LoadFromFile(file); } catch (Exception ex) { throw new LoadFailedException(ex); } try { SaveToFile(LetterSet, File); } catch (Exception ex) { LetterSet = oldLetterSet; throw new SaveFailedException(ex); } }
/// <summary> /// Runs the plugboard configurer. /// </summary> /// /// <exception cref="FileNotFoundException"> /// The input file was not found. /// </exception> /// <exception cref="LoadFailedException"> /// An error occurred while loading the plugboard steckering. /// </exception> public string ConfigurePlugboard(LetterSet letterSet, string input) { if (letterSet == null) { throw new LetterSetMissingException("Cannot configure Plugboard without a loaded letterset!"); } string file = input; try { if (!System.IO.File.Exists(file)) { throw new FileNotFoundException($"Input file \"{file}\" does not exist!"); } } catch (Exception ex) { throw new FileNotFoundException($"Input file \"{file}\" does not exist!\n" + ex.Message, ex); } Steckering oldSteckering = Steckering; try { LoadFromFile(letterSet, file); try { SaveToFile(Steckering, File); } catch (Exception ex) { Steckering = oldSteckering; throw new SaveFailedException(ex); } } catch (Exception ex) { throw new LoadFailedException(ex); } return(null); }
/// <summary> /// Reads the file and returns the <see cref="int[]"/> plugboard steckering. /// </summary> /// <param name="letterSet">The letterset to reference the index of the characters.</param> /// <param name="plugboardFile">The file containing the plugboard setup.</param> /// /// <exception cref="Exception"> /// A file has invalid formatting, a parsed letter was invalid, or mismatched characters. /// </exception> private void LoadFromFile(LetterSet letterSet, string plugboardFile) { string text = System.IO.File.ReadAllText(plugboardFile); string[] lines = text.SplitLines(true); // Keep track of the characters that are consumed. HashSet <char> inputCharacters = new HashSet <char>(); HashSet <char> outputCharacters = new HashSet <char>(); foreach (char c in letterSet) { inputCharacters.Add(c); } foreach (char c in letterSet) { outputCharacters.Add(c); } int[] steckering = new int[letterSet.Count]; foreach (string line in lines) { int spaceIndex = line.IndexOf(' ', 1); if (spaceIndex == -1) { throw new Exception($"Line \"{line}\" is missing space separator!"); } char inputChar = ParseLetter(line.Substring(0, spaceIndex), false).Value; char outputChar = ParseLetter(line.Substring(spaceIndex + 1), false).Value; if (!inputCharacters.Remove(inputChar)) { throw new Exception($"Line \"{line}\" input character \'{inputChar}\' has already " + $"been used or does not exist in the letterset!"); } if (!outputCharacters.Remove(inputChar)) { throw new Exception($"Line \"{line}\" output character \'{outputChar}\' has already " + $"been used or does not exist in the letterset!"); } int inputIndex = letterSet.IndexOf(inputChar); int outputIndex = letterSet.IndexOf(outputChar); steckering[inputIndex] = outputIndex; } foreach (char c in inputCharacters) { if (!outputCharacters.Remove(c)) { throw new Exception($"\'{c}\' is mapped to an output character but not an input " + $"character, cannot self-stecker!"); } } foreach (char c in outputCharacters) { throw new Exception($"\'{c}\' is mapped to an input character but not an output " + $"character, cannot self-stecker!"); } Steckering = new Steckering(steckering); }
public EnigmaService(DiscordBotServiceContainer services, ConfigParserService configParser) : base(services) { letterSet = LetterSetIO.Read(LetterSetFile); steckering = PlugboardIO.Read(letterSet.Count, PlugboardFile); rotorKeys = RotorIO.Read(RotorKeysFile); this.configParser = configParser; Client.ReactionAdded += OnReactionAddedAsync; }
/// <summary> /// Reads the file and returns the <see cref="LetterSet"/>. /// </summary> /// <param name="lettersetFile">The file containing the letterset.</param> /// /// <exception cref="Exception"> /// A parsed letter is invalid. /// </exception> private void LoadFromFile(string lettersetFile) { string text = System.IO.File.ReadAllText(lettersetFile); string[] lines = text.SplitLines(true); var chars = lines.Select(l => ParseLetter(l, false).Value); LetterSet = new LetterSet(chars.ToArray()); }
/// <summary> /// Writes the input letterset to the file. /// </summary> /// <param name="letterSet">The letterset to save.</param> /// <param name="letterSetFile">The letterset file to save the letters to.</param> /// /// <exception cref="SaveFailedException"> /// An error occurred while saving the file. /// </exception> public static void Write(LetterSet letterSet, string letterSetFile) { try { Directory.CreateDirectory(Path.GetDirectoryName(letterSetFile)); string text = string.Join(Environment.NewLine, letterSet.Select(c => EscapeLetter(c))); File.WriteAllText(letterSetFile, text); } catch (Exception ex) { throw new SaveFailedException($"Failed to save the Letterset file!\n{ex.Message}"); } }
/// <summary> /// Writes the input plugboard steckering to the file. /// </summary> /// <param name="letterSet">The letterset to map the steckering to.</param> /// <param name="steckering">The new steckering to save.</param> /// <param name="plugboardFile">The plugboard file to save the steckering to.</param> private void SaveToFile(LetterSet letterSet, Steckering steckering, string plugboardFile) { Directory.CreateDirectory(Path.GetDirectoryName(File)); StringBuilder str = new StringBuilder(); for (int i = 0; i < steckering.Count; i++) { str.AppendLine(steckering[i].ToString()); } System.IO.File.WriteAllText(plugboardFile, str.ToString()); }
/// <summary> /// Writes the input plugboard steckering to the file. /// </summary> /// <param name="letterSet">The letterset to map the steckering to.</param> /// <param name="steckering">The new steckering to save.</param> /// <param name="plugboardFile">The plugboard file to save the steckering to.</param> private void SaveToFile(LetterSet letterSet, Steckering steckering, string plugboardFile) { StringBuilder str = new StringBuilder(); for (int inputIndex = 0; inputIndex < steckering.Count; inputIndex++) { int outputIndex = steckering[inputIndex]; string input = EscapeLetter(letterSet[inputIndex]); string output = EscapeLetter(letterSet[outputIndex]); str.AppendLine($"{input} {output}"); } System.IO.File.WriteAllText(plugboardFile, str.ToString()); }
/// <summary> /// Constructs the Enigma Machine <see cref="PlugboardConfigurer"/>. /// </summary> /// <param name="letterSet">The existing loaded letterset, or null.</param> public PlugboardConfigurer(LetterSet letterSet) { if (letterSet == null) { return; } try { if (System.IO.File.Exists(File)) { LoadFromFile(letterSet, File); } } catch { } }
/// <summary> /// Runs the plugboard randomizer. /// </summary> /// /// <exception cref="SaveFailedException"> /// Failed to save the new plugboard steckering. /// </exception> public void RandomizePlugboard(LetterSet letterSet) { if (letterSet == null) { throw new LetterSetMissingException("Cannot configure Plugboard without a loaded letterset!"); } try { Steckering newSteckering = PlugboardIO.Generate(letterSet.Count); SaveToFile(newSteckering, File); Steckering = newSteckering; } catch (Exception ex) { throw new SaveFailedException(ex); } }
public string Shift(string text, LetterSet letterSet, int shiftAmount) { var letterCount = letterSet.LetterBictionary.Count; var builder = new StringBuilder(text.Length); foreach (var letter in text) { if (letterSet.LetterBictionary.ContainsKey(letter)) { builder.Append(letterSet.LetterBictionary.LookupByCoKey((letterSet.LetterBictionary.LookupByKey(letter) + shiftAmount).GoodModulo(letterCount))); } else { builder.Append(letter); } } return(builder.ToString()); }
public EnigmaService() { char[] letters = new char[127 - 32 + 1]; for (int i = 0; i < 127 - 32; i++) { letters[i] = (char)(i + 32); } letters[letters.Length - 1] = '\n'; LetterSet letterSet = new LetterSet(letters); setup = new SetupArgs(letterSet) { Steckering = letterSet.RandomizeSteckering(), InvalidCharacter = '?', ResetAfter = 50, RotorCount = 3, RotateOnInvalid = true, UnmappedHandling = UnmappedHandling.Keep, }; }
/// <summary> /// Reads the file and returns the <see cref="int[]"/> plugboard steckering. /// </summary> /// <param name="letterSet">The letterset to reference the index of the characters.</param> /// <param name="plugboardFile">The file containing the plugboard setup.</param> /// /// <exception cref="Exception"> /// A file has invalid formatting, a parsed letter was invalid, or mismatched characters. /// </exception> private void LoadFromFile(LetterSet letterSet, string plugboardFile) { string text = System.IO.File.ReadAllText(plugboardFile); string[] lines = text.SplitLines(true); int index = 0; int[] steckering = new int[letterSet.Count]; // Keep track of the indexes that are consumed. bool[] usedIndexes = new bool[steckering.Length]; foreach (string line in lines) { // Empty line, we done bois! if (line.Length == 0) { break; } int newIndex = int.Parse(line.Trim()); if (newIndex >= steckering.Length) { throw new ArgumentOutOfRangeException($"Index of {newIndex} is greater than or " + $"equal to size of letterset!"); } if (usedIndexes[newIndex]) { throw new Exception($"Index of {newIndex} has already been used!"); } usedIndexes[newIndex] = true; steckering[index] = newIndex; index++; } if (index != steckering.Length) { throw new Exception($"Insufficient number of plugboard indexes ({index})!"); } Steckering = new Steckering(steckering); }
/// <summary> /// Reads the file and returns the <see cref="int[]"/> plugboard steckering. /// </summary> /// <param name="letterSet">The letterset to reference the index of the characters.</param> /// <param name="plugboardFile">The file containing the plugboard setup.</param> /// /// <exception cref="Exception"> /// A file has invalid formatting, a parsed letter was invalid, or mismatched characters. /// </exception> private void LoadFromFile(LetterSet letterSet, string plugboardFile) { Steckering = PlugboardIO.Read(letterSet.Count, plugboardFile); }
/// <summary> /// Writes the input letterset to the file. /// </summary> /// <param name="rotorCount">The new number of rotors to save.</param> /// <param name="letterSetFile">The letterset file to save the letters to.</param> private void SaveToFile(LetterSet letterSet, string letterSetFile) { Directory.CreateDirectory(Path.GetDirectoryName(letterSetFile)); LetterSetIO.Write(letterSet, letterSetFile); }
/// <summary> /// Constructs the <see cref="Rotor"/>. /// </summary> /// <param name="letterSet">The letterset to get the count from.</param> /// <param name="key">The prime number key.</param> public Rotor(LetterSet letterSet, int key) { Base = letterSet.Count; InitialOffset = key - (Base * (key / Base)); Offset = InitialOffset; }