for communication via the TNC - PC serial interface
by Jan Schiefer, DL5UE / G0TRR and Dieter Deyke, DK5SG / N0PRA
I assume you are familiar with the KISS protocol as it was defined by Brian Lloyd, WB6RQN and programmed by Phil Karn, KA9Q at 6th August 1986.
Kiss is described clearly in "The KISS TNC, A simple Host-to-TNC communications protocol, Mike Chepponis, K3MC, Phil Karn, KA9Q"
Herein, the second bype of a KISS frame was defined a the command byte.
The low nibble is used for 16 possible commands, as there are: 0=Data follows, 1=TX-Delay follows, 3=Slottime follows, 4=TX-Tail follows, 5=Fulldup on/off follows, FF=Exit/System/Return.
In February 1991, Jan Schiefer, DL5UE/GØTRR and Dieter Deyke, DK5SG/NØPRA suggested a enhanced and compatible KISS which added the possibility of a checksum over the KISS data packets to ensure data integrity over the RS232 line. The enhanced KISS was called SMACK (Stuttgart Modified Amateurradio-CRC-KISS). Here some explanations about SMACK:
KISS was suggested in 1986 by Phil Karn, KA9Q [1]. For his TCP/IP-software a protocol was required, which made an access to packet-radio possible below the AX.25-protocol level. KISS makes a level 2a possible. The task of the TNC is now only the media access control (data carrier detect, channel-busy detection, p-persistence-mode) and the conversion of the synchroneous HDLC-data on packet channels to asynchroneous RS232 format. The KISS-protocol manages the separation of the packets by delimiters, the treatment of the delimiters which may occur inside the data stream and defines a simple set of commands for setting the TNC parameters. There had been made arrangements to operate TNC with more than one packet channels or more than one modem with this commands.
The host computer communicates with KISS in form of packets. The beginning of such a packet is distinguished by the delimiter FEND. The so-called command byte follows. It defines whether the packet is a data or a command packet and which command it is. All commands use only the lower 4 bits (lower nibble) of the command byte, except the reset-command (Command-byte=255). So, the upper 4 bit are left to adress the channel number of multi-port TNC. So, all 16 modem channels (ports) may be adressed and set with different parameters individually.
As we did not find TNC with more than 7 modems, we decided to use the most significant bit of the command byte for the checksum flag purpose. If this bit is set, the packet is a data packet WITH CRC checksum (checksum feature is used with data packets only). At all packets with this bit set, a CRC checksum is appended, least significant byte first. The following picture shows the frame format of a data packet without and with checksum for different ports:
FEND |
0x00 |
DATA |
DATA |
... |
DATA |
FEND |
KISS-frame without checksum, adressed to port 1
FEND |
0x10 |
DATA |
DATA |
... |
DATA |
FEND |
KISS-frame without checksum, adressed to port 2
FEND |
0x80 |
DATA |
DATA |
... |
DATA |
CRC LOW |
CRC HIGH |
FEND |
SMACK-frame with checksum for port 1
FEND |
0x90 |
DATA |
DATA |
... |
DATA |
CRC LOW |
CRC HIGH |
FEND |
SMACK-frame with checksum for port 2
We want to emphasize, that only data packets are CRC-secured. So, it is avoided that there are no more commands to the TNC possible if TNC and host are incompatible according the CRC / non-CRC-mode.
A SMACK-TNC works in KISS-mode after power-on and does not use a checksum. As soon as it receives the first packet with a checksum, it switches ist transmit routines to CRC too. This mode can be ended only by a reset. The host behaves in the same manner. If a standard KISS-TNC is connected to the host computer, it will drop the CRC-Frames received from the host because of the command bytes, which are unknown to it (MSB set) and continue in ist normal mode.
This method has the advantage, that KISS as well as SMACK-TNCs can be operated with a host computer without need for changeing the configuration. We'll show this two possible situations here:
Case 1: KISS-TNC
Host |
TNC |
- Sending a single packet with CRC and switches ist transmitter back to normal-KISS. |
|
- Receives a frame with the unknown command byte 0x80 and drops (ignores) it. |
|
- Continues to transmit KISS-data without checksum |
|
- transmits all data without checksum |
Case 2: SMACK-TNC
Host |
TNC |
- Sending a single packet with CRC and switches its transmitter back to normal KISS. |
|
- Receives a frame with CRC-bit set and switches ist transmitter routine to CRC-on. |
|
- Transmits data without checksum. |
|
- TNC sends the first frame WITH checksum. |
|
- Receives a frame with checksum-bit set and switches ist transmit
routine to checksum-on. |
|
- Uses SMACK-data with checksum now. |
Independant from the state of the transmitter (CRC / no CRC) all received frames are treated as follows:
Received frame |
Action |
No CRC |
process frame |
With CRC, checksum OK |
process frame |
With CRC, checksum test failed |
ignore / drop frame |
This protocol assumes, that a KISS implementation drops all frames with an unknown command byte. This fact is demanded in the KISS-specification [1].
CRC-calculation and hints on the implementation
We cannot explain theory of cyclic redundancy check (CRC) here. See the literature or the papers of Michael Röhner, DC4OX [2]. We shall cover the details for programming the CRC generation routine.
As check polynom the CRC16-polynom is used. This looks like
X
16 + X15 + X2 + 1The CRC-generator is preset to zero. The routine has to process all data-bytes including the command byte 0x80.
It is known, that the KISS-protocol uses the FEND-character as frame delimiter. (0xC0).
If this character occurs within the data stream, this is an special case which is called SLIP-encoding and explained later.
The CRC has to be calculated BEFORE the SLIP-encoding takes place and checked AFTER the SLIP-decoding. There are the following reasons to do so:
- The CRC bytes may contain FESC, TFEND, FEND etc. | |
- The SLIP en/decoder is used in some implementations (e.g. WAMPES) independently from KISS to establish e.g. the link to the unix-kernel. Here, CRC checks would be desirable, but would not be understood by tho other side. |
So, the CRCs belong logically to the KISS layer.
The calculation goes like this:
- preset the CRC-generator to zero. | |
- put all data bytes into the algorithm one by one, including the both CRC-bytes. | |
- at the end the value of the CRC-generator has to be zero again. If the value is not equal zero, a transmission error occured and the frame has to be dropped. |
Some algorithms for CRC generation are described in [2].
The CRC-table can be built with a little C-program:
unsigned short Table[256];
const int Rest[8] = { 0xC0C1, 0xC181, 0xC301, 0xC601, 0xCC01, 0xD801, 0xF001,
0xA001 };
main()
{ int i, j;
unsigned short value;
for (i = 0; i < 256; i++) {
value = 0;
for (j = 0; j < 8; j++)
if (i & (1 << j))
value ^= Rest[j];
Table[i] = value;
}}
If this algorithm is coded in assembler, it uses much less space as storing the table itself. The theory can be found in [2].
Until now (1988) SMACK was implemented in the following systems:
- WAMPES | |
- SMACK, Version 1.3. This software was developed by Jan Schiefer, DL5UE from the K3MC TNC2-KISS-implementation. | |
- in KISS of the NORD><LINK-firmware from version 2.4 (used in mose European TNC2) | |
- in TCP/IP-software NOS | |
- in the TNC3/31 and TNC4 software by Jimi Scherer, DL1GJI |
Literature
[1] Karn, Phil, KA9Q; Proposed "Raw" TNC Functional Spec, 6.8.1986;
veröffentlicht in USENET-News;
[2] Röhner, Michael, DC4OX; Was ist CRC?; veröffentlicht im Packet-Radio
Mailbox-Netz, Mai 1988
[3] FTP Software, Inc.; PC/TCP Version 1.09 Packet Driver Specification;
Wakefield, MA 1989
[4] Schiefer, Jan, DL5UE; WAMPES - Weiterentwicklung; Vortrags-Skriptum des 5.
überregionalen Packet-Radio-Treffens; Frankfurt 1989
Multiport TNC adressing in KISS/SMACK-mode
d7 |
d6 |
d5 |
d4 |
d3 |
d2 |
d1 |
d0 |
KISS/ |
PORT |
PORT |
PORT |
COMMD |
COMMD |
COMMD |
COMMD |
For transmitted and received frames, the command byte contains the
port-information in the d6, d5, and d4 bit. With TNC2 and TNC31 (single port
TNC) and TNC3 (port 1), d6, d5 and d4 are zero.
The TNC3 port 2 data is send with d4=1. To transmit frames via port 2 of TNC3,
d4 has to be set to 1.
There may exist TNCs with more than 2 ports. The adressing however limits the number of modem-ports to a maximum of 8.