1 /* (CC-BY-NC-SA) ROBIN KRENS - ROBIN @ ROBINKRENS.NL
4 * 2019/7/25 - ROBIN KRENS
8 * Basic driver for the TM1637. The TM1637 is 8 segment
9 * ledclock peripheral. Communication is similar to I2C,
10 * but not completely. There is no address selecting.
12 * Alternative I2C protocol : (W)rite or (R)ead
13 * | Start | ADDRESS | W | ACK/NACK | DATA | ACK/NACK | (d+a*n) | St
14 * | Start | ADDRESS | R | ACK/NACK | DATA | ACK/NACK | (d+a*n) | St
23 #include <sys/robsys.h>
25 #include <lib/regfunc.h>
26 #include <lib/string.h>
27 #include <lib/stdio.h>
29 #include <drivers/tm1637.h>
33 #define DISPLAY_ON 0x8F
34 #define DISPLAY_OFF 0x11
50 /* STM32F1 microcontrollers do not provide the ability to pull-up SDA and SCL lines. Their
51 GPIOs must be configured as open-drain. So, you have to add two additional resistors to
52 pull-up I2C lines. Something between 4K and 10K is a proven value.
59 /* Program the peripheral input clock in I2C_CR2 Register in order to generate correct timings
60 Configure the clock control registers CCR
61 Configure the rise time register TRIS
62 Program the I2C_CR1 register to enable the peripheral
64 ENABLE GPIOB6 and B7*/
66 regw_u32(RCC_APB1ENR, 0x1, 21, SETBIT);
67 regw_u32(RCC_APB2ENR, 0x1, 3, SETBIT);
68 // //regw_u8(AFIO_EVCR, 0x89, 0, SETBIT);// set event control register, output on ?
70 regw_u32(GPIOB_CRL, 0xEE444444, 0, OWRITE);
72 regw_u32(I2C_CR2, 0x2, 0, OWRITE); //2 MHz
73 regw_u8(I2C_TRISE, 0x3, 0, OWRITE); // MAX = 1000ns, TPCLK1 = 500ns (+1)
74 regw_u32(I2C_CCR, 0x000A, 0, OWRITE); // standard mode, output 100 kHz (100hz* / perip)
76 regw_u32(I2C_CR1, 0x1, 0, OWRITE); // enable
82 regw_u32(RCC_APB1RSTR, 0x1, 21, SETBIT);
84 regw_u32(RCC_APB1RSTR, 0x00000000, 0, OWRITE); // clr
85 //regw_u32(RCC_APB2ENR, 0x1, 3, SETBIT);
86 // //regw_u8(AFIO_EVCR, 0x89, 0, SETBIT);// set event control register, output on ?
88 regw_u32(RCC_APB1ENR, 0x1, 21, SETBIT);
89 //regw_u32(GPIOB_CRL, 0xEE444444, 0, OWRITE);
91 regw_u32(I2C_CR2, 0x2, 0, OWRITE); //2 MHz
92 regw_u8(I2C_TRISE, 0x3, 0, OWRITE); // MAX = 1000ns, TPCLK1 = 500ns (+1)
93 regw_u32(I2C_CCR, 0x000A, 0, OWRITE); // standard mode, output 100 kHz (100hz* / perip)
95 regw_u32(I2C_CR1, 0x1, 0, OWRITE); // enable
100 static void start_condition() {
102 regw_u32(I2C_CR1, 0x1, 8, SETBIT); //start
106 static void stop_condition() {
108 regw_u32(I2C_CR1, 0x1, 9, SETBIT); //stop
111 static int buf_empty() {
113 while(!(*I2C_SR1 & 0x80)) {
125 while(!(*I2C_SR1 & 0x2)) {
130 uint32_t a = *I2C_SR2;
138 while(!(*I2C_SR1 & 0x8)) {
143 //uint32_t a = *I2C_SR2;
150 while(*I2C_SR2 & 0x2) {
162 for (int i = 0; i < TIMEOUT; i++)
166 void set_brightness(uint8_t degree) {
170 // regw_u32(I2C_DR, 0xF0, 0, OWRITE);
172 // cputs("Error: can not set dummy header");
174 regw_u32(I2C_DR, 0xF1, 0, OWRITE);
180 regw_u32(I2C_CR1, 0x1, 15, SETBIT);
185 void set_startseg(int offset) {
188 regw_u32(I2C_DR, 0x20, 0, OWRITE);
190 cputs("Error: initiating write for start segment \n");
195 cputs("Error: timeout");
198 regw_u32(I2C_DR, 0x03, 0, OWRITE);
200 cputs("Error: Can't set start segment \n");
203 regw_u32(I2C_CR1, 0x1, 15, SETBIT);
208 void tm1637_start() {
210 unsigned char display_number[10] = {0x00, 0x60, 0xDA, 0xF2, 0x66, 0xB6, 0xBE, 0xE0, 0xFF, 0xF6};
211 // regw_u32(I2C_CR1, 0x1, 8, SETBIT);
212 // uint32_t read_status = *I2C_SR1;
214 // regw_u32(I2C_DR, DATASET, 0, OWRITE);
216 // read_status = *I2C_SR1;
217 // read_status = *I2C_SR2;
221 // start_condition();
222 // //uint32_t statusr = *I2C_SR1; // clear start_signal
223 // regw_u32(I2C_DR, 0x20, 0, OWRITE); // write to address CMD
225 // cputs("TIMEOUT!");
226 // //statusr = *I2C_SR1;
227 // //statusr = *I2C_SR2;
235 cputs("Error: timeout");
239 // start_condition();
240 // regw_u32(I2C_DR, 0x20, 0, OWRITE);
242 // cputs("Error: initiating write command\n");
247 // cputs("Error: timeout");
250 // regw_u32(I2C_DR, 0xF0, 0, OWRITE); // dummy header F0 ignored! any value will do as long as last bit is not set
252 // cputs("Error: dummy addr-10 header not acknowledged\n");
253 regw_u32(I2C_DR, display_number[6], 0, OWRITE); // use ack10 if higher
255 cputs("Error: can't set location\n");
256 // regw_u32(I2C_DR, 0xF4, 0, OWRITE);
258 // cputs("Error: can't write\n");
259 // regw_u32(I2C_DR, 0x08, 0, OWRITE);
261 // cputs("Error: can't write\n");
262 // regw_u32(I2C_DR, 0x08, 0, OWRITE);
264 // cputs("Error: can't write\n");
270 regw_u32(I2C_CR1, 0x1, 15, SETBIT);
272 regw_u32(I2C_DR, 0x00, 0, OWRITE); // ? dummy address
275 regw_u32(I2C_DR, 0x03, 0, OWRITE);
278 regw_u32(I2C_DR, 0xFF, 0, OWRITE);
280 cputs("TIMEOUT2B"); */
283 cputs("Error: timeout");
288 set_brightness(0x00);
295 regw_u32(I2C_DR, DISPLAY_ON, 0, OWRITE);
301 /* regw_u32(I2C_CR1, 0x1, 8, SETBIT); //start
302 uint32_t read_status = *I2C_SR1;
303 regw_u32(I2C_DR, 0x40, 0, OWRITE); // write to address CMD
304 read_status = *I2C_SR1;
305 read_status = *I2C_SR2;
306 regw_u32(I2C_CR1, 0x1, 9, SETBIT); //stop
307 read_status = *I2C_SR1;
309 regw_u32(I2C_CR1, 0x1, 8, SETBIT); //start
310 read_status = *I2C_SR1;
311 regw_u32(I2C_DR, 0xC1, 0, OWRITE); // segment address
312 read_status = *I2C_SR1;
313 read_status = *I2C_SR2;
314 regw_u32(I2C_DR, 0x7D, 0, OWRITE); // write a six
316 regw_u32(I2C_CR1, 0x1, 9, SETBIT); //stop
317 read_status = *I2C_SR1;
319 regw_u32(I2C_CR1, 0x1, 8, SETBIT); //start
320 read_status = *I2C_SR1;
322 regw_u32(I2C_DR, DISPLAY_ON, 0, OWRITE);
323 read_status = *I2C_SR1;
324 regw_u32(I2C_CR1, 0x1, 9, SETBIT); //stop */
330 //regw_u32(I2C_CR1, 0x0, 9, SETBIT);