diff --git a/SOURCES/file-5.33-floating-point-exception.patch b/SOURCES/file-5.33-floating-point-exception.patch
new file mode 100644
index 0000000..32415b4
--- /dev/null
+++ b/SOURCES/file-5.33-floating-point-exception.patch
@@ -0,0 +1,77 @@
+diff --git a/src/Makefile.am b/src/Makefile.am
+index a9b245d..c7f184d 100644
+--- a/src/Makefile.am
++++ b/src/Makefile.am
+@@ -17,10 +17,10 @@ MINGWLIBS = -lgnurx -lshlwapi
+ else
+ MINGWLIBS = 
+ endif
+-libmagic_la_LIBADD = $(LTLIBOBJS) $(MINGWLIBS)
++libmagic_la_LIBADD = -lm $(LTLIBOBJS) $(MINGWLIBS)
+ 
+ file_SOURCES = file.c seccomp.c
+-file_LDADD = libmagic.la
++file_LDADD = libmagic.la -lm
+ CLEANFILES = magic.h
+ EXTRA_DIST = magic.h.in
+ HDR= $(top_srcdir)/src/magic.h.in
+diff --git a/src/softmagic.c b/src/softmagic.c
+index 3e76517..57b4677 100644
+--- a/src/softmagic.c
++++ b/src/softmagic.c
+@@ -37,6 +37,7 @@ FILE_RCSID("@(#)$File: softmagic.c,v 1.259 2018/03/11 01:23:52 christos Exp $")
+ 
+ #include "magic.h"
+ #include <assert.h>
++#include <math.h>
+ #include <string.h>
+ #include <ctype.h>
+ #include <stdlib.h>
+@@ -1893,19 +1894,19 @@ magiccheck(struct magic_set *ms, struct magic *m)
+ 			break;
+ 
+ 		case '!':
+-			matched = fv != fl;
++			matched = isunordered(fl, fv) ? 1 : fv != fl;
+ 			break;
+ 
+ 		case '=':
+-			matched = fv == fl;
++			matched = isunordered(fl, fv) ? 0 : fv == fl;
+ 			break;
+ 
+ 		case '>':
+-			matched = fv > fl;
++			matched = isgreater(fv, fl);
+ 			break;
+ 
+ 		case '<':
+-			matched = fv < fl;
++			matched = isless(fv, fl);
+ 			break;
+ 
+ 		default:
+@@ -1926,19 +1927,19 @@ magiccheck(struct magic_set *ms, struct magic *m)
+ 			break;
+ 
+ 		case '!':
+-			matched = dv != dl;
++			matched = isunordered(dv, dl) ? 1 : dv != dl;
+ 			break;
+ 
+ 		case '=':
+-			matched = dv == dl;
++			matched = isunordered(dv, dl) ? 0 : dv == dl;
+ 			break;
+ 
+ 		case '>':
+-			matched = dv > dl;
++			matched = isgreater(dv, dl);
+ 			break;
+ 
+ 		case '<':
+-			matched = dv < dl;
++			matched = isless(dv, dl);
+ 			break;
+ 
+ 		default:
diff --git a/SOURCES/file-5.33-static-PIE-binaries-0.patch b/SOURCES/file-5.33-static-PIE-binaries-0.patch
new file mode 100644
index 0000000..1031626
--- /dev/null
+++ b/SOURCES/file-5.33-static-PIE-binaries-0.patch
@@ -0,0 +1,236 @@
+From 3951ed6ab1ba4b7d6d4d2dd5700858c470627c46 Mon Sep 17 00:00:00 2001
+From: Vincent Mihalkovic <vmihalko@redhat.com>
+Date: Thu, 9 Feb 2023 16:46:43 +0100
+Subject: [PATCH] store copy of the mode info in the magic_set
+
+---
+ src/file.h      |  1 +
+ src/funcs.c     | 53 +++++++++++++++++++++++++++++++------------------
+ src/softmagic.c | 27 +++++++++++--------------
+ 3 files changed, 47 insertions(+), 34 deletions(-)
+
+diff --git a/src/file.h b/src/file.h
+index 66598bc..b3d015d 100644
+--- a/src/file.h
++++ b/src/file.h
+@@ -413,6 +413,7 @@ struct magic_set {
+ #define 		EVENT_HAD_ERR		0x01
+ 	const char *file;
+ 	size_t line;			/* current magic line number */
++	mode_t mode;			/* copy of current stat mode */
+ 
+ 	/* data for searches */
+ 	struct {
+diff --git a/src/funcs.c b/src/funcs.c
+index f59f4a1..0bf92fe 100644
+--- a/src/funcs.c
++++ b/src/funcs.c
+@@ -27,7 +27,7 @@
+ #include "file.h"
+ 
+ #ifndef	lint
+-FILE_RCSID("@(#)$File: funcs.c,v 1.94 2017/11/02 20:25:39 christos Exp $")
++FILE_RCSID("@(#)$File: funcs.c,v 1.95 2018/05/24 18:09:17 christos Exp $")
+ #endif	/* lint */
+ 
+ #include "magic.h"
+@@ -183,9 +183,11 @@ file_buffer(struct magic_set *ms, int fd, const char *inname __attribute__ ((__u
+ 	const char *type = "application/octet-stream";
+ 	const char *def = "data";
+ 	const char *ftype = NULL;
++	char *rbuf = NULL;
+ 	struct buffer b;
+ 
+ 	buffer_init(&b, fd, buf, nb);
++	ms->mode = b.st.st_mode;
+ 
+ 	if (nb == 0) {
+ 		def = "empty";
+@@ -248,31 +250,43 @@ file_buffer(struct magic_set *ms, int fd, const char *inname __attribute__ ((__u
+ 				goto done;
+ 		}
+ 	}
++#ifdef BUILTIN_ELF
++	if ((ms->flags & MAGIC_NO_CHECK_ELF) == 0 && nb > 5 && fd != -1) {
++		file_pushbuf_t *pb;
++		/*
++		 * We matched something in the file, so this
++		 * *might* be an ELF file, and the file is at
++		 * least 5 bytes long, so if it's an ELF file
++		 * it has at least one byte past the ELF magic
++		 * number - try extracting information from the
++		 * ELF headers that cannot easily be  extracted
++		 * with rules in the magic file. We we don't
++		 * print the information yet.
++		 */
++		if ((pb = file_push_buffer(ms)) == NULL)
++			return -1;
++
++		rv = file_tryelf(ms, &b);
++		rbuf = file_pop_buffer(ms, pb);
++		if (rv != 1) {
++			free(rbuf);
++			rbuf = NULL;
++		}
++		if ((ms->flags & MAGIC_DEBUG) != 0)
++			(void)fprintf(stderr, "[try elf %d]\n", m);
++	}
++#endif
+ 
+ 	/* try soft magic tests */
+ 	if ((ms->flags & MAGIC_NO_CHECK_SOFT) == 0) {
+ 		m = file_softmagic(ms, &b, NULL, NULL, BINTEST, looks_text);
+ 		if ((ms->flags & MAGIC_DEBUG) != 0)
+ 			(void)fprintf(stderr, "[try softmagic %d]\n", m);
++		if (m == 1 && rbuf) {
++			if (file_printf(ms, "%s", rbuf) == -1)
++				goto done;
++		}
+ 		if (m) {
+-#ifdef BUILTIN_ELF
+-			if ((ms->flags & MAGIC_NO_CHECK_ELF) == 0 && m == 1 &&
+-			    nb > 5 && fd != -1) {
+-				/*
+-				 * We matched something in the file, so this
+-				 * *might* be an ELF file, and the file is at
+-				 * least 5 bytes long, so if it's an ELF file
+-				 * it has at least one byte past the ELF magic
+-				 * number - try extracting information from the
+-				 * ELF headers that cannot easily * be
+-				 * extracted with rules in the magic file.
+-				 */
+-				m = file_tryelf(ms, &b);
+-				if ((ms->flags & MAGIC_DEBUG) != 0)
+-					(void)fprintf(stderr, "[try elf %d]\n",
+-					    m);
+-			}
+-#endif
+ 			if (checkdone(ms, &rv))
+ 				goto done;
+ 		}
+@@ -318,6 +332,7 @@ simple:
+ #if HAVE_FORK
+  done_encoding:
+ #endif
++	free(rbuf);
+ 	buffer_fini(&b);
+ 	if (rv)
+ 		return rv;
+diff --git a/src/softmagic.c b/src/softmagic.c
+index 57b4677..0197ec4 100644
+--- a/src/softmagic.c
++++ b/src/softmagic.c
+@@ -54,8 +54,7 @@ private int mget(struct magic_set *, struct magic *, const struct buffer *,
+ private int msetoffset(struct magic_set *, struct magic *, struct buffer *,
+     const struct buffer *, size_t, unsigned int);
+ private int magiccheck(struct magic_set *, struct magic *);
+-private int32_t mprint(struct magic_set *, struct magic *,
+-    const struct buffer *);
++private int32_t mprint(struct magic_set *, struct magic *);
+ private int moffset(struct magic_set *, struct magic *, const struct buffer *,
+     int32_t *);
+ private void mdebug(uint32_t, const char *, size_t);
+@@ -63,8 +62,7 @@ private int mcopy(struct magic_set *, union VALUETYPE *, int, int,
+     const unsigned char *, uint32_t, size_t, struct magic *);
+ private int mconvert(struct magic_set *, struct magic *, int);
+ private int print_sep(struct magic_set *, int);
+-private int handle_annotation(struct magic_set *, struct magic *,
+-    const struct buffer *, int);
++private int handle_annotation(struct magic_set *, struct magic *, int);
+ private int cvt_8(union VALUETYPE *, const struct magic *);
+ private int cvt_16(union VALUETYPE *, const struct magic *);
+ private int cvt_32(union VALUETYPE *, const struct magic *);
+@@ -241,7 +239,7 @@ flush:
+ 			goto flush;
+ 		}
+ 
+-		if ((e = handle_annotation(ms, m, b, firstline)) != 0) {
++		if ((e = handle_annotation(ms, m, firstline)) != 0) {
+ 			*need_separator = 1;
+ 			*printed_something = 1;
+ 			*returnval = 1;
+@@ -259,7 +257,7 @@ flush:
+ 				return -1;
+ 		}
+ 
+-		if (print && mprint(ms, m, b) == -1)
++		if (print && mprint(ms, m) == -1)
+ 			return -1;
+ 
+ 		switch (moffset(ms, m, &bb, &ms->c.li[cont_level].off)) {
+@@ -340,7 +338,7 @@ flush:
+ 				} else
+ 					ms->c.li[cont_level].got_match = 1;
+ 
+-				if ((e = handle_annotation(ms, m, b, firstline))
++				if ((e = handle_annotation(ms, m, firstline))
+ 				    != 0) {
+ 					*need_separator = 1;
+ 					*printed_something = 1;
+@@ -374,7 +372,7 @@ flush:
+ 						return -1;
+ 					*need_separator = 0;
+ 				}
+-				if (print && mprint(ms, m, b) == -1)
++				if (print && mprint(ms, m) == -1)
+ 					return -1;
+ 
+ 				switch (moffset(ms, m, &bb,
+@@ -454,7 +452,7 @@ strndup(const char *str, size_t n)
+ #endif /* HAVE_STRNDUP */
+ 
+ static int
+-varexpand(char *buf, size_t len, const struct buffer *b, const char *str)
++varexpand(struct magic_set *ms, char *buf, size_t len, const char *str)
+ {
+ 	const char *ptr, *sptr, *e, *t, *ee, *et;
+ 	size_t l;
+@@ -479,7 +477,7 @@ varexpand(char *buf, size_t len, const struct buffer *b, const char *str)
+ 			return -1;
+ 		switch (*ptr) {
+ 		case 'x':
+-			if (b->st.st_mode & 0111) {
++			if (ms->mode & 0111) {
+ 				ptr = t;
+ 				l = et - t;
+ 			} else {
+@@ -509,7 +507,7 @@ varexpand(char *buf, size_t len, const struct buffer *b, const char *str)
+ 
+ 
+ private int32_t
+-mprint(struct magic_set *ms, struct magic *m, const struct buffer *b)
++mprint(struct magic_set *ms, struct magic *m)
+ {
+ 	uint64_t v;
+ 	float vf;
+@@ -519,7 +517,7 @@ mprint(struct magic_set *ms, struct magic *m, const struct buffer *b)
+ 	const char *desc;
+ 	union VALUETYPE *p = &ms->ms_value;
+ 
+-	if (varexpand(ebuf, sizeof(ebuf), b, m->desc) == -1)
++	if (varexpand(ms, ebuf, sizeof(ebuf), m->desc) == -1)
+ 		desc = m->desc;
+ 	else
+ 		desc = ebuf;
+@@ -2166,8 +2164,7 @@ magiccheck(struct magic_set *ms, struct magic *m)
+ }
+ 
+ private int
+-handle_annotation(struct magic_set *ms, struct magic *m, const struct buffer *b,
+-    int firstline)
++handle_annotation(struct magic_set *ms, struct magic *m, int firstline)
+ {
+ 	if ((ms->flags & MAGIC_APPLE) && m->apple[0]) {
+ 		if (!firstline && file_printf(ms, "\n- ") == -1)
+@@ -2188,7 +2185,7 @@ handle_annotation(struct magic_set *ms, struct magic *m, const struct buffer *b,
+ 		const char *p;
+ 		if (!firstline && file_printf(ms, "\n- ") == -1)
+ 			return -1;
+-		if (varexpand(buf, sizeof(buf), b, m->mimetype) == -1)
++		if (varexpand(ms, buf, sizeof(buf), m->mimetype) == -1)
+ 			p = m->mimetype;
+ 		else
+ 			p = buf;
+-- 
+2.39.1
+
diff --git a/SOURCES/file-5.33-static-PIE-binaries-1.patch b/SOURCES/file-5.33-static-PIE-binaries-1.patch
new file mode 100644
index 0000000..35a6e97
--- /dev/null
+++ b/SOURCES/file-5.33-static-PIE-binaries-1.patch
@@ -0,0 +1,767 @@
+From 493e2676626b530a45fcc17040915f34fa0c5dd3 Mon Sep 17 00:00:00 2001
+From: Vincent Mihalkovic <vmihalko@redhat.com>
+Date: Mon, 6 Feb 2023 14:39:29 +0100
+Subject: [PATCH] add parsing for dynamic sections
+
+9109a696f3289ba00eaa222fd432755ec4287e28
+---
+ src/readelf.c | 295 +++++++++++++++++++++++++++++++-------------------
+ src/readelf.h | 103 ++++++++++++++++++
+ 2 files changed, 289 insertions(+), 109 deletions(-)
+
+diff --git a/src/readelf.c b/src/readelf.c
+index c101483..cdc211f 100644
+--- a/src/readelf.c
++++ b/src/readelf.c
+@@ -62,13 +62,12 @@ private uint64_t getu64(int, uint64_t);
+ 
+ #define MAX_PHNUM	128
+ #define	MAX_SHNUM	32768
+-#define SIZE_UNKNOWN	((off_t)-1)
++#define SIZE_UNKNOWN	CAST(off_t, -1)
+ 
+ private int
+ toomany(struct magic_set *ms, const char *name, uint16_t num)
+ {
+-	if (file_printf(ms, ", too many %s (%u)", name, num
+-	    ) == -1)
++	if (file_printf(ms, ", too many %s (%u)", name, num) == -1)
+ 		return -1;
+ 	return 0;
+ }
+@@ -143,54 +142,55 @@ getu64(int swap, uint64_t value)
+ #define elf_getu64(swap, value) getu64(swap, value)
+ 
+ #define xsh_addr	(clazz == ELFCLASS32			\
+-			 ? (void *)&sh32			\
+-			 : (void *)&sh64)
++			 ? CAST(void *, &sh32)			\
++			 : CAST(void *, &sh64))
+ #define xsh_sizeof	(clazz == ELFCLASS32			\
+ 			 ? sizeof(sh32)				\
+ 			 : sizeof(sh64))
+-#define xsh_size	(size_t)(clazz == ELFCLASS32		\
++#define xsh_size	CAST(size_t, (clazz == ELFCLASS32	\
+ 			 ? elf_getu32(swap, sh32.sh_size)	\
+-			 : elf_getu64(swap, sh64.sh_size))
+-#define xsh_offset	(off_t)(clazz == ELFCLASS32		\
++			 : elf_getu64(swap, sh64.sh_size)))
++#define xsh_offset	CAST(off_t, (clazz == ELFCLASS32	\
+ 			 ? elf_getu32(swap, sh32.sh_offset)	\
+-			 : elf_getu64(swap, sh64.sh_offset))
++			 : elf_getu64(swap, sh64.sh_offset)))
+ #define xsh_type	(clazz == ELFCLASS32			\
+ 			 ? elf_getu32(swap, sh32.sh_type)	\
+ 			 : elf_getu32(swap, sh64.sh_type))
+ #define xsh_name    	(clazz == ELFCLASS32			\
+ 			 ? elf_getu32(swap, sh32.sh_name)	\
+ 			 : elf_getu32(swap, sh64.sh_name))
++
+ #define xph_addr	(clazz == ELFCLASS32			\
+-			 ? (void *) &ph32			\
+-			 : (void *) &ph64)
++			 ? CAST(void *, &ph32)			\
++			 : CAST(void *, &ph64))
+ #define xph_sizeof	(clazz == ELFCLASS32			\
+ 			 ? sizeof(ph32)				\
+ 			 : sizeof(ph64))
+ #define xph_type	(clazz == ELFCLASS32			\
+ 			 ? elf_getu32(swap, ph32.p_type)	\
+ 			 : elf_getu32(swap, ph64.p_type))
+-#define xph_offset	(off_t)(clazz == ELFCLASS32		\
++#define xph_offset	CAST(off_t, (clazz == ELFCLASS32	\
+ 			 ? elf_getu32(swap, ph32.p_offset)	\
+-			 : elf_getu64(swap, ph64.p_offset))
+-#define xph_align	(size_t)((clazz == ELFCLASS32		\
+-			 ? (off_t) (ph32.p_align ? 		\
+-			    elf_getu32(swap, ph32.p_align) : 4) \
+-			 : (off_t) (ph64.p_align ?		\
+-			    elf_getu64(swap, ph64.p_align) : 4)))
+-#define xph_vaddr	(size_t)((clazz == ELFCLASS32		\
+-			 ? (off_t) (ph32.p_vaddr ? 		\
+-			    elf_getu32(swap, ph32.p_vaddr) : 4) \
+-			 : (off_t) (ph64.p_vaddr ?		\
+-			    elf_getu64(swap, ph64.p_vaddr) : 4)))
+-#define xph_filesz	(size_t)((clazz == ELFCLASS32		\
++			 : elf_getu64(swap, ph64.p_offset)))
++#define xph_align	CAST(size_t, (clazz == ELFCLASS32	\
++			 ? CAST(off_t, (ph32.p_align ? 		\
++			    elf_getu32(swap, ph32.p_align) : 4))\
++			 : CAST(off_t, (ph64.p_align ?		\
++			    elf_getu64(swap, ph64.p_align) : 4))))
++#define xph_vaddr	CAST(size_t, (clazz == ELFCLASS32	\
++			 ? CAST(off_t, (ph32.p_vaddr ? 		\
++			    elf_getu32(swap, ph32.p_vaddr) : 4))\
++			 : CAST(off_t, (ph64.p_vaddr ?		\
++			    elf_getu64(swap, ph64.p_vaddr) : 4))))
++#define xph_filesz	CAST(size_t, (clazz == ELFCLASS32	\
+ 			 ? elf_getu32(swap, ph32.p_filesz)	\
+ 			 : elf_getu64(swap, ph64.p_filesz)))
+-#define xnh_addr	(clazz == ELFCLASS32			\
+-			 ? (void *)&nh32			\
+-			 : (void *)&nh64)
+-#define xph_memsz	(size_t)((clazz == ELFCLASS32		\
++#define xph_memsz	CAST(size_t, ((clazz == ELFCLASS32	\
+ 			 ? elf_getu32(swap, ph32.p_memsz)	\
+-			 : elf_getu64(swap, ph64.p_memsz)))
++			 : elf_getu64(swap, ph64.p_memsz))))
++#define xnh_addr	(clazz == ELFCLASS32			\
++			 ? CAST(void *, &nh32)			\
++			 : CAST(void *, &nh64))
+ #define xnh_sizeof	(clazz == ELFCLASS32			\
+ 			 ? sizeof(nh32)				\
+ 			 : sizeof(nh64))
+@@ -203,24 +203,36 @@ getu64(int swap, uint64_t value)
+ #define xnh_descsz	(clazz == ELFCLASS32			\
+ 			 ? elf_getu32(swap, nh32.n_descsz)	\
+ 			 : elf_getu32(swap, nh64.n_descsz))
+-#define prpsoffsets(i)	(clazz == ELFCLASS32			\
+-			 ? prpsoffsets32[i]			\
+-			 : prpsoffsets64[i])
++
++#define xdh_addr	(clazz == ELFCLASS32			\
++			 ? CAST(void *, &dh32)			\
++			 : CAST(void *, &dh64))
++#define xdh_sizeof	(clazz == ELFCLASS32			\
++			 ? sizeof(dh32)				\
++			 : sizeof(dh64))
++#define xdh_tag		(clazz == ELFCLASS32			\
++			 ? elf_getu32(swap, dh32.d_tag)		\
++			 : elf_getu64(swap, dh64.d_tag))
++#define xdh_val		(clazz == ELFCLASS32			\
++			 ? elf_getu32(swap, dh32.d_un.d_val)	\
++			 : elf_getu64(swap, dh64.d_un.d_val))
++
+ #define xcap_addr	(clazz == ELFCLASS32			\
+-			 ? (void *)&cap32			\
+-			 : (void *)&cap64)
++			 ? CAST(void *, &cap32)			\
++			 : CAST(void *, &cap64))
+ #define xcap_sizeof	(clazz == ELFCLASS32			\
+-			 ? sizeof cap32				\
+-			 : sizeof cap64)
++			 ? sizeof(cap32)			\
++			 : sizeof(cap64))
+ #define xcap_tag	(clazz == ELFCLASS32			\
+ 			 ? elf_getu32(swap, cap32.c_tag)	\
+ 			 : elf_getu64(swap, cap64.c_tag))
+ #define xcap_val	(clazz == ELFCLASS32			\
+ 			 ? elf_getu32(swap, cap32.c_un.c_val)	\
+ 			 : elf_getu64(swap, cap64.c_un.c_val))
++
+ #define xauxv_addr	(clazz == ELFCLASS32			\
+-			 ? (void *)&auxv32			\
+-			 : (void *)&auxv64)
++			 ? CAST(void *, &auxv32)		\
++			 : CAST(void *, &auxv64))
+ #define xauxv_sizeof	(clazz == ELFCLASS32			\
+ 			 ? sizeof(auxv32)			\
+ 			 : sizeof(auxv64))
+@@ -231,6 +243,10 @@ getu64(int swap, uint64_t value)
+ 			 ? elf_getu32(swap, auxv32.a_v)		\
+ 			 : elf_getu64(swap, auxv64.a_v))
+ 
++#define prpsoffsets(i)	(clazz == ELFCLASS32			\
++			 ? prpsoffsets32[i]			\
++			 : prpsoffsets64[i])
++
+ #ifdef ELFCORE
+ /*
+  * Try larger offsets first to avoid false matches
+@@ -269,8 +285,8 @@ static const size_t	prpsoffsets64[] = {
+ 	16,		/* FreeBSD, 64-bit */
+ };
+ 
+-#define	NOFFSETS32	(sizeof prpsoffsets32 / sizeof prpsoffsets32[0])
+-#define NOFFSETS64	(sizeof prpsoffsets64 / sizeof prpsoffsets64[0])
++#define	NOFFSETS32	(sizeof(prpsoffsets32) / sizeof(prpsoffsets32[0]))
++#define NOFFSETS64	(sizeof(prpsoffsets64) / sizeof(prpsoffsets64[0]))
+ 
+ #define NOFFSETS	(clazz == ELFCLASS32 ? NOFFSETS32 : NOFFSETS64)
+ 
+@@ -349,7 +365,8 @@ dophn_core(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 	 * Loop through all the program headers.
+ 	 */
+ 	for ( ; num; num--) {
+-		if (pread(fd, xph_addr, xph_sizeof, off) < (ssize_t)xph_sizeof) {
++		if (pread(fd, xph_addr, xph_sizeof, off) <
++		    CAST(ssize_t, xph_sizeof)) {
+ 			file_badread(ms);
+ 			return -1;
+ 		}
+@@ -392,7 +409,7 @@ static void
+ do_note_netbsd_version(struct magic_set *ms, int swap, void *v)
+ {
+ 	uint32_t desc;
+-	(void)memcpy(&desc, v, sizeof(desc));
++	memcpy(&desc, v, sizeof(desc));
+ 	desc = elf_getu32(swap, desc);
+ 
+ 	if (file_printf(ms, ", for NetBSD") == -1)
+@@ -438,7 +455,7 @@ do_note_freebsd_version(struct magic_set *ms, int swap, void *v)
+ {
+ 	uint32_t desc;
+ 
+-	(void)memcpy(&desc, v, sizeof(desc));
++	memcpy(&desc, v, sizeof(desc));
+ 	desc = elf_getu32(swap, desc);
+ 	if (file_printf(ms, ", for FreeBSD") == -1)
+ 		return;
+@@ -536,7 +553,7 @@ do_bid_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ 		}
+ 		if (file_printf(ms, ", BuildID[%s]=", btype) == -1)
+ 			return 1;
+-		(void)memcpy(desc, &nbuf[doff], descsz);
++		memcpy(desc, &nbuf[doff], descsz);
+ 		for (i = 0; i < descsz; i++)
+ 		    if (file_printf(ms, "%02x", desc[i]) == -1)
+ 			return 1;
+@@ -560,7 +577,7 @@ do_os_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ 	if (namesz == 4 && strcmp((char *)&nbuf[noff], "GNU") == 0 &&
+ 	    type == NT_GNU_VERSION && descsz == 16) {
+ 		uint32_t desc[4];
+-		(void)memcpy(desc, &nbuf[doff], sizeof(desc));
++		memcpy(desc, &nbuf[doff], sizeof(desc));
+ 
+ 		*flags |= FLAGS_DID_OS_NOTE;
+ 		if (file_printf(ms, ", for GNU/") == -1)
+@@ -627,7 +644,7 @@ do_os_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ 		*flags |= FLAGS_DID_OS_NOTE;
+ 		if (file_printf(ms, ", for DragonFly") == -1)
+ 			return 1;
+-		(void)memcpy(&desc, &nbuf[doff], sizeof(desc));
++		memcpy(&desc, &nbuf[doff], sizeof(desc));
+ 		desc = elf_getu32(swap, desc);
+ 		if (file_printf(ms, " %d.%d.%d", desc / 100000,
+ 		    desc / 10000 % 10, desc % 10000) == -1)
+@@ -657,7 +674,7 @@ do_pax_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ 		int did = 0;
+ 
+ 		*flags |= FLAGS_DID_NETBSD_PAX;
+-		(void)memcpy(&desc, &nbuf[doff], sizeof(desc));
++		memcpy(&desc, &nbuf[doff], sizeof(desc));
+ 		desc = elf_getu32(swap, desc);
+ 
+ 		if (desc && file_printf(ms, ", PaX: ") == -1)
+@@ -957,7 +974,7 @@ do_auxv_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ 
+ 	nval = 0;
+ 	for (size_t off = 0; off + elsize <= descsz; off += elsize) {
+-		(void)memcpy(xauxv_addr, &nbuf[doff + off], xauxv_sizeof);
++		memcpy(xauxv_addr, &nbuf[doff + off], xauxv_sizeof);
+ 		/* Limit processing to 50 vector entries to prevent DoS */
+ 		if (nval++ >= 50) {
+ 			file_error(ms, 0, "Too many ELF Auxv elements");
+@@ -1021,6 +1038,38 @@ do_auxv_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ #endif
+ }
+ 
++private size_t
++dodynamic(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
++    int clazz, int swap)
++{
++	Elf32_Dyn dh32;
++	Elf64_Dyn dh64;
++	unsigned char *dbuf = CAST(unsigned char *, vbuf);
++
++	if (xdh_sizeof + offset > size) {
++		/*
++		 * We're out of note headers.
++		 */
++		return xdh_sizeof + offset;
++	}
++
++	memcpy(xdh_addr, &dbuf[offset], xdh_sizeof);
++	offset += xdh_sizeof;
++
++	switch (xdh_tag) {
++	case DT_FLAGS_1:
++		if (xdh_val == DF_1_PIE)
++			ms->mode |= 0111;
++		else
++			ms->mode &= ~0111;
++		break;
++	default:
++		break;
++	}
++	return offset;
++}
++
++
+ private size_t
+ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+     int clazz, int swap, size_t align, int *flags, uint16_t *notecount,
+@@ -1043,7 +1092,7 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+ 		return xnh_sizeof + offset;
+ 	}
+ 
+-	(void)memcpy(xnh_addr, &nbuf[offset], xnh_sizeof);
++	memcpy(xnh_addr, &nbuf[offset], xnh_sizeof);
+ 	offset += xnh_sizeof;
+ 
+ 	namesz = xnh_namesz;
+@@ -1057,14 +1106,14 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+ 	}
+ 
+ 	if (namesz & 0x80000000) {
+-	    (void)file_printf(ms, ", bad note name size %#lx",
+-		(unsigned long)namesz);
++	    file_printf(ms, ", bad note name size %#lx",
++		CAST(unsigned long, namesz));
+ 	    return 0;
+ 	}
+ 
+ 	if (descsz & 0x80000000) {
+-	    (void)file_printf(ms, ", bad note description size %#lx",
+-		(unsigned long)descsz);
++	    file_printf(ms, ", bad note description size %#lx",
++		CAST(unsigned long, descsz));
+ 	    return 0;
+ 	}
+ 
+@@ -1118,35 +1167,25 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+ 			return offset;
+ 	}
+ 
+-	if (namesz == 7 && strcmp((char *)&nbuf[noff], "NetBSD") == 0) {
++	if (namesz == 7 && strcmp(CAST(char *, &nbuf[noff]), "NetBSD") == 0) {
++		int descw, flag;
++		const char *str, *tag;
+ 		if (descsz > 100)
+ 			descsz = 100;
+ 		switch (xnh_type) {
+ 	    	case NT_NETBSD_VERSION:
+ 			return offset;
+ 		case NT_NETBSD_MARCH:
+-			if (*flags & FLAGS_DID_NETBSD_MARCH)
+-				return offset;
+-			*flags |= FLAGS_DID_NETBSD_MARCH;
+-			if (file_printf(ms, ", compiled for: %.*s",
+-			    (int)descsz, (const char *)&nbuf[doff]) == -1)
+-				return offset;
++			flag = FLAGS_DID_NETBSD_MARCH;
++			tag = "compiled for";
+ 			break;
+ 		case NT_NETBSD_CMODEL:
+-			if (*flags & FLAGS_DID_NETBSD_CMODEL)
+-				return offset;
+-			*flags |= FLAGS_DID_NETBSD_CMODEL;
+-			if (file_printf(ms, ", compiler model: %.*s",
+-			    (int)descsz, (const char *)&nbuf[doff]) == -1)
+-				return offset;
++			flag = FLAGS_DID_NETBSD_CMODEL;
++			tag = "compiler model";
+ 			break;
+ 		case NT_NETBSD_EMULATION:
+-			if (*flags & FLAGS_DID_NETBSD_EMULATION)
+-				return offset;
+-			*flags |= FLAGS_DID_NETBSD_EMULATION;
+-			if (file_printf(ms, ", emulation: %.*s",
+-			    (int)descsz, (const char *)&nbuf[doff]) == -1)
+-				return offset;
++			flag = FLAGS_DID_NETBSD_EMULATION;
++			tag = "emulation:";
+ 			break;
+ 		default:
+ 			if (*flags & FLAGS_DID_NETBSD_UNKNOWN)
+@@ -1154,8 +1193,15 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+ 			*flags |= FLAGS_DID_NETBSD_UNKNOWN;
+ 			if (file_printf(ms, ", note=%u", xnh_type) == -1)
+ 				return offset;
+-			break;
++			return offset;
+ 		}
++
++		if (*flags & flag)
++			return offset;
++		str = CAST(const char *, &nbuf[doff]);
++		descw = CAST(int, descsz);
++		*flags |= flag;
++		file_printf(ms, ", %s: %.*s", tag, descw, str);
+ 		return offset;
+ 	}
+ 
+@@ -1236,7 +1282,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 
+ 	/* Read offset of name section to be able to read section names later */
+ 	if (pread(fd, xsh_addr, xsh_sizeof, CAST(off_t, (off + size * strtab)))
+-	    < (ssize_t)xsh_sizeof) {
++	    < CAST(ssize_t, xsh_sizeof)) {
+ 		if (file_printf(ms, ", missing section headers") == -1)
+ 			return -1;
+ 		return 0;
+@@ -1245,7 +1291,8 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 
+ 	for ( ; num; num--) {
+ 		/* Read the name of this section. */
+-		if ((namesize = pread(fd, name, sizeof(name) - 1, name_off + xsh_name)) == -1) {
++		if ((namesize = pread(fd, name, sizeof(name) - 1,
++		    name_off + xsh_name)) == -1) {
+ 			file_badread(ms);
+ 			return -1;
+ 		}
+@@ -1255,7 +1302,8 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 			stripped = 0;
+ 		}
+ 
+-		if (pread(fd, xsh_addr, xsh_sizeof, off) < (ssize_t)xsh_sizeof) {
++		if (pread(fd, xsh_addr, xsh_sizeof, off) <
++		    CAST(ssize_t, xsh_sizeof)) {
+ 			file_badread(ms);
+ 			return -1;
+ 		}
+@@ -1281,14 +1329,15 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 		/* Things we can determine when we seek */
+ 		switch (xsh_type) {
+ 		case SHT_NOTE:
+-			if ((uintmax_t)(xsh_size + xsh_offset) >
+-			    (uintmax_t)fsize) {
++			if (CAST(uintmax_t, (xsh_size + xsh_offset)) >
++			    CAST(uintmax_t, fsize)) {
+ 				if (file_printf(ms,
+ 				    ", note offset/size %#" INTMAX_T_FORMAT
+ 				    "x+%#" INTMAX_T_FORMAT "x exceeds"
+ 				    " file size %#" INTMAX_T_FORMAT "x",
+-				    (uintmax_t)xsh_offset, (uintmax_t)xsh_size,
+-				    (uintmax_t)fsize) == -1)
++				    CAST(uintmax_t, xsh_offset),
++				    CAST(uintmax_t, xsh_size),
++				    CAST(uintmax_t, fsize)) == -1)
+ 					return -1;
+ 				return 0; 
+ 			}
+@@ -1298,7 +1347,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 				return -1;
+ 			}
+ 			if (pread(fd, nbuf, xsh_size, xsh_offset) <
+-			    (ssize_t)xsh_size) {
++			    CAST(ssize_t, xsh_size)) {
+ 				file_badread(ms);
+ 				free(nbuf);
+ 				return -1;
+@@ -1306,9 +1355,9 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 
+ 			noff = 0;
+ 			for (;;) {
+-				if (noff >= (off_t)xsh_size)
++				if (noff >= CAST(off_t, xsh_size))
+ 					break;
+-				noff = donote(ms, nbuf, (size_t)noff,
++				noff = donote(ms, nbuf, CAST(size_t, noff),
+ 				    xsh_size, clazz, swap, 4, flags, notecount,
+ 				    fd, 0, 0, 0);
+ 				if (noff == 0)
+@@ -1330,7 +1379,8 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 
+ 			if (nbadcap > 5)
+ 				break;
+-			if (lseek(fd, xsh_offset, SEEK_SET) == (off_t)-1) {
++			if (lseek(fd, xsh_offset, SEEK_SET)
++			    == CAST(off_t, -1)) {
+ 				file_badseek(ms);
+ 				return -1;
+ 			}
+@@ -1339,11 +1389,12 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 				Elf32_Cap cap32;
+ 				Elf64_Cap cap64;
+ 				char cbuf[/*CONSTCOND*/
+-				    MAX(sizeof cap32, sizeof cap64)];
+-				if ((coff += xcap_sizeof) > (off_t)xsh_size)
++				    MAX(sizeof(cap32), sizeof(cap64))];
++				if ((coff += xcap_sizeof) >
++				    CAST(off_t, xsh_size))
+ 					break;
+-				if (read(fd, cbuf, (size_t)xcap_sizeof) !=
+-				    (ssize_t)xcap_sizeof) {
++				if (read(fd, cbuf, CAST(size_t, xcap_sizeof)) !=
++				    CAST(ssize_t, xcap_sizeof)) {
+ 					file_badread(ms);
+ 					return -1;
+ 				}
+@@ -1377,7 +1428,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ #endif
+ 					break;
+ 				}
+-				(void)memcpy(xcap_addr, cbuf, xcap_sizeof);
++				memcpy(xcap_addr, cbuf, xcap_sizeof);
+ 				switch (xcap_tag) {
+ 				case CA_SUNW_NULL:
+ 					break;
+@@ -1392,8 +1443,9 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 					    ", with unknown capability "
+ 					    "%#" INT64_T_FORMAT "x = %#"
+ 					    INT64_T_FORMAT "x",
+-					    (unsigned long long)xcap_tag,
+-					    (unsigned long long)xcap_val) == -1)
++					    CAST(unsigned long long, xcap_tag),
++					    CAST(unsigned long long, xcap_val))
++					    == -1)
+ 						return -1;
+ 					if (nbadcap++ > 2)
+ 						coff = xsh_size;
+@@ -1446,12 +1498,12 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 				if (file_printf(ms,
+ 				    " unknown hardware capability %#"
+ 				    INT64_T_FORMAT "x",
+-				    (unsigned long long)cap_hw1) == -1)
++				    CAST(unsigned long long, cap_hw1)) == -1)
+ 					return -1;
+ 		} else {
+ 			if (file_printf(ms,
+ 			    " hardware capability %#" INT64_T_FORMAT "x",
+-			    (unsigned long long)cap_hw1) == -1)
++			    CAST(unsigned long long, cap_hw1)) == -1)
+ 				return -1;
+ 		}
+ 	}
+@@ -1468,7 +1520,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 			if (file_printf(ms,
+ 			    ", with unknown software capability %#"
+ 			    INT64_T_FORMAT "x",
+-			    (unsigned long long)cap_sf1) == -1)
++			    CAST(unsigned long long, cap_sf1)) == -1)
+ 				return -1;
+ 	}
+ 	return 0;
+@@ -1487,9 +1539,9 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 	Elf32_Phdr ph32;
+ 	Elf64_Phdr ph64;
+ 	const char *linking_style = "statically";
+-	const char *interp = "";
+ 	unsigned char nbuf[BUFSIZ];
+ 	char ibuf[BUFSIZ];
++	char interp[BUFSIZ];
+ 	ssize_t bufsize;
+ 	size_t offset, align, len;
+ 	
+@@ -1499,8 +1551,11 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 		return 0;
+ 	}
+ 
++	interp[0] = '\0';
+   	for ( ; num; num--) {
+-		if (pread(fd, xph_addr, xph_sizeof, off) < (ssize_t)xph_sizeof) {
++		int doread;
++		if (pread(fd, xph_addr, xph_sizeof, off) <
++		    CAST(ssize_t, xph_sizeof)) {
+ 			file_badread(ms);
+ 			return -1;
+ 		}
+@@ -1513,6 +1568,7 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 		switch (xph_type) {
+ 		case PT_DYNAMIC:
+ 			linking_style = "dynamically";
++			doread = 1;
+ 			break;
+ 		case PT_NOTE:
+ 			if (sh_num)	/* Did this through section headers */
+@@ -1521,21 +1577,16 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 			    align < 4) {
+ 				if (file_printf(ms, 
+ 				    ", invalid note alignment %#lx",
+-				    (unsigned long)align) == -1)
++				    CAST(unsigned long, align)) == -1)
+ 					return -1;
+ 				align = 4;
+ 			}
+ 			/*FALLTHROUGH*/
+ 		case PT_INTERP:
+-			len = xph_filesz < sizeof(nbuf) ? xph_filesz
+-			    : sizeof(nbuf);
+-			bufsize = pread(fd, nbuf, len, xph_offset);
+-			if (bufsize == -1) {
+-				file_badread(ms);
+-				return -1;
+-			}
++			doread = 1;
+ 			break;
+ 		default:
++			doread = 0;
+ 			if (fsize != SIZE_UNKNOWN && xph_offset > fsize) {
+ 				/* Maybe warn here? */
+ 				continue;
+@@ -1543,14 +1594,39 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 			break;
+ 		}
+ 
++		if (doread) {
++			len = xph_filesz < sizeof(nbuf) ? xph_filesz
++			    : sizeof(nbuf);
++			bufsize = pread(fd, nbuf, len, xph_offset);
++			if (bufsize == -1) {
++				file_badread(ms);
++				return -1;
++			}
++		} else
++			len = 0;
++
+ 		/* Things we can determine when we seek */
+ 		switch (xph_type) {
++		case PT_DYNAMIC:
++			offset = 0;
++			for (;;) {
++				if (offset >= (size_t)bufsize)
++					break;
++				offset = dodynamic(ms, nbuf, offset,
++				    CAST(size_t, bufsize), clazz, swap);
++				if (offset == 0)
++					break;
++			}
++                        if (ms->flags & MAGIC_MIME)
++                                continue;
++			break;
++
+ 		case PT_INTERP:
+ 			if (bufsize && nbuf[0]) {
+ 				nbuf[bufsize - 1] = '\0';
+-				interp = (const char *)nbuf;
++				memcpy(interp, nbuf, bufsize);
+ 			} else
+-				interp = "*empty*";
++				strlcpy(interp, "*empty*", sizeof(interp));
+ 			break;
+ 		case PT_NOTE:
+ 			/*
+@@ -1562,7 +1638,7 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 				if (offset >= (size_t)bufsize)
+ 					break;
+ 				offset = donote(ms, nbuf, offset,
+-				    (size_t)bufsize, clazz, swap, align,
++				    CAST(size_t, bufsize), clazz, swap, align,
+ 				    flags, notecount, fd, 0, 0, 0);
+ 				if (offset == 0)
+ 					break;
+@@ -1591,7 +1667,7 @@ file_tryelf(struct magic_set *ms, const struct buffer *b)
+ 	size_t nbytes = b->flen;
+ 	union {
+ 		int32_t l;
+-		char c[sizeof (int32_t)];
++		char c[sizeof(int32_t)];
+ 	} u;
+ 	int clazz;
+ 	int swap;
+@@ -1619,7 +1695,8 @@ file_tryelf(struct magic_set *ms, const struct buffer *b)
+ 	/*
+ 	 * If we cannot seek, it must be a pipe, socket or fifo.
+ 	 */
+-	if((lseek(fd, (off_t)0, SEEK_SET) == (off_t)-1) && (errno == ESPIPE))
++	if((lseek(fd, CAST(off_t, 0), SEEK_SET) == CAST(off_t, -1))
++	    && (errno == ESPIPE))
+ 		fd = file_pipe2file(ms, fd, buf, nbytes);
+ 
+ 	if (fstat(fd, &st) == -1) {
+diff --git a/src/readelf.h b/src/readelf.h
+index ef880b9..f2f3dc3 100644
+--- a/src/readelf.h
++++ b/src/readelf.h
+@@ -430,4 +430,107 @@ typedef struct {
+ #define	AV_386_SSE4_1		0x00800000
+ #define	AV_386_SSE4_2		0x01000000
+ 
++/*
++ * Dynamic Section structure array
++ */
++typedef struct {
++	Elf32_Word		d_tag;	/* entry tag value */
++	union {
++		Elf32_Addr	d_ptr;
++		Elf32_Word	d_val;
++	} d_un;
++} Elf32_Dyn;
++
++typedef struct {
++	Elf64_Xword		d_tag;	/* entry tag value */
++	union {
++		Elf64_Addr	d_ptr;
++		Elf64_Xword	d_val;
++	} d_un;
++} Elf64_Dyn;
++
++/* d_tag */
++#define DT_NULL		0	/* Marks end of dynamic array */
++#define DT_NEEDED	1	/* Name of needed library (DT_STRTAB offset) */
++#define DT_PLTRELSZ	2	/* Size, in bytes, of relocations in PLT */
++#define DT_PLTGOT	3	/* Address of PLT and/or GOT */
++#define DT_HASH		4	/* Address of symbol hash table */
++#define DT_STRTAB	5	/* Address of string table */
++#define DT_SYMTAB	6	/* Address of symbol table */
++#define DT_RELA		7	/* Address of Rela relocation table */
++#define DT_RELASZ	8	/* Size, in bytes, of DT_RELA table */
++#define DT_RELAENT	9	/* Size, in bytes, of one DT_RELA entry */
++#define DT_STRSZ	10	/* Size, in bytes, of DT_STRTAB table */
++#define DT_SYMENT	11	/* Size, in bytes, of one DT_SYMTAB entry */
++#define DT_INIT		12	/* Address of initialization function */
++#define DT_FINI		13	/* Address of termination function */
++#define DT_SONAME	14	/* Shared object name (DT_STRTAB offset) */
++#define DT_RPATH	15	/* Library search path (DT_STRTAB offset) */
++#define DT_SYMBOLIC	16	/* Start symbol search within local object */
++#define DT_REL		17	/* Address of Rel relocation table */
++#define DT_RELSZ	18	/* Size, in bytes, of DT_REL table */
++#define DT_RELENT	19	/* Size, in bytes, of one DT_REL entry */
++#define DT_PLTREL	20	/* Type of PLT relocation entries */
++#define DT_DEBUG	21	/* Used for debugging; unspecified */
++#define DT_TEXTREL	22	/* Relocations might modify non-writable seg */
++#define DT_JMPREL	23	/* Address of relocations associated with PLT */
++#define DT_BIND_NOW	24	/* Process all relocations at load-time */
++#define DT_INIT_ARRAY	25	/* Address of initialization function array */
++#define DT_FINI_ARRAY	26	/* Size, in bytes, of DT_INIT_ARRAY array */
++#define DT_INIT_ARRAYSZ 27	/* Address of termination function array */
++#define DT_FINI_ARRAYSZ 28	/* Size, in bytes, of DT_FINI_ARRAY array*/
++#define DT_RUNPATH	29	/* overrides DT_RPATH */
++#define DT_FLAGS	30	/* Encodes ORIGIN, SYMBOLIC, TEXTREL, BIND_NOW, STATIC_TLS */
++#define DT_ENCODING	31	/* ??? */
++#define DT_PREINIT_ARRAY 32	/* Address of pre-init function array */
++#define DT_PREINIT_ARRAYSZ 33	/* Size, in bytes, of DT_PREINIT_ARRAY array */
++#define DT_NUM		34
++
++#define DT_LOOS		0x60000000	/* Operating system specific range */
++#define DT_VERSYM	0x6ffffff0	/* Symbol versions */
++#define DT_FLAGS_1	0x6ffffffb	/* ELF dynamic flags */
++#define DT_VERDEF	0x6ffffffc	/* Versions defined by file */
++#define DT_VERDEFNUM	0x6ffffffd	/* Number of versions defined by file */
++#define DT_VERNEED	0x6ffffffe	/* Versions needed by file */
++#define DT_VERNEEDNUM	0x6fffffff	/* Number of versions needed by file */
++#define DT_HIOS		0x6fffffff
++#define DT_LOPROC	0x70000000	/* Processor-specific range */
++#define DT_HIPROC	0x7fffffff
++
++/* Flag values for DT_FLAGS */
++#define DF_ORIGIN	0x00000001	/* uses $ORIGIN */
++#define DF_SYMBOLIC	0x00000002	/* */
++#define DF_TEXTREL	0x00000004	/* */
++#define DF_BIND_NOW	0x00000008	/* */
++#define DF_STATIC_TLS	0x00000010	/* */
++
++/* Flag values for DT_FLAGS_1 */
++#define	DF_1_NOW	0x00000001	/* Same as DF_BIND_NOW */
++#define	DF_1_GLOBAL	0x00000002	/* Unused */
++#define	DF_1_GROUP	0x00000004	/* Is member of group */
++#define	DF_1_NODELETE	0x00000008	/* Cannot be deleted from process */
++#define	DF_1_LOADFLTR	0x00000010	/* Immediate loading of filters */
++#define	DF_1_INITFIRST	0x00000020	/* init/fini takes priority */
++#define	DF_1_NOOPEN	0x00000040	/* Do not allow loading on dlopen() */
++#define	DF_1_ORIGIN	0x00000080 	/* Require $ORIGIN processing */
++#define	DF_1_DIRECT	0x00000100	/* Enable direct bindings */
++#define	DF_1_INTERPOSE 	0x00000400	/* Is an interposer */
++#define	DF_1_NODEFLIB	0x00000800 	/* Ignore default library search path */
++#define	DF_1_NODUMP	0x00001000 	/* Cannot be dumped with dldump(3C) */
++#define	DF_1_CONFALT	0x00002000 	/* Configuration alternative */
++#define	DF_1_ENDFILTEE	0x00004000	/* Filtee ends filter's search */
++#define	DF_1_DISPRELDNE	0x00008000	/* Did displacement relocation */
++#define	DF_1_DISPRELPND 0x00010000	/* Pending displacement relocation */
++#define	DF_1_NODIRECT	0x00020000 	/* Has non-direct bindings */
++#define	DF_1_IGNMULDEF	0x00040000	/* Used internally */
++#define	DF_1_NOKSYMS	0x00080000	/* Used internally */
++#define	DF_1_NOHDR	0x00100000	/* Used internally */
++#define	DF_1_EDITED	0x00200000	/* Has been modified since build */
++#define	DF_1_NORELOC	0x00400000 	/* Used internally */
++#define	DF_1_SYMINTPOSE 0x00800000 	/* Has individual symbol interposers */
++#define	DF_1_GLOBAUDIT	0x01000000	/* Require global auditing */
++#define	DF_1_SINGLETON	0x02000000	/* Has singleton symbols */
++#define	DF_1_STUB	0x04000000	/* Stub */
++#define	DF_1_PIE	0x08000000	/* Position Independent Executable */
++
+ #endif
+-- 
+2.39.1
+
diff --git a/SOURCES/file-5.33-static-PIE-binaries-2.patch b/SOURCES/file-5.33-static-PIE-binaries-2.patch
new file mode 100644
index 0000000..85446ae
--- /dev/null
+++ b/SOURCES/file-5.33-static-PIE-binaries-2.patch
@@ -0,0 +1,68 @@
+From f8ba1437114e408de0f66efb272fdc1de986017a Mon Sep 17 00:00:00 2001
+From: Vincent Mihalkovic <vmihalko@redhat.com>
+Date: Mon, 6 Feb 2023 14:39:58 +0100
+Subject: [PATCH] We need to process the dynamic section so that we can set $x
+ for mime.
+
+9ffbd485ba4647827c4bdacf3a2de690f6765b0c
+---
+ src/readelf.c | 12 +++++++++++-
+ 1 file changed, 11 insertions(+), 1 deletion(-)
+
+diff --git a/src/readelf.c b/src/readelf.c
+index cdc211f..94cdaca 100644
+--- a/src/readelf.c
++++ b/src/readelf.c
+@@ -1273,6 +1273,8 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ 	uint64_t cap_sf1 = 0;	/* SunOS 5.x software capabilities */
+ 	char name[50];
+ 	ssize_t namesize;
++        if (ms->flags & MAGIC_MIME)
++                return 0;
+ 
+ 	if (size != xsh_sizeof) {
+ 		if (file_printf(ms, ", corrupted section header size") == -1)
+@@ -1622,6 +1624,8 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 			break;
+ 
+ 		case PT_INTERP:
++                        if (ms->flags & MAGIC_MIME)
++                                continue;
+ 			if (bufsize && nbuf[0]) {
+ 				nbuf[bufsize - 1] = '\0';
+ 				memcpy(interp, nbuf, bufsize);
+@@ -1629,6 +1633,8 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 				strlcpy(interp, "*empty*", sizeof(interp));
+ 			break;
+ 		case PT_NOTE:
++			if (ms->flags & MAGIC_MIME)
++				return 0;
+ 			/*
+ 			 * This is a PT_NOTE section; loop through all the notes
+ 			 * in the section.
+@@ -1645,9 +1651,13 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 			}
+ 			break;
+ 		default:
++			if (ms->flags & MAGIC_MIME)
++				continue;
+ 			break;
+ 		}
+ 	}
++	if (ms->flags & MAGIC_MIME)
++		return 0;
+ 	if (file_printf(ms, ", %s linked", linking_style)
+ 	    == -1)
+ 		return -1;
+@@ -1678,7 +1688,7 @@ file_tryelf(struct magic_set *ms, const struct buffer *b)
+ 	Elf64_Ehdr elf64hdr;
+ 	uint16_t type, phnum, shnum, notecount;
+ 
+-	if (ms->flags & (MAGIC_MIME|MAGIC_APPLE|MAGIC_EXTENSION))
++	if (ms->flags & (MAGIC_APPLE|MAGIC_EXTENSION))
+ 		return 0;
+ 	/*
+ 	 * ELF executables have multiple section headers in arbitrary
+-- 
+2.39.1
+
diff --git a/SOURCES/file-5.33-static-PIE-binaries-3.patch b/SOURCES/file-5.33-static-PIE-binaries-3.patch
new file mode 100644
index 0000000..13314a1
--- /dev/null
+++ b/SOURCES/file-5.33-static-PIE-binaries-3.patch
@@ -0,0 +1,36 @@
+From 27c951adbd5d7ebe95f08c18257ea031bdd59ee1 Mon Sep 17 00:00:00 2001
+From: Vincent Mihalkovic <vmihalko@redhat.com>
+Date: Mon, 6 Feb 2023 15:00:16 +0100
+Subject: [PATCH] For dynamic binaries let the df_1 pie flag determine if we
+ are pie or a shared object, and ignore the mode bits.
+
+upstream commit: 03084b161cf888b5286dbbcd964c31ccad4f64d9
+---
+ src/readelf.c | 4 +++-
+ 1 file changed, 3 insertions(+), 1 deletion(-)
+
+diff --git a/src/readelf.c b/src/readelf.c
+index 94cdaca..9c75c0a 100644
+--- a/src/readelf.c
++++ b/src/readelf.c
+@@ -1058,7 +1058,7 @@ dodynamic(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+ 
+ 	switch (xdh_tag) {
+ 	case DT_FLAGS_1:
+-		if (xdh_val == DF_1_PIE)
++		if (xdh_val & DF_1_PIE)
+ 			ms->mode |= 0111;
+ 		else
+ 			ms->mode &= ~0111;
+@@ -1611,6 +1611,8 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 		switch (xph_type) {
+ 		case PT_DYNAMIC:
+ 			offset = 0;
++                        // Let DF_1 determine if we are PIE or not.
++                        ms->mode &= ~0111;
+ 			for (;;) {
+ 				if (offset >= (size_t)bufsize)
+ 					break;
+-- 
+2.39.1
+
diff --git a/SOURCES/file-5.33-static-PIE-binaries-4.patch b/SOURCES/file-5.33-static-PIE-binaries-4.patch
new file mode 100644
index 0000000..03cf938
--- /dev/null
+++ b/SOURCES/file-5.33-static-PIE-binaries-4.patch
@@ -0,0 +1,125 @@
+From 948d0e24f33c3b411b5ec1e320acec889e6781b8 Mon Sep 17 00:00:00 2001
+From: Vincent Mihalkovic <vmihalko@redhat.com>
+Date: Mon, 6 Feb 2023 15:04:33 +0100
+Subject: [PATCH] Improve detection of static-pie binaries, and don't call them
+ "dynamically linked", but call them "static-pie" linked.
+
+363d7fcf703ad3ebf37b45693b2c9e43eb8b4176
+---
+ src/readelf.c | 35 +++++++++++++++++++++++++----------
+ 1 file changed, 25 insertions(+), 10 deletions(-)
+
+diff --git a/src/readelf.c b/src/readelf.c
+index 9c75c0a..0011659 100644
+--- a/src/readelf.c
++++ b/src/readelf.c
+@@ -1040,7 +1040,7 @@ do_auxv_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
+ 
+ private size_t
+ dodynamic(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+-    int clazz, int swap)
++    int clazz, int swap, int *pie, size_t *need)
+ {
+ 	Elf32_Dyn dh32;
+ 	Elf64_Dyn dh64;
+@@ -1058,11 +1058,15 @@ dodynamic(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
+ 
+ 	switch (xdh_tag) {
+ 	case DT_FLAGS_1:
++                *pie = 1;
+ 		if (xdh_val & DF_1_PIE)
+ 			ms->mode |= 0111;
+ 		else
+ 			ms->mode &= ~0111;
+ 		break;
++        case DT_NEEDED:
++                (*need)++;
++                break;
+ 	default:
+ 		break;
+ 	}
+@@ -1529,9 +1533,10 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
+ }
+ 
+ /*
+- * Look through the program headers of an executable image, searching
+- * for a PT_INTERP section; if one is found, it's dynamically linked,
+- * otherwise it's statically linked.
++ * Look through the program headers of an executable image, to determine
++ * if it is statically or dynamically linked. If it has a dynamic section,
++ * it is pie, and does not have an interpreter or needed libraries, we
++ * call it static pie.
+  */
+ private int
+ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+@@ -1540,12 +1545,13 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ {
+ 	Elf32_Phdr ph32;
+ 	Elf64_Phdr ph64;
+-	const char *linking_style = "statically";
++	const char *linking_style;
+ 	unsigned char nbuf[BUFSIZ];
+ 	char ibuf[BUFSIZ];
+ 	char interp[BUFSIZ];
+ 	ssize_t bufsize;
+-	size_t offset, align, len;
++	size_t offset, align, len, need = 0;
++        int pie = 0, dynamic = 0;
+ 	
+ 	if (size != xph_sizeof) {
+ 		if (file_printf(ms, ", corrupted program header size") == -1)
+@@ -1569,7 +1575,6 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 		/* Things we can determine before we seek */
+ 		switch (xph_type) {
+ 		case PT_DYNAMIC:
+-			linking_style = "dynamically";
+ 			doread = 1;
+ 			break;
+ 		case PT_NOTE:
+@@ -1610,6 +1615,7 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 		/* Things we can determine when we seek */
+ 		switch (xph_type) {
+ 		case PT_DYNAMIC:
++			dynamic = 1;
+ 			offset = 0;
+                         // Let DF_1 determine if we are PIE or not.
+                         ms->mode &= ~0111;
+@@ -1617,7 +1623,8 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 				if (offset >= (size_t)bufsize)
+ 					break;
+ 				offset = dodynamic(ms, nbuf, offset,
+-				    CAST(size_t, bufsize), clazz, swap);
++				    CAST(size_t, bufsize), clazz, swap,
++				    &pie, &need);
+ 				if (offset == 0)
+ 					break;
+ 			}
+@@ -1626,6 +1633,7 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 			break;
+ 
+ 		case PT_INTERP:
++                        need++;
+                         if (ms->flags & MAGIC_MIME)
+                                 continue;
+ 			if (bufsize && nbuf[0]) {
+@@ -1660,8 +1668,15 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
+ 	}
+ 	if (ms->flags & MAGIC_MIME)
+ 		return 0;
+-	if (file_printf(ms, ", %s linked", linking_style)
+-	    == -1)
++	if (dynamic) {
++		if (pie && need == 0)
++			linking_style = "static-pie";
++		else
++			linking_style = "dynamically";
++	} else {
++		linking_style = "statically";
++	}
++	if (file_printf(ms, ", %s linked", linking_style) == -1)
+ 		return -1;
+ 	if (interp[0])
+ 		if (file_printf(ms, ", interpreter %s",
+-- 
+2.39.1
+
diff --git a/SOURCES/file-5.33-static-PIE-binaries-5.patch b/SOURCES/file-5.33-static-PIE-binaries-5.patch
new file mode 100644
index 0000000..6597ac1
--- /dev/null
+++ b/SOURCES/file-5.33-static-PIE-binaries-5.patch
@@ -0,0 +1,13 @@
+diff --git a/src/readelf.c b/src/readelf.c
+index d836e68..6d4b40b 100644
+--- a/src/readelf.c
++++ b/src/readelf.c
+@@ -69,7 +69,7 @@ toomany(struct magic_set *ms, const char *name, uint16_t num)
+ {
+ 	if (file_printf(ms, ", too many %s (%u)", name, num) == -1)
+ 		return -1;
+-	return 0;
++	return 1;
+ }
+ 
+ private uint16_t
diff --git a/SPECS/file.spec b/SPECS/file.spec
index 9c984c6..001d59a 100644
--- a/SPECS/file.spec
+++ b/SPECS/file.spec
@@ -15,7 +15,7 @@
 Summary: A utility for determining file types
 Name: file
 Version: 5.33
-Release: 21%{?dist}
+Release: 24%{?dist}
 License: BSD
 Group: Applications/File
 Source0: ftp://ftp.astron.com/pub/file/file-%{version}.tar.gz
@@ -88,6 +88,22 @@ Patch22: file-5.37-CVE-2019-18218.patch
 # not yet upstream (#2095828)
 Patch23: file-5.33-fix-compression.patch
 
+# upstream commit: 709dfecf25c2eb2822f7e0b8c30d6329cd2d97fb (#2061557)
+Patch24: file-5.33-floating-point-exception.patch
+
+# upstream commit: e2adab1456c2bd8b005ddf8ed71540a37d05cb08 (#2071581)
+Patch25: file-5.33-static-PIE-binaries-0.patch
+# upstream commit: 9109a696f3289ba00eaa222fd432755ec4287e28 (#2071581)
+Patch26: file-5.33-static-PIE-binaries-1.patch
+# upstream commit: 9ffbd485ba4647827c4bdacf3a2de690f6765b0c (#2071581)
+Patch27: file-5.33-static-PIE-binaries-2.patch
+# upstream commit: 03084b161cf888b5286dbbcd964c31ccad4f64d9 (#2071581)
+Patch28: file-5.33-static-PIE-binaries-3.patch
+# upstream commit: 363d7fcf703ad3ebf37b45693b2c9e43eb8b4176 (#2071581)
+Patch29: file-5.33-static-PIE-binaries-4.patch
+# upstream commit: 9c3137904e59d68debb97fceaced46a691ba241a (#2071581)
+Patch30: file-5.33-static-PIE-binaries-5.patch
+
 URL: http://www.darwinsys.com/file/
 Requires: file-libs = %{version}-%{release}
 BuildRequires: zlib-devel
@@ -112,6 +128,7 @@ Libraries for applications using libmagic.
 Summary:  Libraries and header files for file development
 Group:    Applications/File
 Requires: %{name} = %{version}-%{release}
+Requires: file-libs%{?_isa} = %{version}-%{release}
 
 %description devel
 The file-devel package contains the header files and libmagic library
@@ -258,6 +275,15 @@ cd %{py3dir}
 %endif
 
 %changelog
+* Wed Feb 22 2023 Vincent Mihalkovic <vmihalko@redhat.com> - 5.33-24
+- fix detection of static-pie binaries (#2071581)
+
+* Wed Feb 01 2023 Vincent Mihalkovic <vmihalko@redhat.com> - 5.33-23
+- fix detection of static-pie binaries (#2071581)
+
+* Tue Jan 31 2023 Vincent Mihalkovic <vmihalko@redhat.com> - 5.33-22
+- fix issue with libmagic and floating point exceptions (#2061557)
+
 * Wed Aug 17 2022 Vincent Mihalkovic <vmihalko@redhat.com> - 5.33-21
 - fix recognition (src/compress.c) of compressed empty files (#2095828)