Extraktion von Icon aus einer Exe-Datei - nicht abfangbare Exception

  • VB.NET
  • .NET (FX) 4.5–4.8

Es gibt 20 Antworten in diesem Thema. Der letzte Beitrag () ist von VaporiZed.

    Extraktion von Icon aus einer Exe-Datei - nicht abfangbare Exception

    Hallo zusammen,

    mit folgendem Code zur Extraktion von Icons aus einer Exe-Datei erhalte ich in Zeile#24 die im Anhang befindliche NullReferenceExeption und ich weiß weder, warum, noch, wie ich sie abfangen oder gar verhindern kann. Vielleicht könnt Ihr mir die Augen öffnen.

    VB.NET-Quellcode

    1. Imports System.Runtime.InteropServices
    2. Friend Class FrmMain
    3. <DllImport("User32.dll", CharSet:=CharSet.Unicode)> Private Shared Function PrivateExtractIcons(IconPath As String, IconIndex As Integer, Width As Integer, Height As Integer, phicon As IntPtr(), ByRef piconid As IntPtr, IconCount As Integer, flags As Integer) As Integer : End Function
    4. <DllImport("Shell32.dll", EntryPoint:="ExtractIcon", SetLastError:=True)> Shared Function ExtractIcon(IconHandle As IntPtr, IconPath As String, IconIndex As Integer) As Integer : End Function
    5. <DllImport("user32.dll", EntryPoint:="DestroyIcon", SetLastError:=True)> Shared Function DestroyIcon(IconHandle As IntPtr) As Integer : End Function
    6. Private Sub FrmMain_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    7. Me.TransparencyKey = Color.Wheat
    8. BackColor = Me.TransparencyKey
    9. ExtractIconsFrom("C:\Program Files\Mozilla Firefox\Firefox.exe")
    10. End Sub
    11. Private Sub ExtractIconsFrom(FilePath As String)
    12. Dim IconCount = ExtractIcon(IntPtr.Zero, FilePath, -1)
    13. For Each ItemSize In {512, 256, 128, 64}
    14. Dim HIcon(IconCount - 1) As IntPtr
    15. Dim ActualIconCount = PrivateExtractIcons(FilePath, 0, ItemSize, ItemSize, HIcon, IntPtr.Zero, HIcon.Count, 0)
    16. For i = 0 To ActualIconCount - 1
    17. Try
    18. If HIcon Is Nothing Then Stop
    19. If HIcon(i) = IntPtr.Zero Then Stop
    20. FlowLayoutPanel1.Controls.Add(New PictureBox With {.Width = ItemSize + 10, .Height = ItemSize + 10, .Image = Icon.FromHandle(HIcon(i)).ToBitmap})
    21. Catch NREx As NullReferenceException
    22. Exit For
    23. End Try
    24. Next
    25. HIcon.ToList.ForEach(Sub(x) DestroyIcon(x))
    26. Exit For
    27. Next
    28. End Sub
    29. End Class
    Bilder
    • NullReferenceException.png

      33,68 kB, 768×301, 38 mal angesehen
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.

    VaporiZed schrieb:

    Dim ActualIconCount = PrivateExtractIcons(FilePath, 0, ItemSize, ItemSize, HIcon, IntPtr.Zero, HIcon.Count, 0)
    Machma aus HIcon.Count => HIcon.Length.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Das Ergebnis bleibt damit leider gleich.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Merkwürdig, ich hatte es ein Mal, nun geht es wieder nicht. :/
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Damit bekomm ich zwar das gewünschte Ergebnis, erklärt mir aber noch nicht die Ursprungsproblematik.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Das ist den Zeilen#10 und #11 geschuldet. Ich will mit dem ganzen Unterfangen eigentlich die Transparenzfähigkeit von WinForms testen bzw. den Darstellungsfehler isolieren, der sich bei teiltransparenten Icons ergibt, wenn man sie extrahiert und in einer PicBox darstellt:
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „VaporiZed“ ()

    @Haudruferzappeltnoch: Du bist offensichtlich in einer .NET-App unterwegs, ich in einer .NET-Fx, entsprechend den Thread-Angaben.
    @-Franky-: Das mag stimmen. Aber selbst wenn ich die ExtractIcon-Funktion weglasse und manuell drei Icons extrahieren will, passiert das.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Jo Framework, krieg ich das auch hin.
    Man kann HIcon auch gar nicht debuggen nach Ausführung von Zeile 19. Vorher sieht man leeres Array, danach zeigt er nix mehr an.

    Ich glaube in PrivatExtractIcons wird eine Exception ausgelöst, die wir nicht sehen.
    Das verhält sich ähnlich zu einem Nothing-Phänomen, das ich habe. Nur kann ich da tatsächlich sehen wie die Referenz nach einer nicht im Zusammenhang stehenden Exception Nothing wird.

    Und auch hier funktioniert alles bei einer anderen Exe. Ich kann dann auch nach Zeile 19 in HIcon reingucken.
    Mein Guess: Die Exception aus Zeile 19 korumpiert HIcon, das stört den Code erstmal nicht, nur das Studio. Deswegen wird der Test HIcon IsNot Nothing bestanden.
    Dann kommt die zweite Exception in Zeile 24, die nicht aufgelöst werden kann, weil dann das Studio über HIcon meckert. Also eine Exception beim Feststellen einer Exception?

    Dieser Beitrag wurde bereits 6 mal editiert, zuletzt von „Haudruferzappeltnoch“ ()

    VaporiZed schrieb:

    Vielleicht könnt Ihr mir die Augen öffnen.


    Das hoffe ich doch 8o . Wirf das Byref in der Signatur von PrivateExtractIcons für den Parameter piconid weg, in der Doku steht zwar OUT-Optional, aber Out bedeuted nicht Byref.

    Du kannst das aber auch so mit dem Out-Attribute machen meine ich, aber kannste auch einfach weglassen,

    VB.NET-Quellcode

    1. <Out> phicon As IntPtr(),
    2. <Out> piconid As IntPtr,

    Zitat von mir 2023:
    Was interessiert mich Rechtschreibung? Der Compiler wird meckern wenn nötig :D

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „DTF“ ()

    Jou, danke. Das hat geholfen.

    ##########

    Eine endgültige Erklärung für das Fehlverhalten (also nicht der Signaturfehler, sondern das Exception-Nichtabfangen) ist immer noch nicht da, aber ich vermute, dass @Haudruferzappeltnoch recht haben könnte. TryCatch-Blöcke können vielleicht nicht alle Sachen abfangen. Exceptions aus anderen Threads muss man ja auch anders angehen als normale.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „VaporiZed“ ()

    Ich sehe sowas nicht zum ersten mal. Als ich mir mit COM-Interfaces Dialoge für WPF gemacht hatte, da hatte ich auch einen Fehler in der Signatur und ich hatte nochmal alle Funktions-Dokus zu studieren. Hier in dem Fall wird wohl Speicher überschrieben oder versucht, denn mit ByRef für den Parameter piconid sind alle Werte im HIcon-Array 0, anstatt gültige "Zeiger".

    VaporiZed schrieb:

    Damit bekomm ich zwar das gewünschte Ergebnis, erklärt mir aber noch nicht die Ursprungsproblematik.


    So aus dem Explorer gestartet gings bei dir? Also mit NET 8 schmiert mir das Programm ab. Hast du die richtige EXE probiert?

    Ich kann mir aber auch vorstellen, das MS absichtlich abbricht um einer möglichen Attacke vorzubeugen. So lässt sich u.U. ein Verhalten erzwingen, das mit normalen Code nicht möglich wäre. Denn wenn ich Byref verwendet hab, waren all Einträge imm Hicon-Array 0. Es gibt durchaus Situationen wo man abzubrechen hat, hatte mal so meine "Spielchen" mit dem Kernel probiert, wurde direkt mit BSODs quittiert.
    Zitat von mir 2023:
    Was interessiert mich Rechtschreibung? Der Compiler wird meckern wenn nötig :D

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „DTF“ ()

    DTF schrieb:

    So aus dem Explorer gestartet gings bei dir? Also mit NET 8 schmiert mir das Programm ab.
    Ja und ich stimme Dir zu. In .NET schmiert mir die EXE ab, in .NET-Fx 4.8 nicht. Da läuft sie durch und ignoriert den Fehler.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Das sollte funktionieren, egal ob .Net-Fx oder .Net.

    Bin mir aber nicht sicher, ob da das extrahieren verschiedener Grössen möglich ist.

    EDIT: @DTF
    Genau den meinte ich. Danke.


    C#-Quellcode

    1. public partial class SIM : Form
    2. {
    3. private Icon IconEdge;
    4. public SIM()
    5. {
    6. this. InitializeComponent();
    7. var strfile = "C:\\Program Files (x86)\\Microsoft\\Edge\\Application\\msedge.exe";
    8. this.IconEdge = Icon.ExtractAssociatedIcon(strfile)!;
    9. this.IconEdge = Icon.ExtractIcon(strfile,0,64)!; //ODER DENN
    10. this.pictureBox1.Image = this.IconEdge.ToBitmap();
    11. }
    12. }


    Freundliche Grüsse

    exc-jdbi

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „exc-jdbi“ ()

    exc-jdbi schrieb:

    ob da das extrahieren verschiedener Grössen möglich ist.


    Mit ExtractAssociatedIcon nein, mit
    Icon.ExtractIcon(String, Int32, Boolean)
    learn.microsoft.com/de-de/dotn…stem-int32-system-boolean)

    und mit dieser überladung, ja.
    Icon.ExtractIcon(String, Int32, Int32)
    learn.microsoft.com/de-de/dotn…system-int32-system-int32)
    Zitat von mir 2023:
    Was interessiert mich Rechtschreibung? Der Compiler wird meckern wenn nötig :D
    Hi @VaporiZed,

    gibt es einen Grund, dass Du in Zeile 23:

    VB.NET-Quellcode

    1. If HIcon Is Nothing Then Stop

    gesetzt hast, und nicht:

    VB.NET-Quellcode

    1. If HIcon(i) Is Nothing Then Stop

    M.E. ist die Variable Hicon nirgendwo definiert und generiert daher die Null-Exception.
    Oder habe ich da einen Denkfehler?

    Beste Grüsse