-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathConfig.hs
99 lines (84 loc) · 2.48 KB
/
Config.hs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
module Config (parseConfig, Rotor, alphabet, ukwB) where
import Text.ParserCombinators.Parsec
type Rotor = ([Char], Int)
--------------- Constants ---------------
-- | Just the alphabet (Uppercase only)
alphabet :: [Char]
alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
-- | Rotor 1
rotorI :: Rotor -- ^ Encoding and turnover position
rotorI = ("EKMFLGDQVZNTOWYHXUSPAIBRCJ", 17)
-- | Rotor 2
rotorII :: Rotor -- ^ Encoding and turnover position
rotorII = ("AJDKSIRUXBLHWTMCQGZNPYFVOE", 5)
-- | Rotor 3
rotorIII :: Rotor -- ^ Encoding and turnover position
rotorIII = ("BDFHJLCPRTXVZNYEIWGAKMUSQO", 22)
-- | Rotor 4
rotorIV :: Rotor -- ^ Encoding and turnover position
rotorIV = ("ESOVPZJAYQUIRHXLNFTGKDCMWB", 10)
-- | Rotor 5
rotorV :: Rotor -- ^ Encoding and turnover position
rotorV = ("VZBRGITYUPSDNHLXAWMJQOFECK", 26)
-- | UkwB "Umkehrwalze B" (reflector)
ukwB :: [Char] -- ^ Encoding (symmetric)
ukwB = "YRUHQSLDPXNGOKMIEBFZCWVJAT"
--------------- Config parsing ---------------
parseRotors :: Parser [Rotor]
parseRotors = do
rotor1 <- rotor
char ','
rotor2 <- rotor
char ','
rotor3 <- rotor
return [rotor1, rotor2, rotor3]
where rotor = (do
try (do
string "III"
pure rotorIII)
<|>
try (do
string "II"
pure rotorII)
<|>
try (do
string "IV"
pure rotorIV)
<|>
try (do
string "I"
pure rotorI)
<|>
try (do
string "V"
pure rotorV))
parseRingsAndGrundstellung :: Parser [Int]
parseRingsAndGrundstellung = do
n1 <- number
char ','
n2 <- number
char ','
n3 <- number
return [n1, n2, n3]
where number = (do
value <- read <$> many1 digit
pure value)
parsePlugboard :: Parser [(Char, Char)]
parsePlugboard = do
plugs <- many plug
return plugs
where plug = (do
c1 <- upper
c2 <- upper
spaces
pure (c1, c2))
parseConfig :: Parser ([Rotor], [Int], [Int], [(Char, Char)])
parseConfig = do
rotors <- parseRotors
spaces
grundstellung <- parseRingsAndGrundstellung
spaces
rings <- parseRingsAndGrundstellung
spaces
plugboard <- parsePlugboard
return (rotors, grundstellung, rings, plugboard)