共3条
1/1 1 跳转至页
SRAM SRAM的最大变量使用地址要比堆栈地址小多少呢?
问
请问一下:SRAM的最大变量使用地址要比堆栈地址小多少呢?
我用mega16做的一个程序。SRAM为1KB,堆栈地址为0x045f,我程序中使用到的地址最大到0x0420就可以正常工作,再向上比如到0x0424就不能正常工作了。
SRAM的最上面应该是存储堆栈,而我的堆栈设置了是16字节就够了。那中间还有一段地址用来干什么呢?我一般能用到多少就安全呢?(动态存储区?)
mp文件:
NOTE: AVR Code addresses are word addresses
All other addresses (including ones in FLASH) are byte addresses
Area Addr Size Decimal Bytes (Attributes)
-------------------------------- ---- ---- ------- ----- ------------
text 0054 3AC0 = 15040. bytes (rel,con,rom)
Addr Global Symbol
----- --------------------------------
002A __text_start
002A __start
004A _exit
004B _Delay_1ms
0051 _Delay_ms
0060 _HexBitToAscII
0072 _AscIIToHexBit
0083 _FcsCal
00A3 _DecToAscII
00C3 _AscIIToHex
0109 _Timer2Ovf
013E _timer0_ovf_isr
0146 _UartRx
02EC _UartTx
0314 _PizInt2
0326 _UartRRInit
035D _UartRDInit
03B0 _SysInit
03E6 _SysNew
053A _SysControl
1CE8 _main
1CFA mod16u
1CFC div16u
1CFD xdiv16u
1D16 empy16s
1D26 pop_gset2
1D29 pop_gset3
1D2C pop_gset5
1D2F push_gset5
1D31 push_gset4
1D33 push_gset3
1D35 push_gset2
1D37 push_gset1
1D3A pop_gset1
1D3B pop
1D4E push_lset
1D65 pop_lset
1D7C lsl16
1D83 lsr16
1D8A __text_end
Area Addr Size Decimal Bytes (Attributes)
-------------------------------- ---- ---- ------- ----- ------------
bss 0060 03C0 = 960. bytes (rel,con,ram)
Addr Global Symbol
----- --------------------------------
0060 _EncAbsAngle
0060 __bss_start
0062 _AscII
0066 _RDNum
0067 _RxState
0068 _ComCmd
0069 _TxNum
006A _RxNum
006B _RxBuf
009E _TxBuf
00AF _PLCRR
00B3 _PLCRD
0417 _Sta
0418 _TimSecBase
0419 _Time
041A _OutDate3
041B _OutDate2
041C _OutDate1
041D _OutDate0
041E _InData0
041F _InDate0
0420 __bss_end
Area Start End Decimal Bytes (Attributes)
-------------------------------- ---- ---- ------- ----- ------------
vector 0000 004C = 76. bytes (abs,ovr,rom)
Files Linked [ module(s) ]
D:\icc\lib\crtatmega.o [ crtatmega.s ]
main.o [ main.c ]
<library> [ div16u.s, emul16s.s, gpop2.s, gpop3.s, gpop5.s, gpush.s, lpush.s, lsl16.s, lsr16.s ]
User Global Definitions
ram_end = 0x45f
hwstk_size = 0x10
User Base Address Definitions
func_lit = 0x54
data = 0x60
eeprom = 0x1 答 1: 中间的这一段是软件堆栈中间的这一段是软件堆栈,向上生长,堆栈向下生长。它的起始位置在你的变量后面。 答 2: EN我也这样听说过,不过软件堆栈到底需要多大呢?
是不是象硬件堆栈可以自己区设置? 答 3: 软件堆栈不可以设置软件堆栈的大小不能设置,在软件调用等场合用来传递参数,变量等。你的程序可能是变量太多引起的。你看一下是否能合并一些变量,压缩一些空间。 答 4: 恩我的程序确实是变量太多引起的,但是没有去运行程序前,我怎么知道变量到多少地址就多了呢?怎么确定?
堆栈检查? 答 5: 哈哈哈找到方法了,仿真的时候看一看堆栈区就知道了。
ICCAVR的启动代码在硬件堆栈和软件堆栈的最低字节分别写进了一个代码0xAA。这样仿真的时候看一看0xAA在哪个地址就可以了。
我的程序0xAA在0x0420(软件堆栈)和0x044f(硬件堆栈)。所以只有我的bss_end<=0x0420才能运行正常。
对应的实际运行检查可以用堆栈检查函数判断是否堆栈溢出。
我用mega16做的一个程序。SRAM为1KB,堆栈地址为0x045f,我程序中使用到的地址最大到0x0420就可以正常工作,再向上比如到0x0424就不能正常工作了。
SRAM的最上面应该是存储堆栈,而我的堆栈设置了是16字节就够了。那中间还有一段地址用来干什么呢?我一般能用到多少就安全呢?(动态存储区?)
mp文件:
NOTE: AVR Code addresses are word addresses
All other addresses (including ones in FLASH) are byte addresses
Area Addr Size Decimal Bytes (Attributes)
-------------------------------- ---- ---- ------- ----- ------------
text 0054 3AC0 = 15040. bytes (rel,con,rom)
Addr Global Symbol
----- --------------------------------
002A __text_start
002A __start
004A _exit
004B _Delay_1ms
0051 _Delay_ms
0060 _HexBitToAscII
0072 _AscIIToHexBit
0083 _FcsCal
00A3 _DecToAscII
00C3 _AscIIToHex
0109 _Timer2Ovf
013E _timer0_ovf_isr
0146 _UartRx
02EC _UartTx
0314 _PizInt2
0326 _UartRRInit
035D _UartRDInit
03B0 _SysInit
03E6 _SysNew
053A _SysControl
1CE8 _main
1CFA mod16u
1CFC div16u
1CFD xdiv16u
1D16 empy16s
1D26 pop_gset2
1D29 pop_gset3
1D2C pop_gset5
1D2F push_gset5
1D31 push_gset4
1D33 push_gset3
1D35 push_gset2
1D37 push_gset1
1D3A pop_gset1
1D3B pop
1D4E push_lset
1D65 pop_lset
1D7C lsl16
1D83 lsr16
1D8A __text_end
Area Addr Size Decimal Bytes (Attributes)
-------------------------------- ---- ---- ------- ----- ------------
bss 0060 03C0 = 960. bytes (rel,con,ram)
Addr Global Symbol
----- --------------------------------
0060 _EncAbsAngle
0060 __bss_start
0062 _AscII
0066 _RDNum
0067 _RxState
0068 _ComCmd
0069 _TxNum
006A _RxNum
006B _RxBuf
009E _TxBuf
00AF _PLCRR
00B3 _PLCRD
0417 _Sta
0418 _TimSecBase
0419 _Time
041A _OutDate3
041B _OutDate2
041C _OutDate1
041D _OutDate0
041E _InData0
041F _InDate0
0420 __bss_end
Area Start End Decimal Bytes (Attributes)
-------------------------------- ---- ---- ------- ----- ------------
vector 0000 004C = 76. bytes (abs,ovr,rom)
Files Linked [ module(s) ]
D:\icc\lib\crtatmega.o [ crtatmega.s ]
main.o [ main.c ]
<library> [ div16u.s, emul16s.s, gpop2.s, gpop3.s, gpop5.s, gpush.s, lpush.s, lsl16.s, lsr16.s ]
User Global Definitions
ram_end = 0x45f
hwstk_size = 0x10
User Base Address Definitions
func_lit = 0x54
data = 0x60
eeprom = 0x1 答 1: 中间的这一段是软件堆栈中间的这一段是软件堆栈,向上生长,堆栈向下生长。它的起始位置在你的变量后面。 答 2: EN我也这样听说过,不过软件堆栈到底需要多大呢?
是不是象硬件堆栈可以自己区设置? 答 3: 软件堆栈不可以设置软件堆栈的大小不能设置,在软件调用等场合用来传递参数,变量等。你的程序可能是变量太多引起的。你看一下是否能合并一些变量,压缩一些空间。 答 4: 恩我的程序确实是变量太多引起的,但是没有去运行程序前,我怎么知道变量到多少地址就多了呢?怎么确定?
堆栈检查? 答 5: 哈哈哈找到方法了,仿真的时候看一看堆栈区就知道了。
ICCAVR的启动代码在硬件堆栈和软件堆栈的最低字节分别写进了一个代码0xAA。这样仿真的时候看一看0xAA在哪个地址就可以了。
我的程序0xAA在0x0420(软件堆栈)和0x044f(硬件堆栈)。所以只有我的bss_end<=0x0420才能运行正常。
对应的实际运行检查可以用堆栈检查函数判断是否堆栈溢出。
共3条
1/1 1 跳转至页
回复
有奖活动 | |
---|---|
【有奖活动】分享技术经验,兑换京东卡 | |
话不多说,快进群! | |
请大声喊出:我要开发板! | |
【有奖活动】EEPW网站征稿正在进行时,欢迎踊跃投稿啦 | |
奖!发布技术笔记,技术评测贴换取您心仪的礼品 | |
打赏了!打赏了!打赏了! |
打赏帖 | |
---|---|
vscode+cmake搭建雅特力AT32L021开发环境被打赏30分 | |
【换取逻辑分析仪】自制底板并驱动ArduinoNanoRP2040ConnectLCD扩展板被打赏47分 | |
【分享评测,赢取加热台】RISC-V GCC 内嵌汇编使用被打赏38分 | |
【换取逻辑分析仪】-基于ADI单片机MAX78000的简易MP3音乐播放器被打赏48分 | |
我想要一部加热台+树莓派PICO驱动AHT10被打赏38分 | |
【换取逻辑分析仪】-硬件SPI驱动OLED屏幕被打赏36分 | |
换逻辑分析仪+上下拉与多路选择器被打赏29分 | |
Let'sdo第3期任务合集被打赏50分 | |
换逻辑分析仪+Verilog三态门被打赏27分 | |
换逻辑分析仪+Verilog多输出门被打赏24分 |