C 我怎样才能让这个蛮力算法以增量方式检查字母
对于这个任务,我必须使用C中的pthreads来制作一个蛮力密码破解程序 下面的代码使用for循环生成一个6个字母的密码(最好是8个字母长),然后我使用crypt_r对其进行散列,并将其与我在执行程序时给出的散列和salt进行比较 散列和salt从一开始就被接收,存储在一个名为dataStr的结构中,然后将其提供给pthreadCreate 这看起来很简单,但即使我将数组设置为空终止字符,在执行时程序仍然将整个设置为“aaaaa”。问题是它忽略了长度为1-4个字符的密码 以下是我使用的数据结构:C 我怎样才能让这个蛮力算法以增量方式检查字母,c,brute-force,C,Brute Force,对于这个任务,我必须使用C中的pthreads来制作一个蛮力密码破解程序 下面的代码使用for循环生成一个6个字母的密码(最好是8个字母长),然后我使用crypt_r对其进行散列,并将其与我在执行程序时给出的散列和salt进行比较 散列和salt从一开始就被接收,存储在一个名为dataStr的结构中,然后将其提供给pthreadCreate 这看起来很简单,但即使我将数组设置为空终止字符,在执行时程序仍然将整个设置为“aaaaa”。问题是它忽略了长度为1-4个字符的密码 以下是我使用的数据结构:
typedef struct {
char * hash; //hashed code given in argv[1]
char * salt; //salt for hashed code given in argv[2]
int start; //starting char in alphabet for first letter
int end; //ending char in alphabet for first letter
int id; //thread id
} dataStruct;
void * thread(void * arg) {
struct timespec start, finish; //Data structure for time.h library
clock_gettime(CLOCK_MONOTONIC, &start); //Start chronometer
double elapsed;
struct crypt_data* cdata = (struct crypt_data *)malloc(sizeof(struct crypt_data));
cdata->initialized = 0;
dataStruct dataStr = *((dataStruct*)(arg)); //receive structure in arguement
const char * alphabet = get_alphabet(); //create alphabet
bool pw_found = false; //boolean used for
int retDone = 1;
char * pwd = malloc(PW_SIZE * sizeof(char));
memset(pwd, '\0', PW_SIZE);
int i,j,k,l,m,n;
for (i = dataStr.start; i <= dataStr.end; i++) {
for (j = 0; j <= ALPHABET_SIZE; j++) {
for (k = 0; k <= ALPHABET_SIZE; k++) {
for (l = 0; l <= ALPHABET_SIZE; l++) {
for (m = 0; m <= ALPHABET_SIZE; m++) {
for (n = 0; n <= ALPHABET_SIZE; n++) {
if (pw_found) {
clock_gettime(CLOCK_MONOTONIC, &finish);
elapsed = finish.tv_sec - start.tv_sec;
elapsed += (finish.tv_nsec - start.tv_nsec) / 1000000000.0;
printf("Time elapsed : %f sec(s) \n\n", elapsed); //Time
pthread_exit(&retDone);
}
pwd[0] = alphabet[i];
pwd[1] = alphabet[j];
pwd[2] = alphabet[k];
pwd[3] = alphabet[l];
pwd[4] = alphabet[m];
pwd[5] = alphabet[n];
printf("%s\n", pwd);
char * hash = crypt_r(pwd, dataStr.salt, cdata);
if (strcmp(hash, dataStr.hash) == 0) {
printf("\nPassword : %s\n", pwd);
pw_found = true;
}
}
}
}
}
}
}
pthread_exit(&retDone);
}
尺寸定义:
//Definitions
#define PW_SIZE 8
#define ALPHABET_SIZE 66
#define HASH_MAX_SIZE 128
下面是代码本身
typedef struct {
char * hash; //hashed code given in argv[1]
char * salt; //salt for hashed code given in argv[2]
int start; //starting char in alphabet for first letter
int end; //ending char in alphabet for first letter
int id; //thread id
} dataStruct;
void * thread(void * arg) {
struct timespec start, finish; //Data structure for time.h library
clock_gettime(CLOCK_MONOTONIC, &start); //Start chronometer
double elapsed;
struct crypt_data* cdata = (struct crypt_data *)malloc(sizeof(struct crypt_data));
cdata->initialized = 0;
dataStruct dataStr = *((dataStruct*)(arg)); //receive structure in arguement
const char * alphabet = get_alphabet(); //create alphabet
bool pw_found = false; //boolean used for
int retDone = 1;
char * pwd = malloc(PW_SIZE * sizeof(char));
memset(pwd, '\0', PW_SIZE);
int i,j,k,l,m,n;
for (i = dataStr.start; i <= dataStr.end; i++) {
for (j = 0; j <= ALPHABET_SIZE; j++) {
for (k = 0; k <= ALPHABET_SIZE; k++) {
for (l = 0; l <= ALPHABET_SIZE; l++) {
for (m = 0; m <= ALPHABET_SIZE; m++) {
for (n = 0; n <= ALPHABET_SIZE; n++) {
if (pw_found) {
clock_gettime(CLOCK_MONOTONIC, &finish);
elapsed = finish.tv_sec - start.tv_sec;
elapsed += (finish.tv_nsec - start.tv_nsec) / 1000000000.0;
printf("Time elapsed : %f sec(s) \n\n", elapsed); //Time
pthread_exit(&retDone);
}
pwd[0] = alphabet[i];
pwd[1] = alphabet[j];
pwd[2] = alphabet[k];
pwd[3] = alphabet[l];
pwd[4] = alphabet[m];
pwd[5] = alphabet[n];
printf("%s\n", pwd);
char * hash = crypt_r(pwd, dataStr.salt, cdata);
if (strcmp(hash, dataStr.hash) == 0) {
printf("\nPassword : %s\n", pwd);
pw_found = true;
}
}
}
}
}
}
}
pthread_exit(&retDone);
}
void*线程(void*arg){
struct timespec start,finish;//time.h库的数据结构
时钟获取时间(时钟单调,&开始);//开始计时
双倍过去;
struct crypt_data*cdata=(struct crypt_data*)malloc(sizeof(struct crypt_data));
cdata->初始化=0;
dataStruct dataStr=*((dataStruct*)(arg));//arguement中的接收结构
const char*alphabet=get_alphabet();//创建字母表
bool pw_found=false;//用于
int-retDone=1;
char*pwd=malloc(PW_大小*sizeof(char));
膜组(pwd,'\0',PW_尺寸);
int i,j,k,l,m,n;
for(i=dataStr.start;i指针可用于完成此操作。ppw
将指向pw
数组中的某个位置。pch
将指向字符
数组中的某个位置。递增(++)和递减(--)指针在各自数组的元素内移动指针。取消引用(*)允许访问指针指向的值。used
是pw
中已使用的元素数。对于第一个元素,它从0开始,向SIZE
增加。可以修改字符,以包括有效的字母、数字和符号。请注意,没有双面字符例如,如果字母u
多次出现,程序将进入无限循环
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define SIZE 5
int main( void)
{
char pw[SIZE + 1] = "";
char *ppw = NULL;
char *pch = NULL;
char characters[] = "abcdefghijklmnopqrstuvwxyz";
int used = 0;
int out = 1;
int last = strlen ( characters) - 1;
//set pw
pw[used] = characters[0];
pw[used + 1] = '\0';
while ( used < SIZE) {//loop until all elements of pw have been used
ppw = &pw[used];//set ppw to point to last used element of pw
while ( ppw >= pw) {//so ppw always points to an element of pw
if ( ( pch = strchr ( characters, *ppw)) != NULL) {//get pointer into characters for current value that ppw point to
if ( out) {//print when appropriate
printf ( "%s\n", pw);
}
if ( pch < &characters[last]) {//pch does not point to last element of characters
++pch;//pch points to next element of characters
*ppw = *pch;//set what ppw points to to be the same as what pch points to
if ( ppw != &pw[used]) {//ppw is not pointing to last element of pw
ppw = &pw[used];
}
out = 1;//allow printing
}
else {//pch is pointing to last element of characters
*ppw = characters[0];//set what ppw points to to be the first element of characters
ppw--;//ppw points to next lower element of pw. ex from pw[n] to pw[n-1]
out = 0;//disable printing
}
}
}//exit loop when ppw points to address less than pw
used++;//increase elements in use
memset ( pw, characters[0], used);//reset all elements to first element of characters
pw[used + 1] = '\0';//just in case, terminate
}//exit loop when all elements have been used
exit ( 0);
}
指针可以用来完成这项任务。ppw
将指向pw
数组中的某个地方。pch
将指向字符
数组中的某个地方。递增(++)和递减(--)指针将在各自数组的元素内移动指针。取消引用(*)允许访问指针指向的值。used
是pw
中已使用的元素数。对于第一个元素,它从0开始,向SIZE
增加。可以修改字符,以包括有效的字母、数字和符号。请注意,没有双面字符例如,如果字母u
多次出现,程序将进入无限循环
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define SIZE 5
int main( void)
{
char pw[SIZE + 1] = "";
char *ppw = NULL;
char *pch = NULL;
char characters[] = "abcdefghijklmnopqrstuvwxyz";
int used = 0;
int out = 1;
int last = strlen ( characters) - 1;
//set pw
pw[used] = characters[0];
pw[used + 1] = '\0';
while ( used < SIZE) {//loop until all elements of pw have been used
ppw = &pw[used];//set ppw to point to last used element of pw
while ( ppw >= pw) {//so ppw always points to an element of pw
if ( ( pch = strchr ( characters, *ppw)) != NULL) {//get pointer into characters for current value that ppw point to
if ( out) {//print when appropriate
printf ( "%s\n", pw);
}
if ( pch < &characters[last]) {//pch does not point to last element of characters
++pch;//pch points to next element of characters
*ppw = *pch;//set what ppw points to to be the same as what pch points to
if ( ppw != &pw[used]) {//ppw is not pointing to last element of pw
ppw = &pw[used];
}
out = 1;//allow printing
}
else {//pch is pointing to last element of characters
*ppw = characters[0];//set what ppw points to to be the first element of characters
ppw--;//ppw points to next lower element of pw. ex from pw[n] to pw[n-1]
out = 0;//disable printing
}
}
}//exit loop when ppw points to address less than pw
used++;//increase elements in use
memset ( pw, characters[0], used);//reset all elements to first element of characters
pw[used + 1] = '\0';//just in case, terminate
}//exit loop when all elements have been used
exit ( 0);
}
不显示大小定义等,但通常显示循环,例如(j=0;j太宽。不要发布文本图像。好吧,它们有助于改进你的问题,使之符合网站规则。这就增加了你的问题得到答案的机会。我认为它们很有建设性。当我看到6个内部循环时,设计中有一些错误,很可能是j
otherwise这基本上是正确的方法,这是对许多循环使用蛮力的方式。有一些小的改进要做,但大部分工作是通过crypt\r
完成的,这会减慢程序的速度。您不显示大小定义等,但通常是一个循环,例如(j=0;j太宽。不要发布文本图像。好吧,它们有助于改进你的问题,使之符合网站规则。这就增加了你的问题得到答案的机会。我认为它们很有建设性。当我看到6个内部循环时,设计中有一些错误,很可能是j
otherwise这基本上是正确的方法,这是对许多循环使用蛮力的方式。有一些小的改进要做,但大部分工作都是通过crypt\u r
来完成的,这会减慢程序的速度。这太棒了!我将其集成到pthread中,以便对密码使用蛮力,它就像一个符咒一样工作。当我们接近6个字符。所以我在程序开始时问我们要执行多少个线程。基于此,我切掉字母表(除以线程数)。这样,每个线程都可以在特定的范围内工作。您知道在这段代码中我可以在哪里设置字符生成的起点和终点吗?下面是完整代码的链接:我使用此函数仅打印字符*字符=[a,b,c];一旦它到达cc,它就不会尝试aaa、aab、aac。相反,它会直接跳到aba、abb、abc。这一个很好,但不需要像第一个while条件中那样将大小定义为超出所需的一个(大小-1)。通过删除此项,我们可以将大小定义为所需的实际大小。将最后两行更改为memset(pw,characters[0],used);
和pw[used]='\0';
这太棒了!我将它集成到一个pthread中,以暴力破解密码,它就像一个符咒一样工作。当我们接近6个字符时,它会变慢。所以我做的是在程序开始时询问我们要执行多少个线程。基于此,我切碎了字母表(除以线程数)。这样每个线程都可以在一定范围内工作。你知道在这段代码中我可以在哪里设置字符生成的起点和终点吗?下面是完整代码的链接:我使用此函数打印长度为3的字符*字符=[a,b,c];以及