Why segmentation(coredump) in the following code in C?

hi
I have a method which returns char*. In this method am using switch case. I am getting segmentation error in case 49 and my code is

case 49:
          if(intFlag == 0210)
          {
                iiIDCode = atoi(getsubstring(sReq,262,2));
                l = atoi(getsubstring(sReq,26+2+iiIDCode,3));
                iiTemp = 26+2+iiFIDCode+l+3;
                j = atoi(getsubstring(sReq,iiTemp,3));
                k  = atoi(getsubstring(sReq,iiTemp+j+3,3));
                fprintf(fp,"\nCurrency Code Transaction:\t\t[%s]",getsubstring       (sReq,iiTemp+j+k+3+3,3));
                strcat(cRes,getsubstring(sReq,iiTemp+j+k+3+3,3));;
          }
         else if(intFlag == 110)
         {
          }   
break;

getsubstring is a method am using to substring the string and it is working fine. If i remove if and else part it is working fine but if i add if else condition in case 49: it is throwing error Segmentation Coredump. Why? What could be the error? How to solve this?
Thanks

As a guess - strcat(). cRes is not large enough to have extra characters added on the end.

Best idea - compile with the -g flag. When a core dumpp occurs use the debugger:
gdb example

gdb myfile core
> ba

ba will print the current stack with line numbers. I am betting on the line with strcat() as the culprit.

I faced the same problem couple of days back.
Either you are using strcat directly on cRes without initialising cRes or cRes is not a char array.

hi All
This is the way i have declared cRes. sReq is very large string and i declared sRes as char sRes[2500] which is global.

char* cRes;
cRes = (char*) malloc(5 + sizeof(sReq));

What could be the problem?
Thanks

Did you analyze the core file.

strcat() will start appending the second string from the end of the first string.

So if cRes is already holding anything more than 5 chars before strcat(), then there may not be enough room to copy the substring of cReq.

What i guess is, as your method returning char *, and if the control goes in to else part, it may be the case that you are returning the invalid pointer.

So check for the return value usage, what is happening with the return value of your method.

segmentation fault can happen for thousands of reason, you need to analyze what cuasing it.
use

gdb a.out core

hi
Please go through my complete code and help me out to solve it.

#define MYSPACE "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
char* GetResponsePrimaryElements(char cResBinary[])
{
int i, j, k,l;
int intTranFlag = iTranFlag;
int iiTemp;
int iiFIDCode;
char* cRes;
cRes = (char*) malloc(1550 * sizeof(MYSPACE));
for(i=0;i<strlen(cResBinary);i++)
{
if(cResBinary[i]=='1')
{
switch(i+1)
{
case 1:
fprintf(fp,"\nSecondary:\t\t\t[%s]", getsubstring(sReq,20,16));
if(intTranFlag == 0210)
strcat(cRes,"0210");
else if(intTranFlag == 0110)
strcat(cRes,"0110");
strcat(cRes,getsubstring(sReq,4,16));
strcat(cRes,getsubstring(sReq,20,16));
iLength = 36;
break;
case 2:
fprintf(fp,"\n Number:\t\t\t\t[%s]", getsubstring(sReq,iLength,20));
strcat(cRes,getsubstring(sReq,iLength,20));
iLength = iLength + 20;
break;
case 3:
fprintf(fp,"\nCode:\t\t\t\t[%s]", getsubstring(sReq,iLength,6));
strcat(cRes,getsubstring(sReq,iLength,6));
iLength = iLength + 6;
break;
case 4:
fprintf(fp,"\nAmount:\t\t\t[%s]", getsubstring(sReq,iLength,12));
strcat(cRes,getsubstring(sReq,iLength,12));
iLength = iLength + 12;
break;
case 5:
fprintf(fp,"\nAmount:\t\t\t[%s]", getsubstring(sReq,iLength,12));
strcat(cRes,getsubstring(sReq,iLength,12));
iLength = iLength + 12;
break;
case 6:
fprintf(fp,"\nAmount,:\t\t[%s] ", getsubstring(sReq,iLength,12));
strcat(cRes,getsubstring(sReq,iLength,12));
iLength = iLength + 12;
break;
case 7:
fprintf(fp,"\nDate:\t\t[%s] ", getsubstring(sReq,iLength,10));
strcat(cRes,getsubstring(sReq,iLength,10));
break;
case 10:
if(intTranFlag == 0110)
{
fprintf(fp,"\nRate:\t[%s]", getsubstring(sReq,iLength,15));
strcat(cRes,getsubstring(sReq,iLength,15));
}
break;
case 11:
fprintf(fp,"\nAudit Number:\t\t[%s]", getsubstring(sReq,123,6));
strcat(cRes,getsubstring(sReq,123,6));
break;
case 15:
fprintf(fp,"\nDate\t\t\t[####]");
strcat(cRes,"####");
break;
case 18:
if(intTranFlag == 0110)
{
fprintf(fp,"\nType:\t\t\t\t[%s]", getsubstring(sReq,153,4));
strcat(cRes,getsubstring(sReq,153,4));
}
break;
case 19:
fprintf(fp,"Code:\t[%s]", getsubstring(sReq,153,3));
strcat(cRes,getsubstring(sReq,153,3));
break;
case 21:
fprintf(fp,"\nCode:\t[%s]", getsubstring(sReq,156,3));
strcat(cRes,getsubstring(sReq,156,3));
break;
case 28:
fprintf(fp,"\nDate:\t\t[####]");
strcat(cRes,"####");
break;
case 32:
iiTemp = atoi(getsubstring(sReq,209,2));
strcat(cRes,getsubstring(sReq,209,2));
if(iiTemp <= 11)
{
fprintf(fp,"\n Code:\t\t[%s]", getsubstring(sReq,209+2,iiTemp));
strcat(cRes,getsubstring(sReq,209+2,iiTemp));
}
else
fprintf(fp,"\n*** Length violates maximum length of Bit 32 ");
break;
case 33:
iiFIDCode = atoi(getsubstring(sReq,209+2+iiTemp,2));
strcat(cRes,getsubstring(sReq,209+2+iiTemp,2));
if(iiFIDCode <= 11)
{
fprintf(fp,"\nCode:\t\t[%s]", getsubstring(sReq,209+2+iiTemp,iiFIDCode));
strcat(cRes,getsubstring(sReq,209+2+iiTemp,iiFIDCode));
iiFIDCode = 209 + 2 + 2 + iiTemp + iiFIDCode;
}
else
fprintf(fp,"\n
Length violates maximum length of Bit 33 **");
break;
case 37:
fprintf(fp,"\n Number:\t\t[%s]", getsubstring(sReq,iiFIDCode,12));
strcat(cRes,getsubstring(sReq,iiFIDCode,12));
break;
case 38:
fprintf(fp,"\n Response:\t[######]");
strcat(cRes,"######");
break;
case 39:
fprintf(fp,"\nAction :\t\t[##]");
strcat(cRes,"##");
break;
case 41:
fprintf(fp,"\nCard :\t\t[%s]", getsubstring(sReq,231,16));
strcat(cRes,getsubstring(sReq,231,16));
break;
case 42:
fprintf(fp,"\nCard:\t[%s]", getsubstring(sReq,247,15));
strcat(cRes,getsubstring(sReq,247,15));
break;
case 48:
fprintf(fp,"\nAdditional Data:\t\t\t[############################]");
strcat(cRes,"###");
break;
case 49:
if(intTranFlag == 0210) /
Here am getting error, if i remove if condition it is working fine */
{
iiFIDCode = atoi(getsubstring(sReq,262,2));
l = atoi(getsubstring(sReq,262+2+iiFIDCode,3));
iiTemp = 262+2+iiFIDCode+l+3;
j = atoi(getsubstring(sReq,iiTemp,3));
k = atoi(getsubstring(sReq,iiTemp+j+3,3));
fprintf(fp,"\nCurrency Code Transaction:\t\t[%s]",getsubstring(sReq,iiTemp+j+k+3+3,3));
strcat(cRes,getsubstring(sReq,iiTemp+j+k+3+3,3));;
}
break;
case 50:
fprintf(fp,"\nCurrency:\t\t[%s]",getsubstring(sReq,iiTemp+j+k+3+3+3,3));
strcat(cRes,getsubstring(sReq,iiTemp+j+k+3+3+3,3));
break;
case 51:
fprintf(fp,"\nCurrency Code Billing:\t\t\t[%s]",getsubstring(sReq,iiTemp+j+k+3+3+3+3,3));
strcat(cRes,getsubstring(sReq,iiTemp+j+k+3+3+3+3,3));
break;
case 54:
fprintf(fp,"\nAm:\t\t\t[######]");
strcat(cRes,"######");
break;
case 62:
fprintf(fp,"\nAm:\t\t\t[%s]", getsubstring(sReq,iiTemp+j+k+3+3+3+3+3+16,12));
strcat(cRes,getsubstring(sReq,iiTemp+j+k+3+3+3+3+3+16,12));
break;
case 64:
fprintf(fp,"\nCurrency:\t\t[%s]", getsubstring(sReq,iiTemp+j+k+3+3+3+3+3+16+12,3));
strcat(cRes,getsubstring(sReq,iiTemp+j+k+3+3+3+3+3+16+12,3));
intTemp = iiTemp+j+k+3+3+3+3+3+16+12+3;
break;
default:
break;
}
}
}
}
return cRes;
}

when i used gdb a.out core
I got this message
Program terminated with signal 11, Segmentation fault.
(no debugging symbols found)...(no debugging symbols found)...#0 0xd03caa24 in strnlen ()
What is this error?

compile your program with -g option and then execute, gdb.

I think you have posted only the one function, the problem could be even at the callee side, how the return value is being used there.

So try gdb and let us know, what you see.

the gdb says that the segmentation fault occurred in strnlen() , strnlen(3) - Linux man page

Check for such functions.

1 Like

Thanks for ur reply
Here is my code.
This is the getsubstring function am using to get substring
char* getsubstring(const char* str, size_t begin, size_t len)
{
if (str == 0 || strlen(str) == 0)
return 0;
return strndup(str + begin, len);
}

and here is, how am catching the retrun char
char* cResponse = GetResponsePrimaryElements(cRPSegBin);

/* my input will be like this cRPSegBin = 11111110000000011111111000000000111111........ */

--> when i try to compile with -g, i got this
cc: 1501-218 (W) file testmsgparse.exe contains an incorrect file suffix
ld: 0711-224 WARNING: Duplicate symbol: __start
ld: 0711-224 WARNING: Duplicate symbol: .__start
ld: 0711-224 WARNING: Duplicate symbol: __threads_init
ld: 0711-224 WARNING: Duplicate symbol: .__threads_init
ld: 0711-224 WARNING: Duplicate symbol: .main
ld: 0711-224 WARNING: Duplicate symbol: .getsubstring
ld: 0711-224 WARNING: Duplicate symbol: .GetResponseSecondaryElements
ld: 0711-224 WARNING: Duplicate symbol: .GetResponsePrimaryElements
ld: 0711-224 WARNING: Duplicate symbol: .GetSecondaryDataElements
ld: 0711-224 WARNING: Duplicate symbol: .GetPrimaryDataElements
ld: 0711-224 WARNING: Duplicate symbol: .ConvertHexToBinary
ld: 0711-224 WARNING: Duplicate symbol: .GetOriginator
ld: 0711-224 WARNING: Duplicate symbol: .GetMessageFunction
ld: 0711-224 WARNING: Duplicate symbol: .GetMessageClass
ld: 0711-224 WARNING: Duplicate symbol: .GetMTIversion
ld: 0711-345 Use the -bloadmap or -bnoquiet option to obtain more information.

What does this mean? How to interpret this?

---------- Post updated at 06:39 AM ---------- Previous update was at 06:22 AM ----------

Thanks Kumaran,
I got it by modifying my getsubstring method as

char* getsubstring(const char* str, size_t begin, size_t len)
{
if (str == 0 || strlen(str) == 0 || strlen(str) < begin || strlen(str) < (begin+len))
return 0;
return strndup(str + begin, len);
}

thanks to all