

TsM
Участник-
Posts
55 -
Joined
-
Last visited
-
LPCXpresso
TsM replied to TsM's topic in GNU/OpenSource средства разработки
Ну мне это и надо. Я хочу регионом по умолчанию сделать внешнюю память (это работает), а модули стартапа через скрипот линкера разместить во внутренней RamLoc32 (не получается). Изучал LD, но пока не разобраться. Не понял, как прописать расположение данных для конкретных файлов в скрипты LPCXpresso. Вот что сгенерила IDE: /* * GENERATED FILE - DO NOT EDIT * © Code Red Technologies Ltd, 2008-2013 * © NXP Semiconductors 2013-2015 * Generated linker script file for LPC4357 * Created from memory.ldt by FMCreateLinkMemory * Using Freemarker v2.3.23 * LPCXpresso v7.9.2 [build 493] [2015-09-14] on 23.09.2015 9:05:06 */ MEMORY { /* Define each memory region */ MFlashA512 (rx) : ORIGIN = 0x1a000000, LENGTH = 0x80000 /* 512K bytes (alias Flash) */ RAM_EXT (rwx) : ORIGIN = 0x28000000, LENGTH = 0x1000000 /* 16M bytes (alias RAM) */ RamLoc32 (rwx) : ORIGIN = 0x10000000, LENGTH = 0x8000 /* 32K bytes (alias RAM2) */ } /* Define a symbol for the top of each memory region */ __base_MFlashA512 = 0x1a000000 ; /* MFlashA512 */ __base_Flash = 0x1a000000; /* Flash */ __top_MFlashA512 = 0x1a000000 + 0x80000; /* 512K bytes */ __top_Flash = 0x1a000000 + 0x80000; /* 512K bytes */ __base_RAM_EXT = 0x28000000 ; /* RAM_EXT */ __base_RAM = 0x28000000; /* RAM */ __top_RAM_EXT = 0x28000000 + 0x1000000; /* 16M bytes */ __top_RAM = 0x28000000 + 0x1000000; /* 16M bytes */ __base_RamLoc32 = 0x10000000 ; /* RamLoc32 */ __base_RAM2 = 0x10000000; /* RAM2 */ __top_RamLoc32 = 0x10000000 + 0x8000; /* 32K bytes */ __top_RAM2 = 0x10000000 + 0x8000; /* 32K bytes */ /* * GENERATED FILE - DO NOT EDIT * © Code Red Technologies Ltd, 2008-2013 * © NXP Semiconductors 2013-2015 * Generated linker script file for LPC4357 * Created from linkscript.ldt by FMCreateLinkLibraries * Using Freemarker v2.3.23 * LPCXpresso v7.9.2 [build 493] [2015-09-14] on 23.09.2015 9:05:06 */ INCLUDE "dc_freertos_webserver_Debug_library.ld" INCLUDE "dc_freertos_webserver_Debug_memory.ld" ENTRY(ResetISR) SECTIONS { /* MAIN TEXT SECTION */ .text : ALIGN(4) { FILL(0xff) __vectors_start__ = ABSOLUTE(.); KEEP(*(.isr_vector)) /* Global Section Table */ . = ALIGN(4); __section_table_start = .; __data_section_table = .; LONG(LOADADDR(.data)); LONG( ADDR(.data)); LONG( SIZEOF(.data)); LONG(LOADADDR(.data_RAM2)); LONG( ADDR(.data_RAM2)); LONG( SIZEOF(.data_RAM2)); __data_section_table_end = .; __bss_section_table = .; LONG( ADDR(.bss)); LONG( SIZEOF(.bss)); LONG( ADDR(.bss_RAM2)); LONG( SIZEOF(.bss_RAM2)); __bss_section_table_end = .; __section_table_end = .; /* End of Global Section Table */ *(.after_vectors*) } >MFlashA512 .text : ALIGN(4) { *(.text*) *(.rodata .rodata.* .constdata .constdata.*) . = ALIGN(4); } > MFlashA512 /* * for exception handling/unwind - some Newlib functions (in common * with C++ and STDC++) use this. */ .ARM.extab : ALIGN(4) { *(.ARM.extab* .gnu.linkonce.armextab.*) } > MFlashA512 __exidx_start = .; .ARM.exidx : ALIGN(4) { *(.ARM.exidx* .gnu.linkonce.armexidx.*) } > MFlashA512 __exidx_end = .; _etext = .; /* DATA section for RamLoc32 */ .data_RAM2 : ALIGN(4) { FILL(0xff) PROVIDE(__start_data_RAM2 = .); *(.ramfunc.$RAM2) *(.ramfunc.$RamLoc32) *(.data.$RAM2*) *(.data.$RamLoc32*) . = ALIGN(4); PROVIDE(__end_data_RAM2 = .); } > RamLoc32 AT>MFlashA512 /* MAIN DATA SECTION */ .uninit_RESERVED : ALIGN(4) { KEEP(*(.bss.$RESERVED*)) . = ALIGN(4); _end_uninit_RESERVED = .; } > RAM_EXT /* Main DATA section (RAM_EXT) */ .data : ALIGN(4) { FILL(0xff) _data = .; *(vtable) *(.ramfunc*) *(.data*) . = ALIGN(4); _edata = .; } > RAM_EXT AT>MFlashA512 /* BSS section for RamLoc32 */ .bss_RAM2 : ALIGN(4) { PROVIDE(__start_bss_RAM2 = .); *(.bss.$RAM2*) *(.bss.$RamLoc32*) . = ALIGN (. != 0 ? 4 : 1); /* avoid empty segment */ PROVIDE(__end_bss_RAM2 = .); } > RamLoc32 /* MAIN BSS SECTION */ .bss : ALIGN(4) { _bss = .; *(.bss*) *(COMMON) . = ALIGN(4); _ebss = .; PROVIDE(end = .); } > RAM_EXT /* NOINIT section for RamLoc32 */ .noinit_RAM2 (NOLOAD) : ALIGN(4) { *(.noinit.$RAM2*) *(.noinit.$RamLoc32*) . = ALIGN(4); } > RamLoc32 /* DEFAULT NOINIT SECTION */ .noinit (NOLOAD): ALIGN(4) { _noinit = .; *(.noinit*) . = ALIGN(4); _end_noinit = .; } > RAM_EXT PROVIDE(_pvHeapStart = DEFINED(__user_heap_base) ? __user_heap_base : .); PROVIDE(_vStackTop = DEFINED(__user_stack_top) ? __user_stack_top : __top_RAM_EXT - 0); /* ## Create checksum value (used in startup) ## */ PROVIDE(__valid_user_code_checksum = 0 - (_vStackTop + (ResetISR + 1) + (NMI_Handler + 1) + (HardFault_Handler + 1) + (( DEFINED(MemManage_Handler) ? MemManage_Handler : 0 ) + 1) /* MemManage_Handler may not be defined */ + (( DEFINED(BusFault_Handler) ? BusFault_Handler : 0 ) + 1) /* BusFault_Handler may not be defined */ + (( DEFINED(UsageFault_Handler) ? UsageFault_Handler : 0 ) + 1) /* UsageFault_Handler may not be defined */ ) ); } -
LPCXpresso
TsM replied to TsM's topic in GNU/OpenSource средства разработки
К сожалению, в GCC такого не нашел ( Буду пока смотреть в сторону скрипта линковки -
LPCXpresso
TsM replied to TsM's topic in GNU/OpenSource средства разработки
Нет. Про внутренние смежные блоки я к примеру сказал. Для первичной инициализации хватает и одной банки. Нужно много внешнего ОЗУ, а оно лежит совсем по другим адресам. А про скрипты согласен. Я нашел уже нашел способ, как использовать свой. Сначала генерю автоматом для шаблона, а потом снимаю найденную галочку в настройках и можно редактировать скрипт, он перезаписываться не будет. Теперь думаю, что там надо править... Это что ко всем переменным __attribute__ ((section... приписывать?! Нет, ну можно, конечно, для краткости задифайнить. Тогда проще весь стартовый код перелопатить таким образом. -
LPCXpresso
TsM replied to TsM's topic in GNU/OpenSource средства разработки
RealView как раз и умеет. Там все на раз-два настраивается прямо через GUI Keil. А если GNU не умеет, то как тогда вообще работать с банками? Мне нужно немного встроенной памяти, что-бы, как минимум, проинициализировать внешнее большое ОЗУ и уйти туда работать. Если не умеет автоматом раскидывать, то как это сделать вручную? -
LPCXpresso
TsM replied to TsM's topic in GNU/OpenSource средства разработки
Да я понимаю, что смотреть надо *.ld файлы. Но там все регионы памяти прописаны (формируются автоматически по настройкам из GUI и их редактировать нет смысла). Кажется должно было бы все работать. Да и описания синтаксиса я не нашел, поэтому не все в них понятно (здесь какой-то свой формат). И такая проблема не только с внешней памятью. Я работаю с LPC4357, у него несколько банков внутреннего ОЗУ. Есть даже два смежных банка, но по мере заполнения первого, данные не "переползают" во второй. Линковщик просто ругается, что не достаточно места в первом. На сайте указано, как код, константы, как массив переменных положить в нужный банк ОЗУ при помощи __attribute__ ((section.... Но это все не то. С LPCXpresso (Eclipse) только начал работать, более привычен Keil. В нем примерно также в GUI указывается распределение памяти и все работает прозрачно для программиста. А здесь даже не знаю куда ткнуться. -
LPCXpresso
TsM posted a topic in GNU/OpenSource средства разработки
Может кто подскажет, как сказать линковщику, что есть внешняя RAM? Использую LPCXpresso 7.9.0. В настройках проекта (MCU setting) добавил соответствующую секцию, но не помогает. При линковке сообщение, что не хватает внутреннего ОЗУ... Во внешнее линковать и не пытается. -
На сколько я понял, то LwIP имеет свой механизм выделения памяти. При беглом просмотре он потокобезопасен. В том варианте, в каком я использую стек, он выделяет память единожды, а потом выделяет/освобождает пулы под/от данные, не пользуясь функциями типа malloc. Я в этот механизм не вмешиваюсь. У меня получается, что заканчиваются свободные пулы при p = pbuf_alloc( PBUF_RAW, len, PBUF_POOL ) (и дальше по цепочке до memp_malloc_fn). Но пробовал и другие варианты, результат аналогичен. Мне кажется, что проблема явно не в самом стеке, а в его порте (emac.c, ethernetif.c) или я что-то не правильно настроил в lwipopts.h
-
Я кое-что из предложенного уже перепробовал. И точки останова ставил, и собирал статистику выделений-освобождений и т.д. и т.п. Не догадался подсовывать на вход стека сгенерированные данные. Повторяемости нет. С длинами пакетов все нормально, с семафорами, критическими секциями тоже все в порядке. Трудность в том, что что-то ломается значительно раньше, чем это уже проявляется. Пока остановился на том, что полноценный стек для моей задачи не нужен (просто хотелось его пощупать). Время, которое я мог себе позволить на решение этой проблемы, закончилось. Сейчас уже проще самому написать простейшую реализацию UDP, чем сейчас и занялся. А с потерей пакетов разбираться буду уже на прикладном уровне. Дальше планирую работать с кортексами, а там есть уже готовые связки (почти официальные, только до ума довести, под себя подстроить) стека, ОС (например в LPCExpresso). Возможно там такой проблемы уже не будет. Но вообще разобраться было бы интересно. При случае кое-что из предложенного попробую. Спасибо.
-
Добрый день! Имеются FreeRTOS 8 + lwIP 1.4.1 + LPC2478. Столкнулся с такой проблемой. Работаю через Netconn API. Шлю на плату TCP пакеты (утилитой netcat передаю файлы по X Мб). Какое-то время пакеты проходят через стек нормально (10...20...40 Мб). Но в какой-то момент времени стек все чаще и чаще начинает выдавать отказ в выделении памяти под принятый пакет (memp_malloc_fn), пока прием совсем не "захлебывается". При этом передача от платы через другое соединение работает нормально. Принятые пакеты netconn_recv не обрабатываю, а просто отбрасываю (пока), затем удаляю буфер netbuf_delete. Стеки, кучи операционки большие и пустые. В lwipopts.h тоже памяти выделено достаточно. Стек по какой-то причине выделяет больше пулов, чем освобождает. Причину утечки никак найти не могу. На вход стека с mac пакеты выдаю корректные (по крайней мере так думаю). Может кто сталкивался с подобной проблемой, в каком направлении копать? ethernetif.zip
-
Здравствуйте! Имеются FreeRTOS и LwIP. Нужно организовать асинхронный обмен по TCP соединению. Использую Netconn API. В одной задаче создаю соединение (режим сервера), через которое принимаю данные. Позволяет ли стек отправлять данные через это же соединение из другой задачи? Спасибо.
-
Keil, JTAG
TsM posted a topic in ARM, 32bit
Добрый день. Подскажите, пожалуйста, как настроить KEIL для работы с JTAG-цепочками. Имеются LPC2378 и LPC2478 в одной цепочке, отладчик JelLink Pro (последние драйвера SEGGER). Прошивки, соответственно, разные. Прошивал один из МК через J-Flash ARM V4.76d (), работает. KEIL видит (по логу), что есть два контроллера, но выдает ошибку перед стиранием. -
Уровень оптимизации компилятора и глобальные переменные
TsM replied to TsM's topic in ARM, 32bit
Точно! Семен Семеныч! ))) Этот указатель я еще не успел использовать в программе. И при включенной оптимизации компилятор его вообще инициализировать не стал. Сергей, спасибо! -
Уровень оптимизации компилятора и глобальные переменные
TsM posted a topic in ARM, 32bit
Добрый день! Среда разработки Keil 4.72, мк LPC2478. typedef unsigned int * pInt32U; #define Adr 0xE0084000 pInt32U a = (pInt32U)Adr ; pInt32U b = (pInt32U)Adr +1; pInt32U c = (pInt32U)Adr +2; pInt32U d = (pInt32U)Adr +3; В результате: a = 0xE0084000, b = 0xE0084004, c = 0xE0084008, d = ЛЕВЫЙ АДРЕС!!!! Если отключить оптимизацию компилятора (Level 0 -O0), то результат становится ожидаемым: a = 0xE0084000, b = 0xE0084004, c = 0xE0084008, d = 0xE008400C Указатели в модуле объявляются глобально. В "чистом" проекте данный код работает нормально. В чем может быть проблема? -
DMA LPC2478 в симуляторе Keil
TsM replied to TsM's topic in ARM, 32bit
Спасибо. Вопрос снят ((( -
DMA LPC2478 в симуляторе Keil
TsM replied to TsM's topic in ARM, 32bit
Такой настройки в симуляторе не нашел. Но в этой памяти у меня много переменных, с которыми симулятор нормально работает.