How to multiplex the GPIO pins of the ADSP-BF706?

There are two bits to select one of four possible connections for each GPIO pin.

How to control those two bits?

  • Hello,

    When a pin is in peripheral mode (not GPIO mode), the PORT_MUX register controls which peripheral takes ownership of a pin. Ports may have multiple, different peripheral functions. Two bits are required to describe every multiplexer on an individual pin-by-pin scheme.

    The Signal Multiplexing table of BF70x processor can be found in its datasheet (Pg:30/116).
    http://www.analog.com/media/en/technical-documentation/data-sheets/adsp-bf700_bf701_bf702_bf703_bf704_bf705_bf706_bf707.pdf
    For example, bit 0 and bit 1 of the PORT_MUX register control the multiplexer of pin 0, bit 2 and bit 3 of PORT_MUX control the multiplexer of pin 1, and so on. The value of any PORT_MUX bit has no effect on the port pins when the associated bit in the PORT_FER register is 0 (selects GPIO mode). Even if a port has only one function, the PORT_MUX register is still present. For single function ports (no
    multiplexing is needed), leave the PORT_MUX bits at 0 (default). For all PORT_MUX bit fields: 00 = default/reset peripheral option, 01 = first alternate peripheral option, 10 = second alternate peripheral option, and 11 = third alternate peripheral option.

    Input tap functionality enables a particular pin to act as input for particular functionality without configuring any of the PORT registers(from reset values). So one can directly feed the input signals without changing any of PORT settings. Input taps lines are implicitly selected when corresponding peripheral input enables are active.

    For example, if you want to enable the SPI0_CLK functionality in the Port C pin 4(PC4), then the PORTC_MUX register should be set to 0x00000100 as it is the first peripheral functionality of PC4.

    For more information about PORT_MUX register and Pin multiplexing, please go through the "General-Purpose Ports (PORT)" chapter in " ADSP-BF70x Blackfin+ Processor Hardware Reference " manual. The manual link as follows: http://www.analog.com/media/en/dsp-documentation/processor-manuals/BF70x_BlackfinProcessorHardwareReference.pdf

    Best Regards,

    Jithul

  • Do you still face any problem with pin multiplexing?

  • If it helps, Here is a function I wrote to provide the control I needed for GPIO or Peripherals connecting to the physical pin.

    #define FOS_PORT_A_FER_REGISTER              0x20040000

    #define FOS_PORT_A_MUX_REGISTER              0x20040030

    #define FOS_PORT_B_FER_REGISTER              0x20040080

    #define FOS_PORT_B_MUX_REGISTER              0x200400B0

    #define FOS_PORT_C_FER_REGISTER              0x20040100

    #define FOS_PORT_C_MUX_REGISTER              0x20040130

    /*******************************************************************************
     *
     *  Function:       fosGpioPinControl
     *
     *  Inputs:         int gpio                 The Pin number to setup  0-47
     *                  int forceAsPeripheral    Flag that indicates GPIO or Peripheral  0 or 1
     *                  u32 peripheralMux        The mux value of the peripherail. 0,1,2 or 3
     *
     *  Outputs:        -1 for error, otherwise 0
     *
     *  Description:    This function will setup the pin to work as a GPIO or as
     *                  a peripheral.  If it is a peripheral, it will set the correct
     *                  mux value to get the correct peripheral out to the pin.
     *                  Pin number 0-15 portA 0:15, 16-31 portB 0:15, 32-47 portC 0:15
     *
     *  Cautions:       None
     *
     ******************************************************************************/
    int fosGpioPinControl(int gpio, int forceAsPeripheral, u32 peripheralMux)
    {
       u32              gpioMask;
       u32              gpioMuxMask;
       volatile u32*    gpioFerRegister;
       volatile u32*    gpioMuxRegister;
       u32              data;
       
       /* There is not any looping going on.  The while loop allows for
        * a convenient way to find the condition and then exit out.
        */
       do
       {
          if (gpio < 16)
          {  /* Port F is 0 to 15 */
             gpioFerRegister = (volatile u32*) FOS_PORT_A_FER_REGISTER;
             gpioMuxRegister = (volatile u32*) FOS_PORT_A_MUX_REGISTER;
             break;
          }
          if (gpio < 32)
          {/* Port G is 16 to 31 */
             gpioFerRegister = (volatile u32*) FOS_PORT_B_FER_REGISTER;
             gpioMuxRegister = (volatile u32*) FOS_PORT_B_MUX_REGISTER;
             gpio -= 16;
             break;
          }
          if (gpio < 48)
          {/* Port H is 32 to 47 */
             gpioFerRegister = (volatile u32*) FOS_PORT_C_FER_REGISTER;
             gpioMuxRegister = (volatile u32*) FOS_PORT_C_MUX_REGISTER;
             gpio -= 32;
             break;
          }
          return -1; /* The gpio value is out of range */
       } while(1); /* End fake while loop */
       
       gpioMask = (0x1 << gpio);
       gpioMuxMask = (0x3 << (gpio * 2));
       peripheralMux &= 0x3;  /* limit the mask to 2 bits */
       peripheralMux = (peripheralMux << (gpio * 2));
       
       if (forceAsPeripheral == 1)
       {
          /* Connect the peripherial to the external pin */
          data = *gpioFerRegister;
          data |= gpioMask;
          *gpioFerRegister =  data;
          asm("ssync;");
          
          /* Calculate and set the requested mux level */
          data = *gpioMuxRegister;
          /* Clear out old mux bits first */
          data &= ~(gpioMuxMask);
          /* Set GPIO pins for the requested mux function */
          data |= peripheralMux;
          *gpioMuxRegister =  data;
          asm("ssync;");
       }
       else
       {
          /* Connect the GPIO functionality to the external pin */
          data = *gpioFerRegister;
          data &= ~(gpioMask);
          *gpioFerRegister =  data;
          asm("ssync;");
       }
       return 0;
    }

  • Thank you for your reply and your follow up.

    I have understood from the previous reply that a certain register in the

    ADSP-BF706 should be set with 16 bits each corresponding to a certain

    definition for the ports to be multiplexed. This setting should be done

    through downloading a 16-bit word to the ADSP-BF706.

    The remaining question is :

    Can this downloading be done from a host computer through USB interface?

    Thank you

    On Tue, Jun 26, 2018 at 5:23 PM gregc <

  • AladdinAssisi wrote:

    Can this downloading be done from a host computer through USB interface?

    What downloading are you talking about?