ATmega1284p w/ ILI9341 - Freezes/resets

Go To Last Post
6 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'm trying to set up an ILI9341 tft for a project that won't be using the arduino framework (partially for learning purposes - I already have the ILI9341 working with an arduino and realize that I could just follow the path of least resistance and use an arduino for this).

 

Initially I tried to go towards just making something arduino-esque by taking the working libraries and porting them to something a non-arduino avr could run. Then I realized that a lot of the SPI and TFT display libraries I was using depended on the whole arduino framework and tabled that approach.

 

Now I am attempting to switch to a premade ILI9341 library for AVR that I found here: https://community.atmel.com/proj... (I will be discussing my attempts at using this code from now on).

 

I made a few modifications for my purposes:

1)modified the cs/dc/mosi/miso/sck/ss pins to work for my setup

2) changed the last line of ili9341_spi_init from "PORTB |=(1<<1);//cs off during startup" to "controlport|=(1<<cs);//cs off during startup"

3) made ili9341_putchar_printf return 0 (printf success) at the end since it specifies a return type.

 

Even with these changes the library is a bit busted, for the ATmega1284p at least. I am getting freezes/resets midway through the display_init function currently. The screen will be cleared to black and then the program will freeze/reset some distance through printing the first line ("mode - constant voltage"). The screen clear and printout of characters (color, appearance) is good in and of itself, so I think this means the hardware interface is working well enough.

 

I've had trouble narrowing this down due to the nature of the issue but the SPI write function (ili9341_spi_send) seems to be the root cause of the problem. Sometimes freezes will happen in the wait ("while(!(SPSR & (1<<SPIF)));//wait till the transmission is finished"). The resets seem to be coming from something else entirely though, and I can't account for those.

 

I've tried making modifications to the file but the freezes plus the resets make it hard to get anything stable. I'd like some high-level advice to direct my attempts at fixing this if possible. The problem seems to have characteristics of a stack overflow but I doubt this is the case given the sram size of the micro I'm using. It might also be a random jump out somewhere in memory, but I'm not sure where that would be happening in the code. What other kind of issue could this be?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

If I look at the main.c example of that lib, I see lots of _delay_ms(2).

This implies some timing problem with that lib.

ili9341_setcursor(vsetx,vsety);
_delay_ms(2);
ili9341_settextsize(3);
ili9341_write('9');
_delay_ms(2);
ili9341_write('0');
_delay_ms(2);
ili9341_write('.');
_delay_ms(2);
ili9341_write('4');
_delay_ms(2);
ili9341_write('5');
_delay_ms(2);

Is there some way to read back a busy status of the ILI9341?

 

About the "reset" issue. Is it the AVR, or the ILI that is being reset?

 

However, when I see such long hardcoded delay's with no further comments I tend to move away from such code immediately and go find better quality code.

My own adventures with TFT code hit some snags ( not electronics related, but big non the less).

You may have better success with the RinkyDink's UTFT library.

http://www.rinkydinkelectronics.com/library.php

 

If you search a bit on github hou may also find a better lib.

 

There is also a possibility your TFT does not have the ILI9341 but a similar chip. There are a bunch of those chips and from what I've heard the Ebay / Ali TFT displays are pretty much shipped with a random controller. If I remember well UTFT / Adafruit has some code to read out the display identification. Have you done that with your particular display?

Paul van der Hoeven.
Bunch of old projects with AVR's:
http://www.hoevendesign.com

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I believe the AVR is being reset. I don't have much debug capability here unfortunately (the tft was mainly going to be used for some debug output) so I've just been testing with an led. (Eventually I should get a real debugger...) Anyway, before main entered the while loop, I added an led flash with some delay in and in reset instances I would see the LED flash occurring multiple times.

 

I will look into that other library. Nothing is holding me down to that admittedly poor implementation, but I do wonder why it's failing in the ways it is at all currently. I will switch if the problems persist.

 

I'm fairly certain I actually have an ILI9341 or at least something that behaves identically, because I've set up this tft using the Adafruit ILI9341 library in Arduino previously.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

AVR's being apparently reset "randomly" may have many causes.

 

- Bad decoupling or PCB layout.

- Marginal power supply, Brown Out level set wrongly.

- Run away pointer.

- I/O ports configured wrong, which results in a short and couse the supply voltage to dip.

- Stack overflow.

- Watchdog problems (I believe there is sometimes a fuse to turn it "always on").

- ...

 

About you debugging with a led...

https://www.avrfreaks.net/forum/led-indicator-software-debugging?skey=debugging%20led

Although Logic Analysers are not the all in one wonder, they are very usefull tools for debugging, and for the USD 5 of the hardware cost there is really no excuse to not buy one or two.

Pulseview has also higher level decoders, which can for example flag your data where errors in communication protocols occur ( UART, SPI, I2C, and about 40 others).

 

Empty Set wrote:
I believe the AVR is being reset.

One of the first things I learned about debugging a long time ago was to flash a led, buzzer, uart string, every time the AVR starts up after reset. This removes the guesswork.

Somekind of visual / audible feedback that your AVR is really reset after you press the reset button is also comforting. This will also immediately alert you if for example the reset button itself is faulty.

You should also examine the MCUCSR register (maybe send it to a terminal emulator). It remembers the last cause of a reset.

Paul van der Hoeven.
Bunch of old projects with AVR's:
http://www.hoevendesign.com

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Good call on MCUSR. I was able to narrow the source down to EXTRF - an external reset. This led me to monitor my reset pin, which I had coming from the arduino for ISP purposes, but had been neglecting to wire back to +5V. I'm unsure why the digital output on the arduino was unreliable enough to trigger resets (it would waver +-0.5V which seemed to be enough) but regardless, with this fix made the code seems to work.

 

Since there are these rather large delays and other peculiarities in the code like you mentioned, I did look into the UTFT library a bit. The problem if I were to switch to this library currently seems to be that it wasn't written with a non-arduino AVR in mind. As such, I don't know what implementation path would be sane if I wanted to switch over. Any suggestions on that front?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

A pullup on the reset line does tend to make AVR's more reliable.

Especially if the reset has a long wire connected and/or runs paralell to other traces.

 

Back in 2015 I did a few experiments with UTFT. Did some compiles and burned the result into some AVR's.

I did not find the AVR performance very aceptable for controlling a TFT's and that was the main reason to start looking into faster uC's. Finally settled on STM32 because:

- Supported by UTFT.

- Used in lots of cheap chinese products such as:

- "Blue Pill" board.

- DPS5005 (open source alternative firmware available on github)

- TS100 soldering IRON.

- FX2N PLC clones.

- EEVblog's DMM (121GW).

- DSO138 / DSO150 (These are worth buying just as a regular STM32 development board with TFT. (Cost < USD20) !!! )

 

But all together I did not get very far beyond compiling Adafruits and RinkyDink's demo projects myself.

But compare that with STM32 on youtube.

Just had a quick peek into the code I compiled in 2015.

Although ther is an "Arduino.h" in that project folder, the dependency of UTFT on Arduino is very minimal.

UTFT is a pretty universal lib, and also runs on platforms for which there is no arduino variant available.

I am not sure if "arduino" was ever ported to PIC32 or CC3200.

I'm not sure, but I think AdaFruit's lib is build from the ground up around arduino and arduino compatibility was added to UTFT as an afterthought because of arduino's popularity.

But If I want to pursue this further, I would probably start with looking what kind of libs mbed has for TFT display's.

 

 

This is a copy of a part of the hardware compatibility in "utft.cpp":

/*
  UTFT.cpp - Multi-Platform library support for Color TFT LCD Boards
  Copyright (C)2015 Rinky-Dink Electronics, Henning Karlsen. All right reserved

  This library is the continuation of my ITDB02_Graph, ITDB02_Graph16
  and RGB_GLCD libraries for Arduino and chipKit. As the number of
  supported display modules and controllers started to increase I felt
  it was time to make a single, universal library as it will be much
  easier to maintain in the future.

  Basic functionality of this library was origianlly based on the
  demo-code provided by ITead studio (for the ITDB02 modules) and
  NKC Electronics (for the RGB GLCD module/shield).

  This library supports a number of 8bit, 16bit and serial graphic
  displays, and will work with both Arduino, chipKit boards and select
  TI LaunchPads. For a full list of tested display modules and controllers,
  see the document UTFT_Supported_display_modules_&_controllers.pdf.

  When using 8bit and 16bit display modules there are some
  requirements you must adhere to. These requirements can be found
  in the document UTFT_Requirements.pdf.
  There are no special requirements when using serial displays.

  You can find the latest version of the library at
  http://www.RinkyDinkElectronics.com/

  This library is free software; you can redistribute it and/or
  modify it under the terms of the CC BY-NC-SA 3.0 license.
  Please see the included documents for further information.

  Commercial use of this library requires you to buy a license that
  will allow commercial use. This includes using the library,
  modified or not, as a tool to sell products.

  The license applies to all part of the library including the
  examples and tools supplied with the library.
*/

#include "utft.h"

// Include hardware-specific functions for the correct MCU
#if defined(__AVR__)
	#include <avr/pgmspace.h>
	#include "hardware/avr/HW_AVR.h"
	#if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__)
		#include "hardware/avr/HW_ATmega1280.h"
	#elif defined(__AVR_ATmega328P__)
		#include "hardware/avr/HW_ATmega328P.h"
	#elif defined(__AVR_ATmega32U4__)
		#include "hardware/avr/HW_ATmega32U4.h"
	#elif defined(__AVR_ATmega168__)
		#error "ATmega168 MCUs are not supported because they have too little flash memory!"
	#elif defined(__AVR_ATmega1284P__)
		#include "hardware/avr/HW_ATmega1284P.h"
	#else
		#error "Unsupported AVR MCU!"
	#endif
#elif defined(__PIC32MX__)
  #include "hardware/pic32/HW_PIC32.h"
  #if defined(__32MX320F128H__)
    #pragma message("Compiling for chipKIT UNO32 (PIC32MX320F128H)")
	#include "hardware/pic32/HW_PIC32MX320F128H.h"
  #elif defined(__32MX340F512H__)
    #pragma message("Compiling for chipKIT uC32 (PIC32MX340F512H)")
	#include "hardware/pic32/HW_PIC32MX340F512H.h"
  #elif defined(__32MX795F512L__)
    #pragma message("Compiling for chipKIT MAX32 (PIC32MX795F512L)")
	#include "hardware/pic32/HW_PIC32MX795F512L.h"
  #else
    #error "Unsupported PIC32 MCU!"
  #endif
#elif defined(__arm__)
	#include "hardware/arm/HW_ARM.h"
	#if defined(__SAM3X8E__)
		#pragma message("Compiling for Arduino Due (AT91SAM3X8E)...")
		#include "hardware/arm/HW_SAM3X8E.h"
	#elif defined(__MK20DX128__) || defined(__MK20DX256__)
		#pragma message("Compiling for Teensy 3.x (MK20DX128VLH7 / MK20DX256VLH7)...")
		#include "hardware/arm/HW_MX20DX256.h"
	#elif defined(__CC3200R1M1RGC__)
		#pragma message("Compiling for TI CC3200 LaunchPad...")
		#include "hardware/arm/HW_CC3200.h"
	#else
		#error "Unsupported ARM MCU!"
	#endif
#endif

 

 

 

 

 

 

Paul van der Hoeven.
Bunch of old projects with AVR's:
http://www.hoevendesign.com

Last Edited: Tue. May 15, 2018 - 10:57 PM