kenken999/php
0
1<?php2class RunnerBase32 {3 public static function encode( $str ) {4 $ret = "";5 $n = 0;6 while( "" !== ( $symbol = self::encodeChunk( $str, $n++ ) ) ) {7 $ret .= $symbol;8 }9 return str_pad( $ret, strlen( $ret ) + strlen( $ret ) % 8 , '=' );10 }11 12 public static function decode( $str ) {13 $ret = "";14 $n = 0;15 while( $n < strlen( $str ) && self::decodeChunk( $str[ $n ], $ret, $n ) ) {16 ++$n;17 }18 return $ret;19 }20 21 /**22 * decode synbol and write n-th 5-bit block to the string23 */24 protected static function decodeChunk( $encoded, &$str, $n ) {25 if( $encoded == '=' ) {26 // reached the end, stop processing27 return false;28 }29 $fiveBits = array_search( $encoded, self::$table );30 if( $fiveBits < 0 ) {31 // wrong symbol, stop procesing32 return false;33 }34 35 $charIdx = (int)floor( $n * 5 / 8 );36 $bitOffset = ($n * 5) % 8;37 if( $charIdx < strlen( $str ) ) {38 $byte = ord( $str[ $charIdx ] );39 } else {40 $byte = 0;41 $str .= ' ';42 }43 44 if( $bitOffset <= 3 ) {45 $byte += $fiveBits << ( 3 - $bitOffset );46 $str[ $charIdx ] = chr( $byte );47 } else {48 $byte += $fiveBits >> ( $bitOffset - 3 );49 $str[ $charIdx ] = chr( $byte );50 51 // if lowest ( $bitOffset - 3 ) bits are not 0, write them to the next byte52 $mask = (1 << ( $bitOffset - 3 )) - 1;53 $nextByte = ( $fiveBits & $mask ) << ( 8 - ( $bitOffset - 3 ) );54 if( $nextByte !== 0 ) {55 if( $charIdx + 1 >= strlen( $str ) ) {56 $str .= chr( $nextByte );57 }58 }59 }60 61 return true;62 }63 64 /**65 * read and encode n-th 5-bit block from the string66 */67 protected static function encodeChunk( &$str, $n ) {68 $charIdx = (int)floor( $n * 5 / 8 );69 $bitOffset = ($n * 5) % 8;70 if( $charIdx >= strlen( $str ) ) {71 return "";72 }73 $byte = ord( $str[ $charIdx ] );74 if( $bitOffset <= 3 ) {75 // read highest ($bitOffset + 5) bits and puth them into $fiveBits76 $fiveBits = ( $byte >> ( 3 - $bitOffset ) ) & 31;77 } else {78 // read 8 - $bitoffset bits from the first byte79 $mask = ( 1 << ( 8 - $bitOffset ) ) - 1;80 $fiveBits = ( $byte & $mask ) << ( $bitOffset - 3 );81 if( $charIdx < strlen( $str ) - 1 ) {82 // read next ($bitOffset - 3) bits and put them in the lowest bits of $fiveBits83 $nextByte = ord( $str[ $charIdx + 1 ] );84 $fiveBits += $nextByte >> ( 8 - ($bitOffset - 3) );85 }86 }87 $ret = self::$table[ $fiveBits ];88 return $ret;89 }90 protected static $table = array(91 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H',92 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P',93 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X',94 'Y', 'Z', '2', '3', '4', '5', '6', '7',95 '='96 );97}98?>99 