From: Tom Lendacky <thomas.lenda...@amd.com>

Secure Encrypted Virtualization (SEV) does not support string I/O, so
unroll the string I/O operation into a loop operating on one element at
a time.

Signed-off-by: Tom Lendacky <thomas.lenda...@amd.com>
---
 arch/x86/include/asm/io.h |   26 ++++++++++++++++++++++----
 1 file changed, 22 insertions(+), 4 deletions(-)

diff --git a/arch/x86/include/asm/io.h b/arch/x86/include/asm/io.h
index 833f7cc..b596114 100644
--- a/arch/x86/include/asm/io.h
+++ b/arch/x86/include/asm/io.h
@@ -327,14 +327,32 @@ static inline unsigned type in##bwl##_p(int port)         
        \
                                                                        \
 static inline void outs##bwl(int port, const void *addr, unsigned long count) \
 {                                                                      \
-       asm volatile("rep; outs" #bwl                                   \
-                    : "+S"(addr), "+c"(count) : "d"(port));            \
+       if (sev_active()) {                                             \
+               unsigned type *value = (unsigned type *)addr;           \
+               while (count) {                                         \
+                       out##bwl(*value, port);                         \
+                       value++;                                        \
+                       count--;                                        \
+               }                                                       \
+       } else {                                                        \
+               asm volatile("rep; outs" #bwl                           \
+                            : "+S"(addr), "+c"(count) : "d"(port));    \
+       }                                                               \
 }                                                                      \
                                                                        \
 static inline void ins##bwl(int port, void *addr, unsigned long count) \
 {                                                                      \
-       asm volatile("rep; ins" #bwl                                    \
-                    : "+D"(addr), "+c"(count) : "d"(port));            \
+       if (sev_active()) {                                             \
+               unsigned type *value = (unsigned type *)addr;           \
+               while (count) {                                         \
+                       *value = in##bwl(port);                         \
+                       value++;                                        \
+                       count--;                                        \
+               }                                                       \
+       } else {                                                        \
+               asm volatile("rep; ins" #bwl                            \
+                            : "+D"(addr), "+c"(count) : "d"(port));    \
+       }                                                               \
 }
 
 BUILDIO(b, b, char)

_______________________________________________
devel mailing list
de...@linuxdriverproject.org
http://driverdev.linuxdriverproject.org/mailman/listinfo/driverdev-devel

Reply via email to