#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "pmake.h"
#define deli " \t\n\r\f\v\\"
int is_comment_or_empty(const char *line) {
    for (int i = 0; i < strlen(line); i++){
        if (line[i] == '#') {
            return 1;
        }
        if (line[i] != '\t' && line[i] != ' ') {
            return 0;
        }
    }
    return 1;
}

void tokenize(char *line, Action *act, Action *next_a){
       
       int white_spaces = 0;
       int count = 0;
       for (int i = 1; i < MAXLINE; i++){
       if (line[i-1] == ' ' &&line[i] != ' '){
       white_spaces += 1;
       }
       if (line[i] == '\t' || line[i] == '\n' || line[i] == '\r'){
       break;
       }
       
       }
       char *placeholder;
       char **args = malloc(sizeof(char*)*(white_spaces+1));
       char *tok = strtok(placeholder, deli);
       while (tok != NULL){
       args[count] = tok;
       tok = strtok(NULL, deli);
       count ++;
       }
       act->args = args;
       act->next_act = next_a;

}

int main() {
    char *filename = "Makefile";
    FILE *fp=fopen(filename, "r");
    Action *acurr=NULL;
            int count=0;
            int com_count=0; 
        char *tok1;
        Action *aprev=NULL;
        Action *ahead=NULL;
	char *placeholder = malloc(sizeof(char)*MAXLINE);
        char *line = fgets(placeholder, MAXLINE, fp);
        int line_count=0;
        Rule *head = malloc(sizeof(Rule));
	Rule *prev = NULL;
        while (line != NULL){
        line = fgets(placeholder, MAXLINE, fp);
        line_count ++;
        }
        fseek(fp, 0, SEEK_SET); 
	Rule *curr = head;
        com_count=0; 
	char ***tab = malloc(sizeof(char**)*line_count); 
	line = fgets(placeholder, MAXLINE, fp);
	char *colon = strchr(line, ':');

        while (line != NULL){
        if (is_comment_or_empty(placeholder)){
        line = fgets(placeholder, MAXLINE, fp);
        }
        else{
        colon = strchr(placeholder, ':');

        
        char *target = malloc(sizeof(char)*MAXLINE);

        if (colon != NULL){
        if (ahead != NULL){
        curr->actions=ahead;
        
        }
        if (aprev != NULL){
        aprev->next_act = NULL;}
        aprev = NULL;
        acurr == NULL;
        ahead=NULL;
        

        
        strncpy(target, placeholder, colon - line);

        target[colon-line-1] = '\0';

        curr->target=target;
        


       char *dep = malloc(sizeof(Dependency)*MAXLINE);
        strcpy(dep, colon + 2);
       char *tok = strtok(dep, deli);
        count = 0;
        char **str = malloc(sizeof(char*)*MAXLINE);
        while (tok != NULL){
        str[count] = tok;

        tok = strtok(NULL, deli);
        count += 1;
        
        }
        str[count] = NULL;
        tab[com_count] = str;
        
        com_count++;}

       }
       
       
       

        
       line = fgets(placeholder, MAXLINE, fp);
       if (colon != NULL){

       curr->next_rule = malloc(sizeof(Rule));
       prev = curr;
       curr=curr->next_rule;       
       }
       }
       prev->next_rule = NULL;
       free(curr);
       curr = head;
       Action *act = NULL;
       Action *act_head;
       Action *prev_a = NULL;
       int state = 0;

       fseek(fp, 0, SEEK_SET); 
       line = fgets(placeholder, MAXLINE, fp);
       Rule *last_state = NULL;
       Action *next_a = NULL;

       while (line != NULL && curr != NULL){
       colon = strchr(placeholder, ':');
       char *target = malloc(sizeof(char)*MAXLINE);
       strncpy(target, placeholder, colon-line);
       target[colon-line-1]='\0';
       if (colon != NULL && strcmp(curr->target, target)==0&& state==0){
       last_state = curr;
       curr = curr -> next_rule;
       state = 1;}
       else if (colon == NULL && state == 1){
       act = malloc(sizeof(Action));
       tokenize(line, act, NULL);
       curr->actions = act_head;
       last_state -> actions = act_head;
       state = 2;
       }
       else if (state == 2 && colon == NULL){
       prev_a = act;
       next_a = malloc(sizeof(Action));
       tokenize(line, act, next_a);
       
       
       }
       
       else if (state == 2 && colon != NULL){
       state = 1;
       act->next_act = NULL;
       next_a = NULL;
       act_head=NULL;
       last_state = curr;
       
       }
       
       else if (state == 1 && colon != NULL){
       state = 1;
       next_a = NULL;
       act_head = NULL;
       last_state = curr;
       }
       
       
       line = fgets(placeholder, MAXLINE, fp);
       colon = strchr(placeholder, ':');
       }
    
       

            
       curr = head;
       com_count = 0;
       Rule *cur = head;
       fseek(fp, 0, SEEK_SET); 

       while (cur != NULL){
       count = 0;
       while (tab[com_count][count] != NULL){


	Rule *inner_curr = head;
	Dependency *dep_curr = NULL;
	Dependency *dep_head = NULL;
	int found=0;
	while (inner_curr != NULL){

	if(strcmp(inner_curr->target, tab[com_count][count]) == 0){
	found=1;
	if (dep_curr==NULL){dep_curr = malloc(sizeof(Dependency));
	dep_head = dep_curr;}
	dep_curr->rule = inner_curr;
        if (tab[com_count][count+1]!=NULL){
           dep_curr->next_dep = malloc(sizeof(Dependency));
           dep_curr = dep_curr->next_dep;
	}
	else{
	
	dep_curr->next_dep=NULL;
	cur->dependencies = dep_head;
	}
	}
	inner_curr = inner_curr->next_rule;
	}
	
	if (found == 0 && dep_head == NULL){

	dep_curr = malloc(sizeof(Dependency));
	dep_head = dep_curr;
	dep_curr->rule = malloc(sizeof(Rule));
	dep_curr->rule->target = tab[com_count][count];
	dep_curr->rule->dependencies = NULL;
	dep_curr->rule->actions = NULL;
	dep_curr->rule->next_rule = NULL;
	curr->next_rule = dep_curr->rule;
	curr = curr->next_rule;
	cur = cur->next_rule;
	
	
	}
	else if(found == 0){
	dep_curr->next_dep = malloc(sizeof(Dependency));
	dep_curr->next_dep->rule=malloc(sizeof(Rule));
	dep_curr->next_dep->rule->target = tab[com_count][count];
	dep_curr->next_dep->rule->next_rule=NULL;
	dep_curr->next_dep->rule->dependencies = NULL;
	curr->next_rule = dep_curr->next_dep->rule;
	curr = curr->next_rule;
	dep_curr = dep_curr->next_dep;
	cur = cur->next_rule;
        
	
	}
	count ++; 
	}
	com_count ++; 
	cur = cur->next_rule;
	}   
	curr->next_rule = NULL;
	
	
	
	while (head != NULL){
	printf("Targ: %s\n",head->target);
	Dependency *dep = head->dependencies;
	while (dep != NULL){
	printf("Dep: %s\n", dep->rule->target);
	dep = dep->next_dep;
	}
	
	Action *act = head->actions;
	while (act != NULL){
	printf("Act: %s\n", *(head->actions->args));
	act = act->next_act;
	}
	head = head->next_rule;
	
	}
	
	
       
     

       
   return 0;
}
segmentation fault