This file is indexed.

/usr/share/doc/HOWTO/fr-html/Assembly-HOWTO.html is in doc-linux-fr-html 2013.01-3ubuntu1.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

   1
   2
   3
   4
   5
   6
   7
   8
   9
  10
  11
  12
  13
  14
  15
  16
  17
  18
  19
  20
  21
  22
  23
  24
  25
  26
  27
  28
  29
  30
  31
  32
  33
  34
  35
  36
  37
  38
  39
  40
  41
  42
  43
  44
  45
  46
  47
  48
  49
  50
  51
  52
  53
  54
  55
  56
  57
  58
  59
  60
  61
  62
  63
  64
  65
  66
  67
  68
  69
  70
  71
  72
  73
  74
  75
  76
  77
  78
  79
  80
  81
  82
  83
  84
  85
  86
  87
  88
  89
  90
  91
  92
  93
  94
  95
  96
  97
  98
  99
 100
 101
 102
 103
 104
 105
 106
 107
 108
 109
 110
 111
 112
 113
 114
 115
 116
 117
 118
 119
 120
 121
 122
 123
 124
 125
 126
 127
 128
 129
 130
 131
 132
 133
 134
 135
 136
 137
 138
 139
 140
 141
 142
 143
 144
 145
 146
 147
 148
 149
 150
 151
 152
 153
 154
 155
 156
 157
 158
 159
 160
 161
 162
 163
 164
 165
 166
 167
 168
 169
 170
 171
 172
 173
 174
 175
 176
 177
 178
 179
 180
 181
 182
 183
 184
 185
 186
 187
 188
 189
 190
 191
 192
 193
 194
 195
 196
 197
 198
 199
 200
 201
 202
 203
 204
 205
 206
 207
 208
 209
 210
 211
 212
 213
 214
 215
 216
 217
 218
 219
 220
 221
 222
 223
 224
 225
 226
 227
 228
 229
 230
 231
 232
 233
 234
 235
 236
 237
 238
 239
 240
 241
 242
 243
 244
 245
 246
 247
 248
 249
 250
 251
 252
 253
 254
 255
 256
 257
 258
 259
 260
 261
 262
 263
 264
 265
 266
 267
 268
 269
 270
 271
 272
 273
 274
 275
 276
 277
 278
 279
 280
 281
 282
 283
 284
 285
 286
 287
 288
 289
 290
 291
 292
 293
 294
 295
 296
 297
 298
 299
 300
 301
 302
 303
 304
 305
 306
 307
 308
 309
 310
 311
 312
 313
 314
 315
 316
 317
 318
 319
 320
 321
 322
 323
 324
 325
 326
 327
 328
 329
 330
 331
 332
 333
 334
 335
 336
 337
 338
 339
 340
 341
 342
 343
 344
 345
 346
 347
 348
 349
 350
 351
 352
 353
 354
 355
 356
 357
 358
 359
 360
 361
 362
 363
 364
 365
 366
 367
 368
 369
 370
 371
 372
 373
 374
 375
 376
 377
 378
 379
 380
 381
 382
 383
 384
 385
 386
 387
 388
 389
 390
 391
 392
 393
 394
 395
 396
 397
 398
 399
 400
 401
 402
 403
 404
 405
 406
 407
 408
 409
 410
 411
 412
 413
 414
 415
 416
 417
 418
 419
 420
 421
 422
 423
 424
 425
 426
 427
 428
 429
 430
 431
 432
 433
 434
 435
 436
 437
 438
 439
 440
 441
 442
 443
 444
 445
 446
 447
 448
 449
 450
 451
 452
 453
 454
 455
 456
 457
 458
 459
 460
 461
 462
 463
 464
 465
 466
 467
 468
 469
 470
 471
 472
 473
 474
 475
 476
 477
 478
 479
 480
 481
 482
 483
 484
 485
 486
 487
 488
 489
 490
 491
 492
 493
 494
 495
 496
 497
 498
 499
 500
 501
 502
 503
 504
 505
 506
 507
 508
 509
 510
 511
 512
 513
 514
 515
 516
 517
 518
 519
 520
 521
 522
 523
 524
 525
 526
 527
 528
 529
 530
 531
 532
 533
 534
 535
 536
 537
 538
 539
 540
 541
 542
 543
 544
 545
 546
 547
 548
 549
 550
 551
 552
 553
 554
 555
 556
 557
 558
 559
 560
 561
 562
 563
 564
 565
 566
 567
 568
 569
 570
 571
 572
 573
 574
 575
 576
 577
 578
 579
 580
 581
 582
 583
 584
 585
 586
 587
 588
 589
 590
 591
 592
 593
 594
 595
 596
 597
 598
 599
 600
 601
 602
 603
 604
 605
 606
 607
 608
 609
 610
 611
 612
 613
 614
 615
 616
 617
 618
 619
 620
 621
 622
 623
 624
 625
 626
 627
 628
 629
 630
 631
 632
 633
 634
 635
 636
 637
 638
 639
 640
 641
 642
 643
 644
 645
 646
 647
 648
 649
 650
 651
 652
 653
 654
 655
 656
 657
 658
 659
 660
 661
 662
 663
 664
 665
 666
 667
 668
 669
 670
 671
 672
 673
 674
 675
 676
 677
 678
 679
 680
 681
 682
 683
 684
 685
 686
 687
 688
 689
 690
 691
 692
 693
 694
 695
 696
 697
 698
 699
 700
 701
 702
 703
 704
 705
 706
 707
 708
 709
 710
 711
 712
 713
 714
 715
 716
 717
 718
 719
 720
 721
 722
 723
 724
 725
 726
 727
 728
 729
 730
 731
 732
 733
 734
 735
 736
 737
 738
 739
 740
 741
 742
 743
 744
 745
 746
 747
 748
 749
 750
 751
 752
 753
 754
 755
 756
 757
 758
 759
 760
 761
 762
 763
 764
 765
 766
 767
 768
 769
 770
 771
 772
 773
 774
 775
 776
 777
 778
 779
 780
 781
 782
 783
 784
 785
 786
 787
 788
 789
 790
 791
 792
 793
 794
 795
 796
 797
 798
 799
 800
 801
 802
 803
 804
 805
 806
 807
 808
 809
 810
 811
 812
 813
 814
 815
 816
 817
 818
 819
 820
 821
 822
 823
 824
 825
 826
 827
 828
 829
 830
 831
 832
 833
 834
 835
 836
 837
 838
 839
 840
 841
 842
 843
 844
 845
 846
 847
 848
 849
 850
 851
 852
 853
 854
 855
 856
 857
 858
 859
 860
 861
 862
 863
 864
 865
 866
 867
 868
 869
 870
 871
 872
 873
 874
 875
 876
 877
 878
 879
 880
 881
 882
 883
 884
 885
 886
 887
 888
 889
 890
 891
 892
 893
 894
 895
 896
 897
 898
 899
 900
 901
 902
 903
 904
 905
 906
 907
 908
 909
 910
 911
 912
 913
 914
 915
 916
 917
 918
 919
 920
 921
 922
 923
 924
 925
 926
 927
 928
 929
 930
 931
 932
 933
 934
 935
 936
 937
 938
 939
 940
 941
 942
 943
 944
 945
 946
 947
 948
 949
 950
 951
 952
 953
 954
 955
 956
 957
 958
 959
 960
 961
 962
 963
 964
 965
 966
 967
 968
 969
 970
 971
 972
 973
 974
 975
 976
 977
 978
 979
 980
 981
 982
 983
 984
 985
 986
 987
 988
 989
 990
 991
 992
 993
 994
 995
 996
 997
 998
 999
1000
1001
1002
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
1283
1284
1285
1286
1287
1288
1289
1290
1291
1292
1293
1294
1295
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309
1310
1311
1312
1313
1314
1315
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2//EN">
<html>
<head>
<meta name="generator" content=
"HTML Tidy for HTML5 for Linux version 5.2.0">
<meta name="GENERATOR" content="LinuxDoc-Tools 0.9.72">
<title>Assembly HOWTO</title>
</head>
<body>
<h1>Assembly HOWTO</h1>
<h2>François-René Rideau <code>rideau@ens.fr</code></h2>
v0.4l, 16 Novembre 1997
<hr>
<em>(Version française réalisée par Eric Dumas
<code>dumas@freenix.fr</code> <code>dumas@Linux.EU.Org</code>, et
Faré Rideau <code>rideau@ens.fr</code>, 11 Novembre 1997). Ce
document décrit comment programmer en assembleur x86 en n'utilisant
que des outils de développement <em>libres</em>, et tout
particulièrement avec le système d'exploitation Linux sur la
plate-forme i386. Les informations contenues dans ce document
peuvent être applicables ou non applicables à d'autres
plates-formes matérielles ou logicielles. Les contributions à ce
documents seront acceptées avec gratitude. <em>mots-clefs</em>:
assembleur, libre, macroprocesseur, préprocesseur, asm, inline asm,
32 bits, x86, i386, gas, as86, nasm</em>
<hr>
<h2><a name="s1">1. Introduction</a></h2>
<h2><a name="ss1.1">1.1 Copyright</a></h2>
<p>Copyright © 1996,1997 François-René Rideau. Ce document peut
être redistribué sous les termes de la license LDP, disponibles à
<a href=
"http://sunsite.unc.edu/LDP/COPYRIGHT.html">http://sunsite.unc.edu/LDP/COPYRIGHT.html</a>.</p>
<h2><a name="ss1.2">1.2 Note importante</a></h2>
<p>Ceci est censé être la dernière version que j'écrirai de ce
document. Il y a un candidat pour reprendre en charge le document,
mais jusqu'à ce qu'il le reprenne complètement en main, je serai
heureux de m'occuper de tout courrier concernant ce document.</p>
<p>Vous êtes tout spécialement invités à poser des questions, à y
répondre, à corriger les données, à ajouter de nouvelles
informations, à compléter les références sur d'autres logiciels, à
mettre en évidence les erreurs et lacunes du document. Si vous êtes
motivés, vous pouvez même <b>prendre en charge ce document</b>. En
un mot, apporter votre contribution!</p>
<p>Pour contribuer à ce document, contactez la personne qui
apparaît actuellement en charge. Au moment où j'écris ces lignes,
il s'agit de <a href="mailto:rideau@clipper.ens.fr">François-René
Rideau</a>) ainsi que de <a href=
"mailto:paul@geeky1.ebtech.net">Paul Anderson</a>.</p>
<h2><a name="ss1.3">1.3 Avant-Propos</a></h2>
<p>Ce document est destiné à répondre aux questions les plus
fréquemment posées par les gens qui développent ou qui souhaitent
développer des programmes en assembleurs x86 32 bits en utilisant
des logiciels <em>libres</em>, et tout particulièrement sous Linux.
Vous y trouverez également des liens sur d'autres documents
traitant d'assembleur, fondés sur des outils logiciels qui ne sont
pas libres, pas 32-bit, ou pas dédiés à l'architecture x86, bien
que cela ne soit pas le but principal de ce document.</p>
<p>Etant donné que l'intéret principal de la programmation en
assembleur est d'établir les fondations de systèmes d'exploitation,
d'interpréteurs, de compilateurs, et de jeux, là où un compilateur
C n'arrive plus à fournir le pouvoir d'expression nécessaire (les
performances étant de plus en plus rarement un problème), nous
insisteront sur le développement de tels logiciels.</p>
<h3>Comment utiliser ce document</h3>
<p>Ce document contient des réponses à un certain nombre de
questions fréquemment posées. Des URL y sont donnés, qui pointent
sur des sites contenant documents ou logiciels. Prenez conscience
que les plus utiles de ces sites sont dupliqués sur des serveurs
miroirs, et qu'en utilisant le site miroir le plus proche de chez
vous, vous évitez à un gâchis inutile aussi bien de précieuses
ressources réseau communes à l'Internet que de votre propre temps.
Ainsi, il existe un certain nombre de gros serveurs disséminés sur
la planète, qui effectuent la duplication d'autres sites
importants. Cherchez où se trouvent ces sites et identifiez les
plus proches de chez vous (du point de vue du réseau). Parfois, la
liste des miroirs est données dans un fichier ou dans le message de
connexion. Suivez ces conseils. Si ces informations ne sont pas
présentes, utilisez le programme archie.</p>
<p>La version la plus récente de ce document peut être trouvée
sur</p>
<p><a href=
"http://www.eleves.ens.fr:8080/home/rideau/Assembly-HOWTO">http://www.eleves.ens.fr:8080/home/rideau/Assembly-HOWTO</a>
ou <a href=
"http://www.eleves.ens.fr:8080/home/rideau/Assembly-HOWTO.sgml">http://www.eleves.ens.fr:8080/home/rideau/Assembly-HOWTO.sgml</a></p>
<p>mais les répertoires de HowTo Linux <em>devraient</em>
normalement être à peu près à jour (je ne peux pas le
garentir):</p>
<p><a href=
"ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/">ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/</a>
(?)</p>
<p>La version française de ce document peut être trouvée sur le
site</p>
<p><a href=
"ftp://ftp.ibp.fr/pub/linux/french/HOWTO/">ftp://ftp.ibp.fr/pub/linux/french/HOWTO/</a></p>
<h3>Autres documents de référence</h3>
<ul>
<li>si vous ne savez ce qu'est le <em>libre</em> logiciel, lisez
avec attention la GPL (GNU General Public License), qui est
utilisée dans un grand nombre de logiciels libres, et est une
source d'inspiration pour la plupart des autres licences
d'utilisations de logiciels libres. Elle se trouve généralement
dans un fichier nommé <code>COPYING</code>, avec une version pour
les bibliothèques de routines dans un fichier nommé
<code>COPYING.LIB</code>. Les écrits publiés par la FSF (free
software foundation) peuvent également vous aider à comprendre le
phénomène.</li>
<li>plus précisément, les logiciels libres intéressants sont ceux
desquels les sources sont disponibles, que l'on peut consulter,
corriger, et desquels on peut emprunter une partie. Lisez les
licences d'utilisation avec attention et conformez-vous y.</li>
<li>il existe une FAQ dans le forum de discussion comp.lang.asm.x86
qui répond aux questions générales concernant la programmation en
assembleur pour x86, et aux questions concernant certains
assembleurs commerciaux dans un environnement DOS 16 bits.
Certaines de ces réponses peuvent s'appliquer à la programmation 32
bits, aussi serez-vous sans-doute intéressés de lire cette FAQ...
<a href=
"http://www2.dgsys.com/~raymoon/faq/asmfaq.zip">http://www2.dgsys.com/~raymoon/faq/asmfaq.zip</a></li>
<li>Sont disponibles des FAQs, de la documentation, et des sources,
concernant la programmation sur votre plate-forme préférée,
quelqu'elle soit, et vous devriez les consulter pour les problèmes
liés à votre plate-forme qui ne seraient pas spécifique à la
programmation en assembleur.</li>
</ul>
<h2><a name="ss1.4">1.4 Historique de document</a></h2>
<p>Chaque version inclue quelques modifications et corrections
mineures, qui ne sont pas indiquées à chaque fois.</p>
<dl>
<dt><b>Version 0.1 23 Avril 1996</b></dt>
<dd>
<p>Francois-Rene "Faré" Rideau &lt;rideau@ens.fr&gt; crée et
diffuse initialement le document sous forme d'un mini-HOWTO car
``Je suis un peu fatigué d'avoir à répondre encore et toujours aux
mêmes questions dans le forum comp.lang.asm.x86''</p>
</dd>
<dt><b>Version 0.2 4 Mai 1996</b></dt>
<dd>
<p>*</p>
</dd>
<dt><b>Version 0.3c 15 Juin 1996</b></dt>
<dd>
<p>*</p>
</dd>
<dt><b>Version 0.3f 17 Octobre 1996</b></dt>
<dd>
<p>Tim Potter indique l'option -fasm pour activer l'assembleur
en-ligne de GCC sans le reste des optimisations de -O.</p>
</dd>
<dt><b>Version 0.3g 2 Novembre 1996</b></dt>
<dd>
<p>Création de l'historique. Ajout de pointeurs dans la section sur
la compilation croisée. Ajout d'une section concernant la
programmation des entrées/sorties sous Linux (en particulier pour
l'accès vidéo).</p>
</dd>
<dt><b>Version 0.3h 6 Novembre 1996</b></dt>
<dd>
<p>plus sur la compilation croisée - voir sur sunsite:
devel/msdos/</p>
</dd>
<dt><b>Version 0.3i 16 Novembre 1996</b></dt>
<dd>
<p>NASM commence à être particulièrement intéressant</p>
</dd>
<dt><b>Version 0.3j 24 Novembre 1996</b></dt>
<dd>
<p>Référence sur la version française</p>
</dd>
<dt><b>Version 0.3k 19 Décembre 1996</b></dt>
<dd>
<p>Quoi? J'avais oublié de parler de Terse?</p>
</dd>
<dt><b>Version 0.3l 11 Janvier 1997</b></dt>
<dd>
<p>*</p>
</dd>
<dt><b>Version 0.4pre1 13 Janvier 1997</b></dt>
<dd>
<p>Le mini-HOWTO au format texte est transformé en un authentique
HOWTO au format linuxdoc-sgml, pour explorer les possibilités dudit
format.</p>
</dd>
<dt><b>Version 0.4 20 Janvier 1997</b></dt>
<dd>
<p>Première diffusion de ce HOWTO.</p>
</dd>
<dt><b>Version 0.4a 20 Janvier 1997</b></dt>
<dd>
<p>Ajout de la section CREDITS</p>
</dd>
<dt><b>Version 0.4b 3 Février 1997</b></dt>
<dd>
<p>NASM mis avant AS86</p>
</dd>
<dt><b>Version 0.4c 9 Février 1997</b></dt>
<dd>
<p>Ajout de la partie "Avez-vous besoin d'utilisateur
l'assembleur?"</p>
</dd>
<dt><b>Version 0.4d 28 Février 1997</b></dt>
<dd>
<p>Annonce fantôme d'un nouveau responsable de ce HowTo.</p>
</dd>
<dt><b>Version 0.4e 13 Mar 1997</b></dt>
<dd>
<p>Version diffusée pour DrLinux</p>
</dd>
<dt><b>Version 0.4f 20 Mars 1997</b></dt>
<dd>
<p>*</p>
</dd>
<dt><b>Version 0.4g 30 Mars 1997</b></dt>
<dd>
<p>*</p>
</dd>
<dt><b>Version 0.4h 19 Juin 1997</b></dt>
<dd>
<p>Ajouts à propos de "Comment ne pas utiliser l'assembleur"; mises
à jour concernant NASM et GAS.</p>
</dd>
<dt><b>Version 0.4i 17 Juillet 1997</b></dt>
<dd>
<p>Informations sur l'accès au mode 16 bits à partir de Linux.</p>
</dd>
<dt><b>Version 0.4j 7 September 1997</b></dt>
<dd>
<p>*</p>
</dd>
<dt><b>Version 0.4k 19 Octobre 1997</b></dt>
<dd>
<p>je (Faré) reprends en main la traduction française du HowTo</p>
</dd>
<dt><b>Version 0.4l 16 Novembre 1997</b></dt>
<dd>
<p>version pour LSL 6ème édition.</p>
<p>Il s'agit encore d'une nouvelle ``toute dernière version
réalisée par Faré avant qu'un nouveau responsable ne prenne la
main''.</p>
</dd>
</dl>
<h2><a name="ss1.5">1.5 Crédits</a></h2>
<p>Je souhaiterais remercier les personnes suivantes:</p>
<ul>
<li><a href="mailto:buried.alive@in.mail">Linus Torvalds</a> pour
Linux</li>
<li><a href="mailto:bde@zeta.org.au">Bruce Evans</a> pour bcc d'où
as86 est extrait</li>
<li><a href="mailto:anakin@poboxes.com">Simon Tatham</a> et
<a href="mailto:jules@earthcorp.com">Julian Hall</a> pour
NASM.</li>
<li><a href="mailto:jim-neil@digital.net">Jim Neil</a> pour
Terse</li>
<li><a href="mailto:gregh@sunsite.unc.edu">Greg Hankins</a> pour la
coordination des HOWTOs</li>
<li><a href="mailto:raymoon@moonware.dgsys.com">Raymond Moon</a>
pour sa FAQ</li>
<li><a href="mailto:dumas@Linux.EU.Org">Eric Dumas</a> pour la
traduction initiale en français... (l'auteur, français, est le
premier attristé de devoir écrire l'original en anglais)</li>
<li><a href="mailto:paul@geeky1.ebtech.net">Paul Anderson</a> et
<a href="mailto:rahim@megsinet.net">Rahim Azizarab</a> pour m'avoir
aidé, à défaut de reprendre le HowTo en main.</li>
<li>toutes les personnes qui ont contribué à l'écriture de ce
document, par leurs idées, remarques ou leur soutient moral.</li>
</ul>
<h2><a name="doyouneedasm"></a> <a name="s2">2. Avez-vous besoin de
l'assembleur?</a></h2>
<p>Je ne veux en aucun cas jouer les empêcheurs-de-tourner-en-rond,
mais voici quelques conseils issus d'une expérience gagnée à la
dure.</p>
<h2><a name="ss2.1">2.1 Le Pour et le Contre</a></h2>
<h3>Les avantages de l'assembleur</h3>
<p>L'assembleur peut vous permettre de réaliser des opérations très
bas niveau:</p>
<ul>
<li>vous pouvez accéder aux registres et aux ports
d'entrées/sorties spécifiques à votre machine;</li>
<li>vous pouvez parfaitement contrôler le comportemant du code dans
des sections critiques où pourraient sinon advenir un blocage du
processeur ou des périphériques;</li>
<li>vous pouvez sortir des conventions de production de code de
votre compilateur habituel; ce qui peut vous permettre d'effectuer
certaines optimisations (par exemple contourner les règles
d'allocation mémoire, gérer manuellement le cours de l'éxécution,
etc.);</li>
<li>accéder à des modes de programmation non courants de votre
processeur (par exemple du code 16 bits pour l'amorçage ou
l'interfaçage avec le BIOS, sur les pécés Intel);</li>
<li>vous pouvez construire des interfaces entre des fragments de
codes utilisant des conventions incompatibles (c'est-à-dire produit
par des compilateurs différents ou séparés par une interface
bas-niveau);</li>
<li>vous pouvez générer un code assez rapide pour les boucles
importantes pour pallier aux défauts d'un compilateur qui ne sait
les optimiser (mais bon, il existe des compilateurs optimisateurs
librement disponibles!);</li>
<li>vous pouvez générer du code optimisé "à la main" qui est plus
parfaitement règlé pour votre configuration matérielle précise,
même s'il ne l'est pour aucune autre configuration;</li>
<li>vous pouvez écrire du code pour le compilateur optimisateur de
votre nouveau langage. (c'est là une activité à laquelle peu se
livrent, et encore, rarement.)</li>
</ul>
<h3>Les inconvénients de l'assembleur</h3>
<p>L'assembleur est un langage très bas niveau (le langage du plus
bas niveau qui soit au dessus du codage à la main de motifs
d'instructions en binaire). En conséquence:</p>
<ul>
<li>l'écriture de code en est longue et ennuyeuse;</li>
<li>les bogues apparaissent aisément;</li>
<li>les bogues sont difficiles à repérer et supprimer;</li>
<li>il est difficile de comprendre et de modifier du code (la
maintenance est très compliquée);</li>
<li>le résultat est extrêmement peu portable vers une autre
architecture, existante ou future;</li>
<li>votre code ne sera optimisé que une certaine implémentation
d'une même architecture: ainsi, parmi les plates-formes compatibles
Intel, chaque réalisation d'un processeur et de ses variantes
(largeur du bus, vitesse et taille relatives des
CPU/caches/RAM/Bus/disques, présence ou non d'un coprocesseur
arithmétique, et d'extensions MMX ou autres) implique des
techniques d'optimisations parfois radicalement différentes. Ainsi
diffèrent grandement les processeurs déjà existant et leurs
variations: Intel 386, 486, Pentium, PPro, Pentium II; Cyrix 5x86,
6x86; AMD K5, K6. Et ce n'est sûrement pas terminé: de nouveaux
modèles apparaissent continuellement, et cette liste même sera
rapidement dépassée, sans parler du code ``optimisé'' qui aura été
écrit pour l'un quelconque des processeurs ci-dessus.</li>
<li>le code peut également ne pas être portable entre différents
systèmes d'exploitation sur la même architecture, par manque
d'outils adaptés (GAS semble fonctionner sur toutes les
plates-formes; NASM semble fonctionner ou être facilement adaptable
sur toutes les plates-formes compatibles Intel);</li>
<li>un temps incroyable de programmation sera perdu sur de menus
détails, plutôt que d'être efficacement utilisé pour la conception
et le choix des algorithmes utilisés, alors que ces derniers sont
connus pour être la source de la majeure partie des gains en
vitesse d'un programme. Par exemple, un grand temps peut être passé
à grapiller quelques cycles en écrivant des routines rapides de
manipulation de chaînes ou de listes, alors qu'un remplacement de
la structure de données à un haut niveau, par des arbres équilibrés
et/ou des tables de hachage permettraient immédiatement un grand
gain en vitesse, et une parallélisation aisée, de façon portable
permettant un entretien facile.</li>
<li>une petite modification dans la conception algorithmique d'un
programme anéantit la validité du code assembleur si patiemment
élaboré, réduisant les développeurs au dilemne de sacrifier le
fruit de leur labeur, ou de s'enchaîner à une conception
algorithmique obsolète.</li>
<li>pour des programmes qui fait des choses non point trop
éloignées de ce que font les benchmarks standards, les
compilateurs/optimiseurs commerciaux produisent du code plus rapide
que le code assembleur écrit à la main (c'est moins vrai sur les
architectures x86 que sur les architectures RISC, et sans doute
moins vrai encore pour les compilateurs librement disponible.
Toujours est-il que pour du code C typique, GCC est plus
qu'honorable).</li>
<li>Quoi qu'il en soit, ains le dit le saige John Levine,
modérateur de comp.compilers, "les compilateurs rendent aisée
l'utilisation de structures de données complexes; ils ne s'arrêtent
pas, morts d'ennui, à mi-chemin du travail, et produisent du code
de qualité tout à fait satisfaisante". Ils permettent également de
propager <em>correctement</em> les transformations du code à
travers l'ensemble du programme, aussi hénaurme soit-il, et peuvent
optimiser le code par-delà les frontières entre procédures ou entre
modules.</li>
</ul>
<h3>Affirmation</h3>
<p>En pesant le pour et le contre, on peut conclure que si
l'assembleur est parfois nécessaire, et peut même être utile dans
certains cas où il ne l'est pas, il vaut mieux:</p>
<ul>
<li>minimiser l'utilisation de code écrit en assembleur;</li>
<li>encapsuler ce code dans des interfaces bien définies;</li>
<li>engendrer automatiquement le code assembleur à partir de motifs
écrits dans un langage plus de haut niveau que l'assembleur (par
exemple, des macros contenant de l'assembleur en-ligne, avec
GCC);</li>
<li>utiliser des outils automatiques pour transformer ces
programmes en code assembleur;</li>
<li>faire en sorte que le code soit optimisé, si possible;</li>
<li>utiliser toutes les techniques précédentes à la fois,
c'est-à-dire écrire ou étendre la passe d'optimisation d'un
compilateur.</li>
</ul>
<p>Même dans les cas où l'assembleur est nécessaire (par exemple
lors de développement d'un système d'exploitation), ce n'est qu'à
petite dose, et sans infirmer les principes ci-dessus.</p>
<p>Consultez à ce sujet les sources du noyau de Linux: vous verrez
qu'il s'y trouve juste le peu qu'il faut d'assembleur, ce qui
permet d'avoir un système d'exploitation rapide, fiable, portable
et d'entretien facile. Même un jeu très célèbre comme DOOM a été en
sa plus grande partie écrit en C, avec une toute petite routine
d'affichage en assembleur pour accélérer un peu.</p>
<h2><a name="ss2.2">2.2 Comment ne pas utiliser
l'assembleur</a></h2>
<h3>Méthode générale pour obtenir du code efficace</h3>
<p>Comme le dit Charles Fiterman dans comp.compilers à propos de la
différence entre code écrit par l'homme ou la machine,</p>
<p>``L'homme devrait toujours gagner, et voici pourquoi:</p>
<ul>
<li>Premièrement, l'homme écrit tout dans un langage de haut
nivrau.</li>
<li>Deuxièmement, il mesure les temps d'éxécution (profiling) pour
déterminer les endroits où le programme passe la majeure partie du
temps.</li>
<li>Troisièmement, il demande au compilateur d'engendrer le code
assembleur produit pour ces petites sections de code.</li>
<li>Enfin, il effectue à la main modifications et réglages, à la
recherche des petites améliorations possibles par rapport au code
engendré par la machine.</li>
</ul>
L'homme gagne parce qu'il peut utiliser la machine.''
<h3>Langages avec des compilateurs optimisateurs</h3>
<p>Des langages comme ObjectiveCAML, SML, CommonLISP, Scheme, ADA,
Pascal, C, C++, parmi tant d'autres, ont tous des compilateurs
optimiseurs librement disponibles, qui optimiseront le gros de vos
programmes, et produiront souvent du code meilleur que de
l'assembleur fait-main, même pour des boucles serrées, tout en vous
permettant de vous concentrer sur des détails haut niveau, et sans
vous interdire de gagner par la méthode précédente quelques
pourcents de performance supplémentaire, une fois la phase de
conception générale terminée. Bien sûr, il existe également des
compilateurs optimiseurs commerciaux pour la plupart de ces
langages.</p>
<p>Certains langages ont des compilateurs qui produisent du code C
qui peut ensuite être optimisé par un compilateur C. C'est le cas
des langages LISP, Scheme, Perl, ainsi que de nombreux autres. La
vitesse des programmes obtenus est toute à fait satisfaisante.</p>
<h3>Procédure générale à suivre pour accélerer votre code</h3>
<p>Pour accélérer votre code, vous ne devriez traiter que les
portions d'un programme qu'un outil de mesure de temps d'éxécution
(profiler) aura identifié comme étant un goulot d'étranglement pour
la performance de votre programme.</p>
<p>Ainsi, si vous identifiez une partie du code comme étant trop
lente, vous devriez</p>
<ul>
<li>d'abord essayer d'utiliser un meilleur algorithme;</li>
<li>essayer de la compiler au lieu de l'interpréter;</li>
<li>essayer d'activer les bonnes options d'optimisation de votre
compilateur;</li>
<li>donner au compilateur des indices d'optimisation (déclarations
de typage en LISP; utilisation des extensions GNU avec GCC; la
plupart des compilos fourmillent d'options);</li>
<li>enfin de compte seulement, se mettre à l'assembleur si
nécessaire.</li>
</ul>
<p>Enfin, avant d'en venir à cette dernière option, vous devriez
inspecter le code généré pour vérifier que le problème vient
effectivement d'une mauvaise génération de code, car il se peut
fort bien que ce ne soit pas le cas: le code produit par le
compilateur pourrait être meilleur que celui que vous auriez écrit,
en particulier sur les architectures modernes à pipelines
multiples! Il se peut que les portions les plus lentes de votre
programme le soit pour des raisons intrinsèques. Les plus gros
problèmes sur les architectures modernes à processeur rapide sont
dues aux délais introduits par les accès mémoires, manqués des
caches et TLB, fautes de page; l'optimisation des registres devient
vaine, et il vaut mieux repenser les structures de données et
l'enchaînement des routines pour obtenir une meilleur localité des
accès mémoire. Il est possible qu'une approche complètement
différente du problème soit alors utile.</p>
<h3>Inspection du code produit par le compilateur</h3>
<p>Il existe de nombreuses raisons pour vouloir regarder le code
assembleur produit par le compilateur. Voici ce que vous pourrez
faire avec ce code:</p>
<ul>
<li>vérifier si le code produit peut ou non être améliorer avec du
code assembleur écrit à la main (ou par un réglage différent des
options du compilateur);</li>
<li>quand c'est le cas, commencer à partir de code automatiquement
engendré et le modifier plutôt que de repartir de zéro;</li>
<li>plus généralement, utilisez le code produit comme des scions à
greffer, ce qui à tout le moins vous laisse permet d'avoir
gratuitement tout le code d'interfaçage avec le monde
extérieur.</li>
<li>repérer des bogues éventuels dus au compilateur lui-même
(espérons-le très rare, quitte à se restreindre à des versions
``stables'' du compilo).</li>
</ul>
<p>La manière standard d'obtenir le code assembleur généré est
d'appeller le compilateur avec l'option <code>-S</code>. Cela
fonctionne avec la plupart des compilateur Unix y compris le
compilateur GNU C (GCC); mais à vous de voir dans votre cas. Pour
ce qui est de GCC, il produira un code un peu plus compréhensible
avec l'option <code>-fverbose-asm</code>. Bien sur, si vous
souhaitez obtenir du code assembleur optimisé, n'oubliez pas
d'ajouter les options et indices d'optimisation appropriées!</p>
<h2><a name="s3">3. Assembleurs</a></h2>
<h2><a name="ss3.1">3.1 Assembleur en-ligne de GCC</a></h2>
<p>Le célèbre GNU C/C++ Compiler (GCC), est un compilateur 32 bits
optimisant situé au coeur du projet GNU. Il gère assez bien les
architectures x86 et permet d'insérer du code assembleur à
l'intérieur de programmes C de telle manière que les registres
puissent être soit spécifiés soit laissé aux bons soins de GCC. GCC
fonctionne sur la plupart des plates-formes dont Linux, *BSD, VSTa,
OS/2, *DOS, Win*, etc.</p>
<h3>Où trouver GCC</h3>
<p>Le site principal de GCC est le site FTP du projet GNU: <a href=
"ftp://prep.ai.mit.edu/pub/gnu/">ftp://prep.ai.mit.edu/pub/gnu/</a>
On y trouve également toutes les applications provenant du projet
GNU. Des versions configurées ou précompilées pour Linux sont
disponibles sur <a href=
"ftp://sunsite.unc.edu/pub/Linux/GCC/">ftp://sunsite.unc.edu/pub/Linux/GCC/</a>.
Il existe un grand nombre de miroirs FTP des deux sites partout de
par le monde, aussi bien que des copies sur CD-ROM.</p>
<p>Le groupe de développement de GCC s'est récemment scindé en
deux; pour plus d'informations sur la version expérimentale, egcs,
voir <a href=
"http://www.cygnus.com/egcs/">http://www.cygnus.com/egcs/</a></p>
<p>Les sources adaptés à votre système d'exploitation préféré ainsi
que les binaires précompilés peuvent être trouvés sur les sites FTP
courants.</p>
<p>Le portage le plus célèbre de GCC pour DOS est DJGPP et il peut
être trouvé dans le répertoire du même nom sur les sites ftp.
Voir:</p>
<p><a href=
"http://www.delorie.com/djgpp/">http://www.delorie.com/djgpp/</a></p>
<p>Il existe également un portage de GCC pour OS/2 appelé EMX qui
fonctionne également sous DOS et inclut un grand nombre de routines
d'émulation Unix. Voir les sites</p>
<p><a href=
"http://www.leo.org/pub/comp/os/os2/gnu/emx+gcc/">http://www.leo.org/pub/comp/os/os2/gnu/emx+gcc/</a></p>
<p><a href=
"http://warp.eecs.berkeley.edu/os2/software/shareware/emx.html">http://warp.eecs.berkeley.edu/os2/software/shareware/emx.html</a></p>
<p><a href=
"ftp://ftp-os2.cdrom.com/pub/os2/emx09c/">ftp://ftp-os2.cdrom.com/pub/os2/emx09c/</a></p>
<h3>Où trouver de la documentation sur l'assembleur en ligne avec
GCC?</h3>
<p>La document de GCC inclus les fichiers de documentation au
format texinfo. Vous pouvez les compiler avec TeX et les imprimer,
ou les convertir au format .info et les parcourir interactivement
avec emacs, ou encore les convertir au format HTML, ou en à peu
près n'importe quel format (avec les outils adéquats). Les fichiers
.info sont généralement installés en même temps que GCC.</p>
<p>La section à consulter est <code>C Extensions::Extended
Asm::</code></p>
<p>La section <code>Invoking GCC::Submodel Options::i386
Options::</code> peut également vous aider. En particulier, elle
donne les noms de contraintes pour les registres du i386: abcdSDB
correspondent respectivement à <code>%eax</code>,
<code>%ebx</code>, <code>%ecx</code>, <code>%edx</code>,
<code>%esi</code>, <code>%edi</code>, <code>%ebp</code> (aucune
lettre pour <code>%esp</code>).</p>
<p>Le site "DJGPP Games resource" (qui n'est pas réservé aux seuls
développeurs de jeux) possède une page particulière sur
l'assembleur:</p>
<p><a href=
"http://www.rt66.com/~brennan/djgpp/djgpp_asm.html">http://www.rt66.com/~brennan/djgpp/djgpp_asm.html</a></p>
<p>Enfin, il existe une page de la Toile appelée "DJGPP Quick ASM
Programming Guide", contenant des URL sur des FAQ, la syntaxe
assembleur AT&amp;T x86, des informations sur l'assembleur en
ligne, et la conversion des fichiers .obj/.lib:</p>
<p><a href=
"http://remus.rutgers.edu/~avly/djasm.html">http://remus.rutgers.edu/~avly/djasm.html</a></p>
<p>GCC soutraite l'assemblage proprement dit à GAS et suit donc sa
syntaxe (voir plus bas), cela implique que l'assembleur en ligne
doit utiliser des caractères pourcents entre apostrophes pour
qu'ils soient passés à GAS. Voir la section dédiée à GAS.</p>
<p>Vous trouverez un <em>grand</em> nombre d'exemples instructifs
dans le répertoire <code>linux/include/asm-i386/</code> des sources
de Linux.</p>
<h3>Appeller GCC pour obtenir du code assembleur en ligne
correcte?</h3>
<p>Assurez-vous d'appeller gcc avec l'option <code>-O</code> (ou
<code>-O2</code>, <code>-O3</code>, etc) pour activer les
optimisations et l'assembleur en ligne. Si vous ne le faîtes pas,
votre code pourra compiler mais ne pas s'exécuter correctement!! En
fait (merci à Tim Potter, timbo@moshpit.air.net.au), il suffit
d'utiliser l'option <code>-fasm</code>, faisant partie de toutes
les fonctionnalités activées par l'option <code>-O</code>. Donc si
vous avez des problèmes en raison d'optimisations boguées dans
votre implémentation de gcc, vous pouvez toujours utiliser
l'assembleur en ligne. De même, utilisez l'option
<code>-fno-asm</code> pour désactiver l'assembleur en ligne (on
peut se demander pourquoi?).</p>
<p>Plus généralement, les bonnes options de compilation à utiliser
avec gcc sur les plates-formes x86 sont</p>
<hr>
<pre>
        gcc -O2 -fomit-frame-pointer -m386 -Wall
</pre>
<hr>
<p><code>-O2</code> est le bon niveau d'optimisation. Les
optimisations supérieures génèrent un code un peu plus important,
mais très légèrement plus rapide. De telles sur-optimisations
peuvent être utiles que dans le cas d'optimisations de boucles que
vous pouvez toujours réaliser en assembleur. Si vous avez besoin de
faire ce genre de choses, ne le faîtes que pour les routines qui en
ont besoin.</p>
<p><code>-fomit-frame-pointer</code> permet au code généré de se
passer de la gestion inutile des pointeurs de fenêtre, ce qui rend
le code plus petit plus rapide et libère un registre pour de plus
amples optimisations. Cette option exclue l'utilisation des outils
de déboggage (<code>gdb</code>), mais lorsque vous les utilisez, la
taille et la vitesse importent peu.</p>
<p><code>-m386</code> génère un code plus compacte sans
ralentissement notable, (moins de code signifie également mois
d'entrées/sorties sur disque et donc une exécution plus rapide).
Vous pouvez également utiliser l'option -mpentium sur la version
GCC gérant l'optimisation pour ce processeur.</p>
<p><code>-Wall</code> active toutes les mises-en-garde (warning) et
vous évite de nombreuses erreurs stupides et évidentes.</p>
<p>Pour optimiser encore plus, vous pouvez utiliser l'option
<code>-mregparm=2</code> et/ou les attributs de fonctions qui
peuvent être utilisés mais ils peuvent dans certains cas poser de
nombreux problèmes lors de l'édition de liens avec du code externe
(notamment les bibliothèques partagées)...</p>
<p>Notez que vous pouvez ajoutez ces options aux options utilisées
par défaut sur votre système en éditant le fichier
<code>/usr/lib/gcc-lib/i486-linux/2.7.2.3/specs</code> (cependant,
ne rajoutez pas <code>-Wall</code> à ces options).</p>
<h2><a name="ss3.2">3.2 GAS</a></h2>
<p>GAS est l'assembleur GNU, utilisé par gcc.</p>
<h3>Où le trouver?</h3>
<p>Au même endroit où vous avez trouvé gcc, dans le paquetage
binutils.</p>
<h3>Qu'est-ce que la syntaxe AT&amp;T</h3>
<p>Comme GAS a été inventé pour supporter un compilateur 32 bits
sous unix, il utilise la syntaxe standard "AT&amp;T", qui
ressemblent assez à l'assembleur m68k. La syntaxe n'est ni pire, ni
meilleur que la syntaxe "Intel". Elle est juste différente. Lorsque
vous aurez l'habitude de vous en servir, vous la trouverez plus
régulière que la syntaxe Intel, quoique que légèrement plus
ennuyeuse aussi.</p>
<p>Voici les points les plus importants à propos de la syntaxe de
GAS:</p>
<ul>
<li>Les noms de registres sont préfixés avec <code>%</code>, de
façon que les registres sont <code>%eax</code>, <code>%dl</code> et
consorts au lieu de juste <code>eax</code>, <code>dl</code>, etc.
Ceci rend possible l'inclusion directe de noms de symboles externes
C sans risque de confusion, ou de nécessité de préfixes _.</li>
<li>L'ordre des opérandes est source(s) d'abord, destination en
dernier, à l'opposé de la convention d'intel consistant à mettre la
destination en premier, les source(s) ensuite. Ainsi, ce qui en
syntaxe intel s'écrit <code>mov ax,dx</code> (affecter au registre
<code>ax</code> le contentu du registre <code>dx</code>) s'écrira
en syntaxe att <code>mov %dx, %ax</code>.</li>
<li>La longueur des opérandes est spécifiée comme suffixe du nom
d'instruction. Le suffixe est <code>b</code> pour un octet (8 bit),
<code>w</code> pour un mot (16 bit), et <code>l</code> pour un mot
long (32 bit). Par exemple, la syntaxe correcte pour l'instruction
ci-dessus aurait dû être <code>movw %dx,%ax</code>. Toutefois, gas
n'est pas trop aussi strict que la syntaxe att l'exige, et le
suffixe est optionel quand la longueur peut être devinée grâce aux
opérandes qui sont des registres, la taille par défaut étant 32 bit
(avec une mise en garde quand on y fait appel).</li>
<li>Les opérandes immediates sont marqués d'un préfixe
<code>$</code>, comme dans <code>addl $5,%eax</code> (ajouter la
valeur longue immédiate 5 au registre <code>%eax</code>).</li>
<li>L'absence de préfixe à une opérande indique une adresse
mémoire; ainsi <code>movl $foo,%eax</code> met l'<em>adresse</em>
de la variable <code>foo</code> dans le registre <code>%eax</code>,
tandis que <code>movl foo,%eax</code> met le <code>contenu</code>
de la variable <code>foo</code> dans le registre
<code>%eax</code>.</li>
<li>L'indexation ou l'indirection se fait en mettant entre
parenthèses le registre d'index ou la case mémoire contenant
l'indirection, comme dans <code>testb $0x80,17(%ebp)</code> (tester
le bit de poids fort de l'octet au déplacement 17 après la case
pointée par <code>%ebp</code>).</li>
</ul>
<p>Un programme existe pour vous aider à convertir des programmes
écrits avec la syntaxe TASM en syntaxe AT&amp;T. Voir</p>
<p><a href=
"ftp://x2ftp.oulu.fi/pub/msdos/programming/convert/ta2asv08.zip">ftp://x2ftp.oulu.fi/pub/msdos/programming/convert/ta2asv08.zip</a></p>
<p>GAS possède une documentation complète au format TeXinfo, qui
est distribuée entre autre avec les sources. Vous pouvez parcourir
les pages .info qui en sont extraites avec Emacs. Il y avait aussi
un fichier nommé gas.doc ou as.doc disponible autour des sources de
GAS, mais il a été fusionné avec la documentation TeXinfo. Bien
sûr, en cas de doute, l'ultime documentation est constituée par les
sources eux-mêmes! Une section qui vous intéressera
particulièrement est <code>Machine
Dependencies::i386-Dependent::</code></p>
<p>Les sources de Linux dont un bon exemple: regardez dans le
répertoire linux/arch/i386 les fichiers suivants: <code>kernel/*.S,
boot/compressed/*.S, mathemu/*.S</code></p>
<p>Si vous codez ce genre de chose, un paquetage de thread, etc
vous devriez regarder d'autres langages (OCaml, gforth, etc), ou
des paquetages sur les thread (QuickThreads, pthreads MIT,
LinuxThreads, etc).</p>
<p>Enfin générer à partir d'un programme C du code assembleur peut
vous montrer le genre d'instructions que vous voulez. Consultez la
section <a href="#doyouneedasm">Avez-vous besoin de
l'assembleur?</a> au début de ce document.</p>
<h3>mode 16 bits limité</h3>
<p>GAS est un assembleur 32 bits, conçu pour assembler le code
produit par un compilateur 32 bits. Il ne reconnaît que d'une
manière limité le mode 16 bits du i386, en ajoutant des préfixes 32
bits aux instructions; vous écrivez donc en réalité du code 32
bits, qui s'exécute en mode 16 bits sur un processeur 32 bits. Dans
les deux modes, il gère les registres 16 bits, mais pas l'adressage
16 bits. Utilisez les instructions <code>.code16</code> et
<code>.code32</code> pour basculer d'un mode à l'autre. Notez que
l'instruction assembleur en ligne <code>asm(".code16\n")</code>
autorisera gcc à générer du code 32 bits qui fonctionnera en mode
réél!</p>
<p>Le code nécessaire pour que GAS gère le mode 16 bits aurait été
ajouté par Bryan Ford (à confirmer?). Toutefois, ce code n'est
présent dans aucune distribution de GAS que j'ai essayée (jusqu'à
binutils-2.8.1.x) ... plus d'informations à ce sujet seraient les
bienvenues dans ce HowTo.</p>
<p>Une solution bon marché pour insérer quelques instructions
16-bit non reconnues pas GAS consiste à définir des macros (voir
plus bas) qui produisent directement du code binaire (avec
<code>.byte</code>), et ce uniquement pour les rares instructions
16 bits dont vous avez besoin (quasiment aucunes, si vous utilisez
le <code>.code16</code> précédement décrit, et pouvez vous
permettre de supposer que le code fonctionnera sur un processeur 32
bits). Pour obtenir le système de codage correct, vous pouvez vous
inspirer des assembleurs 16 bits.</p>
<h2><a name="ss3.3">3.3 GASP</a></h2>
<p>GASP est un préprocesseur pour GAS. Il ajoute des macros et une
syntaxe plus souple à GAS.</p>
<h3>Où trouver gasp?</h3>
<p>gasp est livré avec gas dans le paquetage binutils GNU.</p>
<h3>Comment il fonctionne?</h3>
<p>Cela fonctionne comme un filtre, tout comme cpp et ses
variantes. Je ne connais pas les détails, mais il est livré avec sa
propre documentation texinfo, donc consultez-la, imprimez-la,
assimilez-la. La combinaison GAS/GASP me semble être un
macro-assembleur standard.</p>
<h2><a name="ss3.4">3.4 NASM</a></h2>
<p>Du projet Netwide Assembler est issu encore un autre assembleur,
écrit en C, qui devrait être assez modulaire pour supporter toutes
les syntaxes connues et tous les formats objets existants.</p>
<h3>Où trouver NASM?</h3>
<p><a href=
"http://www.cryogen.com/Nasm">http://www.cryogen.com/Nasm</a></p>
<p>Les versions binaires se trouvent sur votre miroir sunsite
habituel dans le répertoire <code>devel/lang/asm/</code>. Il
devrait également être disponible sous forme d'archive .rpm ou .deb
parmi les contributions à votre distribution préférée RedHat ou
Debian.</p>
<h3>Son rôle</h3>
<p>Au moment de l'écriture de ce HOWTO, NASM en est à la version
0.96.</p>
<p>La syntaxe est à la Intel. Une gestion de macros est
intégrée.</p>
<p>Les formats objets reconnus sont <code>bin</code>,
<code>aout</code>, <code>coff</code>, <code>elf</code>,
<code>as86</code>, (DOS) <code>obj</code>, <code>win32</code>, et
<code>rdf</code> (leur propre format).</p>
<p>NASM peut être utilisée comme assembleur pour le compilateur
libre LCC.</p>
<p>Comme NASM évolue rapidement, ce HowTo peut ne pas être à jour à
son sujet. A moins que vous n'utilisiez BCC comme compilateur 16
bit (ce qui dépasse le cadre de ce document), vous devriez utiliser
NASM plutôt que AS86 ou MASM, car c'est un logiciel libre avec un
excellent service après-don, qui tourne sur toutes plateformes
logicielles et matérielles.</p>
<p>Note: NASM est également livré avec un désassembleur,
NDISASM.</p>
<p>Son analyseur "grammatical", écrit à la main, le rend beaucoup
plus rapide que GAS; en contrepartie, il ne reconnaît qu'une
architecture, en comparaison de la pléthore d'architectures
reconnues par GAS. Pour les plates-formes x86, NASM semble être un
choix judicieux.</p>
<h2><a name="ss3.5">3.5 AS86</a></h2>
<p>AS86 est un assembleur 80x86, à la fois 16 et 32 bits, faisant
partie du compilateur C de Bruce Evans (BCC). Il possède une
syntaxe à la Intel.</p>
<h3>Where to get AS86</h3>
<p>Une version complètement dépassée de AS86 est diffusée par HJLu
juste pour compiler le noyau Linux, dans un paquetage du nom de
bin86 (actuellement version 0.4) disponible dans le répertoire GCC
des sites FTP Linux. Je déconseille son utilisation pour toute
autre chose que compiler Linux. Cette version ne reconnaît qu'un
format de fichiers minix modifié, que ne reconnaissent ni les
binutils GNU ni aucun autre produit. Il possède de plus certains
bogues en mode 32 bits. Ne vous en servez donc vraiment que pour
compiler Linux.</p>
<p>Les versions les plus récentes de Bruce Evans (bde@zeta.org.au)
est diffusée avec la distribution FreeBSD. Enfin, elles l'étaient!
Je n'ai pas pu trouver les sources dans la distribution 2.1.
Toutefois, vous pouvez trouver les sources dans</p>
<p><a href=
"http:///www.eleves.ens.fr:8080/home/rideau/files/bcc-95.3.12.src.tgz">
http:///www.eleves.ens.fr:8080/home/rideau/files/bcc-95.3.12.src.tgz</a></p>
<p>Le projet Linux/8086 (également appelé ELKS) s'est d'une
certaine manière chargée de maintenir bcc (mais je ne crois pas
qu'ils aient inclus les patches 32 bits). Voir les sites <a href=
"http://www.linux.org.uk/Linux8086.html">http://www.linux.org.uk/Linux8086.html</a>
et <a href="ftp://linux.mit.edu/">ftp://linux.mit.edu/</a>.</p>
<p>Entre autres choses, ces versions plus récentes, à la différence
de celle de HJLu, gèrent le format a.out de Linux; vous pouvez donc
effectuer des éditions de liens avec des programmes Linux, et/ou
utiliser les outils habituels provenant du paquetage binutils pour
manipuler vos données. Cette version peut co-exister sans problème
avec les versions précédentes (voir la question à ce sujet un peu
plus loin).</p>
<p>La version du 12 mars 1995 de BCC ainsi que les précédentes a un
problème qui provoque la génération de toutes les opérations
d'empilement/dépilement de segments en 16 bits, ce qui est
particulièrement ennuyant lorsque vous développez en mode 32 bits.
Un patch est diffusé par le projet Tunes</p>
<p><a href=
"http://www.eleves.ens.fr:8080/home/rideau/Tunes/">http://www.eleves.ens.fr:8080/home/rideau/Tunes/</a></p>
<p>à partir du lien suivant:
<code>files/tgz/tunes.0.0.0.25.src.tgz</code> ou dans le répertoire
<code>LLL/i386/</code>.</p>
<p>Le patch peut également être directement récupéré sur</p>
<p><a href=
"http://www.eleves.ens.fr:8080/home/rideau/files/as86.bcc.patch.gz">
http://www.eleves.ens.fr:8080/home/rideau/files/as86.bcc.patch.gz</a></p>
<p>Bruce Evans a accepté ce patch, donc si une version plus récente
de BCC existe, le patch devrait avoir été intégré...</p>
<h3>Comme appeller l'assembleur?</h3>
<p>Voici l'entrée d'un Makefile GNU pour utiliser bcc pour
transformer un fichier assembleur <code>.s</code> à la fois en un
objet a.out GNU <code>.o</code> et un listing <code>.l</code>:</p>
<hr>
<pre>
%.o %.l:        %.s
        bcc -3 -G -c -A-d -A-l -A$*.l -o $*.o $&lt;
</pre>
<hr>
<p>Supprimez <code>%.l</code>, <code>-A-l</code>, et
<code>-A$*.l</code>, si vous ne voulez pas avoir de listing. Si
vous souhaitez obtenir autre chose que du a.out GNU, consultez la
documentation de bcc concernant les autres formats reconnus et/ou
utilisez le programme objcopy du paquetage binutils.</p>
<h3>Où trouver de la documentation</h3>
<p>Les documentations se trouvent dans le paquetage bcc. Des pages
de manuel sont également disponibles quelque part sur le site de
FreeBSD. Dans le doute, les sources sont assez souvent une bonne
documentation: ce n'est pas très commenté mais le style de
programmation est très simple. Vous pouvez essayer de voir comment
as86 est utilisé dans Tunes 0.0.0.25...</p>
<h3>Que faire si je ne peux plus compiler Linux avec cette nouvelle
version</h3>
<p>Linus est submergé par le courrier électronique et mon patch
pour compiler Linux avec un as86 a.out n'a pas dû lui parvenir (!).
Peu importe: conservez le as86 provenant du paquetage bin86 dans le
répertoire /usr/bin, et laissez bcc installer le bon as86 en tant
que /usr/local/libexec/i386/bcc/as comme que de droit. Vous n'aurez
jamais besoin d'appeler explicitement ce dernier, car bcc se charge
très bien de tout, y compris la conversion en a.out Linux,
lorsqu'il est appelé avec les bonnes options. Assemblez les
fichiers uniquement en passant par bcc, et non pas en appelant as86
directement.</p>
<h2><a name="ss3.6">3.6 Autres assembleurs</a></h2>
<p>Il s'agit d'autres possibilités, qui sortent de la voie
ordinaire, pour le cas où les solutions précédentes ne vous
conviennent pas (mais je voudrais bien savoir pourquoi?), que je ne
recommande pas dans les cas habituels, mais qui peuvent se montrer
fort utiles si l'assembleur doit faire partie intégrante du
logiciel que vous concevez (par exemple un système d'exploitation
ou un environnement de développement).</p>
<h3>L'assembleur de Win32Forth</h3>
<p>Win32Forth est un système ANS FORTH 32 bit <em>libre</em> qui
fonctionne sous Win32s, Win95, Win/NT. Il comprend un assembleur 32
bit libre (sous forme préfixe ou postfixe) intégrée au langage
FORTH. Le traitement des macro est effectué en utilisant toute la
puissance du langage réflexif FORTH. Toutefois, le seul contexte
d'entrée et sortie reconnu actuellement est Win32For lui-même
(aucune possibilité d'obtenir un fichier objet, mais vous pouvez
toujours l'ajouter par vous-même, bien sûr). Vous pouvez trouver
Win32For à l'adresse suivante: <a href=
"ftp://ftp.forth.org/pub/Forth/win32for/">ftp://ftp.forth.org/pub/Forth/win32for/</a></p>
<h3>Terse</h3>
<p>Terse est un outil de programmation qui fournit <em>LA</em>
syntaxe assembleur la plus compacte pour la famille des processeur
x86! Voir le site <a href=
"http://www.terse.com">http://www.terse.com</a>. Ce n'est cependant
pas un logiciel libre. Il y aurait eu un clone libre quelque part,
abandonné à la suite de mensongères allégations de droits sur la
syntaxe, que je vous invite à ressusciter si la syntaxe vous
intéresse.</p>
<h3>Assembleurs non libres et/ou non 32 bits</h3>
<p>Vous trouverez un peu plus d'informations sur eux, ainsi que sur
les bases de la programmation assembleur sur x86, dans la FAQ de
Raymond Moon pour le forum comp.lang.asm.x86. Voir <a href=
"http://www2.dgsys.com/~raymoon/faq/asmfaq.zip">http://www2.dgsys.com/~raymoon/faq/asmfaq.zip</a></p>
<p>Remarquez que tous les assembleurs DOS devraient fonctionner
avec l'émulateur DOS de Linux ainsi qu'avec d'autres émulateurs du
même genre. Aussi, si vous en possédez un, vous pouvez toujours
l'utiliser à l'intérieur d'un vrai système d'exploitation. Les
assembleurs sous DOS assez récents gèrent également les formats de
fichiers objets COFF et/ou des formats gérés par la bibliothèque
GNU BFD de telle manière que vous pouvez les utiliser en
conjonction avec les outils 32 bits libres, en utilisant le
programme GNU objcopy (du paquetage binutils) comme un filtre de
conversion.</p>
<h2><a name="s4">4. Méta-programmation/macro-traitement</a></h2>
<p>La programmation en assembleur est particulièrement pénible si
ce n'est pour certaines parties critiques des programmes.</p>
<p>Pour travail donné, il faut l'outil approprié; ne choisissez
donc pas l'assembleur lorsqu'il ne correspond pas au problème à
résoudre: C, OCAML, perl, Scheme peuvent être un meilleur choix
dans la plupart des cas.</p>
<p>Toutefois, il y a certains cas où ces outils n'ont pas un
contrôle suffisamment fin sur la machine, et où l'assembleur est
utile ou nécessaire. Dans ces cas, vous apprécierez un système de
programmation par macros, ou un système de méta-programmation, qui
permet aux motifs répétitifs d'être factorisés chacun en une seule
définition indéfiniment réutilisable. Cela permet une programmation
plus sûre, une propagation automatique des modifications desdits
motifs, etc. Un assembleur de base souvent ne suffit pas, même pour
n'écrire que de petites routines à lier à du code C.</p>
<h2><a name="ss4.1">4.1 Description</a></h2>
<p>Oui, je sais que cette partie peut manquer d'informations utiles
à jour. Vous êtes libres de me faire part des découvertes que vous
auriez dû faire à la dure...</p>
<h3>GCC</h3>
<p>GCC vous permet (et vous oblige) de spécifier les contraintes
entre registres assembleurs et objets C, pour que le compilateur
puisse interfacer le code assembleur avec le code produit par
l'optimiseur. Le code assembleur en ligne est donc constitué de
motifs, et pas forcément de code exact.</p>
<p>Et puis, vous pouvez mettre du code assembleur dans des
macro-définitions de CPP ou des fonctions "en-ligne" (inline), de
telle manière que tout le monde puisse les utiliser comme n'importe
quelle fonction ou macro C. Les fonctions en ligne ressemblent
énormément aux macros mais sont parfois plus propres à utiliser.
Méfiez-vous car dans tous ces cas, le code sera dupliqué, et donc
seules les étiquettes locales (comme <code>1:</code>) devraient
être définies dans ce code assembleur. Toutefois, une macro devrait
permettre de passer en paramètre le nom éventuellement nécessaire
d'une étiquette définie non localement (ou sinon, utilisez des
méthodes supplémentaires de méta-programmation). Notez également
que propager du code assembleur en-ligne répandra les bogues
potentiels qu'il contiendrait, aussi, faites doublement attention à
donner à GCC des contraintes correctes.</p>
<p>Enfin, le langage C lui-même peut être considéré comme étant une
bonne abstraction de la programmation assembleur, qui devrait vous
éviter la plupart des difficultés de la programmation
assembleur.</p>
<p>Méfiez-vous des optimisations consistant à passer les arguments
en utilisant les registres: cela interdit aux fonctions concernées
d'être appelées par des routines exterieurs (en particulier celles
écrites à la main en assembleur) d'une manière standard; l'attribut
asmlinkage devrait empêcher des routines données d'être concernées
par de telles options d'optimisation. Voir les sources du noyau
Linux pour avoir des exemples.</p>
<h3>GAS</h3>
<p>GAS a quelques menues fonctionnalité pour les macro, détaillées
dans la documentation TeXinfo. De plus</p>
<p>J'ai entendu dire que les versions récentes en seront dotées...
voir les fichiers TeXinfo). De plus, tandis que GCC reconnaît les
fichiers en .s comme de l'assembleur à envoyer dans GAS, il
reconnaît aussi les fichiers en .S comme devant être filtrer à
travers CPP avant d'être envoyer à GAS. Au risque de me répéter, je
vous convie à consulter les sources du noyau Linux.</p>
<h3>GASP</h3>
<p>Il ajoute toutes les fonctionnalités habituelles de macro à GAS.
Voir sa documentation sous forme texinfo.</p>
<h3>NASM</h3>
<p>NASM possède aussi son système de macros. Consultez sa
documentation. Si vous avez quelqu'idée lumineuse, contactez les
auteurs, étant donné qu'ils sont en train de développer NASM
activement. Pendant ce même temps, lisez la partie sur les filtres
externes un peu plus loin.</p>
<h3>AS86</h3>
<p>Il possède un système simple de macros, mais je n'ai pas pu
trouver de documentation. Cependant, les sources sont d'une
approche particulièrement aisée, donc si vous êtes intéressé pour
en savoir plus, vous devriez pouvoir les comprendre sans problème.
Si vous avez besoin d'un peu plus que des bases, vous devriez
utiliser un filtre externe (voir un peu plus loin).</p>
<h3>Autres assembleurs</h3>
<ul>
<li>Win32FORTH: CODE et END-CODE sont des macros qui ne basculent
pas du mode interprétation au mode compilation; vous aurez donc
accès à toute la puissance du FORTH lors de l'assemblage.</li>
<li>Tunes: cela ne fonctionne pas encore, mais le langage Scheme
est un langage de très haut niveau qui permet une
méta-programmation arbitraire.</li>
</ul>
<h2><a name="ss4.2">4.2 Filtres externes</a></h2>
<p>Quelque soit la gestion des macros de votre assembleur, ou
quelque soit le langage que vous utilisez (même le C), si le
langage n'est pas assez expressif pour vous, vous pouvez faire
passer vos fichier à travers un filtre externe grâce à une règle
comme suit dans votre Makefile:</p>
<hr>
<pre>
%.s:    %.S autres_dépendances
        $(FILTER) $(FILTER_OPTIONS) &lt; $&lt; &gt; $@
</pre>
<hr>
<h3>CPP</h3>
<p>CPP n'est vraiment pas très expressif, mais il suffit pour les
choses faciles, et il est appelé d'une manière transparente par
GCC.</p>
<p>Comme exemple de limitation, vous ne pouvez pas déclarer d'objet
de façon à ce qu'un destructeur soit automatiquement appelé à la
fin du bloc ayant déclaré l'objet. Vous n'avez pas de diversions ou
de gestion de portée des variables, etc.</p>
<p>CPP est livré avec tout compilateur C. Si vous pouvez faire
sans, n'allez pas chercher CPP (bien que je me demande comment vous
pouvez faire).</p>
<h3>M4</h3>
<p>M4 vous donne la pleine puissance du macro-traitement, avec un
langage Turing-équivalent, récursivité, expressions régulières,
etc. Vous pouvez faire avec tout ce que cpp ne peut faire.</p>
<p>Voir macro4th/This4th que l'on trouve sur <a href=
"ftp://ftp.forth.org/pub/Forth/">ftp://ftp.forth.org/pub/Forth/</a>
dans Reviewed/ ANS/ (?), ou les sources de Tunes 0.0.0.25 comme
exemple de programmation avancée en utilisant m4.</p>
<p>Toutefois, le système de citation est très pénible à utiliser et
vous oblige à utiliser un style de programmation par fonctions
récursives avec passage explicite de continuation (CPS) pour toute
programmation <em>avancée</em> (ce qui n'est pas sans rappeler à
TeX -- au fait quelqu'un a-t-il déjà essayé d'utiliser TeX comme
macro-processeur pour autre chose que de la mise-en-page?).
Toutefois, ce n'est pas pire que cpp qui ne permet ni citation ni
récursivité.</p>
<p>La bonne version de m4 à récupérer est GNU m4 1.4 (ou ultérieure
si elle existe). C'est celle qui contient le plus de fonctionnalité
et le moins de bogues ou de limitations. m4 est conçu pour être
intrinsèquement lent pour toute utilisation sauf la plus simple;
cela suffit sans aucun doute pour la plupart des programmes en
assembleur (vous n'allez quand même pas écrire des millions de
lignes en assembleur, si?).</p>
<h3>Macro-traitement avec votre propre filtre</h3>
<p>Vous pouvez écrire votre propre programme d'expansion de macro
avec les outils courants comme perl, awk, sed, etc. C'est assez
rapide à faire et vous pouvez tout contrôler. Mais bien toute
puissance dans le macro-traitement doit se gagner à la dure.</p>
<h3>Méta-programmation</h3>
<p>Plutôt que d'utiliser un filtre externe qui effectue l'expansion
des macros, une manière de réaliser cela est d'écrire des
programmes qui écrivent d'autres programmes, en partie ou en
totalité.</p>
<p>Par exemple, vous pourriez utiliser un programme générant du
code source</p>
<ul>
<li>pour créer des tables de sinus/cosinus (ou autre),</li>
<li>pour décompiler un fichier binaire en source annoté
annoté,</li>
<li>pour compiler vos bitmaps en des routines d'affichage
rapides,</li>
<li>pour extraire de la documentation, du code d'initilisation ou
finalisation, des tables de descriptions, aussi bien que du code
normal depuis les mêmes fichiers sources;</li>
<li>pour utiliser une technique spécifique de production de code,
produite avec un script perl/shell/scheme</li>
<li>pour propager des données définies en une seule fois dans de
nombreux morceaux de code ou tables avec références croisées.</li>
<li>etc.</li>
</ul>
<p>Pensez-y!</p>
<h3>Backends provenant de compilateur existants</h3>
<p>Des compilateurs comme SML/NJ, Objective CAML, MIT-Scheme, etc,
ont leur propre générateur de code assembleur, que vous pouvez ou
non utiliser, si vous souhaitez générer du code
semi-automatiquement depuis les langages correspondants.</p>
<h3>Le New-Jersey Machine-Code Toolkit</h3>
<p>Il s'agit projet utilisant le langage de programmation Icon pour
bâtir une base de code de manipulation d'assembleur. Voir <a href=
"http://www.cs.virginia.edu/~nr/toolkit/">http://www.cs.virginia.edu/~nr/toolkit/</a></p>
<h3>Tunes</h3>
<p>Le projet de système d'exploitation OS développe son propre
assembleur comme étant une extension du langage Scheme. Il ne
fonctionne pas encore totalement, de l'aide est bienvenue.</p>
<p>L'assembleur manipule des arbres de syntaxes symboliques, de
telle manière qu'il puisse servir comme base d'un traducteur de
syntaxe assembleur, un désassembleur, l'assembleur d'un
compilateur, etc. Le fait qu'il utile un vrai langage de
programmation puissant comme Scheme le rend imbatable pour le
macro-traitement et pour la méta-programmation.</p>
<p><a href=
"http://www.eleves.ens.fr:8080/home/rideau/Tunes/">http://www.eleves.ens.fr:8080/home/rideau/Tunes/</a></p>
<h2><a name="s5">5. Conventions d'appel</a></h2>
<h2><a name="ss5.1">5.1 Linux</a></h2>
<h3>Edition de liens avec GCC</h3>
<p>C'est la solution la plus pratique. Consultez la documentation
de gcc et prenez exemple sur les sources du noyau Linux (fichiers
<code>.S</code> qui sont utilisés avec gas, non pas as86).</p>
<p>Les arguments 32 bits sont empilés dans la pile vers le bas dans
l'ordre inverse de l'ordre syntaxique (c'est-à-dire qu'on accède
aux arguments ou les dépile dans l'ordre syntaxique), au-dessus de
l'adresse de retour 32 bits. <code>%ebp</code>, <code>%esi</code>,
<code>%edi</code>, <code>%ebx</code> doivent être conservés par
l'appelé, les autres registres peuvent être détruits;
<code>%eax</code> doit contenir le résultat, ou
<code>%edx:%eax</code> pour des résultats sur 64 bits.</p>
<p>Pile virgule flottante: je ne suis pas sûr, mais je pense que le
résultat se trouve dans <code>st(0)</code>, la pile étant à la
discrétion de l'appelé.</p>
<p>Notez que GCC possède certaines options pour modifier les
conventions d'appel en réservant certains registres, en mettant les
arguments dans des registres, en supposant que l'on ne possède pas
de FPU, etc. Consultez les pages .info concernant le i386.</p>
<p>Il faut prendre garde à déclarer l'attribut <code>cdecl</code>
pour une fonction qui suit la convention standard GCC (je ne sais
pas exactement ce que cela produit avec des conventions modifiées).
Consultez la documentation GCC dans la section: <code>C
Extensions::Extended Asm::</code></p>
<h3>Problèmes ELF et a.out</h3>
<p>Certains compilateurs C ajoutent un underscore avant tout
symbole, alors que d'autres ne le font pas.</p>
<p>En particulier, la version GCC a.out effectue ce genre d'ajouts,
alors que la version ELF ne le fait pas.</p>
<p>Si vous êtes confronté à ce problème, regardez comment des
paquetages existants traitent le problèmes. Par exemple, récupérer
une ancienne arborescence des sources de Linux, Elk, les qthreads
ou OCAML...</p>
<p>Vous pouvez également redéfinir le renommage implicite de C en
assembleur en ajoutant les instructions suivantes:</p>
<hr>
<pre>
        void truc asm("machin") (void);
</pre>
<hr>
pour s'assurer que la fonction C truc sera réellement appelée
machin en assembleur.
<p>Remarquez que l'outil <code>objcopy</code>, du paquetage
<code>binutils</code>, devrait vous permettre de transformer vos
fichiers objets a.out en objets ELF et peut-être inversement dans
certains cas. D'une manière plus générale, il vous permet
d'effectuer de nombreuses conversions de formats de fichiers.</p>
<h3>Appels systèmes directs</h3>
<p>Il n'est absolument pas recommandé d'effectuer de tels appels
par ce que leurs conventions peuvent changer de temps en temps, ou
d'un type de noyau à un autre (cf L4Linux), de plus, ce n'est pas
portable, difficile à écrire, redondant avec l'effort entrepris par
libc, et enfin, cela empêche les corrections et les extensions
effectuées à travers la libc, comme par exemple avec le programme
<code>zlibc</code> qui réalise une décompression à la volée de
fichiers compressés avec gzip. La manière standard et recommendée
d'effectuer des appels systèmes est et restera de passer par la
libc.</p>
<p>Les objets partagés devraient réduire l'occupation mémoire des
programmes, et si vous souhaitez absolument avoir de petits
exécutables, utilisez <code>#!</code> avec un interpréteur qui
contiendra tout ce que vous ne voulez pas mettre dans vos
binaires.</p>
<p>Maintenant, si pour certaines raisons, vous ne souhaitez pas
effectuer une édition des liens avec la libc, récupérez-la et
essayez de comprendre comment elle fonctionne! Après tout, vous
prétendez bien la remplacer non?</p>
<p>Vous pouvez aussi regarder comment <a href=
"ftp://ftp.forth.org/pub/Forth/Linux/linux-eforth-1.0c.tgz">eforth
1.0c</a> le fait.</p>
<p>Les sources de Linux sont fort utiles, en particulier le fichier
d'en-tête asm/unistd.h qui décrit comment sont effectués les appels
système...</p>
<p>Le principe général est d'utiliser l'instruction <code>int
$0x80</code> avec le numéro de l'appel système
<code>__NR_</code>machin (regarder dans <code>asm/unistd.h</code>)
dans <code>%eax</code>, et les paramètres (jusqu'à cinq) dans
<code>%ebx</code>, <code>%ecx</code>, <code>%edx</code>,
<code>%esi</code>, <code>%edi</code>. Le résultat est renvoyé dans
<code>%eax</code> avec un résultat négatif étant l'erreur dont
l'opposé est tranféré par la libc dans errno. La pile utilisateur
n'est pas modificée donc n'avez pas besoin d'en avoir une correcte
lors de l'appel.</p>
<h3>Entrées/sorties sous Linux</h3>
<p>Si vous souhaitez effectuer des entrées/sorties directement sous
Linux, soit il s'agit de quelque chose de très simple qui n'a pas
besoin de spécificités du système et dans ce cas là, consultez le
mini-HOWTO <code>IO-Port-Programming</code>, ou alors vous devez
créer un nouveau gestionnaire de périphérique et vous devriez alors
lire quelques documents sur les méandres du noyau, le développement
de gestionnaires de périphériques, les modules du noyau, etc. Vous
trouverez d'excellents HOWTO ou autres documents du projet LDP.</p>
<p>Plus particulièrement, si vous souhaitez réaliser des programmes
graphiques, rejoignez le projet GGI: <a href=
"http://synergy.caltech.edu/~ggi/">http://synergy.caltech.edu/~ggi/</a>
<a href=
"http://sunserver1.rz.uni-duesseldorf.de/~becka/doc/scrdrv.html">http://sunserver1.rz.uni-duesseldorf.de/~becka/doc/scrdrv.html</a></p>
<p>Dans tous les cas, vous devriez plutôt utiliser l'assembleur en
ligne de GCC avec les macros provenant des fichiers linux/asm/*.h
que d'écrire des sources en assembleur pur.</p>
<h3>Accéder aux gestionnaires 16 bits avec Linux/i386</h3>
<p>De telles choses sont théoriquement possibles (preuve: voir
comment DOSEMU permet à des programmes d'accéder au port série), et
j'ai entendu des rumeurs que certaines personnes le font (avec le
gestionnaire PCI? Accès aux cartes VESA? PnP ISA? Je ne sais pas).
Si vous avez de plus amples précisions à ce sujet, soyez les
bienvenus. Le bon endroit à regarder est les sources du noyau, les
sources de DOSEMU (et des autres programmes se trouvant dans
<a href="ftp://tsx-11.mit.edu/pub/linux/ALPHA/dosemu/">le
répertoire DOSEMU</a>), ainsi que les sources d'autres programmes
bas niveaux (peut-être GGI s'il gère les cartes VESA).</p>
<p>En fait, vous devez utiliser soit le mode protégé 16 bits, soit
le mode vm86.</p>
<p>Le premier est plus simple à configurer mais il ne fonctionne
qu'avec du code ayant un comportement propre qui n'effectue pas
d'arithmétique de segments ou d'adressage absolu de segment (en
particulier pour l'adressage du segment 0), à moins que par chance
tous les segments utilisés peuvent être configuré à l'avance dans
le LDT.</p>
<p>La seconde possiblité permet d'être plus "compatibles" avec les
environnements 16 bits mais il nécessite une gestion bien plus
compliquée.</p>
<p>Dans les deux cas, avant de sauter sur le code 16 bits, vous
devez:</p>
<ul>
<li>mmapper toute adresse absolue utilisée dans le code 16 bits
(comme la ROM, les tampons vidéo, les adresses DMA et les
entrées/sorties passant des zones de mémoires mappées) à partir de
/dev/mem dans votre espace d'adressage de votre processus.</li>
<li>configurer le LDT et/ou le moniteur en mode vm86.</li>
<li>demander au noyau les droits d'accès nécessaires pour les
entrées/sorties (voir plus haut).</li>
</ul>
<p>Encore une fois, lisez attentivement les codes sources situés
dans le répertoire de DOSEMU et consorts, en particulier ces
mini-émulateurs permettant de faire tourner des programmes ELKS
et/ou des .COM assez simples sous Linux/i386.</p>
<h2><a name="ss5.2">5.2 DOS</a></h2>
<p>La plupart des émulateurs DOS sont livrés avec certaines
interfaces d'accès aux services DOS. Lisez leur documentation à ce
sujet, mais bien souvent, ils ne font que simuler <code>int
$0x21</code> et ainsi de suite, donc c'est comme si vous étiez en
mode réel (je doute qu'ils aient de possibilités de fonctionner
avec des opérandes 32 bits: ils ne font que réfléchir
l'interruption dans le mode réel ou dans le gestionnaire vm86).</p>
<p>Certaines documentations concernant DPMI (ou ses variantes
peuvent) être trouvées sur <a href=
"ftp://x2ftp.oulu.fi/pub/msdos/programming/">ftp://x2ftp.oulu.fi/pub/msdos/programming/</a></p>
<p>DJGPP est livré avec son propre sous-ensemble, dérivé, ou
remplacement (limité) de la glibc.</p>
<p>Il est possible d'effectuer une compilation croisée de Linux
vers DOS. Consultez le répertoire devel/msdos/ de votre miroir FTP
de sunsite.unc.edu. Voir également le dos-extender MOSS du projet
Flux d'utah.</p>
<p>D'autres documentations et FAQ sont plus consacrés à DOS. Nous
déconseillons le développement sous DOS.</p>
<h2><a name="ss5.3">5.3 Windauberies...</a></h2>
<p>Heu, ce document ne traite que de libre logiciel. Téléphonez-moi
lorsque Windaube le deviendra ou du moins ses outils de
développement!</p>
<p>En fait, après tout, cela existe: <a href=
"http://www.cygnus.com">Cygnus Solutions</a> a développé la
bibliothèque cygwin32.dll pour que les programmes GNU puissent
fonctionner sur les machines MicroMerdiques. Donc, vous pouvez
utiliser GCC, GAS et tous les outils GNU ainsi que bon nombre
d'applications Unix. Consultez leur site Web. Je (Faré) ne souhaite
pas m'étendre sur la programmation sous Windaube, mais je suis sûr
que vous trouverez tout un tas d'informations partout...</p>
<h2><a name="ss5.4">5.4 Votre propre système
d'exploitation</a></h2>
<p>Le contrôle sur le système étant ce qui attire de nombreux
programmeurs vers l'assembleur, une prémisse ou un corollaire
naturel de son utilisation est la volonté de développer son propre
système d'exploitation. Remarquons tout d'abord que tout système
permettant son auto-développement pourrait être qualifié de système
d'exploitation, combien même tournerait-il au-dessus d'un autre
système sur lequel il se déchargerait de la gestion du multitâche
(Linux sur Mach) ou des entrées/sorties (OpenGenera sur Digital
Unix), etc. Donc, pour simplifier le débogage, vous pouvez
souhaiter développer votre système d'exploitation comme étant un
processus fonctionnant sous Linux (au prix d'un certain
ralentissement), puis, utiliser le <a href=
"http://ww.cs.utah.edu/projects/flux/">Flux OS kit</a> (qui permet
l'utilisation des drivers Linux et BSD dans votre propre système
d'exploitation) pour le rendre indépendant. Lorsque votre système
est stable, il est toujours temps d'écrire vos propres
gestionnaires de matériels si c'est vraiment votre passion.</p>
<p>Ce HowTo ne couvrira pas des sujets comme le code de chargement
du système, le passage en mode 32 bits, la gestion des
interruptions, les bases concernant les horreurs des processeurs
Intel (mode protégé, V86/R86), la définition de votre format
d'objets ou de vos conventions d'appel. L'endroit où vous pourrez
trouver le plus d'informations concernant tous ces sujets est le
code source de système déjà existants.</p>
<p>Un grand nombre de pointeurs se trouvent dans la page: <a href=
"http://www.eleves.ens.fr:8080/home/rideau/Tunes/Review/OSes.html">http://www.eleves.ens.fr:8080/home/rideau/Tunes/Review/OSes.html</a></p>
<h2><a name="s6">6. A faire et pointeurs</a></h2>
<ul>
<li>compléter les sections incomplètes;</li>
<li>ajouter des pointeurs sur des programmes et des
documentations;</li>
<li>ajouter des exemples de tous les jours pour illustrer la
syntaxe, la puissance et les limitation de chacune des solutions
proposées;</li>
<li>demander aux gens de me donner un coup de main;</li>
<li>trouver quelqu'un qui a assez de temps pour prendre en charge
la maintenance de ce HOWTO;</li>
<li>peut-être dire quelques mots sur l'assembleur d'autres
plates-formes?</li>
<li>Quelques pointeurs (en plus de ceux qui se trouvent dans ce
document)
<ul>
<li><a href="http://www.intel.com/design/pentium/manuals/">pages de
manuel pour pentium</a></li>
<li><a href="http://www.eng.ufl.edu/ftp">hornet.eng.ufl.edu pour
les codages assembleurs</a></li>
<li><a href=
"ftp://ftp.luth.se/pub/msdos/demos/code/">ftp.luth.se</a></li>
<li><a href="ftp://zfja-gate.fuw.edu.pl/cpu/protect.mod">PM
FAQ</a></li>
<li><a href="http://www.fys.ruu.nl/~faber/Amain.html">Page
Assembleur 80x86</a></li>
<li><a href=
"http://www.cit.ac.nz/smac/csware.htm">Courseware</a></li>
<li><a href=
"http://www.ee.ucl.ac.uk/~phart/gameprog.html">programmation de
jeux</a></li>
<li><a href="http://bewoner.dma.be/JanW">experiences de
programmation sous Linux exclusivement en assembleur</a></li>
</ul>
</li>
<li>Et bien sur, utilisez vos outils habituels de recherche sur
Internet pour trouver les informations. Merci de m'envoyer tout ce
que vous trouvez d'interessant.</li>
</ul>
<p>Signature de l'auteur:</p>
<pre>
--    ,                                         ,           _ v    ~  ^  --
--
-- Fare -- rideau@clipper.ens.fr -- Francois-Rene Rideau -- +)ang-Vu Ban --
--                                      '                   / .          --
Join the TUNES project for a computing system based on computing freedom!
                 TUNES is a Useful, Not Expedient System
WWW page at URL: http://www.eleves.ens.fr:8080/home/rideau/Tunes/
</pre>
</body>
</html>