6 #define REAL_MEM_BLOCKS 0x100
11 unsigned int size
: 20;
12 unsigned int free
: 1;
18 struct mem_block blocks
[REAL_MEM_BLOCKS
];
21 static int read_file(char *name
, void *p
, size_t n
)
25 fd
= open(name
, O_RDONLY
);
32 if (read(fd
, p
, n
) != n
) {
43 static int map_file(void *start
, size_t length
, int prot
, int flags
, char *name
, long offset
)
48 fd
= open(name
, (flags
& MAP_SHARED
) ? O_RDWR
: O_RDONLY
);
55 m
= mmap(start
, length
, prot
, flags
, fd
, offset
);
57 if (m
== (void *)-1) {
67 static int real_mem_init(void)
72 if (!map_file((void *)REAL_MEM_BASE
, REAL_MEM_SIZE
,
73 PROT_READ
| PROT_WRITE
| PROT_EXEC
,
74 MAP_FIXED
| MAP_PRIVATE
, "/dev/zero", 0))
81 mem_info
.blocks
[0].size
= REAL_MEM_SIZE
;
82 mem_info
.blocks
[0].free
= 1;
87 static void real_mem_deinit(void)
90 munmap((void *)REAL_MEM_BASE
, REAL_MEM_SIZE
);
95 static void insert_block(int i
)
97 memmove(mem_info
.blocks
+ i
+ 1, mem_info
.blocks
+ i
,
98 (mem_info
.count
- i
) * sizeof(struct mem_block
));
102 static void delete_block(int i
)
105 memmove(mem_info
.blocks
+ i
, mem_info
.blocks
+ i
+ 1,
106 (mem_info
.count
- i
) * sizeof(struct mem_block
));
109 void *v86_mem_alloc(int size
)
112 char *r
= (char *)REAL_MEM_BASE
;
117 if (mem_info
.count
== REAL_MEM_BLOCKS
)
120 size
= (size
+ 15) & ~15;
122 for (i
= 0; i
< mem_info
.count
; i
++) {
123 if (mem_info
.blocks
[i
].free
&& size
< mem_info
.blocks
[i
].size
) {
126 mem_info
.blocks
[i
].size
= size
;
127 mem_info
.blocks
[i
].free
= 0;
128 mem_info
.blocks
[i
+ 1].size
-= size
;
133 r
+= mem_info
.blocks
[i
].size
;
139 void v86_mem_free(void *m
)
142 char *r
= (char *)REAL_MEM_BASE
;
148 while (m
!= (void *)r
) {
149 r
+= mem_info
.blocks
[i
].size
;
151 if (i
== mem_info
.count
)
155 mem_info
.blocks
[i
].free
= 1;
157 if (i
+ 1 < mem_info
.count
&& mem_info
.blocks
[i
+ 1].free
) {
158 mem_info
.blocks
[i
].size
+= mem_info
.blocks
[i
+ 1].size
;
162 if (i
- 1 >= 0 && mem_info
.blocks
[i
- 1].free
) {
163 mem_info
.blocks
[i
- 1].size
+= mem_info
.blocks
[i
].size
;
168 static inline void set_bit(unsigned int bit
, void *array
)
170 unsigned char *a
= array
;
171 a
[bit
/ 8] |= (1 << (bit
% 8));
174 inline u16
get_int_seg(int i
)
176 return *(u16
*)(i
* 4 + 2);
179 inline u16
get_int_off(int i
)
181 return *(u16
*)(i
* 4);
184 int v86_mem_init(void)
192 if (!map_file((void *)IVTBDA_BASE
, IVTBDA_SIZE
,
193 PROT_READ
| PROT_WRITE
| PROT_EXEC
,
194 MAP_FIXED
| MAP_PRIVATE
, "/dev/zero", 0))
200 if (!read_file("/dev/mem", (void *)IVTBDA_BASE
, IVTBDA_SIZE
)) {
201 munmap((void *)IVTBDA_BASE
, IVTBDA_SIZE
);
206 if (!map_file((void *)0xa0000, 0x100000 - 0xa0000,
207 PROT_READ
| PROT_WRITE
,
208 MAP_FIXED
| MAP_SHARED
, "/dev/mem", 0xa0000))
210 munmap((void *)IVTBDA_BASE
, IVTBDA_SIZE
);
218 void v86_mem_cleanup(void)
220 munmap((void *)IVTBDA_BASE
, IVTBDA_SIZE
);
221 munmap((void *)0xa0000, 0x100000 - 0xa0000);