How to make perl work in a chrooted Apache on OpenBSD 4.5

I found this solution on the [email protected] list, and just slightly had to update it:

 Getting Perl/CGI to work in a chroot'd Apache environment :

Intentions

Let me start off by saying that allowing Perl/CGI in a server
environment is generally a not good idea, unless you like to
spend all of your time auditing the Perl/CGI scripts on your
webserver. Lets face it - a lot of the Perl/CGI code out there
is very poorly written security wise and can present a serious
threat to your business or organization. Crackers know this and
will try to exploit the vulnerabilities in your Perl/CGI scripts
to gain access to your system(s).

Nonetheless, since the OpenBSD 3.2 release with the default
chroot'd Apache, I have been getting a lot of e-mails regarding
problems that users and admins have encountered. For example,
admins like the idea of running Apache in chroot, but their
websites rely heavily upon multiple Perl/CGI scripts. With Apache
running in chroot, Perl/CGI will obviously not work by default.
The dillema here, is that admins do not want to sacrifice the
security of running chroot'd Apache, but at the same time, they
cannot operate their business or oganization successfully without
the Perl/CGI applications. So, this paper was written specifically
for that reason - being able to run Apache in chroot with Perl/CGI
capabilities.

* Requirements

This document is specifically written for users and admins of
OpenBSD=>3.2 with chroot'd Apache, but it can be applied to
other operating systems/distributions if the Apache setup follows
the OpenBSD chroot'd Apache setup. If you are an experienced
admin running a different operating system/distribution, this
document can give you the general idea on what to do.

+ OpenBSD=>3.2
+ Perl
+ Default chroot'd Apache

* Instructions

By default, chroot'd Apache is in /var/www. Since Apache cannot
see outside /var/www, we will have to recreate a few directories
for Perl, so it could still be called from scripts with
#!/usr/bin/perl :

[email protected] # cd /var/www
[email protected] # mkdir usr; mkdir usr/lib; mkdir usr/libexec; mkdir usr/bin

Now that the directories have been created, we have to see what
libraries perl depends on :

[email protected] # ldd /usr/bin/perl
/usr/bin/perl:
-lperl.8 => /usr/lib/libperl.so.8.0 (0x4001d000)
-lm.1 => /usr/lib/libm.so.1.0 (0x400fa000)
-lc.29 => /usr/lib/libc.so.29.0 (0x4010e000)
-lutil.8 => /usr/lib/libutil.so.8.0 (0x401cc000)

Copy those libraries to the correct directories in /var/www/usr/* :

[email protected] # cp /usr/lib/libperl.so.8.0 /var/www/usr/lib/
[email protected] # cp /usr/lib/libm.so.1.0 /var/www/usr/lib/
[email protected] # cp /usr/lib/libc.so.29.0 /var/www/usr/lib/
[email protected] # cp /usr/lib/libutil.so.8.0 /var/www/usr/lib/

Copy ld.so to /var/www/usr/libexec :

[email protected] # cp /usr/libexec/ld.so /var/www/usr/libexec/

Copy perl to /var/www/usr/bin :

[email protected] # cp /usr/bin/perl /var/www/usr/bin

Now adjust your /var/www/conf/httpd.conf file as usually by
adding :

AddHandler cgi-script .cgi
ScriptAlias /cgi-bin/ "/var/www/cgi-bin/"

AllowOverride None
Options Indexes FollowSymLinks ExecCGI
Order allow,deny
Allow from all

Restart Apache :

[email protected] # apachectl restart
/usr/sbin/apachectl restart: httpd restarted

As well as what others have mentioned, you may find that
  apachectl restart
doesn't quite work the same because the restart is already chrooted.
Any problems:
  apachectl stop; sleep 1; apachectl start
may solve.

That's it. If you have done everything as said in this document,
you should have access to Perl/CGI on your chroot'd Apache.
Good luck.

* Credits

This document is Copyright 2003 by Daniel Selans (metawire system
administrator)

Dom De Vitto has contributed the apachectl restart workaround.

Interested? Click here to contact us for a free consultation →