SQL2000下非sysadmin固定服务器角色的成员执行xp_cmdshell

时间:2021-10-02 08:32:24

 

SQL2000下非sysadmin固定服务器角色的成员执行xp_cmdshell

 

------------------------------------------------------

-- 11/11/2009 2:32:18 PM

-- Happyflystone

-- blog: http://blog.csdn.net/happyflystone

--  Microsoft SQL Server  2000 - 8.00.2039 (Intel X86)

--        May  3 2005 23:18:38

--        Copyright (c) 1988-2003 Microsoft Corporation

--        Personal Edition on Windows NT 5.2 (Build 3790: Service Pack 2)

--  转载注明出处及相关信息。

------------------------------------------------------

首先我们增加一个login并缺省test_db数据库。

 

--add login

use master

Go

EXEC sp_addlogin 'njslt', 'njslt', 'test_db'

Go

use test_db

Go

EXEC sp_adduser 'njslt', 'njslt', 'db_owner'

Go

/*

这儿一定要执行以下的过程哦,否则会:

服务器: 消息229,级别14,状态5,过程xp_cmdshell,行1

拒绝了对对象'xp_cmdshell'(数据库'master',所有者'dbo')的EXECUTE 权限。

*/

use master 

Go

EXEC sp_adduser  'njslt', 'njslt', 'db_ddladmin'

Go

GRANT exec ON xp_cmdshell TO njslt

GO

 

接着我们以njslt连接数据库,并打开查询分析器,执行如下角本:

 

 

exec master..xp_cmdshell 'dir c:'

 

/*

消息50001,级别1,状态50001

由于LogonUserW 返回错误1326,执行xp_cmdshell 失败。

请确保运行SQL Server 的服务帐户具有适当的特权。

有关详细信息,请在联机丛书中搜索与xp_sqlagent_proxy_account 相关的主题。

*/

 

 

    好,问题出来了,默认情况下,只有 sysadmin 固定服务器角色的成员才能执行此扩展存储过程。但是,也可以授予其他用户执行此存储过程的权限。

当作为 sysadmin 固定服务器角色成员的用户唤醒调用 xp_cmdshell 时,将在运行 SQL Server 服务的安全上下文中执行 xp_cmdshell。当用户不是 sysadmin 组的成员时,xp_cmdshell 将模拟使用 xp_sqlagent_proxy_account 指定的 SQL Server 代理程序的代理帐户。如果代理帐户不能用,则 xp_cmdshell 将失败。这只是针对于 Microsoft® Windows NT® 4.0 Windows 2000。在 Windows 9.x 上,没有模拟,且 xp_cmdshell 始终在启动 SQL Server Windows 9.x 用户的安全上下文下执行。

 

    记得以前有人问题这个问题时,我当时想当然的回答了利用SETUSER来临时切换安全上下文,所以我第一反应想用这个来实现,结果发现失败了,那如何来解决这个问题呢。我做了两种方法,大家看看:

一、提升用户,加入固定服务器角色

根据联机帮助提示,xp_cmdshell只有是sysadmin固定服务器角色成员才可以,那我加它进sysadmin角色里,但是一定要注意sysadmin角色在SQLSERVER里可是能进行任何活动的哦,这是不是有安全隐患?

SA登录执行:

exec sp_addsrvrolemember 'njslt', 'sysadmin'

GO

 

二、 模拟使用 xp_sqlagent_proxy_account 指定的 SQL Server 代理程序的代理帐户

 

DECLARE

    @winuser sysname,

    @password sysname,

    @Nsql varchar(1000);

-- 在操作系统中为xp_cmdshell 代理帐户建立windows 用户

SELECT

    @user = N'xpcmdshell',

    @password = N'xpcmdshell',

    @Nsql = 'NET USER "' + @winuser + '" "' + @password + '" /ADD';

EXEC  xp_cmdshell @Nsql;

go

-- 建立xp_cmdshell 代理帐户

EXEC master.dbo.xp_sqlagent_proxy_account N'SET',

             N'',

             @user,

             @password

 

这时你在刚才以njslt连接用查询分析器再试试,xp_cmdshell有结果了。

 

 

--删除测试环境:

 

--drop db user,login , windows user

/*

use test_db

go

sp_dropuser 'njslt'

go

use master

go

sp_dropuser 'njslt'

go

sp_droplogin 'njslt'

go

DECLARE

    @user sysname,

    @password sysname,

    @sql varchar(1000);

 

SELECT

    @user = N'xpcmdshell',

    @password = N'xpcmdshell',

    @sql = 'NET USER ' + @user + ' /delete';

 select @sql

EXEC  xp_cmdshell @sql;

 

*/