{VERSION 3 0 "IBM INTEL LINUX" "3.0" } {USTYLETAB {CSTYLE "Maple Input" -1 0 "Courier" 0 1 255 0 0 1 0 1 0 0 1 0 0 0 0 }{CSTYLE "2D Math" -1 2 "Times" 0 1 0 0 0 0 0 0 2 0 0 0 0 0 0 }{CSTYLE "2D Output" 2 20 "" 0 1 0 0 255 1 0 0 0 0 0 0 0 0 0 } {PSTYLE "Normal" -1 0 1 {CSTYLE "" -1 -1 "" 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 }0 0 0 -1 -1 -1 0 0 0 0 0 0 -1 0 }{PSTYLE "Heading 1" 0 3 1 {CSTYLE "" -1 -1 "" 1 18 0 0 0 0 0 1 0 0 0 0 0 0 0 }1 0 0 0 8 4 0 0 0 0 0 0 -1 0 }{PSTYLE "Maple Output" 0 11 1 {CSTYLE "" -1 -1 "" 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 }3 3 0 -1 -1 -1 0 0 0 0 0 0 -1 0 }{PSTYLE "" 11 12 1 {CSTYLE "" -1 -1 "" 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 }1 0 0 -1 -1 -1 0 0 0 0 0 0 -1 0 }} {SECT 0 {SECT 0 {PARA 3 "" 0 "" {TEXT -1 165 " Vigenere Programs \n(Do n't read; just open it up by clicking the button, place the cursor on the first line, and press enter. Then close it by clicking the button .)" }}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 9346 "with(linalg): with(s tats): with(plots): with(plottools):\n\n# s is a string of letters and other symbols.\n# numbers returns the vector of numbers corresponding to the \n# letters, ignoring case and the other symbols.\nnumbers:= proc(s)\n local alph,v,n,m,i,c;\n alph:=`abcdefghijklmno pqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ`;\n n:=length(s);\n \+ v:=[];\n for i from 1 to n do\n c:=substring(s,i ..i);\n m:=searchtext(c,alph);\n if m > 0 th en\n v:=[op(v), (m -1 mod 26) + 1] fi;\n od;\n \+ RETURN(v)\nend:\n\n# letters converts a vector of numbers to a \+ \n# string of uppercase letters\nletters:=proc(v)\n local alph,i,m sg;\n alph:=`ABCDEFGHIJKLMNOPQRSTUVWXYZ`;\n msg:=``;\n for i fro m 1 to nops(v) do\n msg:=cat(msg,substring(alph,v[i]..v[i]) );\n od;\n RETURN(msg);\nend:\n\n# upcase converts a string to a stand ard one of only uppercase letters\nupcase:=w->letters(numbers(w)):\n\n vigen_enc:=proc(plaintext,keyword)\n local v, k, l, w, i;\n v:=n umbers(plaintext);\n k:=numbers(keyword);\n l:=nops(k);\n w:= [seq( (v[i]+k[ (i-1 mod l) +1]-2 mod 26) +1, \n \+ i=1..nops(v) )];\n RETURN(letters(w))\nend:\n\nvige n_dec:=proc(ciphertext,keyword)\n local v, k, l, w, i;\n v:=numb ers(ciphertext);\n k:=numbers(keyword);\n l:=nops(k);\n w:=[s eq( (v[i]-k[ (i-1 mod l) +1] mod 26) +1, \n \+ i=1..nops(v) )];\n RETURN(letters(w))\nend:\n\nindex_of _coincidence:=proc(ciphertext)\n local v,x,n,u,ans;\n v:=numbers(c iphertext);\n n:=nops(v);\n u:=[seq( nops(select(has,v,x)), x=1..2 6 )];\n ans:=(evalm(u &* u)-n)/(n*(n-1));\n RETURN( evalf(ans) ); \+ \nend:\n\n# Friedman's formula for the guess for the length of the key word\nfriedman:=proc(ciphertext)\n local k,n,v;\n v:=numbers(ciphe rtext);\n n:=nops(v);\n k:=index_of_coincidence(ciphertext);\n R ETURN( 0.027*n/( (n-1)*k -0.038*n +0.065) );\nend:\n\nfriedman2:=proc( ciphertext)\n local k;\n k:=index_of_coincidence(ciphertext);\n \+ RETURN( 0.027/( k -0.038) );\nend:\n\nnumfreq:=proc(msg)\n local v; \n v:=numbers(msg);\n RETURN([seq( nops(select(has,v,x)), x=1..26 \+ )]);\nend:\n\n# Frequencies of letters in msg\nfreq:=proc(msg)\n loc al alph,v,ans,x;\n alph:=`ABCDEFGHIJKLMNOPQRSTUVWXYZ`;\n v:=numfre q(msg);\n RETURN( evalm(transpose(\n [seq( [substring(alph,x. .x),v[x]] , x=1..26)] )) );\nend:\n\n# Frequencies of letters in subse quence of letters at\n# positions k[1]*x +k[2] (k must be a list .)\nsubfreq:=proc(s,k::list)\n local v,n,u,w,x;\n v:=numbers(s);\n n:=nops(v);\n u:=[seq( v[k[1]*x+k[2]], x=0..floor( (n-k[2])/k[1] \+ ) )];\n w:=letters(u);\n RETURN( freq(w) );\nend:\n\n# Reads in a \+ message from a file\nreadin:=proc(filename)\n local fd,q,ans,s;\n \+ fd:=fopen(filename,READ,TEXT);\n q:=fscanf(fd,`%s`);\n ans:=``;\n \+ while q<>0 do\n s:=upcase(op(q));\n ans:=cat(ans,s);\n \+ q:=fscanf(fd,`%s`);\n od;\n fclose(fd);\n RETURN(ans);\nend:\n \n# Letter frequencies sorted from high to low.\nsortfreq:=proc(msg)\n local alph,v,ans,x;\n alph:=`ABCDEFGHIJKLMNOPQRSTUVWXYZ`;\n v:= sort(numbers(msg));\n ans:=[];\n for x from 1 to 26 do\n a ns:=[op(ans), [substring(alph,x..x) , nops(select(has,v,x))] ];\n od ;\n ans:=sort(ans,(x,y)->evalb(x[2]>y[2]));\n RETURN(evalm(transpo se(ans)));\nend:\n\n# Highest frequency letter in subsequence\ntopfreq :=proc(s,k)\n local v,n,u,w,x;\n v:=numbers(s);\n n:=nops(v);\n \+ u:=[seq( v[k[1]*x+k[2]], x=0..floor( (n-k[2])/k[1] ) )];\n w:=lett ers(u);\n RETURN( col(sortfreq(w),1) );\nend:\n\n# Guess the keyword based on length n and highest frequency letters.\nguesskey:=proc(s,n) \n local i, ans,u,v,m,w;\n ans:=``;\n v:=[];\n for i from 1 to n do\n u:=topfreq(s,[n,i]);\n m:=numbers(u[1]);\n v:=[ op(v),m[1]];\n od;\n w:=map(x-> ( x-5 mod 26) + 1, v);\n RETURN( letters(w));\nend:\n\n# Extract the letters in a subsequence\nsubtext: =proc(s,k)\n local v,n,u,x;\n v:=numbers(s);\n n:=nops(v);\n u :=[seq( v[k[1]*x+k[2]], x=0..floor( (n-k[2])/k[1] ) )];\n RETURN( le tters(u) );\nend:\n\n# Extract a range of subsequences.\n# k[2] sho uld be a range i..j\nsubtexts:=proc(s,k)\n local v,n,u,x,j,l;\n v: =numbers(s);\n n:=nops(v);\n u:=[seq( seq(v[k[1]*x+j],j=k[2]) \n \+ , x=0..floor( (n-max(seq(l,l=k[2])))/k[1] ) )];\n RETURN( \+ letters(u) );\nend:\n\n# Friedman guesses of subtexts\nsub_friedman:=p roc(msg,l)\n local v,x;\n v:=[seq(friedman(subtext(msg,[l,x])),x =1..l)];\n RETURN(evalf(v,3),describe[mean](evalf(v,3)))\nend:\n\n# Collect the message into blocks of length l, b per line\nwordgroups:= proc(w,l,b)\n local n,ans,i,m,j;\n n:=length(w);\n ans:=`\\n` ;\n j:=1;\n for i from 1 to n by l do\n m:=min(i+l-1,n);\n ans:=cat(ans,` `,substring(w,i..m));\n if j=b then \n \+ ans:=cat(ans,`\\n`);\n j:=0;\n fi;\n j:=j+1 ;\n od;\n RETURN(ans)\nend:\n\n# Frequency chart of subtexts\nto pten:=proc(msg,l)\n local i,v,m,ans;\n ans:=[];\n for i from 1 t o l do\n v:=blockfreqsort(subtext(msg,[l,i]),1);\n m:=min(no ps(v),10);\n ans:=[op(ans),v[1..m]];\n od;\n RETURN( op(ans) \+ );\nend:\n\ncaesar:=(plaintext,key)->\n letters( map( (i,k)-> (i-1+ k mod 26)+1 , numbers(plaintext), key)):\n\ntryall:= w ->\n matrix( [[seq( caesar(w,k), k=1..13)],[seq( caesar(w,k), k=14..26)]]):\n\n# Gi ve possible choices for keyletters\n# l = suspected length of keywor d\n# n = minimum frequency\nkeyletters:=proc(msg,l,n)\n local ans, i,x,y,v,w,u;\n ans:=[];\n for i from 1 to l do\n v:=blockfreq sort(subtext(msg,[l,i]),1);\n w:=select( (x,y)->evalb(x[2]>=y), v , n);\n u:=cat(op(map(x->x[1],w)));\n ans:=[op(ans),caesar(u ,-4)];\n od;\n RETURN(ans)\nend:\n\n# Generate a list of keys:\n# \+ v is a list of suffixes for all keys.\n# w is a list of selections for the letters \n# for the prefixes of the keys.\nkeylist:=proc(v,w)\n \+ local l,x,y,ans,u;\n l:=nops(w);\n ans:=v;\n for x from l to 1 \+ by -1 do\n### WARNING: semantics of type `string` have changed\n \+ u:=convert(w[x],string);\n ans:= [seq( \n op(map( (x,y)-> cat(``,y,x),ans,substring(u,y..y) )),\n y=1..length(u) )]; \n od;\n RETURN(ans);\nend:\n\n# Find all occurrences of s in msg. \n# Return the indices in a vector.\nfindstring:=proc(msg,s)\n local l,n,v,i,ans,x;\n l:=length(s);\n n:=length(msg);\n v:=[seq(subs tring(msg,i..(i+l-1)),i=1..(n-l+1))];\n ans:=[];\n for x from 1 to n-l+1 do\n if v[x] = s then ans:=[op(ans),x] fi;\n od;\n RE TURN(ans)\nend:\n\n# Plotting procedures\n\nbarchart:=proc(msg)\n l ocal v, pl, x;\n v:=freq(upcase(msg));\n pl:=seq(\n rectan gle( [x-0.25,v[2,x]],[x+0.25,0],color=blue),\n x=1..26):\n \+ display(pl)\nend:\n\nbasefreq:=[[`A`,`B`,`C`,`D`,`E`,`F`,`G`,`H`,`I`,` J`,`K`,`L`,`M`,\n `N`,`O`,`P`,`Q`,`R`,`S`,`T`,`U`,`V`,`W`,`X`, `Y`,`Z`],\n [8.167,1.492,2.782,4.253,12.702,2.228,2.015,6.094,6.96 6,0.153,0.772,4.025,\n 2.406,6.749,7.507,1.929,0.095,5.987,6.327, 9.056,2.758,0.978,2.360,0.150,\n 1.974,0.074]]:\n\nbasechart:=dis play( seq(\n rectangle( [x-0.25,basefreq[2,x]],[x+0.25,0],color= blue),\n x=1..26) ):\n\nalignalpha:=proc(ciphertext,key)\n \+ global basechart;\n local msg,l,x;\n msg:=vigen_dec(ciphertext,k ey);\n l:=length(key);\n display( array([[basechart], \n \+ seq( [barchart(subtext(msg,[l,x]))],x=1..l)]) );\nend:\n\nblockfr eq:=proc(s,m)\n local v,n,i,ans,block,x,y;\n n:=length(s);\n \+ v:=sort([seq(substring(s,i..(i+m-1)),i=1..(n-m+1))]);\n ans:=[];\n \+ block:=v[1];\n y:=1;\n for x from 2 to n-m+1 do\n if v[x ] = block then\n y:=y+1;\n continue;\n else\n \+ ans:=[op(ans),[block,y]];\n block:=v[x];\n y :=1;\n fi;\n od;\n ans:=[op(ans),[block,y]];\n RETURN(an s)\nend:\n\nblockfreqsort:=proc(s,m)\n local A,x,y;\n A:=blockfr eq(s,m);\n sort( A, (x,y)->evalb(x[2]>y[2]))\nend:\n\nkasiski:=pro c(msg,l,n)\n local v,x,y,ans,u,facs,i;\n v:=select((x,y)->evalb(x[ 2]>=y), blockfreqsort(msg,l),n);\n ans:=[];\n for x from 1 to nops (v) do\n u:=findstring(msg,v[x][1]);\n facs:=[seq( ifactor(u [i+1]-u[i]), i=1..nops(u)-1 )];\n ans:=[op(ans), [v[x],facs] ];\n od;\n RETURN(ans)\nend:\n\n# Search for the highest index of coin cidence among the decipherments\n# of word by all the keys in the list \"keys\"\nkeysearch:=proc(msg,keys)\n local i,imax,ind,l,p,v,m,nums ,j,k,n,dels;\n l:=length(keys[1]);\n p:=[];\n for i from 1 to l \+ do\n v:=subtext(msg,[l,i]);\n m:=length(v);\n p:=[op(p) , convert(map((x,y)->evalf(x/y), row(freq(v),2), m),list) ];\n od;\n imax:=0.0;\n dels:=array(1..l,1..l,1..26);\n for j from 1 to l \+ do\n for k from 1 to l do\n for n from 1 to 26 do\n \+ dels[j,k,n]:= evalm( p[j] &* cycle(p[k], n));\n od; od; o d;\n for i from 1 to nops(keys) do\n nums:=numbers(keys[i]);\n \+ ind:=0;\n for j to l do for k to l do\n ind:=ind+de ls[j,k,res(nums[k]-nums[j])];\n od; od;\n ind:=ind/l^2;\n \+ if evalb(evalf(ind) > evalf(imax)) then\n print(ind,keys[ i],\n wordgroups(vigen_dec(substring(msg,1..5*l),keys[i ]),l,5));\n imax:=ind:\n fi;\n od;\nend:\n\ncycle:=pr oc(v,k)\n local n,w,j,m;\n n:=nops(v);\n w:=[];\n for j from 1 to n do\n m:=(j+k-1 mod n)+1;\n w:=[op(w),v[m]];\n od; \n RETURN(w);\nend:\n\nres:=n-> ((n-1) mod 26) + 1:" }}}}{SECT 0 {PARA 3 "" 0 "" {TEXT -1 25 " First Example Cryptogram" }}{EXCHG {PARA 0 "" 0 "" {TEXT -1 46 "Read in the cryptogram and store it in ci pher." }{TEXT -1 0 "" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 146 "ci pher:=DSJGXAQYFUSJRLQMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUY PUSPSRMGLAZGGZASMJHTCWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGF FGD;" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#>%'cipherG%dsDSJGXAQYFUSJRLQMJ WVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHTCWS DIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 27 "Number of letters in cipher" }{TEXT -1 0 "" }} {PARA 0 "> " 0 "" {MPLTEXT 1 0 15 "length(cipher);" }}{PARA 11 "" 1 " " {XPPMATH 20 "6#\"$P\"" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 46 "Friedm an's guess for the length of the keyword" }{TEXT -1 0 "" }}{PARA 0 "> \+ " 0 "" {MPLTEXT 1 0 17 "friedman(cipher);" }}{PARA 11 "" 1 "" {XPPMATH 20 "6#$\"+H/&zi$!\"*" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 73 " If the keyword has length l, all the \"subtexts\" of letters spaced l \+ apart" }}{PARA 0 "" 0 "" {TEXT -1 68 "should have Friedman guess appro ximately equal to 1. Below, we check" }}{PARA 0 "" 0 "" {TEXT -1 72 "t his out with the function sub_friedman that computes the Friedman gues s" }}{PARA 0 "" 0 "" {TEXT -1 41 "for all the subtexts for a given len gth l" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 52 "for l from 2 to 7 do\n \+ sub_friedman(cipher,l) od;" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%-sub_ friedmanG6$%dsDSJGXAQYFUSJRLQMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCP SZSJMJUYPUSPSRMGLAZGGZASMJHTCWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVW SWWBPWGFFGDG\"\"#" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%-sub_friedmanG6 $%dsDSJGXAQYFUSJRLQMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPU SPSRMGLAZGGZASMJHTCWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFG DG\"\"$" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%-sub_friedmanG6$%dsDSJGXA QYFUSJRLQMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZG GZASMJHTCWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"%" } }{PARA 12 "" 1 "" {XPPMATH 20 "6#-%-sub_friedmanG6$%dsDSJGXAQYFUSJRLQM JWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHTCW SDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"&" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%-sub_friedmanG6$%dsDSJGXAQYFUSJRLQMJWVGWJPWLX ECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHTCWSDIDWVWJIY YXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"'" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%-sub_friedmanG6$%dsDSJGXAQYFUSJRLQMJWVGWJPWLXECRLMPGQ IZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHTCWSDIDWVWJIYYXWBXGYR QMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"(" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 44 "It looks like the keyword is 3 letters long." }}{PARA 0 " " 0 "" {TEXT -1 82 "The function guesskey tries to guess it based on c orrelating the highest frequency" }}{PARA 0 "" 0 "" {TEXT -1 14 "lette r with E." }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 19 "guesskey(cipher,3);" } }{PARA 12 "" 1 "" {XPPMATH 20 "6#-%)guesskeyG6$%dsDSJGXAQYFUSJRLQMJWVG WJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHTCWSDID WVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"$" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 52 "Lets try to decode it with the guess of t he keyword." }{TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 28 "msg:= vigen_dec(cipher, YLS);" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#>%$msgG%dsF HRIMISNNWHRTAYOYEXVELEENMMEGTOEOSXHONRSEIKXSLTVELINMHEEABHROYCAECUEATB ONPHIVHCHULWBELAFXLYKELXGAMEDMOAGYOGEEESEBFMTCHBNELWEKEULEDEEIUNISG" } }}{EXCHG {PARA 0 "" 0 "" {TEXT -1 26 "Group the message into 3's" } {TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 24 "wordgroups( msg, 3, 10);" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%+wordgroupsG6%%dsFHRIMISNNW HRTAYOYEXVELEENMMEGTOEOSXHONRSEIKXSLTVELINMHEEABHROYCAECUEATBONPHIVHCH ULWBELAFXLYKELXGAMEDMOAGYOGEEESEBFMTCHBNELWEKEULEDEEIUNISG\"\"$\"#5" } }}{EXCHG {PARA 0 "" 0 "" {TEXT -1 60 "This decodes cipher with the key word YLS and then shows the " }}{PARA 0 "" 0 "" {TEXT -1 60 "bar chart s of the letter frequencies in the decoded message." }}{PARA 0 "" 0 " " {TEXT -1 78 "The top chart is the frequency distribution of English. The next three charts " }}{PARA 0 "" 0 "" {TEXT -1 23 "are the subtex ts of msg" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 23 "alignalpha(cipher,YLS) ;" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%+alignalphaG6$%dsDSJGXAQYFUSJRL QMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHT CWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG%$YLSG" }}} {EXCHG {PARA 0 "" 0 "" {TEXT -1 48 "The second alphabet looks most out of alignment." }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 54 "This produces l ists of top choices for the key letters" }}{PARA 0 "" 0 "" {TEXT -1 75 "(assuming length 3, give all shifts corresponding to letters occur ring 4 or" }}{PARA 0 "" 0 "" {TEXT -1 29 "more times in the ciphertext )" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 31 "init:=keyletters(cipher, 3, 4) ;" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#>%%initG-%+keylettersG6%%dsDSJGXA QYFUSJRLQMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZG GZASMJHTCWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"$\" \"%" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 43 "This generates a list of p ossible keywords." }}{PARA 0 "" 0 "" {TEXT -1 82 "The first list is a \+ list of known \"ends\" of keywords, which we don't know any yet." }} {PARA 0 "" 0 "" {TEXT -1 67 "The second list has the choices for the b eginnings of the keywords." }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 25 "keys: =keylist([``],init);" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#>%%keysG-%(key listG6$7#%!G-%+keylettersG6%%dsDSJGXAQYFUSJRLQMJWVGWJPWLXECRLMPGQIZMYJ QPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZASMJHTCWSDIDWVWJIYYXWBXGYRQMRWC PKCMXKEUFMFCWOCVWSWWBPWGFFGDG\"\"$\"\"%" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 69 "This does a brute force search for the keyword that gives the highest" }}{PARA 0 "" 0 "" {TEXT -1 41 "index of coincidence in t he decoded text." }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 23 "keysearch(ciphe r,keys);" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#-%*keysearchG6$%dsDSJGXAQY FUSJRLQMJWVGWJPWLXECRLMPGQIZMYJQPAIIKJENCWALXZCPSZSJMJUYPUSPSRMGLAZGGZ ASMJHTCWSDIDWVWJIYYXWBXGYRQMRWCPKCMXKEUFMFCWOCVWSWWBPWGFFGDG-%(keylist G6$7#%!G-%+keylettersG6%F&\"\"$\"\"%" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 17 "The rest is easy." }{TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 22 "vigen_dec(cipher,YES);" }}{PARA 12 "" 1 "" {XPPMATH 20 "6#%dsF ORITISUNWORTHYOFEXCELLENTMENTOLOSEHOURSLIKESLAVESINTHELABOROFCALCULATI ONWHICHCOULDBESAFELYRELEGATEDTOANYONEELSEIFMACHINESWEREUSEDLEIBNIZG" } }}}{SECT 0 {PARA 3 "" 0 "" {TEXT -1 25 "Second Example Cryptogram" }} {EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 250 "cipher:=ORRWXACKGRLWURLPKHC EBPLOPRPIVVQFQTLPGRSIROPUDGXSFFKXMWURLPBRVFRTVVPFJDZMDLRXMWUEMIIOTKMUM SEYLDECIPGIBGCYYCWACZBTGCHKFTTFVJZJMWVZQCHHHFPIAWUICPLCPRLPKHORRWXACKG RLWURLPKHDVAPNGGZRHFCFVMUWWUTMKXFARLSBHUZLCXFNZDTTFGCGZXHJFQTHTVYCPKHU DYGLHQEKDKGG;" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 15 "length(cip her);" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 29 "index_of_coinciden ce(cipher);" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 17 "friedman(cip her);" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 73 "If the keyword has leng th l, we expect all the guesses to be close to 1." }{TEXT -1 0 "" }} {PARA 0 "> " 0 "" {MPLTEXT 1 0 52 "for l from 3 to 8 do\n sub_frie dman(cipher,l) od;" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 67 "Show the bl ocks of 4 cipher letters that occur the most frequently." }{TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 31 "blockfreqsort(cipher,4)[1..10] ;" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 15 "Kasiski Testing" }{TEXT -1 41 " for the ones which occur 3 times or more" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 20 "kasiski(cipher,4,3);" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 56 "Based on the indices, we guess the keyword has length 6 " }}{PARA 0 "" 0 "" {TEXT -1 30 "(the GCD of the factors above)" }}} {EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 22 "w:=guesskey(cipher,6);" }}} {EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 25 "msg:=vigen_dec(cipher,w);" } }}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 20 "wordgroups(msg,6,8);" }}} {EXCHG {PARA 0 "" 0 "" {TEXT -1 42 "This keyword does not give good al ignment." }{TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 26 "alignalp ha(cipher,QNHLTD);" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 29 "init: =keyletters(cipher,6,4);" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 25 "keys:=keylist([``],init):" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 11 "nops(keys);" }}}{EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 23 "keysearc h(cipher,keys):" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 16 "It doesn't wor k." }{TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 32 "msg:=vigen_dec (cipher,`RGNEID`);" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 22 "Look at the alignments" }{TEXT -1 0 "" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 27 "align alpha(cipher, RGNEID);" }}}{EXCHG {PARA 0 "" 0 "" {TEXT -1 66 "Remembe r that the index would be the same under any monoalphabetic" }}{PARA 0 "" 0 "" {TEXT -1 58 "cipher. Maybe the keyword is an additive shift of RGNEID." }}{PARA 0 "" 0 "" {TEXT -1 31 "Do you see one that might \+ work?" }}{PARA 0 "> " 0 "" {MPLTEXT 1 0 15 "tryall(RGNEID);" }}} {EXCHG {PARA 0 "> " 0 "" {MPLTEXT 1 0 0 "" }}}}}{MARK "2 1 0 0" 0 } {VIEWOPTS 1 1 0 1 1 1803 }