Précédent   Forum du club des développeurs et IT Pro > Autres langages > Assembleur > Programmation d'OS
Programmation d'OS Programmation de systèmes d'exploitation
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse
 
Outils de la discussion
Publicité
'
Vieux 25/11/2011, 02h59   #1
romfox17
Nouveau Membre du Club
 
Homme Romain
Inscription : avril 2011
Messages : 60
Détails du profil
Informations personnelles :
Nom : Homme Romain
Âge : 21
Localisation : France, Charente Maritime (Poitou Charente)

Informations forums :
Inscription : avril 2011
Messages : 60
Points : 30
Points : 30
Par défaut Projet mini os embarqué

Salut a tous. Moi c'est Romain, j'approche les 20 ans, je ne fais aucune étude, et actuellement je me suis lancé un petit défi que j'ai vite beaucoup apprécié : un mini OS entièrement fait par moi.
Alors dans ce sens j'entend système de fichier fat12 ou fat16 et quelques utilitaires, ça serait niquel :p

Je suis débutant en asm mais j'aime ça
Actuellement j'ai un secteur de boot qui charge une IDT, initialise les segments, charge les secteurs suivants en 0x1000 et y saute.
Puis c'est mon noyau précédement chargé qui prend la main, il charge une GDT, rempli juste les descripteurs d'interruptions qui seront utiles au timer et au clavier (IRQ0 et IRQ1), programme les PICS (le pic maitre pointe sur mes descripteurs préalablement remlis, et je masque toutes les interruptions sauf le clavier et le timer), puis je démare les interruptions.
J'ai également fais quelques fonctions dont j'ai eu besoin. Mon driver clavier gère quelques touches de base.
Biensur le code n'a pas été revu, tout cela est assez brouillon, mais je le poste pour avoir des critiques sur ma facon de coder.

boot32.asm:

Code :
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
 
%define BASE    0x100  ; 0x0100:0x0 = 0x1000
%define KSIZE   50     ; nombre de secteurs a charger
 
[BITS 16]
[ORG 0x00]
 
jmp start
%include "fn_boot.inc"
start:
 
; initialisation des segments en 0x07C0
    mov ax, 0x07C0
    mov ds, ax
    mov es, ax
    mov ax, 0x8000    ; stack en 0xFFFF
    mov ss, ax
    mov sp, 0xf000
 
; recuparation de l'unite de boot
    mov [bootdrv], dl    
 
; affiche un msg
    mov si, msgDebut
    call print16
 
; charger le noyau
    xor ax, ax
    int 0x13
 
    push es
    mov ax, BASE
    mov es, ax
    mov bx, 0
    mov ah, 2
    mov al, KSIZE
    mov ch, 0
    mov cl, 2
    mov dh, 0
    mov dl, [bootdrv]
    int 0x13
    pop es
 
; initialisation du pointeur sur la GDT
    mov ax, gdtend    ; calcule la limite de GDT
    mov bx, gdt
    sub ax, bx
    mov word [gdtptr], ax
 
    xor eax, eax      ; calcule l'adresse lineaire de GDT
    xor ebx, ebx
    mov ax, ds
    mov ecx, eax
    shl ecx, 4
    mov bx, gdt
    add ecx, ebx
    mov dword [gdtptr+2], ecx
 
; passage en modep
    cli
    lgdt [gdtptr]    ; charge la gdt
    mov eax, cr0
    or  ax, 1
    mov cr0, eax        ; PE mis a 1 (CR0)
 
    jmp next
next:
    mov ax, 0x10        ; segment de donne
    mov ds, ax
    mov fs, ax
    mov gs, ax
    mov es, ax
    mov ss, ax
    mov esp, 0x9F000    
 
    jmp dword 0x8:0x1000    ; reinitialise le segment de code
 
;--------------------------------------------------------------------
bootdrv:  db 0
msgDebut: db "Loading GDT and jumping to CS:0x1000...", 13, 10, 0
;--------------------------------------------------------------------
gdt:
    db 0, 0, 0, 0, 0, 0, 0, 0
gdt_cs:
    db 0xFF, 0xFF, 0x0, 0x0, 0x0, 10011011b, 11011111b, 0x0
gdt_ds:
    db 0xFF, 0xFF, 0x0, 0x0, 0x0, 10010011b, 11011111b, 0x0
gdtend:
;--------------------------------------------------------------------
gdtptr:
    dw 0  ; limite
    dd 0  ; base
;--------------------------------------------------------------------
 
;; NOP jusqu'a 510
times 510-($-$$) db 144
dw 0xAA55
kernel32.asm :

Code :
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
 
%define IDTSIZE 50    ; Nombre d'interruptions
%define BASE 0x1000   
 
; -------------------------------------------------------------
 
[BITS 32]
[ORG 0x1000]
 
jmp debut
 
%include "fn.inc"
 
debut:
    call clear
    mov esi, msgKernel
    call print
 
    lidt [idtptr]
    mov eax, int_clock             ; Init IRQ0
    mov word [idt+32*8], ax            
    mov word [idt+32*8+2], 0x08
    mov word [idt+32*8+4], 0x8e00
    shr eax, 16
    mov word [idt+32*8+6], ax
 
    mov eax, int_kbd               ; Init IRQ1
    mov word [idt+33*8], ax
    mov word [idt+33*8+2], 0x08
    mov word [idt+33*8+4], 0x8e00
    shr eax, 16
    mov word [idt+33*8+6], ax
 
    call remap_pic
 
    sti
 
    jmp $
 
; -------------------------------------------------------------
; IRQ0 : Timer
; -------------------------------------------------------------
 
int_clock:
    mov al, 0x20
    out 0x20, al
    iret
 
; -------------------------------------------------------------
; IRQ1 : Driver Clavier     A chaque fin de ligne la chaine est dans buff_cmd
; -------------------------------------------------------------
 
int_kbd:
    cli
 
.wait:
    in al, 0x64
    and al, 1
    jz .wait
 
    in al, 0x60
 
    cmp al, 224
    je .wait
 
    cmp al, 0xf0
    jl .release
 
    cmp al, 0x3f
    je .refresh
 
    cmp al, 0x0e
    je .backspace
 
    cmp al, 0x2a
    je .shift_enable
 
    movzx ebx, byte [shift]
    call convert_scan
    call putc
 
.refresh:
    call clear
    jmp .end
 
.shift_enable:
    mov byte [shift], 1
    jmp .end
 
.shift_disable:
    mov byte [shift], 0
    jmp .end
 
.release:
    sub al, 0x80
    cmp al, 0x2a
    je .shift_disable
    jmp .end
 
; Backspace, seulement sur la meme ligne pour l'instant
.backspace:
    movzx eax, byte [posx]
    cmp eax, 1
    jl .end
    sub byte [posx], 1
    mov esi, buff_space
    call putc
    sub byte [posx], 1
    call move_cursor
 
.end:
    mov al, 0x20
    out 0x20, al
    sti
    iret
 
; -------------------------------------------------------------
 
msgKernel: db 'Kernel loaded...', 10, 13, 'Welcome to RomOS 0.1', 13, 10, 'Press F5 to refresh sreen.', 10, 0
buff_space: db ' '
shift: db 0
 
buff_cmd: times 256 db 0
buff_cmd_size: db 0
 
;--------------------------------------------------------------------
 
idt:                             ; idt est la table d'interruptions
    times (IDTSIZE*8) db 0       ; 8 * 50 octets aloués (taille_idt_descriptor * nb_interrupt)
 
idtptr:
    dw (IDTSIZE << 3) - 1  ; Nombre de vecteurs d'interruption * 8 - 1
    dd (BASE+idt-$$)    ;  Adresse de la table
 
; -------------------------------------------------------------
 
;; NOP jusqu'a 4096
times 4096-($-$$) db 90
fn.inc :

Code :
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
; -------------------------------------------------------------
; Remplit la chaine ESI de ECX fois
; -------------------------------------------------------------
clear_string:
    pusha
    mov eax, 0
        mov edi, esi
 
.debut:
    stosb
    add edi, 1
    loop .debut
    popa
 
    ret
 
; -------------------------------------------------------------
; Converti scan-code en ASCII    (puis l'affiche pour l'instant)
 
; AL = Scan-code     EBX = Décalage
; -------------------------------------------------------------
 
convert_scan:
    push edi
    push eax
 
    dec eax
    shl eax, 1       ; Scancode x 2 
    mov edi, keyb_fr
    add edi, ebx
    add edi, eax
    mov esi, edi
 
    pop eax
    pop edi    
    ret
 
; -------------------------------------------------------------
; PUTC : Affiche le char dans ESI
; -------------------------------------------------------------
 
putc:
    pusha
 
.debut:  
    lodsb
    cmp al, 0
    jz .end
    cmp al, 10
    je .nl
    mov ah, 3           ; Couleur
    push eax            ; Push le char
 
; Calcul:
    movzx eax, byte [posy]
    mov ebx, 160
    mul ebx
    mov ebx, eax
 
    movzx eax, byte [posx]
    shl eax, 1
 
    mov edi, 0xb8000
    add edi, eax
    add edi, ebx
 
; Ecriture:
    pop eax           ; Pop le char
    mov word [ds:edi], ax
    add byte [posx], 1
    movzx eax, byte [posx]
    cmp eax, 80
    je .nl
.cont:
    movzx eax, byte [posy]
    cmp eax, 25
    je .np
    jmp .end
 
.end:
    call move_cursor
    popa
    ret
 
; New page:
.np:
    call clear
    jmp .end
 
; New line
.nl:
    add byte [posy], 1
    mov byte [posx], 0
    jmp .cont
 
; -------------------------------------------------------------
; PRINT : Fonction d'affichage en mode protégé
 
; ESI = Chaine
; -------------------------------------------------------------
 
print:
    pusha
 
.debut:  
    lodsb
    cmp al, 0
    jz .end
    cmp al, 10
    je .lf
    cmp al, 13
    je .cr
    mov ah, 3
    push eax
 
; Calcul:
    movzx eax, byte [posy]
    mov ebx, 160
    mul ebx
    mov ebx, eax
 
    movzx eax, byte [posx]
    shl eax, 1
 
    mov edi, 0xb8000
    add edi, eax
    add edi, ebx
 
; Ecriture:
    pop eax
    mov word [ds:edi], ax
    add byte [posx], 1
    movzx eax, byte [posx]
    cmp eax, 80
    je .lf
.cont:
    movzx eax, byte [posy]
    cmp eax, 25
    je .np
    call move_cursor
    jmp .debut
 
.end:
    popa
    ret
 
; New page:
.np:
    call clear
    jmp .debut
 
; Carriage-return
.cr: 
    mov byte [posx], 0
    jmp .debut
 
; Line-feed:
.lf:
    add byte [posy], 1
    mov byte [posx], 0
    jmp .cont
 
; -------------------------------------------------------------
; PRINT_REG : Fonction d'affichage registre 32bits
; -------------------------------------------------------------
 
print_reg:
    pusha
    mov edi, outreg
    mov eax, [reg32]
    mov esi, hexchar
    mov ecx, 8
 
.debut:
    rol eax, 4
    mov ebx, eax
    and ebx, 0x0f
    mov bl, [esi+ebx]
    mov [edi], bl
 
    inc edi
    dec ecx
    jnz .debut
 
; End:
    mov esi, outreg
    call print
    popa
    ret
 
; -------------------------------------------------------------
; Fonction Clear
; -------------------------------------------------------------
 
clear:
    pusha
    mov byte [posx], 0
    mov byte [posy], 0
    mov ecx, 80*25
    dec ecx
.loop
    mov esi, space_buff
    call putc
    dec ecx
    cmp ecx, 0
    jne .loop
 
; Clear le dernier byte de l'écran
    mov byte [ds:0xb8f9f], 1
    mov byte [ds:0xb8fa0], ' '
 
    mov byte [posx], 0
    mov byte [posy], 0   
 
    call move_cursor
 
    popa
    ret
 
; -------------------------------------------------------------
; Fonction qui remap les PICs
; -------------------------------------------------------------
 
remap_pic:
    pusha
 
; ICW1 : Séquence d'initalisation:
 
    mov al, 0x11
    out 0x20, al
    out 0xA0, al
    jmp .2
 
; ICW2 : On remap sur les bon vecteur
 
.2:
    mov al, 0x20
    out 0x21, al  
    mov al, 0x28
    out 0xA1, al
    jmp .3
 
; ICW3 : On relie les pic entre eux
 
.3:
    mov al, 0x08
    out 0x21, al
    mov al, 0x03
    out 0xA1, al
    jmp .4
 
; ICW4 : Mode par défaut
 
.4:
    mov al, 0x01
    out 0x21, al
    out 0xA1, al
 
; Mask : 
 
    mov al, 0xfc
    out 0x21, al
    mov al, 0xff
    out 0xA1, al
 
    popa
    ret
 
; -------------------------------------------------------------
; Fonction de mise a jour du curseur
; -------------------------------------------------------------
 
move_cursor:
    pusha
    movzx eax, byte [posx]
    shl eax, 8
    add al, byte [posy]
    mov ebx, eax
 
    and eax, 0xff
    mov ecx, 80
    mul ecx
 
    mov ecx, ebx
    shr ecx, 8
    add eax, ecx
 
    mov ecx, eax
 
 
; Low byte of pos
    mov al, 0x0f
    mov dx, 0x3d4
    out dx, al
    mov eax, ecx
    mov dx, 0x3d5
    out dx, al
 
; High byte of pos
    mov al, 0x0e
    mov dx, 0x3d4
    out dx, al
    mov eax, ecx
    shr eax, 8
    mov dx, 0x3d5
    out dx, al
    popa
    ret
 
 
 
; -------------------------------------------------------------
 
    hexchar: db '0123456789abcdef'
    outreg: db '00000000', 0
    reg32: dd 0
    space_buff: db ' '
 
    posx: db 0
    posy: db 0
 
    keyb_fr: db 0, 0, '1', 0, '2', 0, '3', 0, '4', 0, '5', 0, '6', 0, '7', 0, '8', 0, '9', 0, '0', 0, ')', 0, '=', 0, 0x08, 0x08, 0, 0, 'a', 'A', 'z', 'Z', 'e', 'E', 'r', 'R', 't', 'T', 'y', 'Y', 'u', 'U', 'i', 'I', 'o', 'O', 'p', 'P', '^', '¨', '$', '£' , 10, 10, 0, 0, 'q', 'Q', 's', 'S', 'd', 'D', 'f', 'F', 'g', 'G', 'h', 'H', 'j', 'J', 'k', 'K', 'l', 'L', 'm', 'M', 'ù', '%', 0, 0, 0, 0, 0, 0, 'w', 'W', 'x', 'X', 'c', 'C', 'v', 'V', 'b', 'B', 'n', 'N', ',', '?', ';', '.', ':', '/', '!', '§', 0, 0, 0, 0, 0, 0, ' ', ' ', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 00, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
fn_boot.inc :

Code :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
; -------------------------------------------------------------
; Fonction d'affichage qui utilise le BIOS
; -------------------------------------------------------------
print16:
 
   push ax
   push bx
 
.debut:
   lodsb
   or al, al ; zero=end of str
   jz .end   ; get out
   mov ah, 0x0E
   mov bl, 0xff
   int 0x10
   jmp .debut
 
.end:
   pop bx
   pop ax
   ret
Voila Je pense que je vais faire une fonction strcmp histoire d'implementer un 'help' :p Et qui me servira pour la suite. Et surtout je me penche sur les systèmes de fichiers la...

Edit : tout est en assembleur pour 2 raison : je voulais le faire pour m'y familiariser et étant sous windows actuelement j'ai des soucis lors du linkage... Je me pencherais la dessus quand mon OS aura une taille conséquente

Re-edit : Apparement Cygwin serait une bonne idée pour pouvoir compiler sous windows des fichiers linkables avec des binaires asm. Si quelqu'un pouvait m'en parler car je l'ai lu sur un site en anglais et je ne suis pas sur de tout comprendre.
romfox17 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 26/11/2011, 23h38   #2
romfox17
Nouveau Membre du Club
 
Homme Romain
Inscription : avril 2011
Messages : 60
Détails du profil
Informations personnelles :
Nom : Homme Romain
Âge : 21
Localisation : France, Charente Maritime (Poitou Charente)

Informations forums :
Inscription : avril 2011
Messages : 60
Points : 30
Points : 30
Bonjour,
Petit avancement pour mon OS qui stock désormais la dernière ligne dans un buffer. Du coups j'ai enfin ma 1ère commande qui fonctionne (j'ai implementé strncmp et non strcmp pour le moment. Par contre je ne sais pas pourquoi mais je n'arrive plus a demarer mon os sur mon disque dur externe alors que hier encore cela marchait... Avec une taille de 4,5 ko je devrais pas avoir de soucis nan ? Je précise que je copie directement mon bootloader au début et que je vire le mbr du coups, j'utilise "dd" pour la copie.

Le soucis viendrait il du fait qu'il n'y a pas de MBR, mais directement un jmp pour une initialisation en 7c00 ? Pourtant cela marchait hier, j'ai juste formaté une nouvelle fois mon disque, chose que javais déjà faite plusieurs fois...
romfox17 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 09/12/2011, 02h14   #3
Serv Etud
Invité de passage
 
Homme
Étudiant
Inscription : décembre 2011
Messages : 1
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : Tunisie

Informations professionnelles :
Activité : Étudiant

Informations forums :
Inscription : décembre 2011
Messages : 1
Points : 1
Points : 1
Envoyer un message via Skype™ à Serv Etud
salut romain
sur quel livre tu t'es basé sur l'architecture de ton OS?
Serv Etud est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 14/12/2011, 00h59   #4
romfox17
Nouveau Membre du Club
 
Homme Romain
Inscription : avril 2011
Messages : 60
Détails du profil
Informations personnelles :
Nom : Homme Romain
Âge : 21
Localisation : France, Charente Maritime (Poitou Charente)

Informations forums :
Inscription : avril 2011
Messages : 60
Points : 30
Points : 30
Salut,
Pour te répondre, je n'ai encore aucun livre sur l'assembleur. J'ai juste utilisé les tutos du site ou nous nous trouvons, et OSDev qui est un super site je trouve.
Actuellement j'en suis toujours a la gestion de la mémoire, bien que j'ai toujours mon soucis de boot sur un vrai pc (pas une machine virtuelle). En effet meme avec le bootloader du formatage (celui que le formatage écrit sur mon disque) ou mon bootloader, peut importe, ni mon disque dur USB, ni ma clée USB ne bootent. Par contre tout est niquel en machine virtuelle.
romfox17 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 10/02/2012, 20h47   #5
wqaxs36
Invité régulier
 
Homme
Étudiant
Inscription : janvier 2012
Messages : 5
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France

Informations professionnelles :
Activité : Étudiant
Secteur : Enseignement

Informations forums :
Inscription : janvier 2012
Messages : 5
Points : 5
Points : 5
Par défaut Booter depuis une clé usb

Bonjour romfox17,

Alors voila pour faire court moi aussi je suis en train de développer un OS.
Et pour le tester depuis une clé USB, je modifie son Bootsecteur (1er secteur) avec un éditeur Hexadécimal qui est HxD : http://mh-nexus.de/en/hxd

Tuto pour modifier le Bootsecteur:

1. Ouvrez HxD.exe, ensuite cliquer sur l'icone en forme de disk (OpenDisk
en infobulle).

2. Next choisissez votre clé en décochant 'Open as Readonly'.

3. Puis ouvrez votre binaire, donc le bootloader et le kernel

4. Copy/paste le bootloader à l'offset 0 de la clé USB, et le kernel au début du secteur-1, secteur que vous avez choisi dans les paramètres passer à 'Fonctions 02h de int 0x13 (Écrit dans la RAM)

5. REBOOT

That's all
En espérant que cela t'a aidé

A++
wqaxs36 est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse
Outils de la discussion

Navigation rapide


Fuseau horaire GMT +2. Il est actuellement 21h30.


 
 
 
 
Partenaires

Hébergement Web