· 7 years ago · Apr 03, 2018, 05:40 PM
1package mmoserver.utils;
2
3import mmoserver.utils.configurations.MainConfig;
4import org.apache.log4j.LogManager;
5import org.apache.log4j.Logger;
6
7import javax.crypto.*;
8import javax.crypto.interfaces.DHPrivateKey;
9import javax.crypto.interfaces.DHPublicKey;
10import javax.crypto.spec.DHParameterSpec;
11import javax.crypto.spec.DHPublicKeySpec;
12import javax.crypto.spec.SecretKeySpec;
13import java.math.BigInteger;
14import java.security.*;
15import java.security.spec.InvalidKeySpecException;
16import java.util.Base64;
17
18/**
19 * Project ServerMMO - mmoserver.utils
20 * Created by Igor "BrannByorn" Gromov
21 * Date 12.03.2018 9:18
22 */
23public class Cryptography {
24 private Logger logger = LogManager.getLogger(Cryptography.class.getName());
25 private String secretKey;
26 private String clientPublicKey;
27 private String clientPrivateKey;
28 private long clientPubSignature = 1;
29 private KeyAgreement clientKeyAgree;
30 private BigInteger G; // Любой INT Ð´Ð»Ñ DH шифрованиÑ
31 private static byte[] IV = { Доп ключ Ð´Ð»Ñ BF};
32
33 public String getSecretKey() {
34 return secretKey;
35 }
36
37 public void setSecretKey(String secretKey) {
38 this.secretKey = secretKey;
39 }
40
41 public String getClientPublicKey() {
42 return clientPublicKey;
43 }
44
45
46 public void DiffieHellman_createKeys() {
47 try {
48
49 DHParameterSpec dhSkipParamSpec = new DHParameterSpec(P, G);
50
51 // Alice creates her own DH key pair, using the DH parameters from above
52 KeyPairGenerator aliceKpairGen = KeyPairGenerator.getInstance("DH");
53
54 aliceKpairGen.initialize(dhSkipParamSpec);
55
56 KeyPair aliceKpair = aliceKpairGen.generateKeyPair();
57
58 DHPublicKey dhPub = (DHPublicKey) aliceKpair.getPublic();
59 clientPublicKey = String.valueOf(dhPub.getY());
60
61 DHPrivateKey dhPr = (DHPrivateKey) aliceKpair.getPrivate();
62 clientPrivateKey = String.valueOf(dhPr.getX());
63
64 // Alice creates and initializes her DH KeyAgreement object
65 clientKeyAgree = KeyAgreement.getInstance("DH");
66 clientKeyAgree.init(aliceKpair.getPrivate());
67
68 } catch (InvalidAlgorithmParameterException e) {
69 e.printStackTrace();
70 } catch (NoSuchAlgorithmException e) {
71 e.printStackTrace();
72 } catch (InvalidKeyException e) {
73 e.printStackTrace();
74 }
75
76 }
77
78 public String DiffieHellman_createSecretKey(String publicKey) {
79 try {
80 DHPublicKeySpec dhPubKeySpecs = new DHPublicKeySpec(new BigInteger(publicKey), P, G);
81 KeyFactory kf = KeyFactory.getInstance("DH");
82 DHPublicKey bobPubKey = (DHPublicKey) kf.generatePublic(dhPubKeySpecs);
83
84 clientKeyAgree.doPhase(bobPubKey, true);
85
86 byte[] aliceSecret = clientKeyAgree.generateSecret();
87 byte[] encodedBytes = Base64.getEncoder().encode(aliceSecret);
88
89 String source_key = new String(encodedBytes);
90 return source_key.substring(0, 16);
91 } catch (InvalidKeySpecException e) {
92 e.printStackTrace();
93 } catch (NoSuchAlgorithmException e) {
94 e.printStackTrace();
95 } catch (InvalidKeyException e) {
96 e.printStackTrace();
97 }
98 return null;
99 }
100
101 public byte[] CryptDH(byte[] source, String key) {
102 if (MainConfig.crypt) {
103 try {
104 Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
105 SecretKeySpec skeySpec = new SecretKeySpec(key.getBytes(), "AES");
106 cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
107 return cipher.doFinal(source);
108 } catch (NoSuchPaddingException e) {
109 e.printStackTrace();
110 } catch (BadPaddingException e) {
111 e.printStackTrace();
112 } catch (IllegalBlockSizeException e) {
113 e.printStackTrace();
114 } catch (NoSuchAlgorithmException e) {
115 e.printStackTrace();
116 } catch (InvalidKeyException e) {
117 e.printStackTrace();
118 }
119 } else {
120 return source;
121 }
122 return null;
123 }
124
125 public byte[] DecryptDH(byte[] cryptogram, String key) {
126
127 //System.out.println("ServerMain.bEnableCrypto: " + ServerMain.bEnableCrypto);
128
129 if (MainConfig.crypt) {
130 try {
131 Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
132 SecretKeySpec skeySpec = new SecretKeySpec(key.getBytes(), "AES");
133 cipher.init(Cipher.DECRYPT_MODE, skeySpec);
134 return cipher.doFinal(cryptogram);
135 } catch (InvalidKeyException e) {
136 e.printStackTrace();
137 } catch (NoSuchPaddingException e) {
138 e.printStackTrace();
139 } catch (BadPaddingException e) {
140 e.printStackTrace();
141 } catch (IllegalBlockSizeException e) {
142 e.printStackTrace();
143 } catch (NoSuchAlgorithmException e) {
144 e.printStackTrace();
145 }
146 } else {
147 return cryptogram;
148 }
149 return null;
150 }
151
152 public static byte[] CryptBF(byte[] crypt) {
153 if (true) {
154 try {
155 Cipher cipher = Cipher.getInstance("Blowfish/CFB/NoPadding");
156 SecretKeySpec skeySpec = new SecretKeySpec(Cryptography.bf_key, "Blowfish");
157 cipher.init(Cipher.ENCRYPT_MODE, skeySpec,new javax.crypto.spec.IvParameterSpec(IV));
158 return cipher.doFinal(crypt);
159 } catch (NoSuchPaddingException e) {
160 e.printStackTrace();
161 } catch (BadPaddingException e) {
162 e.printStackTrace();
163 } catch (IllegalBlockSizeException e) {
164 e.printStackTrace();
165 } catch (NoSuchAlgorithmException e) {
166 e.printStackTrace();
167 } catch (InvalidKeyException e) {
168 e.printStackTrace();
169 } catch (InvalidAlgorithmParameterException e) {
170 e.printStackTrace();
171 }
172 } else {
173 return crypt;
174 }
175 return null;
176 }
177
178 public static byte[] DecryptBF(byte[] crypt) {
179 if (true) {
180 try {
181 Cipher cipher = Cipher.getInstance("Blowfish/CFB/NoPadding");
182 SecretKeySpec skeySpec = new SecretKeySpec(Cryptography.bf_key, "Blowfish");
183 cipher.init(Cipher.DECRYPT_MODE, skeySpec,new javax.crypto.spec.IvParameterSpec(IV));
184 return cipher.doFinal(crypt);
185 } catch (InvalidKeyException e) {
186 e.printStackTrace();
187 } catch (NoSuchPaddingException e) {
188 e.printStackTrace();
189 } catch (BadPaddingException e) {
190 e.printStackTrace();
191 } catch (IllegalBlockSizeException e) {
192 e.printStackTrace();
193 } catch (NoSuchAlgorithmException e) {
194 e.printStackTrace();
195 } catch (InvalidAlgorithmParameterException e) {
196 e.printStackTrace();
197 }
198 } else {
199 return crypt;
200 }
201 return null;
202 }
203
204 public static String getMD5(String input) {
205 try {
206 MessageDigest md = MessageDigest.getInstance("MD5");
207 byte[] messageDigest = md.digest(input.getBytes());
208 BigInteger number = new BigInteger(1, messageDigest);
209 String hashtext = number.toString(16);
210 // Now we need to zero pad it if you actually want the full 32 chars.
211 while (hashtext.length() < 32) {
212 hashtext = "0" + hashtext;
213 }
214 return hashtext;
215 } catch (NoSuchAlgorithmException e) {
216 throw new RuntimeException(e);
217 }
218 }
219
220 // Ключ на 1024 бита
221 private static final byte dh1024_p[] = {
222 (byte) 0xF4, (byte) 0x88, (byte) 0xFD, (byte) 0x58, (byte) 0x4E, (byte) 0x49, (byte) 0xDB, (byte) 0xCD,
223 (byte) 0x20, (byte) 0xB4, (byte) 0x9D, (byte) 0xE4, (byte) 0x91, (byte) 0x07, (byte) 0x36, (byte) 0x6B,
224 (byte) 0x33, (byte) 0x6C, (byte) 0x38, (byte) 0x0D, (byte) 0x45, (byte) 0x1D, (byte) 0x0F, (byte) 0x7C,
225 (byte) 0x88, (byte) 0xB3, (byte) 0x1C, (byte) 0x7C, (byte) 0x5B, (byte) 0x2D, (byte) 0x8E, (byte) 0xF6,
226 (byte) 0xF3, (byte) 0xC9, (byte) 0x23, (byte) 0xC0, (byte) 0x43, (byte) 0xF0, (byte) 0xA5, (byte) 0x5B,
227 (byte) 0x18, (byte) 0x8D, (byte) 0x8E, (byte) 0xBB, (byte) 0x55, (byte) 0x8C, (byte) 0xB8, (byte) 0x5D,
228 (byte) 0x38, (byte) 0xD3, (byte) 0x34, (byte) 0xFD, (byte) 0x7C, (byte) 0x17, (byte) 0x57, (byte) 0x43,
229 (byte) 0xA3, (byte) 0x1D, (byte) 0x18, (byte) 0x6C, (byte) 0xDE, (byte) 0x33, (byte) 0x21, (byte) 0x2C,
230 (byte) 0xB5, (byte) 0x2A, (byte) 0xFF, (byte) 0x3C, (byte) 0xE1, (byte) 0xB1, (byte) 0x29, (byte) 0x40,
231 (byte) 0x18, (byte) 0x11, (byte) 0x8D, (byte) 0x7C, (byte) 0x84, (byte) 0xA7, (byte) 0x0A, (byte) 0x72,
232 (byte) 0xD6, (byte) 0x86, (byte) 0xC4, (byte) 0x03, (byte) 0x19, (byte) 0xC8, (byte) 0x07, (byte) 0x29,
233 (byte) 0x7A, (byte) 0xCA, (byte) 0x95, (byte) 0x0C, (byte) 0xD9, (byte) 0x96, (byte) 0x9F, (byte) 0xAB,
234 (byte) 0xD0, (byte) 0x0A, (byte) 0x50, (byte) 0x9B, (byte) 0x02, (byte) 0x46, (byte) 0xD3, (byte) 0x08,
235 (byte) 0x3D, (byte) 0x66, (byte) 0xA4, (byte) 0x5D, (byte) 0x41, (byte) 0x9F, (byte) 0x9C, (byte) 0x7C,
236 (byte) 0xBD, (byte) 0x89, (byte) 0x4B, (byte) 0x22, (byte) 0x19, (byte) 0x26, (byte) 0xBA, (byte) 0xAB,
237 (byte) 0xA2, (byte) 0x5E, (byte) 0xC3, (byte) 0x55, (byte) 0xE9, (byte) 0x2F, (byte) 0x78, (byte) 0xC7
238 };
239
240 private static final byte dh512_p[] = {
241 // То же что и выше но на 512 бит
242 };
243 private static final byte bf_key[] = {
244 // Тут Blowfish ключ на 448 бит
245 };
246 private static final BigInteger P = new BigInteger(1, dh512_p);
247
248
249}