PHP  
 PHP: Test and Code Coverage Analysis
downloads | QA | documentation | faq | getting help | mailing lists | reporting bugs | php.net sites | links | my php.net 
 

LCOV - code coverage report
Current view: top level - ext/standard - base64.c (source / functions) Hit Total Coverage
Test: PHP Code Coverage Lines: 74 79 93.7 %
Date: 2014-10-22 Functions: 5 5 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :    +----------------------------------------------------------------------+
       3             :    | PHP Version 7                                                        |
       4             :    +----------------------------------------------------------------------+
       5             :    | Copyright (c) 1997-2014 The PHP Group                                |
       6             :    +----------------------------------------------------------------------+
       7             :    | This source file is subject to version 3.01 of the PHP license,      |
       8             :    | that is bundled with this package in the file LICENSE, and is        |
       9             :    | available through the world-wide-web at the following url:           |
      10             :    | http://www.php.net/license/3_01.txt                                  |
      11             :    | If you did not receive a copy of the PHP license and are unable to   |
      12             :    | obtain it through the world-wide-web, please send a note to          |
      13             :    | license@php.net so we can mail you a copy immediately.               |
      14             :    +----------------------------------------------------------------------+
      15             :    | Author: Jim Winstead <jimw@php.net>                                  |
      16             :    +----------------------------------------------------------------------+
      17             :  */
      18             : /* $Id$ */
      19             : 
      20             : #include <string.h>
      21             : 
      22             : #include "php.h"
      23             : #include "base64.h"
      24             : 
      25             : /* {{{ base64 tables */
      26             : static const char base64_table[] = {
      27             :         'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
      28             :         'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
      29             :         'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
      30             :         'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
      31             :         '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/', '\0'
      32             : };
      33             : 
      34             : static const char base64_pad = '=';
      35             : 
      36             : static const short base64_reverse_table[256] = {
      37             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -1, -1, -2, -2, -1, -2, -2,
      38             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      39             :         -1, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, 62, -2, -2, -2, 63,
      40             :         52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -2, -2, -2, -2, -2, -2,
      41             :         -2,  0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14,
      42             :         15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -2, -2, -2, -2, -2,
      43             :         -2, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
      44             :         41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, -2, -2, -2, -2, -2,
      45             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      46             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      47             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      48             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      49             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      50             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      51             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2,
      52             :         -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2
      53             : };
      54             : /* }}} */
      55             : 
      56         664 : PHPAPI zend_string *php_base64_encode(const unsigned char *str, size_t length) /* {{{ */
      57             : {
      58         664 :         const unsigned char *current = str;
      59             :         unsigned char *p;
      60             :         zend_string *result;
      61             : 
      62        1328 :         result = zend_string_alloc(((length + 2) / 3) * 4 * sizeof(char), 0);
      63         664 :         p = (unsigned char *)result->val;
      64             : 
      65        7519 :         while (length > 2) { /* keep going until we have less than 24 bits */
      66        6191 :                 *p++ = base64_table[current[0] >> 2];
      67        6191 :                 *p++ = base64_table[((current[0] & 0x03) << 4) + (current[1] >> 4)];
      68        6191 :                 *p++ = base64_table[((current[1] & 0x0f) << 2) + (current[2] >> 6)];
      69        6191 :                 *p++ = base64_table[current[2] & 0x3f];
      70             : 
      71        6191 :                 current += 3;
      72        6191 :                 length -= 3; /* we just handle 3 octets of data */
      73             :         }
      74             : 
      75             :         /* now deal with the tail end of things */
      76         664 :         if (length != 0) {
      77         578 :                 *p++ = base64_table[current[0] >> 2];
      78         578 :                 if (length > 1) {
      79         141 :                         *p++ = base64_table[((current[0] & 0x03) << 4) + (current[1] >> 4)];
      80         141 :                         *p++ = base64_table[(current[1] & 0x0f) << 2];
      81         141 :                         *p++ = base64_pad;
      82             :                 } else {
      83         437 :                         *p++ = base64_table[(current[0] & 0x03) << 4];
      84         437 :                         *p++ = base64_pad;
      85         437 :                         *p++ = base64_pad;
      86             :                 }
      87             :         }
      88         664 :         *p = '\0';
      89             : 
      90         664 :         result->len = (p - (unsigned char *)result->val);
      91             : 
      92         664 :         return result;
      93             : }
      94             : /* }}} */
      95             : 
      96             : /* {{{ */
      97             : /* generate reverse table (do not set index 0 to 64)
      98             : static unsigned short base64_reverse_table[256];
      99             : #define rt base64_reverse_table
     100             : void php_base64_init(void)
     101             : {
     102             :         char *s = emalloc(10240), *sp;
     103             :         char *chp;
     104             :         short idx;
     105             : 
     106             :         for(ch = 0; ch < 256; ch++) {
     107             :                 chp = strchr(base64_table, ch);
     108             :                 if(ch && chp) {
     109             :                         idx = chp - base64_table;
     110             :                         if (idx >= 64) idx = -1;
     111             :                         rt[ch] = idx;
     112             :                 } else {
     113             :                         rt[ch] = -1;
     114             :                 }
     115             :         }
     116             :         sp = s;
     117             :         sprintf(sp, "static const short base64_reverse_table[256] = {\n");
     118             :         for(ch =0; ch < 256;) {
     119             :                 sp = s+strlen(s);
     120             :                 sprintf(sp, "\t% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,% 3d,\n", rt[ch+0], rt[ch+1], rt[ch+2], rt[ch+3], rt[ch+4], rt[ch+5], rt[ch+6], rt[ch+7], rt[ch+8], rt[ch+9], rt[ch+10], rt[ch+11], rt[ch+12], rt[ch+13], rt[ch+14], rt[ch+15]);
     121             :                 ch += 16;
     122             :         }
     123             :         sprintf(sp, "};");
     124             :         php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Reverse_table:\n%s", s);
     125             :         efree(s);
     126             : }
     127             : */
     128             : /* }}} */
     129             : 
     130         128 : PHPAPI zend_string *php_base64_decode(const unsigned char *str, size_t length) /* {{{ */
     131             : {
     132         128 :         return php_base64_decode_ex(str, length, 0);
     133             : }
     134             : /* }}} */
     135             : 
     136         434 : PHPAPI zend_string *php_base64_decode_ex(const unsigned char *str, size_t length, zend_bool strict) /* {{{ */
     137             : {
     138         434 :         const unsigned char *current = str;
     139         434 :         int ch, i = 0, j = 0, k;
     140             :         /* this sucks for threaded environments */
     141             :         zend_string *result;
     142             : 
     143         434 :         result = zend_string_alloc(length, 0);
     144             : 
     145             :         /* run through the whole string, converting as we go */
     146       29799 :         while ((ch = *current++) != '\0' && length-- > 0) {
     147       28951 :                 if (ch == base64_pad) {
     148         501 :                         if (*current != '=' && ((i % 4) == 1 || (strict && length > 0))) {
     149           5 :                                 if ((i % 4) != 1) {
     150           8 :                                         while (isspace(*(++current))) {
     151           2 :                                                 continue;
     152             :                                         }
     153           3 :                                         if (*current == '\0') {
     154           2 :                                                 continue;
     155             :                                         }
     156             :                                 }
     157             :                                 zend_string_free(result);
     158           3 :                                 return NULL;
     159             :                         }
     160         496 :                         continue;
     161             :                 }
     162             : 
     163       28450 :                 ch = base64_reverse_table[ch];
     164       28450 :                 if ((!strict && ch < 0) || ch == -1) { /* a space or some other separator character, we simply skip over */
     165         287 :                         continue;
     166       28163 :                 } else if (ch == -2) {
     167             :                         zend_string_free(result);
     168          17 :                         return NULL;
     169             :                 }
     170             : 
     171       28146 :                 switch(i % 4) {
     172             :                 case 0:
     173        7164 :                         result->val[j] = ch << 2;
     174        7164 :                         break;
     175             :                 case 1:
     176        7154 :                         result->val[j++] |= ch >> 4;
     177        7154 :                         result->val[j] = (ch & 0x0f) << 4;
     178        7154 :                         break;
     179             :                 case 2:
     180        6968 :                         result->val[j++] |= ch >>2;
     181        6968 :                         result->val[j] = (ch & 0x03) << 6;
     182        6968 :                         break;
     183             :                 case 3:
     184        6860 :                         result->val[j++] |= ch;
     185             :                         break;
     186             :                 }
     187       28146 :                 i++;
     188             :         }
     189             : 
     190         414 :         k = j;
     191             :         /* mop things up if we ended on a boundary */
     192         414 :         if (ch == base64_pad) {
     193           0 :                 switch(i % 4) {
     194             :                 case 1:
     195             :                         zend_string_free(result);
     196           0 :                         return NULL;
     197             :                 case 2:
     198           0 :                         k++;
     199             :                 case 3:
     200           0 :                         result->val[k] = 0;
     201             :                 }
     202             :         }
     203         414 :         result->len = j;
     204         414 :         result->val[result->len] = '\0';
     205             : 
     206         414 :         return result;
     207             : }
     208             : /* }}} */
     209             : 
     210             : /* {{{ proto string base64_encode(string str)
     211             :    Encodes string using MIME base64 algorithm */
     212         493 : PHP_FUNCTION(base64_encode)
     213             : {
     214             :         char *str;
     215             :         size_t str_len;
     216             :         zend_string *result;
     217             : 
     218         493 :         if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &str, &str_len) == FAILURE) {
     219           8 :                 return;
     220             :         }
     221         485 :         result = php_base64_encode((unsigned char*)str, str_len);
     222         485 :         if (result != NULL) {
     223         485 :                 RETURN_STR(result);
     224             :         } else {
     225           0 :                 RETURN_FALSE;
     226             :         }
     227             : }
     228             : /* }}} */
     229             : 
     230             : /* {{{ proto string base64_decode(string str[, bool strict])
     231             :    Decodes string using MIME base64 algorithm */
     232         322 : PHP_FUNCTION(base64_decode)
     233             : {
     234             :         char *str;
     235         322 :         zend_bool strict = 0;
     236             :         size_t str_len;
     237             :         zend_string *result;
     238             : 
     239         322 :         if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|b", &str, &str_len, &strict) == FAILURE) {
     240          16 :                 return;
     241             :         }
     242         306 :         result = php_base64_decode_ex((unsigned char*)str, str_len, strict);
     243         306 :         if (result != NULL) {
     244         288 :                 RETURN_STR(result);
     245             :         } else {
     246          18 :                 RETURN_FALSE;
     247             :         }
     248             : }
     249             : /* }}} */
     250             : 
     251             : /*
     252             :  * Local variables:
     253             :  * tab-width: 4
     254             :  * c-basic-offset: 4
     255             :  * End:
     256             :  * vim600: sw=4 ts=4 fdm=marker
     257             :  * vim<600: sw=4 ts=4
     258             :  */

Generated by: LCOV version 1.10

Generated at Wed, 22 Oct 2014 07:24:59 +0000 (3 days ago)

Copyright © 2005-2014 The PHP Group
All rights reserved.