Logo ©1994-2007 Kevin Boone
My professional interests
Computing
Law
Education
Science and research

My leisure interests
Martial arts
Heritage railways
Garden railways
Motorcycles
DIY

Downloads
Linux downloads
Windows downloads
Java downloads
Perl downloads
Home automation downloads

About me
Home & family
My CV

Site info
Contact the author
Download policy
Keyword index

  Home > Downloads > Home automation downloads

twseriald: a Linux driver for TW723/TWSERIAL X10 controller

Last modified: Thu Jul 8 07:18:17 2004

Download source code for current version (C0.2)

What is twseriald?

twseriald is a Linux driver/daemon for the `TWSERIAL' X10 device. TWSERIAL is a serial interface to the TW723 automation controller, which is an X10-compatible home automation controller. The TW723 supports two-way operation, that is, it can control power devices, determine their status, and monitor remote control events. The TW723 itself is not seen very often, but it is very similar to the more common TW523 and PL513, and the software in this package should work with these devices as well.

twseriald allows the TW723/TW523 home automation controllers to be controlled over a TCP/IP port, using a very simple, text-based protocol. twseriald runs on the computer that is connected to the TWSERIAL, but can be controlled from anywhere by a network connection. This software was written to allow Java servlets to control power devices, but may have other applications. It networked mode of operation allows it to be used over the Internet, but its rudimentary security may make this inadvisable.

This software was developed for Linux, although it may be possible to adapt it for other Unix varieties. However, it does require a serial port with specific properties (see below). Not all hardware is suitable, either under Linux or anything else.

Package contents

This package contains the following components
  • Source and (Intel PC) binaries for the twseriald server
  • Samples script for stopping and starting the server
  • This documentation, which includes details of the twseriald client-server protocol

System requirements

To use any of this software you will need the following
  • A TW723 or TW523 X10 controller with TWSERIAL serial cable
  • A Linux system with a modern (2.2 or later) kernel and a serial port capable of half-duplex operation at 300 baud (this is less straightforward than it sounds: see below)
  • Linux `popt' and `pthreads' libraries (these are part of most Linux distributions, and probably installed by default).

Serial port issues

The TW723 uses half-duplex operation at approximately 300 baud, and is synchronized to zero-crossings of the AC mains voltage. Thus it has very strict timing requirements. When the hardware sends a poll request (00) byte to the computer, it expects a response within 100 msec. Ironically, dumb serial ports like those found in PCs don't have a problem with this, because they don't do much buffering. The `SE' serial hardware used in Sun Ultra workstations does not work, because its buffer size is too big, and can't be controlled in software. What happens is that this serial hardware only interrupts the PC every 8 bytes, which takes longer than 100 msec at 300 baud. twseriald does not, therefore, work with Sun Ultra hardware (but this is a limitation of the TW723, not this software). twseriald has been tested with a number of different Intel PC platforms with reasonable success. With some systems I have had to slow down the transmission of data artificially; the places in the source where this might be necessary are well marked.

Building the package

Pre-requisites

To build the twseriald server, which is written in C++, you will need the following:
  • This package
  • A Linux system with a modern (2.2 or later) kernel
  • The development libraries and include files for the `pthreads' package
  • The development libraries and include files for the `popt' package. popt is used for parsing the command-line arguments
  • A complete C++ compiler with Standard Template Library support. Any recent GNU C++ version should be OK

Building and installing the server

Edit the Makefile as appropriate, and then do:
make 

Testing the server

Start the server by executing the compiled program, with full debugging output.
./twseriald -v 2
To test the server you don't necessarily need to have TW723 hardware attached, but you will need an accessible serial port. If you do have the hardware, then you should expect to see this message:
twseriald: TW723 is stable
Shortly after startup. This indicates that the server has received the `00' byte from the controller that indicates that it is ready to receive data.

Now you should be able to control hardware using the TELNET prompt. For example:

telnet localhost 30000
abc on 1 1
Here `abc' is the password (password checking is not enabled by default, but the protocol requires something in that field). `on' is an instruction to switch something on, and the two `1's are housecode 1, unit 1. Of course, you will need to adapt this to suit your hardware. If the command is successful, the server should respond with
0 OK
Full details of the protocol are provided below.

Installing the server

The command make install will copy the binary to the installation directory, which by default is /usr/sbin. In the distribution is an `init' script to start and stop the server at boot time and shutdown time. This is not installed by default. Typically you would copy this script to /etc/init.d and create links to it from /etc/rc3.d with names denoting the requires startup order. This is a Linux issue, not a twseriald issue.

The twseriald server

Overview

The server is fully multithreaded, meaning that it can support a number of simultaneous clients. It multiplexes access to the TW723 hardware so multiple clients can, in theory, be controlling devices at the same time. It takes some trouble to avoid signalling contention, but problems can still arise as a result of limitations of the X10 protocol. The server itself does not manage retries; it is the job of the client to do this if an operation does not appear to have succeeded. In addition, the server does not do anything `smart', it simply converts text to X10 commands and vice versa. There is, for example, no X10 command that means `set brightness level to 50%', so twseriald can't do this either. Again, clients can implement this by interacting with the server in a more appropriate way.

Command line

twseriald accepts the following command-line switches.
  -p, -port=port             IP listen port
  -v, -verbose=level         logging verbosity (0, 1 or 2)
  -d, -device=device         serial device
  -w, -password=password     password
The default IP port number is 30000. There is no compelling reason to change this unless it clashes with something else. The serial device defaults to /dev/twserial, which could be symbolically-linked to the real device; alternatively specify the device on the command line. The verbosity and password switches are discussed below.

Client security issues

twseriald supports a very simple security mechanism; each command sent from the client must be preceded by a password. There is only one password, and it is sent in plaintext, so it is best not used over the Internet. If the `-password' option is not supplied, password checking is disabled, but the client must supply some text in the password field (it doesn't matter what it is).

System security issues

twseriald must not be run as root; there is no need to, and it may present a security hazard. Ensure that whatever account does run it has read and write permissions on the serial device. To use twserial in an init script, use `su -c' to run the twseriald command as a named user. A sample is the provided `twserial.d' script.

Logging

twseriald writes logging information to standard output. The amount of logging can be set on the command line to 0 (critical errors only), 1 (errors and warnings), or 2 (heaps of debugging output). On a Linux system you can use initlog to redirect the standard output to the system logger if necessary (see the twserial.d script for details).

Shutting down twseriald

twserial attempts to shut down gracefully if it receives an INT or TERM interrupt. So, at the command line, the `elegant' way to shut it down is: killall -INT tweriald If you must shut down over the network connection, the `shutdown' command has this effect, but is not very graceful (it is difficult to shutdown gracefully using an open network connection).

twseriald protocol

overview

The client-server protocol is text-based, and could -- at a pinch -- be managed at a TELNET prompt. It's certainly possible to do this for debugging. The protocol is strictly request-response: the client issues a request and the server responds to it. Although the server logs remote control events, it only issues them to the client on demand. This makes writing the client very simple.

Requests

Each request has the following form: [password] [action] [arguments...] The password field must have something in it, even if passwords are disabled. The `action' and `arguments' are as follows.
  • send [event] [housecode] [unitcode] sends the specified event
  • listen enables event logging
  • unlisten disables event logging
  • events get the events logged so far
  • status [housecode] [unitcode] gets the status of the specified device
  • shutdown shuts down twseriald immediately
There is no specific `quit' request; the client should just break the connection when it has finished.

All control operations are carried out using the `send' command, which takes an event code, a housecode, and a unit code (not always relevant). There are 7 different event codes, defined in x10event.h

#define X10EVENT_LIGHTS_OFF			100
#define X10EVENT_LIGHTS_ON			101
#define X10EVENT_ALL_OFF			102
#define X10EVENT_DIM				103
#define X10EVENT_BRIGHT				104
#define X10EVENT_ON				105
#define X10EVENT_OFF				106
Of these, only ON and OFF require both a unitcode and a housecode. The other either operate on the unit last selected (e.g, `dim') or affect all units with the same housecode.

For example, to send an `on' event to unit 1 on housecode 1, the string is:

[password] send 105 1 1

Responses

The response to all commands is an integer, followed by a space, followed by an arbitrary text string. The integer is either zero, meaning `success', or an error code. Error codes are 100 or greater. With the exception of the `status' and `events' requests, the text string is simply a textual representation of the error code.

For the `status' request, the text is a digit `1' meaning `device is on' or `0' meaning `device is off'.

For the `events' request, the text is a list of event codes, and the whole reponse looks like this:

0 E:H:U E:H:U
Where `E' is the event code (same meaning as above), `H' is the housecode (1-16) and `U' is a unit code. Where there is no unit code, the U field is zero.

Error codes

Errors are indicated by a non-zero return code from the server. Usually a short textual description of the error is given as well. This section describes the error codes in more detail. C-language constants are defined for these errors in twserial_protocol.h.
100 Syntax error: the client sent something meaningless like an empty string
101 Bad command: the client send a command other than send, listen, unlisten, events, status, shutdown,
102 Although the command was recognized, an incorrect number of arguments was supplied.
103 A non-number was received where a number was expected.
104 Invalid argument: typically a number was out of range
105 Client tried to get events, but event listening is not enabled
106 Timed out while waiting for X10 line activity to subside. This can happen in normal circumstances in a very `busy' environment. The client should wait a short time and try again.
107 Timed out while waiting for a device to respond to a status request. This normally indicates that the device simply does not understand status requests. The X10 protocol does not provide a way to find out.
108 X10 protocol error reported by TWSERIAL. This may happen in normal circumstances, but if it is frequent it may indicate that your serial port hardware is incompatible.
109 Access denied; client did not supply the correct password. The server password is set using the `-w' switch on its command line.

Notes

  • twseriald is a `thin' wrapper around the X10 protocol; it does little error checking, and does not attempt to implement more sophisticated features like timing, fading and brightening, or even re-tries in the event of failure. These should be implemented by the client.
  • Housecodes and unit codes are one-based, not zero-based; both should be in the range 1 to 15.
  • the `listen' and `unlisten' requests control whether events are logged. After `unlisten', event retrieval does not work but if there are events in the queue they are not cleared, and are available after the next `listen' request. Event listening is per-client. If clients are connected concurrently, some may be listening and some not.
  • The X10 protocol is very simple; there is, for example, no way for a controller to query the capabilities of devices. The twseriald daemon will do whatever its client tells it, however inappropriate. For example, it will send a `dim' event to a non-dimmable device if requested. It is the job of the client to ensure that the correct operations are requested.

Known issues

  • twseriald waits for the controller to indicate that it is idle before sending a command (because TWSERIAL uses half duplex signalling and there's no buffering). If it has to wait too long it gives up. The default timeout is 10 sec. This can happen naturally if there's lots of button-pressing going on nearby.
  • If commands are issued in very quick session, twseriald has occasionally been known to hang. Please contact me (see below) if you find this happening on your system.
  • Even though TWSERIAL has some buffering at the RS-232 level, it is still fairly intolerant of timing problems. Not all serial hardware works.

Legal

This software was written by Kevin Boone and is (c)2000-2001 Kevin Boone/Web-Tomorrow. It is distributed free-of-charge in the hope that it will be useful, but there is no warranty or commitment to support. Use at your own risk.

   
Search

WebThis site

Shameless plug

By the author of this site. Buy on-line from Amazon USA | UK

Editorial
So you want to be a university lecturer? Read this first!

Speak like your boss: new developments in managerese

Computing features
File handling in the Linux kernel: an in-depth look at how Linux handles files, filesystems, and file I/O

All sorts of Linux stuff

Confused about CLASSPATH? answers are here

First steps in EJB using jBoss (recently revised for jBoss 3.2)