/trunk/kernel/generic/include/ipc/ipc.h |
---|
159,7 → 159,7 |
* on answer, the recipient must set: |
* - ARG1 - dst as_area base adress |
*/ |
#define IPC_M_AS_AREA_SEND 4 |
#define IPC_M_SHARE_OUT 4 |
/** Receive as_area over IPC. |
* - ARG1 - destination as_area base address |
171,7 → 171,7 |
* - ARG1 - source as_area base address |
* - ARG2 - flags that will be used for sharing |
*/ |
#define IPC_M_AS_AREA_RECV 5 |
#define IPC_M_SHARE_IN 5 |
/** Send data to another address space over IPC. |
* - ARG1 - source address space virtual address |
/trunk/kernel/generic/src/ipc/sysipc.c |
---|
112,8 → 112,8 |
static inline int method_is_immutable(unative_t method) |
{ |
switch (method) { |
case IPC_M_AS_AREA_SEND: |
case IPC_M_AS_AREA_RECV: |
case IPC_M_SHARE_OUT: |
case IPC_M_SHARE_IN: |
case IPC_M_DATA_WRITE: |
case IPC_M_DATA_READ: |
return 1; |
141,8 → 141,8 |
switch (IPC_GET_METHOD(call->data)) { |
case IPC_M_CONNECT_TO_ME: |
case IPC_M_CONNECT_ME_TO: |
case IPC_M_AS_AREA_SEND: |
case IPC_M_AS_AREA_RECV: |
case IPC_M_SHARE_OUT: |
case IPC_M_SHARE_IN: |
case IPC_M_DATA_WRITE: |
case IPC_M_DATA_READ: |
return 1; |
199,7 → 199,7 |
ipc_phone_connect((phone_t *) IPC_GET_ARG5(*olddata), |
&TASK->answerbox); |
} |
} else if (IPC_GET_METHOD(*olddata) == IPC_M_AS_AREA_SEND) { |
} else if (IPC_GET_METHOD(*olddata) == IPC_M_SHARE_OUT) { |
if (!IPC_GET_RETVAL(answer->data)) { |
/* Accepted, handle as_area receipt */ |
ipl_t ipl; |
218,7 → 218,7 |
IPC_SET_RETVAL(answer->data, rc); |
return rc; |
} |
} else if (IPC_GET_METHOD(*olddata) == IPC_M_AS_AREA_RECV) { |
} else if (IPC_GET_METHOD(*olddata) == IPC_M_SHARE_IN) { |
if (!IPC_GET_RETVAL(answer->data)) { |
ipl_t ipl; |
as_t *as; |
313,7 → 313,7 |
call->flags |= IPC_CALL_CONN_ME_TO; |
call->priv = newphid; |
break; |
case IPC_M_AS_AREA_SEND: |
case IPC_M_SHARE_OUT: |
size = as_area_get_size(IPC_GET_ARG1(call->data)); |
if (!size) |
return EPERM; |
/trunk/uspace/app/klog/klog.c |
---|
63,8 → 63,8 |
printf("Kernel console output.\n"); |
mapping = as_get_mappable_page(PAGE_SIZE); |
res = ipc_call_sync_3_0(PHONE_NS, IPC_M_AS_AREA_RECV, |
(sysarg_t) mapping, PAGE_SIZE, SERVICE_MEM_KLOG); |
res = ipc_share_in_send_1_0(PHONE_NS, mapping, PAGE_SIZE, |
SERVICE_MEM_KLOG); |
if (res) { |
printf("Failed to initialize klog memarea\n"); |
_exit(1); |
/trunk/uspace/lib/libfs/libfs.c |
---|
94,8 → 94,7 |
/* |
* Request sharing the Path Lookup Buffer with VFS. |
*/ |
rc = ipc_call_sync_2_0(vfs_phone, IPC_M_AS_AREA_RECV, |
(ipcarg_t) reg->plb_ro, PLB_SIZE); |
rc = ipc_share_in_send_0_0(vfs_phone, reg->plb_ro, PLB_SIZE); |
if (rc) { |
async_wait_for(req, NULL); |
return rc; |
/trunk/uspace/lib/libc/include/ipc/ipc.h |
---|
262,6 → 262,25 |
ipcarg_t arg1, ipcarg_t arg2, int mode); |
/* |
* User-friendly wrappers for ipc_share_in_send(). |
*/ |
#define ipc_share_in_send_0_0(phoneid, dst, size) \ |
ipc_share_in_send((phoneid), (dst), (size), 0, NULL) |
#define ipc_share_in_send_0_1(phoneid, dst, size, flags) \ |
ipc_share_in_send((phoneid), (dst), (size), 0, (flags)) |
#define ipc_share_in_send_1_0(phoneid, dst, size, arg) \ |
ipc_share_in_send((phoneid), (dst), (size), (arg), NULL) |
#define ipc_share_in_send_1_1(phoneid, dst, size, arg, flags) \ |
ipc_share_in_send((phoneid), (dst), (size), (arg), (flags)) |
extern int ipc_share_in_send(int phoneid, void *dst, size_t size, ipcarg_t arg, |
int *flags); |
extern int ipc_share_in_receive(ipc_callid_t *callid, size_t *size); |
extern int ipc_share_in_deliver(ipc_callid_t callid, void *src, int flags); |
extern int ipc_share_out_send(int phoneid, void *src, int flags); |
extern int ipc_share_out_receive(ipc_callid_t *callid, size_t *size, int *flags); |
extern int ipc_share_out_deliver(ipc_callid_t callid, void *dst); |
extern int ipc_data_read_send(int phoneid, void *dst, size_t size); |
extern int ipc_data_read_receive(ipc_callid_t *callid, size_t *size); |
extern int ipc_data_read_deliver(ipc_callid_t callid, void *src, size_t size); |
/trunk/uspace/lib/libc/generic/time.c |
---|
135,15 → 135,14 |
{ |
void *mapping; |
sysarg_t s1, s2; |
sysarg_t rights; |
int rights; |
int res; |
if (!ktime) { |
mapping = as_get_mappable_page(PAGE_SIZE); |
/* Get the mapping of kernel clock */ |
res = ipc_call_sync_3_2(PHONE_NS, IPC_M_AS_AREA_RECV, |
(sysarg_t) mapping, PAGE_SIZE, SERVICE_MEM_REALTIME, NULL, |
&rights); |
res = ipc_share_in_send_1_1(PHONE_NS, mapping, PAGE_SIZE, |
SERVICE_MEM_REALTIME, &rights); |
if (res) { |
printf("Failed to initialize timeofday memarea\n"); |
_exit(1); |
/trunk/uspace/lib/libc/generic/ipc.c |
---|
666,6 → 666,133 |
arg2, mode); |
} |
/** Wrapper for making IPC_M_SHARE_IN calls. |
* |
* @param phoneid Phone that will be used to contact the receiving side. |
* @param dst Destination address space area base. |
* @param size Size of the destination address space area. |
* @param arg User defined argument. |
* @param flags Storage where the received flags will be stored. Can be |
* NULL. |
* |
* @return Zero on success or a negative error code from errno.h. |
*/ |
int ipc_share_in_send(int phoneid, void *dst, size_t size, ipcarg_t arg, |
int *flags) |
{ |
int res; |
sysarg_t tmp_flags; |
res = ipc_call_sync_3_2(phoneid, IPC_M_SHARE_IN, (ipcarg_t) dst, |
(ipcarg_t) size, arg, NULL, &tmp_flags); |
if (flags) |
*flags = tmp_flags; |
return res; |
} |
/** Wrapper for receiving the IPC_M_SHARE_IN calls. |
* |
* This wrapper only makes it more comfortable to receive IPC_M_SHARE_IN calls |
* so that the user doesn't have to remember the meaning of each IPC argument. |
* |
* So far, this wrapper is to be used from within a connection fibril. |
* |
* @param callid Storage where the hash of the IPC_M_SHARE_IN call will |
* be stored. |
* @param size Destination address space area size. |
* |
* @return Non-zero on success, zero on failure. |
*/ |
int ipc_share_in_receive(ipc_callid_t *callid, size_t *size) |
{ |
ipc_call_t data; |
assert(callid); |
assert(size); |
*callid = async_get_call(&data); |
if (IPC_GET_METHOD(data) != IPC_M_SHARE_IN) |
return 0; |
*size = (size_t) IPC_GET_ARG2(data); |
return 1; |
} |
/** Wrapper for answering the IPC_M_SHARE_IN calls. |
* |
* This wrapper only makes it more comfortable to answer IPC_M_DATA_READ calls |
* so that the user doesn't have to remember the meaning of each IPC argument. |
* |
* @param callid Hash of the IPC_M_DATA_READ call to answer. |
* @param src Source address space base. |
* @param flags Flags to be used for sharing. Bits can be only cleared. |
* |
* @return Zero on success or a value from @ref errno.h on failure. |
*/ |
int ipc_share_in_deliver(ipc_callid_t callid, void *src, int flags) |
{ |
return ipc_answer_2(callid, EOK, (ipcarg_t) src, (ipcarg_t) flags); |
} |
/** Wrapper for making IPC_M_SHARE_OUT calls. |
* |
* @param phoneid Phone that will be used to contact the receiving side. |
* @param src Source address space area base address. |
* @param flags Flags to be used for sharing. Bits can be only cleared. |
* |
* @return Zero on success or a negative error code from errno.h. |
*/ |
int ipc_share_out_send(int phoneid, void *src, int flags) |
{ |
return ipc_call_sync_3_0(phoneid, IPC_M_SHARE_OUT, (ipcarg_t) src, 0, |
(ipcarg_t) flags); |
} |
/** Wrapper for receiving the IPC_M_SHARE_OUT calls. |
* |
* This wrapper only makes it more comfortable to receive IPC_M_SHARE_OUT calls |
* so that the user doesn't have to remember the meaning of each IPC argument. |
* |
* So far, this wrapper is to be used from within a connection fibril. |
* |
* @param callid Storage where the hash of the IPC_M_SHARE_OUT call will |
* be stored. |
* @param size Storage where the source address space area size will be |
* stored. |
* @param flags Storage where the sharing flags will be stored. |
* |
* @return Non-zero on success, zero on failure. |
*/ |
int ipc_share_out_receive(ipc_callid_t *callid, size_t *size, int *flags) |
{ |
ipc_call_t data; |
assert(callid); |
assert(size); |
assert(flags); |
*callid = async_get_call(&data); |
if (IPC_GET_METHOD(data) != IPC_M_DATA_WRITE) |
return 0; |
*size = (size_t) IPC_GET_ARG2(data); |
*flags = (int) IPC_GET_ARG3(data); |
return 1; |
} |
/** Wrapper for answering the IPC_M_SHARE_OUT calls. |
* |
* This wrapper only makes it more comfortable to answer IPC_M_SHARE_OUT calls |
* so that the user doesn't have to remember the meaning of each IPC argument. |
* |
* @param callid Hash of the IPC_M_DATA_WRITE call to answer. |
* @param dst Destination address space area base address. |
* |
* @return Zero on success or a value from @ref errno.h on failure. |
*/ |
int ipc_share_out_deliver(ipc_callid_t callid, void *dst) |
{ |
return ipc_answer_1(callid, EOK, (ipcarg_t) dst); |
} |
/** Wrapper for making IPC_M_DATA_READ calls. |
* |
* @param phoneid Phone that will be used to contact the receiving side. |
/trunk/uspace/srv/ns/ns.c |
---|
117,7 → 117,7 |
while (1) { |
callid = ipc_wait_for_call(&call); |
switch (IPC_GET_METHOD(call)) { |
case IPC_M_AS_AREA_RECV: |
case IPC_M_SHARE_IN: |
switch (IPC_GET_ARG3(call)) { |
case SERVICE_MEM_REALTIME: |
get_as_area(callid, &call, "clock.faddr", |
/trunk/uspace/srv/console/console.c |
---|
537,8 → 537,8 |
sizeof(keyfield_t) * fb_info.cols * fb_info.rows, |
PROTO_READ | PROTO_WRITE, MAP_ANONYMOUS | MAP_PRIVATE, 0, 0); |
if (!interbuffer) { |
if (async_req_3_0(fb_info.phone, IPC_M_AS_AREA_SEND, |
(ipcarg_t) interbuffer, 0, AS_AREA_READ) != 0) { |
if (ipc_share_out_send(fb_info.phone, interbuffer, |
AS_AREA_READ) != EOK) { |
munmap(interbuffer, |
sizeof(keyfield_t) * fb_info.cols * fb_info.rows); |
interbuffer = NULL; |
/trunk/uspace/srv/console/gcons.c |
---|
325,8 → 325,7 |
rc = async_req_1_0(fbphone, FB_PREPARE_SHM, (ipcarg_t) shm); |
if (rc) |
goto exit; |
rc = async_req_3_0(fbphone, IPC_M_AS_AREA_SEND, (ipcarg_t) shm, 0, |
PROTO_READ); |
rc = ipc_share_out_send(fbphone, shm, PROTO_READ); |
if (rc) |
goto drop; |
/* Draw logo */ |
387,8 → 386,7 |
rc = async_req_1_0(fbphone, FB_PREPARE_SHM, (ipcarg_t) shm); |
if (rc) |
goto exit; |
rc = async_req_3_0(fbphone, IPC_M_AS_AREA_SEND, (ipcarg_t) shm, 0, |
PROTO_READ); |
rc = ipc_share_out_send(fbphone, shm, PROTO_READ); |
if (rc) |
goto drop; |
/trunk/uspace/srv/rd/rd.c |
---|
103,14 → 103,14 |
/* |
* Now we wait for the client to send us its communication as_area. |
*/ |
callid = async_get_call(&call); |
if (IPC_GET_METHOD(call) == IPC_M_AS_AREA_SEND) { |
if (IPC_GET_ARG1(call) >= (ipcarg_t) BLOCK_SIZE) { |
size_t size; |
if (ipc_share_out_receive(&callid, &size, NULL)) { |
if (size >= BLOCK_SIZE) { |
/* |
* The client sends an as_area that can absorb the whole |
* block. |
*/ |
ipc_answer_1(callid, EOK, (uintptr_t) fs_va); |
(void) ipc_share_out_deliver(callid, fs_va); |
} else { |
/* |
* The client offered as_area too small. |
/trunk/uspace/srv/fb/fb.c |
---|
747,7 → 747,7 |
unsigned int x, y; |
switch (IPC_GET_METHOD(*call)) { |
case IPC_M_AS_AREA_SEND: |
case IPC_M_SHARE_OUT: |
/* We accept one area for data interchange */ |
if (IPC_GET_ARG1(*call) == shm_id) { |
void *dest = as_get_mappable_page(IPC_GET_ARG2(*call)); |
/trunk/uspace/srv/fb/ega.c |
---|
208,7 → 208,7 |
client_connected = 0; |
ipc_answer_0(callid, EOK); |
return; /* Exit thread */ |
case IPC_M_AS_AREA_SEND: |
case IPC_M_SHARE_OUT: |
/* We accept one area for data interchange */ |
intersize = IPC_GET_ARG2(call); |
if (intersize >= scr_width * scr_height * |
/trunk/uspace/srv/vfs/vfs_register.c |
---|
270,8 → 270,8 |
/* |
* The client will want us to send him the address space area with PLB. |
*/ |
callid = async_get_call(&call); |
if (IPC_GET_METHOD(call) != IPC_M_AS_AREA_RECV) { |
if (!ipc_share_in_receive(&callid, &size)) { |
dprintf("Unexpected call, method = %d\n", IPC_GET_METHOD(call)); |
list_remove(&fs_info->fs_link); |
futex_up(&fs_head_futex); |
285,7 → 285,6 |
/* |
* We can only send the client address space area PLB_SIZE bytes long. |
*/ |
size = IPC_GET_ARG2(call); |
if (size != PLB_SIZE) { |
dprintf("Client suggests wrong size of PFB, size = %d\n", size); |
list_remove(&fs_info->fs_link); |
300,8 → 299,8 |
/* |
* Commit to read-only sharing the PLB with the client. |
*/ |
ipc_answer_2(callid, EOK, (ipcarg_t) plb, |
(ipcarg_t) (AS_AREA_READ | AS_AREA_CACHEABLE)); |
(void) ipc_share_in_deliver(callid, plb, |
AS_AREA_READ | AS_AREA_CACHEABLE); |
dprintf("Sharing PLB.\n"); |