MSSQL数据库总结

这篇文章是紧接着上一篇文章的

大纲: MSSQL中几个有趣的概念 MSSQL在渗透过程中有趣的点 我的环境预期

0x01 MSSQL一些有趣的操作

有意思的操作都在高级对象使用这里 ### 视图 即创建了一个虚表,提供更好的视图,但不另外进行储存。具有更好的安全性。

CREATE VIEW [Products Above Average Price] AS
SELECT ProductName,UnitPrice
FROM Products
WHERE UnitPrice>(SELECT AVG(UnitPrice) FROM Products) 

可以理解为,从几个基表中对你想呈现给用户的部分数据做一个映射,以一种安全、便捷的方式进行查看。而相应的插入、更新操作都需要经过数据完整性检测之后才能透过虚表对实表进行。

存储过程

预先在服务端设置一段SQL程序,以完成一系列处理。该语句事先已预先编译好,执行速度极快。 有以下特性: 1. 标准组件式编程 2. 减少网络流量 3. 安全机制(对数据进行检测)

例子:

USE AdventureWorks2012;  
GO  
CREATE PROCEDURE HumanResources.uspGetEmployeesTest2   
    @LastName nvarchar(50),   
    @FirstName nvarchar(50)   
AS   

    SET NOCOUNT ON;  
    SELECT FirstName, LastName, Department  
    FROM HumanResources.vEmployeeDepartmentHistory  
    WHERE FirstName = @FirstName AND LastName = @LastName  
    AND EndDate IS NULL;  
GO  

函数

系统会自带一些基本的函数,用户也可以自定义函数。和其它脚本语言定义函数的思想是相同的。

语法:

IF OBJECT_ID (N'dbo.ufnGetInventoryStock', N'FN') IS NOT NULL  
    DROP FUNCTION ufnGetInventoryStock;  
GO  
CREATE FUNCTION dbo.ufnGetInventoryStock(@ProductID int)  
RETURNS int   
AS   
-- Returns the stock level for the product.  
BEGIN  
    DECLARE @ret int;  
    SELECT @ret = SUM(p.Quantity)   
    FROM Production.ProductInventory p   
    WHERE p.ProductID = @ProductID   
        AND p.LocationID = '6';  
     IF (@ret IS NULL)   
        SET @ret = 0;  
    RETURN @ret;  
END; 

存储过程的优势来源于事先编译,而在MSSQL中其实函数和存储过程都可能会被事先编译,是否放到缓存库里,只取决于该存储过程/函数的执行频率。 存储过程只能使用out参数回显数据,而函数可以直接RETURN。

触发器

一种特殊类型的存储结构,除约束以外的,保证数据完整性的方法。

在设计小组平台数据库结构的时候写了一些简单的触发器

delimiter $$
CREATE TRIGGER add_data_action AFTER INSERT
    ON `solves` FOR EACH ROW
    BEGIN
        SET @Ins = (SELECT firstblood FROM challenges WHERE challenges.id = new.challenge_id);
        IF @Ins = 0 THEN    
            INSERT INTO challenges(firstblood) VALUES solves(new.team_id);
            INSERT INTO fb_leaderboards(challenge_id,team_id,time,killer_id) VALUES (challenge_id, team_id, time, killer_id);
        ELSE IF @Ins > 0 THEN
        SET @Ins = 'keep id';
        END IF;
    END
$$

创建语句的前后要加上:

delimiter $$
……
$$

目的是在命令行输入多行带分号的SQL语句 这个触发器的功能是当有解题数据插入的时候,检测是否为一血,然后做出加分、添加一血榜单等命令。 因为用的是mysql,而mysql对触发器以及面向过程的SQL编程的支持并不是很好,所以产生了一系列问题,体验感极差。 希望以后写一点大型东西的时候,可以改善这种体验吧。 编程设计真的挺好玩的。

事务

为了确保业务的完整性,避免数据处理了一半,因异常情况干扰了业务的完成而设立 即,在事务中定义的修改,要么全部生效,要么全部不生效。

比如说银行系统中的转账,A的账户中增加了100的同时B的账户中必须要减少100,如果使用两条UPDATA语句的话,万一过程中出现物理异常,甚至是人为异常,导致第一条执行而第二条不执行,那就会导致银行的损失。 因此,像这种财务性操作,必须要通过类似事务的概念去解决。

语法:

BEGIN TRAN[SACTION] [transaction_name | @tran_name_variable]
COMMIT [ TRAN[SATION] [transcation_name] @tran_name_variable]]

事务之间可以互相嵌套 估计只有很大型的项目会用这种东西吧。

在某操作的过程中对其它操作的权限进行限制,防止出现丢失更新、未确定版本泄露、幻象读等问题

锁有一下种类 1. 共享 2. 更新 3. 排它 4. 意图 5. 架构 6. 大容量更新 7. 键范围

同样是大型项目才会用到的概念,手头没有数据,也不方便去测试,就不详细去弄了~

上面那句话是我上午说的,现在我来自打脸……

MSSQL的渗透过程本就要比MYSQL复杂一些,提权之类的操作多要通过一些存储过程之类的的东西去实现,所以对于这些数据库高级对象使用技能是必须的。

0x02 MSSQL在渗透中的一些技巧

主要跟着大佬的文章去学

特殊变量及函数

在MSSQL渗透中部分系统函数和变量和MYSQL不一样 渗透测试的时候可以从MSSQL注入备忘录查看,已经总结的很齐全了,这里就不再搬运了~

神奇的EXEC

使用EXEC是可以执行一些默认的存储过程,从而收获一些意想不到的东东~ 比如: 可以直接查询出某数据库文件的存放路径

变量的使用

在MYSQL的注入中,很少用到变量(或者是我太低端了……) 而MSSQL中就经常用到自定义变量,以此来完成一些绕过,比如下面的这个十六进制绕过

' AND 1=0; DECLARE @S VARCHAR(4000) SET @S=CAST(0x44524f50205441424c4520544d505f44423b AS VARCHAR(4000)); EXEC (@S);--

提权

这也是我之后想要原创题目的部分 一个MSSQL提权的工具 因为自己也不太懂提权,就简单把几种提权列举一下,之后肯定是要详细去弄的 1. 证书提权 2. xp_cmdshell组件(2005之后失效,垃圾~) 3. xp_dirtree 4. openrowset默认关闭 5. 沙盒 6. SP_OACREATE 7. Agent Job 8. Else 9. OBB(为啥也放到这里?)

剩余的一些问题

很奇怪的一点是,在MSSQL中information表依然能用 Google了一下,发现是有一个元数据储存什么的~也不太懂……可能还要去看一下手册?

在MSSQL的一些注入技巧中,SQL的语法都比较复杂,难道在MSSQL中不需要满足什么条件就可以直接注吗?(比如Mysql中的堆叠注入就对数据库连接形式有要求)

0x03 预想我的环境

其实包括安全客的那篇文章,涉及的渗透+提权技巧都是过时了的,应该多去国外搜一些文章去学习新的姿势,而不是拿一些老掉牙的东西反复咀嚼,如果能学到一些的话,大概可以总结很多姿势,然后做环境的同时也屯下一些文章吧 https://pentestlab.blog/2013/03/18/penetration-testing-sql-servers/

简单题: 1. 只是简单的绕过,然后会考到一些语法的不同

中等: 1. 老套&工具提权 2. 数据库简单信息探测,在简单信息中搜集获得更进一步的钥匙

困难: 1. 综合起来,一整套 2. 可不可以通过一个安全性较好的MSSQL转而攻击另一个内网中的MSSQL?备份数据库?

除此之外,还想要学一波阿里云里的数据库教程,看一下市场上的数据库领域再干嘛~