2010-08-31 86 views
4

这个问题是创建一个跟进我刚才的问题的栈是由编译器或OS /建筑

stack growth direction

我想知道堆栈是否由编译器或OS /建筑风格?另外操作系统如何知道这些编译器的具体事情?例如:C++允许变量在堆栈和堆上创建数据,而Java只允许堆。

此外,如果在后文中提到的堆栈被创建,系统如何知道它,因为系统只知道堆栈指针和基址指针。

+2

可能重复[什么和堆栈和堆在哪里](http:// stackoverflow。问题/ 79923 /什么和哪里是堆栈和堆) – 2010-08-31 05:16:10

+2

我从Java的角度看不出两个问题是如何连接的。您确实意识到JVM在Java世界中有效地执行平台/体系结构,对吗? – 2010-08-31 05:18:11

+0

@Byron这只是我上一个问题的后续。另外问题不在于了解堆栈。从我以前的文章中,我曾经说过可以在堆上创建堆栈以防止缓冲区溢出等问题。所以如果在堆上创建,系统怎么知道这个? – brett 2010-08-31 05:18:13

回答

6

堆栈是操作系统为您的程序分配的内存位置。一旦分配完毕,操作系统会将一个寄存器(在x86上,它是esp)设置到堆栈的位置,然后启动程序。编译器知道如果他们使用这个寄存器中的值作为堆栈指针,他们会没事的。然后他们做任何他们想做的事情。操作系统只是分配一个区域。它并不关心它如何被使用。

操作系统不知道你的程序将主要使用堆栈还是堆。但是,由于大多数编程语言都以某种方式使用堆栈,因此它知道应该分配一个堆栈。例如,Java将其对象存储在堆上,但JVM的大多数实现将使用堆栈来维护调用帧(以及原始局部变量),因此它也需要堆栈。

+0

的意思,它应该读**一个栈**,因为我们对每个正在运行的线程都有一个jvm栈。 – 2010-08-31 06:02:34

+0

在可执行文件头中,mainthreads stacksize通常有一个字段(字段由编译器设置,通常可以使用链接器选项进行设置)。另外,在创建堆栈时,通常可以设置线程堆栈大小。 – 2010-08-31 06:34:10

+0

JVM线程堆栈可能与实际的java程序相同或不同。讨论起来很复杂,但是JVM可以为它的系统堆栈中的每个Java线程保留一个单独的堆栈,它用于本地代码。 – nategoose 2010-08-31 19:02:54

3

堆栈绝对由编译器定义,操作系统为它分配空间,但这是相对平凡的。堆栈是编译器使用的内存中的一个专用地方(编译器定义了使用它的指令)以控制程序执行流程并存储局部变量等。

因此操作系统不知道关于编译器的具体内容。堆栈仍然存储在主存中,它不是你(程序员)可以直接控制的存储器的一部分。

+0

我无法操作堆栈内存吗? – Eonil 2011-09-14 05:01:40

+0

这一切都取决于你对Java操作 – radman 2011-10-06 05:11:54

0

传统上,栈是放置机器代码调用的返回地址的位置(所以它可以在完成时返回)。因此有指示可以在内存中轻松访问这个位置。

很快发现将参数与返回地址一起调用是一种非常简单而有效的方法。这随后发展到处理本地地址等。

1

为虚拟机中的每个线程创建一个Java虚拟机堆栈。该堆栈存储,除了帧的推送和弹出操作之外,不能直接操作内容。

每次调用消息时会创建帧,并且使用来存储数据和部分结果,以及执行动态链接,返回方法的值以及调度异常。

语言规范的详细信息,即一个Java虚拟机堆栈类似于传统语言堆栈,如C。所以对我来说,显然jvm堆栈模型已经在jvm实现中被编码和使用了,而不是由主机操作系统提供。