Skip to content

Instantly share code, notes, and snippets.

@MatthaeusHarris
Created February 24, 2017 07:59
Show Gist options
  • Save MatthaeusHarris/72dab3611f32ff5cb7b8d98d5b3d934f to your computer and use it in GitHub Desktop.
Save MatthaeusHarris/72dab3611f32ff5cb7b8d98d5b3d934f to your computer and use it in GitHub Desktop.
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#include "lcd.h"
// Shift register pin info
#define SRCLK_PIN 2
#define DATA_PIN 1
#define RCLK_PIN 0
#define SR_PORT PORTB
// Shift register timing info
// Data sheet says the shift register can run faster than
// the attiny84, but let's make it adjustable anyway.
#define SETUP_TIME 0
#define PULSE_TIME 0
#define HOLD_TIME 0
// Because the attiny84 apparently takes twice as long
// to << 2 as it does to << 1. WTF?
static uint16_t bitmask[] = {
0x0001,
0x0002,
0x0004,
0x0008,
0x0010,
0x0020,
0x0040,
0x0080,
0x0100,
0x0200,
0x0400,
0x0800,
0x1000,
0x2000,
0x4000,
0x8000
};
// Send a pair of bytes to the shift registers
void streamBytes(uint16_t byte) {
uint8_t i, j;
// Need to send in reverse; this could be optimized
// Can't just have i count down because all ints are unsigned
for (i=0, j=15; i < 16; i++, j--) {
// Write the bit to the serial pin
if (byte & bitmask[j]) {
SR_PORT |= _BV(DATA_PIN);
} else {
SR_PORT &= ~_BV(DATA_PIN);
}
// Pulse the clock
_delay_us(SETUP_TIME);
SR_PORT |= _BV(SRCLK_PIN);
_delay_us(PULSE_TIME);
SR_PORT &= ~_BV(SRCLK_PIN);
_delay_us(PULSE_TIME);
}
// Turn off data pin
SR_PORT &= ~_BV(DATA_PIN);
// Move the shift register data to the storage register
_delay_us(SETUP_TIME);
SR_PORT |= _BV(RCLK_PIN);
_delay_us(HOLD_TIME);
SR_PORT &= ~_BV(RCLK_PIN);
}
// Use the pin mapping in lcd.h to prepare a bitstream for transmission
// to the shift registers
void displayByte(byte) {
// Build pin info
uint16_t bitstream;
uint8_t msb, lsb;
msb = byte >> 4;
lsb = byte & 0x0f;
bitstream = (characters[msb] << 8) | characters[lsb];
streamBytes(bitstream);
}
int main(void) {
uint8_t value = 0x00;
// Enable output on shift register pins
DDRB |= _BV(SRCLK_PIN) | _BV(DATA_PIN) | _BV(RCLK_PIN);
while(1) {
displayByte(value);
_delay_ms(250);
value++;
}
return (0);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment