haker_fox 61 24 марта, 2023 Опубликовано 24 марта, 2023 · Жалоба Добрый день, коллеги! Понадобилось в очередном проекте убрать почти все драйвера устройств, обработчики прерываний которых прописаны в startup-файле. И не получается этого сделать, т.к. с использованием методов класса нет аналога __weak-функций. Вот фрагмент файла: Spoiler extern unsigned char CSTACK$$Limit; #pragma location = ".intvec" extern "C" const __root VectorEntry_t __vector_table[256] = { {.pStack = &CSTACK$$Limit }, // stack VectorNum 0 {.pHandler = reset }, // reset VectorNum 1 defaultCoreHandler, // NMI VectorNum 2 hardFaultHandlerAsm, // HardFault VectorNum 3 defaultCoreHandler, // MemManage VectorNum 4 defaultCoreHandler, // BusFault VectorNum 5 defaultCoreHandler, // UsageFault VectorNum 6 defaultCoreHandler, // Reserved VectorNum 7 defaultCoreHandler, // Reserved VectorNum 8 defaultCoreHandler, // Reserved VectorNum 9 defaultCoreHandler, // Reserved VectorNum 10 vPortSVCHandler, // SVC VectorNum 11 defaultCoreHandler, // Reserved VectorNum 12 defaultCoreHandler, // Reserved VectorNum 13 xPortPendSVHandler, // PendSV VectorNum 14 xPortSysTickHandler, // SysTick VectorNum 15 defaultCoreHandler, // your irq handler VectorNum 16, IRQ00 defaultCoreHandler, // your irq handler VectorNum 17, IRQ01 defaultCoreHandler, // your irq handler VectorNum 18, IRQ02 defaultCoreHandler, // your irq handler VectorNum 19, IRQ03 defaultCoreHandler, // your irq handler VectorNum 20, IRQ04 defaultCoreHandler, // your irq handler VectorNum 21, IRQ05 defaultCoreHandler, // your irq handler VectorNum 22, IRQ06 defaultCoreHandler, // your irq handler VectorNum 23, IRQ07 defaultCoreHandler, // your irq handler VectorNum 24, IRQ08 defaultCoreHandler, // your irq handler VectorNum 25, IRQ09 defaultCoreHandler, // your irq handler VectorNum 26, IRQ10 defaultCoreHandler, // your irq handler VectorNum 27, IRQ11 defaultCoreHandler, // your irq handler VectorNum 28, IRQ12 defaultCoreHandler, // your irq handler VectorNum 29, IRQ13 defaultCoreHandler, // your irq handler VectorNum 30, IRQ14 defaultCoreHandler, // your irq handler VectorNum 31, IRQ15 defaultCoreHandler, // your irq handler VectorNum 32, IRQ16 defaultCoreHandler, // your irq handler VectorNum 33, IRQ17 defaultCoreHandler, // your irq handler VectorNum 34, IRQ18 defaultCoreHandler, // your irq handler VectorNum 35, IRQ19 defaultCoreHandler, // your irq handler VectorNum 36, IRQ20 defaultCoreHandler, // your irq handler VectorNum 37, IRQ21 defaultCoreHandler, // your irq handler VectorNum 38, IRQ22 defaultCoreHandler, // your irq handler VectorNum 39, IRQ23 defaultCoreHandler, // your irq handler VectorNum 40, IRQ24 defaultCoreHandler, // your irq handler VectorNum 41, IRQ25 defaultCoreHandler, // your irq handler VectorNum 42, IRQ26 defaultCoreHandler, // your irq handler VectorNum 43, IRQ27 defaultCoreHandler, // your irq handler VectorNum 44, IRQ28 defaultCoreHandler, // your irq handler VectorNum 45, IRQ29 defaultCoreHandler, // your irq handler VectorNum 46, IRQ30 defaultCoreHandler, // your irq handler VectorNum 47, IRQ31 defaultCoreHandler, // your irq handler VectorNum 48, IRQ32 defaultCoreHandler, // your irq handler VectorNum 49, IRQ33 defaultCoreHandler, // your irq handler VectorNum 50, IRQ34 SpiDrv::MakeIsr<SpiDrv::Num::N0>, // your irq handler VectorNum 51, IRQ35 SpiDrv::MakeIsr<SpiDrv::Num::N1>, // your irq handler VectorNum 52, IRQ36 UsartDrv::MakeIsr<UsartDrv::Num::N0>, // uSart0 VectorNum 53, IRQ37 UsartDrv::MakeIsr<UsartDrv::Num::N1>, // uSart1 VectorNum 54, IRQ38 UsartDrv::MakeIsr<UsartDrv::Num::N2>, // uSart2 VectorNum 55, IRQ39 Внизу, да и далее по файлу, находятся обработчики прерываний, которые ещё и прописаны (для ускорения вызова) в заголовчных файлах каждого драйвера. Вообще, startup-файл на Си++ и был изначально нужен, чтобы красиво вызывать обработчики, но не предполагалось, что их не будет. А в текущем проекте их нет. И как выйти из ситуации - непонятно. Прямо хоть возвращайся к старому-доброму вызову обработчиков в Си-стиле с модификатором слабого связывания (линковки) __weak. В таком случае, если какой-то драйвер (файл на Си или Си++) не откомпилирован, т.е. отсутствует в проекте, линковщик подставит вызов функции по умолчанию. Но может быть есть какой-то красивый способ сделать подобное в Си++ с методами класса? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Forger 22 24 марта, 2023 Опубликовано 24 марта, 2023 · Жалоба 5 hours ago, haker_fox said: Но может быть есть какой-то красивый способ сделать подобное в Си++ с методами класса? Метод класса не является обычной c-функцией, за исключением static методов. Но статичные методы не имеют нормально доступа к полям класса, как обычные методы того же класса. В начале и делал именно по такой схеме, но промучался с областями видимости и откроенной костыльностью. Потом нашел прекрасное (на мой взгляд) решение - делегаты. Таблица векторов - таблица делегатов. Вот уже несколько лет использую такую схему. Очень доволен. Не использую ее лишь в крохотные простеньких проектах на крохотных МК. Лень рыться по поиску, но тут на форуме я делился ее построением. В такой схеме обработчиком прерывания можно сделать даже лямбда-функцию, не говоря уж про метод класса, конечно типа void(void). 1 Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться