473,396 Members | 1,590 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,396 software developers and data experts.

char* and char[]

Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered. Where as if I
use char[], I can change the value as many times as I like (which I
want to).

Could someone please tell me how to properly allocate memory to a
local variable (string), so I can copy a string to this variable, and
manipulate it any way and how ever many times I wish.

Thanks in advance,
mike79
Nov 13 '05 #1
13 2570
Artie Gold wrote:
Perhaps this will help:

void some_function() {
/* the following is a pointer to a string literal */
char * cannot_be_altered = "this text cannot be altered";

/* the following is an array of `char's that cannot be altered ^^^^^^
ITYM can (but is of fixed size) */
char can_be_altered[] = "this text can be altered";

/* the following allocated enough space for a 39 character string
and places that address (if successful) in a pointer to char */
char * can_also_be_altered = malloc(40);
if (can_also_be_altered != NULL)
strcpy(can_also_be_altered, "this text can also be altered";

/* the following invokes undefined behavior */
strcpy(cannot_be_altered, "fooled ya!");

/* the following is perfectly OK */
can_be_altered[0] = 'T';

/* the following invokes undefined behavior */
strcpy(can_be_altered, "some string of arbitrary length exceeding "
"what was there before");

/* the following is perfectly OK */
can_also_be_altered[0] = 'T';

/* ... and so on ... */
}


--
Bertrand Mollinier Toublet
"Reality exists" - Richard Heathfield, 1 July 2003

Nov 13 '05 #2
Bertrand Mollinier Toublet wrote:
Artie Gold wrote:
Perhaps this will help:

void some_function() {
/* the following is a pointer to a string literal */
char * cannot_be_altered = "this text cannot be altered";

/* the following is an array of `char's that cannot be altered
^^^^^^
ITYM can


Doh!
Of course!

--ag

[Of course this _could_ lead to a long discussion on comments in code.
Hopefully it won't ;-)]
(but is of fixed size) */
char can_be_altered[] = "this text can be altered";

/* the following allocated enough space for a 39 character string
and places that address (if successful) in a pointer to char */
char * can_also_be_altered = malloc(40);
if (can_also_be_altered != NULL)
strcpy(can_also_be_altered, "this text can also be altered";

/* the following invokes undefined behavior */
strcpy(cannot_be_altered, "fooled ya!");

/* the following is perfectly OK */
can_be_altered[0] = 'T';

/* the following invokes undefined behavior */
strcpy(can_be_altered, "some string of arbitrary length exceeding "
"what was there before");

/* the following is perfectly OK */
can_also_be_altered[0] = 'T';

/* ... and so on ... */
}


--
Artie Gold -- Austin, Texas

Nov 13 '05 #3
Artie Gold <ar*******@austin.rr.com> wrote in message news:<3F**************@austin.rr.com>...
mike79 wrote:
Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered. Where as if I
use char[], I can change the value as many times as I like (which I
want to).


Ah, I see where you're confused!

Perhaps this will help:

void some_function() {
/* the following is a pointer to a string literal */
char * cannot_be_altered = "this text cannot be altered";

/* the following is an array of `char's that cannot be altered
(but is of fixed size) */
char can_be_altered[] = "this text can be altered";

/* the following allocated enough space for a 39 character string
and places that address (if successful) in a pointer to char */
char * can_also_be_altered = malloc(40);
if (can_also_be_altered != NULL)
strcpy(can_also_be_altered, "this text can also be altered";

/* the following invokes undefined behavior */
strcpy(cannot_be_altered, "fooled ya!");

/* the following is perfectly OK */
can_be_altered[0] = 'T';

/* the following invokes undefined behavior */
strcpy(can_be_altered, "some string of arbitrary length exceeding "
"what was there before");

/* the following is perfectly OK */
can_also_be_altered[0] = 'T';


how about
int main (){
char *p = "hello";
char c[5] = "hello";
c[1] = 'y';/* Not sure on this one !*/
p = c;/* Not sure on this one too !*/
return 0;
}
Isnt it that var 'c' memory is read only !
Also p=c; shouldnt be a problem right ?

- Ravi

}
Nov 13 '05 #4
mike79 wrote:

Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered.


That's for the case when the pointer is pointing to
an array specified by a string literal:
char *pointer = "string literal";

If you have
pointer = malloc("string literal");
then, if (pointer != 0), then you can read and write to,
pointer[0] through pointer[sizeof"string literal" - 1]
--
pete
Nov 13 '05 #5
Ravi Uday wrote:

Artie Gold <ar*******@austin.rr.com> wrote in message news:<3F**************@austin.rr.com>...
mike79 wrote:
Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered. Where as if I
use char[], I can change the value as many times as I like (which I
want to).
Ah, I see where you're confused!

Perhaps this will help:

void some_function() {
/* the following is a pointer to a string literal */
char * cannot_be_altered = "this text cannot be altered";

/* the following is an array of `char's that cannot be altered
(but is of fixed size) */
char can_be_altered[] = "this text can be altered";

/* the following allocated enough space for a 39 character string
and places that address (if successful) in a pointer to char */
char * can_also_be_altered = malloc(40);
if (can_also_be_altered != NULL)
strcpy(can_also_be_altered, "this text can also be altered";

/* the following invokes undefined behavior */
strcpy(cannot_be_altered, "fooled ya!");

/* the following is perfectly OK */
can_be_altered[0] = 'T';

/* the following invokes undefined behavior */
strcpy(can_be_altered, "some string of arbitrary length exceeding "
"what was there before");

/* the following is perfectly OK */
can_also_be_altered[0] = 'T';


how about
int main (){
char *p = "hello";
char c[5] = "hello";
c[1] = 'y';/* Not sure on this one !*/
p = c;/* Not sure on this one too !*/
return 0;
}
Isnt it that var 'c' memory is read only !


No.
"hello" is an initialiser list for c.
"hello" is an array for p.
Also p=c; shouldnt be a problem right ?


/* right.c */

#include <stdio.h>

int main (void)
{
char *p = "hello";
char c[] = "hello\0";

p = c;
p[0] = 'y';
p[5] = 'w';
p = "hello";
puts(p);
puts(c);
return 0;
}

--
pete
Nov 13 '05 #6

"Artie Gold" <ar*******@austin.rr.com> wrote in message news:3F**************@austin.rr.com...
mike79 wrote:
Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered. Where as if I
use char[], I can change the value as many times as I like (which I
want to).


Ah, I see where you're confused!

Perhaps this will help:


[snip]

Also pay attention to sizeof() values :

------ C code ------
#include <stdio.h>

#define SHOW_SIZEOF(x) printf ("sizeof(%s) = %u\n", #x, sizeof (x))

int main()
{
char* cannot_be_altered = "this text cannot be altered";
SHOW_SIZEOF(cannot_be_altered);

char can_be_altered[] = "this text can be altered";
SHOW_SIZEOF(can_be_altered);

char* can_also_be_altered = (char*)malloc(40);
if (can_also_be_altered != NULL)
{
strcpy(can_also_be_altered, "this text can also be altered");
}
SHOW_SIZEOF(can_also_be_altered);

return 0;
}

--------------------

------ Run results ------

sizeof(cannot_be_altered) = 4
sizeof(can_be_altered) = 25
sizeof(can_also_be_altered) = 4

-------------------------

=====================================
Alex Vinokur
mailto:al****@connect.to
http://mathforum.org/library/view/10978.html
=====================================
Nov 13 '05 #7
bd
pete wrote:
mike79 wrote:

Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered.


That's for the case when the pointer is pointing to
an array specified by a string literal:
char *pointer = "string literal";

If you have
pointer = malloc("string literal");


"string literal" is not an integer value. Do you mean malloc(strlen("string
literal") + 1)?
--
There is only one thing in the world worse than being talked about, and
that is not being talked about.
-- Oscar Wilde

Nov 13 '05 #8
bd
Ravi Uday wrote:
Artie Gold <ar*******@austin.rr.com> wrote in message
news:<3F**************@austin.rr.com>...
mike79 wrote:
> Hello all,
>
> I am a newbie to C, so please bear with me :)
>
> I need to create an array in a function (a local variable) with size
> of 1MB. Since local variables get stored on the stack, at run-time, I
> get an error.
>
> I tried using mallac() function. This function only works when I am
> allocating memory to a char* and not a char[].
>
> I wish to manipulate the string in my function, but I've heard that
> when using char*, the value is not meant to be altered. Where as if I
> use char[], I can change the value as many times as I like (which I
> want to).
Ah, I see where you're confused!

Perhaps this will help:

void some_function() {
/* the following is a pointer to a string literal */
char * cannot_be_altered = "this text cannot be altered";

/* the following is an array of `char's that cannot be altered
(but is of fixed size) */
char can_be_altered[] = "this text can be altered";

/* the following allocated enough space for a 39 character string
and places that address (if successful) in a pointer to char */
char * can_also_be_altered = malloc(40);
if (can_also_be_altered != NULL)
strcpy(can_also_be_altered, "this text can also be altered";

/* the following invokes undefined behavior */
strcpy(cannot_be_altered, "fooled ya!");

/* the following is perfectly OK */
can_be_altered[0] = 'T';

/* the following invokes undefined behavior */
strcpy(can_be_altered, "some string of arbitrary length exceeding "
"what was there before");

/* the following is perfectly OK */
can_also_be_altered[0] = 'T';


how about
int main (){
char *p = "hello";
char c[5] = "hello";


Not sure - should this be [6], or will it be truncated?
c[1] = 'y';/* Not sure on this one !*/
Ok.
p = c;/* Not sure on this one too !*/
Also ok.
return 0;
}
Isnt it that var 'c' memory is read only !
No. The meaning of a string literal changes in an array initializer:
char *p = "hello"; /* p points to read-only memory of static duration */
/* The data pointer to by p remains valid once you return */
char c[6] = "hello";
/* c is a writable array of 6 chars with automatic storage duration. */
/* c (and any pointers to any elements of c) is invalid once you return from
the function */
Also p=c; shouldnt be a problem right ?


Nope. p itself is writable, but the data pointed to is not. Since you're
only changing p, it's ok.

--
Professor: Doomsday device? Ah, now the ball's in Farnsworth's
court. I suppose I could part with one and still be feared.

Nov 13 '05 #9
bd <bd*****@users.sf.net> writes:
"string literal" is not an integer value. Do you mean malloc(strlen("string
literal") + 1)?


Or malloc(sizeof "string literal"), perhaps?
--
"To get the best out of this book, I strongly recommend that you read it."
--Richard Heathfield
Nov 13 '05 #10
Mike Wahler wrote:

pete <pf*****@mindspring.com> wrote in message
news:3F***********@mindspring.com...
mike79 wrote:
I wish to manipulate the string in my function,
but I've heard that
when using char*, the value is not meant to be altered.


That's for the case when the pointer is pointing to
an array specified by a string literal:
char *pointer = "string literal";

If you have
pointer = malloc("string literal");


pointer = malloc(sizeof("string literal"));


That's it. Thank you.
then, if (pointer != 0), then you can read and write to,
pointer[0] through pointer[sizeof"string literal" - 1]


--
pete
Nov 13 '05 #11
bd wrote:

Ravi Uday wrote:

how about
int main (){
char *p = "hello";
char c[5] = "hello";


Not sure - should this be [6], or will it be truncated?


It will be truncated,
but the program as written, doesn't require a string.
c[1] = 'y';/* Not sure on this one !*/


Ok.
p = c;/* Not sure on this one too !*/


Also ok.
return 0;
}


--
pete
Nov 13 '05 #12
[snip]

how about
int main (){
char *p = "hello";
char c[] = "hello";
c[1] = 'y';/* Not sure on this one !*/
p = c;/* Not sure on this one too !*/
return 0;
}
Isnt it that var 'c' memory is read only !
No.
"hello" is an initialiser list for c.

"hello" is an array for p.
Also p=c; shouldnt be a problem right ?
/* right.c */

#include <stdio.h>

int main (void)
{
char *p = "hello";
char c[] = "hello\0";

But if i do
puts (c);
strcpy(c,"HELLO");
puts(c);
Nothing seems to happen !
So what is the point if we initialize 'c' with some useful data and
not able to access it !
p = c;
p[0] = 'y';
p[5] = 'w';
p = "hello";
puts(p);
puts(c);
return 0;
}

Nov 13 '05 #13
mi****@iprimus.com.au (mike79) wrote in message news:<49************************@posting.google.co m>...
Hello all,

I am a newbie to C, so please bear with me :)

I need to create an array in a function (a local variable) with size
of 1MB. Since local variables get stored on the stack, at run-time, I
get an error.

I tried using mallac() function. This function only works when I am
allocating memory to a char* and not a char[].

I wish to manipulate the string in my function, but I've heard that
when using char*, the value is not meant to be altered. Where as if I
use char[], I can change the value as many times as I like (which I
want to).

Could someone please tell me how to properly allocate memory to a
local variable (string), so I can copy a string to this variable, and
manipulate it any way and how ever many times I wish.

Thanks in advance,
mike79


Use the following code as an example:

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

int main (void)
{
char *a = "Hello";
char b[] = "Hello";
char c[8] = "Hello";
char d[8];
char *e;

strcpy (d, "Goodbye");
e = malloc (1024);
if (e)
{
strcpy (e, a);
strcat (e, d)
}

a = d;
}

Here's a hypothetical memory map to illustrate the concepts below. It
assumes that all instances of the string literal "Hello" map to the
same address; that may not be universally true, but we'll assume it
for this model. This is not meant to correspond to any real memory
model, just to demonstrate what's going on in the code:

Item Address 00 01 02 03 04 05 06 07
---- -------
"Hello" 0x00000100 'H' 'e' 'l' 'l' 'o' 0 .. ..
...
a 0x00400000 00 00 01 00 .. .. .. ..
b 0x00400008 'H' 'e' 'l' 'l' 'o' 0 .. ..
c 0x00400010 'H' 'e' 'l' 'l' 'o' 0 .. ..
d 0x00400018 .. .. .. .. .. .. .. ..
e 0x00400020 .. .. .. .. .. .. .. ..

This is what memory looks like right before the first strcpy().

The string literal "Hello" is stored as an array of 6 characters with
contents {'H', 'e', 'l', 'l', 'o', 0} with static extent, meaning the
memory for it is allocated at program startup, and is not released
until the program terminates. This memory may or may not be writable;
assume that it is not writeable.

The variable a is a pointer to char with auto extent, and it is
initialized with the address of the string literal "Hello" (a ==
0x00000100). Assume for this example that the address of a is
0x00400000. The *variable* a is writeable; you can always assign
another pointer value to it, such as a = d (a will contain the base
address of the d array, or 0x00400018), or a = "Goodbye". However,
what a initially *points to* (address 0x00000100) may not be writable,
so operations like strcpy (a, "Goodbye"); and a[0] = 'J'; may result
in undefined behavior.

The variable b is an array of char with auto extent, implicitly sized
to hold the string literal that is being used to initialize it (sizeof
b == 6), and initialized with the *contents* of the string literal.
The contents of b are writeable, so operations like strcpy (b, "Joe")
and b[0] = 'J'; will succeed. The *variable* b is not writeable; you
may not assign another address to it, so operations like b = a or b =
c are disallowed.

The variable c is an array of char with auto extent, explicitly sized
to hold 8 characters, and initialized with the contents of the string
literal. Behavior is the same as b.

The variable d is an array of char with auto extent, explicitly sized
to hold 8 characters. It has not been initialized, and must be
assumed to contain garbage. Behavior is the same as b and c. After
the call to strcpy, the contents of d are {'H', 'e', 'l', 'l', 'o', 0,
..., .., .., ..}, where '..' represent a random byte value.

The variable e is a pointer to char with auto extent. It has not been
initialized, and since it is auto, it may or may not be initialized to
NULL (assume it initially contains garbage). If the call to malloc()
succeeds, e will contain the address of a chunk of dynamically
allocated memory 1024 bytes long (assume address 0x08000000). This
memory will be writable, so operations like strcpy (e, "Hello"); and
e[0] = 'J'; will succeed. Like a, the *variable* e is writable, so
operations like e = b are permitted.

b, c, d, and e may be copied to as much as you want, as long as you
don't attempt to copy anything larger than what they're sized to hold.
Executing strcpy (b, "Goodbye"); may cause undefined behavior, since
the string being copied is longer than what b is sized to hold.

Here's what the memory looks when the program is about to exit:

Item Address 00 01 02 03 04 05 06 07
---- -------
"Hello" 0x00000100 'H' 'e' 'l' 'l' 'o' 0 .. ..
...
a 0x00400000 00 40 00 18 .. .. .. ..
b 0x00400008 'H' 'e' 'l' 'l' 'o' 0 .. ..
c 0x00400010 'H' 'e' 'l' 'l' 'o' 0 .. ..
d 0x00400018 'G' 'o' 'o' 'd' 'b' 'y' 'e' 0
e 0x00400020 08 00 00 00 .. .. .. ..
...
0x08000000 'H' 'e' 'l' 'l' 'o' 'G' 'o' 'o'
0x08000008 'd' 'b' 'y' 'e' 0 .. .. ..
...
0x08000400

Hope that helps.
Nov 13 '05 #14

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

9
by: Christopher Benson-Manica | last post by:
I need a smart char * class, that acts like a char * in all cases, but lets you do some std::string-type stuff with it. (Please don't say to use std::string - it's not an option...). This is my...
5
by: Alex Vinokur | last post by:
"Richard Bos" <rlb@hoekstra-uitgeverij.nl> wrote in message news:4180f756.197032434@news.individual.net... to news:comp.lang.c > ben19777@hotmail.com (Ben) wrote: > > 2) Structure casted into an...
5
by: Sona | last post by:
I understand the problem I'm having but am not sure how to fix it. My code passes two char* to a function which reads in some strings from a file and copies the contents into the two char*s. Now...
2
by: Peter Nilsson | last post by:
In a post regarding toupper(), Richard Heathfield once asked me to think about what the conversion of a char to unsigned char would mean, and whether it was sensible to actually do so. And pete has...
5
by: jab3 | last post by:
(again :)) Hello everyone. I'll ask this even at risk of being accused of not researching adequately. My question (before longer reasoning) is: How does declaring (or defining, whatever) a...
12
by: GRoll35 | last post by:
I get 4 of those errors. in the same spot. I'll show my parent class, child class, and my driver. All that is suppose to happen is the user enters data and it uses parent/child class to display...
18
by: Pedro Pinto | last post by:
Hi there once more........ Instead of showing all the code my problem is simple. I've tried to create this function: char temp(char *string){ alterString(string); return string;
4
by: Paul Brettschneider | last post by:
Hello all, consider the following code: typedef char T; class test { T *data; public: void f(T, T, T); void f2(T, T, T);
16
by: s0suk3 | last post by:
This code #include <stdio.h> int main(void) { int hello = {'h', 'e', 'l', 'l', 'o'}; char *p = (void *) hello; for (size_t i = 0; i < sizeof(hello); ++i) {
29
by: Kenzogio | last post by:
Hi, I have a struct "allmsg" and him member : unsigned char card_number; //16 allmsg.card_number
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.