summary refs log tree commit diff
path: root/shared/nm-utils/nm-macros-internal.h
diff options
context:
space:
mode:
authorMichael Biebl <biebl@debian.org>2017-12-12 15:53:07 +0100
committerMichael Biebl <biebl@debian.org>2017-12-12 15:53:07 +0100
commitafcd268ea7b1149fbfb66bce4eca659b675da0a2 (patch)
treec3fca2203ad17434daf3ccf576582bd66aa41ab2 /shared/nm-utils/nm-macros-internal.h
parent417f6015c3dc8c47cf27daa59f64e0e36c521b9c (diff)
New upstream version 1.10.2 upstream/1.10.2
Diffstat (limited to 'shared/nm-utils/nm-macros-internal.h')
-rw-r--r--shared/nm-utils/nm-macros-internal.h182
1 files changed, 127 insertions, 55 deletions
diff --git a/shared/nm-utils/nm-macros-internal.h b/shared/nm-utils/nm-macros-internal.h
index d9dab83d..5bd9eac4 100644
--- a/shared/nm-utils/nm-macros-internal.h
+++ b/shared/nm-utils/nm-macros-internal.h
@@ -263,33 +263,117 @@ NM_G_ERROR_MSG (GError *error)
 
 /*****************************************************************************/
 
-#if (defined (__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 9 ))) || (defined (__clang__))
+#ifndef _NM_CC_SUPPORT_AUTO_TYPE
+#if (defined (__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 9 )))
+#define _NM_CC_SUPPORT_AUTO_TYPE 1
+#else
+#define _NM_CC_SUPPORT_AUTO_TYPE 0
+#endif
+#endif
+
+#ifndef _NM_CC_SUPPORT_GENERIC
+#if (defined (__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 9 ))) || (defined (__clang__))
 #define _NM_CC_SUPPORT_GENERIC 1
 #else
 #define _NM_CC_SUPPORT_GENERIC 0
 #endif
+#endif
+
+#if _NM_CC_SUPPORT_AUTO_TYPE
+#define _nm_auto_type __auto_type
+#endif
 
 #if _NM_CC_SUPPORT_GENERIC
-#define _NM_CONSTCAST(type, obj) \
-	(_Generic ((obj), \
-	           void *           : ((type *) (obj)), \
-	           void *const      : ((type *) (obj)), \
-	           const void *     : ((const type *) (obj)), \
-	           const void *const: ((const type *) (obj)), \
-	           const type *     : (obj), \
-	           const type *const: (obj), \
-	           type *           : (obj), \
-	           type *const      : (obj)))
+#define _NM_CONSTCAST_FULL_1(type, obj_expr, obj) \
+	(_Generic ((obj_expr), \
+	           const void        *const: ((const type *) (obj)), \
+	           const void        *     : ((const type *) (obj)), \
+	                 void        *const: ((      type *) (obj)), \
+	                 void        *     : ((      type *) (obj)), \
+	           const type        *const: ((const type *) (obj)), \
+	           const type        *     : ((const type *) (obj)), \
+	                 type        *const: ((      type *) (obj)), \
+	                 type        *     : ((      type *) (obj))))
+#define _NM_CONSTCAST_FULL_2(type, obj_expr, obj, alias_type2) \
+	(_Generic ((obj_expr), \
+	           const void        *const: ((const type *) (obj)), \
+	           const void        *     : ((const type *) (obj)), \
+	                 void        *const: ((      type *) (obj)), \
+	                 void        *     : ((      type *) (obj)), \
+	           const alias_type2 *const: ((const type *) (obj)), \
+	           const alias_type2 *     : ((const type *) (obj)), \
+	                 alias_type2 *const: ((      type *) (obj)), \
+	                 alias_type2 *     : ((      type *) (obj)), \
+	           const type        *const: ((const type *) (obj)), \
+	           const type        *     : ((const type *) (obj)), \
+	                 type        *const: ((      type *) (obj)), \
+	                 type        *     : ((      type *) (obj))))
+#define _NM_CONSTCAST_FULL_3(type, obj_expr, obj, alias_type2, alias_type3) \
+	(_Generic ((obj_expr), \
+	           const void        *const: ((const type *) (obj)), \
+	           const void        *     : ((const type *) (obj)), \
+	                 void        *const: ((      type *) (obj)), \
+	                 void        *     : ((      type *) (obj)), \
+	           const alias_type2 *const: ((const type *) (obj)), \
+	           const alias_type2 *     : ((const type *) (obj)), \
+	                 alias_type2 *const: ((      type *) (obj)), \
+	                 alias_type2 *     : ((      type *) (obj)), \
+	           const alias_type3 *const: ((const type *) (obj)), \
+	           const alias_type3 *     : ((const type *) (obj)), \
+	                 alias_type3 *const: ((      type *) (obj)), \
+	                 alias_type3 *     : ((      type *) (obj)), \
+	           const type        *const: ((const type *) (obj)), \
+	           const type        *     : ((const type *) (obj)), \
+	                 type        *const: ((      type *) (obj)), \
+	                 type        *     : ((      type *) (obj))))
+#define _NM_CONSTCAST_FULL_4(type, obj_expr, obj, alias_type2, alias_type3, alias_type4) \
+	(_Generic ((obj_expr), \
+	           const void        *const: ((const type *) (obj)), \
+	           const void        *     : ((const type *) (obj)), \
+	                 void        *const: ((      type *) (obj)), \
+	                 void        *     : ((      type *) (obj)), \
+	           const alias_type2 *const: ((const type *) (obj)), \
+	           const alias_type2 *     : ((const type *) (obj)), \
+	                 alias_type2 *const: ((      type *) (obj)), \
+	                 alias_type2 *     : ((      type *) (obj)), \
+	           const alias_type3 *const: ((const type *) (obj)), \
+	           const alias_type3 *     : ((const type *) (obj)), \
+	                 alias_type3 *const: ((      type *) (obj)), \
+	                 alias_type3 *     : ((      type *) (obj)), \
+	           const alias_type4 *const: ((const type *) (obj)), \
+	           const alias_type4 *     : ((const type *) (obj)), \
+	                 alias_type4 *const: ((      type *) (obj)), \
+	                 alias_type4 *     : ((      type *) (obj)), \
+	           const type        *const: ((const type *) (obj)), \
+	           const type        *     : ((const type *) (obj)), \
+	                 type        *const: ((      type *) (obj)), \
+	                 type        *     : ((      type *) (obj))))
+#define _NM_CONSTCAST_FULL_x(type, obj_expr, obj, n, ...)   (_NM_CONSTCAST_FULL_##n (type, obj_expr, obj,                        ##__VA_ARGS__))
+#define _NM_CONSTCAST_FULL_y(type, obj_expr, obj, n, ...)   (_NM_CONSTCAST_FULL_x   (type, obj_expr, obj, n,                     ##__VA_ARGS__))
+#define NM_CONSTCAST_FULL(   type, obj_expr, obj,    ...)   (_NM_CONSTCAST_FULL_y   (type, obj_expr, obj, NM_NARG (dummy, ##__VA_ARGS__), ##__VA_ARGS__))
 #else
-/* _NM_CONSTCAST() is there to preserve constness of a pointer.
- * It uses C11's _Generic(). If that is not supported, we fall back
- * to casting away constness. So, with _Generic, we get some additional
- * static type checking by preserving constness, without, we cast it
- * to a non-const pointer. */
-#define _NM_CONSTCAST(type, obj) \
-	((type *) (obj))
+#define NM_CONSTCAST_FULL(   type, obj_expr, obj,    ...)   ((type *) (obj))
 #endif
 
+#define NM_CONSTCAST(type, obj, ...) \
+	NM_CONSTCAST_FULL(type, (obj), (obj), ##__VA_ARGS__)
+
+#define NM_GOBJECT_CAST(type, obj, is_check, ...) \
+	({ \
+		const void *_obj = (obj); \
+		\
+		nm_assert (_obj || (is_check (_obj))); \
+		NM_CONSTCAST_FULL (type, (obj), _obj, GObject, ##__VA_ARGS__); \
+	})
+
+#define NM_GOBJECT_CAST_NON_NULL(type, obj, is_check, ...) \
+	({ \
+		const void *_obj = (obj); \
+		\
+		nm_assert (is_check (_obj)); \
+		NM_CONSTCAST_FULL (type, (obj), _obj, GObject, ##__VA_ARGS__); \
+	})
+
 #if _NM_CC_SUPPORT_GENERIC
 /* returns @value, if the type of @value matches @type.
  * This requires support for C11 _Generic(). If no support is
@@ -302,6 +386,16 @@ NM_G_ERROR_MSG (GError *error)
 #define _NM_ENSURE_TYPE(type, value) (value)
 #endif
 
+#if _NM_CC_SUPPORT_GENERIC
+#define NM_PROPAGATE_CONST(test_expr, ptr) \
+	(_Generic ((test_expr), \
+	           const typeof (*(test_expr)) *: ((const typeof (*(ptr)) *) (ptr)), \
+	                                 default: (_Generic ((test_expr), \
+	                                                     typeof (*(test_expr)) *: (ptr)))))
+#else
+#define NM_PROPAGATE_CONST(test_expr, ptr) (ptr)
+#endif
+
 /*****************************************************************************/
 
 #define _NM_IN_SET_EVAL_1( op, _x, y)           (_x == (y))
@@ -459,7 +553,7 @@ _NM_IN_STRSET_streq (const char *x, const char *s)
 
 /* NM_CACHED_QUARK_FCN() is essentially the same as G_DEFINE_QUARK
  * with two differences:
- * - @string must be a quited string-literal
+ * - @string must be a quoted string-literal
  * - @fcn must be the full function name, while G_DEFINE_QUARK() appends
  *   "_quark" to the function name.
  * Both properties of G_DEFINE_QUARK() are non favorable, because you can no
@@ -581,39 +675,17 @@ _notify (obj_type *obj, _PropertyEnums prop) \
 
 /*****************************************************************************/
 
-/* these are implemented as a macro, because they accept self
- * as both (type*) and (const type*), and return a const
- * private pointer accordingly. */
-#define __NM_GET_PRIVATE(self, type, is_check, addrop) \
-	({ \
-		/* preserve the const-ness of self. Unfortunately, that
-		 * way, @self cannot be a void pointer */ \
-		typeof (self) _self = (self); \
-		\
-		/* Get compiler error if variable is of wrong type */ \
-		_nm_unused const type *const _self2 = (_self); \
-		\
-		nm_assert (is_check (_self)); \
-		( addrop ( _NM_CONSTCAST (type, _self)->_priv) ); \
-	})
-
-#define _NM_GET_PRIVATE(self, type, is_check)     __NM_GET_PRIVATE(self, type, is_check, &)
-#define _NM_GET_PRIVATE_PTR(self, type, is_check) __NM_GET_PRIVATE(self, type, is_check,  )
-
-#define __NM_GET_PRIVATE_VOID(self, type, is_check, result_cmd) \
+#define _NM_GET_PRIVATE(self, type, is_check, ...) (&(NM_GOBJECT_CAST_NON_NULL (type, (self), is_check, ##__VA_ARGS__)->_priv))
+#if _NM_CC_SUPPORT_AUTO_TYPE
+#define _NM_GET_PRIVATE_PTR(self, type, is_check, ...) \
 	({ \
-		/* (self) can be any non-const pointer. It will be cast to "type *".
-		 * We don't explicitly cast but assign first to (void *) which
-		 * will fail if @self is pointing to const. */ \
-		void *const _self1 = (self); \
-		type *const _self = _self1; \
+		_nm_auto_type _self = NM_GOBJECT_CAST_NON_NULL (type, (self), is_check, ##__VA_ARGS__); \
 		\
-		nm_assert (is_check (_self)); \
-		( result_cmd ); \
+		NM_PROPAGATE_CONST (_self, _self->_priv); \
 	})
-
-#define _NM_GET_PRIVATE_VOID(self, type, is_check)     __NM_GET_PRIVATE_VOID(self, type, is_check, &_self->_priv)
-#define _NM_GET_PRIVATE_PTR_VOID(self, type, is_check) __NM_GET_PRIVATE_VOID(self, type, is_check,  _self->_priv)
+#else
+#define _NM_GET_PRIVATE_PTR(self, type, is_check, ...) (NM_GOBJECT_CAST_NON_NULL (type, (self), is_check, ##__VA_ARGS__)->_priv)
+#endif
 
 /*****************************************************************************/
 
@@ -625,6 +697,7 @@ nm_g_object_ref (gpointer obj)
 		g_object_ref (obj);
 	return obj;
 }
+#define nm_g_object_ref(obj) ((typeof (obj)) nm_g_object_ref (obj))
 
 static inline void
 nm_g_object_unref (gpointer obj)
@@ -1174,12 +1247,11 @@ nm_steal_fd (int *p_fd)
 static inline int
 nm_close (int fd)
 {
-	if (fd >= 0) {
-		if (close (fd) == 0)
-			return 0;
-		nm_assert (errno != EBADF);
-	}
-	return -1;
+	int r;
+
+	r = close (fd);
+	nm_assert (r != -1 || fd < 0 || errno != EBADF);
+	return r;
 }
 
 #endif /* __NM_MACROS_INTERNAL_H__ */