zoukankan      html  css  js  c++  java
  • 20135115臧文君实验4

    北京电子科技学院(BESTI)

                            实     验    报     告

    课程:Java    班级:1351班      姓名:臧文君    学号:20135115

    成绩:             指导教师:娄嘉鹏       实验日期:2015.6.9

    实验密级:无       预习程度:           实验时间:15:30-18:00

    仪器组次:         必修/选修:选修     实验序号:四

    实验名称:  服务器与客户端间传送信息加解密                                                   

    实验目的与要求: 1.没有Linux基础的同学建议先学习《Linux基础入门(新版)》《Vim编辑器》 课程。

    2.使用实验楼git服务托管代码。

    3.完成实验、撰写实验报告,实验报告以博客方式发表在博客园,注意实验报告重点是运行结果,遇到的问题(工具查找,安装,使用,程序的编辑,调试,运行等)、解决办法(空洞的方法如“查网络”、“问同学”、“看书”等一律得0分)以及分析(从中可以得到什么启示,有什么收获,教训等)。报告可以参考范飞龙老师的指导

    4. 严禁抄袭,有该行为者实验成绩归零,并附加其他惩罚措施。

    实验仪器:

    名称

    型号

    数量

    笔记本电脑

    Lenovo Z485

    1台

     

     

     

    实验内容、步骤与体会(附纸):

    一、实验内容

    1. 先运行教材上TCP代码,一人服务器,一人客户端。

    2. 下载加解密代码,先编译运行代码,一人加密一人解密,适当修改代码。

    3. 然后集成代码,一人加密后通过TCP发送,加密使用AES或DES,AES或DES加密密钥Key的发送,使用服务器的公钥加密,公钥算法用RSA或DH,发送信息的完整性验证使用MD5或SHA3。

    4.使用试验后git服务托管代码。

    5.完成实验后,找老师验收,课下写Blog。

    二、实验步骤

    结对同学:20135207 王国伊

    Blog网址:www.cnblogs.com/20135207oneking

    1、实验分工:臧文君---服务器,加解密代码整合。

                 王国伊---客户端,实现两台PC机相连。

    2、实验步骤:

    (1)下载老师提供的加解密代码,分析理解代码中语句的功能。

    (2)根据代码中的语句,查找自己主机的IP地址,确定端口号。

         在命令行中输入:ipconfig。

     

    找到自己主机的IP地址为:222.28.128.119。

    (3)根据书上TCP的实例,用BufferedReader获取从服务器传入的数据流,再用PrintWriter获取从客户端传出的输出流。

    (4)用RSA算法加密,加密使用服务器的公钥,再将加密后的密钥传给服务器。

    (5)用DES算法加密输入的明文,将加密后的密文传给服务器。

    (6)使用Hash函数,计算明文的Hash函数值,传给服务器。

    (7)把从服务器返回的结果输出。

     

     

    (8)将代码在实验楼中用git服务托管。

    3、代码:

    服务器:

    package exp4;

    import java.net.*;

    import java.io.*;

    import java.security.*;

    import java.security.spec.*;

    import javax.crypto.*;

    import javax.crypto.spec.*;

    import javax.crypto.interfaces.*;

    import java.security.interfaces.*;

    import java.math.*;

    public class Server {

        public static void main(String srgs[]) throws Exception {

           ServerSocket sc = null;

           Socket socket = null;

           try {

               sc = new ServerSocket(8029);// 创建服务器套接字

               System.out.println("端口号:" + sc.getLocalPort());

               System.out.println("服务器已经启动...");

               socket = sc.accept(); // 等待客户端连接

               System.out.println("已经建立连接");

               // 获得网络输入流对象的引用

               BufferedReader in = new BufferedReader(new InputStreamReader(

                      socket.getInputStream()));

               // //获得网络输出流对象的引用

               PrintWriter out = new PrintWriter(new BufferedWriter(

                      new OutputStreamWriter(socket.getOutputStream())), true);

               String aline2 = in.readLine();

               BigInteger c = new BigInteger(aline2);

               FileInputStream f = new FileInputStream("Skey_RSA_priv.dat");

               ObjectInputStream b = new ObjectInputStream(f);

               RSAPrivateKey prk = (RSAPrivateKey) b.readObject();

               BigInteger d = prk.getPrivateExponent();

               BigInteger n = prk.getModulus();

               BigInteger m = c.modPow(d, n);

               byte[] keykb = m.toByteArray();

               String aline = in.readLine();// 读取客户端传送来的数据

               byte[] ctext = parseHexStr2Byte(aline);

               Key k = new SecretKeySpec(keykb, "DESede");

               Cipher cp = Cipher.getInstance("DESede");

               cp.init(Cipher.DECRYPT_MODE, k);

               byte[] ptext = cp.doFinal(ctext);

               String p = new String(ptext, "UTF8");

               System.out.println("从客户端接收到信息为:" + p); // 通过网络输出流返回结果给客户端

               String aline3 = in.readLine();

               String x = p;

               MessageDigest m2 = MessageDigest.getInstance("MD5");

               m2.update(x.getBytes());

               byte a[] = m2.digest();

               String result = "";

               for (int i = 0; i < a.length; i++) {

                  result += Integer.toHexString((0x000000ff & a[i]) | 0xffffff00)

                         .substring(6);

               }

               System.out.println(result);

               if (aline3.equals(result)) {

                  System.out.println("匹配成功");

               }

               out.println("匹配成功");

               out.close();

               in.close();

               sc.close();

           } catch (Exception e) {

               System.out.println(e);

           }

        }

        public static String parseByte2HexStr(byte buf[]) {

           StringBuffer sb = new StringBuffer();

           for (int i = 0; i < buf.length; i++) {

               String hex = Integer.toHexString(buf[i] & 0xFF);

               if (hex.length() == 1) {

                  hex = '0' + hex;

               }

               sb.append(hex.toUpperCase());

           }

           return sb.toString();

        }

        public static byte[] parseHexStr2Byte(String hexStr) {

           if (hexStr.length() < 1)

               return null;

           byte[] result = new byte[hexStr.length() / 2];

           for (int i = 0; i < hexStr.length() / 2; i++) {

               int high = Integer.parseInt(hexStr.substring(i * 2, i * 2 + 1), 16);

               int low = Integer.parseInt(hexStr.substring(i * 2 + 1, i * 2 + 2),

                      16);

               result[i] = (byte) (high * 16 + low);

           }

           return result;

        }

    }

    客户端:

    package exp4;

    import java.net.*;

    import java.io.*;

    import java.security.*;

    import javax.crypto.*;

    import javax.crypto.spec.*;

    import java.security.spec.*;

    import javax.crypto.interfaces.*;

    import java.security.interfaces.*;

    import java.math.*;

    public class Client {

        public static void main(String srgs[]) throws Exception {

           try {

               KeyGenerator kg = KeyGenerator.getInstance("DESede");

               kg.init(168);

               SecretKey k = kg.generateKey();

               byte[] ptext2 = k.getEncoded();

               // 创建连接特定服务器的指定端口的Socket对象

               Socket socket = new Socket("222.28.128.119", 8028);

               // 网络输入流

               BufferedReader in = new BufferedReader(new InputStreamReader(

                      socket.getInputStream()));

               // 网络输出流

               PrintWriter out = new PrintWriter(new BufferedWriter(

                      new OutputStreamWriter(socket.getOutputStream())), true);

               // 创建键盘输入流

               BufferedReader stdin = new BufferedReader(new InputStreamReader(

                      System.in));

               FileInputStream f3 = new FileInputStream("Skey_RSA_pub.dat");

               ObjectInputStream b2 = new ObjectInputStream(f3);

               RSAPublicKey pbk = (RSAPublicKey) b2.readObject();

               BigInteger e = pbk.getPublicExponent();

               BigInteger n = pbk.getModulus();

               BigInteger m = new BigInteger(ptext2);

               BigInteger c = m.modPow(e, n);

               String cs = c.toString();

               out.println(cs); // 通过网络传送到服务器

               System.out.print("请输入待发送的数据:");

               String s = stdin.readLine();

               Cipher cp = Cipher.getInstance("DESede");

               cp.init(Cipher.ENCRYPT_MODE, k);

               byte ptext[] = s.getBytes("UTF8");

               byte ctext[] = cp.doFinal(ptext);

               String str = parseByte2HexStr(ctext);

               out.println(str);

               String x = s;

               MessageDigest m2 = MessageDigest.getInstance("MD5");

               m2.update(x.getBytes());

               byte a[] = m2.digest();

               String result = "";

               for (int i = 0; i < a.length; i++) {

                  result += Integer.toHexString((0x000000ff & a[i]) | 0xffffff00)

                         .substring(6);

               }

               System.out.println(result);

               out.println(result);

               str = in.readLine();// 从网络输入流读取结果

               System.out.println("从服务器接收到的结果为:" + str); // 输出服务器返回的结果

           } catch (Exception e) {

               System.out.println(e);

           } finally {

           }

        }

        public static String parseByte2HexStr(byte buf[]) {

           StringBuffer sb = new StringBuffer();

           for (int i = 0; i < buf.length; i++) {

               String hex = Integer.toHexString(buf[i] & 0xFF);

               if (hex.length() == 1) {

                  hex = '0' + hex;

               }

               sb.append(hex.toUpperCase());

           }

           return sb.toString();

        }

        public static byte[] parseHexStr2Byte(String hexStr) {

           if (hexStr.length() < 1)

               return null;

           byte[] result = new byte[hexStr.length() / 2];

           for (int i = 0; i < hexStr.length() / 2; i++) {

               int high = Integer.parseInt(hexStr.substring(i * 2, i * 2 + 1), 16);

               int low = Integer.parseInt(hexStr.substring(i * 2 + 1, i * 2 + 2),

                      16);

               result[i] = (byte) (high * 16 + low);

           }

           return result;

        }

    }

    三、实验体会

    这次实验是Java课程的最后一个实验,实验内容比较有难度。

    首先,老师提供了加解密方法的代码和实验的步骤。我们遇到的第一个问题是将代码整合。由于要使用服务器的公钥加密密钥key,还需要验证信息的完整性,在整合代码方面比较有难度。在根据课本TCP的实例,将所需要的java文件和dat文件导入后,整合好了代码。之后,我们进行了测试,遇到了第二个问题,连接成功后提示:

     

    后来经过几次调试发现是网络的问题。调试成功后,可以正常传输信息。

    这次实验,我学会了在客户端和服务器之间加解密传输信息,这对于维护信息安全十分有效。因为加解密都是用老师提供的代码,所以整合代码还相对容易些。但在自己编写代码这方面,还需要课下多多锻炼提高。

    附:

    步骤

    耗时

    百分比

    需求分析

    0.5h

    5%

    设计

    1.5h

    15%

    代码实现

    5h

    50%

    测试

    2h

    20%

    分析总结

    1h

    10%

  • 相关阅读:
    How to publish ASP.NET application
    Enable(Disable) JavaScript on Browsers(Opera,IE,Firefox,Googlechrome,Safari)
    批处理学习笔记
    [转] Springboot 解决跨域的四种姿势
    HTML+CSS编写规范
    利用CSS3的transform做的动态时钟
    JS特效文字逐个显示
    Asp.Net平台下的图片在线裁剪功能的实现
    CSS3实践之路(一):CSS3之我观
    推荐个通用的多图片上传插件 multiimage。
  • 原文地址:https://www.cnblogs.com/CatherineZang/p/4572656.html
Copyright © 2011-2022 走看看