Fredric Rice / Mbed 2 deprecated NextGen-Exerciser

Dependencies:   LCD_DISCO_F429ZI mbed TS_DISCO_F429ZI mbed-os BSP_DISCO_F429ZI

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers NextGen-Exerciser-Modbus.cpp Source File

NextGen-Exerciser-Modbus.cpp

00001 
00002 // ----------------------------------------------------------------------
00003 // NextGen-Exerciser-Modbus.cpp
00004 //
00005 // Fredric L. Rice, May 2019
00006 //
00007 // o A digital output for an LED is instantiated
00008 // o A Serial object is instantiated on Serial-1
00009 // o A thread's mailbox object is instantiated
00010 // o A Thread object is instantiated
00011 // o The serial interface is configured
00012 // o The module's thread is start()ed
00013 //
00014 // The LED is toggled according to timing established by a periodic
00015 // wait() and according to messages pending in the thread's mailbox
00016 //
00017 // The mailbox is checked for any messages that need to go out the
00018 // serial interface, and if there are any, the message is extracted
00019 // from the mailbox and gets sent out the serial interface. If there
00020 // are no messages waiting to go out, a Modbus polling message is
00021 // sent out the serial interface instead.
00022 //
00023 // If there is serial data waiting to be read, the data is collected
00024 // in to a Modbus frame and it gets handled by examining the content
00025 // of the inbound frame.
00026 //
00027 // ----------------------------------------------------------------------
00028 
00029 #include "mbed.h"                       // The mbed operating system
00030 #include "NextGen-Exerciser-Modbus.h"   // Always include ourself
00031 #include "NextGen-Exerciser-Defines.h"  // For defined constants and MACROs
00032 
00033 // ----------------------------------------------------------------------
00034 // Allocate local data storage
00035 //
00036 // ----------------------------------------------------------------------
00037 
00038     static DigitalOut                  st_digitalOutModbusLED(LED1);
00039     static Serial                      st_modbusSerial(PA_9, PA_10);    // TX, RX Serial 1 (This one is working)
00040     static Mail<st_pendingMessage, 16> st_modbusMailbox;
00041     static Thread                      st_threadModbus;
00042     static bool                        b_modbusInitialized = false;
00043     static char                        c_flipFlop = 0;
00044 
00045     static unsigned char               uch_modbusPollFrame[] =
00046     {
00047         0xF7, 0x41, 0x00, 0x00, 0x00, 0x00, 0x00, 0x92, 0xDE
00048     } ;
00049 
00050 // ----------------------------------------------------------------------
00051 // ModbusCheckInbound()
00052 //
00053 // This function will:
00054 //      o Check to see if the serial interface is readable
00055 //      o If there are bytes waiting, the bytes are read and get
00056 //        assembled in to a full Modbus frame.
00057 //      o The inbound message is handled by passing it to a function
00058 //        which examines the content of the inbound message
00059 //
00060 // ----------------------------------------------------------------------
00061 static void ModbusCheckInbound(void)
00062 {
00063     // See if there is inbound serial data
00064     if (st_modbusSerial.readable())
00065     {
00066         
00067     }  
00068 }
00069 
00070 // ----------------------------------------------------------------------
00071 // ModbusCheckOutbound()
00072 //
00073 // This function will:
00074 //      o Get a message from the thread's mailbox, waiting for up to
00075 //        2 milliseconds for a message
00076 //      o If a message is pending, the message is extracted and then
00077 //        gets formatted in to an output Modbus message frame
00078 //      o The newly-formatted Modbus frame gets transmitted out the
00079 //        serial interface
00080 //      o The mailbox message gets released back in to the memory pool
00081 //      o If there was no output message waiting in the mailbox, a
00082 //        Modbus polling message is sent out the serial interface
00083 //
00084 // ----------------------------------------------------------------------
00085 static void ModbusCheckOutbound(void)
00086 {
00087     // Is there an outbound message waiting? Wait up to 2 milliseconds for one
00088     osEvent st_eventResult = st_modbusMailbox.get(2);
00089 
00090     if (st_eventResult.status == osEventMail)
00091     {
00092         // Get a pointer to the message
00093         st_pendingMessage * pst_outFrame = (st_pendingMessage *)st_eventResult.value.p;
00094             
00095         // Format and send the MODBUS frame
00096         
00097         // Finished with the message so release it even if it was not sent
00098         st_modbusMailbox.free(pst_outFrame);
00099     }
00100     else
00101     {
00102         // Send a poll frame
00103         st_modbusSerial.write((uint8_t *)uch_modbusPollFrame, sizeof(uch_modbusPollFrame), NULL);
00104     }
00105 }
00106 
00107 // ----------------------------------------------------------------------
00108 // ModbusThread()
00109 //
00110 // This function will:
00111 //      o Get invoked as a thread under the mbed operating system
00112 //      o Turn ON the lED associated with this module and protocol
00113 //      o Enter in to a forever loop which wakes up ten times a second
00114 //      o Drives the module's LED so that it flashes frim time to time
00115 //        to indicate that the thread is running
00116 //      o Check to ensure that the module has been initialized
00117 //      o If the module is initialized (and it should be) checks to
00118 //        see if there are inbound serial Modbus messages
00119 //      o Checks to see if there are any outbound serial Modbus messages
00120 //
00121 // ----------------------------------------------------------------------
00122 static void ModbusThread(void)
00123 {
00124     char ch_halfSecond = 5;
00125 
00126     // Set the MODBUS LED to ON to indicate that the thread has started
00127     st_digitalOutModbusLED = 1;
00128     
00129     // Enter in to a forever loop 
00130     while (true)
00131     {
00132         // Sleep for one tenth of a second
00133         wait(0.1);
00134         
00135         // Count down the half second timer and see if it expired
00136         if (0 == --ch_halfSecond)
00137         {
00138             // It has expired so restart the half second time
00139             ch_halfSecond = 5;
00140             
00141             // See if we turn on or turn off the LED
00142             if (0 == c_flipFlop)
00143             {
00144                 c_flipFlop = 1;
00145             }
00146             else
00147             {
00148                 c_flipFlop = 0;
00149             }
00150 
00151             st_digitalOutModbusLED = c_flipFlop;
00152         }
00153 
00154         // We check to see if there is inbound or outbound serial traffic 10 times a second
00155         if (TRUE == b_modbusInitialized)
00156         {        
00157             // Check for inbound MODBUS frames
00158             ModbusCheckInbound();
00159         
00160             // See if we need to send outbound MODBUS frames
00161             ModbusCheckOutbound();
00162         }
00163     }
00164 }
00165 
00166 // ----------------------------------------------------------------------
00167 // ModbusInit()
00168 //
00169 // This function will:
00170 //      o Initialize the module protocol's serial interface
00171 //      o Flag the fact that things are initialized
00172 //      o Launch the module's thread
00173 //
00174 // ----------------------------------------------------------------------
00175 void ModbusInit(void)
00176 {
00177     // We configure the CPUM MODBUS serial interface
00178     st_modbusSerial.baud(115200);
00179     st_modbusSerial.format(8, SerialBase::None, 1);
00180 
00181     // Flag the fact that the module has been initialized
00182     b_modbusInitialized = true;
00183     
00184     // Launch the CPUM Modbus thread
00185     st_threadModbus.start(ModbusThread);
00186 }
00187 
00188 // End of file
00189