17

CSIDL_COMMON_APPDATA\company\productアプリケーションのすべてのユーザーに共通のファイルを配置する場所であり、アプリケーションが変更できると考えましたが、Vista では、インストーラーによって変更されない限り、これは読み取り専用の場所です (MSDN によると - http : //msdn.microsoft.com/en-us/library/ms995853.aspx ) では、何が最適でしょうか? 場所のセキュリティ設定を変更して、CSIDL_COMMON_DOCUMENTS\company\product代わりに書き込みまたは使用を許可しますか? たぶん、3番目のオプションがありますか?

また、これに関する「公式の」マイクロソフトの推奨事項はありますか?

4

4 に答える 4

15

AppData ディレクトリの特定のサブディレクトリのセキュリティのみを変更します (これは提供したリンクからのものです)。

CSIDL_COMMON_APPDATA このフォルダーは、ユーザー固有ではないアプリケーション データに使用する必要があります。たとえば、アプリケーションは、スペル チェック辞書、クリップ アートのデータベース、またはログ ファイルを CSIDL_COMMON_APPDATA フォルダーに格納できます。この情報はローミングされず、コンピュータを使用しているすべてのユーザーが利用できます。既定では、この場所は通常の (管理者や電源を持たない) ユーザーに対して読み取り専用です。アプリケーションが通常のユーザーに CSIDL_COMMON_APPDATA のアプリケーション固有のサブディレクトリへの書き込みアクセスを要求する場合、アプリケーションは、アプリケーションのセットアップ中にそのサブディレクトリのセキュリティを明示的に変更する必要があります。変更されたセキュリティは、ベンダー アンケートに記載する必要があります。

于 2008-09-28T23:55:15.490 に答える
5

Common App Data フォルダー (CSIDL_COMMON_APPDATA) 内のすべてのユーザーに対して読み取り/書き込みアクセス許可を持つファイルとフォルダーを作成する方法を示す簡単な例を次に示します。どのユーザーもこのコードを実行して、他のすべてのユーザーにファイルとフォルダーへの書き込み許可を与えることができます。

#include <windows.h>

#include <shlobj.h>
#pragma comment(lib, "shell32.lib")

// for PathAppend
#include <Shlwapi.h>
#pragma comment(lib, "Shlwapi.lib")

#include <stdio.h>
#include <aclapi.h>
#include <tchar.h>
#pragma comment(lib, "advapi32.lib")    

#include <iostream>
#include <fstream>
using namespace std;

int _tmain(int argc, _TCHAR* argv[])
{
    DWORD dwRes, dwDisposition;
    PSID pEveryoneSID = NULL;
    PACL pACL = NULL;
    PSECURITY_DESCRIPTOR pSD = NULL;
    EXPLICIT_ACCESS ea;
    SID_IDENTIFIER_AUTHORITY SIDAuthWorld = SECURITY_WORLD_SID_AUTHORITY;
    SID_IDENTIFIER_AUTHORITY SIDAuthNT = SECURITY_NT_AUTHORITY;
    SECURITY_ATTRIBUTES sa;

    // Create a well-known SID for the Everyone group.
    if (!AllocateAndInitializeSid(&SIDAuthWorld, 1,
                     SECURITY_WORLD_RID, 0, 0, 0, 0, 0, 0, 0,
                     &pEveryoneSID))
    {
        _tprintf(_T("AllocateAndInitializeSid Error %u\n"), GetLastError());
        goto Cleanup;
    }

    // Initialize an EXPLICIT_ACCESS structure for an ACE.
    // The ACE will allow Everyone access to files & folders you create.
    ZeroMemory(&ea, sizeof(EXPLICIT_ACCESS));
    ea.grfAccessPermissions = 0xFFFFFFFF;
    ea.grfAccessMode = SET_ACCESS;

    // both folders & files will inherit this ACE
    ea.grfInheritance= CONTAINER_INHERIT_ACE|OBJECT_INHERIT_ACE;
    ea.Trustee.TrusteeForm = TRUSTEE_IS_SID;
    ea.Trustee.TrusteeType = TRUSTEE_IS_WELL_KNOWN_GROUP;
    ea.Trustee.ptstrName  = (LPTSTR) pEveryoneSID;

    // Create a new ACL that contains the new ACEs.
    dwRes = SetEntriesInAcl(1, &ea, NULL, &pACL);
    if (ERROR_SUCCESS != dwRes)
    {
        _tprintf(_T("SetEntriesInAcl Error %u\n"), GetLastError());
        goto Cleanup;
    }

    // Initialize a security descriptor.
    pSD = (PSECURITY_DESCRIPTOR) LocalAlloc(LPTR, SECURITY_DESCRIPTOR_MIN_LENGTH);
    if (NULL == pSD)
    {
        _tprintf(_T("LocalAlloc Error %u\n"), GetLastError());
        goto Cleanup;
    }

    if (!InitializeSecurityDescriptor(pSD, SECURITY_DESCRIPTOR_REVISION))
    {
        _tprintf(_T("InitializeSecurityDescriptor Error %u\n"), GetLastError());
        goto Cleanup;
    }

    // Add the ACL to the security descriptor.
    if (!SetSecurityDescriptorDacl(pSD,
            TRUE,     // bDaclPresent flag
            pACL,
            FALSE))   // not a default DACL
    {
        _tprintf(_T("SetSecurityDescriptorDacl Error %u\n"), GetLastError());
        goto Cleanup;
    }

    // Initialize a security attributes structure.
    sa.nLength = sizeof(SECURITY_ATTRIBUTES);
    sa.lpSecurityDescriptor = pSD;
    sa.bInheritHandle = FALSE;



    TCHAR szPath[MAX_PATH];

    if (SUCCEEDED(SHGetFolderPath(NULL, CSIDL_COMMON_APPDATA|CSIDL_FLAG_CREATE, NULL, 0, szPath))) 
    {
        PathAppend(szPath, TEXT("Your Shared Folder"));

        if (!CreateDirectory(szPath, &sa)
            && GetLastError() != ERROR_ALREADY_EXISTS) 
        {
            goto Cleanup;
        }

        PathAppend(szPath, TEXT("textitup.txt"));

        HANDLE hFile = CreateFile(szPath, GENERIC_READ | GENERIC_WRITE, 0, &sa, CREATE_ALWAYS, 0, 0);
        if (hFile == INVALID_HANDLE_VALUE)
            goto Cleanup;
        else
            CloseHandle(hFile);

        //TODO: do the writing
        ofstream fsOut;
        fsOut.exceptions(ios::eofbit | ios::failbit | ios::badbit);
        fsOut.open(szPath, ios::out | ios::binary | ios::trunc);

        fsOut << "Hello world!\n";
        fsOut.close();
    }

Cleanup:

    if (pEveryoneSID) 
        FreeSid(pEveryoneSID);
    if (pACL) 
        LocalFree(pACL);
    if (pSD) 
        LocalFree(pSD);

    return 0;
}
于 2011-08-21T04:53:23.883 に答える
2

この投稿はいくつかの質問に答えるかもしれないと思いますが、多くの人にとって難しい問題のようです.

どうやら、CSIDL_COMMON_DOCUMENTS は一般的な回避策を提供します。

于 2008-09-28T23:48:01.653 に答える
1

Vista/UAC のガイドラインについては、こちらを参照してください。そのページで「CSIDL」を検索すると、いくつかの「公式」の回答が見つかります。

于 2008-09-29T00:07:50.327 に答える