source: mainline/generic/src/adt/bitmap.c@ bf56fef

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export 0.2.0
Last change on this file since bf56fef was 8b08cf3, checked in by Jakub Vana <jakub.vana@…>, 20 years ago

Bitmap functions patch

  • Property mode set to 100644
File size: 4.8 KB
Line 
1/*
2 * Copyright (C) 2006 Jakub Jermar
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29/**
30 * @file bitmap.c
31 * @brief Implementation of bitmap ADT.
32 *
33 * This file implements bitmap ADT and provides functions for
34 * setting and clearing ranges of bits.
35 */
36
37#include <adt/bitmap.h>
38#include <typedefs.h>
39#include <arch/types.h>
40#include <align.h>
41#include <debug.h>
42#include <macros.h>
43
44#define ALL_ONES 0xff
45#define ALL_ZEROES 0x00
46
47/** Initialize bitmap.
48 *
49 * No portion of the bitmap is set or cleared by this function.
50 *
51 * @param bitmap Bitmap structure.
52 * @param map Address of the memory used to hold the map.
53 * @param bits Number of bits stored in bitmap.
54 */
55void bitmap_initialize(bitmap_t *bitmap, __u8 *map, count_t bits)
56{
57 bitmap->map = map;
58 bitmap->bits = bits;
59}
60
61/** Set range of bits.
62 *
63 * @param bitmap Bitmap structure.
64 * @param start Starting bit.
65 * @param bits Number of bits to set.
66 */
67void bitmap_set_range(bitmap_t *bitmap, index_t start, count_t bits)
68{
69 index_t i=0;
70 index_t aligned_start;
71 count_t lub; /* leading unaligned bits */
72 count_t amb; /* aligned middle bits */
73 count_t tab; /* trailing aligned bits */
74
75 ASSERT(start + bits <= bitmap->bits);
76
77 aligned_start = ALIGN_UP(start, 8);
78 lub = min(aligned_start - start, bits);
79 amb = bits > lub ? bits - lub : 0;
80 tab = amb % 8;
81
82 if ( start + bits < aligned_start ) {
83 /*
84 * Set bits in the middle of byte
85 */
86 bitmap->map[start / 8] |= ((1 << lub)-1) << (start&7);
87 return;
88 }
89
90 if (lub) {
91 /*
92 * Make sure to set any leading unaligned bits.
93 */
94 bitmap->map[start / 8] |= ~((1 << (8 - lub)) - 1);
95 }
96 for (i = 0; i < amb / 8; i++) {
97 /*
98 * The middle bits can be set byte by byte.
99 */
100 bitmap->map[aligned_start / 8 + i] = ALL_ONES;
101 }
102 if (tab) {
103 /*
104 * Make sure to set any trailing aligned bits.
105 */
106 bitmap->map[aligned_start / 8 + i] |= (1 << tab) - 1;
107 }
108
109}
110
111/** Clear range of bits.
112 *
113 * @param bitmap Bitmap structure.
114 * @param start Starting bit.
115 * @param bits Number of bits to clear.
116 */
117void bitmap_clear_range(bitmap_t *bitmap, index_t start, count_t bits)
118{
119 index_t i=0;
120 index_t aligned_start;
121 count_t lub; /* leading unaligned bits */
122 count_t amb; /* aligned middle bits */
123 count_t tab; /* trailing aligned bits */
124
125 ASSERT(start + bits <= bitmap->bits);
126
127 aligned_start = ALIGN_UP(start, 8);
128 lub = min(aligned_start - start, bits);
129 amb = bits > lub ? bits - lub : 0;
130 tab = amb % 8;
131
132 if ( start + bits < aligned_start )
133 {
134 /*
135 * Set bits in the middle of byte
136 */
137 bitmap->map[start / 8] &= ~(((1 << lub)-1) << (start&7));
138 return;
139 }
140
141
142 if (lub) {
143 /*
144 * Make sure to clear any leading unaligned bits.
145 */
146 bitmap->map[start / 8] &= (1 << (8 - lub)) - 1;
147 }
148 for (i = 0; i < amb / 8; i++) {
149 /*
150 * The middle bits can be cleared byte by byte.
151 */
152 bitmap->map[aligned_start / 8 + i] = ALL_ZEROES;
153 }
154 if (tab) {
155 /*
156 * Make sure to clear any trailing aligned bits.
157 */
158 bitmap->map[aligned_start / 8 + i] &= ~((1 << tab) - 1);
159 }
160
161}
162
163/** Copy portion of one bitmap into another bitmap.
164 *
165 * @param dst Destination bitmap.
166 * @param src Source bitmap.
167 * @param bits Number of bits to copy.
168 */
169void bitmap_copy(bitmap_t *dst, bitmap_t *src, count_t bits)
170{
171 index_t i;
172
173 ASSERT(bits <= dst->bits);
174 ASSERT(bits <= src->bits);
175
176 for (i = 0; i < bits / 8; i++)
177 dst->map[i] = src->map[i];
178
179 if (bits % 8) {
180 bitmap_clear_range(dst, i * 8, bits % 8);
181 dst->map[i] |= src->map[i] & ((1 << (bits % 8)) - 1);
182 }
183}
Note: See TracBrowser for help on using the repository browser.