M0HAX 0 7 декабря, 2010 Опубликовано 7 декабря, 2010 · Жалоба Обращаюсь к гуру с просьбой помочь разобраться. Ситуация такая. Программа зависает либо в процедуре void vPortFree( void *pv ) в prvInsertBlockIntoFreeList( ( ( xBlockLink * ) pxLink ) );, либо в процедуре void *pvPortMalloc( size_t xWantedSize ) в цикле while( ( pxBlock->xBlockSize < xWantedSize ) && ( pxBlock->pxNextFreeBlock ) ) { pxPreviousBlock = pxBlock; pxBlock = pxBlock->pxNextFreeBlock; } Программа сделана так: в нескольких задачах суется в очередь(элементы очереди - это указатели) ссылка на некую структуру. Эта структура перед занесением в очередь создается с помощью pvPortMalloc. Если очередь заполнена, то сразу же в этой задаче эта структура освобождает память с помощью vPortFree(void *pv). Выглядит так,например: pxTestTaskSend = (xSendCadrStruct*)pvPortMalloc(sizeof(xSendCadrStruct)); if (pxTestTaskSend == (xSendCadrStruct*)NULL) GotoGlobalCycleProcedure(); pxTestTaskSend->num = 0xFE; pxTestTaskSend->ulCnt = 0; pxTestTaskSend->ulData = (unsigned portCHAR*)pxBufferStat; xResult = xQueueSendToBack(xSendCadrQueue, (void*)&pxTestTaskSend, 0); if (xResult == errQUEUE_FULL) vPortFree(pxTestTaskSend); Если прошло все нормально, то в задаче, которая берет из этой очереди элементы, после разборки данных структуры, уничтожает выделенную память для этой структуры, т.е. xSendCadrStruct *xSendCadr; for (;;){ xQueueReceive(xSendCadrQueue, &xSendCadr, portMAX_DELAY); /**/ ....... разбор структуры ...... switch (xSendCadr->num){ ................ }; /**/ vPortFree(xSendCadr) }; Вроде как все должно работать: в одном месте выделяется память, в другом - освобождается... По вашему, где мог ошибиться? Подскажите способы/наработки, как быстрее и эффективнее найти причину глюка. PS. В прерываниях не использую void vPortFree( void *pv ) и void *pvPortMalloc( size_t xWantedSize ). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
M0HAX 0 8 декабря, 2010 Опубликовано 8 декабря, 2010 · Жалоба Для отчетности: дело оказалось, похоже, в следующем: есть одна задача, которая использовала глобальную переменную-указатель на выделенную область памяти для структуры. Но у этой задачи есть клоны, т.е. получалось, что эта глобальная переменная использовалась в нескольких запущенных однородных задачах. В этой задаче происходило : xSendCadrStruct *pxGazTaskSend; static portTASK_FUNCTION(vGazRegulationTask, vParameters ){ for (;;){ xQueueReceive(pADCGazQueue[ucNumb], &ulData, portMAX_DELAY); ........... pxGazTaskSend = (xSendCadrStruct*)pvPortMalloc(sizeof(xSendCadrStruct)); if (pxGazTaskSend != (xSendCadrStruct*)NULL){ pxGazTaskSend->num = ucNumb + 0x10; //xGaz->ucAddress pxGazTaskSend->ulData = (unsigned portCHAR*)data; pxGazTaskSend->ulCnt = ++xGazLocal->ucCnt; xResult = xQueueSendToBack(xSendCadrQueue, (void*)&pxGazTaskSend, 0); if (xResult == errQUEUE_FULL) vPortFree(pxGazTaskSend); }; }; Перенес объявление переменной внутрь задачи, и глюк исчез,по крайней мере, пару часов уже работает, раньше зависало в теч 5 мин. Траблы, видать, происходили после вызовов либо pvPortMalloc, либо внутри xQueueSendToBack и соответствующих переключений контекста на следующую однородную задачу, которая использовала ту же глобальную переменную. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться