|
@@ -70,24 +70,19 @@ static const struct fixed31_32 dc_fixpt_ln2_div_2 = { 1488522236LL };
|
|
|
* @brief
|
|
|
* result = numerator / denominator
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_from_fraction(
|
|
|
- long long numerator,
|
|
|
- long long denominator);
|
|
|
+struct fixed31_32 dc_fixpt_from_fraction(long long numerator, long long denominator);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_from_int_nonconst(long long arg);
|
|
|
-static inline struct fixed31_32 dc_fixpt_from_int(long long arg)
|
|
|
+static inline struct fixed31_32 dc_fixpt_from_int(int arg)
|
|
|
{
|
|
|
- if (__builtin_constant_p(arg)) {
|
|
|
- struct fixed31_32 res;
|
|
|
- BUILD_BUG_ON((LONG_MIN > arg) || (arg > LONG_MAX));
|
|
|
- res.value = arg << FIXED31_32_BITS_PER_FRACTIONAL_PART;
|
|
|
- return res;
|
|
|
- } else
|
|
|
- return dc_fixpt_from_int_nonconst(arg);
|
|
|
+ struct fixed31_32 res;
|
|
|
+
|
|
|
+ res.value = (long long) arg << FIXED31_32_BITS_PER_FRACTIONAL_PART;
|
|
|
+
|
|
|
+ return res;
|
|
|
}
|
|
|
|
|
|
/*
|
|
@@ -129,8 +124,7 @@ static inline struct fixed31_32 dc_fixpt_abs(struct fixed31_32 arg)
|
|
|
* @brief
|
|
|
* result = arg1 < arg2
|
|
|
*/
|
|
|
-static inline bool dc_fixpt_lt(struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2)
|
|
|
+static inline bool dc_fixpt_lt(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
{
|
|
|
return arg1.value < arg2.value;
|
|
|
}
|
|
@@ -139,8 +133,7 @@ static inline bool dc_fixpt_lt(struct fixed31_32 arg1,
|
|
|
* @brief
|
|
|
* result = arg1 <= arg2
|
|
|
*/
|
|
|
-static inline bool dc_fixpt_le(struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2)
|
|
|
+static inline bool dc_fixpt_le(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
{
|
|
|
return arg1.value <= arg2.value;
|
|
|
}
|
|
@@ -149,8 +142,7 @@ static inline bool dc_fixpt_le(struct fixed31_32 arg1,
|
|
|
* @brief
|
|
|
* result = arg1 == arg2
|
|
|
*/
|
|
|
-static inline bool dc_fixpt_eq(struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2)
|
|
|
+static inline bool dc_fixpt_eq(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
{
|
|
|
return arg1.value == arg2.value;
|
|
|
}
|
|
@@ -159,8 +151,7 @@ static inline bool dc_fixpt_eq(struct fixed31_32 arg1,
|
|
|
* @brief
|
|
|
* result = min(arg1, arg2) := (arg1 <= arg2) ? arg1 : arg2
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_min(struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_min(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
{
|
|
|
if (arg1.value <= arg2.value)
|
|
|
return arg1;
|
|
@@ -172,8 +163,7 @@ static inline struct fixed31_32 dc_fixpt_min(struct fixed31_32 arg1,
|
|
|
* @brief
|
|
|
* result = max(arg1, arg2) := (arg1 <= arg2) ? arg2 : arg1
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_max(struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_max(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
{
|
|
|
if (arg1.value <= arg2.value)
|
|
|
return arg2;
|
|
@@ -209,17 +199,23 @@ static inline struct fixed31_32 dc_fixpt_clamp(
|
|
|
* @brief
|
|
|
* result = arg << shift
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_shl(
|
|
|
- struct fixed31_32 arg,
|
|
|
- unsigned char shift);
|
|
|
+static inline struct fixed31_32 dc_fixpt_shl(struct fixed31_32 arg, unsigned char shift)
|
|
|
+{
|
|
|
+ struct fixed31_32 res;
|
|
|
+
|
|
|
+ ASSERT(((arg.value >= 0) && (arg.value <= LLONG_MAX >> shift)) ||
|
|
|
+ ((arg.value < 0) && (arg.value >= LLONG_MIN >> shift)));
|
|
|
+
|
|
|
+ res.value = arg.value << shift;
|
|
|
+
|
|
|
+ return res;
|
|
|
+}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg >> shift
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_shr(
|
|
|
- struct fixed31_32 arg,
|
|
|
- unsigned char shift)
|
|
|
+static inline struct fixed31_32 dc_fixpt_shr(struct fixed31_32 arg, unsigned char shift)
|
|
|
{
|
|
|
struct fixed31_32 res;
|
|
|
res.value = arg.value >> shift;
|
|
@@ -235,38 +231,50 @@ static inline struct fixed31_32 dc_fixpt_shr(
|
|
|
* @brief
|
|
|
* result = arg1 + arg2
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_add(
|
|
|
- struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2);
|
|
|
+static inline struct fixed31_32 dc_fixpt_add(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
+{
|
|
|
+ struct fixed31_32 res;
|
|
|
+
|
|
|
+ ASSERT(((arg1.value >= 0) && (LLONG_MAX - arg1.value >= arg2.value)) ||
|
|
|
+ ((arg1.value < 0) && (LLONG_MIN - arg1.value <= arg2.value)));
|
|
|
+
|
|
|
+ res.value = arg1.value + arg2.value;
|
|
|
+
|
|
|
+ return res;
|
|
|
+}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg1 + arg2
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_add_int(struct fixed31_32 arg1,
|
|
|
- int arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_add_int(struct fixed31_32 arg1, int arg2)
|
|
|
{
|
|
|
- return dc_fixpt_add(arg1,
|
|
|
- dc_fixpt_from_int(arg2));
|
|
|
+ return dc_fixpt_add(arg1, dc_fixpt_from_int(arg2));
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg1 - arg2
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_sub(
|
|
|
- struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2);
|
|
|
+static inline struct fixed31_32 dc_fixpt_sub(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
+{
|
|
|
+ struct fixed31_32 res;
|
|
|
+
|
|
|
+ ASSERT(((arg2.value >= 0) && (LLONG_MIN + arg2.value <= arg1.value)) ||
|
|
|
+ ((arg2.value < 0) && (LLONG_MAX + arg2.value >= arg1.value)));
|
|
|
+
|
|
|
+ res.value = arg1.value - arg2.value;
|
|
|
+
|
|
|
+ return res;
|
|
|
+}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg1 - arg2
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_sub_int(struct fixed31_32 arg1,
|
|
|
- int arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_sub_int(struct fixed31_32 arg1, int arg2)
|
|
|
{
|
|
|
- return dc_fixpt_sub(arg1,
|
|
|
- dc_fixpt_from_int(arg2));
|
|
|
+ return dc_fixpt_sub(arg1, dc_fixpt_from_int(arg2));
|
|
|
}
|
|
|
|
|
|
|
|
@@ -279,49 +287,40 @@ static inline struct fixed31_32 dc_fixpt_sub_int(struct fixed31_32 arg1,
|
|
|
* @brief
|
|
|
* result = arg1 * arg2
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_mul(
|
|
|
- struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2);
|
|
|
+struct fixed31_32 dc_fixpt_mul(struct fixed31_32 arg1, struct fixed31_32 arg2);
|
|
|
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg1 * arg2
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_mul_int(struct fixed31_32 arg1,
|
|
|
- int arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_mul_int(struct fixed31_32 arg1, int arg2)
|
|
|
{
|
|
|
- return dc_fixpt_mul(arg1,
|
|
|
- dc_fixpt_from_int(arg2));
|
|
|
+ return dc_fixpt_mul(arg1, dc_fixpt_from_int(arg2));
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = square(arg) := arg * arg
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_sqr(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_sqr(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg1 / arg2
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_div_int(struct fixed31_32 arg1,
|
|
|
- long long arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_div_int(struct fixed31_32 arg1, long long arg2)
|
|
|
{
|
|
|
- return dc_fixpt_from_fraction(arg1.value,
|
|
|
- dc_fixpt_from_int(arg2).value);
|
|
|
+ return dc_fixpt_from_fraction(arg1.value, dc_fixpt_from_int(arg2).value);
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = arg1 / arg2
|
|
|
*/
|
|
|
-static inline struct fixed31_32 dc_fixpt_div(struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2)
|
|
|
+static inline struct fixed31_32 dc_fixpt_div(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
{
|
|
|
- return dc_fixpt_from_fraction(arg1.value,
|
|
|
- arg2.value);
|
|
|
+ return dc_fixpt_from_fraction(arg1.value, arg2.value);
|
|
|
}
|
|
|
|
|
|
/*
|
|
@@ -336,8 +335,7 @@ static inline struct fixed31_32 dc_fixpt_div(struct fixed31_32 arg1,
|
|
|
* @note
|
|
|
* No special actions taken in case argument is zero.
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_recip(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_recip(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -352,8 +350,7 @@ struct fixed31_32 dc_fixpt_recip(
|
|
|
* Argument specified in radians,
|
|
|
* internally it's normalized to [-2pi...2pi] range.
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_sinc(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_sinc(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -363,8 +360,7 @@ struct fixed31_32 dc_fixpt_sinc(
|
|
|
* Argument specified in radians,
|
|
|
* internally it's normalized to [-2pi...2pi] range.
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_sin(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_sin(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -376,8 +372,7 @@ struct fixed31_32 dc_fixpt_sin(
|
|
|
* passing arguments outside that range
|
|
|
* will cause incorrect result!
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_cos(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_cos(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -391,8 +386,7 @@ struct fixed31_32 dc_fixpt_cos(
|
|
|
* @note
|
|
|
* Currently, function is verified for abs(arg) <= 1.
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_exp(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_exp(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -404,8 +398,7 @@ struct fixed31_32 dc_fixpt_exp(
|
|
|
* Currently, no special actions taken
|
|
|
* in case of invalid argument(s). Take care!
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_log(
|
|
|
- struct fixed31_32 arg);
|
|
|
+struct fixed31_32 dc_fixpt_log(struct fixed31_32 arg);
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -419,9 +412,13 @@ struct fixed31_32 dc_fixpt_log(
|
|
|
* @note
|
|
|
* Currently, abs(arg1) should be less than 1. Take care!
|
|
|
*/
|
|
|
-struct fixed31_32 dc_fixpt_pow(
|
|
|
- struct fixed31_32 arg1,
|
|
|
- struct fixed31_32 arg2);
|
|
|
+static inline struct fixed31_32 dc_fixpt_pow(struct fixed31_32 arg1, struct fixed31_32 arg2)
|
|
|
+{
|
|
|
+ return dc_fixpt_exp(
|
|
|
+ dc_fixpt_mul(
|
|
|
+ dc_fixpt_log(arg1),
|
|
|
+ arg2));
|
|
|
+}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
@@ -432,22 +429,56 @@ struct fixed31_32 dc_fixpt_pow(
|
|
|
* @brief
|
|
|
* result = floor(arg) := greatest integer lower than or equal to arg
|
|
|
*/
|
|
|
-int dc_fixpt_floor(
|
|
|
- struct fixed31_32 arg);
|
|
|
+static inline int dc_fixpt_floor(struct fixed31_32 arg)
|
|
|
+{
|
|
|
+ unsigned long long arg_value = arg.value > 0 ? arg.value : -arg.value;
|
|
|
+
|
|
|
+ if (arg.value >= 0)
|
|
|
+ return (int)(arg_value >> FIXED31_32_BITS_PER_FRACTIONAL_PART);
|
|
|
+ else
|
|
|
+ return -(int)(arg_value >> FIXED31_32_BITS_PER_FRACTIONAL_PART);
|
|
|
+}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = round(arg) := integer nearest to arg
|
|
|
*/
|
|
|
-int dc_fixpt_round(
|
|
|
- struct fixed31_32 arg);
|
|
|
+static inline int dc_fixpt_round(struct fixed31_32 arg)
|
|
|
+{
|
|
|
+ unsigned long long arg_value = arg.value > 0 ? arg.value : -arg.value;
|
|
|
+
|
|
|
+ const long long summand = dc_fixpt_half.value;
|
|
|
+
|
|
|
+ ASSERT(LLONG_MAX - (long long)arg_value >= summand);
|
|
|
+
|
|
|
+ arg_value += summand;
|
|
|
+
|
|
|
+ if (arg.value >= 0)
|
|
|
+ return (int)(arg_value >> FIXED31_32_BITS_PER_FRACTIONAL_PART);
|
|
|
+ else
|
|
|
+ return -(int)(arg_value >> FIXED31_32_BITS_PER_FRACTIONAL_PART);
|
|
|
+}
|
|
|
|
|
|
/*
|
|
|
* @brief
|
|
|
* result = ceil(arg) := lowest integer greater than or equal to arg
|
|
|
*/
|
|
|
-int dc_fixpt_ceil(
|
|
|
- struct fixed31_32 arg);
|
|
|
+static inline int dc_fixpt_ceil(struct fixed31_32 arg)
|
|
|
+{
|
|
|
+ unsigned long long arg_value = arg.value > 0 ? arg.value : -arg.value;
|
|
|
+
|
|
|
+ const long long summand = dc_fixpt_one.value -
|
|
|
+ dc_fixpt_epsilon.value;
|
|
|
+
|
|
|
+ ASSERT(LLONG_MAX - (long long)arg_value >= summand);
|
|
|
+
|
|
|
+ arg_value += summand;
|
|
|
+
|
|
|
+ if (arg.value >= 0)
|
|
|
+ return (int)(arg_value >> FIXED31_32_BITS_PER_FRACTIONAL_PART);
|
|
|
+ else
|
|
|
+ return -(int)(arg_value >> FIXED31_32_BITS_PER_FRACTIONAL_PART);
|
|
|
+}
|
|
|
|
|
|
/* the following two function are used in scaler hw programming to convert fixed
|
|
|
* point value to format 2 bits from integer part and 19 bits from fractional
|
|
@@ -455,20 +486,14 @@ int dc_fixpt_ceil(
|
|
|
* fractional
|
|
|
*/
|
|
|
|
|
|
-unsigned int dc_fixpt_u2d19(
|
|
|
- struct fixed31_32 arg);
|
|
|
-
|
|
|
-unsigned int dc_fixpt_u0d19(
|
|
|
- struct fixed31_32 arg);
|
|
|
+unsigned int dc_fixpt_u2d19(struct fixed31_32 arg);
|
|
|
|
|
|
+unsigned int dc_fixpt_u0d19(struct fixed31_32 arg);
|
|
|
|
|
|
-unsigned int dc_fixpt_clamp_u0d14(
|
|
|
- struct fixed31_32 arg);
|
|
|
+unsigned int dc_fixpt_clamp_u0d14(struct fixed31_32 arg);
|
|
|
|
|
|
-unsigned int dc_fixpt_clamp_u0d10(
|
|
|
- struct fixed31_32 arg);
|
|
|
+unsigned int dc_fixpt_clamp_u0d10(struct fixed31_32 arg);
|
|
|
|
|
|
-int dc_fixpt_s4d19(
|
|
|
- struct fixed31_32 arg);
|
|
|
+int dc_fixpt_s4d19(struct fixed31_32 arg);
|
|
|
|
|
|
#endif
|