[llvmlinux] [PATCH 1/2] [mips] Replace named register fix with an upstreamable version.

Vinícius Tinti viniciustinti at gmail.com
Fri Jan 9 18:04:07 UTC 2015


On Fri, Jan 9, 2015 at 4:02 PM, Vinícius Tinti <viniciustinti at gmail.com> wrote:
> On Fri, Jan 9, 2015 at 3:57 PM, Mark Charlebois <charlebm at gmail.com> wrote:
>> The patch you sent does not apply to the current tree. I do not understand
>> what you want to be done.
>>
>> -Mark
>>
>> On Fri, Jan 9, 2015 at 6:20 AM, Daniel Sanders <daniel.sanders at imgtec.com>
>> wrote:
>>>
>>> Also include the necessary LLVM patch which was previously omitted.
>>>
>>> ---
>>>
>>> I've submitted the kernel patch upstream.
>>>
>>>  ...REAM-mips-Remove-all-instances-of-explici.patch | 426
>>> ---------------------
>>>  ...-current_thread_info-to-an-equivalent-sup.patch |  50 +++
>>>  arch/mips/patches/series                           |   3 +-
>>>  .../clang/patches/llvm/mips-named-registers.patch  |  39 ++
>>>  toolchain/clang/patches/llvm/series                |   1 +
>>>  5 files changed, 91 insertions(+), 428 deletions(-)
>>>  delete mode 100644
>>> arch/mips/patches/mips-DO-NOT-UPSTREAM-mips-Remove-all-instances-of-explici.patch
>>>  create mode 100644
>>> arch/mips/patches/mips-change-current_thread_info-to-an-equivalent-sup.patch
>>>  create mode 100644
>>> toolchain/clang/patches/llvm/mips-named-registers.patch
>>>
>>> diff --git
>>> a/arch/mips/patches/mips-DO-NOT-UPSTREAM-mips-Remove-all-instances-of-explici.patch
>>> b/arch/mips/patches/mips-DO-NOT-UPSTREAM-mips-Remove-all-instances-of-explici.patch
>>> deleted file mode 100644
>>> index c661a8a..0000000
>>> ---
>>> a/arch/mips/patches/mips-DO-NOT-UPSTREAM-mips-Remove-all-instances-of-explici.patch
>>> +++ /dev/null
>>> @@ -1,426 +0,0 @@
>>> -From f7d74e066df8cd92e5c310d2354e84e5e26c2dff Mon Sep 17 00:00:00 2001
>>> -From: Daniel Sanders <daniel.sanders at imgtec.com>
>>> -Date: Fri, 19 Dec 2014 13:48:39 +0000
>>> -Subject: [PATCH 2/2] [DO-NOT-UPSTREAM][mips] Remove all instances of
>>> explicit
>>> - register variables from the mips arch.
>>> -
>>> -Clang accepts the syntax but does not honour them. I've asked a colleague
>>> to
>>> -look into supporting explicit register variables in clang. For now,
>>> remove the
>>> -uses of this feature and accept the unnecessary moves.
>>> -
>>> -Signed-off-by: Daniel Sanders <daniel.sanders at imgtec.com>
>>> ----
>>> - .../mips-remove-explicit-register-variables.patch  | 391
>>> +++++++++++++++++++++
>>> - arch/mips/patches/series                           |   1 +
>>> - 2 files changed, 392 insertions(+)
>>> - create mode 100644
>>> arch/mips/patches/mips-remove-explicit-register-variables.patch
>>> -
>>> -diff --git
>>> a/arch/mips/patches/mips-remove-explicit-register-variables.patch
>>> b/arch/mips/patches/mips-remove-explicit-register-variables.patch
>>> -new file mode 100644
>>> -index 0000000..320831a
>>> ---- /dev/null
>>> -+++ b/arch/mips/patches/mips-remove-explicit-register-variables.patch
>>> -@@ -0,0 +1,391 @@
>>> -+From 437530253edbf21d60e98259096a532a90579b8d Mon Sep 17 00:00:00 2001
>>> -+From: Daniel Sanders <daniel.sanders at imgtec.com>
>>> -+Date: Fri, 19 Dec 2014 13:44:48 +0000
>>> -+Subject: [PATCH 2/2] [DO-NOT-UPSTREAM][mips] Remove all instances of
>>> explicit
>>> -+ register variables from the mips arch.
>>> -+
>>> -+Clang accepts the syntax but does not honour them. I've asked a
>>> colleague to
>>> -+look into supporting explicit register variables in clang. For now,
>>> remove the
>>> -+uses of this feature and accept the unnecessary moves.
>>> -+
>>> -+Signed-off-by: Daniel Sanders <daniel.sanders at imgtec.com>
>>> -+---
>>> -+ arch/mips/include/asm/kvm_para.h    | 34 ++++++++++-----
>>> -+ arch/mips/include/asm/sgiarcs.h     | 42 ++++++++++++------
>>> -+ arch/mips/include/asm/thread_info.h |  4 +-
>>> -+ arch/mips/include/asm/uaccess.h     | 85
>>> ++++++++++++++++++++++---------------
>>> -+ arch/mips/lib/uncached.c            |  5 ++-
>>> -+ 5 files changed, 108 insertions(+), 62 deletions(-)
>>> -+
>>> -+diff --git a/arch/mips/include/asm/kvm_para.h
>>> b/arch/mips/include/asm/kvm_para.h
>>> -+index 5a9aa91..b8e987c 100644
>>> -+--- a/arch/mips/include/asm/kvm_para.h
>>> -++++ b/arch/mips/include/asm/kvm_para.h
>>> -+@@ -14,12 +14,14 @@
>>> -+  */
>>> -+ static inline unsigned long kvm_hypercall0(unsigned long num)
>>> -+ {
>>> -+-     register unsigned long n asm("v0");
>>> -+-     register unsigned long r asm("v0");
>>> -++     register unsigned long n;
>>> -++     register unsigned long r;
>>> -+
>>> -+      n = num;
>>> -+      __asm__ __volatile__(
>>> -++                "move $v0,%1\n\t"
>>> -+              KVM_HYPERCALL
>>> -++                "move %0,$v0\n\t"
>>> -+              : "=r" (r) : "r" (n) : "memory"
>>> -+              );
>>> -+
>>> -+@@ -29,14 +31,17 @@ static inline unsigned long kvm_hypercall0(unsigned
>>> long num)
>>> -+ static inline unsigned long kvm_hypercall1(unsigned long num,
>>> -+                                      unsigned long arg0)
>>> -+ {
>>> -+-     register unsigned long n asm("v0");
>>> -+-     register unsigned long r asm("v0");
>>> -+-     register unsigned long a0 asm("a0");
>>> -++     register unsigned long n;
>>> -++     register unsigned long r;
>>> -++     register unsigned long a0;
>>> -+
>>> -+      n = num;
>>> -+      a0 = arg0;
>>> -+      __asm__ __volatile__(
>>> -++                "move $v0,%1\n\t"
>>> -++                "move $a0,%2\n\t"
>>> -+              KVM_HYPERCALL
>>> -++                "move %0,$v0\n\t"
>>> -+              : "=r" (r) : "r" (n), "r" (a0) : "memory"
>>> -+              );
>>> -+
>>> -+@@ -55,7 +60,11 @@ static inline unsigned long kvm_hypercall2(unsigned
>>> long num,
>>> -+      a0 = arg0;
>>> -+      a1 = arg1;
>>> -+      __asm__ __volatile__(
>>> -++                "move $v0,%1\n\t"
>>> -++                "move $a0,%2\n\t"
>>> -++                "move $a1,%3\n\t"
>>> -+              KVM_HYPERCALL
>>> -++                "move $v0,%0\n\t"
>>> -+              : "=r" (r) : "r" (n), "r" (a0), "r" (a1) : "memory"
>>> -+              );
>>> -+
>>> -+@@ -65,18 +74,23 @@ static inline unsigned long kvm_hypercall2(unsigned
>>> long num,
>>> -+ static inline unsigned long kvm_hypercall3(unsigned long num,
>>> -+      unsigned long arg0, unsigned long arg1, unsigned long arg2)
>>> -+ {
>>> -+-     register unsigned long n asm("v0");
>>> -+-     register unsigned long r asm("v0");
>>> -+-     register unsigned long a0 asm("a0");
>>> -+-     register unsigned long a1 asm("a1");
>>> -+-     register unsigned long a2 asm("a2");
>>> -++     register unsigned long n;
>>> -++     register unsigned long r;
>>> -++     register unsigned long a0;
>>> -++     register unsigned long a1;
>>> -++     register unsigned long a2;
>>> -+
>>> -+      n = num;
>>> -+      a0 = arg0;
>>> -+      a1 = arg1;
>>> -+      a2 = arg2;
>>> -+      __asm__ __volatile__(
>>> -++                "move $v0,%1\n\t"
>>> -++                "move $a0,%2\n\t"
>>> -++                "move $a1,%3\n\t"
>>> -++                "move $a2,%4\n\t"
>>> -+              KVM_HYPERCALL
>>> -++                "move $v0,%0\n\t"
>>> -+              : "=r" (r) : "r" (n), "r" (a0), "r" (a1), "r" (a2) :
>>> "memory"
>>> -+              );
>>> -+
>>> -+diff --git a/arch/mips/include/asm/sgiarcs.h
>>> b/arch/mips/include/asm/sgiarcs.h
>>> -+index 26ddfff..a62c267 100644
>>> -+--- a/arch/mips/include/asm/sgiarcs.h
>>> -++++ b/arch/mips/include/asm/sgiarcs.h
>>> -+@@ -388,9 +388,10 @@ struct linux_smonblock {
>>> -+
>>> -+ #define ARC_CALL1(dest, a1)                                          \
>>> -+ ({   long __res;                                                     \
>>> -+-     register signed int __a1 __asm__("$4") = (int) (long) (a1);     \
>>> -++     register signed int __a1 = (int) (long) (a1);   \
>>> -+      long __vec = (long) romvec->dest;                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move\t$4,%3\n\t" \
>>> -+      "dsubu\t$29, 32\n\t"                                            \
>>> -+      "jalr\t%1\n\t"                                                  \
>>> -+      "daddu\t$29, 32\n\t"                                            \
>>> -+@@ -403,10 +404,12 @@ struct linux_smonblock {
>>> -+
>>> -+ #define ARC_CALL2(dest, a1, a2)
>>> \
>>> -+ ({   long __res;                                                     \
>>> -+-     register signed int __a1 __asm__("$4") = (int) (long) (a1);     \
>>> -+-     register signed int __a2 __asm__("$5") = (int) (long) (a2);     \
>>> -++     register signed int __a1 = (int) (long) (a1);   \
>>> -++     register signed int __a2 = (int) (long) (a2);   \
>>> -+      long __vec = (long) romvec->dest;                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move\t$4,%3\n\t" \
>>> -++        "move\t$5,%4\n\t" \
>>> -+      "dsubu\t$29, 32\n\t"                                            \
>>> -+      "jalr\t%1\n\t"                                                  \
>>> -+      "daddu\t$29, 32\n\t"                                            \
>>> -+@@ -419,11 +422,14 @@ struct linux_smonblock {
>>> -+
>>> -+ #define ARC_CALL3(dest, a1, a2, a3)                                  \
>>> -+ ({   long __res;                                                     \
>>> -+-     register signed int __a1 __asm__("$4") = (int) (long) (a1);     \
>>> -+-     register signed int __a2 __asm__("$5") = (int) (long) (a2);     \
>>> -+-     register signed int __a3 __asm__("$6") = (int) (long) (a3);     \
>>> -++     register signed int __a1 = (int) (long) (a1);   \
>>> -++     register signed int __a2 = (int) (long) (a2);   \
>>> -++     register signed int __a3 = (int) (long) (a3);   \
>>> -+      long __vec = (long) romvec->dest;                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move\t$4,%3\n\t" \
>>> -++        "move\t$5,%4\n\t" \
>>> -++        "move\t$6,%5\n\t" \
>>> -+      "dsubu\t$29, 32\n\t"                                            \
>>> -+      "jalr\t%1\n\t"                                                  \
>>> -+      "daddu\t$29, 32\n\t"                                            \
>>> -+@@ -436,12 +442,16 @@ struct linux_smonblock {
>>> -+
>>> -+ #define ARC_CALL4(dest, a1, a2, a3, a4)
>>> \
>>> -+ ({   long __res;                                                     \
>>> -+-     register signed int __a1 __asm__("$4") = (int) (long) (a1);     \
>>> -+-     register signed int __a2 __asm__("$5") = (int) (long) (a2);     \
>>> -+-     register signed int __a3 __asm__("$6") = (int) (long) (a3);     \
>>> -+-     register signed int __a4 __asm__("$7") = (int) (long) (a4);     \
>>> -++     register signed int __a1 = (int) (long) (a1);   \
>>> -++     register signed int __a2 = (int) (long) (a2);   \
>>> -++     register signed int __a3 = (int) (long) (a3);   \
>>> -++     register signed int __a4 = (int) (long) (a4);   \
>>> -+      long __vec = (long) romvec->dest;                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move\t$4,%3\n\t" \
>>> -++        "move\t$5,%4\n\t" \
>>> -++        "move\t$6,%5\n\t" \
>>> -++        "move\t$7,%6\n\t" \
>>> -+      "dsubu\t$29, 32\n\t"                                            \
>>> -+      "jalr\t%1\n\t"                                                  \
>>> -+      "daddu\t$29, 32\n\t"                                            \
>>> -+@@ -455,13 +465,17 @@ struct linux_smonblock {
>>> -+
>>> -+ #define ARC_CALL5(dest, a1, a2, a3, a4, a5)
>>> \
>>> -+ ({   long __res;                                                     \
>>> -+-     register signed int __a1 __asm__("$4") = (int) (long) (a1);     \
>>> -+-     register signed int __a2 __asm__("$5") = (int) (long) (a2);     \
>>> -+-     register signed int __a3 __asm__("$6") = (int) (long) (a3);     \
>>> -+-     register signed int __a4 __asm__("$7") = (int) (long) (a4);     \
>>> -++     register signed int __a1 = (int) (long) (a1);   \
>>> -++     register signed int __a2 = (int) (long) (a2);   \
>>> -++     register signed int __a3 = (int) (long) (a3);   \
>>> -++     register signed int __a4 = (int) (long) (a4);   \
>>> -+      register signed int __a5 = (int) (long) (a5);                   \
>>> -+      long __vec = (long) romvec->dest;                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move\t$4,%3\n\t" \
>>> -++        "move\t$5,%4\n\t" \
>>> -++        "move\t$6,%5\n\t" \
>>> -++        "move\t$7,%6\n\t" \
>>> -+      "dsubu\t$29, 32\n\t"                                            \
>>> -+      "sw\t%7, 16($29)\n\t"                                           \
>>> -+      "jalr\t%1\n\t"                                                  \
>>> -+diff --git a/arch/mips/include/asm/thread_info.h
>>> b/arch/mips/include/asm/thread_info.h
>>> -+index 99eea59..c148256 100644
>>> -+--- a/arch/mips/include/asm/thread_info.h
>>> -++++ b/arch/mips/include/asm/thread_info.h
>>> -+@@ -60,7 +60,9 @@ struct thread_info {
>>> -+ /* How to get the thread information struct from C.  */
>>> -+ static inline struct thread_info *current_thread_info(void)
>>> -+ {
>>> -+-     register struct thread_info *__current_thread_info __asm__("$28");
>>> -++     register struct thread_info *__current_thread_info;
>>> -++
>>> -++        __asm__("move %0, $28": "=r"(__current_thread_info));
>>> -+
>>> -+      return __current_thread_info;
>>> -+ }
>>> -+diff --git a/arch/mips/include/asm/uaccess.h
>>> b/arch/mips/include/asm/uaccess.h
>>> -+index bf8b324..96698c6 100644
>>> -+--- a/arch/mips/include/asm/uaccess.h
>>> -++++ b/arch/mips/include/asm/uaccess.h
>>> -+@@ -788,18 +788,21 @@ extern size_t __copy_user(void *__to, const void
>>> *__from, size_t __n);
>>> -+ #ifndef CONFIG_EVA
>>> -+ #define __invoke_copy_to_user(to, from, n)                           \
>>> -+ ({                                                                   \
>>> -+-     register void __user *__cu_to_r __asm__("$4");                  \
>>> -+-     register const void *__cu_from_r __asm__("$5");                 \
>>> -+-     register long __cu_len_r __asm__("$6");                         \
>>> -++     register void __user *__cu_to_r = (to);                         \
>>> -++     register const void *__cu_from_r = (from);                      \
>>> -++     register long __cu_len_r = (n);                                 \
>>> -+                                                                      \
>>> -+-     __cu_to_r = (to);                                               \
>>> -+-     __cu_from_r = (from);                                           \
>>> -+-     __cu_len_r = (n);                                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move $4, %0\n\t"
>>> \
>>> -++        "move $5, %1\n\t"
>>> \
>>> -++        "move $6, %2\n\t"
>>> \
>>> -+      __MODULE_JAL(__copy_user)                                       \
>>> -++        "move %0, $4\n\t"
>>> \
>>> -++        "move %1, $5\n\t"
>>> \
>>> -++        "move %2, $6\n\t"
>>> \
>>> -+      : "+r" (__cu_to_r), "+r" (__cu_from_r), "+r" (__cu_len_r)       \
>>> -+      :                                                               \
>>> -+-     : "$8", "$9", "$10", "$11", "$12", "$14", "$15", "$24", "$31",  \
>>> -++     : "$4", "$5", "$6", "$8", "$9", "$10", "$11", "$12", "$14", "$15",
>>> "$24", "$31",        \
>>> -+        DADDI_SCRATCH, "memory");                                     \
>>> -+      __cu_len_r;                                                     \
>>> -+ })
>>> -+@@ -923,23 +926,26 @@ extern size_t __copy_user_inatomic(void *__to,
>>> const void *__from, size_t __n);
>>> -+
>>> -+ #define __invoke_copy_from_user(to, from, n)                         \
>>> -+ ({                                                                   \
>>> -+-     register void *__cu_to_r __asm__("$4");                         \
>>> -+-     register const void __user *__cu_from_r __asm__("$5");          \
>>> -+-     register long __cu_len_r __asm__("$6");                         \
>>> -++     register void *__cu_to_r = (to);                                \
>>> -++     register const void __user *__cu_from_r = (from);               \
>>> -++     register long __cu_len_r = (n);                                 \
>>> -+                                                                      \
>>> -+-     __cu_to_r = (to);                                               \
>>> -+-     __cu_from_r = (from);                                           \
>>> -+-     __cu_len_r = (n);                                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -+      ".set\tnoreorder\n\t"                                           \
>>> -++        "move $4, %0\n\t"
>>> \
>>> -++        "move $5, %1\n\t"
>>> \
>>> -++        "move $6, %2\n\t"
>>> \
>>> -+      __MODULE_JAL(__copy_user)                                       \
>>> -+      ".set\tnoat\n\t"                                                \
>>> -+      __UA_ADDU "\t$1, %1, %2\n\t"                                    \
>>> -++        "move %0, $4\n\t"
>>> \
>>> -++        "move %1, $5\n\t"
>>> \
>>> -++        "move %2, $6\n\t"
>>> \
>>> -+      ".set\tat\n\t"                                                  \
>>> -+      ".set\treorder"                                                 \
>>> -+      : "+r" (__cu_to_r), "+r" (__cu_from_r), "+r" (__cu_len_r)       \
>>> -+      :                                                               \
>>> -+-     : "$8", "$9", "$10", "$11", "$12", "$14", "$15", "$24", "$31",  \
>>> -++     : "$4", "$5", "$6", "$8", "$9", "$10", "$11", "$12", "$14", "$15",
>>> "$24", "$31",        \
>>> -+        DADDI_SCRATCH, "memory");                                     \
>>> -+      __cu_len_r;                                                     \
>>> -+ })
>>> -+@@ -957,23 +963,26 @@ extern size_t __copy_user_inatomic(void *__to,
>>> const void *__from, size_t __n);
>>> -+
>>> -+ #define __invoke_copy_from_user_inatomic(to, from, n)
>>> \
>>> -+ ({                                                                   \
>>> -+-     register void *__cu_to_r __asm__("$4");                         \
>>> -+-     register const void __user *__cu_from_r __asm__("$5");          \
>>> -+-     register long __cu_len_r __asm__("$6");                         \
>>> -++     register void *__cu_to_r = (to);                                \
>>> -++     register const void __user *__cu_from_r = (from);       \
>>> -++     register long __cu_len_r = (n);                                 \
>>> -+                                                                      \
>>> -+-     __cu_to_r = (to);                                               \
>>> -+-     __cu_from_r = (from);                                           \
>>> -+-     __cu_len_r = (n);                                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -+      ".set\tnoreorder\n\t"                                           \
>>> -++        "move $4, %0\n\t"
>>> \
>>> -++        "move $5, %1\n\t"
>>> \
>>> -++        "move $6, %2\n\t"
>>> \
>>> -+      __MODULE_JAL(__copy_user_inatomic)                              \
>>> -+      ".set\tnoat\n\t"                                                \
>>> -+      __UA_ADDU "\t$1, %1, %2\n\t"                                    \
>>> -++        "move %0, $4\n\t"
>>> \
>>> -++        "move %1, $5\n\t"
>>> \
>>> -++        "move %2, $6\n\t"
>>> \
>>> -+      ".set\tat\n\t"                                                  \
>>> -+      ".set\treorder"                                                 \
>>> -+      : "+r" (__cu_to_r), "+r" (__cu_from_r), "+r" (__cu_len_r)       \
>>> -+      :                                                               \
>>> -+-     : "$8", "$9", "$10", "$11", "$12", "$14", "$15", "$24", "$31",  \
>>> -++     : "$4", "$5", "$6", "$8", "$9", "$10", "$11", "$12", "$14", "$15",
>>> "$24", "$31",        \
>>> -+        DADDI_SCRATCH, "memory");                                     \
>>> -+      __cu_len_r;                                                     \
>>> -+ })
>>> -+@@ -995,41 +1004,47 @@ extern size_t __copy_in_user_eva(void *__to,
>>> const void *__from, size_t __n);
>>> -+
>>> -+ #define __invoke_copy_from_user_eva_generic(to, from, n, func_ptr)   \
>>> -+ ({                                                                   \
>>> -+-     register void *__cu_to_r __asm__("$4");                         \
>>> -+-     register const void __user *__cu_from_r __asm__("$5");          \
>>> -+-     register long __cu_len_r __asm__("$6");                         \
>>> -++     register void *__cu_to_r = (to);                                \
>>> -++     register const void __user *__cu_from_r = (from);       \
>>> -++     register long __cu_len_r = (n);                         \
>>> -+                                                                      \
>>> -+-     __cu_to_r = (to);                                               \
>>> -+-     __cu_from_r = (from);                                           \
>>> -+-     __cu_len_r = (n);                                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -+      ".set\tnoreorder\n\t"                                           \
>>> -++        "move $4, %0\n\t"
>>> \
>>> -++        "move $5, %1\n\t"
>>> \
>>> -++        "move $6, %2\n\t"
>>> \
>>> -+      __MODULE_JAL(func_ptr)                                          \
>>> -+      ".set\tnoat\n\t"                                                \
>>> -+      __UA_ADDU "\t$1, %1, %2\n\t"                                    \
>>> -++        "move %0, $4\n\t"
>>> \
>>> -++        "move %1, $5\n\t"
>>> \
>>> -++        "move %2, $6\n\t"
>>> \
>>> -+      ".set\tat\n\t"                                                  \
>>> -+      ".set\treorder"                                                 \
>>> -+      : "+r" (__cu_to_r), "+r" (__cu_from_r), "+r" (__cu_len_r)       \
>>> -+      :                                                               \
>>> -+-     : "$8", "$9", "$10", "$11", "$12", "$14", "$15", "$24", "$31",  \
>>> -++     : "$4", "$5", "$6", "$8", "$9", "$10", "$11", "$12", "$14", "$15",
>>> "$24", "$31",        \
>>> -+        DADDI_SCRATCH, "memory");                                     \
>>> -+      __cu_len_r;                                                     \
>>> -+ })
>>> -+
>>> -+ #define __invoke_copy_to_user_eva_generic(to, from, n, func_ptr)     \
>>> -+ ({                                                                   \
>>> -+-     register void *__cu_to_r __asm__("$4");                         \
>>> -+-     register const void __user *__cu_from_r __asm__("$5");          \
>>> -+-     register long __cu_len_r __asm__("$6");                         \
>>> -++     register void *__cu_to_r = (to);                                \
>>> -++     register const void __user *__cu_from_r = (from);               \
>>> -++     register long __cu_len_r = (n);                         \
>>> -+                                                                      \
>>> -+-     __cu_to_r = (to);                                               \
>>> -+-     __cu_from_r = (from);                                           \
>>> -+-     __cu_len_r = (n);                                               \
>>> -+      __asm__ __volatile__(                                           \
>>> -++        "move $4, %0\n\t"
>>> \
>>> -++        "move $5, %1\n\t"
>>> \
>>> -++        "move $6, %2\n\t"
>>> \
>>> -+      __MODULE_JAL(func_ptr)                                          \
>>> -++        "move %0, $4\n\t"
>>> \
>>> -++        "move %1, $5\n\t"
>>> \
>>> -++        "move %2, $6\n\t"
>>> \
>>> -+      : "+r" (__cu_to_r), "+r" (__cu_from_r), "+r" (__cu_len_r)       \
>>> -+      :                                                               \
>>> -+-     : "$8", "$9", "$10", "$11", "$12", "$14", "$15", "$24", "$31",  \
>>> -++     : "$4", "$5", "$6", "$8", "$9", "$10", "$11", "$12", "$14", "$15",
>>> "$24", "$31",        \
>>> -+        DADDI_SCRATCH, "memory");                                     \
>>> -+      __cu_len_r;                                                     \
>>> -+ })
>>> -+diff --git a/arch/mips/lib/uncached.c b/arch/mips/lib/uncached.c
>>> -+index 09d5dee..c520eb1 100644
>>> -+--- a/arch/mips/lib/uncached.c
>>> -++++ b/arch/mips/lib/uncached.c
>>> -+@@ -37,8 +37,9 @@
>>> -+  */
>>> -+ unsigned long run_uncached(void *func)
>>> -+ {
>>> -+-     register long sp __asm__("$sp");
>>> -+-     register long ret __asm__("$2");
>>> -++     register long sp;
>>> -++        __asm__ volatile ("move %0, $sp" : "=r"(sp));
>>> -++     register long ret;
>>> -+      long lfunc = (long)func, ufunc;
>>> -+      long usp;
>>> -+
>>> -+--
>>> -+2.1.3
>>> -+
>>> -diff --git a/arch/mips/patches/series b/arch/mips/patches/series
>>> -index 1aaf96a..e219c25 100644
>>> ---- a/arch/mips/patches/series
>>> -+++ b/arch/mips/patches/series
>>> -@@ -2,3 +2,4 @@ mips-fix-cast-to-type-not-present-in-union.patch
>>> - mips-fix-inline-asm-input-output-type-mismatch.patch
>>> - mips-silence-variable-self-assignment-warnings.patch
>>> - mips-silence-unicode-warnings.patch
>>> -+mips-remove-explicit-register-variables.patch
>>> ---
>>> -2.1.3
>>> -
>>> diff --git
>>> a/arch/mips/patches/mips-change-current_thread_info-to-an-equivalent-sup.patch
>>> b/arch/mips/patches/mips-change-current_thread_info-to-an-equivalent-sup.patch
>>> new file mode 100644
>>> index 0000000..83b17ce
>>> --- /dev/null
>>> +++
>>> b/arch/mips/patches/mips-change-current_thread_info-to-an-equivalent-sup.patch
>>> @@ -0,0 +1,50 @@
>>> +From 3e8b879d48a805fdad49914259511d7f47b36a73 Mon Sep 17 00:00:00 2001
>>> +From: Daniel Sanders <daniel.sanders at imgtec.com>
>>> +Date: Fri, 9 Jan 2015 10:54:22 +0000
>>> +Subject: [PATCH] MIPS: Changed current_thread_info() to an equivalent
>>> + supported by both clang and GCC
>>> +
>>> +Without this, a 'break' instruction is executed very early in the boot
>>> and
>>> +the boot hangs.
>>> +
>>> +The problem is that clang doesn't honour named registers on local
>>> variables
>>> +and silently treats them as normal uninitialized variables. However, it
>>> +does honour them on global variables.
>>> +
>>> +Signed-off-by: Daniel Sanders <daniel.sanders at imgtec.com>
>>> +---
>>> + arch/mips/include/asm/thread_info.h | 6 +++---
>>> + 1 file changed, 3 insertions(+), 3 deletions(-)
>>> +
>>> +For reference, a similar patch for ARM's stack pointer has already been
>>> merged:
>>> +  0abc08b ARM: 8170/1: Add global named register current_stack_pointer
>>> for ARM
>>> +
>>> +This is part of a patch series to get Linux for Mips working when
>>> compiled with
>>> +clang. I've chosen to submit this patch individually since it's my first
>>> kernel
>>> +patch and I'd like to be sure I'm following your processes correctly
>>> before I
>>> +submit all of them.
>>> +
>>> +Please CC me on replies since I'm not subscribed to the mailing list.
>>> +
>>> +diff --git a/arch/mips/include/asm/thread_info.h
>>> b/arch/mips/include/asm/thread_info.h
>>> +index 99eea59..2a2f3c4 100644
>>> +--- a/arch/mips/include/asm/thread_info.h
>>> ++++ b/arch/mips/include/asm/thread_info.h
>>> +@@ -58,11 +58,11 @@ struct thread_info {
>>> + #define init_stack            (init_thread_union.stack)
>>> +
>>> + /* How to get the thread information struct from C.  */
>>> ++register struct thread_info *current_gp_register asm("$28");
>>> ++
>>> + static inline struct thread_info *current_thread_info(void)
>>> + {
>>> +-      register struct thread_info *__current_thread_info __asm__("$28");
>>> +-
>>> +-      return __current_thread_info;
>>> ++      return current_gp_register;
>>> + }
>>> +
>>> + #endif /* !__ASSEMBLY__ */
>>> +--
>>> +2.1.4
>>> +
>>> diff --git a/arch/mips/patches/series b/arch/mips/patches/series
>>> index ad1334a..7fc1a7d 100644
>>> --- a/arch/mips/patches/series
>>> +++ b/arch/mips/patches/series
>>> @@ -2,5 +2,4 @@ mips-fix-cast-to-type-not-present-in-union.patch
>>>  mips-fix-inline-asm-input-output-type-mismatch.patch
>>>  mips-silence-variable-self-assignment-warnings.patch
>>>  mips-silence-unicode-warnings.patch
>>> -mips-WIP-Fix-slab-allocator-bootstrap.patch
>>> -mips-DO-NOT-UPSTREAM-mips-Remove-all-instances-of-explici.patch
>>> +mips-change-current_thread_info-to-an-equivalent-sup.patch
>>> diff --git a/toolchain/clang/patches/llvm/mips-named-registers.patch
>>> b/toolchain/clang/patches/llvm/mips-named-registers.patch
>>> new file mode 100644
>>> index 0000000..99d0888
>>> --- /dev/null
>>> +++ b/toolchain/clang/patches/llvm/mips-named-registers.patch
>>> @@ -0,0 +1,39 @@
>>> +--- llvm.orig/lib/Target/Mips/MipsISelLowering.cpp
>>> ++++ llvm/lib/Target/Mips/MipsISelLowering.cpp
>>> +@@ -3836,3 +3836,25 @@
>>> +
>>> +   return BB;
>>> + }
>>> ++
>>> ++// FIXME? Maybe this could be a TableGen attribute on some registers and
>>> ++// this table could be generated automatically from RegInfo.
>>> ++unsigned MipsTargetLowering::getRegisterByName(const char* RegName,
>>> ++                                               EVT VT) const {
>>> ++  // Named registers is expected to be fairly rare. For now, just
>>> support $28
>>> ++  // since the linux kernel uses it.
>>> ++  if (Subtarget.isGP64bit()) {
>>> ++    unsigned Reg = StringSwitch<unsigned>(RegName)
>>> ++                         .Case("$28", Mips::GP_64)
>>> ++                         .Default(0);
>>> ++    if (Reg)
>>> ++      return Reg;
>>> ++  } else {
>>> ++    unsigned Reg = StringSwitch<unsigned>(RegName)
>>> ++                         .Case("$28", Mips::GP)
>>> ++                         .Default(0);
>>> ++    if (Reg)
>>> ++      return Reg;
>>> ++  }
>>> ++  report_fatal_error("Invalid register name global variable");
>>> ++}
>>> +--- llvm.orig/lib/Target/Mips/MipsISelLowering.h
>>> ++++ llvm/lib/Target/Mips/MipsISelLowering.h
>>> +@@ -262,6 +262,8 @@
>>> +
>>> +     void HandleByVal(CCState *, unsigned &, unsigned) const override;
>>> +
>>> ++    unsigned getRegisterByName(const char* RegName, EVT VT) const;
>>> ++
>>> +   protected:
>>> +     SDValue getGlobalReg(SelectionDAG &DAG, EVT Ty) const;
>>> +
>>> diff --git a/toolchain/clang/patches/llvm/series
>>> b/toolchain/clang/patches/llvm/series
>>> index f0b4536..b65b208 100644
>>> --- a/toolchain/clang/patches/llvm/series
>>> +++ b/toolchain/clang/patches/llvm/series
>>> @@ -1 +1,2 @@
>>>  call_graph.patch
>>> +mips-named-registers.patch
>>> --
>>> 2.1.4
>>>
>>> _______________________________________________
>>> LLVMLinux mailing list
>>> LLVMLinux at lists.linuxfoundation.org
>>> https://lists.linuxfoundation.org/mailman/listinfo/llvmlinux
>>
>>
>>
>> _______________________________________________
>> LLVMLinux mailing list
>> LLVMLinux at lists.linuxfoundation.org
>> https://lists.linuxfoundation.org/mailman/listinfo/llvmlinux
>
> Hi Daniel,
>
> I would like to know if it is really a good idea to do this:
>
>
> --
> Simplicity is the ultimate sophistication

Hi Daniel,

I would like to know if it is really a good idea to do this:

-     register unsigned long n asm("v0");
-     register unsigned long r asm("v0");
+     register unsigned long n;
+     register unsigned long r;

How can you guarantee that the compiler will honor the register placement?

Regards,
Vinicius

-- 
Simplicity is the ultimate sophistication


More information about the LLVMLinux mailing list