Related
The code I write is in C on Visual studio 2022.. I don't understand what part of my code is wrong, but it should be about string manipulation. The SplitStr splits string by another string (strtok does it by character).
#define SplitCount 20
TCHAR** SplitStr(TCHAR* pstr, TCHAR *psplitby)
{
if (pstr == NULL || psplitby == NULL)
return NULL;
TCHAR** res = malloc(SplitCount * sizeof(TCHAR*));
int i = 0, j = 0, c = 0;
TCHAR* splitby = _tcsdup(psplitby); // I need to duplicate here
int len = _tcslen(splitby);
TCHAR* str = _tcsdup(pstr); // and here
int strlen1 = _tcslen(str);
while (i < MAXSTR - strlen1) {
if (i + len < strlen1 && _tcsncmp(splitby, &str[i], len) == 0)
{
res[c] = malloc(MAXSTR * sizeof(TCHAR*));
if (res[c] == NULL)
break;
_tcsncpy_s(res[c], MAXSTR, &str[j], i-j);
i += len;
j = i;
c++;
i--;
}
i++;
}
res[c] = malloc(MAXSTR * sizeof(TCHAR*));
if (res[c] != NULL)
{
_tcsncpy_s(res[c], MAXSTR, &str[j], strlen1 - j);
c++;
}
res[c] = _tcsdup(_T("END"));
return res;
}
TCHAR* StrToLower(TCHAR* Str)
{
int i = 0;
TCHAR * tstr = malloc(MAXSTR * sizeof(TCHAR));
ZeroMemory(tstr, MAXSTR * sizeof(TCHAR));
if (tstr != NULL)
{
_tcsset_s(tstr, MAXSTR, _T('\0'));
for (; i < MAXSTR; i++)
{
tstr[i] = _totlower(Str[i]);
}
}
return tstr;
}
int SelectFromTable(TCHAR* Table, FIELDS fields[], TCHAR* Where);
int execute_sentence(TCHAR* psentence)
{
TCHAR * sentence = StrToLower(psentence);
StrTrim(sentence, _T(" "));
TCHAR* dlimiter = _T("?");
if (_tcsncmp(_T("select"), sentence, _tcslen(_T("select"))) == 0)
{
TCHAR ** split = SplitStr(sentence, _T("where"));
TCHAR* select = split[0];
StrTrim(select, _T(" "));
TCHAR* where = split[1];
StrTrim(where, _T(" "));
//_putts(where); // here value is OK
TCHAR ** split2 = SplitStr(select, _T("from"));
TCHAR * fields = split2[0] + _tcslen(_T("select"));
TCHAR * table = split2[1];
StrTrim(table, _T(" "));
_putts(where); // here value is distorted now if I don't use _tcsdup above
TCHAR ** split3 = SplitStr(fields, dlimiter);
TCHAR* thefield = split3[0];
StrTrim(thefield, _T(" "));
FIELDS fields_arr[Field_Count];
int c_field_pos = 0, i = 1;
while (_tcscmp(thefield, _T("END")) != 0)
{
StrTrim(thefield, _T(" "));
c_field_pos = 0;
if (thefield != NULL)
{
for (int i = 0; i < Field_Count; i++)
{
if (_tcsncmp(thefield, table_columns[i], _tcslen(table_columns[i])) == 0) {
fields_arr[c_field_pos] = (FIELDS)i;
c_field_pos++;
break;
}
}
}
thefield = split3[i];
i++;
}
fields_arr[c_field_pos] = F_END;
SelectFromTable(table, fields_arr, where);
}
return 0;
}
I never expected the need to duplicate, I even used a pointer and kept it intact, still problem exists..
In the main function of my program I make a few malloc calls and what I think are the right free calls at the end. My address sanitizer is telling me that data is still leaking in line 206, which is:
names[size - 1] = malloc(17 * sizeof(char));
The problem is that if I include a free statement for names[size - 1], there is apparently data still leaking from it. I have no idea why. Here is the main:
int main(int argc, char** argv) {
if (argc - 1 != 1) {
printf("Invalid number of arguments\n");
return 0;
}
//get file, return if invalid path
FILE *file = fopen(argv[1], "r");
if (!file) {
printf("Invalid input\n");
return 0;
}
//make temp of circuit with struct directive
int scount = 0;
struct directive* temp = NULL;
int size = 2;
int icount = 0;
int ocount = 0;
int tcount = 0;
char dir[17];
char **names;
int *values;
//get INPUT info
fscanf(file, " %s", dir);
fscanf(file, "%d", &icount);
size += icount;
names = malloc(size * sizeof(char *));
names[0] = malloc(2 * sizeof(char)); //MALLOC
strcpy(names[0], "0");
names[1] = malloc(2 * sizeof(char)); //MALLOC
strcpy(names[1], "1");
int i;
for (i = 0; i < icount; i++) {
names[i + 2] = malloc(17 * sizeof(char));
fscanf(file, "%*[: ]%16s", names[i + 2]);
}
//get OUTPUT info
fscanf(file, " %s", dir);
fscanf(file, "%d", &ocount);
size += ocount;
names = realloc(names, size * sizeof(char *));
for (i = 0; i < ocount; i++) {
names[i + icount + 2] = malloc(17 * sizeof(char));
fscanf(file, "%*[: ]%16s", names[i + icount + 2]);
}
//get temp
struct directive step;
while (!feof(file)) {
int numInputs = 2, numOutputs = 1;
int sc = fscanf(file, " %s", dir);
if (sc != 1) {
break;
}
scount++;
step.n = 0;
step.s = 0;
strcpy(step.gate, dir);
if (strcmp(dir, "NOT") == 0) {
numInputs = 1;
}
if (strcmp(dir, "PASS") == 0) {
numInputs = 1;
}
if (strcmp(dir, "DECODER") == 0) {
fscanf(file, "%d", &numInputs);
step.n = numInputs;
numOutputs = pow(2, numInputs);
}
if (strcmp(dir, "MULTIPLEXER") == 0) {
fscanf(file, "%d", &numInputs);
step.s = numInputs;
numInputs = pow(2, numInputs);
}
step.inputs = malloc(numInputs * sizeof(int));
step.outputs = malloc(numOutputs * sizeof(int));
step.selectors = malloc(step.s * sizeof(int));
char v[17];
for (i = 0; i < numInputs; i++) {
fscanf(file, "%*[: ]%16s", v);
step.inputs[i] = indexOf(size, names, v);
}
for (i = 0; i < step.s; i++) {
fscanf(file, "%*[: ]%16s", v);
step.selectors[i] = indexOf(size, names, v);
}
for (i = 0; i < numOutputs; i++) {
fscanf(file, "%*[: ]%16s", v);
int idx = indexOf(size, names, v);
if (idx == -1) {
size++;
tcount++;
char **tmp = realloc(names, size * sizeof *tmp);
if (!tmp) abort(); // handle alloc failure
names = tmp;
names[size - 1] = malloc(17 * sizeof(char));
strcpy(names[size - 1], v);
step.outputs[i] = size - 1;
}
else {
step.outputs[i] = idx;
}
}
//add step to list of temp
if (!temp) {
temp = malloc(sizeof(struct directive));
} else {
temp = realloc(temp, scount * sizeof(struct directive));
}
temp[scount - 1] = step;
}
// initialize values array
values = malloc(size * sizeof(int));
resetValues(size, values);
while(1 < 2) {
//print inputs
for (i = 0; i < icount; i++) {
printf("%d ", values[i + 2]);
}
printf("|");
//run through temp, calculate outputs
for (i = 0; i < scount; i++) {
struct directive step = temp[i];
if (strcmp(step.gate, "NOT") == 0) {
NOT(values, step.inputs[0], step.outputs[0]);
}
if (strcmp(step.gate, "AND") == 0) {
AND(values, step.inputs[0], step.inputs[1], step.outputs[0]);
}
if (strcmp(step.gate, "OR") == 0) {
OR(values, step.inputs[0], step.inputs[1], step.outputs[0]);
}
if (strcmp(step.gate, "NAND") == 0) {
NAND(values, step.inputs[0], step.inputs[1], step.outputs[0]);
}
if (strcmp(step.gate, "NOR") == 0) {
NOR(values, step.inputs[0], step.inputs[1], step.outputs[0]);
}
if (strcmp(step.gate, "XOR") == 0) {
XOR(values, step.inputs[0], step.inputs[1], step.outputs[0]);
}
if (strcmp(step.gate, "PASS") == 0) {
PASS(values, step.inputs[0], step.outputs[0]);
}
if (strcmp(step.gate, "DECODER") == 0) {
DECODER(values, step.n, step.inputs, step.outputs);
}
if (strcmp(step.gate, "MULTIPLEXER") == 0) {
MUX(values, step.s, step.inputs, step.selectors, step.outputs[0]);
}
}
//print outputs
for (i = 0; i < ocount; i++) {
printf(" %d", values[icount + i + 2]);
}
printf("\n");
if (!incrementInputs(values, icount)) {
break;
}
}
for (i = 0; i < icount; i++) {
free(names[i + 2]);
}
for (i = 0; i < ocount; i++) {
free(names[i + icount + 2]);
}
for (int i = 0; i < scount; i++) {
free(temp[i].inputs);
free(temp[i].outputs);
free(temp[i].selectors);
}
free(names[0]);
free(names[1]);
//free(names[size-1]);
free(values);
free(temp);
free(names);
return 0;
}
Im using a series of double pointers that point to other double pointers.
Currently i have a struct that points to other structs that have double pointers.
I was using the "sprintf" command to store values and it was working great until i encountered a seg fault.
sprintf(a->cs[a->structCount].fs[sFunCount].parameterType[insideParam],
"%s", a->array);
I got rid of the sprintf and just made it equal to a->array and it worked. But it doesnt store it correctly.
a->cs[a->structCount].fs[sFunCount].parameterType[insideParam] = a->type;
It just keep printing out "int" instead of anything else. When i do
a->cs[a->structCount].fs[sFunCount].parameterType[insideParam] = "double";
It stores it correctly.
Can you also advise me if im mallocing all my arrays correctly and if im freeing them correctly as well.
Heres all my code..
#include "header.h"
int main(int argc, char * argv[]){
all * a;
if(argc != 2){
printf("Error: Send input file as command line argument.\n");
return 1;
}
display(argv[1]);
a = openFile(argv[1]);
printProgram(a);
freeMe(a);
return 0;
}
all * openFile(char * fileName){
FILE *fp;
int token = 0, z = 0, x = 0, j = 0, i = 0, dotSwitch = 0,
hashSwitch = 0, leftPacSwitch = 0, varNCount = 0, funNCount = 0,
parameter = 0, parameterName = 0, rightBrace = 0, leftBrace = 0,
structNameSwitch = 0, insideStruct = 0, globalCount = 0,
funRightBrace = 0, funLeftBrace = 0, sFunCount = 0, insideParam = 0;
all * a = malloc(sizeof(all));
switches * s = malloc(sizeof(switches));
//a = m(a);
s->structSwitch = 0;
s->functionSwitch = 0;
s->variableSwitch = 0;
s->commentSwitch = 0;
s->quoteSwitch = 0;
s->slashSwitch = 0;
s->nameSwitch = 0;
s->bracketSwitch = 0;
a->hashCount = 0;
a->cs = malloc(sizeof(cStruct *) * 100);
a->fs = malloc(sizeof(fStruct *) * 100);
a->globalVariableType = malloc(sizeof(char *) * 100);
a->globalVariableName = malloc(sizeof(char *) * 100);
a->includes = malloc(sizeof(char *) * 100);
a->array = malloc(sizeof(char));
a->type = malloc(sizeof(char));
a->vName = malloc(sizeof(char));
a->preDot = malloc(sizeof(char));
a->prePac = malloc(sizeof(char));
a->structName = malloc(sizeof(char));
a->structCount = 0;
a->cs[a->structCount].variableCount = 0;
for(i = 0; i < 100; i++){
a->cs[i].name = malloc(sizeof(char)*50);
a->cs[i].variableType = malloc(sizeof(char)*50);
a->cs[i].variableName = malloc(sizeof(char)*50);
a->cs[i].fs = malloc(sizeof(fStruct)*50);
a->fs[i].functionName = malloc(sizeof(char)*50);
a->fs[i].functionType = malloc(sizeof(char)*50);
a->fs[i].parameterName = malloc(sizeof(char)*50);
a->fs[i].parameterType = malloc(sizeof(char)*50);
a->globalVariableName[i] = malloc(sizeof(char)*50);
a->globalVariableType[i] = malloc(sizeof(char)*50);
a->includes[i] = malloc(sizeof(char)*50);
for(x = 0; x < 100; x++){
a->cs[i].variableType[x] = malloc(sizeof(char)*50);
a->cs[i].variableName[x] = malloc(sizeof(char)*50);
a->cs[i].fs[x].functionName = malloc(sizeof(char)*50);
a->cs[i].fs[x].functionType = malloc(sizeof(char)*50);
a->cs[i].fs[x].parameterType = malloc(sizeof(char)*50);
a->cs[i].fs[x].parameterName = malloc(sizeof(char)*50);
a->fs[i].parameterName[x] = malloc(sizeof(char)*50);
a->fs[i].parameterType[x] = malloc(sizeof(char)*50);
for(z = 0; z < 100; z++){
a->cs[i].fs[x].parameterType[z] = malloc(sizeof(char)*50);
a->cs[i].fs[x].parameterName[z] = malloc(sizeof(char)*50);
}
}
}
//Opening the file
fp = fopen(fileName,"r");
//If file doesnt exist then display output
if(fp == NULL){
perror("Error while opening the file.\n");
exit(EXIT_FAILURE);
}
else{
printf("\nUpdated File(C):\n");
}
while((token = fgetc(fp)) != EOF){
if(token != ' ' && token != '{' && token != '}' && token != ';' && token != '\n' && token != '(' && token != ')' && token != '/' && token != '"' && token != '*' && token != '\\' && token != ',' && token != '.' && token != '>' && token != '#'){
a->array[j] = token;
j++;
}
else{
if(token == '/'){
s->commentSwitch++;
printf("/");
}
else if(token == '>'){
sprintf(a->prePac,"%s%c", a->array, token);
leftPacSwitch = 1;
}
else if(token == '#'){
hashSwitch = 1;
}
else if(token == '.'){
sprintf(a->preDot,"%s%c", a->array, token);
dotSwitch = 1;
}
else if(token == '{' && s->structSwitch == 1 && structNameSwitch == 0){
sprintf(a->cs[a->structCount].name,"%s", a->structName);
//structCount++;
rightBrace++;
printf("%c", token);
structNameSwitch = 1;
insideStruct = 1;
}
else if (token == '{' && s->structSwitch == 1){
rightBrace++;
a->cs[a->structCount].rightBracket = rightBrace;
if (s->structFunctionSwitch == 1){
funRightBrace++;
a->cs[a->structCount].fs[funRightBrace].rightBracket = funRightBrace;
}
printf("%c", token);
}
else if(token == '}' && s->structSwitch == 1){
leftBrace++;
if(rightBrace == leftBrace){
s->structSwitch = 0;
rightBrace = 0;
leftBrace = 0;
insideStruct = 0;
sFunCount = 0;
a->structCount++;
}
else if (s->structFunctionSwitch == 1){
funLeftBrace++;
a->cs[a->structCount].fs[funLeftBrace].leftBracket = funLeftBrace;
if(funRightBrace == funLeftBrace){
s->structFunctionSwitch = 0;
funRightBrace = 0;
funLeftBrace = 0;
}
}
printf("%c", token);
}
else if(token == '\\'){
s->slashSwitch = 1;
s->quoteSwitch = 0;
printf("%s", a->array);
printf("%c", token);
}
else if(token == '(' && s->variableSwitch == 1 && s->structSwitch == 0){
s->bracketSwitch = 1;
sprintf(a->fs[funNCount].functionType, "%s", a->type);
sprintf(a->fs[funNCount].functionName, "%s", a->array);
funNCount++;
printf("%s", a->array);
printf("%c", token);
}
else if(token == '(' && insideStruct == 1 && s->variableSwitch == 1){
s->bracketSwitch = 1;
insideParam = 0;
printf("%s",a->array);
printf("%c", token);
sprintf(a->cs[a->structCount].fs[sFunCount].functionType, "%s", a->type);
sprintf(a->cs[a->structCount].fs[sFunCount].functionName, "%s", a->array);
s->structFunctionSwitch = 1;
s->variableSwitch = 0;
s->nameSwitch = 0;
a->cs[a->structCount].functionCount = sFunCount;
}
else if(token == ')' && insideStruct == 1 && s->bracketSwitch == 1){
s->bracketSwitch = 0;
s->structFunctionSwitch = 0;
a->cs[a->structCount].fs[sFunCount].parameterName[insideParam] = a->array;
a->cs[a->structCount].fs[sFunCount].parameterType[insideParam] = a->type;
printf("%d",insideParam);
a->cs[a->structCount].fs[sFunCount].paraCount = insideParam;
// printf("s: %d , f: %d, i: %d\n", a->structCount,sFunCount,insideParam);
// printf("%s\n", a->cs[a->structCount].fs[sFunCount].parameterName[insideParam]);
printf("%s", a->array);
printf("%c", token);
sFunCount++;
}
else if(token == ')' && s->variableSwitch == 1){
sprintf(a->fs[funNCount].parameterName[a->fs[funNCount].paraCount], "%s", a->array);
parameterName++;
printf("%s",a->array);
printf("%c", token);
s->bracketSwitch = 0;
s->variableSwitch = 0;
parameter = 0;
}
else if(token == '*'){
printf("%s", a->array);
printf("%c", token);
}
else if(s->commentSwitch == 2){
printf("%s",a->array);
printf("%c", token);
if(token == '\n'){
s->commentSwitch = 0;
}
}
else if(s->slashSwitch == 1){
printf("%s",a->array);
printf("%c", token);
s->slashSwitch = 0;
}
else if(token == '"' && s->slashSwitch == 0 && s->commentSwitch == 0){
s->quoteSwitch++;
printf("%s",a->array);
printf("%c", token);
if(s->quoteSwitch == 2){
s->quoteSwitch = 0;
}
}
else if(s->quoteSwitch == 1 && token != '"'){
printf("%s",a->array);
printf("%c", token);
}
else{
if(hashSwitch == 1 && dotSwitch == 1 && leftPacSwitch == 1){
printf("#%s%s", a->preDot,a->prePac);
sprintf(a->includes[a->hashCount], "%s%s", a->preDot,a->prePac);
a->hashCount++;
hashSwitch = 0;
dotSwitch = 0;
leftPacSwitch = 0;
}
else if(strcmp(a->array,"class") == 0 && s->commentSwitch != 2 && s->quoteSwitch != 1){
strcpy(a->array,"struct");
s->structSwitch = 1;
structNameSwitch = 0;
varNCount = 0;
}
else if(s->structSwitch == 1 && insideStruct == 1){
if(strcmp(a->array,"int") == 0 || strcmp(a->array,"double") == 0 || strcmp(a->array,"float") == 0 || strcmp(a->array,"char") == 0 || strcmp(a->array,"void") == 0){
if(s->bracketSwitch == 0 ){
strcpy(a->type,a->array);
s->variableSwitch = 1;
s->nameSwitch = 0;
}
else if(s->bracketSwitch == 1){
// printf("vjjkjj");
a->cs[0].fs[0].parameterType[4] = a->type;
strcpy(a->type,a->array);
s->variableSwitch = 0;
s->nameSwitch = 0;
s->structFunctionSwitch = 1;
insideParam++;
a->cs[a->structCount].fs[sFunCount].paraCount++;
}
// printf("var1: %d nam: %d Bra: %d fun: %d inside: %d st: %d\n", s->variableSwitch, s->nameSwitch,s->bracketSwitch, s->structFunctionSwitch, insideStruct, s->structSwitch);
/*else{
s->variableSwitch = 0;
}*/
}
//Gets all the variables in the struct
else if(s->nameSwitch == 0 && s->variableSwitch == 1 && s->bracketSwitch == 0){
varNCount++;
strcpy(a->vName,a->array);
a->cs[a->structCount].variableCount = varNCount;
sprintf(a->cs[a->structCount].variableType[varNCount], "%s", a->type);
sprintf(a->cs[a->structCount].variableName[varNCount], "%s", a->vName);
s->variableSwitch = 0;
}
else if(s->nameSwitch == 0 && s->variableSwitch == 0 && s->bracketSwitch == 1 && s->structFunctionSwitch == 1){
a->cs[a->structCount].fs[sFunCount].parameterType[insideParam] = a->type;
a->cs[a->structCount].fs[sFunCount].parameterName[insideParam] = a->array;
if(strcmp(a->type, "double") == 0){
a->cs[a->structCount].fs[sFunCount].parameterType[insideParam] = "double";;
}
a->cs[1].fs[0].parameterType[3] = "double";
a->cs[1].fs[0].parameterName[3] = "gg";
printf("struct: %s\n", a->type);
//printf("structh: %d, Function: %d, Param: %d", a->structCount, sFunCount, insideParam);
// a->cs[a->structCount].fs[sFunCount].paraCount = insideParam;
// printf("HAHA%d", a->cs[a->structCount].fs[sFunCount].paraCount);
s->nameSwitch = 1;
}
}
else if(s->structSwitch == 1 && structNameSwitch == 0){
strcpy(a->structName,a->array);
}
else if(strcmp(a->array,"int") == 0 || strcmp(a->array,"double") == 0 || strcmp(a->array,"float") == 0 || strcmp(a->array,"char") == 0 || strcmp(a->array,"void") == 0){
if(s->bracketSwitch == 1){
sprintf(a->fs[funNCount].parameterType[parameter], "%s", a->array);
a->fs[funNCount].paraCount = parameter;
parameter++;
}
else{
strcpy(a->type,a->array);
}
s->variableSwitch = 1;
s->nameSwitch = 0;
}
else if(s->variableSwitch == 1 && s->nameSwitch == 0){
if(s->bracketSwitch == 1){
sprintf(a->fs[funNCount].parameterName[a->fs[funNCount].paraCount], "%s", a->array);
parameterName++;
}
else{
strcpy(a->vName,a->array);
}
s->nameSwitch = 1;
}
else if(s->variableSwitch == 1 && s->nameSwitch == 1 && s->bracketSwitch == 0){
sprintf(a->globalVariableType[globalCount], "%s", a->type);
sprintf(a->globalVariableName[globalCount], "%s", a->vName);
a->globalCount = globalCount;
globalCount++;
s->variableSwitch = 0;
s->nameSwitch = 0;
}
printf("%s",a->array);
printf("%c", token);
}
memset(a->array,0,strlen(a->array));
j = 0;
}
}
a->funCount = funNCount;
printf("%d\n\n",a->fs[2].paraCount);
printf("{ : %d\n", rightBrace);
printf("} : %d\n", leftBrace);
fclose(fp);
return a;
}
int fOrV(char * c){
int len = strlen(c), i;
//char * array = malloc(sizeof(char*));
for(i = 0;i < len; i++){
if(c[i] == '('){
return 1;
}
else if(c[i] == ')' || c[i] == ','){
//printf("LOOL %s\n",c);
return 2;
}
}
return 0;
}
int display(char * fileName){
FILE *fp;
char * array;
int token = 0, totalStruct = 0, totalVariable = 0, j = 0;
array = malloc(sizeof(char));
//Opening the file
fp = fopen(fileName,"r");
//If file doesnt exist then display output
if(fp == NULL){
perror("Error while opening the file.\n");
exit(EXIT_FAILURE);
}
else{
printf("File %s opened successfully\nOriginal Code(C++):\n", fileName);
}
while((token = fgetc(fp)) != EOF){
if(token != ' ' && token != '{' && token != '}' && token != ';' && token != '\n' && token != '(' && token != ')' && token != '/' && token != '"' && token != '*' && token != '\\' && token != ',' && token != '.' && token != '[' && token != ']'){
array[j] = token;
j++;
}
else{
if(strcmp(array,"class") == 0){
totalStruct++;
}
else if(strcmp(array,"int") == 0 || strcmp(array,"double") == 0 || strcmp(array,"float") == 0 || strcmp(array,"char") == 0 || strcmp(array,"void") == 0){
totalVariable++;
}
memset(array,0,strlen(array));
j = 0;
printf("%s",array);
}
printf("%c", token);
}
fclose(fp);
return 0;
}
void printProgram(all * a){
int b, i;
for(b = 0; b < a->structCount; b++){
printf("Struct Name: %s\n", a->cs[b].name);
for(i = 1; i <= a->cs[b].variableCount; i++){
printf("\tVariabe Type: %s %s\n", a->cs[b].variableType[i],a->cs[b].variableName[i]);
}
for(i = 0; i <= a->cs[b].functionCount; i++){
printf("\tFunction Type: %s %s\n", a->cs[b].fs[i].functionType,a->cs[b].fs[i].functionName);
}
}
for(i = 0; i <= a->globalCount; i++){
printf("Global Variable: %s %s\n", a->globalVariableType[i], a->globalVariableName[i]);
}
printf("----------------------------------------------\n");
for(i = 0; i < a->hashCount; i++){
printf("%s\n", a->includes[i]);
}
printf("\n");
for(i = 0; i <= a->globalCount; i++){
printf("%s %s;\n", a->globalVariableType[i], a->globalVariableName[i]);
}
printf("\n");
for(b = 0; b < a->structCount; b++){
printf("struct %s {\n", a->cs[b].name);
for(i = 1; i <= a->cs[b].variableCount; i++){
printf("\t%s %s;\n", a->cs[b].variableType[i],a->cs[b].variableName[i]);
}
for(i = 0; i <= a->cs[b].functionCount; i++){
printf("\t%s (*%s%s)();\n", a->cs[b].fs[i].functionType,a->cs[b].name,a->cs[b].fs[i].functionName);
}
printf("}\n");
}
printf("WHAT: %s\n", a->cs[0].fs[0].parameterType[3]);
int x;
for(b = 0; b < a->structCount; b++){
// printf("S: %d", b);
for(i = 0; i <= a->cs[b].functionCount; i++){
//printf("F: %d", i);
printf("%s %s%s(", a->cs[b].fs[i].functionType,a->cs[b].name,a->cs[b].fs[i].functionName);
for(x = 1; x <= a->cs[b].fs[i].paraCount; x++){
//printf("F: %d\n", x);
if(x == (a->cs[b].fs[i].paraCount)){
printf("%s %s", a->cs[b].fs[i].parameterType[x],a->cs[b].fs[i].parameterName[x]);
}
else if(x == 1){
printf("%s %s,", a->cs[b].fs[i].parameterType[x],a->cs[b].fs[i].parameterName[x]);
}
else{
printf(" %s %s,", a->cs[b].fs[i].parameterType[x],a->cs[b].fs[i].parameterName[x]);
}
}
printf("){\n");
}
printf("\n");
}
for(i = 0; i < a->funCount; i++){
printf("%s %s(", a->fs[i].functionType, a->fs[i].functionName);
for(b = 0; b <= a->fs[i+1].paraCount; b++){
printf("%s %s ", a->fs[i+1].parameterType[b], a->fs[i+1].parameterName[b]);
}
printf("){\n");
}
}
void freeMe(all * a){
int i, x;
/*for(i = 0; i < 100; i++){
free(a->cs[i].name);
free(a->cs[i].variableType);
free(a->cs[i].variableName);
free(a->cs[i].fs);
free(a->fs[i].functionName);
free(a->fs[i].functionType);
free(a->fs[i].parameterName);
free(a->fs[i].parameterType);
free(a->globalVariableName[i]);
free(a->globalVariableType[i]);
free(a->includes[i]);
}
free(a->cs);
free(a->fs);
free(a->globalVariableType);
free(a->globalVariableName);
free(a->includes);
free(a->array);
free(a->type);
free(a->vName);
free(a->preDot);
free(a->prePac);
free(a->structName);*/
free(a);
//free(s);
}
Even without the missing #include "header.h" where all structures were declared, I have used the content of the provided source code to restore the nested-data structure and checked all calls of malloc().
Restored Data - here are all reversed data structures (supposed to come from "header.h")
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
typedef struct st_fStruct {
char *functionName;
char *functionType;
char **parameterName;
char **parameterType;
int rightBracket;
int leftBracket;
int paraCount;
} fStruct;
typedef struct st_cStruct {
int variableCount;
char *name;
char **variableType;
char **variableName;
fStruct *fs;
int rightBracket;
int functionCount;
} cStruct;
typedef struct st_all {
int hashCount;
cStruct *cs;
fStruct *fs;
char **globalVariableType;
char **globalVariableName;
char **includes;
char *array;
char *type;
char *vName;
char *preDot;
char *prePac;
char *structName;
int structCount;
int globalCount;
int funCount;
} all;
typedef struct st_switches {
int structSwitch;
int functionSwitch;
int variableSwitch;
int commentSwitch;
int quoteSwitch;
int slashSwitch;
int nameSwitch;
int bracketSwitch;
int structFunctionSwitch;
} switches;
int display(char * fileName);
all* openFile(char * fileName);
void printProgram(all* p_all);
void freeMe(all* p_all);
Mallocing Analysis - here are all the provided malloc() and corrected proposal.
Error in the sizeof() items when calling malloc().
a->cs = malloc(sizeof(cStruct *) * 100); // must be sizeof(cStruct)
a->fs = malloc(sizeof(fStruct *) * 100); // must be sizeof(fStruct)
Error allocating only one char for a string.
a->array = malloc(sizeof(char)); // must be (sizeof(char)*50)
a->type = malloc(sizeof(char)); // must be (sizeof(char)*50)
a->vName = malloc(sizeof(char)); // must be (sizeof(char)*50)
a->preDot = malloc(sizeof(char)); // must be (sizeof(char)*50)
a->prePac = malloc(sizeof(char)); // must be (sizeof(char)*50)
a->structName = malloc(sizeof(char)); // must be (sizeof(char)*50)
// in the display function
array = malloc(sizeof(char)); // must be (sizeof(char)*50)
Mitigation between string char * and array of strings char **.
a->cs[i].variableType = malloc(sizeof(char)*50); // must be malloc(sizeof(char *)*100);
a->cs[i].variableName = malloc(sizeof(char)*50); // must be malloc(sizeof(char *)*100);
a->fs[i].parameterName = malloc(sizeof(char)*50); // must be malloc(sizeof(char *)*100);
a->fs[i].parameterType = malloc(sizeof(char)*50); // must be malloc(sizeof(char *)*100);
a->cs[i].fs[x].parameterType = malloc(sizeof(char)*50); // must be malloc(sizeof(char *)*100);
a->cs[i].fs[x].parameterName = malloc(sizeof(char)*50); // must be malloc(sizeof(char *)*100);
Bad size of an array of struct fStruct.
a->cs[i].fs = malloc(sizeof(fStruct)*50); // must be malloc(sizeof(fStruct)*100);
Correct use of malloc() (17/33).
all * a = malloc(sizeof(all));
switches * s = malloc(sizeof(switches));
a->globalVariableType = malloc(sizeof(char *) * 100);
a->globalVariableName = malloc(sizeof(char *) * 100);
a->includes = malloc(sizeof(char *) * 100);
for(i = 0; i < 100; i++){
a->cs[i].name = malloc(sizeof(char)*50);
a->fs[i].functionName = malloc(sizeof(char)*50);
a->fs[i].functionType = malloc(sizeof(char)*50);
a->includes[i] = malloc(sizeof(char)*50);
...
for(x = 0; x < 100; x++){
a->cs[i].variableType[x] = malloc(sizeof(char)*50);
a->cs[i].variableName[x] = malloc(sizeof(char)*50);
a->cs[i].fs[x].functionName = malloc(sizeof(char)*50);
a->cs[i].fs[x].functionType = malloc(sizeof(char)*50);
a->fs[i].parameterName[x] = malloc(sizeof(char)*50);
a->fs[i].parameterType[x] = malloc(sizeof(char)*50);
...
for(z = 0; z < 100; z++){
a->cs[i].fs[x].parameterType[z] = malloc(sizeof(char)*50);
a->cs[i].fs[x].parameterName[z] = malloc(sizeof(char)*50);
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 6 years ago.
Improve this question
#include<string.h>
typedef struct{
char Mnemonic[7];
int code;
} code;
typedef struct{
char label[10];
unsigned int location;
} symbolTab;
int opLook(char * mnemonic, code * optable)
{
int i = 0;
int value = 0;
for(i ; i<25 ; i++)
{
if(strcmp(mnemonic, optable[i].Mnemonic) == 0)
{
value = optable[i].code;
return value;
}
}
return value;
}
int opValid(char * mnemonic, code * optable)
{
int i = 0;
for(i ; i<25 ; i++)
{
if(strcmp(mnemonic, optable[i].Mnemonic) == 0)
{
return 1;
}
}
return 0;
}
int labelcheck(char * label, symbolTab * Table, int counter)
{
int i = 0;
int flag = 0;
if (counter == 0)
{
return flag;
}
else
{
for(i; i <counter; i ++)
{
if(strcmp(label, Table[i].label) == 0)
{
flag = 1;
}
}
return flag;
}
}
unsigned int labelVal(char * label, symbolTab * Table, int counter)
{
int i = 0;
for(i; i <counter; i ++)
{
if(strcmp(label, Table[i].label) == 0)
{
return Table[i].location;
}
}
}
void Assemble(char* filename)
{
unsigned int locctr = 0; /*location counter*/
unsigned int prolen = 0; /*program length*/
int mnemoVal; /*mnemonic Value in Int*/
int labelctr = 0;
code Opta[25] = {{"ADD", 24},{"AND",88},{"COMP",40},{"DIV",36},{"J",60},
{"JEQ",48},{"JGT",52},{"JLT",56},{"JSUB",72},{"LDA",00},
{"LDCH",80},{"LDL", 8},{"LDX", 4},{"MUL",32},{"OR",68},
{"RD",216},{"RSUB",76},{"STA",12},{"STCH",84},{"STL",20},
{"STX",16},{"SUB",28},{"TD",224},{"TIX",44},{"WD",220}};
symbolTab symTab[500];
char buffer[255];
FILE * source;
FILE * interFile;
FILE * objF;
FILE * ListFile;
interFile = fopen("intermidiateFile.txt", "w+");
ListFile = fopen("ListingFile.txt", "w+");
objF = fopen("ObjectFile.txt", "w+");
source = fopen("source.txt", "r");
char * lab; /*label*/
char * mnemo; /*mnemonic*/
char * operand;
char * address = "adress";
unsigned int opeaddress;
fgets(buffer, 255, source);
if (buffer[0] != '.')
{
fprintf(interFile, "%s", buffer);
}
/*Getting first line and initialization of Location Counter*/
if(buffer[0] == '.') /* if the line is a comment continue with the next iteration of the loop*/
{
locctr = 0;
}
else
{
if(buffer[0] == ' ' || buffer[0] == '\t')
{
mnemo = strtok(buffer, " \t");
operand = strtok(NULL, " \t");
if(strcmp(mnemo, "START") == 0)
{
locctr = strtol(operand, NULL, 16);
}
else
{
/*error*/
}
}
else
{
lab =strtok(buffer, " \t");
mnemo = strtok(NULL, " \t");
operand = strtok(NULL, " \t");
if(strcmp(mnemo, "START") == 0)
{
locctr = strtol(operand, NULL, 16);
}
else
{
/*error*/
}
}
}
/* End of the location counter initialization */
/*start while loop*/
while(!feof(source))
{
memset(lab, '\0', strlen(lab));
memset(mnemo, '\0', strlen(mnemo));
memset(operand, '\0', strlen(operand));
fgets(buffer, 255, source);
fprintf(interFile, "%s", buffer);
if(buffer[0] == '.') /* if the line is a comment continue with the next iteration of the loop*/
{
continue;
}
else /* Else for... If it is not a comment, then check if it start with a character or a space*/
{
if(buffer[0] == ' ' || buffer[0] == '\t') /* If it start with a space, then it is just a mnemonic or mnemonic & operand*/
{
mnemo = strtok(buffer, " \t\n\r");
if (strcmp(mnemo, "END") == 0)
{
break;
}
if(strcmp(mnemo, "RSUB") == 0)
{
mnemoVal = opLook(mnemo, Opta);
fprintf(interFile, "%x %02x\n", locctr, mnemoVal);
}
else
{
operand = strtok(NULL, " \t\r\n");
mnemoVal = opLook(mnemo, Opta);
fprintf(interFile, "%x %02x %s\n", locctr, mnemoVal, operand);
}
}
else
{
lab = strtok(buffer, " \t\n\r"); /* it has a label, mnemonic and operand*/
if(labelcheck(lab, symTab, labelctr) == 0) /* check if the label is already in the symTab, if not, add it, otherwise it is an error*/
{
strcpy(symTab[labelctr].label, lab);
symTab[labelctr].location = locctr;
labelctr++;
mnemo = strtok(NULL, " \t\n\r");
if (strcmp(mnemo, "END") == 0)
{
break;
}
operand = strtok(NULL, " \t\n\r");
mnemoVal = opLook(mnemo, Opta);
}
else
{
mnemo = strtok(NULL, " \t\n\r");
if (strcmp(mnemo, "END") == 0)
{
break;
}
operand = strtok(NULL, " \t\n\r");
mnemoVal = opLook(mnemo, Opta);
}
fprintf(interFile, "%x %s %02x %s\n", locctr, lab, mnemoVal, operand);
}
}
if(strcmp(mnemo, "WORD") == 0 )
{
locctr = locctr + 3;
}
else if(strcmp(mnemo, "BYTE") == 0 )
{
unsigned int val;
if (operand[0] =='C')
{
val = strlen(operand) - 3;
locctr = locctr + val;
}
else
{
val = (strlen(operand) - 3)/2;
locctr = locctr + val;
}
}
else if(strcmp(mnemo, "RESB") == 0)
{
locctr = locctr + atoi(operand);
}
else if(strcmp(mnemo, "RESW") == 0)
{
locctr = locctr + (3*atoi(operand));
}
else
{
locctr= locctr + 3;
}
}
/* End of While loop*/
prolen = locctr - symTab[0].location;
fprintf(interFile, "\n%x", prolen);
fclose(source);
fclose(interFile);
interFile = fopen("intermidiateFile.txt", "r");
/*Start the Listing File and Object File ---------------------Pass 2----------- */
fgets(buffer, 255, interFile);
if(buffer[0] == '.') /* if the line is a comment continue with the next iteration of the loop*/
{
locctr = 0;
/*Error missung Start or Misplaced*/
}
else
{
if(buffer[0] == ' ' || buffer[0] == '\t')
{
mnemo = strtok(buffer, " \t");
operand = strtok(NULL, " \t");
if(strcmp(mnemo, "START") == 0)
{
locctr = strtol(operand, NULL, 16);
strcpy(address, operand);
fprintf(ListFile, "%X %s %s\n", locctr, mnemo, operand);
}
else
{
/*error*/
}
}
else
{
lab =strtok(buffer, " \t");
mnemo = strtok(NULL, " \t");
operand = strtok(NULL, " \t");
if(strcmp(mnemo, "START") == 0)
{
locctr = strtol(operand, NULL, 16);
fprintf(ListFile, "%x %s %s %s\n", locctr, lab, mnemo, operand);
fprintf(objF, "H%s__%06x%06x\n", lab, locctr, prolen);
}
else
{
/*error*/
}
}
}
while(!feof(interFile))
{
memset(lab, '\0', strlen(lab));
memset(mnemo, '\0', strlen(mnemo));
memset(operand, '\0', strlen(operand));
memset(address, '\0', strlen(address));
memset(buffer, '\0', strlen(buffer));
fgets(buffer, 255, interFile);
if (buffer[0] == '\r')
{
continue;
}
if(buffer[0] == ' ' || buffer[0] == '\t')
{
mnemo = strtok(buffer, " \t\n\r");
if (strcmp(mnemo, "END") == 0)
{
break;
}
if(strcmp(mnemo, "RSUB") == 0)
{
memset(buffer, '\0', strlen(buffer));
fgets(address, 255, interFile);
mnemoVal = opLook(mnemo, Opta);
fprintf(ListFile, "%s %s %X0000", address, mnemo, mnemoVal);
}
else
{
operand = strtok(NULL, " \t\r\n");
mnemoVal = opLook(mnemo, Opta);
memset(buffer, '\0', strlen(buffer));
fgets(address, 255, interFile);
if (labelcheck(operand, symTab, labelctr) == 1)
{
opeaddress = labelVal(operand, symTab, labelctr);
}
else
{
opeaddress = 0;
/* error*/
}
fprintf(ListFile, "%s %s %s %02X%04X", address, mnemo, operand, mnemoVal, opeaddress);
}
}
else if (buffer[0] == '.')
{
fprintf(ListFile, "%s\n", buffer);
}
else
{
lab = strtok(buffer, " \t\n\r");
mnemo = strtok(NULL, " \t\n\r");
operand = strtok(NULL, " \t\n\r");
mnemoVal = opLook(mnemo, Opta);
memset(buffer, '\0', strlen(buffer));
fgets(address, 255, interFile);
if (labelcheck(operand, symTab, labelctr) == 1)
{
opeaddress = labelVal(operand, symTab, labelctr);
}
else
{
opeaddress = 0;
/* error*/
}
fprintf(ListFile, "%s %s %s %s %02X%04X", address, lab, mnemo, operand, mnemoVal, opeaddress);
}
}
fclose(interFile);
fclose(objF);
fclose(ListFile);
}
The error occurs in the last while loop when executing fgets();
I have looked if I had any variable or syntax wrong, but everything looks fine.
This is a part of a two pass assemble. The error varies between the fgets in the last while loop. At first I thought that it was the memset function, but the error still happened when I mark them as comments
Because of
char * address = "adress";
address is pointing to Read Only Memory
Trying to modify string literals (in your case "adress") invokes undefined behavior.
Then in your last loop
strcpy(address, operand);
memset(address, '\0', strlen(address));
fgets(address, 255, interFile);
Are wrong.
You could change that variable to a simple array of chars with enough room for your needs, e.g.:
char address[128];
I'm reading in from a file. Whenever I read in the word 'transition' I'm trying to add the next 5 elements that appear to a 2d array. I have a bunch of printf's which I have commented out that show that I am adding the proper element. However, once I finish reading in from file, I loop through to check my 2d array values and they have all been overwritten by the last row's values.
Here is my code
State* allStates[1002];
State* currentState;
char* input = argv[1];
char* inputStr = argv[2];
int maxTrans = atoi(argv[3]);
int transCount = -1;
FILE* inputFile;
char* transition[maxTrans][5];
inputFile = fopen(input, "r");
if (inputFile == 0)
{
perror("Can't open file\n");
exit(-1);
}
else
{
char next[1000];
//int counter = 0;
while (fgets(next, 1000, inputFile) != NULL)
{
char *nextWord;
nextWord = strtok_r(next, "\t");
if (strcmp(nextWord, "state") == 0)
{
//counter++;
nextWord = strtok_r(NULL, "\t");
//puts(nextWord);
int q = atoi(nextWord);
nextWord = strtok_r(NULL, "\n");
//puts(nextWord);
if (strcmp(nextWord, "accept") == 0)
{
State* newState = makeState(q, 1, 0, 0);
allStates[q] = newState;
}
else if (strcmp(nextWord, "reject") == 0)
{
State* newState = makeState(q, 0, 1, 0);
allStates[q] = newState;
}
else if (strcmp(nextWord, "start") == 0)
{
State* newState = makeState(q, 0, 0, 1);
allStates[q] = newState;
currentState = newState;
}
else
{
State* newState = makeState(q, 0, 0, 0);
allStates[q] = newState;
}
}
if (strcmp(nextWord, "transition") == 0)
{
//printf("\n");
//setup 2d array of transitions
transCount++;
nextWord = strtok_r(NULL, "\t");
//puts(nextWord);
transition[transCount][0] = nextWord;
//printf("%c", *transition[transCount][0]);
nextWord = strtok_r(NULL, "\t");
//puts(nextWord);
transition[transCount][1] = nextWord;
//printf("%c", *transition[transCount][1]);
nextWord = strtok_r(NULL, "\t");
//puts(nextWord);
transition[transCount][2] = nextWord;
//printf("%c", *transition[transCount][2]);
nextWord = strtok_r(NULL, "\t");
//puts(nextWord);
transition[transCount][3] = nextWord;
//printf("%c", *transition[transCount][3]);
nextWord = strtok_r(NULL, "\n");
//puts(nextWord);
transition[transCount][4] = nextWord;
//printf("%c", *transition[transCount][4]);
}
}
}
fclose(inputFile);
int u = 0;
int y = 0;
char m = 'm';
for (u; u < 12; u++)
{
printf("\n");
for (y = 0; y < 5; y++)
{
//transition[u][y] = &m;
printf("%c", *transition[u][y]);
}
}
If the file I'm reading in looks like this,
transition 0 x 0 x R
transition 0 1 4 1 L
transition 0 0 1 x R
I expect the array to look like this
0x0xR
0141L
001xR
Instead the values of the array will be
001xR
001xR
001xR
I know that the overwriting happens at each row. ie: when I'm writing to row 2 the values become:
0141L
0141L
I'm really lost as to how to fix it though.
The problem was with my incorrect usage of strtok(). I took Dmitri's advice and used strdup() which allocates memory for the new string and I'm getting the proper results.
nextWord = strtok(NULL, "\t");
temp = strdup(nextWord);
transition[transCount][0] = temp;