diff options
author | Stefano Babic <sbabic@denx.de> | 2014-03-05 12:51:26 +0100 |
---|---|---|
committer | Stefano Babic <sbabic@denx.de> | 2014-03-05 12:51:26 +0100 |
commit | 1ad6364eeb4f578e423081d1748e8a3fdf1ab01d (patch) | |
tree | f55731737edf1cfd653b21f2ff9d387e6c53ae24 /include/bitfield.h | |
parent | 335143c76612a0ae26eef8abeda77641d4f63b50 (diff) | |
parent | cc07294bc704694ae33db75b25ac557e5917a83f (diff) | |
download | u-boot-1ad6364eeb4f578e423081d1748e8a3fdf1ab01d.tar.gz |
Merge branch 'master' of git://git.denx.de/u-boot-arm
Diffstat (limited to 'include/bitfield.h')
-rw-r--r-- | include/bitfield.h | 58 |
1 files changed, 58 insertions, 0 deletions
diff --git a/include/bitfield.h b/include/bitfield.h new file mode 100644 index 0000000000..ec4815c8e0 --- /dev/null +++ b/include/bitfield.h @@ -0,0 +1,58 @@ +/* + * Copyright 2013 Broadcom Corporation. + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +/* + * Bitfield operations + * + * These are generic bitfield operations which allow manipulation of variable + * width bitfields within a word. One use of this would be to use data tables + * to determine how to reprogram fields within R/W hardware registers. + * + * Example: + * + * old_reg_val + * +--------+----+---+--+-----+----------+ + * | | | | | old | | + * +--------+----+---+--+-----+----------+ + * + * new_reg_val + * +--------+----+---+--+-----+----------+ + * | | | | | new | | + * +--------+----+---+--+-----+----------+ + * + * mask = bitfield_mask(10, 5); + * old = bitfield_extract(old_reg_val, 10, 5); + * new_reg_val = bitfield_replace(old_reg_val, 10, 5, new); + * + * The numbers 10 and 5 could for example come from data + * tables which describe all bitfields in all registers. + */ + +#include <linux/types.h> + +/* Produces a mask of set bits covering a range of a uint value */ +static inline uint bitfield_mask(uint shift, uint width) +{ + return ((1 << width) - 1) << shift; +} + +/* Extract the value of a bitfield found within a given register value */ +static inline uint bitfield_extract(uint reg_val, uint shift, uint width) +{ + return (reg_val & bitfield_mask(shift, width)) >> shift; +} + +/* + * Replace the value of a bitfield found within a given register value + * Returns the newly modified uint value with the replaced field. + */ +static inline uint bitfield_replace(uint reg_val, uint shift, uint width, + uint bitfield_val) +{ + uint mask = bitfield_mask(shift, width); + + return (reg_val & ~mask) | (bitfield_val << shift); +} |