Changeset 40257f5 in mainline
- Timestamp:
- 2008-06-05T22:49:54Z (16 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- e32e092
- Parents:
- 32443b0
- Location:
- uspace/srv/fs/tmpfs
- Files:
-
- 1 added
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/srv/fs/tmpfs/Makefile
r32443b0 r40257f5 45 45 SOURCES = \ 46 46 tmpfs.c \ 47 tmpfs_ops.c 47 tmpfs_ops.c \ 48 tmpfs_dump.c 48 49 49 50 OBJECTS := $(addsuffix .o,$(basename $(SOURCES))) -
uspace/srv/fs/tmpfs/tmpfs.h
r32443b0 r40257f5 61 61 extern fs_reg_t tmpfs_reg; 62 62 63 extern libfs_ops_t tmpfs_libfs_ops; 64 63 65 extern void tmpfs_mount(ipc_callid_t, ipc_call_t *); 64 66 extern void tmpfs_lookup(ipc_callid_t, ipc_call_t *); … … 68 70 extern void tmpfs_destroy(ipc_callid_t, ipc_call_t *); 69 71 72 extern bool tmpfs_restore(dev_handle_t); 73 70 74 #endif 71 75 -
uspace/srv/fs/tmpfs/tmpfs_ops.c
r32443b0 r40257f5 51 51 #include <as.h> 52 52 #include <libfs.h> 53 #include <ipc/services.h>54 #include <ipc/devmap.h>55 #include <sys/mman.h>56 #include <byteorder.h>57 53 58 54 #define min(a, b) ((a) < (b) ? (a) : (b)) … … 62 58 63 59 #define NAMES_BUCKETS 4 64 65 #define BLOCK_SIZE 1024 // FIXME66 #define RD_BASE 1024 // FIXME67 #define RD_READ_BLOCK (RD_BASE + 1)68 60 69 61 /* … … 149 141 hash_table_t dentries; 150 142 151 struct rdentry {152 uint8_t type;153 uint32_t len;154 } __attribute__((packed));155 156 143 /* Implementation of hash table interface for the dentries hash table. */ 157 144 static hash_index_t dentries_hash(unsigned long *key) … … 249 236 root->lnkcnt = 1; 250 237 return true; 251 }252 253 static bool tmpfs_blockread(int phone, void *buffer, size_t *bufpos, size_t *buflen, size_t *pos, void *dst, size_t size)254 {255 size_t offset = 0;256 size_t left = size;257 258 while (left > 0) {259 size_t rd;260 261 if (*bufpos + left < *buflen)262 rd = left;263 else264 rd = *buflen - *bufpos;265 266 if (rd > 0) {267 memcpy(dst + offset, buffer + *bufpos, rd);268 offset += rd;269 *bufpos += rd;270 *pos += rd;271 left -= rd;272 }273 274 if (*bufpos == *buflen) {275 ipcarg_t retval;276 int rc = ipc_call_sync_2_1(phone, RD_READ_BLOCK,277 *pos / BLOCK_SIZE, BLOCK_SIZE,278 &retval);279 if ((rc != EOK) || (retval != EOK))280 return false;281 282 *bufpos = 0;283 *buflen = BLOCK_SIZE;284 }285 }286 287 return true;288 }289 290 static bool tmpfs_restore_recursion(int phone, void *block, size_t *bufpos, size_t *buflen, size_t *pos, tmpfs_dentry_t *parent)291 {292 struct rdentry entry;293 294 do {295 char *fname;296 tmpfs_dentry_t *node;297 uint32_t size;298 299 if (!tmpfs_blockread(phone, block, bufpos, buflen, pos, &entry, sizeof(entry)))300 return false;301 302 entry.len = uint32_t_le2host(entry.len);303 304 switch (entry.type) {305 case 0:306 break;307 case 1:308 fname = malloc(entry.len + 1);309 if (fname == NULL)310 return false;311 312 node = (tmpfs_dentry_t *) tmpfs_create_node(L_FILE);313 if (node == NULL) {314 free(fname);315 return false;316 }317 318 if (!tmpfs_blockread(phone, block, bufpos, buflen, pos, fname, entry.len)) {319 tmpfs_destroy_node((void *) node);320 free(fname);321 return false;322 }323 fname[entry.len] = 0;324 325 if (!tmpfs_link_node((void *) parent, (void *) node, fname)) {326 tmpfs_destroy_node((void *) node);327 free(fname);328 return false;329 }330 free(fname);331 332 if (!tmpfs_blockread(phone, block, bufpos, buflen, pos, &size, sizeof(size)))333 return false;334 335 size = uint32_t_le2host(size);336 337 node->data = malloc(size);338 if (node->data == NULL)339 return false;340 341 node->size = size;342 if (!tmpfs_blockread(phone, block, bufpos, buflen, pos, node->data, size))343 return false;344 345 break;346 case 2:347 fname = malloc(entry.len + 1);348 if (fname == NULL)349 return false;350 351 node = (tmpfs_dentry_t *) tmpfs_create_node(L_DIRECTORY);352 if (node == NULL) {353 free(fname);354 return false;355 }356 357 if (!tmpfs_blockread(phone, block, bufpos, buflen, pos, fname, entry.len)) {358 tmpfs_destroy_node((void *) node);359 free(fname);360 return false;361 }362 fname[entry.len] = 0;363 364 if (!tmpfs_link_node((void *) parent, (void *) node, fname)) {365 tmpfs_destroy_node((void *) node);366 free(fname);367 return false;368 }369 free(fname);370 371 if (!tmpfs_restore_recursion(phone, block, bufpos, buflen, pos, node))372 return false;373 374 break;375 default:376 return false;377 }378 } while (entry.type != 0);379 380 return true;381 }382 383 static bool tmpfs_restore(dev_handle_t dev)384 {385 void *block = mmap(NULL, BLOCK_SIZE,386 PROTO_READ | PROTO_WRITE, MAP_ANONYMOUS | MAP_PRIVATE, 0, 0);387 388 if (block == NULL)389 return false;390 391 int phone = ipc_connect_me_to(PHONE_NS, SERVICE_DEVMAP, DEVMAP_CONNECT_TO_DEVICE, dev);392 393 if (phone < 0) {394 munmap(block, BLOCK_SIZE);395 return false;396 }397 398 if (ipc_share_out_start(phone, block, AS_AREA_READ | AS_AREA_WRITE) != EOK)399 goto error;400 401 size_t bufpos = 0;402 size_t buflen = 0;403 size_t pos = 0;404 405 char tag[6];406 if (!tmpfs_blockread(phone, block, &bufpos, &buflen, &pos, tag, 5))407 goto error;408 409 tag[5] = 0;410 if (strcmp(tag, "TMPFS") != 0)411 goto error;412 413 if (!tmpfs_restore_recursion(phone, block, &bufpos, &buflen, &pos, root))414 goto error;415 416 ipc_hangup(phone);417 munmap(block, BLOCK_SIZE);418 return true;419 420 error:421 ipc_hangup(phone);422 munmap(block, BLOCK_SIZE);423 return false;424 238 } 425 239
Note:
See TracChangeset
for help on using the changeset viewer.