2010-02-15 3 views
6

Можно ли применить (и удалить) параметры политики группы Windows с помощью .NET?Как применить групповую политику Windows с помощью .NET?

Я работаю над приложением, которое должно быть временно положить машину в ограниченное киоскподобное состояние. Одной из вещей, которые мне нужно контролировать, является доступ к USB-накопителям, которые, я считаю, можно выполнять с помощью групповой политики. Я хочу, чтобы мое приложение установило политику при ее запуске и вернуло изменение при выходе из нее ... это что-то, что я могу сделать через вызовы .NET framework?

Это мои основные требования:

  • Применить параметры групповой политики при запуске моей консольного приложения.
  • Определите, когда действие пользователя будет отклонено политикой и зарегистрировано.
    • Доступ к журналу системной безопасности допустим.
  • Отменить изменение моей политики, когда приложение прекратится.
+0

Мне кажется, что запуск вашего приложения в качестве ограниченного пользователя намного безопаснее, чем запуск в качестве повышенного пользователя, который может изменять групповые политики на компьютере. – Will

+0

Согласовано, но это не работает для данного конкретного сценария. Это приложение устанавливается в системах, которые я не контролирую достаточно долго, чтобы пользователь мог выполнять некоторые действия по времени в ограниченной изолированной песочнице, а затем мое приложение удаляется. Я не могу предположить, что достаточно ограниченная учетная запись пользователя уже существует, поэтому мое желание создать среду «на лету». –

+0

Я не думаю, что вы можете изменить локальную политику через управляемый код. Это можно сделать только через IGroupPolicyObject в C \ C++ –

ответ

3

Попробуйте использовать IGroupPolicyObject

bool SetGroupPolicy(HKEY hKey, LPCTSTR subKey, LPCTSTR valueName, DWORD dwType, const BYTE* szkeyValue, DWORD dwkeyValue) 
{ 
    CoInitialize(NULL); 
    HKEY ghKey, ghSubKey, hSubKey; 
    LPDWORD flag = NULL; 
    IGroupPolicyObject *pGPO = NULL; 
    HRESULT hr = CoCreateInstance(CLSID_GroupPolicyObject, NULL, CLSCTX_ALL, IID_IGroupPolicyObject, (LPVOID*)&pGPO); 

    if(!SUCCEEDED(hr)) 
    { 
     MessageBox(NULL, L"Failed to initialize GPO", L"", S_OK); 
    } 

    if (RegCreateKeyEx(hKey, subKey, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hSubKey, flag) != ERROR_SUCCESS) 
    { 
     return false; 
     CoUninitialize(); 
    } 

    if(dwType == REG_SZ) 
    { 
     if(RegSetValueEx(hSubKey, valueName, 0, dwType, szkeyValue, strlen((char*)szkeyValue) + 1) != ERROR_SUCCESS) 
     { 
      RegCloseKey(hSubKey); 
      CoUninitialize(); 
      return false; 
     } 
    } 

    else if(dwType == REG_DWORD) 
    { 
     if(RegSetValueEx(hSubKey, valueName, 0, dwType, (BYTE*)&dwkeyValue, sizeof(dwkeyValue)) != ERROR_SUCCESS) 
     { 
      RegCloseKey(hSubKey); 
      CoUninitialize(); 
      return false; 
     } 
    } 

    if(!SUCCEEDED(hr)) 
    { 
     MessageBox(NULL, L"Failed to initialize GPO", L"", S_OK); 
     CoUninitialize(); 
     return false; 
    } 

    if(pGPO->OpenLocalMachineGPO(GPO_OPEN_LOAD_REGISTRY) != S_OK) 
    { 
     MessageBox(NULL, L"Failed to get the GPO mapping", L"", S_OK); 
     CoUninitialize(); 
     return false; 
    } 

    if(pGPO->GetRegistryKey(GPO_SECTION_USER,&ghKey) != S_OK) 
    { 
     MessageBox(NULL, L"Failed to get the root key", L"", S_OK); 
     CoUninitialize(); 
     return false; 
    } 

    if(RegCreateKeyEx(ghKey, subKey, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &ghSubKey, flag) != ERROR_SUCCESS) 
    { 
     RegCloseKey(ghKey); 
     MessageBox(NULL, L"Cannot create key", L"", S_OK); 
     CoUninitialize(); 
     return false; 
    } 

    if(dwType == REG_SZ) 
    { 
     if(RegSetValueEx(ghSubKey, valueName, 0, dwType, szkeyValue, strlen((char*)szkeyValue) + 1) != ERROR_SUCCESS) 
     { 
      RegCloseKey(ghKey); 
      RegCloseKey(ghSubKey); 
      MessageBox(NULL, L"Cannot create sub key", L"", S_OK); 
      CoUninitialize(); 
      return false; 
     } 
    } 

    else if(dwType == REG_DWORD) 
    { 
     if(RegSetValueEx(ghSubKey, valueName, 0, dwType, (BYTE*)&dwkeyValue, sizeof(dwkeyValue)) != ERROR_SUCCESS) 
     { 
      RegCloseKey(ghKey); 
      RegCloseKey(ghSubKey); 
      MessageBox(NULL, L"Cannot set value", L"", S_OK); 
      CoUninitialize(); 
      return false; 
     } 
    } 

    if(pGPO->Save(false, true, const_cast<GUID*>(&EXTENSION_GUID), const_cast<GUID*>(&CLSID_GPESnapIn)) != S_OK) 
    { 
     RegCloseKey(ghKey); 
     RegCloseKey(ghSubKey); 
     MessageBox(NULL, L"Save failed", L"", S_OK); 
     CoUninitialize(); 
     return false; 
    } 

    pGPO->Release(); 
    RegCloseKey(ghKey); 
    RegCloseKey(ghSubKey); 
    CoUninitialize(); 
    return true; 
} 

Вы можете вызывать эту функцию, как это ..

// Remove the Log Off in start menu 
SetGroupPolicy(HKEY_CURRENT_USER, 
    L"Software\\Microsoft\\Windows\\CurrentVersion\\Policies\\Explorer", 
    L"StartMenuLogOff", REG_DWORD, NULL, 1); 
+0

Спасибо за ответ. К сожалению, я искал что-то в C#, хотя я, вероятно, должен был это указать. Хотя это мне не помогает, я отмечаю это как правильный ответ, потому что это лучший ответ на вопрос, который я действительно спросил, и, скорее всего, помогу кому-то найти подобное решение. –

+0

Каковы будут значения HKEY_CURRENT_USER ?? и REG_DWORD? Например? – Danilo

+0

@ SethPetry-Johnson Какими будут значения HKEY_CURRENT_USER ?? и REG_DWORD? Например? – Danilo

0

Я не играл с ним сам, но System.Security.Policy выглядит так, что это может быть интересной отправной точкой.

разместил Re-ссылка по запросу: Group Policy access via Registry

+1

System.Security.Policy, похоже, связана с безопасностью доступа к CLR-коду, что не является тем, что мне нужно. Спасибо хоть! –

+0

Хм, ты прав. Как насчет этого - похоже, что нет удобного объекта .NET для создания GP объектов, но эта ссылка [http: //www.devx.com/dotnet/Article/34784/1763/page/5] рассказывает о том, как это сделать через реестр (который, в конце концов, там, где на самом деле живет GP). Это ASP.NET, но это может быть способ ... –

+0

Это выглядит несколько обнадеживающим, хотя я надеюсь, что только что добавленная щедрость поможет мне найти более прямой ответ. Не могли бы вы повторно опубликовать эту ссылку в качестве нового ответа? Таким образом, если лучшего ответа не будет предоставлено, вы получите награду, когда она истечет. –

2

Заканчивать www.sdmsoftware.com/group_policy_scripting. Это не бесплатно, но сделает то, что вам нужно.

+0

Спасибо за ссылку. К сожалению, это _looks_ дорого (обычно это когда вам нужно связаться с продавцом для цитаты) и, вероятно, слишком велико для моих потребностей в этом проекте. Но вы правы, он, похоже, делает то, что я просил :) –

3

Примечание: Я использую две ссылки GroupPolicy сборки: C: \ Windows \ Assembly \ GAC_MSIL \ Microsoft .GroupPolicy.Management \ 2.0.0.0__31bf3856ad364e35 \ Microsoft.GroupPolicy.Management.dll и C: \ Windows \ assembly \ GAC_32 \ Microsoft.GroupPolicy.Management.Interop \ 2.0.0.0__31bf3856ad364e35 \ Microsoft.Grou pPolicy.Management.Interop.dll Эта структура 2.0, поэтому есть смешанный код, и вы должны использовать app.config: http://msmvps.com/blogs/rfennell/archive/2010/03/27/mixed-mode-assembly-is-built-against-version-v2-0-50727-error-using-net-4-development-web-server.aspx

Я сделал это так.

using System.Collections.ObjectModel; 
using Microsoft.GroupPolicy; 
using Microsoft.Win32; 

/// <summary> 
/// Change user's registry policy 
/// </summary> 
/// <param name="gpoName">The name of Group Policy Object(DisplayName)</param> 
/// <param name="keyPath">Is KeyPath(like string [email protected]"Software\Microsoft\Windows\CurrentVersion\Policies\Explorer")</param> 
/// <param name="typeOfKey">DWord, ExpandString,... e.t.c </param> 
/// <param name="parameterName">Name of parameter</param> 
/// <param name="value">Value</param> 
/// <returns>result: true\false</returns> 
public bool ChangePolicyUser(string gpoName, string keyPath, RegistryValueKind typeOfKey, string parameterName, object value) 
    { 
     try 
     { 
      RegistrySetting newSetting = new PolicyRegistrySetting(); 
      newSetting.Hive = RegistryHive.CurrentUser; 
      newSetting.KeyPath = keyPath; 
      bool contains = false; 
      //newSetting.SetValue(parameterName, value, typeOfKey); 
      switch (typeOfKey) 
      { 
       case RegistryValueKind.String: 
        newSetting.SetValue(parameterName, (string)value, typeOfKey); 
        break; 
       case RegistryValueKind.ExpandString: 
        newSetting.SetValue(parameterName, (string)value, typeOfKey); 
        break; 
       case RegistryValueKind.DWord: 
        newSetting.SetValue(parameterName, (Int32)value); 
        break; 
       case RegistryValueKind.QWord: 
        newSetting.SetValue(parameterName, (Int64)value); 
        break; 
       case RegistryValueKind.Binary: 
        newSetting.SetValue(parameterName, (byte[])value); 
        break; 
       case RegistryValueKind.MultiString: 
        newSetting.SetValue(parameterName, (string[])value, typeOfKey); 
        break; 
      } 
      Gpo gpoTarget = _gpDomain.GetGpo(gpoName); 
      RegistryPolicy registry = gpoTarget.User.Policy.GetRegistry(false); 
      try 
      { 
       ReadOnlyCollection<RegistryItem> items = gpoTarget.User.Policy.GetRegistry(false).Read(newSetting.Hive, keyPath); 
       foreach (RegistryItem item in items) 
       { 
        if (((RegistrySetting) item).ValueName == parameterName) 
        { 
         contains = true; 
        } 
       } 
       registry.Write((PolicyRegistrySetting) newSetting, !contains); 
       registry.Save(false); 
       return true; 
      } 
      catch (ArgumentException) 
      { 
       registry.Write((PolicyRegistrySetting)newSetting, contains); 
       registry.Save(true); 
       return true; 
      } 
     } 
     catch (Exception) 
     { 
      return false; 
     } 
    } 
Смежные вопросы