使用malloc是否安全?

时间:2010-05-15 16:57:29

标签: c++ c malloc

有人告诉我,分配malloc不再安全了,我不是C / C ++大师,但我用malloc和C / C ++做了一些东西。有谁知道我有什么风险?

引用他:

  

[..]但确实C / C ++的弱点是安全性,而阿基里斯的脚跟确实是malloc和滥用指针。 C / C ++它是一种众所周知的不安全语言。 [..]我不建议继续用C ++编程的应用程序很少。“

12 个答案:

答案 0 :(得分:16)

C ++的new可能malloc()更安全,但这并不会自动使malloc()比以前更安全。你朋友说他为什么认为这是不安全的?


但是,这里有一些你应该注意的事项:

1)使用C ++,当您使用malloc() / free()new / delete时,您需要小心在同一个程序中并排。这是可能的,也是允许的,但是使用malloc()分配的所有内容都必须使用free(),而不是delete。同样,使用new分配的所有内容都必须使用delete,而不能使用free()。 (这个逻辑更进一步:如果您使用new[]分配数组,则必须使用delete[]释放它,而不仅仅使用delete。)始终使用相应的对应项进行分配和释放,每个对象。

int* ni = new int;
free(ni);   // ERROR: don't do this!
delete ni;  // OK

int* mi = (int*)malloc(sizeof(int));
delete mi;  // ERROR!
free(mi);   // OK  

2) malloc()new(再说一次C ++)并没有做同样的事情。 malloc()只是给你一大块内存来使用; new还会调用一个构造函数(如果可用)。同样,delete将调用析构函数(如果可用),而free()则不会。这可能会导致问题,例如错误初始化的对象(因为没有调用构造函数)或未释放的资源(因为没有调用析构函数)。

3) C ++的new还会为指定的类型处理分配适当数量的内存,而您需要自己使用{{{ 1}}:

malloc()

结论:

在C ++中,int *ni = new int; int *mi = (int*)malloc(sizeof(int)); // required amount of memory must be // explicitly specified! // (in some situations, you can make this // a little safer against code changes by // writing sizeof(*mi) instead.) / new应尽可能优先于delete / malloc()。 (在C中,free() / new不可用,因此选择很明显。)

答案 1 :(得分:13)

  

[...] C / C ++它是一种众所周知的不安全语言。 [...]

实际上,那是错的。 实际上,“C / C ++”甚至不存在。 C ,并且 < EM> C ++ 即可。它们共享一些(或者,如果你想要的话)很多语法,但它们确实是 非常不同的语言

他们大不相同的一点是他们管理动态内存的方式。 C方式确实使用malloc() / free(),如果你需要动态内存,除了使用它们(或malloc()的几个兄弟姐妹)之外,你可以做的其他事情很少。 C ++的方式是不 (手动) 处理动态资源 (其中只有一个 。资源管理交给一些实施良好且经过测试的类,最好是从标准库中,然后自动完成。例如,不是手动处理零终止字符缓冲区,而是std::string,而不是手动处理动态分配的数组,而不是手动处理打开的文件,而不是std:vector。{{1}流系列等。

答案 2 :(得分:8)

你的朋友可能在谈论:

  • 一般使用指针的安全性。例如,在C ++中,如果要使用malloc分配char数组,请问为什么不使用stringvector。指针不是不安全的,但由于错误使用指针而导致错误的代码是。

  • 特别是关于malloc的东西。出于安全原因,大多数操作系统在首次将内存交给进程之前清除内存。否则,来自一个应用程序的敏感数据可能泄露给另一个应用程序。在没有这样做的操作系统上,您可能会认为存在与malloc相关的不安全因素。它与free非常相关。

你的朋友也可能不知道他在说什么。当有人说“X不安全”时,我的回答是“以什么方式?”。

答案 3 :(得分:3)

也许你的朋友年纪大了,不熟悉现在的工作方式 - 我曾经认为C和C ++实际上是一样的,直到我发现了许多关于过去十年出现的语言的新事物(我的大多数老师都是老派贝尔实验室的人,他们主要用C语言编写,只有粗略的C ++知识 - 贝尔实验室工程师发明了C ++!)。 不要嘲笑他/她 - 有一天你可能会在那里!

我认为你的朋友对你必须做自己的记忆管理的想法感到不安 - 也就是说,容易犯错误。在这方面,它是不安全的,他/她是正确的......但是,这种不安全的方面可以通过良好的编程实践来克服,例如RAII和使用智能指针。

对于许多应用程序来说,自动垃圾收集可能很好,并且一些程序员对指针如何工作感到困惑,因此,如果没有经过一些培训,让新的,没有经验的开发人员在C / C ++中有效编程可能会很困难。这也许是为什么你的朋友认为应该避免使用C / C ++的原因。

答案 4 :(得分:2)

这是本机分配和释放C内存的唯一方法。如果你误用它,它就像其他任何东西一样不安全。微软提供了一些其他功能的“安全”版本,需要额外的size_t参数 - 也许你的朋友指的是类似的东西?如果是这种情况,也许他只是喜欢calloc()而不是malloc()?

答案 5 :(得分:1)

如果您使用C,则必须使用malloc来分配内存,除非您有第三方库为您分配/管理内存。

当然,你的朋友有一个观点认为很难在C中编写安全代码,特别是在分配内存和处理缓冲区时。但我们都知道,对吧? :)

答案 6 :(得分:1)

他可能想要警告你的是使用指针。是的,如果您不了解它是如何工作的,那将导致问题。否则,问问你的朋友的意思,或者请他提供证明他的肯定的参考。

malloc不安全就像是说“不要使用系统X,因为它不安全”。

在此之前,请在C中使用malloc,在C ++中使用new。 如果你在C ++中使用malloc,人们会对你生气,但在特定情况下这很好。

答案 7 :(得分:1)

malloc没有任何问题。你的朋友显然意味着手动内存管理不安全,容易导致错误。与垃圾收集器自动管理内存的其他语言相比(不是说它不可能有泄漏 - 现在没有人关心程序在终止时是否清理,重要的是在程序运行时某些东西不会占用内存运行)。

当然在C ++中你根本不会真正触及malloc(因为它在功能上与 new 并不相同,只是假设大多数时候你没有做你需要的事情不想只是获得原始内存)。此外,完全可以使用几乎完全消除内存泄漏和损坏(RAII)的技术进行编程,但这需要专业知识。

答案 8 :(得分:0)

从技术上讲,malloc从一开始就不安全,但除此之外,我唯一能想到的是Linux内核使用的臭名昭着的“OOM杀手”(OOM =内存不足) 。如果您愿意,可以read up on it。除此之外,我不知道malloc本身是如何固有的不安全。

答案 9 :(得分:0)

在C ++中,如果坚持良好的约定,就没有这样的问题。在C,嗯,练习。 Malloc本身并不具有固有的不安全功能 - 人们只是可以不恰当地处理它的结果。

答案 10 :(得分:0)

使用malloc是不安全的,因为无法编写大型应用程序并确保以高效方式释放每个malloc。因此,您将有大量的内存泄漏可能会或可能不是一个问题... ,当你加倍free,或使用错误的delete等,undefined行为可能导致。实际上,在C ++中使用错误的delete通常会允许任意代码执行。

使用C或C ++等语言编写的代码的 ONLY 方法是安全的,可以用数学的方式证明整个程序的依赖关系。

现代的内存安全语言可以安全地避免这些类型的错误,只要底层语言实现不易受攻击(这确实很少见,因为这些都是用C / C ++编写的,但是当我们转向硬件JVM时,这个问题会消失)。

答案 11 :(得分:0)

也许这个人指的是通过malloc()访问数据的可能性?

Malloc不会影响它提供的区域的内容,因此可以通过分配较大的区域然后扫描内容来从其他进程收集数据。

free()也不清除内存,因此从原则上讲,可以访问调入动态分配的缓冲区的数据。

我认识一个人,多年以前,当他发现相等大小的malloc将返回最近释放的块的地址时,他利用malloc创建了一个进程间通信方案。