When performing pointer arithmetic, the size of the computation is automatically scaled to the size of the pointer type. For instance, a pointer to a four-byte integer will be scaled by four bytes at a time.
Improper use of pointer arithmetic can lead to miscalculations that result in subtle and hard to spot coding errors.
In this example, taken from Dowd, buf_ptr
is used to insert new integers into buf
, which is an array of 1024 integers. If there is data to be inserted into buf
(which is indicated by havedata()
) and buf_ptr
has not been incremented past buf + sizeof(buf)
, then an integer is inserted into buf
via buf_ptr
. However, the sizeof
operator returns the total number of bytes in buf
, which, assuming four-byte integers, is 4096 bytes. This value is then scaled to the size of an integer and added to buf
. As a result, it is possible to write integers past the end of buf
and cause a buffer overflow.
int buf[1024]; int *buf_ptr = buf; while (havedata() && buf_ptr < buf + sizeof(buf)) { *buf_ptr++ = parseint(getdata()); } |
To correct this example, the size of buf
can be directly added to buf
and used as an upper bound. The integer literal is scaled appropriately
int buf[1024]; int *b = buf; while (havedata() && b < buf+1024) { *b++ = parseint(getdata()); } |
Failure to understand and properly use pointer arithmetic can allow an attacker to execute arbitrary code.
\[[Dowd|AA. C References#Dowd 06]\] Chapter 6, "C Language Issues" (Vulnerabilities) |