paperlined.org
EE > microcontrollers > pic > projects > portable_VT_terminal > ti_86_link_port
document updated 18 years ago, on Apr 5, 2006
All About the TI-86 Link-Port

(this document is simply the expanded version of the zipfile found here, and has no modifications other than this message have been made to Joe Clussman's work)

All About the TI-86 Link Port

By Joe Clussman


Preface

The available documentation on the TI-86's link port is relatively comprehensive, although scattered and sometimes confusing or contradictory. However, there has not been a complete document to date that properly addresses the method of programming for the link port in Z80 assembly language. Here is my attempt at an understandable "all you really need to know" document. Alas, this document comes at a time when programming for the TI-86 is pretty much dead. And unfortunately, there weren't as many multiplayer games as there ought to have been...


Topics:

The Basics
Physical Implementation
Circuit Implementation
Theory of Communication
Port Seven, In and Out
TI-LINK Protocol
Hints and Tips
Appendix
Contact


The Basics

The TI-Link port allows for asynchronous serial communication to and from the calculator. The port works off of the standard TTL signal levels (0 Volts and +5 Volts). The link cable is composed of three conductors: two Signal wires and one Ground wire which serves as a voltage reference. Data bits can only be transferred in a single direction at any given moment. There is a standard protocol which governs the communication from one calculator to another calculator, a Personal Computer, or a CBL/CBR.



Physical Implementation

The TI-Link cable connector is a standard 2.5mm "stereo jack." The three connections on the jack are called the tip, ring, and sleeve. And the fancy coloring does serve a purpose disclosed shortly below.

The link cable is wired "straight-through," versus being a "crossover" cable. This means that the tip of one connector is wired to the tip of the other, and so-on.

Now about those fancy colors-- cut away the rubber coating on the link cable, and three internal wires will be found. The colors of the insulation on those wires are red, white, and black (or bare copper wire). The white wire connects up with the "ring" and the red one connects to the "tip." And since the white and red wires have no official names, they'll just simply have to be called the "White" and "Red" wires.


Circuit Implementation

Below is the schematic for the link portion of the TI-86 calculator.

Things to Notice

Although not shown, inputs LP1 and LP2 are connected to two outputs coming from the Z80-instruction compatible CPU, and outputs LP3 and LP4 are connected to two inputs going into the CPU. Notice I stated "Z80-instruction compatible CPU," because it is not a true Z80 processor-- its not even manufactured by Zilog, but by Toshiba! This custom CPU contains "on-chip" ports which allow for this kind of a direct connection.

Diodes D7 and D8 are present to protect the inputs to the port on the CPU from an excessive positive voltage from the jack. However, these diodes do little to protect the CPU from negative polarity. (If a sustained negative voltage, even as low as -3V, were allowed directly into the CPU, it would most likely be damaged.)

Then there are the "fuse-links," which are actually really low value resistors, maybe 0.1 Ohm. In the event of a negative voltage causing excess current, they'd probably be the first to blow, hence their name. But maybe they are just used as jumpers, as the source I based the picture on suggested.

Transistors Q6 and Q7 are used to amplify the signal coming from the CPU, and the 471 Ohm resistors protect those transistors from sinking excessive current in normal operation.

How the output circuit works:

As stated before, wires LP1 and LP2 are connected to outputs from the CPU. The signal coming from the CPU is digital, either a zero or a one. Let's just focus on one of the two identical output circuits. A zero (0V) at the base (B) of the transistor will not turn it on, allowing a weak +5V to pass through the 10K Ohm resistor and diode, and appear at the signal output of the jack connector. A one (+5V) at the base of the transistor, however, will turn it on. This will drop the signal output at the jack connector to very near 0V, because the pull-up current will flow through the 10K Ohm resistor, the diode, 471 Ohm resistor, and NPN transistor to Ground.

An Open-Collector NOT Output Circuit!

To get even more technical, this output circuit is called an Inverter or NOT circuit. Why? Because the output is the reverse of the input. Also, it is Open-Collector, because the collector (C) of the transistor is used as an output and is not connected to another transistor, but is instead being supplemented by a weak pull-up resistance to get that output to the positive level. That and the fact the output can be shorted to ground without any damage... Whoah... Did I just lose you? I hope not, because it's important.

How the input circuit works:

Now that we got the sending of information out of the way, let's try the input section. (I swear, it's not that complicated!) Right now, we don't have anything connected to the jack, and we'll say that the two NPN transistors are off. A +5V will flow through the 10K resistors and into two inputs of the CPU through LP3 and LP4. The CPU will read the state of the two inputs as a binary ONE.
Let's turn the NPN transistors on again, diverting the pull-up current through them. The voltage at LP3 and LP4, as well as the output at the connector, will also sink down to near 0V. Thus the CPU will read the state of LP3 and LP4 as a zero.

What if another TI-86 is connected to this circuit one using the link cable? This other calculator can drive the signal wires at the jack either high or low, +5V and 0V respectively, using this exact same circuit. There are four possible states...

  1. Let's say a weak ONE (+5V) is being input through the white wire. Transistor Q7 is off for now. If read, the state of LP3 will be a one.
  2. What if the white wire drops to zero (0V)? Now current will flow through the 10K resistor, diode D8, to ground on the other calculator. If LP3 is read, a zero will be detected.
  3. Let's keep the white wire at zero and turn on Q7 (by talking LP1 high). Now the current coming from the 10K resistor will also begin to flow through Q7 to ground. LP3 will still be read as a zero.
  4. Fourth, and finally, the white wire goes high. Q7 is still on though, sinking the current from the 10K resistor through it. LP3 is yet again read as a zero. Notice something? A zero always overpowers a one!

A note about the inputs

If one wants to interface a circuit to the TI-86 link port to a digital output, two rules should be followed:

  1. Never take the signal wires out of the voltage range. This is a serious issue with homebrew link cables connected to a serial port which can have voltages as high as +/- 15V!
  2. Don't drive the signal line with a strong direct connection to +5V or with a push-pull logic gate; use a diode and a pullup resistor, an open-collector gate with a pullup resistor, or at the very least a series resistor.

With the technical details of the hardware out of the way, the focus can finally shift to the software aspects.


Theory of Communication

The way the TI-86 sends serial data is rather elegant. Instead of sending a stream of data bits at a regular interval, the communication method is completely asynchronous. It's essentially handshaking and data all in one, versus having a system with handshaking that signals when data can be sent...
We need a diagram:

Note again that the inactive state is both lines at a binary one (+5V). Now for an explanation of how either a zero or a one is sent:

When sending a zero bit:

When sending a one bit, the process is the reverse:

Simple, effective, and it works out quite well in a system where accurate timing is unavailable and outside EMF interference is not too high...

Now, it's evident that a single bit can be sent, but sending just a single zero or one is useless. In practice, the communication sends eight of these bits at a time, followed by a short wait. This, of course, is a data byte. The transmitting end of the link sends the lowest significant bit (LSB) first, ending with the most significant bit (MSB).

A byte itself is still pretty useless, so a whole series of bytes are sent, which composes a data packet. You can find more about this is in the TI-LINK Protocol section.

Transfer rates are typically around 45 to 50 Kbps, and the timeout period for a receive error is supposed to be 3 seconds.


Port Seven, In and Out

Port 7 is where the link port data can be accessed directly from an assembly program. Data is written to and from port 7 with the OUT and IN instructions, respectively. The table below contains the test data obtained with the "Internal Link Test" Program.

Wrote To PortPhysically
Measured
Port Read
Value??OTFFINWHITERED??OTFFIN
$FC111111000V0V00001100
$E8111010000V+5V00001001
$D411010100+5V0V00000110
$C011000000+5V+5V00000011

Note the following things about the above table:

How to OUT

Bit 5 controls the White wire, and bit 4 controls the Red one. Notice how things get inverted. Take for example the last row where the value $C0 is written, both the White and Red wires rise to +5V. All of the TI-86 programs whose sources are available seem to use the instructions below to change the logic levels of the wires:

        ld A,$C0      ;White wire +5V, Red Wire +5V
        out (7),a
        ld A,$D4      ;White wire +5V, Red Wire 0V
        out (7),a
        ld A,$E8      ;White wire 0V, Red Wire +5V
        out (7),a
        ld A,$FC      ;White wire 0V, Red Wire 0V
        out (7),a

How to IN

Bit 1 is the status of the White wire, and bit 0 is the status of the Red wire. To read the status simply get the value from port 7, mask off the other bits, and then use a compare instruction as in the example below.

        in A,(7)
        and %00000011       ;Only bits 1 and 0 matter
        cp 0                ;In this case check for both being at 0V.


TI-LINK Protocol

Like so many other forms of data transmission, the link port protocol uses command/data, acknowledgment, and end-of-transmission packets.

The packet is composed of the following:

Machine ID Byte

The Machine ID tells what device is sending the data. A value of $86 (hex digits) is, as you may have guessed, the TI-86 calculator; and a value of $06 is the Graph-Link software expecting a TI-86 on the other end. Follow the pattern for the other calculators. An upper nibble of A-F has never been observed, so perhaps one could use this to differentiate a software program.

Command Byte

The command byte tells what this packet is all about. Some examples are: an acknowledge packet has a command byte of $56, $15 means just data, and $5A indicates a checksum error. There are other values, and if interested refer to the TI-86 Link Protocol and Variable Format Guide by Tim Singer

Data Length

This gives the length of any data to follow. A value of $0000 indicates NO DATA and therefore no data bytes or checksum is to follow. If the value is non-zero, it can be in the range of 0-65535 bytes. One byte of data would be sent in the order of $01 then $00 in low-byte then high-byte format. That 16-bit value is the reason why those group files are limited to around 65000 bytes.

Data Byte(s)

This is a string of bytes representing something, whether it be a floating point number, string, or program. If this is any named variable (like what would be found in the VAT), a 12-byte variable header would come before the actual data.

Checksum

This is the 16-bit wrap-around unsigned sum of all the bytes in the data section. It is sent as low-byte then high-byte format.

A Simple Example:

In the Graph-Link Software, there is an option to get what is currently displayed on the calculator's screen. When the button is clicked, the software sends a command packet to the TI-86 composed of $06, $6D, $00, $00. The TI-86 responds with an acknowledge of $86, $56, $00, $00, and then sends a data packet of $86, $15, $00, $04, [1024 bytes of screen], [16-bit checksum]. The software then acknowledges back with $06, $56, $00, $00.


Hints and Tips

The operating system does not use the previous state as stored in bits 2 and 3 of port 7. Furthermore, it will attempt to use its own routine when it detects a 0V on either of the lines. If this happens inside your assembly program it will hang the calculator.

Therefore, your assembly program must be sure to set the lines back to the +5V state by OUTing a value of $C0 before exiting. But it gets a little worse, as routines like _getkey check for link port activity, and again, if both the data lines are not at +5V, the function will hang.

Do not assume that your transmissions will be error free. Maybe not from the errant cosmic particle that comes zipping from Epsilon Eridani, but from the simple fact that some friend could come along and yank the cable in the middle of transmitting a byte.

In addition, transmission tends to get a little bit flakey when the battery level is low. In programs that extensively use the link feature, checking the battery level upon starting the program would be a good idea.

Thus, a robust program would have timeouts, some sort of checksum calculation, and battery level measurement to ensure proper error detection and recovery.


Appendix

Links to program listings

FilenameDescription
linktest.zipWire status reader/changer
link2.asmTransmit and Receive Byte Routines
linktxrx.zipByte reader/sender program

References

A Programmer's Guide to the TI-86 Ports by Alan Bailey

TI-86 Link Protocol and Variable Format Guide by Tim Singer


Contact

Joe Clussman, who can be contacted at DrQueue@Hotmail.com, wrote this document. Especially contact me if something is backwards :)

Original Writing: 6 March 2001
Revised: 1 July 2002