📄 locku.cpp
字号:
/****************************************************************************
本着知识共享的原则,我把程序的源代码也放上来,
希望有人能完善它。允许在遵循 GPL 准则的基础上对程序进行修改和重新发布!
****************************************************************************/
//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
#include "Locku.h"
#include "Password.h"
#include "Help.h"
#include "NewFolder.h"
//#include "NewFile.h"
#include <dos.h>
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TMainForm *MainForm;
//---------------------------------------------------------------------------
__fastcall TMainForm::TMainForm(TComponent* Owner)
: TForm(Owner)
{
}
//---------------------------------------------------------------------------
//加密程序初始化
//---------------------------------------------------------------------------
void __fastcall TMainForm::Initialize()
{
//显示当前状态信息
StatusBar1->Panels->Items[0]->Text="准备执行";
Stop=false;
Timer1->Enabled=true;
//初始化加密字
CoolWordLen=8;
CoolWord=new char[CoolWordLen+1];
strcpy(CoolWord,"$#@%!&*^");
//修正了密码为空死循环的BUG,并增加了加密的安全性,又改回来了,嘻嘻
PasswordLen=PasswordDlg->Password->Text.Length();
if(PasswordLen<8) PasswordLen=8;
Password=new char[PasswordLen+1];
strcpy(Password,"VRW&^#T&^");
strcpy(Password,PasswordDlg->Password->Text.c_str());
for(int i=0;i<PasswordLen;i++){
Password[i]^=CoolWord[i%CoolWordLen];
}
//加密字创建结束
//状态条显示
StatusBar1->Panels->Items[1]->Text="From:"+OriginFileName
+"("+AnsiString(OriginFileLen/1024)+"KB)";
StatusBar1->Panels->Items[2]->Text="To:"+ObjectFileName
+"("+AnsiString(ObjectFileLen/1024)+"KB)";
}
//---------------------------------------------------------------------------
//获得密码
//---------------------------------------------------------------------------
bool __fastcall TMainForm::GetPassword()
{
AnsiString s;
PasswordDlg->Label1->Caption="请输入你的密码:";
do{
if(PasswordDlg->ShowModal()==mrCancel){
return false;
}
}while(PasswordDlg->Password->Text.IsEmpty());
s=PasswordDlg->Password->Text;
PasswordDlg->Label1->Caption="确认密码:";
do{
if(PasswordDlg->ShowModal()==mrCancel){
return false;
}
}while(PasswordDlg->Password->Text.IsEmpty());
if(!(s==PasswordDlg->Password->Text)){
MessageDlg("输入的密码不匹配!",mtError,TMsgDlgButtons()<<mbOK,0);
return false;
}
return true;
}
//---------------------------------------------------------------------------
//直接给文件加密
//---------------------------------------------------------------------------
bool __fastcall TMainForm::DirectPut()
{
//如果文件存在,提示是否替换现有文件
if(FileExists(ObjectFileName)){
int Result=MessageDlg("目标文件:\""+ObjectFileName
+"\"已存在,是否替换现有文件?",mtWarning,
TMsgDlgButtons()<<mbYes<<mbNo<<mbCancel,0);
//如果用户按了取消键,返回主窗口
if(Result==mrCancel) return true;
else if(Result==mrNo){
//如果不替换,创建新的文件,提示输入新文件名,默认值为原目标文件前加一下划线
/*NewFileDlg->NewFile->Text="_"+ExtractFileName(ObjectFileName);
if(NewFileDlg->ShowModal()==mrOk){
//如果新建文件确定,目标文件改名为输入的文件名
ObjectFileName=ExtractFileName(NewFileDlg->NewFile->Text);
}*/
ToFile->SetFocus();
return true;
}
}
////////////如果确定密码,开始执行加密程序初始化,否则返回
// if(!GetPassword()) return true;
//打开(创建)文件
if( (TempFileP=fopen(TempFileName.c_str(),"wb")) == NULL){
MessageDlg("创建目标文件出错,请检查是否磁盘已满或磁盘写保护!",mtError,TMsgDlgButtons()<<mbOK,0);
ToFile->SetFocus();
return true;
}
/////////////////////////////////////////////////////////////
//确定密码,开始程序初始化
Initialize();
Timer1->Enabled=false;
///////////初始化完毕,执行加密
/////////////////////////////////////////////////////////////////
ProgressBar1->Max=OriginFileLen/PasswordLen;
StatusBar1->Panels->Items[0]->Text="正在执行...";
//开始执行
char PassChar;
char TempChar=fgetc(OriginFileP);//临时字符,为实现循环加密
int i;//定义循环变量
while(!feof(OriginFileP)){//如果文件结束退出
for(i=0;i<PasswordLen;i++){
PassChar=fgetc(OriginFileP);//读取一个字节
if(feof(OriginFileP)) break; //如果文件结束,跳出
else //否则执行加密算法
{
PassChar^=Password[i];
fputc(PassChar,TempFileP);
}
}
//进度条前进
ProgressBar1->StepIt();
Application->ProcessMessages();
if(Stop) return false;
}
fputc(TempChar^Password[i%PasswordLen],TempFileP);
return false;
}
//---------------------------------------------------------------------------
//直接解密方式
//---------------------------------------------------------------------------
bool __fastcall TMainForm::DirectGet()
{
//如果文件存在,提示是否替换现有文件
if(FileExists(ObjectFileName)){
int Result=MessageDlg("目标文件:\""+ObjectFileName
+"\"已存在,是否替换现有文件?",mtWarning,
TMsgDlgButtons()<<mbYes<<mbNo<<mbCancel,0);
//如果用户按了取消键,返回主窗口
if(Result==mrCancel) return true;
else if(Result==mrNo){
//如果不替换,创建新的文件,提示输入新文件名,默认值为原目标文件前加一下划线
/*NewFileDlg->NewFile->Text="_"+ExtractFileName(ObjectFileName);
if(NewFileDlg->ShowModal()==mrOk){
//如果新建文件确定,目标文件改名为输入的文件名
ObjectFileName=ExtractFileName(NewFileDlg->NewFile->Text);
}*/
ToFile->SetFocus();
return true;
}
}
////////////如果确定密码,开始执行加密程序初始化,否则返回
// if(!GetPassword()) return true;
//打开(创建)文件
if( (TempFileP=fopen(TempFileName.c_str(),"wb")) == NULL){
MessageDlg("创建目标文件出错,请检查是否磁盘已满或磁盘写保护!",mtError,TMsgDlgButtons()<<mbOK,0);
ToFile->SetFocus();
return true;
}
/////////////////////////////////////////////////////////////
//确定密码,开始程序初始化
Initialize();
Timer1->Enabled=false;
///////////初始化完毕,执行加密
/////////////////////////////////////////////////////////////////
ProgressBar1->Max=OriginFileLen/PasswordLen;
StatusBar1->Panels->Items[0]->Text="正在执行...";
//开始执行
char PassChar[2];
fputc(PassChar[0],TempFileP);//临时字符,为实现循环加密
PassChar[1]=fgetc(OriginFileP);
while(!feof(OriginFileP)){//如果文件结束退出
for(int i=0;i<PasswordLen;i++){
PassChar[0]=PassChar[1];
PassChar[0]^=Password[i];
PassChar[1]=fgetc(OriginFileP);
if(feof(OriginFileP)) break; //如果文件结束,跳出
else //否则执行加密算法
fputc(PassChar[0],TempFileP);
}
//进度条前进
ProgressBar1->StepIt();
Application->ProcessMessages();
if(Stop) return false;
}
rewind(TempFileP);
fputc(PassChar[0],TempFileP);
return false;
}
//---------------------------------------------------------------------------
//将文件加密到24位位图
//---------------------------------------------------------------------------
bool __fastcall TMainForm::AddToBmp24()
{
long pic_offset,bmp_len;
/* pic_offset为位图阵列的偏移量,
OriginFilelen保存了被隐藏文件的长度,
bmp_len为实际位图阵列的长度 */
int i,j=0,tag; //tag为BMP图像文件的颜色深度,j为取密码字节,i取位图位
char byte_buf,byte_bufs[8];//读写文件的缓冲区
char mask[8]={ 0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80 };
//用于将被隐藏文件拆分为位形式的掩码
//如果文件不存在,返回
if(!FileExists(ObjectFileName)){
MessageDlg("目标文件:\""+ObjectFileName+"\"不存在",mtError,
TMsgDlgButtons()<<mbOK,0);
return true;
}
//打开位图文件
if( (ObjectFileP=fopen(ObjectFileName.c_str(),"rb") ) == NULL){
MessageDlg("不能打开目标文件:\""+ObjectFileName+"\"",mtError,
TMsgDlgButtons()<<mbOK,0);
ToFile->SetFocus();
return true;
}
////////////读取位图文件信息文件
fread(byte_bufs,2,1,ObjectFileP);
fseek(ObjectFileP,28L,0);
tag=getw(ObjectFileP);//读取BMP图像颜色深度
/////////////如果文件不是24位图文件,返回
if( (byte_bufs[0]!='B') || (byte_bufs[1]!='M') || (tag!=24) ){
MessageDlg("目标文件:\""+ObjectFileName+
"\"不是24Bit位图文件",mtError,TMsgDlgButtons()<<mbYes,0);
return true;
}
///////////////////////////////////////
// if(!GetPassword()) return true;
////////////如果确定密码,开始执行加密程序初始化,否则返回
/////////////////////////////////////////////////////////////
//确定密码,开始程序初始化
if( (TempFileP=fopen(TempFileName.c_str(),"wb") )==NULL){
MessageDlg("创建临时文件出错,请检查是否磁盘已满或磁盘写保护!",mtError,
TMsgDlgButtons()<<mbOK,0);
return true;
}
fseek(ObjectFileP,10L,0);
fread(&pic_offset,4,1,ObjectFileP);
bmp_len=ObjectFileLen-pic_offset-1;//计算位图阵列长度
///////////如果被加密文件长度大于位图所能装载的最大长度,警告
if(OriginFileLen>=bmp_len/8-2){
MessageDlg("待加密文件\""+OriginFileName+"\"太长,无法将其加密到\""
+ObjectFileName+"\"",mtError,TMsgDlgButtons()<<mbOK,0);
FromFile->SetFocus();
return true;
}//end if
///////////////////////////////////////////////////////////////
//打开目标文件成功,准备加密
Initialize();
////////////////////////////////////////////
// 文件指针定位
char *buff=new char[pic_offset];//文件缓冲区,用来转移图片头信息
rewind(ObjectFileP);
fread(buff,pic_offset,1,ObjectFileP);
fwrite(buff,pic_offset,1,TempFileP);
/* fseek(TempFileP,2L,0);
fwrite(&OriginFileLen,4,1,TempFileP);//将被隐藏文件长度写入图像头部偏移2处
fseek(ObjectFileP,pic_offset,0);//定位读写指针到图像的位图阵列开始处
fseek(TempFileP,pic_offset,0);*/
fread(buff,16,1,ObjectFileP);
for(i=0;i<16;i++){
if( OriginFileLen&(1<<i) )buff[i]&=0xfe;
else buff[i]|=1;
}
//fseek(ObjectFileP,-16L,1);
fwrite(buff,16,1,TempFileP);
delete []buff;
buff=new char[1024];//为写图片预留
///////////////////////////////////////////////////////////
Timer1->Enabled=false;
///////////初始化完毕,执行加密
/////////////////////////////////////////////////////////////////
ProgressBar1->Max=OriginFileLen;
StatusBar1->Panels->Items[0]->Text="正在执行...";
//开始执行
fread(byte_bufs,8,1,ObjectFileP);
byte_buf=fgetc(OriginFileP);
while(!feof(ObjectFileP)&&!feof(OriginFileP))
{ //拆分被隐藏文件为位形式并覆盖位图阵列每字节的最低位
byte_buf^=Password[j];
for(i=0;i<8;i++)
{
if((byte_buf&mask[i])>>i)byte_bufs[i]|=1;
else byte_bufs[i]&=0xfe;
}
fwrite(byte_bufs,8,1,TempFileP);
fread(byte_bufs,8,1,ObjectFileP);
byte_buf=fgetc(OriginFileP);
ProgressBar1->StepIt();
j++;
if(j>=PasswordLen) j=0;
Application->ProcessMessages();
if(Stop)return false;
}//end while
if(!feof(ObjectFileP)){//如果未到文件尾
fseek(ObjectFileP,-8L,1);
fread(buff,1024L,1,ObjectFileP);
while(!feof(ObjectFileP)){
fwrite(buff,1024,1,TempFileP);
fread(buff,1024,1,ObjectFileP);
}
}
//fseek(ObjectFileP,-1024L,1);修正
byte_buf=fgetc(ObjectFileP);
while(!feof(ObjectFileP)){
fputc(byte_buf,TempFileP);
byte_buf=fgetc(ObjectFileP);
}//end while
delete []buff;
return false;
}
//---------------------------------------------------------------------------
//从24位位图中提取加密过的文件
//---------------------------------------------------------------------------
bool __fastcall TMainForm::ExtFromBmp24()
{
long pic_offset,len=0;
/* pic_offset为位图阵列的偏移量,
OriginFilelen保存了被隐藏文件的长度,
bmp_len为实际位图阵列的长度 */
int i,j=0,tag; //tag为BMP图像文件的颜色深度,如8位和24位等
char byte_buf,byte_bufs[8];//读写文件的缓冲区
char mask[8]={ 0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80 };
//用于将被隐藏文件拆分为位形式的掩码
////////////读取位图文件信息文件
fread(byte_bufs,2,1,OriginFileP);
fseek(OriginFileP,28L,0);
tag=getw(OriginFileP);//读取BMP图像颜色深度
/////////////如果文件不是24位图文件,返回
if( (byte_bufs[0]!='B') || (byte_bufs[1]!='M') || (tag!=24) ){
MessageDlg("原文件:\""+OriginFileName+
"\"不是24Bit位图文件",mtError,TMsgDlgButtons()<<mbOK,0);
return true;
}
/////////////////////////////////////////////////////////////
//如果文件存在,提示是否替换现有文件
if(FileExists(ObjectFileName)){
int Result=MessageDlg("目标文件:\""+ObjectFileName
+"\"已存在,是否替换现有文件?",mtWarning,
TMsgDlgButtons()<<mbYes<<mbNo<<mbCancel,0);
//如果用户按了取消键,返回主窗口
if(Result==mrCancel) return true;
else if(Result==mrNo){
//如果不替换,创建新的文件,提示输入新文件名,默认值为原目标文件前加一下划线
/*NewFileDlg->NewFile->Text="_"+ExtractFileName(ObjectFileName);
if(NewFileDlg->ShowModal()==mrOk){
//如果新建文件确定,目标文件改名为输入的文件名
ObjectFileName=ExtractFileName(NewFileDlg->NewFile->Text);
}*/
ToFile->SetFocus();
return true;
}
}
//打开(创建)文件
if( (TempFileP=fopen(TempFileName.c_str(),"wb")) == NULL){
MessageDlg("创建目标文件出错,请检查是否磁盘已满或磁盘写保护",
mtError,TMsgDlgButtons()<<mbOK,0);
ToFile->SetFocus();
return true;
}
//打开目标文件成功
/////////////////////////////////////////////////////////////
//确定密码,开始程序初始化
Initialize();
////////////////////////////////////////////
// 文件指针定位
/* fseek(OriginFileP,2L,0);
fread(&ObjectFileLen,4,1,OriginFileP);*///从图像头部偏移2处读取隐藏文件长度*/
fseek(OriginFileP,10L,0);
fread(&pic_offset,4,1,OriginFileP);
fseek(OriginFileP,pic_offset,0);//定位读写指针到图像的位图阵列开始处
char *buff=new char[16];
fread(buff,16,1,OriginFileP);
ObjectFileLen=0;
for(i=0;i<16;i++){
if(!(buff[i]&1))ObjectFileLen|=(1<<i);
}
delete []buff;
///////////////////////////////////////////////////////////
///////////初始化完毕,执行加密
/////////////////////////////////////////////////////////////////
Timer1->Enabled=false;
ProgressBar1->Max=ObjectFileLen;
StatusBar1->Panels->Items[0]->Text="正在执行...";
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -