IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Windows Presentation Foundation Discussion :

[WPF] Problème de sécurité pour appel d'une fonction COM


Sujet :

Windows Presentation Foundation

  1. #1
    Membre à l'essai
    Inscrit en
    Mai 2007
    Messages
    32
    Détails du profil
    Informations forums :
    Inscription : Mai 2007
    Messages : 32
    Points : 22
    Points
    22
    Par défaut [WPF] Problème de sécurité pour appel d'une fonction COM
    Salut

    Je suis actuellement en train de faire des recherches pour trouver le code le plus rapide afin de créer des miniatures ou de charger des images en WPF et j'ai trouvé le top : l'utilisation de gdiplus.dll et notamment de la méthode GdipLoadImageFromFile.

    En faisant des tests avec une appli Winforms en C# (.Net 2.0), l'appel de la méthode COM fonctionne nickel. Pour exemple, je charge un objet System.Drawing.Image à partir de l'url d'un fichier en 146 ms avec la méthode classique Image.FromFile, alors qu'avec la méthode COM je mets environ 2 ms !!! Le gain est énorme....mais je n'arrive pas à faire fonctionner la même méthode en WPF.

    En fait, l'utilisation de cette dll (gdiplus) ou du moins cette méthode semble nécessiter des attributs ou une certaine config pour un projet WPF.

    Voici la méthode, trouvée sur le net d'ailleurs, puisque j'ai du mal à comprendre comment on utilise COM :


    [DllImport("gdiplus.dll", CharSet = CharSet.Unicode), SuppressUnmanagedCodeSecurity]
    public static extern int GdipLoadImageFromFile(string filename, out IntPtr image);

    private static Type imageType = typeof(Bitmap);

    [SecurityPermission(SecurityAction.Demand, Flags = SecurityPermissionFlag.UnmanagedCode)]
    internal static Image FastFromFile(string filename)
    {
    try
    {
    filename = Path.GetFullPath(filename);
    IntPtr loadingImage = IntPtr.Zero;

    // We are not using ICM at all, fudge that, this should be FAAAAAST!
    if (GdipLoadImageFromFile(filename, out loadingImage) != 0)
    {
    throw new Exception("GDI+ threw a status error code.");
    }

    return (Bitmap)imageType.InvokeMember("FromGDIplus", BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.InvokeMethod, null, null, new object[] { loadingImage });
    }
    catch (SecurityException)
    {
    return Image.FromFile(filename);
    }
    }

    Lorsque j'appelle la méthode FastFromFile, j'obtiens sous WPF l'erreur suivante :

    {System.AccessViolationException: Tentative de lecture ou d'écriture de mémoire protégée. Cela indique souvent qu'une autre mémoire est endommagée.

    Il semble que les attributs SuppressUnmanagedCodeSecurity et SecurityPermission soient insuffisants...j'ai essayé diverses configurations dans les propriétés de mon projet ( ClickOnce, zone full trust...) mais sans résultat...


    Le pire, c'est que le try/catch de la méthode FastFromFile ne joue pas son rôle, puisque l'erreur est remontée directement à ma méthode appelante de ma Form...sûrement dû au fait que ce soit du non-managé j'imagine...

    Quelqu'un a une idée ou une vision globale de la sécurité des applications sous WPF ?

    Merci à vous
    Bye

  2. #2
    Rédacteur
    Avatar de Thomas Lebrun
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    9 161
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 9 161
    Points : 19 434
    Points
    19 434
    Par défaut
    Je suis impressionné par le gain de rapidité Ce serait à mettre dans la FAQ ce genre de chose.....

    Sinon, tu as essayé d'enlever l'attribut:
    [SecurityPermission(SecurityAction.Demand, Flags = SecurityPermissionFlag.UnmanagedCode)]

    ?

  3. #3
    Membre à l'essai
    Inscrit en
    Mai 2007
    Messages
    32
    Détails du profil
    Informations forums :
    Inscription : Mai 2007
    Messages : 32
    Points : 22
    Points
    22
    Par défaut
    Oui, j'ai essayé sans l'attribut.

    J'ai également essayé de mettre les mêmes attributs ou certains similaires sur mes déclarations de classe et sur mes méthodes appelantes, toujours pareil...

    Au début, j'avais mis tout ça dans une des classes d'une librairie que j'appelais via mon projet WPF, mais cela ne fonctionnant pas, j'ai essayé de tout mettre d'un bloc dans un projet à part uniquement WPF, dans le code de ma Form, et ça ne donne toujours rien...

  4. #4
    Rédacteur
    Avatar de Thomas Lebrun
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    9 161
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 9 161
    Points : 19 434
    Points
    19 434
    Par défaut
    Je viens de tester et j'ai en effet le même problème

    Je vais essayer de chercher de mon coté

  5. #5
    Rédacteur
    Avatar de Thomas Lebrun
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    9 161
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 9 161
    Points : 19 434
    Points
    19 434
    Par défaut
    Bon bah j'ai trouvé

    Change ton code pour y rajouter cette ligne:

    Bitmap b = new Bitmap(500, 500);

    Ce qui donne:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
     
    [DllImport("gdiplus.dll", CharSet = CharSet.Unicode), SuppressUnmanagedCodeSecurity]
            public static extern int GdipLoadImageFromFile(string filename, out IntPtr image);
     
            private static Type imageType = typeof(Bitmap);
     
            [SecurityPermission(SecurityAction.Demand, Flags = SecurityPermissionFlag.UnmanagedCode)]
            internal static System.Drawing.Image FastFromFile(string filename)
            {
                try
                {
                    Bitmap b = new Bitmap(500, 500);
     
                    filename = System.IO.Path.GetFullPath(filename);
                    IntPtr loadingImage = IntPtr.Zero;
     
                    // We are not using ICM at all, fudge that, this should be FAAAAAST!
                    if (GdipLoadImageFromFile(filename, out loadingImage) != 0)
                    {
                        throw new Exception("GDI+ threw a status error code.");
                    }
     
                    return (Bitmap)imageType.InvokeMember("FromGDIplus", BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.InvokeMethod, null, null, new object[] { loadingImage });
                }
                catch (SecurityException)
                {
                    return System.Drawing.Image.FromFile(filename);
                }
            }
    Et là, cela fonctionne. La réponse vient de la:
    http://weblogs.asp.net/justin_rogers...13/131664.aspx

    Ou bien tu charges un Bitmap en mémoire, ou bien tu appelles toi-même GdiplusStartup et GdiplusShutdown



    A+

  6. #6
    Membre à l'essai
    Inscrit en
    Mai 2007
    Messages
    32
    Détails du profil
    Informations forums :
    Inscription : Mai 2007
    Messages : 32
    Points : 22
    Points
    22
    Par défaut
    Ouaahaaa...super tordu le truc

    Merci pour ton coup de main, j'vais pouvoir appliquer ça au taf

    Par curiosité, t'as tapé quoi comme recherche pour trouver ça ? J'ai trop galéré cet aprèm. J'ai failli faire une appli à part en mode console ou autre en 2.0 et faire le transfert des thumbnails via Remoting...heureusement que t'es là

    Sinon tu as pu remarquer le gain en rapidité sur l'ouverture de l'image ?

    ++

  7. #7
    Rédacteur
    Avatar de Thomas Lebrun
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    9 161
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 9 161
    Points : 19 434
    Points
    19 434
    Par défaut
    J'ai juste tapé GdipLoadImageFromFile et c'était dans les 1er résultats

    Sinon oui, je viens de faire le test:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
    Stopwatch sw = new Stopwatch();
                sw.Start();
     
                System.Drawing.Image img = FastFromFile("Creek.jpg");
     
                Console.WriteLine(sw.ElapsedMilliseconds.ToString());
                sw.Reset();
                sw.Start();
     
                System.Drawing.Image img2 = System.Drawing.Image.FromFile("Creek.jpg");
     
                Console.WriteLine(sw.ElapsedMilliseconds.ToString());
    Et j'obtiens des résultats impressionnants:
    6
    56
    2
    60
    3
    62
    En même temps, c'est du natif donc encore heureux que ce soit plus performant


    A+

    PS: Demain, si c'est résolu, pense à mettre le tag Résolu stp

  8. #8
    Membre à l'essai
    Inscrit en
    Mai 2007
    Messages
    32
    Détails du profil
    Informations forums :
    Inscription : Mai 2007
    Messages : 32
    Points : 22
    Points
    22
    Par défaut
    ça marche nickel, il me faut maintenant trouver le moyen le plus rapide pour générer une miniature et la stocker dans une base SQLite.

    Allez, au boulot !

    Ciao

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [XL-2000] Problème lors de l'appel d'une fonction
    Par juju05 dans le forum Macros et VBA Excel
    Réponses: 6
    Dernier message: 17/02/2014, 13h18
  2. Problème lors de l'appel d'une fonction
    Par FATENMRABET dans le forum Général Java
    Réponses: 4
    Dernier message: 19/09/2013, 13h55
  3. Problème lors de l'appel d'une fonction Tsql
    Par mobscene dans le forum MS SQL Server
    Réponses: 3
    Dernier message: 23/07/2007, 15h56
  4. [MySQL] problème lors de l'appel d'une fonction
    Par jexl dans le forum PHP & Base de données
    Réponses: 5
    Dernier message: 27/06/2007, 09h53
  5. [POO] Problème lors de l'appel d'une propriété d'un objet.
    Par akecoocoo dans le forum Général JavaScript
    Réponses: 3
    Dernier message: 24/08/2005, 08h51

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo