Subversion Repositories Kolibri OS

Rev

Rev 421 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 421 Rev 427
1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;; IRQ0 HANDLER (TIMER INTERRUPT) ;;
2
;; IRQ0 HANDLER (TIMER INTERRUPT) ;;
3
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
3
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4
 
4
 
5
 
5
 
6
align 32
6
align 32
7
irq0:
7
irq0:
8
        pushfd
8
        pushfd
9
        pushad
9
        pushad
10
        mov   ax, app_data  ;
10
        mov   ax, app_data  ;
11
        mov   ds, ax
11
        mov   ds, ax
12
        mov   es, ax
12
        mov   es, ax
13
 
13
 
14
        inc   dword [timer_ticks]
14
        inc   dword [timer_ticks]
15
 
15
 
16
        mov   eax, [timer_ticks]
16
        mov   eax, [timer_ticks]
17
        call  playNote           ; <<<--- Speaker driver
17
        call  playNote           ; <<<--- Speaker driver
18
 
18
 
19
        cmp   eax,[next_usage_update]
19
        cmp   eax,[next_usage_update]
20
        jb    .nocounter
20
        jb    .nocounter
21
        add   eax,100
21
        add   eax,100
22
        mov   [next_usage_update],eax
22
        mov   [next_usage_update],eax
23
        call  updatecputimes
23
        call  updatecputimes
24
.nocounter:
24
.nocounter:
25
        cmp   [DONT_SWITCH], byte 1
25
        cmp   [DONT_SWITCH], byte 1
26
        jne   .change_task
26
        jne   .change_task
27
 
27
 
28
        mov   al,0x20   ; send End Of Interrupt signal
28
        mov   al,0x20   ; send End Of Interrupt signal
29
        mov   dx,0x20
29
        mov   dx,0x20
30
        out   dx,al
30
        out   dx,al
31
 
31
 
32
        mov   [DONT_SWITCH], byte 0
32
        mov   [DONT_SWITCH], byte 0
33
 
33
 
34
        popad
34
        popad
35
        popfd
35
        popfd
36
        iretd
36
        iretd
37
 
37
 
38
.change_task:
38
.change_task:
39
        call  update_counters
39
        call  update_counters
40
 
40
 
41
        call  find_next_task
41
        call  find_next_task
42
        mov   ecx, eax
42
        mov   ecx, eax
43
 
43
 
44
        mov   al,0x20   ; send End Of Interrupt signal
44
        mov   al,0x20   ; send End Of Interrupt signal
45
        mov   dx,0x20
45
        mov   dx,0x20
46
        out   dx,al
46
        out   dx,al
47
 
47
 
48
	test  ecx, ecx  ; if there is only one running process
48
	test  ecx, ecx  ; if there is only one running process
49
        jnz   .return
49
        jnz   .return
50
 
50
 
51
        call  do_change_task
51
        call  do_change_task
52
 
52
 
53
.return:
53
.return:
54
        popad
54
        popad
55
        popfd
55
        popfd
56
        iretd
56
        iretd
57
 
57
 
58
 
58
 
59
align 4
59
align 4
60
change_task:
60
change_task:
61
 
61
 
62
        pushfd
62
        pushfd
63
        cli
63
        cli
64
        pushad
64
        pushad
65
 
65
 
66
        call  update_counters
66
        call  update_counters
67
 
67
 
68
if 0
68
if 0
69
 
69
 
70
; \begin{Mario79}
70
; \begin{Mario79}
71
        cmp     [dma_task_switched], 1
71
        cmp     [dma_task_switched], 1
72
        jne     .find_next_task
72
        jne     .find_next_task
73
        mov     [dma_task_switched], 0
73
        mov     [dma_task_switched], 0
74
        mov     ebx, [dma_process]
74
        mov     ebx, [dma_process]
75
        cmp     [CURRENT_TASK], ebx
75
        cmp     [CURRENT_TASK], ebx
76
        je      .return
76
        je      .return
77
        mov     edi, [dma_slot_ptr]
77
        mov     edi, [dma_slot_ptr]
78
        mov     [CURRENT_TASK], ebx
78
        mov     [CURRENT_TASK], ebx
79
        mov     [TASK_BASE], edi
79
        mov     [TASK_BASE], edi
80
        jmp     @f
80
        jmp     @f
81
.find_next_task:
81
.find_next_task:
82
; \end{Mario79}
82
; \end{Mario79}
83
 
83
 
84
end if
84
end if
85
 
85
 
86
        call  find_next_task
86
        call  find_next_task
87
        test  eax, eax    ; the same task -> skip switch
87
        test  eax, eax    ; the same task -> skip switch
88
        jnz    .return
88
        jnz    .return
89
@@:
89
@@:
90
        mov   [DONT_SWITCH],byte 1
90
        mov   [DONT_SWITCH],byte 1
91
        call  do_change_task
91
        call  do_change_task
92
 
92
 
93
.return:
93
.return:
94
        popad
94
        popad
95
        popfd
95
        popfd
96
        ret
96
        ret
97
 
97
 
98
 
98
 
99
uglobal
99
uglobal
100
   align 4
100
   align 4
101
   far_jump:
101
   far_jump:
102
    .offs dd ?
102
    .offs dd ?
103
    .sel  dw ?
103
    .sel  dw ?
104
   context_counter     dd ? ;noname & halyavin
104
   context_counter     dd ? ;noname & halyavin
105
   next_usage_update   dd ?
105
   next_usage_update   dd ?
106
   timer_ticks         dd ?
106
   timer_ticks         dd ?
107
   prev_slot           dd ?
107
   prev_slot           dd ?
108
   event_sched         dd ?
108
   event_sched         dd ?
109
endg
109
endg
110
 
110
 
111
 
111
 
112
update_counters:
112
update_counters:
113
        mov   edi, [TASK_BASE]
113
        mov   edi, [TASK_BASE]
114
        mov   ebx, [edi+TASKDATA.counter_add] ; time stamp counter add
114
        mov   ebx, [edi+TASKDATA.counter_add] ; time stamp counter add
115
        rdtsc
115
        rdtsc
116
        sub   eax, ebx
116
        sub   eax, ebx
117
        add   eax, [edi+TASKDATA.counter_sum] ; counter sum
117
        add   eax, [edi+TASKDATA.counter_sum] ; counter sum
118
        mov   [edi+TASKDATA.counter_sum], eax
118
        mov   [edi+TASKDATA.counter_sum], eax
119
ret
119
ret
120
 
120
 
121
 
121
 
122
; Find next task to execute
122
; Find next task to execute
123
; result: ebx = number of the selected task
123
; result: ebx = number of the selected task
124
;         eax = 1  if the task is the same
124
;         eax = 1  if the task is the same
125
;         edi = address of the data for the task in ebx
125
;         edi = address of the data for the task in ebx
126
;         [0x3000] = ebx and [0x3010] = edi
126
;         [0x3000] = ebx and [0x3010] = edi
127
;         corrupts other regs
127
;         corrupts other regs
128
find_next_task:
128
find_next_task:
129
        mov   ebx, [CURRENT_TASK]
129
        mov   ebx, [CURRENT_TASK]
130
        mov   edi, [TASK_BASE]
130
        mov   edi, [TASK_BASE]
131
        mov   [prev_slot], ebx
131
        mov   [prev_slot], ebx
132
 
132
 
133
.waiting_for_termination:
133
.waiting_for_termination:
134
.waiting_for_reuse:
134
.waiting_for_reuse:
135
.waiting_for_event:
135
.waiting_for_event:
136
.suspended:
136
.suspended:
137
        cmp   ebx, [TASK_COUNT]
137
        cmp   ebx, [TASK_COUNT]
138
        jb    @f
138
        jb    @f
139
        mov   edi, CURRENT_TASK
139
        mov   edi, CURRENT_TASK
140
        xor   ebx, ebx
140
        xor   ebx, ebx
141
      @@:
141
@@:
142
 
142
 
143
        add   edi,0x20
143
        add   edi,0x20
144
        inc   ebx
144
        inc   ebx
145
 
145
 
146
        mov   al, byte [edi+TASKDATA.state]
146
        mov   al, byte [edi+TASKDATA.state]
147
        test  al, al
147
        test  al, al
148
        jz    .found
148
        jz    .found
149
	cmp   al, 1
149
	cmp   al, 1
150
	jz    .suspended
150
	jz    .suspended
151
	cmp   al, 2
151
	cmp   al, 2
152
	jz    .suspended
152
	jz    .suspended
153
        cmp   al, 3
153
        cmp   al, 3
154
        je    .waiting_for_termination
154
        je    .waiting_for_termination
155
        cmp   al, 4
155
        cmp   al, 4
156
        je    .waiting_for_termination
156
        je    .waiting_for_termination
157
        cmp   al, 9
157
        cmp   al, 9
158
        je    .waiting_for_reuse
158
        je    .waiting_for_reuse
159
 
159
 
160
        mov   [CURRENT_TASK],ebx
160
        mov   [CURRENT_TASK],ebx
161
        mov   [TASK_BASE],edi
161
        mov   [TASK_BASE],edi
162
 
162
 
163
        cmp   al, 5
163
        cmp   al, 5
164
        jne   .noevents
164
        jne   .noevents
165
        call  get_event_for_app
165
        call  get_event_for_app
166
        test  eax, eax
166
        test  eax, eax
167
        jz    .waiting_for_event
167
        jz    .waiting_for_event
168
        mov   [event_sched], eax
168
        mov   [event_sched], eax
169
        mov   [edi+TASKDATA.state], byte 0
169
        mov   [edi+TASKDATA.state], byte 0
170
.noevents:
170
.noevents:
171
.found:
171
.found:
172
        mov   [CURRENT_TASK],ebx
172
        mov   [CURRENT_TASK],ebx
173
        mov   [TASK_BASE],edi
173
        mov   [TASK_BASE],edi
174
        rdtsc                     ;call  _rdtsc
174
        rdtsc                     ;call  _rdtsc
175
        mov   [edi+TASKDATA.counter_add],eax
175
        mov   [edi+TASKDATA.counter_add],eax
176
 
176
 
177
        mov esi, [prev_slot]
177
        mov esi, [prev_slot]
178
	xor   eax, eax
178
	xor   eax, eax
179
        cmp   ebx, esi
179
        cmp   ebx, esi
180
        sete  al
180
        sete  al
181
ret
181
ret
182
 
182
 
183
; in: ebx = TSS selector index
183
; in: ebx = TSS selector index
184
;
184
;
185
; param
185
; param
186
;  ebx = incoming task
186
;  ebx = incoming task
187
;  esi = outcomig task
187
;  esi = outcomig task
188
 
188
 
189
do_change_task:
189
do_change_task:
190
 
190
 
191
        shl ebx, 8
191
        shl ebx, 8
192
        add ebx, SLOT_BASE
192
        add ebx, SLOT_BASE
193
        mov [current_slot], ebx
193
        mov [current_slot], ebx
194
        shl esi, 8
194
        shl esi, 8
195
        add esi, SLOT_BASE
195
        add esi, SLOT_BASE
196
 
196
 
197
        mov [esi+APPDATA.saved_esp], esp
197
        mov [esi+APPDATA.saved_esp], esp
198
        mov esp, [ebx+APPDATA.saved_esp]
198
        mov esp, [ebx+APPDATA.saved_esp]
199
 
199
 
200
        mov eax, [ebx+APPDATA.dir_table]
200
        mov eax, [ebx+APPDATA.dir_table]
201
        mov cr3, eax
201
        mov cr3, eax
202
 
202
 
203
        mov ebx, [ebx+APPDATA.pl0_stack]
203
        mov ebx, [ebx+APPDATA.pl0_stack]
204
        add ebx, RING0_STACK_SIZE
204
        add ebx, RING0_STACK_SIZE
205
        mov [tss_data+TSS._esp0], ebx
205
        mov [tss_data+TSS._esp0], ebx
206
        mov ecx, cr0
206
        mov ecx, cr0
207
        or ecx, CR0_TS   ;set task switch flag
207
        or ecx, CR0_TS   ;set task switch flag
208
        mov cr0, ecx
208
        mov cr0, ecx
209
        inc   [context_counter] ;noname & halyavin
209
        inc   [context_counter] ;noname & halyavin
210
 
210
 
211
        ret
211
        ret
212
 
212
 
213
;
213
;
214
;        shl   ebx, 3
214
;        shl   ebx, 3
215
;        xor   eax, eax
215
;        xor   eax, eax
216
;        add   ebx, tss0
216
;        add   ebx, tss0
217
;        mov   [far_jump.sel],  bx   ; selector
217
;        mov   [far_jump.sel],  bx   ; selector
218
;        mov   [far_jump.offs], eax  ; offset
218
;        mov   [far_jump.offs], eax  ; offset
219
;        jmp   pword [far_jump]
219
;        jmp   pword [far_jump]
220
;        inc   [context_counter] ;noname & halyavin
220
;        inc   [context_counter] ;noname & halyavin
221
;ret
221
;ret
222
 
222
 
223
align 4
223
align 4
224
updatecputimes:
224
updatecputimes:
225
 
225
 
226
        mov  eax,[idleuse]
226
        mov  eax,[idleuse]
227
        mov  [idleusesec],eax
227
        mov  [idleusesec],eax
228
        mov  [idleuse],dword 0
228
        mov  [idleuse],dword 0
229
        mov  ecx, [TASK_COUNT]
229
        mov  ecx, [TASK_COUNT]
230
        mov  edi, TASK_DATA
230
        mov  edi, TASK_DATA
231
.newupdate:
231
.newupdate:
232
        mov  ebx,[edi+TASKDATA.counter_sum]
232
        mov  ebx,[edi+TASKDATA.counter_sum]
233
        mov  [edi+TASKDATA.cpu_usage],ebx
233
        mov  [edi+TASKDATA.cpu_usage],ebx
234
        mov  [edi+TASKDATA.counter_sum],dword 0
234
        mov  [edi+TASKDATA.counter_sum],dword 0
235
        add  edi,0x20
235
        add  edi,0x20
236
        dec  ecx
236
        dec  ecx
237
        jnz  .newupdate
237
        jnz  .newupdate
238
 
238
 
239
        ret
239
        ret
-
 
240
 
-
 
241
if 0
-
 
242
 
-
 
243
MAX_PROIRITY         0   ; highest, used for kernel tasks
-
 
244
MAX_USER_PRIORITY    0   ; highest priority for user processes
-
 
245
USER_PRIORITY        7   ; default (should correspond to nice 0)
-
 
246
MIN_USER_PRIORITY   14   ; minimum priority for user processes
-
 
247
IDLE_PRIORITY       15   ; lowest, only IDLE process goes here
-
 
248
NR_SCHED_QUEUES     16   ; MUST equal IDLE_PRIORYTY + 1
-
 
249
 
-
 
250
rdy_head   rd 16
-
 
251
 
-
 
252
 
-
 
253
align 4
-
 
254
pick_task:
-
 
255
 
-
 
256
           xor eax, eax
-
 
257
.pick:
-
 
258
           mov ebx, [rdy_head+eax*4]
-
 
259
           test ebx, ebx
-
 
260
           jz .next
-
 
261
 
-
 
262
           mov [next_task], ebx
-
 
263
           test [ebx+flags.billable]
-
 
264
           jz @F
-
 
265
           mov [bill_task], ebx
-
 
266
@@:
-
 
267
           ret
-
 
268
.next:
-
 
269
           inc eax
-
 
270
           jmp .pick
-
 
271
 
-
 
272
 
-
 
273
; param
-
 
274
;  eax= task
-
 
275
;
-
 
276
; retval
-
 
277
;  eax= task
-
 
278
;  ebx= queue
-
 
279
;  ecx= front if 1 or back if 0
-
 
280
 
-
 
281
align 4
-
 
282
shed:
-
 
283
           cmp [eax+.tics_left], 0 ;signed compare
-
 
284
           mov ebx, [eax+.priority]
-
 
285
           setg ecx
-
 
286
           jg @F
-
 
287
 
-
 
288
           mov edx, [eax+.tics_quantum]
-
 
289
           mov [eax+.ticks_left], edx
-
 
290
           cmp ebx, (IDLE_PRIORITY-1)
-
 
291
           je @F
-
 
292
           inc ebx
-
 
293
@@:
-
 
294
           ret
-
 
295
 
-
 
296
; param
-
 
297
;  eax= task
-
 
298
 
-
 
299
align 4
-
 
300
enqueue:
-
 
301
          call shed  ;eax
-
 
302
          cmp [rdy_head+ebx*4],0
-
 
303
          jnz @F
-
 
304
 
-
 
305
          mov [rdy_head+ebx*4], eax
-
 
306
          mov [rdy_tail+ebx*4], eax
-
 
307
          mov [eax+.next_ready], 0
-
 
308
          jmp .pick
-
 
309
@@:
-
 
310
          test ecx, ecx
-
 
311
          jz .back
-
 
312
 
-
 
313
          mov ecx, [rdy_head+ebx*4]
-
 
314
          mov [eax+.next_ready], ecx
-
 
315
          mov [rdy_head+ebx*4], eax
-
 
316
          jmp .pick
-
 
317
.back:
-
 
318
          mov ecx, [rdy_tail+ebx*4]
-
 
319
          mov [ecx+.next_ready], eax
-
 
320
          mov [rdy_tail+ebx*4], eax
-
 
321
          mov [eax+.next_ready], 0
-
 
322
.pick:
-
 
323
          call pick_proc     ;select next task
-
 
324
          ret
-
 
325
 
-
 
326
end if
-
 
327