转载:
首先要建立一张表和一个存储过程:
SQL_DECODE表:
CREATE TABLE [dbo].[SQL_DECODE]( [ID] [int] IDENTITY(1,1) NOT NULL, [SQLTEXT] [nvarchar](max) NOT NULL, CONSTRAINT [ID] PRIMARY KEY CLUSTERED ( [ID] ASC)) ON [PRIMARY]GO
DECODE_PROC存储过程:
CREATE PROCEDURE [dbo].[DECODE_PROC]( @PROC_NAME SYSNAME = NULL)ASSET NOCOUNT ONDECLARE @PROC_NAME_LEN INT --存储过程名长度DECLARE @MAX_COL_ID SMALLINT --最大列IDSELECT @MAX_COL_ID = MAX(subobjid) FROM sys.sysobjvalues WHERE objid = OBJECT_ID(@PROC_NAME) GROUP BY imagevalSELECT @PROC_NAME_LEN = DATALENGTH(@PROC_NAME) + 29DECLARE @REAL_01 NVARCHAR(MAX) --真实加密存储过程数据DECLARE @FACK_01 NVARCHAR(MAX) --修改为假的存储过程,长度(40003 - 存在过程名长度),原理不明?DECLARE @FACK_ENCRYPT_01 NVARCHAR(MAX) --伪加密存储过街程数据DECLARE @REAL_DECRYPT_01 NVARCHAR(MAX) --最终解密后的数据,初始化为原始加密长度的一半的“A”,原理不明?SET @REAL_01 = ( SELECT imageval FROM sys.sysobjvalues WHERE objid = object_id(@PROC_NAME) AND valclass = 1 AND subobjid = 1)DECLARE @REAL_DATA_LEN BIGINTSET @REAL_DATA_LEN = DATALENGTH(@REAL_01)--PRINT @REAL_DATA_LENDECLARE @FACK_LEN BIGINTSET @FACK_LEN = @REAL_DATA_LEN * 10 --改造:假的长度在原真实数据长度上放大10倍--此处需将NVARCHAR显示转换成NVARCHAR(MAX),不然将只能产生4K长度SET @FACK_01 = 'ALTER PROCEDURE ' + @PROC_NAME + ' WITH ENCRYPTION AS ' + REPLICATE(CONVERT(NVARCHAR(MAX), '-'), @FACK_LEN - @PROC_NAME_LEN)--PRINT '@FACK_01 = ' + STR(LEN(@FACK_01))EXECUTE (@FACK_01)SET @FACK_ENCRYPT_01 = ( SELECT imageval FROM sys.sysobjvalues WHERE objid = object_id(@PROC_NAME) AND valclass = 1 AND subobjid = 1)SET @FACK_01 = 'CREATE PROCEDURE ' + @PROC_NAME + ' WITH ENCRYPTION AS ' + REPLICATE(CONVERT(VARCHAR(MAX), '-'), @FACK_LEN - @PROC_NAME_LEN)SET @REAL_DECRYPT_01 = REPLICATE(CONVERT(NVARCHAR(MAX), N'A'), (DATALENGTH(@REAL_01) /2))--PRINT 'LEN(@REAL_DECRYPT_01) = ' + STR(LEN(@REAL_DECRYPT_01))--按位对 @REAL_01、 @FACK_01、 @REAL_DECRYPT_01 进行异或操作。DECLARE @INT_PROC_SPACE BIGINTSET @INT_PROC_SPACE = 1WHILE @INT_PROC_SPACE <= (DATALENGTH(@REAL_01) /2 )BEGIN SET @REAL_DECRYPT_01 = STUFF( @REAL_DECRYPT_01, @INT_PROC_SPACE, 1, NCHAR(UNICODE(SUBSTRING(@REAL_01, @INT_PROC_SPACE, 1)) ^ (UNICODE(SUBSTRING(@FACK_01, @INT_PROC_SPACE, 1)) ^ UNICODE(SUBSTRING(@FACK_ENCRYPT_01, @INT_PROC_SPACE, 1)))) ) SET @INT_PROC_SPACE = @INT_PROC_SPACE + 1END--移除WITH ENCRYPTIONSET @REAL_DECRYPT_01 = REPLACE(@REAL_DECRYPT_01, 'WITH ENCRYPTION', '')INSERT INTO [SQL_DECODE] VALUES (@REAL_DECRYPT_01)--PRINT '@REAL_DECRYPT_01 = ' + @REAL_DECRYPT_01--PRINT 'LEN(@REAL_DECRYPT_01) = ' + STR(LEN(@REAL_DECRYPT_01))--删除原存储过程SET @FACK_01 = 'DROP PROCEDURE ' + @PROC_NAMEEXEC(@FACK_01)GO
然后使用DAC登录数据库:admin:计算机名称,需要在数据库所在的电脑登录,不能使用客户端远程操作这些步骤。
如果不成功,可以先windows身份登录,新建查询,然后更改链接使用admin:计算机名称登录。
然后执行存储过程:
exec dbo.DECODE_PROC '存储过程名'
如果执行成功,SQL_DECODE表会增加一条记录:
复制里面的内容出来就解密后的存储过程了。
vinson