Subversion Repositories Kolibri OS

Rev

Rev 1689 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
431 serge 1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                              ;;
1289 diamond 3
;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
431 serge 4
;; Distributed under terms of the GNU General Public License    ;;
5
;;                                                              ;;
6
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
164 serge 7
 
593 mikedld 8
$Revision: 1710 $
9
 
10
 
164 serge 11
struc MEM_BLOCK
12
{  .next_block  dd ?
13
   .prev_block  dd ? ;+4
357 serge 14
   .list_fd     dd ? ;+8
15
   .list_bk     dd ? ;+12
164 serge 16
   .base        dd ? ;+16
17
   .size        dd ? ;+20
18
   .flags       dd ? ;+24
19
   .handle      dd ? ;+28
20
}
21
 
357 serge 22
MEM_LIST_OFFSET equ  8
164 serge 23
FREE_BLOCK      equ  4
24
USED_BLOCK      equ  8
546 diamond 25
DONT_FREE_BLOCK equ  10h
164 serge 26
 
27
virtual at 0
28
  MEM_BLOCK MEM_BLOCK
29
end virtual
30
 
31
MEM_BLOCK_SIZE equ 8*4
32
 
33
block_next   equ MEM_BLOCK.next_block
34
block_prev   equ MEM_BLOCK.prev_block
357 serge 35
list_fd      equ MEM_BLOCK.list_fd
36
list_bk      equ MEM_BLOCK.list_bk
164 serge 37
block_base   equ MEM_BLOCK.base
38
block_size   equ MEM_BLOCK.size
39
block_flags  equ MEM_BLOCK.flags
40
 
41
macro calc_index op
42
{          shr op, 12
43
           dec op
44
           cmp op, 63
45
           jna @f
46
           mov op, 63
47
@@:
48
}
49
 
50
macro remove_from_list op
357 serge 51
{          mov edx, [op+list_fd]
52
           mov ecx, [op+list_bk]
164 serge 53
           test edx, edx
54
           jz @f
357 serge 55
           mov [edx+list_bk], ecx
164 serge 56
@@:
57
           test ecx, ecx
58
           jz @f
357 serge 59
           mov [ecx+list_fd], edx
164 serge 60
@@:
357 serge 61
           mov [op+list_fd],0
62
           mov [op+list_bk],0
164 serge 63
}
64
 
65
macro remove_from_free op
66
{
67
           remove_from_list op
68
 
69
           mov eax, [op+block_size]
70
           calc_index eax
71
           cmp [mem_block_list+eax*4], op
72
           jne @f
73
           mov [mem_block_list+eax*4], edx
74
@@:
75
           cmp [mem_block_list+eax*4], 0
76
           jne @f
77
           btr [mem_block_mask], eax
78
@@:
79
}
80
 
81
macro remove_from_used op
82
{
357 serge 83
           mov edx, [op+list_fd]
84
           mov ecx, [op+list_bk]
85
           mov [edx+list_bk], ecx
86
           mov [ecx+list_fd], edx
87
           mov [op+list_fd], 0
88
           mov [op+list_bk], 0
164 serge 89
}
90
 
91
align 4
92
proc init_kernel_heap
93
 
1130 diamond 94
           mov ecx, 64
164 serge 95
           mov edi, mem_block_list
96
           xor eax, eax
97
           cld
98
           rep stosd
99
 
100
           mov ecx, 512/4
101
           mov edi, mem_block_map
102
           not eax
103
           rep stosd
104
 
105
           mov [mem_block_start], mem_block_map
106
           mov [mem_block_end], mem_block_map+512
107
           mov [mem_block_arr], HEAP_BASE
108
 
357 serge 109
           mov eax, mem_used.fd-MEM_LIST_OFFSET
110
           mov [mem_used.fd], eax
111
           mov [mem_used.bk], eax
112
 
1710 art_zh 113
	   mov [KERNEL_ALLOC_FLAG], dword PG_SW
164 serge 114
           stdcall alloc_pages, dword 32
115
           mov ecx, 32
116
           mov edx, eax
117
           mov edi, HEAP_BASE
118
.l1:
119
           stdcall map_page,edi,edx,PG_SW
120
           add edi, 0x1000
121
           add edx, 0x1000
122
           dec ecx
123
           jnz .l1
124
 
125
           mov edi, HEAP_BASE
357 serge 126
           mov ebx, HEAP_BASE+MEM_BLOCK_SIZE
164 serge 127
           xor eax, eax
128
           mov [edi+block_next], ebx
129
           mov [edi+block_prev], eax
357 serge 130
           mov [edi+list_fd], eax
131
           mov [edi+list_bk], eax
164 serge 132
           mov [edi+block_base], HEAP_BASE
133
           mov [edi+block_size], 4096*MEM_BLOCK_SIZE
134
           mov [edi+block_flags], USED_BLOCK
135
 
136
           mov [ebx+block_next], eax
137
           mov [ebx+block_prev], eax
357 serge 138
           mov [ebx+list_fd], eax
139
           mov [ebx+list_bk], eax
164 serge 140
           mov [ebx+block_base], HEAP_BASE+4096*MEM_BLOCK_SIZE
141
 
1090 diamond 142
           mov ecx, [pg_data.kernel_pages]
143
           shl ecx, 12
1332 diamond 144
           sub ecx, HEAP_BASE-OS_BASE+4096*MEM_BLOCK_SIZE
170 serge 145
           mov [heap_size], ecx
146
           mov [heap_free], ecx
164 serge 147
           mov [ebx+block_size], ecx
148
           mov [ebx+block_flags], FREE_BLOCK
149
 
150
           mov [mem_block_mask], eax
151
           mov [mem_block_mask+4],0x80000000
152
 
153
           mov [mem_block_list+63*4], ebx
154
           mov byte [mem_block_map], 0xFC
279 serge 155
           and [heap_mutex], 0
170 serge 156
           mov [heap_blocks], 4095
1130 diamond 157
           mov [free_blocks], 4094
164 serge 158
           ret
159
endp
160
 
369 serge 161
; param
162
;  eax= required size
163
;
164
; retval
165
;  edi= memory block descriptor
166
;  ebx= descriptor index
167
 
164 serge 168
align 4
819 serge 169
get_small_block:
164 serge 170
           mov ecx, eax
369 serge 171
           shr ecx, 12
172
           dec ecx
173
           cmp ecx, 63
174
           jle .get_index
175
           mov ecx, 63
176
.get_index:
177
           lea esi, [mem_block_mask]
164 serge 178
           xor ebx, ebx
369 serge 179
           or edx, -1
164 serge 180
 
181
           cmp ecx, 32
182
           jb .bit_test
183
 
184
           sub ecx, 32
185
           add ebx, 32
186
           add esi, 4
187
.bit_test:
188
           shl edx, cl
369 serge 189
           and edx, [esi]
190
.find:
191
           bsf edi, edx
164 serge 192
           jz .high_mask
369 serge 193
           add ebx, edi
194
           mov edi, [mem_block_list+ebx*4]
195
.check_size:
196
           cmp eax, [edi+block_size]
197
           ja .next
164 serge 198
           ret
199
 
200
.high_mask:
201
           add esi, 4
369 serge 202
           cmp esi, mem_block_mask+8
203
           jae .err
164 serge 204
           add ebx, 32
369 serge 205
           mov edx, [esi]
206
           jmp .find
207
.next:
208
           mov edi, [edi+list_fd]
209
           test edi, edi
210
           jnz .check_size
211
.err:
212
           xor edi, edi
164 serge 213
           ret
214
 
215
align 4
819 serge 216
alloc_mem_block:
164 serge 217
 
218
           mov ebx, [mem_block_start]
219
           mov ecx, [mem_block_end]
220
.l1:
221
           bsf eax,[ebx];
222
           jnz found
223
           add ebx,4
224
           cmp ebx, ecx
225
           jb .l1
226
           xor eax,eax
227
           ret
228
 
229
found:
230
           btr [ebx], eax
231
           mov [mem_block_start],ebx
232
           sub ebx, mem_block_map
254 serge 233
           lea eax,[eax+ebx*8]
164 serge 234
           shl eax, 5
235
           add eax, [mem_block_arr]
170 serge 236
           dec [free_blocks]
164 serge 237
           ret
819 serge 238
align 4
239
free_mem_block:
357 serge 240
           mov dword [eax], 0
241
           mov dword [eax+4], 0
242
           mov dword [eax+8], 0
243
           mov dword [eax+12], 0
244
           mov dword [eax+16], 0
245
;           mov dword [eax+20], 0
246
           mov dword [eax+24], 0
247
           mov dword [eax+28], 0
248
 
164 serge 249
           sub eax, [mem_block_arr]
250
           shr eax, 5
251
 
252
           mov ebx, mem_block_map
253
           bts [ebx], eax
170 serge 254
           inc [free_blocks]
164 serge 255
           shr eax, 3
256
           and eax, not 3
257
           add eax, ebx
258
           cmp [mem_block_start], eax
259
           ja @f
260
           ret
261
@@:
262
           mov [mem_block_start], eax
263
	   ret
264
.err:
265
           xor eax, eax
266
	   ret
267
 
268
align 4
269
proc alloc_kernel_space stdcall, size:dword
270
           local block_ind:DWORD
271
 
660 serge 272
           push ebx
273
           push esi
274
           push edi
275
 
164 serge 276
           mov eax, [size]
206 serge 277
           add eax, 4095
278
           and eax, not 4095
164 serge 279
           mov [size], eax
279 serge 280
 
281
           mov ebx, heap_mutex
282
           call wait_mutex    ;ebx
283
 
170 serge 284
           cmp eax, [heap_free]
285
           ja .error
164 serge 286
 
819 serge 287
           call get_small_block ; eax
369 serge 288
           test edi, edi
164 serge 289
           jz .error
290
 
291
           cmp [edi+block_flags], FREE_BLOCK
292
           jne .error
293
 
294
           mov [block_ind], ebx   ;index of allocated block
295
 
296
           mov eax, [edi+block_size]
297
           cmp eax, [size]
298
           je .m_eq_size
299
 
300
           call alloc_mem_block
301
           and eax, eax
302
           jz .error
303
 
304
           mov esi, eax           ;esi - splitted block
305
 
306
           mov [esi+block_next], edi
307
           mov eax, [edi+block_prev]
308
           mov [esi+block_prev], eax
309
           mov [edi+block_prev], esi
357 serge 310
           mov [esi+list_fd], 0
311
           mov [esi+list_bk], 0
164 serge 312
           and eax, eax
313
           jz @f
314
           mov [eax+block_next], esi
315
@@:
316
           mov ebx, [edi+block_base]
317
           mov [esi+block_base], ebx
318
           mov edx, [size]
319
           mov [esi+block_size], edx
320
           add [edi+block_base], edx
321
           sub [edi+block_size], edx
322
 
323
           mov eax, [edi+block_size]
324
           shr eax, 12
325
           sub eax, 1
326
           cmp eax, 63
327
           jna @f
328
           mov eax, 63
329
@@:
330
           cmp eax, [block_ind]
331
           je .m_eq_ind
332
 
192 serge 333
           remove_from_list edi
164 serge 334
 
335
           mov ecx, [block_ind]
211 serge 336
           mov [mem_block_list+ecx*4], edx
164 serge 337
 
211 serge 338
           test edx, edx
164 serge 339
           jnz @f
340
           btr [mem_block_mask], ecx
341
@@:
342
           mov edx, [mem_block_list+eax*4]
357 serge 343
           mov [edi+list_fd], edx
164 serge 344
           test edx, edx
345
           jz @f
357 serge 346
           mov [edx+list_bk], edi
164 serge 347
@@:
348
           mov [mem_block_list+eax*4], edi
349
           bts [mem_block_mask], eax
350
.m_eq_ind:
357 serge 351
           mov ecx, mem_used.fd-MEM_LIST_OFFSET
352
           mov edx, [ecx+list_fd]
353
           mov [esi+list_fd], edx
354
           mov [esi+list_bk], ecx
355
           mov [ecx+list_fd], esi
356
           mov [edx+list_bk], esi
357
 
164 serge 358
           mov [esi+block_flags], USED_BLOCK
359
           mov eax, [esi+block_base]
170 serge 360
           mov ebx, [size]
361
           sub [heap_free], ebx
279 serge 362
           and [heap_mutex], 0
660 serge 363
           pop edi
364
           pop esi
365
           pop ebx
164 serge 366
           ret
367
.m_eq_size:
368
           remove_from_list edi
192 serge 369
           mov [mem_block_list+ebx*4], edx
164 serge 370
           and edx, edx
371
           jnz @f
192 serge 372
           btr [mem_block_mask], ebx
164 serge 373
@@:
357 serge 374
           mov ecx, mem_used.fd-MEM_LIST_OFFSET
375
           mov edx, [ecx+list_fd]
376
           mov [edi+list_fd], edx
377
           mov [edi+list_bk], ecx
378
           mov [ecx+list_fd], edi
379
           mov [edx+list_bk], edi
380
 
164 serge 381
           mov [edi+block_flags], USED_BLOCK
382
           mov eax, [edi+block_base]
170 serge 383
           mov ebx, [size]
384
           sub [heap_free], ebx
279 serge 385
           and [heap_mutex], 0
660 serge 386
           pop edi
387
           pop esi
388
           pop ebx
164 serge 389
           ret
390
.error:
391
           xor eax, eax
279 serge 392
           mov [heap_mutex], eax
660 serge 393
           pop edi
394
           pop esi
395
           pop ebx
164 serge 396
           ret
397
endp
398
 
399
align 4
321 diamond 400
proc free_kernel_space stdcall uses ebx ecx edx esi edi, base:dword
660 serge 401
           push ebx
402
           push esi
403
           push edi
279 serge 404
           mov ebx, heap_mutex
405
           call wait_mutex    ;ebx
406
 
164 serge 407
           mov eax, [base]
357 serge 408
           mov esi, [mem_used.fd]
164 serge 409
@@:
357 serge 410
           cmp esi, mem_used.fd-MEM_LIST_OFFSET
411
           je .fail
164 serge 412
 
413
           cmp [esi+block_base], eax
414
           je .found
357 serge 415
           mov esi, [esi+list_fd]
164 serge 416
           jmp @b
417
.found:
418
           cmp [esi+block_flags], USED_BLOCK
419
           jne .fail
420
 
170 serge 421
           mov eax, [esi+block_size]
422
           add [heap_free], eax
423
 
164 serge 424
           mov edi, [esi+block_next]
425
           test edi, edi
426
           jz .prev
427
 
428
           cmp [edi+block_flags], FREE_BLOCK
429
           jne .prev
430
 
431
           remove_from_free edi
432
 
433
           mov edx, [edi+block_next]
434
           mov [esi+block_next], edx
435
           test edx, edx
436
           jz @f
437
 
438
           mov [edx+block_prev], esi
439
@@:
440
           mov ecx, [edi+block_size]
441
           add [esi+block_size], ecx
442
 
443
           mov eax, edi
444
           call free_mem_block
445
.prev:
446
           mov edi, [esi+block_prev]
447
           test edi, edi
448
           jz .insert
449
 
450
           cmp [edi+block_flags], FREE_BLOCK
451
           jne .insert
452
 
453
           remove_from_used esi
454
 
455
           mov edx, [esi+block_next]
456
           mov [edi+block_next], edx
457
           test edx, edx
458
           jz @f
459
           mov [edx+block_prev], edi
460
@@:
461
           mov eax, esi
462
           call free_mem_block
463
 
464
           mov ecx, [edi+block_size]
465
           mov eax, [esi+block_size]
466
           add eax, ecx
467
           mov [edi+block_size], eax
468
 
469
           calc_index eax
470
           calc_index ecx
471
           cmp eax, ecx
472
           je .m_eq
473
 
474
           push ecx
475
           remove_from_list edi
476
           pop ecx
477
 
478
           cmp [mem_block_list+ecx*4], edi
479
           jne @f
480
           mov [mem_block_list+ecx*4], edx
481
@@:
482
           cmp [mem_block_list+ecx*4], 0
483
           jne @f
484
           btr [mem_block_mask], ecx
485
@@:
486
           mov esi, [mem_block_list+eax*4]
487
           mov [mem_block_list+eax*4], edi
357 serge 488
           mov [edi+list_fd], esi
164 serge 489
           test esi, esi
490
           jz @f
357 serge 491
           mov [esi+list_bk], edi
164 serge 492
@@:
493
           bts [mem_block_mask], eax
494
.m_eq:
495
           xor eax, eax
279 serge 496
           mov [heap_mutex], eax
321 diamond 497
           dec eax
660 serge 498
           pop edi
499
           pop esi
500
           pop ebx
164 serge 501
           ret
502
.insert:
503
           remove_from_used esi
504
 
505
           mov eax, [esi+block_size]
506
           calc_index eax
507
 
508
           mov edi, [mem_block_list+eax*4]
509
           mov [mem_block_list+eax*4], esi
357 serge 510
           mov [esi+list_fd], edi
164 serge 511
           test edi, edi
512
           jz @f
357 serge 513
           mov [edi+list_bk], esi
164 serge 514
@@:
515
           bts [mem_block_mask], eax
516
           mov [esi+block_flags],FREE_BLOCK
517
           xor eax, eax
279 serge 518
           mov [heap_mutex], eax
321 diamond 519
           dec eax
660 serge 520
           pop edi
521
           pop esi
522
           pop ebx
164 serge 523
           ret
524
.fail:
525
           xor eax, eax
279 serge 526
           mov [heap_mutex], eax
660 serge 527
           pop edi
528
           pop esi
529
           pop ebx
164 serge 530
           ret
531
endp
532
 
533
align 4
534
proc kernel_alloc stdcall, size:dword
535
           locals
536
             lin_addr    dd ?
537
             pages_count dd ?
538
           endl
539
 
662 serge 540
           push ebx
541
           push edi
542
 
164 serge 543
           mov eax, [size]
206 serge 544
           add eax, 4095
545
           and eax, not 4095;
164 serge 546
           mov [size], eax
547
           and eax, eax
357 serge 548
           jz .err
164 serge 549
           mov ebx, eax
550
           shr ebx, 12
551
           mov [pages_count], ebx
552
 
553
           stdcall alloc_kernel_space, eax
357 serge 554
           test eax, eax
555
           jz .err
164 serge 556
           mov [lin_addr], eax
557
 
558
           mov ecx, [pages_count]
559
           mov edx, eax
560
           mov ebx, ecx
561
 
562
           shr ecx, 3
563
           jz .next
564
 
565
           and ebx, not 7
566
           push ebx
567
           stdcall alloc_pages, ebx
568
           pop ecx                   ; yes ecx!!!
569
           and eax, eax
357 serge 570
           jz .err
164 serge 571
 
572
           mov edi, eax
573
           mov edx, [lin_addr]
574
@@:
1710 art_zh 575
           stdcall map_page,edx,edi,dword [KERNEL_ALLOC_FLAG]
164 serge 576
           add edx, 0x1000
577
           add edi, 0x1000
578
           dec ecx
579
           jnz @B
580
.next:
581
           mov ecx, [pages_count]
582
           and ecx, 7
583
           jz .end
357 serge 584
@@:
585
           push ecx
164 serge 586
           call alloc_page
587
           pop ecx
588
           test eax, eax
357 serge 589
           jz .err
164 serge 590
 
591
           stdcall map_page,edx,eax,dword PG_SW
592
           add edx, 0x1000
593
           dec ecx
594
           jnz @B
595
.end:
596
           mov eax, [lin_addr]
662 serge 597
           pop edi
598
           pop ebx
164 serge 599
           ret
357 serge 600
.err:
164 serge 601
           xor eax, eax
662 serge 602
           pop edi
603
           pop ebx
164 serge 604
           ret
605
endp
606
 
607
align 4
608
proc kernel_free stdcall, base:dword
321 diamond 609
           push ebx esi
164 serge 610
 
279 serge 611
           mov ebx, heap_mutex
612
           call wait_mutex    ;ebx
613
 
164 serge 614
           mov eax, [base]
357 serge 615
           mov esi, [mem_used.fd]
164 serge 616
@@:
357 serge 617
           cmp esi, mem_used.fd-MEM_LIST_OFFSET
618
           je .fail
164 serge 619
 
620
           cmp [esi+block_base], eax
621
           je .found
357 serge 622
           mov esi, [esi+list_fd]
164 serge 623
           jmp @b
624
.found:
625
           cmp [esi+block_flags], USED_BLOCK
626
           jne .fail
627
 
279 serge 628
           and [heap_mutex], 0
629
 
321 diamond 630
           push ecx
164 serge 631
           mov ecx, [esi+block_size];
281 serge 632
           shr ecx, 12
279 serge 633
           call release_pages   ;eax, ecx
321 diamond 634
           pop ecx
164 serge 635
           stdcall free_kernel_space, [base]
321 diamond 636
           pop esi ebx
279 serge 637
           ret
164 serge 638
.fail:
1689 art_zh 639
           xor eax, eax
640
           mov [heap_mutex], eax
321 diamond 641
           pop esi ebx
164 serge 642
           ret
643
endp
644
 
645
restore block_next
646
restore block_prev
647
restore block_list
648
restore block_base
649
restore block_size
650
restore block_flags
651
 
652
;;;;;;;;;;;;;;      USER     ;;;;;;;;;;;;;;;;;
653
 
188 serge 654
HEAP_TOP  equ 0x5FC00000
655
 
164 serge 656
align 4
188 serge 657
proc init_heap
164 serge 658
 
465 serge 659
           mov ebx,[current_slot]
660
           mov eax, [ebx+APPDATA.heap_top]
172 serge 661
           test eax, eax
662
           jz @F
465 serge 663
           sub eax,[ebx+APPDATA.heap_base]
172 serge 664
           sub eax, 4096
665
           ret
666
@@:
465 serge 667
           mov esi, [ebx+APPDATA.mem_size]
188 serge 668
           add esi, 4095
669
           and esi, not 4095
465 serge 670
           mov [ebx+APPDATA.mem_size], esi
188 serge 671
           mov eax, HEAP_TOP
465 serge 672
           mov [ebx+APPDATA.heap_base], esi
673
           mov [ebx+APPDATA.heap_top], eax
164 serge 674
 
188 serge 675
           sub eax, esi
676
           shr esi, 10
677
           mov ecx, eax
164 serge 678
           sub eax, 4096
188 serge 679
           or ecx, FREE_BLOCK
365 serge 680
           mov [page_tabs+esi], ecx
164 serge 681
           ret
682
endp
683
 
684
align 4
685
proc user_alloc stdcall, alloc_size:dword
686
 
662 serge 687
           push ebx
688
           push esi
689
           push edi
690
 
164 serge 691
           mov ecx, [alloc_size]
692
           add ecx, (4095+4096)
693
           and ecx, not 4095
694
 
465 serge 695
           mov ebx, [current_slot]
696
           mov esi, dword [ebx+APPDATA.heap_base]  ; heap_base
697
           mov edi, dword [ebx+APPDATA.heap_top]   ; heap_top
164 serge 698
l_0:
699
           cmp esi, edi
700
           jae m_exit
701
 
702
           mov ebx, esi
703
           shr ebx, 12
365 serge 704
           mov eax, [page_tabs+ebx*4]
620 diamond 705
           test al, FREE_BLOCK
164 serge 706
           jz test_used
707
           and eax, 0xFFFFF000
708
           cmp eax, ecx    ;alloc_size
709
           jb  m_next
940 serge 710
           jz  @f
164 serge 711
 
620 diamond 712
           lea edx, [esi+ecx]
713
           sub eax, ecx
714
           or al, FREE_BLOCK
164 serge 715
           shr edx, 12
365 serge 716
           mov [page_tabs+edx*4], eax
294 diamond 717
@@:
164 serge 718
           or ecx, USED_BLOCK
365 serge 719
           mov [page_tabs+ebx*4], ecx
164 serge 720
           shr ecx, 12
620 diamond 721
           inc ebx
164 serge 722
           dec ecx
620 diamond 723
           jz  .no
164 serge 724
@@:
365 serge 725
           mov dword [page_tabs+ebx*4], 2
164 serge 726
           inc ebx
727
           dec ecx
728
           jnz @B
620 diamond 729
.no:
164 serge 730
 
465 serge 731
           mov     edx, [current_slot]
732
           mov     ebx, [alloc_size]
733
           add     ebx, 0xFFF
734
           and     ebx, not 0xFFF
735
           add     ebx, [edx+APPDATA.mem_size]
736
           call    update_mem_size
294 diamond 737
 
620 diamond 738
           lea eax, [esi+4096]
662 serge 739
 
740
           pop edi
741
           pop esi
742
           pop ebx
164 serge 743
           ret
744
test_used:
620 diamond 745
           test al, USED_BLOCK
164 serge 746
           jz m_exit
747
 
748
           and eax, 0xFFFFF000
620 diamond 749
m_next:
164 serge 750
           add esi, eax
751
           jmp l_0
752
m_exit:
753
           xor eax, eax
662 serge 754
           pop edi
755
           pop esi
756
           pop ebx
164 serge 757
           ret
758
endp
759
 
760
align 4
1289 diamond 761
proc user_alloc_at stdcall, address:dword, alloc_size:dword
762
 
763
           push ebx
764
           push esi
765
           push edi
766
 
767
           mov ebx, [current_slot]
768
           mov edx, [address]
769
           and edx, not 0xFFF
770
           mov [address], edx
771
           sub edx, 0x1000
772
           jb  .error
773
           mov esi, [ebx+APPDATA.heap_base]
774
           mov edi, [ebx+APPDATA.heap_top]
775
           cmp edx, esi
776
           jb  .error
777
.scan:
778
           cmp esi, edi
779
           jae .error
780
           mov ebx, esi
781
           shr ebx, 12
782
           mov eax, [page_tabs+ebx*4]
783
           mov ecx, eax
784
           and ecx, 0xFFFFF000
785
           add ecx, esi
786
           cmp edx, ecx
787
           jb  .found
788
           mov esi, ecx
789
           jmp .scan
790
.error:
791
           xor eax, eax
792
           pop edi
793
           pop esi
794
           pop ebx
795
           ret
796
.found:
797
           test al, FREE_BLOCK
798
           jz  .error
799
           mov eax, ecx
800
           sub eax, edx
801
           sub eax, 0x1000
802
           cmp eax, [alloc_size]
803
           jb  .error
804
 
805
; Here we have 1 big free block which includes requested area.
806
; In general, 3 other blocks must be created instead:
807
; free at [esi, edx);
808
; busy at [edx, edx+0x1000+ALIGN_UP(alloc_size,0x1000));
809
; free at [edx+0x1000+ALIGN_UP(alloc_size,0x1000), ecx)
810
; First or third block (or both) may be absent.
811
           mov eax, edx
812
           sub eax, esi
813
           jz  .nofirst
814
           or  al, FREE_BLOCK
815
           mov [page_tabs+ebx*4], eax
816
.nofirst:
817
           mov eax, [alloc_size]
818
           add eax, 0x1FFF
819
           and eax, not 0xFFF
820
           mov ebx, edx
821
           add edx, eax
822
           shr ebx, 12
823
           or  al, USED_BLOCK
824
           mov [page_tabs+ebx*4], eax
825
           shr eax, 12
826
           dec eax
827
           jz  .second_nofill
828
           inc ebx
829
.fill:
830
           mov dword [page_tabs+ebx*4], 2
831
           inc ebx
832
           dec eax
833
           jnz .fill
834
.second_nofill:
835
           sub ecx, edx
836
           jz  .nothird
837
           or  cl, FREE_BLOCK
838
           mov [page_tabs+ebx*4], ecx
839
.nothird:
840
 
841
           mov     edx, [current_slot]
842
           mov     ebx, [alloc_size]
843
           add     ebx, 0xFFF
844
           and     ebx, not 0xFFF
845
           add     ebx, [edx+APPDATA.mem_size]
846
           call    update_mem_size
847
 
848
           mov eax, [address]
849
 
850
           pop edi
851
           pop esi
852
           pop ebx
853
           ret
854
endp
855
 
856
align 4
164 serge 857
proc user_free stdcall, base:dword
858
 
662 serge 859
           push esi
860
 
164 serge 861
           mov esi, [base]
862
           test esi, esi
863
           jz .exit
864
 
662 serge 865
           push ebx
866
 
294 diamond 867
           xor ebx, ebx
164 serge 868
           shr esi, 12
620 diamond 869
           mov eax, [page_tabs+(esi-1)*4]
546 diamond 870
           test al, USED_BLOCK
620 diamond 871
           jz .cantfree
546 diamond 872
           test al, DONT_FREE_BLOCK
873
           jnz .cantfree
164 serge 874
 
875
           and eax, not 4095
876
           mov ecx, eax
620 diamond 877
           or al, FREE_BLOCK
878
           mov [page_tabs+(esi-1)*4], eax
164 serge 879
           sub ecx, 4096
620 diamond 880
           mov ebx, ecx
164 serge 881
           shr ecx, 12
620 diamond 882
           jz .released
164 serge 883
.release:
188 serge 884
           xor eax, eax
365 serge 885
           xchg eax, [page_tabs+esi*4]
620 diamond 886
           test al, 1
188 serge 887
           jz @F
940 serge 888
           test eax, PG_SHARED
889
           jnz @F
164 serge 890
           call free_page
448 diamond 891
           mov eax, esi
892
           shl eax, 12
893
           invlpg [eax]
188 serge 894
@@:
164 serge 895
           inc esi
896
           dec ecx
897
           jnz .release
620 diamond 898
.released:
662 serge 899
           push edi
900
 
465 serge 901
           mov edx, [current_slot]
902
           mov esi, dword [edx+APPDATA.heap_base]
903
           mov edi, dword [edx+APPDATA.heap_top]
904
           sub ebx, [edx+APPDATA.mem_size]
294 diamond 905
           neg ebx
906
           call update_mem_size
448 diamond 907
           call user_normalize
662 serge 908
           pop edi
909
           pop ebx
910
           pop esi
448 diamond 911
           ret
912
.exit:
913
           xor eax, eax
914
           inc eax
662 serge 915
           pop esi
448 diamond 916
           ret
546 diamond 917
.cantfree:
918
           xor eax, eax
662 serge 919
           pop ebx
920
           pop esi
546 diamond 921
           ret
448 diamond 922
endp
923
 
924
user_normalize:
925
; in: esi=heap_base, edi=heap_top
926
; out: eax=0 <=> OK
927
; destroys: ebx,edx,esi,edi
164 serge 928
           shr esi, 12
929
           shr edi, 12
930
@@:
365 serge 931
           mov eax, [page_tabs+esi*4]
620 diamond 932
           test al, USED_BLOCK
164 serge 933
           jz .test_free
934
           shr eax, 12
935
           add esi, eax
936
           jmp @B
937
.test_free:
620 diamond 938
           test al, FREE_BLOCK
164 serge 939
           jz .err
940
           mov edx, eax
941
           shr edx, 12
942
           add edx, esi
943
           cmp edx, edi
944
           jae .exit
945
 
365 serge 946
           mov ebx, [page_tabs+edx*4]
620 diamond 947
           test bl, USED_BLOCK
164 serge 948
           jz .next_free
949
 
950
           shr ebx, 12
951
           add edx, ebx
952
           mov esi, edx
953
           jmp @B
954
.next_free:
620 diamond 955
           test bl, FREE_BLOCK
164 serge 956
           jz .err
365 serge 957
           and dword [page_tabs+edx*4], 0
164 serge 958
           add eax, ebx
959
           and eax, not 4095
960
           or eax, FREE_BLOCK
365 serge 961
           mov [page_tabs+esi*4], eax
164 serge 962
           jmp @B
963
.exit:
964
           xor eax, eax
965
           inc eax
966
           ret
967
.err:
968
           xor eax, eax
969
           ret
970
 
448 diamond 971
user_realloc:
972
; in: eax = pointer, ebx = new size
973
; out: eax = new pointer or NULL
974
        test    eax, eax
975
        jnz     @f
976
; realloc(NULL,sz) - same as malloc(sz)
977
        push    ebx
978
        call    user_alloc
979
        ret
980
@@:
981
        push    ecx edx
465 serge 982
        lea     ecx, [eax - 0x1000]
448 diamond 983
        shr     ecx, 12
984
        mov     edx, [page_tabs+ecx*4]
620 diamond 985
        test    dl, USED_BLOCK
448 diamond 986
        jnz     @f
987
; attempt to realloc invalid pointer
988
.ret0:
989
        pop     edx ecx
990
        xor     eax, eax
991
        ret
992
@@:
620 diamond 993
        test    dl, DONT_FREE_BLOCK
546 diamond 994
        jnz     .ret0
448 diamond 995
        add     ebx, 0x1FFF
996
        shr     edx, 12
997
        shr     ebx, 12
998
; edx = allocated size, ebx = new size
999
        add     edx, ecx
1000
        add     ebx, ecx
1001
        cmp     edx, ebx
1002
        jb      .realloc_add
1003
; release part of allocated memory
1004
.loop:
1005
        cmp     edx, ebx
1006
        jz      .release_done
1007
        dec     edx
1008
        xor     eax, eax
1009
        xchg    eax, [page_tabs+edx*4]
1010
        test    al, 1
1011
        jz      .loop
1012
        call    free_page
1013
        mov     eax, edx
1014
        shl     eax, 12
1015
        invlpg  [eax]
1016
        jmp     .loop
1017
.release_done:
1018
        sub     ebx, ecx
1019
        cmp     ebx, 1
1020
        jnz     .nofreeall
1021
        mov     eax, [page_tabs+ecx*4]
1022
        and     eax, not 0xFFF
465 serge 1023
        mov     edx, [current_slot]
1024
        mov     ebx, [APPDATA.mem_size+edx]
448 diamond 1025
        sub     ebx, eax
1026
        add     ebx, 0x1000
1027
        or      al, FREE_BLOCK
1028
        mov     [page_tabs+ecx*4], eax
1029
        push    esi edi
465 serge 1030
        mov     esi, [APPDATA.heap_base+edx]
1031
        mov     edi, [APPDATA.heap_top+edx]
448 diamond 1032
        call    update_mem_size
1033
        call    user_normalize
1034
        pop     edi esi
1035
        jmp     .ret0   ; all freed
1036
.nofreeall:
1037
        sub     edx, ecx
1038
        shl     ebx, 12
1039
        or      ebx, USED_BLOCK
1040
        xchg    [page_tabs+ecx*4], ebx
1041
        shr     ebx, 12
1042
        sub     ebx, edx
1043
        push    ebx ecx edx
465 serge 1044
        mov     edx, [current_slot]
448 diamond 1045
        shl     ebx, 12
465 serge 1046
        sub     ebx, [APPDATA.mem_size+edx]
448 diamond 1047
        neg     ebx
1048
        call    update_mem_size
1049
        pop     edx ecx ebx
465 serge 1050
        lea     eax, [ecx+1]
448 diamond 1051
        shl     eax, 12
1052
        push    eax
823 diamond 1053
        add     ecx, edx
1054
        lea     edx, [ecx+ebx]
448 diamond 1055
        shl     ebx, 12
1056
        jz      .ret
1057
        push    esi
465 serge 1058
        mov     esi, [current_slot]
1059
        mov     esi, [APPDATA.heap_top+esi]
448 diamond 1060
        shr     esi, 12
1061
@@:
1062
        cmp     edx, esi
1063
        jae     .merge_done
1064
        mov     eax, [page_tabs+edx*4]
1065
        test    al, USED_BLOCK
823 diamond 1066
        jnz     .merge_done
448 diamond 1067
        and     dword [page_tabs+edx*4], 0
823 diamond 1068
        shr     eax, 12
1069
        add     edx, eax
1070
        shl     eax, 12
448 diamond 1071
        add     ebx, eax
1072
        jmp     @b
1073
.merge_done:
1074
        pop     esi
1075
        or      ebx, FREE_BLOCK
1076
        mov     [page_tabs+ecx*4], ebx
1077
.ret:
1078
        pop     eax edx ecx
1079
        ret
1080
.realloc_add:
1081
; get some additional memory
465 serge 1082
        mov     eax, [current_slot]
1083
        mov     eax, [APPDATA.heap_top+eax]
448 diamond 1084
        shr     eax, 12
1085
        cmp     edx, eax
1086
        jae     .cant_inplace
1087
        mov     eax, [page_tabs+edx*4]
620 diamond 1088
        test    al, FREE_BLOCK
1089
        jz      .cant_inplace
448 diamond 1090
        shr     eax, 12
1091
        add     eax, edx
620 diamond 1092
        sub     eax, ebx
448 diamond 1093
        jb      .cant_inplace
1094
        jz      @f
1095
        shl     eax, 12
1096
        or      al, FREE_BLOCK
1097
        mov     [page_tabs+ebx*4], eax
1098
@@:
1099
        mov     eax, ebx
1100
        sub     eax, ecx
1101
        shl     eax, 12
1102
        or      al, USED_BLOCK
1103
        mov     [page_tabs+ecx*4], eax
465 serge 1104
        lea     eax, [ecx+1]
448 diamond 1105
        shl     eax, 12
1106
        push    eax
1107
        push    edi
1108
        lea     edi, [page_tabs+edx*4]
1109
        mov     eax, 2
1110
        sub     ebx, edx
1111
        mov     ecx, ebx
1112
        cld
1113
        rep     stosd
1114
        pop     edi
465 serge 1115
        mov     edx, [current_slot]
448 diamond 1116
        shl     ebx, 12
465 serge 1117
        add     ebx, [APPDATA.mem_size+edx]
448 diamond 1118
        call    update_mem_size
1119
        pop     eax edx ecx
1120
        ret
1121
.cant_inplace:
1122
        push    esi edi
465 serge 1123
        mov     eax, [current_slot]
1124
        mov     esi, [APPDATA.heap_base+eax]
1125
        mov     edi, [APPDATA.heap_top+eax]
448 diamond 1126
        shr     esi, 12
1127
        shr     edi, 12
1128
        sub     ebx, ecx
1129
.find_place:
1130
        cmp     esi, edi
1131
        jae     .place_not_found
1132
        mov     eax, [page_tabs+esi*4]
1133
        test    al, FREE_BLOCK
1134
        jz      .next_place
1135
        shr     eax, 12
1136
        cmp     eax, ebx
1137
        jae     .place_found
1138
        add     esi, eax
1139
        jmp     .find_place
1140
.next_place:
1141
        shr     eax, 12
1142
        add     esi, eax
1143
        jmp     .find_place
1144
.place_not_found:
1145
        pop     edi esi
1146
        jmp     .ret0
1147
.place_found:
1148
        sub     eax, ebx
1149
        jz      @f
1150
        push    esi
620 diamond 1151
        add     esi, ebx
448 diamond 1152
        shl     eax, 12
1153
        or      al, FREE_BLOCK
1154
        mov     [page_tabs+esi*4], eax
1155
        pop     esi
1156
@@:
1157
        mov     eax, ebx
1158
        shl     eax, 12
1159
        or      al, USED_BLOCK
1160
        mov     [page_tabs+esi*4], eax
1161
        inc     esi
1162
        mov     eax, esi
1163
        shl     eax, 12
1164
        push    eax
1165
        mov     eax, [page_tabs+ecx*4]
1166
        and     eax, not 0xFFF
1167
        or      al, FREE_BLOCK
1168
        sub     edx, ecx
1169
        mov     [page_tabs+ecx*4], eax
1170
        inc     ecx
620 diamond 1171
        dec     ebx
1172
        dec     edx
1173
        jz      .no
448 diamond 1174
@@:
1175
        xor     eax, eax
1176
        xchg    eax, [page_tabs+ecx*4]
1177
        mov     [page_tabs+esi*4], eax
940 serge 1178
        mov     eax, ecx
1179
        shl     eax, 12
1180
        invlpg  [eax]
620 diamond 1181
        inc     esi
448 diamond 1182
        inc     ecx
1183
        dec     ebx
1184
        dec     edx
1185
        jnz     @b
620 diamond 1186
.no:
448 diamond 1187
        push    ebx
465 serge 1188
        mov     edx, [current_slot]
448 diamond 1189
        shl     ebx, 12
465 serge 1190
        add     ebx, [APPDATA.mem_size+edx]
448 diamond 1191
        call    update_mem_size
1192
        pop     ebx
1193
@@:
1194
        mov     dword [page_tabs+esi*4], 2
1195
        inc     esi
1196
        dec     ebx
1197
        jnz     @b
1198
        pop     eax edi esi edx ecx
1199
        ret
1200
 
278 serge 1201
if 0
164 serge 1202
align 4
1203
proc alloc_dll
1204
           pushf
1205
           cli
1206
           bsf eax, [dll_map]
1207
           jnz .find
1208
           popf
1209
           xor eax, eax
1210
           ret
1211
.find:
1212
           btr [dll_map], eax
1213
           popf
1214
           shl eax, 5
1215
           add eax, dll_tab
1216
           ret
1217
endp
1218
 
1219
align 4
1220
proc alloc_service
1221
           pushf
1222
           cli
1223
           bsf eax, [srv_map]
1224
           jnz .find
1225
           popf
1226
           xor eax, eax
1227
           ret
214 serge 1228
.find:
1229
           btr [srv_map], eax
164 serge 1230
           popf
214 serge 1231
           shl eax,0x02
1232
           lea eax,[srv_tab+eax+eax*8]   ;srv_tab+eax*36
164 serge 1233
           ret
1234
endp
278 serge 1235
 
1236
end if
940 serge 1237
 
1238
 
1239
;;;;;;;;;;;;;;      SHARED      ;;;;;;;;;;;;;;;;;
1240
 
1241
 
1242
; param
1243
;  eax= shm_map object
1244
 
1245
align 4
1246
destroy_smap:
1247
 
1248
           pushfd
1249
           cli
1250
 
945 serge 1251
           push esi
1252
           push edi
940 serge 1253
 
945 serge 1254
           mov edi, eax
1255
           mov esi, [eax+SMAP.parent]
1256
           test esi, esi
1257
           jz .done
940 serge 1258
 
945 serge 1259
           lock dec [esi+SMEM.refcount]
1260
           jnz .done
940 serge 1261
 
945 serge 1262
           mov ecx, [esi+SMEM.bk]
1263
           mov edx, [esi+SMEM.fd]
1264
 
1265
           mov [ecx+SMEM.fd], edx
1266
           mov [edx+SMEM.bk], ecx
1267
 
1268
           stdcall kernel_free, [esi+SMEM.base]
1269
           mov eax, esi
1270
           call free
1271
.done:
1272
           mov eax, edi
940 serge 1273
           call destroy_kernel_object
1274
 
945 serge 1275
           pop edi
1276
           pop esi
940 serge 1277
           popfd
1278
 
1279
           ret
1280
 
1281
E_NOTFOUND      equ  5
1282
E_ACCESS        equ 10
1283
E_NOMEM         equ 30
1284
E_PARAM         equ 33
1285
 
1286
SHM_READ        equ 0
1287
SHM_WRITE       equ 1
1288
 
1289
SHM_ACCESS_MASK equ 3
1290
 
1291
SHM_OPEN        equ (0 shl 2)
1292
SHM_OPEN_ALWAYS equ (1 shl 2)
1293
SHM_CREATE      equ (2 shl 2)
1294
 
1295
SHM_OPEN_MASK   equ (3 shl 2)
1296
 
1297
align 4
1298
proc shmem_open stdcall name:dword, size:dword, access:dword
1299
           locals
1300
              action         dd ?
1301
              owner_access   dd ?
1302
              mapped         dd ?
1303
           endl
1304
 
1305
           push ebx
1306
           push esi
1307
           push edi
1308
 
1309
           mov [mapped], 0
1310
           mov [owner_access], 0
1311
 
1312
           pushfd                      ;mutex required
1313
           cli
1314
 
1315
           mov eax, [access]
1316
           and eax, SHM_OPEN_MASK
1317
           mov [action], eax
1318
 
1213 serge 1319
           mov ebx, [name]
1320
           test ebx, ebx
940 serge 1321
           mov edx, E_PARAM
1213 serge 1322
           jz .fail
940 serge 1323
 
1324
           mov esi, [shmem_list.fd]
1325
align 4
1326
@@:
1327
           cmp esi, shmem_list
1328
           je .not_found
1329
 
943 serge 1330
           lea edx, [esi+SMEM.name] ; link , base, size
1213 serge 1331
           stdcall strncmp, edx, ebx, 32
940 serge 1332
           test eax, eax
1333
           je .found
1334
 
943 serge 1335
           mov esi, [esi+SMEM.fd]
940 serge 1336
           jmp @B
1337
 
1338
.not_found:
1339
           mov eax, [action]
1340
 
1341
           cmp eax, SHM_OPEN
1342
           mov edx, E_NOTFOUND
1213 serge 1343
           je .fail
940 serge 1344
 
1345
           cmp eax, SHM_CREATE
1346
           mov edx, E_PARAM
1347
           je .create_shm
1348
 
1349
           cmp eax, SHM_OPEN_ALWAYS
1213 serge 1350
           jne .fail
940 serge 1351
 
1352
.create_shm:
1353
 
1354
           mov ecx, [size]
1355
           test ecx, ecx
1213 serge 1356
           jz .fail
940 serge 1357
 
1358
           add ecx, 4095
1359
           and ecx, -4096
1360
           mov [size], ecx
1361
 
943 serge 1362
           mov eax, SMEM.sizeof
940 serge 1363
           call malloc
1364
           test eax, eax
1365
           mov esi, eax
1366
           mov edx, E_NOMEM
1213 serge 1367
           jz .fail
940 serge 1368
 
1369
           stdcall kernel_alloc, [size]
1370
           test eax, eax
1371
           mov [mapped], eax
1372
           mov edx, E_NOMEM
1373
           jz .cleanup
1374
 
1375
           mov ecx, [size]
1376
           mov edx, [access]
1377
           and edx, SHM_ACCESS_MASK
1378
 
943 serge 1379
           mov [esi+SMEM.base], eax
1380
           mov [esi+SMEM.size], ecx
1381
           mov [esi+SMEM.access], edx
1382
           mov [esi+SMEM.refcount], 0
1383
           mov [esi+SMEM.name+28], 0
940 serge 1384
 
943 serge 1385
           lea eax, [esi+SMEM.name]
940 serge 1386
           stdcall strncpy, eax, [name], 31
1387
 
1388
           mov eax, [shmem_list.fd]
943 serge 1389
           mov [esi+SMEM.bk], shmem_list
1390
           mov [esi+SMEM.fd], eax
940 serge 1391
 
943 serge 1392
           mov [eax+SMEM.bk], esi
940 serge 1393
           mov [shmem_list.fd], esi
1394
 
1395
           mov [action], SHM_OPEN
1396
           mov [owner_access], SHM_WRITE
1397
 
1398
.found:
1399
           mov eax, [action]
1400
 
1401
           cmp eax, SHM_CREATE
1402
           mov edx, E_ACCESS
1403
           je .exit
1404
 
1405
           cmp eax, SHM_OPEN
1406
           mov edx, E_PARAM
1407
           je .create_map
1408
 
1409
           cmp eax, SHM_OPEN_ALWAYS
1213 serge 1410
           jne .fail
940 serge 1411
 
1412
.create_map:
1413
 
1414
           mov eax, [access]
1415
           and eax, SHM_ACCESS_MASK
943 serge 1416
           cmp eax, [esi+SMEM.access]
940 serge 1417
           mov [access], eax
1418
           mov edx, E_ACCESS
1213 serge 1419
           ja .fail
940 serge 1420
 
1421
           mov ebx, [CURRENT_TASK]
1422
           shl ebx, 5
1423
           mov ebx, [CURRENT_TASK+ebx+4]
943 serge 1424
           mov eax, SMAP.sizeof
940 serge 1425
 
1426
           call create_kernel_object
1427
           test eax, eax
1428
           mov edi, eax
1429
           mov edx, E_NOMEM
1213 serge 1430
           jz .fail
940 serge 1431
 
1213 serge 1432
           inc [esi+SMEM.refcount]
1433
 
943 serge 1434
           mov [edi+SMAP.magic], 'SMAP'
1435
           mov [edi+SMAP.destroy], destroy_smap
1213 serge 1436
           mov [edi+SMAP.parent], esi
943 serge 1437
           mov [edi+SMAP.base], 0
940 serge 1438
 
943 serge 1439
           stdcall user_alloc, [esi+SMEM.size]
940 serge 1440
           test eax, eax
1441
           mov [mapped], eax
1442
           mov edx, E_NOMEM
1443
           jz .cleanup2
1444
 
943 serge 1445
           mov [edi+SMAP.base], eax
940 serge 1446
 
943 serge 1447
           mov ecx, [esi+SMEM.size]
940 serge 1448
           mov [size], ecx
1449
 
1450
           shr ecx, 12
1451
           shr eax, 10
1452
 
943 serge 1453
           mov esi, [esi+SMEM.base]
940 serge 1454
           shr esi, 10
1455
           lea edi, [page_tabs+eax]
1456
           add esi, page_tabs
1457
 
1458
           mov edx, [access]
1459
           or edx, [owner_access]
1460
           shl edx, 1
1461
           or edx, PG_USER+PG_SHARED
1462
@@:
1463
           lodsd
1464
           and eax, 0xFFFFF000
1465
           or eax, edx
1466
           stosd
1467
           loop @B
1468
 
1469
           xor edx, edx
1470
 
1471
           cmp [owner_access], 0
1213 serge 1472
           jne .fail
1473
.exit:
940 serge 1474
           mov edx, [size]
1213 serge 1475
.fail:
940 serge 1476
           mov eax, [mapped]
1477
 
1478
           popfd
1479
           pop edi
1480
           pop esi
1481
           pop ebx
1482
           ret
1483
.cleanup:
1213 serge 1484
           mov [size], edx
940 serge 1485
           mov eax, esi
1486
           call free
1487
           jmp .exit
1488
 
1489
.cleanup2:
1213 serge 1490
           mov [size], edx
940 serge 1491
           mov eax, edi
1492
           call destroy_smap
1493
           jmp .exit
1494
endp
943 serge 1495
 
1496
align 4
1497
proc shmem_close stdcall, name:dword
1498
 
1499
           mov eax, [name]
1500
           test eax, eax
1501
           jz .fail
1502
 
1503
           push esi
1504
           push edi
945 serge 1505
           pushfd
1506
           cli
943 serge 1507
 
1508
           mov esi, [current_slot]
1509
           add esi, APP_OBJ_OFFSET
1510
.next:
1511
           mov eax, [esi+APPOBJ.fd]
1512
           test eax, eax
1513
           jz @F
1514
 
1515
           cmp eax, esi
1516
           mov esi, eax
1517
           je @F
1518
 
1519
           cmp [eax+SMAP.magic], 'SMAP'
1520
           jne .next
1521
 
1522
           mov edi, [eax+SMAP.parent]
1523
           test edi, edi
1524
           jz .next
1525
 
1501 mario79 1526
           lea edi, [edi+SMEM.name]
943 serge 1527
           stdcall strncmp, [name], edi, 32
1528
           test eax, eax
1529
           jne .next
1530
 
945 serge 1531
           stdcall user_free, [esi+SMAP.base]
1532
 
1501 mario79 1533
           mov eax,esi
943 serge 1534
           call [esi+APPOBJ.destroy]
1535
@@:
945 serge 1536
           popfd
943 serge 1537
           pop edi
1538
           pop esi
1539
.fail:
1540
           ret
1541
endp
1710 art_zh 1542
diff16 "heap  code end ",0,$
1543
diff16 "heap  code size",init_kernel_heap,$