LinuxQuestions.org
Latest LQ Deal: Latest LQ Deals
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 03-14-2006, 08:28 PM   #1
mfrick
Member
 
Registered: Sep 2004
Location: Perth
Posts: 51

Rep: Reputation: 15
strcat is causing seg fault (c program)


Hi peoples,
I have a bit of code that compiles perfectly but when I run it I get a segmentation fault (core dumped) which is not fun. I have broken up my code (I had some nested functions etc) and found that the error is being generated at the below line of code.

Code:
temp = strcat("evusrseq=\"",temp1);
*not the most descriptive variable names but only used to break up the code to find the line that breaks. temp & temp1 are both strings.

** this code is being compiled by gcc v 2.95.3 on SunOS 5.9 if that makes any difference.

Basically this bit of c code looks fine to me as I have used strcat in other places with no problem so if anyone can see any reason that this would seg fault I would appreciate knowing why also

(I am hoping it is something obvious that I am just missing that when found makes me look like an idiot)
 
Old 03-14-2006, 09:20 PM   #2
jschiwal
LQ Guru
 
Registered: Aug 2001
Location: Fargo, ND
Distribution: SuSE AMD64
Posts: 15,733

Rep: Reputation: 682Reputation: 682Reputation: 682Reputation: 682Reputation: 682Reputation: 682
The destination should be a pointer to a character string instead of a pointer to a constant. You also need to make sure that you don't end up with a string larger then the memory you allocated. That could cause a runtime error which is harder to find.
 
Old 03-14-2006, 10:00 PM   #3
paulsm4
LQ Guru
 
Registered: Mar 2004
Distribution: SusE 8.2
Posts: 5,863
Blog Entries: 1

Rep: Reputation: Disabled
jschiwal is absolutely correct: you should *never* try to modify a string literal:
Code:
  // WRONG
  char *temp1 = "something";
  strcat("evusrseq=\"",temp1);

  // BETTER
  char *temp1 = "evusrseq=\"                 ";
  char *temp2 = "something";
  char temp1[10] = 0;
  strcat(temp1,temp2);

  // BEST
  char temp1[MAX_STRING];
  strncpy (temp1, "evusrseq=\"", MAX_STRING);
  strncat (temp1, "something", MAX_STRING);

Last edited by paulsm4; 03-14-2006 at 10:04 PM.
 
Old 03-14-2006, 10:27 PM   #4
mfrick
Member
 
Registered: Sep 2004
Location: Perth
Posts: 51

Original Poster
Rep: Reputation: 15
Thanks guys you were 100% correct

I think I was thrown by the fact that I wasn't recieving any errors on a windows implementation that was using similar code.

It has been quite a few years so I guess my c rust has built up more than I had hoped.

Once again thanks for your help.
 
Old 08-12-2014, 09:20 AM   #5
Gamecock
LQ Newbie
 
Registered: Aug 2014
Distribution: git/gitHUb
Posts: 2

Rep: Reputation: Disabled
correct use of strncat

@paulsm4 your implementation for strncat would overflow. The n is number of char to copy, not number of char in destination total. See http://www.cplusplus.com/reference/cstring/strncat/

The safest representation is:
// BEST
char temp1[MAX_STRING];
strncpy (temp1, "evusrseq=\"", MAX_STRING);
strncat (temp1, "something", sizeof(temp1)-strlen(temp1));
 
Old 08-12-2014, 10:39 AM   #6
NevemTeve
Senior Member
 
Registered: Oct 2011
Location: Budapest
Distribution: Debian/GNU/Linux, AIX
Posts: 4,862
Blog Entries: 1

Rep: Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869
That's what snprintf is good for...
 
Old 08-13-2014, 05:22 PM   #7
mina86
Member
 
Registered: Aug 2008
Distribution: Debian
Posts: 517

Rep: Reputation: 229Reputation: 229Reputation: 229
Quote:
Originally Posted by paulsm4 View Post
Code:
// BEST
  char temp1[MAX_STRING];
  strncpy (temp1, "evusrseq=\"", MAX_STRING);
  strncat (temp1, "something", MAX_STRING);
No, it is not! It will fail if MAX_STRING == strlen("evusrseq=\""). Also, strncat's third argument is not the length of the buffer, but maximum amount of characters to read from the source. I.e. strncat is totally broken.

Choose one of:
Code:
char temp[…];
temp[0] = 0;
strncat(temp, "foo", sizeof temp - 1);
strncat(temp, "bar", sizeof temp - 1 - len(temp));
Code:
char temp[…];
strncpy(temp, "foo", sizeof temp);
temp[sizeof temp - 1] = 0;
strncat(temp, "bar", sizeof temp - 1 - len(temp));
Code:
char temp[…];
snprintf(temp, sizeof temp, "%s%s", "foo", "bar");
Of course, if some of the strings are actual literals, snprintf with proper format is most readable, eg.:
Code:
char temp[…];
snprintf(temp, sizeof temp, "foo%s", "bar");
Quote:
Originally Posted by Gamecock View Post
@paulsm4 your implementation for strncat would overflow. The n is number of char to copy, not number of char in destination total. See http://www.cplusplus.com/reference/cstring/strncat/

The safest representation is:
// BEST
char temp1[MAX_STRING];
strncpy (temp1, "evusrseq=\"", MAX_STRING);
strncat (temp1, "something", sizeof(temp1)-strlen(temp1));
Still not safe. You need to subtract 1 for the NUL byte.

Last edited by mina86; 08-14-2014 at 09:09 AM. Reason: Added some more on strncat
 
Old 08-15-2014, 07:21 PM   #8
zer0python
Member
 
Registered: Sep 2003
Posts: 104

Rep: Reputation: 20
Just to note, doing

Quote:
char temp1[MAX_STRING];
is using memory on the local stack. Which can cause issues if the code is being executed in a thread.
my two cents:

Code:
char *temp1 = malloc(MAX_STRING+1);
if(temp1 == NULL) {
  /* bail */
}

sprintf(temp1, "evusrseq=\"%s\", temp2);
/* where strlen(temp2) will never be > MAX_STRING-strlen("evusrseq=\"\""); */
/* ... use temp1 ... */
free(temp1);
temp1 = NULL; /* pedantic */
Edit: This *is* lazy coding, I'm aware using malloc(strlen(temp2) + ... + 1) would be ideal for memory constraints.

Last edited by zer0python; 08-15-2014 at 07:24 PM.
 
Old 08-16-2014, 07:09 AM   #9
NevemTeve
Senior Member
 
Registered: Oct 2011
Location: Budapest
Distribution: Debian/GNU/Linux, AIX
Posts: 4,862
Blog Entries: 1

Rep: Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869Reputation: 1869
What about asnprintf?
 
Old 08-20-2014, 07:34 AM   #10
mina86
Member
 
Registered: Aug 2008
Distribution: Debian
Posts: 517

Rep: Reputation: 229Reputation: 229Reputation: 229
Quote:
Originally Posted by NevemTeve View Post
What about asnprintf?
One must remember it's non-standard (even though easy to implement with snprintf if efficiency is not a concern).
 
  


Reply



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
weird seg fault zaichik Programming 7 01-29-2005 06:34 AM
Segmentation fault on strcat() Ephracis Programming 8 12-17-2004 01:28 AM
RH 7.2 crash...getting seg fault when using ls sakima Red Hat 1 10-11-2004 09:14 AM
C seg fault drigz Programming 5 10-01-2004 03:35 PM
strcat and direntp->d_name segmentation fault [I'm guessing the problem, plz propose] zeppelin Programming 3 04-12-2004 02:52 PM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 03:01 AM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration