Skip to content

Commit

Permalink
Merge branch 'olimex-avr-mt128' into hd44780-opengl-mutex-olimex
Browse files Browse the repository at this point in the history
  • Loading branch information
Juhász Dániel committed Oct 6, 2022
2 parents 6300d5e + c51a8f5 commit 83d13ed
Show file tree
Hide file tree
Showing 12 changed files with 2,863 additions and 1,118 deletions.
12 changes: 6 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -68,9 +68,9 @@ graphically as “waveforms” with tools like _gtkwave_ (see below).
Documentation And Further Information
-------------------------------------

* Manual / Developer Guide: https://github.com/buserror-uk/simavr/blob/master/doc/manual/manual.pdf?raw=true
* Examples: https://github.com/buserror-uk/simavr/tree/master/examples
* Mailing List: http://groups.google.com/group/simavr
* [Manual / Developer Guide](doc/manual/manual.pdf?raw=true)
* [Examples](examples)
* [Mailing List](https://groups.google.com/g/simavr)
* IRC: _#simavr_ on Freenode

Contributing
Expand Down Expand Up @@ -114,7 +114,7 @@ a file that will display:
simavr: sleeping with interrupts off, quitting gracefully

And when the file is loaded in gtkwave, you see:
![gtkwave](https://github.com/buserror-uk/simavr/raw/master/doc/img/gtkwave1.png)
![gtkwave](doc/img/gtkwave1.png)

You get a very precise timing breakdown of any change that you add to the trace, down
to the AVR cycle.
Expand All @@ -137,13 +137,13 @@ need to generate the proper stimulus so that the AVR is fooled.
HD44780 LCD Board Demo
----------------------

![lcd](https://github.com/buserror-uk/simavr/raw/master/doc/img/hd44780.png)
![lcd](doc/img/hd44780.png)

This example board hooks up an Atmega48 to an emulated HD44780 LCD and display a running
counter in the 'lcd'. Everything is emulated, the firmware runs exactly like this
on a real hardware.

![lcd-gtkwave](https://github.com/buserror-uk/simavr/raw/master/doc/img/hd44780-wave.png)
![lcd-gtkwave](doc/img/hd44780-wave.png)

And this is a gtkwave trace of what the firmware is doing. You can zoom in, measure, etc
in gtkwave, select trades to see etc.
Expand Down
53 changes: 53 additions & 0 deletions examples/board_olimex_avr_mt128/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
#
# Copyright 2008-2011 Michel Pollet <buserror@gmail.com>
#
# This file is part of simavr.
#
# simavr 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, either version 3 of the License, or
# (at your option) any later version.
#
# simavr 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 simavr. If not, see <http://www.gnu.org/licenses/>.

target = mt128
firmware_srcs = ${wildcard at*.c}

simavr = ../../

IPATH = .
IPATH += ../parts
IPATH += ${simavr}/include
IPATH += ${simavr}/simavr/sim

VPATH = .
VPATH += ../parts

LDFLAGS += -lpthread

include ../Makefile.opengl

all: obj axf ${target}

axf: ${firmware_srcs:.c=.axf}

include ${simavr}/Makefile.common

board = ${OBJ}/${target}.elf

${board} : ${OBJ}/button.o
${board} : ${OBJ}/hd44780.o
${board} : ${OBJ}/hd44780_glut.o
${board} : ${OBJ}/${target}.o

${target}: ${board}
@echo $@ done

clean: clean-${OBJ}
rm -rf *.hex *.a *.axf *.vcd .*.swo .*.swp .*.swm .*.swn
8 changes: 8 additions & 0 deletions examples/board_olimex_avr_mt128/README
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
board_olimex_avr_mt128

(C) 2020 Akos Kiss <akiss@inf.u-szeged.hu>

Experimental Olimex AVR-MT128 development board simulation.
Based on works of and sample code from
- Michel Pollet <buserror@gmail.com> and
- Luki <humbell@ethz.ch>.
155 changes: 155 additions & 0 deletions examples/board_olimex_avr_mt128/atmega128_charset.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,155 @@
// NOTE: lines below added to allow compilation in simavr's build system
#undef F_CPU
#define F_CPU 16000000
#include "avr_mcu_section.h"
AVR_MCU(F_CPU, "atmega128");

#include "avr/io.h"
#include "avr_lcd.h" // NOTE: changed header name to better fit in simavr's file naming conventions

#define __AVR_ATMEGA128__ 1

static void Delay(unsigned int b)
{
volatile unsigned int a = b; // NOTE: volatile added to prevent the compiler to optimization the loop away
while (a)
{
a--;
}
}

static void EPulse()
{
PORTC = PORTC | 0b00000100; // set E to high
Delay(1400); // delay ~110ms
PORTC = PORTC & 0b11111011; // set E to low
}

void LCDInit()
{
// LCD initialization
// step by step (from Gosho) - from DATASHEET

PORTC = PORTC & 0b11111110;

Delay(10000);


PORTC = 0b00110000; // set D4, D5 port to 1
EPulse(); // high->low to E port (pulse)
Delay(1000);

PORTC = 0b00110000; // set D4, D5 port to 1
EPulse(); // high->low to E port (pulse)
Delay(1000);

PORTC = 0b00110000; // set D4, D5 port to 1
EPulse(); // high->low to E port (pulse)
Delay(1000);

PORTC = 0b00100000; // set D4 to 0, D5 port to 1
EPulse(); // high->low to E port (pulse)

// NOTE: added missing initialization steps
LCDSendCommand(0x28); // function set: 4 bits interface, 2 display lines, 5x8 font
LCDSendCommand(DISP_OFF); // display off, cursor off, blinking off
LCDSendCommand(CLR_DISP); // clear display
LCDSendCommand(0x06); // entry mode set: cursor increments, display does not shift
}

void LCDSendCommand(unsigned char a)
{
unsigned char data = 0b00001111 | a; // get high 4 bits
PORTC = (PORTC | 0b11110000) & data; // set D4-D7
PORTC = PORTC & 0b11111110; // set RS port to 0
EPulse(); // pulse to set D4-D7 bits

data = a<<4; // get low 4 bits
PORTC = (PORTC & 0b00001111) | data; // set D4-D7
PORTC = PORTC & 0b11111110; // set RS port to 0 -> display set to command mode
EPulse(); // pulse to set d4-d7 bits
}

void LCDSendChar(unsigned char a)
{
unsigned char data = 0b00001111 | a; // get high 4 bits
PORTC = (PORTC | 0b11110000) & data; // set D4-D7
PORTC = PORTC | 0b00000001; // set RS port to 1
EPulse(); // pulse to set D4-D7 bits

data = a<<4; // get low 4 bits
PORTC = (PORTC & 0b00001111) | data; // clear D4-D7
PORTC = PORTC | 0b00000001; // set RS port to 1 -> display set to command mode
EPulse(); // pulse to set d4-d7 bits
}

static unsigned char cgram[64] = {
0b00000, 0b01110, 0b01010, 0b01010, 0b01010, 0b01110, 0b00000, 0b11111,
0b00000, 0b00100, 0b00100, 0b00100, 0b00100, 0b00100, 0b00000, 0b11111,
0b00000, 0b01110, 0b00010, 0b01110, 0b01000, 0b01110, 0b00000, 0b11111,
0b00000, 0b01110, 0b00010, 0b01110, 0b00010, 0b01110, 0b00000, 0b11111,
0b00000, 0b01000, 0b01000, 0b01110, 0b00100, 0b00100, 0b00000, 0b11111,
0b00000, 0b01110, 0b01000, 0b01110, 0b00010, 0b01110, 0b00000, 0b11111,
0b00000, 0b01110, 0b01000, 0b01110, 0b01010, 0b01110, 0b00000, 0b11111,
0b00000, 0b01110, 0b00010, 0b00010, 0b00010, 0b00010, 0b00000, 0b11111,
};

static void LCDInitCGRAM()
{
LCDSendCommand(0x40);
for (unsigned int i = 0; i < 64; ++i) {
LCDSendChar(cgram[i]);
}
}

static void PortInit()
{
PORTA = 0b00011111; DDRA = 0b01000000; // NOTE: set A4-0 to initialize buttons to unpressed state
PORTB = 0b00000000; DDRB = 0b00000000;
PORTC = 0b00000000; DDRC = 0b11110111;
PORTD = 0b11000000; DDRD = 0b00001000;
PORTE = 0b00000000; DDRE = 0b00110000;
PORTF = 0b00000000; DDRF = 0b00000000;
PORTG = 0b00000000; DDRG = 0b00000000;
}

int main()
{
PortInit();
LCDInit();
LCDInitCGRAM();

unsigned int b = 1; // button lock (0: pressed, 1: released)
unsigned int c = 0; // char start index

while (1)
{
// Middle Button (Button 3)
if (!(PINA & 0b00000100) && b)
{
LCDSendCommand(DD_RAM_ADDR);
for (unsigned int i = 0; i < 16; ++i)
{
LCDSendChar(c + i);
}
LCDSendCommand(DD_RAM_ADDR2);
for (unsigned int i = 0; i < 16; ++i)
{
LCDSendChar(c + 16 + i);
}
c = (c + 32) & 0xff;
b = 0; // button is pressed
}

//check state of all buttons
if (
((PINA & 0b00000001)
|(PINA & 0b00000010)
|(PINA & 0b00000100)
|(PINA & 0b00001000)
|(PINA & 0b00010000)) == 31)
b = 1; // if all buttons are released b gets value 1
}

return 0;
}
Loading

0 comments on commit 83d13ed

Please sign in to comment.