diff --git a/ChangeLog b/ChangeLog index ea191b3bd..88fd76309 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,10 @@ +2013-01-05 Vladimir Serbinenko + + * grub-core/fs/ntfs.c: Eliminate useless divisions in favor of shifts. + * grub-core/fs/ntfscomp.c: Likewise. + * include/grub/ntfs.h (grub_ntfs_data): Replace spc with log_spc. + (grub_ntfs_comp): Likewise. + 2013-01-05 Vladimir Serbinenko * grub-core/fs/nilfs2.c (-grub_nilfs2_palloc_groups_per_desc_block): diff --git a/grub-core/fs/ntfs.c b/grub-core/fs/ntfs.c index b9762b6a0..6004e1f71 100644 --- a/grub-core/fs/ntfs.c +++ b/grub-core/fs/ntfs.c @@ -391,7 +391,7 @@ read_data (struct grub_ntfs_attr *at, char *pa, char *dest, grub_memset (&cc, 0, sizeof (cc)); ctx = &cc; ctx->attr = at; - ctx->comp.spc = at->mft->data->spc; + ctx->comp.log_spc = at->mft->data->log_spc; ctx->comp.disk = at->mft->data->disk; if (pa[8] == 0) @@ -440,11 +440,11 @@ read_data (struct grub_ntfs_attr *at, char *pa, char *dest, at->save_pos = 1; } - vcn = ctx->target_vcn = (ofs >> GRUB_NTFS_COM_LOG_LEN) * (GRUB_NTFS_COM_SEC / ctx->comp.spc); + vcn = ctx->target_vcn = (ofs >> GRUB_NTFS_COM_LOG_LEN) * (GRUB_NTFS_COM_SEC >> ctx->comp.log_spc); ctx->target_vcn &= ~0xFULL; } else - vcn = ctx->target_vcn = grub_divmod64 (ofs >> GRUB_NTFS_BLK_SHR, ctx->comp.spc, 0); + vcn = ctx->target_vcn = ofs >> (GRUB_NTFS_BLK_SHR + ctx->comp.log_spc); ctx->next_vcn = u32at (pa, 0x10); ctx->curr_lcn = 0; @@ -459,17 +459,17 @@ read_data (struct grub_ntfs_attr *at, char *pa, char *dest, grub_disk_addr_t st0, st1; grub_uint64_t m; - grub_divmod64 (ofs >> GRUB_NTFS_BLK_SHR, ctx->comp.spc, &m); + m = (ofs >> GRUB_NTFS_BLK_SHR) & ((1 << ctx->comp.log_spc) - 1); st0 = - (ctx->target_vcn - ctx->curr_vcn + ctx->curr_lcn) * ctx->comp.spc + m; + ((ctx->target_vcn - ctx->curr_vcn + ctx->curr_lcn) << ctx->comp.log_spc) + m; st1 = st0 + 1; if (st1 == - (ctx->next_vcn - ctx->curr_vcn + ctx->curr_lcn) * ctx->comp.spc) + (ctx->next_vcn - ctx->curr_vcn + ctx->curr_lcn) << ctx->comp.log_spc) { if (grub_ntfs_read_run_list (ctx)) return grub_errno; - st1 = ctx->curr_lcn * ctx->comp.spc; + st1 = ctx->curr_lcn << ctx->comp.log_spc; } grub_set_unaligned32 (dest, grub_cpu_to_le32 (st0)); grub_set_unaligned32 (dest + 4, grub_cpu_to_le32 (st1)); @@ -478,12 +478,10 @@ read_data (struct grub_ntfs_attr *at, char *pa, char *dest, if (!(ctx->flags & GRUB_NTFS_RF_COMP)) { - unsigned int pow; - - if (!grub_fshelp_log2blksize (ctx->comp.spc, &pow)) - grub_fshelp_read_file (ctx->comp.disk, (grub_fshelp_node_t) ctx, - read_hook, ofs, len, dest, - grub_ntfs_read_block, ofs + len, pow, 0); + grub_fshelp_read_file (ctx->comp.disk, (grub_fshelp_node_t) ctx, + read_hook, ofs, len, dest, + grub_ntfs_read_block, ofs + len, + ctx->comp.log_spc, 0); return grub_errno; } @@ -515,11 +513,11 @@ read_attr (struct grub_ntfs_attr *at, char *dest, grub_disk_addr_t ofs, /* If compression is possible make sure that we include possible compressed block size. */ - if (GRUB_NTFS_COM_SEC >= at->mft->data->spc) + if (GRUB_NTFS_LOG_COM_SEC >= at->mft->data->log_spc) vcn = ((ofs >> GRUB_NTFS_COM_LOG_LEN) - * (GRUB_NTFS_COM_SEC / at->mft->data->spc)) & ~0xFULL; + << (GRUB_NTFS_LOG_COM_SEC - at->mft->data->log_spc)) & ~0xFULL; else - vcn = grub_divmod64 (ofs, at->mft->data->spc << GRUB_NTFS_BLK_SHR, 0); + vcn = ofs >> (at->mft->data->log_spc + GRUB_NTFS_BLK_SHR); pa = at->attr_nxt + u16at (at->attr_nxt, 4); while (pa < at->attr_end) { @@ -934,6 +932,7 @@ grub_ntfs_mount (grub_disk_t disk) { struct grub_ntfs_bpb bpb; struct grub_ntfs_data *data = 0; + grub_uint32_t spc; if (!disk) goto fail; @@ -955,23 +954,25 @@ grub_ntfs_mount (grub_disk_t disk) || (bpb.bytes_per_sector & (bpb.bytes_per_sector - 1)) != 0) goto fail; - data->spc = (((grub_uint32_t) bpb.sectors_per_cluster - * (grub_uint32_t) grub_le_to_cpu16 (bpb.bytes_per_sector)) - >> GRUB_NTFS_BLK_SHR); - if (!data->spc) + spc = (((grub_uint32_t) bpb.sectors_per_cluster + * (grub_uint32_t) grub_le_to_cpu16 (bpb.bytes_per_sector)) + >> GRUB_NTFS_BLK_SHR); + if (spc == 0 || (spc & (spc - 1))) goto fail; + for (data->log_spc = 0; (1U << data->log_spc) < spc; data->log_spc++); + if (bpb.clusters_per_mft > 0) - data->mft_size = data->spc * bpb.clusters_per_mft; + data->mft_size = bpb.clusters_per_mft << data->log_spc; else data->mft_size = 1 << (-bpb.clusters_per_mft - GRUB_NTFS_BLK_SHR); if (bpb.clusters_per_index > 0) - data->idx_size = data->spc * bpb.clusters_per_index; + data->idx_size = bpb.clusters_per_index << data->log_spc; else data->idx_size = 1 << (-bpb.clusters_per_index - GRUB_NTFS_BLK_SHR); - data->mft_start = grub_le_to_cpu64 (bpb.mft_lcn) * data->spc; + data->mft_start = grub_le_to_cpu64 (bpb.mft_lcn) << data->log_spc; if ((data->mft_size > GRUB_NTFS_MAX_MFT) || (data->idx_size > GRUB_NTFS_MAX_IDX)) goto fail; diff --git a/grub-core/fs/ntfscomp.c b/grub-core/fs/ntfscomp.c index ec359fa9d..9b3b75da4 100644 --- a/grub-core/fs/ntfscomp.c +++ b/grub-core/fs/ntfscomp.c @@ -33,8 +33,9 @@ decomp_nextvcn (struct grub_ntfs_comp *cc) if (grub_disk_read (cc->disk, (cc->comp_table[cc->comp_head].next_lcn - - (cc->comp_table[cc->comp_head].next_vcn - cc->cbuf_vcn)) * cc->spc, 0, - cc->spc << GRUB_NTFS_BLK_SHR, cc->cbuf)) + (cc->comp_table[cc->comp_head].next_vcn - cc->cbuf_vcn)) << cc->log_spc, + 0, + 1 << (cc->log_spc + GRUB_NTFS_BLK_SHR), cc->cbuf)) return grub_errno; cc->cbuf_vcn++; if ((cc->cbuf_vcn >= cc->comp_table[cc->comp_head].next_vcn)) @@ -46,7 +47,7 @@ decomp_nextvcn (struct grub_ntfs_comp *cc) static grub_err_t decomp_getch (struct grub_ntfs_comp *cc, unsigned char *res) { - if (cc->cbuf_ofs >= (cc->spc << GRUB_NTFS_BLK_SHR)) + if (cc->cbuf_ofs >= (1U << (cc->log_spc + GRUB_NTFS_BLK_SHR))) { if (decomp_nextvcn (cc)) return grub_errno; @@ -159,7 +160,7 @@ decomp_block (struct grub_ntfs_comp *cc, char *dest) { int n; - n = (cc->spc << GRUB_NTFS_BLK_SHR) - cc->cbuf_ofs; + n = (1 << (cc->log_spc + GRUB_NTFS_BLK_SHR)) - cc->cbuf_ofs; if (n > cnt) n = cnt; if ((dest) && (n)) @@ -178,7 +179,7 @@ decomp_block (struct grub_ntfs_comp *cc, char *dest) static grub_err_t read_block (struct grub_ntfs_rlst *ctx, char *buf, grub_size_t num) { - int cpb = GRUB_NTFS_COM_SEC / ctx->comp.spc; + int log_cpb = GRUB_NTFS_LOG_COM_SEC - ctx->comp.log_spc; while (num) { @@ -192,7 +193,7 @@ read_block (struct grub_ntfs_rlst *ctx, char *buf, grub_size_t num) return grub_error (GRUB_ERR_BAD_FS, "invalid compression block"); ctx->comp.comp_head = ctx->comp.comp_tail = 0; ctx->comp.cbuf_vcn = ctx->target_vcn; - ctx->comp.cbuf_ofs = (ctx->comp.spc << GRUB_NTFS_BLK_SHR); + ctx->comp.cbuf_ofs = (1 << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR)); if (ctx->target_vcn >= ctx->next_vcn) { if (grub_ntfs_read_run_list (ctx)) @@ -211,14 +212,14 @@ read_block (struct grub_ntfs_rlst *ctx, char *buf, grub_size_t num) } } - nn = (16 - (unsigned) (ctx->target_vcn & 0xF)) / cpb; + nn = (16 - (unsigned) (ctx->target_vcn & 0xF)) >> log_cpb; if (nn > num) nn = num; num -= nn; if (ctx->flags & GRUB_NTFS_RF_BLNK) { - ctx->target_vcn += nn * cpb; + ctx->target_vcn += nn << log_cpb; if (ctx->comp.comp_tail == 0) { if (buf) @@ -241,7 +242,7 @@ read_block (struct grub_ntfs_rlst *ctx, char *buf, grub_size_t num) } else { - nn *= cpb; + nn <<= log_cpb; while ((ctx->comp.comp_head < ctx->comp.comp_tail) && (nn)) { grub_disk_addr_t tt; @@ -258,10 +259,10 @@ read_block (struct grub_ntfs_rlst *ctx, char *buf, grub_size_t num) (ctx->comp.disk, (ctx->comp.comp_table[ctx->comp.comp_head].next_lcn - (ctx->comp.comp_table[ctx->comp.comp_head].next_vcn - - ctx->target_vcn)) * ctx->comp.spc, 0, - tt * (ctx->comp.spc << GRUB_NTFS_BLK_SHR), buf)) + ctx->target_vcn)) << ctx->comp.log_spc, 0, + tt << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR), buf)) return grub_errno; - buf += tt * (ctx->comp.spc << GRUB_NTFS_BLK_SHR); + buf += tt << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR); } nn -= tt; if (ctx->target_vcn >= @@ -275,10 +276,10 @@ read_block (struct grub_ntfs_rlst *ctx, char *buf, grub_size_t num) if (grub_disk_read (ctx->comp.disk, (ctx->target_vcn - ctx->curr_vcn + - ctx->curr_lcn) * ctx->comp.spc, 0, - nn * (ctx->comp.spc << GRUB_NTFS_BLK_SHR), buf)) + ctx->curr_lcn) << ctx->comp.log_spc, 0, + nn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR), buf)) return grub_errno; - buf += nn * (ctx->comp.spc << GRUB_NTFS_BLK_SHR); + buf += nn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR); } ctx->target_vcn += nn; } @@ -294,7 +295,7 @@ ntfscomp (struct grub_ntfs_attr *at, char *dest, grub_disk_addr_t ofs, grub_err_t ret; ctx->comp.comp_head = ctx->comp.comp_tail = 0; - ctx->comp.cbuf = grub_malloc ((ctx->comp.spc) << GRUB_NTFS_BLK_SHR); + ctx->comp.cbuf = grub_malloc (1 << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR)); if (!ctx->comp.cbuf) return 0; @@ -304,7 +305,7 @@ ntfscomp (struct grub_ntfs_attr *at, char *dest, grub_disk_addr_t ofs, if ((vcn > ctx->target_vcn) && (read_block - (ctx, NULL, ((vcn - ctx->target_vcn) * ctx->comp.spc) / GRUB_NTFS_COM_SEC))) + (ctx, NULL, (vcn - ctx->target_vcn) >> (GRUB_NTFS_LOG_COM_SEC - ctx->comp.log_spc)))) { ret = grub_errno; goto quit; @@ -314,7 +315,7 @@ ntfscomp (struct grub_ntfs_attr *at, char *dest, grub_disk_addr_t ofs, { grub_uint32_t t, n, o; - t = ctx->target_vcn * (ctx->comp.spc << GRUB_NTFS_BLK_SHR); + t = ctx->target_vcn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR); if (read_block (ctx, at->sbuf, 1)) { ret = grub_errno; @@ -346,7 +347,7 @@ ntfscomp (struct grub_ntfs_attr *at, char *dest, grub_disk_addr_t ofs, { grub_uint32_t t; - t = ctx->target_vcn * (ctx->comp.spc << GRUB_NTFS_BLK_SHR); + t = ctx->target_vcn << (ctx->comp.log_spc + GRUB_NTFS_BLK_SHR); if (read_block (ctx, at->sbuf, 1)) { ret = grub_errno; diff --git a/include/grub/ntfs.h b/include/grub/ntfs.h index 093534205..cc28a01e4 100644 --- a/include/grub/ntfs.h +++ b/include/grub/ntfs.h @@ -87,6 +87,7 @@ enum #define GRUB_NTFS_COM_LEN 4096 #define GRUB_NTFS_COM_LOG_LEN 12 #define GRUB_NTFS_COM_SEC (GRUB_NTFS_COM_LEN >> GRUB_NTFS_BLK_SHR) +#define GRUB_NTFS_LOG_COM_SEC (GRUB_NTFS_COM_LOG_LEN - GRUB_NTFS_BLK_SHR) enum { @@ -156,7 +157,7 @@ struct grub_ntfs_data grub_disk_t disk; grub_uint32_t mft_size; grub_uint32_t idx_size; - grub_uint32_t spc; + int log_spc; grub_uint32_t mft_start; grub_uint64_t uuid; }; @@ -172,7 +173,8 @@ struct grub_ntfs_comp grub_disk_t disk; int comp_head, comp_tail; struct grub_ntfs_comp_table_element comp_table[16]; - grub_uint32_t cbuf_ofs, cbuf_vcn, spc; + grub_uint32_t cbuf_ofs, cbuf_vcn; + int log_spc; char *cbuf; };