
September 28th, 2006, 10:45 AM
| | | segfault strlen
Hello!!
I'm studying c++ and I'm trying to get a little piece of code working,
but I'm getting a segfault with strlen here:
void tabhash::set (url *U) {
uint hash = U->hashCode();
char* url = U->giveUrl();
char* chash = (char*)hash;
char* Insert1="INSERT INTO sep_hashtable VALUES (";
char* Insert2=",0,'";
char* Insert3="');";
char* Insert=new
char[strlen(Insert1)+strlen(chash)+strlen(Insert2)+strl en(url)+strlen(Insert3)];
strcpy( Insert, Insert1);
strcat( Insert, chash);
strcat( Insert, Insert2);
strcat( Insert, url);
strcat( Insert, Insert3);
if (mysql_query(&mysql,Insert)) {
cerr << "Cannot insert into sep_hashtable : "
<< strerror(errno) << endl;
exit(1);
}
}
I can't find out why I'm getting this segfault error...can you help me
a bit? | 
September 28th, 2006, 11:05 AM
| | | Re: segfault strlen danielesalatti@gmail.com wrote: Quote:
Hello!!
I'm studying c++ and I'm trying to get a little piece of code working,
but I'm getting a segfault with strlen here:
>
void tabhash::set (url *U) {
uint hash = U->hashCode();
char* url = U->giveUrl();
char* chash = (char*)hash;
| Why are you casting an unsigned int to a char*? A cast is not a
lexical conversion, which you have probably intended. But then I do not
know how to interpret the return value of url::hashCode. But I doubt it
is meant to be casted to a char*.
hth
--
jb
(reply address in rot13, unscramble first) | 
September 28th, 2006, 12:35 PM
| | | Re: segfault strlen
Dnia 28 Sep 2006 02:58:51 -0700, danielesalatti@gmail.com napisał(a): Quote: |
I'm studying c++ and I'm trying to get a little piece of code working,
| Are you sure it's c++? This code doesn't show it.
Use i.e. std::string or std::stringstream if you are about to write good
c++ code. Quote:
char* Insert1="INSERT INTO sep_hashtable VALUES (";
char* Insert2=",0,'";
char* Insert3="');";
| WTF? Don't do that. That's why you have segfault.
If you still want to use C style strings try:
char Insert1[] = {"abcd"};
or allocate some memory before writing to the pointer:
char *Insert1 = new char[BUFFER_SIZE];
strcpy(Insert1, "abcd"); // BE CAREFUL - DO NOT PUT longer string than the
buffer size
--
SirMike - http://www.sirmike.org
C makes it easy to shoot yourself in the foot; C++ makes it harder, but
when you do, it blows away your whole leg. - Bjarne Stroustrup | 
September 28th, 2006, 12:45 PM
| | | Re: segfault strlen danielesalatti@gmail.com wrote: Quote:
Hello!!
I'm studying c++ and I'm trying to get a little piece of code working,
but I'm getting a segfault with strlen here:
>
void tabhash::set (url *U) {
uint hash = U->hashCode();
char* url = U->giveUrl();
char* chash = (char*)hash;
>
char* Insert1="INSERT INTO sep_hashtable VALUES (";
char* Insert2=",0,'";
char* Insert3="');";
>
char* Insert=new
char[strlen(Insert1)+strlen(chash)+strlen(Insert2)+strl en(url)+strlen(Insert3)];
| Shouldn't this buffer be bigger to allow for the terminating '\0'? Quote:
strcpy( Insert, Insert1);
strcat( Insert, chash);
strcat( Insert, Insert2);
strcat( Insert, url);
strcat( Insert, Insert3);
if (mysql_query(&mysql,Insert)) {
cerr << "Cannot insert into sep_hashtable : "
<< strerror(errno) << endl;
exit(1);
}
}
>
I can't find out why I'm getting this segfault error...can you help me
a bit?
| Anyway, that's what dealing with C-style strings usually brings
about -- a lot of strcpy()'s, strcat()'s and buffer overruns.
Consider using std::strings, they are way safer and can be
concatenated like
string Insert = Insert1 + Insert2 + Insert3;
while automatically growing to accommodate their contents.
HTH,
- J. | 
September 28th, 2006, 12:45 PM
| | | Re: segfault strlen
SirMike wrote: Quote:
Dnia 28 Sep 2006 02:58:51 -0700, danielesalatti@gmail.com napisał(a): Quote: |
>>I'm studying c++ and I'm trying to get a little piece of code working,
|
Are you sure it's c++? This code doesn't show it.
Use i.e. std::string or std::stringstream if you are about to write good
c++ code.
| This I agree with. Quote: Quote:
>> char* Insert1="INSERT INTO sep_hashtable VALUES (";
>> char* Insert2=",0,'";
>> char* Insert3="');";
|
WTF? Don't do that. That's why you have segfault.
| But not because of this? These are well formed
C-style string literals. They are fine in themselves,
except that they cannot be written to, right? Quote:
If you still want to use C style strings try:
char Insert1[] = {"abcd"};
or allocate some memory before writing to the pointer:
char *Insert1 = new char[BUFFER_SIZE];
strcpy(Insert1, "abcd"); // BE CAREFUL - DO NOT PUT longer string than the
buffer size
| ... or rather "longer string than buffer size minus one".
- J. | 
September 28th, 2006, 12:55 PM
| | | Re: segfault strlen
Jacek Dziedzic wrote: Quote: Quote: Quote: |
>> char* Insert1="INSERT INTO sep_hashtable VALUES (";
| >>
>WTF? Don't do that. That's why you have segfault.
| >
But not because of this? These are well formed
C-style string literals. They are fine in themselves,
except that they cannot be written to, right?
| They should be declared const, then the compiler will be able to help
you. The standard still allows non-const for reasons of C compatibility,
but this is deprecated. | 
September 28th, 2006, 12:55 PM
| | | Re: segfault strlen
Dnia Thu, 28 Sep 2006 13:57:14 +0200, Jacek Dziedzic napisał(a): Quote:
But not because of this? These are well formed
C-style string literals. They are fine in themselves,
except that they cannot be written to, right?
| You're right. I only tried to emphasize that the whole code was wrong ;) Quote: |
... or rather "longer string than buffer size minus one".
| Exactly.
--
SirMike - http://www.sirmike.org
C makes it easy to shoot yourself in the foot; C++ makes it harder, but
when you do, it blows away your whole leg. - Bjarne Stroustrup | 
September 28th, 2006, 02:45 PM
| | | Re: segfault strlen danielesalatti@gmail.com wrote: Quote:
Hello!!
I'm studying c++ and I'm trying to get a little piece of code working,
but I'm getting a segfault with strlen here:
| Your first problem is that you're not really using C++. You're just
using C++ as a better C. In C++ a much better way would be something
like the following:
#include <sstream>
....
std::stringstream stream;
stream
<< "INSERT INTO seb_hashtable VALUES ("
<< hashcode
<< ",0,'"
<< url
<< "');"
<< std::flush;
my_database.execute(stream.str());
See how easy? No need to manipulate char arrays and getting segfaults
for weird reasons.
You also have another potential problem too, but it's off-topic. Google
"SQL injection" for more info.
Regards,
Bart. | 
September 28th, 2006, 04:15 PM
| | | Re: segfault strlen danielesalatti@gmail.com wrote: Quote:
>
char* Insert=new
char[strlen(Insert1)+strlen(chash)+strlen(Insert2)+strl en(url)+strlen(Insert3)];
strcpy( Insert, Insert1);
strcat( Insert, chash);
strcat( Insert, Insert2);
strcat( Insert, url);
strcat( Insert, Insert3);
>
I can't find out why I'm getting this segfault error...can you help me
a bit?
| You are only allocating enough memory in Insert for the characters
you're putting in there, you need to add one more for the null
terminator, ie:
char* Insert = new char[strlen(Insert1)+...+strlen(Insert3) /** NB**/ +
1];
But anyway, all those strcats are a very brain-damaged way of achieving
what you want. There are better ways of achieving this in C, but in C++
you should be using std::string and std::stringstream. Look:
void tabhash::set (url *U) {
std::ostringstream os;
os << "INSERT INTO sep_hashtable VALUES ("
<< U->hashCode()
<< ",0,"
<< U->giveUrl()
<< ");"
;
if (mysql_query(&mysql, os.str().c_str())) {
cerr << "Cannot insert into sep_hashtable : "
<< strerror(errno) << endl;
exit(1);
}
}
It's quite a bit cleaner, no ? | 
September 29th, 2006, 03:55 AM
| | | Re: segfault strlen danielesalatti@gmail.com wrote: Quote:
char* Insert=new
char[strlen(Insert1)+strlen(chash)+strlen(Insert2)+strl en(url)+strlen(Insert3)];
| Remember that in C and C++ a string is zero-terminated, so you must make
your stringbuffer large enough:
char* Insert = new char[LengthOffAllStrings + 1];
That "+ 1" is important..
Best regards, Martin | 
September 29th, 2006, 12:05 PM
| | | Re: segfault strlen
Martin Steen wrote: Quote: danielesalatti@gmail.com wrote: Quote:
> char* Insert=new
>char[strlen(Insert1)+strlen(chash)+strlen(Insert2)+strl en(url)+strlen(Insert3)];
>>
| >
Remember that in C and C++ a string is zero-terminated, so you must make
your stringbuffer large enough:
| A C++ string is NOT necessarily null terminated.
It may contain nulls or not at any position.
It's only the use of char* as a defacto C-string that is so encumbered. |
Posting Rules
| You may not post new threads You may not post replies You may not post attachments You may not edit your posts HTML code is Off | | | | | | What is Bytes?
We are a network of experts and professionals in IT and software development that help one another with answers to tough questions and share insights.
Get the best answers to your questions from over network members.
|