wasSharp – Blame information for rev 5

Subversion Repositories:
Rev:
Rev Author Line No. Line
1 zed 1 ///////////////////////////////////////////////////////////////////////////
2 // Copyright (C) Wizardry and Steamworks 2013 - License: GNU GPLv3 //
3 // Please see: http://www.gnu.org/licenses/gpl.html for legal details, //
4 // rights of fair usage, the disclaimer and warranty conditions. //
5 ///////////////////////////////////////////////////////////////////////////
6  
7 using System;
8 using System.Collections.Generic;
9 using System.Linq;
10 using System.Text;
11 using System.Threading.Tasks;
12  
13 namespace wasSharp
14 {
15 public class Cryptography
16 {
17 ///////////////////////////////////////////////////////////////////////////
18 // Copyright (C) Wizardry and Steamworks 2014 - License: GNU GPLv3 //
19 ///////////////////////////////////////////////////////////////////////////
20 /// <summary>
21 /// Encrypt or decrypt a message given a set of rotors, plugs and a reflector.
22 /// </summary>
23 /// <param name="message">the message to encyrpt or decrypt</param>
24 /// <param name="rotors">any combination of: 1, 2, 3, 4, 5, 6, 7, 8, b, g</param>
25 /// <param name="plugs">the letter representing the start character for the rotor</param>
26 /// <param name="reflector">any one of: B, b, C, c</param>
27 /// <returns>either a decrypted or encrypted string</returns>
5 eva 28 public static string ENIGMA(string message, char[] rotors, char[] plugs, char reflector)
1 zed 29 {
30 Dictionary<char, char[]> def_rotors = new Dictionary<char, char[]>
31 {
32 {
33 '1', new[]
34 {
35 'e', 'k', 'm', 'f', 'l',
36 'g', 'd', 'q', 'v', 'z',
37 'n', 't', 'o', 'w', 'y',
38 'h', 'x', 'u', 's', 'p',
39 'a', 'i', 'b', 'r', 'c',
40 'j'
41 }
42 },
43 {
44 '2', new[]
45 {
46 'a', 'j', 'd', 'k', 's',
47 'i', 'r', 'u', 'x', 'b',
48 'l', 'h', 'w', 't', 'm',
49 'c', 'q', 'g', 'z', 'n',
50 'p', 'y', 'f', 'v', 'o',
51 'e'
52 }
53 },
54 {
55 '3', new[]
56 {
57 'b', 'd', 'f', 'h', 'j',
58 'l', 'c', 'p', 'r', 't',
59 'x', 'v', 'z', 'n', 'y',
60 'e', 'i', 'w', 'g', 'a',
61 'k', 'm', 'u', 's', 'q',
62 'o'
63 }
64 },
65 {
66 '4', new[]
67 {
68 'e', 's', 'o', 'v', 'p',
69 'z', 'j', 'a', 'y', 'q',
70 'u', 'i', 'r', 'h', 'x',
71 'l', 'n', 'f', 't', 'g',
72 'k', 'd', 'c', 'm', 'w',
73 'b'
74 }
75 },
76 {
77 '5', new[]
78 {
79 'v', 'z', 'b', 'r', 'g',
80 'i', 't', 'y', 'u', 'p',
81 's', 'd', 'n', 'h', 'l',
82 'x', 'a', 'w', 'm', 'j',
83 'q', 'o', 'f', 'e', 'c',
84 'k'
85 }
86 },
87 {
88 '6', new[]
89 {
90 'j', 'p', 'g', 'v', 'o',
91 'u', 'm', 'f', 'y', 'q',
92 'b', 'e', 'n', 'h', 'z',
93 'r', 'd', 'k', 'a', 's',
94 'x', 'l', 'i', 'c', 't',
95 'w'
96 }
97 },
98 {
99 '7', new[]
100 {
101 'n', 'z', 'j', 'h', 'g',
102 'r', 'c', 'x', 'm', 'y',
103 's', 'w', 'b', 'o', 'u',
104 'f', 'a', 'i', 'v', 'l',
105 'p', 'e', 'k', 'q', 'd',
106 't'
107 }
108 },
109 {
110 '8', new[]
111 {
112 'f', 'k', 'q', 'h', 't',
113 'l', 'x', 'o', 'c', 'b',
114 'j', 's', 'p', 'd', 'z',
115 'r', 'a', 'm', 'e', 'w',
116 'n', 'i', 'u', 'y', 'g',
117 'v'
118 }
119 },
120 {
121 'b', new[]
122 {
123 'l', 'e', 'y', 'j', 'v',
124 'c', 'n', 'i', 'x', 'w',
125 'p', 'b', 'q', 'm', 'd',
126 'r', 't', 'a', 'k', 'z',
127 'g', 'f', 'u', 'h', 'o',
128 's'
129 }
130 },
131 {
132 'g', new[]
133 {
134 'f', 's', 'o', 'k', 'a',
135 'n', 'u', 'e', 'r', 'h',
136 'm', 'b', 't', 'i', 'y',
137 'c', 'w', 'l', 'q', 'p',
138 'z', 'x', 'v', 'g', 'j',
139 'd'
140 }
141 }
142 };
143  
144 Dictionary<char, char[]> def_reflectors = new Dictionary<char, char[]>
145 {
146 {
147 'B', new[]
148 {
149 'a', 'y', 'b', 'r', 'c', 'u', 'd', 'h',
150 'e', 'q', 'f', 's', 'g', 'l', 'i', 'p',
151 'j', 'x', 'k', 'n', 'm', 'o', 't', 'z',
152 'v', 'w'
153 }
154 },
155 {
156 'b', new[]
157 {
158 'a', 'e', 'b', 'n', 'c', 'k', 'd', 'q',
159 'f', 'u', 'g', 'y', 'h', 'w', 'i', 'j',
160 'l', 'o', 'm', 'p', 'r', 'x', 's', 'z',
161 't', 'v'
162 }
163 },
164 {
165 'C', new[]
166 {
167 'a', 'f', 'b', 'v', 'c', 'p', 'd', 'j',
168 'e', 'i', 'g', 'o', 'h', 'y', 'k', 'r',
169 'l', 'z', 'm', 'x', 'n', 'w', 't', 'q',
170 's', 'u'
171 }
172 },
173 {
174 'c', new[]
175 {
176 'a', 'r', 'b', 'd', 'c', 'o', 'e', 'j',
177 'f', 'n', 'g', 't', 'h', 'k', 'i', 'v',
178 'l', 'm', 'p', 'w', 'q', 'z', 's', 'x',
179 'u', 'y'
180 }
181 }
182 };
183  
184 // Setup rotors from plugs.
185 foreach (char rotor in rotors)
186 {
187 char plug = plugs[Array.IndexOf(rotors, rotor)];
188 int i = Array.IndexOf(def_rotors[rotor], plug);
189 if (i.Equals(0)) continue;
5 eva 190 def_rotors[rotor] = Arrays.ConcatenateArrays(new[] {plug},
191 Arrays.GetSubArray(Arrays.DeleteSubArray(def_rotors[rotor], i, i), i, -1),
192 Arrays.GetSubArray(Arrays.DeleteSubArray(def_rotors[rotor], i + 1, -1), 0, i - 1));
1 zed 193 }
194  
195 StringBuilder result = new StringBuilder();
196 foreach (char c in message)
197 {
198 if (!char.IsLetter(c))
199 {
200 result.Append(c);
201 continue;
202 }
203  
204 // Normalize to lower.
205 char l = char.ToLower(c);
206  
207 Action<char[]> rotate = o =>
208 {
209 int i = o.Length - 1;
210 do
211 {
5 eva 212 def_rotors[o[0]] = Arrays.ForwardPermuteArrayElements(def_rotors[o[0]], 1);
1 zed 213 if (i.Equals(0))
214 {
5 eva 215 rotors = Arrays.ReversePermuteArrayElements(o, 1);
1 zed 216 continue;
217 }
5 eva 218 l = Arrays.GetElementAt(def_rotors[o[1]], Array.IndexOf(def_rotors[o[0]], l) - 1);
219 o = Arrays.ReversePermuteArrayElements(o, 1);
1 zed 220 } while (--i > -1);
221 };
222  
223 // Forward pass through the Enigma's rotors.
224 rotate.Invoke(rotors);
225  
226 // Reflect
227 int x = Array.IndexOf(def_reflectors[reflector], l);
228 l = (x + 1)%2 == 0 ? def_reflectors[reflector][x - 1] : def_reflectors[reflector][x + 1];
229  
230 // Reverse the order of the rotors.
231 Array.Reverse(rotors);
232  
233 // Reverse pass through the Enigma's rotors.
234 rotate.Invoke(rotors);
235  
236 if (char.IsUpper(c))
237 {
238 l = char.ToUpper(l);
239 }
240 result.Append(l);
241 }
242  
243 return result.ToString();
244 }
245  
246 ///////////////////////////////////////////////////////////////////////////
247 // Copyright (C) Wizardry and Steamworks 2014 - License: GNU GPLv3 //
248 ///////////////////////////////////////////////////////////////////////////
249 /// <summary>
250 /// Expand the VIGENRE key to the length of the input.
251 /// </summary>
252 /// <param name="input">the input to expand to</param>
253 /// <param name="enc_key">the key to expand</param>
254 /// <returns>the expanded key</returns>
5 eva 255 public static string VIGENEREExpandKey(string input, string enc_key)
1 zed 256 {
257 string exp_key = string.Empty;
258 int i = 0, j = 0;
259 do
260 {
261 char p = input[i];
262 if (!char.IsLetter(p))
263 {
264 exp_key += p;
265 ++i;
266 continue;
267 }
268 int m = j%enc_key.Length;
269 exp_key += enc_key[m];
270 ++j;
271 ++i;
272 } while (i < input.Length);
273 return exp_key;
274 }
275  
276 ///////////////////////////////////////////////////////////////////////////
277 // Copyright (C) Wizardry and Steamworks 2014 - License: GNU GPLv3 //
278 ///////////////////////////////////////////////////////////////////////////
279 /// <summary>
280 /// Encrypt using VIGENERE.
281 /// </summary>
282 /// <param name="input">the input to encrypt</param>
283 /// <param name="enc_key">the key to encrypt with</param>
284 /// <returns>the encrypted input</returns>
5 eva 285 public static string EncryptVIGENERE(string input, string enc_key)
1 zed 286 {
287 char[] a =
288 {
289 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
290 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'
291 };
292  
5 eva 293 enc_key = VIGENEREExpandKey(input, enc_key);
1 zed 294 string result = string.Empty;
295 int i = 0;
296 do
297 {
298 char p = input[i];
299 if (!char.IsLetter(p))
300 {
301 result += p;
302 ++i;
303 continue;
304 }
305 char q =
5 eva 306 Arrays.ReversePermuteArrayElements(a, Array.IndexOf(a, enc_key[i]))[
1 zed 307 Array.IndexOf(a, char.ToLowerInvariant(p))];
308 if (char.IsUpper(p))
309 {
310 q = char.ToUpperInvariant(q);
311 }
312 result += q;
313 ++i;
314 } while (i < input.Length);
315 return result;
316 }
317  
318 ///////////////////////////////////////////////////////////////////////////
319 // Copyright (C) Wizardry and Steamworks 2014 - License: GNU GPLv3 //
320 ///////////////////////////////////////////////////////////////////////////
321 /// <summary>
322 /// Decrypt using VIGENERE.
323 /// </summary>
324 /// <param name="input">the input to decrypt</param>
325 /// <param name="enc_key">the key to decrypt with</param>
326 /// <returns>the decrypted input</returns>
5 eva 327 public static string DecryptVIGENERE(string input, string enc_key)
1 zed 328 {
329 char[] a =
330 {
331 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
332 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'
333 };
334  
5 eva 335 enc_key = VIGENEREExpandKey(input, enc_key);
1 zed 336 string result = string.Empty;
337 int i = 0;
338 do
339 {
340 char p = input[i];
341 if (!char.IsLetter(p))
342 {
343 result += p;
344 ++i;
345 continue;
346 }
347 char q =
348 a[
5 eva 349 Array.IndexOf(Arrays.ReversePermuteArrayElements(a, Array.IndexOf(a, enc_key[i])),
1 zed 350 char.ToLowerInvariant(p))];
351 if (char.IsUpper(p))
352 {
353 q = char.ToUpperInvariant(q);
354 }
355 result += q;
356 ++i;
357 } while (i < input.Length);
358 return result;
359 }
360  
361 ///////////////////////////////////////////////////////////////////////////
362 // Copyright (C) Wizardry and Steamworks 2015 - License: GNU GPLv3 //
363 ///////////////////////////////////////////////////////////////////////////
364 /// <summary>
365 /// An implementation of the ATBASH cypher for latin alphabets.
366 /// </summary>
367 /// <param name="data">the data to encrypt or decrypt</param>
368 /// <returns>the encrypted or decrypted data</returns>
5 eva 369 public static string ATBASH(string data)
1 zed 370 {
371 char[] a =
372 {
373 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
374 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'
375 };
376  
377 char[] input = data.ToCharArray();
378  
379 Parallel.ForEach(Enumerable.Range(0, data.Length), i =>
380 {
381 char e = input[i];
382 if (!char.IsLetter(e)) return;
383 int x = 25 - Array.BinarySearch(a, char.ToLowerInvariant(e));
384 if (!char.IsUpper(e))
385 {
386 input[i] = a[x];
387 return;
388 }
389 input[i] = char.ToUpperInvariant(a[x]);
390 });
391  
392 return new string(input);
393 }
394 }
395 }