奉獻一個能進行rsa計算的小工具

看雪資料發表於2015-11-15

標 題:奉獻一個能進行rsa計算的小工具 

發信人:moon 

時 間:2004-07-10,19:23

詳細資訊:



好久沒有作品可以放上來與大家分享了,今特奉上一款本人獨立創作完成的完全用匯編語言編寫而成的小工具"rsa計算器"。輸入輸出全部都用十六進位制格式,可對資料進行運算,而不是對文字。

點選下載:附件!

n能到1024位。也有疑問,位數再高不知為何不行。(改變DD_NUM等值的數即可改變位數)

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    .386
    .model flat, stdcall
    option casemap :none
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
include    windows.inc
include    user32.inc
includelib  user32.lib
include    kernel32.inc
includelib  kernel32.lib
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
ICO_MAIN  equ    1000  ;圖示
DLG_MAIN  equ    100

DD_NUM     EQU   8;32    ;位數除以32,即DWORD數
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    .data?

hInstance  dd    ?

actural_b  dd  DD_NUM * 2 dup (0)
actural_n  dd  DD_NUM * 2 dup (0)
actural_m  dd  DD_NUM * 2 dup (0)
result    dd  DD_NUM * 2 dup (0)
presult    dd  ?

    .data

rsa_a  dd  DD_NUM dup (0)
rsa_b  dd  DD_NUM dup (0)
rsa_c  dd  DD_NUM dup (0)
rsa_n  dd  DD_NUM dup (0)
rsa_p  dd  DD_NUM dup (0)
rsa_m  dd  DD_NUM dup (0)
rsa_back dd  DD_NUM dup (0)

    .const
default_b  db  "10001",0  ;設定預設的私鑰
default_n  db  "C7B71C573A60F571",0  ;設定預設的模
default_m  db  "BCF0DB712E6595F1",0    ;設定預設的資料
num_error  db  "有非法字元!",0
blank_error  db  "輸入所有資料!",0
format    db   "%X",0
format8    db   "%8X",0
can_not_factor  db  "這個n是素數,不能分解!",0
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    .code
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
rsa  proc
  push ebp
  mov  ebp,esp

;------------------------------;  置初值
  mov rsa_c,1
;-------------------------------迴圈計算
rsa0:  mov eax,rsa_b    ;bl
  and eax,1        ;b&1
  .if eax == 0        ;b偶數?
;------------------------------b = b >> 1  ;b是偶數時
    rcl eax,1    
    mov esi,DD_NUM ;2
    .repeat
      rcr eax,1
      rcr [rsa_b-4+esi*4],1  
      rcl eax,1
      dec esi
    .until esi == 0
;------------------------------a = (a * a) mod n
    lea  eax,rsa_a  ;c--[EBP-08h][EBP-04h] 
    call bigmul    ;<--呼叫兩數相乘再除以n的子程式
    lea  eax,rsa_a  ;c--[EBP-08h][EBP-04h] 
    call bigdiv
  .else
    sub rsa_b,1  ;b = b - 1 只需將b的最低位置0即可
;------------------------------c = (c * a) mod n
    lea  eax,rsa_c    ;a
    call bigmul    ;<--呼叫兩數相乘再除以n的子程式
    lea  eax,rsa_c    ;a
    call bigdiv
  .endif
;------------------------------判斷b是否0  while(b)
  mov esi,DD_NUM ;
  .repeat
    cmp [rsa_b-4+esi*4],0  ;判斷b是否0
    ja rsa0
    dec esi
  .until esi == 0
;------------------------------計算結束
  pop      ebp
  retn
rsa  endp
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;-----------------------------兩數相乘的子程式,這裡利用了資料連續儲存的特點,乘積的長度與兩個資料一樣,
bigmul  proc      ;超出的部分會自動存到餘數所在的空間
  mov ebx,eax    ;唯一的一個輸入引數,是一個乘數的地址,另一個乘數固定為rsa_a
  lea ecx,rsa_a    ;乘積存放在rsa_p和rsa_m合起來的連續空間
  xor eax,eax
  xor esi,esi
  .repeat
    mov [rsa_p+esi*4],eax    ;乘積置初值0
    inc esi
  .until  esi == DD_NUM + DD_NUM ;4

  xor edi,edi
  push ebp
  .repeat
    lea ecx,[ecx+edi*4]    ;ecx=ecx+edi*4
    xor esi,esi      ;esi=0
    lea ebp,[rsa_p+edi*4]
    .repeat
      mov eax,[ebx+esi*4]
      mul DWORD ptr [ecx]
      lea ebp,[ebp+esi*4]
      add DWORD ptr [ebp],eax
      adc DWORD ptr [ebp+4],edx
      adc DWORD ptr [ebp+8],0
      inc esi
    .until esi == DD_NUM ;
    inc edi
  .until edi == DD_NUM ;
  pop ebp
  retn
bigmul  endp
;--------------------------------兩個數相除 取餘數
bigdiv  proc      ;被除數為rsa_p,存在於rsa_p至rsa_m的連續空間,除數為rsa_n
  mov ebx,eax
  mov edx,DD_NUM * 20H ;<--設迴圈次數

mydiv:  xor esi,esi
  inc esi
  mov ecx,DD_NUM + DD_NUM - 1
  shl DWORD ptr [rsa_p],1;被除數左移1位,rsa_p至rsa_m連續左移
shiftp:  rcl DWORD ptr [rsa_p+esi*4],1
  inc esi
  loop shiftp

  mov esi,DD_NUM;2    ;比較
  .repeat
    mov eax,[rsa_n-4+esi*4]
    cmp [rsa_m-4+esi*4],eax
    jc  loop0
    ja  asubb
    dec esi
  .until esi == 0

asubb:  xor esi,esi    ;相減
  clc
  mov ecx,DD_NUM
msubn:  mov eax,[rsa_n+esi*4]
  sbb [rsa_m+esi*4],eax
  inc esi
  loop msubn

  inc DWORD ptr [rsa_p]  ;為了取商,加上了這一段
  xor esi,esi
  inc esi
  mov ecx,DD_NUM - 1
padd1:  adc DWORD ptr [rsa_p+esi*4],0
  inc esi
  loop padd1

loop0:  dec edx
  jnz mydiv
;相除結束,[rsa_p]是商,[rsa_m]是餘數
  xor esi,esi
  .repeat
    mov eax,[rsa_m+esi*4]    ;儲存餘數
    mov [ebx+esi*4],eax
    inc esi
  .until esi == DD_NUM ;2

  retn
bigdiv  endp
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
scan_data  proc  hWnd
;檢查輸入資料的長度
  mov edi,eax
  invoke lstrlen,eax
  .if eax ==0 
    jmp nonum
  .endif

;檢查輸入資料中是否有非法字元
scan_b:
  mov al,BYTE ptr [edi]
  .if al == 0
    xor eax,eax
    inc eax
    jmp scan_end
  .elseif al >= '0' && al <= '9' || al >= 'A' && al <= 'F' || al >= 'a' && al <= 'f'
    inc edi
    jmp scan_b
  .else
    jmp notnum
  .endif
notnum:  
  invoke SetDlgItemText,hWnd,104,addr num_error
  xor eax,eax
  jmp scan_end
nonum:  
  invoke SetDlgItemText,hWnd,104,addr blank_error
  xor eax,eax
scan_end:
  pop ebp
  retn 4
scan_data  endp
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
stringtoint  proc
  mov esi,eax
  mov edi,edx
  invoke lstrlen,eax
  xchg eax,esi
  mov edx,edi
  xor ebx,ebx
conv:  mov cl,BYTE ptr [eax+esi-1]
  .if cl >= 'A' && cl <= 'F'
    sub cl,'A'-0ah
  .elseif cl >= 'a' && cl <= 'f'
    sub cl,'a'-0ah
  .else
    sub cl,'0'
  .endif
  mov bl,cl

  dec esi
  jz oddbit
  mov cl,BYTE ptr [eax+esi-1]
  .if cl >= 'A' && cl <= 'F'
    sub cl,'A'-0ah
  .elseif cl >= 'a' && cl <= 'f'
    sub cl,'a'-0ah
  .else
    sub cl,'0'
  .endif
  shl cl,4
  add bl,cl
  mov BYTE ptr [edx],bl
  inc edx
  dec esi
  jnz conv
  jmp convert_end

oddbit:  mov BYTE ptr [edx],bl
  
convert_end:
  retn
stringtoint  endp
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
inttostring  proc
  mov esi,eax
  mov edi,edx
  invoke lstrlen,eax
  cdq
  mov ecx,4
  div ecx
  mov ebx,eax
  xor eax,eax
  lea eax,result
  mov presult,eax
  .if edx != 0
    mov eax,DWORD ptr [esi+ebx*4]
    invoke wsprintf,presult,addr format,eax
    add presult,eax
  .endif
  .while ebx > 0
    mov eax,DWORD ptr [esi+ebx*4-4]
    invoke wsprintf,presult,addr format,eax
    add presult,eax
    dec ebx
  .endw
  retn
inttostring  endp
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
_ProcDlgMain  proc  uses ebx edi esi hWnd,wMsg,wParam,lParam

    mov  eax,wMsg
    .if  eax == WM_CLOSE
      invoke  EndDialog,hWnd,NULL
    .elseif  eax == WM_INITDIALOG
      invoke  LoadIcon,hInstance,ICO_MAIN
      invoke  SendMessage,hWnd,WM_SETICON,ICON_BIG,eax
      invoke SetDlgItemText,hWnd,101,addr default_b
      invoke SetDlgItemText,hWnd,102,addr default_n
      invoke SetDlgItemText,hWnd,103,addr default_m
    .elseif  eax == WM_COMMAND
      mov  eax,wParam
      .if  ax == IDCANCEL 
        invoke  EndDialog,hWnd,NULL
      .elseif  ax == IDOK
        invoke SetDlgItemText,hWnd,104,NULL 
        lea eax,actural_b
        xor edx,edx
        mov ecx,DD_NUM * 8 + 1 
clrmem:        mov [eax + ecx * 4 - 4],edx
        loop clrmem
        lea eax,rsa_a
        mov ecx,DD_NUM * 6 + 1
clrmem1:      mov [eax + ecx * 4 - 4],edx
        loop clrmem1

        invoke GetDlgItemText,hWnd,101,addr actural_b,sizeof actural_b
        invoke GetDlgItemText,hWnd,102,addr actural_n,sizeof actural_n
        invoke GetDlgItemText,hWnd,103,addr actural_m,sizeof actural_m
        lea eax,actural_b
        invoke scan_data,hWnd
        .if eax 
          lea eax,actural_n
          invoke scan_data,hWnd
          .if eax
            lea eax,actural_m
            invoke scan_data,hWnd
            .if eax 
              lea eax,actural_b
              lea edx,rsa_b
              call stringtoint
              lea eax,actural_n
              lea edx,rsa_n
              call stringtoint
              lea eax,actural_m
              lea edx,rsa_a
              call stringtoint
              call rsa
              lea eax,rsa_c
              lea edx,result
              call inttostring
              invoke SetDlgItemText,hWnd,104,addr result
            .endif
          .endif
        .endif
      .endif
    .else
      mov  eax,FALSE
      ret
    .endif
    mov  eax,TRUE
    ret

_ProcDlgMain  endp
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
start:
    invoke  GetModuleHandle,NULL
    mov  hInstance,eax
    invoke  DialogBoxParam,hInstance,DLG_MAIN,NULL,offset _ProcDlgMain,NULL
    invoke  ExitProcess,NULL
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    end  start

相關文章