Revision 37ec01d4 exec.c
b/exec.c | ||
---|---|---|
3399 | 3399 |
addr += mmio->base; |
3400 | 3400 |
addr -= section->offset_within_address_space; |
3401 | 3401 |
addr += section->offset_within_region; |
3402 |
return io_mem_read(section->mr->ram_addr, addr, len);
|
|
3402 |
return io_mem_read(section->mr, addr, len); |
|
3403 | 3403 |
} |
3404 | 3404 |
|
3405 | 3405 |
static void subpage_write(void *opaque, target_phys_addr_t addr, |
... | ... | |
3418 | 3418 |
addr += mmio->base; |
3419 | 3419 |
addr -= section->offset_within_address_space; |
3420 | 3420 |
addr += section->offset_within_region; |
3421 |
io_mem_write(section->mr->ram_addr, addr, value, len);
|
|
3421 |
io_mem_write(section->mr, addr, value, len); |
|
3422 | 3422 |
} |
3423 | 3423 |
|
3424 | 3424 |
static const MemoryRegionOps subpage_ops = { |
... | ... | |
3562 | 3562 |
return phys_section_add(§ion); |
3563 | 3563 |
} |
3564 | 3564 |
|
3565 |
target_phys_addr_t section_to_ioaddr(target_phys_addr_t section_io_addr)
|
|
3565 |
MemoryRegion *iotlb_to_region(target_phys_addr_t index)
|
|
3566 | 3566 |
{ |
3567 |
MemoryRegionSection *section; |
|
3568 |
|
|
3569 |
section = &phys_sections[section_io_addr & ~TARGET_PAGE_MASK]; |
|
3570 |
return (section_io_addr & TARGET_PAGE_MASK) |
|
3571 |
| (section->mr->ram_addr & ~TARGET_PAGE_MASK); |
|
3567 |
return phys_sections[index & ~TARGET_PAGE_MASK].mr; |
|
3572 | 3568 |
} |
3573 | 3569 |
|
3574 | 3570 |
static void io_mem_init(void) |
... | ... | |
3838 | 3834 |
void cpu_physical_memory_rw(target_phys_addr_t addr, uint8_t *buf, |
3839 | 3835 |
int len, int is_write) |
3840 | 3836 |
{ |
3841 |
int l, io_index;
|
|
3837 |
int l; |
|
3842 | 3838 |
uint8_t *ptr; |
3843 | 3839 |
uint32_t val; |
3844 | 3840 |
target_phys_addr_t page; |
... | ... | |
3854 | 3850 |
if (is_write) { |
3855 | 3851 |
if (!memory_region_is_ram(section->mr)) { |
3856 | 3852 |
target_phys_addr_t addr1; |
3857 |
io_index = memory_region_get_ram_addr(section->mr) |
|
3858 |
& (IO_MEM_NB_ENTRIES - 1); |
|
3859 | 3853 |
addr1 = section_addr(section, addr); |
3860 | 3854 |
/* XXX: could force cpu_single_env to NULL to avoid |
3861 | 3855 |
potential bugs */ |
3862 | 3856 |
if (l >= 4 && ((addr1 & 3) == 0)) { |
3863 | 3857 |
/* 32 bit write access */ |
3864 | 3858 |
val = ldl_p(buf); |
3865 |
io_mem_write(io_index, addr1, val, 4);
|
|
3859 |
io_mem_write(section->mr, addr1, val, 4);
|
|
3866 | 3860 |
l = 4; |
3867 | 3861 |
} else if (l >= 2 && ((addr1 & 1) == 0)) { |
3868 | 3862 |
/* 16 bit write access */ |
3869 | 3863 |
val = lduw_p(buf); |
3870 |
io_mem_write(io_index, addr1, val, 2);
|
|
3864 |
io_mem_write(section->mr, addr1, val, 2);
|
|
3871 | 3865 |
l = 2; |
3872 | 3866 |
} else { |
3873 | 3867 |
/* 8 bit write access */ |
3874 | 3868 |
val = ldub_p(buf); |
3875 |
io_mem_write(io_index, addr1, val, 1);
|
|
3869 |
io_mem_write(section->mr, addr1, val, 1);
|
|
3876 | 3870 |
l = 1; |
3877 | 3871 |
} |
3878 | 3872 |
} else if (!section->readonly) { |
... | ... | |
3895 | 3889 |
if (!is_ram_rom_romd(section)) { |
3896 | 3890 |
target_phys_addr_t addr1; |
3897 | 3891 |
/* I/O case */ |
3898 |
io_index = memory_region_get_ram_addr(section->mr) |
|
3899 |
& (IO_MEM_NB_ENTRIES - 1); |
|
3900 | 3892 |
addr1 = section_addr(section, addr); |
3901 | 3893 |
if (l >= 4 && ((addr1 & 3) == 0)) { |
3902 | 3894 |
/* 32 bit read access */ |
3903 |
val = io_mem_read(io_index, addr1, 4);
|
|
3895 |
val = io_mem_read(section->mr, addr1, 4);
|
|
3904 | 3896 |
stl_p(buf, val); |
3905 | 3897 |
l = 4; |
3906 | 3898 |
} else if (l >= 2 && ((addr1 & 1) == 0)) { |
3907 | 3899 |
/* 16 bit read access */ |
3908 |
val = io_mem_read(io_index, addr1, 2);
|
|
3900 |
val = io_mem_read(section->mr, addr1, 2);
|
|
3909 | 3901 |
stw_p(buf, val); |
3910 | 3902 |
l = 2; |
3911 | 3903 |
} else { |
3912 | 3904 |
/* 8 bit read access */ |
3913 |
val = io_mem_read(io_index, addr1, 1);
|
|
3905 |
val = io_mem_read(section->mr, addr1, 1);
|
|
3914 | 3906 |
stb_p(buf, val); |
3915 | 3907 |
l = 1; |
3916 | 3908 |
} |
... | ... | |
4106 | 4098 |
static inline uint32_t ldl_phys_internal(target_phys_addr_t addr, |
4107 | 4099 |
enum device_endian endian) |
4108 | 4100 |
{ |
4109 |
int io_index; |
|
4110 | 4101 |
uint8_t *ptr; |
4111 | 4102 |
uint32_t val; |
4112 | 4103 |
MemoryRegionSection *section; |
... | ... | |
4115 | 4106 |
|
4116 | 4107 |
if (!is_ram_rom_romd(section)) { |
4117 | 4108 |
/* I/O case */ |
4118 |
io_index = memory_region_get_ram_addr(section->mr) |
|
4119 |
& (IO_MEM_NB_ENTRIES - 1); |
|
4120 | 4109 |
addr = section_addr(section, addr); |
4121 |
val = io_mem_read(io_index, addr, 4);
|
|
4110 |
val = io_mem_read(section->mr, addr, 4);
|
|
4122 | 4111 |
#if defined(TARGET_WORDS_BIGENDIAN) |
4123 | 4112 |
if (endian == DEVICE_LITTLE_ENDIAN) { |
4124 | 4113 |
val = bswap32(val); |
... | ... | |
4167 | 4156 |
static inline uint64_t ldq_phys_internal(target_phys_addr_t addr, |
4168 | 4157 |
enum device_endian endian) |
4169 | 4158 |
{ |
4170 |
int io_index; |
|
4171 | 4159 |
uint8_t *ptr; |
4172 | 4160 |
uint64_t val; |
4173 | 4161 |
MemoryRegionSection *section; |
... | ... | |
4176 | 4164 |
|
4177 | 4165 |
if (!is_ram_rom_romd(section)) { |
4178 | 4166 |
/* I/O case */ |
4179 |
io_index = memory_region_get_ram_addr(section->mr) |
|
4180 |
& (IO_MEM_NB_ENTRIES - 1); |
|
4181 | 4167 |
addr = section_addr(section, addr); |
4182 | 4168 |
|
4183 | 4169 |
/* XXX This is broken when device endian != cpu endian. |
4184 | 4170 |
Fix and add "endian" variable check */ |
4185 | 4171 |
#ifdef TARGET_WORDS_BIGENDIAN |
4186 |
val = io_mem_read(io_index, addr, 4) << 32;
|
|
4187 |
val |= io_mem_read(io_index, addr + 4, 4);
|
|
4172 |
val = io_mem_read(section->mr, addr, 4) << 32;
|
|
4173 |
val |= io_mem_read(section->mr, addr + 4, 4);
|
|
4188 | 4174 |
#else |
4189 |
val = io_mem_read(io_index, addr, 4);
|
|
4190 |
val |= io_mem_read(io_index, addr + 4, 4) << 32;
|
|
4175 |
val = io_mem_read(section->mr, addr, 4);
|
|
4176 |
val |= io_mem_read(section->mr, addr + 4, 4) << 32;
|
|
4191 | 4177 |
#endif |
4192 | 4178 |
} else { |
4193 | 4179 |
/* RAM case */ |
... | ... | |
4236 | 4222 |
static inline uint32_t lduw_phys_internal(target_phys_addr_t addr, |
4237 | 4223 |
enum device_endian endian) |
4238 | 4224 |
{ |
4239 |
int io_index; |
|
4240 | 4225 |
uint8_t *ptr; |
4241 | 4226 |
uint64_t val; |
4242 | 4227 |
MemoryRegionSection *section; |
... | ... | |
4245 | 4230 |
|
4246 | 4231 |
if (!is_ram_rom_romd(section)) { |
4247 | 4232 |
/* I/O case */ |
4248 |
io_index = memory_region_get_ram_addr(section->mr) |
|
4249 |
& (IO_MEM_NB_ENTRIES - 1); |
|
4250 | 4233 |
addr = section_addr(section, addr); |
4251 |
val = io_mem_read(io_index, addr, 2);
|
|
4234 |
val = io_mem_read(section->mr, addr, 2);
|
|
4252 | 4235 |
#if defined(TARGET_WORDS_BIGENDIAN) |
4253 | 4236 |
if (endian == DEVICE_LITTLE_ENDIAN) { |
4254 | 4237 |
val = bswap16(val); |
... | ... | |
4298 | 4281 |
bits are used to track modified PTEs */ |
4299 | 4282 |
void stl_phys_notdirty(target_phys_addr_t addr, uint32_t val) |
4300 | 4283 |
{ |
4301 |
int io_index; |
|
4302 | 4284 |
uint8_t *ptr; |
4303 | 4285 |
MemoryRegionSection *section; |
4304 | 4286 |
|
4305 | 4287 |
section = phys_page_find(addr >> TARGET_PAGE_BITS); |
4306 | 4288 |
|
4307 | 4289 |
if (!memory_region_is_ram(section->mr) || section->readonly) { |
4290 |
addr = section_addr(section, addr); |
|
4308 | 4291 |
if (memory_region_is_ram(section->mr)) { |
4309 |
io_index = io_mem_rom.ram_addr; |
|
4310 |
} else { |
|
4311 |
io_index = memory_region_get_ram_addr(section->mr); |
|
4292 |
section = &phys_sections[phys_section_rom]; |
|
4312 | 4293 |
} |
4313 |
addr = section_addr(section, addr); |
|
4314 |
io_mem_write(io_index, addr, val, 4); |
|
4294 |
io_mem_write(section->mr, addr, val, 4); |
|
4315 | 4295 |
} else { |
4316 | 4296 |
unsigned long addr1 = (memory_region_get_ram_addr(section->mr) |
4317 | 4297 |
& TARGET_PAGE_MASK) |
... | ... | |
4333 | 4313 |
|
4334 | 4314 |
void stq_phys_notdirty(target_phys_addr_t addr, uint64_t val) |
4335 | 4315 |
{ |
4336 |
int io_index; |
|
4337 | 4316 |
uint8_t *ptr; |
4338 | 4317 |
MemoryRegionSection *section; |
4339 | 4318 |
|
4340 | 4319 |
section = phys_page_find(addr >> TARGET_PAGE_BITS); |
4341 | 4320 |
|
4342 | 4321 |
if (!memory_region_is_ram(section->mr) || section->readonly) { |
4322 |
addr = section_addr(section, addr); |
|
4343 | 4323 |
if (memory_region_is_ram(section->mr)) { |
4344 |
io_index = io_mem_rom.ram_addr; |
|
4345 |
} else { |
|
4346 |
io_index = memory_region_get_ram_addr(section->mr) |
|
4347 |
& (IO_MEM_NB_ENTRIES - 1); |
|
4324 |
section = &phys_sections[phys_section_rom]; |
|
4348 | 4325 |
} |
4349 |
addr = section_addr(section, addr); |
|
4350 | 4326 |
#ifdef TARGET_WORDS_BIGENDIAN |
4351 |
io_mem_write(io_index, addr, val >> 32, 4);
|
|
4352 |
io_mem_write(io_index, addr + 4, (uint32_t)val, 4);
|
|
4327 |
io_mem_write(section->mr, addr, val >> 32, 4);
|
|
4328 |
io_mem_write(section->mr, addr + 4, (uint32_t)val, 4);
|
|
4353 | 4329 |
#else |
4354 |
io_mem_write(io_index, addr, (uint32_t)val, 4);
|
|
4355 |
io_mem_write(io_index, addr + 4, val >> 32, 4);
|
|
4330 |
io_mem_write(section->mr, addr, (uint32_t)val, 4);
|
|
4331 |
io_mem_write(section->mr, addr + 4, val >> 32, 4);
|
|
4356 | 4332 |
#endif |
4357 | 4333 |
} else { |
4358 | 4334 |
ptr = qemu_get_ram_ptr((memory_region_get_ram_addr(section->mr) |
... | ... | |
4366 | 4342 |
static inline void stl_phys_internal(target_phys_addr_t addr, uint32_t val, |
4367 | 4343 |
enum device_endian endian) |
4368 | 4344 |
{ |
4369 |
int io_index; |
|
4370 | 4345 |
uint8_t *ptr; |
4371 | 4346 |
MemoryRegionSection *section; |
4372 | 4347 |
|
4373 | 4348 |
section = phys_page_find(addr >> TARGET_PAGE_BITS); |
4374 | 4349 |
|
4375 | 4350 |
if (!memory_region_is_ram(section->mr) || section->readonly) { |
4351 |
addr = section_addr(section, addr); |
|
4376 | 4352 |
if (memory_region_is_ram(section->mr)) { |
4377 |
io_index = io_mem_rom.ram_addr; |
|
4378 |
} else { |
|
4379 |
io_index = memory_region_get_ram_addr(section->mr) |
|
4380 |
& (IO_MEM_NB_ENTRIES - 1); |
|
4353 |
section = &phys_sections[phys_section_rom]; |
|
4381 | 4354 |
} |
4382 |
addr = section_addr(section, addr); |
|
4383 | 4355 |
#if defined(TARGET_WORDS_BIGENDIAN) |
4384 | 4356 |
if (endian == DEVICE_LITTLE_ENDIAN) { |
4385 | 4357 |
val = bswap32(val); |
... | ... | |
4389 | 4361 |
val = bswap32(val); |
4390 | 4362 |
} |
4391 | 4363 |
#endif |
4392 |
io_mem_write(io_index, addr, val, 4);
|
|
4364 |
io_mem_write(section->mr, addr, val, 4);
|
|
4393 | 4365 |
} else { |
4394 | 4366 |
unsigned long addr1; |
4395 | 4367 |
addr1 = (memory_region_get_ram_addr(section->mr) & TARGET_PAGE_MASK) |
... | ... | |
4443 | 4415 |
static inline void stw_phys_internal(target_phys_addr_t addr, uint32_t val, |
4444 | 4416 |
enum device_endian endian) |
4445 | 4417 |
{ |
4446 |
int io_index; |
|
4447 | 4418 |
uint8_t *ptr; |
4448 | 4419 |
MemoryRegionSection *section; |
4449 | 4420 |
|
4450 | 4421 |
section = phys_page_find(addr >> TARGET_PAGE_BITS); |
4451 | 4422 |
|
4452 | 4423 |
if (!memory_region_is_ram(section->mr) || section->readonly) { |
4424 |
addr = section_addr(section, addr); |
|
4453 | 4425 |
if (memory_region_is_ram(section->mr)) { |
4454 |
io_index = io_mem_rom.ram_addr; |
|
4455 |
} else { |
|
4456 |
io_index = memory_region_get_ram_addr(section->mr) |
|
4457 |
& (IO_MEM_NB_ENTRIES - 1); |
|
4426 |
section = &phys_sections[phys_section_rom]; |
|
4458 | 4427 |
} |
4459 |
addr = section_addr(section, addr); |
|
4460 | 4428 |
#if defined(TARGET_WORDS_BIGENDIAN) |
4461 | 4429 |
if (endian == DEVICE_LITTLE_ENDIAN) { |
4462 | 4430 |
val = bswap16(val); |
... | ... | |
4466 | 4434 |
val = bswap16(val); |
4467 | 4435 |
} |
4468 | 4436 |
#endif |
4469 |
io_mem_write(io_index, addr, val, 2);
|
|
4437 |
io_mem_write(section->mr, addr, val, 2);
|
|
4470 | 4438 |
} else { |
4471 | 4439 |
unsigned long addr1; |
4472 | 4440 |
addr1 = (memory_region_get_ram_addr(section->mr) & TARGET_PAGE_MASK) |
... | ... | |
4678 | 4646 |
{ |
4679 | 4647 |
int mmu_idx, page_index, pd; |
4680 | 4648 |
void *p; |
4649 |
MemoryRegion *mr; |
|
4681 | 4650 |
|
4682 | 4651 |
page_index = (addr >> TARGET_PAGE_BITS) & (CPU_TLB_SIZE - 1); |
4683 | 4652 |
mmu_idx = cpu_mmu_index(env1); |
... | ... | |
4686 | 4655 |
ldub_code(addr); |
4687 | 4656 |
} |
4688 | 4657 |
pd = env1->iotlb[mmu_idx][page_index] & ~TARGET_PAGE_MASK; |
4689 |
if (pd != io_mem_ram.ram_addr && pd != io_mem_rom.ram_addr |
|
4690 |
&& !io_mem_region[pd]->rom_device) { |
|
4658 |
mr = iotlb_to_region(pd); |
|
4659 |
if (mr != &io_mem_ram && mr != &io_mem_rom |
|
4660 |
&& mr != &io_mem_notdirty && !mr->rom_device) { |
|
4691 | 4661 |
#if defined(TARGET_ALPHA) || defined(TARGET_MIPS) || defined(TARGET_SPARC) |
4692 | 4662 |
cpu_unassigned_access(env1, addr, 0, 1, 0, 4); |
4693 | 4663 |
#else |
Also available in: Unified diff