2. Modem

You are going to connect to the internet with your modem - yes? So you want to be sure that your modem works, and that it is working correctly. What can go wrong?

2.1 A Normal Modem
2.2 COM IO port conflict
2.3 Modem on wrong IRQ
2.4 irq conflict
2.5 HINT: COM-3 IRQ-5
2.6 /dev/modem -> /dev/cua2
2.7 Permission Denied
2.8 Modem not spd_vhi
2.9 Modem at correct BAUD rate
2.10 CONNECT 115200 -or- CONNECT 28800
2.11 Modem prefers rtscts
2.12 Sharing the modem with a getty
2.13 Other possible problems
2.14 Modem Tests
2.15 Query UART during session
2.16 Test with minicom
2.17 Dead modem card
2.18 Modem card not jumpered to defaults
2.19 Screen Capture with minicom
2.20 Reset Defaults with minicom
2.21 Check from boot
2.22 Now what ?


A Normal Modem

If it's a Windows specific modem, be worried.

You want a normal V34 modem, that isn't tied to the OS. It might still work, but you will have to look into Plug'N'Play and hope that the compression is done by the modem, and not the software.


COM IO port conflict

Each UART serial chip (and surrounding 'glue' hardware), must be configured to use unique IO port addresses. This is usually set on the card using a jumper that switches the card to use COM1 COM2 COM3 COM4 addresses. I.E. changing the IO_ADDR changes the COM port number.

As far as hardware reasons go, the IO addresses are "arbitrary", but the PC design spec, reserves specific port mappings, so that everyone can 'find' the UART easily, and call it the same name.

0x3F8 --> COM1
0x2F8 --> COM2
0x3E8 --> COM3
0x2E8 --> COM4

UART IO_ADDR's are standard, the only conflict you are likely to have, is if you have two cards installed that both provide COM ports.

You know which IO_PORTS the hardware is using, because the BIOS looks and reports them during system startup, and so does the kernel. See dmesg(8)


Modem on wrong IRQ

The jumpers on the card, tells the card which IRQ to use. Every card must use different IRQ's. You have to tell the software driver what IRQ you jumpered the hardware to. RTFM: setserial(8)

setserial /dev/modem reports the IRQ that the driver is currently trying to use. If your hardware is on IRQ-5, the driver won't know, unless you set it with a line in /etc/rc.serial or /etc/rc.local (or other).

setserial /dev/modem irq 5

This tells the driver where the modem really is. Once you have manually checked that it works, put it in one of the system boot startup files, so that it happens automatically (see Issue-2-SysBuild).

I don't understand how, but with the wrong irq, the serial driver still managed to send small pieces of data to and from the modem (hint: <20 bytes), but it was extremely slow, with 7 seconds delay.


irq conflict

You cannot have two different ISA cards, on the same irq. One of them must move! (or be disabled).

This is a characteristic of the ISA bus, and some machines allow you to "get away" with it. Don't be lucky, be certain.

The default COM port IRQ's are for when they are all on the same card or on the main-baord. The standards mean that you should use the correct IO_PORT but can use ANY IRQ. Ignore the following table of defaults:

COM1:   IRQ 4
COM2:   IRQ 3
COM3:   IRQ 4  <-- use IRQ-5 for internal modem card
COM4:   IRQ 3

You can see which IRQ's are currently in use using cat /proc/interrupts Refer to Issue-1-Hardware for more details.



The COM3 IRQ-5 setting works for my internal modem. It's also fixed other peoples problems too! Other settings should work, but if you are having problems, re-jumper your cards.

If you've just installed a new internal modem, and IRQ-5 is already in use, you can use any IRQ that is genuinely free. Just make sure that you haven't already allocated it to another card.

Plug-and-play cards might not have jumpers, and use software instead. "Windows Only Modems" are not standard, avoid them.

If you have an external modem, the IO_PORT and IRQ are for the internal card (main board) that holds the serial UART, so use whatever works.


/dev/modem -> /dev/cua2

Simce my modem is COM3, the Linux device is cua2. You can also use ttyS2 the difference is in the kernel level locking.

COM1:   /dev/cua0  ttyS0
COM2:   /dev/cua1  ttyS1
COM3:   /dev/cua2  ttyS2
COM4:   /dev/cua3  ttyS3

I only have one modem, but lots of apps need to be told which device to use. I tell them all to use /dev/modem and create the following link:

ln -s cua2 /dev/modem

Then if it breaks, and I revert to the old external 14.4K monster, I just switch the link, and all the apps are already re-configured! RTFM: ln(1)


Permission Denied

In-order to establish a PPP link, you must have root permission, so the permissions on the device is mostly irrelevent. However, if you also wish to send faxes, or use minicom, then non-root user(s) must have write permission on the modem (read also helps). Remember to set it on the device node, not the link to the device. RTFM: chown(1) chgrp(1) chmod(1) which make system calls: chown(2) chgrp(2) chmod(2)

vi /etc/group
chgrp phone /dev/cua2
chmod 660 /dev/cua2

You also need to add each of those users to the /etc/group file (if the phone group doesn't exist the above chgrp command would have failed). After editing /etc/group, the relevent users need to logout and login again for it to take effect. The following line appears in /etc/group


Any GID number (18) is OK, as long as it is unique on your system.


Modem not spd_vhi

The old POSIX, can't nominate BAUD rates above 38400. This is because of the bits in the termios structure, and the stty(1) documentation.

To get round this, Linux has a hack, where the driver UART runs at 115200 BAUD, but the kernel reports 38400 with spd_vhi set. If you set spd_hi and 38400, you get 57600 BAUD.

setserial /dev/modem spd_vhi
stty 38400 < /dev/modem

To get around this, newer releases of DIP and PPPD have extra Linux intelligence, which does the setserial spd_vhi for you. IE you request 115200 in the pppd options, and it makes sure that you get it. But if you asked for 38400, should it ... ?

Beware! If you have an old minicom, dip or pppd this might not be true. If in doubt check by running a suitably designed experiment. Then update your rc.serial file.


Modem at correct BAUD rate

Well it would run at 115200 if you selected 38400, but you didn't, so it gives you the "default", or "as currently found" which may be 9600.

Two V34 modems will still connect at V34, even if the surrounding serial wire(s) are limited to 9600, but the overall connection will be slow.


CONNECT 115200 -or- CONNECT 28800

You can tell the modem to report the speed of the (virtual) serial wire, or the speed of the phone line. It only tells you when it actually connects, so you will have to run two experiments and make two calls.

This is how you know that setting spd_vhi worked.

The command AT S95=47 (on my modem) tells it to display CONNECT 115200, S95=46 tells it to display CONNECT 28800 (or whatever the line quality is). Different modems use different S95 registers, check your modems manual.

You should run it once, to confirm 115200. Normally, you want it to report the actual connect speed (28800), since that can vary, and you want to know.

If the modem is an external one, and the serial cable picks up a lot of "noise", you may have to use a speed slower than 115200.


Modem prefers rtscts

There isn't much in it, especially with control-character escaping, but RTS/CTS is preferred over XON/XOFF.

Of course, you have to make sure that it is switched on! With pppd you simply add rtscts to the options list, with slip you can set it in the calling shell script, and with minicom it is set in a menu somewhere.

Since I like RTS/CTS so much, I try to have it set as soon as the system boots (so you get it by default), and set it within each application (script).

stty crtscts < /dev/modem

NOTE: if /dev/modem isn't working, the above command might wait forever for a result. If you put it in /etc/rc.d/rc.serial and your hardware breaks, you will have to boot into single user mode (which doesn't run the /etc/rc.d scripts). Putting in an "echo" that says what's happening when, will tell you where your system stops.


Sharing the modem with a getty

Both programs (pppd and getty) must agree on the locking mechanism and name of the lock file. Note that /dev/modem and /dev/ttyS2 will create two different LOCK files! So be consistent, always tell the application to use /dev/modem, and it will use /var/lock/LCK..modem

The getty might want to (re-)initialise the modem, after pppd has finished, to reset options like auto-answer and number of rings, it does this automatically, mostly by checking every 10 seconds to see if the device is still locked. Look at it's log file and prevent it from filling your disk!


Other possible problems

The modem's AT-S99 settings can be saved and loaded in non-volatile memory, so don't be supprised if ATZ doesn't fully reset the modem. Instead see what it is set to and either override it or manually store some improved settings.

(NOTE: do not save them every day, NVRAM has a limited lifespan).

Most modems have intelligent defaults, but yours might do something strange that needs attention. It may need some AT flags to make it behave. If you have a relevent URL that explains what needed to be done for your favourite modem (which I don't have), send it every month until I cross-reference it!

Another reason for special AT commands, is a bad cable.

Modems require CARRIAGE-RETURN on AT command lines.

Remember, that the people with the REAL answers (that's not me), are too busy solving problems to write docs. Linux is a user supported OS, so if you had problems with your particular situation, create a WEB page.


Modem Tests

So that's how to configure it to work, and why it might not, now we need to check that it really does.


Query UART during session

In general, if a device is active, don't touch it, leave it alone! But it is important to know what the current setting actually are, as well as what they should be!

You can run these whilst a session is active. As long as you only read the settings and don't attempt to change them.

setserial /dev/modem

/dev/modem, UART: 16550A, Port: 0x03e8, IRQ: 5, Flags: spd_vhi

stty < /dev/modem

speed 38400 baud; line = 0;
-brkint -imaxbel

stty -a < /dev/modem # shows crtscts NOT -crtscts

speed 38400 baud; rows 24; columns 80; line = 0;
intr = ^C; quit = ^\; erase = ^?; kill = ^U; eof = ^D; eol = <undef>;
eol2 = <undef>; start = ^Q; stop = ^S; susp = ^Z; rprnt = ^R; werase = ^W;
lnext = ^V; flush = ^O; min = 1; time = 0;
-parenb -parodd cs8 hupcl -cstopb cread clocal crtscts    <-- HERE IT IS!!!
-ignbrk -brkint -ignpar -parmrk -inpck -istrip -inlcr -igncr icrnl ixon -ixoff
-iuclc -ixany -imaxbel
opost -olcuc -ocrnl onlcr -onocr -onlret -ofill -ofdel nl0 cr0 tab0 bs0 vt0 ff0
isig icanon iexten echo echoe echok -echonl -noflsh -xcase -tostop -echoprt
echoctl echoke

In case you missed it, look for crtscts and make sure that it doesn't have a '-' minus infront of it.


Test with minicom

Without dialing out, you can look at the modem, and see that it is alive and well.

Minicom will run the setserial option, when it opens the device. It will also initialise the modem, by sending it's AT command to the modem.

Minicom 1.71 Copyright (c) Miquel van Smoorenburg
Press CTRL-A Z for help on special keys

AT S7=45 S0=0 L1 V1 X4 &c1 E1 Q0

The modem should echo them back along with OK. If it doesn't, maybe the modem is dead, or on the wrong port. Some modems settings supress the (command) echo, but not the OK.

You should then dial out, to a plain old BBS, to see that it works. My ISP provides a BBS on the same number. Just login as guest or whatever it says on the login prompt. This also tests the phone line.

AT S97=47
ATDT 0181-123-4567
CONNECT 115200

login: _

When you first establish a connection, run one of the two tests (in the previous section) to get the CONNECT speed of the phone wire, and of the local serial cable (or virtual one). That is reassuring, although stty reports 38400, and setserial says spd_vhi it's the only utility that tells you the line speed in one number. After that check the reported sppeds from ftp, but they will suggest 2.7 KPS, which doesn't tell you if you have a fast wire or a very fast wire.


Dead modem card

Sometimes, my modem card doesn't work, (immediately after boot), but a power off, wait 10 secs, power on, works just fine!

This is probably a hardware or intermittent design fault, but it is very irritating, especially after starting X11, and several logins.

Now, I make a point of running dial_ppp test as soon as the machine is booted. This just sends ATZ to the modem, which (hopefully) replies with OK. Then I know it's working.


Modem card not jumpered to defaults

This is the same, cheap card that doesn't like being jumpered to anything other than COM3, IRQ 5. I suspect that that is all it was ever tested at in the factory.

A lot of problems went away when I put it back on the defaults, but it may be the OTHER card, that it swapped places with. Either way, it used to fail BADLY one time in four (as in complete machine lockups), now it fails once a month (not locking the machine up).


Screen Capture with minicom

To write your chat script, or dip script, you need to know what key prompts are displayed by the remote system (is it Login or login?)

In particular, my account gets a "Protocol:" prompt, where I type "ppp" or "slip". In both cases, sucessfully getting past that point gives me "Packet Mode Enabled", but that is just a string that came into their script writer's head.

To get and keep this, you can either use a pencil, or minicoms capture facility. Save the text to a file, use cut+paste, and re-use the exact same original bytes.


Reset Defaults with minicom

Default pppd scripts simply accept the modem in the state they found it. Ususally this is OK, but you may prefer to reset the modem to a known state.

ATZ returns the modem to it's remembered default state. Most modems have two of these, and they are programmable. IE they get remembered after power off. There is a third "factory" state, in the modems ROM.

You can go through your modems code book, and try out options.


Check from boot

Before leaving a working machine, reboot it (power off the modem) and test it once more. For example, minicom resets the AT defaults, so it works. But after reboot, you haven't run minicom, so it might not work.

If you are doing this to someone elses machine. Get them to power up and connect, without you touching the machine or telling them what to do.


Now what ?

The above gives you a working modem, but we haven't set up TCP/IP over the ethernet or over PPP. You could also setup some FAX software.

Inorder to make PPP and Internet work, you have to make TCP/IP work locally. The other sections go through the files that you MUST edit, and a few that should already be setup for you, so they don't need customisation.

Then when you have the TCP/IP connection to the Internet, you will need to setup a few applications to send and receive. Read through the following sections and work through each item.