energia / Energia

Fork of Arduino for the Texas Instruments LaunchPad's
http://energia.nu
Other
795 stars 671 forks source link

fast digital read #355

Closed cosmok82 closed 10 years ago

cosmok82 commented 10 years ago

Hi. I'd like to read raw data on a specific port for a more fast digital input from this port.

My intention is to decode an ir signal with code, but digitalRead(IRpin) (IRpin = a fixed pin) is too much slow.

I inspire my project on this code http://learn.adafruit.com/trinket-gemma-ir-remote-control/using-ir-codes , but I don't know which is the port manipulation, such as IRpin_PIN & _BV(IRpin), in energia for a Stellaris Launchpad.

Do you have any solutions?

rei-vilo commented 10 years ago

For the Stellaris now Tiva C Series, the topic has been discussed and solved based on HWREG on the 43oh and Stellarisiti forums.

cosmok82 commented 10 years ago

For Stellaris Launchpad LM8F120, excuse me.

cosmok82 commented 10 years ago

I answer me by myself. I haven't tested in-depth the code still now, but I think that it work.

On top I include this for the device:

#include "inc/lm4f120h5qr.h"

// IRpin = PB_5;
#define IRpin GPIOPinRead(GPIO_PORTB_BASE, 0x20)

Then in setup() I put this lines:

// setting of PORTB on only pin 5 (0x20), fixed to 2mA (_2MA), with pull-up (_STD)
GPIOPadConfigSet(GPIO_PORTB_BASE, 0x20, GPIO_STRENGTH_2MA, GPIO_PIN_TYPE_STD);

And I used this construction to check the bit "0" and "1" in input on port: while (! IRpin ){ ... } ; while ( IRpin ){ ... }

I think that it's all right :)

cosmok82 commented 10 years ago

rei-vilo I ask your help. This is my code; I applied the rules for a fast reading, but even with these I get an strange/failed reading of port.

You has closed this issue, but could you answer me about?

#include "inc/lm4f120h5qr.h"

// IRpin = PB_5
#define IRpin GPIOPinRead(GPIO_PORTB_BASE, 0x20)

const int MAXPULSE =  5000; // the maximum pulse we'll listen for - 5 milliseconds
const int NUMPULSES =  100; // max IR pulse pairs to sample
const int RESOLUTION =   1; // time between IR measurements

// we will store up to 100 pulse pairs (this is -a lot-)
uint16_t pulses[100][2];   // pair is high and low pulse
uint16_t currentpulse = 0; // index for pulses we're storing
uint32_t irCode = 0;

void setup(void) {

  // setting of PORTB on only pin 5 (0x20), fixed to 2mA (_2MA), with open-drain (_OD)
  GPIOPadConfigSet(GPIO_PORTB_BASE, 0x20, GPIO_STRENGTH_2MA, GPIO_PIN_TYPE_OD);

  Serial.begin(9600);
  Serial.println("Ready to decode IR!");
}

void loop(void) {

  uint16_t numpulse = listenForIR(); // Wait for an IR Code

  // Process the pulses to get a single number representing code
  for (int i = 0; i < 32; i++) {
    irCode = irCode << 1;
    if((pulses[i][0] * RESOLUTION)>0 && (pulses[i][0] * RESOLUTION)<500) {
      // leave the "0" 
    } else {
      irCode++; // add an "1"
    }
  }

  printcode();  // Print IR code to softwareserial

}

void printcode(void) {

  uint16_t half;
  half = irCode >> 16;  // Get first 16 bits of code
  Serial.print(half ^ 0xFFFF, HEX);  // Print upper inverted 16 bits in hex
  Serial.print(' ');
  Serial.println((irCode & 0xFFFF) ^ 0xFFFF, HEX); // Print lower inverted 16 bits in hex
}

uint16_t listenForIR() {  // IR receive code

  currentpulse = 0;
  while (1) {
   unsigned int highpulse, lowpulse;  // temporary storage timing
   highpulse = lowpulse = 0; // start out with no pulse length 

   // read IRpin "1" input
   while ( IRpin ){
      highpulse++; 
      delayMicroseconds(RESOLUTION);
      if (((highpulse >= MAXPULSE) && (currentpulse != 0))|| currentpulse == NUMPULSES) {
        return currentpulse; 
      }
   }
   pulses[currentpulse][0] = highpulse;

   // read IRpin "0" input
   while (! IRpin ){
      lowpulse++; 
      delayMicroseconds(RESOLUTION);
      if (((lowpulse >= MAXPULSE) && (currentpulse != 0))|| currentpulse == NUMPULSES) {
        return currentpulse; 
      }
   }
   pulses[currentpulse][1] = lowpulse;

   currentpulse++;
  }
}
rei-vilo commented 10 years ago

For fast digital reason pin PB_7, we need to

#define LCD_DATAH_PERIPH        SYSCTL_PERIPH_GPIOB
#define LCD_DATAH_BASE          GPIO_PORTB_BASE
#define LCD_DATAH_PINS          GPIO_PIN_7
GPIOPinTypeGPIOInput(LCD_DATAH_BASE, GPIO_PIN_7);
result = HWREG(LCD_DATAH_BASE + GPIO_O_DATA + (LCD_DATAH_PINS << 2));

Hope that helps!