Changes in uspace/lib/c/generic/ddi.c [8cd680c:b5c2f56] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/lib/c/generic/ddi.c
r8cd680c rb5c2f56 42 42 #include <ddi.h> 43 43 #include <libarch/ddi.h> 44 #include <device/hw_res.h>45 #include <device/hw_res_parsed.h>46 #include <device/pio_window.h>47 44 #include <libc.h> 48 45 #include <task.h> … … 71 68 * @param flags Flags for the new address space area. 72 69 * @param virt Virtual address of the starting page. 73 * If set to AS_AREA_ANY ((void *) -1), a suitable value 74 * is found by the kernel, otherwise the kernel tries to 75 * obey the desired value. 76 * 77 * @return EOK on success. 78 * @return EPERM if the caller lacks the CAP_MEM_MANAGER capability. 70 * 71 * @return EOK on success 72 * @return EPERM if the caller lacks the CAP_MEM_MANAGER capability 73 * @return ENOENT if there is no task with specified ID 79 74 * @return ENOMEM if there was some problem in creating 80 75 * the address space area. 81 76 * 82 77 */ 83 int physmem_map( uintptr_tphys, size_t pages, unsigned int flags, void **virt)78 int physmem_map(void *phys, size_t pages, unsigned int flags, void **virt) 84 79 { 85 80 return __SYSCALL5(SYS_PHYSMEM_MAP, (sysarg_t) phys, … … 87 82 } 88 83 89 /** Unmap a piece of physical memory to task.90 *91 * Caller of this function must have the CAP_MEM_MANAGER capability.92 *93 * @param virt Virtual address from the phys-mapped region.94 *95 * @return EOK on success.96 * @return EPERM if the caller lacks the CAP_MEM_MANAGER capability.97 *98 */99 int physmem_unmap(void *virt)100 {101 return __SYSCALL1(SYS_PHYSMEM_UNMAP, (sysarg_t) virt);102 }103 104 /** Lock a piece physical memory for DMA transfers.105 *106 * The mapping of the specified virtual memory address107 * to physical memory address is locked in order to108 * make it safe for DMA transferts.109 *110 * Caller of this function must have the CAP_MEM_MANAGER capability.111 *112 * @param virt Virtual address of the memory to be locked.113 * @param size Number of bytes to lock.114 * @param map_flags Desired virtual memory area flags.115 * @param flags Flags for the physical memory address.116 * @param phys Locked physical memory address.117 *118 * @return EOK on success.119 * @return EPERM if the caller lacks the CAP_MEM_MANAGER capability.120 * @return ENOMEM if there was some problem in creating121 * the address space area.122 *123 */124 84 int dmamem_map(void *virt, size_t size, unsigned int map_flags, 125 unsigned int flags, uintptr_t*phys)85 unsigned int flags, void **phys) 126 86 { 127 87 return (int) __SYSCALL6(SYS_DMAMEM_MAP, (sysarg_t) size, … … 130 90 } 131 91 132 /** Map a piece of physical memory suitable for DMA transfers. 133 * 134 * Caller of this function must have the CAP_MEM_MANAGER capability. 135 * 136 * @param size Number of bytes to map. 137 * @param constraint Bit mask defining the contraint on the physical 138 * address to be mapped. 139 * @param map_flags Desired virtual memory area flags. 140 * @param flags Flags for the physical memory address. 141 * @param virt Virtual address of the starting page. 142 * If set to AS_AREA_ANY ((void *) -1), a suitable value 143 * is found by the kernel, otherwise the kernel tries to 144 * obey the desired value. 145 * 146 * @return EOK on success. 147 * @return EPERM if the caller lacks the CAP_MEM_MANAGER capability. 148 * @return ENOMEM if there was some problem in creating 149 * the address space area. 150 * 151 */ 152 int dmamem_map_anonymous(size_t size, uintptr_t constraint, 153 unsigned int map_flags, unsigned int flags, uintptr_t *phys, void **virt) 154 { 155 *phys = constraint; 156 92 int dmamem_map_anonymous(size_t size, unsigned int map_flags, 93 unsigned int flags, void **phys, void **virt) 94 { 157 95 return (int) __SYSCALL6(SYS_DMAMEM_MAP, (sysarg_t) size, 158 96 (sysarg_t) map_flags, (sysarg_t) flags | DMAMEM_FLAGS_ANONYMOUS, … … 194 132 195 133 return __SYSCALL1(SYS_IOSPACE_ENABLE, (sysarg_t) &arg); 196 }197 198 /** Disable I/O space range to task.199 *200 * Caller of this function must have the IO_MEM_MANAGER capability.201 *202 * @param id Task ID.203 * @param ioaddr Starting address of the I/O range.204 * @param size Size of the range.205 *206 * @return EOK on success207 * @return EPERM if the caller lacks the CAP_IO_MANAGER capability208 * @return ENOENT if there is no task with specified ID209 *210 */211 static int iospace_disable(task_id_t id, void *ioaddr, size_t size)212 {213 const ddi_ioarg_t arg = {214 .task_id = id,215 .ioaddr = ioaddr,216 .size = size217 };218 219 return __SYSCALL1(SYS_IOSPACE_DISABLE, (sysarg_t) &arg);220 }221 222 /** Enable PIO for specified address range.223 *224 * @param range I/O range to be enable.225 * @param virt Virtual address for application's PIO operations.226 */227 int pio_enable_range(addr_range_t *range, void **virt)228 {229 return pio_enable(RNGABSPTR(*range), RNGSZ(*range), virt);230 }231 232 /** Enable PIO for specified HW resource wrt. to the PIO window.233 *234 * @param win PIO window. May be NULL if the resources are known to be235 * absolute.236 * @param res Resources specifying the I/O range wrt. to the PIO window.237 * @param virt Virtual address for application's PIO operations.238 *239 * @return EOK on success.240 * @return Negative error code on failure.241 *242 */243 int pio_enable_resource(pio_window_t *win, hw_resource_t *res, void **virt)244 {245 uintptr_t addr;246 size_t size;247 248 switch (res->type) {249 case IO_RANGE:250 addr = res->res.io_range.address;251 if (res->res.io_range.relative) {252 if (!win)253 return EINVAL;254 addr += win->io.base;255 }256 size = res->res.io_range.size;257 break;258 case MEM_RANGE:259 addr = res->res.mem_range.address;260 if (res->res.mem_range.relative) {261 if (!win)262 return EINVAL;263 addr += win->mem.base;264 }265 size = res->res.mem_range.size;266 break;267 default:268 return EINVAL;269 }270 271 return pio_enable((void *) addr, size, virt);272 134 } 273 135 … … 296 158 if (!virt) 297 159 return EINVAL; 298 299 uintptr_tphys_frame =300 ALIGN_DOWN((uintptr_t) pio_addr, PAGE_SIZE);301 size_t offset = (uintptr_t)pio_addr - phys_frame;160 161 void *phys_frame = 162 (void *) ALIGN_DOWN((uintptr_t) pio_addr, PAGE_SIZE); 163 size_t offset = pio_addr - phys_frame; 302 164 size_t pages = SIZE2PAGES(offset + size); 303 165 304 void *virt_page = AS_AREA_ANY;166 void *virt_page; 305 167 int rc = physmem_map(phys_frame, pages, 306 168 AS_AREA_READ | AS_AREA_WRITE, &virt_page); … … 312 174 } 313 175 314 /** Disable PIO for specified I/O range.315 *316 * @param virt I/O start address.317 * @param size Size of the I/O region.318 *319 * @return EOK on success.320 * @return Negative error code on failure.321 *322 */323 int pio_disable(void *virt, size_t size)324 {325 #ifdef IO_SPACE_BOUNDARY326 if (virt < IO_SPACE_BOUNDARY)327 return iospace_disable(task_get_id(), virt, size);328 #else329 (void) iospace_disable;330 #endif331 return physmem_unmap(virt);332 }333 334 176 void pio_write_8(ioport8_t *reg, uint8_t val) 335 177 { … … 371 213 } 372 214 215 /** Register IRQ notification. 216 * 217 * @param inr IRQ number. 218 * @param devno Device number of the device generating inr. 219 * @param method Use this method for notifying me. 220 * @param ucode Top-half pseudocode handler. 221 * 222 * @return Value returned by the kernel. 223 * 224 */ 225 int irq_register(int inr, int devno, int method, irq_code_t *ucode) 226 { 227 return __SYSCALL4(SYS_IRQ_REGISTER, inr, devno, method, 228 (sysarg_t) ucode); 229 } 230 231 /** Unregister IRQ notification. 232 * 233 * @param inr IRQ number. 234 * @param devno Device number of the device generating inr. 235 * 236 * @return Value returned by the kernel. 237 * 238 */ 239 int irq_unregister(int inr, int devno) 240 { 241 return __SYSCALL2(SYS_IRQ_UNREGISTER, inr, devno); 242 } 243 373 244 /** @} 374 245 */
Note:
See TracChangeset
for help on using the changeset viewer.