Bitcoin/address validation: Difference between revisions
Content added Content deleted
m (minor tidy) |
(Update Seed7 example) |
||
Line 1,970: | Line 1,970: | ||
=={{header|Seed7}}== |
=={{header|Seed7}}== |
||
The Seed7 library [http://seed7.sourceforge.net/libraries/encoding.htm encoding.s7i] defines |
|||
the function [http://seed7.sourceforge.net/libraries/encoding.htm#fromBase58(in_string) fromBase58], |
|||
which decodes a Base58 encoded string. |
|||
The Seed7 library [http://seed7.sourceforge.net/libraries/msgdigest.htm msgdigest.s7i] defines |
The Seed7 library [http://seed7.sourceforge.net/libraries/msgdigest.htm msgdigest.s7i] defines |
||
the function [http://seed7.sourceforge.net/libraries/msgdigest.htm#sha256(in_var_string) sha256] |
the function [http://seed7.sourceforge.net/libraries/msgdigest.htm#sha256(in_var_string) sha256], |
||
which computes a SHA-256 message digest. |
|||
No external library is needed. |
No external library is needed. |
||
<lang seed7>$ include "seed7_05.s7i"; |
<lang seed7>$ include "seed7_05.s7i"; |
||
include "msgdigest.s7i"; |
include "msgdigest.s7i"; |
||
include "encoding.s7i"; |
|||
const |
const proc: assertBitcoin (in string: stri, in string: expected) is func |
||
result |
|||
var string: state is ""; |
|||
local |
local |
||
var string: decoded is ""; |
|||
var |
var string: state is "okay"; |
||
var integer: digit is 0; |
|||
var integer: index is 0; |
|||
begin |
begin |
||
if not succeeds(decoded := fromBase58(stri)) then |
|||
for ch range stri until state <> "" do |
|||
state := "bad char"; |
|||
elsif length(decoded) <> 25 then |
|||
state := "wrong length"; |
|||
⚫ | |||
else |
|||
state := "not version 0"; |
|||
⚫ | |||
digit +:= 58 * ord(out[index]); |
|||
out @:= [index] char(digit rem 256); |
|||
digit := digit div 256; |
|||
⚫ | |||
⚫ | |||
state := "address too long"; |
|||
end if; |
|||
end if; |
|||
end for; |
|||
end func; |
|||
const func string: valid (in string: stri) is func |
|||
result |
|||
var string: state is ""; |
|||
local |
|||
var string: decoded is "\0;" mult 25; |
|||
begin |
|||
state := unbase58(stri, decoded); |
|||
⚫ | |||
state := "bad digest"; |
state := "bad digest"; |
||
⚫ | |||
⚫ | |||
⚫ | |||
⚫ | |||
writeln(" *** Expected " <& literal(expected) <& " for " <& stri <& ", but got " <& literal(state) <& "."); |
|||
end if; |
end if; |
||
end func; |
end func; |
||
const proc: main is func |
const proc: main is func |
||
local |
|||
⚫ | |||
"1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i", |
|||
"1Q1pE5vPGEEMqRcVRMbtBK842Y6Pzo6nJ9", |
|||
"1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62I"); |
|||
var string: test is ""; |
|||
var string: state is ""; |
|||
begin |
begin |
||
⚫ | |||
for test range tests do |
|||
⚫ | |||
state := valid(test); |
|||
⚫ | |||
⚫ | |||
assertBitcoin("1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62j", "bad digest"); |
|||
⚫ | |||
assertBitcoin("1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62X", "bad digest"); |
|||
else |
|||
assertBitcoin("1ANNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i", "bad digest"); |
|||
⚫ | |||
assertBitcoin("oMRDCDfyQhEerkaSmwCfSPqf3MLgBwNvs", "not version 0"); |
|||
end if; |
|||
assertBitcoin("1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62iz", "wrong length"); |
|||
end for; |
|||
assertBitcoin("1BGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i", "bad digest"); |
|||
assertBitcoin("1A Na15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i", "bad char"); |
|||
⚫ | |||
assertBitcoin("1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62!", "bad char"); |
|||
assertBitcoin("1AGNa15ZQXAZUgFiqJ3i7Z2DPU2J6hW62i", "bad digest"); |
|||
assertBitcoin("1111111111111111111114oLvT2", "okay"); |
|||
assertBitcoin("17NdbrSGoUotzeGCcMMCqnFkEvLymoou9j", "okay"); |
|||
assertBitcoin("1badbadbadbadbadbadbadbadbadbadbad", "wrong length"); |
|||
assertBitcoin("BZbvjr", "wrong length"); |
|||
assertBitcoin("i55j", "wrong length"); |
|||
assertBitcoin("16UwLL9Risc3QfPqBUvKofHmBQ7wMtjvM", "okay"); |
|||
end func;</lang> |
end func;</lang> |
||
{{out}} |
{{out}} |
||
<pre> |
<pre> |
||
1Q1pE5vPGEEMqRcVRMbtBK842Y6Pzo6nK9: okay |
1Q1pE5vPGEEMqRcVRMbtBK842Y6Pzo6nK9: okay |
||
1Q1pE5vPGEEMqRcVRMbtBK842Y6Pzo6nJ9: bad digest |
|||
⚫ | |||
1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i: okay |
|||
⚫ | |||
1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62j: bad digest |
|||
⚫ | |||
1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62X: bad digest |
|||
1ANNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i: bad digest |
|||
oMRDCDfyQhEerkaSmwCfSPqf3MLgBwNvs: not version 0 |
|||
1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62iz: wrong length |
|||
1BGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i: bad digest |
|||
1A Na15ZQXAZUgFiqJ2i7Z2DPU2J6hW62i: bad char |
|||
1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62I: bad char |
|||
1AGNa15ZQXAZUgFiqJ2i7Z2DPU2J6hW62!: bad char |
|||
1AGNa15ZQXAZUgFiqJ3i7Z2DPU2J6hW62i: bad digest |
|||
1111111111111111111114oLvT2: okay |
|||
17NdbrSGoUotzeGCcMMCqnFkEvLymoou9j: okay |
|||
1badbadbadbadbadbadbadbadbadbadbad: wrong length |
|||
BZbvjr: wrong length |
|||
i55j: wrong length |
|||
16UwLL9Risc3QfPqBUvKofHmBQ7wMtjvM: okay |
|||
</pre> |
</pre> |
||