/trunk/uspace/lib/libc/include/unistd.h |
---|
50,6 → 50,8 |
extern off_t lseek(int, off_t, int); |
extern int ftruncate(int, off_t); |
extern int close(int); |
extern int unlink(const char *); |
extern int rmdir(const char *); |
extern void _exit(int status); |
extern void *sbrk(ssize_t incr); |
/trunk/uspace/lib/libc/generic/vfs.c |
---|
310,7 → 310,6 |
{ |
int res; |
ipcarg_t rc; |
ipc_call_t answer; |
aid_t req; |
futex_down(&vfs_phone_futex); |
323,7 → 322,7 |
return res; |
} |
} |
req = async_send_1(vfs_phone, VFS_MKDIR, mode, &answer); |
req = async_send_1(vfs_phone, VFS_MKDIR, mode, NULL); |
rc = ipc_data_write_start(vfs_phone, path, strlen(path)); |
if (rc != EOK) { |
async_wait_for(req, NULL); |
337,5 → 336,45 |
return EOK; |
} |
static int _unlink(const char *path, int lflag) |
{ |
int res; |
ipcarg_t rc; |
aid_t req; |
futex_down(&vfs_phone_futex); |
async_serialize_start(); |
if (vfs_phone < 0) { |
res = vfs_connect(); |
if (res < 0) { |
async_serialize_end(); |
futex_up(&vfs_phone_futex); |
return res; |
} |
} |
req = async_send_0(vfs_phone, VFS_UNLINK, NULL); |
rc = ipc_data_write_start(vfs_phone, path, strlen(path)); |
if (rc != EOK) { |
async_wait_for(req, NULL); |
async_serialize_end(); |
futex_up(&vfs_phone_futex); |
return (int) rc; |
} |
async_wait_for(req, &rc); |
async_serialize_end(); |
futex_up(&vfs_phone_futex); |
return EOK; |
} |
int unlink(const char *path) |
{ |
return _unlink(path, L_NONE); |
} |
int rmdir(const char *path) |
{ |
return _unlink(path, L_DIRECTORY); |
} |
/** @} |
*/ |
/trunk/uspace/srv/fs/tmpfs/tmpfs_ops.c |
---|
330,10 → 330,10 |
/* handle hit */ |
if (lflag & L_DESTROY) { |
unsigned old_lnkcnt = TMPFS_GET_LNKCNT(dcur); |
int res = destroy_component(dcur); |
unsigned lnkcnt = (res == EOK) ? 0 : TMPFS_GET_LNKCNT(dcur); |
ipc_answer_5(rid, (ipcarg_t)res, tmpfs_reg.fs_handle, |
dev_handle, dcur->index, dcur->size, lnkcnt); |
dev_handle, dcur->index, dcur->size, old_lnkcnt); |
return; |
} |
if ((lflag & (L_CREATE | L_EXCLUSIVE)) == (L_CREATE | L_EXCLUSIVE)) { |
/trunk/uspace/srv/vfs/vfs.c |
---|
111,6 → 111,9 |
case VFS_MKDIR: |
vfs_mkdir(callid, &call); |
break; |
case VFS_UNLINK: |
vfs_unlink(callid, &call); |
break; |
default: |
ipc_answer_0(callid, ENOTSUP); |
break; |
/trunk/uspace/srv/vfs/vfs_ops.c |
---|
590,8 → 590,8 |
void vfs_mkdir(ipc_callid_t rid, ipc_call_t *request) |
{ |
int mode = IPC_GET_ARG1(*request); |
size_t len; |
ipc_callid_t callid; |
if (!ipc_data_write_receive(&callid, &len)) { |
629,6 → 629,63 |
ipc_answer_0(rid, rc); |
} |
void vfs_unlink(ipc_callid_t rid, ipc_call_t *request) |
{ |
int lflag = IPC_GET_ARG1(*request); |
size_t len; |
ipc_callid_t callid; |
if (!ipc_data_write_receive(&callid, &len)) { |
ipc_answer_0(callid, EINVAL); |
ipc_answer_0(rid, EINVAL); |
return; |
} |
/* |
* Now we are on the verge of accepting the path. |
* |
* There is one optimization we could do in the future: copy the path |
* directly into the PLB using some kind of a callback. |
*/ |
char *path = malloc(len); |
if (!path) { |
ipc_answer_0(callid, ENOMEM); |
ipc_answer_0(rid, ENOMEM); |
return; |
} |
int rc; |
if ((rc = ipc_data_write_finalize(callid, path, len))) { |
ipc_answer_0(rid, rc); |
free(path); |
return; |
} |
rwlock_write_lock(&namespace_rwlock); |
lflag &= L_DIRECTORY; /* sanitize lflag */ |
vfs_lookup_res_t lr; |
rc = vfs_lookup_internal(path, len, lflag | L_DESTROY, &lr, NULL); |
free(path); |
if (rc != EOK) { |
rwlock_write_unlock(&namespace_rwlock); |
ipc_answer_0(rid, rc); |
return; |
} |
/* |
* The name has already been unlinked by vfs_lookup_internal(). |
* We have to get and put the VFS node to ensure that it is |
* VFS_FREE'd after the last reference to it is dropped. |
*/ |
vfs_node_t *node = vfs_node_get(&lr); |
node->lnkcnt--; |
rwlock_write_unlock(&namespace_rwlock); |
vfs_node_put(node); |
ipc_answer_0(rid, EOK); |
} |
/** |
* @} |
*/ |
/trunk/uspace/srv/vfs/vfs.h |
---|
141,6 → 141,10 |
* Lookup flags. |
*/ |
/** |
* No lookup flags used. |
*/ |
#define L_NONE 0 |
/** |
* Lookup will succeed only if the object is a regular file. If L_CREATE is |
* specified, an empty file will be created. This flag is mutually exclusive |
* with L_DIRECTORY. |
275,6 → 279,7 |
extern void vfs_seek(ipc_callid_t, ipc_call_t *); |
extern void vfs_truncate(ipc_callid_t, ipc_call_t *); |
extern void vfs_mkdir(ipc_callid_t, ipc_call_t *); |
extern void vfs_unlink(ipc_callid_t, ipc_call_t *); |
#endif |