|
 |
|
2013/4/10(Wed) 17:43:05|NO.53519
今暗号化について勉強しているのですが、どうしても私が作ったプログラムの処理に時間がかかってしまいます。
私が書いたプログラムでは、1Mbほどで10秒以上かかってしまいます。
私が書いたプログラムで、もっと処理を高速化できないでしょうか。
*ファイルのサイズは1mbくらいのものをご利用ください。
#module
//----10進数から2進数
#defcfunc v10to2 int p
if p=0:return "0"
v="":a=p
repeat
if a=0:break
x=a\2:v=""+x+v:a=a/2
loop
return v
//----2進数から10進数
#defcfunc v2to10 var p
v=0
repeat 8
ftt1="":ftt1=strmid(p,strlen(p)-cnt-1,1);1文字ずつ読み込む(右から読み込む)
zi=1:zi<<cnt;ビットシフト
v+int(ftt1)*zi
loop
return v
//----NULL文字を変換
#defcfunc mesnulhht var p_2,str f_2;(バッファを割り当てた文字列,変換用文字,読み込むサイズ)p3を省略した場合は自動的に処理される。(一旦保存されてから読み込まれる。)
fsssizerr=s_2
if s_2<=0{;省略した場合は自動処理
dupptr fsssizerr,varptr(p_2)-16,4,4
}a=f_2:rratt=peek(a,0)
sdim v,fsssizerr
repeat fsssizerr
srrf=peek(p_2,cnt)
if srrf=0{srrf=rratt};変換
poke v,cnt,srrf
loop
return v
#global
dialog "",16,""
if stat=0{end}
fname=refstr
exist fname
size=strsize
sdim angkaku,4
bload fname,angkaku,4
anghou=0;暗号実行法
if angkaku="panr"{anghou=1:size-275};暗号化されたファイルを読み込む場合
else{anghou=0};暗号化する前のファイルをよみこむ場合
if anghou=1{;暗号化されたファイルでない場合
sdim ang1,size
sdim ang2,size
bload fname,ang1,size,275
sdim angkaku,260
bload fname,angkaku,260,10
fsave=""+getpath(fname,32)+"/"+angkaku+"";ファイル名取得
}
else{;暗号化されたファイルの場合
sdim ang1,size
sdim ang2,size+275
bload fname,ang1,size
dialog "",17,""
if stat=0{end}
fsave=refstr
sdim kr,275
kr+"panr "
fname2=getpath(fname,8)
kr+fname2
repeat 260-strlen(fname2)+5:kr+" ":loop
repeat 275
d=peek(kr,cnt)
if d=32:d=0;スペースはヌルーコードに変換
poke ang2,cnt,d
loop
}
cls
//----ファイル暗号複合化
dupptr lop,varptr(ang1)-16,4,4
repeat lop
ftt=peek(ang1,cnt);1バイト読み出し
ftt2=str(v10to2(ftt));2進数読み出し
ftt4="":repeat 8-strlen(ftt2):ftt4+"0":loop;NULL文字追加
ftt4+ftt2;コード追加
ftt3=""
repeat 8
pas=str(cnt\2);暗号用コードを作成
if pas=strmid(ftt4,cnt,1){ftt3+"1"};同じコードであれば1
else{ftt3+"0"};異なる場合は0
loop
if anghou=0{poke ang2,cnt+275,v2to10(ftt3)}
if anghou=1{poke ang2,cnt,v2to10(ftt3)}
w=1.00*100/lop*cnt
w=int(w)+1
if w2!=w{
if w\10=0:mes ""+w+"%完了":await 1
w2=w
}
loop
bsave fsave,ang2
if anghou=0:dialog ""+fname+"\n保存完了\n暗号化完了"
if anghou=1:dialog ""+fname+"\n保存完了\n複合化完了"

| |
|
2013/4/10(Wed) 20:46:04|NO.53521
> 今暗号化について勉強しているのですが、どうしても私が作ったプログラムの処理に時間がかかってしまいます。
> 私が書いたプログラムでは、1Mbほどで10秒以上かかってしまいます。
> 私が書いたプログラムで、もっと処理を高速化できないでしょうか。
> *ファイルのサイズは1mbくらいのものをご利用ください。
基本的に、バイトを扱う時は文字列で処理すべきではありません。
バイトは非常に小さいビット数の単位であることと、大抵扱う入力データのバイト数は大きいことが多いため、
そこにただでさえ処理に時間のかかる文字列を使用してしまうと、場合によっては現実的な時間で処理できなくなることがあるからです。
つまり今回の件がそうですね。
暗号化について勉強されている途中だとは思いますが、次のサイトやページなどは見てみましたか?
・暗号化 - HSP開発wiki
http://hspdev-wiki.net/?%B0%C5%B9%E6%B2%BD
・ファイルを暗号化するの巻
http://www.hspdx.net/hspyarou/0010.html
・HSPメモ帳 xorを使った暗号化
http://blog.goo.ne.jp/hiro239415/e/325c2d262ea882d9b89b3cd5b87413bf
実は今回ご提示頂いたスクリプト、XORを用いると簡単に等価な処理が記述出来るんですよね…。
#module
//----10進数から2進数
#defcfunc v10to2 int p
if p=0:return "0"
v="":a=p
repeat
if a=0:break
x=a\2:v=""+x+v:a=a/2
loop
return v
//----2進数から10進数
#defcfunc v2to10 var p
v=0
repeat 8
ftt1="":ftt1=strmid(p,strlen(p)-cnt-1,1);1文字ずつ読み込む(右から読み込む)
zi=1:zi<<cnt;ビットシフト
v+int(ftt1)*zi
loop
return v
//----NULL文字を変換
#defcfunc mesnulhht var p_2,str f_2;(バッファを割り当てた文字列,変換用文字,読み込むサイズ)p3を省略した場合は自動的に処理される。(一旦保存されてから読み込まれる。)
fsssizerr=s_2
if s_2<=0{;省略した場合は自動処理
dupptr fsssizerr,varptr(p_2)-16,4,4
}a=f_2:rratt=peek(a,0)
sdim v,fsssizerr
repeat fsssizerr
srrf=peek(p_2,cnt)
if srrf=0{srrf=rratt};変換
poke v,cnt,srrf
loop
return v
#global
dialog "",16,""
if stat=0{end}
fname=refstr
exist fname
size=strsize
sdim angkaku,4
bload fname,angkaku,4
anghou=0;暗号実行法
if angkaku="panr"{anghou=1:size-275};暗号化されたファイルを読み込む場合
else{anghou=0};暗号化する前のファイルをよみこむ場合
if anghou=1{;暗号化されたファイルでない場合
sdim ang1,size
sdim ang2,size
bload fname,ang1,size,275
sdim angkaku,260
bload fname,angkaku,260,10
fsave=""+getpath(fname,32)+"/"+angkaku+"";ファイル名取得
}
else{;暗号化されたファイルの場合
sdim ang1,size
sdim ang2,size+275
bload fname,ang1,size
dialog "",17,""
if stat=0{end}
fsave=refstr
sdim kr,275
kr+"panr "
fname2=getpath(fname,8)
kr+fname2
repeat 260-strlen(fname2)+5:kr+" ":loop
repeat 275
d=peek(kr,cnt)
if d=32:d=0;スペースはヌルーコードに変換
poke ang2,cnt,d
loop
}
cls
//----ファイル暗号複合化
dupptr lop,varptr(ang1)-16,4,4
repeat lop
ftt=peek(ang1,cnt);1バイト読み出し
#if 0
// オリジナル
ftt2=str(v10to2(ftt));2進数読み出し
ftt4="":repeat 8-strlen(ftt2):ftt4+"0":loop;NULL文字追加
ftt4+ftt2;コード追加
ftt3=""
repeat 8
pas=str(cnt\2);暗号用コードを作成
if pas=strmid(ftt4,cnt,1){ftt3+"1"};同じコードであれば1
else{ftt3+"0"};異なる場合は0
loop
if anghou=0{poke ang2,cnt+275,v2to10(ftt3)}
if anghou=1{poke ang2,cnt,v2to10(ftt3)}
#else
// xor を用いた場合
val = ftt ^ 170
if anghou=0{poke ang2,cnt+275,val}
if anghou=1{poke ang2,cnt,val}
#endif
w=1.00*100/lop*cnt
w=int(w)+1
if w2!=w{
if w\10=0:mes ""+w+"%完了":await 1
w2=w
}
loop
bsave fsave,ang2
if anghou=0:dialog ""+fname+"\n保存完了\n暗号化完了"
if anghou=1:dialog ""+fname+"\n保存完了\n複合化完了"
余談かもしれませんが、”HSPで行う”暗号化について個人的な見解を述べておきますと、例え数値として処理した場合でもHSP本来の速度のため、
あまり複雑な暗号化はスクリプトでは組んでも(実行速度的に)使い物になりません。
(前に一度、ゲームのファイル暗号化においてビットシャッフル等を用いたことがありましたが、ロード時間が長くなってストレスになったのでカットしたことがあります)
XORは簡単かつ高速で、更に暗号化に詳しくない人に対しては対策できるので、一番妥当な手法だと思います。
乱数列を用いた実装(下記参照)では、鍵も(バイトに比べ)ある程度大きい空間を使用でき、パッと見で鍵も見えないのでお勧めです。
#module
/**
@brief 入力された変数をバイナリデータとしてXORで暗号化・復号化
@param[in,out] buf 暗号化・復号化するデータが入った文字列型変数
@param[in] buflen bufのデータ長
@param[in] key 暗号化に用いる鍵(数値)
@attention randomizeを内部で用いるので、それまで使用していた乱数列はリセットされる
local valでリエントラントっぽく見えますが、実際には違いますね…
スタックに変数積まない方が早いんだろうか
*/
#deffunc xor_crypt var buf, int buflen, int key, local val
if ( buflen < 1 ) : return// repeat -1って確かまずかったよね…?
randomize key
repeat buflen
val = peek( buf, cnt ) ^ rnd(256)
poke buf, cnt, val
loop
return
#global
// 以下サンプル
key = 100
sample = "サンプル文字列"
mes "オリジナル:"+sample
// 一回やると暗号化
xor_crypt sample, strlen(sample), key
mes "暗号化:"+sample
// 二回やると元に戻る
xor_crypt sample, strlen(sample), key
mes "復号化:"+sample
(似たようなスクリプトをどこかで見た気がするんですが、直ぐに見つからなかったので直接書いてしまいます)
あるいは複雑な暗号化を使いたい場合は、実行速度と品質の観点から外部プラグインを探してくることをお勧めします。
以上。

| |
|
2013/4/11(Thu) 08:30:47|NO.53525
なるほどXORですね。(初めて知りました^^)
a=191
mes a
a^106
mes a
a^106
mes a
まさか[^]を使うなんて思っても見ませんでした。
//----バッファ割り当て
sdim ang1,320;元の文字
sdim ang2,320;暗号化文字
sdim ang3,320;復号化文字
ang1="あいうえおかきくけこさしすせそabcdefg"
//----暗号化
dupptr lop,varptr(ang1)-16,4,4;バッファ確保数
gt=175
for ct,0,lop,1
gt^200
ftt1=peek(ang1,ct)
ftt1^gt
poke ang2,ct,ftt1
next
//----復号化
dupptr lop,varptr(ang2)-16,4,4;バッファ確保数
gt=175
for ct,0,lop,1
gt^200
ftt1=peek(ang2,ct)
ftt1^gt
poke ang3,ct,ftt1
next
//----結果表示
mes ang1
mes ang2
mes ang3
XORを使って、簡単な暗号化を作ってみたのですが、質問と全く別物になってしまいました。
|
|