Question

Je comprends les pointeurs et le besoin rare de les utiliser en code C #. Ma question est la suivante: quel est le raisonnement qui sous-tend le fait de déclarer explicitement "dangereux" dans un bloc de code. De plus, pourquoi une option du compilateur doit-elle être modifiée pour autoriser "non sécurisé"? code?

Résultat inférieur: Ce que le CLR (ou les spécifications de langage) permet de ne pas utiliser de pointeur à tout moment (comme le C et C ++) sans devoir taper "non sécurisé" et changer l'option du compilateur?

Pour plus de précision, je sais ce que "non sûr". et " safe " le code est. C'est juste une question de pourquoi nous devons faire tout le travail supplémentaire (ok, pas tant que ça en plus) juste pour pouvoir utiliser ces fonctionnalités.

Était-ce utile?

La solution

Une interview du créateur de C #, Anders Hejlsberg, aborde le sujet. ici . Fondamentalement, exactement ce que @Marc Gravell a dit: la sécurité typographique en premier, l'insécurité par déclaration explicite.

Donc, pour répondre à votre question, rien dans le CLR ne l’empêche; C'est un idiome de langage conçu pour vous permettre de travailler avec des gants de protection lorsque vous traitez avec des types. Si vous souhaitez retirer les gants, c'est votre choix, mais vous devez faire le choix actif de les retirer.

Modifier:

  

Pour clarification: je sais quoi   " unsafe " et " safe " le code est. C'est juste   une question de pourquoi devons-nous faire tous les   travail supplémentaire (ok, pas beaucoup supplémentaire)   juste pour pouvoir utiliser ces fonctionnalités.

Comme mentionné dans l'entretien que j'ai lié, il s'agissait d'une décision de conception explicite. C # est essentiellement une évolution de Java et en Java, vous n’avez pas de pointeur du tout. Mais les concepteurs ont voulu autoriser les pointeurs. Toutefois, étant donné que C # faisait généralement appel à des développeurs Java, ils estimaient qu'il serait préférable que le comportement par défaut soit similaire à Java, c'est-à-dire sans pointeur, tout en permettant l'utilisation de pointeurs par déclaration explicite.

Donc, le "travail supplémentaire" est délibéré pour vous obliger à penser à ce que vous faites avant de le faire. En étant explicite, cela vous oblige au moins à considérer: "Pourquoi est-ce que je fais cela?" Dois-je vraiment avoir besoin d'un pointeur lorsqu'un type de référence suffit? "

Autres conseils

Il s'agit en grande partie d'être vérifiable. En indiquant non sécurisé , les gants sont désactivés - le système ne peut plus garantir que votre code ne fonctionnera pas de façon démesurée. Dans la plupart des cas, il est hautement souhaitable de rester dans la zone de sécurité.

Cela devient plus visible avec une confiance partielle (addins, etc.), mais reste valable dans le code habituel.

En réalité, le CLR n’exige aucune obligation en ce qui concerne un commutateur / mot clé / unsafe. En fait, C ++ / CLI (le langage C ++ qui s'exécute sous le CLR) n'a pas de commutateur de ce type / non sécurisé, et les pointeurs peuvent être utilisés librement sur le CLR.

Je reformulerais donc votre question comme suit: "Pourquoi C # requiert-il l’utilisation de / unsafe avant que les pointeurs puissent être utilisés?" Et la réponse à cette question est comme indiqué dans d'autres réponses données ici: aider l'utilisateur à prendre une décision consciente de perdre la capacité de fonctionner en mode autre que Full Trust sur le CLR. C ++ requiert pratiquement toujours une confiance totale sur le CLR, et C # peut chaque fois que vous appelez un code nécessitant une confiance totale ou chaque fois que vous utilisez des pointeurs.

Lorsque vous utilisez un bloc dangereux, il a pour effet de rendre le code invérifiable. Cela nécessite certaines autorisations pour pouvoir s'exécuter et vous ne voudrez peut-être pas l'autoriser dans votre sortie (surtout si vous êtes dans un environnement source partagé), il y a donc un commutateur dans le compilateur pour l'interdire.

Pensez-y du point de vue opposé: comme le code n'est pas marqué comme dangereux, vous pouvez en déduire que la plupart du code est "sûr". par défaut. Alors, qu'est-ce que cela signifie d'être "sûr"? Pour le code .Net, cela inclut (sans toutefois s'y limiter):

  • Le ramasse-miettes peut faire les choses comme d'habitude.
  • Les références à un type spécifique feront référence à des objets de ce type (ou null).
  • Il est garanti que le code est conforme aux exigences de confiance / sécurité .Net.
  • Il est mathématiquement prouvé que le code ne touche pas directement la mémoire en dehors de son propre AppDomain. Cela peut sembler trivial, mais imaginez si vous avez plusieurs domaines d’application dans la même application. Le programmeur peut en toute confiance les traiter comme des entités logiquement distinctes.

Chaque fois que vous utilisez des pointeurs, vous avez la possibilité de casser l’une de ces garanties. Par conséquent, le fait de marquer le code comme non sûr abandonne ces protections.

En bref, .NET souhaite que vous énonçiez votre intention.

Bien sûr, le compilateur pourrait en déduire la nécessité du code "non sécurisé". drapeau. Mais les concepteurs veulent que ce soit une décision délibérée.

Pour moi, cela ressemble à un certain nombre d'exigences syntaxiques en C #:

  • pas de boîtier de commutateur sans pause
  • pas de niveau d'accès " sections " (comme le marqueur "public:" en C ++)
  • aucun champ de classe utilisant "var" ni

En règle générale, vous ne devez ni déplacer ni changer une chose et en affecter par inadvertance une autre. Dans les limites du raisonnable, ils veulent vous empêcher de vous tirer une balle dans le pied.

Beaucoup de bonnes réponses informatives ici & # 8212; peut-être que cela va plus à votre question.

De sorte qu'il soit immédiatement évident quel code ne fonctionnera pas dans les services Web sans autorisations élevées, etc.

Cultiver de bonnes habitudes & amp; Sécurité. Chaque fois que vous utilisez un bloc non sécurisé dans un assemblage, une autorisation NativeCode sera demandée à la pile. Cela pourrait bien sûr être fait implicitement, mais ne pourrions-nous pas aussi simplement supprimer complètement le mot-clé privé? Je pense qu'il est bon d'obliger les développeurs à exiger spécifiquement du code non sécurisé avant de pouvoir l'utiliser.

La différence la plus significative entre le code sûr et le code non sécurisé réside dans le fait que le code non sécurisé est inaccessible par le ramasse-miettes de .net. GC automatique est une partie importante de la langue vernaculaire de .net et, lorsque vous dépassez ses limites, vous modifiez en grande partie ce que vous pouvez supposer à propos de votre code.

Les pointeurs permettent en particulier de créer des objets sur le tas sans références au catalogue global. Cela conduit à une autre excellente raison pour exiger que le code soit marqué comme "non sécurisé". Il est facile de déterminer l’origine d’une fuite de mémoire lorsque vous réalisez que vous en avez une.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top