473,708 Members | 2,355 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

Accessing void * buffer/array through char * pointer

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) {
printf("byte %2zu: <%c>", i, p[i]);
if (!p[i])
printf(" (null char)");
printf("\n");
}

return 0;
}

produces this output

byte 0: <h>
byte 1: <(null char)
byte 2: <(null char)
byte 3: <(null char)
byte 4: <e>
byte 5: <(null char)
byte 6: <(null char)
byte 7: <(null char)
byte 8: <l>
byte 9: <(null char)
byte 10: <(null char)
byte 11: <(null char)
byte 12: <l>
byte 13: <(null char)
byte 14: <(null char)
byte 15: <(null char)
byte 16: <o>
byte 17: <(null char)
byte 18: <(null char)
byte 19: <(null char)

I'm confused about the int *-to-void *-to char * conversion. The
output shows that ints are four bytes on my machine, and the values in
the initializer 'h', 'e', 'l', 'l', 'o' have the values 104, 101, 108,
108, and 111, respectively, so they're able to be represented as chars
(duh...). But if I'd change the initializer to something like

int hello[] = {1000, 43676, 362, 6364, 2575};

I'd get this output

byte 0: <�>
byte 1: <>
byte 2: <(null char)
byte 3: <(null char)
byte 4: <�>
byte 5: <�>
byte 6: <(null char)
byte 7: <(null char)
byte 8: <j>
byte 9: <>
byte 10: <(null char)
byte 11: <(null char)
byte 12: <�>
byte 13: <▒>
byte 14: <(null char)
byte 15: <(null char)
byte 16: <>
byte 17: <
>
byte 18: <(null char)
byte 19: <(null char)

(In other words, non-printable characters.)

Is some kind of overflow happening when I subscript the char pointer?
Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?

Sebastian

Sep 6 '08 #1
16 6788
s0****@gmail.co m writes:
#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) {
printf("byte %2zu: <%c>", i, p[i]);
if (!p[i])
printf(" (null char)");
printf("\n");
}

return 0;
}
<snip>
I'm confused about the int *-to-void *-to char * conversion. The
output shows that ints are four bytes on my machine, and the values in
the initializer 'h', 'e', 'l', 'l', 'o' have the values 104, 101, 108,
108, and 111, respectively, so they're able to be represented as chars
(duh...). But if I'd change the initializer to something like

int hello[] = {1000, 43676, 362, 6364, 2575};

I'd get this output

byte 0: <�>
byte 1: <>
byte 2: <(null char)
byte 3: <(null char)
byte 4: <�>
byte 5: <�>
byte 6: <(null char)
byte 7: <(null char)
<snip>
(In other words, non-printable characters.)

Is some kind of overflow happening when I subscript the char
pointer?
No, no overflow is happening on access.
Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?
First, they are not meaningless. Some process governs exactly what
you see but since it may involve things like the terminal setting it
can be a very complex one.

Secondly, a char pointer always points at a char object. C does not
mandate the value but any object of any type can be accessed as if it
is a sequence of char objects. In your case the first two characters
are almost certainly 1000 % 256 and 1000 / 256, i.e. the least and
second least significant bytes of the binary representation of 1000.

I know this is not an actual answer, but your either/or questions
don't give me much room!

--
Ben.
Sep 6 '08 #2
On Sep 6, 4:26 pm, s0s...@gmail.co m wrote:
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) {
printf("byte %2zu: <%c>", i, p[i]);
if (!p[i])
printf(" (null char)");
printf("\n");
}

return 0;

}

produces this output

byte 0: <h>
byte 1: <(null char)
byte 2: <(null char)
byte 3: <(null char)
byte 4: <e>
byte 5: <(null char)
byte 6: <(null char)
byte 7: <(null char)
byte 8: <l>
byte 9: <(null char)
byte 10: <(null char)
byte 11: <(null char)
byte 12: <l>
byte 13: <(null char)
byte 14: <(null char)
byte 15: <(null char)
byte 16: <o>
byte 17: <(null char)
byte 18: <(null char)
byte 19: <(null char)

I'm confused about the int *-to-void *-to char * conversion. The
output shows that ints are four bytes on my machine, and the values in
the initializer 'h', 'e', 'l', 'l', 'o' have the values 104, 101, 108,
108, and 111, respectively, so they're able to be represented as chars
(duh...). But if I'd change the initializer to something like

int hello[] = {1000, 43676, 362, 6364, 2575};

I'd get this output

byte 0: < >
byte 1: <>
byte 2: <(null char)
byte 3: <(null char)
byte 4: < >
byte 5: < >
byte 6: <(null char)
byte 7: <(null char)
byte 8: <j>
byte 9: <>
byte 10: <(null char)
byte 11: <(null char)
byte 12: < >
byte 13: <>
byte 14: <(null char)
byte 15: <(null char)
byte 16: <>
byte 17: <

byte 18: <(null char)
byte 19: <(null char)

(In other words, non-printable characters.)

Is some kind of overflow happening when I subscript the char pointer?
Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?

Sebastian
your question is same as i asked here before acutally acutally when we
have array of chars or int the linker allocates bytes of initialized
values plus 4 BYTES MORE which also include a NuLL char '\0'
Sep 6 '08 #3
On Sep 6, 4:26 pm, s0s...@gmail.co m wrote:
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) {
printf("byte %2zu: <%c>", i, p[i]);
if (!p[i])
printf(" (null char)");
printf("\n");
}

return 0;

}

produces this output

byte 0: <h>
byte 1: <(null char)
byte 2: <(null char)
byte 3: <(null char)
byte 4: <e>
byte 5: <(null char)
byte 6: <(null char)
byte 7: <(null char)
byte 8: <l>
byte 9: <(null char)
byte 10: <(null char)
byte 11: <(null char)
byte 12: <l>
byte 13: <(null char)
byte 14: <(null char)
byte 15: <(null char)
byte 16: <o>
byte 17: <(null char)
byte 18: <(null char)
byte 19: <(null char)

I'm confused about the int *-to-void *-to char * conversion. The
output shows that ints are four bytes on my machine, and the values in
the initializer 'h', 'e', 'l', 'l', 'o' have the values 104, 101, 108,
108, and 111, respectively, so they're able to be represented as chars
(duh...). But if I'd change the initializer to something like

int hello[] = {1000, 43676, 362, 6364, 2575};

I'd get this output

byte 0: < >
byte 1: <>
byte 2: <(null char)
byte 3: <(null char)
byte 4: < >
byte 5: < >
byte 6: <(null char)
byte 7: <(null char)
byte 8: <j>
byte 9: <>
byte 10: <(null char)
byte 11: <(null char)
byte 12: < >
byte 13: <>
byte 14: <(null char)
byte 15: <(null char)
byte 16: <>
byte 17: <

byte 18: <(null char)
byte 19: <(null char)

(In other words, non-printable characters.)

Is some kind of overflow happening when I subscript the char pointer?
Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?

Sebastian
here is the post
http://groups.google.co.in/group/com...42714e7b3e6c17
Sep 6 '08 #4
On Sep 6, 2:26 pm, s0s...@gmail.co m wrote:
This code
Is broken. :P
#include <stdio.h>

int main(void)
{
int hello[] = {'h', 'e', 'l', 'l', 'o'};
char *p = (void *) hello;
Change p to `unsigned char'. And the cast can be (void *) or (unsigned
char *).
for (size_t i = 0; i < sizeof(hello); ++i) {
printf("byte %2zu: <%c>", i, p[i]);
Remove the 2 in %2zu, else the output might not be meaningful.
Evaluating p[i] can invoke undefined behavior. Changing p to type
`unsigned char *' as I have suggested previously fixes this.
if (!p[i])
printf(" (null char)");
printf("\n");
}

return 0;

}

produces this output
<snip output>

I'm confused about the int *-to-void *-to char * conversion. The
output shows that ints are four bytes on my machine, and the values in
the initializer 'h', 'e', 'l', 'l', 'o' have the values 104, 101, 108,
108, and 111, respectively, so they're able to be represented as chars
(duh...). But if I'd change the initializer to something like
You can convert any pointer to object to unsigned char * to inspect
its object representation.
int hello[] = {1000, 43676, 362, 6364, 2575};

I'd get this output
<snip>
(In other words, non-printable characters.)
So what?
Is some kind of overflow happening when I subscript the char pointer?
Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?
*ASSUMING* you change p to unsigned char *, you split the objects
representation in CHAR_BIT chunks, and you treat those bits as value
bits, even though in the original object they might be padding bits or
a sign bit.

Change your program to this for more meaningful output:

#include <stdio.h>

typedef int object_type;
#define SIZE 10

int main(void) {

object_type object[SIZE];
unsigned char *p;
size_t i;

p = (unsigned char *)object;

for(i = 0; i < sizeof object; i++)
if(isprint(p[i])) printf("p[%zu] = '%c'\n", i, p[i]);
else printf("p[%zu] = not printable\n", i);

return 0;
}
Sep 6 '08 #5
raashid bhatt said:

<snip>
your question is same as i asked here before acutally acutally when we
have array of chars or int the linker allocates bytes of initialized
values plus 4 BYTES MORE which also include a NuLL char '\0'
You were told you were wrong before, and why. You are wrong now, for the
same reason.

--
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
Sep 6 '08 #6
raashid bhatt <ra**********@g mail.comwrites:
On Sep 6, 4:26 pm, s0s...@gmail.co m wrote:
<snip>
>int main(void)
{
int hello[] = {'h', 'e', 'l', 'l', 'o'};
char *p = (void *) hello;
<snip>
>}
<snip>
here is the post
http://groups.google.co.in/group/com...42714e7b3e6c17
In case you are confused by this reply, there is no connection between
your code and the thread cited by raashid bhatt.

--
Ben.
Sep 6 '08 #7

<s0****@gmail.c omwrote in message
Is some kind of overflow happening when I subscript the char pointer?
Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?
It's the second. You're using a char pointer to point to a list of integers.
On your machine, as is typical, ints are 4 bytes wide, i.e. 4 chars. So you
are printing out the internal representation of an integer, in its
ASCII-encoded value. However it isn't too meaningless because the low byte
happens to be set to a constant value that is a char, whilst the high bytes
are zero. If your machine was big-endian you'd see <null<null<null h
and so on.

--
Free games and programming goodies.
http://www.personal.leeds.ac.uk/~bgy1mm
Sep 6 '08 #8
vi******@gmail. com writes:
On Sep 6, 2:26 pm, s0s...@gmail.co m wrote:
<snip>
> for (size_t i = 0; i < sizeof(hello); ++i) {
printf("byte %2zu: <%c>", i, p[i]);

Remove the 2 in %2zu, else the output might not be meaningful.
What on earth is wrong with the 2?
Evaluating p[i] can invoke undefined behavior.
I think it is better to say "may invoke undefined behaviour". I
accept that you don't agree (there's been a long thread about this
already) but just for the benefit of the OP there are systems on which
the code posted can't go wrong in any way. Using a potentially signed
char pointer merely limits the portability to a very specific class of
implementations and you, as the programmer, can know (with absolute
certainty) if the code's behaviour is defined or not beforehand. This
is quite unlike some other kinds of UB.

However, one should always used unsigned char for this purpose since
there is no advantage to be gained by using char *.

--
Ben.
Sep 6 '08 #9
On Sep 6, 7:02*am, Ben Bacarisse <be********@bsb .me.ukwrote:
s0****@gmail.co m writes:
<snip>
>Or am I simply getting meaningless values because of accessing a char
pointer that points to something that wasn't a char object?

First, they are not meaningless. *Some process governs exactly what
you see but since it may involve things like the terminal setting it
can be a very complex one.
Well, I meant meaningless in the sense that the values were produced
in an unnatural way. For example, with the second initializer, the
bits that make up for the 1000 in the first element of the int array
are then broken when accessed through the char pointer and everything
becomes a mess! (I got -24 when trying to see the numerical value of
the first element that the char pointer was pointing to.)
Secondly, a char pointer always points at a char object. *C does not
mandate the value but any object of any type can be accessed as if it
is a sequence of char objects. *In your case the first two characters
are almost certainly 1000 % 256 and 1000 / 256, i.e. the least and
second least significant bytes of the binary representation of 1000.
Changing the printf format string to "byte %2zu: <%d>" (i.e., to print
a number instead of a character) yields -24 (which is not 1000 % 256)
for the first character and 3 (which is indeed 1000 / 256) for the
second.
I know this is not an actual answer, but your either/or questions
don't give me much room!
No, it was indeed useful. Anyway, I was just unsure whether accessing
the char pointer in that way was safe. Thanks.

Sebastian

Sep 6 '08 #10

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

Similar topics

1
2068
by: J. Campbell | last post by:
I have a feeling that I'm doing things all ass-backwards (again ;-), and would like some advice. What I want to do is: put some data to memory and then access that memory space as an array of data-types of my choosing (eg an array of char, short, or int). The application has to do with generating checksum-type values for files or strings, so speed is important, as I just want to quickly get this value then move on to the next task. As...
8
1585
by: Olaf Martens | last post by:
Greetings! Here's another problem that appeared recently: I have the following function call: l_test->Compress(&"filename.dat",l_buf); l_test is a pointer-to-packer that I want to check here. The file name thing should be plain enough, whereas l_buf is declared as a
4
16156
by: Pushkar Pradhan | last post by:
I have some functions which take as i/p a buffer (it can be float, char, or 16 bit, int etc.). The result is another o/p buffer, its type is also flexible (it could be a float, char etc.). I try to pass both as "void *buf" so that it can accept any data type. But since I access the buffer and try to assign its elements to another I get compile errors (I have pasted at the end). Now my question is how can I pass the i/p and o/p buffers...
14
1635
by: sachin_mzn | last post by:
Hi, Why I am not getting any run time error while accessing a freed memory in following code. This is printing h in std output. #include<stdio.h> main() { char* buffer = (char*)malloc(6); strcpy(buffer,"hello");
8
1866
by: Dawn Minnis | last post by:
Hey guys If I have a program (see codeSnippet1) that I compile to be called test.o Then run it as test.o n n 2 3 4 I want the code to be able to strip out the two characters at the start (always going to be 2) and store them as characters. But I can't seem to get it to work because it is a pointer to a vector of characters. However, if I only run with integer arguements and use codeSnippet2 it works fine and they convert nicely to...
27
8959
by: Erik de Castro Lopo | last post by:
Hi all, The GNU C compiler allows a void pointer to be incremented and the behaviour is equivalent to incrementing a char pointer. Is this legal C99 or is this a GNU C extention? Thanks in advance. Erik
4
4876
by: Wallace | last post by:
Hai All, Can anyone suggest or provide me sample code for making ODBC connection and executing simple queries from c++. I am using sql server 2000. Also please tell what are the header files to be included. I created a DSN and now I need to make connection with that DSN and execute query from my code. Thanks in advance.. Please help!!!! Looking forward for the response.
2
2285
by: ...vagrahb | last post by:
I am having accessing individual rows from a multidimensional array pass to a function as reference CODE: function Declaration int Part_Buffer(char (*buffer),int Low, int High)
160
5644
by: raphfrk | last post by:
Is this valid? int a; void *b; b = (void *)a; // b points to a b += 5*sizeof(*a); // b points to a a = 100;
0
8792
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, people are often confused as to whether an ONU can Work As a Router. In this blog post, well explore What is ONU, What Is Router, ONU & Routers main usage, and What is the difference between ONU and Router. Lets take a closer look ! Part I. Meaning of...
0
8699
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
9293
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, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
0
9163
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
1
9064
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
0
9003
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 protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the choice of these technologies. I'm particularly interested in Zigbee because I've heard it does some...
1
6617
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupr who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
4456
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
3
2097
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

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.