/**
* Author . . . . . . : See docs / credits . txt
* License . . . . . : MIT
*/
# include "common.h"
# include "types.h"
# include "memory.h"
# include "event.h"
# include "logfile.h"
# include "shared.h"
# include "folder.h"
# include "rp.h"
# include "wordlist.h"
# include "straight.h"
static int straight_ctx_add_wl ( hashcat_ctx_t * hashcat_ctx , const char * dict )
{
if ( hc_path_has_bom ( dict ) = = true )
{
event_log_error ( hashcat_ctx , " %s: Byte Order Mark (BOM) was detected " , dict ) ;
return - 1 ;
}
straight_ctx_t * straight_ctx = hashcat_ctx - > straight_ctx ;
if ( straight_ctx - > dicts_avail = = straight_ctx - > dicts_cnt )
{
straight_ctx - > dicts = ( char * * ) hcrealloc ( straight_ctx - > dicts , straight_ctx - > dicts_avail * sizeof ( char * ) , INCR_DICTS * sizeof ( char * ) ) ;
straight_ctx - > dicts_avail + = INCR_DICTS ;
}
straight_ctx - > dicts [ straight_ctx - > dicts_cnt ] = hcstrdup ( dict ) ;
straight_ctx - > dicts_cnt + + ;
return 0 ;
}
int straight_ctx_update_loop ( hashcat_ctx_t * hashcat_ctx )
{
combinator_ctx_t * combinator_ctx = hashcat_ctx - > combinator_ctx ;
induct_ctx_t * induct_ctx = hashcat_ctx - > induct_ctx ;
hashes_t * hashes = hashcat_ctx - > hashes ;
logfile_ctx_t * logfile_ctx = hashcat_ctx - > logfile_ctx ;
mask_ctx_t * mask_ctx = hashcat_ctx - > mask_ctx ;
status_ctx_t * status_ctx = hashcat_ctx - > status_ctx ;
straight_ctx_t * straight_ctx = hashcat_ctx - > straight_ctx ;
user_options_extra_t * user_options_extra = hashcat_ctx - > user_options_extra ;
user_options_t * user_options = hashcat_ctx - > user_options ;
if ( user_options - > attack_mode = = ATTACK_MODE_STRAIGHT )
{
if ( user_options_extra - > wordlist_mode = = WL_MODE_FILE )
{
if ( induct_ctx - > induction_dictionaries_cnt )
{
straight_ctx - > dict = induct_ctx - > induction_dictionaries [ induct_ctx - > induction_dictionaries_pos ] ;
}
else
{
straight_ctx - > dict = straight_ctx - > dicts [ straight_ctx - > dicts_pos ] ;
}
logfile_sub_string ( straight_ctx - > dict ) ;
for ( u32 i = 0 ; i < user_options - > rp_files_cnt ; i + + )
{
logfile_sub_var_string ( " rulefile " , user_options - > rp_files [ i ] ) ;
}
HCFILE fp ;
if ( hc_fopen ( & fp , straight_ctx - > dict , " rb " ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , straight_ctx - > dict , strerror ( errno ) ) ;
return - 1 ;
}
const int rc = count_words ( hashcat_ctx , & fp , straight_ctx - > dict , & status_ctx - > words_cnt ) ;
hc_fclose ( & fp ) ;
if ( rc = = - 1 )
{
event_log_error ( hashcat_ctx , " Integer overflow detected in keyspace of wordlist: %s " , straight_ctx - > dict ) ;
return - 1 ;
}
if ( status_ctx - > words_cnt = = 0 )
{
logfile_sub_msg ( " STOP " ) ;
return 0 ;
}
}
}
else if ( user_options - > attack_mode = = ATTACK_MODE_COMBI )
{
logfile_sub_string ( combinator_ctx - > dict1 ) ;
logfile_sub_string ( combinator_ctx - > dict2 ) ;
if ( combinator_ctx - > combs_mode = = COMBINATOR_MODE_BASE_LEFT )
{
HCFILE fp ;
if ( hc_fopen ( & fp , combinator_ctx - > dict1 , " rb " ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , combinator_ctx - > dict1 , strerror ( errno ) ) ;
return - 1 ;
}
const int rc = count_words ( hashcat_ctx , & fp , combinator_ctx - > dict1 , & status_ctx - > words_cnt ) ;
hc_fclose ( & fp ) ;
if ( rc = = - 1 )
{
event_log_error ( hashcat_ctx , " Integer overflow detected in keyspace of wordlist: %s " , combinator_ctx - > dict1 ) ;
return - 1 ;
}
}
else if ( combinator_ctx - > combs_mode = = COMBINATOR_MODE_BASE_RIGHT )
{
HCFILE fp ;
if ( hc_fopen ( & fp , combinator_ctx - > dict2 , " rb " ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , combinator_ctx - > dict2 , strerror ( errno ) ) ;
return - 1 ;
}
const int rc = count_words ( hashcat_ctx , & fp , combinator_ctx - > dict2 , & status_ctx - > words_cnt ) ;
hc_fclose ( & fp ) ;
if ( rc = = - 1 )
{
event_log_error ( hashcat_ctx , " Integer overflow detected in keyspace of wordlist: %s " , combinator_ctx - > dict2 ) ;
return - 1 ;
}
}
if ( status_ctx - > words_cnt = = 0 )
{
logfile_sub_msg ( " STOP " ) ;
return 0 ;
}
}
else if ( user_options - > attack_mode = = ATTACK_MODE_BF )
{
logfile_sub_string ( mask_ctx - > mask ) ;
}
else if ( ( user_options - > attack_mode = = ATTACK_MODE_HYBRID1 ) | | ( user_options - > attack_mode = = ATTACK_MODE_HYBRID2 ) )
{
if ( induct_ctx - > induction_dictionaries_cnt )
{
straight_ctx - > dict = induct_ctx - > induction_dictionaries [ induct_ctx - > induction_dictionaries_pos ] ;
}
else
{
straight_ctx - > dict = straight_ctx - > dicts [ straight_ctx - > dicts_pos ] ;
}
logfile_sub_string ( straight_ctx - > dict ) ;
logfile_sub_string ( mask_ctx - > mask ) ;
HCFILE fp ;
if ( hc_fopen ( & fp , straight_ctx - > dict , " rb " ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , straight_ctx - > dict , strerror ( errno ) ) ;
return - 1 ;
}
const int rc = count_words ( hashcat_ctx , & fp , straight_ctx - > dict , & status_ctx - > words_cnt ) ;
hc_fclose ( & fp ) ;
if ( rc = = - 1 )
{
event_log_error ( hashcat_ctx , " Integer overflow detected in keyspace of wordlist: %s " , straight_ctx - > dict ) ;
return - 1 ;
}
if ( status_ctx - > words_cnt = = 0 )
{
logfile_sub_msg ( " STOP " ) ;
return 0 ;
}
}
else if ( user_options - > attack_mode = = ATTACK_MODE_ASSOCIATION )
{
if ( user_options_extra - > wordlist_mode = = WL_MODE_FILE )
{
straight_ctx - > dict = straight_ctx - > dicts [ straight_ctx - > dicts_pos ] ;
logfile_sub_string ( straight_ctx - > dict ) ;
for ( u32 i = 0 ; i < user_options - > rp_files_cnt ; i + + )
{
logfile_sub_var_string ( " rulefile " , user_options - > rp_files [ i ] ) ;
}
HCFILE fp ;
if ( hc_fopen ( & fp , straight_ctx - > dict , " rb " ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , straight_ctx - > dict , strerror ( errno ) ) ;
return - 1 ;
}
const int rc = count_words ( hashcat_ctx , & fp , straight_ctx - > dict , & status_ctx - > words_cnt ) ;
hc_fclose ( & fp ) ;
if ( rc = = - 1 )
{
event_log_error ( hashcat_ctx , " Integer overflow detected in keyspace of wordlist: %s " , straight_ctx - > dict ) ;
return - 1 ;
}
if ( ( status_ctx - > words_cnt / straight_ctx - > kernel_rules_cnt ) ! = hashes - > salts_cnt )
{
event_log_error ( hashcat_ctx , " Number of words in wordlist %s is not in sync with number of salts (words: % " PRIu64 " , salts: %d) " , straight_ctx - > dict , status_ctx - > words_cnt , hashes - > salts_cnt ) ;
return - 1 ;
}
if ( status_ctx - > words_cnt = = 0 )
{
logfile_sub_msg ( " STOP " ) ;
return 0 ;
}
}
}
return 0 ;
}
int straight_ctx_init ( hashcat_ctx_t * hashcat_ctx )
{
straight_ctx_t * straight_ctx = hashcat_ctx - > straight_ctx ;
user_options_extra_t * user_options_extra = hashcat_ctx - > user_options_extra ;
user_options_t * user_options = hashcat_ctx - > user_options ;
straight_ctx - > enabled = false ;
if ( user_options - > hash_info = = true ) return 0 ;
if ( user_options - > left = = true ) return 0 ;
if ( user_options - > backend_info = = true ) return 0 ;
if ( user_options - > show = = true ) return 0 ;
if ( user_options - > usage = = true ) return 0 ;
if ( user_options - > version = = true ) return 0 ;
if ( user_options - > attack_mode = = ATTACK_MODE_BF ) return 0 ;
straight_ctx - > enabled = true ;
/**
* generate NOP rules
*/
if ( ( user_options - > rp_files_cnt = = 0 ) & & ( user_options - > rp_gen = = 0 ) )
{
straight_ctx - > kernel_rules_buf = ( kernel_rule_t * ) hcmalloc ( sizeof ( kernel_rule_t ) ) ;
straight_ctx - > kernel_rules_buf [ 0 ] . cmds [ 0 ] = RULE_OP_MANGLE_NOOP ;
straight_ctx - > kernel_rules_cnt = 1 ;
}
else
{
if ( user_options - > rp_files_cnt )
{
if ( kernel_rules_load ( hashcat_ctx , & straight_ctx - > kernel_rules_buf , & straight_ctx - > kernel_rules_cnt ) = = - 1 ) return - 1 ;
}
else if ( user_options - > rp_gen )
{
if ( kernel_rules_generate ( hashcat_ctx , & straight_ctx - > kernel_rules_buf , & straight_ctx - > kernel_rules_cnt ) = = - 1 ) return - 1 ;
}
}
/**
* wordlist based work
*/
if ( ( user_options - > attack_mode = = ATTACK_MODE_STRAIGHT ) | | ( user_options - > attack_mode = = ATTACK_MODE_ASSOCIATION ) )
{
if ( user_options_extra - > wordlist_mode = = WL_MODE_FILE )
{
for ( int i = 0 ; i < user_options_extra - > hc_workc ; i + + )
{
char * l0_filename = user_options_extra - > hc_workv [ i ] ;
// at this point we already verified the path actually exist and is readable
if ( hc_path_is_directory ( l0_filename ) = = true )
{
char * * dictionary_files ;
dictionary_files = scan_directory ( l0_filename ) ;
if ( dictionary_files ! = NULL )
{
qsort ( dictionary_files , ( size_t ) count_dictionaries ( dictionary_files ) , sizeof ( char * ) , sort_by_stringptr ) ;
for ( int d = 0 ; dictionary_files [ d ] ! = NULL ; d + + )
{
char * l1_filename = dictionary_files [ d ] ;
if ( hc_path_read ( l1_filename ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , l1_filename , strerror ( errno ) ) ;
hcfree ( dictionary_files ) ;
return - 1 ;
}
if ( hc_path_is_file ( l1_filename ) = = true )
{
if ( straight_ctx_add_wl ( hashcat_ctx , l1_filename ) = = - 1 )
{
hcfree ( dictionary_files ) ;
return - 1 ;
}
}
}
}
hcfree ( dictionary_files ) ;
}
else
{
if ( straight_ctx_add_wl ( hashcat_ctx , l0_filename ) = = - 1 ) return - 1 ;
}
}
if ( straight_ctx - > dicts_cnt = = 0 )
{
event_log_error ( hashcat_ctx , " No usable dictionary file found. " ) ;
return - 1 ;
}
}
}
else if ( user_options - > attack_mode = = ATTACK_MODE_COMBI )
{
}
else if ( user_options - > attack_mode = = ATTACK_MODE_BF )
{
}
else if ( user_options - > attack_mode = = ATTACK_MODE_HYBRID1 )
{
for ( int i = 0 ; i < user_options_extra - > hc_workc - 1 ; i + + )
{
char * l0_filename = user_options_extra - > hc_workv [ i ] ;
// at this point we already verified the path actually exist and is readable
if ( hc_path_is_directory ( l0_filename ) = = true )
{
char * * dictionary_files ;
dictionary_files = scan_directory ( l0_filename ) ;
if ( dictionary_files ! = NULL )
{
qsort ( dictionary_files , ( size_t ) count_dictionaries ( dictionary_files ) , sizeof ( char * ) , sort_by_stringptr ) ;
for ( int d = 0 ; dictionary_files [ d ] ! = NULL ; d + + )
{
char * l1_filename = dictionary_files [ d ] ;
if ( hc_path_read ( l1_filename ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , l1_filename , strerror ( errno ) ) ;
hcfree ( dictionary_files ) ;
return - 1 ;
}
if ( hc_path_is_file ( l1_filename ) = = true )
{
if ( straight_ctx_add_wl ( hashcat_ctx , l1_filename ) = = - 1 )
{
hcfree ( dictionary_files ) ;
return - 1 ;
}
}
}
}
hcfree ( dictionary_files ) ;
}
else
{
if ( straight_ctx_add_wl ( hashcat_ctx , l0_filename ) = = - 1 ) return - 1 ;
}
}
if ( straight_ctx - > dicts_cnt = = 0 )
{
event_log_error ( hashcat_ctx , " No usable dictionary file found. " ) ;
return - 1 ;
}
}
else if ( user_options - > attack_mode = = ATTACK_MODE_HYBRID2 )
{
for ( int i = 1 ; i < user_options_extra - > hc_workc ; i + + )
{
char * l0_filename = user_options_extra - > hc_workv [ i ] ;
// at this point we already verified the path actually exist and is readable
if ( hc_path_is_directory ( l0_filename ) = = true )
{
char * * dictionary_files ;
dictionary_files = scan_directory ( l0_filename ) ;
if ( dictionary_files ! = NULL )
{
qsort ( dictionary_files , ( size_t ) count_dictionaries ( dictionary_files ) , sizeof ( char * ) , sort_by_stringptr ) ;
for ( int d = 0 ; dictionary_files [ d ] ! = NULL ; d + + )
{
char * l1_filename = dictionary_files [ d ] ;
if ( hc_path_read ( l1_filename ) = = false )
{
event_log_error ( hashcat_ctx , " %s: %s " , l1_filename , strerror ( errno ) ) ;
hcfree ( dictionary_files ) ;
return - 1 ;
}
if ( hc_path_is_file ( l1_filename ) = = true )
{
if ( straight_ctx_add_wl ( hashcat_ctx , l1_filename ) = = - 1 )
{
hcfree ( dictionary_files ) ;
return - 1 ;
}
}
}
}
hcfree ( dictionary_files ) ;
}
else
{
if ( straight_ctx_add_wl ( hashcat_ctx , l0_filename ) = = - 1 ) return - 1 ;
}
}
if ( straight_ctx - > dicts_cnt = = 0 )
{
event_log_error ( hashcat_ctx , " No usable dictionary file found. " ) ;
return - 1 ;
}
}
return 0 ;
}
void straight_ctx_destroy ( hashcat_ctx_t * hashcat_ctx )
{
straight_ctx_t * straight_ctx = hashcat_ctx - > straight_ctx ;
if ( straight_ctx - > enabled = = false ) return ;
for ( u32 dict_pos = 0 ; dict_pos < straight_ctx - > dicts_cnt ; dict_pos + + )
{
hcfree ( straight_ctx - > dicts [ dict_pos ] ) ;
}
hcfree ( straight_ctx - > dicts ) ;
hcfree ( straight_ctx - > kernel_rules_buf ) ;
memset ( straight_ctx , 0 , sizeof ( straight_ctx_t ) ) ;
}