Categories
Administration Development Software

Displaying PHP errors with Xdebug in Ubuntu Server

Ubuntu Server packages are generally pretty well-configured right out of the box–usually requiring little or no configuration for simple operation. It’s one of the reasons why, despite my preference toward Arch Linux for the desktop, I’ve long advocated Ubuntu as a great starting point for a LAMP development server. Yet, on occasion, a package ships with a configuration that needs some work in order to be useful. Xdebug is such a package.

Xdebug’s most immediately helpful feature is the display of stack traces for all PHP errors. (Actually, it does a whole lot more than that, but that’s beyond the scope of this post.) Stack traces appear in place of the ordinary PHP error notices, so they require that the PHP config option **display_errors** is enabled. But Ubuntu disables this option by default.

This is actually a sane default, because error notices may potentially expose security holes or other sensitive data, and thus should be suppressed in production environments. But installing Xdebug implies that the target is a development and/or testing environment (for a lot of reasons, not the least of which is Xdebug’s non-trivial processing overhead). So it makes sense that display_errors should be enabled.

This is a simple fix. Edit */etc/php5/apache2/php.ini*, locate the **display_errors** option, and change its value from **Off** to **On**. The final result should look like this:

display_errors = On

Alternatively, you can add that line to the end of the Xdebug config file located in */etc/php5/conf.d/*. This allows you to enable/disable the display of errors at the same time as you enable/disable the Xdebug module. (This can be done by invoking either of the provided scripts **php5enmod** and **php5dismod** and reloading Apache.)

I have filed [a bug report]( https://bugs.launchpad.net/ubuntu/+source/xdebug/+bug/1096464) to notify the devs about this issue. I hope this post and an eventual bug fix will save other folks some frustration.

Categories
Development Software

File Access Bug in LAMP Virtual Machine

Using a VM as a web development test server is a great way to optimize workstation resources. My test VM is an Ubuntu installation with a standard Apache/MySQL/PHP stack. I use VirtualBox shared folders to grant the VM access to my development directory.

For some time I have been wrestling with an irritating bug that crops up when using shared folders with Apache: when a new file is created, and sometimes when existing files are modified, Apache fails to recognize the change. Any attempt to access the file via HTTP will result in a 404 error. Some searching led me to this VirtualBox bug report and the solution.

By default, Apache leverages the kernel’s *sendfile* mechanism to deliver resources to HTTP clients in order to optimize performance. But when a small file on a network share is altered, sometimes sendfile doesn’t bother to check its length or contents. Most of the time this is not an issue for production servers, which rarely use network storage and which don’t experience the frequent file changes of a development server. But in this case the default behavior needs to be changed.

To turn off sendfile in apache, add the following line to the Apache server configuration (i.e. **/etc/apache2.conf**):

EnableSendfile Off

Restart Apache to apply the new configuration.

###Related Links
* [vboxsf and small files](http://frankooh.wordpress.com/2011/01/21/vboxsf-and-small-files/)
* [Apache EnableSendfile Directive](http://httpd.apache.org/docs/2.2/mod/core.html#enablesendfile)

Categories
Software

Simple Wake-on-LAN Wrapper Script

Our home network includes a number of Linux-based systems and one Apple iMac. Because the Mac hosts all of our family photos, and because printing from a Mac to a Linux printer is a headache, it made the most sense for us to connect the printer directly to the Mac. However, this creates an issue when printing from one of the other computers: if the Mac is asleep, the shared printer does not respond to requests.

The workaround is simple: get up, walk over to the Mac, and hit the space bar or click the mouse to wake up the machine before trying to print. But we don’t want to get up, so we’ll issue a Wake-on-LAN packet to the Mac instead, using **wakeonlan**.

**wakeonlan** is a simple Perl script written by Jose Pedro Oliveira and maintained by Ico Doornekamp. It is available from the repositories for most Linux distributions. The script broadcasts “magic packets” over the network that are read by WOL-compatible interfaces. If the interface recognizes its own MAC address in the magic packet, the interface signals the host machine to “wake up.”

Sure, it’s a neat trick, but we have to know the destination machine’s MAC address. So we can either make MAC address flash cards for our LAN, or we can write a wrapper script to find the MAC address for us and issue the packet.

### Finding the MAC Address ###

To find the MAC address we can use **arp**, a standard Linux utility, to read the local host’s ARP cache. The ARP cache is an important part of any Ethernet network–it stores a table of every known host on the network by IP and MAC address. Essentially, it serves as the local host’s “address book,” making sure requests to a given IP address are sent to the appropriate network interface. Most of the time, this translation is done in the background while the user remains happily oblivious. But Wake-on-LAN packets are special, and they need our help to get to where they’re going.

The output of **arp** looks something like this:

$ arp
Address HWtype HWaddress Flags Mask Iface
server ether ab:cd:ef:01:23:45 C eth0
bobs-machine ether 11:22:33:44:55:66 C eth0
arpeggio ether 56:45:34:23:12:01 C eth0
My-iMac.domain ether c8:2a:14:ff:ff:ff C eth0
My-iMac.local ether e4:ce:8f:00:00:00 C eth0

We’re interested in the third column–the MAC address–of the machine called `My-iMac`. Because the iMac’s Ethernet and Wi-Fi interfaces are both enabled, the same hostname shows up twice (albeit with different domains). We’re only interested in the Ethernet interface, which, fortunately, shows up first (the output of **arp** does not tell us which is which–in my case, I know this because I’ve set up static DHCP leases on my home network–finding this out may require some digging or trial and error). This means that we can write our script to search for the first line matching the hostname, then to extract the third column from that line. We accomplish this using **grep** and **awk**, respectively.

$ arp | grep -i -m1 imac
My-iMac.domain ether c8:2a:14:ff:ff:ff C eth0
$ arp | grep -i -m1 imac | awk ‘{print $3}’
c8:2a:14:ff:ff:ff

For this discussion we’ll bypass a detailed explanation of the **grep** and **awk** commands. See the Linux man pages for details.

Now that we have a command line string that finds the right MAC address, we can write our script.

### The Script ###

Below is our Wake-on-LAN wrapper script, saved in a file named **wol**:

#!/bin/sh

MACADDR=`arp | grep -i -m1 $1 | awk ‘{print $3}’`
wakeonlan $MACADDR

All we’ve done is taken our command line string and replaced the hostname search string (`imac`) with the variable `$1`, which is interpreted by the shell as the first argument passed to the script by the user. This way we can use the same script to send WOL packets to any machine on the network. Executing the script looks like this:


$ ./wol imac

There. Wasn’t that easier than getting up and hitting the space bar?

### Further Reading ###
* [Wake-on-LAN at Wikipedia](http://en.wikipedia.org/wiki/Wake-on-LAN)
* [ARP cache: What is it and how can it help you?](http://www.petri.co.il/csc_arp_cache.htm)

Categories
Software

MP3 Encoding Support in Ubuntu 11.04

Today I went to copy my music library from Banshee to an old iPod mini. I found out the hard way that the Ubuntu 11.04 upgrade tool uninstalls the necessary programs for MP3 encoding support, causing Banshee to fill my iPod with WAV files.

This is most likely a [philosophical decision](http://www.ubuntu.com/project/about-ubuntu/our-philosophy “Our philosophy | Ubuntu”) stemming from the ongoing debate between [open-source pragmatists and free software idealists](http://en.wikipedia.org/wiki/Free_software_movement#Criticism_and_controversy “Free software movement – Wikipedia”). We won’t get into that here, but assuming you *do* want MP3 support, it’s a simple fix:

# apt-get install ubuntu-restricted-extras

Once this package is istalled, restart Banshee and it should automatically encode to MP3 without changing any settings.

Don’t get me wrong–I admire the idealists, but I also want to fit more than 20 songs on my iPod.

Categories
Software

Command Line DVD Ripping

I recently took on the task of digitizing our old VHS tapes. While
digging through the tapes I came across an old, region-2-encoded DVD
copy of *Rocketman*, starring Harland Williams. I bought it years
ago before it was available on region 1 DVD. In those days I had a DVD
drive which I kept set to region 2, but no longer. It’s time to get rid
of this thing, but not before we make ourselves an MP4 copy.

DVD region 2 is the designation for most of Europe, so in addition to
the region issue, most region 2 disks are formatted for PAL systems.
This particular movie was sped up approximately 1fps to match PAL
framerates, and stretched vertically to fill in the extra vertical space
on PAL screens. Since we’re going to be dealing with raw video streams
anyway, we’ll take the time to slow down and rescale the final product.

Linux wants for nothing when it comes to video processing applications.
The trick is to sort through them all and find the right tools for the
job. Everything we need is available in the Ubuntu repositories.

First, we set the region flag on the DVD drive to region 2. This can be
done with a simple program called **regionset**. Note that most DVD
drives only permit a limited number of changes to this setting. We’ll
run **regionset** and follow the prompts:

$ regionset

Next, we copy the VOB file from the DVD to the disk, so that we can
manipulate the audio and video streams. **vobcopy** will do the job:

$ vobcopy -l

This creates a file called ROCKETMAN1.vob in the current directory. At
this point we can eject the DVD and re-set the region flag. Everything
else will be based on this VOB file.

Our next step is to use **mplayer** to extract the audio from the VOB
file so that we can slow it down to match the new frame rate:

mplayer ROCKETMAN1.vob -ao pcm:file=rocketman.wav -vo null

Once that’s finished, we’ll start the rather long process of ripping and
reformatting the video:

ffmpeg -i ROCKETMAN1.vob \
-f rawvideo -pix_fmt yuv420p – 2>/dev/null \
| ffmpeg -f rawvideo -r 23.976 -s 720×576 -pix_fmt yuv420p -i – \
-vcodec libx264 -pass 1 -vpre slow_firstpass -b 768K -s 720×480 \
-threads 0 -y rocketman.mp4 \
&& ffmpeg -i ROCKETMAN1.vob \
-f rawvideo -pix_fmt yuv420p – 2>/dev/null \
| ffmpeg -f rawvideo -r 23.976 -s 720×576 -pix_fmt yuv420p -i – \
-vcodec libx264 -pass 2 -vpre slow -b 768K -s 720×480 \
-threads 0 -y rocketman.mp4

That monster command actually invokes two instances of **ffmpeg**; one to
feed the raw video stream from the VOB into a pipe, the second to read
in the raw stream, apply the new frame rate, then resize and encode the
result.

While that runs we can process the audio using **sox**. This particular
movie is a little quiet, so we’ll normalize the volume while we’re
changing the speed. Our speed ratio is based on the source and
destination frame rates. The PAL-formatted VOB stream is 25fps, and
our final product will be 23.976fps (an NTSC standard). 23.976/25 is
.95904, so that is our ratio:

sox –norm rocketman.wav rocketman.flac speed .95904

When all of this time-consuming processing is finished, we can take our
converted video and audio streams and reunite them (a process known as
*muxing*) using **ffmpeg**:

ffmpeg -i rocketman.mp4 -vcodec copy \
-i rocketman.flac -acodec libfaac -ab 128K \
rocketman.final.mp4

Notice that we’re copying the video stream instead of encoding it.
That’s because we already encoded it during the ripping process.
However, we still have to compress the audio, so we specify an audio codec and bitrate.

This last step is surprisingly quick, and when it’s finished, so are we.
Of course, we’ll confirm that everything was successful before we delete
our working files. But then we’re ready to sit back and enjoy some
ridiculous antics!

Categories
Software

Migrating IMAP Accounts Between Remote Hosts

I have come to rely on IMAP for email access. It is the most convenient way to ensure access to all my mail from more than one computer. I recently switched to a new hosting provider and I didn’t want to lose all of my archived email stored on the old host’s server. Fortunately, I found a Perl script designed to synchronize IMAP mailboxes between two servers. The script is called **imapsync**.

I was able to install imapsync from the Ubuntu repositories. The package includes a man page which explains the options and contains some example use cases. My needs were simple–copy everything from point A to point B.

The first step is to create mailboxes for the users in question on the new server. I did this, preserving the same passwords as well as the same usernames. It is not necessary to use the same login/password on each server, but doing so allowed me to simplify the bash command line a great deal. Below are the commands I used to migrate two mailboxes, followed by an explanation of each command:

$ touch passwd_nick passwd_karie
$ chmod 600 passwd_*
$ echo “[HISPASSWORD]” > passwd_nick
$ echo “[HERPASSWORD]” > passwd_karie
$ for USER in nick karie; do
> imapsync \
> –host1 [SOURCE_IP] –user1 $USER –passfile1 passwd_$USER \
> –host2 [DEST_IP] –user2 $USER –passfile2 passwd_$USER \
> –ssl1 –ssl2 –noauthmd5
> done

The **touch** and **chmod** commands create empty files with the appropriate permissions to prevent other local users from viewing the contents. This may not be necessary on every machine, but it is a good practice to consider privacy when working with plaintext passwords. It is possible to pass plaintext passwords to imapsync using the arguments `–password1` and `–password2`, but they would then appear to any local user who executes `ps axww` for as long as the command runs.

The **echo** lines actually write the passwords to the empty files. Obviously, I used placeholder text within the brackets.

The **for** statement iterates through the usernames *nick* and *karie*, and the bash interpreter reads these values wherever `$USER` is seen in the imapsync argument list. `[SOURCE_IP]` and `[DEST_IP]` are placeholders for the numeric IP addresses of each remote server.

The `–ssl1` and `–ssl2` flags enable SSL for their respective connections. This is almost certainly preferred for better security. If your servers support TLS you can use `–tls1` and `–tls2` instead. I also had to pass the `–noauthmd5` flag, as neither server in my situation supported that feature.

The script ran for a long time. In fact, I left it running and went to work. When I got home I ran it again to transfer whatever new messages had been delivered since the sync (there were 25). Then, confident that things were ready to go, I logged in to my domain registrar and updated the nameservers to reflect the new host. Last but not least, I opened up Thunderbird to see if it worked. Thunderbird didn’t even notice the switch. In fact, it worked so flawlessly that I actually had to perform a DNS search to make sure the nameservers had been updated properly.

As the name suggests, imapsync is designed to synchronize IMAP mailboxes. Migration is only a small part of its featureset. It may be wise to consider implementing this script into your normal backup routine; of course, this requires that a backup IMAP server be running.

While a number of utilities exist that can migrate mailboxes, the simplicity of imapsync makes it a great choice for occasional use.

Categories
Software

Printing in Booklet Format from the Linux Command Line

Here is a Linux command to take a PDF of half-letter-sized pages
(5.5″x8.5″) and arrange them, two pages per side, for booklet printing:

$ pdftops -level3 source.pdf – | psbook | psnup -2 -W5.5in -H8.5in | ps2pdf – booklet.pdf

All of these utilities are standard on a Debian-based system. Several filters are tied together using [pipes](http://en.wikipedia.org/wiki/Pipeline_%28Unix%29 “Learn more about Unix Pipelines”) to produce a properly-formatted PDF.

### A Closer Look ###

Here’s a pipe-by-pipe breakdown of the command:

$ pdftops -level3 source.pdf

convert the source PDF to a level 3 postscript file (this is necessary
because the remaining steps require a postscript source file).

| psbook

rearrange the pages from the resulting postscript source file into the
appropriate order for notebook printing.

| psnup -2 -W5.5in -H8.5in

read in the reordered source file and arrange the reordered pages so
that two logical pages are printed on one physical sheet. If your
source pages are a different size, change the values of the `-W` and
`-H` options. You can use the `-p` option (or lowercase `-w` and `-h`)
to specify the output page size, but on Debian-based systems this value
is automatically read from `/etc/papersize`.

| ps2pdf – booklet.pdf

convert the resulting postscript file back into a PDF using the
filename specified. This step is not necessary if you know that the
machine you will print from can handle postscript files. If you leave
this step out, replace it with `> booklet.ps` to write the output to
a file named `booklet.ps`.

This method comes in handy because you don’t have to rely on printer
driver options to handle the booklet reordering. In my experience,
those driver options are terribly fussy and hard to work with.
Further, many printer drivers don’t offer this ability.

I hope you find this info helpful.

Based on info from
[Scribus Wiki](http://wiki.scribus.net/index.php/How_to_make_a_booklet#Method_A-1:_using_psutils_only).

**Update:** I experienced a bug in postscript that was causing a single
page to be rendered upside-down (rotated 180 degrees) when converted to
PDF. Unable to trace the source of the bug, I did find out that
filtering the postscript through `ps2ps` immediately after the initial
conversion from PDF, fixed the problem. `ps2ps` is a postscript
“distiller” which optimizes postscript into simpler form. This does
result in the loss of anti-aliasing, which uglies up the result on the
screen, but it does not affect printed copies.

If you experience rendering bugs, try adding `ps2ps`, as in the
following command:

$ pdftops -level3 source.pdf – | ps2ps – – | psbook | psnup -2 -W5.5in -H8.5in | ps2pdf – booklet.pdf

Categories
Software

Strong Password Generator in Python

I wanted a CLI-based strong password generator for Linux. `mkpasswd` is
nice, but I wanted something more flexible. I didn’t like having to
provide my own character sequence. I wanted something with a built-in
character sequence generator with an easy way to control the likelihood
of numbers and symbols. I wanted something that could read in a
character sequence from a file or standard input. And I wanted
something that not only had sensible default values, but was easily
configurable. It was one of those times where searching for such a tool
was a bigger hassle than writing my own. So I opened up vim and got to
work. The result is a Python-based password generator called
`mkstrongpw`.

`mkstrongpw` can generate a character sequence based on four character
categories: lowercase letters, uppercase letters, numerical digits, and
non-alphanumeric symbols. By default, the likelihood (or odds) of each
character type is as follows: lowercase: 5/10; uppercase: 2/10; digits:
2/10; symbols: 1/10. These values can be easily changed via command
line options. A single, non-option argument can be passed, specifying a
filename to be read in as the character sequence. If this argument is a
single hyphen (-), standard input is used. Newlines and whitespace are
stripped from the beginning and end of each line of the input file.

By default, `mkstrongpw` uses its built-in sequence generator to
produce 10 passwords, 8 characters in length. Command line options can
be used to modify these values. Take a look at the following examples:

Default operation (no arguments):

$ mkstrongpw
x5mHpZum
zc{onlKH
O5WlkYaV
i&hgb?pX
cjw0Gjni
aVtxjuve
aDeVHym8
1SDWKhEr
U3Kja!/dev/null | uuencode – | mkstrongpw –
+DTS@]B\
C>R60’&9
6X])H$(,
GP7_^9\(
FM;^)84F
E)RGR4+[
`<1^_NT_ 8":\7%R- DJSLJ*I` =MQ^]2D9 That's a broad overview of `mkstrongpw`. Use the `--help` option for more details. ### Get it ### * [Latest version (github)](https://github.com/njbair/mkstrongpw) * [Download mkstrongpw 1.0 (.tar.gz)](http://nickbair.net/files/mkstrongpw.tar.gz) (md5sum: 34725c0509e0d0d9c5ef7441c8b5088c) * [View source](http://nickbair.net/files/mkstrongpw)

Categories
Software

Making Bootup Music with beep and rc.local

In my house I run a headless server which I administrate via SSH. I reboot the server regularly, but because there is no monitor there is no way of knowing when the machine is finished booting (since, of course, my SSH connection is terminated during reboot). In a situation like this you can just ping the server’s IP until you get a response, then log in via SSH, check the logs, and make sure everything is
running properly.

But rather than having to ping the server we can use a program called **beep** and the startup script */etc/rc.local* to let us know when the machine has finished booting.

As you may know, */etc/rc.local* is a startup script which runs at the end of the boot process, after everything else, immediately before the login prompt appears. It is usually empty by default. There are a handful of reasons why someone might need to modify *rc.local*. As the post’s title suggests, we will use it in conjunction with beep to make our machine play some bootup music.

**beep** is a program that beeps the PC speaker. It may or may not be installed by default in your distribution, but it is almost certainly available in the repositories. beep is highly configurable and allows for any number of beeps, of any duration, at any frequency. After reading the beep man page, I got my music on and wrote a couple of bash scripts to play some simple tunes. I saved the scripts in */usr/local/bin*, and added one of them to */etc/rc.local*. Now when my server finishes rebooting it plays the Imperial March! If you have beep installed, give it a try:

#!/bin/sh

beep \
-f 392 -l 450 -r 3 -D 150 \
-n -f 311.13 -l 400 -D 50 \
-n -f 466.16 -l 100 -D 50 \
-n -f 392 -l 500 -D 100 \
-n -f 311.13 -l 400 -D 50 \
-n -f 466.16 -l 100 -D 50 \
-n -f 392 -l 600 -D 600 \
-n -f 587.33 -l 450 -r 3 -D 150 \
-n -f 622.25 -l 400 -D 50 \
-n -f 466.16 -l 100 -D 50 \
-n -f 369.99 -l 500 -D 100 \
-n -f 311.13 -l 400 -D 50 \
-n -f 466.16 -l 100 -D 50 \
-n -f 392 -l 500 -D 100

The frequencies for the notes came from a page which you can find linked in the *Additional Resources* below. I must warn you, if you are not musical you are going to have a very hard time authoring your own beep music. But if you are up for the challenge, it is the geekiest music you will ever write. Like, geekier than [Pocket Calculator](http://www.youtube.com/watch?v=zZt64_XOflk).

### Additional Resources ###

[An introduction to services, runlevels, and rc.d scripts](http://www.linux.com/news/enterprise/systems-management/8116-an-introduction-to-services-runlevels-and-rcd-scripts) – linux.com
[Arch Boot Process](http://wiki.archlinux.org/index.php/Arch_Boot_Process) – archlinux.org
[Frequencies of Musical Notes](http://www.phy.mtu.edu/~suits/notefreqs.html)