Changes in kernel/arch/amd64/src/ddi/ddi.c [c5396c1:9d58539] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/arch/amd64/src/ddi/ddi.c
rc5396c1 r9d58539 42 42 #include <errno.h> 43 43 #include <arch/cpu.h> 44 #include <cpu.h>45 44 #include <arch.h> 46 45 #include <align.h> … … 59 58 int ddi_iospace_enable_arch(task_t *task, uintptr_t ioaddr, size_t size) 60 59 { 61 size_t elements = ioaddr + size;62 if ( elements > IO_PORTS)60 size_t bits = ioaddr + size; 61 if (bits > IO_PORTS) 63 62 return ENOENT; 64 63 65 if (task->arch.iomap. elements < elements) {64 if (task->arch.iomap.bits < bits) { 66 65 /* 67 66 * The I/O permission bitmap is too small and needs to be grown. 68 67 */ 69 68 70 void *store = malloc(bitmap_size(elements), FRAME_ATOMIC);71 if (! store)69 uint8_t *newmap = (uint8_t *) malloc(BITS2BYTES(bits), FRAME_ATOMIC); 70 if (!newmap) 72 71 return ENOMEM; 73 72 74 73 bitmap_t oldiomap; 75 bitmap_initialize(&oldiomap, task->arch.iomap. elements,74 bitmap_initialize(&oldiomap, task->arch.iomap.map, 76 75 task->arch.iomap.bits); 77 78 bitmap_initialize(&task->arch.iomap, elements, store); 76 bitmap_initialize(&task->arch.iomap, newmap, bits); 79 77 80 78 /* 81 79 * Mark the new range inaccessible. 82 80 */ 83 bitmap_set_range(&task->arch.iomap, oldiomap. elements,84 elements - oldiomap.elements);81 bitmap_set_range(&task->arch.iomap, oldiomap.bits, 82 bits - oldiomap.bits); 85 83 86 84 /* … … 90 88 if (oldiomap.bits) { 91 89 bitmap_copy(&task->arch.iomap, &oldiomap, 92 oldiomap.elements); 93 94 free(oldiomap.bits); 90 oldiomap.bits); 91 free(oldiomap.map); 95 92 } 96 93 } … … 99 96 * Enable the range and we are done. 100 97 */ 101 bitmap_clear_range(&task->arch.iomap, (size_t) ioaddr, size);98 bitmap_clear_range(&task->arch.iomap, (size_t) ioaddr, (size_t) size); 102 99 103 100 /* … … 121 118 /* First, copy the I/O Permission Bitmap. */ 122 119 irq_spinlock_lock(&TASK->lock, false); 123 124 120 size_t ver = TASK->arch.iomapver; 125 size_t elements = TASK->arch.iomap.elements; 126 127 if (elements > 0) { 128 ASSERT(TASK->arch.iomap.bits); 121 size_t bits = TASK->arch.iomap.bits; 122 if (bits) { 123 ASSERT(TASK->arch.iomap.map); 129 124 130 125 bitmap_t iomap; 131 bitmap_initialize(&iomap, TSS_IOMAP_SIZE * 8,132 CPU->arch.tss->iomap);133 bitmap_copy(&iomap, &TASK->arch.iomap, elements);126 bitmap_initialize(&iomap, CPU->arch.tss->iomap, 127 TSS_IOMAP_SIZE * 8); 128 bitmap_copy(&iomap, &TASK->arch.iomap, bits); 134 129 135 130 /* … … 137 132 * I/O access. 138 133 */ 139 bitmap_set_range(&iomap, elements, 140 ALIGN_UP(elements, 8) - elements); 141 134 bitmap_set_range(&iomap, bits, ALIGN_UP(bits, 8) - bits); 142 135 /* 143 136 * It is safe to set the trailing eight bits because of the 144 137 * extra convenience byte in TSS_IOMAP_SIZE. 145 138 */ 146 bitmap_set_range(&iomap, ALIGN_UP( elements, 8), 8);139 bitmap_set_range(&iomap, ALIGN_UP(bits, 8), 8); 147 140 } 148 149 141 irq_spinlock_unlock(&TASK->lock, false); 150 142 151 143 /* 152 144 * Second, adjust TSS segment limit. 153 * Take the extra ending byte wi th all bits set into account.145 * Take the extra ending byte will all bits set into account. 154 146 */ 155 147 ptr_16_64_t cpugdtr; … … 157 149 158 150 descriptor_t *gdt_p = (descriptor_t *) cpugdtr.base; 159 size_t size = bitmap_size(elements); 160 gdt_tss_setlimit(&gdt_p[TSS_DES], TSS_BASIC_SIZE + size); 151 gdt_tss_setlimit(&gdt_p[TSS_DES], TSS_BASIC_SIZE + BITS2BYTES(bits)); 161 152 gdtr_load(&cpugdtr); 162 153
Note:
See TracChangeset
for help on using the changeset viewer.