[phpass](http://www.openwall.com/phpass/) uses a strange (to me) algorithm in [encode64()](http://cvsweb.openwall.com/cgi/cvsweb.cgi/projects/phpass/PasswordHash.php?rev=1.8;content-type=text/x-cvsweb-markup;only_with_tag=MAIN) to base 64 encode. [Base64](http://en.wikipedia.org/wiki/Base64#Examples) and [Uuencode](http://en.wikipedia.org/wiki/Uuencoding#Formatting_Mechanism) linearly chunk 6 bits to produce each octet before mapping to a printable char. `encode64` shuffles the bits around:

```
input bit location:    abcdefgh ijklmnop qrstuvwx
base64 bit location:   ..abcdef ..ghijkl ..mnopqr ..stuvwx
encode64 bit location: ..cdefgh ..mnopab ..wxijkl ..qrstuv

```

**Is this algorithm commonly known?** And besides backward compatibility, **why choose it over Base64**?

Below I've rewritten it to clarify the algorithm:

```
function encode64($input, $bytesToProcess)
{
    // convert to array of ints
    for ($i = 0; $i < $bytesToProcess; $i++) {
        $bytes[] = ord($input[$i]);
    }

    $octets = array();
    $i = 0;
    do {
        $value = $bytes[$i++];
        $octets[] = $value & 0x3f;
        if ($i < $bytesToProcess) {
            $value |= $bytes[$i] << 8;
        }
        $octets[] = ($value >> 6) & 0x3f;
        if ($i++ >= $bytesToProcess) {
            break;
        }
        if ($i < $bytesToProcess) {
            $value |= $bytes[$i] << 16;
        }
        $octets[] = ($value >> 12) & 0x3f;
        if ($i++ >= $bytesToProcess) {
            break;
        }
        $octets[] = ($value >> 18) & 0x3f;
    } while ($i < $bytesToProcess);

    return array_map(function ($i) {
        return str_pad(base_convert($i, 10, 2), 6, '0', STR_PAD_LEFT);
    }, $octets);
}

var_export(encode64("Man", 3));

```

(updated to indicate exactly where each input bit is moved)