这个是程序编码训练我做的题目。
加密采用右键方式调用,具体参见程序说明。
应该说加密强度还是比较高的,就是速度太慢了,因为需要大量的CPU计算。
而且我还不会利用双核的资源。

/***********************************************************/
/*                           主要源代码                    */
/***********************************************************/
 
#include <stdlib.h>
#include <stdio.h>
#include <conio.h>
#include <string.h>
#include <time.h>
#include "md5.cpp"
 
char S1[] = "PbWuLYL'p@MY&H5T;S1q](v8SW@Mo)s`";
char S2[] = "v8SWT;S@q](@Mo)s`PbMY&WLYL'puH51";
 
/***************************获取密码***************************/
void getpass(char *psw, int len)
{
	int i = 0;
	char cKEY;
	while (1)
	{
		cKEY = getch();
		if (cKEY == -32 || cKEY == 0) getch();
		if (i < len && (cKEY >= 32 && cKEY <= 126))
		{
			putchar('*');
			psw[i++] = cKEY;
		}
		if (i > 0 && cKEY == 8)
		{
			printf("\b \b");
			i--;
		}
		if (i > 0 && (cKEY == 9 || cKEY == 13))
		{
			psw[i++] = 0;
			putchar('\n');
			break ;
		}
	}
}
 
 
/***************************转换16进制数为字符串***************************/
void convHEX(char *src, char *des, int len)
{
	int i, j;
	unsigned char ch;
	for (i = 0, j = 0; i < len; i++)
	{
		ch=(unsigned char)src[i];
		if (ch / 16 >= 10) des[j++] = ch / 16 + 87;
		else des[j++] = ch / 16 + '0';
		if (ch % 16 >= 10) des[j++] = ch % 16 + 87;
		else des[j++] = ch % 16 + '0';
	}
	des[j++] = 0;
}
 
 
/***************************注册功能***************************/
void reg(char *path)
{
	char command[1024];
	//使用vbscript脚本进行注册
	char DATA[] = "'The script is made by sungjira\nOn Error Resume Next\nSet w = WScript.CreateObject(\"WScript.Shell\")\nSet a = WScript.Arguments\nif StrComp(\"文件加密\",w.regread(\"HKCR\\*\\shell\\en\\\"))=0 then call unreg\nw.regwrite \"HKCR\\*\\shell\\en\\\",\"文件加密\", \"REG_SZ\"\nw.regwrite \"HKCR\\*\\shell\\de\\\",\"文件解密\", \"REG_SZ\"\nw.regwrite \"HKCR\\*\\shell\\en\\command\\\",chr(34)&a(0)&chr(34)&\" 0 \"&chr(34)&\"%1\"&chr(34), \"REG_SZ\"\nw.regwrite \"HKCR\\*\\shell\\de\\command\\\",chr(34)&a(0)&chr(34)&\" 1 \"&chr(34)&\"%1\"&chr(34), \"REG_SZ\"\nwscript.quit\nsub unreg\nw.RegDelete(\"HKCR\\*\\shell\\en\\command\\\")\nw.RegDelete(\"HKCR\\*\\shell\\en\\\")\nw.RegDelete(\"HKCR\\*\\shell\\de\\command\\\")\nw.RegDelete(\"HKCR\\*\\shell\\de\\\")\nwscript.quit\nend sub";
	FILE *vbsfile;
	vbsfile = fopen("reg.vbs", "w");
	fputs(DATA, vbsfile);
	fclose(vbsfile);
	//传递程序路径给vbs
	strcpy(command, "wscript.exe reg.vbs \"");
	strcat(command, path);
	strcat(command, "\"");
	system(command);
	remove("reg.vbs");
	HANDLE consolehwnd; 
    consolehwnd = GetStdHandle(STD_OUTPUT_HANDLE);
	system("CLS");
	SetConsoleTextAttribute(consolehwnd,10);
 
	printf("************************************************************");
	printf("                        文件加密程序                        ");
	printf("************************************************************");
	SetConsoleTextAttribute(consolehwnd,15);
	printf("程序功能:\n\n");
	printf("    ·运行一次即可完成注册。\n");
	printf("    ·再次运行即可完成卸载。\n");
	printf("    ·采用md5加密。\n");
	printf("    ·右键方式快捷调用。\n\n\n");
	printf("成员:刘迎、张小容、简琳、舒俊杰\n");
	printf("联系QQ:369339353\n");
	printf("2009年5月\n\n");
	printf("按任意键退出...");
 
	getch();
	exit(EXIT_SUCCESS);
}
 
 
/***************************主函数***************************/
int main(int argc, char **argv)
{
	SetConsoleTitle("文件加密程序");
	system("mode con cols=60 lines=16");
 
	if (argc == 1) reg(argv[0]);
 
	//开始
	char password1[512], password2[512], szDigest[16];
	double begin, end;
	int i;
	FILE *fp, *temp;
	long filelen, speed;
 
	fp = fopen(argv[2], "rb");
	fseek(fp, 0L, 2);
	filelen = ftell(fp);
 
	if (argv[1][0] == '0')   //参数为0则为加密
	{
		//加密
		while (1)
		{
			system("CLS");
			puts("您正在进行的是加密操作。");
			printf("文件:\"%s\"\n\n", argv[2]);
			printf("加密密码:");
			getpass(password1, 50);
			printf("确认密码:");
			getpass(password2, 50);
			if (strcmp(password1, password2) != 0)
			{
				printf("\n\n你输入的两次密码不相同,请重新输入。");
				Sleep(800);
			}
			else break;
		}
 
		//密码验证通过,生成md5值,并且转换成字符串,然后参与加密
		MD5Digest(password1, strlen(password1), szDigest);
		convHEX(szDigest, password1, 16);
		for (i = 0;i < 32;i++) S1[i] += password1[i];
 
		//开始加密算法,原来的数据加上S1
		puts("\n\n正在进行加密,请耐心等待....");
		begin = clock();
		temp = fopen("temp", "wb");
		fseek(fp, 0L, 0);
		for (;ftell(fp) < filelen;)
			fputc(fgetc(fp) + S1[(ftell(fp) + 32) % 32], temp);
		//加密密码,然后输出到文件尾
		for (i = 0;i < 32;i++) password1[i] ^= S2[i];
		fputs(password1, temp);
		fclose(temp);
		fclose(fp);
		//用临时文件覆盖源文件
		remove(argv[2]);
		rename("temp", argv[2]);
		end = clock();
		puts("\n\n加密完成。");
		//统计信息,程序结束
		printf("总共耗时:%.2f秒\n", (end - begin) / 1000);
		speed = (long)((double)filelen / (end - begin) / 1.024);
		if (filelen < 1024) speed = 500;
		printf("处理速度:%dkb/s\n", speed);
		puts("\n按任意键退出.");
		getch();
	}
	else
	{
		//解密
		while (1)
		{
			system("CLS");
			puts("您正在进行的是解密操作。");
			printf("文件:\"%s\"\n\n", argv[2]);
			printf("解密密码:");
			getpass(password1, 50);
			MD5Digest(password1, strlen(password1), szDigest);
			convHEX(szDigest, password1, 16);
			//从文件尾读取密码,并还原成md5
			fseek(fp, -32L, 2);
			fgets(password2, 33, fp);
			for (i = 0;i < 32;i++) password2[i] ^= S2[i];
			if (strcmp(password1, password2) != 0)
			{
				printf("\n\n你输入的解密密码不正确,请重新输入。");
				Sleep(800);
			}
			else break;
		}
		//密码验证通过,密码然后参与解密,这里再减回来,抛弃文件末尾的密码信息。
		for (i = 0;i < 32;i++) S1[i] += password1[i];
		puts("\n\n正在进行解密,请耐心等待....");
		begin = clock();
		temp = fopen("temp", "wb");
		fseek(fp, 0L, 0);
		for (;ftell(fp) < filelen - 32;)
			fputc(fgetc(fp) - S1[(ftell(fp) + 32) % 32], temp);
		fclose(temp);
		fclose(fp);
		//用临时文件覆盖源文件
		remove(argv[2]);
		rename("temp", argv[2]);
		end = clock();
		puts("\n\n解密完成。");
		//统计信息,程序结束
		printf("总共耗时:%.2f秒\n", (end - begin) / 1000);
		speed = (long)((double)filelen / (end - begin) / 1.024);
		if (filelen < 1024) speed = 500;
		printf("处理速度:%dkb/s\n", speed);
		puts("\n按任意键退出.");
		getch();
	}
}

这个本来是一个小组完成的,不过所有的代码都是我写的,呜呜……
其他的几个全是女生,我带着她们。
下载附件:
编码训练(包含源代码,执行程序,课程报告书)

原创文章,转载请注明: 转载自耍下
本文链接地址: 自己写的C语言文件加密