[alsa-devel] [PATCH 02/24] ALSA: ctl: add serializer/deserializer of 'elem_list' structure for 32bit ABI compatibility

Takashi Sakamoto o-takashi at sakamocchi.jp
Sat Nov 25 10:19:44 CET 2017


A 'snd_ctl_elem_list' structure includes a member of 'pointer' type.
A machine type for the type is known to have different size and alignment
between System V ABIs for architectures which adopts 'ILP32' or 'LP64'
data model.

This commit adds a pair of serializer and deserializer to convert data
between different layout of the structure on the ABIs.

Signed-off-by: Takashi Sakamoto <o-takashi at sakamocchi.jp>
---
 sound/core/control_compat.c | 82 +++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 82 insertions(+)

diff --git a/sound/core/control_compat.c b/sound/core/control_compat.c
index dec89717d8e3..3bd04ef5d221 100644
--- a/sound/core/control_compat.c
+++ b/sound/core/control_compat.c
@@ -23,6 +23,88 @@
 #include <linux/compat.h>
 #include <linux/slab.h>
 
+/*
+ * In this file, System V ABIs for any 64 bit architecture are assumed:
+ *  - Machine type for storage class of 1 byte has:
+ *    - size: 1 byte
+ *    - alignment: 1 byte
+ *  - Machine type for storage class of 2 bytes has:
+ *    - size: 2 bytes
+ *    - alignment: 2 bytes
+ *  - Machine type for storage class of 4 bytes has:
+ *    - size: 4 bytes
+ *    - alignment: 4 bytes
+ *  - Machine type for storage class of 8 bytes has:
+ *    - size: 8 bytes
+ *    - alignment: 8 bytes
+ *
+ * And System V ABIs for modern 32 bit architecture are assumed to have the same
+ * rule about size and alignment as the above machine types.
+ *
+ * As an exception, System V ABI for i386 architecture is assumed:
+ *  - Machine type for storage class of 8 bytes has:
+ *    - size: 8 bytes
+ *    - alignment: 4 bytes
+ *
+ * Any System V ABIs are assumed to have the same rule for aggregates, unions
+ * and alignment of members with bitfields. Additionally, 'packed' of attribute
+ * is a hint for compiles to remove internal and tail paddings even if bitfields
+ * are used.
+ */
+
+/*
+ * In any System V ABI for 32 bit architecture, the maximum length of members on
+ * this structure is 4 bytes. This member has 4 byte alignment and the size of
+ * this structure is multiples of 4 bytes, equals to 72 bytes. However, total
+ * size of all members is 70 bytes. As a result, 2 bytes are added as padding in
+ * the end.
+ */
+struct snd_ctl_elem_list_32 {
+	u32 offset;
+	u32 space;
+	u32 used;
+	u32 count;
+	u32 pids;		/* pointer on ILP32. */
+	u8 reserved[50];
+	u8 padding[2];
+} __packed;
+
+static int deserialize_from_elem_list_32(struct snd_ctl_file *ctl_file,
+					 void *dst, void *src)
+{
+	struct snd_ctl_elem_list *data = dst;
+	struct snd_ctl_elem_list_32 *data32 = src;
+
+	data->offset = data32->offset;
+	data->space = data32->space;
+	data->used = data32->used;
+	data->count = data32->count;
+
+	data->pids = (struct snd_ctl_elem_id __user *)compat_ptr(data32->pids);
+
+	memcpy(data->reserved, data32->reserved, sizeof(data->reserved));
+
+	return 0;
+}
+
+static int serialize_to_elem_list_32(struct snd_ctl_file *ctl_file, void *dst,
+				     void *src)
+{
+	struct snd_ctl_elem_list_32 *data32 = dst;
+	struct snd_ctl_elem_list *data = src;
+
+	data32->offset = data->offset;
+	data32->space = data->space;
+	data32->used = data->used;
+	data32->count = data->count;
+
+	data32->pids = (u32)ptr_to_compat(data->pids);
+
+	memcpy(data32->reserved, data->reserved, sizeof(data32->reserved));
+
+	return 0;
+}
+
 struct snd_ctl_elem_list32 {
 	u32 offset;
 	u32 space;
-- 
2.14.1



More information about the Alsa-devel mailing list