[Contest] RIOT Clock

Let's talk about anything related to the 6502 microprocessor.
Chromatix
Posts: 1462
Joined: 21 May 2018

[Contest] RIOT Clock

Post by Chromatix »

Project Aims:
Make a nice and useful clock to hang on the wall. It needs to keep accurate time (as good as my watch), be readable from a distance, easy to set, and have a countdown timer function for kitchen utility; perhaps an alarm function as well. Preferably incorporating more than one simultaneous timer, as many kitchen projects have overlapping processes that need timing independently.
Oh, and I'd like it to chime and strike the hours, too. That'll be the fun part. :lol:

Central Logic:
I'll probably use a modern 8Kx8 EEPROM, but only 2KB of it, and design the socket so that a correctly programmed 2716 can also be used. The RIOT contains enough RAM for the task by itself. The RIOT's timer is not really suited to running a clock with long-term accuracy, so I'll delegate that task to a DS1501 RTC, which also contains a small NVRAM and supports keeping time from a coin-cell backup battery. This means the power outages I occasionally have won't disrupt timekeeping. Instead I'll reserve the RIOT's timer for the chime function. Since I don't need a lot of computing power for this, I may divide a standard 1.8432 MHz UART crystal oscillator down to 115.2 kHz, just above the reliable minimum speed for an NMOS 650x.

Display:
For readability at a distance, I would either need a rather large LCD panel or an LED display, unless I stumble across a way to implement computer-controlled clock hands. This is likely to be the most expensive part of the system, in any case. Absolute minimum requirements would be a four-digit 7-segment block, but it'd be nice to show seconds, day and date, lunar phase, and an auxiliary display for the kitchen timer function. Fourteen or sixteen segment digits should work well for day-of-week and month-name abbreviations. Figuring out the best way to hang so many LED segments off the RIOT will be a large part of the challenge here; there are a number of LED driver ICs that can be driven serially, which will seriously help.
My family's grandfather clock had a lunar-phase dial which I never remember having been in working order, but I've worked out a way to calculate it even on as tiny a machine as this.

Input:
Hold down a button to select which item gets adjusted by a rotary encoder, the latter needing just two input pins to handle. Six buttons could cover year, month, day, hour, minute, second. Day of week and lunar phase would be calculated, not set. Two more buttons would be available from an 8-to-3 priority encoder, and could be associated with the timer function. Of course I could cascade a second button encoder if I needed more buttons. I still need to work out exactly how best to implement the timer interface here, given that it will get used much more often than the clock adjustment.

Chiming & Striking:
A striking clock is one that counts the hours on its bell; technically a cuckoo clock fits this definition. A chiming clock is one that precedes the strike with a tune, and usually also chimes the quarter-hours. Several different chimes are popularly used in clocks, generally implemented on eight bells representing a major scale, as a set of five musical phrases which end up being played twice an hour (the quarters being phrase 1, then 2-3, then 4-5-1, and finally 2-3-4-5). Characteristic of this process is that each bell reverberates for some time after the next note has been struck, and indeed after the complete chime has finished.
I've worked out a reasonably simple circuit to produce a decaying tone, crudely simulating a physical bell. Nine of these circuits ganged together can implement a major scale plus a separate striking bell, with appropriately independent reverberation; these will be followed by a pair of op-amps to implement a filter and drive a speaker. The bells can easily be driven by one of the RIOT's ports, via a '138 decoder to reduce the number of pins required.
At 115.2 kHz Phi2, the RIOT can time an interval of up to 2.267 seconds (1024*255 cycles) without special effort. This is just about perfect for timing out a chime and strike sequence.

Software:
Most of the time, the job is just noticing when the RTC registers change and updating the display to match. The RTC can be configured to produce a 1PPS signal to facilitate this. This job gets modified when the countdown timers are active, as the 1PPS signal now also needs to decrement the timer and compare it against zero. Additionally, the display still needs to be updated when a chime sequence is active, even though the chimes will take several seconds to complete (and I don't want them rigidly synchronised to the seconds). The process of setting the time may also expose some corner cases.
The 2KB ROM essentially precludes the use of any high-level languages or even VMs. Which is fine by me; I've made sure some of the RIOT's RAM is mapped for use as a stack, precisely so that I can still use subroutines sensibly. This is also one of the relatively few serious uses I expect to make of the 6502's Decimal mode, as that's what the RTC chip uses and it's convenient to not have to convert it for display.
thedrip
Posts: 48
Joined: 02 Oct 2018

Re: [Contest] RIOT Clock

Post by thedrip »

For computer controlled clock hands, stepper/servo motors driven through the RIOT could work!
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

Sure, but setting up the mechanical end of that is not exactly my area of expertise. Clock hands tend to be co-axial, you know.
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

A little something on the lunar phase calculations:

There are several established algorithms for calculating these from a date, some more accurate than others. The more accurate ones tend to use trigonometry to approximate the actual celestial motion (which is quite complex for the Moon's orbit), which I don't have the code space for. But I don't need it super accurate for this project, so I'll be happy with merely following the mean period of the moon phases (ie. the synodic month) accurately; this should be quite good accuracy in the medium term (by which I mean the next century or so).

The established mean synodic month is 29.530588861 days at 86400 seconds each, or about 2551443 seconds, increasing very slowly (much less than a second per century) as the Moon's orbit expands. We can use this to count forward to the current date from the known time of a reference new-moon (eg. 2019 Dec 26 05:13 UTC), and determine the correct number of seconds since the most recent new-moon, from which the correct pattern of LEDs to indicate the current moon phase can be determined with a small table lookup. Since this only requires successive additions and subtractions, plus iteration through a calendar (which is needed anyway while setting the time), this algorithm is a good fit for the 6502.

Both 2551443 and 86400 are 3-byte integers, lying between 65536 and 16777215. So the algorithm will involve, for each day, adding 86400 to a 3-byte accumulator, comparing the result with 2551443, and subtracting the latter if it turns out to be greater. This is then repeated for each hour (3600 increment) and minute (60 increment) and second, up to the current time, after which the phase counter can be incremented every second to keep it in lockstep with real time. Conveniently, 2551443's most-significant byte is 38, which means that a 39-entry lookup table based on the MSB of the seconds remainder is sufficient to establish the LED pattern. And if the time is changed manually, there is the choice of running the lunar clock backwards by the same amount (adding 2551443 when it underflows) or recalculating it from the start.
User avatar
BigEd
Posts: 11463
Joined: 11 Dec 2008
Location: England
Contact:

Re: [Contest] RIOT Clock

Post by BigEd »

I like it! (Hands don't have to be coaxial... and maybe rotating disks from the outside is easier than rotating hands from the middle. Lots of possibilities.)
Klaus2m5
Posts: 442
Joined: 28 Jul 2012
Location: Wiesbaden, Germany

Re: [Contest] RIOT Clock

Post by Klaus2m5 »

I build a radio clock 10 years ago, but with an ATMega8. So I will not build one again. However, the clock had its own way to display the time and maybe some of you will be inspired by it.

The time is counted on LEDs like an Abacus calculator. To match the 60 minutes / 24 (12) hours of how we count time, digits have different numbering schemes.
Abaclock.png
Abaclock.png (6.03 KiB) Viewed 1410 times
The 10^0 position of seconds, minutes and days works exactly as digits are counted on an Abacus. The 10^1 position however counts only up to 50. So the blue LED of the seconds shows also half a minute, the blue LED of the minutes also shows half an hour.

The base of 3 numbering system of the hours (and of the month) corresponds to the position of the short hand of a clock. The amber LED shows 6 and the red LED 3 or 9 for both AM and PM which is determined by the blue LED. The numbering system is simply copied to the month because I needed the space for the day of week LEDs.
Abaclock_klein.jpg
So the picture was taken on Thurday, the 16th of January. The time was 14:05:43.
6502 sources on GitHub: https://github.com/Klaus2m5
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

Interesting, but somewhat more difficult to read than I'd really prefer. It's not terribly difficult to drive segment displays, in a brute-force kind of way using shift registers with integrated constant-current drivers, but I haven't settled on exactly which method would be most efficient here. It's the kind of detail I've got plenty of time to work out.
User avatar
Dr Jefyll
Posts: 3525
Joined: 11 Dec 2009
Location: Ontario, Canada
Contact:

Re: [Contest] RIOT Clock

Post by Dr Jefyll »

BigEd wrote:
Hands don't have to be coaxial...
OT, but I'm reminded of a project published well back in the 20th century by Popular Mechanics, perhaps, or maybe Popular Science. It was a clock disguised as a piece of artwork, to be hung on the wall in the office of a doctor or other professional. The schtick was, the doc could discreetly keep track of the time, and thus know when to wrap up an appointment with a client!

The "artwork" was just a goofy frame with six disks mounted on a backdrop, and the whole thing colorfully painted in a seemingly meaningless design. But two of the disks rotated, serving as the hour and minute "hands" of the clock. It was easy enough to read, once you knew how.

No disk was provided to serve as a seconds "hand," however. Its motion would be too apparent, and that'd give away the secret! :lol:
In 1988 my 65C02 got six new registers and 44 new full-speed instructions!
https://laughtonelectronics.com/Arcana/ ... mmary.html
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

The tone generators are built around one and a half 74HC14s - the hex schmitt-trigger inverters - with RC delays between output and input. This is about as simple a square-wave generator as you could imagine, but one complication is that the trigger levels are very loosely specified. In theory they could even vary considerably across different gates on the same chip. Hence this makes it difficult to specify the RC values in advance of building a test rig around the actual chips to be used. I'll just have to live with that, I suppose, and work out an initial guess based on the "typical" specification.

The output of each oscillator is used to conditionally ground (through a Schottky diode and resistor) the corresponding capacitor acting as an envelope generator. This capacitor is charged through a PMOS transistor driven by the RIOT, and the grounding action of the oscillator causes it to decay more-or-less exponentially. There is a node in this arrangement which contains a decaying square wave, and this is tapped to a simple resistive mixer. The common line of this mixer is the input to the first op-amp, which is wired as a bandpass filter, and the second op-amp produces a unity-gain inversion of the first's output, both referred to a midway point between the power rails. A small speaker is then connected between the two complementary op-amp outputs.

I don't actually know precisely how good this will sound, but there is at least some scope for tweaking before I finalise the design.
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

Today's update concerns the conversion of the 6507's RDY input into an effective "wait for interrupt" system. This is integrated into the address decoding logic, so that it is triggered by reading from an address range rather than executing a dedicated instruction.

I think I'll be using a total of three 74HCT138s in this system, of which only one is involved in address decoding. Indeed, only A11 and A12 are decoded by it, leaving four outputs unused and the other four selecting 2KB chunks of address space. The highest selects the ROM and the lowest the RIOT, of course; the next lowest selects the RTC, and the remaining one is the /WAIT trigger.

An /IRQ signal is generated in the usual way, by wiring together the open-drain /IRQ outputs from the RTC and RIOT and providing a pull-up resistor. It is not connected to the CPU, because it doesn't have an /IRQ input. Instead, the RDY signal is then produced as ~(/IRQ & ~(/WAIT)), which only needs two gates to implement, both of which I have spare on other chips in the design. A read on, say, $1000 will then stall the CPU until an interrupt occurs, and as a side-effect the real devices are deselected to reduce power consumption. (A write would also pull RDY low, but an NMOS CPU won't delay a write in this case, and will move on to another address which would pull RDY high again on the next cycle.)

I haven't yet put in a system to indicate the interrupting device through the CPU bus. This would require deviating from the usual wired-OR structure of the /IRQ line.
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

The problem of wiring up the displays just got significantly easier with the expansion of my search to DigiKey, which carries several types of LED display and driver IC that Mouser doesn't. The key to the whole thing is the MAX6954 driver, which can handle 8 16-segment (or 14-segment) digits, or 16 7-segment digits, or some combination thereof (two 7-segment digits can replace a 16-segment one). It has built-in fonts for each display type (saving me some ROM space), is available in a perfectly manageable 40-pin DIP package with a bit-bangable SPI interface, and while pricey it is much cheaper than buying multiple MAX6969s (one 16-segment digit each), and much easier than bodging something together from discrete logic and resistors.

Theoretically I could get away with one or two MAX6969 drivers and multiplex them in software, but that seems like it would quickly become a headache. Given that the cost of the MAX6954 is broadly comparable to the display modules it'll be driving, I think it's not unreasonable to use it.

One additional consequence of the lunar clock is that ideally, I should also account for timezone offset. Otherwise, the calculated moon phase could be wrong by several additional hours on a systematic basis, on top of the oscillating errors resulting from unmodelled aspects of the orbital mechanics. This would also simplify adjusting the clock on the twice-yearly occasions that are legally mandated (but utterly stupid). So the time display is now augmented by an additional sixteen-segment digit and a few extra discrete LEDs, to indicate the nautical timezone code letter and fractional-hour offset needed to represent almost all timezones in current use (the ones between -12h45 and +12h45 from UT1). Only the oddball zones on the wrong side of the Date Line (there's one at -14h00) will be excluded.

This totals eight 7-segment digits plus eight 16-segment digits in the time and date sections of the display. A pair of MAX6954s can handle this with a further 8 7-segment or 4 16-segment digits in hand, which I can use for the alarm/timer section.
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

I'm now considering an alternative display style which would give me analogue-type hour, minute and second hands, with the remainder still being in digits. The downside: it requires assembling almost 200 individual LEDs in three circles. However, since only one LED needs to be lit in each circle, a simplified driving arrangement is possible using ordinary discrete logic ICs and a few resistors. Two HCT138s are capable of addressing 64 LEDs in a matrix, which is slightly more than I actually need.
User avatar
Dr Jefyll
Posts: 3525
Joined: 11 Dec 2009
Location: Ontario, Canada
Contact:

Re: [Contest] RIOT Clock

Post by Dr Jefyll »

Chromatix wrote:
Two HCT138s are capable of addressing 64 LEDs in a matrix
Hmm, maybe a '138 paired with a '238 ? (it's equivalent to '138, but with active-high outputs) Just a suggestion.
Quote:
almost 200 individual LEDs in three circles
I'd be tempted to economize by reducing the number of circles from three down to two (for Hours & Minutes)... although it'd result in less eye candy, I admit.

I suspect the Seconds indication could be implied... maybe by a flash or flicker in one LED of the Hours or Minutes array, for example. The trick would be to hit on the right scheme -- one that's so natural and obvious that it doesn't create a distraction by drawing attention to itself.

So, a UI / Psychology challenge! :)
In 1988 my 65C02 got six new registers and 44 new full-speed instructions!
https://laughtonelectronics.com/Arcana/ ... mmary.html
User avatar
BillO
Posts: 1038
Joined: 12 Dec 2008
Location: Canada

Re: [Contest] RIOT Clock

Post by BillO »

If you used RGB LEDs you could get by with one circle of 60 LEDs.
Bill
Chromatix
Posts: 1462
Joined: 21 May 2018

Re: [Contest] RIOT Clock

Post by Chromatix »

One of the things that LEDs don't really like is being held in reverse bias for long periods of time. Driving them directly between a '138 and a '238 would keep them in reverse bias about 7/8ths of the time. However, using one of the '138s to gate a bank of PMOS transistors would instead keep all the LEDs in either high-impedance, low impedance but zero bias, or forward bias. I'm already using small PMOS transistors in the chime section, so this doesn't increase the complexity of inventory.

I'm keen to make this clock easy to read, even by someone who's never seen this particular clock before. There's no established convention for making the hour and minute hands different colours, and they move too slowly to be reliably distinguishable jut by watching for a few seconds, so using a single ring of RGB LEDs doesn't solve the problem. Using two concentric rings, separated by fixed LEDs for the hour marks, uses the established convention of the hands being different lengths. I could then quite reasonably use a smaller ring of LEDs for the seconds, similar to how most grandfather clocks are set up (the second hand is usually an extension of the main escapement shaft, hence separate from the concentric gear train of the hour and minute hands).

Fitting this many LEDs will be tedious, of course, but perfectly doable.
Post Reply