Du bist nicht angemeldet.

Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!

Werbeanzeige

BurningWave

Alter Hase

  • »BurningWave« ist der Autor dieses Themas

Beiträge: 1 106

Wohnort: Filderstadt/Konstanz

Beruf: Student

  • Private Nachricht senden

1

09.11.2010, 21:03

Environment-Variablen setzen bzw. Administratorrechte zum Setzen erhalten [WinAPI]

Hallo,

mein Programm "Sound Maker" (Programm zum Komponieren von elektronischer Musik mit Csound), von dem ich hier im Forum schon berichtet habe, ist endlich fast fertig (90 - 95%). Jedoch habe ich ein Problem: Mein Programm soll Csound Quelltext erzeugen und anschließend den Csound-Compiler aufrufen, der Sounddateien erstellt. Jedoch benötigt der Compiler eine Umgebungsvariable, die ich manuell setzen muss, damit er seine DLLs alle findet. Ich habe den Befehl SetEnvironmentVariable() gefunden, der unter Windows XP funktioniert. Mit diesem Befehl kann man eine Umgebungsvariable für den aktuellen Prozess und untergeordnete Prozesse setzen (der Compiler ist doch untergeordnet, wenn ich ihn mit ShellExecuteEx() aufrufe und das Handle des Hauptprozesses übergebe oder?). Jedoch zeigt der Befehl unter Windows 7 keine Wirkung, der Compiler findet seine Dateien trotzdem nicht.
Also habe ich mir einen neuen Weg überlegt: Ich schreibe die Variable einfach direkt in die Registry. Das funktioniert auch soweit, jedoch benötige ich dafür Administratorrechte. Das wäre ja eigentlich kein Problem, wenn der UAC-Dialog mit der Frage, ob man Administratorrechte gewähren will erscheinen würde, jedoch schlägt die Funktion RegSetValueEx() einfach fehl, wenn man das Programm nicht mit Administratorrechten startet.

Meine Fragen sind jetzt:
1. Warum funktioniert SetEnvironmentVariable() unter XP, aber nicht unter Windows 7? (Das ist eigentlich meine bevorzugte Lösung, da sie einfacher und benutzerfreundlicher ist.)
2. Wie kann ich diesen UAC-Dialog öffnen, um nach Administratorrechten zu fragen, bzw. herausfinden, ob das Programm bereits Administratorrechte besitzt (ich habe mit Google irgendwas über irgendwelche Manifeste gefunden, jedoch konnte ich nichts damit anfangen)?
3. Warum liefert RegOpenKeyEx(), selbst wenn der gewünschte Key nicht existiert, ERROR_SUCCESS zurück (ich habe eigentlich gedacht, dass ich mit der Funktion u.a. abfragen kann, ob ein bestimmter Key existiert)?

Hier ist mein Quelltext:

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
    int iTmp = FindCharReverse(ParamStr(0), "\\");
    SetCurrentDirectory(ParamStr(0).Delete(iTmp+1, ParamStr(0).Length() - iTmp).c_str());

    HKEY hKey;
    if(RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Control\\Session Manager\\Environment", NULL, KEY_READ, &hKey) != ERROR_SUCCESS)
    {
        DWORD dwDisposition;
        if(RegCreateKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Control\\Session Manager\\Environment", NULL, NULL, REG_OPTION_NON_VOLATILE, KEY_ALL_ACCESS, NULL, &hKey, &dwDisposition) != ERROR_SUCCESS)
            err("Fehler beim Erstellen einer benötigten Umgebungsvariablen.", __FILE__, __LINE__, ERR_FAILED);
        else
        {
            AnsiString sOpcodePath = ParamStr(0).Delete(iTmp+1, ParamStr(0).Length() - iTmp) + "bin\\plugins";
            if(RegSetValueEx(hKey, "OPCODEDIR", NULL, REG_EXPAND_SZ, sOpcodePath.c_str(), sOpcodePath.Length() * sizeof(char)) != ERROR_SUCCESS)
                err("Fehler beim Setzen der benötigten Umgebungsvariablen.\n\nManche Instrumente werden evtl. nicht funktionieren.", __FILE__, __LINE__, ERR_FAILED);
            else
            {
                RegCloseKey(hKey);
                PostMessage(HWND_BROADCAST, WM_SETTINGCHANGE, NULL, (LPARAM)("Environment"));
            }
        }
    }
    else
        RegCloseKey(hKey);


Ich hoffe ihr könnt mir helfen.
MfG BurningWave

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

2

09.11.2010, 21:40

Schau mal nach was genau SetEnvironmentVariable() für einen Fehler liefert (Rückgabewert + GetLastError()). Um Administratorrechte zu verlangen musst du nur in den Linkereinstellungen unter Manifest File das Flag UAC Execution Level auf requireAdministrator setzen. Wenn du das so lösen willst könntest du das aber auch vielleicht einfach nur einmal beim Setup machen!? Ich würde als Nutzer eine Lösung die nur temporär die EnvVars für den aktuellen Prozess verändert allerdings sicherlich bevorzugen.

BurningWave

Alter Hase

  • »BurningWave« ist der Autor dieses Themas

Beiträge: 1 106

Wohnort: Filderstadt/Konstanz

Beruf: Student

  • Private Nachricht senden

3

09.11.2010, 23:02

Das Problem scheint sich gerade in Luft aufgelöst zu haben. Ich habe alles neu erstellt und nun scheint SetEnvironmentVariable() zu funktionieren (GetLastError meldet auch keinen Fehler).

Mich würden Antworten auf meine Fragen aber für die Zukunft trotzdem interessieren.

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

4

09.11.2010, 23:24

Nun Frage 1 hat sich ja erledigt, Frage 2 hab ich oben schon beantwortet und was Frage 3 angeht vermute ich mal dass das an der UAC liegt...

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »dot« (09.11.2010, 23:32)


BurningWave

Alter Hase

  • »BurningWave« ist der Autor dieses Themas

Beiträge: 1 106

Wohnort: Filderstadt/Konstanz

Beruf: Student

  • Private Nachricht senden

5

10.11.2010, 12:06

Ja ich habe das was die UAC angeht nochmal überdacht. Ich habe nur zuerst nicht verstanden, wie das gemeint war.

Danke für die Hilfe.

Werbeanzeige