0
#include <stdio.h>
#include <string.h>

#define SRC_BUFF_SIZE 32
#define DST_BUFF_SIZE 8

int tempfn1(char *p)
{
    printf("p %p\n", p);
    return 0;
}

int tempfn(char *ip, int size)
{
    char pttt[DST_BUFF_SIZE];
    printf("ip %p\n", ip);
    tempfn1(ip);
    // ERROR - copying more data to a local buffer of 4 bytes

    //memcpy(pttt, ip, size); // This will lead to stack corruption as     
                              // the size exceeds the size of destination

    // IDEALLY the copy should be done with min of size of destination buffer 
    // or source size rather than source size... 
    // anyways dest can hold only the size so it is better to crop the buffer 
    // than to crash due to overflow. 
    // proper call is as follows
    #define MIN(a,b) (((a) < (b)) ? (a) : (b))
    memcpy(pttt, ip, MIN(size, DST_BUFF_SIZE));

    printf("ip %p\n", ip);
    tempfn1(ip);
    return 0;
}

int main()
{
    char ip[SRC_BUFF_SIZE] = {0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 
    0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 
    0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 
    0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2, 0xe2 };
    tempfn(ip, SRC_BUFF_SIZE);
    return 0;
}

这是一个避免堆栈损坏的示例程序。是否有任何其他功能可以检查目标长度和源长度以避免堆栈损坏?

4

2 回答 2

4

您的问题实际上归结为-

给定一个指针,找出它所指向的内存块的大小

这是不可能的,也没有意义。因此,为了使这个难题更简单,您需要做出一些假设,例如指针是char指针并且\0将被视为End-Of-Block指标。然后你可以使用诸如strlenetc之类的功能

但在你给定的情况下,这一切都不成立,你正在做的事情( using MIN)似乎还可以,并且尽可能接近你想要的。

于 2012-08-08T09:48:40.493 回答
3

您所指的概念不仅适用于堆栈损坏。它通常用于避免内存溢出。当与堆栈变量一起使用时,内存溢出会导致堆栈损坏,或者与堆变量一起使用时会导致堆损坏。基本上它会导致未定义的行为。

避免这种情况的最佳方法是:

  1. 正如Kerrek SB 在他的评论中正确指出的那样正确编程(即使用正确的逻辑)。
  2. 要使用 strncpy 代替 strcpy、strncat 代替 strcat 等函数,这将有助于应用您在此处尝试应用的相同安全概念。

以下关于安全编码指南和实践的两个链接可能会有所帮助:

http://www.atsec.com/downloads/pdf/secure-coding-guidelines.pdf
https://www.securecoding.cert.org/confluence/display/seccode/Top+10+Secure+Coding+Practices

于 2012-08-08T09:57:48.257 回答