diff options
Diffstat (limited to 'sys/arch/i386/i386/machdep.c')
-rw-r--r-- | sys/arch/i386/i386/machdep.c | 238 |
1 files changed, 56 insertions, 182 deletions
diff --git a/sys/arch/i386/i386/machdep.c b/sys/arch/i386/i386/machdep.c index 60f984e5f38..74af9afb577 100644 --- a/sys/arch/i386/i386/machdep.c +++ b/sys/arch/i386/i386/machdep.c @@ -1,4 +1,4 @@ -/* $OpenBSD: machdep.c,v 1.377 2007/02/17 23:59:03 marco Exp $ */ +/* $OpenBSD: machdep.c,v 1.378 2007/02/20 21:15:01 tom Exp $ */ /* $NetBSD: machdep.c,v 1.214 1996/11/10 03:16:17 thorpej Exp $ */ /*- @@ -218,9 +218,6 @@ int bufcachepercent = BUFCACHEPERCENT; extern int boothowto; int physmem; -#ifndef SMALL_KERNEL -int pae_copy; -#endif struct dumpmem { paddr_t start; @@ -246,7 +243,7 @@ int i386_has_sse2; int i386_has_xcrypt; bootarg_t *bootargp; -paddr_t avail_end, avail_end2; +paddr_t avail_end; struct vm_map *exec_map = NULL; struct vm_map *phys_map = NULL; @@ -328,12 +325,6 @@ int allowaperture = 0; #endif #endif -#ifdef I686_PAE -int cpu_pae = 1; -#else -int cpu_pae = 0; -#endif - void winchip_cpu_setup(struct cpu_info *); void amd_family5_setperf_setup(struct cpu_info *); void amd_family5_setup(struct cpu_info *); @@ -2849,6 +2840,7 @@ fix_f00f(void) struct region_descriptor region; vaddr_t va; void *p; + pt_entry_t *pte; /* Allocate two new pages */ va = uvm_km_zalloc(kernel_map, NBPG*2); @@ -2863,7 +2855,8 @@ fix_f00f(void) GCODE_SEL); /* Map first page RO */ - pmap_pte_setbits(va, 0, PG_RW); + pte = PTE_BASE + atop(va); + *pte &= ~PG_RW; /* Reload idtr */ setregion(®ion, idt, sizeof(idt_region) - 1); @@ -3018,11 +3011,11 @@ init386(paddr_t first_avail) if (bootargc > NBPG) panic("too many boot args"); - if (extent_alloc_region(iomem_ex, (u_long)bootargv, bootargc, + if (extent_alloc_region(iomem_ex, (paddr_t)bootargv, bootargc, EX_NOWAIT)) panic("cannot reserve /boot args memory"); - pmap_enter(pmap_kernel(), (vaddr_t)bootargp, (u_long)bootargv, + pmap_enter(pmap_kernel(), (vaddr_t)bootargp, (paddr_t)bootargv, VM_PROT_READ|VM_PROT_WRITE, VM_PROT_READ|VM_PROT_WRITE|PMAP_WIRED); @@ -3035,6 +3028,15 @@ init386(paddr_t first_avail) if (bios_memmap == NULL) panic("no BIOS memory map supplied"); #endif + +#if defined(MULTIPROCESSOR) + /* install the page after boot args as PT page for first 4M */ + pmap_enter(pmap_kernel(), (u_long)vtopte(0), + round_page((vaddr_t)(bootargv + bootargc)), + VM_PROT_READ|VM_PROT_WRITE, + VM_PROT_READ|VM_PROT_WRITE|PMAP_WIRED); + memset(vtopte(0), 0, NBPG); /* make sure it is clean before using */ +#endif /* * account all the memory passed in the map from /boot @@ -3048,12 +3050,27 @@ init386(paddr_t first_avail) for(i = 0, im = bios_memmap; im->type != BIOS_MAP_END; im++) if (im->type == BIOS_MAP_FREE) { paddr_t a, e; +#ifdef DEBUG + printf(" %llx-%llx", im->addr, im->addr + im->size); +#endif + + if (im->addr >= 0x100000000ULL) { +#ifdef DEBUG + printf("-H"); +#endif + continue; + } a = round_page(im->addr); - e = trunc_page(im->addr + im->size); + if (im->addr + im->size <= 0xfffff000ULL) + e = trunc_page(im->addr + im->size); + else { #ifdef DEBUG - printf(" %llx-%llx", a, e); + printf("-T"); #endif + e = 0xfffff000; + } + /* skip first eight pages */ if (a < 8 * NBPG) a = 8 * NBPG; @@ -3073,16 +3090,7 @@ init386(paddr_t first_avail) continue; } - if (a >= 0x100000000ULL) { -#ifdef DEBUG - printf("-H"); -#endif - if (!cpu_pae) - continue; - } - - if (e <= 0x100000000ULL && - extent_alloc_region(iomem_ex, a, e - a, EX_NOWAIT)) + if (extent_alloc_region(iomem_ex, a, e - a, EX_NOWAIT)) /* XXX What should we do? */ printf("\nWARNING: CAN'T ALLOCATE RAM (%x-%x)" " FROM IOMEM EXTENT MAP!\n", a, e); @@ -3091,15 +3099,11 @@ init386(paddr_t first_avail) dumpmem[i].start = atop(a); dumpmem[i].end = atop(e); i++; - avail_end2 = MAX(avail_end2, e); - if (avail_end2 < 0x100000000ULL) - avail_end = avail_end2; + avail_end = max(avail_end, e); } ndumpmem = i; avail_end -= round_page(MSGBUFSIZE); - if (avail_end2 < 0x100000000ULL) - avail_end2 = avail_end; #ifdef DEBUG printf(": %lx\n", avail_end); @@ -3130,34 +3134,30 @@ init386(paddr_t first_avail) e = dumpmem[i].end; if (a < atop(first_avail) && e > atop(first_avail)) a = atop(first_avail); - if (a < atop(avail_end) && e > atop(avail_end)) + if (e > atop(avail_end)) e = atop(avail_end); if (a < e) { if (a < atop(16 * 1024 * 1024)) { lim = MIN(atop(16 * 1024 * 1024), e); #ifdef DEBUG - printf(" %llx-%llx (<16M)", a, lim); +- printf(" %x-%x (<16M)", a, lim); #endif uvm_page_physload(a, lim, a, lim, VM_FREELIST_FIRST16); if (e > lim) { #ifdef DEBUG - printf(" %llx-%llx", lim, e); +- printf(" %x-%x", lim, e); #endif uvm_page_physload(lim, e, lim, e, VM_FREELIST_DEFAULT); } } else { #ifdef DEBUG - printf(" %llx-%llx", a, e); +- printf(" %x-%x", a, e); #endif - if (a >= atop(0x100000000ULL)) - uvm_page_physload(a, e, a, a - 1, - VM_FREELIST_ABOVE4G); - else - uvm_page_physload(a, e, a, e, - VM_FREELIST_DEFAULT); + uvm_page_physload(a, e, a, e, + VM_FREELIST_DEFAULT); } } } @@ -3566,8 +3566,8 @@ bus_mem_add_mapping(bus_addr_t bpa, bus_size_t size, int cacheable, bus_space_handle_t *bshp) { u_long pa, endpa; - u_int32_t bits; vaddr_t va; + pt_entry_t *pte; bus_size_t map_size; #ifdef MULTIPROCESSOR u_int32_t cpumask = 0; @@ -3599,12 +3599,13 @@ bus_mem_add_mapping(bus_addr_t bpa, bus_size_t size, int cacheable, * on those machines. */ if (cpu_class != CPUCLASS_386) { + pte = kvtopte(va); if (cacheable) - bits = pmap_pte_setbits(va, 0, PG_N); + *pte &= ~PG_N; else - bits = pmap_pte_setbits(va, PG_N, 0); + *pte |= PG_N; #ifdef MULTIPROCESSOR - pmap_tlb_shootdown(pmap_kernel(), va, bits, + pmap_tlb_shootdown(pmap_kernel(), va, *pte, &cpumask); #else pmap_update_pg(va); @@ -3624,7 +3625,7 @@ bus_space_unmap(bus_space_tag_t t, bus_space_handle_t bsh, bus_size_t size) { struct extent *ex; u_long va, endva; - paddr_t bpa; + bus_addr_t bpa; /* * Find the correct extent and bus physical address. @@ -3634,7 +3635,7 @@ bus_space_unmap(bus_space_tag_t t, bus_space_handle_t bsh, bus_size_t size) bpa = bsh; } else if (t == I386_BUS_SPACE_MEM) { ex = iomem_ex; - bpa = (u_long)ISA_PHYSADDR(bsh); + bpa = (bus_addr_t)ISA_PHYSADDR(bsh); if (IOM_BEGIN <= bpa && bpa <= IOM_END) goto ok; @@ -3670,7 +3671,7 @@ _bus_space_unmap(bus_space_tag_t t, bus_space_handle_t bsh, bus_size_t size, bus_addr_t *adrp) { u_long va, endva; - paddr_t bpa; + bus_addr_t bpa; /* * Find the correct bus physical address. @@ -3678,7 +3679,7 @@ _bus_space_unmap(bus_space_tag_t t, bus_space_handle_t bsh, bus_size_t size, if (t == I386_BUS_SPACE_IO) { bpa = bsh; } else if (t == I386_BUS_SPACE_MEM) { - bpa = (u_long)ISA_PHYSADDR(bsh); + bpa = (bus_addr_t)ISA_PHYSADDR(bsh); if (IOM_BEGIN <= bpa && bpa <= IOM_END) goto ok; @@ -3732,7 +3733,6 @@ _bus_dmamap_create(bus_dma_tag_t t, bus_size_t size, int nsegments, struct i386_bus_dmamap *map; void *mapstore; size_t mapsize; - int npages; /* * Allocate and initialize the DMA map. The end of the map @@ -3748,17 +3748,6 @@ _bus_dmamap_create(bus_dma_tag_t t, bus_size_t size, int nsegments, */ mapsize = sizeof(struct i386_bus_dmamap) + (sizeof(bus_dma_segment_t) * (nsegments - 1)); - npages = 0; -#ifndef SMALL_KERNEL - if (avail_end2 > avail_end && - (flags & (BUS_DMA_64BIT|BUS_DMA_24BIT)) == 0) { - /* this many pages plus one in case we get split */ - npages = round_page(size) / PAGE_SIZE + 1; - if (npages < nsegments) /* looks stupid, but possible */ - npages = nsegments; - mapsize += sizeof(struct vm_page *) * npages; - } -#endif /* !SMALL_KERNEL */ if ((mapstore = malloc(mapsize, M_DEVBUF, (flags & BUS_DMA_NOWAIT) ? M_NOWAIT : M_WAITOK)) == NULL) return (ENOMEM); @@ -3769,55 +3758,10 @@ _bus_dmamap_create(bus_dma_tag_t t, bus_size_t size, int nsegments, map->_dm_segcnt = nsegments; map->_dm_maxsegsz = maxsegsz; map->_dm_boundary = boundary; - map->_dm_pages = npages? (void *)&map->dm_segs[nsegments] : NULL; - map->_dm_npages = npages; map->_dm_flags = flags & ~(BUS_DMA_WAITOK|BUS_DMA_NOWAIT); map->dm_mapsize = 0; /* no valid mappings */ map->dm_nsegs = 0; -#ifndef SMALL_KERNEL - if (npages) { - struct pglist mlist; - vaddr_t va; - int error; - - size = npages << PGSHIFT; - va = uvm_km_valloc(kernel_map, size); - if (va == 0) { - map->_dm_npages = 0; - free(map, M_DEVBUF); - return (ENOMEM); - } - - TAILQ_INIT(&mlist); - /* if not a 64bit map -- allocate some bouncy-bouncy */ - error = uvm_pglistalloc(size, - round_page(ISA_DMA_BOUNCE_THRESHOLD), 0xfffff000, - PAGE_SIZE, boundary, &mlist, nsegments, - (flags & BUS_DMA_NOWAIT) == 0); - if (error) { - map->_dm_npages = 0; - uvm_km_free(kernel_map, (vaddr_t)va, size); - free(map, M_DEVBUF); - return (ENOMEM); - } else { - struct vm_page **pg = map->_dm_pages; - - npages--; - *pg = TAILQ_FIRST(&mlist); - pmap_kenter_pa(va, VM_PAGE_TO_PHYS(*pg), - VM_PROT_READ | VM_PROT_WRITE | PMAP_WIRED); - for (pg++, va += PAGE_SIZE; npages--; - pg++, va += PAGE_SIZE) { - *pg = TAILQ_NEXT(pg[-1], pageq); - pmap_kenter_pa(va, VM_PAGE_TO_PHYS(*pg), - VM_PROT_READ | VM_PROT_WRITE | PMAP_WIRED); - } - } - map->_dm_pgva = va; - } -#endif /* !SMALL_KERNEL */ - *dmamp = map; return (0); } @@ -3841,7 +3785,7 @@ int _bus_dmamap_load(bus_dma_tag_t t, bus_dmamap_t map, void *buf, bus_size_t buflen, struct proc *p, int flags) { - paddr_t lastaddr; + bus_addr_t lastaddr; int seg, error; /* @@ -4009,7 +3953,6 @@ _bus_dmamap_unload(bus_dma_tag_t t, bus_dmamap_t map) */ map->dm_mapsize = 0; map->dm_nsegs = 0; - map->_dm_nused = 0; } /* @@ -4017,43 +3960,10 @@ _bus_dmamap_unload(bus_dma_tag_t t, bus_dmamap_t map) * by bus-specific DMA map synchronization functions. */ void -_bus_dmamap_sync(bus_dma_tag_t t, bus_dmamap_t map, bus_addr_t offset, +_bus_dmamap_sync(bus_dma_tag_t t, bus_dmamap_t map, bus_addr_t addr, bus_size_t size, int op) { -#ifndef SMALL_KERNEL - bus_dma_segment_t *sg; - int i, off = offset; - bus_size_t l; - - /* scan the segment list performing necessary copies */ - if (!(map->_dm_flags & BUS_DMA_64BIT) && map->_dm_nused) { - for (i = map->_dm_segcnt, sg = map->dm_segs; - size && i--; sg++) { - if (off >= sg->ds_len) { - off -= sg->ds_len; - continue; - } - - l = sg->ds_len - off; - if (l > size) - l = size; - size -= l; - if (sg->ds_addr2) { - if (op & BUS_DMASYNC_POSTREAD) { - bcopy((void *)(sg->ds_va2 + off), - (void *)(sg->ds_va + off), l); - pae_copy++; - } - if (op & BUS_DMASYNC_PREWRITE) { - bcopy((void *)(sg->ds_va + off), - (void *)(sg->ds_va2 + off), l); - pae_copy++; - } - } - off = 0; - } - } -#endif /* !SMALL_KERNEL */ + /* Nothing to do here. */ } /* @@ -4197,8 +4107,8 @@ _bus_dmamap_load_buffer(bus_dma_tag_t t, bus_dmamap_t map, void *buf, int first) { bus_size_t sgsize; - paddr_t curaddr, lastaddr, oaddr, baddr, bmask; - vaddr_t pgva, vaddr = (vaddr_t)buf; + bus_addr_t curaddr, lastaddr, baddr, bmask; + vaddr_t vaddr = (vaddr_t)buf; int seg; pmap_t pmap; @@ -4214,24 +4124,7 @@ _bus_dmamap_load_buffer(bus_dma_tag_t t, bus_dmamap_t map, void *buf, /* * Get the physical address for this segment. */ - pmap_extract(pmap, vaddr, &curaddr); - oaddr = 0; - pgva = 0; -#ifndef SMALL_KERNEL - if (!(map->_dm_flags & BUS_DMA_64BIT) && - curaddr >= 0x100000000ULL) { - struct vm_page *pg; - int page, off; - - if (map->_dm_nused + 1 >= map->_dm_npages) - return (ENOMEM); - off = vaddr & PAGE_MASK; - pg = map->_dm_pages[page = map->_dm_nused++]; - oaddr = curaddr; - curaddr = VM_PAGE_TO_PHYS(pg) + off; - pgva = map->_dm_pgva + (page << PGSHIFT) + off; - } -#endif /* !SMALL_KERNEL */ + pmap_extract(pmap, vaddr, (paddr_t *)&curaddr); /* * Compute the segment size, and adjust counts. @@ -4255,10 +4148,7 @@ _bus_dmamap_load_buffer(bus_dma_tag_t t, bus_dmamap_t map, void *buf, */ if (first) { map->dm_segs[seg].ds_addr = curaddr; - map->dm_segs[seg].ds_addr2 = oaddr; map->dm_segs[seg].ds_len = sgsize; - map->dm_segs[seg].ds_va = vaddr; - map->dm_segs[seg].ds_va2 = pgva; first = 0; } else { if (curaddr == lastaddr && @@ -4272,10 +4162,7 @@ _bus_dmamap_load_buffer(bus_dma_tag_t t, bus_dmamap_t map, void *buf, if (++seg >= map->_dm_segcnt) break; map->dm_segs[seg].ds_addr = curaddr; - map->dm_segs[seg].ds_addr2 = oaddr; map->dm_segs[seg].ds_len = sgsize; - map->dm_segs[seg].ds_va = vaddr; - map->dm_segs[seg].ds_va2 = pgva; } } @@ -4311,19 +4198,6 @@ _bus_dmamem_alloc_range(bus_dma_tag_t t, bus_size_t size, bus_size_t alignment, /* Always round the size. */ size = round_page(size); - if (flags & BUS_DMA_64BIT) { - if (high > 0x100000000ULL && low < 0x100000000ULL) - low = 0x100000000ULL; - } else if (high > 0x100000000ULL) { - if (low >= 0x100000000ULL) { -#ifdef DIAGNOSTIC - printf("_bus_dmamem_alloc_range: " - "32bit request in above 4GB space\n"); -#endif - return (EINVAL); - } else - high = 0x100000000ULL; - } TAILQ_INIT(&mlist); /* |