Troubleshooters.Com
Presents
Linux Productivity
Magazine
Volume
2 Issue 5, May 2003
IPTables
|
Copyright (C) 2003 by Steve Litt. All rights reserved.
Materials from guest authors copyrighted by them and licensed for perpetual
use to Linux Productivity Magazine. All rights reserved to the copyright holder,
except for items specifically marked otherwise (certain free software source
code, GNU/GPL, etc.). All material herein provided "As-Is". User assumes all
risk and responsibility for any outcome.
[ Troubleshooters.Com
| Back Issues |Troubleshooting Professional Magazine
]
The fool wonders, the wise man asks.
-- Benjamin Disraeli
|
CONTENTS
Editor's Desk
By Steve Litt
Security and convenience. They're usually a tradeoff. So it is for firewalls.
It would be most convenient to have the firewall pass everything (in other
words, no firewall at all). Trouble is, in all but the most benign environments,
your box would quickly be owned. Ultra security would dictate the most selective
possible firewall. The downside of such an ultra-selective firewall is that
the slightest oversight would lead to a service not being accessible, or
possibly being slow or intermittent, and the firewall wouldn't be the obvious
root cause. So we balance the convenience we need with the security called
for, and hopefully come up with a proper firewall.
Modern Linux distributions use a program called IPTables for firewalling.
Daunting at first, IPTables becomes logical with a little explanation and
a little experience. That's where this issue of Linux Productivity Magazine
comes in -- it gives an explanation, and if you follow the articles, you
get a little experience.
So kick back, relax, and have fun reading and working with this magazine.
And remember -- if you enjoy, use, or write Open Source software, this is
your magazine.
Help Publicize Linux
Productivity Magazine
By Steve Litt
Loyal readers, I need your help.
For months I've publicized Linux Productivity Magazine, expanding it from
a new magazine to a mainstay read by thousands. There's a limit to what I
can do alone, but if you take one minute to help, the possibilities are boundless.
If you like this magazine, please report it to one of the Linux magazines.
Tell them the URL, why you like it, and ask them to link to it.
I report it to them, but they don't take it very seriously when an author
blows his own horn. When a hundred readers report the magazine, they'll sit
up and take notice.
Reporting is simple enough. Just click on one of these links, and report the
magazine. It will take less than 5 minutes.
If you really like this magazine, please take 5 minutes to help bring it to
a wider audience. Submit it to one of the preceding sites.
IPTables Overview
By Steve Litt
IPTables is a firewall program. It can restrict access by port, by IP address,
or by the properties of packets. Firewalls aren't everything you need for
security, but they're an excellent first step.
IPTables consists of a series of tables. A default IPTables setup comes with
three tables:
Table
|
:
|
Usage
|
|
filter
|
:
|
This is the table that "filters out" packets, preventing
them from coming in or going out. This is the most used table.
|
|
nat
|
:
|
This is the table that provides network address translation.
|
|
mangle
|
:
|
This table has the capability of actually modifying
packets according to various criteria.
|
|
|
Conceptually, each table looks like an automobile radiator. Here's a picture
of a radiator.
Hot coolant comes into the left tank via the top hose, and flows across a
series of parallel tubes to the right tank, losing heat in the process, and
then the water comes out the bottom hose. The following is a conceptual picture
of the IPTables filter table:
As you can see from the preceding diagram, a packet can flow left to right
through one or more of the 3 chains. Generally, incoming packets come through
the INPUT chain, outgoing packets go through the OUTPUT chain, and packets
that come in and then go out go through the FORWARD chain. Each chain consists
of a sequence of rules. Each rule consists of a condition which may or may
not be met, and a target to which the packet is sent if the condition is matched.
If the condition is not matched, the packet is passed to the next rule in
the chain.
The filter table comes with chains INPUT, OUTPUT and FORWARD, but
as the administrator you can create other chains, and populate those chains
with rules.
There are four primary built-in target values:
Target
|
Valid in
|
Action
|
ACCEPT
|
All tables and chains
|
Let the packet all the way through, without regard
to subsequent rules. In other words, on the input chain, let the packet in
-- on the output chain, let the packet go out, and on the forward chain,
let the packet go through.
|
DROP
|
All tables and chains |
Do not accept the packet, and do not issue an error.
Drop the packet in the bitbucket, and that's the end of it.
|
QUEUE
|
All tables and chains |
Pass the packet to userspace. This is not common,
and some kernels don't support it.
|
RETURN
|
All tables and chains |
Stop traversing this chain and resume at the rule
after the calling rule in the calling chain. This is conceptually similar
to a return from subroutine in computer programming. |
The preceding primary built-in target values are valid anywhere within iptables.
There are several other built-in targets that are valid only in certain circumstances:
Target |
Valid in |
Action |
REJECT
|
INPUT, FORWARD and OUTPUT chains
|
Like DROP, but sends back an error message
|
LOG
|
All tables and chains
|
Write to the log, and then resume at the next rule.
Note the distinction -- this target first performs a task and
then drops through as if there were no match.
|
MARK
|
mangle table
|
Sets the netfilter mark value associated with the
packet. It is only valid in the mangle table.
|
TOS
|
mangle table |
Sets the 8-bit Type of Service field in the IP header
|
MIRROR
|
INPUT, FORWARD and PREROUTING chains, and user
defined chains only called from those chains
|
Inverts the source and destination fields in
the IP header and retransmits the packet. Experimental.
|
SNAT
|
POSTROUTING chain of nat table
|
Specifies that the source address of the packet should
be modified (and all future packets in this connection will also
be mangled), and rules should cease being examined.
|
DNAT
|
PREROUTING chain of nat table |
Specifies that the destination address of the packet
should be modified (and all future packets in this connection
will also be mangled), and rules should cease being examined. |
MASQUERADE
|
POSTROUTING chain of nat table |
Should only be used with dynamically assigned IP (dialup)
connections. See iptables man page for details.
|
REDIRECT
|
PREROUTING and OUTPUT chains, and user-defined
chains which are only called from those chains.
|
See iptables man page.
|
Of the preceding, REJECT and LOG are particularly common. REJECT is used
to send an error message back to the source, on the theory that the source
made a legitimate mistake. If you feel it probable that the majority of sources
sending packets matching the rule are hostile, you'd probably use DROP to
give the badguys less information.
Using user-defined chains (that means chains defined by you, the iptables
administrator), plus the RETURN target, you can create complex logic for
ultra-fine handling of packets.
Packet matching criteria can be fine tuned.
Safety First
By Steve Litt
Many of the exercises in this Linux Productivity Magazine issue leave your
computer completely open to crackers, script kiddies, and other badguys.
I HIGHLY suggest you perform these exercises on a computer that is not connected
to the Internet.
Also, IPTables configuration must be performed as user root, so be careful.
A slip of the finger can destroy a box when you're logged in as root.
NFS Gotchas
By Steve Litt
Much of this Linux Productivity Magazine issue discusses NFS, and there are
many NFS tests. NFS can be tricky for a number of reasons. In its default
form, it uses ports assigned at NFS restart time by the portmapper. That makes
creating a focused NFS pinhole quite tricky. We'll discuss how to do that.
Another NFS problem occurs when identical user names on different boxes have
different user id numbers. For instance, user myuid could be id 500
on one box, 505 on another, and 508 on a third. On a default NFS mount, if
the mounted ID is different than the ID for that user on the mounting machine,
files will have a user name of the mounted ID, not the mounted name, and
therefore the "other" permissions determine access.
If you have trouble accessing mounted directories or files, to save time,
check this first.
For much more complete NFS information, see NFS: Overview and Gotchas.
iptables Proof of Concept: Wide
Open and Closed Shut
By Steve Litt
This article presents an iptables proof of concept by toggling iptables between
total packet acceptance and total packet rejection. Obviously this is purely
academic. Dropping all packets disables all networking functionality, while
total packet acceptance is a welcome mat for script kiddies. I suggest you
perform these exercises on a local subnet not connected to the Internet.
Wide Open iptables
Back up any existing /etc/sysconfig/iptables.The following /etc/sysconfig/iptables
file yields a firewall enabling all access in the filter table:
*mangle COMMIT
*nat COMMIT
*filter :INPUT ACCEPT [0:0] :FORWARD ACCEPT [0:0] :OUTPUT ACCEPT [0:0] COMMIT
|
Examining the preceding, you notice the three lines beginning with a colon
(:). Each declares a default policy for a chain. The default policy
is what happens if a packets "falls through" every rule in a chain without
matching. In this case we have declared default policies of ACCEPT, meaning
that any packet not matching goes where it is trying to go. Because no rules
are declared, this means that all packets will be accepted.
Once you've created that file, restart iptables with the following
command:
service iptables restart
If the service command doesn't work, you can do it the old fashioned
way:
/etc/rc.d/init.d/iptables restart
Now verify that you can ssh into the box from another box. Assuming
the IP address is 192.168.100.91, perform the following command on the other
box:
ssh 192.168.100.91
If you have ssh enabled on both ends, the preceding should work.
If ssh isn't implemented, substitute telnet. Next, verify that ICMP
packets can get through by executing the following command from another box:
ping 192.168.100.91
Last but not least, verify NFS. Place the following line in /etc/exports
on the server (the box with which you're experimenting on iptables):
/home/myuid 192.168.100.0/24(ro)
Naturally, you must have a user myuid. If not, substitute an existing
user. Now restart NFS by performing BOTH the following commands, in the order
shown:
service portmap restart
service nfs restart
Now, on another box, as user root, create directory /mnt/test .
Then log in as user myuid and perform the following commands:
mount -t nfs -o ro 192.168.100.91:/home/myuid /mnt/test
ls -la /mnt/test
The preceding should show you a file listing of /home/myuid on the
server.
Closed Shut iptables
The following /etc/sysconfig/iptables file will yield a firewall
that lets nothing through the filter table:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] COMMIT
|
The preceding is exactly like the wide open iptables file, except that all
the ACCEPT default policies have been changed to DROP, meaning that if a
packet doesn't match any rule in a chain, that packet is dropped. Given the
fact that there are no rules, this means all packets travelling the filter
table are dropped.
Once you've modified the file as shown above, restart iptables with
the following command:
service iptables restart
Now try to ssh into the box from another box. Assuming the IP address
is 192.168.100.91, perform the following command:
ssh 192.168.100.91
It should fail. Remember, if you don't have ssh enabled on both
ends you can substitute telnet. Next, try ping from another
box to test ICMP packets:
ping 192.168.100.91
That should also fail. Last but not least, verify NFS. Place the following
line in /etc/exports on the server (the box with which you're experimenting
on iptables):
/home/myuid 192.168.100.0/24(ro)
Restart NFS on the serverby performing BOTH the following commands, in the
order shown:
service portmap restart
service nfs restart
Now, on a client machine, as user root, create directory /mnt/test
. Then log in as user myuid and perform the following commands:
mount -t nfs -o ro 192.168.100.91:/home/myuid /mnt/test
ls -la /mnt/test
The preceding should fail.
Lessons Learned
You've just toggled the ability to access the box, via ssh, ping
and nfs, from another box, by changing /etc/sysconfig/iptables and
then restarting iptables. This is proof that you successfully implemented
and configured a firewall, without any cute little GUI tools. You've proved
the concept. From here it's a matter of learning to fine tune rules in various
chains of various tables to achieve the desired packet security profile.
As you might have guessed, it's much safer to use DROP as the default. That
way an oversight will result in failed connectivity, rather than an intrusion.
The eth0 Pass Firewall
By Steve Litt
The preceding article described how to pass all packets, and how to reject
all packets. This article shows how to pass all packets coming in through,
or going out through, the eth0 network interface, while dropping all other
packets. This might be of practical value if your computer has 2 network
interfaces, and eth0 is on a subnet you consider trusted (truuuust me!).
The real value of this exercise is to demonstrate how to match or not match
based on network interface, as well as to give you an excellent iptables
debugging technique. Construct the following /etc/sysconfig/iptables:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -i eth0 -j ACCEPT [0:0] -A OUTPUT -o eth0 -j ACCEPT COMMIT
|
You'll notice the preceding is identical to the drop-all version in the preceding
article, except that we've added two lines. The first line, in English, states
"Add the rule (-A means add rule) to the INPUT chain, that if the interface
is eth0 (-i means "match interface"), accept the packet (-j means "jump to
target"). The initial [0:0] defines the starting packet count and
byte count. The second line states the same thing for packets travelling
the OUTPUT chain.
Interestingly enough, packets from the console fail this firewall. They come
in through interface lo (localhost), not eth0. They don't
match the rules, so the default policy of DROP applies. Typical firewalls
actually trust interface lo for both the INPUT and OUTPUT chains.
To accomplish that, you'd substitute lo for eth0 in the
preceding code.
Perhaps the best benefit of trusting eth0 is for debugging. If you
suspect problems are caused by iptables, you can verify or disprove
that hypothesis by trusting eth0 and restarting iptables.
If the problem disappears, you've proven it's an iptables problem.
If not, look elsewhere.
The tcp and udp Pass Firewall
By Steve Litt
Have you noticed websites you can visit but cannot ping? www.microsoft.com
is one such website. How do they do that? They do it with their firewall.
Ping requests are a special packet type called ICMP packets. Other packet
types include TCP and UDP. By enabling all TCP and UDP packets on a DROP
policy filter table, we can enable various activities while disabling
Ping. Unfortunately, many network activities that seem to be primarily TCP
and UDP also depend on ICMP for various communications and handshaking, so
disabling all ICMP is not practical. But it makes a great demonstration.
As a first step in filtering based on packet type, we build a TCP and UDP
pass firewall. Construct the following /etc/sysconfig/iptables:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -i eth0 -j REJECT [0:0] -A OUTPUT -o eth0 -j REJECT COMMIT
|
The preceding passes any tcp or udp packet whose source or destination port
is between 0 and 65535. ICMP isn't mentioned, so it falls through to the
default, which is DROP. The English translation of the first line in red
is as follows:
"Add (-A) the rule to the INPUT chain that any packet of protocol (-p) tcp,
matching (-m) tcp with destination port between 0 and 65535 (--dport means
destination port), if there's a match, jump to (-j) the ACCEPT target. By
omission, all ICMP packets are dropped.
What about the bottom two red lines -- the ones that rejects everything from
and to eth0? In this case, we want to let any querying client know that ICMP
was rejected, so it that client has an alternative to ICMP it can use that
right away, instead of waiting for a timeout.
Verify that ssh succeeds and ping fails from another box.
Ping packets are ICMP. If you try NFS, it might succeed, fail, or succeed
after a huge delay, depending on many factors. NFS depends on ICMP for much
of its communication, so depending on various other configuration parameters
on the client and server, it might succeed or fail. Later in this magazine
we'll focus more finely on which ICMP packets are allowed, in order to enable
NFS. Be aware that getting NFS through firewalls is always a challenge.
Lessons Learned
This article walked you through selecting packets by packet type, and also
demonstrated that ICMP packets are used for much more than just Ping.
Steve Litt is the author of the course
on the Universal Troubleshooting Process. He can be reached at Steve Litt's email address.
Diagnostic Logging with
iptables
By Steve Litt
Firewalls are complex, and when things go wrong, it's not always easy to
tell what happened. One of the diagnostic tools at your disposal is the LOG
target. Unlike other targets, the LOG target performs an action (creates
a log entry) and then allows the packet to "fall through" to the next rule.
Thus you can have an series of LOG entries throughout a chain. LOG entries
perform much the same function as diagnostic print statements do in programming.
Create the following /etc/sysconfig/iptables file and restart iptables:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_iptables_input [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_iptables_output [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_iptables_forward [0:0] -A INPUT -i eth0 -j REJECT [0:0] -A OUTPUT -o eth0 -j REJECT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_input_fellthrough [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_output_fellthrough [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_forward_fellthrough COMMIT
|
In the preceding, the lines in bold red have been added to the tcp/udp pass
configuration. These lines simply write to the log file (by default /var/log/messages)
and then drop through to the next rule. As root on that box, perform the
following command after restarting iptables:
tail -n0 -f /var/log/messages
Now ssh in from another box, and notice ssh succeeds and there are no messages.
Then surf in using lynx and once again notice there are no messages and that
lynx pulls up the box's default website. Now try to mount an NFS share, and
you'll probably notice a log message something like this, except not formatted
as nicely:
Apr 27 21:58:04 myserver91 rpc.mountd: authenticated mount request from 192.168.100.2:880 for /home/slitt (/home/slitt) Apr 27 21:58:04 myserver91 kernel: test_iptables_input IN=eth0 OUT= MAC=00:50:bf:d1:df:d3:00:d0:b7:1b:0b:78:08:00 SRC=192.168.100.2 DST=192.168.100.91 LEN=112 TOS=0x00 PREC=0xC0 TTL=64 ID=10709 PROTO=ICMP TYPE=3 CODE=3 [ SRC=192.168.100.91 DST=192.168.100.2 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=0 DF PROTO=UDP SPT=32769 DPT=880 LEN=64 ]
|
Be aware that in reality the preceding is 2 lines. I split the second line
into components, and indented appropriately, to make it readable. The preceding
says that rpc.mountd authenticated the NFS request, and then a packet, whose
protocol is IMCP, type 3, code 3, fell through all the ACCEPT lines and therefore
was rejected. It's the rejection of that ICMP packet causing the NFS failure.
We want Ping requests to fail, but want NFS to work. So let's get a little
more selective. Start by observing the log when a Ping request comes in over
the network:
Apr 27 22:14:53 myserver91 kernel: test_iptables_input IN=eth0 OUT= MAC=00:50:bf:d1:df:d3:00:d0:b7:1b:0b:78:08:00 SRC=192.168.100.2 DST=192.168.100.91 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=0 DF PROTO=ICMP TYPE=8 CODE=0 ID=23071 SEQ=256
Apr 27 22:14:53 myserver91 kernel: test_iptables_output IN= OUT=eth0 SRC=192.168.100.91 DST=192.168.100.2 LEN=112 TOS=0x00 PREC=0xC0 TTL=255 ID=0 DF PROTO=ICMP TYPE=3 CODE=3 [ SRC=192.168.100.2 DST=192.168.100.91 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=0 DF PROTO=ICMP TYPE=8 CODE=0 ID=23071 SEQ=256 ]
|
The incoming packet is ICMP, type 8, code 0. The outgoing packet is ICMP,
type 3, code 3.
When the time comes to create a fine firewall that screens very specific
classes of packets, logging can help you create rules to accomplish what
you need. Also, when your firewall is not working the way you'd imagine it
should work, logging provides a view into what would otherwise be a black
box.
Lessons Learned
Diagnostic logging is accomplished with the LOG target. The LOG target takes
action (writing the log), and then, unlike other targets, it passes the packet
on to the next rule in the chain.
Logging is the best way to see inside your IPTables setup, which would otherwise
appear more or less as a black box. It's also an excellent way to find out
what types of packets you need to let through (or block).
Passing All ICMP
By Steve Litt
The preceding article displayed an IPTables setup to block all ICMP. As expected,
this disabled ping, but it also disabled NFS. To completely accept
all ICMP, the following two rules need to be added:
[0:0] -A INPUT -p icmp -j ACCEPT
[0:0] -A OUTPUT -p icmp -j ACCEPT
The following shows the entire /etc/sysconfig/iptables file:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p icmp -j ACCEPT [0:0] -A OUTPUT -p icmp -j ACCEPT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_iptables_input [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_iptables_output [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_iptables_forward [0:0] -A INPUT -i eth0 -j REJECT [0:0] -A OUTPUT -o eth0 -j REJECT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_input_fellthrough [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_output_fellthrough [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_forward_fellthrough COMMIT
|
Restart IPTables and note that both ping and NFS now work.
Lessons Learned
The entire universe of ICMP packets can be accepted with the following 2
lines:
[0:0] -A INPUT -p icmp -j ACCEPT
[0:0] -A OUTPUT -p icmp -j ACCEPT
Obviously, if the ACCEPT were changed to REJECT, they could be rejected.
Accepting Only ICMP type 3
By Steve Litt
In the Diagnostic Logging with
iptables article, the logs indicated that upon trying to mount an NFS
share exported by this server, an ICMP type 3 packet would pass
through the INPUT chain unaccepted. This article demonstrates how to accept
that exact type of packet, while allowing other ICMP packets to be rejected.
Interestingly enough, enabling ICMP type 3 on input only does not fully enable
NFS, because mounts and dismounts often fail unless type 3 is enabled on
output also.
What is needed is to delete the lines accepting all ICMP, and replace them
with two lines accepting type 3 ICMP on the INPUT and OUTPUT chains only.
Here's the /etc/sysconfig/iptables file:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p icmp -m icmp --icmp-type 3 -j ACCEPT [0:0] -A OUTPUT -p icmp -m icmp --icmp-type 3 -j ACCEPT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_iptables_input [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_iptables_output [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_iptables_forward [0:0] -A INPUT -i eth0 -j REJECT [0:0] -A OUTPUT -o eth0 -j REJECT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_input_fellthrough [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_output_fellthrough [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_forward_fellthrough COMMIT
|
As an experiment, you might want to comment out the type 3 acceptance on
the OUTPUT chain, and note that NFS mounting and dismounting become slow
and intermittent.
Disabling Ping Only
By Steve Litt
Disabling ping is often a valid security step, in order to prevent
ping floods and ping sweeps. What is needed is to disable ping. In this case
we'll disable it by named type rather than type number/code. The first step
is to find the ping types. Perform the following command:
iptables -p icmp -h | less
Go near the bottom to find the list of valid icmp types, and notice the echo-reply
and echo-request types. You want to reject incoming echo requests
(ping), and also reject any outgoing echo reply (pong). The following /etc/sysconfig/iptables
file performs those rejections but passes all other ICMP packets:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p icmp -m icmp --icmp-type echo-request -j REJECT [0:0] -A OUTPUT -p icmp -m icmp --icmp-type echo-reply -j REJECT [0:0] -A INPUT -p icmp -j ACCEPT [0:0] -A OUTPUT -p icmp -j ACCEPT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_iptables_input [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_iptables_output [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_iptables_forward [0:0] -A INPUT -i eth0 -j REJECT [0:0] -A OUTPUT -o eth0 -j REJECT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_input_fellthrough [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_output_fellthrough [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_forward_fellthrough COMMIT
|
Create the preceding /etc/sysconfig/iptables file, restart iptables,
and notice that NFS works perfectly but pings result in "destination port
unreachable".
Blocking Incoming Telnet
By Steve Litt
Telnet is about as dangerous as it gets. Plain text passwords, ability to
do just about anything. One way of blocking telnet is by not running its
daemon. However, if someone unwittingly runs its daemon, you're wide open.
It's much better to close its port.
The first step is to find its port in /etc/services as shown:
[root@myserver91 root]# grep telnet /etc/services telnet 23/tcp telnet 23/udp rtelnet 107/tcp # Remote Telnet rtelnet 107/udp telnets 992/tcp telnets 992/udp [root@myserver91 root]#
|
So telnet is port 23, and it uses both tcp and udp. Let's assume you're only
trying to block incoming telnet, and not trying to prevent your users from
using telnet clients to access other boxes. In that case you need block port
23 only in the INPUT chain. Here's the /etc/sysconfig/iptables file
to accomplish that:
*mangle COMMIT
*nat COMMIT
*filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0] [0:0] -A INPUT -p tcp -m tcp --dport 23:23 -j REJECT [0:0] -A INPUT -p udp -m udp --dport 23:23 -j REJECT [0:0] -A INPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --dport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 0:65535 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --dport 0:65535 -j ACCEPT [0:0] -A INPUT -p icmp -m icmp --icmp-type echo-request -j REJECT [0:0] -A OUTPUT -p icmp -m icmp --icmp-type echo-reply -j REJECT [0:0] -A INPUT -p icmp -j ACCEPT [0:0] -A OUTPUT -p icmp -j ACCEPT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_iptables_input [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_iptables_output [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_iptables_forward [0:0] -A INPUT -i eth0 -j REJECT [0:0] -A OUTPUT -o eth0 -j REJECT [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_input_fellthrough [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_output_fellthrough [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_forward_fellthrough COMMIT
|
You've just blocked any packets with destination port 23 for both tcp and
udp packets in the INPUT chain, so that incoming telnet requests cannot be
serviced.
Lessons Learned
You can block a port using the -m --dport #:# syntax. Be careful -- there's
also a --sport syntax. You need to know the source and destination ports
in order to accurately block a port. Diagnostic logging is your
friend. Do not rely in the absence of a daemon to block a port -- somebody
might unwittingly run the daemon.
A Somewhat Practical
Server Firewall
By Steve Litt
I call this "A Somewhat Practical Server Firewall" because security
is a complex and ever changing discipline. If you're operating in a nasty
environment you'll want much more knowledge than is contained in this Linux
Productivity Magazine issue. What this article gives you is a firewall doing
the following:
- Enable export of NFS
- Enable ssh serving and client
- Enable httpd serving and client
- Enable httpsd serving and client
- Enable just enough ICMP to enable NFS
- Trust anything from localhost
- Reject anything else
Enabling NFS
Getting NFS through a practical firewall is a bear. First, it requires enabling
the portmapper daemon at port 111. Worse yet, the portmapper daemon arbitrarily
sets some ports for NFS on each NFS daemon restart. And, as you've seen previously,
NFS requires passage of certain ICMP packets, namely, type 3. And you must
be able to pass mountd packets, even though by default mountd
operates at a different port every time NFS is restarted.
Passing mountd Packets
The portmap and nfs packets are at ports defined by /etc/services.
No such luck with the mountd packets. Those packets go to ports
defined at restart time by the portmap daemon. In fact, if you repeatedly
restart NFS and run the following command:
rpcinfo -p 192.168.100.85
You will see that the mountd daemon is bound to different ports
every time you restart NFS. How do you accurately pinhole such as service?
There are 3 ways:
- The shotgun method -- pass all TCP and UDP from 32000 to 34000
- Use the NFS start script to peg it to a single port
- Create an NFS restart script to first detect all mountd ports, then
restart NFS, then detect all new NFS ports, then alter the firewall to accommodate
the changes.
#1 is out of the question because it leaves 2000 open ports that a script
kiddie can exploit. #2 is discussed in this article. If, for some reason
you choose not to peg the mountd port, your alternative is #3. #3 is doable
by a reasonably skilled programmer, but it's clearly beyond the scope of
this article.
As user root on the server, edit /etc/rc.d/init.d/nfs. From the
top of the file, search for the first occurrence of the string MOUNTD_PORT.
Right above that line, insert a new line with the following code:
MOUNTD_PORT=33333
In the preceding, the number can be any high number. I'd make it somewhere
between 32000 and 34000. BE SURE it's not already used. It should not be
named in an rpcinfo -p command, nor should it exist as
a port in /etc/services.
Once you've added the line of code, restart NFS and using the rpcinfo -p
command, verify that indeed all instances of mountd are pegged at
your chosen number. Once you've pegged it, you can pinhole the firewall to
accommodate NFS.
Making the iptables File
Now that you know what needs to be let through, the following /etc/sysconfig/iptables
does what's needed. It's commented, so please spend a few minutes studying
it.
*mangle COMMIT
*nat COMMIT
# DEFAULT ALL CHAINS TO DROP ON FALLTHROUGH *filter :INPUT DROP [0:0] :FORWARD DROP [0:0] :OUTPUT DROP [0:0]
# PASS ALL FROM LOCALHOST # OTHERWISE MUCH REMOTE, INCLUDING GVIM, WON'T WORK [0:0] -A INPUT -i lo -j ACCEPT [0:0] -A OUTPUT -o lo -j ACCEPT
# PASS ICMP TYPE 3 PACKETS, INPUT AND OUTPUT [0:0] -A INPUT -p icmp -m icmp --icmp-type 3 -j ACCEPT [0:0] -A OUTPUT -p icmp -m icmp --icmp-type 3 -j ACCEPT
# PASS PORTMAP AT 111, INPUT AND OUTPUT, TCP AND UDP [0:0] -A INPUT -p tcp -m tcp --dport 111 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 111 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 111 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 111 -j ACCEPT
# PASS NFS AT 2049, INPUT AND OUTPUT, TCP AND UDP [0:0] -A INPUT -p tcp -m tcp --dport 2049 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 2049 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 2049 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 2049 -j ACCEPT
# PASS MOUNTD AT 33333, INPUT AND OUTPUT, TCP AND UDP [0:0] -A INPUT -p tcp -m tcp --dport 33333 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 33333 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 33333 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 33333 -j ACCEPT
# PASS SSH AT 22, INPUT AND OUTPUT, TCP AND UDP [0:0] -A INPUT -p tcp -m tcp --dport 22 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 22 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 22 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 22 -j ACCEPT
# PASS http AT 80, INPUT AND OUTPUT, TCP AND UDP [0:0] -A INPUT -p tcp -m tcp --dport 80 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 80 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 80 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 80 -j ACCEPT
# PASS https AT 443, INPUT AND OUTPUT, TCP AND UDP [0:0] -A INPUT -p tcp -m tcp --dport 443 -j ACCEPT [0:0] -A INPUT -p udp -m udp --dport 443 -j ACCEPT [0:0] -A OUTPUT -p tcp -m tcp --sport 443 -j ACCEPT [0:0] -A OUTPUT -p udp -m udp --sport 443 -j ACCEPT
# LOG ALL eth0 DROP THROUGHS FOR DIAGNOSTICS # ENTRIES WRITTEN TO /var/log/messages # COMMENT OUT ONCE WORKING [0:0] -A INPUT -i eth0 -j LOG --log-prefix test_eth0_input [0:0] -A OUTPUT -o eth0 -j LOG --log-prefix test_eth0_output [0:0] -A FORWARD -i eth0 -j LOG --log-prefix test_eth0_forward
# LOG ALL lo DROP THROUGHS FOR DIAGNOSTICS # ENTRIES WRITTEN TO /var/log/messages # COMMENT OUT ONCE WORKING [0:0] -A INPUT -i lo -j LOG --log-prefix test_lo_input [0:0] -A OUTPUT -o lo -j LOG --log-prefix test_lo_output [0:0] -A FORWARD -i lo -j LOG --log-prefix test_lo_forward
COMMIT
|
The preceding /etc/sysconfig/iptables does the following:
- Lets through all packets to or from localhost.
- Lets through all ICMP type 3 packets, incoming and outgoing.
- Lets through all incoming and outgoing portmap packets (port 111).
- Lets through all incoming and outgoing NFS packets (port 2049).
- Lets through all incoming and outgoing mountd packets at port 33333.
You previously tweaked /etc/rc.d/init.d/nfs in order to peg mountd
at port 33333.
- Lets through incoming and outgoing ssh at port 22, http at 80, and
https at 443.
- Logs and drops all other packets
Summary
NFS requires packets from the portmap daemon, the NFS daemon, and the mountd
daemon, as well as ICMP type 3 packets. Further enhance the firewall by enabling
http, https, and ssh. Additionally, pass all packets that come through the
localhost interface.
This is typical of firewall creation. Start by blocking everything, and then
open small pinholes to let through what you want getting through. In a real
firewall you'd cut it finer, perhaps letting through only INPUT or only OUTPUT
on some of the ports. As you test your firewall, when you find functionalities
that don't work, use the diagnostic logs on the bottom to find out what's
getting dropped, and then create the proper pinholes.
Blocking a Subnet
By Steve Litt
You might want to block a specific subnet. Here's how to do it. Add the following
two lines high up in your /etc/sysconfig/iptables:
[0:0] -A INPUT -s 192.168.100.0/29 -j REJECT
[0:0] -A INPUT -s 192.168.100.0/29 -j REJECT
The 29 is a subnet mask, meaning 29 bits of 1's followed by 3 bits
of zeros. This corresponds to a range between 192.168.100.0 and 192.168.100.7.
You can verify that worked by trying to ssh in from 192.168.100.2 and then
try again from 192.168.100.20 or whatever. You'll see you can't get in from
192.168.100.2.
You can also block everything EXCEPT a subnet, by changing the REJECT
targets to ACCEPT, and follow it with a line that rejects everything
from eth0.
IPTables Summary
By Steve Litt
IPTables is Linux's current firewalling technology. Conceptually, it's built
like a car radiator, with packets flowing through one or more chains (similar
to the tubes in a car radiator). Each chain is comprised of one or more rules.
Each rule is comprised of match criteria and a target to which to send
matching packets. A target can be either a predefined target like ACCEPT,
REJECT, DROP, or LOG, or a user defined chain. Most targets do not return
control to the rule after the one that sent the packet to the target, but
the LOG target does. User defined chains can be constructed to return control
to the rule following the sending rule.
One easy way to configure IPTables is with the /etc/sysconfig/iptables
file, which is the default configuration file for IPTables. IPTables can also
be configured with a script calling the iptables command with the
-A argument. Once you fully understand the config file method, the script
method will be easily understood.
IPTables does its magic by opening pinholes to and through various ports,
based on various match criteria. When software has nomadic ports, steps must
be taken either to peg those ports to a specific number, or do deduce them
in real time and modify iptables. This was discussed in this document in
the context of NFS.
This document barely scratched the surface, but it serves to facilitate understanding
of a topic that initially appears daunting. If you're responsible for protecting
a computer in a hostile environment, you'll need to learn more. Man pages,
the Internet and books should suffice, now that you have enough knowledge
to understand those sources.
You might have noticed that this Linux Productivity Magazine issue does not
discuss network address translation or masquerading. That will come in a
future Linux Productivity Magazine.
Life After Windows: A Trip Back to Windows-Land
Life After Windows is a regular Linux Productivity Magazine column,
by Steve Litt, bringing you observations and tips subsequent to Troubleshooters.Com's
Windows to Linux conversion.
By Steve Litt
This week I finally did it -- I networked everyone in our house. You might
think hardware was the big pain. Buying switches and network cabling, stringing
the cabling, etc. Hardware was about what you'd expect.
I replaced Brett's Pentium 150 Linux box with a newly revamped Athlon 2000+
with 512MB of PC400 RDRAM Mandrake 9.1 machine. No surprises -- it performs
spectacularly. The "Broadcom" network interface imbedded in the motherboard
was easily detected and enabled. A second nic, an $11.00 Realtek 8139 clone,
was also easily detected and enabled.
My buddy Richard gave me a diskless Pentium 133 with an ancient NIC. Within
a couple hours the computer was an IPCOP firewall for my father. It took IPCop
all of 1 minute to recognize and configure the ancient NIC -- it turned out
to be a RealTek 8129 chipset. Remember the days when Linux hardware compatibility
was problematic? Those days are gone.
The big news this week is I discovered what Windows is like from a Linux user's
perspective, and the view isn't pretty.
Windows Threw Me a Curve
Life got ugly trying to connect my wife's and daughters' Windows 98 boxes.
First, my $11.00 8139's couldn't be installed on Win98. Win98 itself didn't
recognize them, and using the installation CD that comes with these cards
wasted hours with no joy. First, you need to identify exactly which of the
vendor's similar cards you're dealing with, and then you need to configure
using the correct directory on the CD. Meanwhile, the installer keeps telling
you it's a plug and play NIC, to turn the computer off and install the NIC,
and to turn the computer on. No matter how many times you do it, or how many
variations you try on the basic theme, it doesn't work. Half a day gone.
Richard also gave me several used CNET NICs complete with install floppies.
I installed one in my daughters' Windows 98 computer, and after a little
trial and error with the install floppy, I got it on the net. My wife's computer
would have installed similarly, but a bad CDROM prevented my from using my
favorite Windows diagnostic -- Knoppix. Worse yet, a subtle network problem
prevented connectivity. These aren't Windows' fault, but combine them with
the obscene gyrations necessary to install a NIC on a Windows box, and it
took hours to get the CNET NIC working.
You might be thinking: "Steve -- it's your fault. You forgot what NIC was
installed, and where you put the original installation floppies. And in the
case of the RealTek 8139's, those didn't exist when Windows 98 came out. What
do you expect?".
What do I expect? Several years ago my expectations were those of the Windows
user -- keep every installation media for every piece of hardware, and keep
track of which hardware was in which box. But 5 years of Linux use have raised
my expectations. Now I expect for my operating system to find and configure
hardware devices. If it can't, I expect to quickly find the solution on the
net. I expect not to be asked for time consuming reboots. I expect hardware
installation to take a few minutes, and be very straightforward. I expect
to have the insmod, modprobe, rmmod and lsmod commands
to help me troubleshoot. And I expect to throw out the installation media
given me by the hardware manufacturer. Armed with these new expectations,
Windows is anything but "user friendly". It's "user hostile".
Let Hardware Manufactures Stick to Hardware
I once griped that hardware manufacturers don't write Linux drivers for their
equipment. Now I know their "negligence" was a blessing! Hardware manufacturers
can't deploy decent installation software. All too often they give you drivers
for 20 different product on one CD, and expect you to know which of these
lookalike products you have. That expectation becomes unrealistic the day
you throw out the original box.
Hardware manufacturer's idea of documentation is all too often a front end
to Windows Explorer. If you're a computer store and install hundreds of their
products per year, this isn't a problem. But if you have one or two, all too
often you'll need to throw out the hardware the first time you need to reinstall
the OS. Or switch to Linux :-)
In fact, I'd go so far as to state that by not supporting Linux, the hardware
manufacturers did us an immense favor. Without vendor-supplied drivers, the
Linux community was forced to supply its own, and because those community
supplied drivers were free software, they could easily be included on all
Linux distro CD's. Because the Linux community needed to produce a product
that could be used by an actual user, the installation procedures were extremely
simple. Most Linux distros now have extremely sophisticated hardware detection
and configuration facilities.
What Do You Expect From a 5 Year Old OS?
Perhaps I could be faulted for placing new hardware in a 5 year old operating
system (Windows 98, first edition). After all, I'd have had similar results
had I tried to install my 8139's in the RedHat 5.1 I purchased in October
1998. But before criticizing me for running a 5 year old OS, consider why
I do so. Windows 98 was the last Windows unencumbered with horrid licensing
provisions. I can reinstall Windows 98 every 6 months. Its data is easily
read by Open Source programs. Its partitions can be mounted on Linux.
Contrast that with a modern OS like Windows XP. Forced registration. You'll
need to beg Microsoft for permission to reinstall OS you purchased with your
hard earned money. Replace a few too many hardware items and the system will
refuse to run, unless you beg Microsoft for permission. Think XP is bad?
Windows versions now on the drawing board have no files -- just a database.
The stated reason is so all data can be accessed by a common set of tools,
and displayed the same way. The fact that it renders Windows data unreadable
by other operating systems is just a byproduct. Right?
I have very good and sensible reasons for eschewing Win ME, 2000, XP, 2003
and Longhorn. I own my data, and want to keep it that way.
Life After Windows
What's life like after Windows? It's new expectations.
My new IPCop computer with an unknown NIC took 10 minutes. My son's new motherboard
with an integrated NIC took 45 minutes via an NFS install. Rewiring the house
took several hours. Getting my wife's and daughters' Windows computers to
accept NICs took over a day.
After 5 years of Linux, I expect more. NICs, video cards and sound cards should
be inserted, detected, and run. No floppy flipping. No having to remember
the exact model number of a 2 year old card. No wondering whether misunderstanding
a step in a hastily written fuzzy checklist provided by a hardware supplier
led to failure.
I expect what Windows has bragged about for years and never delivered -- plug
and play. Not in the Windows sense of shifting ports and addresses so you
don't even know what you're dealing with, but in the sense that you push the
card into the slot, power the computer on, and the computer configures the
new card.
I expect Linux.
I had fond memories of my Windows days. Days when I could confidently buy
any hardware and know it would work in my computer. Days when I was confident
I could quickly get the hardware working. Life seemed so easy. So what if
I needed a database of what hardware was in which machine, and which installation
media corresponded to each piece of hardware?
But that was a Windows user's view. After a few years in the Linux world,
going back to Windows is pure frustration. User friendliness, the very cornerstone
of Windows marketing, is the sole domain of Linux.
Steve Litt is the author of the course
on the Universal Troubleshooting Process. He can be reached at Steve Litt's email address.
Letters to the Editor
All letters become the property of the publisher (Steve Litt), and may
be edited for clarity or brevity. We especially welcome additions, clarifications,
corrections or flames from vendors whose products have been reviewed in this
magazine. We reserve the right to not publish letters we deem in bad taste
(bad language, obscenity, hate, lewd, violence, etc.).
Submit letters to the editor to Steve Litt's email address, and be sure
the subject reads "Letter to the Editor". We regret that we cannot return
your letter, so please make a copy of it for future reference.
How to Submit an Article
We anticipate two to five articles per issue, with issues coming out monthly.
We look for articles that pertain to the Linux or Open Source. This can be
done as an essay, with humor, with a case study, or some other literary device.
A Troubleshooting poem would be nice. Submissions may mention a specific product,
but must be useful without the purchase of that product. Content must greatly
overpower advertising. Submissions should be between 250 and 2000 words long.
Any article submitted to Linux Productivity Magazine must be licensed with
the Open Publication License, which you can view at http://opencontent.org/openpub/.
At your option you may elect the option to prohibit substantive modifications.
However, in order to publish your article in Linux Productivity Magazine,
you must decline the option to prohibit commercial use, because Linux Productivity
Magazine is a commercial publication.
Obviously, you must be the copyright holder and must be legally able to
so license the article. We do not currently pay for articles.
Troubleshooters.Com reserves the right to edit any submission for clarity
or brevity, within the scope of the Open Publication License. If you elect
to prohibit substantive modifications, we may elect to place editors notes
outside of your material, or reject the submission, or send it back for modification.
Any published article will include a two sentence description of the author,
a hypertext link to his or her email, and a phone number if desired. Upon
request, we will include a hypertext link, at the end of the magazine issue,
to the author's website, providing that website meets the Troubleshooters.Com
criteria for links and that the author's
website first links to Troubleshooters.Com. Authors: please understand we
can't place hyperlinks inside articles. If we did, only the first article
would be read, and we can't place every article first.
Submissions should be emailed to Steve Litt's email address, with subject
line Article Submission. The first paragraph of your message should read as
follows (unless other arrangements are previously made in writing):
Copyright (c) 2003 by <your name>. This material
may be distributed only subject to the terms and conditions set forth in the
Open Publication License, version Draft v1.0, 8 June 1999 (Available
at http://www.troubleshooters.com/openpub04.txt/ (wordwrapped for readability
at http://www.troubleshooters.com/openpub04_wrapped.txt). The latest version
is presently available at http://www.opencontent.org/openpub/).
Open Publication License Option A [ is | is not] elected,
so this document [may | may not] be modified. Option B is not elected, so
this material may be published for commercial purposes.
After that paragraph, write the title, text of the article, and a two sentence
description of the author.
Why not Draft v1.0, 8 June 1999 OR LATER
The Open Publication License recommends using the word "or later" to describe
the version of the license. That is unacceptable for Troubleshooting Professional
Magazine because we do not know the provisions of that newer version, so it
makes no sense to commit to it. We all hope later versions will be better,
but there's always a chance that leadership will change. We cannot take the
chance that the disclaimer of warranty will be dropped in a later version.
Trademarks
All trademarks are the property of their respective owners. Troubleshooters.Com(R)
is a registered trademark of Steve Litt.
URLs Mentioned in this Issue