Fix typo in help output.
[qemu/mini2440.git] / exec.c
blob37d58a43ea2ee5f161a57669ec639be6324ad4e3
1 /*
2 * virtual page mapping and translated block handling
3 *
4 * Copyright (c) 2003 Fabrice Bellard
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 #include "config.h"
21 #ifdef _WIN32
22 #include <windows.h>
23 #else
24 #include <sys/types.h>
25 #include <sys/mman.h>
26 #endif
27 #include <stdlib.h>
28 #include <stdio.h>
29 #include <stdarg.h>
30 #include <string.h>
31 #include <errno.h>
32 #include <unistd.h>
33 #include <inttypes.h>
35 #include "cpu.h"
36 #include "exec-all.h"
37 #if defined(CONFIG_USER_ONLY)
38 #include <qemu.h>
39 #endif
41 //#define DEBUG_TB_INVALIDATE
42 //#define DEBUG_FLUSH
43 //#define DEBUG_TLB
44 //#define DEBUG_UNASSIGNED
46 /* make various TB consistency checks */
47 //#define DEBUG_TB_CHECK
48 //#define DEBUG_TLB_CHECK
50 #if !defined(CONFIG_USER_ONLY)
51 /* TB consistency checks only implemented for usermode emulation. */
52 #undef DEBUG_TB_CHECK
53 #endif
55 /* threshold to flush the translated code buffer */
56 #define CODE_GEN_BUFFER_MAX_SIZE (CODE_GEN_BUFFER_SIZE - CODE_GEN_MAX_SIZE)
58 #define SMC_BITMAP_USE_THRESHOLD 10
60 #define MMAP_AREA_START 0x00000000
61 #define MMAP_AREA_END 0xa8000000
63 #if defined(TARGET_SPARC64)
64 #define TARGET_PHYS_ADDR_SPACE_BITS 41
65 #elif defined(TARGET_PPC64)
66 #define TARGET_PHYS_ADDR_SPACE_BITS 42
67 #else
68 /* Note: for compatibility with kqemu, we use 32 bits for x86_64 */
69 #define TARGET_PHYS_ADDR_SPACE_BITS 32
70 #endif
72 TranslationBlock tbs[CODE_GEN_MAX_BLOCKS];
73 TranslationBlock *tb_phys_hash[CODE_GEN_PHYS_HASH_SIZE];
74 int nb_tbs;
75 /* any access to the tbs or the page table must use this lock */
76 spinlock_t tb_lock = SPIN_LOCK_UNLOCKED;
78 uint8_t code_gen_buffer[CODE_GEN_BUFFER_SIZE] __attribute__((aligned (32)));
79 uint8_t *code_gen_ptr;
81 int phys_ram_size;
82 int phys_ram_fd;
83 uint8_t *phys_ram_base;
84 uint8_t *phys_ram_dirty;
85 static ram_addr_t phys_ram_alloc_offset = 0;
87 CPUState *first_cpu;
88 /* current CPU in the current thread. It is only valid inside
89 cpu_exec() */
90 CPUState *cpu_single_env;
92 typedef struct PageDesc {
93 /* list of TBs intersecting this ram page */
94 TranslationBlock *first_tb;
95 /* in order to optimize self modifying code, we count the number
96 of lookups we do to a given page to use a bitmap */
97 unsigned int code_write_count;
98 uint8_t *code_bitmap;
99 #if defined(CONFIG_USER_ONLY)
100 unsigned long flags;
101 #endif
102 } PageDesc;
104 typedef struct PhysPageDesc {
105 /* offset in host memory of the page + io_index in the low 12 bits */
106 uint32_t phys_offset;
107 } PhysPageDesc;
109 #define L2_BITS 10
110 #define L1_BITS (32 - L2_BITS - TARGET_PAGE_BITS)
112 #define L1_SIZE (1 << L1_BITS)
113 #define L2_SIZE (1 << L2_BITS)
115 static void io_mem_init(void);
117 unsigned long qemu_real_host_page_size;
118 unsigned long qemu_host_page_bits;
119 unsigned long qemu_host_page_size;
120 unsigned long qemu_host_page_mask;
122 /* XXX: for system emulation, it could just be an array */
123 static PageDesc *l1_map[L1_SIZE];
124 PhysPageDesc **l1_phys_map;
126 /* io memory support */
127 CPUWriteMemoryFunc *io_mem_write[IO_MEM_NB_ENTRIES][4];
128 CPUReadMemoryFunc *io_mem_read[IO_MEM_NB_ENTRIES][4];
129 void *io_mem_opaque[IO_MEM_NB_ENTRIES];
130 static int io_mem_nb;
132 /* log support */
133 char *logfilename = "/tmp/qemu.log";
134 FILE *logfile;
135 int loglevel;
137 /* statistics */
138 static int tlb_flush_count;
139 static int tb_flush_count;
140 static int tb_phys_invalidate_count;
142 static void page_init(void)
144 /* NOTE: we can always suppose that qemu_host_page_size >=
145 TARGET_PAGE_SIZE */
146 #ifdef _WIN32
148 SYSTEM_INFO system_info;
149 DWORD old_protect;
151 GetSystemInfo(&system_info);
152 qemu_real_host_page_size = system_info.dwPageSize;
154 VirtualProtect(code_gen_buffer, sizeof(code_gen_buffer),
155 PAGE_EXECUTE_READWRITE, &old_protect);
157 #else
158 qemu_real_host_page_size = getpagesize();
160 unsigned long start, end;
162 start = (unsigned long)code_gen_buffer;
163 start &= ~(qemu_real_host_page_size - 1);
165 end = (unsigned long)code_gen_buffer + sizeof(code_gen_buffer);
166 end += qemu_real_host_page_size - 1;
167 end &= ~(qemu_real_host_page_size - 1);
169 mprotect((void *)start, end - start,
170 PROT_READ | PROT_WRITE | PROT_EXEC);
172 #endif
174 if (qemu_host_page_size == 0)
175 qemu_host_page_size = qemu_real_host_page_size;
176 if (qemu_host_page_size < TARGET_PAGE_SIZE)
177 qemu_host_page_size = TARGET_PAGE_SIZE;
178 qemu_host_page_bits = 0;
179 while ((1 << qemu_host_page_bits) < qemu_host_page_size)
180 qemu_host_page_bits++;
181 qemu_host_page_mask = ~(qemu_host_page_size - 1);
182 l1_phys_map = qemu_vmalloc(L1_SIZE * sizeof(void *));
183 memset(l1_phys_map, 0, L1_SIZE * sizeof(void *));
186 static inline PageDesc *page_find_alloc(unsigned int index)
188 PageDesc **lp, *p;
190 lp = &l1_map[index >> L2_BITS];
191 p = *lp;
192 if (!p) {
193 /* allocate if not found */
194 p = qemu_malloc(sizeof(PageDesc) * L2_SIZE);
195 memset(p, 0, sizeof(PageDesc) * L2_SIZE);
196 *lp = p;
198 return p + (index & (L2_SIZE - 1));
201 static inline PageDesc *page_find(unsigned int index)
203 PageDesc *p;
205 p = l1_map[index >> L2_BITS];
206 if (!p)
207 return 0;
208 return p + (index & (L2_SIZE - 1));
211 static PhysPageDesc *phys_page_find_alloc(target_phys_addr_t index, int alloc)
213 void **lp, **p;
214 PhysPageDesc *pd;
216 p = (void **)l1_phys_map;
217 #if TARGET_PHYS_ADDR_SPACE_BITS > 32
219 #if TARGET_PHYS_ADDR_SPACE_BITS > (32 + L1_BITS)
220 #error unsupported TARGET_PHYS_ADDR_SPACE_BITS
221 #endif
222 lp = p + ((index >> (L1_BITS + L2_BITS)) & (L1_SIZE - 1));
223 p = *lp;
224 if (!p) {
225 /* allocate if not found */
226 if (!alloc)
227 return NULL;
228 p = qemu_vmalloc(sizeof(void *) * L1_SIZE);
229 memset(p, 0, sizeof(void *) * L1_SIZE);
230 *lp = p;
232 #endif
233 lp = p + ((index >> L2_BITS) & (L1_SIZE - 1));
234 pd = *lp;
235 if (!pd) {
236 int i;
237 /* allocate if not found */
238 if (!alloc)
239 return NULL;
240 pd = qemu_vmalloc(sizeof(PhysPageDesc) * L2_SIZE);
241 *lp = pd;
242 for (i = 0; i < L2_SIZE; i++)
243 pd[i].phys_offset = IO_MEM_UNASSIGNED;
245 return ((PhysPageDesc *)pd) + (index & (L2_SIZE - 1));
248 static inline PhysPageDesc *phys_page_find(target_phys_addr_t index)
250 return phys_page_find_alloc(index, 0);
253 #if !defined(CONFIG_USER_ONLY)
254 static void tlb_protect_code(ram_addr_t ram_addr);
255 static void tlb_unprotect_code_phys(CPUState *env, ram_addr_t ram_addr,
256 target_ulong vaddr);
257 #endif
259 void cpu_exec_init(CPUState *env)
261 CPUState **penv;
262 int cpu_index;
264 if (!code_gen_ptr) {
265 code_gen_ptr = code_gen_buffer;
266 page_init();
267 io_mem_init();
269 env->next_cpu = NULL;
270 penv = &first_cpu;
271 cpu_index = 0;
272 while (*penv != NULL) {
273 penv = (CPUState **)&(*penv)->next_cpu;
274 cpu_index++;
276 env->cpu_index = cpu_index;
277 *penv = env;
280 static inline void invalidate_page_bitmap(PageDesc *p)
282 if (p->code_bitmap) {
283 qemu_free(p->code_bitmap);
284 p->code_bitmap = NULL;
286 p->code_write_count = 0;
289 /* set to NULL all the 'first_tb' fields in all PageDescs */
290 static void page_flush_tb(void)
292 int i, j;
293 PageDesc *p;
295 for(i = 0; i < L1_SIZE; i++) {
296 p = l1_map[i];
297 if (p) {
298 for(j = 0; j < L2_SIZE; j++) {
299 p->first_tb = NULL;
300 invalidate_page_bitmap(p);
301 p++;
307 /* flush all the translation blocks */
308 /* XXX: tb_flush is currently not thread safe */
309 void tb_flush(CPUState *env1)
311 CPUState *env;
312 #if defined(DEBUG_FLUSH)
313 printf("qemu: flush code_size=%d nb_tbs=%d avg_tb_size=%d\n",
314 code_gen_ptr - code_gen_buffer,
315 nb_tbs,
316 nb_tbs > 0 ? (code_gen_ptr - code_gen_buffer) / nb_tbs : 0);
317 #endif
318 nb_tbs = 0;
320 for(env = first_cpu; env != NULL; env = env->next_cpu) {
321 memset (env->tb_jmp_cache, 0, TB_JMP_CACHE_SIZE * sizeof (void *));
324 memset (tb_phys_hash, 0, CODE_GEN_PHYS_HASH_SIZE * sizeof (void *));
325 page_flush_tb();
327 code_gen_ptr = code_gen_buffer;
328 /* XXX: flush processor icache at this point if cache flush is
329 expensive */
330 tb_flush_count++;
333 #ifdef DEBUG_TB_CHECK
335 static void tb_invalidate_check(unsigned long address)
337 TranslationBlock *tb;
338 int i;
339 address &= TARGET_PAGE_MASK;
340 for(i = 0;i < CODE_GEN_PHYS_HASH_SIZE; i++) {
341 for(tb = tb_phys_hash[i]; tb != NULL; tb = tb->phys_hash_next) {
342 if (!(address + TARGET_PAGE_SIZE <= tb->pc ||
343 address >= tb->pc + tb->size)) {
344 printf("ERROR invalidate: address=%08lx PC=%08lx size=%04x\n",
345 address, (long)tb->pc, tb->size);
351 /* verify that all the pages have correct rights for code */
352 static void tb_page_check(void)
354 TranslationBlock *tb;
355 int i, flags1, flags2;
357 for(i = 0;i < CODE_GEN_PHYS_HASH_SIZE; i++) {
358 for(tb = tb_phys_hash[i]; tb != NULL; tb = tb->phys_hash_next) {
359 flags1 = page_get_flags(tb->pc);
360 flags2 = page_get_flags(tb->pc + tb->size - 1);
361 if ((flags1 & PAGE_WRITE) || (flags2 & PAGE_WRITE)) {
362 printf("ERROR page flags: PC=%08lx size=%04x f1=%x f2=%x\n",
363 (long)tb->pc, tb->size, flags1, flags2);
369 void tb_jmp_check(TranslationBlock *tb)
371 TranslationBlock *tb1;
372 unsigned int n1;
374 /* suppress any remaining jumps to this TB */
375 tb1 = tb->jmp_first;
376 for(;;) {
377 n1 = (long)tb1 & 3;
378 tb1 = (TranslationBlock *)((long)tb1 & ~3);
379 if (n1 == 2)
380 break;
381 tb1 = tb1->jmp_next[n1];
383 /* check end of list */
384 if (tb1 != tb) {
385 printf("ERROR: jmp_list from 0x%08lx\n", (long)tb);
389 #endif
391 /* invalidate one TB */
392 static inline void tb_remove(TranslationBlock **ptb, TranslationBlock *tb,
393 int next_offset)
395 TranslationBlock *tb1;
396 for(;;) {
397 tb1 = *ptb;
398 if (tb1 == tb) {
399 *ptb = *(TranslationBlock **)((char *)tb1 + next_offset);
400 break;
402 ptb = (TranslationBlock **)((char *)tb1 + next_offset);
406 static inline void tb_page_remove(TranslationBlock **ptb, TranslationBlock *tb)
408 TranslationBlock *tb1;
409 unsigned int n1;
411 for(;;) {
412 tb1 = *ptb;
413 n1 = (long)tb1 & 3;
414 tb1 = (TranslationBlock *)((long)tb1 & ~3);
415 if (tb1 == tb) {
416 *ptb = tb1->page_next[n1];
417 break;
419 ptb = &tb1->page_next[n1];
423 static inline void tb_jmp_remove(TranslationBlock *tb, int n)
425 TranslationBlock *tb1, **ptb;
426 unsigned int n1;
428 ptb = &tb->jmp_next[n];
429 tb1 = *ptb;
430 if (tb1) {
431 /* find tb(n) in circular list */
432 for(;;) {
433 tb1 = *ptb;
434 n1 = (long)tb1 & 3;
435 tb1 = (TranslationBlock *)((long)tb1 & ~3);
436 if (n1 == n && tb1 == tb)
437 break;
438 if (n1 == 2) {
439 ptb = &tb1->jmp_first;
440 } else {
441 ptb = &tb1->jmp_next[n1];
444 /* now we can suppress tb(n) from the list */
445 *ptb = tb->jmp_next[n];
447 tb->jmp_next[n] = NULL;
451 /* reset the jump entry 'n' of a TB so that it is not chained to
452 another TB */
453 static inline void tb_reset_jump(TranslationBlock *tb, int n)
455 tb_set_jmp_target(tb, n, (unsigned long)(tb->tc_ptr + tb->tb_next_offset[n]));
458 static inline void tb_phys_invalidate(TranslationBlock *tb, unsigned int page_addr)
460 CPUState *env;
461 PageDesc *p;
462 unsigned int h, n1;
463 target_ulong phys_pc;
464 TranslationBlock *tb1, *tb2;
466 /* remove the TB from the hash list */
467 phys_pc = tb->page_addr[0] + (tb->pc & ~TARGET_PAGE_MASK);
468 h = tb_phys_hash_func(phys_pc);
469 tb_remove(&tb_phys_hash[h], tb,
470 offsetof(TranslationBlock, phys_hash_next));
472 /* remove the TB from the page list */
473 if (tb->page_addr[0] != page_addr) {
474 p = page_find(tb->page_addr[0] >> TARGET_PAGE_BITS);
475 tb_page_remove(&p->first_tb, tb);
476 invalidate_page_bitmap(p);
478 if (tb->page_addr[1] != -1 && tb->page_addr[1] != page_addr) {
479 p = page_find(tb->page_addr[1] >> TARGET_PAGE_BITS);
480 tb_page_remove(&p->first_tb, tb);
481 invalidate_page_bitmap(p);
484 tb_invalidated_flag = 1;
486 /* remove the TB from the hash list */
487 h = tb_jmp_cache_hash_func(tb->pc);
488 for(env = first_cpu; env != NULL; env = env->next_cpu) {
489 if (env->tb_jmp_cache[h] == tb)
490 env->tb_jmp_cache[h] = NULL;
493 /* suppress this TB from the two jump lists */
494 tb_jmp_remove(tb, 0);
495 tb_jmp_remove(tb, 1);
497 /* suppress any remaining jumps to this TB */
498 tb1 = tb->jmp_first;
499 for(;;) {
500 n1 = (long)tb1 & 3;
501 if (n1 == 2)
502 break;
503 tb1 = (TranslationBlock *)((long)tb1 & ~3);
504 tb2 = tb1->jmp_next[n1];
505 tb_reset_jump(tb1, n1);
506 tb1->jmp_next[n1] = NULL;
507 tb1 = tb2;
509 tb->jmp_first = (TranslationBlock *)((long)tb | 2); /* fail safe */
511 tb_phys_invalidate_count++;
514 static inline void set_bits(uint8_t *tab, int start, int len)
516 int end, mask, end1;
518 end = start + len;
519 tab += start >> 3;
520 mask = 0xff << (start & 7);
521 if ((start & ~7) == (end & ~7)) {
522 if (start < end) {
523 mask &= ~(0xff << (end & 7));
524 *tab |= mask;
526 } else {
527 *tab++ |= mask;
528 start = (start + 8) & ~7;
529 end1 = end & ~7;
530 while (start < end1) {
531 *tab++ = 0xff;
532 start += 8;
534 if (start < end) {
535 mask = ~(0xff << (end & 7));
536 *tab |= mask;
541 static void build_page_bitmap(PageDesc *p)
543 int n, tb_start, tb_end;
544 TranslationBlock *tb;
546 p->code_bitmap = qemu_malloc(TARGET_PAGE_SIZE / 8);
547 if (!p->code_bitmap)
548 return;
549 memset(p->code_bitmap, 0, TARGET_PAGE_SIZE / 8);
551 tb = p->first_tb;
552 while (tb != NULL) {
553 n = (long)tb & 3;
554 tb = (TranslationBlock *)((long)tb & ~3);
555 /* NOTE: this is subtle as a TB may span two physical pages */
556 if (n == 0) {
557 /* NOTE: tb_end may be after the end of the page, but
558 it is not a problem */
559 tb_start = tb->pc & ~TARGET_PAGE_MASK;
560 tb_end = tb_start + tb->size;
561 if (tb_end > TARGET_PAGE_SIZE)
562 tb_end = TARGET_PAGE_SIZE;
563 } else {
564 tb_start = 0;
565 tb_end = ((tb->pc + tb->size) & ~TARGET_PAGE_MASK);
567 set_bits(p->code_bitmap, tb_start, tb_end - tb_start);
568 tb = tb->page_next[n];
572 #ifdef TARGET_HAS_PRECISE_SMC
574 static void tb_gen_code(CPUState *env,
575 target_ulong pc, target_ulong cs_base, int flags,
576 int cflags)
578 TranslationBlock *tb;
579 uint8_t *tc_ptr;
580 target_ulong phys_pc, phys_page2, virt_page2;
581 int code_gen_size;
583 phys_pc = get_phys_addr_code(env, pc);
584 tb = tb_alloc(pc);
585 if (!tb) {
586 /* flush must be done */
587 tb_flush(env);
588 /* cannot fail at this point */
589 tb = tb_alloc(pc);
591 tc_ptr = code_gen_ptr;
592 tb->tc_ptr = tc_ptr;
593 tb->cs_base = cs_base;
594 tb->flags = flags;
595 tb->cflags = cflags;
596 cpu_gen_code(env, tb, CODE_GEN_MAX_SIZE, &code_gen_size);
597 code_gen_ptr = (void *)(((unsigned long)code_gen_ptr + code_gen_size + CODE_GEN_ALIGN - 1) & ~(CODE_GEN_ALIGN - 1));
599 /* check next page if needed */
600 virt_page2 = (pc + tb->size - 1) & TARGET_PAGE_MASK;
601 phys_page2 = -1;
602 if ((pc & TARGET_PAGE_MASK) != virt_page2) {
603 phys_page2 = get_phys_addr_code(env, virt_page2);
605 tb_link_phys(tb, phys_pc, phys_page2);
607 #endif
609 /* invalidate all TBs which intersect with the target physical page
610 starting in range [start;end[. NOTE: start and end must refer to
611 the same physical page. 'is_cpu_write_access' should be true if called
612 from a real cpu write access: the virtual CPU will exit the current
613 TB if code is modified inside this TB. */
614 void tb_invalidate_phys_page_range(target_ulong start, target_ulong end,
615 int is_cpu_write_access)
617 int n, current_tb_modified, current_tb_not_found, current_flags;
618 CPUState *env = cpu_single_env;
619 PageDesc *p;
620 TranslationBlock *tb, *tb_next, *current_tb, *saved_tb;
621 target_ulong tb_start, tb_end;
622 target_ulong current_pc, current_cs_base;
624 p = page_find(start >> TARGET_PAGE_BITS);
625 if (!p)
626 return;
627 if (!p->code_bitmap &&
628 ++p->code_write_count >= SMC_BITMAP_USE_THRESHOLD &&
629 is_cpu_write_access) {
630 /* build code bitmap */
631 build_page_bitmap(p);
634 /* we remove all the TBs in the range [start, end[ */
635 /* XXX: see if in some cases it could be faster to invalidate all the code */
636 current_tb_not_found = is_cpu_write_access;
637 current_tb_modified = 0;
638 current_tb = NULL; /* avoid warning */
639 current_pc = 0; /* avoid warning */
640 current_cs_base = 0; /* avoid warning */
641 current_flags = 0; /* avoid warning */
642 tb = p->first_tb;
643 while (tb != NULL) {
644 n = (long)tb & 3;
645 tb = (TranslationBlock *)((long)tb & ~3);
646 tb_next = tb->page_next[n];
647 /* NOTE: this is subtle as a TB may span two physical pages */
648 if (n == 0) {
649 /* NOTE: tb_end may be after the end of the page, but
650 it is not a problem */
651 tb_start = tb->page_addr[0] + (tb->pc & ~TARGET_PAGE_MASK);
652 tb_end = tb_start + tb->size;
653 } else {
654 tb_start = tb->page_addr[1];
655 tb_end = tb_start + ((tb->pc + tb->size) & ~TARGET_PAGE_MASK);
657 if (!(tb_end <= start || tb_start >= end)) {
658 #ifdef TARGET_HAS_PRECISE_SMC
659 if (current_tb_not_found) {
660 current_tb_not_found = 0;
661 current_tb = NULL;
662 if (env->mem_write_pc) {
663 /* now we have a real cpu fault */
664 current_tb = tb_find_pc(env->mem_write_pc);
667 if (current_tb == tb &&
668 !(current_tb->cflags & CF_SINGLE_INSN)) {
669 /* If we are modifying the current TB, we must stop
670 its execution. We could be more precise by checking
671 that the modification is after the current PC, but it
672 would require a specialized function to partially
673 restore the CPU state */
675 current_tb_modified = 1;
676 cpu_restore_state(current_tb, env,
677 env->mem_write_pc, NULL);
678 #if defined(TARGET_I386)
679 current_flags = env->hflags;
680 current_flags |= (env->eflags & (IOPL_MASK | TF_MASK | VM_MASK));
681 current_cs_base = (target_ulong)env->segs[R_CS].base;
682 current_pc = current_cs_base + env->eip;
683 #else
684 #error unsupported CPU
685 #endif
687 #endif /* TARGET_HAS_PRECISE_SMC */
688 /* we need to do that to handle the case where a signal
689 occurs while doing tb_phys_invalidate() */
690 saved_tb = NULL;
691 if (env) {
692 saved_tb = env->current_tb;
693 env->current_tb = NULL;
695 tb_phys_invalidate(tb, -1);
696 if (env) {
697 env->current_tb = saved_tb;
698 if (env->interrupt_request && env->current_tb)
699 cpu_interrupt(env, env->interrupt_request);
702 tb = tb_next;
704 #if !defined(CONFIG_USER_ONLY)
705 /* if no code remaining, no need to continue to use slow writes */
706 if (!p->first_tb) {
707 invalidate_page_bitmap(p);
708 if (is_cpu_write_access) {
709 tlb_unprotect_code_phys(env, start, env->mem_write_vaddr);
712 #endif
713 #ifdef TARGET_HAS_PRECISE_SMC
714 if (current_tb_modified) {
715 /* we generate a block containing just the instruction
716 modifying the memory. It will ensure that it cannot modify
717 itself */
718 env->current_tb = NULL;
719 tb_gen_code(env, current_pc, current_cs_base, current_flags,
720 CF_SINGLE_INSN);
721 cpu_resume_from_signal(env, NULL);
723 #endif
726 /* len must be <= 8 and start must be a multiple of len */
727 static inline void tb_invalidate_phys_page_fast(target_ulong start, int len)
729 PageDesc *p;
730 int offset, b;
731 #if 0
732 if (1) {
733 if (loglevel) {
734 fprintf(logfile, "modifying code at 0x%x size=%d EIP=%x PC=%08x\n",
735 cpu_single_env->mem_write_vaddr, len,
736 cpu_single_env->eip,
737 cpu_single_env->eip + (long)cpu_single_env->segs[R_CS].base);
740 #endif
741 p = page_find(start >> TARGET_PAGE_BITS);
742 if (!p)
743 return;
744 if (p->code_bitmap) {
745 offset = start & ~TARGET_PAGE_MASK;
746 b = p->code_bitmap[offset >> 3] >> (offset & 7);
747 if (b & ((1 << len) - 1))
748 goto do_invalidate;
749 } else {
750 do_invalidate:
751 tb_invalidate_phys_page_range(start, start + len, 1);
755 #if !defined(CONFIG_SOFTMMU)
756 static void tb_invalidate_phys_page(target_ulong addr,
757 unsigned long pc, void *puc)
759 int n, current_flags, current_tb_modified;
760 target_ulong current_pc, current_cs_base;
761 PageDesc *p;
762 TranslationBlock *tb, *current_tb;
763 #ifdef TARGET_HAS_PRECISE_SMC
764 CPUState *env = cpu_single_env;
765 #endif
767 addr &= TARGET_PAGE_MASK;
768 p = page_find(addr >> TARGET_PAGE_BITS);
769 if (!p)
770 return;
771 tb = p->first_tb;
772 current_tb_modified = 0;
773 current_tb = NULL;
774 current_pc = 0; /* avoid warning */
775 current_cs_base = 0; /* avoid warning */
776 current_flags = 0; /* avoid warning */
777 #ifdef TARGET_HAS_PRECISE_SMC
778 if (tb && pc != 0) {
779 current_tb = tb_find_pc(pc);
781 #endif
782 while (tb != NULL) {
783 n = (long)tb & 3;
784 tb = (TranslationBlock *)((long)tb & ~3);
785 #ifdef TARGET_HAS_PRECISE_SMC
786 if (current_tb == tb &&
787 !(current_tb->cflags & CF_SINGLE_INSN)) {
788 /* If we are modifying the current TB, we must stop
789 its execution. We could be more precise by checking
790 that the modification is after the current PC, but it
791 would require a specialized function to partially
792 restore the CPU state */
794 current_tb_modified = 1;
795 cpu_restore_state(current_tb, env, pc, puc);
796 #if defined(TARGET_I386)
797 current_flags = env->hflags;
798 current_flags |= (env->eflags & (IOPL_MASK | TF_MASK | VM_MASK));
799 current_cs_base = (target_ulong)env->segs[R_CS].base;
800 current_pc = current_cs_base + env->eip;
801 #else
802 #error unsupported CPU
803 #endif
805 #endif /* TARGET_HAS_PRECISE_SMC */
806 tb_phys_invalidate(tb, addr);
807 tb = tb->page_next[n];
809 p->first_tb = NULL;
810 #ifdef TARGET_HAS_PRECISE_SMC
811 if (current_tb_modified) {
812 /* we generate a block containing just the instruction
813 modifying the memory. It will ensure that it cannot modify
814 itself */
815 env->current_tb = NULL;
816 tb_gen_code(env, current_pc, current_cs_base, current_flags,
817 CF_SINGLE_INSN);
818 cpu_resume_from_signal(env, puc);
820 #endif
822 #endif
824 /* add the tb in the target page and protect it if necessary */
825 static inline void tb_alloc_page(TranslationBlock *tb,
826 unsigned int n, target_ulong page_addr)
828 PageDesc *p;
829 TranslationBlock *last_first_tb;
831 tb->page_addr[n] = page_addr;
832 p = page_find_alloc(page_addr >> TARGET_PAGE_BITS);
833 tb->page_next[n] = p->first_tb;
834 last_first_tb = p->first_tb;
835 p->first_tb = (TranslationBlock *)((long)tb | n);
836 invalidate_page_bitmap(p);
838 #if defined(TARGET_HAS_SMC) || 1
840 #if defined(CONFIG_USER_ONLY)
841 if (p->flags & PAGE_WRITE) {
842 target_ulong addr;
843 PageDesc *p2;
844 int prot;
846 /* force the host page as non writable (writes will have a
847 page fault + mprotect overhead) */
848 page_addr &= qemu_host_page_mask;
849 prot = 0;
850 for(addr = page_addr; addr < page_addr + qemu_host_page_size;
851 addr += TARGET_PAGE_SIZE) {
853 p2 = page_find (addr >> TARGET_PAGE_BITS);
854 if (!p2)
855 continue;
856 prot |= p2->flags;
857 p2->flags &= ~PAGE_WRITE;
858 page_get_flags(addr);
860 mprotect(g2h(page_addr), qemu_host_page_size,
861 (prot & PAGE_BITS) & ~PAGE_WRITE);
862 #ifdef DEBUG_TB_INVALIDATE
863 printf("protecting code page: 0x%08lx\n",
864 page_addr);
865 #endif
867 #else
868 /* if some code is already present, then the pages are already
869 protected. So we handle the case where only the first TB is
870 allocated in a physical page */
871 if (!last_first_tb) {
872 tlb_protect_code(page_addr);
874 #endif
876 #endif /* TARGET_HAS_SMC */
879 /* Allocate a new translation block. Flush the translation buffer if
880 too many translation blocks or too much generated code. */
881 TranslationBlock *tb_alloc(target_ulong pc)
883 TranslationBlock *tb;
885 if (nb_tbs >= CODE_GEN_MAX_BLOCKS ||
886 (code_gen_ptr - code_gen_buffer) >= CODE_GEN_BUFFER_MAX_SIZE)
887 return NULL;
888 tb = &tbs[nb_tbs++];
889 tb->pc = pc;
890 tb->cflags = 0;
891 return tb;
894 /* add a new TB and link it to the physical page tables. phys_page2 is
895 (-1) to indicate that only one page contains the TB. */
896 void tb_link_phys(TranslationBlock *tb,
897 target_ulong phys_pc, target_ulong phys_page2)
899 unsigned int h;
900 TranslationBlock **ptb;
902 /* add in the physical hash table */
903 h = tb_phys_hash_func(phys_pc);
904 ptb = &tb_phys_hash[h];
905 tb->phys_hash_next = *ptb;
906 *ptb = tb;
908 /* add in the page list */
909 tb_alloc_page(tb, 0, phys_pc & TARGET_PAGE_MASK);
910 if (phys_page2 != -1)
911 tb_alloc_page(tb, 1, phys_page2);
912 else
913 tb->page_addr[1] = -1;
915 tb->jmp_first = (TranslationBlock *)((long)tb | 2);
916 tb->jmp_next[0] = NULL;
917 tb->jmp_next[1] = NULL;
918 #ifdef USE_CODE_COPY
919 tb->cflags &= ~CF_FP_USED;
920 if (tb->cflags & CF_TB_FP_USED)
921 tb->cflags |= CF_FP_USED;
922 #endif
924 /* init original jump addresses */
925 if (tb->tb_next_offset[0] != 0xffff)
926 tb_reset_jump(tb, 0);
927 if (tb->tb_next_offset[1] != 0xffff)
928 tb_reset_jump(tb, 1);
930 #ifdef DEBUG_TB_CHECK
931 tb_page_check();
932 #endif
935 /* find the TB 'tb' such that tb[0].tc_ptr <= tc_ptr <
936 tb[1].tc_ptr. Return NULL if not found */
937 TranslationBlock *tb_find_pc(unsigned long tc_ptr)
939 int m_min, m_max, m;
940 unsigned long v;
941 TranslationBlock *tb;
943 if (nb_tbs <= 0)
944 return NULL;
945 if (tc_ptr < (unsigned long)code_gen_buffer ||
946 tc_ptr >= (unsigned long)code_gen_ptr)
947 return NULL;
948 /* binary search (cf Knuth) */
949 m_min = 0;
950 m_max = nb_tbs - 1;
951 while (m_min <= m_max) {
952 m = (m_min + m_max) >> 1;
953 tb = &tbs[m];
954 v = (unsigned long)tb->tc_ptr;
955 if (v == tc_ptr)
956 return tb;
957 else if (tc_ptr < v) {
958 m_max = m - 1;
959 } else {
960 m_min = m + 1;
963 return &tbs[m_max];
966 static void tb_reset_jump_recursive(TranslationBlock *tb);
968 static inline void tb_reset_jump_recursive2(TranslationBlock *tb, int n)
970 TranslationBlock *tb1, *tb_next, **ptb;
971 unsigned int n1;
973 tb1 = tb->jmp_next[n];
974 if (tb1 != NULL) {
975 /* find head of list */
976 for(;;) {
977 n1 = (long)tb1 & 3;
978 tb1 = (TranslationBlock *)((long)tb1 & ~3);
979 if (n1 == 2)
980 break;
981 tb1 = tb1->jmp_next[n1];
983 /* we are now sure now that tb jumps to tb1 */
984 tb_next = tb1;
986 /* remove tb from the jmp_first list */
987 ptb = &tb_next->jmp_first;
988 for(;;) {
989 tb1 = *ptb;
990 n1 = (long)tb1 & 3;
991 tb1 = (TranslationBlock *)((long)tb1 & ~3);
992 if (n1 == n && tb1 == tb)
993 break;
994 ptb = &tb1->jmp_next[n1];
996 *ptb = tb->jmp_next[n];
997 tb->jmp_next[n] = NULL;
999 /* suppress the jump to next tb in generated code */
1000 tb_reset_jump(tb, n);
1002 /* suppress jumps in the tb on which we could have jumped */
1003 tb_reset_jump_recursive(tb_next);
1007 static void tb_reset_jump_recursive(TranslationBlock *tb)
1009 tb_reset_jump_recursive2(tb, 0);
1010 tb_reset_jump_recursive2(tb, 1);
1013 #if defined(TARGET_HAS_ICE)
1014 static void breakpoint_invalidate(CPUState *env, target_ulong pc)
1016 target_ulong addr, pd;
1017 ram_addr_t ram_addr;
1018 PhysPageDesc *p;
1020 addr = cpu_get_phys_page_debug(env, pc);
1021 p = phys_page_find(addr >> TARGET_PAGE_BITS);
1022 if (!p) {
1023 pd = IO_MEM_UNASSIGNED;
1024 } else {
1025 pd = p->phys_offset;
1027 ram_addr = (pd & TARGET_PAGE_MASK) | (pc & ~TARGET_PAGE_MASK);
1028 tb_invalidate_phys_page_range(ram_addr, ram_addr + 1, 0);
1030 #endif
1032 /* add a breakpoint. EXCP_DEBUG is returned by the CPU loop if a
1033 breakpoint is reached */
1034 int cpu_breakpoint_insert(CPUState *env, target_ulong pc)
1036 #if defined(TARGET_HAS_ICE)
1037 int i;
1039 for(i = 0; i < env->nb_breakpoints; i++) {
1040 if (env->breakpoints[i] == pc)
1041 return 0;
1044 if (env->nb_breakpoints >= MAX_BREAKPOINTS)
1045 return -1;
1046 env->breakpoints[env->nb_breakpoints++] = pc;
1048 breakpoint_invalidate(env, pc);
1049 return 0;
1050 #else
1051 return -1;
1052 #endif
1055 /* remove a breakpoint */
1056 int cpu_breakpoint_remove(CPUState *env, target_ulong pc)
1058 #if defined(TARGET_HAS_ICE)
1059 int i;
1060 for(i = 0; i < env->nb_breakpoints; i++) {
1061 if (env->breakpoints[i] == pc)
1062 goto found;
1064 return -1;
1065 found:
1066 env->nb_breakpoints--;
1067 if (i < env->nb_breakpoints)
1068 env->breakpoints[i] = env->breakpoints[env->nb_breakpoints];
1070 breakpoint_invalidate(env, pc);
1071 return 0;
1072 #else
1073 return -1;
1074 #endif
1077 /* enable or disable single step mode. EXCP_DEBUG is returned by the
1078 CPU loop after each instruction */
1079 void cpu_single_step(CPUState *env, int enabled)
1081 #if defined(TARGET_HAS_ICE)
1082 if (env->singlestep_enabled != enabled) {
1083 env->singlestep_enabled = enabled;
1084 /* must flush all the translated code to avoid inconsistancies */
1085 /* XXX: only flush what is necessary */
1086 tb_flush(env);
1088 #endif
1091 /* enable or disable low levels log */
1092 void cpu_set_log(int log_flags)
1094 loglevel = log_flags;
1095 if (loglevel && !logfile) {
1096 logfile = fopen(logfilename, "w");
1097 if (!logfile) {
1098 perror(logfilename);
1099 _exit(1);
1101 #if !defined(CONFIG_SOFTMMU)
1102 /* must avoid mmap() usage of glibc by setting a buffer "by hand" */
1104 static uint8_t logfile_buf[4096];
1105 setvbuf(logfile, logfile_buf, _IOLBF, sizeof(logfile_buf));
1107 #else
1108 setvbuf(logfile, NULL, _IOLBF, 0);
1109 #endif
1113 void cpu_set_log_filename(const char *filename)
1115 logfilename = strdup(filename);
1118 /* mask must never be zero, except for A20 change call */
1119 void cpu_interrupt(CPUState *env, int mask)
1121 TranslationBlock *tb;
1122 static int interrupt_lock;
1124 env->interrupt_request |= mask;
1125 /* if the cpu is currently executing code, we must unlink it and
1126 all the potentially executing TB */
1127 tb = env->current_tb;
1128 if (tb && !testandset(&interrupt_lock)) {
1129 env->current_tb = NULL;
1130 tb_reset_jump_recursive(tb);
1131 interrupt_lock = 0;
1135 void cpu_reset_interrupt(CPUState *env, int mask)
1137 env->interrupt_request &= ~mask;
1140 CPULogItem cpu_log_items[] = {
1141 { CPU_LOG_TB_OUT_ASM, "out_asm",
1142 "show generated host assembly code for each compiled TB" },
1143 { CPU_LOG_TB_IN_ASM, "in_asm",
1144 "show target assembly code for each compiled TB" },
1145 { CPU_LOG_TB_OP, "op",
1146 "show micro ops for each compiled TB (only usable if 'in_asm' used)" },
1147 #ifdef TARGET_I386
1148 { CPU_LOG_TB_OP_OPT, "op_opt",
1149 "show micro ops after optimization for each compiled TB" },
1150 #endif
1151 { CPU_LOG_INT, "int",
1152 "show interrupts/exceptions in short format" },
1153 { CPU_LOG_EXEC, "exec",
1154 "show trace before each executed TB (lots of logs)" },
1155 { CPU_LOG_TB_CPU, "cpu",
1156 "show CPU state before bloc translation" },
1157 #ifdef TARGET_I386
1158 { CPU_LOG_PCALL, "pcall",
1159 "show protected mode far calls/returns/exceptions" },
1160 #endif
1161 #ifdef DEBUG_IOPORT
1162 { CPU_LOG_IOPORT, "ioport",
1163 "show all i/o ports accesses" },
1164 #endif
1165 { 0, NULL, NULL },
1168 static int cmp1(const char *s1, int n, const char *s2)
1170 if (strlen(s2) != n)
1171 return 0;
1172 return memcmp(s1, s2, n) == 0;
1175 /* takes a comma separated list of log masks. Return 0 if error. */
1176 int cpu_str_to_log_mask(const char *str)
1178 CPULogItem *item;
1179 int mask;
1180 const char *p, *p1;
1182 p = str;
1183 mask = 0;
1184 for(;;) {
1185 p1 = strchr(p, ',');
1186 if (!p1)
1187 p1 = p + strlen(p);
1188 if(cmp1(p,p1-p,"all")) {
1189 for(item = cpu_log_items; item->mask != 0; item++) {
1190 mask |= item->mask;
1192 } else {
1193 for(item = cpu_log_items; item->mask != 0; item++) {
1194 if (cmp1(p, p1 - p, item->name))
1195 goto found;
1197 return 0;
1199 found:
1200 mask |= item->mask;
1201 if (*p1 != ',')
1202 break;
1203 p = p1 + 1;
1205 return mask;
1208 void cpu_abort(CPUState *env, const char *fmt, ...)
1210 va_list ap;
1212 va_start(ap, fmt);
1213 fprintf(stderr, "qemu: fatal: ");
1214 vfprintf(stderr, fmt, ap);
1215 fprintf(stderr, "\n");
1216 #ifdef TARGET_I386
1217 cpu_dump_state(env, stderr, fprintf, X86_DUMP_FPU | X86_DUMP_CCOP);
1218 #else
1219 cpu_dump_state(env, stderr, fprintf, 0);
1220 #endif
1221 va_end(ap);
1222 abort();
1225 CPUState *cpu_copy(CPUState *env)
1227 CPUState *new_env = cpu_init();
1228 /* preserve chaining and index */
1229 CPUState *next_cpu = new_env->next_cpu;
1230 int cpu_index = new_env->cpu_index;
1231 memcpy(new_env, env, sizeof(CPUState));
1232 new_env->next_cpu = next_cpu;
1233 new_env->cpu_index = cpu_index;
1234 return new_env;
1237 #if !defined(CONFIG_USER_ONLY)
1239 /* NOTE: if flush_global is true, also flush global entries (not
1240 implemented yet) */
1241 void tlb_flush(CPUState *env, int flush_global)
1243 int i;
1245 #if defined(DEBUG_TLB)
1246 printf("tlb_flush:\n");
1247 #endif
1248 /* must reset current TB so that interrupts cannot modify the
1249 links while we are modifying them */
1250 env->current_tb = NULL;
1252 for(i = 0; i < CPU_TLB_SIZE; i++) {
1253 env->tlb_table[0][i].addr_read = -1;
1254 env->tlb_table[0][i].addr_write = -1;
1255 env->tlb_table[0][i].addr_code = -1;
1256 env->tlb_table[1][i].addr_read = -1;
1257 env->tlb_table[1][i].addr_write = -1;
1258 env->tlb_table[1][i].addr_code = -1;
1261 memset (env->tb_jmp_cache, 0, TB_JMP_CACHE_SIZE * sizeof (void *));
1263 #if !defined(CONFIG_SOFTMMU)
1264 munmap((void *)MMAP_AREA_START, MMAP_AREA_END - MMAP_AREA_START);
1265 #endif
1266 #ifdef USE_KQEMU
1267 if (env->kqemu_enabled) {
1268 kqemu_flush(env, flush_global);
1270 #endif
1271 tlb_flush_count++;
1274 static inline void tlb_flush_entry(CPUTLBEntry *tlb_entry, target_ulong addr)
1276 if (addr == (tlb_entry->addr_read &
1277 (TARGET_PAGE_MASK | TLB_INVALID_MASK)) ||
1278 addr == (tlb_entry->addr_write &
1279 (TARGET_PAGE_MASK | TLB_INVALID_MASK)) ||
1280 addr == (tlb_entry->addr_code &
1281 (TARGET_PAGE_MASK | TLB_INVALID_MASK))) {
1282 tlb_entry->addr_read = -1;
1283 tlb_entry->addr_write = -1;
1284 tlb_entry->addr_code = -1;
1288 void tlb_flush_page(CPUState *env, target_ulong addr)
1290 int i;
1291 TranslationBlock *tb;
1293 #if defined(DEBUG_TLB)
1294 printf("tlb_flush_page: " TARGET_FMT_lx "\n", addr);
1295 #endif
1296 /* must reset current TB so that interrupts cannot modify the
1297 links while we are modifying them */
1298 env->current_tb = NULL;
1300 addr &= TARGET_PAGE_MASK;
1301 i = (addr >> TARGET_PAGE_BITS) & (CPU_TLB_SIZE - 1);
1302 tlb_flush_entry(&env->tlb_table[0][i], addr);
1303 tlb_flush_entry(&env->tlb_table[1][i], addr);
1305 /* Discard jump cache entries for any tb which might potentially
1306 overlap the flushed page. */
1307 i = tb_jmp_cache_hash_page(addr - TARGET_PAGE_SIZE);
1308 memset (&env->tb_jmp_cache[i], 0, TB_JMP_PAGE_SIZE * sizeof(tb));
1310 i = tb_jmp_cache_hash_page(addr);
1311 memset (&env->tb_jmp_cache[i], 0, TB_JMP_PAGE_SIZE * sizeof(tb));
1313 #if !defined(CONFIG_SOFTMMU)
1314 if (addr < MMAP_AREA_END)
1315 munmap((void *)addr, TARGET_PAGE_SIZE);
1316 #endif
1317 #ifdef USE_KQEMU
1318 if (env->kqemu_enabled) {
1319 kqemu_flush_page(env, addr);
1321 #endif
1324 /* update the TLBs so that writes to code in the virtual page 'addr'
1325 can be detected */
1326 static void tlb_protect_code(ram_addr_t ram_addr)
1328 cpu_physical_memory_reset_dirty(ram_addr,
1329 ram_addr + TARGET_PAGE_SIZE,
1330 CODE_DIRTY_FLAG);
1333 /* update the TLB so that writes in physical page 'phys_addr' are no longer
1334 tested for self modifying code */
1335 static void tlb_unprotect_code_phys(CPUState *env, ram_addr_t ram_addr,
1336 target_ulong vaddr)
1338 phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS] |= CODE_DIRTY_FLAG;
1341 static inline void tlb_reset_dirty_range(CPUTLBEntry *tlb_entry,
1342 unsigned long start, unsigned long length)
1344 unsigned long addr;
1345 if ((tlb_entry->addr_write & ~TARGET_PAGE_MASK) == IO_MEM_RAM) {
1346 addr = (tlb_entry->addr_write & TARGET_PAGE_MASK) + tlb_entry->addend;
1347 if ((addr - start) < length) {
1348 tlb_entry->addr_write = (tlb_entry->addr_write & TARGET_PAGE_MASK) | IO_MEM_NOTDIRTY;
1353 void cpu_physical_memory_reset_dirty(ram_addr_t start, ram_addr_t end,
1354 int dirty_flags)
1356 CPUState *env;
1357 unsigned long length, start1;
1358 int i, mask, len;
1359 uint8_t *p;
1361 start &= TARGET_PAGE_MASK;
1362 end = TARGET_PAGE_ALIGN(end);
1364 length = end - start;
1365 if (length == 0)
1366 return;
1367 len = length >> TARGET_PAGE_BITS;
1368 #ifdef USE_KQEMU
1369 /* XXX: should not depend on cpu context */
1370 env = first_cpu;
1371 if (env->kqemu_enabled) {
1372 ram_addr_t addr;
1373 addr = start;
1374 for(i = 0; i < len; i++) {
1375 kqemu_set_notdirty(env, addr);
1376 addr += TARGET_PAGE_SIZE;
1379 #endif
1380 mask = ~dirty_flags;
1381 p = phys_ram_dirty + (start >> TARGET_PAGE_BITS);
1382 for(i = 0; i < len; i++)
1383 p[i] &= mask;
1385 /* we modify the TLB cache so that the dirty bit will be set again
1386 when accessing the range */
1387 start1 = start + (unsigned long)phys_ram_base;
1388 for(env = first_cpu; env != NULL; env = env->next_cpu) {
1389 for(i = 0; i < CPU_TLB_SIZE; i++)
1390 tlb_reset_dirty_range(&env->tlb_table[0][i], start1, length);
1391 for(i = 0; i < CPU_TLB_SIZE; i++)
1392 tlb_reset_dirty_range(&env->tlb_table[1][i], start1, length);
1395 #if !defined(CONFIG_SOFTMMU)
1396 /* XXX: this is expensive */
1398 VirtPageDesc *p;
1399 int j;
1400 target_ulong addr;
1402 for(i = 0; i < L1_SIZE; i++) {
1403 p = l1_virt_map[i];
1404 if (p) {
1405 addr = i << (TARGET_PAGE_BITS + L2_BITS);
1406 for(j = 0; j < L2_SIZE; j++) {
1407 if (p->valid_tag == virt_valid_tag &&
1408 p->phys_addr >= start && p->phys_addr < end &&
1409 (p->prot & PROT_WRITE)) {
1410 if (addr < MMAP_AREA_END) {
1411 mprotect((void *)addr, TARGET_PAGE_SIZE,
1412 p->prot & ~PROT_WRITE);
1415 addr += TARGET_PAGE_SIZE;
1416 p++;
1421 #endif
1424 static inline void tlb_update_dirty(CPUTLBEntry *tlb_entry)
1426 ram_addr_t ram_addr;
1428 if ((tlb_entry->addr_write & ~TARGET_PAGE_MASK) == IO_MEM_RAM) {
1429 ram_addr = (tlb_entry->addr_write & TARGET_PAGE_MASK) +
1430 tlb_entry->addend - (unsigned long)phys_ram_base;
1431 if (!cpu_physical_memory_is_dirty(ram_addr)) {
1432 tlb_entry->addr_write |= IO_MEM_NOTDIRTY;
1437 /* update the TLB according to the current state of the dirty bits */
1438 void cpu_tlb_update_dirty(CPUState *env)
1440 int i;
1441 for(i = 0; i < CPU_TLB_SIZE; i++)
1442 tlb_update_dirty(&env->tlb_table[0][i]);
1443 for(i = 0; i < CPU_TLB_SIZE; i++)
1444 tlb_update_dirty(&env->tlb_table[1][i]);
1447 static inline void tlb_set_dirty1(CPUTLBEntry *tlb_entry,
1448 unsigned long start)
1450 unsigned long addr;
1451 if ((tlb_entry->addr_write & ~TARGET_PAGE_MASK) == IO_MEM_NOTDIRTY) {
1452 addr = (tlb_entry->addr_write & TARGET_PAGE_MASK) + tlb_entry->addend;
1453 if (addr == start) {
1454 tlb_entry->addr_write = (tlb_entry->addr_write & TARGET_PAGE_MASK) | IO_MEM_RAM;
1459 /* update the TLB corresponding to virtual page vaddr and phys addr
1460 addr so that it is no longer dirty */
1461 static inline void tlb_set_dirty(CPUState *env,
1462 unsigned long addr, target_ulong vaddr)
1464 int i;
1466 addr &= TARGET_PAGE_MASK;
1467 i = (vaddr >> TARGET_PAGE_BITS) & (CPU_TLB_SIZE - 1);
1468 tlb_set_dirty1(&env->tlb_table[0][i], addr);
1469 tlb_set_dirty1(&env->tlb_table[1][i], addr);
1472 /* add a new TLB entry. At most one entry for a given virtual address
1473 is permitted. Return 0 if OK or 2 if the page could not be mapped
1474 (can only happen in non SOFTMMU mode for I/O pages or pages
1475 conflicting with the host address space). */
1476 int tlb_set_page_exec(CPUState *env, target_ulong vaddr,
1477 target_phys_addr_t paddr, int prot,
1478 int is_user, int is_softmmu)
1480 PhysPageDesc *p;
1481 unsigned long pd;
1482 unsigned int index;
1483 target_ulong address;
1484 target_phys_addr_t addend;
1485 int ret;
1486 CPUTLBEntry *te;
1488 p = phys_page_find(paddr >> TARGET_PAGE_BITS);
1489 if (!p) {
1490 pd = IO_MEM_UNASSIGNED;
1491 } else {
1492 pd = p->phys_offset;
1494 #if defined(DEBUG_TLB)
1495 printf("tlb_set_page: vaddr=" TARGET_FMT_lx " paddr=0x%08x prot=%x u=%d smmu=%d pd=0x%08lx\n",
1496 vaddr, (int)paddr, prot, is_user, is_softmmu, pd);
1497 #endif
1499 ret = 0;
1500 #if !defined(CONFIG_SOFTMMU)
1501 if (is_softmmu)
1502 #endif
1504 if ((pd & ~TARGET_PAGE_MASK) > IO_MEM_ROM && !(pd & IO_MEM_ROMD)) {
1505 /* IO memory case */
1506 address = vaddr | pd;
1507 addend = paddr;
1508 } else {
1509 /* standard memory */
1510 address = vaddr;
1511 addend = (unsigned long)phys_ram_base + (pd & TARGET_PAGE_MASK);
1514 index = (vaddr >> TARGET_PAGE_BITS) & (CPU_TLB_SIZE - 1);
1515 addend -= vaddr;
1516 te = &env->tlb_table[is_user][index];
1517 te->addend = addend;
1518 if (prot & PAGE_READ) {
1519 te->addr_read = address;
1520 } else {
1521 te->addr_read = -1;
1523 if (prot & PAGE_EXEC) {
1524 te->addr_code = address;
1525 } else {
1526 te->addr_code = -1;
1528 if (prot & PAGE_WRITE) {
1529 if ((pd & ~TARGET_PAGE_MASK) == IO_MEM_ROM ||
1530 (pd & IO_MEM_ROMD)) {
1531 /* write access calls the I/O callback */
1532 te->addr_write = vaddr |
1533 (pd & ~(TARGET_PAGE_MASK | IO_MEM_ROMD));
1534 } else if ((pd & ~TARGET_PAGE_MASK) == IO_MEM_RAM &&
1535 !cpu_physical_memory_is_dirty(pd)) {
1536 te->addr_write = vaddr | IO_MEM_NOTDIRTY;
1537 } else {
1538 te->addr_write = address;
1540 } else {
1541 te->addr_write = -1;
1544 #if !defined(CONFIG_SOFTMMU)
1545 else {
1546 if ((pd & ~TARGET_PAGE_MASK) > IO_MEM_ROM) {
1547 /* IO access: no mapping is done as it will be handled by the
1548 soft MMU */
1549 if (!(env->hflags & HF_SOFTMMU_MASK))
1550 ret = 2;
1551 } else {
1552 void *map_addr;
1554 if (vaddr >= MMAP_AREA_END) {
1555 ret = 2;
1556 } else {
1557 if (prot & PROT_WRITE) {
1558 if ((pd & ~TARGET_PAGE_MASK) == IO_MEM_ROM ||
1559 #if defined(TARGET_HAS_SMC) || 1
1560 first_tb ||
1561 #endif
1562 ((pd & ~TARGET_PAGE_MASK) == IO_MEM_RAM &&
1563 !cpu_physical_memory_is_dirty(pd))) {
1564 /* ROM: we do as if code was inside */
1565 /* if code is present, we only map as read only and save the
1566 original mapping */
1567 VirtPageDesc *vp;
1569 vp = virt_page_find_alloc(vaddr >> TARGET_PAGE_BITS, 1);
1570 vp->phys_addr = pd;
1571 vp->prot = prot;
1572 vp->valid_tag = virt_valid_tag;
1573 prot &= ~PAGE_WRITE;
1576 map_addr = mmap((void *)vaddr, TARGET_PAGE_SIZE, prot,
1577 MAP_SHARED | MAP_FIXED, phys_ram_fd, (pd & TARGET_PAGE_MASK));
1578 if (map_addr == MAP_FAILED) {
1579 cpu_abort(env, "mmap failed when mapped physical address 0x%08x to virtual address 0x%08x\n",
1580 paddr, vaddr);
1585 #endif
1586 return ret;
1589 /* called from signal handler: invalidate the code and unprotect the
1590 page. Return TRUE if the fault was succesfully handled. */
1591 int page_unprotect(target_ulong addr, unsigned long pc, void *puc)
1593 #if !defined(CONFIG_SOFTMMU)
1594 VirtPageDesc *vp;
1596 #if defined(DEBUG_TLB)
1597 printf("page_unprotect: addr=0x%08x\n", addr);
1598 #endif
1599 addr &= TARGET_PAGE_MASK;
1601 /* if it is not mapped, no need to worry here */
1602 if (addr >= MMAP_AREA_END)
1603 return 0;
1604 vp = virt_page_find(addr >> TARGET_PAGE_BITS);
1605 if (!vp)
1606 return 0;
1607 /* NOTE: in this case, validate_tag is _not_ tested as it
1608 validates only the code TLB */
1609 if (vp->valid_tag != virt_valid_tag)
1610 return 0;
1611 if (!(vp->prot & PAGE_WRITE))
1612 return 0;
1613 #if defined(DEBUG_TLB)
1614 printf("page_unprotect: addr=0x%08x phys_addr=0x%08x prot=%x\n",
1615 addr, vp->phys_addr, vp->prot);
1616 #endif
1617 if (mprotect((void *)addr, TARGET_PAGE_SIZE, vp->prot) < 0)
1618 cpu_abort(cpu_single_env, "error mprotect addr=0x%lx prot=%d\n",
1619 (unsigned long)addr, vp->prot);
1620 /* set the dirty bit */
1621 phys_ram_dirty[vp->phys_addr >> TARGET_PAGE_BITS] = 0xff;
1622 /* flush the code inside */
1623 tb_invalidate_phys_page(vp->phys_addr, pc, puc);
1624 return 1;
1625 #else
1626 return 0;
1627 #endif
1630 #else
1632 void tlb_flush(CPUState *env, int flush_global)
1636 void tlb_flush_page(CPUState *env, target_ulong addr)
1640 int tlb_set_page_exec(CPUState *env, target_ulong vaddr,
1641 target_phys_addr_t paddr, int prot,
1642 int is_user, int is_softmmu)
1644 return 0;
1647 /* dump memory mappings */
1648 void page_dump(FILE *f)
1650 unsigned long start, end;
1651 int i, j, prot, prot1;
1652 PageDesc *p;
1654 fprintf(f, "%-8s %-8s %-8s %s\n",
1655 "start", "end", "size", "prot");
1656 start = -1;
1657 end = -1;
1658 prot = 0;
1659 for(i = 0; i <= L1_SIZE; i++) {
1660 if (i < L1_SIZE)
1661 p = l1_map[i];
1662 else
1663 p = NULL;
1664 for(j = 0;j < L2_SIZE; j++) {
1665 if (!p)
1666 prot1 = 0;
1667 else
1668 prot1 = p[j].flags;
1669 if (prot1 != prot) {
1670 end = (i << (32 - L1_BITS)) | (j << TARGET_PAGE_BITS);
1671 if (start != -1) {
1672 fprintf(f, "%08lx-%08lx %08lx %c%c%c\n",
1673 start, end, end - start,
1674 prot & PAGE_READ ? 'r' : '-',
1675 prot & PAGE_WRITE ? 'w' : '-',
1676 prot & PAGE_EXEC ? 'x' : '-');
1678 if (prot1 != 0)
1679 start = end;
1680 else
1681 start = -1;
1682 prot = prot1;
1684 if (!p)
1685 break;
1690 int page_get_flags(target_ulong address)
1692 PageDesc *p;
1694 p = page_find(address >> TARGET_PAGE_BITS);
1695 if (!p)
1696 return 0;
1697 return p->flags;
1700 /* modify the flags of a page and invalidate the code if
1701 necessary. The flag PAGE_WRITE_ORG is positionned automatically
1702 depending on PAGE_WRITE */
1703 void page_set_flags(target_ulong start, target_ulong end, int flags)
1705 PageDesc *p;
1706 target_ulong addr;
1708 start = start & TARGET_PAGE_MASK;
1709 end = TARGET_PAGE_ALIGN(end);
1710 if (flags & PAGE_WRITE)
1711 flags |= PAGE_WRITE_ORG;
1712 spin_lock(&tb_lock);
1713 for(addr = start; addr < end; addr += TARGET_PAGE_SIZE) {
1714 p = page_find_alloc(addr >> TARGET_PAGE_BITS);
1715 /* if the write protection is set, then we invalidate the code
1716 inside */
1717 if (!(p->flags & PAGE_WRITE) &&
1718 (flags & PAGE_WRITE) &&
1719 p->first_tb) {
1720 tb_invalidate_phys_page(addr, 0, NULL);
1722 p->flags = flags;
1724 spin_unlock(&tb_lock);
1727 /* called from signal handler: invalidate the code and unprotect the
1728 page. Return TRUE if the fault was succesfully handled. */
1729 int page_unprotect(target_ulong address, unsigned long pc, void *puc)
1731 unsigned int page_index, prot, pindex;
1732 PageDesc *p, *p1;
1733 target_ulong host_start, host_end, addr;
1735 host_start = address & qemu_host_page_mask;
1736 page_index = host_start >> TARGET_PAGE_BITS;
1737 p1 = page_find(page_index);
1738 if (!p1)
1739 return 0;
1740 host_end = host_start + qemu_host_page_size;
1741 p = p1;
1742 prot = 0;
1743 for(addr = host_start;addr < host_end; addr += TARGET_PAGE_SIZE) {
1744 prot |= p->flags;
1745 p++;
1747 /* if the page was really writable, then we change its
1748 protection back to writable */
1749 if (prot & PAGE_WRITE_ORG) {
1750 pindex = (address - host_start) >> TARGET_PAGE_BITS;
1751 if (!(p1[pindex].flags & PAGE_WRITE)) {
1752 mprotect((void *)g2h(host_start), qemu_host_page_size,
1753 (prot & PAGE_BITS) | PAGE_WRITE);
1754 p1[pindex].flags |= PAGE_WRITE;
1755 /* and since the content will be modified, we must invalidate
1756 the corresponding translated code. */
1757 tb_invalidate_phys_page(address, pc, puc);
1758 #ifdef DEBUG_TB_CHECK
1759 tb_invalidate_check(address);
1760 #endif
1761 return 1;
1764 return 0;
1767 /* call this function when system calls directly modify a memory area */
1768 /* ??? This should be redundant now we have lock_user. */
1769 void page_unprotect_range(target_ulong data, target_ulong data_size)
1771 target_ulong start, end, addr;
1773 start = data;
1774 end = start + data_size;
1775 start &= TARGET_PAGE_MASK;
1776 end = TARGET_PAGE_ALIGN(end);
1777 for(addr = start; addr < end; addr += TARGET_PAGE_SIZE) {
1778 page_unprotect(addr, 0, NULL);
1782 static inline void tlb_set_dirty(CPUState *env,
1783 unsigned long addr, target_ulong vaddr)
1786 #endif /* defined(CONFIG_USER_ONLY) */
1788 /* register physical memory. 'size' must be a multiple of the target
1789 page size. If (phys_offset & ~TARGET_PAGE_MASK) != 0, then it is an
1790 io memory page */
1791 void cpu_register_physical_memory(target_phys_addr_t start_addr,
1792 unsigned long size,
1793 unsigned long phys_offset)
1795 target_phys_addr_t addr, end_addr;
1796 PhysPageDesc *p;
1797 CPUState *env;
1799 size = (size + TARGET_PAGE_SIZE - 1) & TARGET_PAGE_MASK;
1800 end_addr = start_addr + size;
1801 for(addr = start_addr; addr != end_addr; addr += TARGET_PAGE_SIZE) {
1802 p = phys_page_find_alloc(addr >> TARGET_PAGE_BITS, 1);
1803 p->phys_offset = phys_offset;
1804 if ((phys_offset & ~TARGET_PAGE_MASK) <= IO_MEM_ROM ||
1805 (phys_offset & IO_MEM_ROMD))
1806 phys_offset += TARGET_PAGE_SIZE;
1809 /* since each CPU stores ram addresses in its TLB cache, we must
1810 reset the modified entries */
1811 /* XXX: slow ! */
1812 for(env = first_cpu; env != NULL; env = env->next_cpu) {
1813 tlb_flush(env, 1);
1817 /* XXX: temporary until new memory mapping API */
1818 uint32_t cpu_get_physical_page_desc(target_phys_addr_t addr)
1820 PhysPageDesc *p;
1822 p = phys_page_find(addr >> TARGET_PAGE_BITS);
1823 if (!p)
1824 return IO_MEM_UNASSIGNED;
1825 return p->phys_offset;
1828 /* XXX: better than nothing */
1829 ram_addr_t qemu_ram_alloc(unsigned int size)
1831 ram_addr_t addr;
1832 if ((phys_ram_alloc_offset + size) >= phys_ram_size) {
1833 fprintf(stderr, "Not enough memory (requested_size = %u, max memory = %d)\n",
1834 size, phys_ram_size);
1835 abort();
1837 addr = phys_ram_alloc_offset;
1838 phys_ram_alloc_offset = TARGET_PAGE_ALIGN(phys_ram_alloc_offset + size);
1839 return addr;
1842 void qemu_ram_free(ram_addr_t addr)
1846 static uint32_t unassigned_mem_readb(void *opaque, target_phys_addr_t addr)
1848 #ifdef DEBUG_UNASSIGNED
1849 printf("Unassigned mem read 0x%08x\n", (int)addr);
1850 #endif
1851 return 0;
1854 static void unassigned_mem_writeb(void *opaque, target_phys_addr_t addr, uint32_t val)
1856 #ifdef DEBUG_UNASSIGNED
1857 printf("Unassigned mem write 0x%08x = 0x%x\n", (int)addr, val);
1858 #endif
1861 static CPUReadMemoryFunc *unassigned_mem_read[3] = {
1862 unassigned_mem_readb,
1863 unassigned_mem_readb,
1864 unassigned_mem_readb,
1867 static CPUWriteMemoryFunc *unassigned_mem_write[3] = {
1868 unassigned_mem_writeb,
1869 unassigned_mem_writeb,
1870 unassigned_mem_writeb,
1873 static void notdirty_mem_writeb(void *opaque, target_phys_addr_t addr, uint32_t val)
1875 unsigned long ram_addr;
1876 int dirty_flags;
1877 ram_addr = addr - (unsigned long)phys_ram_base;
1878 dirty_flags = phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS];
1879 if (!(dirty_flags & CODE_DIRTY_FLAG)) {
1880 #if !defined(CONFIG_USER_ONLY)
1881 tb_invalidate_phys_page_fast(ram_addr, 1);
1882 dirty_flags = phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS];
1883 #endif
1885 stb_p((uint8_t *)(long)addr, val);
1886 #ifdef USE_KQEMU
1887 if (cpu_single_env->kqemu_enabled &&
1888 (dirty_flags & KQEMU_MODIFY_PAGE_MASK) != KQEMU_MODIFY_PAGE_MASK)
1889 kqemu_modify_page(cpu_single_env, ram_addr);
1890 #endif
1891 dirty_flags |= (0xff & ~CODE_DIRTY_FLAG);
1892 phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS] = dirty_flags;
1893 /* we remove the notdirty callback only if the code has been
1894 flushed */
1895 if (dirty_flags == 0xff)
1896 tlb_set_dirty(cpu_single_env, addr, cpu_single_env->mem_write_vaddr);
1899 static void notdirty_mem_writew(void *opaque, target_phys_addr_t addr, uint32_t val)
1901 unsigned long ram_addr;
1902 int dirty_flags;
1903 ram_addr = addr - (unsigned long)phys_ram_base;
1904 dirty_flags = phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS];
1905 if (!(dirty_flags & CODE_DIRTY_FLAG)) {
1906 #if !defined(CONFIG_USER_ONLY)
1907 tb_invalidate_phys_page_fast(ram_addr, 2);
1908 dirty_flags = phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS];
1909 #endif
1911 stw_p((uint8_t *)(long)addr, val);
1912 #ifdef USE_KQEMU
1913 if (cpu_single_env->kqemu_enabled &&
1914 (dirty_flags & KQEMU_MODIFY_PAGE_MASK) != KQEMU_MODIFY_PAGE_MASK)
1915 kqemu_modify_page(cpu_single_env, ram_addr);
1916 #endif
1917 dirty_flags |= (0xff & ~CODE_DIRTY_FLAG);
1918 phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS] = dirty_flags;
1919 /* we remove the notdirty callback only if the code has been
1920 flushed */
1921 if (dirty_flags == 0xff)
1922 tlb_set_dirty(cpu_single_env, addr, cpu_single_env->mem_write_vaddr);
1925 static void notdirty_mem_writel(void *opaque, target_phys_addr_t addr, uint32_t val)
1927 unsigned long ram_addr;
1928 int dirty_flags;
1929 ram_addr = addr - (unsigned long)phys_ram_base;
1930 dirty_flags = phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS];
1931 if (!(dirty_flags & CODE_DIRTY_FLAG)) {
1932 #if !defined(CONFIG_USER_ONLY)
1933 tb_invalidate_phys_page_fast(ram_addr, 4);
1934 dirty_flags = phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS];
1935 #endif
1937 stl_p((uint8_t *)(long)addr, val);
1938 #ifdef USE_KQEMU
1939 if (cpu_single_env->kqemu_enabled &&
1940 (dirty_flags & KQEMU_MODIFY_PAGE_MASK) != KQEMU_MODIFY_PAGE_MASK)
1941 kqemu_modify_page(cpu_single_env, ram_addr);
1942 #endif
1943 dirty_flags |= (0xff & ~CODE_DIRTY_FLAG);
1944 phys_ram_dirty[ram_addr >> TARGET_PAGE_BITS] = dirty_flags;
1945 /* we remove the notdirty callback only if the code has been
1946 flushed */
1947 if (dirty_flags == 0xff)
1948 tlb_set_dirty(cpu_single_env, addr, cpu_single_env->mem_write_vaddr);
1951 static CPUReadMemoryFunc *error_mem_read[3] = {
1952 NULL, /* never used */
1953 NULL, /* never used */
1954 NULL, /* never used */
1957 static CPUWriteMemoryFunc *notdirty_mem_write[3] = {
1958 notdirty_mem_writeb,
1959 notdirty_mem_writew,
1960 notdirty_mem_writel,
1963 static void io_mem_init(void)
1965 cpu_register_io_memory(IO_MEM_ROM >> IO_MEM_SHIFT, error_mem_read, unassigned_mem_write, NULL);
1966 cpu_register_io_memory(IO_MEM_UNASSIGNED >> IO_MEM_SHIFT, unassigned_mem_read, unassigned_mem_write, NULL);
1967 cpu_register_io_memory(IO_MEM_NOTDIRTY >> IO_MEM_SHIFT, error_mem_read, notdirty_mem_write, NULL);
1968 io_mem_nb = 5;
1970 /* alloc dirty bits array */
1971 phys_ram_dirty = qemu_vmalloc(phys_ram_size >> TARGET_PAGE_BITS);
1972 memset(phys_ram_dirty, 0xff, phys_ram_size >> TARGET_PAGE_BITS);
1975 /* mem_read and mem_write are arrays of functions containing the
1976 function to access byte (index 0), word (index 1) and dword (index
1977 2). All functions must be supplied. If io_index is non zero, the
1978 corresponding io zone is modified. If it is zero, a new io zone is
1979 allocated. The return value can be used with
1980 cpu_register_physical_memory(). (-1) is returned if error. */
1981 int cpu_register_io_memory(int io_index,
1982 CPUReadMemoryFunc **mem_read,
1983 CPUWriteMemoryFunc **mem_write,
1984 void *opaque)
1986 int i;
1988 if (io_index <= 0) {
1989 if (io_mem_nb >= IO_MEM_NB_ENTRIES)
1990 return -1;
1991 io_index = io_mem_nb++;
1992 } else {
1993 if (io_index >= IO_MEM_NB_ENTRIES)
1994 return -1;
1997 for(i = 0;i < 3; i++) {
1998 io_mem_read[io_index][i] = mem_read[i];
1999 io_mem_write[io_index][i] = mem_write[i];
2001 io_mem_opaque[io_index] = opaque;
2002 return io_index << IO_MEM_SHIFT;
2005 CPUWriteMemoryFunc **cpu_get_io_memory_write(int io_index)
2007 return io_mem_write[io_index >> IO_MEM_SHIFT];
2010 CPUReadMemoryFunc **cpu_get_io_memory_read(int io_index)
2012 return io_mem_read[io_index >> IO_MEM_SHIFT];
2015 /* physical memory access (slow version, mainly for debug) */
2016 #if defined(CONFIG_USER_ONLY)
2017 void cpu_physical_memory_rw(target_phys_addr_t addr, uint8_t *buf,
2018 int len, int is_write)
2020 int l, flags;
2021 target_ulong page;
2022 void * p;
2024 while (len > 0) {
2025 page = addr & TARGET_PAGE_MASK;
2026 l = (page + TARGET_PAGE_SIZE) - addr;
2027 if (l > len)
2028 l = len;
2029 flags = page_get_flags(page);
2030 if (!(flags & PAGE_VALID))
2031 return;
2032 if (is_write) {
2033 if (!(flags & PAGE_WRITE))
2034 return;
2035 p = lock_user(addr, len, 0);
2036 memcpy(p, buf, len);
2037 unlock_user(p, addr, len);
2038 } else {
2039 if (!(flags & PAGE_READ))
2040 return;
2041 p = lock_user(addr, len, 1);
2042 memcpy(buf, p, len);
2043 unlock_user(p, addr, 0);
2045 len -= l;
2046 buf += l;
2047 addr += l;
2051 #else
2052 void cpu_physical_memory_rw(target_phys_addr_t addr, uint8_t *buf,
2053 int len, int is_write)
2055 int l, io_index;
2056 uint8_t *ptr;
2057 uint32_t val;
2058 target_phys_addr_t page;
2059 unsigned long pd;
2060 PhysPageDesc *p;
2062 while (len > 0) {
2063 page = addr & TARGET_PAGE_MASK;
2064 l = (page + TARGET_PAGE_SIZE) - addr;
2065 if (l > len)
2066 l = len;
2067 p = phys_page_find(page >> TARGET_PAGE_BITS);
2068 if (!p) {
2069 pd = IO_MEM_UNASSIGNED;
2070 } else {
2071 pd = p->phys_offset;
2074 if (is_write) {
2075 if ((pd & ~TARGET_PAGE_MASK) != IO_MEM_RAM) {
2076 io_index = (pd >> IO_MEM_SHIFT) & (IO_MEM_NB_ENTRIES - 1);
2077 /* XXX: could force cpu_single_env to NULL to avoid
2078 potential bugs */
2079 if (l >= 4 && ((addr & 3) == 0)) {
2080 /* 32 bit write access */
2081 val = ldl_p(buf);
2082 io_mem_write[io_index][2](io_mem_opaque[io_index], addr, val);
2083 l = 4;
2084 } else if (l >= 2 && ((addr & 1) == 0)) {
2085 /* 16 bit write access */
2086 val = lduw_p(buf);
2087 io_mem_write[io_index][1](io_mem_opaque[io_index], addr, val);
2088 l = 2;
2089 } else {
2090 /* 8 bit write access */
2091 val = ldub_p(buf);
2092 io_mem_write[io_index][0](io_mem_opaque[io_index], addr, val);
2093 l = 1;
2095 } else {
2096 unsigned long addr1;
2097 addr1 = (pd & TARGET_PAGE_MASK) + (addr & ~TARGET_PAGE_MASK);
2098 /* RAM case */
2099 ptr = phys_ram_base + addr1;
2100 memcpy(ptr, buf, l);
2101 if (!cpu_physical_memory_is_dirty(addr1)) {
2102 /* invalidate code */
2103 tb_invalidate_phys_page_range(addr1, addr1 + l, 0);
2104 /* set dirty bit */
2105 phys_ram_dirty[addr1 >> TARGET_PAGE_BITS] |=
2106 (0xff & ~CODE_DIRTY_FLAG);
2109 } else {
2110 if ((pd & ~TARGET_PAGE_MASK) > IO_MEM_ROM &&
2111 !(pd & IO_MEM_ROMD)) {
2112 /* I/O case */
2113 io_index = (pd >> IO_MEM_SHIFT) & (IO_MEM_NB_ENTRIES - 1);
2114 if (l >= 4 && ((addr & 3) == 0)) {
2115 /* 32 bit read access */
2116 val = io_mem_read[io_index][2](io_mem_opaque[io_index], addr);
2117 stl_p(buf, val);
2118 l = 4;
2119 } else if (l >= 2 && ((addr & 1) == 0)) {
2120 /* 16 bit read access */
2121 val = io_mem_read[io_index][1](io_mem_opaque[io_index], addr);
2122 stw_p(buf, val);
2123 l = 2;
2124 } else {
2125 /* 8 bit read access */
2126 val = io_mem_read[io_index][0](io_mem_opaque[io_index], addr);
2127 stb_p(buf, val);
2128 l = 1;
2130 } else {
2131 /* RAM case */
2132 ptr = phys_ram_base + (pd & TARGET_PAGE_MASK) +
2133 (addr & ~TARGET_PAGE_MASK);
2134 memcpy(buf, ptr, l);
2137 len -= l;
2138 buf += l;
2139 addr += l;
2143 /* used for ROM loading : can write in RAM and ROM */
2144 void cpu_physical_memory_write_rom(target_phys_addr_t addr,
2145 const uint8_t *buf, int len)
2147 int l;
2148 uint8_t *ptr;
2149 target_phys_addr_t page;
2150 unsigned long pd;
2151 PhysPageDesc *p;
2153 while (len > 0) {
2154 page = addr & TARGET_PAGE_MASK;
2155 l = (page + TARGET_PAGE_SIZE) - addr;
2156 if (l > len)
2157 l = len;
2158 p = phys_page_find(page >> TARGET_PAGE_BITS);
2159 if (!p) {
2160 pd = IO_MEM_UNASSIGNED;
2161 } else {
2162 pd = p->phys_offset;
2165 if ((pd & ~TARGET_PAGE_MASK) != IO_MEM_RAM &&
2166 (pd & ~TARGET_PAGE_MASK) != IO_MEM_ROM &&
2167 !(pd & IO_MEM_ROMD)) {
2168 /* do nothing */
2169 } else {
2170 unsigned long addr1;
2171 addr1 = (pd & TARGET_PAGE_MASK) + (addr & ~TARGET_PAGE_MASK);
2172 /* ROM/RAM case */
2173 ptr = phys_ram_base + addr1;
2174 memcpy(ptr, buf, l);
2176 len -= l;
2177 buf += l;
2178 addr += l;
2183 /* warning: addr must be aligned */
2184 uint32_t ldl_phys(target_phys_addr_t addr)
2186 int io_index;
2187 uint8_t *ptr;
2188 uint32_t val;
2189 unsigned long pd;
2190 PhysPageDesc *p;
2192 p = phys_page_find(addr >> TARGET_PAGE_BITS);
2193 if (!p) {
2194 pd = IO_MEM_UNASSIGNED;
2195 } else {
2196 pd = p->phys_offset;
2199 if ((pd & ~TARGET_PAGE_MASK) > IO_MEM_ROM &&
2200 !(pd & IO_MEM_ROMD)) {
2201 /* I/O case */
2202 io_index = (pd >> IO_MEM_SHIFT) & (IO_MEM_NB_ENTRIES - 1);
2203 val = io_mem_read[io_index][2](io_mem_opaque[io_index], addr);
2204 } else {
2205 /* RAM case */
2206 ptr = phys_ram_base + (pd & TARGET_PAGE_MASK) +
2207 (addr & ~TARGET_PAGE_MASK);
2208 val = ldl_p(ptr);
2210 return val;
2213 /* warning: addr must be aligned */
2214 uint64_t ldq_phys(target_phys_addr_t addr)
2216 int io_index;
2217 uint8_t *ptr;
2218 uint64_t val;
2219 unsigned long pd;
2220 PhysPageDesc *p;
2222 p = phys_page_find(addr >> TARGET_PAGE_BITS);
2223 if (!p) {
2224 pd = IO_MEM_UNASSIGNED;
2225 } else {
2226 pd = p->phys_offset;
2229 if ((pd & ~TARGET_PAGE_MASK) > IO_MEM_ROM &&
2230 !(pd & IO_MEM_ROMD)) {
2231 /* I/O case */
2232 io_index = (pd >> IO_MEM_SHIFT) & (IO_MEM_NB_ENTRIES - 1);
2233 #ifdef TARGET_WORDS_BIGENDIAN
2234 val = (uint64_t)io_mem_read[io_index][2](io_mem_opaque[io_index], addr) << 32;
2235 val |= io_mem_read[io_index][2](io_mem_opaque[io_index], addr + 4);
2236 #else
2237 val = io_mem_read[io_index][2](io_mem_opaque[io_index], addr);
2238 val |= (uint64_t)io_mem_read[io_index][2](io_mem_opaque[io_index], addr + 4) << 32;
2239 #endif
2240 } else {
2241 /* RAM case */
2242 ptr = phys_ram_base + (pd & TARGET_PAGE_MASK) +
2243 (addr & ~TARGET_PAGE_MASK);
2244 val = ldq_p(ptr);
2246 return val;
2249 /* XXX: optimize */
2250 uint32_t ldub_phys(target_phys_addr_t addr)
2252 uint8_t val;
2253 cpu_physical_memory_read(addr, &val, 1);
2254 return val;
2257 /* XXX: optimize */
2258 uint32_t lduw_phys(target_phys_addr_t addr)
2260 uint16_t val;
2261 cpu_physical_memory_read(addr, (uint8_t *)&val, 2);
2262 return tswap16(val);
2265 /* warning: addr must be aligned. The ram page is not masked as dirty
2266 and the code inside is not invalidated. It is useful if the dirty
2267 bits are used to track modified PTEs */
2268 void stl_phys_notdirty(target_phys_addr_t addr, uint32_t val)
2270 int io_index;
2271 uint8_t *ptr;
2272 unsigned long pd;
2273 PhysPageDesc *p;
2275 p = phys_page_find(addr >> TARGET_PAGE_BITS);
2276 if (!p) {
2277 pd = IO_MEM_UNASSIGNED;
2278 } else {
2279 pd = p->phys_offset;
2282 if ((pd & ~TARGET_PAGE_MASK) != IO_MEM_RAM) {
2283 io_index = (pd >> IO_MEM_SHIFT) & (IO_MEM_NB_ENTRIES - 1);
2284 io_mem_write[io_index][2](io_mem_opaque[io_index], addr, val);
2285 } else {
2286 ptr = phys_ram_base + (pd & TARGET_PAGE_MASK) +
2287 (addr & ~TARGET_PAGE_MASK);
2288 stl_p(ptr, val);
2292 /* warning: addr must be aligned */
2293 void stl_phys(target_phys_addr_t addr, uint32_t val)
2295 int io_index;
2296 uint8_t *ptr;
2297 unsigned long pd;
2298 PhysPageDesc *p;
2300 p = phys_page_find(addr >> TARGET_PAGE_BITS);
2301 if (!p) {
2302 pd = IO_MEM_UNASSIGNED;
2303 } else {
2304 pd = p->phys_offset;
2307 if ((pd & ~TARGET_PAGE_MASK) != IO_MEM_RAM) {
2308 io_index = (pd >> IO_MEM_SHIFT) & (IO_MEM_NB_ENTRIES - 1);
2309 io_mem_write[io_index][2](io_mem_opaque[io_index], addr, val);
2310 } else {
2311 unsigned long addr1;
2312 addr1 = (pd & TARGET_PAGE_MASK) + (addr & ~TARGET_PAGE_MASK);
2313 /* RAM case */
2314 ptr = phys_ram_base + addr1;
2315 stl_p(ptr, val);
2316 if (!cpu_physical_memory_is_dirty(addr1)) {
2317 /* invalidate code */
2318 tb_invalidate_phys_page_range(addr1, addr1 + 4, 0);
2319 /* set dirty bit */
2320 phys_ram_dirty[addr1 >> TARGET_PAGE_BITS] |=
2321 (0xff & ~CODE_DIRTY_FLAG);
2326 /* XXX: optimize */
2327 void stb_phys(target_phys_addr_t addr, uint32_t val)
2329 uint8_t v = val;
2330 cpu_physical_memory_write(addr, &v, 1);
2333 /* XXX: optimize */
2334 void stw_phys(target_phys_addr_t addr, uint32_t val)
2336 uint16_t v = tswap16(val);
2337 cpu_physical_memory_write(addr, (const uint8_t *)&v, 2);
2340 /* XXX: optimize */
2341 void stq_phys(target_phys_addr_t addr, uint64_t val)
2343 val = tswap64(val);
2344 cpu_physical_memory_write(addr, (const uint8_t *)&val, 8);
2347 #endif
2349 /* virtual memory access for debug */
2350 int cpu_memory_rw_debug(CPUState *env, target_ulong addr,
2351 uint8_t *buf, int len, int is_write)
2353 int l;
2354 target_ulong page, phys_addr;
2356 while (len > 0) {
2357 page = addr & TARGET_PAGE_MASK;
2358 phys_addr = cpu_get_phys_page_debug(env, page);
2359 /* if no physical page mapped, return an error */
2360 if (phys_addr == -1)
2361 return -1;
2362 l = (page + TARGET_PAGE_SIZE) - addr;
2363 if (l > len)
2364 l = len;
2365 cpu_physical_memory_rw(phys_addr + (addr & ~TARGET_PAGE_MASK),
2366 buf, l, is_write);
2367 len -= l;
2368 buf += l;
2369 addr += l;
2371 return 0;
2374 void dump_exec_info(FILE *f,
2375 int (*cpu_fprintf)(FILE *f, const char *fmt, ...))
2377 int i, target_code_size, max_target_code_size;
2378 int direct_jmp_count, direct_jmp2_count, cross_page;
2379 TranslationBlock *tb;
2381 target_code_size = 0;
2382 max_target_code_size = 0;
2383 cross_page = 0;
2384 direct_jmp_count = 0;
2385 direct_jmp2_count = 0;
2386 for(i = 0; i < nb_tbs; i++) {
2387 tb = &tbs[i];
2388 target_code_size += tb->size;
2389 if (tb->size > max_target_code_size)
2390 max_target_code_size = tb->size;
2391 if (tb->page_addr[1] != -1)
2392 cross_page++;
2393 if (tb->tb_next_offset[0] != 0xffff) {
2394 direct_jmp_count++;
2395 if (tb->tb_next_offset[1] != 0xffff) {
2396 direct_jmp2_count++;
2400 /* XXX: avoid using doubles ? */
2401 cpu_fprintf(f, "TB count %d\n", nb_tbs);
2402 cpu_fprintf(f, "TB avg target size %d max=%d bytes\n",
2403 nb_tbs ? target_code_size / nb_tbs : 0,
2404 max_target_code_size);
2405 cpu_fprintf(f, "TB avg host size %d bytes (expansion ratio: %0.1f)\n",
2406 nb_tbs ? (code_gen_ptr - code_gen_buffer) / nb_tbs : 0,
2407 target_code_size ? (double) (code_gen_ptr - code_gen_buffer) / target_code_size : 0);
2408 cpu_fprintf(f, "cross page TB count %d (%d%%)\n",
2409 cross_page,
2410 nb_tbs ? (cross_page * 100) / nb_tbs : 0);
2411 cpu_fprintf(f, "direct jump count %d (%d%%) (2 jumps=%d %d%%)\n",
2412 direct_jmp_count,
2413 nb_tbs ? (direct_jmp_count * 100) / nb_tbs : 0,
2414 direct_jmp2_count,
2415 nb_tbs ? (direct_jmp2_count * 100) / nb_tbs : 0);
2416 cpu_fprintf(f, "TB flush count %d\n", tb_flush_count);
2417 cpu_fprintf(f, "TB invalidate count %d\n", tb_phys_invalidate_count);
2418 cpu_fprintf(f, "TLB flush count %d\n", tlb_flush_count);
2421 #if !defined(CONFIG_USER_ONLY)
2423 #define MMUSUFFIX _cmmu
2424 #define GETPC() NULL
2425 #define env cpu_single_env
2426 #define SOFTMMU_CODE_ACCESS
2428 #define SHIFT 0
2429 #include "softmmu_template.h"
2431 #define SHIFT 1
2432 #include "softmmu_template.h"
2434 #define SHIFT 2
2435 #include "softmmu_template.h"
2437 #define SHIFT 3
2438 #include "softmmu_template.h"
2440 #undef env
2442 #endif