• STATISTIQUES
  • Il y a eu un total de 2 membres et 14817 visiteurs sur le site dans les dernières 24h pour un total de 14 819 personnes!


    Membres: 2 433
    Discussions: 3 585
    Messages: 32 832
    Tutoriels: 78
    Téléchargements: 38
    Sites dans l'annuaire: 58


  • ANNUAIRE
  • [FR] Le site du zero
    Découvrez gratuitement la programmation (C, C++, PHP, MySQL, XHTML, CSS...), Linux, le Mapping, la modé...
    Programmation
    [EN] Rankk
    Site de challenge construit sur le principe d'une pyramide à 9 level. Level 1: 60,Level 2: 72,Level 3: 68,Lev...
    Challenges
    [EN] Big-Daddy
    Big-Daddy est site internet communautaire avec un effectif diversifié, y compris des artistes, des programmeur...
    Hacking
    [FR] Forum-Webmaster
    Une communauté webmaster pour apporter / recevoir de l'aide en création de site internet. Webmaster...
    Webmaster
    [FR] dcode
    dcode.fr est le site indispensable pour décoder des messages, tricher aux jeux de lettres, résoudre des énigmes...
    Outils / Add-on
    [EN] social-engineer
    Site dédié au Social Engineering en général.
    Hacking
    [EN] Listbrain Version 3
    Site proposant 66 challenges présentés dans une liste mélangée.
    Challenges

  • DONATION
  • Si vous avez trouvé ce site internet utile, nous vous invitons à nous faire un don du montant de votre choix via Paypal. Ce don servira à financer notre hébergement.

    MERCI!




Note de ce sujet :
  • Moyenne : 0 (0 vote(s))
  • 1
  • 2
  • 3
  • 4
  • 5
[C] extern // static
14-02-2015, 07h44 (Modification du message : 14-02-2015, 07h44 par ark.)
Message : #1
ark Hors ligne
Psyckomodo!
*****



Messages : 1,033
Sujets : 48
Points: 317
Inscription : Sep 2011
[C] extern // static
Yop,

la question sur l'utilisation du mot cle extern s'etant pose sur IRC, je vais donc faire un petit post par rapport a l'utilisatiion des mots cles suivants: extern et static.

1. extern

Ce mot cle est utile pour acceder a une variable presente dans un autre objet. En voici un exemple:
Nous avons deux fichier,
le premier, contenant la fonction main(), ou la variable int bar est declaree en globale.

Code C :
#include <stdio.h>

/* Prototype de la fonction dans l'autre fichier */
void foo(void);

/* ma variable partagee. */
int bar = 0;

int main(void) {
  foo();
  printf("bar = %d\n", bar);
  return 0;
}


Le second, ou l'on recupere la variable, pour effectuer un traitement dans la fonction foo()
Code C :
/* cette variable a deja ete declare,
   on ne fait que recuperer son adresse */

extern int bar;

void foo(void) {
  bar += 1;
}


Et comme prevu, la sortie de ce programme sera:
shell a écrit :tmp $> ./a.out
bar = 1

On rappellera tout de meme que les variable globale, c'est mal, et si vous pouvez vous en passer, faites le, merci. :)



2. static


Celui-ci a deux utilisations differente en fonction de si vous l'utiliser a l'interieur ou a l'exterieur du scope d'une fonction.

A l'interieur du scope d'une fonction, il permet de faire en sortes que la valeur de la variable soit conserve entre chaque appel de la fonction.

Exemple:

Code C :
#include <stdio.h>

void foo(void) {
  static int bar = 0;

  ++bar;
  printf("bar = %d\n", bar);
}

int main(void) {
  foo();
  foo();
  foo();
  return 0;
}


Ici, bar est initialisee a 0. (C'est fait de maniere explicite, mais on est pas oblige de le mettre puisque toutes les variables declarees globale ou static seront automatiquement init a 0 si vous ne precisez rien. Mais dans un soucis de lisibilite, je prefere le faire)
A chaque appel de la fonction foo, sa valeur sera incremente de 1. L'output de ce code donne donc:

shell a écrit :tmp $> ./a.out
bar = 1
bar = 2
bar = 3


Le deuxieme cas d'utilisation de ce mot cle, lorsqu'il est utilise en dehors du scope d'une fonction, permet de restreindre la fonction ou la variable sur laquelle vous l'appliquez a l'objet courant.
Pour faire simple, si vous declarez une fonction en static, vous y aurez acces uniquement dans ce fichier.

Et pour l'exemple, deux fichiers ici aussi:

bar.c, qui contient le main, et qui appelle une fonction foo
Code C :
int main(void) {
  foo();
  return 0;
}


et foo.c, qui contient la fonction foo, declare en static.
Code C :
#include <stdio.h>

static void foo(void) {
  puts("coucou");
}


Le resultat, c'est qu'on ne pourra pas compiler tout ca:
shell a écrit :tmp $> gcc bar.c foo.c
/tmp/ccjd6zly.o: In function `main':
bar.c:(.text+0xa): undefined reference to `foo'
collect2: error: ld returned 1 exit status

voila voila, c'etait pas grands chose, mais j'espere que ca aura appris des choses a certains.
+1 (8) -1 (0) Répondre
01-04-2016, 10h54
Message : #2
airday Hors ligne
Newbie
*



Messages : 24
Sujets : 4
Points: 0
Inscription : Feb 2013
RE: [C] extern // static
Ce qui est interressant dans ces variables c'est que la variable globale a une adresse memoire plus importante par rapport a celle de la variable statique (son adresse ne change pas et est faible)
+1 (0) -1 (0) Répondre
01-04-2016, 11h04
Message : #3
ark Hors ligne
Psyckomodo!
*****



Messages : 1,033
Sujets : 48
Points: 317
Inscription : Sep 2011
RE: [C] extern // static
(01-04-2016, 10h54)airday a écrit : Ce qui est interressant dans ces variables c'est que la variable globale a une adresse memoire plus importante par rapport a celle de la variable statique (son adresse ne change pas et est faible)

wtf?
+1 (0) -1 (0) Répondre
01-04-2016, 11h16
Message : #4
airday Hors ligne
Newbie
*



Messages : 24
Sujets : 4
Points: 0
Inscription : Feb 2013
RE: [C] extern // static
@ark, Je viens de le faire et constate par toi meme.

Code :
global = 5, adresse = 0x7fff56575b68
bar = 1, adresse = 0x10968b018
bar = 2, adresse = 0x10968b018
bar = 3, adresse = 0x10968b018

Apres surment je me suis mal exprime.
+1 (0) -1 (0) Répondre
01-04-2016, 11h20 (Modification du message : 01-04-2016, 11h23 par supersnail.)
Message : #5
supersnail Hors ligne
Éleveur d'ornithorynques
*******



Messages : 1,614
Sujets : 72
Points: 466
Inscription : Jan 2012
RE: [C] extern // static
EDIT: faut faire la différence entre adresse de pile (là où vivent les variables locales) et section de données, où sont stockées généralement les variables globales (qui résident dans le binaire que tu compiles, et mappées par l'OS).
Mon blog

Code :
push esp ; dec eax ; inc ebp ; and [edi+0x41],al ; dec ebp ; inc ebp

"VIM est merveilleux" © supersnail
+1 (2) -1 (0) Répondre
01-04-2016, 14h14
Message : #6
b0fh Hors ligne
Membre actif
*



Messages : 210
Sujets : 17
Points: 309
Inscription : Jul 2012
RE: [C] extern // static
C'est en effet bien mieux d'avoir des addresses courtes; en effet, pendant un accès mémoire, le contrôleur du bus mémoire doit vérifier le ticket de la requête mémoire, et il mettra forcément moins de temps à lire une addresse courte.

Le mieux étant d'utiliser des addresses d'un byte, qui seront les plus rapides à lire. Malheureusement, le compilo ne permet pas de s'en servir par défaut, a cause du DMA qui n'est pas activé par défaut, donc pour obtenir une variable super-rapide il faut caster un pointeur à la main, par exemple:

int *case_1 = (int *)(1);
int *case_2 = (int *)(2);

et ensuite s'en servir comme des pointeurs normaux:

*case1 = *case2

Note que dans de très rares cas (par exemple si le noyau a été infecté par la backdoor Dual_EC_DRBD de la NSA) ce type de code peut provoquer des segfaults, justement parce que la backdoor réserve ces accès mémoire ultrarapides à son propre usage.
+1 (2) -1 (0) Répondre


Atteindre :


Utilisateur(s) parcourant ce sujet : 5 visiteur(s)
N-PN
Accueil | Challenges | Tutoriels | Téléchargements | Forum | Retourner en haut