Why does const int main = 195 result in a working program but without the const it ends in a segmentation fault?

旧街凉风 提交于 2019-11-28 22:34:30

Observe how the value 195 corresponds to the ret (return from function) instruction on 8086 compatibles. This definition of main thus behaves as if you defined it as int main() {} when executed.

On some platforms, const data is loaded into an executable but not writeable memory region whereas mutable data (i.e. data not qualified const) is loaded into a writeable but not executable memory region. For this reason, the program “works” when you declare main as const but not when you leave off the const qualifier.

Traditionally, binaries contained three segments:

  • The text segment is (if supported by the architecture) write-protected and executable, and contains executable code, variables of static storage duration qualified const, and string literals
  • The data segment is writeable and cannot be executed. It contains variables not qualified const with static storage duration and (at runtime) objects with allocated storage duration
  • The bss segment is similar to the data segment but is initialized to all zeroes. It contains variables of static storage duration not qualified const that have been declared without an initializer
  • The stack segment is not present in the binary and contains variables with automatic storage duration

Removing the const qualifier from the variable main causes it to be moved from the text to the data segment, which isn't executable, causing the segmentation violation you observe.

Modern platforms often have further segments (e.g. a rodata segment for data that is neither writeable nor executable) so please don't take this as an accurate description of your platform without consulting platform-specific documentation.

Please understand that not making main a function is usually incorrect, although technically a platform could allow main to be declared as a variable, cf. ISO 9899:2011 §5.1.2.2.1 ¶1, emphasis mine:

1 The function called at program startup is named main. The implementation declares no prototype for this function. It shall be defined with a return type of int and with no parameters (...) or with two parameters (...) or equivalent; or in some other implementation-defined manner.

In C, main at global scope is almost always a function.

To use main as a variable at global scope makes the behaviour of the program undefined.

(It just might be the case that when you write const the compiler optimises out the variable to a constant and so your program behaviour is different. But the program behaviour is still undefined).

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!