shithub: opus

Download patch

ref: 94a4989cdbb07e310d3e9486fa3e81a8b2e68bf9
parent: 367c39486618fe6a6f9ffe85e834d59cae241253
author: Jean-Marc Valin <[email protected]>
date: Thu Apr 12 12:35:19 EDT 2012

Makes silk_ADD_SAT32() conform to the C standard

This changes the saturation test to ensure that it relies on the
unsigned overflow behaviour (which is allowed) rather than the signed
overflow behaviour (which is undefined).

--- a/silk/MacroDebug.h
+++ b/silk/MacroDebug.h
@@ -98,7 +98,7 @@
 #undef silk_ADD_SAT32
 static inline opus_int32 silk_ADD_SAT32(opus_int32 a32, opus_int32 b32){
     opus_int32 res;
-    res =    ((((a32) + (b32)) & 0x80000000) == 0 ?                                   \
+    res =    ((((opus_uint32)(a32) + (opus_uint32)(b32)) & 0x80000000) == 0 ?                                   \
             ((((a32) & (b32)) & 0x80000000) != 0 ? silk_int32_MIN : (a32)+(b32)) :    \
             ((((a32) | (b32)) & 0x80000000) == 0 ? silk_int32_MAX : (a32)+(b32)) );
     silk_assert( res == silk_SAT32( (opus_int64)a32 + (opus_int64)b32 ) );
@@ -133,7 +133,7 @@
 #undef silk_SUB_SAT32
 static inline opus_int32 silk_SUB_SAT32( opus_int32 a32, opus_int32 b32 ) {
     opus_int32 res;
-    res =     ((((a32)-(b32)) & 0x80000000) == 0 ?                                           \
+    res =     ((((opus_uint32)(a32)-(opus_uint32)(b32)) & 0x80000000) == 0 ?                                           \
             (( (a32) & ((b32)^0x80000000) & 0x80000000) ? silk_int32_MIN : (a32)-(b32)) :    \
             ((((a32)^0x80000000) & (b32)  & 0x80000000) ? silk_int32_MAX : (a32)-(b32)) );
     silk_assert( res == silk_SAT32( (opus_int64)a32 - (opus_int64)b32 ) );
--- a/silk/macros.h
+++ b/silk/macros.h
@@ -68,11 +68,11 @@
 #define silk_SMLAWW(a32, b32, c32)       silk_MLA(silk_SMLAWB((a32), (b32), (c32)), (b32), silk_RSHIFT_ROUND((c32), 16))
 
 /* add/subtract with output saturated */
-#define silk_ADD_SAT32(a, b)             ((((a) + (b)) & 0x80000000) == 0 ?                              \
+#define silk_ADD_SAT32(a, b)             ((((opus_uint32)(a) + (opus_uint32)(b)) & 0x80000000) == 0 ?                              \
                                         ((((a) & (b)) & 0x80000000) != 0 ? silk_int32_MIN : (a)+(b)) :   \
                                         ((((a) | (b)) & 0x80000000) == 0 ? silk_int32_MAX : (a)+(b)) )
 
-#define silk_SUB_SAT32(a, b)             ((((a)-(b)) & 0x80000000) == 0 ?                                        \
+#define silk_SUB_SAT32(a, b)             ((((opus_uint32)(a)-(opus_uint32)(b)) & 0x80000000) == 0 ?                                        \
                                         (( (a) & ((b)^0x80000000) & 0x80000000) ? silk_int32_MIN : (a)-(b)) :    \
                                         ((((a)^0x80000000) & (b)  & 0x80000000) ? silk_int32_MAX : (a)-(b)) )