defragster
Senior Member+
I never tried that, I could with my resume code with 2 line comments, the cpu would return to normal on power up
// if we need faster than the crystal, turn on the PLL
#if defined(__MK66FX1M0__)
#if F_CPU > 120000000
// SMC_PMCTRL = SMC_PMCTRL_RUNM(3); // enter HSRUN mode
// while (SMC_PMSTAT != SMC_PMSTAT_HSRUN) ; // wait for HSRUN
#endif
__disable_irq( );
SMC_PMCTRL = SMC_PMCTRL_RUNM(0); // exit HSRUN mode
while (SMC_PMSTAT == SMC_PMSTAT_HSRUN) ; // wait for !HSRUN
__enable_irq( );
__disable_irq( );
SMC_PMCTRL = SMC_PMCTRL_RUNM(3); // enter HSRUN mode
while (SMC_PMSTAT != SMC_PMSTAT_HSRUN) ; // wait for HSRUN
__enable_irq( );
if (DropState ) { // TODO - do we want to see that we are in HSRUN - we should be per F.M. spec
__disable_irq( ); [B]// Turn off interrupts for the DURATION ???[/B]
SMC_PMCTRL = SMC_PMCTRL_RUNM(0); // exit HSRUN mode
while (SMC_PMSTAT == SMC_PMSTAT_HSRUN) ; // wait for !HSRUN
}
else {
SMC_PMCTRL = SMC_PMCTRL_RUNM(3); // enter HSRUN mode
while (SMC_PMSTAT != SMC_PMSTAT_HSRUN) ; // wait for HSRUN
__enable_irq( ); [B]// Restore interrupts only when HSRUN restored[/B]
}
else {
SMC_PMCTRL = SMC_PMCTRL_RUNM(3); // enter HSRUN mode
while (SMC_PMSTAT != SMC_PMSTAT_HSRUN) ; // wait for HSRUN
delay(10);
__enable_irq( ); // Restore interrupts only when HSRUN restored
}
// HSRUN DROP and RESTORE EEPROM WRITE :: https://forum.pjrc.com/threads/36808-EEPROM-writing-on-T_3-6-in-HSRUN-mode?p=115314&viewfull=1#post115314
#include <EEPROM.h>
[B]// ------------------- COPY THIS TO YOUR CODE \/ \/ \/ \/ \/ \/ \/ \/ \/ \/
uint8_t waitHSRUN = 4;
uint8_t DropHSRUN( uint8_t DropState ) {
if (DropState) {
Serial.print ("\n ----- HSRUN drop ... "); // BUGBUG DEBUG
Serial.flush(); // make sure nothing queued to send
delay(120); // USB needs time to complete
}
if (DropState ) { // TODO - Compile time was HSRUN - is it now?
__disable_irq( ); // Turn off interrupts for the DURATION !!!!
SMC_PMCTRL = SMC_PMCTRL_RUNM(0); // exit HSRUN mode
while (SMC_PMSTAT == SMC_PMSTAT_HSRUN) ; // wait for !HSRUN
}
else {
SMC_PMCTRL = SMC_PMCTRL_RUNM(3); // enter HSRUN mode
while (SMC_PMSTAT != SMC_PMSTAT_HSRUN) delay(1); // wait for HSRUN
delay(waitHSRUN);
__enable_irq( ); // Restore interrupts only when HSRUN restored
}
if ( !DropState ) {
delay(100); // Allow USB a pause
Serial.print(" ... HSRUN raised +++++ @"); Serial.println(waitHSRUN); // BUGBUG DEBUG
}
return DropState; // macro needs 1 on drop call and 0 on raise call to process
}
#define TYPE uint8_t
#if F_CPU > 120000000 && defined(__MK66FX1M0__)
#define HSRUN_DROP_BLOCK( ) for ( TYPE __ToDo = DropHSRUN( 1 ); __ToDo; __ToDo = DropHSRUN( 0 ) )
#else
#define HSRUN_DROP_BLOCK( ) for ( TYPE __ToDo = 1; __ToDo; __ToDo = 0 )
#endif
// ------------------- COPY THIS TO YOUR CODE /\ /\ /\ /\ /\ /\ /\ /\ /\ /\ /\
[/B]
// thanks stevech :: https://forum.pjrc.com/threads/24304-_reboot_Teensyduino()-vs-_restart_Teensyduino()?p=45253&viewfull=1#post45253
#define CPU_RESTART_ADDR (uint32_t *)0xE000ED0C
#define CPU_RESTART_VAL 0x5FA0004
uint8_t ReducedResetRCB() {
//delay(1); // confirmed no delay needed for EEPROM write to finish
*CPU_RESTART_ADDR = CPU_RESTART_VAL;
delay(1000);
return 0;
}
#define qBlink() (digitalWriteFast(LED_BUILTIN, !digitalReadFast(LED_BUILTIN) ))
String HelpMe = "\n EEPROM Testing: ?:this text, b:test_BLOCK, c:CPUspecs, r:RESET, s:Show_EEtext t:Test1_RESET, w:Text_Write, z:Stop else:echo";
#define WT_FLAG 43
char getText[256];
#define BT_FLAG 42
#define TEXT_ADDR (E2END / 2)
#define TEST_FLAG_ADDR (E2END - 2)
#define BT_INDEX_ADDR (E2END - 1)
const uint16_t BlockSize = 255;
uint8_t TestBlock[ BlockSize ];
byte TestVal = 100; // Change this value to test another value and force write
const uint16_t StartLoc = 3500; // Pick a number with room for 100 bytes in EEPROM :: 0-3899
uint32_t NeedWrite = 0; // Do not force speed change when EEPROM values match, prevents extra CPU_RESTART
void setup() {
pinMode(LED_BUILTIN, OUTPUT);
Serial.begin(38400);
while (!Serial && (millis () <= 8000));
if ( BT_FLAG != EEPROM[TEST_FLAG_ADDR] ) {
CPUspecs(); // Show the current config of processor
Serial.println(HelpMe);
}
if ( WT_FLAG == EEPROM[TEST_FLAG_ADDR] ) {
ShowEEtext();
}
digitalWrite(LED_BUILTIN, HIGH); // turn the LED_BUILTIN on (HIGH is the voltage level)
}
void loop() {
if ( BT_FLAG == EEPROM[TEST_FLAG_ADDR] ) {
// This indicates run through all of EEPROM test was selected
// As long as there is more EEPROM Write the next block and resume test
int ii, jj, aa = 0;
if ( (EEPROM[BT_INDEX_ADDR] * BlockSize) < E2END ) {
AllBlockTest( EEPROM[BT_INDEX_ADDR] );
}
else {
for ( ii = 0; ii < E2END / BlockSize; ii++) {
for ( jj = 0; jj < BlockSize; jj++) {
if ( ii != EEPROM[ jj + ii * BlockSize] )
aa++;
}
}
Serial.print( "\n # Errors Found in full EEPROM block test ="); Serial.println( aa );
Serial.print( "\n # One more RESET to CLEAR EEPROM block test. . . ");
delay(10);
HSRUN_DROP_BLOCK( ) { // DO NO I/O in this block
EEPROM[BT_INDEX_ADDR] = EEPROM[TEST_FLAG_ADDR] = 255;
}
}
}
}
uint32_t TestFlash1() {
uint32_t ErrCnt = 0;
for ( int ii = StartLoc; ii < StartLoc + 100; ii++ ) {
if ( TestVal != EEPROM[ ii ] ) {
ErrCnt++;
}
}
return (ErrCnt);
}
void AllBlockTest( uint8_t CurrentBlock ) {
int ii;
for ( ii = 0; ii < BlockSize; ii++ )
TestBlock[ ii ] = CurrentBlock;
Serial.print( "EEPROM block test BLOCK ="); Serial.println( CurrentBlock );
HSRUN_DROP_BLOCK( ) { // DO NO I/O in this block
EEPROM.put(CurrentBlock * BlockSize, TestBlock);
EEPROM[TEST_FLAG_ADDR] = BT_FLAG; // Write after to preserve flag on last block
EEPROM[ 7 + (CurrentBlock * BlockSize) ] = 7; // DEBUG_7 - force one error per block
EEPROM[BT_INDEX_ADDR] = CurrentBlock + 1;
}
}
void WriteFlash() {
for ( int ii = StartLoc; ii < StartLoc + 100; ii++ ) {
EEPROM[ ii ] = TestVal;
if (TestVal != EEPROM[ ii ]) {
digitalWrite(LED_BUILTIN, HIGH); delay(50);
digitalWrite(LED_BUILTIN, LOW); delay(25);
}
}
}
void CPUspecs() {
#if defined(__MK66FX1M0__)
Serial.println( "\nCPU is T_3.6");
Serial.print( "F_CPU ="); Serial.println( F_CPU );
#if F_CPU > 120000000
Serial.print( "F_PLL ="); Serial.println( F_PLL );
Serial.print( "F_BUS ="); Serial.println( F_BUS );
Serial.print( "F_MEM ="); Serial.println( F_MEM );
#else
Serial.println( "CPU not in HSRUN");
#endif
#else
Serial.println( "\nCPU is not T_3.6");
#endif
}
void serialEvent() {
qBlink();
while (Serial.available() ) {
char inChar = (char)Serial.read();
switch ( inChar ) {
case '+':
if (waitHSRUN < 10 )
waitHSRUN++;
Serial.print("waitHSRUN="); Serial.println(waitHSRUN);
break;
case '-':
if (waitHSRUN > 0 )
waitHSRUN--;
Serial.print("waitHSRUN="); Serial.println(waitHSRUN);
break;
case '?':
Serial.println(HelpMe);
break;
case 'b':
AllBlockTest( 0 );
break;
case 'c':
CPUspecs();
break;
case 'r':
ReducedResetRCB();
break;
case 's':
ShowEEtext();
break;
case 't':
TestVal++;
Serial.print(" Test write with TestVal="); Serial.println(TestVal);
Serial.flush();
delay(10);
Serial.flush();
DoTestReset();
break;
case 'w':
{ // This set of braces is needed here to compile and contain the macro
int ii = 0;
while ( Serial.available() && ii < 255 ) {
getText[ii] = (char)Serial.read();
if ( '\n' == getText[ii] )
getText[ii] = 0;
ii++;
delayMicroseconds(10); // allow time for full text to arrive through USB
}
getText[ii] = 0;
HSRUN_DROP_BLOCK( ) { // DO NO I/O in this block
for ( int jj = 0; jj <= ii; jj++ )
EEPROM[ TEXT_ADDR + jj ] = getText[jj];
EEPROM[TEST_FLAG_ADDR] = WT_FLAG;
}
} // This set of braces is needed here to compile and contain the macro
ShowEEtext();
break;
case 'z': // ZERO the test in progress byte
Serial.print("\nIn One Second :: Zero test byte and RESET . . .");
Serial.flush();
delay(10);
HSRUN_DROP_BLOCK( ) { // DO NO I/O in this block
EEPROM[TEST_FLAG_ADDR] = 0;
}
break;
default:
Serial.print(inChar);
break;
}
}
}
void DoTestReset(void) {
NeedWrite = TestFlash1(); // Test Read Flash at F_CPU
if ( NeedWrite ) {
HSRUN_DROP_BLOCK( ) { // DO NO I/O in this block
WriteFlash();
}
}
else Serial.println("Hello World - EEPROM values already MATCH! No speed change Write.");
}
void ShowEEtext() {
for ( int ii = TEXT_ADDR; ii < TEXT_ADDR + 256; ii++ ) {
if ( EEPROM[ ii ] ) {
Serial.print( (char)EEPROM[ ii ]);
if ( !((ii - (TEXT_ADDR - 1)) % 61) )
Serial.println( "..." );
}
else
break;
}
Serial.println( "<<<\n ----- Done Showing Write Text. " );
}
In One Second :: Test with TestVal=117
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =0
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =1
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =2
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =3
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =4
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =5
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =6
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =7
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =8
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =9
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =10
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =11
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =12
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =13
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =14
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =15
----- HSRUN drop ... ... HSRUN raised +++++
EEPROM block test BLOCK =16
----- HSRUN drop ... ... HSRUN raised +++++
# Errors Found in full EEPROM block test =15
# One more RESET to CLEAR EEPROM block test. . .
----- HSRUN drop ... ... HSRUN raised +++++
----- HSRUN drop ... ... HSRUN raised +++++
text goes here<<<
----- Done Showing Write Text.
CPU is T_3.6
F_CPU =240000000
F_PLL =240000000
F_BUS =60000000
F_MEM =30000000
while (SMC_PMSTAT != SMC_PMSTAT_HSRUN) delay(1); // wait for HSRUN
delay(waitHSRUN);
__enable_irq( ); // Restore interrupts only when HSRUN restored
----- HSRUN drop ... ... HSRUN raised +++++ @0
Test write with TestVal=130
----- HSRUN drop ... ... HSRUN raised +++++ @0
waitHSRUN=0
output line each 10 seconds:
__ Math loopCount=36421 >>> RTCcompare=10001__ticks=81_=?=_LastRTCval=81__us delta=10000097
__ Math loopCount=36421 // number of passes in loop()
>>> RTCcompare=10001 // this is the elapsedMillis value that times the print
__ticks=81 // this is the BYTE number of ticks seen by the RTC stored in RAM
_=?=_LastRTCval=81 // this is the BYTE number of ticks seen by the RTC stored in EEPROM
__us delta=10000097 // the difference in microseconds since the last 10 second elapsedMillis
__ Math loopCount=36422 >>> RTCcompare=10001__ticks=245_=?=_LastRTCval=245__us delta=9999940
// ----- OPTIONAL BUSY WORK MATH
//TestDouble();
//TestFloat();
[B]#include "EESpeedDHR.h"[/B]
void setup() {
pinMode(LED_BUILTIN, OUTPUT);
Serial.begin(38400);
while (!Serial && (millis () <= 8000));
// put your setup code here, to run once:
[B] setupEESpeedDHR();[/B]
}
void loop() {
// put your main code here, to run repeatedly:
[B] loopEESpeedDHR();[/B]
}
HSRUN_DROP_BLOCK( ) { // DO NO I/O in this block
EEPROM[ RTCTestLoc ] = LastRTCval;
}
[B]__ Math loopCount=34376 >>> RTCcompare=10000_=~=_us delta=10000.09 <> __ticks=206_=?=_LastRTCval=27[/B]
MEANING::
__ Math loopCount=34376 :: How many loop cycles per 10 seconds
>>> RTCcompare=10000 :: should be 10,000 this is the elapsedMillis trigger for output
_=~=_us delta=10000.09 :: should be near 10,000 is the diff in usecs from last RTC interrupt
<> __ticks=206 :: rolling BYTE count of RTC isr() calls [B]**[/B]
_=?=_LastRTCval=27 :: rolling BYTE count of RTC isr() calls as recorded in EEPROM [B]**[/B]
#define CPU_RESET_CYCLECOUNTER do { ARM_DEMCR |= ARM_DEMCR_TRCENA; \
ARM_DWT_CTRL |= ARM_DWT_CTRL_CYCCNTENA; \
ARM_DWT_CYCCNT = 0; } while(0)
volatile int TTcycles;
uint32_t TimeThis( char *szDisplay ) { // call TimeThis( NULL ); then after TimeThis( "text" );
if ( !szDisplay ) {
Serial.print( "TT>>" );
CPU_RESET_CYCLECOUNTER;
}
else {
TTcycles = ARM_DWT_CYCCNT;
Serial.print( szDisplay ); Serial.println( TTcycles / (F_CPU/1000000.0) );
}
return TTcycles;
}