bits.c 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. /*
  2. * Copyright (C) Sistina Software, Inc. 1997-2003 All rights reserved.
  3. * Copyright (C) 2004-2005 Red Hat, Inc. All rights reserved.
  4. *
  5. * This copyrighted material is made available to anyone wishing to use,
  6. * modify, copy, or redistribute it subject to the terms and conditions
  7. * of the GNU General Public License v.2.
  8. */
  9. /*
  10. * These routines are used by the resource group routines (rgrp.c)
  11. * to keep track of block allocation. Each block is represented by two
  12. * bits. One bit indicates whether or not the block is used. (1=used,
  13. * 0=free) The other bit indicates whether or not the block contains a
  14. * dinode or not. (1=dinode, 0=not-dinode) So, each byte represents
  15. * GFS2_NBBY (i.e. 4) blocks.
  16. */
  17. #include <linux/sched.h>
  18. #include <linux/slab.h>
  19. #include <linux/spinlock.h>
  20. #include <linux/completion.h>
  21. #include <linux/buffer_head.h>
  22. #include <asm/semaphore.h>
  23. #include "gfs2.h"
  24. #include "bits.h"
  25. static const char valid_change[16] = {
  26. /* current */
  27. /* n */ 0, 1, 0, 1,
  28. /* e */ 1, 0, 0, 0,
  29. /* w */ 0, 0, 0, 0,
  30. 1, 0, 0, 0
  31. };
  32. /**
  33. * gfs2_setbit - Set a bit in the bitmaps
  34. * @buffer: the buffer that holds the bitmaps
  35. * @buflen: the length (in bytes) of the buffer
  36. * @block: the block to set
  37. * @new_state: the new state of the block
  38. *
  39. */
  40. void gfs2_setbit(struct gfs2_rgrpd *rgd, unsigned char *buffer,
  41. unsigned int buflen, uint32_t block, unsigned char new_state)
  42. {
  43. unsigned char *byte, *end, cur_state;
  44. unsigned int bit;
  45. byte = buffer + (block / GFS2_NBBY);
  46. bit = (block % GFS2_NBBY) * GFS2_BIT_SIZE;
  47. end = buffer + buflen;
  48. gfs2_assert(rgd->rd_sbd, byte < end);
  49. cur_state = (*byte >> bit) & GFS2_BIT_MASK;
  50. if (valid_change[new_state * 4 + cur_state]) {
  51. *byte ^= cur_state << bit;
  52. *byte |= new_state << bit;
  53. } else
  54. gfs2_consist_rgrpd(rgd);
  55. }
  56. /**
  57. * gfs2_testbit - test a bit in the bitmaps
  58. * @buffer: the buffer that holds the bitmaps
  59. * @buflen: the length (in bytes) of the buffer
  60. * @block: the block to read
  61. *
  62. */
  63. unsigned char gfs2_testbit(struct gfs2_rgrpd *rgd, unsigned char *buffer,
  64. unsigned int buflen, uint32_t block)
  65. {
  66. unsigned char *byte, *end, cur_state;
  67. unsigned int bit;
  68. byte = buffer + (block / GFS2_NBBY);
  69. bit = (block % GFS2_NBBY) * GFS2_BIT_SIZE;
  70. end = buffer + buflen;
  71. gfs2_assert(rgd->rd_sbd, byte < end);
  72. cur_state = (*byte >> bit) & GFS2_BIT_MASK;
  73. return cur_state;
  74. }
  75. /**
  76. * gfs2_bitfit - Search an rgrp's bitmap buffer to find a bit-pair representing
  77. * a block in a given allocation state.
  78. * @buffer: the buffer that holds the bitmaps
  79. * @buflen: the length (in bytes) of the buffer
  80. * @goal: start search at this block's bit-pair (within @buffer)
  81. * @old_state: GFS2_BLKST_XXX the state of the block we're looking for;
  82. * bit 0 = alloc(1)/free(0), bit 1 = meta(1)/data(0)
  83. *
  84. * Scope of @goal and returned block number is only within this bitmap buffer,
  85. * not entire rgrp or filesystem. @buffer will be offset from the actual
  86. * beginning of a bitmap block buffer, skipping any header structures.
  87. *
  88. * Return: the block number (bitmap buffer scope) that was found
  89. */
  90. uint32_t gfs2_bitfit(struct gfs2_rgrpd *rgd, unsigned char *buffer,
  91. unsigned int buflen, uint32_t goal,
  92. unsigned char old_state)
  93. {
  94. unsigned char *byte, *end, alloc;
  95. uint32_t blk = goal;
  96. unsigned int bit;
  97. byte = buffer + (goal / GFS2_NBBY);
  98. bit = (goal % GFS2_NBBY) * GFS2_BIT_SIZE;
  99. end = buffer + buflen;
  100. alloc = (old_state & 1) ? 0 : 0x55;
  101. while (byte < end) {
  102. if ((*byte & 0x55) == alloc) {
  103. blk += (8 - bit) >> 1;
  104. bit = 0;
  105. byte++;
  106. continue;
  107. }
  108. if (((*byte >> bit) & GFS2_BIT_MASK) == old_state)
  109. return blk;
  110. bit += GFS2_BIT_SIZE;
  111. if (bit >= 8) {
  112. bit = 0;
  113. byte++;
  114. }
  115. blk++;
  116. }
  117. return BFITNOENT;
  118. }
  119. /**
  120. * gfs2_bitcount - count the number of bits in a certain state
  121. * @buffer: the buffer that holds the bitmaps
  122. * @buflen: the length (in bytes) of the buffer
  123. * @state: the state of the block we're looking for
  124. *
  125. * Returns: The number of bits
  126. */
  127. uint32_t gfs2_bitcount(struct gfs2_rgrpd *rgd, unsigned char *buffer,
  128. unsigned int buflen, unsigned char state)
  129. {
  130. unsigned char *byte = buffer;
  131. unsigned char *end = buffer + buflen;
  132. unsigned char state1 = state << 2;
  133. unsigned char state2 = state << 4;
  134. unsigned char state3 = state << 6;
  135. uint32_t count = 0;
  136. for (; byte < end; byte++) {
  137. if (((*byte) & 0x03) == state)
  138. count++;
  139. if (((*byte) & 0x0C) == state1)
  140. count++;
  141. if (((*byte) & 0x30) == state2)
  142. count++;
  143. if (((*byte) & 0xC0) == state3)
  144. count++;
  145. }
  146. return count;
  147. }