 |
 |
View previous topic :: View next topic |
Author |
Message |
benoitstjean
Joined: 30 Oct 2007 Posts: 583 Location: Ottawa, Ontario, Canada
|
PIC24EP512GP806 - PMD register question |
Posted: Mon Sep 29, 2025 11:58 am |
|
|
Device: PIC24EP512GP806
Compiler: 5.026 (all of a sudden my 5.116 version no longer opens for some reason)
Hi guys,
Its been a while since I posted here and this pertains to a piece of code written a long time ago and I'm just curious about the behavior.
I believe this was actually TTelmah who had given it to me.
Basically, my device goes to sleep and the following code is called:
Code: | // Get peripherral disable module snapshot
#byte PMD1 = getenv("byte:PMD1")
#byte PMD2 = getenv("byte:PMD2")
#byte PMD3 = getenv("byte:PMD3")
#byte PMD4 = getenv("byte:PMD4")
#byte PMD5 = getenv("byte:PMD5")
#byte PMD6 = getenv("byte:PMD6")
#byte PMD7 = getenv("byte:PMD7")
fprintf( MONITOR_SERIAL, "\n\rPMD1: 0x%02X -- PMD2: 0x%02X -- PMD3: 0x%02X -- PMD4: 0x%02X -- PMD5: 0x%02X -- PMD6: 0x%02X -- PMD7: 0x%02X", PMD1, PMD2, PMD3, PMD4, PMD5, PMD6, PMD7 );
delay_ms( 1000 );
// Disable all peripheral disable modules
PMD1 = 0xFF;
PMD2 = 0xFF;
PMD3 = 0xFF;
PMD4 = 0xFF;
PMD5 = 0xFF;
PMD6 = 0xFF;
PMD7 = 0xFF;
fprintf( MONITOR_SERIAL, "\n\rPMD1: 0x%02X -- PMD2: 0x%02X -- PMD3: 0x%02X -- PMD4: 0x%02X -- PMD5: 0x%02X -- PMD6: 0x%02X -- PMD7: 0x%02X", PMD1, PMD2, PMD3, PMD4, PMD5, PMD6, PMD7 );
delay_ms( 1000 );
fprintf( MONITOR_SERIAL, "\n\r\n\r*** Unit now sleeping ***" );
// SOME CODE
// Sleep NOW
sleep( SLEEP_FULL );
//----------------------------
// From here, only a UART or external interrupt will wake-up the device.
//----------------------------
// Wake-up - wait a few cycles
delay_cycles( 10 );
// Clear RAM **don't add anything above this line**
#zero_ram
fprintf( MONITOR_SERIAL, "\n\r\n\r*** Unit waking-up ***");
// SOME CODE
fprintf( MONITOR_SERIAL, "\n\rPMD1: 0x%02X -- PMD2: 0x%02X -- PMD3: 0x%02X -- PMD4: 0x%02X -- PMD5: 0x%02X -- PMD6: 0x%02X -- PMD7: 0x%02X", PMD1, PMD2, PMD3, PMD4, PMD5, PMD6, PMD7 );
|
The printout looks like this:
*** Unit now sleeping ***
PMD1: 0x0E -- PMD2: 0x1E -- PMD3: 0x2E -- PMD4: 0x3E -- PMD5: 0x4E -- PMD6: 0x5E -- PMD7: 0x6E
PMD1: 0x0E -- PMD2: 0x1E -- PMD3: 0x2E -- PMD4: 0x3E -- PMD5: 0x4E -- PMD6: 0x5E -- PMD7: 0x6E
*** Unit waking-up ***
PMD1: 0x0E -- PMD2: 0x1E -- PMD3: 0x2E -- PMD4: 0x3E -- PMD5: 0x4E -- PMD6: 0x5E -- PMD7: 0x6E
I've never used much #byte and getenv() other than for power management so my impression was that where it says #byte, it creates that variable then gets the value of each PMD then it sets the value of each to 0xFF.... but clearly, it does not because the printout is the same for both. Then when the MCU wakes-up, the values are still the same but I2C is not working because I guess I2C is still disabled after wake-up because my I2C sensors are not responding.
So what's wrong here and what would be the proper usage/implementation of the PMD code so that everything shuts-down to the lowest current draw possible but when it wakes-up, the peripheral work like if I was to do a cold power-up?
Thanks!
Ben |
|
 |
gaugeguy
Joined: 05 Apr 2011 Posts: 344
|
|
Posted: Mon Sep 29, 2025 12:08 pm |
|
|
Before you initialize the I2C module (or any other module you want to use) you need to turn it back on in the appropriate PMD location. The data sheet will detail which bits disable/enable which peripheral. |
|
 |
benoitstjean
Joined: 30 Oct 2007 Posts: 583 Location: Ottawa, Ontario, Canada
|
|
Posted: Mon Sep 29, 2025 12:14 pm |
|
|
Actually, I may have just realized that I may be confused:
1) I call getenv(), print-out the value;
2) I set all the values to 0xFF then I print them again without calling getenv() and the values are the same;
Unit goes to sleep.
-wait-
Unit wakes-up.
Then I don't call getenv(), I simply print the values again and they are again the same.
So I guess I'm really confused as to how I should be getting/setting values. |
|
 |
gaugeguy
Joined: 05 Apr 2011 Posts: 344
|
|
Posted: Mon Sep 29, 2025 12:26 pm |
|
|
Read section 10 of the data sheet on Peripheral Module Disable. specifically 10.4 and 10.6
Your existing code is also suspect as the PMD registers are 16 bit and your code is treating them as 8-bit. |
|
 |
benoitstjean
Joined: 30 Oct 2007 Posts: 583 Location: Ottawa, Ontario, Canada
|
|
Posted: Mon Sep 29, 2025 12:54 pm |
|
|
Oh yeah, good catch on that one but I'm still trying to wrap my head around the usage of getenv and setting these value registers. This code has been there for years and I never looked back at it....
I changed #byte to #word just to see if it would maybe change something but it does not...
Code: |
#word PMD1 = getenv("SFR:PMD1")
#word PMD2 = getenv("SFR:PMD2")
#word PMD3 = getenv("SFR:PMD3")
#word PMD4 = getenv("SFR:PMD4")
#word PMD5 = getenv("SFR:PMD5")
#word PMD6 = getenv("SFR:PMD6")
#word PMD7 = getenv("SFR:PMD7")
fprintf( MONITOR_SERIAL, "\n\rPMD1: 0x%04X -- PMD2: 0x%04X -- PMD3: 0x%04X -- PMD4: 0x%04X -- PMD5: 0x%04X -- PMD6: 0x%04X -- PMD7: 0x%04X", PMD1, PMD2, PMD3, PMD4, PMD5, PMD6, PMD7 );
|
PMD1: 0x0009 -- PMD2: 0x0019 -- PMD3: 0x0029 -- PMD4: 0x0039 -- PMD5: 0x0049 -- PMD6: 0x0059 -- PMD7: 0x0069
As for the documentation, I have MCP and CCS opened but the help I am seeking is with the CCS functionality of how to get and set the PMD registers and I think we all agree that CCS's documentation is not the greatest. So how would I disable all peripheral registers before going to sleep, how can I confirm that it actually worked and how do I set them when the MCU wakes-up?
Sorry, I'm not a student and I'm not a basement tinkerer, this is for work and I just want to get this out of the way and move-on to something else.
Thank you for your understanding.
Ben |
|
 |
benoitstjean
Joined: 30 Oct 2007 Posts: 583 Location: Ottawa, Ontario, Canada
|
|
Posted: Mon Sep 29, 2025 6:04 pm |
|
|
UPDATE: So I've commented-out all the code pertaining to PMD registers and after waking-up from sleep, I2C is still off because my sensors aren't working contrary to when I do a real power-up.
In all honesty, I have no idea how the use the getenv() function for what I want to do and CCS docs, well, it's CCS docs. It's good for what it's worth.
The problem here is that I know what my end goal is, I just don't know how to achieve it. I've looked at section 10.4 and 10.6 of the PIC manual and that's all nice and fine but it doesn't explain how to do what I want to do using the CCS compiler.
So:
1) How do I use getenv() to get/read the current status of PMD registers (so that I can set each PMD register back to these values upon waking-up);
2) How do I disable all PMD registers to save on power;
3) When the MCU wakes-up, how do I set-back all PMD registers to the same states as they were before going to sleep;
4) How do I confirm that what I've set the PMD registers to has worked (using just an fprintf is fine);
5) How do I force I2C to be up and running after waking-up from sleep, if that has anything to do with the PMD registers;
Thanks again and sorry for the confusion.
Ben |
|
 |
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|