tags:

views:

213

answers:

4

In my class we are writing our own copy of C's malloc() function. To test my code (which can currently allocate space fine) I was using:

char* ptr = my_malloc(6*sizeof(char));
memcpy(ptr, "Hello\n", 6*sizeof(char));
printf("%s", ptr);

The output would typically be this:

Hello
Unprintable character

Some debugging figured that my code wasn't causing this per say, as ptr's memory is as follows:

[24 bytes of meta info][Number of requested bytes][Padding]

So I figured that printf was reaching into the padding, which is just garbage. So I ran a test of: printf("%s", "test\nd"); and got:

test
d

Which makes me wonder, when DOES printf("%s", char*) stop printing chars?

+14  A: 

It stops printing when it reaches a null character (\0), because %s expects the string to be null terminated (i.e., it expects the argument to be a C string).

The string literal "test\nd" is null terminated (all string literals are null terminated). Your character array ptr is not, however, because you only copy six characters into the buffer (Hello\n), and you do not copy the seventh character--the null terminator.

James McNellis
+2  A: 

C strings are null terminated (there's a \0 character at the end), that's how C knows when to stop printing or dealing with the buffer as a string . It is your responsibility to never put a string in a longer space than what you have allocated.

Note that Hello\n is not a six character string, it is actually a seven character string. You use five for the Hello, one for the newline, and one for the null terminator.

Trying to fit 7 characters into a six character buffer is considered a bug, I am not sure if it is responsible for the problems you are currently having, but it seems like the copying of 6 characters would not copy the null terminator. So I would actually expect your print to go beyond the Hello and into some actual junk.

Uri
Dur, I should be using \0 to terminate strings? Dur Dur Dur
You don't have to add \0 yourself. When you create a literal string or get one as input, C adds it for you. You don't actually see the \0. That "Hello\n" string is seven characters if you looked at the actual assembly code.
Uri
A: 

when it reaches a zero. you need 7 chars.

Sanjay Manohar
+2  A: 

James is correct about printf stopping when it gets to the null character, and Uri is correct that you need to allocate a 7-character buffer to hold "hello\n".

Some of the confusion with terminators would be mitigated if you used the usual C idiom for copying a string: strcpy(ptr, "Hello\n"), rather than memcpy.

Also, by definition, sizeof(char) == 1 in C, so 6*sizeof(char) is redundant

David Gelhar