RSA 암호화 알고리즘
RSA의 암호화 알고리즘을 검토합시다. 우리는 비교적 표준화 된 언어를 사용하여 공개 키 암호화 알고리즘 및 서명 알고리즘의 정의를 기반 으로이 알고리즘을 설명합니다.
RSA 공개 키 암호화 시스템에는 다음 3 가지 알고리즘이 포함되어 있습니다 : keygen (키 생성 알고리즘), 암호화 (암호화) 및 해독 (암호 해독 알고리즘)이 포함됩니다.
키 생성 알고리즘은 공개 키 PK 및 개인 키 SK를 출력하기위한 입력으로 보안 상수를 사용합니다. 보안 상수는 암호화 알고리즘이 어떻게 보안인지를 결정하는 데 사용되며, 이는 일반적으로 암호화 알고리즘에 사용되는 소수 P의 크기와 관련이 있습니다. 소수 P가 클수록 시스템이 클수록 보안이 높아집니다. RSA에서 주요 생성 알고리즘은 다음과 같습니다. 알고리즘은 먼저 두 개의 다른 큰 소수 P와 Q를 무작위로 생성하고 n = pq를 계산합니다. 그런 다음 알고리즘은 오일러 함수를 계산합니다. 다음으로, 알고리즘은 e보다 적은 정수를 무작위로 선택하고 e의 모듈로 역 요소 d를 계산합니다. 마지막으로, 공개 키는 pk = (n, e)이고 개인 키는 sk = (n, d)입니다.
암호화 알고리즘은 공개 키 PK와 메시지 m을 사용하여 입력으로 암호화하고 암호 텍스트 CT를 출력합니다. RSA에서 암호화 알고리즘은 다음과 같습니다.이 알고리즘은 암호 해독 알고리즘이 개인 키 SK 및 CipherText CT를 입력으로 사용하고 메시지 M을 출력함에 따라 암호 텍스트를 직접 출력합니다. RSA에서는 Mosyption 알고리즘이 다음과 같습니다. e와 d는 서로 반대 방향이므로 우리는 다음과 같습니다.
따라서 알고리즘 설명에서 공개 키가 데이터를 암호화하는 데 사용되며 개인 키는 데이터를 해독하는 데 사용됩니다. 물론 이것은 직관적으로 이해 될 수 있습니다. 공개 키는 공개 키이며, 공개 될 때만 모든 사람이 데이터를 암호화하는 데 사용할 수 있습니다. 개인 키는 개인 키 이며이 키를 가진 사람은 암호 텍스트를 해독 할 수 있습니다. 그렇지 않으면 모든 사람이 개인 키를보고 해독 할 수 있다면 혼란 스러울 것입니다.
Java의 간단한 구현을 살펴 보겠습니다.
패키지 com.stone.security; java.security.keypair import; java.security.keypairgenerator import; java.security.privatekey import; java.security.publickey import; import java.util.arrays; javax.crypto.cipher 가져 오기; / *** RSA 알고리즘 공개 키 암호화 비대칭 암호화*/ public class rsa {public static final String key_algorithm = "rsa"; 공개 정적 최종 문자열 cipher_algorithm_ecb1 = "rsa/ecb/pkcs1padding"; 공개 정적 최종 문자열 cipher_algorithm_ecb2 = "rsa/ecb/oaepshawithsha-1andmgf1padding"; // 공개 정적 최종 문자열 cipher_algorithm_ecb3 = "oaepwithsha-256andmgf1padding"을 사용할 수 없습니다. // 정적 publickey publickey를 사용할 수 없습니다. 정적 개인 키 프라이빗 키; 정적 암호 암호; 정적 키어 키어; public static void main (string [] args)은 예외 {method1 ( "skoda u*(sfsad7f ()*^%% $"); 메소드 2 ( "skoda u*(sfsad7f ()*^%% $"); method3 ( "skoda u*(sfsad7f ()*^%% $"; Default CipireS는 예외 {kyypairgenerator keygenerator = kyypairgenerator.getinstance (key_algorithm); kyypair.getPriver (Cipher.Init) (cipher.encrypt_mode, public Keyption byte); Cipher.Init (Cipher.decrypt_mode, privatekey); cipher_algorithm_ecb1 * @param str * @throws Exception */ static void method2 (string str) 예외 {kyypairgenerator keygenerator = kyypairgenerator.getinstance (key_algorithm); Keypair kyypair = keygenerator.generatekeypair (); publickey = kyypair.getPublic (); privatekey = kyypair.getPrivate (); cipher = cipher.getinstance (key_algorithm); cipher.init (cipher.encrypt_mode, privatekey); // 개인 키 암호화 바이트 [] alcrypt = cipher.dofinal (str.getBytes ()); System.out.println ( "개인 키 암호화 2 :" + arrays.tostring (암호화)); cipher.init (cipher.decrypt_mode, publickey); // public key decrypt byte [] decrypt = cipher.dofinal (encrypt); System.out.println ( "공개 키 데스 크립스 2 :" + new String (decrypt)); }/** * 개인 키 암호화, 공개 키 암호 해독은 cipher_algorithm_ecb1 = rsa/ecb/pkcs1padding * @param str * @throws 예외 */static void method3 (String Str)를 사용합니다. Keypair kyypair = keygenerator.generatekeypair (); publickey = kyypair.getPublic (); privatekey = kyypair.getPrivate (); cipher = cipher.getinstance (cipher_algorithm_ecb1); cipher.init (cipher.encrypt_mode, privatekey); // 개인 키 암호화 바이트 [] alcrypt = cipher.dofinal (str.getBytes ()); System.out.println ( "개인 키 암호화 3 :" + arrays.tostring (암호화)); cipher.init (cipher.decrypt_mode, publickey); // 공개 키 암호 해독 바이트 [] decrypt = cipher.dofinal (Encrypt); System.out.println ( "공개 키 암호 해독 후 3 :" + 새 문자열 (decrypt)); }} DSA 알고리즘 및 디지털 서명
DSA는 일반적으로 디지털 서명 및 인증에 사용됩니다.
DSA는 Schnorr 및 Elgamal 서명 알고리즘의 변형이며 미국의 NIST에 의해 DSS (Digital Signature Standard)로 사용됩니다.
DSA는 정수 유한 도메인 이산 로그 문제를 기반으로하며 보안은 RSA와 유사합니다.
DSA 디지털 서명 및 인증에서 발신자는 자신의 개인 키를 사용하여 파일 또는 메시지에 서명하고 수신자는 발신자의 공개 키를 사용하여 메시지를 수신 한 후 서명의 진위를 확인합니다. DSA는 알고리즘 일 뿐이며 RSA의 차이점은 암호화 및 암호 해독 또는 키 교환에 사용할 수 없다는 것입니다.
서명의 경우 RSA보다 훨씬 빠릅니다.
패키지 com.stone.security; java.security.key 가져 오기; java.security.keyfactory import; java.security.keypair import; java.security.keypairgenerator import; java.security.privatekey import; java.security.publickey import; java.security.securerandom import; java.security. signature import; java.security.spec.pkcs8encodedkeyspec import; import java.security.spec.x509encodedKeyspec; java.util.hashmap import; java.util.map import; import sun.misc.base64decoder; import sun.misc.base64encoder; /*** DSA 디지털 서명 알고리즘은 Schnorr 및 Elgamal 서명 알고리즘의 변형이며 미국의 NIST에 의해 DSS로 사용됩니다. * 요컨대, 이것은 디지털 서명으로 사용되는 고급 검증 방법입니다. 공공 및 개인 키뿐만 아니라 디지털 서명도 있습니다. 개인 키 암호화는 디지털 서명, 공개 키 검증 데이터 및 서명을 생성합니다. * 데이터와 서명이 일치하지 않으면 검증이 실패한 것으로 간주됩니다! 즉, 전송의 데이터를 더 이상 암호화 할 수 없습니다. 수신기가 데이터를 얻은 후에는 데이터가 유효한지 확인하기 위해 공개 키와 서명을 얻습니다. */ public class dsa {/ ***DSA 알고리즘을 사용할 수있을뿐만 아니라 디지털 서명에 RSA 알고리즘을 사용할 수도 있습니다.*/ public static final String key_algorithm = "RSA"; public static final string signature_algorithm = "md5withrsa";*/ public static final String key_algorithm = "dsa"; 공개 정적 최종 문자열 signature_algorithm = "dsa"; public static final string default_seed = "$%^*%^() (hjg8awfjas7"; // default seed public static final string public_key = "dsapublickey"; public static final string private_key = "dsaprivatekey"; public static void main (string [] args) 예외 {string str =! You*() _ + "; byte [] data = str.getBytes (); map <string, object> keymap = initkey (); // Key PublicKey publicKey = (publicKey) keymap.get (public_key); privatekey) keymap.get (private_key); system.out.println (개인 키 포르트 :"); System.out.println (공개 키 형식 : " + publickey.getformat ()); verify1); boolean verify = verify (data, getpublickey (keymap), system.err.println; " + verify); } / *** 키를 생성** @param seed seed* @return 키 객체* @throws Exception* / public static map <string, object> initkey (String seed)는 예외 {system.out.println ( "generate key"); KeyPairGenerator keygen = kyypairgenerator.getInstance (key_algorithm); Securerandom Securerandom = New Securerandom (); Securerandom.setseed (seed.getBytes ()); // 모듈러스 크기는 512 ~ 1024 범위이며 64 keygen.initialize (640, Securerandom)의 배수 여야합니다. Keypair 키 = keygen.genkeypair (); privateKey privateKey = keys.getPrivate (); publickey publickey = keys.getPublic (); map <string, object> map = new Hashmap <String, Object> (2); map.put (public_key, publickey); map.put (private_key, privatekey); 리턴 맵; } / *** 기본 키를 생성** @return 키 객체* @throws Exception* / public static map <string, object> initkey ()는 예외 {return initkey (default_seed); } / ** * 개인 키를 가져옵니다 * * @param keymap * @return * @throws Exception * / public static string getPrivatekey (map <String, Object> keymap)는 예외 {key key = (키) keyp.get (private_key); encryptbase64 (key.getencoded ()); // base64 암호화 개인 키}/** * 공개 키를 얻습니다 * @param keymap * @Throws Exception */public static string getPublicKey (Map <String, Object> Keymap) 예외 {key key = (key) keyp.get (public_key); encryptbase64 (key.getencoded ()); // base64 암호화 공개 키}/** * 개인 키를 사용하여 정보 * @param 데이터 암호화 데이터 * @param privatekey private key -base64 암호화 * @return * @throws Exception */public static string 표시 (byte [] data, string privatekey) 예외 {system.out.println ( "개인 키와 함께 디지털화"); 바이트 [] keybytes = decryptbase64 (privatekey); pkcs8encodedkeyspec keyspec = 새로운 pkcs8encodedkeyspec (keybytes); keyfactory factory = keyfactory.getInstance (key_algorithm); privatekey prikey = factory.generate -private (keyspec); // 개인 키를 생성 // 개인 키 서명으로 digitsign 정보 = signature.getinstance (signature_algorithm); Signature.initsign (Prikey); 서명 .update (데이터); encryptbase64 (signature.sign ()); } / *** Base64encoder 암호화* @param 데이터 암호화* @return 암호화 문자열* / private static string encryptbase64 (byte [] data) {Base64encoder encoder = new Base64encoder (); String encode = encoder.encode (data); 리턴 인코딩; } / *** Base64decoder Decrypt* @Param Data String은 해독 될* @return decryped byte []* @throws Exception* / private static byte [] decryptbase64 (String Data) 예외 던지기 {base64decoder decoder = new Base64decoder (); 바이트 [] buffer = decoder.decodebuffer (데이터); 리턴 버퍼; } / *** 디지털 서명 확인* @param 데이터 암호화 데이터* @param publickey* @param sign 디지털 서명* @rerrows 예외* / public static boolean verify (byte [] data, String publickey, String Sign) 예외 {byte [] keybytes = depryptbase64 (publickey); X509ENCODEDKEYSPEC KEYSPEC = NEW X509ENCODEDKEYSPEC (keyBytes); keyfactory keyfactory = keyfactory.getInstance (key_algorithm); publickey pubkey = keyfactory.generatepublic (keyspec); Signature Signature = Signature.getInstance (signature_algorithm); Signature.initverify (Pubkey); 서명 .update (데이터); return signature.verify (decryptbase64 (sign)); // 서명 확인}}