ITPub博客

首页 > IT基础架构 > 网络安全 > 保证应用程序中私有对象安全技术(转)

保证应用程序中私有对象安全技术(转)

原创 网络安全 作者:RegisterForBlog 时间:2007-09-19 22:12:14 0 删除 编辑
保证应用程序中私有对象安全技术(转)[@more@]

  引言

  您是否考虑过扩展 Windows® 操作系统丰富的安全功能以将其应用于自己的应用程序的方法?您是否用过 Windows 文件系统安全编辑器,并希望能够为自己的业务对象提供这一级别的安全性?本文将首先介绍 Windows 安全授权的基础。然后介绍操纵安全描述符的步骤、创建自己的安全描述符的方法,以及如何使用不同的方法来编辑安全描述符。读过本文后,您将掌握足够的信息,使您能够将这些技术应用到自己的应用程序中。

  撰写本文的目的之一,是希望有助于使安全编程切实可行,且便于访问。所以这里不会对特定的函数进行全面、深入的剖析,我将介绍若干 helper 函数和类,使用它们可以使您的安全代码更可靠、更便于管理。helper 函数和示例不仅说明了使用各种安全函数的方法,而且着重说明了在出现异常和错误的情况下如何安全、可靠地使用它们。

  令牌及其概念

  本文的内容全部是有关管理访问控制的,管理访问控制也称为授权。在讨论此问题之前,我们需要具备一种方法,用来识别尝试对采取了安全措施的资源进行访问的用户。这就是令牌的作用。令牌代表计算机中的登录会话。只要用户以交互方式或远程方式访问计算机,就会创建登录会话。令牌是一个处理程序,可用来对登录会话进行查询和操纵。如果具有令牌,您就可以得到登录会话所代表的用户,以及确定是否应授予该用户访问已采取安全措施的资源的权限。

  因为所有应用程序都运行于登录会话的上下文中,所以总是可以使用某些类型的令牌来指示用户。在任何给定的时刻,可能有一个或多个不同的令牌或安全上下文,这会有些使人产生混淆。每一个登录会话都代表着不同的用户。至少有一个令牌附加到该进程。可以使用 OpenProcessToken 函数获取此令牌。

  CHandle token;

  Helpers::CheckError(::OpenProcessToken(::GetCurrentProcess(),

  TOKEN_QUERY,

  &token.m_h));

  CHandle 是一个由活动模版库 (ATL) 提供的包装类,当令牌超出范围时,它用来确保能够通过调用 CloseHandle 函数关闭处理程序。CheckError 是我的 Helpers 命名空间中的一个 helper 函数。CheckError 抛出一个 HRESULT,用于说明所发生的错误。使用不同的方法可以在 Windows 的 C 语言编程中表示出错的情况,我倾向使 HRESULT 标准化,以保证一致性。如果下载本文,则可以使用 Helpers 命名空间。GetCurrentProcess 函数的返回值是一个伪处理程序,它代表当前的进程。因为不是真正的处理程序,所以不需要调用 CloseHandle 函数来释放返回的 HANDLE。

  可以使用的另外一个令牌是线程令牌。可以通过调用 OpenThreadToken 函数来检索线程令牌。

  CHandle token;

  Helpers::CheckError(::OpenThreadToken(::GetCurrentThread(),

  TOKEN_QUERY,

  TRUE, // 打开自身

  &token.m_h));

  与 GetCurrentProcess 相同,GetCurrentThread 也返回一个伪处理程序,所以也不需要针对该程序调用 CloseHandle。与 OpenProcessToken 不同的是,如果没有任何令牌与当前线程相关联,那么可能无法成功调用 OpenThreadToken,这时函数返回 ERROR_NO_TOKEN。

  在某些情况下,甚至存在第三令牌,该令牌代表其他安全上下文。例如,ASP.NET 允许关闭客户模拟,在这种情况下,可以通过 HttpContext 类获取客户标识。

  获取令牌后,如果能够利用它执行一些有趣的操作,会有助于我们对它的理解。使用令牌能够执行的最简单的操作,就是对它进行查询,以获取登录会话的有关信息。可以使用 GetTokenInformation 函数执行此操作。因为 GetTokenInformation 函数可用来查询不同类的信息,调用方法相当复杂,所以我编写了一个包装函数模板,以减少调用时可能出现的错误。下面示例说明了查询令牌以获取令牌用户信息的方法。

  CLocalMemoryT tokenUser(Helpers::GetTokenInformation(token,

  TokenUser));

  CComBSTR string = Helpers::ConvertSidToStringSid(tokenUser->User.Sid);

  ConvertSidToStringSid helper 函数用于将二进制安全标识符 (SID) 转换为用户易识别的字符串。使用 SID 表示用户帐户是计算机易识别的格式。如果您的兴趣只在包装函数的功能,可以下载并查看本文所附的源代码。有关 CLocalMemoryT 类模板的内容将在介绍了内存管理之后讨论。

  安全描述符基础

  了解了如何识别用户后,我们需要一种方法,用来管理不同用户所具有的不同的权限。这就是使用安全描述符的必要性。安全描述符包含许多不同类型的信息。其中最有趣的是所有者安全识别符 (SID) 和两个访问控制列表 (ACL)。所有者 SID 可标识拥有对象的用户。两个 ACL 分别是随机 ACL 和系统 ACL。因为系统 ACL 实际上与访问控制无关,所以本文集中讨论随机 ACL (DACL)。

  安全描述符以 SECURITY_DESCRIPTOR 结构表示,因为没有关于此结构的说明,所以应避免直接对其进行操纵。Microsoft 提供了若干使用简便的函数,用于查询和操纵内置对象(比如,文件和注册表项)的安全描述符。下面示例说明了获取本地计算机中 Program Files 目录的所有者 SID 和 DACL 的方法。

  CLocalMemory securityDescriptor;

  PSID sid = 0;

  PACL dacl = 0;

  Helpers::CheckError(::GetNamedSecurityInfo(_T("C:Program Files"),

  SE_FILE_OBJECT,

  OWNER_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION,

  &sid,

  0, // 组

  &dacl,

  0, // sacl

  &securityDescriptor.m_ptr));

  GetNamedSecurityInfo 是一个具有多种用途的函数。它允许查询绝大多数(如果不要求全部查询的话)内置安全对象。第一个参数是要查询的对象的名称(或路径)。第二个参数指示对象的类型。本例查询的是文件系统对象。例如,若要查询注册表对象,可以将其更改为 SE_REGISTRY_KEY。下一步是使用枚举类型的参数 SECURITY_INFORMATION 指定感兴趣的信息。再后面的四个参数是分别指向安全描述符的四个主要部分的指针。这里的方便之处是,对于不感兴趣的部分,可以向相应的参数传递 0。最后一个参数是指向安全描述符本身的指针,它实际上是安全描述符的一个副本,必须使用 LocalFree 函数释放。

  还可以使用名为 SetNamedSecurityInfo 的函数来更新内置对象的安全描述符。因为此函数的工作方式与上面所述相同,所以这里不对其进行深入的剖析。

  内存管理

  在继续之前,我认为有必要讨论一下内存管理方面的内容。内存管理以及对资源的整体管理,是编写安全、可靠的代码的一个重要方面。编写内存管理代码的最佳方式就是根本不编写代码。首先需要了解将要调用的各种函数所使用的内存管理技术,然后应将这些函数包装到一个或两个类中,以确保能够在合适的时机正确清除。如果不进行这个工作,那么编写的代码将泄露资源,甚至出现更严重的情况,使程序出现漏洞,为存心不良的人访问采取了安全措施的资源提供可乘之机。

  上面介绍了 CLocalMemoryT 类模板,但没有真正说明它的用途。绝大多数与安全描述符有关的安全函数都使用了本地内存。本地内存的使用可溯源至 16 位的 Windows 操作系统,在这类操作系统中,内存管理相当复杂。目前可供使用的本地内存函数(比如,LocalAlloc 和 LocalFree)主要是用来向后兼容 16 位的应用程序,以及兼容该类应用程序将其作为部分语义的以前的 API 函数。

  为了使得处理本地内存更加容易,我编写了一个简单的类,该类用于包装本地内存指针。在重载成员选择运算符 (operator ->)时,可以将 CLocalMemoryT 看作一个具有智能的指针类。这样做是可能的,因为它是一个类模板,并且您可以通过模板参数指示所指向的内存的类型或结构。可以使用 CLocalMemoryT 创建新的本地内存块,但一般使用它附加到函数所返回的现有的内存块。然后析构函数通过调用 LocalFree 释放内存。安全函数所使用的某些数据结构是不透明的。为了能够更方便地使用这些结构,我在 CLocalMemory 头文件的末尾定义了以下类型定义。

  typedef CLocalMemoryT CLocalMemory;

  使用这些类型能够有效地管理 SECURITY_DESCRIPTOR 对象占用的内存单元,例如:

  私有安全描述符

  GetNamedSecurityInfo 和 SetNamedSecurityInfo 具有很强的处理内置对象的功能。但是对于私有对象(比如,在自己的应用程序业务逻辑中所使用的对象),它们具有什么功能呢?可以对这些函数的功能进行扩展,使其支持私有对象吗?很不幸,答案是否定的。因为每个资源(比如,文件系统或注册表)都定义了自己的保留安全描述符的方法,这些函数不可能了解查询或设置您所创建的私有对象的安全信息。万幸的是,我们有解决的方法。

  首先我们需要一种创建私有安全描述符的方法。使用 CreatePrivateObjectSecurityEx 函数

  

本文来自:http://www.linuxpk.com/30710.html

-->linux电子图书免费下载和技术讨论基地

·上一篇:电子商务经济的关键安全问题(一)

·下一篇:斩草除根—分析木马是如何编写的(三)
 
     最新更新
·注册表备份和恢复

·低级格式化的主要作用

·如何防范恶意网站

·常见文件扩展名和它们的说明

·专家:警惕骇客骗局,严守企业信息

·PGPforWindows介紹基本设定(2)

·解剖安全帐号管理器(SAM)结构

·“恶作剧之王”揭秘

·绿色警戒

·黑客反击战

·网络四大攻击方法及安全现状描述

·可攻击3种浏览器代码流于互联网

·黑客最新的兴趣点,下个目标会是谁?

·“僵尸”——垃圾邮件的主要传播源

·Lebreat蠕虫惊现3变种

·POSTFIX反病毒反垃圾Ų…

·在FreeBSD上用PHP实现在线添加FTP用户

·简单让你在FreeBSDADSL上…

·安全版本:OpenBSD入门技巧解析

·Internet连接共享上网完全攻略

·关于ADSL上网网速常识

·静态缓存和动态缓存的比较

·最友好的SQL注入防御方法

·令网站提速的7大秘方

·网络基础知识大全

·路由基本知识

·端口映射的几种实现方法

·VLAN经典诠释

·问题分析与解决——ADSL错误代码

·问题分析——关于2条E1的线路绑定


关于我们 | 联系方式 | 广告合作 | 诚聘英才 | 网站地图 | 网址大全 | 友情链接 | 免费注册

Copyright © 2004 - 2007 All Rights Reserved

来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/10763080/viewspace-970251/,如需转载,请注明出处,否则将追究法律责任。

请登录后发表评论 登录
全部评论