int main(void) { while(1) { resetCoreTimer(); delay(1); printInt(readCoreTimer(), 10 + (10 << 16)); printStr("\r\n"); } }
int main(void) { int delay; int ack, temperature; i2c1_init(TC74_CLK_FREQ); while(1) { //start event i2c1_start(); //send write addr ack = i2c1_send(ADDR_WR); //command (read temp) i2c1_send(RTR); //start event i2c1_start(); //send read addr ack += i2c1_send(ADDR_RD); //printInt10(ack); if (ack != 0) { i2c1_stop(); printStr("An error has ocurred, exiting.\n"); } else { printStr("\nReading temperature: "); temperature = i2c1_receive(I2C_NACK); i2c1_stop(); printInt10(temperature); } //delay 250ms delay = readCoreTimer(); while (readCoreTimer() - delay < 5000000); } return 0; }
int main(void){ unsigned int i = 0; static const unsigned char codes[] = {0x4, 0x2, 0x1, 0x8, 0x10, 0x20, 0x40, 0x8}; TRISB = TRISB & 0xFC00; // Configure TRISB bits 9-0 as Digital Output LATBbits.LATB9 = 1; // Turn On MSDisplay LATBbits.LATB8 = 0; while(1){ resetCoreTimer(); while(readCoreTimer() < 5000000); // Wait 250ms (0.25 sec) LATB = (LATB & 0xFF00) | codes[i]; // Turn On Segment if(++i > 7) i = 0; // Reset Index } return 0; }
int main(void){ initPIC32(); closedLoopControl( false ); setVel2(0, 0); //Stop Engines int start, oldStart = 2; resetCoreTimer(); while(1){ start = startButton(); if(start != oldStart) printf("%10d %d\n",readCoreTimer()/1000, start); oldStart = start; } return 0; }
// Primary worker function for SoftPWM // Is called from within CoreTimer interrupt from wiring.c // Schedules next CoreTimer interrupt based upon what needs to happen next // - another falling edge, or all rising edges, or 1ms CoreTimer interrupt. uint32_t HandlePWMServo(uint32_t CurrentCount) { uint32_t NextTime = 0; // The number of CoreTimer counts into the future when our next edge should occur uint32_t OldPeriod; // The CoreTimer value that caused the ISR to fire static ChanType * CurChanP = NULL; // Pointer to the current channel we're operating on bool DoItAgain = false; // True if we don't have time to leave the ISR and come back in uint32_t NextTimeAcc = CurrentCount; // Records the sum of NextTime values while we stay in the do-while loop // This do-while loop keeps us inside this function as long as there are // edges to process. Only once we have enough time to leave and get back // in for the next edge do we break out of the while loop. do { // If it's time to do the rising edge of all enabled channels- if (RisingEdge) { // Start at the first channel CurChanP = ISRFirstChanP; // Check to see if we have zero channels actually loaded with data if (CurChanP != NULL) { // For each channel that's active, set its pin high while (CurChanP != NULL) { // But only if it is not at %0 if (CurChanP->PWMValue != 0) { // Make an exception for servos - only set them // high when ServoFrameCounter is zero. if ( (CurChanP->IsServo && !ServoFrameCounter) || (!CurChanP->IsServo) ) { *(CurChanP->SetPort) |= CurChanP->Bit; } } // Advance to next channel to check it CurChanP = CurChanP->NextChanP; } // Now start back at the beginning again, for the setting pins low part CurChanP = ISRFirstChanP; // And load up the time for the next (first) edge (falling edge of first channel) NextTime = CurChanP->PWMValue; CurChanP->NextEdgeTime = NextTime; // And mark this time as the beginning of the PWM cycle CurrentTime = 0; // We don't want to do this again until next time RisingEdge = false; } else { // We have no channels actually turned on (enabled or otherwise) // So just load the NextTime with the duraction of the whole PWM cycle and do this // all over again. NextTime = FrameTime; // Don't set SoftPWMRisingEdge to FALSE - leave it TRUE so we just keep doing this // If it's time to swap buffers, then do that here if (InactiveBufferReady) { if (ActiveBuffer) { ActiveBuffer = 0; InactiveBuffer = 1; } else { ActiveBuffer = 1; InactiveBuffer = 0; } // And have ISR use FirstChanP from new active buffer ISRFirstChanP = FirstChanP[ActiveBuffer]; // Tell mainline code we've swapped InactiveBufferReady = false; } } // Count this frame, for the serov pins ServoFrameCounter++; // If we're reached our ServoFrames, limit, then set to zero to mark that // the next frame will have all servos do their rising edges. if (ServoFrameCounter == ServoFrames) { ServoFrameCounter = 0; } } else { // Now we have a falling edge. So we need to set some channel's pin low here. // Always set the next bit low, if the channel is not at 100% // But if it's a servo, always set it low. if (CurChanP->PWMValue < FrameTime || CurChanP->IsServo) { *(CurChanP->ClearPort) |= CurChanP->Bit; } // Record how much time has passed (where are we in the frame) CurrentTime += CurChanP->NextEdgeTime; // Check for more channels that have this same time - but only if we // haven't hit the end of the list yet. (Channels with same edges // will have PWMValues that are the same.) while ( (CurChanP->NextChanP != NULL) && (CurChanP->PWMValue == CurChanP->NextChanP->PWMValue) ) { // Now start working on the next channel in the linked list CurChanP = CurChanP->NextChanP; // Only touch the output if it's not at 100% or if it is a servo // pin (they always go low). if (CurChanP->PWMValue < FrameTime || CurChanP->IsServo) { // Set this bit low *(CurChanP->ClearPort) |= CurChanP->Bit; } } // Have we run out of active channels? if (CurChanP->NextChanP == NULL) { // Yup, so set the next interrupt should happen at the beginning of the next frame NextTime = FrameTime - CurrentTime; // And make all of our channels go high then RisingEdge = true; // If it's time to swap buffers, then do that here if (InactiveBufferReady) { if (ActiveBuffer) { ActiveBuffer = 0; InactiveBuffer = 1; } else { ActiveBuffer = 1; InactiveBuffer = 0; } // And have ISR use FirstChanP from new active buffer ISRFirstChanP = FirstChanP[ActiveBuffer]; // Tell mainline code we've swapped InactiveBufferReady = false; } } else { // Now start working on the next channel in the linked list CurChanP = CurChanP->NextChanP; // Time to compute the NextEdgeTime for the next channel // But only if we're not at the end. if (CurChanP != NULL) { // Compute the next channel's NextEdgeTime based upon our current time and it's PWMValue CurChanP->NextEdgeTime = CurChanP->PWMValue - CurrentTime; } // Just load up the time of the next falling edge NextTime = CurChanP->NextEdgeTime; } } // Each time through the main do-while loop, keep adding in the times between // edges (that would have caused CoreTimer fires if we had left the ISR). Then, // when there is finally time to leave the ISR and come back in to get to the // next edge, schedule the next edge to be the sum of all of those NextTimes. NextTimeAcc += NextTime; // Determine if we have enough time to leave the ISR, return to the mainline // code, and have the CoreTimer ISR fire again to get to our next edge time. // If not, then just stay in the do-while loop (by setting DoItAgain) and // don't leave, and just pretend that we let the CoreTimer fire. // There's a fudge factor added in to where we think we are in time so that // we can copmensate for the number of CoreTimer counts it takes to leave // the ISR. // // Change from v1.0 to v1.1: we now do this calculation by first subtracting // off the OldPeriod from our current CoreTimer value. This subtraction will // eleminate problems where adding NextTimeAcc rolls OldPeriod over, or where // the CoreTimer has rolled over from OldPeriod. if (NextTimeAcc < (readCoreTimer() + EXTRA_ISR_EXIT_CYCLES)) { DoItAgain = true; // We need to wait until the time when we _would_ have actually let the // CoreTimer fire has come and gone. We also put a fuge factor in here to // simulate the number of cycles necessary to get into the ISR and to the // point where the top of the do-while loop starts executing. while(readCoreTimer() < (NextTimeAcc + EXTRA_ISR_ENTRY_CYCLES)) { } } else { DoItAgain = false; } } // We will continue to stay in this loop (which encompases almost the entire function) // until our next edge (PWM or 1ms) is far enough in the future that we can spend the // cycles leaving the ISR and coming back in again. while (DoItAgain); // Return 0 so we don't run the 1ms 'stuff' in the main Core Timer ISR, or 1 // so that we do (this is set only once, to a 1, if we have the 1ms tick // fire off. Since we don't clear RetVal during this ISR, any time we enter // the ISR and have the 1ms tick happen, we will be telling the wiring.c code // to run the 1ms code.) return(NextTimeAcc); }