@ -9,6 +9,7 @@
# include "platform.h"
# include "platform.h"
# include <stdbool.h>
# include <stdbool.h>
# include "splitflap.h"
# include "splitflap.h"
# include "splitflap_positions.h"
# include "McuRTOS.h"
# include "McuRTOS.h"
# include "McuULN2003.h"
# include "McuULN2003.h"
# include <stdbool.h>
# include <stdbool.h>
@ -22,11 +23,6 @@
/* dynamic dictionary for the letters of the dictionary */
/* dynamic dictionary for the letters of the dictionary */
static dict_t * * splitFlapDict ;
static dict_t * * splitFlapDict ;
/* all letters of the splitflap in the correct order */
static Flap_t SF_Letters [ ] = { " " , " A " , " B " , " C " , " D " , " E " , " F " , " G " , " H " , " I " , " J " , " K " ,
" L " , " M " , " N " , " O " , " P " , " Q " , " R " , " S " , " T " , " U " , " V " , " W " , " X " , " Y " , " Z " ,
" 0 " , " 1 " , " 2 " , " 3 " , " 4 " , " 5 " , " 6 " , " 7 " , " 8 " , " 9 " ,
" ! " , " ? " , " : " } ;
/* function declarations */
/* function declarations */
static bool OngoingMoveMutex_Lock ( SF_Handle_t instance ) ;
static bool OngoingMoveMutex_Lock ( SF_Handle_t instance ) ;
@ -50,7 +46,7 @@ void SF_InitConfig(void){
// + 0.5 so the rounding is done correctly
// + 0.5 so the rounding is done correctly
int32_t position = ( stepsPerSegment * ( float ) i + 0.5 ) ;
int32_t position = ( stepsPerSegment * ( float ) i + 0.5 ) ;
addItem ( splitFlapDict , SF_Letters [ i ] , ( int32_t * ) position ) ;
addItem ( splitFlapDict , SF_Letters [ i ] , ( int32_t * ) position ) ;
McuLog_info ( " Letter '%s': Position %i \n " , SF_Letters [ i ] , ( int ) position ) ;
McuLog_info ( " Letter '%s': Position %i " , SF_Letters [ i ] , ( int ) position ) ;
}
}
}
}
@ -58,29 +54,31 @@ void SF_DeInitConfig(void){
dictDealoc ( splitFlapDict ) ;
dictDealoc ( splitFlapDict ) ;
}
}
SF_Handle_t SF_Init ( SF_Config_t * instance , int id ) {
SF_Handle_t SF_Init ( SF_Config_t * config ) {
SF_t * splitflap ;
SF_t * splitflap ;
# if SPLITFLAP_CONFIG_USE_FREERTOS_HEAP
# if SPLITFLAP_CONFIG_USE_FREERTOS_HEAP
splitflap = ( SF_t * ) pvPortMalloc ( sizeof ( SF_t ) ) ; /* get a new device descriptor */
splitflap = ( SF_t * ) pvPortMalloc ( sizeof ( SF_t ) ) ; // get memory for device from FreeRtos heap
# else
# else
splitflap = ( SF_t * ) malloc ( sizeof ( SF_t ) ) ; /* get a new device descriptor */
splitflap = ( SF_t * ) malloc ( sizeof ( SF_t ) ) ; // get memory for device from MCU heap
# endif
# endif
splitflap - > magSensor = McuGPIO_InitGPIO ( & instance - > magSensorConfig ) ;
splitflap - > magSensor = McuGPIO_InitGPIO ( & config - > magSensorConfig ) ; // initialize magnet sensor GPIO
splitflap - > motor = McuULN2003_InitMotor ( & instance - > motorConfig ) ;
splitflap - > motor = McuULN2003_InitMotor ( & config - > motorConfig ) ; // initialize ULN driver for stepper motor
splitflap - > ongoingMoveMutex = xSemaphoreCreateRecursiveMutex ( ) ; // create mutex for ongoing move
splitflap - > ongoingMoveMutex = xSemaphoreCreateRecursiveMutex ( ) ; // create mutex for ongoing move
splitflap - > flapQueue = xQueueCreate ( FLAP_QUEUE_LENGTH , FLAP_QUEUE_SELEM_SIZE ) ; // create queue
splitflap - > flapQueue = xQueueCreate ( FLAP_QUEUE_LENGTH , // create queue
splitflap - > id = id ;
FLAP_QUEUE_SELEM_SIZE ) ;
# ifndef APP_DEBUG // when not debugging => set to false
splitflap - > id = config - > setupIdentifier ; // copy setup identifier
splitflap - > hwId = config - > hardwareIdentifier ; // copy hardware identifier
# ifndef APP_DEBUG // when not debugging => set to "not initialized"
splitflap - > initialized = false ;
splitflap - > initialized = false ;
# else // when debugging => set to true
# else // when debugging => set to "initialized"
splitflap - > initialized = true ;
splitflap - > initialized = true ;
# endif
# endif
// check if queue was created
// check if queue was created
if ( splitflap - > flapQueue = = NULL ) {
if ( splitflap - > flapQueue = = NULL ) {
McuLog_error ( " Flap queue creation failed for Splitflap <%i> " , id ) ;
McuLog_error ( " Flap queue creation failed for Splitflap <%i> " , splitflap - > id ) ;
for ( ; ; ) { }
for ( ; ; ) { }
}
}
// if yes: add queue to registry
// if yes: add queue to registry
@ -88,7 +86,7 @@ SF_Handle_t SF_Init(SF_Config_t* instance, int id){
// check if queue was created
// check if queue was created
if ( splitflap - > ongoingMoveMutex = = NULL ) {
if ( splitflap - > ongoingMoveMutex = = NULL ) {
McuLog_error ( " Ongoing Move mutex creation failed for Splitflap <%i> " , id ) ;
McuLog_error ( " Ongoing Move mutex creation failed for Splitflap <%i> " , splitflap - > id ) ;
for ( ; ; ) { }
for ( ; ; ) { }
}
}
// if yes: add ongoing move mutex to registry
// if yes: add ongoing move mutex to registry
@ -103,7 +101,7 @@ SF_Handle_t SF_Init(SF_Config_t* instance, int id){
NULL ) ;
NULL ) ;
if ( res ! = pdPASS ) // task creation not successful?
if ( res ! = pdPASS ) // task creation not successful?
{
{
McuLog_error ( " Creation of task for Splitflap <%i> failed " , id ) ;
McuLog_error ( " Creation of task for Splitflap <%i> failed " , splitflap - > id ) ;
for ( ; ; ) { } // Endless loop
for ( ; ; ) { } // Endless loop
}
}
@ -111,18 +109,34 @@ SF_Handle_t SF_Init(SF_Config_t* instance, int id){
}
}
void SF_Deinit ( SF_Handle_t instance ) {
void SF_Deinit ( SF_Handle_t instance ) {
McuLog_warn ( " Deinitializing Splitflap <%i> " , ( ( SF_t * ) instance ) - > id ) ;
vSemaphoreDelete ( ( ( SF_t * ) instance ) - > ongoingMoveMutex ) ;
vSemaphoreDelete ( ( ( SF_t * ) instance ) - > ongoingMoveMutex ) ;
vQueueDelete ( ( ( SF_t * ) instance ) - > flapQueue ) ;
( ( SF_t * ) instance ) - > initialized = false ;
( ( SF_t * ) instance ) - > initialized = false ;
McuULN2003_DeinitMotor ( ( ( SF_t * ) instance ) - > motor ) ;
McuULN2003_DeinitMotor ( ( ( SF_t * ) instance ) - > motor ) ;
McuGPIO_DeinitGPIO ( ( ( SF_t * ) instance ) - > magSensor ) ;
McuGPIO_DeinitGPIO ( ( ( SF_t * ) instance ) - > magSensor ) ;
# if SPLITFLAP_CONFIG_USE_FREERTOS_HEAP
vPortFree ( ( SF_t * ) instance ) ; // free FreeRTOS heap
# else
free ( ( SF_t * ) instance ) ; // free MCU heap
# endif
}
}
/**********************/
/**********************/
/* PUBLIC FUNCTIONS */
/* PUBLIC FUNCTIONS */
/**********************/
/**********************/
bool SF_MoveMotorToZeroPosition ( SF_Handle_t instance , uint16_t offsetSteps ) {
bool SF_MoveMotorToZeroPosition ( SF_Handle_t instance ) {
int numStepsMoved = 0 ;
int numStepsMoved = 0 ;
uint16_t offsetSteps = 0 ;
// check if the hwId needs an offset init position
for ( int i = 0 ; i < sizeof ( offsetStepsPerHw ) / sizeof ( offsetStepsPerHw [ 0 ] ) ; + + i ) {
if ( offsetStepsPerHw [ i ] [ 0 ] = = ( ( SF_t * ) instance ) - > hwId ) {
offsetSteps = offsetStepsPerHw [ i ] [ 1 ] ;
McuLog_info ( " SF_MoveMotorToZeroPosition found offsetSteps=%i for Splitflap <%i> with hwId=%i " , offsetSteps , ( ( SF_t * ) instance ) - > id , ( ( SF_t * ) instance ) - > hwId ) ;
break ;
}
}
if ( ( ( SF_t * ) instance ) - > initialized ) {
if ( ( ( SF_t * ) instance ) - > initialized ) {
McuLog_warn ( " Tried to initialize motor of Splitflap <%i>, but already initialized => skipping " , ( ( SF_t * ) instance ) - > id ) ;
McuLog_warn ( " Tried to initialize motor of Splitflap <%i>, but already initialized => skipping " , ( ( SF_t * ) instance ) - > id ) ;
@ -158,10 +172,16 @@ bool SF_MoveMotorToZeroPosition(SF_Handle_t instance, uint16_t offsetSteps){
// success if less than one rotation
// success if less than one rotation
( ( SF_t * ) instance ) - > initialized = ( numStepsMoved < SPLITFLAP_STEPS_ONE_ROUND ) ;
( ( SF_t * ) instance ) - > initialized = ( numStepsMoved < SPLITFLAP_STEPS_ONE_ROUND ) ;
McuLog_info ( " SF_MoveMotorToZeroPosition finished for Splitflap <%i>, success=%s " , ( ( SF_t * ) instance ) - > id , ( ( SF_t * ) instance ) - > initialized ? " true " : " false " ) ;
return ( ( SF_t * ) instance ) - > initialized ;
return ( ( SF_t * ) instance ) - > initialized ;
}
}
void SF_MoveMotorToZeroPositionAsync ( SF_Handle_t instance ) {
// TODO TO IMPLEMENT
}
void SF_MoveSteps ( SF_Handle_t instance , uint32_t steps ) {
void SF_MoveSteps ( SF_Handle_t instance , uint32_t steps ) {
if ( ( ( SF_t * ) instance ) - > initialized ) {
if ( ( ( SF_t * ) instance ) - > initialized ) {
if ( OngoingMoveMutex_Lock ( instance ) ) {
if ( OngoingMoveMutex_Lock ( instance ) ) {
@ -233,7 +253,7 @@ static void SF_Task(void *pv){
SF_Handle_t instance = ( SF_Handle_t ) pv ;
SF_Handle_t instance = ( SF_Handle_t ) pv ;
SF_t * splitflap = ( SF_t * ) instance ;
SF_t * splitflap = ( SF_t * ) instance ;
Flap_t nextFlap = " " ;
Flap_t nextFlap = " " ;
McuLog_info ( " Splitflap: Task for Splitflap <%i> started. \n " , splitflap - > id ) ;
McuLog_info ( " Splitflap: Task for Splitflap <%i> started. " , splitflap - > id ) ;
for ( ; ; ) {
for ( ; ; ) {
// delay task
// delay task
@ -256,7 +276,7 @@ static void SF_Task(void *pv){
if ( OngoingMoveMutex_Lock ( instance ) ) {
if ( OngoingMoveMutex_Lock ( instance ) ) {
// now get the queue item
// now get the queue item
if ( xQueueReceive ( splitflap - > flapQueue , & nextFlap , 0 ) ! = pdPASS ) {
if ( xQueueReceive ( splitflap - > flapQueue , & nextFlap , 0 ) ! = pdPASS ) {
/* failed to receive => queue empty but previously an itea m was there? error */
/* failed to receive => queue empty but previously an item was there? error */
McuLog_error ( " Failed to receive Queue item of Splitflap <%i>. " , splitflap - > id ) ;
McuLog_error ( " Failed to receive Queue item of Splitflap <%i>. " , splitflap - > id ) ;
OngoingMoveMutex_Unlock ( instance ) ;
OngoingMoveMutex_Unlock ( instance ) ;
continue ; // ignore & proceed
continue ; // ignore & proceed
@ -266,6 +286,7 @@ static void SF_Task(void *pv){
McuLog_info ( " Splitflap <%i> moving to flap '%c'. " , splitflap - > id , nextFlap [ 0 ] ) ;
McuLog_info ( " Splitflap <%i> moving to flap '%c'. " , splitflap - > id , nextFlap [ 0 ] ) ;
SF_MoveToFlap ( instance , nextFlap ) ;
SF_MoveToFlap ( instance , nextFlap ) ;
McuLog_info ( " Splitflap <%i> move done to flap '%c'. " , splitflap - > id , nextFlap [ 0 ] ) ;
McuLog_info ( " Splitflap <%i> move done to flap '%c'. " , splitflap - > id , nextFlap [ 0 ] ) ;
vTaskDelay ( pdMS_TO_TICKS ( 100 ) ) ; // wait for logger to finish
OngoingMoveMutex_Unlock ( instance ) ;
OngoingMoveMutex_Unlock ( instance ) ;
}
}