如何将Windows SID转换为SQL Server server_user_sid?


8

有一个不错的SQL Server函数SUSER_SNAME,可将server_user_sid转换为用户名。这对于将众所周知的Windows SID转换为(可能本地化的)用户名很有用。

例:

SELECT SUSER_SNAME(0x01020000000000052000000021020000)

-- yields 'BUILTIN\USERS' (or, on a German system, 'VORDEFINIERT\Benutzer')

通过一些Google搜索和反复试验(=手动创建用户,然后进行检查sys.server_principals),我确定了以下等效条件:

Built-in User/Group    Windows SID      SQL Server server_user_sid

BUILTIN\USERS          S-1-5-32-545     0x01020000000000052000000021020000
NT AUTHORITY\SYSTEM    S-1-5-18         0x010100000000000512000000

将Windows SID转换为SQL Server server_user_sids的算法是什么?

Answers:


12

形式为SID的0x01020000000000052000000021020000不是“ SQL Server” SID。那只是SID的基础二进制值。它可以采用的另一种形式(仍然是相同的值)是“字符串”形式(SID字符串格式语法),它看起来像S-1-5-32-545(在某些MSDN文档中称为“ SDDL”格式,尽管SDDL所涵盖的不仅限于此)。 SID)。两者都是相同的Windows SID。此设置类似于GUID具有不同于其基础二进制值的字符串表示形式的方式。

有一个未记录的内置函数,SID_BINARY它可以将SDDL形式转换为二进制形式:

SELECT SID_BINARY(N'S-1-5-21-408552231-458724953-3089381293-513');
-- 0x01050000000000051500000027035A185996571BAD3724B801020000

此功能应适用于大多数SID类型。以下两个查询显示它对于证书和非对称密钥可以正常工作(您可以验证正确的转换,因为这两个系统目录视图中都有SID的两种形式)。它适用于从证书和非对称密钥创建的任何登录名,因为这些证书(非登录名和用户)的SID是证书/密钥SID:

SELECT [name], [string_sid], [sid], SID_BINARY([string_sid])
FROM   [master].sys.certificates;

SELECT [name], [string_sid], [sid], SID_BINARY([string_sid])
FROM   [master].sys.asymmetric_keys;

请注意,类型“ S”(SQL Server登录名/ SQL Server用户)和“ R”(服务器角色/数据库角色)的主体不具有SDDL表示,因为它们不是Windows SID。这两种类型的主体具有SQL Server专有SID,所以我猜它们将是“ SQL Server SID”,尽管区别(Windows SID和SQL Server SID之间)是有价值的,而不是形式。

如果您不想使用未记录的功能,也可以使用.NET的SecurityIdentifier类通过SQLCLR来实现。

可以在SQL#库的免费版本(我创建的)中找到预制的SQLCLR函数(我创建):Convert_SddlSidToBinary(与进行相同的翻译SID_BINARY)和Convert_BinarySidToSddl


2

sys.server_principals 是您的朋友,因为它公开了Windows版本的SID。

请参考Aaron的解决方案:SQL Server SID和Windows SID之间的映射

为了完整起见,下面是代码:

CREATE TABLE dbo.TinyNumbers(Number TINYINT PRIMARY KEY);

INSERT dbo.TinyNumbers(Number) 
  SELECT TOP (256) ROW_NUMBER() OVER (ORDER BY number)-1 
  FROM master.dbo.spt_values;

CREATE FUNCTION dbo.GetWindowsSID
(
  @sid VARBINARY(85)
)
RETURNS TABLE
WITH SCHEMABINDING
AS
  RETURN 
  (
    SELECT ADsid = STUFF((SELECT '-' + part FROM 
    (
      SELECT Number = -1, part = 'S-' 
        + CONVERT(VARCHAR(30),CONVERT(TINYINT,CONVERT(VARBINARY(30),LEFT(@sid,1)))) 
        + '-' 
        + CONVERT(VARCHAR(30),CONVERT(INT,CONVERT(VARBINARY(30),SUBSTRING(@sid,3,6))))
      UNION ALL
      SELECT TOP ((LEN(@sid)-5)/4) Number, 
     part = CONVERT(VARCHAR(30),CONVERT(BIGINT,CONVERT(VARBINARY(30), 
  REVERSE(CONVERT(VARBINARY(30),SUBSTRING(@sid,9+Number*4,4)))))) 
      FROM dbo.TinyNumbers ORDER BY Number
    ) AS x ORDER BY Number
    FOR XML PATH(''), TYPE).value(N'.[1]','nvarchar(max)'),1,1,'')
  );
GO

CREATE VIEW dbo.server_principal_sids
AS
  SELECT sp.name, sp.[sid], ad.ADsid, sp.type_desc
    FROM sys.server_principals AS sp
    CROSS APPLY dbo.GetWindowsSID(sp.[sid]) AS ad
    WHERE [type] IN ('U','G') 
    AND LEN([sid]) % 4 = 0;

-- select the data
SELECT name,[sid],ADSid,type_desc FROM dbo.server_principal_sids;
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.