pgp-wordlist 0.1.0.1 → 0.1.0.2
raw patch · 8 files changed
+382/−349 lines, 8 filesdep +deepseqdep +doctestdep ~base
Dependencies added: deepseq, doctest
Dependency ranges changed: base
Files
- pgp-wordlist.cabal +15/−7
- src/Data/Text/PgpWordlist.hs +2/−2
- src/Data/Text/PgpWordlist/Internal/Convert.hs +35/−15
- src/Data/Text/PgpWordlist/Internal/Types.hs +3/−3
- src/Data/Text/PgpWordlist/Internal/Word8Bimap.hs +2/−2
- src/Data/Text/PgpWordlist/Internal/Words.hs +261/−261
- test/Doctest.hs +6/−0
- test/Main.hs +58/−59
pgp-wordlist.cabal view
@@ -1,8 +1,5 @@--- Initial pgp-wordlist.cabal generated by cabal init. For further--- documentation, see http://haskell.org/cabal/users-guide/- name: pgp-wordlist-version: 0.1.0.1+version: 0.1.0.2 synopsis: Translate between binary data and a human-readable collection of words. description: Translate between binary data and a human-readable@@ -29,9 +26,7 @@ build-type: Simple cabal-version: >=1.10 extra-source-files: README.md-tested-with: GHC == 7.6.3- , GHC == 7.8.4- , GHC == 7.10.1+tested-with: GHC == 7.10.3 @@ -67,8 +62,21 @@ build-depends: pgp-wordlist , base , bytestring+ , deepseq , HUnit , tasty >= 0.10 , tasty-hunit >= 0.9 , tasty-quickcheck , text++++test-suite doctest+ type: exitcode-stdio-1.0+ hs-source-dirs: test+ main-is: Doctest.hs+ build-depends:+ base+ , doctest >= 0.10+ ghc-options: -Wall -threaded -rtsopts -with-rtsopts=-N+ default-language: Haskell2010
src/Data/Text/PgpWordlist.hs view
@@ -7,5 +7,5 @@ -import Data.Text.PgpWordlist.Internal.Convert-import Data.Text.PgpWordlist.Internal.Types+import Data.Text.PgpWordlist.Internal.Convert+import Data.Text.PgpWordlist.Internal.Types
src/Data/Text/PgpWordlist/Internal/Convert.hs view
@@ -6,19 +6,22 @@ -import qualified Data.Text.PgpWordlist.Internal.AltList as Alt+import qualified Data.Text.PgpWordlist.Internal.AltList as Alt import Data.Text.PgpWordlist.Internal.Types-import Data.Text.PgpWordlist.Internal.Words import Data.Text.PgpWordlist.Internal.Word8Bimap+import Data.Text.PgpWordlist.Internal.Words -import qualified Data.ByteString.Lazy as BSL-import Data.Text (Text)-import qualified Data.Text as T+import qualified Data.ByteString.Lazy as BSL+import Data.Text (Text)+import qualified Data.Text as T import Data.Word -- | Inverse of 'fromText', modulo whitespace count.+--+-- >>> toText (BSL.pack [104, 101, 108, 108, 111])+-- "frighten glossary glucose handiwork gremlin" toText :: BSL.ByteString -> Text toText = T.intercalate " " . Alt.toList@@ -30,6 +33,20 @@ -- | Convert a text of whitespace-separated words to their binary -- representation. The whitespace splitting behaviour is given by 'T.words'.+--+-- >>> fromText (T.pack "frighten glossary glucose handiwork gremlin")+-- Right "hello"+--+-- Invalid words are recognized:+--+-- >>> fromText (T.pack "frighten dragon glucose handiwork gremlin")+-- Left (BadWord "dragon")+--+-- Typical mistakes include accidentally swapping numbers, which leads to a+-- parity error:+--+-- >>> fromText (T.pack "frighten glucose glossary handiwork gremlin")+-- Left (BadParity "glucose" 108) fromText :: Text -> Either TranslationError BSL.ByteString fromText = fmap (BSL.pack . Alt.toList) . Alt.bitraverse fromEvenWord fromOddWord@@ -50,19 +67,22 @@ -- | Simple conversion, taking into account invalid words. fromEvenWord :: Text -> Either TranslationError Word8-fromEvenWord word = case lookupR evenMap (EvenWord word) of- Just i -> Right i- Nothing -> Left (case lookupR oddMap (OddWord word) of- Just j -> BadParity word j- Nothing -> BadWord word)+fromEvenWord word = case lookupEvenOdd word of+ (Just byte, _x ) -> Right byte+ (Nothing , Just byte) -> Left (BadParity word byte)+ (Nothing , Nothing ) -> Left (BadWord word) -- | Simple conversion, taking into account invalid words. fromOddWord :: Text -> Either TranslationError Word8-fromOddWord word = case lookupR oddMap (OddWord word) of- Just i -> Right i- Nothing -> Left (case lookupR evenMap (EvenWord word) of- Just j -> BadParity word j- Nothing -> BadWord word)+fromOddWord word = case lookupEvenOdd word of+ (_x , Just byte) -> Right byte+ (Just byte, Nothing ) -> Left (BadParity word byte)+ (Nothing , Nothing ) -> Left (BadWord word)++-- | Look up a word in both databases.+lookupEvenOdd :: Text -> (Maybe Word8, Maybe Word8)+lookupEvenOdd word = ( lookupR evenMap (EvenWord word)+ , lookupR oddMap (OddWord word) )
src/Data/Text/PgpWordlist/Internal/Types.hs view
@@ -2,9 +2,9 @@ -import Data.Text (Text)-import Data.Text.PgpWordlist.Internal.AltList-import Data.Word+import Data.Text (Text)+import Data.Text.PgpWordlist.Internal.AltList+import Data.Word
src/Data/Text/PgpWordlist/Internal/Word8Bimap.hs view
@@ -15,8 +15,8 @@ import Data.Vector (Vector, (!)) import qualified Data.Vector as V -import Data.Tuple-import Data.Word+import Data.Tuple+import Data.Word
src/Data/Text/PgpWordlist/Internal/Words.hs view
@@ -4,269 +4,269 @@ -import Data.Text.PgpWordlist.Internal.Types-import Data.Word+import Data.Text.PgpWordlist.Internal.Types +import Data.Word + -- | Database of PGP words wordList :: [(Word8, EvenWord, OddWord)]-wordList = map (\(i,e,o) -> (i, EvenWord e, OddWord o)) table- where- table = [ (0x00, "aardvark" , "adroitness" )- , (0x01, "absurd" , "adviser" )- , (0x02, "accrue" , "aftermath" )- , (0x03, "acme" , "aggregate" )- , (0x04, "adrift" , "alkali" )- , (0x05, "adult" , "almighty" )- , (0x06, "afflict" , "amulet" )- , (0x07, "ahead" , "amusement" )- , (0x08, "aimless" , "antenna" )- , (0x09, "algol" , "applicant" )- , (0x0a, "allow" , "apollo" )- , (0x0b, "alone" , "armistice" )- , (0x0c, "ammo" , "article" )- , (0x0d, "ancient" , "asteroid" )- , (0x0e, "apple" , "atlantic" )- , (0x0f, "artist" , "atmosphere" )- , (0x10, "assume" , "autopsy" )- , (0x11, "athens" , "babylon" )- , (0x12, "atlas" , "backwater" )- , (0x13, "aztec" , "barbecue" )- , (0x14, "baboon" , "belowground")- , (0x15, "backfield", "bifocals" )- , (0x16, "backward" , "bodyguard" )- , (0x17, "banjo" , "bookseller" )- , (0x18, "beaming" , "borderline" )- , (0x19, "bedlamp" , "bottomless" )- , (0x1a, "beehive" , "bradbury" )- , (0x1b, "beeswax" , "bravado" )- , (0x1c, "befriend" , "brazilian" )- , (0x1d, "belfast" , "breakaway" )- , (0x1e, "berserk" , "burlington" )- , (0x1f, "billiard" , "businessman")- , (0x20, "bison" , "butterfat" )- , (0x21, "blackjack", "camelot" )- , (0x22, "blockade" , "candidate" )- , (0x23, "blowtorch", "cannonball" )- , (0x24, "bluebird" , "capricorn" )- , (0x25, "bombast" , "caravan" )- , (0x26, "bookshelf", "caretaker" )- , (0x27, "brackish" , "celebrate" )- , (0x28, "breadline", "cellulose" )- , (0x29, "breakup" , "certify" )- , (0x2a, "brickyard", "chambermaid")- , (0x2b, "briefcase", "cherokee" )- , (0x2c, "burbank" , "chicago" )- , (0x2d, "button" , "clergyman" )- , (0x2e, "buzzard" , "coherence" )- , (0x2f, "cement" , "combustion" )- , (0x30, "chairlift", "commando" )- , (0x31, "chatter" , "company" )- , (0x32, "checkup" , "component" )- , (0x33, "chisel" , "concurrent" )- , (0x34, "choking" , "confidence" )- , (0x35, "chopper" , "conformist" )- , (0x36, "christmas", "congregate" )- , (0x37, "clamshell", "consensus" )- , (0x38, "classic" , "consulting" )- , (0x39, "classroom", "corporate" )- , (0x3a, "cleanup" , "corrosion" )- , (0x3b, "clockwork", "councilman" )- , (0x3c, "cobra" , "crossover" )- , (0x3d, "commence" , "crucifix" )- , (0x3e, "concert" , "cumbersome" )- , (0x3f, "cowbell" , "customer" )- , (0x40, "crackdown", "dakota" )- , (0x41, "cranky" , "decadence" )- , (0x42, "crowfoot" , "december" )- , (0x43, "crucial" , "decimal" )- , (0x44, "crumpled" , "designing" )- , (0x45, "crusade" , "detector" )- , (0x46, "cubic" , "detergent" )- , (0x47, "dashboard", "determine" )- , (0x48, "deadbolt" , "dictator" )- , (0x49, "deckhand" , "dinosaur" )- , (0x4a, "dogsled" , "direction" )- , (0x4b, "dragnet" , "disable" )- , (0x4c, "drainage" , "disbelief" )- , (0x4d, "dreadful" , "disruptive" )- , (0x4e, "drifter" , "distortion" )- , (0x4f, "dropper" , "document" )- , (0x50, "drumbeat" , "embezzle" )- , (0x51, "drunken" , "enchanting" )- , (0x52, "dupont" , "enrollment" )- , (0x53, "dwelling" , "enterprise" )- , (0x54, "eating" , "equation" )- , (0x55, "edict" , "equipment" )- , (0x56, "egghead" , "escapade" )- , (0x57, "eightball", "eskimo" )- , (0x58, "endorse" , "everyday" )- , (0x59, "endow" , "examine" )- , (0x5a, "enlist" , "existence" )- , (0x5b, "erase" , "exodus" )- , (0x5c, "escape" , "fascinate" )- , (0x5d, "exceed" , "filament" )- , (0x5e, "eyeglass" , "finicky" )- , (0x5f, "eyetooth" , "forever" )- , (0x60, "facial" , "fortitude" )- , (0x61, "fallout" , "frequency" )- , (0x62, "flagpole" , "gadgetry" )- , (0x63, "flatfoot" , "galveston" )- , (0x64, "flytrap" , "getaway" )- , (0x65, "fracture" , "glossary" )- , (0x66, "framework", "gossamer" )- , (0x67, "freedom" , "graduate" )- , (0x68, "frighten" , "gravity" )- , (0x69, "gazelle" , "guitarist" )- , (0x6a, "geiger" , "hamburger" )- , (0x6b, "glitter" , "hamilton" )- , (0x6c, "glucose" , "handiwork" )- , (0x6d, "goggles" , "hazardous" )- , (0x6e, "goldfish" , "headwaters" )- , (0x6f, "gremlin" , "hemisphere" )- , (0x70, "guidance" , "hesitate" )- , (0x71, "hamlet" , "hideaway" )- , (0x72, "highchair", "holiness" )- , (0x73, "hockey" , "hurricane" )- , (0x74, "indoors" , "hydraulic" )- , (0x75, "indulge" , "impartial" )- , (0x76, "inverse" , "impetus" )- , (0x77, "involve" , "inception" )- , (0x78, "island" , "indigo" )- , (0x79, "jawbone" , "inertia" )- , (0x7a, "keyboard" , "infancy" )- , (0x7b, "kickoff" , "inferno" )- , (0x7c, "kiwi" , "informant" )- , (0x7d, "klaxon" , "insincere" )- , (0x7e, "locale" , "insurgent" )- , (0x7f, "lockup" , "integrate" )- , (0x80, "merit" , "intention" )- , (0x81, "minnow" , "inventive" )- , (0x82, "miser" , "istanbul" )- , (0x83, "mohawk" , "jamaica" )- , (0x84, "mural" , "jupiter" )- , (0x85, "music" , "leprosy" )- , (0x86, "necklace" , "letterhead" )- , (0x87, "neptune" , "liberty" )- , (0x88, "newborn" , "maritime" )- , (0x89, "nightbird", "matchmaker" )- , (0x8a, "oakland" , "maverick" )- , (0x8b, "obtuse" , "medusa" )- , (0x8c, "offload" , "megaton" )- , (0x8d, "optic" , "microscope" )- , (0x8e, "orca" , "microwave" )- , (0x8f, "payday" , "midsummer" )- , (0x90, "peachy" , "millionaire")- , (0x91, "pheasant" , "miracle" )- , (0x92, "physique" , "misnomer" )- , (0x93, "playhouse", "molasses" )- , (0x94, "pluto" , "molecule" )- , (0x95, "preclude" , "montana" )- , (0x96, "prefer" , "monument" )- , (0x97, "preshrunk", "mosquito" )- , (0x98, "printer" , "narrative" )- , (0x99, "prowler" , "nebula" )- , (0x9a, "pupil" , "newsletter" )- , (0x9b, "puppy" , "norwegian" )- , (0x9c, "python" , "october" )- , (0x9d, "quadrant" , "ohio" )- , (0x9e, "quiver" , "onlooker" )- , (0x9f, "quota" , "opulent" )- , (0xa0, "ragtime" , "orlando" )- , (0xa1, "ratchet" , "outfielder" )- , (0xa2, "rebirth" , "pacific" )- , (0xa3, "reform" , "pandemic" )- , (0xa4, "regain" , "pandora" )- , (0xa5, "reindeer" , "paperweight")- , (0xa6, "rematch" , "paragon" )- , (0xa7, "repay" , "paragraph" )- , (0xa8, "retouch" , "paramount" )- , (0xa9, "revenge" , "passenger" )- , (0xaa, "reward" , "pedigree" )- , (0xab, "rhythm" , "pegasus" )- , (0xac, "ribcage" , "penetrate" )- , (0xad, "ringbolt" , "perceptive" )- , (0xae, "robust" , "performance")- , (0xaf, "rocker" , "pharmacy" )- , (0xb0, "ruffled" , "phonetic" )- , (0xb1, "sailboat" , "photograph" )- , (0xb2, "sawdust" , "pioneer" )- , (0xb3, "scallion" , "pocketful" )- , (0xb4, "scenic" , "politeness" )- , (0xb5, "scorecard", "positive" )- , (0xb6, "scotland" , "potato" )- , (0xb7, "seabird" , "processor" )- , (0xb8, "select" , "provincial" )- , (0xb9, "sentence" , "proximate" )- , (0xba, "shadow" , "puberty" )- , (0xbb, "shamrock" , "publisher" )- , (0xbc, "showgirl" , "pyramid" )- , (0xbd, "skullcap" , "quantity" )- , (0xbe, "skydive" , "racketeer" )- , (0xbf, "slingshot", "rebellion" )- , (0xc0, "slowdown" , "recipe" )- , (0xc1, "snapline" , "recover" )- , (0xc2, "snapshot" , "repellent" )- , (0xc3, "snowcap" , "replica" )- , (0xc4, "snowslide", "reproduce" )- , (0xc5, "solo" , "resistor" )- , (0xc6, "southward", "responsive" )- , (0xc7, "soybean" , "retraction" )- , (0xc8, "spaniel" , "retrieval" )- , (0xc9, "spearhead", "retrospect" )- , (0xca, "spellbind", "revenue" )- , (0xcb, "spheroid" , "revival" )- , (0xcc, "spigot" , "revolver" )- , (0xcd, "spindle" , "sandalwood" )- , (0xce, "spyglass" , "sardonic" )- , (0xcf, "stagehand", "saturday" )- , (0xd0, "stagnate" , "savagery" )- , (0xd1, "stairway" , "scavenger" )- , (0xd2, "standard" , "sensation" )- , (0xd3, "stapler" , "sociable" )- , (0xd4, "steamship", "souvenir" )- , (0xd5, "sterling" , "specialist" )- , (0xd6, "stockman" , "speculate" )- , (0xd7, "stopwatch", "stethoscope")- , (0xd8, "stormy" , "stupendous" )- , (0xd9, "sugar" , "supportive" )- , (0xda, "surmount" , "surrender" )- , (0xdb, "suspense" , "suspicious" )- , (0xdc, "sweatband", "sympathy" )- , (0xdd, "swelter" , "tambourine" )- , (0xde, "tactics" , "telephone" )- , (0xdf, "talon" , "therapist" )- , (0xe0, "tapeworm" , "tobacco" )- , (0xe1, "tempest" , "tolerance" )- , (0xe2, "tiger" , "tomorrow" )- , (0xe3, "tissue" , "torpedo" )- , (0xe4, "tonic" , "tradition" )- , (0xe5, "topmost" , "travesty" )- , (0xe6, "tracker" , "trombonist" )- , (0xe7, "transit" , "truncated" )- , (0xe8, "trauma" , "typewriter" )- , (0xe9, "treadmill", "ultimate" )- , (0xea, "trojan" , "undaunted" )- , (0xeb, "trouble" , "underfoot" )- , (0xec, "tumor" , "unicorn" )- , (0xed, "tunnel" , "unify" )- , (0xee, "tycoon" , "universe" )- , (0xef, "uncut" , "unravel" )- , (0xf0, "unearth" , "upcoming" )- , (0xf1, "unwind" , "vacancy" )- , (0xf2, "uproot" , "vagabond" )- , (0xf3, "upset" , "vertigo" )- , (0xf4, "upshot" , "virginia" )- , (0xf5, "vapor" , "visitor" )- , (0xf6, "village" , "vocalist" )- , (0xf7, "virus" , "voyager" )- , (0xf8, "vulcan" , "warranty" )- , (0xf9, "waffle" , "waterloo" )- , (0xfa, "wallet" , "whimsical" )- , (0xfb, "watchword", "wichita" )- , (0xfc, "wayside" , "wilmington" )- , (0xfd, "willow" , "wyoming" )- , (0xfe, "woodlark" , "yesteryear" )- , (0xff, "zulu" , "yucatan" )- ]+wordList = map (\(i,e,o) -> (i, EvenWord e, OddWord o))+ [ (0x00, "aardvark" , "adroitness" )+ , (0x01, "absurd" , "adviser" )+ , (0x02, "accrue" , "aftermath" )+ , (0x03, "acme" , "aggregate" )+ , (0x04, "adrift" , "alkali" )+ , (0x05, "adult" , "almighty" )+ , (0x06, "afflict" , "amulet" )+ , (0x07, "ahead" , "amusement" )+ , (0x08, "aimless" , "antenna" )+ , (0x09, "algol" , "applicant" )+ , (0x0a, "allow" , "apollo" )+ , (0x0b, "alone" , "armistice" )+ , (0x0c, "ammo" , "article" )+ , (0x0d, "ancient" , "asteroid" )+ , (0x0e, "apple" , "atlantic" )+ , (0x0f, "artist" , "atmosphere" )+ , (0x10, "assume" , "autopsy" )+ , (0x11, "athens" , "babylon" )+ , (0x12, "atlas" , "backwater" )+ , (0x13, "aztec" , "barbecue" )+ , (0x14, "baboon" , "belowground")+ , (0x15, "backfield", "bifocals" )+ , (0x16, "backward" , "bodyguard" )+ , (0x17, "banjo" , "bookseller" )+ , (0x18, "beaming" , "borderline" )+ , (0x19, "bedlamp" , "bottomless" )+ , (0x1a, "beehive" , "bradbury" )+ , (0x1b, "beeswax" , "bravado" )+ , (0x1c, "befriend" , "brazilian" )+ , (0x1d, "belfast" , "breakaway" )+ , (0x1e, "berserk" , "burlington" )+ , (0x1f, "billiard" , "businessman")+ , (0x20, "bison" , "butterfat" )+ , (0x21, "blackjack", "camelot" )+ , (0x22, "blockade" , "candidate" )+ , (0x23, "blowtorch", "cannonball" )+ , (0x24, "bluebird" , "capricorn" )+ , (0x25, "bombast" , "caravan" )+ , (0x26, "bookshelf", "caretaker" )+ , (0x27, "brackish" , "celebrate" )+ , (0x28, "breadline", "cellulose" )+ , (0x29, "breakup" , "certify" )+ , (0x2a, "brickyard", "chambermaid")+ , (0x2b, "briefcase", "cherokee" )+ , (0x2c, "burbank" , "chicago" )+ , (0x2d, "button" , "clergyman" )+ , (0x2e, "buzzard" , "coherence" )+ , (0x2f, "cement" , "combustion" )+ , (0x30, "chairlift", "commando" )+ , (0x31, "chatter" , "company" )+ , (0x32, "checkup" , "component" )+ , (0x33, "chisel" , "concurrent" )+ , (0x34, "choking" , "confidence" )+ , (0x35, "chopper" , "conformist" )+ , (0x36, "christmas", "congregate" )+ , (0x37, "clamshell", "consensus" )+ , (0x38, "classic" , "consulting" )+ , (0x39, "classroom", "corporate" )+ , (0x3a, "cleanup" , "corrosion" )+ , (0x3b, "clockwork", "councilman" )+ , (0x3c, "cobra" , "crossover" )+ , (0x3d, "commence" , "crucifix" )+ , (0x3e, "concert" , "cumbersome" )+ , (0x3f, "cowbell" , "customer" )+ , (0x40, "crackdown", "dakota" )+ , (0x41, "cranky" , "decadence" )+ , (0x42, "crowfoot" , "december" )+ , (0x43, "crucial" , "decimal" )+ , (0x44, "crumpled" , "designing" )+ , (0x45, "crusade" , "detector" )+ , (0x46, "cubic" , "detergent" )+ , (0x47, "dashboard", "determine" )+ , (0x48, "deadbolt" , "dictator" )+ , (0x49, "deckhand" , "dinosaur" )+ , (0x4a, "dogsled" , "direction" )+ , (0x4b, "dragnet" , "disable" )+ , (0x4c, "drainage" , "disbelief" )+ , (0x4d, "dreadful" , "disruptive" )+ , (0x4e, "drifter" , "distortion" )+ , (0x4f, "dropper" , "document" )+ , (0x50, "drumbeat" , "embezzle" )+ , (0x51, "drunken" , "enchanting" )+ , (0x52, "dupont" , "enrollment" )+ , (0x53, "dwelling" , "enterprise" )+ , (0x54, "eating" , "equation" )+ , (0x55, "edict" , "equipment" )+ , (0x56, "egghead" , "escapade" )+ , (0x57, "eightball", "eskimo" )+ , (0x58, "endorse" , "everyday" )+ , (0x59, "endow" , "examine" )+ , (0x5a, "enlist" , "existence" )+ , (0x5b, "erase" , "exodus" )+ , (0x5c, "escape" , "fascinate" )+ , (0x5d, "exceed" , "filament" )+ , (0x5e, "eyeglass" , "finicky" )+ , (0x5f, "eyetooth" , "forever" )+ , (0x60, "facial" , "fortitude" )+ , (0x61, "fallout" , "frequency" )+ , (0x62, "flagpole" , "gadgetry" )+ , (0x63, "flatfoot" , "galveston" )+ , (0x64, "flytrap" , "getaway" )+ , (0x65, "fracture" , "glossary" )+ , (0x66, "framework", "gossamer" )+ , (0x67, "freedom" , "graduate" )+ , (0x68, "frighten" , "gravity" )+ , (0x69, "gazelle" , "guitarist" )+ , (0x6a, "geiger" , "hamburger" )+ , (0x6b, "glitter" , "hamilton" )+ , (0x6c, "glucose" , "handiwork" )+ , (0x6d, "goggles" , "hazardous" )+ , (0x6e, "goldfish" , "headwaters" )+ , (0x6f, "gremlin" , "hemisphere" )+ , (0x70, "guidance" , "hesitate" )+ , (0x71, "hamlet" , "hideaway" )+ , (0x72, "highchair", "holiness" )+ , (0x73, "hockey" , "hurricane" )+ , (0x74, "indoors" , "hydraulic" )+ , (0x75, "indulge" , "impartial" )+ , (0x76, "inverse" , "impetus" )+ , (0x77, "involve" , "inception" )+ , (0x78, "island" , "indigo" )+ , (0x79, "jawbone" , "inertia" )+ , (0x7a, "keyboard" , "infancy" )+ , (0x7b, "kickoff" , "inferno" )+ , (0x7c, "kiwi" , "informant" )+ , (0x7d, "klaxon" , "insincere" )+ , (0x7e, "locale" , "insurgent" )+ , (0x7f, "lockup" , "integrate" )+ , (0x80, "merit" , "intention" )+ , (0x81, "minnow" , "inventive" )+ , (0x82, "miser" , "istanbul" )+ , (0x83, "mohawk" , "jamaica" )+ , (0x84, "mural" , "jupiter" )+ , (0x85, "music" , "leprosy" )+ , (0x86, "necklace" , "letterhead" )+ , (0x87, "neptune" , "liberty" )+ , (0x88, "newborn" , "maritime" )+ , (0x89, "nightbird", "matchmaker" )+ , (0x8a, "oakland" , "maverick" )+ , (0x8b, "obtuse" , "medusa" )+ , (0x8c, "offload" , "megaton" )+ , (0x8d, "optic" , "microscope" )+ , (0x8e, "orca" , "microwave" )+ , (0x8f, "payday" , "midsummer" )+ , (0x90, "peachy" , "millionaire")+ , (0x91, "pheasant" , "miracle" )+ , (0x92, "physique" , "misnomer" )+ , (0x93, "playhouse", "molasses" )+ , (0x94, "pluto" , "molecule" )+ , (0x95, "preclude" , "montana" )+ , (0x96, "prefer" , "monument" )+ , (0x97, "preshrunk", "mosquito" )+ , (0x98, "printer" , "narrative" )+ , (0x99, "prowler" , "nebula" )+ , (0x9a, "pupil" , "newsletter" )+ , (0x9b, "puppy" , "norwegian" )+ , (0x9c, "python" , "october" )+ , (0x9d, "quadrant" , "ohio" )+ , (0x9e, "quiver" , "onlooker" )+ , (0x9f, "quota" , "opulent" )+ , (0xa0, "ragtime" , "orlando" )+ , (0xa1, "ratchet" , "outfielder" )+ , (0xa2, "rebirth" , "pacific" )+ , (0xa3, "reform" , "pandemic" )+ , (0xa4, "regain" , "pandora" )+ , (0xa5, "reindeer" , "paperweight")+ , (0xa6, "rematch" , "paragon" )+ , (0xa7, "repay" , "paragraph" )+ , (0xa8, "retouch" , "paramount" )+ , (0xa9, "revenge" , "passenger" )+ , (0xaa, "reward" , "pedigree" )+ , (0xab, "rhythm" , "pegasus" )+ , (0xac, "ribcage" , "penetrate" )+ , (0xad, "ringbolt" , "perceptive" )+ , (0xae, "robust" , "performance")+ , (0xaf, "rocker" , "pharmacy" )+ , (0xb0, "ruffled" , "phonetic" )+ , (0xb1, "sailboat" , "photograph" )+ , (0xb2, "sawdust" , "pioneer" )+ , (0xb3, "scallion" , "pocketful" )+ , (0xb4, "scenic" , "politeness" )+ , (0xb5, "scorecard", "positive" )+ , (0xb6, "scotland" , "potato" )+ , (0xb7, "seabird" , "processor" )+ , (0xb8, "select" , "provincial" )+ , (0xb9, "sentence" , "proximate" )+ , (0xba, "shadow" , "puberty" )+ , (0xbb, "shamrock" , "publisher" )+ , (0xbc, "showgirl" , "pyramid" )+ , (0xbd, "skullcap" , "quantity" )+ , (0xbe, "skydive" , "racketeer" )+ , (0xbf, "slingshot", "rebellion" )+ , (0xc0, "slowdown" , "recipe" )+ , (0xc1, "snapline" , "recover" )+ , (0xc2, "snapshot" , "repellent" )+ , (0xc3, "snowcap" , "replica" )+ , (0xc4, "snowslide", "reproduce" )+ , (0xc5, "solo" , "resistor" )+ , (0xc6, "southward", "responsive" )+ , (0xc7, "soybean" , "retraction" )+ , (0xc8, "spaniel" , "retrieval" )+ , (0xc9, "spearhead", "retrospect" )+ , (0xca, "spellbind", "revenue" )+ , (0xcb, "spheroid" , "revival" )+ , (0xcc, "spigot" , "revolver" )+ , (0xcd, "spindle" , "sandalwood" )+ , (0xce, "spyglass" , "sardonic" )+ , (0xcf, "stagehand", "saturday" )+ , (0xd0, "stagnate" , "savagery" )+ , (0xd1, "stairway" , "scavenger" )+ , (0xd2, "standard" , "sensation" )+ , (0xd3, "stapler" , "sociable" )+ , (0xd4, "steamship", "souvenir" )+ , (0xd5, "sterling" , "specialist" )+ , (0xd6, "stockman" , "speculate" )+ , (0xd7, "stopwatch", "stethoscope")+ , (0xd8, "stormy" , "stupendous" )+ , (0xd9, "sugar" , "supportive" )+ , (0xda, "surmount" , "surrender" )+ , (0xdb, "suspense" , "suspicious" )+ , (0xdc, "sweatband", "sympathy" )+ , (0xdd, "swelter" , "tambourine" )+ , (0xde, "tactics" , "telephone" )+ , (0xdf, "talon" , "therapist" )+ , (0xe0, "tapeworm" , "tobacco" )+ , (0xe1, "tempest" , "tolerance" )+ , (0xe2, "tiger" , "tomorrow" )+ , (0xe3, "tissue" , "torpedo" )+ , (0xe4, "tonic" , "tradition" )+ , (0xe5, "topmost" , "travesty" )+ , (0xe6, "tracker" , "trombonist" )+ , (0xe7, "transit" , "truncated" )+ , (0xe8, "trauma" , "typewriter" )+ , (0xe9, "treadmill", "ultimate" )+ , (0xea, "trojan" , "undaunted" )+ , (0xeb, "trouble" , "underfoot" )+ , (0xec, "tumor" , "unicorn" )+ , (0xed, "tunnel" , "unify" )+ , (0xee, "tycoon" , "universe" )+ , (0xef, "uncut" , "unravel" )+ , (0xf0, "unearth" , "upcoming" )+ , (0xf1, "unwind" , "vacancy" )+ , (0xf2, "uproot" , "vagabond" )+ , (0xf3, "upset" , "vertigo" )+ , (0xf4, "upshot" , "virginia" )+ , (0xf5, "vapor" , "visitor" )+ , (0xf6, "village" , "vocalist" )+ , (0xf7, "virus" , "voyager" )+ , (0xf8, "vulcan" , "warranty" )+ , (0xf9, "waffle" , "waterloo" )+ , (0xfa, "wallet" , "whimsical" )+ , (0xfb, "watchword", "wichita" )+ , (0xfc, "wayside" , "wilmington" )+ , (0xfd, "willow" , "wyoming" )+ , (0xfe, "woodlark" , "yesteryear" )+ , (0xff, "zulu" , "yucatan" )+ ]
+ test/Doctest.hs view
@@ -0,0 +1,6 @@+module Main (main) where++import Test.DocTest++main :: IO ()+main = doctest ["src"]
test/Main.hs view
@@ -1,3 +1,4 @@+{-# LANGUAGE NumDecimals #-} {-# LANGUAGE OverloadedStrings #-} {-# LANGUAGE ParallelListComp #-} @@ -5,17 +6,18 @@ -import Data.Text.PgpWordlist.Internal.Convert-+import Control.DeepSeq import qualified Data.ByteString.Lazy as BSL import Test.Tasty import qualified Test.Tasty.HUnit as HU import qualified Test.Tasty.QuickCheck as QC import Text.Printf-import Data.Word +import Data.Text.PgpWordlist.Internal.Convert+import Data.Text.PgpWordlist.Internal.Types + main :: IO () main = defaultMain tree @@ -31,83 +33,79 @@ allBytesConvertible :: TestTree-allBytesConvertible = testGroup "All bytes have a corresponding word" tests+allBytesConvertible = HU.testCase description test where- tests = splice (map evenTest allWord8) (map oddTest allWord8)- allWord8 = [minBound ..] :: [Word8]- evenTest = testExists "%02x is convertible to an even word" toEvenWord- oddTest = testExists "%02x is convertible to an odd word" toOddWord- testExists msg f i = HU.testCase (printf msg i) (exists (f i))- exists x = HU.assertBool "" (x `seq` True)-- -- Combine two lists alternatingly- -- splice [1,3,5] [2,4,6,8,10] ==> [1,2,3,4,5,6,7,10]- splice [] ys = ys- splice (x:xs) ys = x : splice ys xs+ description = "All bytes have a corresponding even/odd word"+ assertNoBottoms x = x `deepseq` HU.assertBool "" True+ test = assertNoBottoms (do+ byte <- [minBound ..]+ convert <- [unEvenWord . toEvenWord, unOddWord . toOddWord]+ return $! convert byte ) examplesBackAndForth :: TestTree-examplesBackAndForth = testGroup "Conversion beween various examples" tests+examplesBackAndForth = testGroup "Explicit example conversions" tests where tests = concat- [ [ HU.testCase (printf "#%2d: Bytes to PGP words" i)+ [ [ HU.testCase (printf "#%d: Bytes to PGP words" i) (HU.assertEqual "" (toText bytes) pgpWords)- , HU.testCase (printf "#%2d: PGP words to bytes" i)+ , HU.testCase (printf "#%d: PGP words to bytes" i) (HU.assertEqual "" (Right bytes) (fromText pgpWords)) ] | (bytes, pgpWords) <- testCases | i <- [0..] :: [Int] ] - testCases = map (\(x,y) -> (BSL.pack x, y))- [ ( [0xce, 0xe7, 0x1c, 0xbf, 0xe6, 0x59, 0x49, 0x48]- , "spyglass truncated befriend rebellion tracker examine deckhand dictator"- )- , ( [0x06, 0x7a, 0xd2, 0xfc, 0xb7, 0x74, 0x48, 0x18]- , "afflict infancy standard wilmington seabird hydraulic deadbolt borderline"- )- , ( [0xb3, 0xc6, 0x75, 0x64, 0xa7, 0x9e, 0x0a, 0xbb]- , "scallion responsive indulge getaway repay onlooker allow publisher"- )- , ( [0x84, 0x98, 0xd3, 0x33, 0xf1, 0xe4, 0x2a, 0x92]- , "mural narrative stapler concurrent unwind tradition brickyard misnomer"- )- , ( [0xb2, 0x8d, 0x47, 0xf8, 0x8c, 0x57, 0xb5, 0x09]- , "sawdust microscope dashboard warranty offload eskimo scorecard applicant"- )- , ( [0x2e, 0x26, 0xf1, 0x24, 0x65, 0xb9, 0xae, 0xd7]- , "buzzard caretaker unwind capricorn fracture proximate robust stethoscope"- )- , ( [0x72, 0x19, 0x07, 0xf2, 0xca, 0x6f, 0xe4, 0xee]- , "highchair bottomless ahead vagabond spellbind hemisphere tonic universe"- )- , ( [0x52, 0x8f, 0x47, 0x3a, 0xbd, 0xf3, 0x64, 0x5b]- , "dupont midsummer dashboard corrosion skullcap vertigo flytrap exodus"- )- , ( [0xe9, 0x75, 0x73, 0x8c, 0x03, 0xc1, 0x49, 0x7f]- , "treadmill impartial hockey megaton acme recover deckhand integrate"+ first f (a,b) = (f a, b) -- Bifunctor came into Base in 7.10 only++ testCases = map (first BSL.pack)+ [ ( [ 0xce, 0xe7, 0x1c, 0xbf, 0xe6, 0x59, 0x49, 0x48+ , 0x06, 0x7a, 0xd2, 0xfc, 0xb7, 0x74, 0x48, 0x18 ]+ , "spyglass truncated befriend rebellion tracker examine deckhand \+ \dictator afflict infancy standard wilmington seabird hydraulic \+ \deadbolt borderline" )- , ( [0xfd, 0xce, 0xd3, 0x8f, 0xfa, 0x3d, 0xd8, 0xf2]- , "willow sardonic stapler midsummer wallet crucifix stormy vagabond"+ , ( [ 0xb3, 0xc6, 0x75, 0x64, 0xa7, 0x9e, 0x0a, 0xbb+ , 0x84, 0x98, 0xd3, 0x33, 0xf1, 0xe4, 0x2a, 0x92 ]+ , "scallion responsive indulge getaway repay onlooker allow \+ \publisher mural narrative stapler concurrent unwind tradition \+ \brickyard misnomer" )- , ( [0x2d, 0x56, 0x8c, 0x11, 0x95, 0x47, 0x4f, 0x6f]- , "button escapade offload babylon preclude determine dropper hemisphere"+ , ( [ 0xb2, 0x8d, 0x47, 0xf8, 0x8c, 0x57, 0xb5, 0x09+ , 0x2e, 0x26, 0xf1, 0x24, 0x65, 0xb9, 0xae, 0xd7 ]+ , "sawdust microscope dashboard warranty offload eskimo scorecard \+ \applicant buzzard caretaker unwind capricorn fracture proximate \+ \robust stethoscope" )- , ( [0xe4, 0x05, 0x46, 0xfe, 0xc9, 0xf4, 0x41, 0x9a]- , "tonic almighty cubic yesteryear spearhead virginia cranky newsletter"+ , ( [ 0x72, 0x19, 0x07, 0xf2, 0xca, 0x6f, 0xe4, 0xee+ , 0x52, 0x8f, 0x47, 0x3a, 0xbd, 0xf3, 0x64, 0x5b ]+ , "highchair bottomless ahead vagabond spellbind hemisphere tonic \+ \universe dupont midsummer dashboard corrosion skullcap vertigo \+ \flytrap exodus" )- , ( [0xb2, 0x68, 0xfc, 0xe4, 0x2c, 0xf5, 0xe5, 0x04]- , "sawdust gravity wayside tradition burbank visitor topmost alkali"+ , ( [ 0xe9, 0x75, 0x73, 0x8c, 0x03, 0xc1, 0x49, 0x7f+ , 0xfd, 0xce, 0xd3, 0x8f, 0xfa, 0x3d, 0xd8, 0xf2 ]+ , "treadmill impartial hockey megaton acme recover deckhand \+ \integrate willow sardonic stapler midsummer wallet crucifix \+ \stormy vagabond" )- , ( [0xb4, 0xfb, 0xec, 0xe3, 0xc8, 0xe4, 0x29, 0xa5]- , "scenic wichita tumor torpedo spaniel tradition breakup paperweight"+ , ( [ 0x2d, 0x56, 0x8c, 0x11, 0x95, 0x47, 0x4f, 0x6f+ , 0xe4, 0x05, 0x46, 0xfe, 0xc9, 0xf4, 0x41, 0x9a ]+ , "button escapade offload babylon preclude determine dropper \+ \hemisphere tonic almighty cubic yesteryear spearhead virginia \+ \cranky newsletter" )- , ( [0xbb, 0x96, 0x68, 0xc6, 0x33, 0x11, 0x4f, 0x7c]- , "shamrock monument frighten responsive chisel babylon dropper informant"+ , ( [ 0xb2, 0x68, 0xfc, 0xe4, 0x2c, 0xf5, 0xe5, 0x04+ , 0xb4, 0xfb, 0xec, 0xe3, 0xc8, 0xe4, 0x29, 0xa5 ]+ , "sawdust gravity wayside tradition burbank visitor topmost alkali \+ \scenic wichita tumor torpedo spaniel tradition breakup paperweight" )- , ( [0x51, 0x5e, 0x7f, 0xe3, 0x1b, 0xc0, 0x6f, 0xc7]- , "drunken finicky lockup torpedo beeswax recipe gremlin retraction"+ , ( [ 0xbb, 0x96, 0x68, 0xc6, 0x33, 0x11, 0x4f, 0x7c+ , 0x51, 0x5e, 0x7f, 0xe3, 0x1b, 0xc0, 0x6f, 0xc7 ]+ , "shamrock monument frighten responsive chisel babylon dropper \+ \informant drunken finicky lockup torpedo beeswax recipe gremlin \+ \retraction" ) ] @@ -115,6 +113,7 @@ randomRoundtrips = makeGroup tests where makeGroup = localOption (QC.QuickCheckMaxSize 1024)+ . localOption (QC.QuickCheckTests 1e3) . testGroup "Random roundtrips" tests = [ QC.testProperty "Bytes -> PGP words -> Bytes" $ \bytes -> let bs = BSL.pack bytes