git: 54b5d177aa98 - main - LinuxKPI: Add devm_memremap and devm_ioremap_wc functions

From: Vladimir Kondratyev <wulf_at_FreeBSD.org>
Date: Fri, 18 Sep 2026 06:51:28 UTC
The branch main has been updated by wulf:

URL: https://cgit.FreeBSD.org/src/commit/?id=54b5d177aa988207a4ca68763ac8e20c8145c17f

commit 54b5d177aa988207a4ca68763ac8e20c8145c17f
Author:     Vladimir Kondratyev <wulf@FreeBSD.org>
AuthorDate: 2026-09-18 06:49:36 +0000
Commit:     Vladimir Kondratyev <wulf@FreeBSD.org>
CommitDate: 2026-09-18 06:50:21 +0000

    LinuxKPI: Add devm_memremap and devm_ioremap_wc functions
    
    Required by drm-kmod 6.12.101.
    
    Reviewed by:    bz, dumbbell
    Differential Revision:  https://reviews.freebsd.org/D59732
---
 sys/compat/linuxkpi/common/include/linux/io.h | 14 +++++++++++++
 sys/compat/linuxkpi/common/src/linux_page.c   | 30 +++++++++++++++++++++++++++
 2 files changed, 44 insertions(+)

diff --git a/sys/compat/linuxkpi/common/include/linux/io.h b/sys/compat/linuxkpi/common/include/linux/io.h
index 4dfc04b3f3fc..5da0b64045f2 100644
--- a/sys/compat/linuxkpi/common/include/linux/io.h
+++ b/sys/compat/linuxkpi/common/include/linux/io.h
@@ -521,6 +521,20 @@ done:
 	return (addr);
 }
 
+#define	devm_memremap(...)	linuxkpi_devm_memremap(__VA_ARGS__)
+void *linuxkpi_devm_memremap(struct device *dev, resource_size_t offset,
+    size_t size, unsigned long flags);
+
+static inline void *
+devm_ioremap_wc(struct device *dev, resource_size_t offset,
+    resource_size_t size)
+{
+	void *addr;
+
+	addr = devm_memremap(dev, offset, size, MEMREMAP_WC);
+	return (IS_ERR(addr) ? NULL : addr);
+}
+
 static inline void
 memunmap(void *addr)
 {
diff --git a/sys/compat/linuxkpi/common/src/linux_page.c b/sys/compat/linuxkpi/common/src/linux_page.c
index 14abc3376a1c..430f05175179 100644
--- a/sys/compat/linuxkpi/common/src/linux_page.c
+++ b/sys/compat/linuxkpi/common/src/linux_page.c
@@ -65,6 +65,7 @@
 #include <linux/idr.h>
 #include <linux/io.h>
 #include <linux/io-mapping.h>
+#include <linux/device.h>
 
 #ifdef __i386__
 DEFINE_IDR(mtrr_idr);
@@ -420,6 +421,35 @@ iounmap(void *addr)
 	kfree(vmmap);
 }
 
+static void
+lkpi_devm_memremap_unmap(struct device *dev, void *p)
+{
+	void **dr = p;
+
+	memunmap(*dr);
+}
+
+void *
+linuxkpi_devm_memremap(struct device *dev, resource_size_t offset, size_t size,
+    unsigned long flags)
+{
+	void **dr, *addr;
+
+	dr = devres_alloc(lkpi_devm_memremap_unmap, sizeof(*dr), GFP_KERNEL);
+	if (dr == NULL)
+		return (ERR_PTR(-ENOMEM));
+	addr = memremap(offset, size, flags);
+	if (addr != NULL) {
+		*dr = addr;
+		devres_add(dev, dr);
+	} else {
+                addr = ERR_PTR(-ENXIO);
+		devres_free(dr);
+	}
+
+	return (addr);
+}
+
 void *
 vmap(struct page **pages, unsigned int count, unsigned long flags, int prot)
 {