Showing posts with label php. Show all posts
Showing posts with label php. Show all posts

2019-10-20

OpenBSD 6.6 released early!

OpenBSD 6.6 was released earlier this week. Along with it come a number of exciting enhancements to not just hardware support, but improvements to the installer, and security enhancements to the userland as unveil and pledge continue to get integrated more. You can read the entire change log at the link above.

As I had mentioned when OpenBSD 6.5 came out, sysupgrade(8) was making snapshot upgrades a breeze for those of us running -CURRENT. A few weeks back, the team made a sysupgrade patch available to bring this functionality to OpenBSD 6.5, so that folks could take advantage of it to upgrade to OpenBSD 6.6 when it was released. I spent some time this week testing it on my VMM virtual machines running OpenBSD-Stable and indeed, it's just as easy as upgrading snapshots. Then I upgraded everything else, including my production servers.

To upgrade from OpenBSD 6.5, as root or with doas, just run these commands:
syspatch
sysupgrade (it'll download what it needs, reboot, do the upgrade, and reboot again, fully unattended)
pkg_add -u (to upgrade all of your binary packages to the latest version)

As per usual, I updated the OpenBSD/httpd/MariaDB/PHP walk-through

 

2018-10-24

OpenBSD 6.4 released, Web server guide updated

OpenBSD 6.4 was released last week. It comes chock full of new goodies, including a built-in Wireless network manager ('join' syntax for ifconfig), derived snapshots for vmm virtual machine disk images (based on qcow2 support), improvements to pledge including the addition of unveil, and RETGUARD, a new stack protector for thwarting ROP attacks just to name a few new features.

I've been busy with the new job and getting settled into the new digs here in the Austin suburbs, but I carved out some time to update the OpenBSD/HTTPD/MySQL/PHP guide. There are a few changes to how PHP-FPM is configured, so you may want to pay close attention if you've followed the guide before.

The nginx and apache pages haven't gotten that many views lately, so I am not updating them this go-around. The httpd in OpenBSD's base install is a pretty well-proven web server at this point, and I've been using it in production, reliably, for years now. If you're thinking of running nginx or apache on OpenBSD, I'd urge you to take a look at httpd.

2018-09-25

Running pkgsrc on OpenBSD

After a discussion somewhere on teh webs, I decided to dig into the state of PHP 7.1 and PHP 7.2 on OpenBSD. The short version is "we're working on it" (in OpenBSD ports) but no ETA. However, being keen to NetBSD's pkgsrc distribution, I knew that they had been cooking up newer versions in their software tree. So I decided to kick the tires.

Pkgsrc is roughly NetBSD's equivalent to the OpenBSD/FreeBSD "Ports" repository, however, they've put significant effort into making it quite portable. It works in one way or another on other BSDs, Linux, OS X and even more esoteric platforms like Haiku and Illumos.

Initially, bootstrapping pkgsrc on OpenBSD 6.3-STABLE didn't work. Buried deep in my inbox from the pkgsrc mailing list in April, I found a hint from Sevan Janiyan about some patches that are needed to make it work. Partially, this is because OpenBSD uses both clang and gcc compilers in the base distribution on modern hardware.

Anyhow, on with the show.

First, check out the pkgsrc repository. You can do it with cvs:

env CVS_RSH=ssh cvs -d anoncvs@anoncvs.NetBSD.org:/cvsroot checkout -P pkgsrc

It's going to churn for a few minutes while it downloads all the files.

When it's done downloading, you can move it to /usr (/usr/pkgsrc) if you want, but I usually just leave the pkgsrc tree in my home directory. Change into the pkgsrc directory:
cd pkgsrc

make a file called pkgsrc.patch with the following contents:

--- archivers/libarchive/files/libarchive/archive_openssl_hmac_private.h
1 Aug 2017 22:21:17 -0000       1.1.1.2
+++ archivers/libarchive/files/libarchive/archive_openssl_hmac_private.h
5 Apr 2018 20:50:09 -0000
@@ -28,7 +28,8 @@
 #include
 #include

-#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
+#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
+    (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x2070000fL)
 #include /* malloc, free */
 #include /* memset */
 static inline HMAC_CTX *HMAC_CTX_new(void)

Apply the patch:
patch -p0 < pkgsrc.patch

cd bootstrap

A "privileged" install requires root (via doas or su) but will store all of the binaries into /usr/pkg:
doas ./bootstrap --compiler clang

-- OR --

If you wish to build "unprivileged" without root, the binary packages will be installed in the "pkg" directory under your home dir.
./bootstrap --unprivileged --compiler clang

Then go have a coffee or something. It takes a while.

If it finishes up with out a screen full of errors, you're almost all the way there:


You'll need to edit your .profile (or .bashrc if you roll that way) to add the pkg/bin directory to your path. In a privileged install, add /usr/pkg/bin and /usr/pkg/sbin to your path. In an unprivileged install, add ~/pkg/bin and ~/pkg/sbin instead.

Adding these paths to the end of the PATH line in the default .profile should work for a privileged pkgsrc install:

PATH=$HOME/bin:/bin:/sbin:/usr/bin:/usr/sbin:/usr/X11R6/bin:/usr/local/bin:/usr/local/sbin:/usr/games:/usr/pkg/bin:/usr/pkg/sbin

You need that in your path, because pkgsrc portable requires you to use NetBSD's "bmake" in the pkgsrc tree, and bmake is compiled as part of the bootstrap. You can log out and log back in, or just run this command to get bmake into your working path.

PATH=$PATH:/usr/pkg/bin:/usr/pkg/sbin

Let's try building something. It works a lot like ports. It will recursively build any dependencies or libraries that are needed, and install them into the pkg directory before building the application you're trying to compile. I'll start with the latest version of PHP in pkgsrc, PHP 7.2, since that's how this whole journey started. I'm using doas since I did a privileged install.

cd pkgsrc/lang/php72
doas bmake

It compiled.



I'm going to run doas bmake install without running bmake test because pkgsrc isn't the boss of me.



And it all works.

2017-04-15

PHP/MySQL Walk-Throughs updated for OpenBSD 6.1

I've stopped maintaining the page for nginx because it hasn't received many views since I updated it about six months ago. I suspect that nginx on OpenBSD is not all that popular because the httpd that ships with OpenBSD provides almost the same functionality as a basic installation of nginx. The pages for httpd in base and Apache2 now cover PHP7 and both configurations appear to work really well.  

PHP/MySQL on OpenBSD's relayd-based httpd 
HiR's Secure OpenBSD/Apache/MySQL/PHP Guide

Feel free to comment on this post if you find any discrepancies or have suggestions. Comments are disabled on the walk-through pages.

(2017-04-23) Edited to add: I went ahead and re-worked the nginx guide, based on the httpd guide with new formatting.
PHP/MySQL with nginx on OpenBSD

2015-06-14

OpenBSD PHP/MySQL Walk-throughs are up to date (Finally!)

First and foremost, I finally took the time to wrap my brain around OpenBSD's new relayd-based httpd. You can see the walk-through here:


While I was at it, I refreshed the guides for nginx and apache.
These should be maintained for future versions of OpenBSD going forward. Enjoy!

2012-01-08

PHP Programming: Clean URLs

I've spent the past two weekends re-writing old, horrible, ugly code that I wrote as a kid. I still have a lot of work ahead of me, and there's still no guarantee that the code I'm writing now will be great, but it'll be better than the stuff I wrote before. I'm not a web developer by any means, but it won't keep me from having some nerdy fun on the weekend. I've learned some tricks, and figured I'd share them here in a few short entries. Today, it's so-called "Clean" URLs.

In most dynamic web scripting languages such as PHP, dynamic pages can be accessed by passing parameters through a query string. As an example: http://foo.somesite.com/article.php?p=42

You've undoubtedly seen dynamic websites that don't pass query strings, but instead generate nice, friendly URLs that look more like this: http://foo.somesite.com/article/Hello_World

Clean URLs are easier to link to, they're better for search engine optimization, and with proper implementation provide a few security features as well. The project I'm working on is a custom CMS that was my very first Apache/PHP/MySQL project. It ended up getting kind of popular among a niche crowd, so I left it online in all its ugly glory. I have an article list script that can filter articles by category, and another script to display the articles. I'll just call them list.php and article.php here for the sake of discussion.

Removing .php from the URL

The first part of the problem is the fact that I'd rather not have ".php" show up in the URL, so that "article" and "list" would appear to be sub-directories of my site.

After playing around with a bunch of promising hacks that tended to work fine, including mod_rewrite, I decided that the most elegant way to tackle this was to rely on Apache's "FilesMatch" directive. I created symbolic links from list.php and article.php to strip the .php extension. You could just as easily rename them, though. Then I added the FilesMatch directive to .htaccess for "article" and "list" as shown below. Make sure "AllowOverride All" is set in your Apache configuration, too.



At this point, pulling up http://foo.somesite.com/list will try to run "list" as a PHP script. In my case, it shows a list of articles.

Parsing URI parameters with PHP
The next part is mostly easy. As far as I know, any PHP script will let you add a bunch of parameters to it with slashes like this: http://foo.somesite.com/index.php/testing/1/2/3/4/5. It may not render well, but it doesn't keep it from executing. Above, we got list to show a list of articles, so now it's time to set up filtering. As you can see below, the last element of the URL (split by /) is considered to be the category. The following URL would show a category of "Widgets": http://foo.somesite.com/list/Widgets

To avoid the problem of getting a category of "list" or "list.php" (remember, I chose to symlink my .php files), I included logic to check to see if the category matches the script name. If so, it assumes that it should instead display the Table Of Contents. You'll also see I am setting the title based on what happens here. As the category types are stored in the database and displayed with spaces, I am using str_replace to replace underscores in the URI with spaces. This means that I have to ensure spaces are turned into underscores elsewhere in the code and in all links to my site. That's beyond the scope of this article, though. What matters is that a URL of http://foo.somesite.com/list/Arts_and_Crafts would pull up a category of "Arts and Crafts".
$category=(end(explode('/', urldecode($_SERVER['REQUEST_URI']))));
if((
$category) && ($category != 'list.php' && $type != 'list'))
{
$rawcat=str_replace('_', ' ', $category);
$list=getlist($rawcat);
$title=$rawcat." Articles";
}
else
{
$toc=TRUE;
$list=getlist();
$title="Table of Contents";
}

From here, the rest of my PHP code can query the database for articles. getlist() is a function that I wrote. If its parameter is null, it gets all of them, otherwise it (safely!) queries the database for a category.

I used similar code in the article php script, which queries the database for the title of an article, so I get nice-looking URLs for individual articles as well, such as:

http://foo.somesite.com/article/How_to_narfle_the_Garthok

2011-11-12

OpenBSD 5.0: Apache, PHP and MySQL

The basic steps for taking a bare-bones install of OpenBSD and adding an AMP stack for web applications hadn't changed much in the past 2 years. Although 5.0 is not seen as a "major update", but simply a continuation of the normal development cycle, the OpenBSD team did a few things that make the installation a bit different this go around. I'll cover some of the recent changes to OpenBSD and its packages in this post, then you can dive right into the updated OpenBSD Chroot Apache, PHP, MySQL setup guide.

Initialization scripts: Starting with OpenBSD 4.9, the RC scripts became modular. This is similar to how NetBSD and FreeBSD have worked for many years. Individual daemons have startup scripts in /etc/rc.d, but rc.conf, rc.local and rc.conf.local still work the same, so it wouldn't surprise me if many OpenBSD users didn't even notice the change. It seems like OpenBSD 5.0 packages for most of the popular services (samba, cups, postgres, etc) are actually creating these startup scripts now. If a third-party application from packages installs a startup script in /etc/rc.d, you can add it to the pkg_scripts variable in /etc/rc.conf.local like so, and it'll magically start.

pkg_scripts="mysqld cups samba"

See the OpenBSD man page for rc.d for more details.

MySQL and chroot: I'm not sure why it didn't dawn on me before, but one really simple way around hard-linking MySQL's socket file into the chroot environment is to simply have your web applications connect to MySQL's TCP port on 127.0.0.1 (not localhost, because that means "use the socket file" in MySQL-ese) I think I'll be doing it this way in the future.

PHP: PHP 5.3 added a lot of features, such that PHP 5.2.x and PHP 5.3 might as well be different major version numbers when complex web applications are considered. OpenBSD 5.0 adds packages for PHP 5.3 for the first time, but PHP 5.2 is still available in the repository. For this reason, the PHP core and module packages are no longer prefixed by php5-, they're just php, php-mysql, etc. Since PHP 5.2 is still supported, the version numbers are used to distinguish them, like this:

$ sudo pkg_add php-mysql
Ambiguous: php-mysql could be php-mysql-5.2.17p3 php-mysql-5.3.6

Further, some configuration file locations have been changed. If you pay attention to the text after installing packages, this shouldn't make much difference. Hint: you can always re-read the post-install notes afterward by using pkg_info -M.

All in all, the recent changes to OpenBSD are welcome. Some of the things I outlined here are areas where OpenBSD had some catching up to do. They've managed to do a lot of proactive stuff in the realm of hardware support and (of course) security and encryption. This is still one of my favorite platforms to tinker with.

2010-12-02

Automate posting links from Delicious to Blogger

As you can tell, I've been playing with a way to create real blog posts from Delicious, not just an RSS feed splice. The old feed splice was being done with Feedburner, and it usually worked pretty well, but it lacked the flexibility I wanted and furthermore, it wouldn't actually create a post here. It would only show up in the RSS feed.


Delicious has an "experimental" (as in, not maintained since 2008) "Blog Posting Tool" that simply refuses to work with Blogger, the platform we currently use. In fact, it's so arcane that I don't really know if anyone has ever really made it work on anything other than Wordpress.

I threw something together in PHP that uses the Simple HTML DOM library to parse the output of the Delicious API. One part of that library that broke pretty spectacularly at first was trying to grab the "tag" attribute of each element. Simple HTML DOM uses "tag" as a variable name all over the place, and it caused some major recursion. I used preg_replace to change the name of "tag" to something else to avoid this namespace collision.

It's written in PHP because I was originally planning on cooking up something web-based, but I went more lightweight instead. Who knows, maybe I'll re-write it later on. Perhaps perl, python, ruby or even newLISP would have been better for this. It's designed to be run manually from the command-line or (more specifically) a nightly cron job.

I just know that there aren't any easy-to-use solutions for posting Delicious links to Blogger, and a lot of people seem to want something like this. It's rough, has some vestigial debugging code left in it, and it's probably not easy enough for most folks. It does what I wanted it to do, though, and you'll probably be seeing a lot more frequent link posts because of it.

Source. Public Domain. Yadda yadda. Enjoy.

2010-10-18

OpenBSD 4.8 is almost here! Chroot Apache, MySQL and Suhosin Hardened PHP


OpenBSD 4.8 is going to be released on November 1st, and that means it's time to revisit the setup of a highly-secure AMP stack on OpenBSD for hosting your web apps, blogs, and projects!

I actually cheated a bit to make this article, if you can call busting my ass performing a "make package" for hundreds ports in OpenBSD-current and doing a bunch of Virtual Machine snapshot reversions "cheating." It was a major pain in the butt to do, but I won't have much free time when OpenBSD 4.8 actually ships, so here you have it.

My Chroot OAMP series of articles is pretty popular, especially since attacks against PHP web applications are on the rise and people are looking for ways to get a little extra security for their web hosting environments.

By default, OpenBSD ships with a specially patched and code-audited derivative of Apache web server. It has been engineered specifically to run in a chroot environment, which is to say that even if someone or something could make Apache run arbitrary code, it can only impact what's in the web directory. It can't readily harm or disrupt the rest of the system.

The version of PHP in OpenBSD's package repository has also been tweaked with the Suhosin Hardened-PHP patch, which can defend vulnerable PHP applications from certain kinds of malicious attacks.

A relatively current version of MySQL is also in the package repository. The configuration provided isn't too bad.

Getting the software installed is easy, but turning it into a functional and secure AMP environment can be a chore if you haven't done it before.

Preparation:
During the installation of OpenBSD, you are prompted to create a non-root user. This feature was introduced last year with OpenBSD 4.6, and is primarily to discourage the improper use of the root account. The user you create during installation will be automatically added to the wheel group, which grants permission to use the su command. I generally add the wheel group to sudo as well, by adding this line to /etc/sudoers (with the root user):
%wheel   ALL=(ALL) SETENV: ALL
If you are currently logged in with your user-level account, you will need to log off and log in again in order to use sudo.

Package management used to be one of the more annoying aspects of OpenBSD. In 2004, I even wrote my own scripts to wrangle the packages. They've gotten consistently better over the years, and with OpenBSD 4.8, they introduced yet another great feature: /etc/pkg.conf (manual page .) There are only a few options available for this file right now, but it allows you to set global options for the package tools instead of setting up and relying on the PKG_PATH environment variable. If you perform an FTP install, the installer should automatically add the FTP mirror you used to this file. If you installed from CD but would like to use an ftp mirror for pkg_add, you need to add an "installpath" line to /etc/pkg.conf, which may not exist yet.
installpath=ftp://ftp5.usa.openbsd.org/pub/OpenBSD/4.8/packages/i386
Of course, you can pick whichever mirror you like. The OpenBSD project maintainers frown upon pointing direct downloads at the main ftp site. You can easily add local package repositories to this path.

Installing Packages
Installing php5-mysql and mysql-server will fetch all of the dependencies for OAMP. This process may take a while depending on your connection speed. There are several dependencies that will be installed, including php5-core and some perl modules.
sudo pkg_add php5-mysql mysql-server
Next, copy the PHP + MySQL sample files into place
sudo cp /var/www/conf/modules.sample/php5.conf \
/var/www/conf/modules/

sudo cp /var/www/conf/php5.sample/mysql.ini \
/var/www/conf/php5/
Run the script to get the default MySQL database installed, start MySQL and set a MySQL root password.
sudo /usr/local/bin/mysql_install_db

sudo /usr/local/share/mysql/mysql.server start

sudo /usr/local/bin/mysqladmin \
-u root password 'your-password'
At this point, both MySQL and PHP are installed and set up with a default configuration that will probably work fine for most applications.

Chroot Setup
In this version of OpenBSD, a chroot /tmp directory already exists with the proper permissions in /var/www, which simplifies setup of the chroot environment. All we're left to do is to reproduce the directory structure for the MySQL socket under /var/www.
sudo mkdir -p /var/www/var/run/mysql  # -p creates subdirs as needed
Start Apache and MySQL at boot
Set apache to start on boot by editing /etc/rc.conf. Find the httpd_flags line in the file, change NO to "" -- literally, two double quotes as shown below.
sudo vi /etc/rc.conf
# use -u to disable chroot, see httpd(8)
httpd_flags=""
Then, make sure that MySQL starts at boot and that the real mysql.sock file gets hard linked into the new directory by editing /etc/rc.local. I also added a line to remove the old hard link before starting MySQL. The end of my /etc/rc.local looks like this:
rm /var/www/var/run/mysql/mysql.sock
/usr/local/share/mysql/mysql.server starr
sleep 5

ln /var/run/mysql/mysql.sock /var/www/var/run/mysql/mysql.sock

After getting all of the services set up to start automatically, I usually reboot to make sure everything starts up as expected.
sudo reboot

Testing
Once the system comes back online, the most basic test of Apache and PHP is to create a phpinfo script. This can be done with one line of shell-fu, which will launch "tee" with root permissions to write the phpinfo.php file.

echo "<?php phpinfo(); ?>" | sudo tee /var/www/htdocs/phpinfo.php

Then, navigate to http://your.openbsd.ip.address/phpinfo.php in your web browser. It should load a nice-looking document containing details about PHP's configuration. In particular, check for MySQL.



To wrap up, I performed the usual "5 minute install" of Wordpress 3.0.1 (current as of writing) to see what happens. The end result was a totally painless and fully functional setup that's ready to go.

Wordpress on OAMP

2010-05-17

OpenBSD 4.7 + Chrooted Apache, MySQL & Suhosin PHP

FYI - There's now a page that covers OAMP for all recent versions of OpenBSD. My OAMP series is a popular one. Although OpenBSD 4.7 doesn't come out for 2 more days, the media has already shipped to those who pre-ordered. And, as I mentioned previously, you'll want to get crack-a-lacking on those patches. As of the time of writing, there are already 4 patches to install for OpenBSD 4.7, which affect all architectures.

I'll spare you the verbosity. The installation procedure for getting OpenBSD, Chrooted Apache, MySQL and Suhosin-hardened PHP all working together hasn't changed one bit in OpenBSD 4.7. You can follow my instructions verbatim from the OAMP 4.6 Walk-Through, with one minor difference: make sure you change "4.6" to "4.7" when defining PKG_PATH in your .profile.

I was able to go from an empty virtual machine to a fully-functioning, chrooted install of WordPress in under 30 minutes just by following the instructions (and, of course, pointing the PKG_PATH to the packages on the media, not FTP, since the 4.7 branch hasn't hit the Internet yet)

Now that blogger has the ability to store "pages", I may eventually convert this article series to a living document. There are also some lazy shortcuts I take that kind of go against traditional OpenBSD methods (directly launching stuff from rc.local, editing rc.conf instead of making changes in rc.conf.local, etc) - I may get around to de-cruft-ifying this how-to at the same time. Otherwise: Enjoy!

2010-03-24

Guest post: Pulling audio from YouTube with PHP and ffmpeg

Editorial note:
Patrick Teague is a colleague of mine from my first job in the mid-1990s. When I heard of the project he was working on, I asked if he wanted to share it here, and he obliged.

I got this working instantly on OpenBSD. All I needed to do was:
sudo pkg_add install pear php5-curl ffmpeg (and then copy the sample php5-curl config into place)
sudo pear install console_commandline

I also noticed that occasionally, I needed to run the script twice, once to set the proper cookies for curl, then it would work after that.

Enjoy!


The attached script requires the following... I've noted the Ubuntu packages and they should match Debian, other linux and/or BSD distros should be similar. Windows MSI installer should just be a simple matter of ticking off the options.

  • PHP 5.2+ CLI (php5-cli) with cURL installed (php5-curl)
  • PEAR's (php-pear) Console/CommandLine
  • ffmpeg binary should be in your environment $PATH and should have access to libmp3lame

I have no idea why people enjoy listening to music as videos with a static image, but Youtube is full of these as well as music videos and people playing their own remixes or original music. If I hear something I like I then try to get it off of emusic, itunes, directly from the artist at a show, or somewhere else. Sometimes the music just isn't available yet (no official CD/mp3 release) or the tunes are available directly off the musician's website, but there's a better/live remix on Youtube...

I found myself listening to something the other night and I was able to find plenty of tracks from the artist on emusic and itunes, but not the particular track. In 1 of the comments somebody asked where they could get a copy of the track and a reply mentioned mp3ify. I googled it and found http://www.mp3ify.com/ which I initially used to grab the mp3. After using it 2 or 3 times it screamed at me for not making a donation so I figured I should be able to figure out how they did it and stop wasting somebody else's bandwidth and processing time. Not to mention the more control I have over something the more control I have over my results.

I have flashgot installed and it allows me to download the flv (flash) files on Youtube pages, but it wasn't letting me see what the URL was and the only flv that I was easily finding in the HTML code was the player. Flashgot does allow you to add downloaders and send the downloader various different options including URL, cookie data, referer URL, etc. I wrote a quick shell script that would dump this information to a text file and used this information in my various attempts to grab the flv from Youtube.

Note: I must have really needed sleep because I completely forgot that I could have had an easier time grabbing the URL and cookie data from firebug.

I haven't done extensive testing, but the Youtube cdn seems to require a combination of several settings. I found that the I couldn't grab the flv without having certain cookie data, a referer URL, a "valid" User-Agent string, and a particular URL. The User-Agent it may not care about as I was rushing my testing, but I couldn't seem to get wget or curl to download the flv without setting it to a Firefox UA string. It seems to want certain cookie data, but I'm not sure how much of the cookie data is relevant vs the generated timestamp in the flv's URL - again, I was rushing this.

From what I can tell Youtube creates a javascript object named yt and adds settings to it via the yt.setConfig() function. This yt.setConfig() can accept single key/value pairs [i.e. yt.setConfig('LOGGED_IN', true);] or large JSON objects with several key/value pairs. In 1 of these large objects the value for VIDEO_TITLE is set (needed for modifying the URL) and the flv URL is listed within the SWF_ARGS key which is a property list and the particular value I found the URL listed in is fmt_url_map. The value for fmt_url_map is URL encoded with a pipe seperating 3 values. The 1st value is a number, the 2nd value is the URL that I used for the flv, and the 3rd value is another URL (I'm not sure what this URL is for). This 2nd value that I used as the URL is mostly correct, but can't be used without being modified. At the very end of the URL is a comma followed by a couple of characters, these need to be trimmed off the end and replaced with &#/ + a modified version of the VIDEO_TITLE + _video.flv.

I've only seen a limited set of translated characters in the modified VIDEO_TITLE. So far I've only seen space ( ), dash (-), period (.), and ampersand (&) are converted to an underscore (_) and square brackets (both [ and ]) are removed. I'm guessing there's a larger set of translated characters, but I'm not sure what they are... I'm also not sure how important it is to get these correct as at least 1 of my attempts had an incorrect name, but worked anyway (I would prefer to use a correct name just in case so it doesn't cause any red flags).

Honestly I'd prefer to run the html page through some shell utility (possibly rhino) that could process javascript and output the variables needed so I could let Youtube's code do it's own work. That would also make it more forward compatible if Youtube decided to change how they structure their URLs or something. In the meantime I used a combination of grep and sed to initially pull out the values I needed (exchanged for preg_grep() and preg_replace() in PHP code).

The final part was to convert the flv to a different format. I've used ffmpeg in the past for converting between media formats, but this was the 1st time I've used it to convert an flv. There are several nifty things that ffmpeg can do - merge raw video files with audio files, transcode decrypted VOBs into a video+audio format, audio and/or video conversions (i.e. wav into mp3), etc. I googled for ffmpeg convert flv to mp3 to get some quick solutions... 1 of the solutions I found suggested using -acodec mp3, but I couldn't get that to work. Initially I dropped back to mp2, but later discovered I needed to use -acodec libmp3lame instead. I should probably also state that -acodec copy is valid, but could cause problems if the embedded audio is in a format that isn't acceptable in an mp3 wrapper.

The other switches on ffmpeg I'm using are -ac 2 (setting the audio channels to 2), -ab 128k (the audio bitrate), -vn (disable video recording - don't need the video for an mp3), and -y (overwrite output files). There are many other switches available and I've thought about adding the following (possibly via some switches set up in Console/CommandLine) - -title string, -author string, -copyright string, -comment string, -album string, -track number, and -year number as these should populate the fields in the id3 tag.

The final bit is more of a pet peeve than anything that's really needed. My preference is to set the date on files to match what's on the server - otherwise how do you know if it's been modified. If you don't want or need this, feel free to comment out the if statement surrounding the curl_getinfo( $ch, CURLINFO_FILETIME ) as well as the if ( !touch( $file_mp3, $GLOBALS['server_filetime'] ) ) { section at the very end right after the passthru( $cmd );.

Download:

get-youtube (syntax highlighted)

get-youtube (plain text source code)

2009-10-28

OAMP: OpenBSD 4.6 + Chroot Apache + MySQL + PHP

Introduction
I'm combining the OAMP howto with chroot from the start this time because it's really the proper and secure thing to do. You can read more about how chroot works in my last article about it, but the premise is that chrooting Apache limits the amount of damage that can be caused by vulnerabilities in web applications. Keep in mind that we'll be accessing MySQL from within the chroot in this article, so all content within MySQL is potentially at risk if you're serving up SQLi-vulnerable content. The best things the average sysadmin can do to protect the server is to keep webapps and system patches up-to-date, and to perform periodic database dumps and system-wide backups.

I will walk through the commands here without showing the output they generate. You can reference my OAMP walk-through from OpenBSD 4.4 if you want to see example output, which should look similar for OpenBSD 4.6. The output shouldn't matter much, because I'll walk you through everything here.

Preparation
To start off, I make sure that a user-level admin account has access to run anything as root from sudo. Note: all the administrative commands in this post begin with "sudo" for a reason. To do this, I add my admin account to the wheel group. You can do this during the adduser process or with usermod, but if you created a non-root admin user during the OpenBSD 4.6 installation process, that user will be in the wheel group by default. All you need to do is add a sudo rule for the wheel group. It's commented out in /etc/sudoers.

$ su -
Password:
# visudo
... or use whatever editor you want on /etc/sudoers. Not recommended.

Find the line that grants access to the wheel group, and uncomment it. It's about 35-40 lines down in the default configuration. Optionally, there's a NOPASSWD version of the same, a few lines down. I don't recommend using this option on a production server, but it may make system management more friendly on your development servers and workstations.

%wheel ALL=(ALL) SETENV: ALL
-- or --
%wheel ALL=(ALL) NOPASSWD: SETENV: ALL

I also set up the path for pkg_add by adding these lines to my user-level account's .profile, then logging out and back in to reload the profile. I usually use an OpenBSD mirror, like ftp5.usa.openbsd.org instead of the main FTP site. You can also use any of the http mirrors in this path.
vi .profile

PKG_PATH=ftp://ftp5.usa.openbsd.org/pub/OpenBSD/4.6/packages/i386/
export PKG_PATH
Installing Packages
Installing php5-mysql and mysql-server will fetch all of the dependencies for OAMP. This particular version of PHP comes pre-compiled with the suhosin hardened PHP patches in place, which is a nice touch! This process may take a while depending on your connection speed. There are eight or nine packages in total, including php5-core and some perl modules that MySQL depends on for its management tools.
sudo pkg_add php5-mysql mysql-server
Next, copy the PHP + MySQL sample files into place
sudo cp /var/www/conf/modules.sample/php5.conf \
/var/www/conf/modules/

sudo cp /var/www/conf/php5.sample/mysql.ini \
/var/www/conf/php5/
Run the script to get the default MySQL database installed, start MySQL and set a MySQL root password.
sudo /usr/local/bin/mysql_install_db

sudo /usr/local/share/mysql/mysql.server start

sudo /usr/local/bin/mysqladmin \
-u root password 'your-password'
At this point, both MySQL and PHP are installed and set up with a default configuration that will probably work fine for most applications.

Chroot Setup
Most AMP packages only need somewhere to store Session information and a way to get to the MySQL socket. Since the real /tmp contains information that is not needed for Apache, we'll just create a new tmp directory specifically for Apache within /var/www and make it world-writable with the "sticky bit" set (exactly like the real /tmp)
sudo mkdir /var/www/tmp
sudo chmod 1777 /var/www/tmp
Next, reproduce the directory structure for the MySQL socket under /var/www.
sudo mkdir -p /var/www/var/run/mysql  # -p creates subdirs as needed
Start Apache and MySQL at boot
Set apache to start on boot by editing /etc/rc.conf. Find the httpd_flags line in the file, change NO to "" -- literally, two double quotes as shown below.
sudo vi /etc/rc.conf
# use -u to disable chroot, see httpd(8)
httpd_flags=""
-or-
httpd_flags="-u" #disables chroot. You can if you want.
Then, make sure that MySQL starts at boot and that the real mysql.sock file gets hard linked into the new directory by editing /etc/rc.local. I also added a line to remove the old hard link before starting MySQL. The end of my /etc/rc.local looks like this:

rm /var/www/var/run/mysql/mysql.sock
/usr/local/share/mysql/mysql.server start
ln /var/run/mysql/mysql.sock /var/www/var/run/mysql/mysql.sock

After getting all of the services set up to start automatically, I usually reboot to make sure everything starts up as expected.

sudo reboot

Testing
Once the system comes back online, the most basic test of Apache and PHP is to create a phpinfo script. This can be done with one line of shell-fu, which will launch "tee" with root permissions to write the phpinfo.php file.

echo "<?php phpinfo(); ?>" | sudo tee /var/www/htdocs/phpinfo.php

Then, navigate to http://your.openbsd.ip.address/phpinfo.php in your web browser. It should load a nice-looking document containing details about PHP's configuration. In particular, check for MySQL.


To really put our fresh chrooted OAMP installation through its paces, I downloaded the latest version of Wordpress, then followed the instructions using "the famous 5-minute install", which is way beyond the scope of this article. It's as simple as creating a database, setting up a privileged user for that database, editing a configuration file and copying wordpress into /var/www/htdocs (or a subdirectory) before accessing the control panel to finish up.

The wordpress install worked without changing anything from the instructions, and it's all running under chroot without any problems!


If you find that things are not working well with a particular AMP application, check file permissions, and copy or create hard links to files or directories that are needed. Example: sometimes you need a fake /etc/password file, some tools from /usr/bin or a /dev structure to be replicated within the chroot environment. Add these only as needed.

2009-10-02

Solving transit questions with PHP

When I saw Visualmotive's "Walk or Bus?" chart, I was fascinated. I love stuff like this! It answers the question of "If I have to be somewhere, is it going to be faster to wait for a bus, or just start hiking?"

I am a multi-mode commuter. I often use my bike combined with the bus to get myself downtown. Sometimes, I also need to get around the city. I almost always do this on my bike unless it's somewhere really close. Still, I felt compelled to create a chart that included bicycling, as well as walking.


The top header is how long you'll have to wait for the bus.Where there's a gray bus icon, it's faster to wait for the bus. Where there's a blue bicycle, it's faster to hop on the bike and ride. The yellow jogging man represents a brisk walking pace and the green foot represents trudging along with an average gait. I extended the chart out to 4.0 miles, which is about how far one can get on a bicycle in an urban setting within half an hour at 8 MPH. These are just guidelines, of course. Some people are considerably faster on bicycles. Others are slower. Same with walking and the bus, actually.

Click for big:


I ended up making a quick program in PHP to draw the main part of the above chart for me. I sourced the icons from the same place Visualmotive did (icons.mysitemyway.com) but opted to modify their icon colors, then added the headers manually in GIMP. I'll upload a .zip file (and link to it) later, with the icons.

The algorithm is pretty straightforward. Urban buses probably average 15 MPH with all their stops included, or about 4 minutes for every mile. Most people can get around on a bicycle at an average speed of 8 MPH (7:30) and so on and so forth as commented in the code below.

The code is pretty simple and very ugly. Not only did I use tables (ew) but I also barf out HTML with PHP. This is why I say there's a massive difference between programmers (like me) and developers (who code for a living).


<html><head><title>Walk, Bike, or Bus?</title></head><body>
<TABLE cellpadding='0' cellspacing='0'><TR>
<TD></TD><TD><CENTER>1</CENTER></TD><TD><CENTER>2</CENTER></TD>
<TD><CENTER>3</CENTER></TD><TD><CENTER>4</CENTER></TD>
<TD><CENTER>5</CENTER></TD><TD><CENTER>6</CENTER></TD>
<TD><CENTER>7</CENTER></TD><TD><CENTER>8</CENTER></TD>
<TD><CENTER>9</CENTER></TD><TD><CENTER>10</CENTER></TD>
<TD><CENTER>11</CENTER></TD><TD><CENTER>12</CENTER></TD>
<TD><CENTER>13</CENTER></TD><TD><CENTER>14</CENTER></TD>
<TD><CENTER>15</CENTER></TD><TD><CENTER>16</CENTER></TD>
<TD><CENTER>17</CENTER></TD><TD><CENTER>18</CENTER></TD>
<TD><CENTER>19</CENTER></TD><TD><CENTER>20</CENTER></TD>
<TD><CENTER>21</CENTER></TD><TD><CENTER>22</CENTER></TD>
<TD><CENTER>23</CENTER></TD><TD><CENTER>24</CENTER></TD>
<TD><CENTER>25</CENTER></TD><TD><CENTER>26</CENTER></TD>
<TD><CENTER>27</CENTER></TD><TD><CENTER>28</CENTER></TD>
<TD><CENTER>29</CENTER></TD><TD><CENTER>30</CENTER></TD></TR><TR>
<!-- Model View Controller what? -->
<?php
$Miles
=.2; # .2 Miles. Just walk it. Jeez.
while ($Miles <= 4.0){
$Miles=$Miles+.1;
$TravelTime['Bus'] = $Miles * 4; # Bus ! 15 MPH (4:00 mile)
$TravelTime['Bike'] = $Miles * 7.5; # Bike ~ 8 MPH (7:30 mile)
$TravelTime['Brisk'] = $Miles * 15; # Brisk walk ~ 4 MPH (15:00)
$TravelTime['Walk'] = $Miles * 20; # Walk ~ 3 MPH (20:00)
$Mins=0;
print
"<TR><TD><CENTER>$Miles</CENTER></TD>";
while (
$Mins < 30){
print
"<TD><CENTER>";
$Mins++;
if (
$Mins >= $TravelTime['Walk'])
{print
"<IMG WIDTH='45' SRC='img/iconwalk.png'>";}
elseif (
$Mins >= $TravelTime['Brisk'])
{print
"<IMG WIDTH='45' SRC='img/iconbrisk.png'>";}
elseif (
$Mins >= $TravelTime['Bike'])
{print
"<IMG WIDTH='45' SRC='img/iconbike.png'>";}
else
{print
"<IMG WIDTH='45' SRC='img/iconbus.png'>";}
print
"</CENTER></TD>";
}
print
"</TR>"; #I know you're not supposed to print HTML. Byte Me.
}
?></body></html>

So, what started as a desire to have a cool chart to share with other bicycling/pedestrian friends of mine turned into an exercise in algorithms last night, with a little bit of PHP programming tossed into the mix. This is yet another example of a quick-n-dirty program I wrote for something simple.

2009-05-11

PHP Editing In The Cloud

I ran across PHP Anywhere over the weekend. At first glance, it looks as feature-rich as the free version of PHP Designer, a Windows-only tool I use at work when I have to mess with PHP (which isn't too often)

There's just one question I have: who in their right mind would store the FTP password to their web site "in the cloud" like this? In fact, I don't even have FTP access ENABLED on my primary web server. I set up a test instance somewhere else to play with PHP Anywhere. I usually scp my files to their destination. Sadly, that's not an option for PHP Anywhere yet, but if it did, you'd still be storing credentials to modify your website...



I suppose if you are really in a crunch somewhere and lack your usual desktop IDE of choice (and for some reason can't get on the system to edit it locally), it makes for a neat toy.

That's all for today. I'm going to change my password on that FTP account now...

2009-05-01

Securing Php Web Applications

PHP is a popular server side scripting language, it's as simple or as complex as you want to make it. It is typically used along with Linux, Apache Web server and MySQL RDBMS. In most web applications the script acts on user provided information and returns processed data. To this end there are a number of simple steps you can take to help make your web application less vulnerable to exploitation by an unfriendly party.

This article is intended for beginning to intermediate web application programmers.

=======ToC=========
1. Introduction
2. Methods of input
3. Input data validation
4. Trusted processing
5. Database queries
6. Raising the bar
7. Informative resources
===================
1. Introduction

PHP is a HTML pre-processor, meaning that it reads a file before it is sent to the user and if it contains PHP script, it processes it and returns the document and the processed results to the user. There are many other technologies which do the same thing each with their benefits and flaws. The importance here is not to proclaim the benefits of PHP over the others but to show some good ideas of how to protect your applications from un-friendlies.

2. Methods of input

In PHP we can get information externally from the webserver itself ($_SERVER), Cookies ($_COOKIE), Get variables ($_GET), Post Variables ($_POST) . In addition PHP can internally connect to just about anything.

Example:
So when Joe, our end user goes to your website to check this weeks Fantasy Football scores on your website, he will login (sending login information using POST variables) to a script which then reads the login information and decides whether he can login. Then it returns a page with the result of his attempt and then either takes him to the next page or back to the login prompt. Once he is logged in, PHP sets a Cookie with a unique random session id. Every time a browser returns that cookie to a page, it knows that this session is good and belongs to Joe. Then Joe sorts his results page sending some criteria via a Get variable which is used to control a query to the sports database.

The important thing to know is that Joe can control everything he sends to the server. He can see the cookie contents, post data and get variables. Lets say that Joe wants to check a friends team score. The site allows Joe to sort his scores using GET variables. Joe just places in an escape character and appends some SQL to view his friends score.

3. Input data validation

Think of a web application like a game of D&D, if you are out on the desert plains with a 12th level Barbarian named Ogar, whats keeping the player from making Ogar go left when the DM expects the player to go right? There is no reason Ogar the barbarian can't sit down and whittle a set of dice, mark up a parchment with character stats and then play Cube farms & Bosses.

You have a nice HTML page which provides for the intended actions of the user but everything in the browser or on the computer is out of your control. Java script, plug ins, input, cookies and URLs are not controllable and therefore cannot be fully trusted.

The key is limiting the users choices, and abstracting their decisions. If your scripts inputs expect a phone number, then the input should only be numbers or else its invalid. If there is only search methods A,B or C then if the input isn't A,B or C then it has to be invalid. Simply filtering out known bad data such as embedded javascript isn't 100% effective, if the data type is contaminated it cannot be trusted.

The quality of the data you take in is important, the other part of this is abstraction of the users decisions. If a persons available choices are A,B and C, and internally you identify A, B and C as actions and everything else as false input then that is more effective than allowing user input directly control your data.

4. Trusted processing

Assuming that you have done your due diligence and secured your server, it is more trustworthy of a computing platform than your clients workstation. A clients workstation could be infected with mal-ware, it could have a malfunctioning or obsolete browser or the user could intentionally manipulate the http variables to trick the application. Input validation cannot be done using JavaScript alone, trusting JavaScript or any other plug in to obfuscate your applications process just isn't a good idea. Client side scripting is good for enhancing the presentation and for providing a means to communicate information effectively to the user but it should not be relied upon to process information.

5. Database queries

Filtering valid data is just one step, the other step is on your data sources such as MySQL, Postgres, Oracle ... most modern Databases allow you to do a prepared statement which auto-magically binds input into a SQL string. Because its binding data directly to a variable the chances that a user's escape string can hijack the SQL query is greatly diminished. By limiting the users input to only data and not to the program execution process you greatly reduce the possibility of your script becoming compromised.

For example:

"http://example.com/mypage.php?display=select * from mydatabase.mytable where user=Joe order by date;"

Including SQL in a user accessible variable is a really really bad idea. Even if it is on a link that Joe wont see and Java script is used to obscure the URL. Joe controls the machine so any obfuscation used will never be effective. What is stopping Joe from substituting "select 'joe' as user password as score, currdate() as date from mysql.users where username=root;"?

6. Raising the bar

There are alot of "Magic Bullet" solutions to web application security. Application firewalls monitor information going both to and the web application. SQL application firewalls filter out suspicious SQL commands going to your RDBMS server. For most developers, these solutions are
either too expensive or too complex to implement for individual web applications. Here are some PHP security plug ins and tools to help raise the bar on the cheap.

When you use this or any other security plug-in, it is vital that you evaluate your applications baseline performance to know what is normal behavior. For instance PHPBB2, a popular PHP bulletin board application display a large list of forums. And mysteriously the settings would not save. I was using Suhosin and this was caused because the number of variables being posted was above Suhosin's default limit and the script was aborting before it could save the changes.

On the server side there is Green SQL, which is a MySQL sanitizer/proxy. Then there is mod_security which hardens Apache and turns it into an application firewall. mod_chroot is similar in the basic functionality of mod-security except it just chroots Apache transparently to the user. Then there are web application security scanners such as the ones included in Nesssus.

Wapiti checks for cross-site scripting (XSS), injection and other common issues. OWASP's WebScarab is a good utility for testing user access to http variables on the client side and intercepting the raw http conversation between the client and the server.

7. Informative resources


Breach Security "Mod Security home page". (Accessed April 2009)
http://www.modsecurity.org

Dawes, Rogan "OWASP WebScarab Project" (Accessed April 2009)
http://www.owasp.org/index.php/Category:OWASP_WebScarab_Project

Esser, Stefan "Hardened PHP Project" (Accessed April 2009)
http://www.hardened-php.net/suhosin/

Freitag, Pete "20 ways to Secure your Apache Configuration" (Accessed April 2009)
http://www.petefreitag.com/item/505.cfm (Posted Dec 5, 2005)

Green SQLProject "Green SQL home page". (Accessed April 2009)
http://www.greensql.net

Hobbit "mod_chroot" (Accessed April 2009)
http://core.segfault.pl/~hobbit/mod_chroot/


OWASP Foundation. "Main Page" (Accessed April 2009)
http://www.owasp.org/index.php/Main_Page

Tenable network security inc. "Nessus Product Page" (Accessed April 2009)
http://www.nessus.org/nessus/

The Apache Foundation. "Apache HTTP Server Project". (Accessed April 2009)
http://httpd.apache.org/

The PHP Group. "PHP: Hypertext Preprocessor". (Accessed April 2009)
http://www.php.net/

Surribas, Nicolas "Wapiti Web application vulnerability scanner / security auditor" (Accessed April 2009)
http://wapiti.sourceforge.net/

See also:
Ax0n's OAMP (Apache, Mysql, PHP on OpenBSD) Article:
http://www.h-i-r.net/2008/12/sysadmin-sunday-amp-on-openbsd-44.html

Asmodian X's Name based hosting mini-howto:
http://www.h-i-r.net/2008/10/sysadmin-sunday-apache-name-based.html

Asmodian X's Workbench - Suhosin :
http://www.h-i-r.net/2008/12/asmodians-workbench-suhosin-hardened.html

2008-12-23

Asmodian's Workbench: Suhosin Hardened PHP extension and patch.

Suhosin is a plug-in and patch for PHP. It places a white-list filter of actions which are allowed. It prevents a pile of PHP exploits from happening such as buffer overflows and certain kinds of injection attacks. You can find it at the Hardened PHP project web-page. It has a number of default items it blocks, one of which is the number of variables it allows to be posted and received.

You can configure it to either block potential attacks a and to log the results in unix syslog. you can also configure it to allow issues to occur and to only log events too.

You can control the Suhosin default values in your php.ini file.

Some php applications use an enormous amount of post variables so the default value (200) is probably too low. As I have explained to my co-worker, getting rid of the plug-in because your script uses too many post variables is probably not the best solution.

The solution in the that event is to modify the maximum request and post vars.

You can also tell suhosin to in the event of encountering a possible attack to run a different script or a http redirect instead. Like perhaps something like this:
(php.ini entry)


[suhosin]
suhosin.filter.action=[302,]http://www.youtube.com/watch?v=Yu_moia-oVI

As you can see this has a number of interesting possibilities.

If you are interested in PHP and AMP (oamp,lamp ...etc) technologies See also:

The hardened PHP project:
http://www.hardened-php.net/suhosin/

Ax0n's OAMP (Apache, Mysql, PHP on OpenBSD) Article:
http://www.h-i-r.net/2008/12/sysadmin-sunday-amp-on-openbsd-44.html

Asmodian X's Name based hosting mini-howto:
http://www.h-i-r.net/2008/10/sysadmin-sunday-apache-name-based.html

The PHP main website:
http://www.php.net/

The Apache webserver website:
http://httpd.apache.org/

2008-12-21

Sysadmin Sunday: AMP on OpenBSD 4.4

FYI - There's now a page that covers OAMP for all recent versions of OpenBSD.


At the beginning of 2008, I posted how to get Apache, PHP, and MySQL running on OpenBSD 4.2. This is commonly known as LAMP when running under Linux. I call this OAMP.

I decided to AMP my OpenBSD 4.4 rig, and followed those instructions. No surprise, things have changed a little bit.

Before installing packages
First and foremost, make sure you can easily install packages. In this case, I've added the FTP repository to the PKG_PATH environment variable, then I've made sure my user-level account has access to sudo.

OpenBSD's package system has finally become a little less flaky about remote packages and dependencies, so I finally added this to my user-level account's .profile:
PKG_PATH=ftp://ftp.openbsd.org/pub/OpenBSD/4.4/packages/i386/
export PKG_PATH
My user-level account is also in the wheel group, and the following line was uncommented from /etc/sudoers:
%wheel ALL=(ALL) SETENV: ALL
That means anyone in wheel can run anything with sudo as any other user (root by default)

Installing packages
Obviously, you've got OpenBSD 4.4 installed and patched. If not, you'd better get crack-a-lacking, homeslice! OpenBSD comes with Apache, so you're basically halfway there by installing OpenBSD.

The following command will install php5-mysql and mysql-server (obviously)
That will grab all the dependencies in one swoop, including the mysql-client package and php5-core. I'll snip the output to only display the relevant stuff, and address that afterwards
-bash-3.2$ sudo pkg_add php5-mysql mysql-server
--- php5-core-5.2.6 -------------------
To enable the php5 module please create a symbolic
link from /var/www/conf/modules.sample/php5.conf
to /var/www/conf/modules/php5.conf.

ln -s /var/www/conf/modules.sample/php5.conf \
/var/www/conf/modules

The recommended php configuration has been installed
to /var/www/conf/php.ini.

Don't forget that the default OpenBSD httpd is chrooted
into /var/www by default, so you may need to create support
directories such as /var/www/tmp for PHP to work correctly.
--- php5-mysql-5.2.6 -------------------
You can enable this module by creating a symbolic
link from /var/www/conf/php5.sample/mysql.ini to
/var/www/conf/php5/mysql.ini.

ln -fs /var/www/conf/php5.sample/mysql.ini \
/var/www/conf/php5/mysql.ini
Configuring Packages
As shown above, there's some work to do in order to make PHP work with Apache and make the PHP module load the MySQL client library.

I'm not a huge fan of symbolic links to sample files. I opted to copy them.
sudo cp /var/www/conf/modules.sample/php5.conf \
/var/www/conf/modules/

sudo cp /var/www/conf/php5.sample/mysql.ini \
/var/www/conf/php5/

Install the default database and start MySQL, then assign a password for the MySQL root user with the following commands (the output doesn't really matter)
sudo /usr/local/bin/mysql_install_db

sudo /usr/local/share/mysql/mysql.server start

sudo /usr/local/bin/mysqladmin \
-u root password 'your-password'

Now, we want to make sure that both Apache and MySQL start automatically.

Find the "httpd_flags" line in /etc/rc.conf and set it to literally two quotes: "" or, if you want to disable chroot (not recommended, but can make OAMP life much easier for you when you go to install webapps) set it to "-u":
sudo vi /etc/rc.conf
(find httpd_flags once editing the file)

# use -u to disable chroot, see httpd(8)
httpd_flags=""
-or-
httpd_flags="-u"

You can launch apache easily from the command line now by executing httpd, so you don't need to reboot. Use -u if you specified it in /etc/rc.conf.
sudo httpd
This is kind of a cheap and non-official way to do make MySQL start, but it works just fine and it's how I always do it. You're supposed to make an rc function and all that so you can enable/disable it in /etc/rc.conf. Bah. Add the following line to the end of /etc/rc.local.
sudo vi /etc/rc.local
(add the following line to the end)
/usr/local/share/mysql/mysql.server start
At this point, you have OpenBSD set up to start Apache and MySQL at boot, and both should be running. Additionally, the PHP module should be loaded. To test MySQL, use mysql_setpermission, a perl script that lets you manage and create databases and users.

mysql_setpermission -u root
Password for user root to connect to MySQL: your-password
######################################################################
## Welcome to the permission setter 1.4 for MySQL.
## made by Luuk de Boer
######################################################################
What would you like to do:
1. Set password for an existing user.
2. Create a database + user privilege for that database
and host combination (user can only do SELECT)
3. Create/append user privilege for an existing database
and host combination (user can only do SELECT)
4. Create/append broader user privileges for an existing
database and host combination
(user can do SELECT,INSERT,UPDATE,DELETE)
5. Create/append quite extended user privileges for an
existing database and host combination (user can do
SELECT,INSERT,UPDATE,DELETE,CREATE,DROP,INDEX,
LOCK TABLES,CREATE TEMPORARY TABLES)
6. Create/append full privileges for an existing database
and host combination (user has FULL privilege)
7. Remove all privileges for for an existing database and
host combination.
(user will have all permission fields set to N)
0. exit this program

Make your choice [1,2,3,4,5,6,7,0]:
If it shows the menu, then MySQL is running and the password you configured is working.

Test PHP and Apache by creating a phpinfo.php file in /var/www/htdocs/phpinfo.php:
<?php
phpinfo();
?>


Hit it with your web browser to make sure it loads. It should show you information about your PHP installation, including the MySQL module.


If you experience problems installing *AMP-based web apps, try:
  • Making a hard link to /var/run/mysql/mysql.sock within /var/www somewhere, and editing the php.ini file accordingly
  • Disabling apache chroot by setting httpd_flags="-u"
  • Checking the php, mysql, and apache error logs for more information about what went wrong