Gegen Internetzensur
Stoppt die Vorratsdatenspeicherung! Jetzt klicken & handeln!Willst du auch bei der Aktion teilnehmen? Hier findest du alle relevanten Infos und Materialien:
  • Flickr Photos

    www.flickr.com
22. Jan
Don

Mal eben in die DirectX.Capture-Library getaucht und nach nicht ganz ner Minute nen ersten Erfolg verbucht.

QuickCam Pro 9000 in C# via DirectX.Capture Library

Da krieg ich ja direkt wieder Hoffnung, dass das mit der Bildverarbeitung doch noch klappt.

31. Jul
Don

Seit einiger Zeit ärgere ich mich mit Vistas „User Account Control“-Berechtigungsmechanismus herum, insbesondere mit der Frage, ob es möglich ist, Berechtigungen für eine bestimmte Anfrage anzufordern. Grundsätzlich scheint der Tenor zu sein: Nein, geht nicht. Berechtigungen gibt es entweder für den gesamten Prozess – und zwar beim Start – oder gar nicht.

Eine Möglichkeit in den Genuss erhöhter Berechtigungen zu kommen ist das Manifest einer Anwendung. In Visual Studio 2008 lässt sich ein solches „Application Manifest File“ recht locker zum Projekt hinzufügen (es wird dann auch in den Projekteinstellungen als Manifest angewählt“. Um z.B. immer mit vollen Berechtigungen zu fahren – d.h., den Benutzer bei jedem Programmstart einen Bestätigungsklick abzufordern – kann man folgendes Manifest vergeben:

  1. <trustinfo xmlns="urn:schemas-microsoft-com:asm.v2">
  2.     <security>
  3.       <requestedprivileges xmlns="urn:schemas-microsoft-com:asm.v3">
  4.         <requestedexecutionlevel level="requireAdministrator" uiAccess="false"></requestedexecutionlevel>
  5.       </requestedprivileges>
  6.     </security>
  7.   </trustinfo>

Der Knackpunkt ist hier requireAdministrator: „Administratorrechte sind (immer) nötig“. Als absolutes Minimum unter Vista sollte IMHO immer asInvoker gesetzt sein, d.h.: „Starte das Programm mit den Rechten des aufrufenden Benutzers“. Egal wie: Nur anhand dieses Manifestes erkennt Vista, dass ein Programm sich mit den Gepflogenheiten der neuen Umgebung Vista auskennt und wendet Technologien wie die Ordnervirtualisierung nicht an. Das führt dazu, dass Zugriffe auf Order wie C:\Program Files nicht nach C:\users\...xyz...\AppData\Local\VirtualStore\Program Files virtualisiert werden, sondern einfach mit einer UnauthorizedAccessException fehlschlagen.

Mehr zu den Manifesten etwa hier auf CodeProject.

Um zu testen, ob eine Anwendung mit erhöhten Privilegien läuft oder um sie mit eben solchen (erneut) zu starten (und wie man solche niedlichen „Schild“-Buttons hinbekommt), zeigt dieser Artikel auf CodeProject.

Das ist die Zusammenfassung:

  1. static internal bool IsElevated()
  2. {
  3.         WindowsIdentity id = WindowsIdentity.GetCurrent();
  4.         WindowsPrincipal p = new WindowsPrincipal(id);
  5.         return p.IsInRole(WindowsBuiltInRole.Administrator);
  6. }

… testet, ob die Anwendung mit vollen Administratorrechten läuft (und folglich Zugriff auf alle Ressourcen hat, die nicht durch Codesicherheitsrichtlinien eingeschränkt sind) und …

  1. ProcessStartInfo startInfo = new ProcessStartInfo();
  2. startInfo.UseShellExecute = true;
  3. startInfo.WorkingDirectory = Environment.CurrentDirectory;
  4. startInfo.FileName = Assembly.GetExecutingAssembly().Location;
  5. startInfo.Verb = "runas";
  6. try
  7. {
  8.         Process p = Process.Start(startInfo);
  9.         // Erfolg; Diesen Prozess können wir nun beenden
  10.         // Application.Exit() o.ä.
  11. }
  12. catch (System.ComponentModel.Win32Exception ex)
  13. {
  14.         // Benutzer hat abgebrochen
  15. }

… startet den Prozess als Administrator neu (Rückfrage unter Vista) bzw. springt in den catch-Block, wenn der Benutzer die erhöhten Rechte verweigerte.

Weiterhin lässt sich sagen, dass ein Prozess, der mit erhöhten Privilegien läuft, diese auch an alle Prozesse weiterreicht, die von ihm gestartet werden. Würde man denselben Process.Start()-Code also aus einem „elevated“-Prozess heraus starten, bliebe die Nachfrage aus.

Wer will, kann mit dem folgenden Testprogramm ja mal etwas herumspielen – es ist nur eben nötig, ein entsprechendes Manifest zu setzen. Ich habe für diesen Zweck "asInvoker" gewählt, um prinzipiell im Benutzermodus zu starten, es sei denn, das Programm wurde explizit als Admin aufgerufen.

Zum Download: C# Vista Permission Test (ZIP)
Und zum Lesen: Weiterlesen »

22. Mai
Don

Ich weiß gar nicht, wieso ich mir früher so einen Stress gemacht habe.
Für bestimmte Klassen oder Strukturen ist es nötig, Relationsoperatoren zu implementieren. Nehmen wir das klassische Beispiel einer Struktur, die eine komplexe Zahl darstellt. Diese hat einen Real- und einen Imaginäranteil, aber weil sie eben kein primitiver Typ ist (z.B. eine Zahl), weiß das System auch nicht, wie man sie verrechnen, geschweige denn vergleichen soll – woher auch?

Für den Relationstest gibt es typischerweise sechs Operatoren: ==, !=, < , < =, > und >=. Im Falle einer komplexen Zahl ist die Geschäftslogik dahinter noch sehr überschaubar, aber wenn es einmal komplizierter wird, kann das auch unter Zuhilfenahme von Dr. Copy und Mr. Paste schon anstrengend werden.

Man kommt allerdings auch mit nur zwei sauber implementierten Operatoren aus, die restlichen vier lassen sich dann mit einfachen Kombinationen daraus abbilden. Folgende Überlegung dazu: Weiterlesen »

17. Mai
Sam

Manchmal möchte man testen, ob ein (erst) zur Laufzeit bekanntes Objekt ein bestimmtes Interface implementiert. Die Type-Klasse bietet hierfür die Funktion FindInterfaces(), die allerdings unter Umständen etwas mehr Overhead darstellt, als eigentlich nötig ist. Wenn man das Problem häufiger hat, ist hier ein Ansatz, um den Aufwand zu verringern. Es ist eine Implementierung als Extension Method und setzt daher Framework 3.5 oder einen kleinen Kniff voraus; Es ist allerdings auch nicht weiter schwierig, es als normale, statische Funktion zu implementieren – einfach das this in der Parameterliste entfernen.

  1. [DebuggerStepThrough]
  2. public static bool HasInterface(this Type type, Type interfaceType)
  3. {
  4.     Type[] array = type.FindInterfaces(
  5.         delegate(Type typeObj, Object criteriaObj)
  6.         {
  7.             return typeObj.Equals((Type)criteriaObj);
  8.         },
  9.         interfaceType
  10.     );
  11.     return array.Length > 0;
  12. }

Beispiel zur Anwendung:

  1. // als Extension Method
  2. bool hasInterface = myVariable.GetType().HasInterface(typeof(ISomeInterface));
  3.  
  4. // als normale, statische Methode
  5. bool hasInterface = HasInterface(myVariable.GetType(), typeof(ISomeInterface));

Der Vergleich wird platzsparend in Form einer anonymen Funktion (die delegate) durchgeführt, das [DebuggerStepThrough]-Attribut sorgt dafür, dass der Debugger die Funktion nicht besucht, wenn man Step Into benutzt – spart Zeit und Nerven.

Weiterlesen »

6. Mrz
Don

Grad auf dem Postweg bekommen:

<piercings> A programmer started to cuss
<piercings> Because getting to sleep was a fuss
<piercings> As he lay there in bed
<piercings> Looping 'round in his head
<piercings> was: while(!asleep()) sheep++;

oh oh … random flash …

  1. lock( brain ) {
  2.     if( brain.ProviderIsEmbarassed ) {
  3.         brain.EmbarassingMemories.Deqeue();
  4.         brain.InitiateAsyncBodyRollAction( BodyRollActionType.Alternating );
  5.         return;
  6.     }
  7.     Idea i = IdeaFactory.GetIdea();
  8.     if( idea != null ) {
  9.         brain.Enqeue( idea );
  10.     }
  11. }

Is mir langweilig oder was?