]> granicus.if.org Git - strace/commitdiff
Support C libraries without System V shared memory/ipc
authorMike Frysinger <vapier@gentoo.org>
Sat, 31 Oct 2015 04:47:53 +0000 (00:47 -0400)
committerDmitry V. Levin <ldv@altlinux.org>
Thu, 26 Nov 2015 01:36:58 +0000 (01:36 +0000)
Some systems (like Bionic) omit support for SysV related code.  That
means no C library headers for strace to include.  Add configure tests
to probe the headers from the kernel and use them when they are
available.

It might make more sense to never rely on the C library's headers as
there is no guarantee or requirement that the structure layout between
apps and the C library match that what is passed to the kernel.

* configure.ac (AC_CHECK_HEADERS): Check for linux/ipc.h,
linux/mqueue.h, linux/msg.h, linux/sem.h, linux/shm.h,
sys/ipc.h, sys/msg.h, sys/sem.h, and sys/shm.h.
* ipc_defs.h: Include <sys/ipc.h> or <linux/ipc.h> depending
on what is available.
* ipc_msg.c: Replace <sys/ipc.h> with "ipc_defs.h".
Fallback to <linux/msg.h> when available.
* ipc_msgctl.c: Include <sys/msg.h>, <asm/msgbuf.h>, or <linux/msg.h>
based on what is available.  Note missing support for old ipc structs.
* ipc_sem.c: Include <sys/sem.h> or <linux/sem.h> depending
on what is available.  Only decode sembuf when available.
* ipc_shm.c: Fallback to <linux/shm.h> when available.
* ipc_shmctl.c: Include <sys/shm.h>, <asm/shmbuf.h>, or <linux/shm.h>
based on what is available.  Note missing support for old ipc structs.
* print_mq_attr.c: Fallback to <linux/mqueue.h> when available.

configure.ac
ipc_defs.h
ipc_msg.c
ipc_msgctl.c
ipc_sem.c
ipc_shm.c
ipc_shmctl.c
print_mq_attr.c

index 9a1134e96d197dd5044575a7e08e2763131a47f8..286db29cd603dd2b1c59a336a563e1ed6b782d45 100644 (file)
@@ -269,10 +269,14 @@ AC_CHECK_HEADERS(m4_normalize([
        linux/filter.h
        linux/hiddev.h
        linux/ip_vs.h
+       linux/ipc.h
        linux/mmtimer.h
+       linux/msg.h
        linux/perf_event.h
        linux/seccomp.h
        linux/securebits.h
+       linux/sem.h
+       linux/shm.h
        linux/utsname.h
        mqueue.h
        netinet/sctp.h
@@ -283,11 +287,16 @@ AC_CHECK_HEADERS(m4_normalize([
        sys/eventfd.h
        sys/fanotify.h
        sys/ioctl.h
+       sys/ipc.h
+       sys/msg.h
        sys/reg.h
+       sys/sem.h
+       sys/shm.h
        sys/signalfd.h
        sys/vfs.h
        sys/xattr.h
 ]))
+AC_CHECK_HEADERS([linux/mqueue.h],,, [#include <linux/types.h>])
 AC_CHECK_HEADERS([linux/icmp.h linux/in6.h linux/netlink.h linux/if_packet.h],
                  [], [], [#include <stddef.h>
 #include <sys/socket.h>
index 31f7ab3185ebd30e8f43ad74407fed7498c3f150..b6c85c1aa53ca6f2501e9b7a2603eceb7286aeac 100644 (file)
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
-#include <sys/ipc.h>
+#ifdef HAVE_SYS_IPC_H
+# include <sys/ipc.h>
+#elif defined HAVE_LINUX_IPC_H
+# include <linux/ipc.h>
+/* While glibc uses __key, the kernel uses key. */
+# define __key key
+#endif
 
 #if !defined IPC_64
 # define IPC_64 0x100
index 55747cbb562773e79c132e981af291bcd5f60ba3..965e2e493e2b54c1fa9f55c94d4af9722edeb444 100644 (file)
--- a/ipc_msg.c
+++ b/ipc_msg.c
  */
 
 #include "defs.h"
+#include "ipc_defs.h"
 
-#include <sys/ipc.h>
-#include <sys/msg.h>
+#ifdef HAVE_SYS_MSG_H
+# include <sys/msg.h>
+#elif defined HAVE_LINUX_MSG_H
+# include <linux/msg.h>
+#endif
 
 #include "xlat/ipc_msg_flags.h"
 #include "xlat/resource_flags.h"
index a97dd1a1f6b01875eaf7a31d7a47192b6c56fb46..e46f6e2e5a723fa57dced8a433ccb52b3d6de2a0 100644 (file)
  */
 
 #include "defs.h"
-#include "ipc_defs.h"
 
-#include <sys/msg.h>
 #include DEF_MPERS_TYPE(msqid_ds_t)
+
+#include "ipc_defs.h"
+
+#ifdef HAVE_SYS_MSG_H
+/* The C library generally exports the struct the current kernel expects. */
+# include <sys/msg.h>
 typedef struct msqid_ds msqid_ds_t;
+#elif defined HAVE_LINUX_MSG_H
+/* The linux header might provide the right struct. */
+# include <linux/msg.h>
+typedef struct msqid64_ds msqid_ds_t;
+#endif
+
 #include MPERS_DEFS
 
 #include "xlat/msgctl_flags.h"
@@ -43,6 +53,7 @@ typedef struct msqid_ds msqid_ds_t;
 static void
 print_msqid_ds(struct tcb *tcp, const long addr, int cmd)
 {
+       /* TODO: We don't properly decode old compat ipc calls. */
        if (cmd & IPC_64)
                cmd &= ~IPC_64;
        msqid_ds_t msqid_ds;
index e98f8ef6aa2a6ea3c7c3cb6fe83300f05d8eb107..c7351ae84cb0ef89cd90d7f9eb6204d61f9f4898 100644 (file)
--- a/ipc_sem.c
+++ b/ipc_sem.c
 #include "defs.h"
 #include "ipc_defs.h"
 
-#include <sys/sem.h>
+#ifdef HAVE_SYS_SEM_H
+# include <sys/sem.h>
+#elif defined HAVE_LINUX_SEM_H
+# include <linux/sem.h>
+#endif
 
 #include "xlat/semctl_flags.h"
 #include "xlat/semop_flags.h"
 
+#if defined HAVE_SYS_SEM_H || defined HAVE_LINUX_SEM_H
 static void
 tprint_sembuf(const struct sembuf *sb)
 {
@@ -45,10 +50,12 @@ tprint_sembuf(const struct sembuf *sb)
        printflags(semop_flags, sb->sem_flg, "SEM_???");
        tprints("}");
 }
+#endif
 
 static void
 tprint_sembuf_array(struct tcb *tcp, const long addr, const unsigned long count)
 {
+#if defined HAVE_SYS_SEM_H || defined HAVE_LINUX_SEM_H
        unsigned long max_count;
        struct sembuf sb;
 
@@ -78,6 +85,9 @@ tprint_sembuf_array(struct tcb *tcp, const long addr, const unsigned long count)
 
                tprints("]");
        }
+#else
+       printaddr(addr);
+#endif
        tprintf(", %lu", count);
 }
 
index 4a41690a4f75c64c3c10d2dfef2544fb70026c6d..c418884a5b9223acc1c63f2d562a84b522a1c83f 100644 (file)
--- a/ipc_shm.c
+++ b/ipc_shm.c
 
 #include "defs.h"
 
-#include <sys/shm.h>
+#ifdef HAVE_SYS_SHM_H
+# include <sys/shm.h>
+#elif defined HAVE_LINUX_SHM_H
+# include <linux/shm.h>
+#endif
 
 #include "xlat/shm_resource_flags.h"
 #include "xlat/shm_flags.h"
index 4bd6c85ce4e56d45b35a83cd2c4abc94c3fbc8cd..3498455de370992e82d6f54b6ab092587d969f45 100644 (file)
  */
 
 #include "defs.h"
-#include "ipc_defs.h"
-
-#include <sys/shm.h>
 
 #include DEF_MPERS_TYPE(shmid_ds_t)
-#include <sys/shm.h>
+
+#include "ipc_defs.h"
+
+#ifdef HAVE_SYS_SHM_H
+/* The C library generally exports the struct the current kernel expects. */
+# include <sys/shm.h>
 typedef struct shmid_ds shmid_ds_t;
+#elif defined HAVE_LINUX_SHM_H
+/* The linux header might provide the right struct. */
+# include <linux/shm.h>
+typedef struct shmid64_ds shmid_ds_t;
+#endif
+
 #include MPERS_DEFS
 
 #include "xlat/shmctl_flags.h"
@@ -45,6 +53,7 @@ typedef struct shmid_ds shmid_ds_t;
 static void
 print_shmid_ds(struct tcb *tcp, const long addr, int cmd)
 {
+       /* TODO: We don't properly decode old compat ipc calls. */
        if (cmd & IPC_64)
                cmd &= ~IPC_64;
        shmid_ds_t shmid_ds;
index f9bff3429bdc56873cb0c979d68c557c17a2749d..a43d4376815e7b23c83cfbfada978e7c604df233 100644 (file)
 #include "defs.h"
 
 #include DEF_MPERS_TYPE(mq_attr_t)
+
 #ifdef HAVE_MQUEUE_H
 # include <mqueue.h>
 typedef struct mq_attr mq_attr_t;
+#elif defined HAVE_LINUX_MQUEUE_H
+# include <linux/types.h>
+# include <linux/mqueue.h>
+typedef struct mq_attr mq_attr_t;
 #endif
+
 #include MPERS_DEFS
 
 MPERS_PRINTER_DECL(void, printmqattr)(struct tcb *tcp, const long addr)
 {
-# ifndef HAVE_MQUEUE_H
-       printaddr(addr);
-# else
+#if defined HAVE_MQUEUE_H || defined HAVE_LINUX_MQUEUE_H
        mq_attr_t attr;
        if (umove_or_printaddr(tcp, addr, &attr))
                return;
@@ -48,5 +52,7 @@ MPERS_PRINTER_DECL(void, printmqattr)(struct tcb *tcp, const long addr)
        tprintf(", mq_maxmsg=%ld, mq_msgsize=%ld, mq_curmsg=%ld}",
                (long) attr.mq_maxmsg, (long) attr.mq_msgsize,
                (long) attr.mq_curmsgs);
-# endif
+#else
+       printaddr(addr);
+#endif
 }