Durante los últimos diez años, los procesadores de casi todos nuestros dispositivos se han convertido en multinúcleo. Les siguen microcontroladores multinúcleo. En los catálogos de los principales fabricantes, ya puedes encontrar microcontroladores de uso general con múltiples núcleos a precios razonables. Por lo tanto, parece que es hora de comenzar a usar microcontroladores de múltiples núcleos en sus propios dispositivos. Por supuesto, en los casos en que esté justificado.
. , . , . . .
-. ARM Cortex M NXP (LPC), STMicroelectronics Infineon (Cypress).
, .
- . , , . - , , .
- . ( , , ), . , ( Cortex M0) (, Cortex M4). , . , .
- . , . , . , , . .
.
. . . .
, (Master Core). . , (Slave Core), , reset. . System Control ( ).
, . . .
, , . , (Cortex M0), , (Cortex M4 / M7).
, . , – , . . . , .
, . (, LPC55S6x Cypress CY8C6xx5) . . (bus matrix). , . , , .
, STM32H747. , . , . .
, . , . , , . , , .
, , . , .
. . () FLASH- SRAM. . .
, (AHB1, AHB2, APB1, APB2…). , , «» .
(NVIC). . , , , NVIC. , NVIC . , : , , / . , , . , GPIO , , , .
. -. STM32 Hardware Semaphore (HSEM), NXP – Inter-CPU mailbox, Cypress – Inter-Processor Communication Block (IPC). , .
. « » (mailbox). , . NVIC . , , , - ( ).
– , . . . , , . , . , . , , . , . , . .
. .
. (Debug Access Port). - . ( ) . . .
. , , .
LPC55S69-EVK NXP LPC55S69, Cortex M33. IAR Embedded Workbench 8. , , . , .
CMSIS. . , .
0
. CPU0.
.
- C: Project > Create New Project. C / main. , 0, . CPU0.
- : File > Save Workspace.
- General Options > Target .
: , , .
- General Options > Library Configuration Use CMSIS.
- (C/C++ Compiler > Preprocessor) :
< SDK>\devices\LPC55S69
. Defined symbolsCPU_LPC55S69JBD100_cm33_core0
( , ). - Linker > Config Override default
LPC55S69_cm33_core0_flash.icf
SDK (< SDK>\devices\LPC55S69\iar
). - Debugger > Setup (Driver) CMSIS DAP.
- , Debugger > Download Verify Download Use flash loader(s).
-
system_LPC55S69_cm33_core0.c
startup_LPC55S69_cm33_core0.s
(< SDK>\devices\LPC55S69
< SDK>\devices\LPC55S69\iar
). , . ,
GPIO1_7
.
#include "LPC55S69_cm33_core0.h" #define LED_GPIO_BLOCK 1 #define LED_GPIO_PIN 7 static inline void Delay(void) { for(int i = 0; i < 8000000; i++); } int main() { /**** LED setup ****/ // Enable clocking for GPIO1 (located on AHB bus) SYSCON->AHBCLKCTRLX[0] |= SYSCON_AHBCLKCTRL0_GPIO1_MASK; // Set direction for GPIO1 7 as output GPIO->DIR[LED_GPIO_BLOCK] |= GPIO_DIR_DIRP(1 << LED_GPIO_PIN); while(1) { /**** LED blinking ****/ GPIO->B[LED_GPIO_BLOCK][LED_GPIO_PIN] = 0; // Turn led On Delay(); GPIO->B[LED_GPIO_BLOCK][LED_GPIO_PIN] = 1; // Turn led off Delay(); } }
- , , , .
1
, . . , .
, 3, 5, 6, 9, 10 core0
core1
.
, , , GPIO1_4
:
#define LED_GPIO_PIN 7 --> #define LED_GPIO_PIN 4
. … Reading CPU status failed
.
, , LPC55S69 . 0 , 1 — . 1 0 :
- 1.
- , 1 .
- 1.
- reset 1.
0 :
// Sequence required to be written
// to SYSCON->CPUCTRL register ORed with other bits
// to applay settings
// See UM11126 4.5.70 for more details
#define SYSCON_CPUCTRL_ENABLING_SEQ 0xC0C40000
// Warning!!! IAR specific code.
// core1_image_start is defined in
// LPC55S69_cm33_core0_flash.icf linker config file
extern unsigned char core1_image_start[];
#define CORE1_IMAGE_START core1_image_start
main()
1:
/**** CPU1 (slave) setup ****/
// Enable CPU1
SYSCON->CPUCFG |= SYSCON_CPUCFG_CPU1ENABLE_MASK;
// Setup firmware boot address
SYSCON->CPBOOT = SYSCON_CPBOOT_CPBOOT(CORE1_IMAGE_START);
// Enable clock and reset CPU1
SYSCON->CPUCTRL = SYSCON->CPUCTRL | SYSCON_CPUCTRL_ENABLING_SEQ |
SYSCON_CPUCTRL_CPU1RSTEN_MASK | SYSCON_CPUCTRL_CPU1CLKEN_MASK;
// Release reset for CPU1
SYSCON->CPUCTRL = (SYSCON->CPUCTRL | SYSCON_CPUCTRL_ENABLING_SEQ) &
(~SYSCON_CPUCTRL_CPU1RSTEN_MASK);
, 0.
1 . .
. . .
, :
- ( 1).
- . Converter > Output, Generate Additional Output Raw binary.
- Debugger > Download Verify Download. .
- .
- ( 0).
- Debugger > Multicore, Simple .
- Linker > Input . ( ).
_CPU1_image
, , 1,__sec_core
4
.
- . , . , .
IAR , .
Failed to synch with multicore partner
, . CPU1 CPU0.
The debugging session could not be started.
Either the debugger initialization filed, or else the file "iar_all_modules_loaded" was missing, corrupt or of an unsupported format.
, Verify download 3. , , .
: , , , , . . , 6 7. ( , ), , , . , .
SRAM
FLASH-. . . SRAM. FLASH-, SRAM . :
- ( 1).
- (Linker > Config)
LPC55S69_cm33_core1_flash.icf
LPC55S69_cm33_core1_ram.icf
. - .
- ( 0).
-
main.c
:
#include "string.h" // for memcpy
.- SRAM, 1.
// Address of RAM, where the image for CPU1 should be copied // According to UM11126 2.1.5 it is SRAM 3 on CM33 data bus #define CORE1_BOOT_ADDRESS (void *)0x20033000
- .
// Firmware image size calculation uint32_t get_core1_image_size(void) { uint32_t core1_image_size; #pragma section = "__sec_core" core1_image_size = (uint32_t)__section_end("__sec_core") - (uint32_t)&core1_image_start; return core1_image_size; }
- 1 FLASH- SRAM.
// Copy CPU1 image to an other SRAM block memcpy(CORE1_BOOT_ADDRESS, (void *)CORE1_IMAGE_START, get_core1_image_size());
- ( , ).
// Setup boot address SYSCON->CPBOOT = SYSCON_CPBOOT_CPBOOT(CORE1_BOOT_ADDRESS);
- 0, , .
, ( 2 7 ).
, . - MAILBOX
.
MAILBOX
, . .
/**** Mailbox setup for mutex ****/
// Enable mailbox clocking
SYSCON->AHBCLKCTRLX[0] |= SYSCON_AHBCLKCTRL0_MAILBOX_MASK;
- , , .
— , . .
// Try to acquire mutex
while (!(MAILBOX->MUTEX & MAILBOX_MUTEX_EX_MASK));
.
// Release mutex
MAILBOX->MUTEX = MAILBOX_MUTEX_EX_MASK;
.
, .
.
#include "LPC55S69_cm33_core0.h"
#include "string.h" // for memcpy
#define LED_GPIO_BLOCK 1
#define LED_GPIO_PIN 7
// Address of RAM, where the image for CPU1 should be copied
// According to UM11126 2.1.5 it is SRAM 3 on CM33 data bus
#define CORE1_BOOT_ADDRESS (void *) 0x20033000
// Sequence required to be written
// to SYSCON->CPUCTRL register ORed with other bits
// to applay settings
// See UM11126 4.5.70 for more details
#define SYSCON_CPUCTRL_ENABLING_SEQ 0xC0C40000
// Warning!!! IAR specific code.
// core1_image_start is defined in
// LPC55S69_cm33_core0_flash.icf linker config file
extern unsigned char core1_image_start[];
#define CORE1_IMAGE_START core1_image_start
static inline void Delay(void)
{
for(int i = 0; i < 8000000; i++);
}
// Firmware image size calculation
uint32_t get_core1_image_size(void)
{
uint32_t core1_image_size;
#pragma section = "__sec_core"
core1_image_size = (uint32_t)__section_end("__sec_core") -
(uint32_t)&core1_image_start;
return core1_image_size;
}
int main()
{
/**** LED setup ****/
// Enable clocking for GPIO1 (located on AHB bus)
SYSCON->AHBCLKCTRLX[0] |= SYSCON_AHBCLKCTRL0_GPIO1_MASK;
// Set direction for GPIO1 7 as output
GPIO->DIR[LED_GPIO_BLOCK] |= GPIO_DIR_DIRP(1 << LED_GPIO_PIN);
/**** Mailbox setup for mutex ****/
// Enable mailbox clocking
SYSCON->AHBCLKCTRLX[0] |= SYSCON_AHBCLKCTRL0_MAILBOX_MASK;
/**** CPU1 (slave) setup ****/
// Copy CPU1 image to an other SRAM block
memcpy(CORE1_BOOT_ADDRESS, (void *)CORE1_IMAGE_START, get_core1_image_size());
// Enable CPU1
SYSCON->CPUCFG |= SYSCON_CPUCFG_CPU1ENABLE_MASK;
// Setup firmware boot address
SYSCON->CPBOOT = SYSCON_CPBOOT_CPBOOT(CORE1_BOOT_ADDRESS);
// Enable clock and reset CPU1
SYSCON->CPUCTRL = SYSCON->CPUCTRL | SYSCON_CPUCTRL_ENABLING_SEQ |
SYSCON_CPUCTRL_CPU1RSTEN_MASK | SYSCON_CPUCTRL_CPU1CLKEN_MASK;
// Release reset for CPU1
SYSCON->CPUCTRL = (SYSCON->CPUCTRL | SYSCON_CPUCTRL_ENABLING_SEQ) &
(~SYSCON_CPUCTRL_CPU1RSTEN_MASK);
while(1)
{
/**** LED blinking ****/
while (!(MAILBOX->MUTEX & MAILBOX_MUTEX_EX_MASK)); // Try to acquire mutex
GPIO->B[LED_GPIO_BLOCK][LED_GPIO_PIN] = 0; // Turn led On
Delay();
GPIO->B[LED_GPIO_BLOCK][LED_GPIO_PIN] = 1; // Turn led off
MAILBOX->MUTEX = MAILBOX_MUTEX_EX_MASK; // Release mutex
Delay();
}
}
#include "LPC55S69_cm33_core1.h"
#define LED_GPIO_BLOCK 1
#define LED_GPIO_PIN 4
static inline void Delay(void)
{
for(int i = 0; i < 8000000; i++);
}
int main()
{
/**** LED setup ****/
// Enable clocking for GPIO1 (located on AHB bus)
SYSCON->AHBCLKCTRLX[0] |= SYSCON_AHBCLKCTRL0_GPIO1_MASK;
// Set direction for GPIO1 7 as output
GPIO->DIR[LED_GPIO_BLOCK] |= GPIO_DIR_DIRP(1 << LED_GPIO_PIN);
/**** Mailbox setup for mutex ****/
// Enable mailbox clocking
SYSCON->AHBCLKCTRLX[0] |= SYSCON_AHBCLKCTRL0_MAILBOX_MASK;
while(1)
{
/**** LED blinking ****/
while (!(MAILBOX->MUTEX & MAILBOX_MUTEX_EX_MASK)); // Try to acquire mutex
GPIO->B[LED_GPIO_BLOCK][LED_GPIO_PIN] = 0; // Turn led On
Delay();
GPIO->B[LED_GPIO_BLOCK][LED_GPIO_PIN] = 1; // Turn led off
MAILBOX->MUTEX = MAILBOX_MUTEX_EX_MASK; // Release mutex
Delay();
}
}
:
- AN12335 NXP LPC55xx/LPC55Sxx Dual Core Communication
- Depuración de microcontroladores de doble núcleo AN5286 STM32H7x5 / x7
- Semáforo de hardware del sistema STM32H7 (HSEM)
- Depuración de IAR multinúcleo
- AN215656 Cypress PSoC 6 MCU Diseño de sistema de doble CPU
- RM0399 STM32H745 / 755 y STM32H747 / 757 MCU avanzados de
32 bits basados en brazo Manual de referencia - Manual de referencia técnica de la arquitectura Cypress CY8C6xx5 (TRM)
- UM11126 NXP LPC55S6x / LPC55S2x / LPC552x Manual de usuario