Notice. New forum software under development. It's going to miss a few functions and look a bit ugly for a while, but I'm working on it full time now as the old forum was too unstable. Couple days, all good. If you notice any issues, please contact me.
|
Forum Index : Microcontroller and PC projects : MMBASIC program for DS1302 RTC to set Micromite clock
Page 1 of 2 | |||||
Author | Message | ||||
dvanaria Newbie Joined: 04/03/2018 Location: United StatesPosts: 15 |
I'm working on a project getting a Micromite (MkII with MMBASIC Ver 5.2) to communicate with a DS1302 RTC module, in order to set TIME$ and DATE$ with the current time/date. I know the DS1302 isn't on the supported list for the Micromite, at least for modules that support the I2C protocol (the DS1302 does not). But since it's all I have, I thought I'd try to get it to work. I downloaded the datasheet for the DS1302 (see screenshots) and I'm confused about how to interface it using MMBASIC. There are certain parts that mention things like "simple 3-wire interface" and another section that describes input/output details that make it sound like Mode 2 for the SPI protocol. I'm not too familiar with SPI but I know the Micromite has separate lines for SPI IN (pin 14) and SPI OUT (pin 3), so I'm not sure if it's possible to use MMBASIC's SPI functions to work with this module, or I would have to maybe write something from scratch to communicate with it (I'm not entirely sure the module does use SPI either). The RTC module has 5 pins, and it seems that the Vcc and GND are only used for a second power source, if desired, and don't have anything to do with communicating with the chip (though I could be mistaken). From this information (and the screenshots) can anyone point me in the right direction of where to start with this? Edited 2023-04-28 09:30 by dvanaria |
||||
phil99 Guru Joined: 11/02/2018 Location: AustraliaPosts: 2135 |
It appears to be I2C, not SPI and you do need power (2 to 5V - so use 3.3V) and ground to set or read it. I don't see any pullup resistors in your pics so add 4.7k resistors from 3.3V to SDA (Data) and SCL (Clock) lines. The MM2 does enable its own pullups but they may be too high (100k). Then try RTC SETTIME. It might be similar enough to a DS1307 to work. |
||||
Quazee137 Guru Joined: 07/08/2016 Location: United StatesPosts: 567 |
That is the VMA301 and is I2C. You do need to add the pullups. I have a box of them that was 1st used on my controllers. Now use the DS3231 AT24C32 Clock Module but changed out the AT24C32 for FRAM. Quazee137 |
||||
Turbo46 Guru Joined: 24/12/2017 Location: AustraliaPosts: 1611 |
You may find something here to help: https://www.thebackshed.com/forum/ViewTopic.php?TID=3775 Bill Keep safe. Live long and prosper. |
||||
Quazee137 Guru Joined: 07/08/2016 Location: United StatesPosts: 567 |
My bad it is a 3 wire SPI which is why I switched them out for the DS3231 module. I had I2C Fram chips I wanted to use. The MM170 MMBasic code I used is on a laptop some where in storage. I'll see if I can find it and get the code. Quazee137 Think of DAT as a TX/RX tied together CLK is CLK and RST it Chip select. Could try MOSI --- 1K ohm ----+------- DAT MSIO --- 1K ohm ----| SCLK ----------------------- CLK Sen ----------------------- RST its been a while less brain cells at work. |
||||
Mixtel90 Guru Joined: 05/10/2019 Location: United KingdomPosts: 6779 |
All these signals are relative to GND so you have to have that. Even the "1-wire interface" needs GND as well as it's signal wire. :) It isn't I2C and doesn't use I2C protocols, it has its own 3-wire interface. Neither is it SPI. /RST has to be pulled high to activate it for both tx and rx. After that the DAT line is used bi-directionally, in a similar way to I2C. DAT (I/O} has an internal pulldown. CLK (SCLK) has an internal pulldown /RST (CE) has an internal pulldown (it was called /RST on early datasheets) all about 40k The VCC pin and battery are isolated by diodes, so whichever has the higher voltage provides power. https://datasheets.maximintegrated.com/en/ds/DS1302.pdf I'm pretty certain that it won't be recognised by MMBasic. You'll have to write your own routines to bitbang the /RST CLK and DAT pins. . Edited 2023-04-28 17:17 by Mixtel90 Mick Zilog Inside! nascom.info for Nascom & Gemini Preliminary MMBasic docs & my PCB designs |
||||
Quazee137 Guru Joined: 07/08/2016 Location: United StatesPosts: 567 |
dvanaria Have a look Quazee137 |
||||
Volhout Guru Joined: 05/03/2018 Location: NetherlandsPosts: 4222 |
Hi dvanaria, Not sure what the purpose of this task is. Are you willing and capable of writing the code yourself ? Is this a project in itself ? Or are you looking for a solution for a larger project. If the later is the case, my advise would be to buy a DS1307 or DS3231 module, and connect it to the micromite, and enjoy all the support you get from the build in features the Micromite has. If you are dedicated to making the set work (MX170 and DS1302) then you may get help from forum members, but when they do not have the same hardware (DS1302) they cannot provide you with a turnkey solution. Volhout P.S. I owned the same board, and threw it away, after I realized it was not I2C. Too much hassle to make it work, almost impossible to integrate it seamless, and for few dollars you have something that works immediately (DS1307 or DS3231). PicomiteVGA PETSCII ROBOTS |
||||
dvanaria Newbie Joined: 04/03/2018 Location: United StatesPosts: 15 |
I appreciate all the help! It's definitely helped point me in the right direction. Just to clarify, I'm really just starting out learning electronics and microcontrollers, and so this is a small project, just connecting a DS1302 to a Micromite and seeing if I can get it to work. I'm enjoying the challenge, and learning how to read a datasheet for this (relatively) simple device. That said, I've made some progress. I believe the DS1302 uses a non-standard 3-wire protocol, and by reading the datasheet I was able to put together some MMBASIC code to test it out. Screenshots show how I've connected the DS1302 to the Micromite: PIN 2 connected to DAT on DS1302 PIN 4 connected to SCLK PIN 6 connected to RST The source code below just tries to write a certain test byte value (01010101) to the YEAR register in the DS1302, then the program attempts to read that register back again to see if it actually worked. The results aren't correct, the byte that the program is receiving isn't the test byte I was expecting, but I'll keep trying to figure it out. If anyone sees something wrong with this approach I'd appreciate further feedback. Thanks again. SETPIN 2, DOUT PRINT "Pin 2 set to DIGITAL OUT, connected to DS1302's DAT" SETPIN 4, DOUT PRINT "Pin 4 set to DIGITAL OUT, connected to DS1302's SCLK" SETPIN 6, DOUT PRINT "Pin 6 set to DIGITAL OUT, connected to DS1302's RST" DIM INTEGER MS1 = 30 DIM INTEGER COMMAND_SET_YEAR(7) = (1,0,0,0,1,1,0,0) DIM INTEGER SET_YEAR(7) = (0,1,0,1,0,1,0,1) DIM INTEGER COMMAND_READ_YEAR(7) = (1,0,0,0,1,1,0,1) DIM INTEGER RECEIVE_YEAR(7) = (1,1,1,1,1,1,1,1) PIN(2) = 1 : ' initialize DAT PIN(4) = 0 : ' SCLK must be 0 before initiating transfer PAUSE MS1 PIN(6) = 0 : ' This intiates transfer, setting ~RST to 1 PAUSE MS1 ' SEND COMMAND BYTE (SET REGISTER 'YEAR') FOR I = 0 TO 7 PIN(2) = COMMAND_SET_YEAR(I) PAUSE MS1 PIN(4) = 1 PAUSE MS1 PIN(4) = 0 PAUSE MS1 NEXT I FOR I = 0 TO 7 PIN(2) = SET_YEAR(I) PAUSE MS1 PIN(4) = 1 PAUSE MS1 PIN(4) = 0 PAUSE MS1 NEXT I PIN(6) = 1 : ' This ENDS transfer, setting ~RST to 0 PAUSE MS1 PIN(2) = 1 : ' initialize DAT PIN(4) = 0 : ' SCLK must be 0 before initiating transfer PAUSE MS1 PIN(6) = 0 : ' This intiates transfer, setting ~RST to 1 PAUSE MS1 ' SEND COMMAND BYTE (READ REGISTER 'YEAR') FOR I = 0 TO 7 PIN(2) = COMMAND_READ_YEAR(I) PAUSE MS1 PIN(4) = 1 PAUSE MS1 PIN(4) = 0 PAUSE MS1 NEXT I SETPIN 2, DIN PRINT "Pin 2 set to DIGITAL IN" PAUSE MS1 PIN(4) = 1 PAUSE MS1 FOR I = 0 TO 7 RECEIVE_YEAR(I) = PIN(2) PAUSE MS1 PIN(4) = 0 PAUSE MS1 PIN(4) = 1 PAUSE MS1 PRINT RECEIVE_YEAR(I); NEXT I END Edited 2023-04-30 01:01 by dvanaria |
||||
dvanaria Newbie Joined: 04/03/2018 Location: United StatesPosts: 15 |
I did some more testing and it turns out the pin labeled "RST" on the VMA301 module gets fed directly to the DS1302's pin labeled "~RST", so I had the settings for that signal backwards in the code above. That didn't fix the problem however. I'm not sure if it's good practice to switch pin 2 from OUTPUT mode to INPUT mode in the middle of a program, or if that's even possible once it's set. Thinking that was the problem, I connected the DAT line to both pin 2 and pin 26 and set 2 as output and 26 as input. I think this is working better. |
||||
dvanaria Newbie Joined: 04/03/2018 Location: United StatesPosts: 15 |
Ok got it. I was doing several things wrong, but the biggest was that I was bitbanging the command byte to the DS1302 in reverse order, so it was never going to work that way. Below is working code that does a test write to the YEAR register and then reads it back in again. It turns out you can set an OUTPUT pin to be an INPUT pin later in the same program. I'm not sure if this is bad practice but it was the most straightforward thing to do with this 3-wire protocol the DS1302 uses. I didn't end up running another line out to pin 26 to use that as in INPUT pin. Here is the demo code. Once I get a full implementation of setting all the registers with the current date/time, and then reading them back into the Micromite to set DATE$ and TIME$, I'll post that final code here in case anyone else is interested. CONST DAT = 2 CONST SCLK = 4 CONST RST = 6 SETPIN DAT, DOUT PRINT "Pin 2 set to DIGITAL OUT, connected to DS1302's DAT" SETPIN SCLK, DOUT PRINT "Pin 4 set to DIGITAL OUT, connected to DS1302's SCLK" SETPIN RST, DOUT PRINT "Pin 6 set to DIGITAL OUT, connected to DS1302's RST" REM NOTE: THE INPUT PIN ON THE VMA301 MODULE LABELED "RST" IS FED ' DIRECTLY TO THE DS1302'S ~RST PIN, SO = 0 PRE-INITIALIZATION, ' THEN SET = 1 TO INITIALIZE A DATA TRANSFER (2 BYTES) REM NOTE: DS1302: "DATA IS SERIALLY INPUT ON THE RISING EDGE OF THE SCLK" ' SO MAKE SURE TO SET DAT_OUT VALUE BEFORE SETTING SCLK = 1 DIM INTEGER MS1 = 30 DIM INTEGER COMMAND_SET_YEAR(7) = (0,0,1,1,0,0,0,1) DIM INTEGER COMMAND_READ_YEAR(7) = (1,0,1,1,0,0,0,1) DIM INTEGER SET_YEAR(7) = (0,1,0,1,0,0,1,1) ' YEAR = 53, BCD FORMAT DIM INTEGER RECEIVE_YEAR(7) = (1,0,1,0,1,0,1,0) PRINT "INITIALIZING DATA TRANSFER TO DS1302" PIN(DAT) = 0 PIN(SCLK) = 0 : ' SCLK must be 0 before initiating transfer PIN(RST) = 0 PAUSE MS1 PIN(RST) = 1 : ' This intiates transfer, setting ~RST to 1 PAUSE MS1 PRINT "SENDING COMMAND BYTE: 'WRITE TO REGISTER'" FOR I = 0 TO 7 PIN(DAT) = COMMAND_SET_YEAR(I) PAUSE MS1 PIN(SCLK) = 1 PAUSE MS1 PIN(SCLK) = 0 PAUSE MS1 NEXT I PRINT "WRITING TO REGISTER" FOR I = 0 TO 7 PIN(DAT) = SET_YEAR(I) PAUSE MS1 PIN(SCLK) = 1 PAUSE MS1 PIN(SCLK) = 0 PAUSE MS1 NEXT I PRINT "END OF FIRST TRANSFER (WRITE)" PIN(RST) = 0 : ' This ENDS first transfer, setting ~RST to 0 PAUSE MS1 PIN(DAT) = 0 PIN(SCLK) = 0 : ' SCLK must be 0 before initiating transfer PAUSE MS1 PIN(RST) = 1 : ' This intiates next transfer, setting ~RST to 1 PAUSE MS1 PRINT "SENDING COMMAND BYTE: 'READ REGISTER'" FOR I = 0 TO 7 PIN(DAT) = COMMAND_READ_YEAR(I) PAUSE MS1 PIN(SCLK) = 1 PAUSE MS1 IF I <> 7 THEN ' DON'T SET CLOCK TO 0 AFTER LAST COMMAND BIT PIN(SCLK) = 0 PAUSE MS1 ENDIF NEXT I SETPIN DAT, DIN, PULLUP PAUSE MS1 PRINT "READING DATA: "; FOR I = 0 TO 7 IF I <> 0 THEN PIN(SCLK) = 1 PAUSE MS1 ENDIF PIN(SCLK) = 0 PAUSE MS1 RECEIVE_YEAR(I) = PIN(DAT) PAUSE MS1 NEXT I PRINT "RESULTS: "; FOR I = 0 TO 7 PRINT RECEIVE_YEAR(I); NEXT I END Edited 2023-04-30 11:11 by dvanaria |
||||
Volhout Guru Joined: 05/03/2018 Location: NetherlandsPosts: 4222 |
Well done! Save this in a MX library.. and you can use it from your main program. Edited 2023-04-30 18:03 by Volhout PicomiteVGA PETSCII ROBOTS |
||||
pwillard Senior Member Joined: 07/06/2022 Location: United StatesPosts: 292 |
The bummer is that these keep rather crappy time compared to the DS3231 |
||||
Mixtel90 Guru Joined: 05/10/2019 Location: United KingdomPosts: 6779 |
The tiny little "Raspberry Pi compatible" DS3231 RTCs can be pretty poor too. I suspect they don't get calibrated, and you've no idea how old the (unobtainable) batteries are anyway. They are cheap though. Mick Zilog Inside! nascom.info for Nascom & Gemini Preliminary MMBasic docs & my PCB designs |
||||
phil99 Guru Joined: 11/02/2018 Location: AustraliaPosts: 2135 |
Some time ago Volhout posted a calibration program. If the 32kHz is a bit high adding a few pF in parallel can pull it down. I used it on a poor DS1307, though adding enough to get the frequency right made it unstable. Salvaged a crystal from a dead mother board and it now keeps excellent time with no capacitor. |
||||
dvanaria Newbie Joined: 04/03/2018 Location: United StatesPosts: 15 |
Here is the finished code for this project, just posting it here in case anyone else has use for it. Thanks for all the help! Screenshots of how the program works are below. I wasn't sure what to call the programs so I went with MMBASIC's "RTC SETTIME" and "RTC GETTIME" pattern and replaced RTC with DS1302 to make it clear. DS1302 RTC.zip |
||||
Volhout Guru Joined: 05/03/2018 Location: NetherlandsPosts: 4222 |
Hi Darron, I may adapt your program to the picomite format, where date and time are set as: RTC SETTIME 2023,5,3,17,03,24 Thank you for creating this... Volhout Edited 2023-05-04 01:04 by Volhout PicomiteVGA PETSCII ROBOTS |
||||
dvanaria Newbie Joined: 04/03/2018 Location: United StatesPosts: 15 |
Volhout, absolutely, thanks for doing that. Hopefully someone else can get some use out of it! |
||||
Chopperp Guru Joined: 03/01/2018 Location: AustraliaPosts: 1057 |
Hi Volhout Did you ever get around to doing this? I found a couple of the DS1302 modules & I was thinking of using one on a Webmite in case the network goes down for a short period. Thanks Brian ChopperP |
||||
Volhout Guru Joined: 05/03/2018 Location: NetherlandsPosts: 4222 |
No, sorry Never did. Actually I could not find my DS1302 back, and left it at that. I purchased a DS3231 board in stead. Volhout PicomiteVGA PETSCII ROBOTS |
||||
Page 1 of 2 |
Print this page |