dataprop MUL1 (int, int, int) =
| {n:int}
MUL1bas (0, n, 0)
| {m,n,p:int | m >= 0}
MUL1ind (m+1, n, p+n) of MUL1 (m, n, p)
| {m,n,p:int | m > 0}
MUL1neg (~m, n, ~p) of MUL1 (m, n, p)
prfun lemma00 {m:nat} {x:int} .<m>. (pf: MUL1 (m, 0, x)): [x == 0] void =
sif m > 0 then begin
let prval MUL1ind pf1 = pf in lemma00 pf1 end
end else begin
let prval MUL1bas () = pf in () end
end
prfun lemma01 {m,n:nat} {x:int} .<m>. (pf: MUL1 (m, n, x))
: MUL1 (m, n-1, x-m) =
sif m > 0 then begin
let prval MUL1ind pf1 = pf in MUL1ind (lemma01 pf1) end
end else begin
let prval MUL1bas () = pf in MUL1bas () end
end
prfun lemma_commute {m,n:nat} {x:int} .<n>. (pf: MUL1 (m, n, x))
:<prf> MUL1 (n, m, x) =
sif n > 0 then begin
let prval pf1 = lemma01 (pf) in
MUL1ind (lemma_commute {m,n-1} (pf1))
end
end else begin
let prval () = lemma00 (pf) in MUL1bas () end
end
prfun lemma1 {p:nat} {x:int} .<p>.
(pf: MUL1 (p+p, p+p, x)):<prf> [x4:int | x == 4*x4] MUL1 (p, p, x4) =
sif p > 0 then let
prval MUL1ind pf1 = pf
prval MUL1ind pf2 = pf1
prval pf2' = lemma_commute {p+p-2,p+p} (pf2)
prval MUL1ind pf21' = pf2'
prval MUL1ind pf22' = pf21'
prval [x41:int] pf_1 = lemma1 {p-1} {x-8*p+4} (pf22')
prval pf_2 = MUL1ind (pf_1)
prval pf_3 = lemma_commute (pf_2)
prval pf_4 = MUL1ind (pf_3)
in
#[x41+2*p-1 | pf_4]
end else let
prval MUL1bas () = pf
in
#[0 | pf]
end
prfun lemma2 {p:nat} {x:int} .<p>.
(pf: MUL1 (p, p, x+x)):<prf> [p2:int | p == 2*p2] void =
sif p >= 2 then let
prval MUL1ind pf1 = pf
prval MUL1ind pf2 = pf1
prval pf2' = lemma_commute {p-2,p} (pf2)
prval MUL1ind pf21' = pf2'
prval MUL1ind pf22' = pf21'
prval [p21:int] () = lemma2 {p-2}{x-2*p+2} (pf22')
in
#[p21+1 | ()]
end else sif p == 1 then let
prval MUL1ind pf1 = pf
prval MUL1bas () = pf1
in
#[0 | ()] end else let
prval MUL1bas () = pf
in
#[0 | ()]
end
prfun lemma_main {p,q:nat} {x:int} .<p>.
(pf1: MUL1 (p, p, x), pf2: MUL1 (q, q, x+x)): [x == 0] void =
sif p > 0 then let
prval [q2:int] () = lemma2 {q} {x} (pf2) prval [x2:int] pf2' = lemma1 {q2} {x+x} (pf2) prval [p2:int] () = lemma2 {p} {x2} (pf1) prval [x4:int] pf1' = lemma1 {p2} {x2+x2} (pf1) in
lemma_main {p2,q2} {x4} (pf1', pf2')
end else begin
let prval MUL1bas () = pf1 in () end
end