P1: Setting TestMode Pin LOW during WiFi Acquisition


I would like to use the Test Mode (pin 33 on P1, port PA8 on STM32F205) Pin’s Timer 1 Channel 1 functionality on the P1. How can I set the Test Mode pin to digital LOW when the P1 is in WiFi acquisition mode (blinking green)? (i.e. which firmware source code file do I need to modify?)

You should be able to do that with this (without firmware hacks)


void setTestMode()
  int bit = 8;
  // reestablish reset state if required
  //GPIOA->MODER  &= ~(0x11 << (2*bit)); // INPUT 
  //GPIOA->OTYPER &= ~(0x1 << bit);      // PUSH-PULL

  // set pin mode and value 
  GPIOA->MODER |= 0x01 << (2*bit);       // set to OUTPUT
  GPIOA->BSRRH  = 0x1  << bit;           // reset pin (default LOW)

A quick primer in low level GPIO programming (in this case only for STM32F0, but the general idea is the same for F2)

There might be a way to do that with Wiring commands, but I’ve not found a pin name for PA8 to use.

Hello ScruffR,

Thank you for the tip on the STARTUP( ) call. Code below compiled for me:


void setTestModePin(){
GPIO_InitTypeDef GPIO_InitStructure;
// Testmode pin is Port PA8 on STM32F205;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_25MHz;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_Init(GPIOA, &GPIO_InitStructure);
// set TestMode Pin LOW
GPIO_ResetBits(GPIOA, GPIO_Pin_8);


but no luck on keeping the TestMode pin low during acquisition.


Could a Particle engineer please point me toward where in the Particle firmware i should set the TestMode pin LOW so that the pin is turned off during WiFi acqusition (blinking green)?


Would a Particle engineer please answer my question on setting the TestMode pin low?

Thank you,

@shm45 It looks like this pin was overlooked as a useable pin, given that it’s name was indicated as TESTMODE it was deemed a reserved pin.

A new pin P1S6 - 30 definition would have to be added here:

A definition here:

And TOTAL_PINS bumped to 31 for P1 here:

That should allow you to use pinMode(P1S6, OUTPUT) and digitalWrite(P1S6, LOW)

If that works well for you, please submit a PR for the change based off of the latest develop or just chime in here that it works well and we can add that pretty easily. Since a TIM1_CH1 is involved, we will want to explore all of the timer based peripherals this may affect as well (PWM, Tone, Servo, Gen purpose timers, etc…)

I added an issue here: https://github.com/spark/firmware/issues/1059


@BDub, thank you for the hal source and header files–your suggestion works on the P1 for

pinMode(P1S6, OUTPUT);

digitalWrite(P1S6, HIGH); digitalWrite(P1S6, LOW);

However, the TestMode/P1S6 pin still turns HIGH during WiFi acquisition (blinking green). Where can I modify the firmware to set the TestMode/P1S6 pin low “from the beginning of time”, to include during WiFi acquisition?


@shm45 great to hear that’s working. Could you try @ScruffR’s suggestion of using STARTUP()


void setTestMode()
    pinMode(P1S6, OUTPUT);
    digitalWrite(P1S6, LOW);

I also missed a spot in the code initialization for P1 pins. This should ensure the pin gets set as an INPUT floating by default. change to pin<=30

@BDub I tried the STARTUP(setTestMode()) method again: no luck. I measured the voltage on the TestMode pin at 1.65V during WiFi acquisition, so doesn’t seem to be going completely HIGH during WiFi acquisition.

I also tried changing the “pin<=29” to “pin<=30” in core_hal_stm32f2xx.c, but that didn’t work either–the TestMode pin still goes to 1.65V during WiFi acquisition.

I also tried inserting the below in core_hal_stm32f2xx.c to force the TestMode/P1S6 to LOW:

#if PLATFORM_ID==8 // Additional pins for P1
for (pin_t pin=24; pin<=29; pin++){
HAL_Pin_Mode(pin, INPUT);
HAL_Pin_Mode(30, OUTPUT);
HAL_GPIO_Write(30, 0);

But no luck either.

Which source file(s) control WiFi acquisition? Maybe there is a pin setting there.


Well it appeared that WICED was re-initializing this pin again since STARTUP() will run right at boot. I looked all over and finally tracked it to some initialization code in WICED that appears to use this pin in it’s alternate function MCO1 as the Main Clock Output 1 which is connected to the LSE (32kHz) oscillator. When you look at the pin on a scope, it’s not 1.65V… it’s a 50% DC squarewave oscillating at 32kHz. WICED uses this pin as a clock for powersave mode. Wi-Fi Powersave Mode is not enabled by default, and when taking over this pin as a GPIO it doesn’t appear to crash the Wi-Fi which is further validation that it’s not currently used. However it’s most definitely hooked up as a standby clock source. For documentation sake, the WICED function called is host_platform_init_wlan_powersave_clock(). You won’t find that in our source, it’s only in WICED source code. To get the functionality you want, we’d have to modify the WICED stack to make this alternate function initialization disabled by default, and only enabled when powersave mode is also enabled. The pin should probably only then be used as a GPIO, and any transients or ESD on this pin could be fatal to the BCM (Wi-Fi chip). So it’s not looking likely that we’d want to enable this pin as a GPIO, but if you can’t live without this pin, and you won’t ever want powersave mode… it seems possible to use it.

1 Like

Thanks very much for all of the additional research, @BDub. We are using the TestMode pin as the control input to the gate of a MOSFET serving as a Low-Side switch to control a relatively high-current LED, so we cannot tolerate the 32kHz square wave during WiFi acquisition–we do not want the high-current LED turned on during WiFi acquisition.

We are pin constrained in our design, which is why we selected the TestMode Pin for use since it hosts Timer1 Channel1.

How is the WICED code integrated into the firmware? Is it pre-compiled as a binary?