Unix Programming - Pointer hell

This is Interesting: Free IT Magazines  
Home > Archive > Unix Programming > March 2006 > Pointer hell





You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

Author Pointer hell
Simon Simple

2006-03-21, 3:17 am

Linux, GCC.

Can't figure out why this generates a SIGSEGV in fillGlobalBuffer()
(below).

globalBuffer is allocated in caller.c, then its address is passed to
a pointer of the same type inside of callee.c, and that local pointer
is used as the reference written to.

I increment the offset into globalBuffer to write successive bits of
data (in this case, timestamps but it's just for illustration).

I apparently can't assign and use a pointer this way, but I'm not
clear as to why. Or, I can do this but I'm going about it the wrong
way.

I get a zeros from the printf() call in fillGlobalBuffer() before it
crashes.

References to, or other info describing, what I'm being stupid about
would be greatly appreciated.

===== Compile
% gcc -g -Wall -o test caller.c callee.c -I.


===== Code
/* caller.c
*/
#include "callee.h"

unsigned char * globalBuffer ;

int
main(void)
{
int i, bytes_written ;
struct timeval tv ;

if ( (globalBuffer=calloc(1, GLOBAL_BUFSIZE)) == NULL )
{
fprintf(stderr,"calloc() failed on globalBuffer\n" );
exit(-1);
}
setGlobalBuffer( globalBuffer, GLOBAL_BUFSIZE ) ;

bytes_written = 0 ;
for ( i = 0 ; i < GLOBAL_BUFSIZE ; )
{
gettimeofday( &tv, NULL ) ;
fillGlobalBuffer(&tv, sizeof(struct timeval), &bytes_written);
i += bytes_written ;
}

// verify globalBuffer contents
for ( i = 0 ; i < GLOBAL_BUFSIZE ; i += sizeof(struct timeval) )
{
struct timeval * tv ;
tv = (struct timeval *)(globalBuffer+i) ;
// HERE
printf("Index=%d, timeval=%lu.%lu\n",i,tv->tv_sec,tv->tv_usec);
}

return 0 ;
}

/* callee.h
*/
#include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/time.h>
#include <string.h>

#define GLOBAL_BUFSIZE 1024

void
setGlobalBuffer( unsigned char * gb, int gbmax ) ;

int
fillGlobalBuffer( void * data, int datalen, int * written ) ;

/* callee.c
*/
#include "callee.h"

unsigned char * bigBuf ;
int bbIndex ;
int bbMax ;

void
setGlobalBuffer( unsigned char * gb, int gbmax )
{
bigBuf = gb ;
bbIndex = 0 ;
bbMax = gbmax ;
}

int
fillGlobalBuffer( void * data, int datalen, int * written )
{
struct timeval * tv ;

if ( bbIndex + datalen > bbMax )
return -1 ;

memcpy( bigBuf+bbIndex, data, datalen ) ;

tv = (struct timeval *)bigBuf+bbIndex ;
printf("fGB(): wrote %lu.%lu to bigBuf\n",tv->tv_sec,tv->tv_usec);

bbIndex += datalen ;
*written = datalen ;
return 0 ;
}

===== Output
% ./test
fGB(): wrote 1142826382.680840 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.4833 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf
fGB(): wrote 0.0 to bigBuf

Segmentation fault (core dumped)
Simple Simon

2006-03-21, 3:17 am

ssimple@domain.invalid wrote...
> Linux, GCC.


Sorry; left this out:

%uname -a
Linux tmdev 2.4.20-4GB #1 Tue May 24 16:14:53 UTC 2005 i686 unknown
unknown GNU/Linux

%gcc --version
gcc (GCC) 3.3 20030226 (prerelease) (SuSE Linux)
Copyright (C) 2002 Free Software Foundation, Inc.

%ld --version
GNU ld version 2.13.90.0.18 20030121 (SuSE Linux)
Copyright 2002 Free Software Foundation, Inc.

%/lib/libc.so.6
GNU C Library stable release version 2.3.2, by Roland McGrath et al.
Copyright (C) 2003 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.
There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE.
Compiled by GNU CC version 3.3 20030226 (prerelease) (SuSE Linux).
Compiled on a Linux 2.4.20 system on 2003-03-13.


> Can't figure out why this generates a SIGSEGV in fillGlobalBuffer()
> (below).
>
> globalBuffer is allocated in caller.c, then its address is passed to
> a pointer of the same type inside of callee.c, and that local pointer
> is used as the reference written to.


....within callee.c

> I increment the offset into globalBuffer to write successive bits of
> data (in this case, timestamps but it's just for illustration).
>
> I apparently can't assign and use a pointer this way, but I'm not
> clear as to why. Or, I can do this but I'm going about it the wrong
> way.
>
> I get a zeros from the printf() call in fillGlobalBuffer() before it
> crashes.
>
> References to, or other info describing, what I'm being stupid about
> would be greatly appreciated.
>
> ===== Compile
> % gcc -g -Wall -o test caller.c callee.c -I.
>
>
> ===== Code
> /* caller.c
> */
> #include "callee.h"
>
> unsigned char * globalBuffer ;
>
> int
> main(void)
> {
> int i, bytes_written ;
> struct timeval tv ;
>
> if ( (globalBuffer=calloc(1, GLOBAL_BUFSIZE)) == NULL )
> {
> fprintf(stderr,"calloc() failed on globalBuffer\n" );
> exit(-1);
> }
> setGlobalBuffer( globalBuffer, GLOBAL_BUFSIZE ) ;
>
> bytes_written = 0 ;
> for ( i = 0 ; i < GLOBAL_BUFSIZE ; )
> {
> gettimeofday( &tv, NULL ) ;
> fillGlobalBuffer(&tv, sizeof(struct timeval), &bytes_written);
> i += bytes_written ;
> }
>
> // verify globalBuffer contents
> for ( i = 0 ; i < GLOBAL_BUFSIZE ; i += sizeof(struct timeval) )
> {
> struct timeval * tv ;
> tv = (struct timeval *)(globalBuffer+i) ;
> // HERE
> printf("Index=%d, timeval=%lu.%lu\n",i,tv->tv_sec,tv->tv_usec);
> }
>
> return 0 ;
> }
>
> /* callee.h
> */
> #include <stdlib.h>
> #include <stdio.h>
> #include <sys/types.h>
> #include <sys/time.h>
> #include <string.h>
>
> #define GLOBAL_BUFSIZE 1024
>
> void
> setGlobalBuffer( unsigned char * gb, int gbmax ) ;
>
> int
> fillGlobalBuffer( void * data, int datalen, int * written ) ;
>
> /* callee.c
> */
> #include "callee.h"
>
> unsigned char * bigBuf ;
> int bbIndex ;
> int bbMax ;
>
> void
> setGlobalBuffer( unsigned char * gb, int gbmax )
> {
> bigBuf = gb ;
> bbIndex = 0 ;
> bbMax = gbmax ;
> }
>
> int
> fillGlobalBuffer( void * data, int datalen, int * written )
> {
> struct timeval * tv ;
>
> if ( bbIndex + datalen > bbMax )
> return -1 ;
>
> memcpy( bigBuf+bbIndex, data, datalen ) ;
>
> tv = (struct timeval *)bigBuf+bbIndex ;
> printf("fGB(): wrote %lu.%lu to bigBuf\n",tv->tv_sec,tv->tv_usec);
>
> bbIndex += datalen ;
> *written = datalen ;
> return 0 ;
> }
>
> ===== Output
> % ./test
> fGB(): wrote 1142826382.680840 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.4833 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
> fGB(): wrote 0.0 to bigBuf
>
> Segmentation fault (core dumped)

Heinz Ozwirk

2006-03-21, 3:17 am

"Simon Simple" <ssimple@domain.invalid> schrieb im Newsbeitrag =
news:MPG.1e87efcc5829000898a86e@news.verizon.net...
> Linux, GCC.
>=20
> Can't figure out why this generates a SIGSEGV in fillGlobalBuffer()=20
> (below).

....
> if ( (globalBuffer=3Dcalloc(1, GLOBAL_BUFSIZE)) =3D=3D NULL )


This allocates GLOBAL_BUFSIZE (1024) bytes.

> for ( i =3D 0 ; i < GLOBAL_BUFSIZE ; )
> {
> gettimeofday( &tv, NULL ) ;=20
> fillGlobalBuffer(&tv, sizeof(struct timeval), &bytes_written);
> i +=3D bytes_written ;
> }


This writes 1024 * sizeof(struct timeval) bytes to a 1024 bytes buffer. =
I don't know what timeval is, but from the way you are using it, it is =
larger than one byte. So after writing 1024/sizeof(struct timeval) =
entries your buffer will overflow and the program may do whatever it =
likes (even blowing up your computer would be acceptable). To write n =
records with m bytes each, you have to allocate at least n*m bytes of =
memory, so use calloc(n, m), or in your example

calloc(GLOBAL_BUFSIZE, sizeof(struct timeval)

HTH
Heinz
Giorgos Keramidas

2006-03-21, 3:17 am

On Mon, 20 Mar 2006 11:04:47 +0100, "Heinz Ozwirk" <hozwirk.SPAM@arcor.de> wrote:
>"Simon Simple" <ssimple@domain.invalid> schrieb
>im Newsbeitrag news:MPG.1e87efcc5829000898a86e@news.verizon.net...
> ...
>
> This allocates GLOBAL_BUFSIZE (1024) bytes.
>
>
> This writes 1024 * sizeof(struct timeval) bytes to a 1024 bytes
> buffer. I don't know what timeval is, but from the way you are using
> it, it is larger than one byte. So after writing 1024/sizeof(struct
> timeval) entries your buffer will overflow and the program may do
> whatever it likes (even blowing up your computer would be
> acceptable). To write n records with m bytes each, you have to
> allocate at least n*m bytes of memory, so use calloc(n, m), or in your
> example
>
> calloc(GLOBAL_BUFSIZE, sizeof(struct timeval)


A `struct timeval' is most certainly more than one byte. In FreeBSD
here, it's defined as:

% /*
% * Structure returned by gettimeofday(2) system call, and used in other calls.
% */
% struct timeval {
% #ifdef __alpha__
% long tv_sec; /* seconds */
% #else
% time_t tv_sec; /* seconds */
% #endif
% suseconds_t tv_usec; /* and microseconds */
% };

So you're 100% right about overflowing `globalBuffer' and the correct
fix for allocating GLOBAL_BUFSIZE entries is of course:

globalBuffer = calloc(GLOBAL_BUFSIZE, sizeof(struct timeval));

Simple Simon

2006-03-21, 3:17 am

hozwirk.SPAM@arcor.de wrote...
> "Simon Simple" <ssimple@domain.invalid> schrieb im Newsbeitrag news:MPG.1e87efcc5829000898a86e@news.verizon.net...
> ...
>
> This allocates GLOBAL_BUFSIZE (1024) bytes.
>
>
> This writes 1024 * sizeof(struct timeval) bytes to a 1024 bytes buffer. I don't know what timeval is, but from the way you are using it, it is larger than one byte. So after writing 1024/sizeof(struct timeval) entries your buffer will overflow and the p

rogram may do whatever it likes (even blowing up your computer would be acceptable). To write n records with m bytes each, you have to allocate at least n*m bytes of memory, so use calloc(n, m), or in your example

Thank you.

'i' is being incremented by sizeof(struct timeval) after each return
from fillGlobalBuffer(). I'm not sure how that translates into your
statement that I'm writing 1024 * sizeof(struct timeval) records.

I'll make the change you suggest, but I'm not convinced that you're
picking up on the meaning of 'i += bytes_written'.

The problem I believe I'm having is that I allocate globalBuffer in
caller.c, pass its pointer to callee.c which uses that point to
initialize a pointer of the same time with file scope (in callee.c).

Then when I try to read from globalBuffer in caller.c, I apparently
get the uninitialized values (from the calloc()) instead of what I
was trying to write into globalBuffer using the pointer to it that is
local to callee.c.

> calloc(GLOBAL_BUFSIZE, sizeof(struct timeval)
>
> HTH
> Heinz
>

Fred Kleinschmidt

2006-03-21, 3:17 am


"Simon Simple" <ssimple@domain.invalid> wrote in message
news:MPG.1e87efcc5829000898a86e@news.verizon.net...
> Linux, GCC.
>
> Can't figure out why this generates a SIGSEGV in fillGlobalBuffer()
> (below).
>
> globalBuffer is allocated in caller.c, then its address is passed to
> a pointer of the same type inside of callee.c, and that local pointer
> is used as the reference written to.
>
> I increment the offset into globalBuffer to write successive bits of
> data (in this case, timestamps but it's just for illustration).
>
> I apparently can't assign and use a pointer this way, but I'm not
> clear as to why. Or, I can do this but I'm going about it the wrong
> way.
>
> I get a zeros from the printf() call in fillGlobalBuffer() before it
> crashes.
>
> References to, or other info describing, what I'm being stupid about
> would be greatly appreciated.
>
> ===== Compile
> % gcc -g -Wall -o test caller.c callee.c -I.
>
>
> ===== Code
> /* caller.c
> */
> #include "callee.h"
>
> unsigned char * globalBuffer ;
>
> int
> main(void)
> {
> int i, bytes_written ;
> struct timeval tv ;
>
> if ( (globalBuffer=calloc(1, GLOBAL_BUFSIZE)) == NULL )
> {
> fprintf(stderr,"calloc() failed on globalBuffer\n" );
> exit(-1);
> }
> setGlobalBuffer( globalBuffer, GLOBAL_BUFSIZE ) ;
>
> bytes_written = 0 ;
> for ( i = 0 ; i < GLOBAL_BUFSIZE ; )
> {
> gettimeofday( &tv, NULL ) ;
> fillGlobalBuffer(&tv, sizeof(struct timeval), &bytes_written);
> i += bytes_written ;
> }
>
> // verify globalBuffer contents
> for ( i = 0 ; i < GLOBAL_BUFSIZE ; i += sizeof(struct timeval) )
> {
> struct timeval * tv ;
> tv = (struct timeval *)(globalBuffer+i) ;
> // HERE
> printf("Index=%d, timeval=%lu.%lu\n",i,tv->tv_sec,tv->tv_usec);
> }
>
> return 0 ;
> }
>
> /* callee.h
> */
> #include <stdlib.h>
> #include <stdio.h>
> #include <sys/types.h>
> #include <sys/time.h>
> #include <string.h>
>
> #define GLOBAL_BUFSIZE 1024
>
> void
> setGlobalBuffer( unsigned char * gb, int gbmax ) ;
>
> int
> fillGlobalBuffer( void * data, int datalen, int * written ) ;
>
> /* callee.c
> */
> #include "callee.h"
>
> unsigned char * bigBuf ;
> int bbIndex ;
> int bbMax ;
>
> void
> setGlobalBuffer( unsigned char * gb, int gbmax )
> {
> bigBuf = gb ;
> bbIndex = 0 ;
> bbMax = gbmax ;
> }
>
> int
> fillGlobalBuffer( void * data, int datalen, int * written )
> {
> struct timeval * tv ;
>
> if ( bbIndex + datalen > bbMax )
> return -1 ;
>
> memcpy( bigBuf+bbIndex, data, datalen ) ;
>
> tv = (struct timeval *)bigBuf+bbIndex ;


be very careful ablut pointer arithmetic.
Are you sure the above statement is what you want?
I think you probably mean
tv = (struct timeval *)(bigBuf+bbIndex);
since that is where you just copied data into.

(struct timeval *)bigBuf+bbIndex
casts bigBur into a ponter to a timeval struct.
Adding bbIndex to this increments the address by
bbIndex*sizeof(struct timeval)

But in the memcpy above you used bigBuf+bbIndex without the cast,
so that increments bigBuf by (bbIndex * sizeof(unsigned char))
since bigBuf is declared as a pointer to unsigned char.

> printf("fGB(): wrote %lu.%lu to bigBuf\n",tv->tv_sec,tv->tv_usec);
>
> bbIndex += datalen ;
> *written = datalen ;
> return 0 ;
> }
>
> ===== Output

<snip>


Simon Elliott

2006-03-21, 3:17 am

On 20/03/2006, Simon Simple wrote:

> fillGlobalBuffer(&tv, sizeof(struct timeval), &bytes_written);


You should probably check your return code here.

> tv = (struct timeval *)bigBuf+bbIndex ;


This may be the cause of the
> fGB(): wrote 0.0 to bigBuf

messages. AIUI a cast has higher precedence than an addition operator,
so this is what I think is happening here:

1/ (struct timeval *)bigBuf
bigBuf is converted to a pointer to struct timeval

2/ +bbIndex
bigBuf, now a pointer to struct timeval, is incremented by bbIndex,
which increments the pointer by bbIndex*sizeof(struct timeval)

To check if I'm correct, try changing this line to:
tv = (struct timeval *)(bigBuf+bbIndex);

I'm not sure what's causing your segmentation fault, but it might be an
idea to
fflush(stdout);
after your printf() calls, to make sure that you know when the
segmentation fault is happening. One possibility:

for ( i = 0 ; i < GLOBAL_BUFSIZE ; i += sizeof(struct timeval) )

At the end of the loop, it's possible that i<GLOBAL_BUFSIZE, but
i+sizeof(struct timeval)>=GLOBAL_BUFSIZE. This will inevitably happen
unless GLOBAL_BUFSIZE is evenly divisible by sizeof(struct timeval). In
other words, your buffer holds a number of timeval structs, and then
has a few bytes at the end which are unused. I think you may be trying
to look at those unused bytes as if they contained a timeval struct,
and reading over the end of the buffer.


--
Simon Elliott http://www.ctsn.co.uk
Simple Simon

2006-03-21, 8:07 am

Just wanted to post a big THANKS to everyone who helped me out with
this.
Sponsored Links






Free braindumps | Software forum | Database administration forum

Copyright 2003 - 2008 webservertalk.com