Saturday 11 March 2017

Gethrforexception Ioexception When Try

J'ai un code IO qui lit un flux dans un try..catch. Il attrape IOException et appelle System. Runtime. InteropServices. Marshal. GetHRForException () dans le catch, dans une tentative de prendre différentes actions basées sur le HResult. Quelque chose comme ceci: Mais en exécutant ce code dans ASP avec trustmedium, j'obtiens cette exception: Quelques questions: Je pense que l'exception se produit car GetHRForException appelle dans le code non géré, ce qui n'est pas permis dans la confiance moyenne. Correct Cette exception est lancée, pas au moment de l'exécution de GetHRForException, mais au moment où la méthode est JITed Correct (Le stacktrace montre ma méthode, mais je suis certain qu'une exception IO n'a pas eu lieu). Si oui, Est il un moyen pour moi de varier le comportement dans un environnement de confiance partielle, de sorte que je n'appelez pas le GetHRForException (code non géré) où il n'est pas permis En d'autres termes, comment puis je permettre au JIT de réussir à la compilation, Évaluer au moment de l'exécution si le code doit appeler GetHRForException () quelque chose comme ceci: Je pense qu'il ya un mécanisme d'exécution pour tester si les autorisations sont disponibles, mais havent été en mesure de le trouver. MODIFIER . Est cet article de blog la réponse ShawnFa de Microsoft dit que vous ne pouvez pas faire un essai. Catch (SecurityException) autour d'une méthode protégée par un LinkDemand. Si MethodA () appelle MethodB () et MethodB () est marqué avec LinkDemand pour la confiance totale, puis le LinkDemand est vérifié avec MethodA est Jited. Par conséquent, pour éviter la SecurityException, je dois extraire Marshal. GetHRForException dans une méthode distincte. Est ce correct Appliqué à mon code, MethodA () pourrait être le code qui appelle Read, et puis dans le catch essaie d'appeler GetHRForException (). GetHRForException est MethodB (). Le LinkDemand est évalué lorsque MethodA () est JITd. (Ce LinkDemand échoue dans mon scénario ASP à moyenne confiance). Si je déplace la GetHRForException dans une nouvelle méthode, MethodC (), et conditionnellement appeler MethodC () seulement après un imperatif permission. Demand () réussit, théoriquement je devrais être capable d'éviter la SecurityException à JIT time, parce que MethodC () JITd seulement après la permission. Demain () réussit. Demandé Jul 12 09 at 14:20 La méthode requise est SecurityPermission. IsUnrestricted (). Il retourne un vrai ou un faux indiquant si l'autorisation est autorisée ou non. Il n'exige pas une autorisation, comme le fait SecurityPermission. Demand (). J'utilise IsUnresticted avec SecurityPermissionFlag. UnmanagedCode pour voir si l'assembly est autorisé à appeler le code non géré et puis appelez le code non géré uniquement si autorisé. Il ya une autre torsion. Le compilateur JIT, lors de la compilation d'une méthode, vérifie le CodeAccessPermission LinkDemands sur toute méthode appelée my la méthode à compiler. Marshal. GetHRForException () est marqué avec un LinkDemand. Par conséquent, ma méthode qui appelle Marshal. GetHRForException () va lancer une exception SecurityException uncatchable au moment de la compilation JIT, lorsqu'elle est exécutée dans un environnement restreint, comme ASP avec confiance moyenne. Par conséquent, nous ne devons jamais JIT la méthode qui appelle Marshal. GetHRForException () dans ce cas, ce qui signifie que j'ai besoin de sortir Marshal. GetHRForException () dans une méthode distincte dans mon code qui est appelé (et donc JITted) seulement lorsque UnmanagedCode est libre. Voici un exemple de code: répondu Jul 20 09 at 17:56 Oui la confiance moyenne ne permettra pas les appels dans le code non géré. Le seul niveau de confiance qui le permet est la pleine confiance. Ça dépend. Les demandes CAS peuvent avoir lieu à l'exécution, mais l'environnement d'hébergement peut également se déplacer et chercher des choses qu'il ne peut pas faire. Vous pouvez tester pour voir si vous pouvez faire un appel au code non géré en utilisant une demande CAS avec une instance de SecurityPermission. Le code pour faire une demande CAS ressemble à ceci a répondu Jul 12 09 at 14:32 OK, c'est une excellente info. Cela couvre la partie b du Q3. Mais que dire de la partie a Comment puis je obtenir la compilation JIT pour réussir Puis je marquer ma méthode avec un attribut de sécurité ou. Rappelez vous, ma théorie est que l'erreur SecurityPermission ne se produit pas à l'exécution, il se passe pendant JIT et je pense que vous avez confirmé que c'est possible. La question est donc de savoir comment écrire le code pour permettre au JIT de compiler. Ndash Cheeso Jul 12 09 at 15:50 Cela devrait se produire au moment de l'exécution, sinon l'assemblage ne serait même pas chargé et pour que cela se produise, l'assemblage doit être marqué comme nécessitant l'autorisation. Même alors cela pourrait être un contrôle d'exécution, car il se produira sur la charge d'assemblage, ce qui pourrait être à l'exécution. Ndash blowdart Jul 12 09 at 16:24 Différent type de contrôle, les exigences de lien sont des attributs sur une méthode, et sont effectivement vérifiés à JIT temps. Il est assez utilisé par le cadre lui même et il est rare de le voir en dehors de la source CLR. Ce que je démontre est une demande impérative, pas un déclaratif comme un SecurityPermission (SecurityAction. LinkDemand, Unrestricted true) ndash blowdart Jul 12 09 à 18: 55Putting It All Together Les sections précédentes ont décrit comment construire l'essai. capture. Et enfin les blocs de code pour la méthode writeList dans la classe ListOfNumbers. Maintenant, let's marcher à travers le code et d'enquêter sur ce qui peut arriver. Lorsque tous les composants sont assemblés, la méthode writeList ressemble à ce qui suit. Comme mentionné précédemment, ce bloc de try de méthode a trois possibilités de sortie différentes ici sont deux d'entre eux. Code dans l'instruction try échoue et lance une exception. Cela peut être une exception IOException provoquée par la nouvelle instruction FileWriter ou une exception IndexOutOfBoundsException causée par une valeur d'index erronée dans la boucle for. Tout réussit et l'instruction try quitte normalement. Examinons ce qui se passe dans la méthode writeList pendant ces deux possibilités de sortie. Scénario 1: une exception se produit L'instruction qui crée un FileWriter peut échouer pour un certain nombre de raisons. Par exemple, le constructeur de FileWriter lance une exception IOException si le programme ne peut pas créer ou écrire dans le fichier indiqué. Lorsque FileWriter lève une exception IOException. Le système d'exécution interrompt immédiatement l'exécution de la méthode du bloc try Les appels en cours d'exécution ne sont pas terminés. Le système d'exécution commence alors la recherche en haut de la pile d'appels de méthode pour un gestionnaire d'exceptions approprié. Dans cet exemple, lorsque l'IOException se produit, le constructeur FileWriter se trouve en haut de la pile d'appels. Toutefois, le constructeur FileWriter n'a pas de gestionnaire d'exceptions approprié, donc le système d'exécution vérifie la méthode suivante 151 la méthode writeList 151 dans la pile d'appels de méthode. La méthode writeList a deux gestionnaires d'exception: un pour IOException et un pour IndexOutOfBoundsException. Le système d'exécution vérifie les gestionnaires writeList 39 dans l'ordre dans lequel ils apparaissent après l'instruction try. L'argument au premier gestionnaire d'exception est IndexOutOfBoundsException. Cela ne correspond pas au type d'exception lancée, de sorte que le système d'exécution vérifie le gestionnaire d'exceptions suivant 151 IOException. Cela correspond au type d'exception qui a été lancé, de sorte que le système d'exécution termine sa recherche d'un gestionnaire d'exceptions approprié. Maintenant que le runtime a trouvé un gestionnaire approprié, le code dans ce bloc catch est exécuté. Une fois le gestionnaire d'exception exécuté, le système d'exécution passe le contrôle au bloc finally. Code dans le bloc finally s'exécute indépendamment de l'exception pris au dessus. Dans ce scénario, FileWriter n'a jamais été ouvert et ne doit pas être fermé. Une fois le bloc final terminé, le programme continue avec la première instruction après le bloc finally. Voici la sortie complète du programme ListOfNumbers qui s'affiche lorsqu'une exception IOException est lancée. Scénario 2: Le bloc d'essai quitte normalement Dans ce scénario, toutes les instructions comprises dans la portée du bloc try s'exécutent avec succès et ne lancent aucune exception. L'exécution tombe à la fin du bloc try et le système d'exécution passe le contrôle au bloc finally. Parce que tout a réussi, le PrintWriter est ouvert lorsque le contrôle atteint le bloc finally, qui ferme le PrintWriter. Encore une fois, après que le bloc final termine l'exécution, le programme continue avec la première instruction après le bloc finally. Voici la sortie du programme ListOfNumbers quand aucune exception n'est déclenchée. Le code gras dans l'exemple suivant montre les instructions qui sont exécutées pendant ce scénario.


No comments:

Post a Comment