ADAPT / src / report.c
report.c
Raw
#include "report.h"
#include <pthread.h>
#include "utility.h"
#include "mape_k.h"
#include "arc_model.h"
#include <stdio.h>
#include <stdlib.h>

void pentest_write_report(struct string_buffer *s_b, struct knowledge_base *k_b, char *filename)
{
    FILE *fp = fopen(filename, "w");
    fprintf(fp,"{\n\"Iterations\" : [");
    fprintf(fp,"%s\n",s_b->b_buff);
    fprintf(fp,"\n]}");
    fclose(fp);
}


void pentest_update_report(struct string_buffer *s_b, struct knowledge_base *k_b, size_t loop)
{

    struct pentest_state *pt_s = knowledge_base_get_res(k_b,"PentestState");
    //TODO: Decide if we should lock here or on every function individually to let attacks succeed in the meantime.
    pthread_mutex_lock(&pt_s->lock);
    if(loop > 1)
    {
	string_buffer_add_str(s_b,",");
    }
    string_buffer_add_fmt(s_b,"\n{\n\t\"PentestStep\" : \"%zu\",",loop);
    target_utility_json_dump(s_b,k_b);
    attack_utility_json_dump(s_b,k_b);
    pentest_state_json_dump_targets(s_b,pt_s,k_b->model);
    pentest_state_json_dump(s_b, pt_s);
    
    pthread_mutex_unlock(&pt_s->lock);

    string_buffer_add_str(s_b,"\n}");
}


void pentest_state_json_dump(struct string_buffer *s_b, struct pentest_state *pt_s)
{ 
    pentest_state_json_dump_attacks_worked(s_b, pt_s);
    pentest_state_json_dump_attacks_failed(s_b, pt_s);
    pentest_state_json_dump_attacks_active(s_b, pt_s);
    pentest_state_json_dump_scans_active(s_b, pt_s);
}


void pentest_state_json_dump_attacks_failed(struct string_buffer *s_b, struct pentest_state *pt_s)
{
    string_buffer_add_str(s_b,"\n\t\"AttacksFailed\" : [");

    for(size_t i = 0 ; i < pt_s->num_failed ; i++)
    {
	struct past_attack *p_a = &pt_s->failed[i];
	string_buffer_add_fmt(s_b,"\n\t\t{\"%s\" : \"%s\"}",p_a->a_p, p_a->target);
	if(i < pt_s->num_failed -1)
	{
	    string_buffer_add_str(s_b,",");
	}
	
	
    }
    
    string_buffer_add_str(s_b,"\n\t],\n");
}

void pentest_state_json_dump_attacks_worked(struct string_buffer *s_b, struct pentest_state *pt_s)
{
    string_buffer_add_str(s_b,"\n\t\"AttacksWorked\" : [");


    for(size_t i = 0 ; i < pt_s->num_worked ; i++)
    {
	struct past_attack *p_a = &pt_s->worked[i];
	string_buffer_add_fmt(s_b,"\n\t\t{\"%s\" : \"%s\"}",p_a->a_p, p_a->target);
	if(i < pt_s->num_worked -1)
	{
	    string_buffer_add_str(s_b,",");
	}
	
    }
    
    string_buffer_add_str(s_b,"\n\t],\n");
}

void pentest_state_json_dump_attacks_active(struct string_buffer *s_b, struct pentest_state *pt_s)
{
    string_buffer_add_str(s_b,"\n\t\"AttacksActive\" : [");

    for(size_t i = 0 ; i < pt_s->num_attacks ; i++)
    {
	struct active_attack *a_a = pt_s->attacks[i];
	string_buffer_add_str(s_b,"\n\t\t\t{");
	string_buffer_add_fmt(s_b,"\n\t\t\t\t\"target\" : \"%s\",",a_a->target);
	string_buffer_add_fmt(s_b,"\n\t\t\t\t\"attack\" : \"%s\",",a_a->attack->name);
	string_buffer_add_fmt(s_b,"\n\t\t\t\t\"progress\" : \"%d%%\"",a_a->cur_step*100/a_a->attack->num_steps);
	if(i < pt_s->num_attacks -1)
	{
	    string_buffer_add_str(s_b,",");
	}
	string_buffer_add_str(s_b,"\n\t\t\t}");
    }
    
    string_buffer_add_str(s_b,"\n\t]\n");
}

void pentest_state_json_dump_targets(struct string_buffer *s_b, struct pentest_state *pt_s, struct arc_model *a_m)
{
    string_buffer_add_str(s_b,"\n\t\"TargetsActive\" : [");

    for(size_t i = 0 ; i < pt_s->num_targets ; i++)
    {
	char *target = pt_s->targets[i];
	string_buffer_add_str(s_b,"\n\t\t\t{");
	string_buffer_add_fmt(s_b,"\n\t\t\t\t\"name\" : \"%s\",",target);
	//TODO: only print exploitation state, utility is already printed, do we care about other properties?
	char es_p_buff[128];
	sprintf(es_p_buff,"%s:EXPLOITATION_STATE",target);
	struct arc_value es_v = arc_model_get_property(a_m, es_p_buff);

	if(es_v.type == V_STRING)
	{
	   string_buffer_add_fmt(s_b,"\n\t\t\t\t\"exploitation_state\" : \"%s\"",es_v.v_str);
	   free(es_v.v_str);
	}
	string_buffer_add_str(s_b,"\n\t\t\t}");
	if(i < pt_s->num_targets -1)
	{
	    string_buffer_add_str(s_b,",");
	}
	
    }
    
    string_buffer_add_str(s_b,"\n\t],\n");
}

void pentest_state_json_dump_scans_active(struct string_buffer *s_b, struct pentest_state *pt_s)
{
    
}

void target_utility_json_dump(struct string_buffer *s_b, struct knowledge_base *k_b)
{
    struct utility_score *target_utility = knowledge_base_get_res(k_b,"TargetUtilityRanking");
    size_t num_t_utility_entries = knowledge_base_num_res(k_b,"TargetUtilityRanking");

    string_buffer_add_str(s_b,"\n\t\"TargetUtility\" : [");

    for(size_t i = 0 ; i < num_t_utility_entries ; i++)
    {
	struct utility_score *u_s = &target_utility[i];
	string_buffer_add_fmt(s_b,"\n\t\t{\"%s\" : %g}",u_s->option,u_s->value);
	if(i < num_t_utility_entries -1)
	{
	    string_buffer_add_str(s_b,",");
	}
	
    }

    string_buffer_add_str(s_b,"\n\t],\n");

}


void attack_utility_json_dump(struct string_buffer *s_b, struct knowledge_base *k_b)
{
    struct utility_score *attack_utility = knowledge_base_get_res(k_b,"AttackUtilityRanking");
    size_t num_a_utility_entries = knowledge_base_num_res(k_b,"AttackUtilityRanking");


    string_buffer_add_str(s_b,"\n\t\"AttackUtility\" : [");

    for(size_t i = 0 ; i < num_a_utility_entries ; i++)
    {
	struct utility_score *u_s = &attack_utility[i];
	string_buffer_add_fmt(s_b,"\n\t\t{\"%s\" : %g}",u_s->option,u_s->value);
	if(i < num_a_utility_entries -1)
	{
	    string_buffer_add_str(s_b,",");
	}
    }
    string_buffer_add_str(s_b,"\n\t],\n");
}