Subversion Repositories HelenOS

Compare Revisions

Ignore whitespace Rev 4327 → Rev 4326

/branches/network/uspace/srv/fs/tmpfs/tmpfs_dump.c
177,7 → 177,7
goto error;
tag[5] = 0;
if (str_cmp(tag, "TMPFS") != 0)
if (strcmp(tag, "TMPFS") != 0)
goto error;
if (!tmpfs_restore_recursion(dev, &bufpos, &buflen, &pos,
/branches/network/uspace/srv/fs/tmpfs/tmpfs.c
127,12 → 127,7
int main(int argc, char **argv)
{
printf(NAME ": HelenOS TMPFS file system server\n");
 
if (!tmpfs_init()) {
printf(NAME ": failed to initialize TMPFS\n");
return -1;
}
 
int vfs_phone = ipc_connect_me_to_blocking(PHONE_NS, SERVICE_VFS, 0, 0);
if (vfs_phone < EOK) {
printf(NAME ": Unable to connect to VFS\n");
145,7 → 140,7
printf(NAME ": Failed to register file system (%d)\n", rc);
return rc;
}
 
printf(NAME ": Accepting connections\n");
async_manager();
/* not reached */
/branches/network/uspace/srv/fs/tmpfs/tmpfs_ops.c
58,11 → 58,14
 
#define NAMES_BUCKETS 4
 
/** All root nodes have index 0. */
#define TMPFS_SOME_ROOT 0
/** Global counter for assigning node indices. Shared by all instances. */
fs_index_t tmpfs_next_index = 1;
/*
* For now, we don't distinguish between different dev_handles/instances. All
* requests resolve to the only instance, rooted in the following variable.
*/
static tmpfs_dentry_t *root;
 
#define TMPFS_DEV 0 /**< Dummy device handle for TMPFS */
 
/*
* Implementation of the libfs interface.
*/
99,7 → 102,7
 
static void *tmpfs_root_get(dev_handle_t dev_handle)
{
return tmpfs_node_get(dev_handle, TMPFS_SOME_ROOT);
return root;
}
 
static char tmpfs_plb_get_char(unsigned pos)
139,22 → 142,18
/** Hash table of all directory entries. */
hash_table_t dentries;
 
#define DENTRIES_KEY_INDEX 0
#define DENTRIES_KEY_DEV 1
 
/* Implementation of hash table interface for the dentries hash table. */
static hash_index_t dentries_hash(unsigned long key[])
static hash_index_t dentries_hash(unsigned long *key)
{
return key[DENTRIES_KEY_INDEX] % DENTRIES_BUCKETS;
return *key % DENTRIES_BUCKETS;
}
 
static int dentries_compare(unsigned long key[], hash_count_t keys,
static int dentries_compare(unsigned long *key, hash_count_t keys,
link_t *item)
{
tmpfs_dentry_t *dentry = hash_table_get_instance(item, tmpfs_dentry_t,
dh_link);
return (dentry->index == key[DENTRIES_KEY_INDEX] &&
dentry->dev_handle == key[DENTRIES_KEY_DEV]);
return dentry->index == *key;
}
 
static void dentries_remove_callback(link_t *item)
168,6 → 167,8
.remove_callback = dentries_remove_callback
};
 
fs_index_t tmpfs_next_index = 1;
 
typedef struct {
char *name;
tmpfs_dentry_t *parent;
214,7 → 215,6
static bool tmpfs_dentry_initialize(tmpfs_dentry_t *dentry)
{
dentry->index = 0;
dentry->dev_handle = 0;
dentry->sibling = NULL;
dentry->child = NULL;
dentry->type = TMPFS_NONE;
226,21 → 226,15
&names_ops);
}
 
bool tmpfs_init(void)
static bool tmpfs_init(void)
{
if (!hash_table_create(&dentries, DENTRIES_BUCKETS, 2, &dentries_ops))
if (!hash_table_create(&dentries, DENTRIES_BUCKETS, 1, &dentries_ops))
return false;
return true;
}
 
static bool tmpfs_instance_init(dev_handle_t dev_handle)
{
tmpfs_dentry_t *root;
root = (tmpfs_dentry_t *) tmpfs_create_node(dev_handle, L_DIRECTORY);
if (!root)
root = (tmpfs_dentry_t *) tmpfs_create_node(TMPFS_DEV, L_DIRECTORY);
if (!root) {
hash_table_destroy(&dentries);
return false;
}
root->lnkcnt = 0; /* FS root is not linked */
return true;
}
261,7 → 255,7
link_t *hlp = hash_table_find(&childp->names, &key);
assert(hlp);
tmpfs_name_t *namep = hash_table_get_instance(hlp, tmpfs_name_t, link);
return !str_cmp(namep->name, component);
return !strcmp(namep->name, component);
}
 
void *tmpfs_match(void *prnt, const char *component)
278,11 → 272,8
void *
tmpfs_node_get(dev_handle_t dev_handle, fs_index_t index)
{
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = index,
[DENTRIES_KEY_DEV] = dev_handle
};
link_t *lnk = hash_table_find(&dentries, key);
unsigned long key = index;
link_t *lnk = hash_table_find(&dentries, &key);
if (!lnk)
return NULL;
return hash_table_get_instance(lnk, tmpfs_dentry_t, dh_link);
305,11 → 296,7
free(node);
return NULL;
}
if (!tmpfs_root_get(dev_handle))
node->index = TMPFS_SOME_ROOT;
else
node->index = tmpfs_next_index++;
node->dev_handle = dev_handle;
node->index = tmpfs_next_index++;
if (lflag & L_DIRECTORY)
node->type = TMPFS_DIRECTORY;
else
316,11 → 303,8
node->type = TMPFS_FILE;
 
/* Insert the new node into the dentry hash table. */
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = node->index,
[DENTRIES_KEY_DEV] = node->dev_handle
};
hash_table_insert(&dentries, key, &node->dh_link);
unsigned long key = node->index;
hash_table_insert(&dentries, &key, &node->dh_link);
return (void *) node;
}
 
335,13 → 319,13
if (!namep)
return ENOMEM;
tmpfs_name_initialize(namep);
size_t size = str_size(nm);
namep->name = malloc(size + 1);
size_t len = strlen(nm);
namep->name = malloc(len + 1);
if (!namep->name) {
free(namep);
return ENOMEM;
}
str_cpy(namep->name, size + 1, nm);
strcpy(namep->name, nm);
namep->parent = parentp;
childp->lnkcnt++;
400,11 → 384,8
assert(!dentry->child);
assert(!dentry->sibling);
 
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = dentry->index,
[DENTRIES_KEY_DEV] = dentry->dev_handle
};
hash_table_remove(&dentries, key, 2);
unsigned long key = dentry->index;
hash_table_remove(&dentries, &key, 1);
 
hash_table_destroy(&dentry->names);
 
418,36 → 399,13
{
dev_handle_t dev_handle = (dev_handle_t) IPC_GET_ARG1(*request);
 
/* accept the mount options */
ipc_callid_t callid;
size_t size;
if (!ipc_data_write_receive(&callid, &size)) {
ipc_answer_0(callid, EINVAL);
ipc_answer_0(rid, EINVAL);
return;
}
char *opts = malloc(size + 1);
if (!opts) {
ipc_answer_0(callid, ENOMEM);
/* Initialize TMPFS. */
if (!root && !tmpfs_init()) {
ipc_answer_0(rid, ENOMEM);
return;
}
ipcarg_t retval = ipc_data_write_finalize(callid, opts, size);
if (retval != EOK) {
ipc_answer_0(rid, retval);
free(opts);
return;
}
opts[size] = '\0';
 
/* Initialize TMPFS instance. */
if (!tmpfs_instance_init(dev_handle)) {
ipc_answer_0(rid, ENOMEM);
return;
}
 
tmpfs_dentry_t *root = tmpfs_root_get(dev_handle);
if (str_cmp(opts, "restore") == 0) {
if (dev_handle >= 0) {
if (tmpfs_restore(dev_handle))
ipc_answer_3(rid, EOK, root->index, root->size,
root->lnkcnt);
483,11 → 441,8
* Lookup the respective dentry.
*/
link_t *hlp;
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = index,
[DENTRIES_KEY_DEV] = dev_handle,
};
hlp = hash_table_find(&dentries, key);
unsigned long key = index;
hlp = hash_table_find(&dentries, &key);
if (!hlp) {
ipc_answer_0(rid, ENOENT);
return;
499,8 → 454,8
* Receive the read request.
*/
ipc_callid_t callid;
size_t size;
if (!ipc_data_read_receive(&callid, &size)) {
size_t len;
if (!ipc_data_read_receive(&callid, &len)) {
ipc_answer_0(callid, EINVAL);
ipc_answer_0(rid, EINVAL);
return;
508,7 → 463,7
 
size_t bytes;
if (dentry->type == TMPFS_FILE) {
bytes = max(0, min(dentry->size - pos, size));
bytes = max(0, min(dentry->size - pos, len));
(void) ipc_data_read_finalize(callid, dentry->data + pos,
bytes);
} else {
539,7 → 494,7
link);
 
(void) ipc_data_read_finalize(callid, namep->name,
str_size(namep->name) + 1);
strlen(namep->name) + 1);
bytes = 1;
}
 
559,11 → 514,8
* Lookup the respective dentry.
*/
link_t *hlp;
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = index,
[DENTRIES_KEY_DEV] = dev_handle
};
hlp = hash_table_find(&dentries, key);
unsigned long key = index;
hlp = hash_table_find(&dentries, &key);
if (!hlp) {
ipc_answer_0(rid, ENOENT);
return;
575,8 → 527,8
* Receive the write request.
*/
ipc_callid_t callid;
size_t size;
if (!ipc_data_write_receive(&callid, &size)) {
size_t len;
if (!ipc_data_write_receive(&callid, &len)) {
ipc_answer_0(callid, EINVAL);
ipc_answer_0(rid, EINVAL);
return;
585,13 → 537,13
/*
* Check whether the file needs to grow.
*/
if (pos + size <= dentry->size) {
if (pos + len <= dentry->size) {
/* The file size is not changing. */
(void) ipc_data_write_finalize(callid, dentry->data + pos, size);
ipc_answer_2(rid, EOK, size, dentry->size);
(void) ipc_data_write_finalize(callid, dentry->data + pos, len);
ipc_answer_2(rid, EOK, len, dentry->size);
return;
}
size_t delta = (pos + size) - dentry->size;
size_t delta = (pos + len) - dentry->size;
/*
* At this point, we are deliberately extremely straightforward and
* simply realloc the contents of the file on every write that grows the
609,8 → 561,8
memset(newdata + dentry->size, 0, delta);
dentry->size += delta;
dentry->data = newdata;
(void) ipc_data_write_finalize(callid, dentry->data + pos, size);
ipc_answer_2(rid, EOK, size, dentry->size);
(void) ipc_data_write_finalize(callid, dentry->data + pos, len);
ipc_answer_2(rid, EOK, len, dentry->size);
}
 
void tmpfs_truncate(ipc_callid_t rid, ipc_call_t *request)
623,11 → 575,8
* Lookup the respective dentry.
*/
link_t *hlp;
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = index,
[DENTRIES_KEY_DEV] = dev_handle
};
hlp = hash_table_find(&dentries, key);
unsigned long key = index;
hlp = hash_table_find(&dentries, &key);
if (!hlp) {
ipc_answer_0(rid, ENOENT);
return;
661,11 → 610,8
int rc;
 
link_t *hlp;
unsigned long key[] = {
[DENTRIES_KEY_INDEX] = index,
[DENTRIES_KEY_DEV] = dev_handle
};
hlp = hash_table_find(&dentries, key);
unsigned long key = index;
hlp = hash_table_find(&dentries, &key);
if (!hlp) {
ipc_answer_0(rid, ENOENT);
return;
/branches/network/uspace/srv/fs/tmpfs/tmpfs.h
52,7 → 52,6
 
typedef struct tmpfs_dentry {
fs_index_t index; /**< TMPFS node index. */
dev_handle_t dev_handle;/**< Device handle. */
link_t dh_link; /**< Dentries hash table link. */
struct tmpfs_dentry *sibling;
struct tmpfs_dentry *child;
67,8 → 66,6
 
extern libfs_ops_t tmpfs_libfs_ops;
 
extern bool tmpfs_init(void);
 
extern void tmpfs_mounted(ipc_callid_t, ipc_call_t *);
extern void tmpfs_mount(ipc_callid_t, ipc_call_t *);
extern void tmpfs_lookup(ipc_callid_t, ipc_call_t *);
/branches/network/uspace/srv/fs/fat/fat_dentry.c
62,18 → 62,15
int fat_dentry_namecmp(char *name, const char *component)
{
int rc;
size_t size;
 
if (!(rc = stricmp(name, component)))
return rc;
if (!str_chr(name, '.')) {
if (!strchr(name, '.')) {
/*
* There is no '.' in the name, so we know that there is enough
* space for appending an extra '.' to name.
*/
size = str_size(name);
name[size] = '.';
name[size + 1] = '\0';
name[strlen(name)] = '.';
name[strlen(name) + 1] = '\0';
rc = stricmp(name, component);
}
return rc;
/branches/network/uspace/srv/fs/fat/fat_ops.c
487,10 → 487,10
b = fat_block_get(bs, childp, 0, BLOCK_FLAGS_NONE);
d = (fat_dentry_t *)b->data;
if (fat_classify_dentry(d) == FAT_DENTRY_LAST ||
str_cmp(d->name, FAT_NAME_DOT) == 0) {
strcmp(d->name, FAT_NAME_DOT) == 0) {
memset(d, 0, sizeof(fat_dentry_t));
str_cpy(d->name, 8, FAT_NAME_DOT);
str_cpy(d->ext, 3, FAT_EXT_PAD);
strcpy(d->name, FAT_NAME_DOT);
strcpy(d->ext, FAT_EXT_PAD);
d->attr = FAT_ATTR_SUBDIR;
d->firstc = host2uint16_t_le(childp->firstc);
/* TODO: initialize also the date/time members. */
497,10 → 497,10
}
d++;
if (fat_classify_dentry(d) == FAT_DENTRY_LAST ||
str_cmp(d->name, FAT_NAME_DOT_DOT) == 0) {
strcmp(d->name, FAT_NAME_DOT_DOT) == 0) {
memset(d, 0, sizeof(fat_dentry_t));
str_cpy(d->name, 8, FAT_NAME_DOT_DOT);
str_cpy(d->ext, 3, FAT_EXT_PAD);
strcpy(d->name, FAT_NAME_DOT_DOT);
strcpy(d->ext, FAT_EXT_PAD);
d->attr = FAT_ATTR_SUBDIR;
d->firstc = (parentp->firstc == FAT_CLST_ROOT) ?
host2uint16_t_le(FAT_CLST_RES0) :
755,28 → 755,6
uint16_t rde;
int rc;
 
/* accept the mount options */
ipc_callid_t callid;
size_t size;
if (!ipc_data_write_receive(&callid, &size)) {
ipc_answer_0(callid, EINVAL);
ipc_answer_0(rid, EINVAL);
return;
}
char *opts = malloc(size + 1);
if (!opts) {
ipc_answer_0(callid, ENOMEM);
ipc_answer_0(rid, ENOMEM);
return;
}
ipcarg_t retval = ipc_data_write_finalize(callid, opts, size);
if (retval != EOK) {
ipc_answer_0(rid, retval);
free(opts);
return;
}
opts[size] = '\0';
 
/* initialize libblock */
rc = block_init(dev_handle, BS_SIZE);
if (rc != EOK) {
959,7 → 937,7
ipc_answer_1(rid, ENOENT, 0);
return;
hit:
(void) ipc_data_read_finalize(callid, name, str_size(name) + 1);
(void) ipc_data_read_finalize(callid, name, strlen(name) + 1);
bytes = (pos - spos) + 1;
}