实验二 电子传输系统安全-进展2
一、利用java程序实现文件加密
我们的文件在计算机中都是以二进制的形式存储,而Java中IO流(字节流和字符流)可以实现对底层文件的读取,故利用Java的IO流进行文件拷贝时,可以对底层二进制进行加密操作,随后通过解密操可以还原。
java代码:
package demo;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
public class IOSercet {
public static void main(String[] args) throws IOException {
decrypt("C:\\Users\\Dell\\Desktop\\原视频.avi");
}
//加密
public static void secret(String str) throws IOException{
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(str));
String [] s=str.split("\\.");
BufferedOutputStream bos = new BufferedOutputStream(new
FileOutputStream("C:\\Users\\Dell\\Desktop\\marden1."+s[1]));
int n;
long a=System.currentTimeMillis();
while((n=bis.read())!=-1){
bos.write(n+1);
}
long b=System.currentTimeMillis();
bis.close();
bos.close();
System.out.println("加密拷贝成功!");
System.out.println("加密用时:"+(b-a)+"ms");
}
//解密
public static void decrypt(String str) throws IOException{
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(str));
String [] s=str.split("\\.");
BufferedOutputStream bos = new BufferedOutputStream(new
FileOutputStream("C:\\Users\\Dell\\Desktop\\marden2."+s[1]));
int n;
long a=System.currentTimeMillis();
while((n=bis.read())!=-1){
bos.write(n-1);
}
long b=System.currentTimeMillis();
bis.close();
bos.close();
System.out.println("解密拷贝成功!");
System.out.println("解密用时:"+(b-a)+"ms");
}
}
二、编程实现HASH算法-摘要计算
1、封装HASH类
封装为一个类,支持多种计算算法,如下:
hash.h:
#ifndef HASH_H
#define HASH_H
#include <QObject>
#include <QMetaEnum>
#include <QString>
#include <QByteArray>
#include <openssl/sha.h>
/**
* @brief The HASH class
* HASH加密算法实现类,包括Sha、Sha1、Sha224等。
*/
class HASH : public QObject
{
Q_OBJECT
public:
enum Mode
{
SHA1,
SHA224,
SHA256,
SHA384,
SHA512,
RIPEMD160,
MD5
};
Q_ENUM(Mode)
HASH(Mode mode);
void addData(const QByteArray &data);
QByteArray result();
private:
QString modeToString(Mode value);
private:
Mode _mode; ///<HASH算法类型
QByteArray _data; ///<待加密数据
};
#endif // HASH_H
HASH.cpp
#include "HASH.h"
#include <openssl/evp.h>
/**
* @brief HASH::HASH
* @param mode HASH算法类型
*/
HASH::HASH(Mode mode)
:_mode(mode)
{
}
/**
* @brief HASH::addData
* 添加待加密数据
* @param data 数据
*/
void HASH::addData(const QByteArray &data)
{
_data = data;
}
/**
* @brief HASH::result
* 获取加密结果
* @return 加密结果
*/
QByteArray HASH::result()
{
OpenSSL_add_all_digests();
const EVP_MD *md = nullptr;
md = EVP_get_digestbyname(modeToString(_mode).toStdString().c_str());
if(!md) // 不支持的格式
{
return QByteArray();
}
unsigned char mdValue[EVP_MAX_MD_SIZE] = {0};
unsigned int mdLen = 0;
EVP_MD_CTX *mdctx = EVP_MD_CTX_new();
EVP_MD_CTX_init(mdctx);
EVP_DigestInit_ex(mdctx, md, nullptr);
EVP_DigestUpdate(mdctx, _data.data(), _data.size());
EVP_DigestFinal_ex(mdctx, mdValue, &mdLen);
EVP_MD_CTX_free(mdctx);
QByteArray out((const char *)mdValue, mdLen);
return out;
}
/**
* @brief HASH::modeToString
* Mode型枚举值转字符串
* @param value 枚举值
* @return 字符串
*/
QString HASH::modeToString(HASH::Mode value)
{
QMetaEnum metaEnum = QMetaEnum::fromType<Mode>();
const char* key = metaEnum.valueToKey(value);
Q_ASSERT(key != nullptr);
return QString(key);
}
2、测试代码
void createTestData(QByteArray& data, int size)
{
data.resize(size);
for (int i = 0; i < size; i++)
{
data[i] = i % 128;
}
}
void testHash(const QByteArray& data)
{
// Sha1
HASH hash1(HASH::SHA1);
hash1.addData(data);
qDebug() << "SHA1:" << hash1.result().toHex();
// Sha224
HASH hash2(HASH::SHA224);
hash2.addData(data);
qDebug() << "SHA224:" << hash2.result().toHex();
// Sha256
HASH hash3(HASH::SHA256);
hash3.addData(data);
qDebug() << "SHA256:" << hash3.result().toHex();
// Sha384
HASH hash4(HASH::SHA384);
hash4.addData(data);
qDebug() << "SHA384:" << hash4.result().toHex();
// Sha512
HASH hash5(HASH::SHA512);
hash5.addData(data);
qDebug() << "SHA512:" << hash5.result().toHex();
// Ripemd160
HASH hash6(HASH::RIPEMD160);
hash6.addData(data);
qDebug() << "RIPEMD160:" << hash6.result().toHex();
// Md5
HASH hash7(HASH::MD5);
hash7.addData(data);
qDebug() << "MD5:" << hash7.result().toHex();
}
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
// 产生1MB+3B的测试数据,为了使该测试数据长度,不为8或16的整数倍
QByteArray data;
createTestData(data, 1*1024*1024+3);
// 测试HASH
testHash(data);
return a.exec();
}
三、下周计划
1、设计将加密与摘要计算的算法封装进系统代码里
2、学习java调用其他加密算法(如SM3)的方法
3、web页面美化设计
4、小组讨论web安全性问题