// File: jmfenner92[P]Log-Parser/src/log_parser.cpp
// Function: main
int main(int argc, char** argv) {

	// check the number of arguments. it should be 2: one for the name of the program and 
	// one for the log file to be read in
	if (argc != 2) {
		cerr << "Invalid number of arguments!" << endl;
		cerr << "Usage: ./log_parser.cpp <log file>" << endl;
		exit(-1);
	}

	// open the file for reading and check for success
	ifstream log_file;
	log_file.open(argv[1]);
	if (!log_file) {
		cerr << "File failed to open. Are you sure it exists?" << endl;
		exit(-1);
	}

	/* 
	** Okay, real talk...
	** We set up a temp_record variable of type CmdRecord to start collecting the data for the
	** record to be put into the list. If we see one the the addresses that we need, we can
	** insert the record at the end of the record loop. If it's not, then just keep moving on.
	** TODO: this might be better as a function. 
	*/
	

	// now that we're in the clear, let's define some useful variables
	string curr_field = "";
	int counter = 0;
	int field_counter = 0;
	string temp_data = "";
	string past_time = "";

	// we also have to set up a new command list, and a temporary record collector
	CmdList commands;
	CmdRecord temp_record;

	// do a getline() to remove the header and fire up the record collection loop
	std::string temp;
	getline(log_file, temp);
	while(log_file >> curr_field) {
		field_counter++;

		if (field_counter == RELTIME) {
			// we have the Rel Time field value
			temp_record.Set_RelTime(curr_field);

		} else if (field_counter == ADDRESS) {
			// we have the Address field value
			temp_record.Set_Address(curr_field);

		} else if (field_counter == DATA) {
			// we have the Data field value (this is special if it's in the address of
			// a command we want, so set it aside for later)
			temp_data = curr_field;

		} else if(field_counter == SIZE) {
			// we have the Size field value
			temp_record.Set_Size(curr_field);

		} else if(field_counter == CYCLE) {
			// we have the Cycle field value
			temp_record.Set_Cycle(curr_field);

		}

		// if the field_counter is 14, that means we've hit the end of a line. this is
		// where decision making comes in. two things can happen here: if it's not a 
		// record want (the easist), we reset the field_counter and increment the 
		// line_count. if it's a record we want, we do the above and calculate the size
		// of the data, and then enter the data collection loop.
		if (field_counter == ENDLINE) {
			if (temp_record.Get_Address() == CMD1 || 
				temp_record.Get_Address() == CMD2) {
				// set the line number and past time (which is the time for the 
				// current command)
				temp_record.Set_Line_Number(patch::to_string(line_count));
				temp_record.Set_RelTime(past_time);

				// pass the current node and the ifstream to the dataCollection 
				// function to keep this from getting cluttered
				dataCollection(&temp_record, log_file, temp_data);

				//add # of words to record
				//std::cout << temp_record.HexToDec(temp_data) / 2 << "\n";
				temp_record.Set_Total_Words(temp_record.HexToDec(temp_data) / 2);
				//std::cout << temp_record.Get_Total_Words() << "\n";

				// add it to the command list
				commands.AddRecord(temp_record);
			}
			
			// this happens every time we reach the end of a line
			past_time = temp_record.Get_RelTime();
			field_counter = 0;
			line_count++;
		}  

	}
	
	log_file.close();
	//commands.PrintList();
	commands.Display();
	return 0;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x610, %rsp            # imm = 0x610
movl $0x0, -0x4(%rbp)
movl %edi, -0x8(%rbp)
movq %rsi, -0x10(%rbp)
cmpl $0x2, -0x8(%rbp)
je 0x362d
movq 0x9a0a(%rip), %rdi      # 0xcff0
leaq 0x5a17(%rip), %rsi      # 0x9004
callq 0x3210
movq %rax, %rdi
movq 0x99c4(%rip), %rsi      # 0xcfc0
callq 0x3260
movq 0x99e8(%rip), %rdi      # 0xcff0
leaq 0x5a12(%rip), %rsi      # 0x9021
callq 0x3210
movq %rax, %rdi
movq 0x99a2(%rip), %rsi      # 0xcfc0
callq 0x3260
movl $0xffffffff, %edi       # imm = 0xFFFFFFFF
callq 0x32c0
leaq -0x218(%rbp), %rdi
movq %rdi, -0x5c0(%rbp)
callq 0x32b0
movq -0x5c0(%rbp), %rdi
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rsi
movl $0x8, %edx
callq 0x3160
jmp 0x365b
movq -0x218(%rbp), %rax
movq -0x18(%rax), %rax
leaq -0x218(%rbp,%rax), %rdi
callq 0x3120
movb %al, -0x5c1(%rbp)
jmp 0x367b
movb -0x5c1(%rbp), %al
testb $0x1, %al
jne 0x3687
jmp 0x36d9
movq 0x9962(%rip), %rdi      # 0xcff0
leaq 0x59af(%rip), %rsi      # 0x9044
callq 0x3210
movq %rax, -0x5d0(%rbp)
jmp 0x36a3
movq -0x5d0(%rbp), %rdi
movq 0x990f(%rip), %rsi      # 0xcfc0
callq 0x3260
jmp 0x36b8
movl $0xffffffff, %edi       # imm = 0xFFFFFFFF
callq 0x32c0
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
jmp 0x3ee7
leaq -0x249(%rbp), %rdi
movq %rdi, -0x5d8(%rbp)
callq 0x33f0
movq -0x5d8(%rbp), %rdx
leaq 0x5da3(%rip), %rsi      # 0x949d
leaq -0x248(%rbp), %rdi
callq 0x42d0
jmp 0x3708
leaq -0x249(%rbp), %rdi
callq 0x3280
movl $0x0, -0x250(%rbp)
movl $0x0, -0x254(%rbp)
leaq -0x279(%rbp), %rdi
movq %rdi, -0x5e0(%rbp)
callq 0x33f0
movq -0x5e0(%rbp), %rdx
leaq 0x5d54(%rip), %rsi      # 0x949d
leaq -0x278(%rbp), %rdi
callq 0x42d0
jmp 0x3757
leaq -0x279(%rbp), %rdi
callq 0x3280
leaq -0x2a1(%rbp), %rdi
movq %rdi, -0x5e8(%rbp)
callq 0x33f0
movq -0x5e8(%rbp), %rdx
leaq 0x5d19(%rip), %rsi      # 0x949d
leaq -0x2a0(%rbp), %rdi
callq 0x42d0
jmp 0x3792
leaq -0x2a1(%rbp), %rdi
callq 0x3280
leaq -0x2b0(%rbp), %rdi
callq 0x7450
jmp 0x37ac
leaq -0x370(%rbp), %rdi
callq 0x51b0
jmp 0x37ba
leaq -0x390(%rbp), %rdi
movq %rdi, -0x5f0(%rbp)
callq 0x3360
movq -0x5f0(%rbp), %rsi
leaq -0x218(%rbp), %rdi
callq 0x3050
jmp 0x37e2
jmp 0x37e4
leaq -0x218(%rbp), %rdi
leaq -0x248(%rbp), %rsi
callq 0x3310
movq %rax, -0x5f8(%rbp)
jmp 0x3800
movq -0x5f8(%rbp), %rdi
movq (%rdi), %rax
movq -0x18(%rax), %rax
addq %rax, %rdi
callq 0x3300
movb %al, -0x5f9(%rbp)
jmp 0x381e
movb -0x5f9(%rbp), %al
testb $0x1, %al
jne 0x382d
jmp 0x3e1c
movl -0x254(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x254(%rbp)
cmpl $0x3, -0x254(%rbp)
jne 0x3955
leaq -0x3b0(%rbp), %rdi
leaq -0x248(%rbp), %rsi
callq 0x30f0
jmp 0x385e
leaq -0x370(%rbp), %rdi
leaq -0x3b0(%rbp), %rsi
callq 0x5520
jmp 0x3873
leaq -0x3b0(%rbp), %rdi
callq 0x3150
jmp 0x3ab2
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x249(%rbp), %rdi
callq 0x3280
jmp 0x3ee7
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x279(%rbp), %rdi
callq 0x3280
jmp 0x3edb
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x2a1(%rbp), %rdi
callq 0x3280
jmp 0x3ecf
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
jmp 0x3ec3
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
jmp 0x3eb7
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
jmp 0x3e9f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x3b0(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
cmpl $0x7, -0x254(%rbp)
jne 0x39bc
leaq -0x3d0(%rbp), %rdi
leaq -0x248(%rbp), %rsi
callq 0x30f0
jmp 0x3973
leaq -0x370(%rbp), %rdi
leaq -0x3d0(%rbp), %rsi
callq 0x53a0
jmp 0x3988
leaq -0x3d0(%rbp), %rdi
callq 0x3150
jmp 0x3ab0
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x3d0(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
cmpl $0x8, -0x254(%rbp)
jne 0x39df
leaq -0x278(%rbp), %rdi
leaq -0x248(%rbp), %rsi
callq 0x3030
jmp 0x39da
jmp 0x3aae
cmpl $0x9, -0x254(%rbp)
jne 0x3a46
leaq -0x3f0(%rbp), %rdi
leaq -0x248(%rbp), %rsi
callq 0x30f0
jmp 0x39fd
leaq -0x370(%rbp), %rdi
leaq -0x3f0(%rbp), %rsi
callq 0x5460
jmp 0x3a12
leaq -0x3f0(%rbp), %rdi
callq 0x3150
jmp 0x3aac
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x3f0(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
cmpl $0xa, -0x254(%rbp)
jne 0x3aaa
leaq -0x410(%rbp), %rdi
leaq -0x248(%rbp), %rsi
callq 0x30f0
jmp 0x3a64
leaq -0x370(%rbp), %rdi
leaq -0x410(%rbp), %rsi
callq 0x54c0
jmp 0x3a79
leaq -0x410(%rbp), %rdi
callq 0x3150
jmp 0x3aaa
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x410(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
jmp 0x3aac
jmp 0x3aae
jmp 0x3ab0
jmp 0x3ab2
cmpl $0xe, -0x254(%rbp)
jne 0x3e17
movb $0x0, -0x451(%rbp)
leaq -0x430(%rbp), %rdi
leaq -0x370(%rbp), %rsi
callq 0x53d0
jmp 0x3adb
leaq 0x558f(%rip), %rsi      # 0x9071
leaq -0x430(%rbp), %rdi
callq 0x4380
movb %al, -0x5fa(%rbp)
jmp 0x3af6
movb -0x5fa(%rbp), %cl
movb $0x1, %al
testb $0x1, %cl
movb %al, -0x5fb(%rbp)
jne 0x3b50
jmp 0x3b0b
leaq -0x450(%rbp), %rdi
leaq -0x370(%rbp), %rsi
callq 0x53d0
jmp 0x3b20
movb $0x1, -0x451(%rbp)
leaq 0x554c(%rip), %rsi      # 0x907a
leaq -0x450(%rbp), %rdi
callq 0x4380
movb %al, -0x5fc(%rbp)
jmp 0x3b42
movb -0x5fc(%rbp), %al
movb %al, -0x5fb(%rbp)
jmp 0x3b50
movb -0x5fb(%rbp), %al
movb %al, -0x5fd(%rbp)
testb $0x1, -0x451(%rbp)
jne 0x3b67
jmp 0x3b73
leaq -0x450(%rbp), %rdi
callq 0x3150
leaq -0x430(%rbp), %rdi
callq 0x3150
movb -0x5fd(%rbp), %al
testb $0x1, %al
jne 0x3b8e
jmp 0x3dca
leaq 0x969b(%rip), %rsi      # 0xd230
leaq -0x478(%rbp), %rdi
callq 0x43b0
jmp 0x3ba3
leaq -0x370(%rbp), %rdi
leaq -0x478(%rbp), %rsi
callq 0x5350
jmp 0x3bb8
leaq -0x478(%rbp), %rdi
callq 0x3150
leaq -0x498(%rbp), %rdi
leaq -0x2a0(%rbp), %rsi
callq 0x30f0
jmp 0x3bd9
leaq -0x370(%rbp), %rdi
leaq -0x498(%rbp), %rsi
callq 0x5520
jmp 0x3bee
leaq -0x498(%rbp), %rdi
callq 0x3150
leaq -0x4b8(%rbp), %rdi
leaq -0x278(%rbp), %rsi
callq 0x30f0
jmp 0x3c0f
leaq -0x370(%rbp), %rdi
leaq -0x218(%rbp), %rsi
leaq -0x4b8(%rbp), %rdx
callq 0x3f00
jmp 0x3c2b
leaq -0x4b8(%rbp), %rdi
callq 0x3150
leaq -0x4d8(%rbp), %rdi
leaq -0x278(%rbp), %rsi
callq 0x30f0
jmp 0x3c4c
leaq -0x370(%rbp), %rdi
leaq -0x4d8(%rbp), %rsi
callq 0x5850
movl %eax, -0x604(%rbp)
jmp 0x3c67
movl -0x604(%rbp), %esi
movl %esi, %eax
shrl $0x1f, %eax
addl %eax, %esi
sarl %esi
leaq -0x370(%rbp), %rdi
callq 0x5590
jmp 0x3c84
leaq -0x4d8(%rbp), %rdi
callq 0x3150
leaq -0x598(%rbp), %rdi
leaq -0x370(%rbp), %rsi
callq 0x4460
jmp 0x3ca5
leaq -0x2b0(%rbp), %rdi
leaq -0x598(%rbp), %rsi
callq 0x74f0
jmp 0x3cba
leaq -0x598(%rbp), %rdi
callq 0x45b0
jmp 0x3dca
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
jmp 0x3d0a
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
testb $0x1, -0x451(%rbp)
jne 0x3cfc
jmp 0x3d08
leaq -0x450(%rbp), %rdi
callq 0x3150
jmp 0x3d0a
leaq -0x430(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x478(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x498(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x4b8(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x4d8(%rbp), %rdi
callq 0x3150
jmp 0x3e9f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x220(%rbp)
movl %eax, -0x224(%rbp)
leaq -0x598(%rbp), %rdi
callq 0x45b0
jmp 0x3e9f
leaq -0x5b8(%rbp), %rdi
leaq -0x370(%rbp), %rsi
callq 0x5550
jmp 0x3ddf
leaq -0x2a0(%rbp), %rdi
leaq -0x5b8(%rbp), %rsi
callq 0x32d0
leaq -0x5b8(%rbp), %rdi
callq 0x3150
movl $0x0, -0x254(%rbp)
movl 0x9422(%rip), %eax      # 0xd230
addl $0x1, %eax
movl %eax, 0x9419(%rip)      # 0xd230
jmp 0x37e4
leaq -0x218(%rbp), %rdi
callq 0x3060
jmp 0x3e2a
leaq -0x2b0(%rbp), %rdi
callq 0x78c0
jmp 0x3e38
movl $0x0, -0x4(%rbp)
leaq -0x390(%rbp), %rdi
callq 0x3150
leaq -0x370(%rbp), %rdi
callq 0x45b0
leaq -0x2b0(%rbp), %rdi
callq 0x7470
leaq -0x2a0(%rbp), %rdi
callq 0x3150
leaq -0x278(%rbp), %rdi
callq 0x3150
leaq -0x248(%rbp), %rdi
callq 0x3150
leaq -0x218(%rbp), %rdi
callq 0x3090
movl -0x4(%rbp), %eax
addq $0x610, %rsp            # imm = 0x610
popq %rbp
retq
leaq -0x390(%rbp), %rdi
callq 0x3150
leaq -0x370(%rbp), %rdi
callq 0x45b0
leaq -0x2b0(%rbp), %rdi
callq 0x7470
leaq -0x2a0(%rbp), %rdi
callq 0x3150
leaq -0x278(%rbp), %rdi
callq 0x3150
leaq -0x248(%rbp), %rdi
callq 0x3150
leaq -0x218(%rbp), %rdi
callq 0x3090
movq -0x220(%rbp), %rdi
callq 0x33e0
nop