命名内核对象有一种问题:任何程序都可以创建一个命名对象,这样如果某个程序要实现单例运行而创建了一个内核对象,这种情况下另一程序也创建了同名的内核对象时,该单例程序就无法正常运行了。这是DoS攻击的一种。

 

Vista中有一种机制使得用户创建的命名内核对象永远不会和其它程序创建的对象冲突,要使用定制的前缀并把它作为人的私有命名空间,如GlobalLocal,服务进程会确保为内核对象定义一边界描述符来保护命名空间。
下面是检查实例的代码:

None.gifvoid CheckInstances() 
ExpandedBlockStart.gifContractedBlock.gifdot.gif{//检查实例
InBlock.gif   // Create the boundary descriptor
InBlock.gif   g_hBoundary = CreateBoundaryDescriptor(g_szBoundary, 0);
InBlock.gif
InBlock.gif   // Create a SID corresponding to the Local Administrator group
InBlock.gif   BYTE localAdminSID[SECURITY_MAX_SID_SIZE];
InBlock.gif   PSID pLocalAdminSID = &localAdminSID;
InBlock.gif   DWORD cbSID = sizeof(localAdminSID);
InBlock.gif   if (!CreateWellKnownSid(
InBlock.gif      WinBuiltinAdministratorsSid, NULL, pLocalAdminSID, &cbSID)
ExpandedSubBlockStart.gifContractedSubBlock.gif      ) dot.gif{
InBlock.gif      AddText(TEXT("AddSIDToBoundaryDescriptor failed: %u\r\n"), 
InBlock.gif         GetLastError());
InBlock.gif      return;
ExpandedSubBlockEnd.gif   }
InBlock.gif   
InBlock.gif   // Associate the Local Admin SID to the boundary descriptor
InBlock.gif   // --> only applications running under an administrator user
InBlock.gif   //     will be able to access the kernel objects in the same namespace
ExpandedSubBlockStart.gifContractedSubBlock.gif   if (!AddSIDToBoundaryDescriptor(&g_hBoundary, pLocalAdminSID)) dot.gif{
InBlock.gif      AddText(TEXT("AddSIDToBoundaryDescriptor failed: %u\r\n"), 
InBlock.gif         GetLastError());
InBlock.gif      return;
ExpandedSubBlockEnd.gif   }
InBlock.gif
InBlock.gif   // Create the namespace for Local Administrators only
InBlock.gif   SECURITY_ATTRIBUTES sa;
InBlock.gif   sa.nLength = sizeof(sa);
InBlock.gif   sa.bInheritHandle = FALSE;
InBlock.gif   if (!ConvertStringSecurityDescriptorToSecurityDescriptor(
InBlock.gif      TEXT("D:(A;;GA;;;BA)"), 
ExpandedSubBlockStart.gifContractedSubBlock.gif      SDDL_REVISION_1, &sa.lpSecurityDescriptor, NULL)) dot.gif{
InBlock.gif      AddText(TEXT("Security Descriptor creation failed: %u\r\n"), GetLastError());
InBlock.gif      return;
ExpandedSubBlockEnd.gif   }
InBlock.gif
InBlock.gif   g_hNamespace = 
InBlock.gif      CreatePrivateNamespace(&sa, g_hBoundary, g_szNamespace);
InBlock.gif
InBlock.gif   // Don't forget to release memory for the security descriptor
InBlock.gif   LocalFree(sa.lpSecurityDescriptor);
InBlock.gif
InBlock.gif
InBlock.gif   // Check the private namespace creation result
InBlock.gif   DWORD dwLastError = GetLastError();
InBlock.gif   if (g_hNamespace == NULL) 
ExpandedSubBlockStart.gifContractedSubBlock.gif   dot.gif{
InBlock.gif      // Nothing to do if access is denied
InBlock.gif      // --> this code must run under a Local Administrator account
InBlock.gif      if (dwLastError == ERROR_ACCESS_DENIED) 
ExpandedSubBlockStart.gifContractedSubBlock.gif      dot.gif{
InBlock.gif         AddText(TEXT("Access denied when creating the namespace.\r\n"));
InBlock.gif         AddText(TEXT("   You must be running as Administrator.\r\n\r\n"));
InBlock.gif         return;
ExpandedSubBlockEnd.gif      }
InBlock.gif      else 
ExpandedSubBlockStart.gifContractedSubBlock.gif      dot.gif
InBlock.gif         if (dwLastError == ERROR_ALREADY_EXISTS) 
ExpandedSubBlockStart.gifContractedSubBlock.gif         dot.gif{
InBlock.gif         // If another instance has already created the namespace, 
InBlock.gif         // we need to open it instead. 
InBlock.gif            AddText(TEXT("CreatePrivateNamespace failed: %u\r\n"), dwLastError);
InBlock.gif            g_hNamespace = OpenPrivateNamespace(g_hBoundary, g_szNamespace);
InBlock.gif            if (g_hNamespace == NULL) 
ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
InBlock.gif               AddText(TEXT("   and OpenPrivateNamespace failed: %u\r\n"), 
InBlock.gif               dwLastError);
InBlock.gif               return;
ExpandedSubBlockEnd.gif            } 
InBlock.gif            else 
ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
InBlock.gif               g_bNamespaceOpened = TRUE;
InBlock.gif               AddText(TEXT("   but OpenPrivateNamespace succeeded\r\n\r\n"));
ExpandedSubBlockEnd.gif            }
ExpandedSubBlockEnd.gif         } 
InBlock.gif         else
ExpandedSubBlockStart.gifContractedSubBlock.gif         dot.gif{
InBlock.gif            AddText(TEXT("Unexpected error occured: %u\r\n\r\n"),dwLastError);
InBlock.gif            return;
ExpandedSubBlockEnd.gif         }
ExpandedSubBlockEnd.gif      }
ExpandedSubBlockEnd.gif   }
InBlock.gif   
InBlock.gif   // Try to create the mutex object with a name 
InBlock.gif   // based on the private namespace 
InBlock.gif   TCHAR szMutexName[64];
InBlock.gif   StringCchPrintf(szMutexName, _countof(szMutexName), TEXT("%s\\%s"), g_szNamespace, TEXT("Singleton"));
InBlock.gif
InBlock.gif   g_hSingleton = CreateMutex(NULL, FALSE, szMutexName);//创建互斥量
InBlock.gif   if (GetLastError() == ERROR_ALREADY_EXISTS) 
ExpandedSubBlockStart.gifContractedSubBlock.gif   dot.gif{
InBlock.gif      // There is already an instance of this Singleton object
InBlock.gif      AddText(TEXT("Another instance of Singleton is running:\r\n"));
InBlock.gif      AddText(TEXT("--> Impossible to access application features.\r\n"));
ExpandedSubBlockEnd.gif   }
InBlock.gif   else  
ExpandedSubBlockStart.gifContractedSubBlock.gif   dot.gif{
InBlock.gif      // First time the Singleton object is created
InBlock.gif      AddText(TEXT("First instance of Singleton:\r\n"));
InBlock.gif      AddText(TEXT("--> Access application features now.\r\n"));
ExpandedSubBlockEnd.gif   }
ExpandedBlockEnd.gif}
None.gif
None.gif
None.gif

 

ExpandedBlockStart.gifContractedBlock.gifvoid AddText(PCTSTR pszFormat, dot.gifdot.gif{
InBlock.gif
InBlock.gif   va_list argList;
InBlock.gif   va_start(argList, pszFormat);
InBlock.gif
InBlock.gif   TCHAR sz[20 * 1024];
InBlock.gif
InBlock.gif   Edit_GetText(DETAILS_CTRL, sz, _countof(sz));
InBlock.gif   _vstprintf_s(
InBlock.gif      _tcschr(sz, TEXT('\0')), _countof(sz) - _tcslen(sz), 
InBlock.gif      pszFormat, argList);
InBlock.gif   Edit_SetText(DETAILS_CTRL, sz);
InBlock.gif   va_end(argList);
ExpandedBlockEnd.gif}
None.gif