/* kernel headers */ #include #include #include #include #include #include #include /* system headers */ #include #include /* usr headers */ #include #include #include #include #include #include /* used for logging */ static struct log clk_log = { .name = "omap_clkconf", .log_level = LEVEL_INFO, .log_func = default_log }; #define DM37XX_CM_BASE 0x48004000 #define AM335X_CM_BASE 0x44E00000 static u32_t base = 0; static u32_t use_count = 0; int clkconf_init() { use_count++; struct machine machine; sys_getmachine(&machine); u32_t cm_base = 0; if (base != 0) { /* when used in a library we can't guaranty we only call this * method once */ log_trace(&clk_log, "Called %d times\n", use_count); return OK; } if (BOARD_IS_BBXM(machine.board_id)){ cm_base = DM37XX_CM_BASE; } else if (BOARD_IS_BB(machine.board_id)){ cm_base = AM335X_CM_BASE; } struct minix_mem_range mr; mr.mr_base = cm_base; mr.mr_limit = cm_base + 0x1000; if (sys_privctl(SELF, SYS_PRIV_ADD_MEM, &mr) != 0) { log_warn(&clk_log, "Unable to request permission to map memory\n"); return EPERM; } base = (uint32_t) vm_map_phys(SELF, (void *) cm_base, 0x1000); if (base == (uint32_t) MAP_FAILED) { log_warn(&clk_log, "Unable to map GPIO memory\n"); return EPERM; } return OK; } int clkconf_set(u32_t clk, u32_t mask, u32_t value) { set32(base + clk, mask, value); return OK; } int clkconf_release() { assert(use_count > 0); use_count--; if (use_count == 0) { vm_unmap_phys(SELF, (void *) base, 0x1000); } return OK; }