When attempting to setup CLA1 for use, I've run into a consistent "undefined symbol" error during the link step. The apparent undefined symbols include the names of each of my declared CLA tasks (Cla1Task1, Cla1Task8) along with variables that I believe should be made available from the link command file (Cla1ConstLoadSize, Cla1ConstLoadStart, Cla1ConstRunStart, Cla1ProgLoadSize, Cla1ProgLoadStart, Cla1ProgRunStart). This project is configured as an EABI project using the latest compiler version (TI v22.6.1 LTS).
I've managed to somewhat duplicate this error in the "CLA Hands On Workshop" example project by simply changing a few project properties (albeit, along with many warnings about using COFF library files in an EABI project):
- Compiler version => TI v22.6.1 LTS
- Output format => eabi (ELF)
- Runtime support library => rts2800_fpu32_eabi.lib
I've attached some relevant files in my own project related to CLA definitions/initialization. The project itself can be made available on GitHub if that may assist in reproducing the error. Any pointers or advice would be much appreciated, thank you!
/*
* 2837xD_FLASH_CLA_lnk_cpu1.cmd
*/
// The user must define CLA_C in the project linker settings if using the
// CLA C compiler
// Project Properties -> C2000 Linker -> Advanced Options -> Command File
// Preprocessing -> --define
#ifdef CLA_C
// Define a size for the CLA scratchpad area that will be used
// by the CLA compiler for local symbols and temps
// Also force references to the special symbols that mark the
// scratchpad are.
CLA_SCRATCHPAD_SIZE = 0x100;
--undef_sym=__cla_scratchpad_end
--undef_sym=__cla_scratchpad_start
#endif //CLA_C
MEMORY
{
PAGE 0 :
/* BEGIN is used for the "boot to SARAM" bootloader mode */
BEGIN : origin = 0x080000, length = 0x000002
RAMM0 : origin = 0x000123, length = 0x0002DD
RAMD0 : origin = 0x00B000, length = 0x000800
RAMLS0 : origin = 0x008000, length = 0x000800
RAMLS1 : origin = 0x008800, length = 0x000800
/* RAMLS4 : origin = 0x00A000, length = 0x000800 */
/* RAMLS5 : origin = 0x00A800, length = 0x000800 */
RAMLS4_5 : origin = 0x00A000, length = 0x001000
RAMGS14 : origin = 0x01A000, length = 0x001000 /* Only Available on F28379D, F28377D, F28375D devices. Remove line on other devices. */
RAMGS15 : origin = 0x01B000, length = 0x000FF8 /* Only Available on F28379D, F28377D, F28375D devices. Remove line on other devices. */
// RAMGS15_RSVD : origin = 0x01BFF8, length = 0x000008 /* Reserve and do not use for code as per the errata advisory "Memory: Prefetching Beyond Valid Memory" */
RESET : origin = 0x3FFFC0, length = 0x000002
/* Flash sectors */
FLASHA : origin = 0x080002, length = 0x001FFE /* on-chip Flash */
FLASHB : origin = 0x082000, length = 0x002000 /* on-chip Flash */
FLASHC : origin = 0x084000, length = 0x002000 /* on-chip Flash */
FLASHD : origin = 0x086000, length = 0x002000 /* on-chip Flash */
FLASHE : origin = 0x088000, length = 0x008000 /* on-chip Flash */
FLASHF : origin = 0x090000, length = 0x008000 /* on-chip Flash */
FLASHG : origin = 0x098000, length = 0x008000 /* on-chip Flash */
FLASHH : origin = 0x0A0000, length = 0x008000 /* on-chip Flash */
FLASHI : origin = 0x0A8000, length = 0x008000 /* on-chip Flash */
FLASHJ : origin = 0x0B0000, length = 0x008000 /* on-chip Flash */
FLASHK : origin = 0x0B8000, length = 0x002000 /* on-chip Flash */
FLASHL : origin = 0x0BA000, length = 0x002000 /* on-chip Flash */
FLASHM : origin = 0x0BC000, length = 0x002000 /* on-chip Flash */
FLASHN : origin = 0x0BE000, length = 0x001FF0 /* on-chip Flash */
// FLASHN_RSVD : origin = 0x0BFFF0, length = 0x000010 /* Reserve and do not use for code as per the errata advisory "Memory: Prefetching Beyond Valid Memory" */
PAGE 1 :
BOOT_RSVD : origin = 0x000002, length = 0x000121 /* Part of M0, BOOT rom will use this for stack */
RAMM1 : origin = 0x000400, length = 0x0003F8 /* on-chip RAM block M1 */
// RAMM1_RSVD : origin = 0x0007F8, length = 0x000008 /* Reserve and do not use for code as per the errata advisory "Memory: Prefetching Beyond Valid Memory" */
RAMLS2 : origin = 0x009000, length = 0x000800
RAMLS3 : origin = 0x009800, length = 0x000800
RAMGS0 : origin = 0x00C000, length = 0x001000
RAMGS1 : origin = 0x00D000, length = 0x001000
RAMGS2 : origin = 0x00E000, length = 0x001000
RAMGS3 : origin = 0x00F000, length = 0x001000
RAMGS4 : origin = 0x010000, length = 0x001000
RAMGS5 : origin = 0x011000, length = 0x001000
RAMGS6 : origin = 0x012000, length = 0x001000
RAMGS7 : origin = 0x013000, length = 0x001000
RAMGS8 : origin = 0x014000, length = 0x001000
RAMGS9 : origin = 0x015000, length = 0x001000
RAMGS10 : origin = 0x016000, length = 0x001000
// RAMGS11 : origin = 0x017000, length = 0x000FF8 /* Uncomment for F28374D, F28376D devices */
// RAMGS11_RSVD : origin = 0x017FF8, length = 0x000008 /* Reserve and do not use for code as per the errata advisory "Memory: Prefetching Beyond Valid Memory" */
RAMGS11 : origin = 0x017000, length = 0x001000 /* Only Available on F28379D, F28377D, F28375D devices. Remove line on other devices. */
RAMGS12 : origin = 0x018000, length = 0x001000 /* Only Available on F28379D, F28377D, F28375D devices. Remove line on other devices. */
RAMGS13 : origin = 0x019000, length = 0x001000 /* Only Available on F28379D, F28377D, F28375D devices. Remove line on other devices. */
EMIF1_CS0n : origin = 0x80000000, length = 0x10000000
EMIF1_CS2n : origin = 0x00100000, length = 0x00200000
EMIF1_CS3n : origin = 0x00300000, length = 0x00080000
EMIF1_CS4n : origin = 0x00380000, length = 0x00060000
EMIF2_CS0n : origin = 0x90000000, length = 0x10000000
EMIF2_CS2n : origin = 0x00002000, length = 0x00001000
CLA1_MSGRAMLOW : origin = 0x001480, length = 0x000080
CLA1_MSGRAMHIGH : origin = 0x001500, length = 0x000080
}
SECTIONS
{
/* Allocate program areas: */
.cinit : > FLASHB PAGE = 0, ALIGN(8)
.text : > FLASHB PAGE = 0, ALIGN(8)
codestart : > BEGIN PAGE = 0, ALIGN(8)
.stack : > RAMM1 PAGE = 1
.switch : > FLASHB PAGE = 0, ALIGN(8)
/* Allocate uninitalized data sections: */
#if defined(__TI_EABI__)
.init_array : > FLASHB, PAGE = 0, ALIGN(8)
.bss : > RAMLS2, PAGE = 1
.bss:output : > RAMLS2, PAGE = 1
.data : > RAMLS2, PAGE = 1
.sysmem : > RAMLS2, PAGE = 1
.const : > FLASHB, PAGE = 0, ALIGN(8)
#else
.pinit : > FLASHB, PAGE = 0, ALIGN(8)
.ebss : > RAMLS2, PAGE = 1
.esysmem : > RAMLS2, PAGE = 1
.econst : > FLASHB PAGE = 0, ALIGN(8)
#endif
.reset : > RESET, PAGE = 0, TYPE = DSECT /* not used, */
Filter_RegsFile : > RAMGS0, PAGE = 1
.em2_cs0 : > EMIF2_CS0n, PAGE = 1
.em2_cs2 : > EMIF2_CS2n, PAGE = 1
/* CLA specific sections */
#if defined(__TI_EABI__)
Cla1Prog : LOAD = FLASHD,
RUN = RAMLS4_5,
LOAD_START(Cla1funcsLoadStart),
LOAD_END(Cla1funcsLoadEnd),
RUN_START(Cla1funcsRunStart),
LOAD_SIZE(Cla1funcsLoadSize),
PAGE = 0, ALIGN(8)
#else
Cla1Prog : LOAD = FLASHD,
RUN = RAMLS4_5,
LOAD_START(_Cla1funcsLoadStart),
LOAD_END(_Cla1funcsLoadEnd),
RUN_START(_Cla1funcsRunStart),
LOAD_SIZE(_Cla1funcsLoadSize),
PAGE = 0, ALIGN(8)
#endif
CLADataLS0 : > RAMLS0, PAGE=0
CLADataLS1 : > RAMLS1, PAGE=0
Cla1ToCpuMsgRAM : > CLA1_MSGRAMLOW, PAGE = 1
CpuToCla1MsgRAM : > CLA1_MSGRAMHIGH, PAGE = 1
#ifdef __TI_COMPILER_VERSION__
#if __TI_COMPILER_VERSION__ >= 15009000
#if defined(__TI_EABI__)
.TI.ramfunc : {} LOAD = FLASHD,
RUN = RAMD0,
LOAD_START(RamfuncsLoadStart),
LOAD_SIZE(RamfuncsLoadSize),
LOAD_END(RamfuncsLoadEnd),
RUN_START(RamfuncsRunStart),
RUN_SIZE(RamfuncsRunSize),
RUN_END(RamfuncsRunEnd),
PAGE = 0, ALIGN(8)
#else
.TI.ramfunc : {} LOAD = FLASHD,
RUN = RAMD0,
LOAD_START(_RamfuncsLoadStart),
LOAD_SIZE(_RamfuncsLoadSize),
LOAD_END(_RamfuncsLoadEnd),
RUN_START(_RamfuncsRunStart),
RUN_SIZE(_RamfuncsRunSize),
RUN_END(_RamfuncsRunEnd),
PAGE = 0, ALIGN(8)
#endif
#else
ramfuncs : LOAD = FLASHD,
RUN = RAMD0,
LOAD_START(_RamfuncsLoadStart),
LOAD_SIZE(_RamfuncsLoadSize),
LOAD_END(_RamfuncsLoadEnd),
RUN_START(_RamfuncsRunStart),
RUN_SIZE(_RamfuncsRunSize),
RUN_END(_RamfuncsRunEnd),
PAGE = 0, ALIGN(8)
#endif
#endif
/* The following section definition are for SDFM examples */
Filter1_RegsFile : > RAMGS1, PAGE = 1, fill=0x1111
Filter2_RegsFile : > RAMGS2, PAGE = 1, fill=0x2222
Filter3_RegsFile : > RAMGS3, PAGE = 1, fill=0x3333
Filter4_RegsFile : > RAMGS4, PAGE = 1, fill=0x4444
#ifdef CLA_C
/* CLA C compiler sections */
//
// Must be allocated to memory the CLA has write access to
//
CLAscratch :
{ *.obj(CLAscratch)
. += CLA_SCRATCHPAD_SIZE;
*.obj(CLAscratch_end) } > RAMLS1, PAGE = 0
.scratchpad : > RAMLS1, PAGE = 0
.bss_cla : > RAMLS1, PAGE = 0
.const_cla : LOAD = FLASHB,
RUN = RAMLS1,
RUN_START(_Cla1ConstRunStart),
LOAD_START(_Cla1ConstLoadStart),
LOAD_SIZE(_Cla1ConstLoadSize),
PAGE = 0
#endif //CLA_C
}
/*
//===========================================================================
// End of file.
//===========================================================================
*/
/* * CLA/shared.c */ #include "CLA/shared.h" #include "CLA/tasks.h" #include <stdint.h> #include <inc/hw_types.h> #pragma DATA_SECTION(encoder_sine_max, "CpuToCla1MsgRAM"); volatile uint16_t encoder_sine_max[6]; #pragma DATA_SECTION(encoder_sine_min, "CpuToCla1MsgRAM"); volatile uint16_t encoder_sine_min[6]; #pragma DATA_SECTION(encoder_cosine_max, "CpuToCla1MsgRAM"); volatile uint16_t encoder_cosine_max[6]; #pragma DATA_SECTION(encoder_cosine_min, "CpuToCla1MsgRAM"); volatile uint16_t encoder_cosine_min[6]; #pragma DATA_SECTION(encoder_angle, "Cla1ToCpuMsgRAM"); volatile float32_t encoder_angle[6];
/* * CLA/tasks.h */ #ifndef INCLUDE_CLA_TASKS_H_ #define INCLUDE_CLA_TASKS_H_ __attribute__((interrupt)) void Cla1Task1(void); __attribute__((interrupt)) void Cla1Task8(void); #endif /* INCLUDE_CLA_TASKS_H_ */
/* * CLA/shared.h * * Contains variable declarations shared between CLA and CPU. */ #ifndef INCLUDE_CLA_SHARED_H_ #define INCLUDE_CLA_SHARED_H_ #include <stdint.h> #include <inc/hw_types.h> extern volatile uint16_t encoder_sine_max[6]; extern volatile uint16_t encoder_sine_min[6]; extern volatile uint16_t encoder_cosine_max[6]; extern volatile uint16_t encoder_cosine_min[6]; extern volatile float32_t encoder_angle[6]; #endif /* INCLUDE_CLA_SHARED_H_ */
/*
* CLA/tasks.cla
*/
#include "CLA/shared.h"
#include "CLA/tasks.h"
#include <stdint.h>
#include <inc/hw_types.h>
#include <adc.h>
#include <gpio.h>
#include <CLAmath.h>
uint16_t encoder_gpio;
// Copies of max/min in CLA memory that can dynamically adjust to new values.
uint16_t sin_max[6];
uint16_t sin_min[6];
uint16_t cos_max[6];
uint16_t cos_min[6];
float32_t amplitude(float32_t const max, float32_t const min) {
return (max - min) / 2.0f;
}
float32_t normalize(
uint32_t const measured_sub_min,
float32_t const amplitude
) {
float32_t const numerator = (float32_t)measured_sub_min - amplitude;
return numerator / amplitude;
}
/* Process ADC results and calculate encoder angles. */
__attribute__((interrupt)) void CLA1Task1(void) {
uint16_t const a1 = 0;
uint16_t const a2 = 1;
uint16_t const a3 = 2;
uint32_t sine_reads[3];
uint32_t cosine_reads[3];
float32_t sin_amp[3];
float32_t cos_amp[3];
float32_t sine_n[3];
float32_t cosine_n[3];
sine_reads[a1] = ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER1);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER2);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER3);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER4);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER5);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER6);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER7);
sine_reads[a1] += ADC_readResult(ADCARESULT_BASE, ADC_SOC_NUMBER8);
cosine_reads[a1] = ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER1);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER2);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER3);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER4);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER5);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER6);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER7);
cosine_reads[a1] += ADC_readResult(ADCBRESULT_BASE, ADC_SOC_NUMBER8);
sine_reads[a2] = ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER1);
sine_reads[a2] += ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER3);
sine_reads[a2] += ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER5);
sine_reads[a2] += ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER7);
sine_reads[a3] = ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER2);
sine_reads[a3] += ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER4);
sine_reads[a3] += ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER6);
sine_reads[a3] += ADC_readResult(ADCCRESULT_BASE, ADC_SOC_NUMBER8);
cosine_reads[a2] = ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER1);
cosine_reads[a2] += ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER3);
cosine_reads[a2] += ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER5);
cosine_reads[a2] += ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER7);
cosine_reads[a3] = ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER2);
cosine_reads[a3] += ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER4);
cosine_reads[a3] += ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER6);
cosine_reads[a3] += ADC_readResult(ADCDRESULT_BASE, ADC_SOC_NUMBER8);
sine_reads[a1] >>= 3; // Divide by 8 for average.
cosine_reads[a1] >>= 3; // Divide by 8 for average.
sine_reads[a2] >>= 2; // Divide by 4 for average.
cosine_reads[a2] >>= 2; // Divide by 4 for average.
sine_reads[a3] >>= 2; // Divide by 4 for average.
cosine_reads[a3] >>= 2; // Divide by 4 for average.
uint16_t const a1_ex = 0 + encoder_gpio;
uint16_t const a2_ex = 2 + encoder_gpio;
uint16_t const a3_ex = 4 + encoder_gpio;
/** Bit manipulations to emulate comparison-less min/max. **/
/* Axis 1 Sine/Cosine */
// 0xFFFFFFFF if sine_reads[a1] > sin_max[a1_ex]
int32_t mask = ((int32_t)sin_max[a1_ex] - sine_reads[a1]) >> 31;
sin_max[a1_ex] = (mask & sine_reads[a1]) + ((~mask) & sin_max[a1_ex]);
// 0xFFFFFFFF if sin_min[a1_ex] > sine_reads[a1]
mask = ((int32_t)sine_reads[a1] - sin_min[a1_ex]) >> 31;
sin_min[a1_ex] = (mask & sine_reads[a1]) + ((~mask) & sin_min[a1_ex]);
mask = ((int32_t)cos_max[a1_ex] - cosine_reads[a1]) >> 31;
cos_max[a1_ex] = (mask & cosine_reads[a1]) + ((~mask) & cos_max[a1_ex]);
mask = ((int32_t)cosine_reads[a1] - cos_min[a1_ex]) >> 31;
cos_min[a1_ex] = (mask & cosine_reads[a1]) + ((~mask) & cos_min[a1_ex]);
/* Axis 2 Sine/Cosine */
mask = ((int32_t)sin_max[a2_ex] - sine_reads[a2]) >> 31;
sin_max[a2_ex] = (mask & sine_reads[a2]) + ((~mask) & sin_max[a2_ex]);
mask = ((int32_t)sine_reads[a2] - sin_min[a2_ex]) >> 31;
sin_min[a2_ex] = (mask & sine_reads[a2]) + ((~mask) & sin_min[a2_ex]);
mask = ((int32_t)cos_max[a2_ex] - cosine_reads[a2]) >> 31;
cos_max[a2_ex] = (mask & cosine_reads[a2]) + ((~mask) & cos_max[a2_ex]);
mask = ((int32_t)cosine_reads[a2] - cos_min[a2_ex]) >> 31;
cos_min[a2_ex] = (mask & cosine_reads[a2]) + ((~mask) & cos_min[a2_ex]);
/* Axis 3 Sine/Cosine */
mask = ((int32_t)sin_max[a3_ex] - sine_reads[a3]) >> 31;
sin_max[a3_ex] = (mask & sine_reads[a3]) + ((~mask) & sin_max[a3_ex]);
mask = ((int32_t)sine_reads[a3] - sin_min[a3_ex]) >> 31;
sin_min[a3_ex] = (mask & sine_reads[a3]) + ((~mask) & sin_min[a3_ex]);
mask = ((int32_t)cos_max[a3_ex] - cosine_reads[a3]) >> 31;
cos_max[a3_ex] = (mask & cosine_reads[a3]) + ((~mask) & cos_max[a3_ex]);
mask = ((int32_t)cosine_reads[a3] - cos_min[a3_ex]) >> 31;
cos_min[a3_ex] = (mask & cosine_reads[a3]) + ((~mask) & cos_min[a3_ex]);
/** With updated min/max values, normalize to 0.0-1.0 for atan2. **/
sin_amp[a1] = amplitude(sin_max[a1_ex], sin_min[a1_ex]);
sin_amp[a2] = amplitude(sin_max[a2_ex], sin_min[a2_ex]);
sin_amp[a3] = amplitude(sin_max[a3_ex], sin_min[a3_ex]);
cos_amp[a1] = amplitude(cos_max[a1_ex], cos_min[a1_ex]);
cos_amp[a2] = amplitude(cos_max[a2_ex], cos_min[a2_ex]);
cos_amp[a3] = amplitude(cos_max[a3_ex], cos_min[a3_ex]);
sine_n[a1] = normalize(sine_reads[a1] - sin_min[a1_ex], sin_amp[a1]);
cosine_n[a1] = normalize(cosine_reads[a1] - cos_min[a1_ex], cos_amp[a1]);
sine_n[a2] = normalize(sine_reads[a2] - sin_min[a2_ex], sin_amp[a2]);
cosine_n[a2] = normalize(cosine_reads[a2] - cos_min[a2_ex], cos_amp[a2]);
sine_n[a3] = normalize(sine_reads[a3] - sin_min[a3_ex], sin_amp[a3]);
cosine_n[a3] = normalize(cosine_reads[a3] - cos_min[a3_ex], cos_amp[a3]);
encoder_angle[a1_ex] = CLAatan2(sine_n[a1], cosine_n[a1]);
encoder_angle[a2_ex] = CLAatan2(sine_n[a2], cosine_n[a2]);
encoder_angle[a3_ex] = CLAatan2(sine_n[a3], cosine_n[a3]);
// Flip hall encoder mux GPIO.
encoder_gpio ^= 1;
GPIO_writePin(99, encoder_gpio);
GPIO_writePin(103, encoder_gpio);
GPIO_writePin(107, encoder_gpio);
}
/* Initialize CLA memory. */
__attribute__((interrupt)) void CLA1Task8(void) {
__mdebugstop();
encoder_gpio = 0;
for (uint16_t i = 0; i < 6; ++i) {
sin_max[i] = encoder_sine_max[i];
sin_min[i] = encoder_sine_min[i];
cos_max[i] = encoder_cosine_max[i];
cos_min[i] = encoder_cosine_min[i];
}
}
/*
* device/cla.c
*
* -> In the application, this file's header simply contains the
* `claInitialize` function declaration with no other
* declarations/definitions/includes. The "main.c" file calls
* this initialization after `Device_init`, `Interrupt_initModule`,
* `Interrupt_initVectorTable`, `EINT`/`ERTM`, and GPIO pin
* initialization.
*/
#include "device/cla.h"
#include <stdint.h>
#include <memcfg.h>
#include <cla.h>
#include <sysctl.h>
#include "CLA/shared.h"
#include "CLA/tasks.h"
// Below declarations allow access to linker-defined placement variables.
// These variables are needed to copy over CLA code and data to the correct
// places from FLASH to RAM.
extern uint32_t Cla1ProgRunStart, Cla1ProgLoadStart, Cla1ProgLoadSize;
extern uint32_t Cla1ConstRunStart, Cla1ConstLoadStart, Cla1ConstLoadSize;
void claInitialize(void) {
memcpy((uint32_t*)&Cla1ProgRunStart, (uint32_t*)&Cla1ProgLoadStart, (uint32_t)&Cla1ProgLoadSize);
memcpy((uint32_t*)&Cla1ConstRunStart, (uint32_t*)&Cla1ConstLoadStart, (uint32_t)&Cla1ConstLoadSize);
MemCfg_initSections(MEMCFG_SECT_MSGCLA1TOCPU);
MemCfg_initSections(MEMCFG_SECT_MSGCPUTOCLA1);
while (!MemCfg_getInitStatus(MEMCFG_SECT_MSGCLA1TOCPU)) {}
while (!MemCfg_getInitStatus(MEMCFG_SECT_MSGCPUTOCLA1)) {}
MemCfg_initSections(MEMCFG_SECT_LS4 | MEMCFG_SECT_LS5 | MEMCFG_SECT_LS0 | MEMCFG_SECT_LS1);
while (!MemCfg_getInitStatus(MEMCFG_SECT_LS4 | MEMCFG_SECT_LS5 | MEMCFG_SECT_LS0 | MEMCFG_SECT_LS1)) {};
MemCfg_setLSRAMControllerSel(MEMCFG_SECT_LS4, MEMCFG_LSRAMCONTROLLER_CPU_CLA1);
MemCfg_setLSRAMControllerSel(MEMCFG_SECT_LS5, MEMCFG_LSRAMCONTROLLER_CPU_CLA1);
MemCfg_setCLAMemType(MEMCFG_SECT_LS4, MEMCFG_CLA_MEM_PROGRAM);
MemCfg_setCLAMemType(MEMCFG_SECT_LS5, MEMCFG_CLA_MEM_PROGRAM);
MemCfg_setLSRAMControllerSel(MEMCFG_SECT_LS0, MEMCFG_LSRAMCONTROLLER_CPU_CLA1);
MemCfg_setLSRAMControllerSel(MEMCFG_SECT_LS1, MEMCFG_LSRAMCONTROLLER_CPU_CLA1);
MemCfg_setCLAMemType(MEMCFG_SECT_LS0, MEMCFG_CLA_MEM_DATA);
MemCfg_setCLAMemType(MEMCFG_SECT_LS1, MEMCFG_CLA_MEM_DATA);
// SysCtl_enablePeripheral(SYSCTL_PERIPH_CLK_CLA1);
CLA_mapTaskVector(CLA1_BASE, CLA_MVECT_1, (uint16_t)&Cla1Task1);
CLA_mapTaskVector(CLA1_BASE, CLA_MVECT_8, (uint16_t)&Cla1Task8);
// Default values for ADC peak calibration.
for (uint16_t i = 0; i < 6; ++i) {
encoder_sine_max[i] = 0;
encoder_sine_min[i] = 65535;
encoder_cosine_max[i] = 0;
encoder_cosine_min[i] = 65535;
}
CLA_enableTasks(CLA1_BASE, CLA_TASKFLAG_1 | CLA_TASKFLAG_8);
CLA_clearTaskFlags(CLA1_BASE, CLA_TASKFLAG_ALL);
// Two triggers set so task runs regardless of which axes are enabled.
CLA_setTriggerSource(CLA_TASK_1, CLA_TRIGGER_ADCA1);
CLA_setTriggerSource(CLA_TASK_1, CLA_TRIGGER_ADCC1);
CLA_forceTasks(CLA1_BASE, CLA_TASKFLAG_8);
// while (CLA_getTaskRunStatus(CLA1_BASE, CLA_TASK_8)) {}
}

