реклама на сайте
подробности

 
 
> EW430-4.21 Утекает стек
Галстук
сообщение Oct 26 2009, 14:39
Сообщение #1


Частый гость
**

Группа: Свой
Сообщений: 112
Регистрация: 5-12-05
Из: Москва, Россия
Пользователь №: 11 818



Всем доброго времени суток!

Просветите, пожалуйста.

Есть такая функция, которая чинно-благородно вызывает другую функцию, а та еще одну, а та еще одну - и рисует буковку.

CODE
void RenderStringDisplay(const char *pString, const CharInfo *pFont,
uint16 row, uint16 column, uint16 spacing,
uint16 address)
{
uint16 x, y, initColumn;
const CharInfo *pCharInfo;

initColumn = column;

// Loop through characters until NULL (0) found.
while (*pString)
{
if (*pString == '\n') // Newline character?
{
column = initColumn;
row += spacing;
}
else // Not new line.
{
// Compute pointer to font information for current character.
pCharInfo = &pFont[(unsigned char)*pString];

// Compute origin of character bounding box.
x = column + pCharInfo->offsetX;
y = row - pCharInfo->offsetY - pCharInfo->height + 1;

// Display the character
DrawDisplayCharacter(pCharInfo, y, x, address);

// Advance along line by appropriate horizontal spacing.
column += pCharInfo->dwidth;
}

// Advance to next character.
pString++;
}
}


Все это прекрасно работает в отладчике, однако при возврате указатель стека уменьшается на 4. После нескольких вызовов уже начинает ругаться отладчик на переполнение стека. Впрочем, программа никуда не улетает и продолжает работать. Все прерывания запрещены.
Если выбрать опцию reduce stack usage, то это дело прекращается, SP при возврате возвращается точно назад. Что бы это значило?
При этом более простенькии функции с меньшей иерархией вложений стек отдают.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов (1 - 3)
VAI
сообщение Oct 26 2009, 14:52
Сообщение #2


Профессионал
*****

Группа: Модераторы
Сообщений: 1 120
Регистрация: 17-06-04
Пользователь №: 37



Непрятно разбираться в тексте, когда Вы игнорируете форматирование.
Вы не первый раз пишете, не новичок, "свой", разве трудно выделить код и нажать на иконку "Код" (самая левая). Это же неуважение к тем, кого Вы спрашиваете...
Вы можете включить генерацию ассемблерного листинга и найти, где Вас компилятор обманывает.
Конкретно по Вашему компилятору ничего не скажу, я использую старую версию 3.30, а вложений у меня очень много и прерывания разрешены, стек не утекает...


--------------------
Если зайца бить, его можно и спички научить зажигать
Сколько дурака не бей - умнее не будет. Зато опытнее
Go to the top of the page
 
+Quote Post
Галстук
сообщение Oct 26 2009, 15:33
Сообщение #3


Частый гость
**

Группа: Свой
Сообщений: 112
Регистрация: 5-12-05
Из: Москва, Россия
Пользователь №: 11 818



Обманывает, конечно. Вот кусок call frame, каждый повторный вызов RenderStringDisplay смещает стек на 4, пока дело не дойдет до "приличных" функций, которые стек не отгрызают.


CODE

FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 12, STACK
FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 16, STACK
FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 20, STACK
.............................................
FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 32, STACK
FUNCALL main, RenderCursor
LOCFRAME CSTACK, 32, STACK
FUNCALL main, WaitNonBusy
LOCFRAME CSTACK, 32, STACK


Удивительно, но через какое-то время стек "вдруг" отдается.

CODE

FUNCALL main, EnableRXInterrupts
LOCFRAME CSTACK, 32, STACK
FUNCALL main, RenderCursor
LOCFRAME CSTACK, 8, STACK


Т.е. как бы все само излечивается. Однако факт переполнения стека отладчиком отмечается, что не есть хорошо. Вот такая странность. Ну и если reduce stack usage, что, вроде, ухудшает код, то этих фокусов не наблюдается.

CODE
FUNCALL main, ClearDisplayImageBuffer
LOCFRAME CSTACK, 8, STACK
FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 12, STACK
FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 12, STACK
....................................................

FUNCALL main, RenderStringDisplay
LOCFRAME CSTACK, 12, STACK
FUNCALL main, RenderCursor
LOCFRAME CSTACK, 8, STACK
Go to the top of the page
 
+Quote Post
VAI
сообщение Oct 27 2009, 07:36
Сообщение #4


Профессионал
*****

Группа: Модераторы
Сообщений: 1 120
Регистрация: 17-06-04
Пользователь №: 37



Кстати, если в опциях проекта (я пишу для v3.30, в Ваше может быть несколько по иному, но смысл понятен), в категрии "Linker" во вкладке "Cmd Opt" поставить птичку "Use command line options" и вписать там -xmos, то в конце map-файла будет CALL GRAPH - там использование стека Вашей программой. Основываясь на этих данных Вы увеличиваете стек в категории "General Options" во вкладке "Stack/Heap".

Кстати, генерацию ассемблерного листинга включать в категории "C/C++ compiler" во вкладке "List" - птички "Ounput list file" и под ней "Assembler mnemonics" - позновательно иногда смотреть, что компилятор городит...


--------------------
Если зайца бить, его можно и спички научить зажигать
Сколько дурака не бей - умнее не будет. Зато опытнее
Go to the top of the page
 
+Quote Post

Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 22nd July 2025 - 06:46
Рейтинг@Mail.ru


Страница сгенерированна за 0.0277 секунд с 7
ELECTRONIX ©2004-2016