cancel
Showing results for 
Search instead for 
Did you mean: 

PSoC 6 MCU

StNu_1610991
Contributor

The CY8CPROTO-063-BLE board is being used with hibernate and periodic alarms to save system power.  The RTC is producing the expected alarms and the hibernate control is working properly.  There is an external PMIC with an enable input to turn it on and off to generate the 3.3V input for the VDD .  A supercap is attached to VBACKUP  and R29 is removed on the board.  When the unit is also powered from the KipProg3 adapter (via VTARG) it works as intended, hibernating and waking up periodically.  However, When the KitProg3 is unpowered and the external power is only applied into the PMIC, it never gets out of hibernation.

The problem is that pin P0.5 is not being controlled by the hibernate logic as needed.  The PMIC enable (active high) is pulled high by a weak pull-up resistor for when the PSoC 6 is not yet powered or not yet in control ( P0.5 assumed high impedance).  When hibernate mode is started, P0.5 should be pulled low by the PmicEnableOutput and when it goes out of hibernate, it should be pulled high to turn the external PMIC on.   This is not happening.

In response to the forum question "PSoC 6 PMIC Control deep sleep best practise", GaneshD_41 replied suggesting control that is built into the following code:

Cy_SysPm_SetHibWakeupSource( CY_SYSPM_HIBALARM // Wake-up source for RTC alarm

                                                         | CY_SYSPM_HIBPIN1_LOW // Wake-up source for Pin1 input low

                                                         );

  Cy_SysPm_PmicUnlock();                          // Unlock in case locked

//NU   Cy_SysPm_PmicEnable();                // enable Pmic control

  Cy_SysPm_PmicEnableOutput();                // enable P0.5 output control

  Cy_SysPm_PmicLock();                          // Lock again but why?

// Configure the PMIC controller output pin to be active logic low

// after the PMIC is disabled.

//     Note: I do not understand the above comment

  Cy_GPIO_SetDrivemode(P0_5_PORT, P0_5_PIN, CY_GPIO_DM_STRONG_IN_OFF);      //  What does this do?

  Cy_GPIO_Clr(P0_5_PORT, P0_5_PIN);                                                                                 // What does this do?

  if ( Cy_SysPm_PmicIsOutputEnabled() )                // It was just enabled above; so why check?

    {

    Cy_SysPm_PmicUnlock();

    Cy_SysPm_PmicDisable(CY_SYSPM_PMIC_POLARITY_LOW);           // what does this do?

    }

// Prepare the device for system Hibernate

  if ( Cy_SysPm_SystemEnterHibernate() != CY_SYSPM_SUCCESS )

    {

        /* System did not enter Hibernate mode because a registered

        *  Hibernate "check ready" callback returned a "not success" status

        */

    printf(" Hibernate failed\r\n\n");

    Cy_SysLib_Delay(1000); // wait for output

    failed= 1;

    }

The above code was put into the project; yet P0.5 still does not have any output; it always stays low.

Are there any suggestions as to properly controlling the P0.5 pin while going into and out of hibernation?

9 Replies
StNu_1610991
Contributor

It has been a week now and there has not been a reply.  It seems that trying to control the PSoC 6 power via the P0.5 pin may be a catch 22 situation.  It would be nice for a Cypress expert to either say that doing so is not possible or to provide code with which it can be done.

Attached is a Creator 4.3 project which is being used for testing.  It is based on the RC Daily Alarm example.

The following is a reply I sent earlier to clarify the problem.

More information on the problem:

The startup of the main_cm4.c program has the following code:

  was_in_hib= 0;

  reset_reason= Cy_SysLib_GetResetReason();

  if ( reset_reason & CY_SYSLIB_RESET_HIB_WAKEUP )

    {

    was_in_hib= 1;

    }

  if ( Cy_SysPm_GetIoFreezeStatus() )

    {

    Cy_SysPm_IoUnfreeze();

    }

  #ifdef INC_supercap

  Cy_SysPm_BackupSuperCapCharge(CY_SYSPM_SC_CHARGE_ENABLE);

  #endif // ifdef INC_supercap

When the unit is also powered from VTARG, p0.5 is pulled high until hibernate is entered again.  However, I found that if the IoUnfeeze lines were commented out, p0.5 is no longer pulled high.  This says that the pull-up is happening after the PSoC 6 again receives power at VDD.  But, it should be happening BEFORE power is applied to VDD.  To experiment, the output from the supercap was pulled down with an extra resistive load.  The height of the p0.5 pull-up was then reduced.  This verifies that p0.5 is being powered by the back up domain (VBACKUP).  So, why is p0.5 not pulled up before VDD receives power?

There must be some register setting to control this.

0 Likes
ErJo_3974796
New Contributor

Does someone have a temporary solution to the P0.5 pin control problem until we hear from a Cypress expert?

0 Likes
DheerajK_81
Moderator
Moderator

You mentioned that PMIC_EN is pulled high by a weak pull-up resistor when the PSoC6 is not powered. So, I hope you have loaded R44 and R45 resistors, since you haven't mentioned it. You only mentioned the removal of R29 resistor.

pmic.PNG

Once these resistors are loaded, you should see the necessary pull-up when P0_5 is at high impedance.

pastedImage_2.png

Let me know if this resolves your issue

Regards,

Dheeraj

0 Likes
StNu_1610991
Contributor

Hi Dheeraj:

Thanks for the reply.

In our systems, the PMIC is off the 63-BLE board on an adapter board.  The equivalent of R44 is loaded with a 0 ohm resistor and the equivalent of R46 is a 100K resistor.  Vin is a 7.2 V battery.

From the documentation, I had assumed that the P0.5 output was in strong drive mode when driven by the PMIC controller in the backup domain.  The need for a pull-up was not mentioned.

I will add a 10K pull-up to VBACKUP (R45).  However, this seems a pretty hefty load on the supercap and will limit the hibernate time.  Can this be increased to 100K to reduce the current draw?

Steve

0 Likes
StNu_1610991
Contributor

Modified response to Dheeraj:

Sorry, that is not the right solution.

Even though R45 was not loaded, R46 (using a 100K resistor) was also acting as a pull-up since R44 had a 0 ohm resistor installed.

Therefore if the PMIC controller in the backup domain would have released P0.5 from ground, p0.5 would have gone high.   This does happen properly when the power is first applied since p0.5 is then high impedance.

I am pretty sure that the solution has something to do with proper register settings and the sequence of instructions used now is not the correct one.  Did you get a chance to try the project which I attached to a previous response?

Why are the response always marked as "Correct Answer" even when they are not?

Steve

0 Likes
DheerajK_81
Moderator
Moderator

Hello Steve,

I, unfortunately, cannot test the code as I do not have the setup to make any hardware modifications to the kit I have. 

I went through your code and this is what you have: 

 

  Cy_SysPm_SetHibWakeupSource( CY_SYSPM_HIBALARM	// Wake-up source for RTC alarm | CY_SYSPM_HIBPIN1_LOW	// Wake-up source for Pin1 input low 
); 

 

Note that here, you are setting the device to wake up from hibernate either when there is a RTC alarm or when Pin1 (P0_4) goes low. So basically, apart from the alarm waking up the device, you can wake up the device from hibernate by pressing the switch P0_4. 

The reason I bring this up is because the same switch P0_4 has an additional functionality of being the PMIC_Wakeup_In pin that can be used to wakeup the PMIC. If you look at the switch, it is pulled-up using R33. When pressed it provides an active low input to the PMIC. 

Now PMIC is turned on when it gets an active HIGH input from the PMIC_Wakeup_In pin. So, by default, you have the PMIC set to always enabled because PMIC_Wakeup_In logic from the switch is always HIGH. SW2 should be externally pulled down to ground to use PMIC control. Moreover, when the switch is pressed, the active high logic should push P0.4 to the VBACKUP supply. However, the kit is configured by default to use active-low logic. 

So make sure you are taking care of this. You can set the hibernate wakeup source to be CY_SYSPM_HIBPIN1_HIGH after the rework of this switch. 

 

Cy_SysPm_PmicUnlock(); // Unlock in case locked
//NU Cy_SysPm_PmicEnable(); // enable Pmic control; not needed
Cy_SysPm_PmicEnableOutput(); // enable P0.5 output control
Cy_SysPm_PmicLock(); // Lock again but why?

 

Next you need to call the functions in the following order, the order you have doesn't seem to call PMIC_Enable. 

Cy_SysPm_PmicLock();

You don't need to call Cy_SysPm_PMICEnableOutput again, as CySysPm_PMIC_Enable already does that. 

Also, you have the following line of code:
if ( Cy_SysPm_PmicIsOutputEnabled())
{
    Cy_SysPm_PmicUnlock();
    Cy_SysPm_PmicDisable(CY_SYSPM_PMIC_POLARITY_LOW);	// what does this do?
}​

So basically what these lines do is they unlock the PMIC so that it can be modified. You have the option to disable the PMIC controller so that it can be enabled only when the polarity of the PMIC_Wakeup_In matches the polarity given. You can find this information in the PDL Reference Guide, Register TRM as shown below:

DheerajK_81_0-1610560010001.png

 



So the line Cy_SysPm_PmicDisable(CY_SYSPM_PMIC_POLARITY_LOW) is actually not supported by hardware. PMIC can only be enabled on active HIGH logic and hence this function should be modified to:
Cy_SysPm_PmicDisable(CY_SYSPM_PMIC_POLARITY_HIGH);

This also aligns with the switch logic we talked about earlier. Once the switch SW2 is reworked to be active HIGH, only when the switch is pressed, the PMIC will be enabled. 

I have made the modifications to your code and attached the file. Please run the code and let me know if it works with these changes. I cannot test it on my side. 

You mentioned the responses are always marked Correct Answer in the community. Please let me know which thread of yours had this problem and we will make sure this doesn't happen 🙂

Regards,
Dheeraj

 
0 Likes
StNu_1610991
Contributor

Hi Dheeraj:

Thanks for the response.  I will try your modifications when I get a chance and let let you know the results.

Steve

 

0 Likes
StNu_1610991
Contributor

Hi Dheeraj:

Close but no cigar!

I finally had time to look into the problem again.  I incorporated your suggestions and tried many variations.  But, I could not get it to control the P0.5 pin properly for controlling the external PMIC.  It is doing the hibernating OK but when the alarm ends the hibernate, it does not set the P0.5 pin high as it is supposed to.

Attached is a bundle of a "hib_to_alarm" project with changes to the original.  In the original, SW2 was also being used to end hibernation.  But, as you mentioned that is not compatible with the 063-BLE board so it was removed from the project.  Just getting the P0.5 control would be good enough.

If you or someone has ideas as to what to change, I would appreciate a response.

Until there is a solution, our project will have to live with keeping the external PMIC on all the time and using hibernate without P0.5 control.  

Thanks

Steve

 

0 Likes
DheerajK_81
Moderator
Moderator

Hello Steve,

Please try the following modifications and let me know if it works. I cannot test it on my side.

1. Set the interrupt mask for RTC Alarm for Hibernate Wakeup:

Cy_SysPm_SetHibWakeupSource( CY_SYSPM_HIBALARM );


2. Configure the wakeup out pin P0_5:

Cy_GPIO_SetDrivemode(P0_5_PORT, P0_5_PIN, CY_GPIO_DM_STRONG_IN_OFF);
Cy_GPIO_Clr(P0_5_PORT, P0_5_PIN);


3. Enable the PMIC and Enable the PMIC Output as well:

Cy_SysPm_PmicUnlock();
Cy_SysPm_PmicEnable();
Cy_SysPm_PmicEnableOutput();
Cy_SysPm_PmicLock();	


4. Enter Hibernate

Cy_SysPm_SystemEnterHibernate()


The sequence is important. Now, when the RTC Alarm interrupt occurs, you should be seeing the P0_5 being driven by the PMIC Controller.  

Let me know your observations.

Regards,
Dheeraj

0 Likes
Top labels