国产av日韩一区二区三区精品,成人性爱视频在线观看,国产,欧美,日韩,一区,www.成色av久久成人,2222eeee成人天堂

首頁(yè) 類庫(kù)下載 PHP類庫(kù) PHP獲取APK的包信息

PHP獲取APK的包信息

Oct 08, 2016 pm 05:35 PM

php上傳安卓apk包的時(shí)候,需要獲取安卓apk包內(nèi)的信息
<?php

/*解析安卓apk包中的壓縮XML文件,還原和讀取XML內(nèi)容

依賴功能:需要PHP的ZIP包函數(shù)支持。*/

include(&#39;./Apkparser.php&#39;);

$appObj    = new Apkparser(); 

$targetFile = a.apk;//apk所在的路徑地址

$res     = $appObj->open($targetFile);

$appObj->getAppName();         // 應(yīng)用名稱

$appObj->getPackage();        // 應(yīng)用包名

$appObj->getVersionName();    // 版本名稱

$appObj->getVersionCode();    // 版本代碼
?>
以下是Apkparser類包,把以下代碼復(fù)制出來(lái)保存為Apkparser.php就可以執(zhí)行以上代碼
<?php
class ApkParser{
//----------------------
// 公共函數(shù),供外部調(diào)用
//----------------------
  public function open($apk_file, $xml_file=&#39;AndroidManifest.xml&#39;){
    $zip = new \ZipArchive;
    if ($zip->open($apk_file) === TRUE) {
      $xml = $zip->getFromName($xml_file);
      $zip->close();
      if ($xml){
        try {
          return $this->parseString($xml);
        }catch (Exception $e){
        }
      }
    }
    return false;
  }
 
  public function parseString($xml){
    $this->xml = $xml;
    $this->length = strlen($xml);
 
    $this->root = $this->parseBlock(self::AXML_FILE);
    return true;
  }
 
  public function getXML($node=NULL, $lv=-1){
    if ($lv == -1) $node = $this->root;
    if (!$node) return &#39;&#39;;
 
    if ($node[&#39;type&#39;] == self::END_TAG) $lv--;
    $xml = @($node[&#39;line&#39;] == 0 || $node[&#39;line&#39;] == $this->line) ? &#39;&#39; : "\n".str_repeat(&#39;  &#39;, $lv);
    $xml .= $node[&#39;tag&#39;];
    $this->line = @$node[&#39;line&#39;];
    foreach ($node[&#39;child&#39;] as $c){
      $xml .= $this->getXML($c, $lv+1);
    }
    return $xml;
  }
 
  public function getPackage(){
    return $this->getAttribute(&#39;manifest&#39;, &#39;package&#39;);
  }
 
  public function getVersionName(){
    return $this->getAttribute(&#39;manifest&#39;, &#39;android:versionName&#39;);
  }
 
  public function getVersionCode(){
    return $this->getAttribute(&#39;manifest&#39;, &#39;android:versionCode&#39;);
  }
 
  public function getAppName(){
    return $this->getAttribute(&#39;manifest/application&#39;, &#39;android:name&#39;);
  }
 
  public function getMainActivity(){
    for ($id=0; true; $id++){
      $act = $this->getAttribute("manifest/application/activity[{$id}]/intent-filter/action", &#39;android:name&#39;);
      if (!$act) break;
      if ($act == &#39;android.intent.action.MAIN&#39;) return $this->getActivity($id);
    }
    return NULL;
  }
 
  public function getActivity($idx=0){
    $idx = intval($idx);
    return $this->getAttribute("manifest/application/activity[{$idx}]", &#39;android:name&#39;);
  }
 
  public function getAttribute($path, $name){
    $r = $this->getElement($path);
    if (is_null($r)) return NULL;
 
    if (isset($r[&#39;attrs&#39;])){
      foreach ($r[&#39;attrs&#39;] as $a){
        if ($a[&#39;ns_name&#39;] == $name) return $this->getAttributeValue($a);
      }
    }
    return NULL;
  }
 
//----------------------
// 類型常量定義
//----------------------
  const AXML_FILE             = 0x00080003;
  const STRING_BLOCK          = 0x001C0001;
  const RESOURCEIDS           = 0x00080180;
  const START_NAMESPACE       = 0x00100100;
  const END_NAMESPACE         = 0x00100101;
  const START_TAG             = 0x00100102;
  const END_TAG               = 0x00100103;
  const TEXT                  = 0x00100104;
 
  const TYPE_NULL             =0;
  const TYPE_REFERENCE        =1;
  const TYPE_ATTRIBUTE        =2;
  const TYPE_STRING           =3;
  const TYPE_FLOAT            =4;
  const TYPE_DIMENSION        =5;
  const TYPE_FRACTION         =6;
  const TYPE_INT_DEC          =16;
  const TYPE_INT_HEX          =17;
  const TYPE_INT_BOOLEAN      =18;
  const TYPE_INT_COLOR_ARGB8  =28;
  const TYPE_INT_COLOR_RGB8   =29;
  const TYPE_INT_COLOR_ARGB4  =30;
  const TYPE_INT_COLOR_RGB4   =31;
 
  const UNIT_MASK             = 15;
  private static $RADIX_MULTS = array(0.00390625, 3.051758E-005, 1.192093E-007, 4.656613E-010);
  private static $DIMENSION_UNITS = array("px","dip","sp","pt","in","mm","","");
  private static $FRACTION_UNITS  = array("%","%p","","","","","","");
 
  private $xml=&#39;&#39;;
  private $length = 0;
  private $stringCount = 0;
  private $styleCount  = 0;
  private $stringTab = array();
  private $styleTab  = array();
  private $resourceIDs = array();
  private $ns = array();
  private $cur_ns = NULL;
  private $root = NULL;
  private $line = 0;
 
//----------------------
// 內(nèi)部私有函數(shù)
//----------------------
  private function getElement($path){
    if (!$this->root) return NULL;
    $ps = explode(&#39;/&#39;, $path);
    $r  = $this->root;
    foreach ($ps as $v){
      if (preg_match(&#39;/([^\[]+)\[([0-9]+)\]$/&#39;, $v, $ms)){
        $v = $ms[1];
        $off = $ms[2];
      }else {
        $off = 0;
      }
      foreach ($r[&#39;child&#39;] as $c){
        if ($c[&#39;type&#39;] == self::START_TAG && $c[&#39;ns_name&#39;] == $v){
          if ($off == 0){
            $r = $c; continue 2;
          }else {
            $off--;
          }
        }
      }
      // 沒有找到節(jié)點(diǎn)
      return NULL;
    }
    return $r;
  }
 
  private function parseBlock($need = 0){
    $o = 0;
    $type = $this->get32($o);
    if ($need && $type != $need) throw new Exception(&#39;Block Type Error&#39;, 1);
    $size = $this->get32($o);
    if ($size < 8 || $size > $this->length) throw new Exception(&#39;Block Size Error&#39;, 2);
    $left = $this->length - $size;
 
    $props = false;
    switch ($type){
      case self::AXML_FILE:
        $props = array(
          &#39;line&#39; => 0,
          &#39;tag&#39; => &#39;<?xml version="1.0" encoding="utf-8"?>&#39;
        );
      break;
      case self::STRING_BLOCK:
        $this->stringCount = $this->get32($o);
        $this->styleCount  = $this->get32($o);
        $o += 4;
        $strOffset = $this->get32($o);
        $styOffset = $this->get32($o);
        $strListOffset = $this->get32array($o, $this->stringCount);
        $styListOffset = $this->get32array($o, $this->styleCount);
        $this->stringTab = $this->stringCount > 0 ? $this->getStringTab($strOffset, $strListOffset) : array();
        $this->styleTab  = $this->styleCount > 0 ? $this->getStringTab($styOffset, $styListOffset) : array();
        $o = $size;
      break;
      case self::RESOURCEIDS:
        $count = $size / 4 - 2;
        $this->resourceIDs = $this->get32array($o, $count);
      break;
      case self::START_NAMESPACE:
        $o += 8;
        $prefix = $this->get32($o);
        $uri = $this->get32($o);
 
        if (empty($this->cur_ns)){
          $this->cur_ns = array();
          $this->ns[] = &$this->cur_ns;
        }
        $this->cur_ns[$uri] = $prefix;
      break;
      case self::END_NAMESPACE:
        $o += 8;
        $prefix = $this->get32($o);
        $uri = $this->get32($o);
 
        if (empty($this->cur_ns)) break;
        unset($this->cur_ns[$uri]);
      break;
      case self::START_TAG:
        $line = $this->get32($o);
 
        $o += 4;
        $attrs = array();
        $props = array(
          &#39;line&#39; => $line,
          &#39;ns&#39; => $this->getNameSpace($this->get32($o)),
          &#39;name&#39; => $this->getString($this->get32($o)),
          &#39;flag&#39; => $this->get32($o),
          &#39;count&#39; => $this->get16($o),
          &#39;id&#39; => $this->get16($o)-1,
          &#39;class&#39; => $this->get16($o)-1,
          &#39;style&#39; => $this->get16($o)-1,
          &#39;attrs&#39; => &$attrs
        );
        $props[&#39;ns_name&#39;] = $props[&#39;ns&#39;].$props[&#39;name&#39;];
        for ($i=0; $i < $props[&#39;count&#39;]; $i++){
          $a = array(
            &#39;ns&#39; => $this->getNameSpace($this->get32($o)),
            &#39;name&#39; => $this->getString($this->get32($o)),
            &#39;val_str&#39; => $this->get32($o),
            &#39;val_type&#39; => $this->get32($o),
            &#39;val_data&#39; => $this->get32($o)
          );
          $a[&#39;ns_name&#39;] = $a[&#39;ns&#39;].$a[&#39;name&#39;];
          $a[&#39;val_type&#39;] >>= 24;
          $attrs[] = $a;
        }
        // 處理TAG字符串
        $tag = "<{$props[&#39;ns_name&#39;]}";
        foreach ($this->cur_ns as $uri => $prefix){
          $uri = $this->getString($uri);
          $prefix = $this->getString($prefix);
          $tag .= " xmlns:{$prefix}=\"{$uri}\"";
        }
        foreach ($props[&#39;attrs&#39;] as $a){
          $tag .= " {$a[&#39;ns_name&#39;]}=\"".
              $this->getAttributeValue($a).
              &#39;"&#39;;
        }
        $tag .= &#39;>&#39;;
        $props[&#39;tag&#39;] = $tag;
 
        unset($this->cur_ns);
        $this->cur_ns = array();
        $this->ns[] = &$this->cur_ns;
        $left = -1;
      break;
      case self::END_TAG:
        $line = $this->get32($o);
        $o += 4;
        $props = array(
          &#39;line&#39; => $line,
          &#39;ns&#39; => $this->getNameSpace($this->get32($o)),
          &#39;name&#39; => $this->getString($this->get32($o))
        );
        $props[&#39;ns_name&#39;] = $props[&#39;ns&#39;].$props[&#39;name&#39;];
        $props[&#39;tag&#39;] = "</{$props[&#39;ns_name&#39;]}>";
        if (count($this->ns) > 1){
          array_pop($this->ns);
          unset($this->cur_ns);
          $this->cur_ns = array_pop($this->ns);
          $this->ns[] = &$this->cur_ns;
        }
      break;
      case self::TEXT:
        $o += 8;
        $props = array(
          &#39;tag&#39; => $this->getString($this->get32($o))
        );
        $o += 8;
      break;
      default:
        throw new Exception(&#39;Block Type Error&#39;, 3);
      break;
    }
 
    $this->skip($o);
    $child = array();
    while ($this->length > $left){
      $c = $this->parseBlock();
      if ($props && $c) $child[] = $c;
      if ($left == -1 && $c[&#39;type&#39;] == self::END_TAG){
        $left = $this->length;
        break;
      }
    }
    if ($this->length != $left) throw new Exception(&#39;Block Overflow Error&#39;, 4);
    if ($props){
      $props[&#39;type&#39;] = $type;
      $props[&#39;size&#39;] = $size;
      $props[&#39;child&#39;] = $child;
      return $props;
    }else {
      return false;
    }
  }
 
  private function getAttributeValue($a){
    $type = &$a[&#39;val_type&#39;];
    $data = &$a[&#39;val_data&#39;];
    switch ($type){
      case self::TYPE_STRING:
        return $this->getString($a[&#39;val_str&#39;]);
      case self::TYPE_ATTRIBUTE:
        return sprintf(&#39;?%s%08X&#39;, self::_getPackage($data), $data);
      case self::TYPE_REFERENCE:
        return sprintf(&#39;@%s%08X&#39;, self::_getPackage($data), $data);
      case self::TYPE_INT_HEX:
        return sprintf(&#39;0x%08X&#39;, $data);
      case self::TYPE_INT_BOOLEAN:
        return ($data != 0 ? &#39;true&#39; : &#39;false&#39;);
      case self::TYPE_INT_COLOR_ARGB8:
      case self::TYPE_INT_COLOR_RGB8:
      case self::TYPE_INT_COLOR_ARGB4:
      case self::TYPE_INT_COLOR_RGB4:
        return sprintf(&#39;#%08X&#39;, $data);
      case self::TYPE_DIMENSION:
        return $this->_complexToFloat($data).self::$DIMENSION_UNITS[$data & self::UNIT_MASK];
      case self::TYPE_FRACTION:
        return $this->_complexToFloat($data).self::$FRACTION_UNITS[$data & self::UNIT_MASK];
      case self::TYPE_FLOAT:
        return $this->_int2float($data);
    }
    if ($type >=self::TYPE_INT_DEC && $type < self::TYPE_INT_COLOR_ARGB8){
      return (string)$data;
    }
    return sprintf(&#39;<0x%X, type 0x%02X>&#39;, $data, $type);
  }
 
  private function _complexToFloat($data){
    return (float)($data & 0xFFFFFF00) * self::$RADIX_MULTS[($data>>4) & 3];
  }
  private function _int2float($v) {
    $x = ($v & ((1 << 23) - 1)) + (1 << 23) * ($v >> 31 | 1);
    $exp = ($v >> 23 & 0xFF) - 127;
    return $x * pow(2, $exp - 23);
  }
  private static function _getPackage($data){
    return ($data >> 24 == 1) ? &#39;android:&#39; : &#39;&#39;;
  }
 
  private function getStringTab($base, $list){
    $tab = array();
    foreach ($list as $off){
      $off += $base;
      $len = $this->get16($off);
      $mask = ($len >> 0x8) & 0xFF;
      $len = $len & 0xFF;
      if ($len == $mask){
        if ($off + $len > $this->length) throw new Exception(&#39;String Table Overflow&#39;, 11);
        $tab[] = substr($this->xml, $off, $len);
      }else {
        if ($off + $len * 2 > $this->length) throw new Exception(&#39;String Table Overflow&#39;, 11);
        $str = substr($this->xml, $off, $len * 2);
        $tab[] = mb_convert_encoding($str, &#39;UTF-8&#39;, &#39;UCS-2LE&#39;);
      }
    }
    return $tab;
  }
  private function getString($id){
    if ($id > -1 && $id < $this->stringCount){
      return $this->stringTab[$id];
    }else {
      return &#39;&#39;;
    }
  }
  private function getNameSpace($uri){
    for ($i=count($this->ns); $i > 0; ){
      $ns = $this->ns[--$i];
      if (isset($ns[$uri])){
        $ns = $this->getString($ns[$uri]);
        if (!empty($ns)) $ns .= &#39;:&#39;;
        return $ns;
      }
    }
    return &#39;&#39;;
  }
  private function get32(&$off){
    $int = unpack(&#39;V&#39;, substr($this->xml, $off, 4));
    $off += 4;
    return array_shift($int);
  }
  private function get32array(&$off, $size){
    if ($size <= 0) return NULL;
    $arr = unpack(&#39;V*&#39;, substr($this->xml, $off, 4 * $size));
    if (count($arr) != $size) throw new Exception(&#39;Array Size Error&#39;, 10);
    $off += 4 * $size;
    return $arr;
  }
  private function get16(&$off){
    $int = unpack(&#39;v&#39;, substr($this->xml, $off, 2));
    $off += 2;
    return array_shift($int);
  }
  private function skip($size){
    $this->xml = substr($this->xml, $size);
    $this->length -= $size;
  }
}
?>
<br/>


本站聲明
本文內(nèi)容由網(wǎng)友自發(fā)貢獻(xiàn),版權(quán)歸原作者所有,本站不承擔(dān)相應(yīng)法律責(zé)任。如您發(fā)現(xiàn)有涉嫌抄襲侵權(quán)的內(nèi)容,請(qǐng)聯(lián)系admin@php.cn

熱AI工具

Undress AI Tool

Undress AI Tool

免費(fèi)脫衣服圖片

Undresser.AI Undress

Undresser.AI Undress

人工智能驅(qū)動(dòng)的應(yīng)用程序,用于創(chuàng)建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用于從照片中去除衣服的在線人工智能工具。

Clothoff.io

Clothoff.io

AI脫衣機(jī)

Video Face Swap

Video Face Swap

使用我們完全免費(fèi)的人工智能換臉工具輕松在任何視頻中換臉!

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費(fèi)的代碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

功能強(qiáng)大的PHP集成開發(fā)環(huán)境

Dreamweaver CS6

Dreamweaver CS6

視覺化網(wǎng)頁(yè)開發(fā)工具

SublimeText3 Mac版

SublimeText3 Mac版

神級(jí)代碼編輯軟件(SublimeText3)

熱門話題

Laravel 教程
1600
29
PHP教程
1502
276