ILI 9341 Parallel Library

Status
Not open for further replies.
I've narrowed the problem down to the write8 functions in which I set the GPIOC_PSOR and GPIOC_PCOR registers. When I replace these register writes with digitalWrite everything starts working again.
 
I don't think it matters. The big thing is the display looks at the data when the write strobe does the rising...

So for example if I were you I would maybe try it like:
Code:
void write8special(uint8_t c) {

  WR_ACTIVE;
  GPIOC_PSOR = c;
  GPIOC_PCOR = (~c & 0xff);  
  WR_IDLE;
  //GPIOC_PCOR = 0xff;  // probably not needed. 
}
That is it looks like from the timing diagrams, that you might set the write line low, then set the data bits, then bring the write level back high.
Note: I removed the setting the values back to zero as if you do the PCOR_0xff so fast, maybe the display will not react fast enough and will grab the zero value instead.

But again not setup to test this. If I do get interested, I think one of my Adafruit displays does have the parallel pins on it... But so far I am happy with SpI
 
This display protocol is so annoying. I tried your code, and it still doesn't work. The problem is when I set the bits one by one, it works, but when I set them all at once, it doesn't. The thing is if I can get these hardware registers to work with just one write, the library will be extremely fast.
 
This code works:
GPIOC_PDOR |= c & 1;
GPIOC_PDOR |= c & 2;
GPIOC_PDOR |= c & 4;
GPIOC_PDOR |= c & 8;
GPIOC_PDOR |= c & 16;
GPIOC_PDOR |= c & 32;
GPIOC_PDOR |= c & 64;
GPIOC_PDOR |= c & 128;
//TFT_DATA->regs->ODR = ((TFT_DATA->regs->ODR & 0xFF00) | ((c) & 0x00FF));//FF00 is Binary 1111111100000000
//TFT_DATA->regs->ODR = ((TFT_DATA->regs->ODR & 0xFF00) | ((c) & 0x00FF));//FF00 is Binary 1111111100000000


WR_STROBE();


GPIOC_PCOR = (1 << 0);
GPIOC_PCOR = (1 << 1);
GPIOC_PCOR = (1 << 2);
GPIOC_PCOR = (1 << 3);
GPIOC_PCOR = (1 << 4);
GPIOC_PCOR = (1 << 5);
GPIOC_PCOR = (1 << 6);
GPIOC_PCOR = (1 << 7);
 
How about:
Code:
void write8special(uint8_t c) {

  WR_ACTIVE;
  noInterrupts();
  GPIOC_PDOR = (GPIOC_PDOR & 0xffffff00) | c;
  interrupts();
  WR_IDLE;
}
Note: I disabled interrupts around touch PDOR as if you have some other code that touches some other hardware on port_c... They could change the state between the point where you read the data update and write it back out...

Edit: mask was wrong
 
Ok at this point I'm just going to conclude that the ILI9341 can't read when all the bits are put onto the data lines at the same time for some reason.
 
My guess is that the Teensy is running too fast for the display...

That is: if you do the code like I mentioned before, maybe even more simplified:
Code:
void write8special(uint8_t c) {
  digitalWriteFast(TFT_WR, LOW);
   *((volatile uint8_t *)(&GPIOC_PDOR)) = c;
  digitalWriteFast(TFT_WR, HIGH);
}
In this version I removed the disable/enable interrupts and tried to make sure the compiler only did an 8 bit write as the GPIO section of the manuals says that ports support 8 bit, 16 bit and 32 bit...
Note: In this message I replaced your macros with the digitalwrites to make it easier to read. So we are basically doing three register writes.

If I read the ili manual correctly the system needs the signal to be set a minimum of 10ns before the WR pin goes high and stay at that level for 10ns after this point... With logic analyzer I am missing several of the TFT_WR transisitions as you call it real quick in loop, that is:
Code:
...
  for(y=h; y>0; y--) {
    for(x=w; x>0; x--){
      write8special(hi);
      write8special(lo);
    }
The LA is missing all of the transitions between HI/LO byte outputs. But catches the others as the for loop adds some delay... So again the display may be having same issue. So doing one bit at a time adds in time which may be the difference. You might experiment adding a slight delay between output HI to LO. Couple of NOPS? And see if that changes...

Or stick with output a bit at a time, which is what the LiquidCrystal library appears to do... Or simply go to SPI
 
Should I just change the code to:
void write8special(uint8_t c) {
digitalWriteFast(TFT_WR, LOW);
*((volatile uint8_t *)(&GPIOC_PDOR)) = c;
digitalWriteFast(TFT_WR, HIGH);
asm("NOP");
asm("NOP");
asm("NOP");
asm("NOP");
}

For both write8 functions?
 
IT WORKED!! Finally! I have super fast results too!
Here:
ILI9341 Test!
Display Power Mode: 0x9C
MADCTL Mode: 0x48
Pixel Format: 0x5
Image Format: 0x0
Self Diagnostic: 0xC0
Device ID: 0x9341
Benchmark Time (microseconds)
Screen fill 88319
Text 12309
Lines 87538
Horiz/Vert Lines 7062
Rectangles (outline) 4670
Rectangles (filled) 183556
Circles (filled) 35540
Circles (outline) 35868
Triangles (outline) 27423
Triangles (filled) 62862
Rounded rects (outline) 14888
Rounded rects (filled) 200625
Done!
 
Status
Not open for further replies.
Back
Top