# HW 18 - Spring 2024 # OK to post. Pablo Blanco. MakeCubic:=proc(L,n): if nops(L)<>20 then RETURN(FAIL): fi: BinToIn([op(1..5,L)]) + BinToIn([op(6..10,L)])*n+BinToIn([op(11..15,L)])*n^2+BinToIn([op(16..20,L)])*n^3: end: EncodeDES:=proc(M,K,r) local i, pol, M1: if nops(M) mod 2<>0 or nops(K)<>20*r then RETURN(FAIL): fi: M1:=M: for i from 0 to r-1 do: pol:=n->MakeCubic([op(1+(i)..20+i,K)],n): M1:=Feistel(M1,pol): od: M1: end: DecodeDES:= proc(M,K,r) local i, pol, M1: if nops(M) mod 2<>0 or nops(K)<>20*r then RETURN(FAIL): fi: M1:=M: for i from 0 to r-1 do: pol:=n->MakeCubic([op(1+(r-1-i)..20+(r-1-i),K)],n): M1:=revFeistel(M1,pol): od: M1: end: ##################################################################################################################### #C18.txt, March 25, 2024 Help:=proc(): print(` RW(k), BinToIn(L) , InToBin(n,k), BinFun(F,L) , Feistel(LR,F)`): print(`revFeistel(LR,F)`): end: #RW(k): a random binary word of length k RW:=proc(k) local ra,i: ra:=rand(0..1): [seq(ra(),i=1..k)]: end: #BinToIn(L): inputs a binary word L and outputs the integer n whose binary representation #it is BinToIn:=proc(L) local k,i: k:=nops(L): #[1,0,1]: 1*2^2+0*2^1+1*2^0 add(L[i]*2^(k-i) , i=1..k): end: #InToBin(n,k): inputs a non-neg. integer n<2^k into its binary representation with #0's in front if neccessary so that it is of length k InToBin:=proc(n,k) local i: #option remember: if ( n>=2^k or n<0) or not (type(n,integer)) then RETURN(FAIL): fi: if k=1 then if n=0 then RETURN([0]): else RETURN([1]): fi: fi: if n<2^(k-1) then RETURN([0,op(InToBin(n,k-1))]): else RETURN([1,op(InToBin(n-2^(k-1),k-1))]): fi: end: #BinFun(F,L): conmverts a function on the integers (mod 2^k) to a function #on binary words BinFun:=proc(F,L) local k: k:=nops(L): InToBin(F(BinToIn(L)) mod 2^k,k): end: #Feistel(LR,F): The Feistel transform that takes [L,R]->[R+F(L) mod 2, L] #For example Feistel([1,1,0,1],n->n^5+n); Feistel:=proc(LR,F) local k,L,R: k:=nops(LR): if k mod 2<>0 then RETURN(FAIL): fi: L:=[op(1..k/2,LR)]: R:=[op(k/2+1..k,LR)]: [op(R+ BinFun(F,L) mod 2) , op(L) ]: end: #revFeistel(LR,F): The reverse Feistel transform that takes [L,R]->[R,L+F(R)] #For example Feistel([1,1,0,1],n->n^5+n); revFeistel:=proc(LR,F) local k,L,R: k:=nops(LR): if k mod 2<>0 then RETURN(FAIL): fi: L:=[op(1..k/2,LR)]: R:=[op(k/2+1..k,LR)]: [op(R), op(L+ BinFun(F,R ) mod 2) ]: end: