int ds_retrieve_map(const char *ds_name, char *vaddr, size_t *length, int nr_snapshot, int flags) { cp_grant_id_t gid; int r; /* Map a mapped memory range. */ if(flags & DSMF_MAP_MAPPED) { /* Request DS to grant. */ m.DS_FLAGS = DSF_TYPE_MAP | DSMF_MAP_MAPPED; r = do_invoke_ds(DS_RETRIEVE, ds_name); if(r != OK) return r; /* Do the safemap. */ if(*length > (size_t) m.DS_VAL_LEN) *length = (size_t) m.DS_VAL_LEN; *length = (size_t) CLICK_FLOOR(*length); r = sys_safemap(DS_PROC_NR, m.DS_VAL, 0, (vir_bytes)vaddr, *length, D, 0); /* Copy mapped memory range or a snapshot. */ } else if(flags & (DSMF_COPY_MAPPED|DSMF_COPY_SNAPSHOT)) { /* Grant for memory range first. */ gid = cpf_grant_direct(DS_PROC_NR, (vir_bytes)vaddr, *length, CPF_WRITE); if(!GRANT_VALID(gid)) return errno; m.DS_VAL = gid; m.DS_VAL_LEN = *length; if(flags & DSMF_COPY_MAPPED) { m.DS_FLAGS = DSF_TYPE_MAP | DSMF_COPY_MAPPED; } else { m.DS_NR_SNAPSHOT = nr_snapshot; m.DS_FLAGS = DSF_TYPE_MAP | DSMF_COPY_SNAPSHOT; } r = do_invoke_ds(DS_RETRIEVE, ds_name); *length = m.DS_VAL_LEN; cpf_revoke(gid); } else { return EINVAL; } return r; }
/*===========================================================================* * get_mem_chunks * *===========================================================================*/ void get_mem_chunks( struct memory *mem_chunks) /* store mem chunks here */ { /* Initialize the free memory list from the kernel-provided memory map. Translate * the byte offsets and sizes in this list to clicks, properly truncated. */ phys_bytes base, size, limit; int i; struct memory *memp; /* Initialize everything to zero. */ memset(mem_chunks, 0, NR_MEMS*sizeof(*mem_chunks)); /* Obtain and parse memory from kernel environment. */ /* XXX Any memory chunk in excess of NR_MEMS is silently ignored. */ for(i = 0; i < MIN(MAXMEMMAP, NR_MEMS); i++) { mem_chunks[i].base = kernel_boot_info.memmap[i].mm_base_addr; mem_chunks[i].size = kernel_boot_info.memmap[i].mm_length; } /* Round physical memory to clicks. Round start up, round end down. */ for (i = 0; i < NR_MEMS; i++) { memp = &mem_chunks[i]; /* next mem chunk is stored here */ base = mem_chunks[i].base; size = mem_chunks[i].size; limit = base + size; base = (phys_bytes) (CLICK_CEIL(base)); limit = (phys_bytes) (CLICK_FLOOR(limit)); if (limit <= base) { memp->base = memp->size = 0; } else { memp->base = base >> CLICK_SHIFT; memp->size = (limit - base) >> CLICK_SHIFT; } } }