Page 1 of 1

u8g2 ported to ChibiOS first draft - working

Posted: Fri Jan 19, 2018 12:23 pm
by robert_o
Hardware SPI is working,
Parallel is not tested,
I2C is not implemented.
Read the readme.
Tested with STM32 Nucleo 401.
Please test and give feedback.
I started here: https://github.com/olikraus/u8g2/wiki/Porting-to-new-MCU-platform.
Basically i made three files: ch_hal.c and ch_hal.h. In these files there are two functions:
uint8_t u8g2_ch_spi_byte_cb(u8x8_t *u8x8, uint8_t msg, uint8_t arg_int, void *arg_ptr);
which handles all the SPI stuff including CS line,
uint8_t u8g2_ch_gpio_and_delay_cb(u8x8_t *u8x8, uint8_t msg, uint8_t arg_int, void *arg_ptr);
where all initialisation takes place and all the delays are and the u8g2.mk Makefile.
Tested Displays:
Nokia 5110 - SPI
ST7920 - SPI
have fun.

Re: u8g2 ported to ChibiOS first draft - working

Posted: Mon Jan 22, 2018 10:33 am
by robert_o
UPDATE:
Parallel 8-bit is also working.
Tested Displays:
T6963 Parallel,
ST7920 over SPI,
Nokia5110 over SPI.
Download the u8g2 sources from https://github.com/olikraus/u8g2 and copy the files from the csrc folder into chibios176\u8g2\src folder.
Also copy ch_hal.c/h into chibios176\u8g2\src.
Finally copy u8g2.mk into chibios176\u8g2.

Re: u8g2 ported to ChibiOS first draft - working

Posted: Mon Jan 22, 2018 11:33 am
by Giovanni
Just a note from me, about delays.

Sleep resolution depends on settings in chconf.h, the chThdSleepMicroseconds() will round up the interval to the real resolution. You may use chSysPolledDelayX() for small delays, it is very accurate being based on an HW timer. It is not present on Cortex-M0 platforms however.

Another option is to use gptPolledDelays() which is an HAL service and always available. The resolution depends on the timer setup.

Giovanni

Re: u8g2 ported to ChibiOS first draft - working

Posted: Mon Jan 22, 2018 4:14 pm
by robert_o
I am trying with gptPolledDelays(), but i need one nanosecond resolution which is not possible. I came up with some macros but i need t do some testing.

For now i have in ch_hal.h:

Code: Select all

#define F_TIM 72 //in MHz! One Tic @ 72MHz is 13.8ns
#define GPTIM GPTD4

and in ch_hal.c:

Code: Select all

#define TICS_P100 ((F_TIM/10)+1) //Tics per 100ns - rounding up
#define TIC        ((1000/F_TIM)+1) //one tic in ns
static const GPTConfig gptXcfg = { //Timer for polled delay needs 1ns resolution
    F_TIM*1000000,
    NULL,
    0,
    0
};
//############################
      case U8X8_MSG_DELAY_NANO:           // delay arg_int * 1 nano second
        //chprintf((BaseSequentialStream *)&SD2, "Delay nano: \r\n"); //DEBUG
        if (arg_int > TIC){
          gptPolledDelay(&GPTIM, arg_int/TIC);
        }
        gptPolledDelay(&GPTIM, 1);
        break;
      case U8X8_MSG_DELAY_100NANO:        // delay arg_int * 100 nano seconds
        gptPolledDelay(&GPTIM, arg_int * TICS_P100);
        break;

Re: u8g2 ported to ChibiOS first draft - working

Posted: Mon Jan 22, 2018 4:46 pm
by Polux
Hi,

Just my 2 cents: Nanosecond resolution ???' :shock:

How is this handled on Arduino boards at 16MHz, or even 8MHz ???? :roll:

Angelo

Re: u8g2 ported to ChibiOS first draft - working

Posted: Mon Jan 22, 2018 5:06 pm
by robert_o
Yes, i know. On Arduino nop's are used and timed to get the desired timings. For example the E-cycle needs about 5ns minimum. If it is more, the picture is just slower renewed. For one display and one controller nop's are fine, but to be independent of hardware the timing needs to be exact.

Re: u8g2 ported to ChibiOS first draft - working

Posted: Wed Jan 24, 2018 4:35 pm
by robert_o
Version 0.3 is ready for testing.
Added polled delay,
tested KS0108 Display (8-bit parallel).
The timing of the KS0108 is way off! Datasheet says 450ns - in reality 2.8us are needed. I made a hack because the u8g2 lib has only 8bit for timings. I guess it wasn't a problem because slower micros need that time anyway or a few nop's are added. I made a compiler warning for KS0108 dislays to be aware of the timing problem.

Re: u8g2 ported to ChibiOS first draft - working

Posted: Thu Jan 25, 2018 7:18 am
by wurstnase
Instead of F_TIM you could use STM32_SYSCLK or probably the one for the timer, when it is different. I guess there is somewhere a macro for it.

I'm now doing it like this

Code: Select all

#define fsmc_time_ns2i(ns) \
  ((((ns) * 1000) * (STM32_SYSCLK / 1000000) / 1000000) + 1)

#define fsmc_delay(ns) \
  gptPolledDelay(&GPTD4, fsmc_time_ns2i(ns))

Re: u8g2 ported to ChibiOS first draft - working

Posted: Thu Jan 25, 2018 1:38 pm
by wurstnase
Another idea is to use the continuous mode and reset the counter by yourself.
This could make the timer more accurate.

e.g.

Code: Select all

void init_somewhere(void) {
  /* check your timer. this can be 16bit or 32bit */
  gptStartContinuous(&GPTD4, 0xFF);
}

void doint_things(void) {
  gptGetCounterX(&GPTD4) = 0;
  timing_critical_stuff(); //done in e.g. ~10 ticks

  /* timing stuff done in 10 ticks. We want to wait 100ns */
  while(gptGetCounterX(&GPTD4) <= (10 + GPTD4_TIME_NS2I(100)));

  go_ahead();
}


In this case I found the specific clock frequency. It can be found in GPTDx->clock.

Re: u8g2 ported to ChibiOS first draft - working

Posted: Sat Jan 27, 2018 8:12 am
by robert_o
Thank you for your suggestions. I think until there is some feedback from somebody who actually needs this and the timing problem with ks0108 display is addressed from the u8g2 developer i won't change the code again. Furthermore are this small patches, easily added. The "framework" is functional and should help anybody getting started quickly.