Move display functions to own file

This commit is contained in:
Olaf Rempel 2020-01-08 22:55:25 +01:00
parent 6a75a0aec3
commit 49ffbdb579
4 changed files with 284 additions and 115 deletions

206
display.c Normal file
View File

@ -0,0 +1,206 @@
/***************************************************************************
* Copyright (C) 2006 - 2020 by Olaf Rempel *
* razzor AT kopf MINUS tisch DOT de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; version 2 of the License, *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <avr/io.h>
#include "display.h"
#include "target.h"
#if (USE_DISPLAY)
static display_mode_t m_mode = DISPLAY_MODE_OFF;
static char m_buffer[24];
static uint8_t m_buffer_length = 0;
static uint8_t m_buffer_pos = 0;
/* ***********************************************************************
* display_putc
* *********************************************************************** */
static void display_putc(uint8_t pos, char ch)
{
if (ch >= 'a' && ch <= 'z')
{
ch &= ~0x20;
}
PORTD = ((ch & 0x7E) << 1);
PORTC = ((ch & 0x01) << 3) | (3 - (pos & 0x03));
PORTC |= (1<<DISP_WR);
} /* display_putc */
/* ***********************************************************************
* display_put4
* *********************************************************************** */
static void display_put4(const char * p_str)
{
display_putc(0, *p_str++);
display_putc(1, *p_str++);
display_putc(2, *p_str++);
display_putc(3, *p_str++);
} /* display_put4 */
/* ***********************************************************************
* _hexnibble
* *********************************************************************** */
static char _hexnibble(char value)
{
value &= 0x0F;
return (value < 0x0A) ? ('0' + value)
: ('A' + value - 0x0A);
} /* _hexnibble */
/* ***********************************************************************
* display_show_string
* *********************************************************************** */
void display_show_string(const char * p_string, uint8_t append)
{
char * p_dst = m_buffer;
uint8_t pos = 0;
if (append)
{
p_dst += m_buffer_length;
pos = m_buffer_length;
}
while ((pos < sizeof(m_buffer) -1) &&
(*p_string != '\0'))
{
*p_dst++ = *p_string++;
pos++;
}
*p_dst++ = ' ';
m_buffer_length = pos;
m_buffer_pos = 0;
} /* display_show_string */
/* ***********************************************************************
* display_show_hex
* *********************************************************************** */
void display_show_hex(uint8_t value, uint8_t append)
{
char * p_dst = m_buffer;
uint8_t pos = 0;
if (append)
{
p_dst += m_buffer_length;
pos = m_buffer_length;
}
if (pos < (sizeof(m_buffer) -3))
{
*p_dst++ = _hexnibble(value >> 4);
*p_dst++ = _hexnibble(value);
*p_dst++ = ' ';
}
m_buffer_length = pos +2;
m_buffer_pos = 0;
} /* display_show_hex */
/* ***********************************************************************
* display_set_mode
* *********************************************************************** */
void display_set_mode(display_mode_t mode)
{
m_mode = mode;
} /* display_set_mode */
/* ***********************************************************************
* display_update
* *********************************************************************** */
void display_update(void)
{
static uint8_t update_timer;
update_timer++;
switch (m_mode)
{
default:
case DISPLAY_MODE_OFF:
display_put4(" ");
break;
case DISPLAY_MODE_RUN_ANIM:
display_put4("RUN-");
m_mode = DISPLAY_MODE_RUN_ANIM_LOOP;
/* fallthrough */
case DISPLAY_MODE_RUN_ANIM_LOOP:
switch (update_timer & 0x18)
{
case 0x00:
display_putc(3, '-');
break;
case 0x08:
display_putc(3, '\\');
break;
case 0x10:
display_putc(3, '1');
break;
case 0x18:
display_putc(3, '/');
break;
default:
break;
}
break;
case DISPLAY_MODE_STATIC:
display_put4(m_buffer);
break;
case DISPLAY_MODE_SCROLL:
case DISPLAY_MODE_SCROLL_ONCE:
if ((m_buffer_length != 0x00) &&
(!(update_timer & 0x1F))
)
{
display_put4(m_buffer + m_buffer_pos);
if (m_buffer_pos <= (m_buffer_length -3))
{
m_buffer_pos++;
}
else
{
m_buffer_pos = 0x00;
if (m_mode == DISPLAY_MODE_SCROLL_ONCE)
{
m_mode = DISPLAY_MODE_RUN_ANIM;
}
}
}
break;
}
} /* display_update */
#endif /* (USE_DISPLAY) */

26
display.h Normal file
View File

@ -0,0 +1,26 @@
#ifndef DISPLAY_H_
#define DISPLAY_H_
#include <stdint.h>
/* *********************************************************************** */
typedef enum display_mode_e {
DISPLAY_MODE_OFF, /* disable display */
DISPLAY_MODE_RUN_ANIM, /* show RUN animation */
DISPLAY_MODE_RUN_ANIM_LOOP, /* change last char of RUN animation */
DISPLAY_MODE_STATIC, /* show first 4 chars */
DISPLAY_MODE_SCROLL, /* scroll through buffer */
DISPLAY_MODE_SCROLL_ONCE, /* scroll once, then switch to RUN_ANIM */
} display_mode_t;
/* *********************************************************************** */
void display_show_string (const char * p_string, uint8_t append);
void display_show_hex (uint8_t value, uint8_t append);
void display_set_mode (display_mode_t mode);
void display_update (void);
/* *********************************************************************** */
#endif /* DISPLAY_H_ */

164
ispprog.c
View File

@ -23,6 +23,7 @@
#include <string.h>
#include "avrdevice.h"
#include "display.h"
#include "target.h"
#include <util/delay.h>
@ -141,40 +142,6 @@ static uint8_t ser_recv(void)
} /* ser_recv */
#if defined(DISP_WR)
static char disp_text[24];
static uint8_t disp_length = 0;
static uint8_t disp_pos = 0;
static void disp_putc(uint8_t pos, char ch)
{
if (ch >= 'a' && ch <= 'z')
ch &= ~0x20;
PORTD = ((ch & 0x7E) << 1);
PORTC = ((ch & 0x01) << 3) | (3 - (pos & 0x03));
PORTC |= (1<<DISP_WR);
} /* disp_putc */
static void disp_put4(const char *str)
{
disp_putc(0, *str++);
disp_putc(1, *str++);
disp_putc(2, *str++);
disp_putc(3, *str++);
} /* disp_put4 */
static char _hexnibble(char value)
{
value &= 0x0F;
return (value < 0x0A) ? ('0' + value)
: ('A' + value - 0x0A);
} /* _hexnibble */
#endif /* defined(DISP_WR) */
/* Send one byte to target, and return received one */
static uint8_t spi_rxtx(uint8_t val)
{
@ -274,6 +241,19 @@ static void cmdloop(void)
static uint8_t page_buf[256];
while (1) {
#if (USE_DISPLAY)
if (reset_state == STATE_RESET_PROGMODE)
{
uint16_t byte_address;
byte_address = (addr << 1);
display_show_hex(byte_address >> 8, 0);
display_show_hex(byte_address & 0xFF, 1);
display_set_mode(DISPLAY_MODE_STATIC);
}
#endif /* (USE_DISPLAY) */
switch (ser_recv()) {
/* Enter programming mode */
case 'P': {
@ -657,46 +637,6 @@ static void reset_statemachine(uint8_t event)
/* put device in RUN mode */
set_reset(1);
#if defined(DISP_WR)
char *dst = disp_text;
const char *src;
if (m_device.name[0] != '\0')
{
src = m_device.name;
while (*src != '\0')
{
*dst++ = *src++;
}
}
else
{
*dst++ = ' ';
*dst++ = '0';
*dst++ = 'X';
*dst++ = _hexnibble(m_device.sig[0] >> 4);
*dst++ = _hexnibble(m_device.sig[0]);
*dst++ = _hexnibble(m_device.sig[1] >> 4);
*dst++ = _hexnibble(m_device.sig[1]);
*dst++ = _hexnibble(m_device.sig[2] >> 4);
*dst++ = _hexnibble(m_device.sig[2]);
}
if (m_device.flags & POLL_UNTESTED) {
src = " untested";
while (*src != '\0') {
*dst++ = *src++;
}
}
*dst++ = ' ';
*dst++ = '\0';
disp_length = dst - disp_text;
disp_pos = 0x00;
#endif /* defined(DISP_WR) */
} else if ((event == EV_BUTTON_PRESSED) || (event == EV_PROG_ENTER)) {
reset_retries = 5;
reset_cause = event;
@ -739,8 +679,7 @@ static void reset_statemachine(uint8_t event)
avrdevice_get_by_signature(&m_device, m_device.sig);
state = (reset_cause == EV_PROG_ENTER) ? STATE_RESET_PROGMODE
: STATE_IDLE;
state = STATE_RESET_PROGMODE;
} else {
state = STATE_RESET_RETRY;
@ -776,6 +715,10 @@ static void reset_statemachine(uint8_t event)
case STATE_RESET_PROGMODE:
if (event == EV_STATE_ENTER) {
if (reset_cause == EV_BUTTON_PRESSED)
{
state = STATE_IDLE;
}
} else if (event == EV_PROG_LEAVE) {
/* was in prog mode (osc changed?), probe speed next time */
@ -792,6 +735,33 @@ static void reset_statemachine(uint8_t event)
break;
}
#if (USE_DISPLAY)
if ((m_state == STATE_IDLE) &&
((oldstate == STATE_RESET_RETRY) ||
(oldstate == STATE_RESET_PROGMODE)
))
{
if (m_device.name[0] != '\0')
{
display_show_string(m_device.name, 0);
if (m_device.flags & POLL_UNTESTED)
{
display_show_string(" untested", 1);
}
}
else
{
display_show_string("unknown 0X", 0);
display_show_hex(m_device.sig[0], 1);
display_show_hex(m_device.sig[1], 1);
display_show_hex(m_device.sig[2], 1);
}
display_set_mode(DISPLAY_MODE_SCROLL_ONCE);
}
#endif /* (USE_DISPLAY) */
event = (oldstate != state) ? EV_STATE_ENTER
: EV_NONE;
@ -847,45 +817,9 @@ ISR(TIMER0_OVF_vect)
ISP_LED_OFF();
}
#if defined(DISP_WR)
if (reset_state == STATE_IDLE) {
if (disp_length != 0x00) {
if (!(led_timer & 0x1F)) {
disp_put4(disp_text + disp_pos);
if (disp_pos < (disp_length -4)) {
disp_pos++;
} else {
disp_putc(0, 'R');
disp_putc(1, 'U');
disp_putc(2, 'N');
disp_putc(3, '-');
disp_length = 0x00;
disp_pos = 0x00;
}
}
} else {
switch (led_timer & 0x18) {
case 0x00: disp_putc(3, '-'); break;
case 0x08: disp_putc(3, '\\'); break;
case 0x10: disp_putc(3, '1'); break;
case 0x18: disp_putc(3, '/'); break;
default:
break;
}
}
} else if (reset_state == STATE_RESET_PROGMODE) {
uint16_t byte_addres = (addr << 1);
disp_putc(0, _hexnibble(byte_addres >> 12));
disp_putc(1, _hexnibble(byte_addres >> 8));
disp_putc(2, _hexnibble(byte_addres >> 4));
disp_putc(3, _hexnibble(byte_addres));
}
#endif /* defined(DISP_WR) */
#if (USE_DISPLAY)
display_update();
#endif /* (USE_DISPLAY) */
} /* TIMER0_OVF_vect */

View File

@ -33,6 +33,8 @@
#define ISP_LED_OFF() { PORTB |= (1<<ISP_LED); };
#define ISP_CHECK() (PIND & (1<<RESET_IN))
#define USE_DISPLAY 0
#define TIMER_INIT() { /* timer0, FCPU/1024, overflow interrupt */ \
TCCR0 = (1<<CS02) | (1<<CS00); \
TIMSK = (1<<TOIE0); \
@ -80,6 +82,7 @@
#define ISP_CHECK() !(PINB & (1<<RESET_IN))
/* DL1414 display */
#define USE_DISPLAY 1
#define DISP_WR PORTC2 /* low active */
#define DISP_A0 PORTC0
#define DISP_A1 PORTC1