Question

Je suis récemment tombé sur un article qui prétend que Microsoft interdit le memcpy() fonctionner dans ses boutiques de programmation sécurisées.Je comprends les vulnérabilités inhérentes à la fonction, mais est-il nécessaire d’interdire totalement son utilisation ?

Les programmes que j'écris devraient-ils être évités memcpy() entièrement, ou simplement s'assurer qu'il est utilisé en toute sécurité ?Quelles alternatives existent qui offrent des fonctionnalités similaires mais plus sûres ?

Était-ce utile?

La solution

Microsoft fournit alternatives à memcpy et wmemcpy qui valident leurs paramètres.

memcpy_s dit : "Hmm, avant de lire cette adresse, permettez-moi de vérifier par moi-même qu'il ne s'agit pas d'un pointeur nul ;et avant d'écrire à cette adresse, je vais refaire ce test.Je comparerai également le nombre d'octets qu'il m'a été demandé de copier à la taille revendiquée de la destination ;si et seulement si l'appel réussit tous ces tests, j'effectuerai la copie.

Memcpy dit "Fargez la destination dans un registre, fourrez la source dans un registre, fourrez le compte dans un registre, effectuez des mouvements ou des mouvements." (Exemple sur les géocités, peu de temps pour ce monde: http://www.geocities.com/siliconvalley/park/3230/x86asm/asml1013.html)

Modifier:Pour un exemple dans la nature Vos désirs sont des ordres approche de memcpy, pensez à OpenSolaris, où se trouve memcpy (pour certaines configurations) défini en termes de bcopy, et bcopie (pour certaines configurations) est...

void
     33 bcopy(from, to, count)
     34 #ifdef vax
     35     unsigned char *from, *to;
     36     int count;
     37 {
     38 
     39     asm("   movc3   12(ap),*4(ap),*8(ap)");
     40 }
     41 #else
     42 #ifdef u3b      /* movblkb only works with register args */
     43     unsigned char *from, *to;
     44     int count;
     45 {
     46     asm("   movblkb %r6, %r8, %r7");
     47 }
     48 #else
     49     unsigned char *from, *to;
     50     int count;
     51 {
     52     while ((count--) > 0)
     53         *to++ = *from++;
     54 }
     55 #endif

Modifier:Merci Millie Smith !Voici ce qui se trouvait sur la page des géocités que j'ai liée ci-dessus :

MOVS

L'instruction movs est utilisée pour copier la chaîne source dans la destination (oui, copier, ne pas déplacer).Cette instruction comporte deux variantes :movsb et movsw.Le movsb ("move string byte") déplace un octet à la fois, tandis que movsw déplace deux octets à la fois.

Puisque nous souhaitons déplacer plusieurs octets à la fois, ces instructions de déplacement sont effectuées par lots en utilisant le préfixe rep.Le nombre de mouvements est spécifié par le registre CX.Voir l'exemple ci-dessous :

:
lds   si, [src]
les   di, [dest]
cld
mov   cx, 100
rep   movsb
:

Cet exemple copiera 100 octets de src vers dest.Si vous remplacez movsb par movsw, vous copiez 200 octets à la place.Si vous supprimez le préfixe rep, le registre CX n'aura aucun effet.Vous déplacerez un octet (s'il s'agit de movsb, ou de 2 octets s'il s'agit de movsw).

Autres conseils

Une scie à chaîne, si elle est utilisée correctement, est sûr. Même chose avec memcpy (). Mais dans les deux cas, si vous frappez un clou, il peut voler et vous blesser.

En bref, memcpy () est nécessaire pour le calcul de bas niveau et ne va pas disparaître, mais pour la programmation de haut niveau vous n'avez pas besoin. Il n'y a pas memcpy () en Python.

Ne pas déranger. alternatives Microsofts ne sont pas beaucoup mieux. La valeur principale est que ceux-ci provoquent votre code pour devenir à Linux non portable. Microsoft fait beaucoup plus d'argent sur le système d'exploitation qu'ils vendent à vos clients que qu'ils font sur la copie de Visual C ++ que vous avez acheté.

L'article lui-même décrit une alternative plus sûre: memcpy_s, ce qui vous oblige à préciser la longueur maximale de la cible. Lorsque ce nombre est fourni indépendamment de la quantité d'octets à copier, il agit comme une barrière pour éviter le débordement de la mémoire tampon. Bien sûr, vous pouvez abuser en donnant le même nombre à la fois.

est l'interdiction memcpy () dans mon code me faire un meilleur programmeur et mon application plus sûre ou plus simplement incompatibles? Je suis incertain, si MS veut vraiment changer quoi que ce soit ou tout simplement faire tout nouveau code C incompatible avec d'autres compilateurs. BTW. MS fait cette astuce sur de nombreuses fonctions et il est assez ennuyeux. strcpy -> strcpy_s -.> StringCchCopy

Je pense que C devrait laisser une option pour le programmeur de tirer son propre pied. gestion de la mémoire manuelle est sûre si elle est faite correctement.

Vous avez dit vous-même: "Microsoft interdit la pratique memcpy () dans ses magasins de programmation sécurisée , je comprends les vulnérabilités inhérentes à la fonction ,"

memcpy () et une pléthore d'autres fonctions standard sont connues pour causer des vulnérabilités, alors pourquoi un atelier de programmation sécurisée permettent leur utilisation lorsqu'un (quoique progressive) l'amélioration est trivial?

Sans doute, dans leurs efforts pour améliorer la sécurité de leurs propres produits, les revues de code indiqué clairement que ces fonctions étaient responsables d'une part importante des vulnérabilités, des dépassements de mémoire tampon, etc. Plutôt que de faire des emballages à usage interne seulement ils les introduits dans la bibliothèque standard et a ajouté un avertissement compilateur (pas une interdiction) au profit de tous.

Si vous utilisez des versions plus anciennes, comme C99 ou 98 C ++ ou sur Solaris, vous ne pouvez pas utiliser memcpy_s, sauf si vous avez la bibliothèque C Safe installé.

memcpy_s () est une implémentation spécifique à Microsoft qui n'existe pas sur les implémentations non-MS, y compris ANSI, avant C11, selon leurs propres normes.

Je vais laisser les choses pro-MS et anti-MS de côté, parce qu'il est hors de propos.

memmove () est une meilleure solution de toute façon car il a abordé la question de chevauchement. memmove_s () est plus robuste, mais encore une fois, que si vous êtes en C11 ou plus tard.

L'alternative est d'appeler memcpy_s

Vous êtes censé utiliser memcpy_s () à la place. Le même genre de _S versions existent pour une variété d'autres fonctions considérées comme non sécurisés.

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