URGENT! c question (updated, PLEASE HELP on the last reply)

Started by
4 comments, last by JinJo 19 years, 6 months ago
didnt want to do a title like that but i am running out of time and i need to get this working. Hi all, I have to finish an assignment today that takes in two command line arguments for a code file and a memory file. The code file contains a number specifying how many assembly instructions are in the code, the memory file contains the initial memory contents. The program must simulate the assembly code. It has to be done in C and I am more use to C++. Here are a few examples of stupid errors that I think are right (remember it's been a while since I used any standard library functions as I use all my own now) memory.txt contents:

0 0 0 0 12 0 16 0 24 0 2 0 0 0 0 0 4 3 1 8 




now i open the file memory.txt and start reading in like so

for(i = 0; i < 20; i++)
{
    fscanf(file2, "%d ",&memory);
}




there are only 20 ints to store the memory. but my output shows that i read in all 0's except memory[8] has the value 20, what's up with that? Also when reading the code file i use: fscanf(file1, "%d", &numOfInstructions); to read in an int. But when I use this value later in loops it act silly e.g.

        for(i = 0; i < numOfInstructions; i++)
	{
		//why do i need this?
		if(i > 7)
			break;
		//read line from file
		strcpy(instructions.string, getLine(file1));
	}




if i don't have that if statement the code crashes but quite clearly i shouldnt need it. there is stuff like this happening all over my code and i only have about an hour to finish it (i think that all my program is mostly right or at least has the right idea going) here's my program anyway incase you need to see anything else to spot what's going on (also i am using vc++ .net console application) note the code may look dodgy and doesn't reflect my usual style

// emulator.cpp 
//

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

int registers[8];
int memory[20];
struct instructionString
{
	char string[80];
};

int programCounter = 0;


struct instruction
{
	char name[10];
	int op1, op2;
	char operand1[10];
	char operand2[10];
	bool op2Register; //used to flag if op2 is a register or a value
};

char *getLine(FILE *file)
{
	char *s;
	char tok = getc(file);
	int count = 0;
	s = (char*)malloc(80);
	while(tok != '\n')
	{
		s[count++] = tok;
		tok = getc(file);
	}
	s[count] = '\0';
	return s;
}

struct instruction instTable[20];
struct instructionString instructions[20];

int main(int argc, char *argv[])
{
	char *fileName1;
	char *fileName2;
	int i;
	int numOfInstructions;

	//initialise register
	for(i = 0; i < 8; i++)
	{
		registers = 0;
	}
	
	//initialise memory
	for(i = 0; i < 20; i++)
	{
		memory = 0;
	}
	
	fileName1 = argv[1];
	fileName2 = argv[2];

	FILE *file1;
	FILE *file2;

	if((file1 = fopen(fileName1, "r")) == NULL)
	{	printf("Can't open file: %s\nProgram ending", fileName1);
		return 0;
	}

	if((file2 = fopen(fileName2, "r")) == NULL)
	{	printf("Can't open file: %s\nProgram ending", fileName2);
		return 0;
	}
	
	//read initial memory values from file2
	for(i = 0; i < 20; i++)
	{
		fscanf(file2, "%d ",&memory);
	}

	//read number of assembler instructions from file 1
	fscanf(file1, "%d", &numOfInstructions);

	for(i = 0; i < numOfInstructions; i++)
	{
		//why do i need this?
		if(i > 7)
			break;
		//read line from file
		strcpy(instructions.string, getLine(file1));
	}
	
	//close files
	fclose(file1);
	fclose(file2);
	
	//split each instruction into individual parts

	//process each instruction
	for(i = 0; i < numOfInstructions; i++)
	{
		if(i > 6)
			break;
		//get instruction name
		int j = 0,k = 0;
		
		while(instructions.string[j] != ' ')
		{
			instTable.name[k] = instructions.string[j];
			j++; k++;
		}
		instTable.name[k] = '\0';
		j++; k = 0;

		//get first operand
		while(instructions.string[j] != ' ')
		{
			instTable.operand1[k] = instructions.string[j];
			j++; k++;
		}
		instTable.operand1[k] = '\0';
		j++; k = 0;

		//get 2nd operand
		while(instructions.string[j] != ' ')
		{
			instTable.operand2[k] = instructions.string[j];
			j++; k++;
		}
		instTable.operand2[k] = '\0';
		j++; k = 0;

		//convert 1st operand into a register number
		instTable.op1 = atoi(&instTable.operand1[1]);

		//if(operand2[0] != r then convert the whole string to a number else
		if(instTable.operand1[0] == 'R')
		{
			char temp[9];
			memcpy(temp, &instTable.operand1[1], strlen(instTable.operand1)-1);
			instTable.op2Register = true;
		}
		else
		{
			instTable.op2 = atoi(&instTable.operand2[1]);
			instTable.op2Register = false;
		}
		
	}
	
	//main loop simulator
	while(programCounter < 20)
	{
		printf("here1");
		//printf("%d", programCounter);
		//programCounter++;
		if(strcmp(instTable[programCounter].name, "load") == 0)
		{
			printf("here2");
			if(instTable[programCounter].op2Register)
				registers[instTable[programCounter].op1] = registers[instTable[programCounter].op2];
			programCounter++;
		}
		if(strcmp(instTable[programCounter].name, "add") == 0)
		{
			printf("here2");
			if(instTable[programCounter].op2Register)
				registers[instTable[programCounter].op1] += registers[instTable[programCounter].op2];
			else
				registers[instTable[programCounter].op1] += memory[instTable[programCounter].op2];
			programCounter++;
		}
		if(strcmp(instTable[programCounter].name, "sub") == 0)
		{
			printf("here3");
			if(instTable[programCounter].op2Register)
				registers[instTable[programCounter].op1] -= registers[instTable[programCounter].op2];
			else
				registers[instTable[programCounter].op1] -= memory[instTable[programCounter].op2];
			programCounter++;
		}
		if(strcmp(instTable[programCounter].name, "loadind") == 0)
		{
			printf("here4");
			if(instTable[programCounter].op2Register)
				registers[instTable[programCounter].op1] = memory[registers[instTable[programCounter].op2]];
			programCounter++;
		}
		if(strcmp(instTable[programCounter].name, "storeind") == 0)
		{
			printf("here5");
			if(instTable[programCounter].op2Register)
				memory[registers[instTable[programCounter].op1]] = registers[instTable[programCounter].op2];
			programCounter++;
		} 
		
	}
	printf("here8");
	for(int i = 0; i < 8; i++)
	{
		printf("R%d = %d\n", i, registers);
	}

	for(int i = 0; i < 20; i++)
	{
		printf("mem location %d = %d\n", i, registers);
	}

	//end
	

	return 0;
}




also here is the code.txt file

8
load R1 R8
add R1 16
loadind R2 R1
add R1 8
loadind R3 R1
add R3 R2
sub R1 4
storeind R3 R1



any help is appreciated. [Edited by - JinJo on November 12, 2004 9:18:54 AM]
Advertisement
anybody any tips?
Are you sure you're passing the files in in the right order?

I ran the code and the reading in of the data was fine.
===========================There are 10 types of people in the world. Those that understand binary and those that don't.( My views in no way reflect the views of my employer. )
yeah i am, turns out my debug info was wron, so now the data is read in correctly although it still only lets me process 6 instructions (see the part of the code that says if i > 6)
there is 8 in the file

i have sorted out a few more things too like the bit saying if > 7

here is the new updated code that is getting there
// emulator.cpp //#include "stdafx.h"#include <stdio.h>#include <stdlib.h>#include <string.h>int registers[8];int memory[20];struct instructionString{	char string[80];};int programCounter = 0;struct instruction{	char name[10];	int op1, op2;	char operand1[10];	char operand2[10];	bool op2Register; //used to flag if op2 is a register or a value};char *getLine(FILE *file){	char *s;	char tok = getc(file);	int count = 0;	s = (char*)malloc(80);	while(tok != '\n')	{		s[count++] = tok;		tok = getc(file);	}	s[count] = '\0';	return s;}struct instruction instTable[10];struct instructionString instructions[10];int main(int argc, char *argv[]){	char *fileName1;	char *fileName2;	int i;	int numOfInstructions;	//initialise register	for(i = 0; i < 8; i++)	{		registers = 0;	}		//initialise memory	for(i = 0; i < 20; i++)	{		memory = 0;	}		fileName1 = argv[1];	fileName2 = argv[2];	FILE *file1;	FILE *file2;	if((file1 = fopen(fileName1, "r")) == NULL)	{	printf("Can't open file: %s\nProgram ending", fileName1);		return 0;	}	if((file2 = fopen(fileName2, "r")) == NULL)	{	printf("Can't open file: %s\nProgram ending", fileName2);		return 0;	}		//read initial memory values from file2	for(i = 0; i < 20; i++)	{		fscanf(file2, "%d ",&memory);	}	//read number of assembler instructions from file 1	fscanf(file1, "%d", &numOfInstructions);	for(i = 0; i < numOfInstructions; i++)	{		//why do i need this?		//if(i > 7)		//	break;		//read line from file		strcpy(instructions.string, getLine(file1));	}		//close files	fclose(file1);	fclose(file2);		//split each instruction into individual parts	//process each instruction	for(i = 0; i < numOfInstructions; i++)	{		if(i > 6)			break;		//get instruction name		int j = 0,k = 0;				while(instructions.string[j] != ' ')		{			instTable.name[k] = instructions.string[j];			j++; k++;		}		instTable.name[k] = '\0';		j++; k = 0;		//get first operand		while(instructions.string[j] != ' ')		{			instTable.operand1[k] = instructions.string[j];			j++; k++;		}		instTable.operand1[k] = '\0';		j++; k = 0;		//get 2nd operand		while(instructions.string[j] != ' ')		{			instTable.operand2[k] = instructions.string[j];			j++; k++;		}		instTable.operand2[k] = '\0';		j++; k = 0;		//convert 1st operand into a register number		instTable.op1 = atoi(&instTable.operand1[1]);		//if(operand2[0] != r then convert the whole string to a number else		if(instTable.operand1[0] == 'R')		{			char temp[9];			memcpy(temp, &instTable.operand1[1], strlen(instTable.operand1)-1);			instTable.op2Register = true;		}		else		{			instTable.op2 = atoi(&instTable.operand2[1]);			instTable.op2Register = false;		}			}		//main loop simulator	while(programCounter < 8)	{		printf("here1\n");		printf("programCounter = %d\n", programCounter);		printf("%s\n", instTable[programCounter].name);		if(strcmp(instTable[programCounter].name, "load") == 0)		{			printf("here2\n");			if(instTable[programCounter].op2Register)			{				registers[instTable[programCounter].op1] = registers[instTable[programCounter].op2];				//programCounter++;			}		}		else		if(strcmp(instTable[programCounter].name, "add") == 0)		{			printf("here3\n");			if(instTable[programCounter].op2Register)				registers[instTable[programCounter].op1] += registers[instTable[programCounter].op2];			else				registers[instTable[programCounter].op1] += memory[instTable[programCounter].op2];			//programCounter++;		}		else		if(strcmp(instTable[programCounter].name, "sub") == 0)		{			printf("here4\n");			if(instTable[programCounter].op2Register)				registers[instTable[programCounter].op1] -= registers[instTable[programCounter].op2];			else				registers[instTable[programCounter].op1] -= memory[instTable[programCounter].op2];			//programCounter++;		}		else		if(strcmp(instTable[programCounter].name, "loadind") == 0)		{			printf("here5\n");			if(instTable[programCounter].op2Register)			{				registers[instTable[programCounter].op1] = memory[registers[instTable[programCounter].op2]];				//programCounter++;			}		}		else		if(strcmp(instTable[programCounter].name, "storeind") == 0)		{			printf("here6\n");			if(instTable[programCounter].op2Register)			{				memory[registers[instTable[programCounter].op1]] = registers[instTable[programCounter].op2];				//programCounter++;			}		} 		programCounter++;	}		for(int i = 0; i < 8; i++)	{		printf("R%d = %d\n", i, registers);	}	for(int i = 0; i < 20; i++)	{		printf("mem location %d = %d\n", i, memory);	}	//end		return 0;}


i think most of the problems are coming from hard coded numbers or strings.

did you get the rest of the code running (the instruction parts)
as far as i know, it's the bit saying i > 6 that is giving the problems but i don't know why it won't allow it to be greater than 6
Didnt want to do a title like that but i am running out of time and this needs to be finished.

well it turns out here that my read instructions from file part of the code isnt reading all the instructions only the first 7, but thats after it has read in 83 characters of god knows what.

I think it may be that the scanf before isnt skipping onto the new line.

here's the code
//read number of assembler instructions from file 1	fscanf(file1, "%d", &numOfInstructions);	//read instructions from file	for(i = 0; i < numOfInstructions; i++)		{		//read line from file		strcpy(instructions.string, getLine(file1));	}


what should i do?

Also now if i add a little code to skip the first line of the code file (but still reading the number of instructions), my program only allows me to read a further 6 instructions from the file (odd?) and then later when processing these instructions it only allows me to process 5 of them (aaaahhhggg ;) )

updated code
// emulator.cpp //#include "stdafx.h"#include <stdio.h>#include <stdlib.h>#include <string.h>#define NUM_OF_REGISTERS 8#define MEM_SIZE 20#define INSTRUCTIONS 8int registers[NUM_OF_REGISTERS];int memory[MEM_SIZE];struct instructionString{	char string[80];};int programCounter = 0;struct instruction{	char name[10];	int op1, op2;	char operand1[10];	char operand2[10];	bool op2Register; //used to flag if op2 is a register or a value};char *getLine(FILE *file){	char *s;	char tok = getc(file);	int count = 0;	s = (char*)malloc(80);	while(tok != '\n')	{		s[count++] = tok;		tok = getc(file);	}	s[count] = '\0';	return s;}struct instruction instTable[INSTRUCTIONS];struct instructionString instructions[INSTRUCTIONS];int main(int argc, char *argv[]){	char *fileName1;	char *fileName2;	int i;	int numOfInstructions;	//initialise register	for(i = 0; i < NUM_OF_REGISTERS; i++)	{		registers = 0;	}		//initialise memory	for(i = 0; i < MEM_SIZE; i++)	{		memory = 0;	}		fileName1 = argv[1];	fileName2 = argv[2];	FILE *file1;	FILE *file2;	if((file1 = fopen(fileName1, "r")) == NULL)	{	printf("Can't open file: %s\nProgram ending", fileName1);		return 0;	}	if((file2 = fopen(fileName2, "r")) == NULL)	{	printf("Can't open file: %s\nProgram ending", fileName2);		return 0;	}		//read initial memory values from file2	for(i = 0; i < MEM_SIZE; i++)	{		fscanf(file2, "%d ",&memory);	}	//read number of assembler instructions from file 1	char line[80];	strcpy(line, getLine(file1));	numOfInstructions = atoi(&line[0]);	printf("%d", numOfInstructions);	//fscanf(file1, "%d", &numOfInstructions);	//read instructions from file	for(i = 0; i < numOfInstructions; i++)		{		//read line from file		if(i > 6)			break;		strcpy(instructions.string, getLine(file1));		printf("\n i = %d\n", i);		printf("%s", instructions.string);	}		//close files	fclose(file1);	fclose(file2);		//split each instruction into individual parts	for(i = 0; i < numOfInstructions; i++) //?	{		printf("%d", i);		if(i > 5)			break;		//get instruction name		int j = 0,k = 0;				while(instructions.string[j] != ' ')		{			instTable.name[k] = instructions.string[j];			j++; k++;		}		instTable.name[k] = '\0';		printf("\n j = %d\n", j);		j++; k = 0;		printf("%s", instTable.name);		//get first operand		while(instructions.string[j] != ' ')		{			instTable.operand1[k] = instructions.string[j];			j++; k++;		}		instTable.operand1[k] = '\0';		j++; k = 0;		//get 2nd operand		while(instructions.string[j] != ' ')		{			instTable.operand2[k] = instructions.string[j];			j++; k++;		}		instTable.operand2[k] = '\0';		j++; k = 0;		//convert 1st operand into a register number		instTable.op1 = atoi(&instTable.operand1[1]);		//if(operand2[0] != r then convert the whole string to a number else		if(instTable.operand1[0] == 'R')		{			char temp[9];			memcpy(temp, &instTable.operand1[1], strlen(instTable.operand1)-1);			instTable.op2Register = true;		}		else		{			instTable.op2 = atoi(&instTable.operand2[1]);			instTable.op2Register = false;		}					}	printf("here");		//main loop simulator	while(programCounter < INSTRUCTIONS)	{		printf("here1\n");		printf("programCounter = %d\n", programCounter);		printf("%s\n", instTable[programCounter].name);		if(strcmp(instTable[programCounter].name, "load") == 0)		{			printf("here2\n");			if(instTable[programCounter].op2Register)			{				registers[instTable[programCounter].op1] = registers[instTable[programCounter].op2];				//programCounter++;			}		}		else		if(strcmp(instTable[programCounter].name, "add") == 0)		{			printf("here3\n");			if(instTable[programCounter].op2Register)				registers[instTable[programCounter].op1] += registers[instTable[programCounter].op2];			else				registers[instTable[programCounter].op1] += memory[instTable[programCounter].op2];			//programCounter++;		}		else		if(strcmp(instTable[programCounter].name, "sub") == 0)		{			printf("here4\n");			if(instTable[programCounter].op2Register)				registers[instTable[programCounter].op1] -= registers[instTable[programCounter].op2];			else				registers[instTable[programCounter].op1] -= memory[instTable[programCounter].op2];			//programCounter++;		}		else		if(strcmp(instTable[programCounter].name, "loadind") == 0)		{			printf("here5\n");			if(instTable[programCounter].op2Register)			{				registers[instTable[programCounter].op1] = memory[registers[instTable[programCounter].op2]];				//programCounter++;			}		}		else		if(strcmp(instTable[programCounter].name, "storeind") == 0)		{			printf("here6\n");			if(instTable[programCounter].op2Register)			{				memory[registers[instTable[programCounter].op1]] = registers[instTable[programCounter].op2];				//programCounter++;			}		} 		programCounter++;	}		for(i = 0; i < NUM_OF_REGISTERS; i++)	{		printf("R%d = %d\n", i, registers);	}	for(i = 0; i < MEM_SIZE; i++)	{		printf("mem location %d = %d\n", i, memory);	}	//end		return 0;}


[Edited by - JinJo on November 12, 2004 9:50:39 AM]

This topic is closed to new replies.

Advertisement