Rev 3588 | Rev 3674 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
| Rev 3588 | Rev 3598 | ||
|---|---|---|---|
| Line 87... | Line 87... | ||
| 87 | bps = uint16_t_le2host(bs->bps); |
87 | bps = uint16_t_le2host(bs->bps); |
| 88 | dps = bps / sizeof(fat_dentry_t); |
88 | dps = bps / sizeof(fat_dentry_t); |
| 89 | 89 | ||
| 90 | /* Read the block that contains the dentry of interest. */ |
90 | /* Read the block that contains the dentry of interest. */ |
| 91 | b = _fat_block_get(bs, node->idx->dev_handle, node->idx->pfc, |
91 | b = _fat_block_get(bs, node->idx->dev_handle, node->idx->pfc, |
| 92 | (node->idx->pdi * sizeof(fat_dentry_t)) / bps); |
92 | (node->idx->pdi * sizeof(fat_dentry_t)) / bps, BLOCK_FLAGS_NONE); |
| 93 | 93 | ||
| 94 | d = ((fat_dentry_t *)b->data) + (node->idx->pdi % dps); |
94 | d = ((fat_dentry_t *)b->data) + (node->idx->pdi % dps); |
| 95 | 95 | ||
| 96 | d->firstc = host2uint16_t_le(node->firstc); |
96 | d->firstc = host2uint16_t_le(node->firstc); |
| 97 | if (node->type == FAT_FILE) |
97 | if (node->type == FAT_FILE) |
| Line 179... | Line 179... | ||
| 179 | spc = bs->spc; |
179 | spc = bs->spc; |
| 180 | dps = bps / sizeof(fat_dentry_t); |
180 | dps = bps / sizeof(fat_dentry_t); |
| 181 | 181 | ||
| 182 | /* Read the block that contains the dentry of interest. */ |
182 | /* Read the block that contains the dentry of interest. */ |
| 183 | b = _fat_block_get(bs, idxp->dev_handle, idxp->pfc, |
183 | b = _fat_block_get(bs, idxp->dev_handle, idxp->pfc, |
| 184 | (idxp->pdi * sizeof(fat_dentry_t)) / bps); |
184 | (idxp->pdi * sizeof(fat_dentry_t)) / bps, BLOCK_FLAGS_NONE); |
| 185 | assert(b); |
185 | assert(b); |
| 186 | 186 | ||
| 187 | d = ((fat_dentry_t *)b->data) + (idxp->pdi % dps); |
187 | d = ((fat_dentry_t *)b->data) + (idxp->pdi % dps); |
| 188 | if (d->attr & FAT_ATTR_SUBDIR) { |
188 | if (d->attr & FAT_ATTR_SUBDIR) { |
| 189 | /* |
189 | /* |
| Line 280... | Line 280... | ||
| 280 | bs = block_bb_get(parentp->idx->dev_handle); |
280 | bs = block_bb_get(parentp->idx->dev_handle); |
| 281 | bps = uint16_t_le2host(bs->bps); |
281 | bps = uint16_t_le2host(bs->bps); |
| 282 | dps = bps / sizeof(fat_dentry_t); |
282 | dps = bps / sizeof(fat_dentry_t); |
| 283 | blocks = parentp->size / bps; |
283 | blocks = parentp->size / bps; |
| 284 | for (i = 0; i < blocks; i++) { |
284 | for (i = 0; i < blocks; i++) { |
| 285 | b = fat_block_get(bs, parentp, i); |
285 | b = fat_block_get(bs, parentp, i, BLOCK_FLAGS_NONE); |
| 286 | for (j = 0; j < dps; j++) { |
286 | for (j = 0; j < dps; j++) { |
| 287 | d = ((fat_dentry_t *)b->data) + j; |
287 | d = ((fat_dentry_t *)b->data) + j; |
| 288 | switch (fat_classify_dentry(d)) { |
288 | switch (fat_classify_dentry(d)) { |
| 289 | case FAT_DENTRY_SKIP: |
289 | case FAT_DENTRY_SKIP: |
| 290 | continue; |
290 | continue; |
| Line 370... | Line 370... | ||
| 370 | blocks = nodep->size / bps; |
370 | blocks = nodep->size / bps; |
| 371 | 371 | ||
| 372 | for (i = 0; i < blocks; i++) { |
372 | for (i = 0; i < blocks; i++) { |
| 373 | fat_dentry_t *d; |
373 | fat_dentry_t *d; |
| 374 | 374 | ||
| 375 | b = fat_block_get(bs, nodep, i); |
375 | b = fat_block_get(bs, nodep, i, BLOCK_FLAGS_NONE); |
| 376 | for (j = 0; j < dps; j++) { |
376 | for (j = 0; j < dps; j++) { |
| 377 | d = ((fat_dentry_t *)b->data) + j; |
377 | d = ((fat_dentry_t *)b->data) + j; |
| 378 | switch (fat_classify_dentry(d)) { |
378 | switch (fat_classify_dentry(d)) { |
| 379 | case FAT_DENTRY_SKIP: |
379 | case FAT_DENTRY_SKIP: |
| 380 | continue; |
380 | continue; |
| Line 572... | Line 572... | ||
| 572 | bytes = 0; |
572 | bytes = 0; |
| 573 | (void) ipc_data_read_finalize(callid, NULL, 0); |
573 | (void) ipc_data_read_finalize(callid, NULL, 0); |
| 574 | } else { |
574 | } else { |
| 575 | bytes = min(len, bps - pos % bps); |
575 | bytes = min(len, bps - pos % bps); |
| 576 | bytes = min(bytes, nodep->size - pos); |
576 | bytes = min(bytes, nodep->size - pos); |
| 577 | b = fat_block_get(bs, nodep, pos / bps); |
577 | b = fat_block_get(bs, nodep, pos / bps, |
| - | 578 | BLOCK_FLAGS_NONE); |
|
| 578 | (void) ipc_data_read_finalize(callid, b->data + pos % bps, |
579 | (void) ipc_data_read_finalize(callid, b->data + pos % bps, |
| 579 | bytes); |
580 | bytes); |
| 580 | block_put(b); |
581 | block_put(b); |
| 581 | } |
582 | } |
| 582 | } else { |
583 | } else { |
| Line 597... | Line 598... | ||
| 597 | */ |
598 | */ |
| 598 | bnum = (pos * sizeof(fat_dentry_t)) / bps; |
599 | bnum = (pos * sizeof(fat_dentry_t)) / bps; |
| 599 | while (bnum < nodep->size / bps) { |
600 | while (bnum < nodep->size / bps) { |
| 600 | off_t o; |
601 | off_t o; |
| 601 | 602 | ||
| 602 | b = fat_block_get(bs, nodep, bnum); |
603 | b = fat_block_get(bs, nodep, bnum, BLOCK_FLAGS_NONE); |
| 603 | for (o = pos % (bps / sizeof(fat_dentry_t)); |
604 | for (o = pos % (bps / sizeof(fat_dentry_t)); |
| 604 | o < bps / sizeof(fat_dentry_t); |
605 | o < bps / sizeof(fat_dentry_t); |
| 605 | o++, pos++) { |
606 | o++, pos++) { |
| 606 | d = ((fat_dentry_t *)b->data) + o; |
607 | d = ((fat_dentry_t *)b->data) + o; |
| 607 | switch (fat_classify_dentry(d)) { |
608 | switch (fat_classify_dentry(d)) { |
| Line 645... | Line 646... | ||
| 645 | block_t *b; |
646 | block_t *b; |
| 646 | uint16_t bps; |
647 | uint16_t bps; |
| 647 | unsigned spc; |
648 | unsigned spc; |
| 648 | unsigned bpc; /* bytes per cluster */ |
649 | unsigned bpc; /* bytes per cluster */ |
| 649 | off_t boundary; |
650 | off_t boundary; |
| - | 651 | int flags = BLOCK_FLAGS_NONE; |
|
| 650 | 652 | ||
| 651 | if (!nodep) { |
653 | if (!nodep) { |
| 652 | ipc_answer_0(rid, ENOENT); |
654 | ipc_answer_0(rid, ENOENT); |
| 653 | return; |
655 | return; |
| 654 | } |
656 | } |
| Line 673... | Line 675... | ||
| 673 | * but this one greatly simplifies fat_write(). Note that we can afford |
675 | * but this one greatly simplifies fat_write(). Note that we can afford |
| 674 | * to do this because the client must be ready to handle the return |
676 | * to do this because the client must be ready to handle the return |
| 675 | * value signalizing a smaller number of bytes written. |
677 | * value signalizing a smaller number of bytes written. |
| 676 | */ |
678 | */ |
| 677 | bytes = min(len, bps - pos % bps); |
679 | bytes = min(len, bps - pos % bps); |
| - | 680 | if (bytes == bps) |
|
| - | 681 | flags |= BLOCK_FLAGS_NOREAD; |
|
| 678 | 682 | ||
| 679 | boundary = ROUND_UP(nodep->size, bpc); |
683 | boundary = ROUND_UP(nodep->size, bpc); |
| 680 | if (pos < boundary) { |
684 | if (pos < boundary) { |
| 681 | /* |
685 | /* |
| 682 | * This is the easier case - we are either overwriting already |
686 | * This is the easier case - we are either overwriting already |
| 683 | * existing contents or writing behind the EOF, but still within |
687 | * existing contents or writing behind the EOF, but still within |
| 684 | * the limits of the last cluster. The node size may grow to the |
688 | * the limits of the last cluster. The node size may grow to the |
| 685 | * next block size boundary. |
689 | * next block size boundary. |
| 686 | */ |
690 | */ |
| 687 | fat_fill_gap(bs, nodep, FAT_CLST_RES0, pos); |
691 | fat_fill_gap(bs, nodep, FAT_CLST_RES0, pos); |
| 688 | b = fat_block_get(bs, nodep, pos / bps); |
692 | b = fat_block_get(bs, nodep, pos / bps, flags); |
| 689 | (void) ipc_data_write_finalize(callid, b->data + pos % bps, |
693 | (void) ipc_data_write_finalize(callid, b->data + pos % bps, |
| 690 | bytes); |
694 | bytes); |
| 691 | b->dirty = true; /* need to sync block */ |
695 | b->dirty = true; /* need to sync block */ |
| 692 | block_put(b); |
696 | block_put(b); |
| 693 | if (pos + bytes > nodep->size) { |
697 | if (pos + bytes > nodep->size) { |
| Line 716... | Line 720... | ||
| 716 | ipc_answer_0(rid, status); |
720 | ipc_answer_0(rid, status); |
| 717 | return; |
721 | return; |
| 718 | } |
722 | } |
| 719 | /* zero fill any gaps */ |
723 | /* zero fill any gaps */ |
| 720 | fat_fill_gap(bs, nodep, mcl, pos); |
724 | fat_fill_gap(bs, nodep, mcl, pos); |
| 721 | b = _fat_block_get(bs, dev_handle, lcl, (pos / bps) % spc); |
725 | b = _fat_block_get(bs, dev_handle, lcl, (pos / bps) % spc, |
| - | 726 | flags); |
|
| 722 | (void) ipc_data_write_finalize(callid, b->data + pos % bps, |
727 | (void) ipc_data_write_finalize(callid, b->data + pos % bps, |
| 723 | bytes); |
728 | bytes); |
| 724 | b->dirty = true; /* need to sync block */ |
729 | b->dirty = true; /* need to sync block */ |
| 725 | block_put(b); |
730 | block_put(b); |
| 726 | /* |
731 | /* |