Премини към съдържанието
valkosoft

MSSQL SQL Injection

Препоръчан отговор


Днес разбрах че някак един хакер има достъп до базата данни и може да прави каквото си иска. Та въпроса ми е единствения пхп код в целия сайт е този:

<?php
function GetStbName( $id )
{
	$types = array(1=>'LIST_FACEITEM',2=>'LIST_CAP',3=>'LIST_BODY',4=>'LIST_ARMS',
		5=>'LIST_FOOT',6=>'LIST_BACK',7=>'LIST_JEWEL',8=>'LIST_WEAPON',9=>'LIST_SUBWPN',10=>'LIST_USEITEM',
		11=>'LIST_JEMITEM',12=>'LIST_NATURAL',14=>'LIST_PAT');
	return $types[ $id ];
}

function CleanInput( $text )
{
	$text = str_replace( '\'', '\'\'', $text );
	return $text;
}

function BAGetByte( $array, $pos )
{
	return hexdec( bin2hex( $array[$pos] ) );
}

function BAGetWord( $array, $pos )
{
	return hexdec( bin2hex( $array[$pos+1] . $array[$pos] ) );
}

function BAGetDWord( $array, $pos )
{
	return hexdec( bin2hex( $array[$pos+3] . $array[$pos+2] . $array[$pos+1] . $array[$pos] ) );
}

function BAGetQWord( $array, $pos )
{
	return hexdec( bin2hex( $array[$pos+7] . $array[$pos+6] . $array[$pos+5] . $array[$pos+4] . $array[$pos+3] . $array[$pos+2] . $array[$pos+1] . $array[$pos] ) );
}


class CItem
{
	var $itemid;
	var $itemtype;
	var $count;
	var $statid;
	var $durability;
	var $lifespan;
	var $socketed;
	var $appraised;
	var $refine;
	var $itemsn1;
	var $itemsn2;

	function __construct( $data, $pos )
	{
		$itemhead = BAGetWord( $data, $pos );
		$itemdata = BAGetDWord( $data, $pos + 2 );
		$this->itemsn1 = BAGetDWord( $data, $pos + 6 );
		$this->itemsn2 = BAGetDWord( $data, $pos + 10 );
		$this->itemtype = $itemhead & 0x1f;
		$this->itemid = $itemhead >> 5;
		$this->count = $itemdata;
		$this->statid = $itemdata & 0x1ff;
		$this->durability = $itemdata >> 9 & 0x7f;
		$this->lifespan = $itemdata >> 16 & 0x3ff;
		$this->socketed = $itemdata >> 26 & 0x1;
		$this->appraised = $itemdata >> 27 & 0x1;
		$this->refine = $itemdata >> 28 & 0xf;
	}
	function GetHex( )
	{
		$retval = '';

		$itemhead = $this->itemtype | ( $this->itemid << 5 );
		if( $this->itemtype >= 10 && $this->itemtype <= 13 )
		{
			$itemdata = $this->count;
		}else{
			$itemdata = 0;
			$itemdata |= ( $this->statid & 0x1ff );
			$itemdata |= ( $this->durability & 0x7f ) << 9;
			$itemdata |= ( $this->lifespan & 0x3ff ) << 16;
			$itemdata |= ( $this->socketed & 0x1 ) << 26;
			$itemdata |= ( $this->appraised & 0x1 ) << 27;
			$itemdata |= ( $this->refine & 0xf ) << 28;
		}

		$retval .= sprintf( '%02x', $itemhead & 0xff );
		$retval .= sprintf( '%02x', $itemhead >> 8 & 0xff );

		$retval .= sprintf( '%02x', $itemdata & 0xff );
		$retval .= sprintf( '%02x', $itemdata >> 8 & 0xff );
		$retval .= sprintf( '%02x', $itemdata >> 16 & 0xff );
		$retval .= sprintf( '%02x', $itemdata >> 24 & 0xff );

		$retval .= sprintf( '%02x', $this->itemsn1 & 0xff );
		$retval .= sprintf( '%02x', $this->itemsn1 >> 8 & 0xff );
		$retval .= sprintf( '%02x', $this->itemsn1 >> 16 & 0xff );
		$retval .= sprintf( '%02x', $this->itemsn1 >> 24 & 0xff );

		$retval .= sprintf( '%02x', $this->itemsn2 & 0xff );
		$retval .= sprintf( '%02x', $this->itemsn2 >> 8 & 0xff );
		$retval .= sprintf( '%02x', $this->itemsn2 >> 16 & 0xff );
		$retval .= sprintf( '%02x', $this->itemsn2 >> 24 & 0xff );

		return $retval;
	}
	
	function IsEmpty( )
	{
		return ( $this->itemtype == 0 ) && ( $this->itemid == 0 );
	}
};

class CUserStorage
{
	var $items;
	var $money1;
	var $money2;
	
	function __construct( $data )
	{
		for( $i = 0; $i < 4 * 5 * 8; $i++ )
			$this->items[ $i ] = new CItem( $data, $i * 14 );
		$this->money1 = BAGetDWord( $data, 4 * 5 * 8 * 14 + 0 );
		$this->money2 = BAGetDWord( $data, 4 * 5 * 8 * 14 + 4 );
	}
	
	function GetHex( )
	{
		for( $i = 0; $i < 4 * 5 * 8; $i++ )
			$retval .= $this->items[ $i ]->GetHex( );
		$retval .= sprintf( '%02x', $this->money1 & 0xff );
		$retval .= sprintf( '%02x', $this->money1 >> 8 & 0xff );
		$retval .= sprintf( '%02x', $this->money1 >> 16 & 0xff );
		$retval .= sprintf( '%02x', $this->money1 >> 24 & 0xff );
		$retval .= sprintf( '%02x', $this->money2 & 0xff );
		$retval .= sprintf( '%02x', $this->money2 >> 8 & 0xff );
		$retval .= sprintf( '%02x', $this->money2 >> 16 & 0xff );
		$retval .= sprintf( '%02x', $this->money2 >> 24 & 0xff );
		return $retval;
	}
	
	function IsEmpty( )
	{
		for( $i = 0; $i < 4 * 5 * 8; $i++ ) {
			if( !$this->items[ $i ]->IsEmpty( ) )
				return false;
		}
		if( $this->money1 > 0 || $this->money2 > 0 )
			return false;
		return true;
	}
};

class CRuffSite
{
	// Class Variables
	var $db = 0;
	
	// Class Constructors
	function __construct( )
	{
		
	}

	// Basic DB Functions
	function OpenDb( )
	{
		

$this->db = mssql_connect( '127.0.0.1', 'sa', 'wrgrgrege' );
	}


	
	function QueryDb( $query )
	{
		if( $this->db == 0 )
			$this->OpenDb( );
			
		return mssql_query( $query, $this->db );
	}
	
	function CloseDb( )
	{
		mssql_close( $this->db );
		$this->db = 0;
	}
	
	// User Functions
	function LogIn( $user, $pass )
	{
		$user = CleanInput( $user );
		$pass = CleanInput( $pass );
		
		if( $_SESSION[ 'loggedin' ] )
			return true;
			
 		$query = $this->QueryDb( "SELECT AID,[Right] FROM seven_ORA..UserInfo WHERE Account='" . $user . "' AND MD5Password='" . md5( $pass ) . "'" );
		if( mssql_num_rows( $query ) > 0 ) {
			$data = mssql_fetch_array( $query );
			
			$_SESSION[ 'loggedin' ] = true;
			$_SESSION[ 'userid' ] = $query[ 'AID' ];
			$_SESSION[ 'username' ] = $user;
			$_SESSION[ 'password' ] = $pass;
			$_SESSION[ 'right' ] = $query[ 'Right' ];
			
		
			return true;
		} else {
			
			return false;
		}
	}
	
	function IsLoggedIn( )
	{
		return $_SESSION[ 'loggedin' ];
	}
	
	function GetRight( )
	{
		if( !$this->IsLoggedIn( ) )
			return -1;
		return $_SESSION[ 'right' ];
	}
	
	function GetUser( )
	{
		if( !$this->IsLoggedIn( ) )
			return '';
		return $_SESSION[ 'username' ];
	}
	
	function LogOut( )
	{
		$_SESSION[ 'loggedin' ] = false;
		$_SESSION[ 'password' ] = '';
		$_SESSION[ 'right' ] = 0;
	}
	
	function ChangePassword( $user, $email, $mothername, $newpass )
	{
		$user = CleanInput( $user );
		$email = CleanInput( $email );
		$mothername = CleanInput( $mothername );
		$newpass = md5( $newpass );
		
		$query = $this->QueryDb( "SELECT AID FROM seven_ORA..UserInfo WHERE Account='" . $user . "' AND MotherLName='" . $mothername . "' AND Email='" . $email . "'" );
		if( mssql_num_rows( $query ) > 0 ) {
			$this->QueryDb( "UPDATE seven_ORA..UserInfo SET MD5Password='" . $newpass . "' WHERE Account='" . $user . "'" );
			
		
			return true;
		} else {
		
			return false;
		}
	}
	
	function Register( $user, $email, $mothername, $pass1, $pass2 )
	{
		$user = CleanInput( $user );
		$email = CleanInput( $email );
		$mothername = CleanInput( $mothername );
		$pass1 = md5( $pass1 );
		$pass2 = md5( $pass2 );
		
		if( $pass1 != $pass2 )
			return 1;
		
		$query = $this->QueryDb( "SELECT AID FROM seven_ORA..UserInfo WHERE Account='" . $user . "'" );
		if( mssql_num_rows( $query ) > 0 )
			return 2;
			
		$query = $this->QueryDb( "SELECT AID FROM seven_ORA..UserInfo WHERE Email='" . $email . "'" );
		if( mssql_num_rows( $query ) > 0 )
			return 3;
			
		//mssql_query( "DECLARE @NEWID int SET @NEWID=(select max(AID)+1 from seven_ORA..UserInfo) INSERT INTO seven_ORA..UserInfo (AID,Account,MD5Password,AscPassword,MotherLName,Email,[Right],memberinfo,MailIsConfirm) VALUES(@NEWID,'" . $_POST[ 'username' ] . "','" . $_POST[ 'passwordenc' ] . "','" . $_POST[ 'password' ] . "','" . $_POST[ 'mothername' ] . "','" . $_POST[ 'email' ] . "', 1, 2, 1)" );
		$this->QueryDb( "DECLARE @NEWID int SET @NEWID=(select max(AID)+1 from seven_ORA..UserInfo) INSERT INTO seven_ORA..UserInfo (AID,Account,MD5Password,MotherLName,Email,[Right],memberinfo,MailIsConfirm) VALUES(@NEWID,'$user','$pass1','$mothername','$email',1,2,1)" );
		return 0;
	}
	
	function GetStorageData( $user )
	{
		$user = CleanInput( $user );
	
		$query = $this->QueryDb( "SELECT CONVERT(TEXT,CONVERT(VARCHAR(8000),blobITEMS)) AS blobITEMS FROM SHO..tblGS_BANK WHERE txtACCOUNT='" . $user . "'" );
		if( mssql_num_rows( $query ) > 0 ) {
			$row = mssql_fetch_array( $query );
			return new CUserStorage( $row[ 'blobITEMS' ] );
		} else {
			$site->QueryDb( "INSERT INTO SHO..tblGS_BANK (txtACCOUNT) VALUES('" . $user . "')" );
			return new CUserStorage( '' );
		}
	}
	
	// Avatar Functions
	
};

$site = new CRuffSite( );
?>

Та въпросами е как да го променя та да не може да се вкарва Sql инжекция , и как да защита моят MSSQL SERVER 2008 по добре?

Редактирано от valkosoft (преглед на промените)

Сподели този отговор


Линк към този отговор
Сподели в други сайтове

Много умно - да си покажеш целия код, че който не го е видял и той да го види и намери и други слаби места.

Сподели този отговор


Линк към този отговор
Сподели в други сайтове

Пробвай в CleanInput да е return "'$text'"; Или примерно друг regex - /(.)/\\$1/

Сподели този отговор


Линк към този отговор
Сподели в други сайтове

Регистрирайте се или влезете в профила си за да коментирате

Трябва да имате регистрация за да може да коментирате това

Регистрирайте се

Създайте нова регистрация в нашия форум. Лесно е!

Нова регистрация

Вход

Имате регистрация? Влезте от тук.

Вход

×

Информация

Поставихме бисквитки на устройството ви за най-добро потребителско изживяване. Можете да промените настройките си за бисквитки, или в противен случай приемаме, че сте съгласни с нашите условия за ползване.