通过


安全注意事项:Microsoft Windows Shell

本主题提供有关与 Windows Shell 相关的安全注意事项的信息。 本文档无法提供有关安全问题的全部信息,而是将其用作此特定技术领域的起点和参考。

Shell 控制系统的一些重要方面,包括一些在未正确处理时存在潜在安全风险的方面。 本主题概述了一些更常见问题以及如何在应用程序中解决这些问题。 请记住,安全性不限于基于 Internet 的攻击。 在共享系统上(包括可通过终端服务访问的系统)上,还必须确保用户无法执行可能损害共享系统的其他人员的任何操作。

正确安装应用程序

大多数潜在的 Shell 安全问题可以通过正确安装应用程序来缓解。

  • 在 Program Files 文件夹下安装应用程序。

    操作系统 位置
    Windows XP、Windows Server 2003 及更早版本 CSIDL_PROGRAM_FILES
    Windows Vista及更高版本 FOLDERID_ProgramFiles、FOLDERID_ProgramFilesX86、FOLDERID_ProgramFilesX64、FOLDERID_ProgramFilesCommon、FOLDERID_ProgramFilesCommonX86或FOLDERID_ProgramFilesCommonX64。 有关详细信息,请参阅 KNOWNFOLDERID

     

  • 不要将用户数据存储在 Program Files 文件夹下。

    对所有用户通用的数据使用适当的数据文件夹。

    操作系统 位置
    Windows XP、Windows Server 2003 及更早版本 CSIDL_COMMON_APPDATA
    Windows Vista及更高版本 FOLDERID_ProgramData

     

    对属于特定用户的数据使用适当的用户数据文件夹。

    操作系统 位置
    Windows XP、Windows Server 2003 及更早版本 CSIDL_APPDATA、CSIDL_PERSONAL等。
    Windows Vista及更高版本 FOLDERID_RoamingAppData、FOLDERID_Documents等。

     

  • 如果必须安装到 Program Files 文件夹以外的位置,请确保正确设置访问控制列表(ACL),以便用户无权访问文件系统的不适当部分。 特定于特定用户的任何数据都应具有 ACL,该 ACL 可阻止任何其他用户访问它。

  • 设置文件关联时,请务必正确指定命令行。 使用完全限定的路径,并将包含空格的任何元素包装在引号中。 用单独的引号包装命令参数。 否则,字符串可能无法正确分析,并且应用程序无法正确启动。 此处显示了两个正确格式的命令行示例。

    "C:\Program Files\MyApp\MyApp.exe" "%1" "%2"
    C:\MyAppDir\MyApp\MyApp.exe "%1"
    

注释

标准安装文件夹的位置可能因系统而异。 若要获取特定Windows Vista或更高版本系统上标准文件夹的位置,< 请使用相应的 KNOWNFOLDERID>c1><>SHGetKnownFolderPath 调用 KNOWNFOLDERID 值。 在 Windows XP、Windows Server 2003 或更早的系统中, call SHGetFolderLocationSHGetFolder 具有相应CSIDL值的Path

 

Shlwapi

Shell 轻型 API (Shlwapi) 包括许多字符串操作函数。 错误地使用这些函数可能会导致意外截断的字符串,且未返回截断通知。 在以下情况下,不应使用 Shlwapi 函数。 应在其位置使用列出的替代函数,从而带来更少的风险。

Shlwapi 函数 备用函数
StrCatStrNCat StringCchCatStringCbCat 和相关函数
StrCpyStrCpyN StringCchCopyStringCbCopy 和相关函数
wnsprintfwvnsprintf StringCchPrintfStringCbPrintf 和相关函数

 

使用返回文件路径 的 PathRelativePathTo 等函数,始终将缓冲区的大小设置为MAX_PATH个字符。 这样做可确保缓冲区足够大,可以容纳最大可能的文件路径,以及终止 null 字符。

有关备用字符串函数的详细信息,请参阅 About Strsafe.h

自动完成

不要将“自动完成”功能用于密码。

可以使用多个 Shell 函数来启动应用程序: ShellExecuteShellExecuteExWinExecSHCreateProcessAsUserW。 请确保提供要执行的应用程序的明确定义。

  • 提供可执行文件的路径时,请提供完全限定的路径。 不依赖于 Shell 来查找文件。
  • 如果提供包含空格的命令行字符串,请用引号包装字符串。 否则,分析程序可能会将包含空格的单个元素解释为多个元素。

移动和复制文件

系统安全的一个密钥是正确分配 ACL。 还可以使用加密的文件。 请确保移动或复制文件时,会为其分配正确的 ACL,并且它们未被意外解密。 这包括将文件移动到 回收站,以及文件系统内部。 使用 IFileOperation (Windows Vista 或更高版本) 或 SHFileOperation (Windows XP 及更早版本)。 请勿使用 MoveFile,这可能不会为目标文件设置预期的 ACL。

编写安全命名空间扩展

Shell 命名空间扩展是向用户呈现数据的一种强大且灵活的方法。 但是,如果未正确写入系统故障,它们可能会导致系统故障。 要记住的一些要点:

  • 不要假定图像等数据的格式正确。
  • 不要假定MAX_PATH相当于字符串中的 字节 数。 它是 字符数。

安全警报

下表列出了某些功能(如果使用错误)会损害应用程序的安全性。

功能 缓解措施
ShellExecuteShellExecuteEx 根据检查一系列默认位置来查找特定文件的搜索可用于欺骗攻击。 使用完全限定的路径来确保访问所需的文件。
StrCat 第一个参数 psz1 必须足够大才能容纳 psz2 和结束“\0”,否则可能会出现缓冲区溢出。 请改用以下替代方法之一。 StringCbCatStringCbCatExStringCbCatNStringCbCatNExStringCchCatExStringCchCatNStringCchCatNEx
StrCatBuff 不能保证最终字符串以 null 结尾。 请改用以下替代方法之一。 StringCbCatStringCbCatExStringCbCatNStringCbCatNExStringCchCatExStringCchCatNStringCchCatNEx
StrCatChainW 不能保证最终字符串以 null 结尾。 请改用以下替代方法之一。 StringCbCatExStringCbCatNExStringCchCatExStringCchCatNEx
StrCpy 第一个参数 psz1 必须足够大才能容纳 psz2 和结束“\0”,否则可能会出现缓冲区溢出。 请改用以下替代方法之一。 StringCbCopyStringCbCopyExStringCbCopyNStringCbCopyNExStringCchCopyStringCchCopyEx、StringCchCopyNStringCchCopyNEx
StrCpyN 无法保证复制的字符串以 null 结尾。 请改用以下替代方法之一。 StringCbCopyStringCbCopyExStringCbCopyNStringCbCopyNExStringCchCopyStringCchCopyEx、StringCchCopyNStringCchCopyNEx
StrDup StrDup 假定 lpsz 是一个以 null 结尾的字符串。 此外,不保证返回的字符串以 null 结尾。 请改用以下替代方法之一。 StringCbCatStringCbCopyExStringCbCopyNStringCbCopyNExStringCchCopyStringCchCopyEx、StringCchCopyNStringCchCopyNEx
StrNCat 第一个参数 pszFront 必须足够大才能保存 pszBack 和结束“\0”,否则可能会出现缓冲区溢出。 请注意,最后一个参数 cchMax 是要复制到 pszFront 中的字符数,不一定 是 pszFront 的大小(以字节为单位)。 请改用以下替代方法之一。 StringCbCatStringCbCatExStringCbCatNStringCbCatNExStringCchCatExStringCchCatNStringCchCatNEx
wnsprintf 无法保证复制的字符串以 null 结尾。 请改用以下替代方法之一。 StringCbPrintfStringCbPrintfExStringCbVPrintf、StringCbVPrintfExStringCchPrintf、StringCchPrintfExStringCchVPrintfStringCchVPrintfEx
wvnsprintf 无法保证复制的字符串以 null 结尾。 请改用以下替代方法之一。 StringCbPrintfStringCbPrintfExStringCbVPrintf、StringCbVPrintfExStringCchPrintf、StringCchPrintfExStringCchVPrintfStringCchVPrintfEx

 

Microsoft 安全

安全开发人员中心

Microsoft解决方案加速器

安全技术中心

关于 Strsafe.h