2 Replies Latest reply on Oct 1, 2019 7:47 AM by KyTr_1955226

    Determining Bootloader interface at runtime?

    KyTr_1955226

      Hi all,

       

      I have a question about bootloader interfaces.  In my current project I want to be able to load over either UART or USB HID interfaces.  I would probably determine the interface in the application, save a value with this choice in NVM, then read it in the bootloader and use the specified interface.  It looks like through "normal" means this isn't really possible, however it looks like I could possibly use the functions from their respective UART_Boot.c/USBFS_Boot.c files, choosing which communications  functions to use based on the selection made in the application.  In simple form, I'm thinking something like this:

       

      static cystatus Bootloader_WritePacket(uint8 status, uint8 buffer[], uint16 size) CYSMALL \                                       
      {
          uint16 CYDATA checksum;
      
          /* Start of packet. */
          /*These indeces may also need changing depending on interface?*/
          buffer[Bootloader_SOP_ADDR]      = Bootloader_SOP;
          buffer[Bootloader_CMD_ADDR]      = status;
          buffer[Bootloader_SIZE_ADDR]     = LO8(size);
          buffer[Bootloader_SIZE_ADDR + 1u] = HI8(size);
      
          /* Compute checksum. */
          checksum = Bootloader_CalcPacketChecksum(buffer, size + Bootloader_DATA_ADDR);
      
          buffer[Bootloader_CHK_ADDR(size)]     = LO8(checksum);
          buffer[Bootloader_CHK_ADDR(1u + size)] = HI8(checksum);
          buffer[Bootloader_EOP_ADDR(size)]     = Bootloader_EOP;
      
          /* Start packet transmit. */
          /*Bootl_HID would be read from NVM upon entering bootloader*/
          if (Bootl_HID){
              return(USBFS_CyBtldrCommWrite(buffer, size + Bootloader_MIN_PKT_SIZE, &size, 150u));
          } else {
              return(PC_UART_CyBtldrCommWrite(buffer, size + Bootloader_MIN_PKT_SIZE, &size, 150u));
          }
      }
      

       

      Some tweaking would obviously be needed, determining if things like the addresses in the buffer will need to change, and making sure #ifdefs aren't removing stuff I would need for both interfaces, but I feel like this would be doable.

       

      However surely there's a reason why we aren't just given the option to do this out of the box, so I'm curious as to what that might be.  Basically, is there a good reason why I SHOULDN'T try something like this?  Is it just a case of it would be too difficult to automatically generate code to use two or more arbitrary interfaces so it's not gui-configurable?

       

      Thanks in advance for the tips!

        • 1. Re: Determining Bootloader interface at runtime?
          GeonaP_26

          Bootloader GUI does not support multiple communications straight away. Instead bootloader component provides Custom interface option to customize bootloader designs. Once this feature is selected in bootloader component configuration window, user needs to define five bootloader functions i.e., CyBtldrCommStart, CyBtldrCommStop, CyBtldrCommReset, CyBtldrCommWrite and CyBtldrCommRead. For your application, you can select the Custom interface option and select the communication component dependent API depending upon the Bootl_HID variable. An example is appended for your reference. For more details regarding bootloader functions, please refer to section: 10. Adding Bootloader Support (Advanced) of PSoC Creator Component Author Guide.

           

          void CyBtldrCommStart(void)
          {
               if(Bootl_HID)
               {
                    USBFS_CyBtldrCommStart();
               }
          
               else
               {
                    PC_UART_CyBtldrCommStart();   
               }
          }
          }
          
          1 of 1 people found this helpful
          • 2. Re: Determining Bootloader interface at runtime?
            KyTr_1955226

            Thanks for the input!

            I'll do exactly that.