By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
434,637 Members | 1,945 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 434,637 IT Pros & Developers. It's quick & easy.

why this does n't works

P: n/a
Hi all,

why

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int main(void)
{
char *t[5]; /*= {"BASIC"};*/

strcpy(t[0],"BASIC");
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
/* i am getting segmentation violation in lcc compiler*/

is not working whereas

int main(void)
{
char *t[5] = {"BASIC"};

/*strcpy(t[0],"BASIC");*/
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
is working ?

Does this mean that while using strcpy the char pointer should
always be initialized ...?????
Jun 27 '08 #1
Share this Question
Share on Google+
8 Replies


P: n/a
aa*****@gmail.com said:
Hi all,

why

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int main(void)
{
char *t[5]; /*= {"BASIC"};*/
This defines, and reserves storage for, an array of five char *, but
doesn't point them anywhere and doesn't reserve any storage for them to
point at.
strcpy(t[0],"BASIC");
t[0] exists, but doesn't point anywhere special, so you're trashing memory
you don't own.
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
/* i am getting segmentation violation in lcc compiler*/
Deep shock.
>
is not working whereas

int main(void)
{
char *t[5] = {"BASIC"};

/*strcpy(t[0],"BASIC");*/
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
is working ?
No, it just isn't breaking in the way you were hoping it to break.
Undefined behaviour *doesn't* necessarily mean "it will crash".

Does this mean that while using strcpy the char pointer should
always be initialized ...?????
Gee, ya think?

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
Jun 27 '08 #2

P: n/a
i guess the problem arises because you have not allocated any memory
for the string. Probably you can try this because it seems to work for
me:

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

int main(void)
{
char *t[5]; /*= {"BASIC"};*/
int i;
i = strlen("BASIC");
t[0] = malloc(i * sizeof(char));
strcpy(t[0],"BASIC");
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
Jun 27 '08 #3

P: n/a
pereges said:
i guess the problem arises because you have not allocated any memory
for the string. Probably you can try this because it seems to work for
me:
Doesn't make it right.
>
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
Is your space bar broken?
int main(void)
{
char *t[5]; /*= {"BASIC"};*/
int i;
i = strlen("BASIC");
i is 5
t[0] = malloc(i * sizeof(char));
5 * sizeof(char) is 5 (by definition)
strcpy(t[0],"BASIC");
this call attempts to copy SIX bytes, but you only reserved five (assuming
the malloc worked, which you didn't check) - so you've written into memory
you don't own, and the behaviour of your program is now undefined.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
Jun 27 '08 #4

P: n/a
On Apr 16, 11:16 pm, Richard Heathfield <r...@see.sig.invalidwrote:
pereges said:
i guess the problem arises because you have not allocated any memory
for the string. Probably you can try this because it seems to work for
me:

Doesn't make it right.
#include<stdio.h>
#include<stdlib.h>
#include<string.h>

Is your space bar broken?
int main(void)
{
char *t[5]; /*= {"BASIC"};*/
int i;
i = strlen("BASIC");

i is 5
t[0] = malloc(i * sizeof(char));

5 * sizeof(char) is 5 (by definition)
strcpy(t[0],"BASIC");

this call attempts to copy SIX bytes, but you only reserved five (assuming
the malloc worked, which you didn't check) - so you've written into memory
you don't own, and the behaviour of your program is now undefined.
Yes, I think I forgot about the null character.
Jun 27 '08 #5

P: n/a

pereges <Br*****@gmail.comwrites:
i guess the problem arises because you have not allocated any memory
for the string. Probably you can try this because it seems to work for
me:
Seems to. You are lucky. I have listed some issues below. Hope it helps.
>
#include<stdio.h>
#include<stdlib.h>
#include<string.h>

int main(void)
{
char *t[5]; /*= {"BASIC"};*/
int i;
i = strlen("BASIC");
t[0] = malloc(i * sizeof(char));
strcpy(t[0],"BASIC");
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
Your code has errors. I thought Id try the output of "splint" to make
the diagnosis a little more consistent.

Since I didn't see the previous post I wonder why you are creating an
array of 5 character pointers? or did you think the 5 was the length of
BASIC? It's not clear in the absence of any comment what you really
intend.

From splint(*) :

test2.c:9:3: Assignment of size_t to int: i = strlen("BASIC")

In other words strlen returns a size_t and not an int. Personally when I
write C I tend to still use "int" where I KNOW the string is short
enough. But its not "correct". Use a size_t.

Also you only malloc enough for the "BASIC" part and not for the
trailing zero to indicate "end of string". Look up "strings" in C. Read
the manual for strlen and strcpy. This is one of the most basic but
important things to know in C.

More from splint:

test2.c:10:34: Parameter to sizeof is type char: sizeof(char)
Operand of sizeof operator is a type. (Safer to use expression, int *x =
sizeof (*x); instead of sizeof (int).) (Use -sizeoftype to inhibit warning)

Personally, for me, this line would just be

t[0] = malloc(strlen("BASIC")+1);

But even then we have a problem that something like splint can tell us
no matter how much we think we know best:

strcpy (t[0], ...)
A possibly null pointer is passed as a parameter corresponding to a formal
parameter with no /*@null@*/ annotation. If NULL may be used for this
parameter, add a /*@null@*/ annotation to the function parameter declaration.

Why is this? It's because you did not check for malloc returning NULL,
but that is another story and down to good programming practices.

So following that hint we can do:

char *p = malloc(strlen("BASIC")+1);
if(p==NULL)
return EXIT_FAILURE;
t[0]=p;
strcpy(t[0],"BASIC");
(*)(Splint is a tool for statically checking C programs for
security vulnerabilities and coding mistakes. With minimal effort,
Splint can be used as a better lint. If additional effort is invested
adding annotations to programs, Splint can perform stronger checking
than can be done by any standard lint. See http://www.splint.org/ ).

Jun 27 '08 #6

P: n/a
Richard Heathfield wrote:
>
aa*****@gmail.com said:
[... snip first version which SEGV's ...]

int main(void)
{
char *t[5] = {"BASIC"};

/*strcpy(t[0],"BASIC");*/
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
is working ?

No, it just isn't breaking in the way you were hoping it to break.
Undefined behaviour *doesn't* necessarily mean "it will crash".
Isn't this second version perfectly well-defined? Doesn't the line:

char *t[5] = {"BASIC"};

mean:

t is an array of 5 character pointers, the first one points
to the literal "BASIC", and the rest are NULL

and so the reference to t[0] means the string "BASIC"?
Does this mean that while using strcpy the char pointer should
always be initialized ...?????

Gee, ya think?

--
+-------------------------+--------------------+-----------------------+
| Kenneth J. Brody | www.hvcomputer.com | #include |
| kenbrody/at\spamcop.net | www.fptech.com | <std_disclaimer.h|
+-------------------------+--------------------+-----------------------+
Don't e-mail me at: <mailto:Th*************@gmail.com>

Jun 27 '08 #7

P: n/a
On Wed, 16 Apr 2008 16:44:54 -0400, Kenneth Brody
<ke******@spamcop.netwrote:
>Richard Heathfield wrote:
>>
aa*****@gmail.com said:
[... snip first version which SEGV's ...]
>
int main(void)
{
char *t[5] = {"BASIC"};

/*strcpy(t[0],"BASIC");*/
printf("....%s",t[0]);

return EXIT_SUCCESS;
}
is working ?

No, it just isn't breaking in the way you were hoping it to break.
Undefined behaviour *doesn't* necessarily mean "it will crash".

Isn't this second version perfectly well-defined? Doesn't the line:

char *t[5] = {"BASIC"};

mean:

t is an array of 5 character pointers, the first one points
to the literal "BASIC", and the rest are NULL
Yes
>
and so the reference to t[0] means the string "BASIC"?
Yes but it might be better phrased as'"the string literal "BASIC"'.

It is only well defined as long as there is no attempt to update the
characters pointed to by t[0]. Any attempt to do so (as implied by
the commented call to strcpy) invokes undefined behavior.
Remove del for email
Jun 27 '08 #8

P: n/a
Kenneth Brody said:
Richard Heathfield wrote:
>>
<snip>
>Undefined behaviour *doesn't* necessarily mean "it will crash".

Isn't this second version perfectly well-defined?
Yes, it is, and I owe the OP an apology. I misread the code.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
Jun 27 '08 #9

This discussion thread is closed

Replies have been disabled for this discussion.