use DAKKAR::p 'test';
use Enigmatic::Rotor;
use Enigmatic::Reflector;
use Enigmatic::RotorBox;
use Enigmatic::ReflectorBox;
use Enigmatic::CryptTrain;
subtest 'first position' => sub {
my @in = 'A'..'Z';
my @rots = map { Enigmatic::Rotor->new(@in->join) } 1..3;
my $refl = Enigmatic::Reflector->new(@in->join);
my $train = Enigmatic::CryptTrain->new({
rotors => \@rots,
reflector => $refl,
positions => [0,0,0],
});
my $pos=0;
for my $c ('A' .. 'Z') {
is($train->map($c),
$c,
"identity train on $c");
++$pos;$pos%=26;
is_deeply([$train->positions],
[$pos,0,0],
'no notches, only 1st moved');
}
};
subtest 'some stepping' => sub {
my @in = 'A'..'Z';
my @rots = map { Enigmatic::Rotor->new({
wiring => @in->join,
notches => ['Z'],
}) } 1..3;
my $refl = Enigmatic::Reflector->new(@in->join);
my $train = Enigmatic::CryptTrain->new({
rotors => \@rots,
reflector => $refl,
positions => [0,0,0],
});
my $pos=0;
for my $c ('A' .. 'Y') {
$train->step_positions();
++$pos;
is_deeply([$train->positions],
[$pos,0,0],
'single notch');
}
$train->step_positions();
is_deeply([$train->positions],
[0,1,0],
'single notch');
};
sub _test_double_stepping {
my ($train,$init,$steps) = @_;
for my $rot (0..2) {
$train->set_position($rot,$init->[$rot]);
}
for my $step_idx (0..$#$steps) {
$train->step_positions();
my $now_windows = $steps->[$step_idx];
is_deeply([$train->rotor_windows],
$now_windows,
'correct step');
}
}
subtest 'double-stepping' => sub {
my $rotbox = Enigmatic::RotorBox->new();
my $reflbox = Enigmatic::ReflectorBox->new();
my $train = sub { Enigmatic::CryptTrain->new({
rotors => [
$rotbox->get('I'),
$rotbox->get('II'),
$rotbox->get('III'),
],
reflector => $reflbox->get('B'),
}) };
_test_double_stepping($train->(),
[qw(O D K)],
[
[qw(P D K)],
[qw(Q D K)],
[qw(R E K)],
[qw(S F L)],
[qw(T F L)],
]);
$train = sub { Enigmatic::CryptTrain->new({
rotors => [
$rotbox->get('III'),
$rotbox->get('II'),
$rotbox->get('I'),
],
reflector => $reflbox->get('B'),
}) };
_test_double_stepping($train->(),
[qw(T A A)],
[
[qw(U A A)],
[qw(V A A)],
[qw(W B A)],
[qw(X B A)],
[qw(Y B A)],
]);
_test_double_stepping($train->(),
[qw(T D A)],
[
[qw(U D A)],
[qw(V D A)],
[qw(W E A)],
[qw(X F B)],
[qw(Y F B)],
]);
};
done_testing();