暗号回路の単体テスト


前回、プロセッサに接続する暗号回路をFPGAに実装した。
実際にプロセッサからハードウェアを操作して正しく動作しているか単体テストを行う。
FPGAに実装した回路の入出力端子は、プロセッサに接続されているGPIOを介して操作する。
GPIOはLinuxからはsysfsによりアクセスする。
sysfsと暗号回路の端子との対応は以下の通りである。

sysfs 制御回路
端子
プロセッサから見た
入出力方向
FPGAから見た
入出力方向
FPGAの
物理端子名
/sys/class/gpio/CON9_17 PE 入力出力P68
/sys/class/gpio/CON9_18 DE 出力入力P67
/sys/class/gpio/CON9_21 ST 出力入力P78
/sys/class/gpio/CON9_22 KY 出力入力P78
/sys/class/gpio/CON9_23 SO 入力出力P84
/sys/class/gpio/CON9_24 SI 出力入力P95
/sys/class/gpio/CON9_25 CK 出力入力P95
/sys/class/gpio/CON9_26 RS 出力入力P95

sysfs の GPIO クラスの操作方法は以下の通りである。

組込みシステムの操作方法

  1. パソコン上で traterm を COM1 で起動する。

  2. 組込みシステムの電源をつなぐ(スイッチングレギュレータをコンセントに差し込む)

  3. traterm 上に起動メッセージが出ていることを確認

  4. login プロンプトが出たら root にてログイン
    ※ rootのパスワードについては,実験時に指示する。

  5. dateコマンドを用いて現在時刻を確認する。(グリニッジ時間なので注意)
    もし現在時刻が異なるようならntpdateコマンドを用いて現在時刻を設定する(サーバは133.95.10.2)
    ntpdate 133.95.10.2

  6. 使用終了後は halt コマンドにより停止する。(実験中は、最後に落せばよい)

  7. System halted. メッセージが出たのを確認したのち,組込みシステムの電源を外す
    halt せずに電源を落とした場合,OSが記録されたフラッシュメモリが破壊される可能性があるので注意

perl による暗号回路のテストプログラム

以下のテストプログラムを組込みシステム内に保存し、実行属性を付けて実行すればよい。
なお、このテストプログラムは jjpc10302:/root/usr/prog/des/desif.pl として準備しているので,改めてファイル転送する必要はない。
#! /usr/bin/perl

$key = "0001001111001011011100111011111110100001110000011110110001011011";
$str = "0101010001100101011100110111010001010100011001010111001101110100";

&io_init;

print "key transfer: ";
$old_key = &key_trans( $key );
printf "Parity error:%s\n", ($pe)?"detect":"none";
# print "Old key=$old_key\n";

print "string transfer\n";
print "in str.=$str\n";
$st = &str_trans( $str );

print "encrypt";
&io_enc;
$st = &str_trans( $str );
print "=$st\n";

print "string transfer\n";
print "in str.=$st\n";
$st = &str_trans( $st );

print "decrypt";
&io_dec;
$st = &str_trans( $st );
print "=$st\n";

&io_close;

sub key_trans {
  local( $key_in ) = @_;

  my $key_out = "";
  &io_key( "1" );
  for( my $i=0 ; $i<64 ; $i=$i+1 ) {
    &io_si( substr( $key_in, 63-$i, 1 ) );
    &io_clk;
    $key_out = &io_so . $key_out;
  }
  &io_key( "0" );
  $pe = &io_pe;
  return $key_out;
}

sub str_trans {
  local( $str_in ) = @_;

  my $str_out = "";
  &io_str( "1" );
  for( my $i=0 ; $i<64 ; $i=$i+1 ) {
    &io_si( substr( $str_in, 63-$i, 1 ) );
    &io_clk;
    $str_out = &io_so . $str_out;
  }
  &io_str( "0" );
  return $str_out;
}

sub io_enc {
  &io_de( "0" ); # encrypt
  &io_clk;
}

sub io_dec {
  &io_de( "1" ); # decrypt
  &io_clk;
  &io_de( "0" );
}

sub io_de {
  local( $value ) = @_;
  syswrite( F_DE, $value, 1 );
}

sub io_str {
  local( $value ) = @_;
  syswrite( F_ST, $value, 1 );
}

sub io_key {
  local( $value ) = @_;
  syswrite( F_KY, $value, 1 );
}

sub io_pe {
  my $pe;
  read( F_PE, $pe, 1 );
  seek( F_PE, 0, 0 );	# rewind
  return $pe;
}

sub io_so {
  my $ch;
  read( F_SO, $ch, 1 );
  seek( F_SO, 0, 0 );	# rewind
  return $ch;
}

sub io_si {
  local( $value ) = @_;
  syswrite( F_SI, $value, 1 );
}

sub io_clk {
  syswrite( F_CK, "1", 1 );
  syswrite( F_CK, "0", 1 );
}

sub io_init {
  my $f;

  $D_PE="/sys/class/gpio/CON9_17";
  $D_DE="/sys/class/gpio/CON9_18";
  $D_ST="/sys/class/gpio/CON9_21";
  $D_KY="/sys/class/gpio/CON9_22";
  $D_SO="/sys/class/gpio/CON9_23";
  $D_SI="/sys/class/gpio/CON9_24";
  $D_CK="/sys/class/gpio/CON9_25";
  $D_RS="/sys/class/gpio/CON9_26";

  foreach $f ( $D_PE, $D_SO ) {
    open FP, ">$f/direction";
    syswrite( FP, "in",  2 );
    close FP;
  }
  foreach $f ( $D_DE, $D_ST, $D_KY, $D_SI, $D_CK, $D_RS ) {
    open FP, ">$f/direction";
    syswrite( FP, "out", 3 );
    close FP;
  }

  open F_PE,"<$D_PE/value"; # open for input
  open F_SO,"<$D_SO/value";

  open F_DE,">$D_DE/value"; # open for output
  open F_ST,">$D_ST/value";
  open F_KY,">$D_KY/value";
  open F_SI,">$D_SI/value";
  open F_CK,">$D_CK/value";
  open F_RS,">$D_RS/value";

  syswrite( F_DE, "0", 1 );
  syswrite( F_SI, "0", 1 );
  syswrite( F_ST, "0", 1 );
  syswrite( F_KY, "0", 1 );
  syswrite( F_CK, "0", 1 );
  syswrite( F_RS, "1", 1 ); # reset
  syswrite( F_RS, "0", 1 );
}

sub io_close {
  close F_PE;
  close F_SO;

  close F_DE;
  close F_ST;
  close F_KY;
  close F_SI;
  close F_CK;
  close F_RS;
}

実行結果

/root/usr/prog/des/desif.pl を実行する。
ハードウェア設計時のシミュレーションで正しい結果を得ていれば、
以下のような実行結果が得られるはずである。
jjpc10302:~/usr/Sample# ./desif.pl
key transfer: Parity error:none
string transfer
in str.=0101010001100101011100110111010001010100011001010111001101110100
encrypt=0000111111001011110011101010101110100010101011111000000000100010
string transfer
in str.=0000111111001011110011101010101110100010101011111000000000100010
decrypt=0101010001100101011100110111010001010100011001010111001101110100
jjpc10302:~/usr/Sample#
入力ワードを暗号化した後に復号を行うと、元の入力ワードに戻っていることが確認できる。
もし、暗号前と復号後の値が異なる場合は、設計時のシミュレーションで誤りを見落としたか、
FPGAへの実装手順を誤った可能性が高い。
| Back |