Re: [RFC] fs: add userspace critical mounts event support

2016-09-23 Thread Herbert, Marc
On 03/09/2016 11:10, Dmitry Torokhov wrote:
> I was thinking if we kernel could post
> "conditions" (maybe simple stings) that it waits for, and userspace
> could unlock these "conditions". One of them might be "firmware
> available".

On idea offered by Josh Triplett that seems to overlap with this one
is to have something similar to the (deprecated) userhelper with
*per-blob* requests and notifications except for one major difference:
userspace would not anymore be in charge of *providing* the blob but
would instead only *signal* when a given blob becomes available and is
either found or found missing. Then the kernel loads the blob _by
itself_; unlike the userhelper. No new “critical filesystem” concept
and a *per-blob basis*, allowing any variation of blob locations
across any number of initramfs and filesystems.

Could this one fly?



[PATCH] crypto: sha1-powerpc: little-endian support

2016-09-23 Thread Marcelo Cerri
The driver does not handle endianness properly when loading the input
data.

Signed-off-by: Marcelo Cerri 
---
 arch/powerpc/crypto/sha1-powerpc-asm.S | 13 +++--
 1 file changed, 11 insertions(+), 2 deletions(-)

diff --git a/arch/powerpc/crypto/sha1-powerpc-asm.S 
b/arch/powerpc/crypto/sha1-powerpc-asm.S
index 125e165..82ddc9b 100644
--- a/arch/powerpc/crypto/sha1-powerpc-asm.S
+++ b/arch/powerpc/crypto/sha1-powerpc-asm.S
@@ -7,6 +7,15 @@
 #include 
 #include 
 
+#ifdef __BIG_ENDIAN__
+#define LWZ(rt, d, ra) \
+   lwz rt,d(ra)
+#else
+#define LWZ(rt, d, ra) \
+   li  rt,d;   \
+   lwbrx   rt,rt,ra
+#endif
+
 /*
  * We roll the registers for T, A, B, C, D, E around on each
  * iteration; T on iteration t is A on iteration t+1, and so on.
@@ -23,7 +32,7 @@
 #define W(t)   (((t)%16)+16)
 
 #define LOADW(t)   \
-   lwz W(t),(t)*4(r4)
+   LWZ(W(t),(t)*4,r4)
 
 #define STEPD0_LOAD(t) \
andcr0,RD(t),RB(t); \
@@ -33,7 +42,7 @@
add r0,RE(t),r15;   \
add RT(t),RT(t),r6; \
add r14,r0,W(t);\
-   lwz W((t)+4),((t)+4)*4(r4); \
+   LWZ(W((t)+4),((t)+4)*4,r4); \
rotlwi  RB(t),RB(t),30; \
add RT(t),RT(t),r14
 
-- 
2.7.4



[powerpc:test 88/124] arch/powerpc/kernel/exceptions-64s.S:1493: Error: attempt to move .org backwards

2016-09-23 Thread kbuild test robot
Hi Nicholas,

First bad commit (maybe != root cause):

tree:   https://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git test
head:   6f13ef67fa45546813f6a7f798d95a27ba469f29
commit: 5bbf2094b13af5f9253a607681a51e27de249ab8 [88/124] powerpc/64s: 
consolidate Machine Check 0x200 interrupt
config: powerpc-g5_defconfig (attached as .config)
compiler: powerpc64-linux-gnu-gcc (Debian 6.1.1-9) 6.1.1 20160705
reproduce:
wget 
https://git.kernel.org/cgit/linux/kernel/git/wfg/lkp-tests.git/plain/sbin/make.cross
 -O ~/bin/make.cross
chmod +x ~/bin/make.cross
git checkout 5bbf2094b13af5f9253a607681a51e27de249ab8
# save the attached .config to linux build tree
make.cross ARCH=powerpc 

Note: the powerpc/test HEAD 6f13ef67fa45546813f6a7f798d95a27ba469f29 builds 
fine.
  It only hurts bisectibility.

All errors (new ones prefixed by >>):

   arch/powerpc/kernel/exceptions-64s.S: Assembler messages:
>> arch/powerpc/kernel/exceptions-64s.S:1493: Error: attempt to move .org 
>> backwards

vim +1493 arch/powerpc/kernel/exceptions-64s.S

087aa036 Chen Gang   2013-03-25  1487   ld  r10,_LINK(r1)   
/* make idle task do the */
087aa036 Chen Gang   2013-03-25  1488   std r10,_NIP(r1)
/* equivalent of a blr */
087aa036 Chen Gang   2013-03-25  1489   blr
00f29fdb Nicholas Piggin 2016-09-21  1490  TRAMP_HANDLER_END(power4_fixup_nap)
087aa036 Chen Gang   2013-03-25  1491  #endif
087aa036 Chen Gang   2013-03-25  1492  
fe06bbba Nicholas Piggin 2016-09-21 @1493  CLOSE_FIXED_SECTION(real_vectors);
fe06bbba Nicholas Piggin 2016-09-21  1494  
CLOSE_FIXED_SECTION(real_trampolines);
fe06bbba Nicholas Piggin 2016-09-21  1495  CLOSE_FIXED_SECTION(virt_vectors);
fe06bbba Nicholas Piggin 2016-09-21  1496  
CLOSE_FIXED_SECTION(virt_trampolines);

:: The code at line 1493 was first introduced by commit
:: fe06bbbaa8c7b8b2600e08af1aeb105e6f0c10f3 powerpc/64: use gas sections 
for arranging exception vectors

:: TO: Nicholas Piggin 
:: CC: Michael Ellerman 

---
0-DAY kernel test infrastructureOpen Source Technology Center
https://lists.01.org/pipermail/kbuild-all   Intel Corporation


.config.gz
Description: application/gzip


[bug] crypto/vmx/p8_ghash memory corruption in 4.8-rc7

2016-09-23 Thread Jan Stancek
Hi,

I'm chasing a memory corruption with 4.8-rc7 as I'm observing random Oopses
on ppc BE/LE systems (lpars, KVM guests). About 30% of issues is that
module list gets corrupted, and "cat /proc/modules" or "lsmod" triggers
an Oops, for example:

[   88.486041] Unable to handle kernel paging request for data at address 
0x0020
...
[   88.487658] NIP [c020f820] m_show+0xa0/0x240
[   88.487689] LR [c020f834] m_show+0xb4/0x240
[   88.487719] Call Trace:
[   88.487736] [c004b605bbb0] [c020f834] m_show+0xb4/0x240 
(unreliable)
[   88.487796] [c004b605bc50] [c045e73c] seq_read+0x36c/0x520
[   88.487843] [c004b605bcf0] [c04e1014] proc_reg_read+0x84/0x120
[   88.487889] [c004b605bd30] [c040df88] vfs_read+0xf8/0x380
[   88.487934] [c004b605bde0] [c040fd40] SyS_read+0x60/0x110
[   88.487981] [c004b605be30] [c0009590] system_call+0x38/0xec

0x20 offset is module_use->source, module_use is NULL because module.source_list
gets corrupted.

The source of corruption appears to originate from a 'ahash' test for p8_ghash:

cryptomgr_test
 alg_test
  alg_test_hash
   test_hash
__test_hash
 ahash_partial_update
  shash_async_export
   memcpy

With some extra traces [1], I'm seeing that ahash_partial_update() allocates 56 
bytes
for 'state', and then crypto_ahash_export() writes 76 bytes into it:

[5.970887] __test_hash alg name p8_ghash, result: c4333ac0, key: 
c004b860a500, req: c004b860a380
[5.970963] state: c4333f00, statesize: 56
[5.970995] shash_default_export memcpy c4333f00 c004b860a3e0, 
len: 76

This seems to directly correspond with:
  p8_ghash_alg.descsize = sizeof(struct p8_ghash_desc_ctx) == 56
  shash_tfm->descsize = sizeof(struct p8_ghash_desc_ctx) + 
crypto_shash_descsize(fallback) == 56 + 20
where 20 is presumably coming from "ghash_alg.descsize".

My gut feeling was that these 2 should match, but I'd love to hear
what crypto people think.

Thank you,
Jan

[1]
diff --git a/crypto/shash.c b/crypto/shash.c
index a051541..49fe182 100644
--- a/crypto/shash.c
+++ b/crypto/shash.c
@@ -188,6 +188,8 @@ EXPORT_SYMBOL_GPL(crypto_shash_digest);

 static int shash_default_export(struct shash_desc *desc, void *out)
 {
+   int len = crypto_shash_descsize(desc->tfm);
+   printk("shash_default_export memcpy %p %p, len: %d\n", out, 
shash_desc_ctx(desc), len);
memcpy(out, shash_desc_ctx(desc), crypto_shash_descsize(desc->tfm));
return 0;
 }
diff --git a/crypto/testmgr.c b/crypto/testmgr.c
index 5c9d5a5..2e54579 100644
--- a/crypto/testmgr.c
+++ b/crypto/testmgr.c
@@ -218,6 +218,8 @@ static int ahash_partial_update(struct ahash_request **preq,
pr_err("alt: hash: Failed to alloc state for %s\n", algo);
goto out_nostate;
}
+   printk("state: %p, statesize: %d\n", state, statesize);
+
ret = crypto_ahash_export(req, state);
if (ret) {
pr_err("alt: hash: Failed to export() for %s\n", algo);
@@ -288,6 +290,7 @@ static int __test_hash(struct crypto_ahash *tfm, struct 
hash_testvec *template,
   "%s\n", algo);
goto out_noreq;
}
+   printk("__test_hash alg name %s, result: %p, key: %p, req: %p\n", algo, 
result, key, req);
ahash_request_set_callback(req, CRYPTO_TFM_REQ_MAY_BACKLOG,
   tcrypt_complete, );


Re: [PATCH 2/3] bpf powerpc: implement support for tail calls

2016-09-23 Thread Daniel Borkmann

On 09/23/2016 10:35 PM, Naveen N. Rao wrote:

Tail calls allow JIT'ed eBPF programs to call into other JIT'ed eBPF
programs. This can be achieved either by:
(1) retaining the stack setup by the first eBPF program and having all
subsequent eBPF programs re-using it, or,
(2) by unwinding/tearing down the stack and having each eBPF program
deal with its own stack as it sees fit.

To ensure that this does not create loops, there is a limit to how many
tail calls can be done (currently 32). This requires the JIT'ed code to
maintain a count of the number of tail calls done so far.

Approach (1) is simple, but requires every eBPF program to have (almost)
the same prologue/epilogue, regardless of whether they need it. This is
inefficient for small eBPF programs which may not sometimes need a
prologue at all. As such, to minimize impact of tail call
implementation, we use approach (2) here which needs each eBPF program
in the chain to use its own prologue/epilogue. This is not ideal when
many tail calls are involved and when all the eBPF programs in the chain
have similar prologue/epilogue. However, the impact is restricted to
programs that do tail calls. Individual eBPF programs are not affected.

We maintain the tail call count in a fixed location on the stack and
updated tail call count values are passed in through this. The very
first eBPF program in a chain sets this up to 0 (the first 2
instructions). Subsequent tail calls skip the first two eBPF JIT
instructions to maintain the count. For programs that don't do tail
calls themselves, the first two instructions are NOPs.

Signed-off-by: Naveen N. Rao 


Thanks for adding support, Naveen, that's really great! I think 2) seems
fine as well in this context as prologue size can vary quite a bit here,
and depending on program types likelihood of tail call usage as well (but
I wouldn't expect deep nesting). Thanks a lot!


Re: [PATCH 3/3] bpf powerpc: add support for bpf constant blinding

2016-09-23 Thread Daniel Borkmann

On 09/23/2016 10:35 PM, Naveen N. Rao wrote:

In line with similar support for other architectures by Daniel Borkmann.

'MOD Default X' from test_bpf without constant blinding:
84 bytes emitted from JIT compiler (pass:3, flen:7)
d58a4688 + :
0:  nop
4:  nop
8:  std r27,-40(r1)
c:  std r28,-32(r1)
   10:  xor r8,r8,r8
   14:  xor r28,r28,r28
   18:  mr  r27,r3
   1c:  li  r8,66
   20:  cmpwi   r28,0
   24:  bne 0x0030
   28:  li  r8,0
   2c:  b   0x0044
   30:  divwu   r9,r8,r28
   34:  mullw   r9,r28,r9
   38:  subfr8,r9,r8
   3c:  rotlwi  r8,r8,0
   40:  li  r8,66
   44:  ld  r27,-40(r1)
   48:  ld  r28,-32(r1)
   4c:  mr  r3,r8
   50:  blr

... and with constant blinding:
140 bytes emitted from JIT compiler (pass:3, flen:11)
dbd6ab24 + :
0:  nop
4:  nop
8:  std r27,-40(r1)
c:  std r28,-32(r1)
   10:  xor r8,r8,r8
   14:  xor r28,r28,r28
   18:  mr  r27,r3
   1c:  lis r2,-22834
   20:  ori r2,r2,36083
   24:  rotlwi  r2,r2,0
   28:  xorir2,r2,36017
   2c:  xoris   r2,r2,42702
   30:  rotlwi  r2,r2,0
   34:  mr  r8,r2
   38:  rotlwi  r8,r8,0
   3c:  cmpwi   r28,0
   40:  bne 0x004c
   44:  li  r8,0
   48:  b   0x007c
   4c:  divwu   r9,r8,r28
   50:  mullw   r9,r28,r9
   54:  subfr8,r9,r8
   58:  rotlwi  r8,r8,0
   5c:  lis r2,-17137
   60:  ori r2,r2,39065
   64:  rotlwi  r2,r2,0
   68:  xorir2,r2,39131
   6c:  xoris   r2,r2,48399
   70:  rotlwi  r2,r2,0
   74:  mr  r8,r2
   78:  rotlwi  r8,r8,0
   7c:  ld  r27,-40(r1)
   80:  ld  r28,-32(r1)
   84:  mr  r3,r8
   88:  blr

Signed-off-by: Naveen N. Rao 


Acked-by: Daniel Borkmann 


[PATCH 2/2] bpf samples: update tracex5 sample to use __seccomp_filter

2016-09-23 Thread Naveen N. Rao
seccomp_phase1() does not exist anymore. Instead, update sample to use
__seccomp_filter(). While at it, set max locked memory to unlimited.

Signed-off-by: Naveen N. Rao 
---
I am not completely sure if __seccomp_filter is the right place to hook
in. This works for me though. Please review.

Thanks,
Naveen


 samples/bpf/tracex5_kern.c | 16 +++-
 samples/bpf/tracex5_user.c |  3 +++
 2 files changed, 10 insertions(+), 9 deletions(-)

diff --git a/samples/bpf/tracex5_kern.c b/samples/bpf/tracex5_kern.c
index f95f232..fd12d71 100644
--- a/samples/bpf/tracex5_kern.c
+++ b/samples/bpf/tracex5_kern.c
@@ -19,20 +19,18 @@ struct bpf_map_def SEC("maps") progs = {
.max_entries = 1024,
 };
 
-SEC("kprobe/seccomp_phase1")
+SEC("kprobe/__seccomp_filter")
 int bpf_prog1(struct pt_regs *ctx)
 {
-   struct seccomp_data sd;
-
-   bpf_probe_read(, sizeof(sd), (void *)PT_REGS_PARM1(ctx));
+   int sc_nr = (int)PT_REGS_PARM1(ctx);
 
/* dispatch into next BPF program depending on syscall number */
-   bpf_tail_call(ctx, , sd.nr);
+   bpf_tail_call(ctx, , sc_nr);
 
/* fall through -> unknown syscall */
-   if (sd.nr >= __NR_getuid && sd.nr <= __NR_getsid) {
+   if (sc_nr >= __NR_getuid && sc_nr <= __NR_getsid) {
char fmt[] = "syscall=%d (one of get/set uid/pid/gid)\n";
-   bpf_trace_printk(fmt, sizeof(fmt), sd.nr);
+   bpf_trace_printk(fmt, sizeof(fmt), sc_nr);
}
return 0;
 }
@@ -42,7 +40,7 @@ PROG(__NR_write)(struct pt_regs *ctx)
 {
struct seccomp_data sd;
 
-   bpf_probe_read(, sizeof(sd), (void *)PT_REGS_PARM1(ctx));
+   bpf_probe_read(, sizeof(sd), (void *)PT_REGS_PARM2(ctx));
if (sd.args[2] == 512) {
char fmt[] = "write(fd=%d, buf=%p, size=%d)\n";
bpf_trace_printk(fmt, sizeof(fmt),
@@ -55,7 +53,7 @@ PROG(__NR_read)(struct pt_regs *ctx)
 {
struct seccomp_data sd;
 
-   bpf_probe_read(, sizeof(sd), (void *)PT_REGS_PARM1(ctx));
+   bpf_probe_read(, sizeof(sd), (void *)PT_REGS_PARM2(ctx));
if (sd.args[2] > 128 && sd.args[2] <= 1024) {
char fmt[] = "read(fd=%d, buf=%p, size=%d)\n";
bpf_trace_printk(fmt, sizeof(fmt),
diff --git a/samples/bpf/tracex5_user.c b/samples/bpf/tracex5_user.c
index a04dd3c..36b5925 100644
--- a/samples/bpf/tracex5_user.c
+++ b/samples/bpf/tracex5_user.c
@@ -6,6 +6,7 @@
 #include 
 #include "libbpf.h"
 #include "bpf_load.h"
+#include 
 
 /* install fake seccomp program to enable seccomp code path inside the kernel,
  * so that our kprobe attached to seccomp_phase1() can be triggered
@@ -27,8 +28,10 @@ int main(int ac, char **argv)
 {
FILE *f;
char filename[256];
+   struct rlimit r = {RLIM_INFINITY, RLIM_INFINITY};
 
snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]);
+   setrlimit(RLIMIT_MEMLOCK, );
 
if (load_bpf_file(filename)) {
printf("%s", bpf_log_buf);
-- 
2.9.3



[PATCH 1/2] bpf samples: fix compiler errors with sockex2 and sockex3

2016-09-23 Thread Naveen N. Rao
These samples fail to compile as 'struct flow_keys' conflicts with
definition in net/flow_dissector.h. Fix the same by renaming the
structure used in the sample.

Signed-off-by: Naveen N. Rao 
---
 samples/bpf/sockex2_kern.c | 10 +-
 samples/bpf/sockex3_kern.c |  8 
 samples/bpf/sockex3_user.c |  4 ++--
 3 files changed, 11 insertions(+), 11 deletions(-)

diff --git a/samples/bpf/sockex2_kern.c b/samples/bpf/sockex2_kern.c
index ba0e177..44e5846 100644
--- a/samples/bpf/sockex2_kern.c
+++ b/samples/bpf/sockex2_kern.c
@@ -14,7 +14,7 @@ struct vlan_hdr {
__be16 h_vlan_encapsulated_proto;
 };
 
-struct flow_keys {
+struct bpf_flow_keys {
__be32 src;
__be32 dst;
union {
@@ -59,7 +59,7 @@ static inline __u32 ipv6_addr_hash(struct __sk_buff *ctx, 
__u64 off)
 }
 
 static inline __u64 parse_ip(struct __sk_buff *skb, __u64 nhoff, __u64 
*ip_proto,
-struct flow_keys *flow)
+struct bpf_flow_keys *flow)
 {
__u64 verlen;
 
@@ -83,7 +83,7 @@ static inline __u64 parse_ip(struct __sk_buff *skb, __u64 
nhoff, __u64 *ip_proto
 }
 
 static inline __u64 parse_ipv6(struct __sk_buff *skb, __u64 nhoff, __u64 
*ip_proto,
-  struct flow_keys *flow)
+  struct bpf_flow_keys *flow)
 {
*ip_proto = load_byte(skb,
  nhoff + offsetof(struct ipv6hdr, nexthdr));
@@ -96,7 +96,7 @@ static inline __u64 parse_ipv6(struct __sk_buff *skb, __u64 
nhoff, __u64 *ip_pro
return nhoff;
 }
 
-static inline bool flow_dissector(struct __sk_buff *skb, struct flow_keys 
*flow)
+static inline bool flow_dissector(struct __sk_buff *skb, struct bpf_flow_keys 
*flow)
 {
__u64 nhoff = ETH_HLEN;
__u64 ip_proto;
@@ -198,7 +198,7 @@ struct bpf_map_def SEC("maps") hash_map = {
 SEC("socket2")
 int bpf_prog2(struct __sk_buff *skb)
 {
-   struct flow_keys flow;
+   struct bpf_flow_keys flow;
struct pair *value;
u32 key;
 
diff --git a/samples/bpf/sockex3_kern.c b/samples/bpf/sockex3_kern.c
index 41ae2fd..95907f8 100644
--- a/samples/bpf/sockex3_kern.c
+++ b/samples/bpf/sockex3_kern.c
@@ -61,7 +61,7 @@ struct vlan_hdr {
__be16 h_vlan_encapsulated_proto;
 };
 
-struct flow_keys {
+struct bpf_flow_keys {
__be32 src;
__be32 dst;
union {
@@ -88,7 +88,7 @@ static inline __u32 ipv6_addr_hash(struct __sk_buff *ctx, 
__u64 off)
 }
 
 struct globals {
-   struct flow_keys flow;
+   struct bpf_flow_keys flow;
 };
 
 struct bpf_map_def SEC("maps") percpu_map = {
@@ -114,14 +114,14 @@ struct pair {
 
 struct bpf_map_def SEC("maps") hash_map = {
.type = BPF_MAP_TYPE_HASH,
-   .key_size = sizeof(struct flow_keys),
+   .key_size = sizeof(struct bpf_flow_keys),
.value_size = sizeof(struct pair),
.max_entries = 1024,
 };
 
 static void update_stats(struct __sk_buff *skb, struct globals *g)
 {
-   struct flow_keys key = g->flow;
+   struct bpf_flow_keys key = g->flow;
struct pair *value;
 
value = bpf_map_lookup_elem(_map, );
diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c
index d4184ab..3fcfd8c4 100644
--- a/samples/bpf/sockex3_user.c
+++ b/samples/bpf/sockex3_user.c
@@ -7,7 +7,7 @@
 #include 
 #include 
 
-struct flow_keys {
+struct bpf_flow_keys {
__be32 src;
__be32 dst;
union {
@@ -49,7 +49,7 @@ int main(int argc, char **argv)
(void) f;
 
for (i = 0; i < 5; i++) {
-   struct flow_keys key = {}, next_key;
+   struct bpf_flow_keys key = {}, next_key;
struct pair value;
 
sleep(1);
-- 
2.9.3



[PATCH 3/3] bpf powerpc: add support for bpf constant blinding

2016-09-23 Thread Naveen N. Rao
In line with similar support for other architectures by Daniel Borkmann.

'MOD Default X' from test_bpf without constant blinding:
84 bytes emitted from JIT compiler (pass:3, flen:7)
d58a4688 + :
   0:   nop
   4:   nop
   8:   std r27,-40(r1)
   c:   std r28,-32(r1)
  10:   xor r8,r8,r8
  14:   xor r28,r28,r28
  18:   mr  r27,r3
  1c:   li  r8,66
  20:   cmpwi   r28,0
  24:   bne 0x0030
  28:   li  r8,0
  2c:   b   0x0044
  30:   divwu   r9,r8,r28
  34:   mullw   r9,r28,r9
  38:   subfr8,r9,r8
  3c:   rotlwi  r8,r8,0
  40:   li  r8,66
  44:   ld  r27,-40(r1)
  48:   ld  r28,-32(r1)
  4c:   mr  r3,r8
  50:   blr

... and with constant blinding:
140 bytes emitted from JIT compiler (pass:3, flen:11)
dbd6ab24 + :
   0:   nop
   4:   nop
   8:   std r27,-40(r1)
   c:   std r28,-32(r1)
  10:   xor r8,r8,r8
  14:   xor r28,r28,r28
  18:   mr  r27,r3
  1c:   lis r2,-22834
  20:   ori r2,r2,36083
  24:   rotlwi  r2,r2,0
  28:   xorir2,r2,36017
  2c:   xoris   r2,r2,42702
  30:   rotlwi  r2,r2,0
  34:   mr  r8,r2
  38:   rotlwi  r8,r8,0
  3c:   cmpwi   r28,0
  40:   bne 0x004c
  44:   li  r8,0
  48:   b   0x007c
  4c:   divwu   r9,r8,r28
  50:   mullw   r9,r28,r9
  54:   subfr8,r9,r8
  58:   rotlwi  r8,r8,0
  5c:   lis r2,-17137
  60:   ori r2,r2,39065
  64:   rotlwi  r2,r2,0
  68:   xorir2,r2,39131
  6c:   xoris   r2,r2,48399
  70:   rotlwi  r2,r2,0
  74:   mr  r8,r2
  78:   rotlwi  r8,r8,0
  7c:   ld  r27,-40(r1)
  80:   ld  r28,-32(r1)
  84:   mr  r3,r8
  88:   blr

Signed-off-by: Naveen N. Rao 
---
 arch/powerpc/net/bpf_jit64.h  |  9 +
 arch/powerpc/net/bpf_jit_comp64.c | 36 +---
 2 files changed, 34 insertions(+), 11 deletions(-)

diff --git a/arch/powerpc/net/bpf_jit64.h b/arch/powerpc/net/bpf_jit64.h
index 038e00b..62fa758 100644
--- a/arch/powerpc/net/bpf_jit64.h
+++ b/arch/powerpc/net/bpf_jit64.h
@@ -39,10 +39,10 @@
 #ifndef __ASSEMBLY__
 
 /* BPF register usage */
-#define SKB_HLEN_REG   (MAX_BPF_REG + 0)
-#define SKB_DATA_REG   (MAX_BPF_REG + 1)
-#define TMP_REG_1  (MAX_BPF_REG + 2)
-#define TMP_REG_2  (MAX_BPF_REG + 3)
+#define SKB_HLEN_REG   (MAX_BPF_JIT_REG + 0)
+#define SKB_DATA_REG   (MAX_BPF_JIT_REG + 1)
+#define TMP_REG_1  (MAX_BPF_JIT_REG + 2)
+#define TMP_REG_2  (MAX_BPF_JIT_REG + 3)
 
 /* BPF to ppc register mappings */
 static const int b2p[] = {
@@ -62,6 +62,7 @@ static const int b2p[] = {
/* frame pointer aka BPF_REG_10 */
[BPF_REG_FP] = 31,
/* eBPF jit internal registers */
+   [BPF_REG_AX] = 2,
[SKB_HLEN_REG] = 25,
[SKB_DATA_REG] = 26,
[TMP_REG_1] = 9,
diff --git a/arch/powerpc/net/bpf_jit_comp64.c 
b/arch/powerpc/net/bpf_jit_comp64.c
index 3ec29d6..0fe98a5 100644
--- a/arch/powerpc/net/bpf_jit_comp64.c
+++ b/arch/powerpc/net/bpf_jit_comp64.c
@@ -974,21 +974,37 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *fp)
int pass;
int flen;
struct bpf_binary_header *bpf_hdr;
+   struct bpf_prog *org_fp = fp;
+   struct bpf_prog *tmp_fp;
+   bool bpf_blinded = false;
 
if (!bpf_jit_enable)
-   return fp;
+   return org_fp;
+
+   tmp_fp = bpf_jit_blind_constants(org_fp);
+   if (IS_ERR(tmp_fp))
+   return org_fp;
+
+   if (tmp_fp != org_fp) {
+   bpf_blinded = true;
+   fp = tmp_fp;
+   }
 
flen = fp->len;
addrs = kzalloc((flen+1) * sizeof(*addrs), GFP_KERNEL);
-   if (addrs == NULL)
-   return fp;
+   if (addrs == NULL) {
+   fp = org_fp;
+   goto out;
+   }
+
+   memset(, 0, sizeof(struct codegen_context));
 
-   cgctx.idx = 0;
-   cgctx.seen = 0;
/* Scouting faux-generate pass 0 */
-   if (bpf_jit_build_body(fp, 0, , addrs))
+   if (bpf_jit_build_body(fp, 0, , addrs)) {
/* We hit something illegal or unsupported. */
+   fp = org_fp;
goto out;
+   }
 
/*
 * Pretend to build prologue, given the features we've seen.  This will
@@ -1003,8 +1019,10 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *fp)
 
bpf_hdr = bpf_jit_binary_alloc(alloclen, , 4,
bpf_jit_fill_ill_insns);
-   if (!bpf_hdr)
+   if (!bpf_hdr) {
+   fp = org_fp;
goto out;
+   }
 
code_base = (u32 *)(image + FUNCTION_DESCR_SIZE);
 
@@ -1041,6 +1059,10 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *fp)
 
 out:
kfree(addrs);
+
+   if (bpf_blinded)
+   bpf_jit_prog_release_other(fp, fp == org_fp ? tmp_fp : org_fp);
+
return fp;
 }
 
-- 
2.9.3



[PATCH 2/3] bpf powerpc: implement support for tail calls

2016-09-23 Thread Naveen N. Rao
Tail calls allow JIT'ed eBPF programs to call into other JIT'ed eBPF
programs. This can be achieved either by:
(1) retaining the stack setup by the first eBPF program and having all
subsequent eBPF programs re-using it, or,
(2) by unwinding/tearing down the stack and having each eBPF program
deal with its own stack as it sees fit.

To ensure that this does not create loops, there is a limit to how many
tail calls can be done (currently 32). This requires the JIT'ed code to
maintain a count of the number of tail calls done so far.

Approach (1) is simple, but requires every eBPF program to have (almost)
the same prologue/epilogue, regardless of whether they need it. This is
inefficient for small eBPF programs which may not sometimes need a
prologue at all. As such, to minimize impact of tail call
implementation, we use approach (2) here which needs each eBPF program
in the chain to use its own prologue/epilogue. This is not ideal when
many tail calls are involved and when all the eBPF programs in the chain
have similar prologue/epilogue. However, the impact is restricted to
programs that do tail calls. Individual eBPF programs are not affected.

We maintain the tail call count in a fixed location on the stack and
updated tail call count values are passed in through this. The very
first eBPF program in a chain sets this up to 0 (the first 2
instructions). Subsequent tail calls skip the first two eBPF JIT
instructions to maintain the count. For programs that don't do tail
calls themselves, the first two instructions are NOPs.

Signed-off-by: Naveen N. Rao 
---
 arch/powerpc/include/asm/ppc-opcode.h |   2 +
 arch/powerpc/net/bpf_jit.h|   2 +
 arch/powerpc/net/bpf_jit64.h  |   1 +
 arch/powerpc/net/bpf_jit_comp64.c | 149 +++---
 4 files changed, 126 insertions(+), 28 deletions(-)

diff --git a/arch/powerpc/include/asm/ppc-opcode.h 
b/arch/powerpc/include/asm/ppc-opcode.h
index 127ebf5..54ff8ce 100644
--- a/arch/powerpc/include/asm/ppc-opcode.h
+++ b/arch/powerpc/include/asm/ppc-opcode.h
@@ -236,6 +236,7 @@
 #define PPC_INST_STWU  0x9400
 #define PPC_INST_MFLR  0x7c0802a6
 #define PPC_INST_MTLR  0x7c0803a6
+#define PPC_INST_MTCTR 0x7c0903a6
 #define PPC_INST_CMPWI 0x2c00
 #define PPC_INST_CMPDI 0x2c20
 #define PPC_INST_CMPW  0x7c00
@@ -250,6 +251,7 @@
 #define PPC_INST_SUB   0x7c50
 #define PPC_INST_BLR   0x4e800020
 #define PPC_INST_BLRL  0x4e800021
+#define PPC_INST_BCTR  0x4e800420
 #define PPC_INST_MULLD 0x7c0001d2
 #define PPC_INST_MULLW 0x7c0001d6
 #define PPC_INST_MULHWU0x7c16
diff --git a/arch/powerpc/net/bpf_jit.h b/arch/powerpc/net/bpf_jit.h
index d5301b6..89f7007 100644
--- a/arch/powerpc/net/bpf_jit.h
+++ b/arch/powerpc/net/bpf_jit.h
@@ -40,6 +40,8 @@
 #define PPC_BLR()  EMIT(PPC_INST_BLR)
 #define PPC_BLRL() EMIT(PPC_INST_BLRL)
 #define PPC_MTLR(r)EMIT(PPC_INST_MTLR | ___PPC_RT(r))
+#define PPC_BCTR() EMIT(PPC_INST_BCTR)
+#define PPC_MTCTR(r)   EMIT(PPC_INST_MTCTR | ___PPC_RT(r))
 #define PPC_ADDI(d, a, i)  EMIT(PPC_INST_ADDI | ___PPC_RT(d) |   \
 ___PPC_RA(a) | IMM_L(i))
 #define PPC_MR(d, a)   PPC_OR(d, a, a)
diff --git a/arch/powerpc/net/bpf_jit64.h b/arch/powerpc/net/bpf_jit64.h
index a1645d7..038e00b 100644
--- a/arch/powerpc/net/bpf_jit64.h
+++ b/arch/powerpc/net/bpf_jit64.h
@@ -88,6 +88,7 @@ DECLARE_LOAD_FUNC(sk_load_byte);
 #define SEEN_FUNC  0x1000 /* might call external helpers */
 #define SEEN_STACK 0x2000 /* uses BPF stack */
 #define SEEN_SKB   0x4000 /* uses sk_buff */
+#define SEEN_TAILCALL  0x8000 /* uses tail calls */
 
 struct codegen_context {
/*
diff --git a/arch/powerpc/net/bpf_jit_comp64.c 
b/arch/powerpc/net/bpf_jit_comp64.c
index 5f8c91f..3ec29d6 100644
--- a/arch/powerpc/net/bpf_jit_comp64.c
+++ b/arch/powerpc/net/bpf_jit_comp64.c
@@ -17,6 +17,7 @@
 #include 
 #include 
 #include 
+#include 
 
 #include "bpf_jit64.h"
 
@@ -77,6 +78,11 @@ static int bpf_jit_stack_local(struct codegen_context *ctx)
return -(BPF_PPC_STACK_SAVE + 16);
 }
 
+static int bpf_jit_stack_tailcallcnt(struct codegen_context *ctx)
+{
+   return bpf_jit_stack_local(ctx) + 8;
+}
+
 static int bpf_jit_stack_offsetof(struct codegen_context *ctx, int reg)
 {
if (reg >= BPF_PPC_NVR_MIN && reg < 32)
@@ -102,33 +108,25 @@ static void bpf_jit_emit_skb_loads(u32 *image, struct 
codegen_context *ctx)
PPC_BPF_LL(b2p[SKB_DATA_REG], 3, offsetof(struct sk_buff, data));
 }
 
-static void bpf_jit_emit_func_call(u32 *image, struct codegen_context *ctx, 
u64 func)
+static void bpf_jit_build_prologue(u32 *image, struct 

[PATCH 1/3] bpf powerpc: introduce accessors for using the tmp local stack space

2016-09-23 Thread Naveen N. Rao
While at it, ensure that the location of the local save area is
consistent whether or not we setup our own stackframe. This property is
utilised in the next patch that adds support for tail calls.

Signed-off-by: Naveen N. Rao 
---
 arch/powerpc/net/bpf_jit64.h  | 16 +---
 arch/powerpc/net/bpf_jit_comp64.c | 79 ++-
 2 files changed, 55 insertions(+), 40 deletions(-)

diff --git a/arch/powerpc/net/bpf_jit64.h b/arch/powerpc/net/bpf_jit64.h
index 5046d6f..a1645d7 100644
--- a/arch/powerpc/net/bpf_jit64.h
+++ b/arch/powerpc/net/bpf_jit64.h
@@ -16,22 +16,25 @@
 
 /*
  * Stack layout:
+ * Ensure the top half (upto local_tmp_var) stays consistent
+ * with our redzone usage.
  *
  * [   prev sp ] <-
  * [   nv gpr save area] 8*8   |
+ * [tail_call_cnt  ] 8 |
+ * [local_tmp_var  ] 8 |
  * fp (r31) -->[   ebpf stack space] 512   |
- * [  local/tmp var space  ] 16|
  * [ frame header  ] 32/112|
  * sp (r1) --->[stack pointer  ] --
  */
 
-/* for bpf JIT code internal usage */
-#define BPF_PPC_STACK_LOCALS   16
 /* for gpr non volatile registers BPG_REG_6 to 10, plus skb cache registers */
 #define BPF_PPC_STACK_SAVE (8*8)
+/* for bpf JIT code internal usage */
+#define BPF_PPC_STACK_LOCALS   16
 /* Ensure this is quadword aligned */
-#define BPF_PPC_STACKFRAME (STACK_FRAME_MIN_SIZE + BPF_PPC_STACK_LOCALS + \
-MAX_BPF_STACK + BPF_PPC_STACK_SAVE)
+#define BPF_PPC_STACKFRAME (STACK_FRAME_MIN_SIZE + MAX_BPF_STACK + \
+BPF_PPC_STACK_LOCALS + BPF_PPC_STACK_SAVE)
 
 #ifndef __ASSEMBLY__
 
@@ -65,6 +68,9 @@ static const int b2p[] = {
[TMP_REG_2] = 10
 };
 
+/* PPC NVR range -- update this if we ever use NVRs below r24 */
+#define BPF_PPC_NVR_MIN24
+
 /* Assembly helpers */
 #define DECLARE_LOAD_FUNC(func)u64 func(u64 r3, u64 r4);   
\
u64 func##_negative_offset(u64 r3, u64 r4); 
\
diff --git a/arch/powerpc/net/bpf_jit_comp64.c 
b/arch/powerpc/net/bpf_jit_comp64.c
index 6073b78..5f8c91f 100644
--- a/arch/powerpc/net/bpf_jit_comp64.c
+++ b/arch/powerpc/net/bpf_jit_comp64.c
@@ -58,6 +58,35 @@ static inline bool bpf_has_stack_frame(struct 
codegen_context *ctx)
return ctx->seen & SEEN_FUNC || bpf_is_seen_register(ctx, BPF_REG_FP);
 }
 
+/*
+ * When not setting up our own stackframe, the redzone usage is:
+ *
+ * [   prev sp ] <-
+ * [ ...   ]   |
+ * sp (r1) --->[stack pointer  ] --
+ * [   nv gpr save area] 8*8
+ * [tail_call_cnt  ] 8
+ * [local_tmp_var  ] 8
+ * [   unused red zone ] 208 bytes protected
+ */
+static int bpf_jit_stack_local(struct codegen_context *ctx)
+{
+   if (bpf_has_stack_frame(ctx))
+   return STACK_FRAME_MIN_SIZE + MAX_BPF_STACK;
+   else
+   return -(BPF_PPC_STACK_SAVE + 16);
+}
+
+static int bpf_jit_stack_offsetof(struct codegen_context *ctx, int reg)
+{
+   if (reg >= BPF_PPC_NVR_MIN && reg < 32)
+   return (bpf_has_stack_frame(ctx) ? BPF_PPC_STACKFRAME : 0)
+   - (8 * (32 - reg));
+
+   pr_err("BPF JIT is asking about unknown registers");
+   BUG();
+}
+
 static void bpf_jit_emit_skb_loads(u32 *image, struct codegen_context *ctx)
 {
/*
@@ -100,9 +129,8 @@ static void bpf_jit_emit_func_call(u32 *image, struct 
codegen_context *ctx, u64
 static void bpf_jit_build_prologue(u32 *image, struct codegen_context *ctx)
 {
int i;
-   bool new_stack_frame = bpf_has_stack_frame(ctx);
 
-   if (new_stack_frame) {
+   if (bpf_has_stack_frame(ctx)) {
/*
 * We need a stack frame, but we don't necessarily need to
 * save/restore LR unless we call other functions
@@ -122,9 +150,7 @@ static void bpf_jit_build_prologue(u32 *image, struct 
codegen_context *ctx)
 */
for (i = BPF_REG_6; i <= BPF_REG_10; i++)
if (bpf_is_seen_register(ctx, i))
-   PPC_BPF_STL(b2p[i], 1,
-   (new_stack_frame ? BPF_PPC_STACKFRAME : 0) -
-   (8 * (32 - b2p[i])));
+   PPC_BPF_STL(b2p[i], 1, bpf_jit_stack_offsetof(ctx, 
b2p[i]));
 
/*
 * Save additional non-volatile regs if we cache skb
@@ -132,22 +158,21 @@ static void bpf_jit_build_prologue(u32 *image, struct 
codegen_context *ctx)
 */
if (ctx->seen & SEEN_SKB) {
PPC_BPF_STL(b2p[SKB_HLEN_REG], 1,

Re: [PATCH 2/2] powernv:idle:Implement lite variant of power_enter_stop

2016-09-23 Thread Gautham R Shenoy
Hi Michael,

On Fri, Sep 23, 2016 at 09:03:45PM +1000, Michael Ellerman wrote:
> "Gautham R. Shenoy"  writes:
> 
> > From: "Gautham R. Shenoy" 
> >
> > This patch adds a function named power_enter_stop_lite() that can
> > execute a stop instruction when ESL and EC bits are set to zero in the
> > PSSCR.  The function handles the wake-up from idle at the instruction
> > immediately after the stop instruction.
> >
> > If the flag OPAL_PM_WAKEUP_AT_NEXT_INST[1] is set in the device tree
> > for a stop state, then use the lite variant for that particular stop
> > state.
> 
> Hi Gautham,
> 
> It seems to me that this would be cleaner if it was modelled as a new
> stop state? Surely it must have different power saving characteristics
> to the existing state?

It is supposed to be a new stop state, whose behaviour is different
from the existing stop states in terms of where it wakes up from stop.

You are right, it has different power saving characteristics to the
existing state.

> 
> > [1] : The corresponding patch in skiboot that defines
> >   OPAL_PM_WAKEUP_AT_NEXT_INST and enables it in the device tree
> >   can be found here:
> >   https://lists.ozlabs.org/pipermail/skiboot/2016-September/004805.html
> 
> Which says "This will reduce the exit latency of the idle state", and
> yet it doesn't change any of the latency/residency values?
> 
> If all it does is reduce the exit latency, then shouldn't we always use
> it? Presumably it also saves less power?

It does save less power compared to the corresponding variant where
ESL=EC=1.

> 
> > diff --git a/arch/powerpc/kernel/idle_book3s.S 
> > b/arch/powerpc/kernel/idle_book3s.S
> > index 32d666b..47ee106 100644
> > --- a/arch/powerpc/kernel/idle_book3s.S
> > +++ b/arch/powerpc/kernel/idle_book3s.S
> > @@ -43,6 +43,8 @@
> >  #define PSSCR_HV_TEMPLATE  PSSCR_ESL | PSSCR_EC | \
> > PSSCR_PSLL_MASK | PSSCR_TR_MASK | \
> > PSSCR_MTL_MASK
> > +#define PSSCR_HV_TEMPLATE_LITE PSSCR_PSLL_MASK | PSSCR_TR_MASK | \
> > +PSSCR_MTL_MASK
> 
> Why do we have these at all? Firmware tells us the PSSCR values to use
> in the "ibm,cpu-idle-state-psscr" property.
> 
> If we just used what firmware gave us then we wouldn't need the above,
> or the juggling below.

Let me rework the patch to use the cpu-idle-state-psscr property which
is currently set to 0 in the firmware and
cpu-idle-state-psscr-mask which is set to 0xF for all the stop
states.

I agree, we can do without the hardcoding of the mask in the
kernel.

> 
> > @@ -333,13 +349,19 @@ ALT_FTR_SECTION_END_NESTED_IFSET(CPU_FTR_ARCH_207S, 
> > 66);  \
> >  
> >  /*
> >   * r3 - requested stop state
> > + * r4 - Indicates if the lite variant with ESL=EC=0 should be executed.
> >   */
> >  _GLOBAL(power9_idle_stop)
> > -   LOAD_REG_IMMEDIATE(r4, PSSCR_HV_TEMPLATE)
> > -   or  r4,r4,r3
> > +   cmpdi   r4, 1
> > +   bne 4f
> > +   LOAD_REG_IMMEDIATE(r4, PSSCR_HV_TEMPLATE_LITE)
> > +   LOAD_REG_ADDR(r5,power_enter_stop_lite)
> > +   b   5f
> > +4: LOAD_REG_IMMEDIATE(r4, PSSCR_HV_TEMPLATE)
> > +   LOAD_REG_ADDR(r5,power_enter_stop)
> > +5: or  r4,r4,r3
> > mtspr   SPRN_PSSCR, r4
> > li  r4, 1
> > -   LOAD_REG_ADDR(r5,power_enter_stop)
> > b   pnv_powersave_common
> > /* No return */
> >  /*
> 
> > diff --git a/arch/powerpc/platforms/powernv/idle.c 
> > b/arch/powerpc/platforms/powernv/idle.c
> > index 479c256..c3d3fed 100644
> > --- a/arch/powerpc/platforms/powernv/idle.c
> > +++ b/arch/powerpc/platforms/powernv/idle.c
> > @@ -244,8 +244,15 @@ static DEVICE_ATTR(fastsleep_workaround_applyonce, 
> > 0600,
> >  static void power9_idle(void)
> >  {
> > /* Requesting stop state 0 */
> > -   power9_idle_stop(0);
> >  }
> 
> That seems like the root of the problem, why aren't we passing a PSSCR
> value here?
> 
> I also don't see us using the psscr-mask property anywhere. Why isn't
> that a bug?

Because we are only setting the Requested Level field which is the
bottom 4 bits. Everything else is taken from the hardcoded mask, which
is not incorrect, but not a very flexible design.

Thanks for the comments Michael. I will come back with a cleaner
patch.

> 
> cheers
> 

--
Thanks and Regards
gautham.



ehea crash on boot

2016-09-23 Thread Denis Kirjanov
Heh, another thing to debug :)

mm: Hashing failure ! EA=0xd80080124040 access=0x800e
current=NetworkManager
trap=0x300 vsid=0x13d349c ssize=1 base psize=2 psize 2 pte=0xc0003bc0300301ae
mm: Hashing failure ! EA=0xd80080124040 access=0x800e
current=NetworkManager
trap=0x300 vsid=0x13d349c ssize=1 base psize=2 psize 2 pte=0xc0003bc0300301ae
Unable to handle kernel paging request for data at address 0xd80080124040
Faulting instruction address: 0xc06f21a0
cpu 0x8: Vector: 300 (Data Access) at [c005a8b92b50]
pc: c06f21a0: .ehea_create_cq+0x160/0x230
lr: c06f2164: .ehea_create_cq+0x124/0x230
sp: c005a8b92dd0
msr: 80009032
dar: d80080124040
dsisr: 4200
current = 0xc005a8b68200
paca = 0xcea94000 softe: 0 irq_happened: 0x01
pid = 6787, comm = NetworkManager
Linux version 4.8.0-rc6-00214-g4cea877 (kda@ps700) (gcc version 4.8.5
20150623 (Red Hat 4.8.5-4) (GCC) ) #1 SMP Fri Sep 23 15:01:08 MSK 2016
enter ? for help
[c005a8b92dd0] c06f2140 .ehea_create_cq+0x100/0x230 (unreliable)
[c005a8b92e70] c06ed448 .ehea_up+0x288/0xed0
[c005a8b92fe0] c06ee314 .ehea_open+0x44/0x130
[c005a8b93070] c0812324 .__dev_open+0x154/0x220
[c005a8b93110] c0812734 .__dev_change_flags+0xd4/0x1e0
[c005a8b931b0] c081286c .dev_change_flags+0x2c/0x80
[c005a8b93240] c0829f0c .do_setlink+0x37c/0xe50
[c005a8b933c0] c082c884 .rtnl_newlink+0x5e4/0x9b0
[c005a8b936d0] c082cd08 .rtnetlink_rcv_msg+0xb8/0x2f0
[c005a8b937a0] c084e25c .netlink_rcv_skb+0x12c/0x150
[c005a8b93830] c0829458 .rtnetlink_rcv+0x38/0x60
[c005a8b938b0] c084d814 .netlink_unicast+0x1e4/0x350
[c005a8b93960] c084def8 .netlink_sendmsg+0x418/0x480
[c005a8b93a40] c07defac .sock_sendmsg+0x2c/0x60
[c005a8b93ab0] c07e0cbc .___sys_sendmsg+0x30c/0x320
[c005a8b93c90] c07e21bc .__sys_sendmsg+0x4c/0xb0
[c005a8b93d80] c07e2dec .SyS_socketcall+0x34c/0x3d0
[c005a8b93e30] c000946c system_call+0x38/0x108


Re: [PATCH v2] powerpc/mm: export current mmu mode info

2016-09-23 Thread Michael Ellerman
Hari Bathini  writes:

> diff --git a/arch/powerpc/include/asm/mmu.h b/arch/powerpc/include/asm/mmu.h
> index e2fb408..558987c 100644
> --- a/arch/powerpc/include/asm/mmu.h
> +++ b/arch/powerpc/include/asm/mmu.h
> @@ -199,6 +199,21 @@ static inline void mmu_clear_feature(unsigned long 
> feature)
>  
>  extern unsigned int __start___mmu_ftr_fixup, __stop___mmu_ftr_fixup;
>  
> +/*
> + * Possible MMU modes
> + */
> +#define MMU_MODE_NONE   0
> +#define MMU_MODE_RADIX  1
> +#define MMU_MODE_HASH   2
> +#define MMU_MODE_HASH32 3
> +#define MMU_MODE_NOHASH 4
> +#define MMU_MODE_NOHASH32   5

These are already defined in the same file:

/*
 * MMU families
 */
#define MMU_FTR_HPTE_TABLE  ASM_CONST(0x0001)
#define MMU_FTR_TYPE_8xxASM_CONST(0x0002)
#define MMU_FTR_TYPE_40xASM_CONST(0x0004)
#define MMU_FTR_TYPE_44xASM_CONST(0x0008)
#define MMU_FTR_TYPE_FSL_E  ASM_CONST(0x0010)
#define MMU_FTR_TYPE_47xASM_CONST(0x0020)
#define MMU_FTR_TYPE_RADIX  ASM_CONST(0x0040)

And the values for the current CPU are in cur_cpu_spec->mmu_features.

So if you must export anything, make it that value, and hopefully the
rest of the patch goes away.

cheers


Re: [PATCH 2/2] powernv:idle:Implement lite variant of power_enter_stop

2016-09-23 Thread Michael Ellerman
"Gautham R. Shenoy"  writes:

> From: "Gautham R. Shenoy" 
>
> This patch adds a function named power_enter_stop_lite() that can
> execute a stop instruction when ESL and EC bits are set to zero in the
> PSSCR.  The function handles the wake-up from idle at the instruction
> immediately after the stop instruction.
>
> If the flag OPAL_PM_WAKEUP_AT_NEXT_INST[1] is set in the device tree
> for a stop state, then use the lite variant for that particular stop
> state.

Hi Gautham,

It seems to me that this would be cleaner if it was modelled as a new
stop state? Surely it must have different power saving characteristics
to the existing state?

> [1] : The corresponding patch in skiboot that defines
>   OPAL_PM_WAKEUP_AT_NEXT_INST and enables it in the device tree
>   can be found here:
>   https://lists.ozlabs.org/pipermail/skiboot/2016-September/004805.html

Which says "This will reduce the exit latency of the idle state", and
yet it doesn't change any of the latency/residency values?

If all it does is reduce the exit latency, then shouldn't we always use
it? Presumably it also saves less power?

> diff --git a/arch/powerpc/kernel/idle_book3s.S 
> b/arch/powerpc/kernel/idle_book3s.S
> index 32d666b..47ee106 100644
> --- a/arch/powerpc/kernel/idle_book3s.S
> +++ b/arch/powerpc/kernel/idle_book3s.S
> @@ -43,6 +43,8 @@
>  #define PSSCR_HV_TEMPLATEPSSCR_ESL | PSSCR_EC | \
>   PSSCR_PSLL_MASK | PSSCR_TR_MASK | \
>   PSSCR_MTL_MASK
> +#define PSSCR_HV_TEMPLATE_LITE   PSSCR_PSLL_MASK | PSSCR_TR_MASK | \
> +  PSSCR_MTL_MASK

Why do we have these at all? Firmware tells us the PSSCR values to use
in the "ibm,cpu-idle-state-psscr" property.

If we just used what firmware gave us then we wouldn't need the above,
or the juggling below.

> @@ -333,13 +349,19 @@ ALT_FTR_SECTION_END_NESTED_IFSET(CPU_FTR_ARCH_207S, 
> 66);\
>  
>  /*
>   * r3 - requested stop state
> + * r4 - Indicates if the lite variant with ESL=EC=0 should be executed.
>   */
>  _GLOBAL(power9_idle_stop)
> - LOAD_REG_IMMEDIATE(r4, PSSCR_HV_TEMPLATE)
> - or  r4,r4,r3
> + cmpdi   r4, 1
> + bne 4f
> + LOAD_REG_IMMEDIATE(r4, PSSCR_HV_TEMPLATE_LITE)
> + LOAD_REG_ADDR(r5,power_enter_stop_lite)
> + b   5f
> +4:   LOAD_REG_IMMEDIATE(r4, PSSCR_HV_TEMPLATE)
> + LOAD_REG_ADDR(r5,power_enter_stop)
> +5:   or  r4,r4,r3
>   mtspr   SPRN_PSSCR, r4
>   li  r4, 1
> - LOAD_REG_ADDR(r5,power_enter_stop)
>   b   pnv_powersave_common
>   /* No return */
>  /*

> diff --git a/arch/powerpc/platforms/powernv/idle.c 
> b/arch/powerpc/platforms/powernv/idle.c
> index 479c256..c3d3fed 100644
> --- a/arch/powerpc/platforms/powernv/idle.c
> +++ b/arch/powerpc/platforms/powernv/idle.c
> @@ -244,8 +244,15 @@ static DEVICE_ATTR(fastsleep_workaround_applyonce, 0600,
>  static void power9_idle(void)
>  {
>   /* Requesting stop state 0 */
> - power9_idle_stop(0);
>  }

That seems like the root of the problem, why aren't we passing a PSSCR
value here?

I also don't see us using the psscr-mask property anywhere. Why isn't
that a bug?

cheers


Re: [PATCH] percpu: improve generic percpu modify-return implementation

2016-09-23 Thread Nicholas Piggin
On Thu, 22 Sep 2016 12:07:49 -0400
Tejun Heo  wrote:

> Hello,
> 
> On Thu, Sep 22, 2016 at 02:35:00PM +1000, Nicholas Piggin wrote:
> > Well thank you, how about you?  
> 
> Heh, can't complain.  Hope to see you around sometime.  It's been
> forever.

Yeah, it has been. Hopefully I'll see you around.


> > Trying a new mail client, sorry. It *seems* to be working now, how's
> > this?  
> 
> Hmm... Still encoded.

It looks to be a helpful surprise feature of claws. Any line starting with
the word "From" make it go q-p due to some mail servers treating that
differently. Sigh.

> 
> > From d0cb9052d6f4c31d24f999b7b0cecb34681eee9b Mon Sep 17 00:00:00 2001
> > From: Nicholas Piggin 
> > Date: Wed, 21 Sep 2016 18:23:43 +1000
> > Subject: [PATCH] percpu: improve generic percpu modify-return 
> > implementations
> > 
> > Some architectures require an additional load to find the address of
> > percpu pointers. In some implemenatations, the C aliasing rules do not
> > allow the result of that load to be kept over the store that modifies
> > the percpu variable, which causes additional loads.
> > 
> > Work around this by finding the pointer first, then operating on that.
> > 
> > It's also possible to mark things as restrict and those kind of games,
> > but that can require larger and arch specific changes.  
> 
> QP-decoded and applied to percpu/for-4.9.
> 
> Thanks.
> 

Thanks!


Re: [PATCH kernel 14/15] vfio/spapr_tce: Export container API for external users

2016-09-23 Thread David Gibson
On Wed, Sep 21, 2016 at 04:56:52PM +1000, Alexey Kardashevskiy wrote:
> On 07/09/16 19:09, Alexey Kardashevskiy wrote:
> > On 29/08/16 23:27, David Gibson wrote:
> >> On Mon, Aug 29, 2016 at 04:35:15PM +1000, Alexey Kardashevskiy wrote:
> >>> On 18/08/16 10:22, Alexey Kardashevskiy wrote:
>  On 17/08/16 13:17, David Gibson wrote:
> > On Fri, Aug 12, 2016 at 09:22:01AM -0600, Alex Williamson wrote:
> >> On Fri, 12 Aug 2016 15:46:01 +1000
> >> David Gibson  wrote:
> >>
> >>> On Wed, Aug 10, 2016 at 10:46:30AM -0600, Alex Williamson wrote:
>  On Wed, 10 Aug 2016 15:37:17 +1000
>  Alexey Kardashevskiy  wrote:
>    
> > On 09/08/16 22:16, Alex Williamson wrote:  
> >> On Tue, 9 Aug 2016 15:19:39 +1000
> >> Alexey Kardashevskiy  wrote:
> >> 
> >>> On 09/08/16 02:43, Alex Williamson wrote:
>  On Wed,  3 Aug 2016 18:40:55 +1000
>  Alexey Kardashevskiy  wrote:
>    
> > This exports helpers which are needed to keep a VFIO container 
> > in
> > memory while there are external users such as KVM.
> >
> > Signed-off-by: Alexey Kardashevskiy 
> > ---
> >  drivers/vfio/vfio.c | 30 
> > ++
> >  drivers/vfio/vfio_iommu_spapr_tce.c | 16 +++-
> >  include/linux/vfio.h|  6 ++
> >  3 files changed, 51 insertions(+), 1 deletion(-)
> >
> > diff --git a/drivers/vfio/vfio.c b/drivers/vfio/vfio.c
> > index d1d70e0..baf6a9c 100644
> > --- a/drivers/vfio/vfio.c
> > +++ b/drivers/vfio/vfio.c
> > @@ -1729,6 +1729,36 @@ long 
> > vfio_external_check_extension(struct vfio_group *group, 
> > unsigned long arg)
> >  EXPORT_SYMBOL_GPL(vfio_external_check_extension);
> >  
> >  /**
> > + * External user API for containers, exported by symbols to be 
> > linked
> > + * dynamically.
> > + *
> > + */
> > +struct vfio_container *vfio_container_get_ext(struct file 
> > *filep)
> > +{
> > +   struct vfio_container *container = filep->private_data;
> > +
> > +   if (filep->f_op != _fops)
> > +   return ERR_PTR(-EINVAL);
> > +
> > +   vfio_container_get(container);
> > +
> > +   return container;
> > +}
> > +EXPORT_SYMBOL_GPL(vfio_container_get_ext);
> > +
> > +void vfio_container_put_ext(struct vfio_container *container)
> > +{
> > +   vfio_container_put(container);
> > +}
> > +EXPORT_SYMBOL_GPL(vfio_container_put_ext);
> > +
> > +void *vfio_container_get_iommu_data_ext(struct vfio_container 
> > *container)
> > +{
> > +   return container->iommu_data;
> > +}
> > +EXPORT_SYMBOL_GPL(vfio_container_get_iommu_data_ext);
> > +
> > +/**
> >   * Sub-module support
> >   */
> >  /*
> > diff --git a/drivers/vfio/vfio_iommu_spapr_tce.c 
> > b/drivers/vfio/vfio_iommu_spapr_tce.c
> > index 3594ad3..fceea3d 100644
> > --- a/drivers/vfio/vfio_iommu_spapr_tce.c
> > +++ b/drivers/vfio/vfio_iommu_spapr_tce.c
> > @@ -1331,6 +1331,21 @@ const struct vfio_iommu_driver_ops 
> > tce_iommu_driver_ops = {
> > .detach_group   = tce_iommu_detach_group,
> >  };
> >  
> > +struct iommu_table 
> > *vfio_container_spapr_tce_table_get_ext(void *iommu_data,
> > +   u64 offset)
> > +{
> > +   struct tce_container *container = iommu_data;
> > +   struct iommu_table *tbl = NULL;
> > +
> > +   if (tce_iommu_find_table(container, offset, ) < 0)
> > +   return NULL;
> > +
> > +   iommu_table_get(tbl);
> > +
> > +   return tbl;
> > +}
> > +EXPORT_SYMBOL_GPL(vfio_container_spapr_tce_table_get_ext);
> > +
> >  static int __init tce_iommu_init(void)
> >  {
> > return 
> > vfio_register_iommu_driver(_iommu_driver_ops);
> > @@ -1348,4 +1363,3 @@ MODULE_VERSION(DRIVER_VERSION);
> >  MODULE_LICENSE("GPL v2");
> >  

Re: [PATCH v2] powerpc/mm: export current mmu mode info

2016-09-23 Thread Hari Bathini



On Friday 23 September 2016 10:14 AM, Aneesh Kumar K.V wrote:

Hari Bathini  writes:


Hi Aneesh,


On Thursday 22 September 2016 09:54 PM, Aneesh Kumar K.V wrote:

Hari Bathini  writes:


The kernel now supports both radix and hash MMU modes. Tools like crash
and makedumpfile need to know the current MMU mode the kernel is using,
to debug/analyze it.  The current MMU mode depends on hardware support
and also whether disable_radix cmdline parameter is passed to the kernel.
The mmu_features member of cpu_spec structure holds the current MMU mode
a cpu is using. But the above mentioned tools need to know the MMU mode
early in their init process, when they may not have access to offset info
of structure members. A hard-coded offset may help but it won't be robust.

IIUC, you walk the linux page table and that should be more or less same

Taking the case of crash tool, vmemmap start value is currently
hard-coded to 0xf000UL but it changed to
0xc00aUL in case of radix.

All of that is already defined as variables in the kernel. You can look at
radix__early_init_mmu().



between radix/hash right except few bits. Now what crash will be
interested in will be the RPN part of the table which should be same
between hash/radix.

Though the walk is pretty much the same, the tool still needs to know
the right index values and vmemmap start to use, as they are different
for radix and hash..


This patch introduces a new global variable, which holds the current MMU
mode the kernel is running in and can be accessed by tools early in thier
init process,

Init process of what ? kernel or crash tool ?

tool initialization - crash or makedumpfile..


helping tools to initialize accurately for each MMU mode.
This patch also optimizes the radix_enabled() function call.


how do you differentiate between the hold linux page table format and
the new ? Can you also summarize what crash tool look for in the page
table ?

It needs the index sizes, masked bit values and page flag info to
do the page table walk. Since they can be different for hash and
radix..


Can you look at radix__early_init_mmu/hash__early_init_mmu and see you
can work with the variables defined there ?


Did consider that but didn't opt for it for a few reasons:

1. Will still need to know the MMU mode as huge page address translation
   is not the same for radix & hash.

2. Will have to get all these values from a crashed kernel when I can 
set them

   based on MMU mode. Less dependence on the failed kernel, the better..

3. Stash more variables in vmcoreinfo (for makedumpfile) when one is 
sufficient

   to serve the purpose.

Thanks
Hari



[PATCH v5 17/20] selftests/powerpc: Add checks for transactional VSXs in signal contexts

2016-09-23 Thread Cyril Bur
If a thread receives a signal while transactional the kernel creates a
second context to show the transactional state of the process. This
test loads some known values and waits for a signal and confirms that
the expected values are in the signal context.

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/tm/Makefile|   2 +-
 .../powerpc/tm/tm-signal-context-chk-vsx.c | 125 +
 2 files changed, 126 insertions(+), 1 deletion(-)
 create mode 100644 
tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vsx.c

diff --git a/tools/testing/selftests/powerpc/tm/Makefile 
b/tools/testing/selftests/powerpc/tm/Makefile
index 06c44aa..9d53f8b 100644
--- a/tools/testing/selftests/powerpc/tm/Makefile
+++ b/tools/testing/selftests/powerpc/tm/Makefile
@@ -1,5 +1,5 @@
 SIGNAL_CONTEXT_CHK_TESTS := tm-signal-context-chk-gpr 
tm-signal-context-chk-fpu \
-   tm-signal-context-chk-vmx
+   tm-signal-context-chk-vmx tm-signal-context-chk-vsx
 
 TEST_PROGS := tm-resched-dscr tm-syscall tm-signal-msr-resv tm-signal-stack \
tm-vmxcopy tm-fork tm-tar tm-tmspr $(SIGNAL_CONTEXT_CHK_TESTS)
diff --git a/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vsx.c 
b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vsx.c
new file mode 100644
index 000..b99c3d8
--- /dev/null
+++ b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vsx.c
@@ -0,0 +1,125 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ *
+ * Test the kernel's signal frame code.
+ *
+ * The kernel sets up two sets of ucontexts if the signal was to be
+ * delivered while the thread was in a transaction.
+ * Expected behaviour is that the checkpointed state is in the user
+ * context passed to the signal handler. The speculated state can be
+ * accessed with the uc_link pointer.
+ *
+ * The rationale for this is that if TM unaware code (which linked
+ * against TM libs) installs a signal handler it will not know of the
+ * speculative nature of the 'live' registers and may infer the wrong
+ * thing.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include 
+
+#include "utils.h"
+#include "tm.h"
+
+#define MAX_ATTEMPT 50
+
+#define NV_VSX_REGS 12
+
+long tm_signal_self_context_load(pid_t pid, long *gprs, double *fps, vector 
int *vms, vector int *vss);
+
+static sig_atomic_t fail;
+
+vector int vss[] = {
+   {1, 2, 3, 4 },{5, 6, 7, 8 },{9, 10,11,12},
+   {13,14,15,16},{17,18,19,20},{21,22,23,24},
+   {25,26,27,28},{29,30,31,32},{33,34,35,36},
+   {37,38,39,40},{41,42,43,44},{45,46,47,48},
+   {-1, -2, -3, -4 },{-5, -6, -7, -8 },{-9, -10,-11,-12},
+   {-13,-14,-15,-16},{-17,-18,-19,-20},{-21,-22,-23,-24},
+   {-25,-26,-27,-28},{-29,-30,-31,-32},{-33,-34,-35,-36},
+   {-37,-38,-39,-40},{-41,-42,-43,-44},{-45,-46,-47,-48}
+};
+
+static void signal_usr1(int signum, siginfo_t *info, void *uc)
+{
+   int i;
+   uint8_t vsc[sizeof(vector int)];
+   uint8_t vst[sizeof(vector int)];
+   ucontext_t *ucp = uc;
+   ucontext_t *tm_ucp = ucp->uc_link;
+
+   /*
+* The other half of the VSX regs will be after v_regs.
+*
+* In short, vmx_reserve array holds everything. v_regs is a 16
+* byte aligned pointer at the start of vmx_reserve (vmx_reserve
+* may or may not be 16 aligned) where the v_regs structure exists.
+* (half of) The VSX regsters are directly after v_regs so the
+* easiest way to find them below.
+*/
+   long *vsx_ptr = (long *)(ucp->uc_mcontext.v_regs + 1);
+   long *tm_vsx_ptr = (long *)(tm_ucp->uc_mcontext.v_regs + 1);
+   for (i = 0; i < NV_VSX_REGS && !fail; i++) {
+   memcpy(vsc, >uc_mcontext.fp_regs[i + 20], 8);
+   memcpy(vsc + 8, _ptr[20 + i], 8);
+   fail = memcmp(vsc, [i], sizeof(vector int));
+   memcpy(vst, _ucp->uc_mcontext.fp_regs[i + 20], 8);
+   memcpy(vst + 8, _vsx_ptr[20 + i], 8);
+   fail |= memcmp(vst, [i + NV_VSX_REGS], sizeof(vector int));
+
+   if (fail) {
+   int j;
+
+   fprintf(stderr, "Failed on %d vsx 0x", i);
+   for (j = 0; j < 16; j++)
+   fprintf(stderr, "%02x", vsc[j]);
+   fprintf(stderr, " vs 0x");
+   for (j = 0; j < 16; j++)
+   fprintf(stderr, "%02x", vst[j]);
+   fprintf(stderr, "\n");
+   }
+   }
+}
+
+static int tm_signal_context_chk()
+{
+   struct sigaction act;
+   int i;
+   long rc;
+   pid_t pid = getpid();
+
+   

[PATCH v5 13/20] selftests/powerpc: Check that signals always get delivered

2016-09-23 Thread Cyril Bur
Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/Makefile   |   1 +
 tools/testing/selftests/powerpc/signal/Makefile|  12 +++
 tools/testing/selftests/powerpc/signal/signal.S|  50 ++
 tools/testing/selftests/powerpc/signal/signal.c| 111 +
 tools/testing/selftests/powerpc/signal/signal_tm.c | 110 
 5 files changed, 284 insertions(+)
 create mode 100644 tools/testing/selftests/powerpc/signal/Makefile
 create mode 100644 tools/testing/selftests/powerpc/signal/signal.S
 create mode 100644 tools/testing/selftests/powerpc/signal/signal.c
 create mode 100644 tools/testing/selftests/powerpc/signal/signal_tm.c

diff --git a/tools/testing/selftests/powerpc/Makefile 
b/tools/testing/selftests/powerpc/Makefile
index 1cc6d64..db54a33 100644
--- a/tools/testing/selftests/powerpc/Makefile
+++ b/tools/testing/selftests/powerpc/Makefile
@@ -19,6 +19,7 @@ SUB_DIRS = alignment  \
   dscr \
   mm   \
   pmu  \
+  signal   \
   primitives   \
   stringloops  \
   switch_endian\
diff --git a/tools/testing/selftests/powerpc/signal/Makefile 
b/tools/testing/selftests/powerpc/signal/Makefile
new file mode 100644
index 000..97944cf
--- /dev/null
+++ b/tools/testing/selftests/powerpc/signal/Makefile
@@ -0,0 +1,12 @@
+TEST_PROGS := signal signal_tm
+
+all: $(TEST_PROGS)
+
+$(TEST_PROGS): ../harness.c ../utils.c signal.S
+
+signal_tm: CFLAGS += -mhtm
+
+include ../../lib.mk
+
+clean:
+   rm -f $(TEST_PROGS) *.o
diff --git a/tools/testing/selftests/powerpc/signal/signal.S 
b/tools/testing/selftests/powerpc/signal/signal.S
new file mode 100644
index 000..7043d52
--- /dev/null
+++ b/tools/testing/selftests/powerpc/signal/signal.S
@@ -0,0 +1,50 @@
+/*
+ * Copyright 2015, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+#include "../basic_asm.h"
+
+/* long signal_self(pid_t pid, int sig); */
+FUNC_START(signal_self)
+   li  r0,37 /* sys_kill */
+   /* r3 already has our pid in it */
+   /* r4 already has signal type in it */
+   sc
+   bc  4,3,1f
+   subfze  r3,r3
+1: blr
+FUNC_END(signal_self)
+
+/* long tm_signal_self(pid_t pid, int sig, int *ret); */
+FUNC_START(tm_signal_self)
+   PUSH_BASIC_STACK(8)
+   std r5,STACK_FRAME_PARAM(0)(sp) /* ret */
+   tbegin.
+   beq 1f
+   tsuspend.
+   li  r0,37 /* sys_kill */
+   /* r3 already has our pid in it */
+   /* r4 already has signal type in it */
+   sc
+   ld  r5,STACK_FRAME_PARAM(0)(sp) /* ret */
+   bc  4,3,2f
+   subfze  r3,r3
+2: std r3,0(r5)
+   tabort. 0
+   tresume. /* Be nice to some cleanup, jumps back to tbegin then to 1: */
+   /*
+* Transaction should be proper doomed and we should never get
+* here
+*/
+   li  r3,1
+   POP_BASIC_STACK(8)
+   blr
+1: li  r3,0
+   POP_BASIC_STACK(8)
+   blr
+FUNC_END(tm_signal_self)
diff --git a/tools/testing/selftests/powerpc/signal/signal.c 
b/tools/testing/selftests/powerpc/signal/signal.c
new file mode 100644
index 000..e7dedd2
--- /dev/null
+++ b/tools/testing/selftests/powerpc/signal/signal.c
@@ -0,0 +1,111 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ * Sending one self a signal should always get delivered.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include 
+
+#include "utils.h"
+
+#define MAX_ATTEMPT 50
+#define TIMEOUT 5
+
+extern long signal_self(pid_t pid, int sig);
+
+static sig_atomic_t signaled;
+static sig_atomic_t fail;
+
+static void signal_handler(int sig)
+{
+   if (sig == SIGUSR1)
+   signaled = 1;
+   else
+   fail = 1;
+}
+
+static int test_signal()
+{
+   int i;
+   struct sigaction act;
+   pid_t ppid = getpid();
+   pid_t pid;
+
+   act.sa_handler = signal_handler;
+   act.sa_flags = 0;
+   sigemptyset(_mask);
+   if (sigaction(SIGUSR1, , NULL) < 0) {
+   perror("sigaction SIGUSR1");
+   exit(1);
+   }
+   if (sigaction(SIGALRM, , NULL) < 0) {
+   perror("sigaction SIGALRM");
+   exit(1);
+   }
+
+   /* Don't do this for MAX_ATTEMPT, its simply too long */
+   for(i  = 0; i < 1000; i++) {
+   

[PATCH v5 12/20] selftests/powerpc: Add TM tcheck helpers in C

2016-09-23 Thread Cyril Bur
Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/tm/tm.h | 27 +++
 1 file changed, 27 insertions(+)

diff --git a/tools/testing/selftests/powerpc/tm/tm.h 
b/tools/testing/selftests/powerpc/tm/tm.h
index 60318ba..2c8da74 100644
--- a/tools/testing/selftests/powerpc/tm/tm.h
+++ b/tools/testing/selftests/powerpc/tm/tm.h
@@ -52,4 +52,31 @@ static inline bool failure_is_nesting(void)
return (__builtin_get_texasru() & 0x40);
 }
 
+static inline int tcheck(void)
+{
+   long cr;
+   asm volatile ("tcheck 0" : "=r"(cr) : : "cr0");
+   return (cr >> 28) & 4;
+}
+
+static inline bool tcheck_doomed(void)
+{
+   return tcheck() & 8;
+}
+
+static inline bool tcheck_active(void)
+{
+   return tcheck() & 4;
+}
+
+static inline bool tcheck_suspended(void)
+{
+   return tcheck() & 2;
+}
+
+static inline bool tcheck_transactional(void)
+{
+   return tcheck() & 6;
+}
+
 #endif /* _SELFTESTS_POWERPC_TM_TM_H */
-- 
2.10.0



[PATCH v5 02/20] powerpc: Always restore FPU/VEC/VSX if hardware transactional memory in use

2016-09-23 Thread Cyril Bur
Comment from arch/powerpc/kernel/process.c:967:
 If userspace is inside a transaction (whether active or
 suspended) and FP/VMX/VSX instructions have ever been enabled
 inside that transaction, then we have to keep them enabled
 and keep the FP/VMX/VSX state loaded while ever the transaction
 continues.  The reason is that if we didn't, and subsequently
 got a FP/VMX/VSX unavailable interrupt inside a transaction,
 we don't know whether it's the same transaction, and thus we
 don't know which of the checkpointed state and the ransactional
 state to use.

restore_math() restore_fp() and restore_altivec() currently may not
restore the registers. It doesn't appear that this is more serious
than a performance penalty. If the math registers aren't restored the
userspace thread will still be run with the facility disabled.
Userspace will not be able to read invalid values. On the first access
it will take an facility unavailable exception and the kernel will
detected an active transaction, at which point it will abort the
transaction. There is the possibility for a pathological case
preventing any progress by transactions, however, transactions
are never guaranteed to make progress.

Fixes: 70fe3d9 ("powerpc: Restore FPU/VEC/VSX if previously used")
Signed-off-by: Cyril Bur 
---
 arch/powerpc/kernel/process.c | 21 ++---
 1 file changed, 18 insertions(+), 3 deletions(-)

diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index ce8a26a..3846fab 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -89,7 +89,13 @@ static void check_if_tm_restore_required(struct task_struct 
*tsk)
set_thread_flag(TIF_RESTORE_TM);
}
 }
+
+static inline bool msr_tm_active(unsigned long msr)
+{
+   return MSR_TM_ACTIVE(msr);
+}
 #else
+static inline bool msr_tm_active(unsigned long msr) { return false; }
 static inline void check_if_tm_restore_required(struct task_struct *tsk) { }
 #endif /* CONFIG_PPC_TRANSACTIONAL_MEM */
 
@@ -209,7 +215,7 @@ void enable_kernel_fp(void)
 EXPORT_SYMBOL(enable_kernel_fp);
 
 static int restore_fp(struct task_struct *tsk) {
-   if (tsk->thread.load_fp) {
+   if (tsk->thread.load_fp || msr_tm_active(tsk->thread.regs->msr)) {
load_fp_state(>thread.fp_state);
current->thread.load_fp++;
return 1;
@@ -279,7 +285,8 @@ EXPORT_SYMBOL_GPL(flush_altivec_to_thread);
 
 static int restore_altivec(struct task_struct *tsk)
 {
-   if (cpu_has_feature(CPU_FTR_ALTIVEC) && tsk->thread.load_vec) {
+   if (cpu_has_feature(CPU_FTR_ALTIVEC) &&
+   (tsk->thread.load_vec || msr_tm_active(tsk->thread.regs->msr))) 
{
load_vr_state(>thread.vr_state);
tsk->thread.used_vr = 1;
tsk->thread.load_vec++;
@@ -465,7 +472,8 @@ void restore_math(struct pt_regs *regs)
 {
unsigned long msr;
 
-   if (!current->thread.load_fp && !loadvec(current->thread))
+   if (!msr_tm_active(regs->msr) &&
+   !current->thread.load_fp && !loadvec(current->thread))
return;
 
msr = regs->msr;
@@ -984,6 +992,13 @@ void restore_tm_state(struct pt_regs *regs)
msr_diff = current->thread.ckpt_regs.msr & ~regs->msr;
msr_diff &= MSR_FP | MSR_VEC | MSR_VSX;
 
+   /* Ensure that restore_math() will restore */
+   if (msr_diff & MSR_FP)
+   current->thread.load_fp = 1;
+#ifdef CONFIG_ALIVEC
+   if (cpu_has_feature(CPU_FTR_ALTIVEC) && msr_diff & MSR_VEC)
+   current->thread.load_vec = 1;
+#endif
restore_math(regs);
 
regs->msr |= msr_diff;
-- 
2.10.0



[PATCH v5 01/20] selftests/powerpc: Compile selftests against headers without AT_HWCAP2

2016-09-23 Thread Cyril Bur
It might be nice to compile selftests against older kernels and
headers but which may not have HWCAP2.

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/utils.h | 7 +++
 1 file changed, 7 insertions(+)

diff --git a/tools/testing/selftests/powerpc/utils.h 
b/tools/testing/selftests/powerpc/utils.h
index fbd33e5..ecd11b5 100644
--- a/tools/testing/selftests/powerpc/utils.h
+++ b/tools/testing/selftests/powerpc/utils.h
@@ -32,10 +32,17 @@ static inline bool have_hwcap(unsigned long ftr)
return ((unsigned long)get_auxv_entry(AT_HWCAP) & ftr) == ftr;
 }
 
+#ifdef AT_HWCAP2
 static inline bool have_hwcap2(unsigned long ftr2)
 {
return ((unsigned long)get_auxv_entry(AT_HWCAP2) & ftr2) == ftr2;
 }
+#else
+static inline bool have_hwcap2(unsigned long ftr2)
+{
+   return false;
+}
+#endif
 
 /* Yes, this is evil */
 #define FAIL_IF(x) \
-- 
2.10.0



[PATCH v5 03/20] powerpc: Add check_if_tm_restore_required() to giveup_all()

2016-09-23 Thread Cyril Bur
giveup_all() causes FPU/VMX/VSX facilities to be disabled in a threads
MSR. If the thread performing the giveup was transactional, the kernel
must record which facilities were in use before the giveup as the
thread must have these facilities re-enabled on return to userspace.

>From process.c:
 /*
  * This is called if we are on the way out to userspace and the
  * TIF_RESTORE_TM flag is set.  It checks if we need to reload
  * FP and/or vector state and does so if necessary.
  * If userspace is inside a transaction (whether active or
  * suspended) and FP/VMX/VSX instructions have ever been enabled
  * inside that transaction, then we have to keep them enabled
  * and keep the FP/VMX/VSX state loaded while ever the transaction
  * continues.  The reason is that if we didn't, and subsequently
  * got a FP/VMX/VSX unavailable interrupt inside a transaction,
  * we don't know whether it's the same transaction, and thus we
  * don't know which of the checkpointed state and the transactional
  * state to use.
  */

Calling check_if_tm_restore_required() will set TIF_RESTORE_TM and
save the MSR if needed.

Fixes: c208505 ("powerpc: create giveup_all()")
Signed-off-by: Cyril Bur 
---
 arch/powerpc/kernel/process.c | 1 +
 1 file changed, 1 insertion(+)

diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 3846fab..5029567 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -446,6 +446,7 @@ void giveup_all(struct task_struct *tsk)
return;
 
msr_check_and_set(msr_all_available);
+   check_if_tm_restore_required(tsk);
 
 #ifdef CONFIG_PPC_FPU
if (usermsr & MSR_FP)
-- 
2.10.0



[PATCH v5 10/20] selftests/powerpc: Introduce GPR asm helper header file

2016-09-23 Thread Cyril Bur
Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/gpr_asm.h | 96 +++
 1 file changed, 96 insertions(+)
 create mode 100644 tools/testing/selftests/powerpc/gpr_asm.h

diff --git a/tools/testing/selftests/powerpc/gpr_asm.h 
b/tools/testing/selftests/powerpc/gpr_asm.h
new file mode 100644
index 000..f6f3885
--- /dev/null
+++ b/tools/testing/selftests/powerpc/gpr_asm.h
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+#ifndef _SELFTESTS_POWERPC_GPR_ASM_H
+#define _SELFTESTS_POWERPC_GPR_ASM_H
+
+#include "basic_asm.h"
+
+#define __PUSH_NVREGS(top_pos); \
+   std r31,(top_pos)(%r1); \
+   std r30,(top_pos - 8)(%r1); \
+   std r29,(top_pos - 16)(%r1); \
+   std r28,(top_pos - 24)(%r1); \
+   std r27,(top_pos - 32)(%r1); \
+   std r26,(top_pos - 40)(%r1); \
+   std r25,(top_pos - 48)(%r1); \
+   std r24,(top_pos - 56)(%r1); \
+   std r23,(top_pos - 64)(%r1); \
+   std r22,(top_pos - 72)(%r1); \
+   std r21,(top_pos - 80)(%r1); \
+   std r20,(top_pos - 88)(%r1); \
+   std r19,(top_pos - 96)(%r1); \
+   std r18,(top_pos - 104)(%r1); \
+   std r17,(top_pos - 112)(%r1); \
+   std r16,(top_pos - 120)(%r1); \
+   std r15,(top_pos - 128)(%r1); \
+   std r14,(top_pos - 136)(%r1)
+
+#define __POP_NVREGS(top_pos); \
+   ld r31,(top_pos)(%r1); \
+   ld r30,(top_pos - 8)(%r1); \
+   ld r29,(top_pos - 16)(%r1); \
+   ld r28,(top_pos - 24)(%r1); \
+   ld r27,(top_pos - 32)(%r1); \
+   ld r26,(top_pos - 40)(%r1); \
+   ld r25,(top_pos - 48)(%r1); \
+   ld r24,(top_pos - 56)(%r1); \
+   ld r23,(top_pos - 64)(%r1); \
+   ld r22,(top_pos - 72)(%r1); \
+   ld r21,(top_pos - 80)(%r1); \
+   ld r20,(top_pos - 88)(%r1); \
+   ld r19,(top_pos - 96)(%r1); \
+   ld r18,(top_pos - 104)(%r1); \
+   ld r17,(top_pos - 112)(%r1); \
+   ld r16,(top_pos - 120)(%r1); \
+   ld r15,(top_pos - 128)(%r1); \
+   ld r14,(top_pos - 136)(%r1)
+
+#define PUSH_NVREGS(stack_size) \
+   __PUSH_NVREGS(stack_size + STACK_FRAME_MIN_SIZE)
+
+/* 18 NV FPU REGS */
+#define PUSH_NVREGS_BELOW_FPU(stack_size) \
+   __PUSH_NVREGS(stack_size + STACK_FRAME_MIN_SIZE - (18 * 8))
+
+#define POP_NVREGS(stack_size) \
+   __POP_NVREGS(stack_size + STACK_FRAME_MIN_SIZE)
+
+/* 18 NV FPU REGS */
+#define POP_NVREGS_BELOW_FPU(stack_size) \
+   __POP_NVREGS(stack_size + STACK_FRAME_MIN_SIZE - (18 * 8))
+
+/*
+ * Careful calling this, it will 'clobber' NVGPRs (by design)
+ * Don't call this from C
+ */
+FUNC_START(load_gpr)
+   ld  r14,0(r3)
+   ld  r15,8(r3)
+   ld  r16,16(r3)
+   ld  r17,24(r3)
+   ld  r18,32(r3)
+   ld  r19,40(r3)
+   ld  r20,48(r3)
+   ld  r21,56(r3)
+   ld  r22,64(r3)
+   ld  r23,72(r3)
+   ld  r24,80(r3)
+   ld  r25,88(r3)
+   ld  r26,96(r3)
+   ld  r27,104(r3)
+   ld  r28,112(r3)
+   ld  r29,120(r3)
+   ld  r30,128(r3)
+   ld  r31,136(r3)
+   blr
+FUNC_END(load_gpr)
+
+
+#endif /* _SELFTESTS_POWERPC_GPR_ASM_H */
-- 
2.10.0



[PATCH v5 06/20] powerpc: signals: Stop using current in signal code

2016-09-23 Thread Cyril Bur
Much of the signal code takes a pt_regs on which it operates. Over
time the signal code has needed to know more about the thread than
what pt_regs can supply, this information is obtained as needed by
using 'current'.

This approach is not strictly incorrect however it does mean that
there is now a hard requirement that the pt_regs being passed around
does belong to current, this is never checked. A safer approach is for
the majority of the signal functions to take a task_struct from which
they can obtain pt_regs and any other information they need. The
caveat that the task_struct they are passed must be current doesn't go
away but can more easily be checked for.

Functions called from outside powerpc signal code are passed a pt_regs
and they can confirm that the pt_regs is that of current and pass
current to other functions, furthurmore, powerpc signal functions can
check that the task_struct they are passed is the same as current
avoiding possible corruption of current (or the task they are passed)
if this assertion ever fails.

CC: pau...@samba.org
Signed-off-by: Cyril Bur 
---
 arch/powerpc/include/asm/signal.h |   2 -
 arch/powerpc/kernel/signal.c  |  41 
 arch/powerpc/kernel/signal.h  |  10 +-
 arch/powerpc/kernel/signal_32.c   |  31 +++---
 arch/powerpc/kernel/signal_64.c   | 201 +-
 5 files changed, 159 insertions(+), 126 deletions(-)

diff --git a/arch/powerpc/include/asm/signal.h 
b/arch/powerpc/include/asm/signal.h
index 9322c28..5ff7772 100644
--- a/arch/powerpc/include/asm/signal.h
+++ b/arch/powerpc/include/asm/signal.h
@@ -5,6 +5,4 @@
 #include 
 #include 
 
-extern unsigned long get_tm_stackpointer(struct pt_regs *regs);
-
 #endif /* _ASM_POWERPC_SIGNAL_H */
diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c
index cb64d6f..bbe77ae 100644
--- a/arch/powerpc/kernel/signal.c
+++ b/arch/powerpc/kernel/signal.c
@@ -99,22 +99,24 @@ static void check_syscall_restart(struct pt_regs *regs, 
struct k_sigaction *ka,
}
 }
 
-static void do_signal(struct pt_regs *regs)
+static void do_signal(struct task_struct *tsk)
 {
sigset_t *oldset = sigmask_to_save();
struct ksignal ksig;
int ret;
int is32 = is_32bit_task();
 
+   BUG_ON(tsk != current);
+
get_signal();
 
/* Is there any syscall restart business here ? */
-   check_syscall_restart(regs, , ksig.sig > 0);
+   check_syscall_restart(tsk->thread.regs, , ksig.sig > 0);
 
if (ksig.sig <= 0) {
/* No signal to deliver -- put the saved sigmask back */
restore_saved_sigmask();
-   regs->trap = 0;
+   tsk->thread.regs->trap = 0;
return;   /* no signals delivered */
}
 
@@ -124,23 +126,22 @@ static void do_signal(struct pt_regs *regs)
 * user space. The DABR will have been cleared if it
 * triggered inside the kernel.
 */
-   if (current->thread.hw_brk.address &&
-   current->thread.hw_brk.type)
-   __set_breakpoint(>thread.hw_brk);
+   if (tsk->thread.hw_brk.address && tsk->thread.hw_brk.type)
+   __set_breakpoint(>thread.hw_brk);
 #endif
/* Re-enable the breakpoints for the signal stack */
-   thread_change_pc(current, regs);
+   thread_change_pc(tsk, tsk->thread.regs);
 
if (is32) {
if (ksig.ka.sa.sa_flags & SA_SIGINFO)
-   ret = handle_rt_signal32(, oldset, regs);
+   ret = handle_rt_signal32(, oldset, tsk);
else
-   ret = handle_signal32(, oldset, regs);
+   ret = handle_signal32(, oldset, tsk);
} else {
-   ret = handle_rt_signal64(, oldset, regs);
+   ret = handle_rt_signal64(, oldset, tsk);
}
 
-   regs->trap = 0;
+   tsk->thread.regs->trap = 0;
signal_setup_done(ret, , test_thread_flag(TIF_SINGLESTEP));
 }
 
@@ -151,8 +152,10 @@ void do_notify_resume(struct pt_regs *regs, unsigned long 
thread_info_flags)
if (thread_info_flags & _TIF_UPROBE)
uprobe_notify_resume(regs);
 
-   if (thread_info_flags & _TIF_SIGPENDING)
-   do_signal(regs);
+   if (thread_info_flags & _TIF_SIGPENDING) {
+   BUG_ON(regs != current->thread.regs);
+   do_signal(current);
+   }
 
if (thread_info_flags & _TIF_NOTIFY_RESUME) {
clear_thread_flag(TIF_NOTIFY_RESUME);
@@ -162,7 +165,7 @@ void do_notify_resume(struct pt_regs *regs, unsigned long 
thread_info_flags)
user_enter();
 }
 
-unsigned long get_tm_stackpointer(struct pt_regs *regs)
+unsigned long get_tm_stackpointer(struct task_struct *tsk)
 {
/* When in an active transaction that takes a signal, we need to be
 * careful with the stack.  It's possible that the stack has moved back
@@ -187,11 

[PATCH v5 04/20] powerpc: Return the new MSR from msr_check_and_set()

2016-09-23 Thread Cyril Bur
msr_check_and_set() always performs a mfmsr() to determine if it needs
to perform an mtmsr(), as mfmsr() can be a costly operation
msr_check_and_set() could return the MSR now on the CPU to avoid
callers of msr_check_and_set having to make their own mfmsr() call.

Signed-off-by: Cyril Bur 
---
 arch/powerpc/include/asm/reg.h | 2 +-
 arch/powerpc/kernel/process.c  | 4 +++-
 2 files changed, 4 insertions(+), 2 deletions(-)

diff --git a/arch/powerpc/include/asm/reg.h b/arch/powerpc/include/asm/reg.h
index 9dddabc..a8f63bc 100644
--- a/arch/powerpc/include/asm/reg.h
+++ b/arch/powerpc/include/asm/reg.h
@@ -1250,7 +1250,7 @@ static inline void mtmsr_isync(unsigned long val)
 : "memory")
 #endif
 
-extern void msr_check_and_set(unsigned long bits);
+extern unsigned long msr_check_and_set(unsigned long bits);
 extern bool strict_msr_control;
 extern void __msr_check_and_clear(unsigned long bits);
 static inline void msr_check_and_clear(unsigned long bits)
diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 5029567..34ee5f2 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -111,7 +111,7 @@ static int __init enable_strict_msr_control(char *str)
 }
 early_param("ppc_strict_facility_enable", enable_strict_msr_control);
 
-void msr_check_and_set(unsigned long bits)
+unsigned long msr_check_and_set(unsigned long bits)
 {
unsigned long oldmsr = mfmsr();
unsigned long newmsr;
@@ -125,6 +125,8 @@ void msr_check_and_set(unsigned long bits)
 
if (oldmsr != newmsr)
mtmsr_isync(newmsr);
+
+   return newmsr;
 }
 
 void __msr_check_and_clear(unsigned long bits)
-- 
2.10.0



[PATCH v5 00/20] Consistent TM structures

2016-09-23 Thread Cyril Bur
v5: Rebased on powerpc-next to solve conflict with
  commit e1c0d66fcb179a1737b3d5cc11c6e37bcabbd861
  Author: Simon Guo 
  Date:   Tue Jul 26 16:06:01 2016 +0800

powerpc: Set used_(vsr|vr|spe) in sigreturn path when MSR bits are
active

v4: Address review from Mikey, comment and commit message changes.
Dropped patch "selftests/powerpc: Add TM tcheck helpers in C" as
it was unused.

V3:
In v2 the MSR_{FP,VEC,VSX} bits were left on (if in use) after a
reclaim which meant that signal code did the correct thing.
This also meant that the bits would stay on when a (transactional)
thread was not running and ptrace flush code would notice that tasks
not current have MSR_{FP,VEC,VSX} set when attempting to flush, this
is incorrect. The correct solution was to have the signal code make
decisions about the use of FP,VEC or VSX by observing the checkpointed
MSR and not the regs->msr. This meant adding another reference to
current in signal code which was getting messy.
Patch "powerpc: signals: Stop using current in signal code" addresses
this and allows for a cleaner fix.

Fix build issues for 32bit.

V2 Coverletter:

This series has grown considerably from v1.

Similarities with v1 include:
- Selftests are all the same, they have simply been split into several
  patches with comments from MPE and Daniel Axtens incorporated. It
  is possible some things slipped through the cracks selftest wise as
  the focus has been on the final three patches.
- The final three patches have been reworked following extra testing
  and from review by Simon Guo.

Differences include:
- Patches 2-5 are fixes for existing problems found in the course of
  verifying the final three patches. In the case of "powerpc: Never
  giveup a reclaimed thread when enabling kernel {fp, altivec, vsx}"
  it has proven difficult to narrow down when the bug was introduced.
  It does not exist in 3.8 when TM was introduced but does exist in 4.4.
  I was unable to boot 3.13 (or 3.12) in an attempt to further bisect.
- As ptrace code was merged between v1 and v2, work was needed there
  to make it fit in with the final three patches.

The overall aim of this series may have gotten lost here. The final
three patches are the goal here.



Cyril Bur (20):
  selftests/powerpc: Compile selftests against headers without AT_HWCAP2
  powerpc: Always restore FPU/VEC/VSX if hardware transactional memory
in use
  powerpc: Add check_if_tm_restore_required() to giveup_all()
  powerpc: Return the new MSR from msr_check_and_set()
  powerpc: Never giveup a reclaimed thread when enabling kernel {fp,
altivec, vsx}
  powerpc: signals: Stop using current in signal code
  selftests/powerpc: Check for VSX preservation across userspace
preemption
  selftests/powerpc: Rework FPU stack placement macros and move to
header file
  selftests/powerpc: Move VMX stack frame macros to header file
  selftests/powerpc: Introduce GPR asm helper header file
  selftests/powerpc: Allow tests to extend their kill timeout
  selftests/powerpc: Add TM tcheck helpers in C
  selftests/powerpc: Check that signals always get delivered
  selftests/powerpc: Add checks for transactional GPRs in signal
contexts
  selftests/powerpc: Add checks for transactional FPUs in signal
contexts
  selftests/powerpc: Add checks for transactional VMXs in signal
contexts
  selftests/powerpc: Add checks for transactional VSXs in signal
contexts
  powerpc: tm: Always use fp_state and vr_state to store live registers
  powerpc: tm: Rename transct_(*) to ck(\1)_state
  powerpc: Remove do_load_up_transact_{fpu,altivec}

 arch/powerpc/include/asm/processor.h   |  15 +-
 arch/powerpc/include/asm/reg.h |   2 +-
 arch/powerpc/include/asm/signal.h  |   2 -
 arch/powerpc/include/asm/tm.h  |   5 -
 arch/powerpc/kernel/asm-offsets.c  |  12 +-
 arch/powerpc/kernel/fpu.S  |  26 --
 arch/powerpc/kernel/process.c  | 152 +--
 arch/powerpc/kernel/ptrace.c   | 278 +
 arch/powerpc/kernel/signal.c   |  41 +--
 arch/powerpc/kernel/signal.h   |  18 +-
 arch/powerpc/kernel/signal_32.c| 115 -
 arch/powerpc/kernel/signal_64.c| 203 ---
 arch/powerpc/kernel/tm.S   |  94 +++
 arch/powerpc/kernel/traps.c|  12 +-
 arch/powerpc/kernel/vector.S   |  25 --
 tools/testing/selftests/powerpc/Makefile   |   1 +
 tools/testing/selftests/powerpc/fpu_asm.h  |  81 ++
 tools/testing/selftests/powerpc/gpr_asm.h  |  96 +++
 tools/testing/selftests/powerpc/harness.c  |   9 +-
 tools/testing/selftests/powerpc/math/Makefile  |   4 +-
 tools/testing/selftests/powerpc/math/fpu_asm.S |  73 +-
 

[PATCH v5 20/20] powerpc: Remove do_load_up_transact_{fpu,altivec}

2016-09-23 Thread Cyril Bur
Previous rework of TM code leaves these functions unused

Signed-off-by: Cyril Bur 
---
 arch/powerpc/include/asm/tm.h |  5 -
 arch/powerpc/kernel/fpu.S | 26 --
 arch/powerpc/kernel/vector.S  | 25 -
 3 files changed, 56 deletions(-)

diff --git a/arch/powerpc/include/asm/tm.h b/arch/powerpc/include/asm/tm.h
index c22d704..82e06ca 100644
--- a/arch/powerpc/include/asm/tm.h
+++ b/arch/powerpc/include/asm/tm.h
@@ -9,11 +9,6 @@
 
 #ifndef __ASSEMBLY__
 
-#ifdef CONFIG_PPC_TRANSACTIONAL_MEM
-extern void do_load_up_transact_fpu(struct thread_struct *thread);
-extern void do_load_up_transact_altivec(struct thread_struct *thread);
-#endif
-
 extern void tm_enable(void);
 extern void tm_reclaim(struct thread_struct *thread,
   unsigned long orig_msr, uint8_t cause);
diff --git a/arch/powerpc/kernel/fpu.S b/arch/powerpc/kernel/fpu.S
index 181c187..08d14b0 100644
--- a/arch/powerpc/kernel/fpu.S
+++ b/arch/powerpc/kernel/fpu.S
@@ -50,32 +50,6 @@ END_FTR_SECTION_IFSET(CPU_FTR_VSX);  
\
 #define REST_32FPVSRS(n,c,base) __REST_32FPVSRS(n,__REG_##c,__REG_##base)
 #define SAVE_32FPVSRS(n,c,base) __SAVE_32FPVSRS(n,__REG_##c,__REG_##base)
 
-#ifdef CONFIG_PPC_TRANSACTIONAL_MEM
-/* void do_load_up_transact_fpu(struct thread_struct *thread)
- *
- * This is similar to load_up_fpu but for the transactional version of the FP
- * register set.  It doesn't mess with the task MSR or valid flags.
- * Furthermore, we don't do lazy FP with TM currently.
- */
-_GLOBAL(do_load_up_transact_fpu)
-   mfmsr   r6
-   ori r5,r6,MSR_FP
-#ifdef CONFIG_VSX
-BEGIN_FTR_SECTION
-   orisr5,r5,MSR_VSX@h
-END_FTR_SECTION_IFSET(CPU_FTR_VSX)
-#endif
-   SYNC
-   MTMSRD(r5)
-
-   addir7,r3,THREAD_CKFPSTATE
-   lfd fr0,FPSTATE_FPSCR(r7)
-   MTFSF_L(fr0)
-   REST_32FPVSRS(0, R4, R7)
-
-   blr
-#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */
-
 /*
  * Load state from memory into FP registers including FPSCR.
  * Assumes the caller has enabled FP in the MSR.
diff --git a/arch/powerpc/kernel/vector.S b/arch/powerpc/kernel/vector.S
index 7dc4021..bc85bdf 100644
--- a/arch/powerpc/kernel/vector.S
+++ b/arch/powerpc/kernel/vector.S
@@ -7,31 +7,6 @@
 #include 
 #include 
 
-#ifdef CONFIG_PPC_TRANSACTIONAL_MEM
-/* void do_load_up_transact_altivec(struct thread_struct *thread)
- *
- * This is similar to load_up_altivec but for the transactional version of the
- * vector regs.  It doesn't mess with the task MSR or valid flags.
- * Furthermore, VEC laziness is not supported with TM currently.
- */
-_GLOBAL(do_load_up_transact_altivec)
-   mfmsr   r6
-   orisr5,r6,MSR_VEC@h
-   MTMSRD(r5)
-   isync
-
-   li  r4,1
-   stw r4,THREAD_USED_VR(r3)
-
-   li  r10,THREAD_CKVRSTATE+VRSTATE_VSCR
-   lvx v0,r10,r3
-   mtvscr  v0
-   addir10,r3,THREAD_CKVRSTATE
-   REST_32VRS(0,r4,r10)
-
-   blr
-#endif
-
 /*
  * Load state from memory into VMX registers including VSCR.
  * Assumes the caller has enabled VMX in the MSR.
-- 
2.10.0



[PATCH v5 11/20] selftests/powerpc: Allow tests to extend their kill timeout

2016-09-23 Thread Cyril Bur
Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/harness.c | 9 +++--
 tools/testing/selftests/powerpc/utils.h   | 2 +-
 2 files changed, 8 insertions(+), 3 deletions(-)

diff --git a/tools/testing/selftests/powerpc/harness.c 
b/tools/testing/selftests/powerpc/harness.c
index 52f9be7..248a820 100644
--- a/tools/testing/selftests/powerpc/harness.c
+++ b/tools/testing/selftests/powerpc/harness.c
@@ -19,9 +19,9 @@
 #include "subunit.h"
 #include "utils.h"
 
-#define TIMEOUT120
 #define KILL_TIMEOUT   5
 
+static uint64_t timeout = 120;
 
 int run_test(int (test_function)(void), char *name)
 {
@@ -44,7 +44,7 @@ int run_test(int (test_function)(void), char *name)
setpgid(pid, pid);
 
/* Wake us up in timeout seconds */
-   alarm(TIMEOUT);
+   alarm(timeout);
terminated = false;
 
 wait:
@@ -94,6 +94,11 @@ static struct sigaction alarm_action = {
.sa_handler = alarm_handler,
 };
 
+void test_harness_set_timeout(uint64_t time)
+{
+   timeout = time;
+}
+
 int test_harness(int (test_function)(void), char *name)
 {
int rc;
diff --git a/tools/testing/selftests/powerpc/utils.h 
b/tools/testing/selftests/powerpc/utils.h
index ecd11b5..53405e8 100644
--- a/tools/testing/selftests/powerpc/utils.h
+++ b/tools/testing/selftests/powerpc/utils.h
@@ -22,7 +22,7 @@ typedef uint32_t u32;
 typedef uint16_t u16;
 typedef uint8_t u8;
 
-
+void test_harness_set_timeout(uint64_t time);
 int test_harness(int (test_function)(void), char *name);
 extern void *get_auxv_entry(int type);
 int pick_online_cpu(void);
-- 
2.10.0



[PATCH v5 19/20] powerpc: tm: Rename transct_(*) to ck(\1)_state

2016-09-23 Thread Cyril Bur
Make the structures being used for checkpointed state named
consistently with the pt_regs/ckpt_regs.

Signed-off-by: Cyril Bur 
---
 arch/powerpc/include/asm/processor.h |  8 ++---
 arch/powerpc/kernel/asm-offsets.c| 12 
 arch/powerpc/kernel/fpu.S|  2 +-
 arch/powerpc/kernel/process.c|  4 +--
 arch/powerpc/kernel/ptrace.c | 46 +--
 arch/powerpc/kernel/signal.h |  8 ++---
 arch/powerpc/kernel/signal_32.c  | 60 ++--
 arch/powerpc/kernel/signal_64.c  | 32 +--
 arch/powerpc/kernel/tm.S | 12 
 arch/powerpc/kernel/vector.S |  4 +--
 10 files changed, 94 insertions(+), 94 deletions(-)

diff --git a/arch/powerpc/include/asm/processor.h 
b/arch/powerpc/include/asm/processor.h
index feab2ce..b3e0cfc 100644
--- a/arch/powerpc/include/asm/processor.h
+++ b/arch/powerpc/include/asm/processor.h
@@ -147,7 +147,7 @@ typedef struct {
 } mm_segment_t;
 
 #define TS_FPR(i) fp_state.fpr[i][TS_FPROFFSET]
-#define TS_TRANS_FPR(i) transact_fp.fpr[i][TS_FPROFFSET]
+#define TS_CKFPR(i) ckfp_state.fpr[i][TS_FPROFFSET]
 
 /* FP and VSX 0-31 register set */
 struct thread_fp_state {
@@ -275,9 +275,9 @@ struct thread_struct {
 *
 * These are analogous to how ckpt_regs and pt_regs work
 */
-   struct thread_fp_state transact_fp;
-   struct thread_vr_state transact_vr;
-   unsigned long   transact_vrsave;
+   struct thread_fp_state ckfp_state; /* Checkpointed FP state */
+   struct thread_vr_state ckvr_state; /* Checkpointed VR state */
+   unsigned long   ckvrsave; /* Checkpointed VRSAVE */
 #endif /* CONFIG_PPC_TRANSACTIONAL_MEM */
 #ifdef CONFIG_KVM_BOOK3S_32_HANDLER
void*   kvm_shadow_vcpu; /* KVM internal data */
diff --git a/arch/powerpc/kernel/asm-offsets.c 
b/arch/powerpc/kernel/asm-offsets.c
index b89d14c..dd0fc33 100644
--- a/arch/powerpc/kernel/asm-offsets.c
+++ b/arch/powerpc/kernel/asm-offsets.c
@@ -142,12 +142,12 @@ int main(void)
DEFINE(THREAD_TM_PPR, offsetof(struct thread_struct, tm_ppr));
DEFINE(THREAD_TM_DSCR, offsetof(struct thread_struct, tm_dscr));
DEFINE(PT_CKPT_REGS, offsetof(struct thread_struct, ckpt_regs));
-   DEFINE(THREAD_TRANSACT_VRSTATE, offsetof(struct thread_struct,
-transact_vr));
-   DEFINE(THREAD_TRANSACT_VRSAVE, offsetof(struct thread_struct,
-   transact_vrsave));
-   DEFINE(THREAD_TRANSACT_FPSTATE, offsetof(struct thread_struct,
-transact_fp));
+   DEFINE(THREAD_CKVRSTATE, offsetof(struct thread_struct,
+ckvr_state));
+   DEFINE(THREAD_CKVRSAVE, offsetof(struct thread_struct,
+   ckvrsave));
+   DEFINE(THREAD_CKFPSTATE, offsetof(struct thread_struct,
+ckfp_state));
/* Local pt_regs on stack for Transactional Memory funcs. */
DEFINE(TM_FRAME_SIZE, STACK_FRAME_OVERHEAD +
   sizeof(struct pt_regs) + 16);
diff --git a/arch/powerpc/kernel/fpu.S b/arch/powerpc/kernel/fpu.S
index 15da2b5..181c187 100644
--- a/arch/powerpc/kernel/fpu.S
+++ b/arch/powerpc/kernel/fpu.S
@@ -68,7 +68,7 @@ END_FTR_SECTION_IFSET(CPU_FTR_VSX)
SYNC
MTMSRD(r5)
 
-   addir7,r3,THREAD_TRANSACT_FPSTATE
+   addir7,r3,THREAD_CKFPSTATE
lfd fr0,FPSTATE_FPSCR(r7)
MTFSF_L(fr0)
REST_32FPVSRS(0, R4, R7)
diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 6e9a054..e220330 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -851,8 +851,8 @@ static inline void tm_reclaim_task(struct task_struct *tsk)
 *
 * In switching we need to maintain a 2nd register state as
 * oldtask->thread.ckpt_regs.  We tm_reclaim(oldproc); this saves the
-* checkpointed (tbegin) state in ckpt_regs and saves the transactional
-* (current) FPRs into oldtask->thread.transact_fpr[].
+* checkpointed (tbegin) state in ckpt_regs, ckfp_state and
+* ckvr_state
 *
 * We also context switch (save) TFHAR/TEXASR/TFIAR in here.
 */
diff --git a/arch/powerpc/kernel/ptrace.c b/arch/powerpc/kernel/ptrace.c
index 7ae744f..b1ec62f 100644
--- a/arch/powerpc/kernel/ptrace.c
+++ b/arch/powerpc/kernel/ptrace.c
@@ -404,7 +404,7 @@ static int gpr_set(struct task_struct *target, const struct 
user_regset *regset,
 
 /*
  * Regardless of transactions, 'fp_state' holds the current running
- * value of all FPR registers and 'transact_fp' holds the last checkpointed
+ * value of all FPR registers and 'ckfp_state' holds the last checkpointed
  * value of all FPR registers for the current transaction.
  *
  * Userspace 

[PATCH v5 18/20] powerpc: tm: Always use fp_state and vr_state to store live registers

2016-09-23 Thread Cyril Bur
There is currently an inconsistency as to how the entire CPU register
state is saved and restored when a thread uses transactional memory
(TM).

Using transactional memory results in the CPU having duplicated
(almost) all of its register state. This duplication results in a set
of registers which can be considered 'live', those being currently
modified by the instructions being executed and another set that is
frozen at a point in time.

On context switch, both sets of state have to be saved and (later)
restored. These two states are often called a variety of different
things. Common terms for the state which only exists after the CPU has
entered a transaction (performed a TBEGIN instruction) in hardware are
'transactional' or 'speculative'.

Between a TBEGIN and a TEND or TABORT (or an event that causes the
hardware to abort), regardless of the use of TSUSPEND the
transactional state can be referred to as the live state.

The second state is often to referred to as the 'checkpointed' state
and is a duplication of the live state when the TBEGIN instruction is
executed. This state is kept in the hardware and will be rolled back
to on transaction failure.

Currently all the registers stored in pt_regs are ALWAYS the live
registers, that is, when a thread has transactional registers their
values are stored in pt_regs and the checkpointed state is in
ckpt_regs. A strange opposite is true for fp_state/vr_state. When a
thread is non transactional fp_state/vr_state holds the live
registers. When a thread has initiated a transaction fp_state/vr_state
holds the checkpointed state and transact_fp/transact_vr become the
structure which holds the live state (at this point it is a
transactional state).

This method creates confusion as to where the live state is, in some
circumstances it requires extra work to determine where to put the
live state and prevents the use of common functions designed (probably
before TM) to save the live state.

With this patch pt_regs, fp_state and vr_state all represent the
same thing and the other structures [pending rename] are for
checkpointed state.

Acked-by: Simon Guo 
Signed-off-by: Cyril Bur 
---
 arch/powerpc/include/asm/processor.h |   7 +-
 arch/powerpc/kernel/process.c|  83 +++
 arch/powerpc/kernel/ptrace.c | 278 +--
 arch/powerpc/kernel/signal_32.c  |  50 +++
 arch/powerpc/kernel/signal_64.c  |  54 +++
 arch/powerpc/kernel/tm.S |  94 ++--
 arch/powerpc/kernel/traps.c  |  12 +-
 7 files changed, 197 insertions(+), 381 deletions(-)

diff --git a/arch/powerpc/include/asm/processor.h 
b/arch/powerpc/include/asm/processor.h
index 68e3bf5..feab2ce 100644
--- a/arch/powerpc/include/asm/processor.h
+++ b/arch/powerpc/include/asm/processor.h
@@ -267,16 +267,13 @@ struct thread_struct {
unsigned long   tm_dscr;
 
/*
-* Transactional FP and VSX 0-31 register set.
-* NOTE: the sense of these is the opposite of the integer ckpt_regs!
+* Checkpointed FP and VSX 0-31 register set.
 *
 * When a transaction is active/signalled/scheduled etc., *regs is the
 * most recent set of/speculated GPRs with ckpt_regs being the older
 * checkpointed regs to which we roll back if transaction aborts.
 *
-* However, fpr[] is the checkpointed 'base state' of FP regs, and
-* transact_fpr[] is the new set of transactional values.
-* VRs work the same way.
+* These are analogous to how ckpt_regs and pt_regs work
 */
struct thread_fp_state transact_fp;
struct thread_vr_state transact_vr;
diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 45b6ea0..6e9a054 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -815,26 +815,6 @@ static inline bool hw_brk_match(struct arch_hw_breakpoint 
*a,
 static void tm_reclaim_thread(struct thread_struct *thr,
  struct thread_info *ti, uint8_t cause)
 {
-   unsigned long msr_diff = 0;
-
-   /*
-* If FP/VSX registers have been already saved to the
-* thread_struct, move them to the transact_fp array.
-* We clear the TIF_RESTORE_TM bit since after the reclaim
-* the thread will no longer be transactional.
-*/
-   if (test_ti_thread_flag(ti, TIF_RESTORE_TM)) {
-   msr_diff = thr->ckpt_regs.msr & ~thr->regs->msr;
-   if (msr_diff & MSR_FP)
-   memcpy(>transact_fp, >fp_state,
-  sizeof(struct thread_fp_state));
-   if (msr_diff & MSR_VEC)
-   memcpy(>transact_vr, >vr_state,
-  sizeof(struct thread_vr_state));
-   clear_ti_thread_flag(ti, TIF_RESTORE_TM);
-   msr_diff &= MSR_FP | MSR_VEC | MSR_VSX | MSR_FE0 | MSR_FE1;

[PATCH v5 14/20] selftests/powerpc: Add checks for transactional GPRs in signal contexts

2016-09-23 Thread Cyril Bur
If a thread receives a signal while transactional the kernel creates a
second context to show the transactional state of the process. This
test loads some known values and waits for a signal and confirms that
the expected values are in the signal context.

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/tm/Makefile|   7 +-
 .../powerpc/tm/tm-signal-context-chk-gpr.c |  90 
 tools/testing/selftests/powerpc/tm/tm-signal.S | 114 +
 3 files changed, 210 insertions(+), 1 deletion(-)
 create mode 100644 
tools/testing/selftests/powerpc/tm/tm-signal-context-chk-gpr.c
 create mode 100644 tools/testing/selftests/powerpc/tm/tm-signal.S

diff --git a/tools/testing/selftests/powerpc/tm/Makefile 
b/tools/testing/selftests/powerpc/tm/Makefile
index 9d301d7..2b6fe8f 100644
--- a/tools/testing/selftests/powerpc/tm/Makefile
+++ b/tools/testing/selftests/powerpc/tm/Makefile
@@ -1,5 +1,7 @@
+SIGNAL_CONTEXT_CHK_TESTS := tm-signal-context-chk-gpr
+
 TEST_PROGS := tm-resched-dscr tm-syscall tm-signal-msr-resv tm-signal-stack \
-   tm-vmxcopy tm-fork tm-tar tm-tmspr tm-exec tm-execed
+   tm-vmxcopy tm-fork tm-tar tm-tmspr $(SIGNAL_CONTEXT_CHK_TESTS)
 
 all: $(TEST_PROGS)
 
@@ -11,6 +13,9 @@ tm-syscall: tm-syscall-asm.S
 tm-syscall: CFLAGS += -I../../../../../usr/include
 tm-tmspr: CFLAGS += -pthread
 
+$(SIGNAL_CONTEXT_CHK_TESTS): tm-signal.S
+$(SIGNAL_CONTEXT_CHK_TESTS): CFLAGS += -mhtm -m64
+
 include ../../lib.mk
 
 clean:
diff --git a/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-gpr.c 
b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-gpr.c
new file mode 100644
index 000..df91330
--- /dev/null
+++ b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-gpr.c
@@ -0,0 +1,90 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ *
+ * Test the kernel's signal frame code.
+ *
+ * The kernel sets up two sets of ucontexts if the signal was to be
+ * delivered while the thread was in a transaction.
+ * Expected behaviour is that the checkpointed state is in the user
+ * context passed to the signal handler. The speculated state can be
+ * accessed with the uc_link pointer.
+ *
+ * The rationale for this is that if TM unaware code (which linked
+ * against TM libs) installs a signal handler it will not know of the
+ * speculative nature of the 'live' registers and may infer the wrong
+ * thing.
+ */
+
+#include 
+#include 
+#include 
+#include 
+
+#include 
+
+#include "utils.h"
+#include "tm.h"
+
+#define MAX_ATTEMPT 50
+
+#define NV_GPR_REGS 18
+
+long tm_signal_self_context_load(pid_t pid, long *gprs, double *fps, vector 
int *vms, vector int *vss);
+
+static sig_atomic_t fail;
+
+static long gps[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 
17, 18,
+
-1,-2,-3,-4,-5,-6,-7,-8,-9,-10,-11,-12,-13,-14,-15,-16,-17,-18};
+
+static void signal_usr1(int signum, siginfo_t *info, void *uc)
+{
+   int i;
+   ucontext_t *ucp = uc;
+   ucontext_t *tm_ucp = ucp->uc_link;
+
+   for (i = 0; i < NV_GPR_REGS && !fail; i++) {
+   fail = (ucp->uc_mcontext.gp_regs[i + 14] != gps[i]);
+   fail |= (tm_ucp->uc_mcontext.gp_regs[i + 14] != gps[i + 
NV_GPR_REGS]);
+   if (fail)
+   printf("Failed on %d GPR %lu or %lu\n", i,
+   ucp->uc_mcontext.gp_regs[i + 14], 
tm_ucp->uc_mcontext.gp_regs[i + 14]);
+   }
+}
+
+static int tm_signal_context_chk_gpr()
+{
+   struct sigaction act;
+   int i;
+   long rc;
+   pid_t pid = getpid();
+
+   SKIP_IF(!have_htm());
+
+   act.sa_sigaction = signal_usr1;
+   sigemptyset(_mask);
+   act.sa_flags = SA_SIGINFO;
+   if (sigaction(SIGUSR1, , NULL) < 0) {
+   perror("sigaction sigusr1");
+   exit(1);
+   }
+
+   i = 0;
+   while (i < MAX_ATTEMPT && !fail) {
+   rc = tm_signal_self_context_load(pid, gps, NULL, NULL, NULL);
+   FAIL_IF(rc != pid);
+   i++;
+   }
+
+   return fail;
+}
+
+int main(void)
+{
+   return test_harness(tm_signal_context_chk_gpr, 
"tm_signal_context_chk_gpr");
+}
diff --git a/tools/testing/selftests/powerpc/tm/tm-signal.S 
b/tools/testing/selftests/powerpc/tm/tm-signal.S
new file mode 100644
index 000..4e13e8b
--- /dev/null
+++ b/tools/testing/selftests/powerpc/tm/tm-signal.S
@@ -0,0 +1,114 @@
+/*
+ * Copyright 2015, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version

[PATCH v5 05/20] powerpc: Never giveup a reclaimed thread when enabling kernel {fp, altivec, vsx}

2016-09-23 Thread Cyril Bur
After a thread is reclaimed from its active or suspended transactional
state the checkpointed state exists on CPU, this state (along with the
live/transactional state) has been saved in its entirety by the
reclaiming process.

There exists a sequence of events that would cause the kernel to call
one of enable_kernel_fp(), enable_kernel_altivec() or
enable_kernel_vsx() after a thread has been reclaimed. These functions
save away any user state on the CPU so that the kernel can use the
registers. Not only is this saving away unnecessary at this point, it
is actually incorrect. It causes a save of the checkpointed state to
the live structures within the thread struct thus destroying the true
live state for that thread.

Signed-off-by: Cyril Bur 
---
 arch/powerpc/kernel/process.c | 39 ---
 1 file changed, 36 insertions(+), 3 deletions(-)

diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 34ee5f2..45b6ea0 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -205,12 +205,23 @@ EXPORT_SYMBOL_GPL(flush_fp_to_thread);
 
 void enable_kernel_fp(void)
 {
+   unsigned long cpumsr;
+
WARN_ON(preemptible());
 
-   msr_check_and_set(MSR_FP);
+   cpumsr = msr_check_and_set(MSR_FP);
 
if (current->thread.regs && (current->thread.regs->msr & MSR_FP)) {
check_if_tm_restore_required(current);
+   /*
+* If a thread has already been reclaimed then the
+* checkpointed registers are on the CPU but have definitely
+* been saved by the reclaim code. Don't need to and *cannot*
+* giveup as this would save  to the 'live' structure not the
+* checkpointed structure.
+*/
+   if(!msr_tm_active(cpumsr) && 
msr_tm_active(current->thread.regs->msr))
+   return;
__giveup_fpu(current);
}
 }
@@ -257,12 +268,23 @@ EXPORT_SYMBOL(giveup_altivec);
 
 void enable_kernel_altivec(void)
 {
+   unsigned long cpumsr;
+
WARN_ON(preemptible());
 
-   msr_check_and_set(MSR_VEC);
+   cpumsr = msr_check_and_set(MSR_VEC);
 
if (current->thread.regs && (current->thread.regs->msr & MSR_VEC)) {
check_if_tm_restore_required(current);
+   /*
+* If a thread has already been reclaimed then the
+* checkpointed registers are on the CPU but have definitely
+* been saved by the reclaim code. Don't need to and *cannot*
+* giveup as this would save  to the 'live' structure not the
+* checkpointed structure.
+*/
+   if(!msr_tm_active(cpumsr) && 
msr_tm_active(current->thread.regs->msr))
+   return;
__giveup_altivec(current);
}
 }
@@ -331,12 +353,23 @@ static void save_vsx(struct task_struct *tsk)
 
 void enable_kernel_vsx(void)
 {
+   unsigned long cpumsr;
+
WARN_ON(preemptible());
 
-   msr_check_and_set(MSR_FP|MSR_VEC|MSR_VSX);
+   cpumsr = msr_check_and_set(MSR_FP|MSR_VEC|MSR_VSX);
 
if (current->thread.regs && (current->thread.regs->msr & MSR_VSX)) {
check_if_tm_restore_required(current);
+   /*
+* If a thread has already been reclaimed then the
+* checkpointed registers are on the CPU but have definitely
+* been saved by the reclaim code. Don't need to and *cannot*
+* giveup as this would save  to the 'live' structure not the
+* checkpointed structure.
+*/
+   if(!msr_tm_active(cpumsr) && 
msr_tm_active(current->thread.regs->msr))
+   return;
if (current->thread.regs->msr & MSR_FP)
__giveup_fpu(current);
if (current->thread.regs->msr & MSR_VEC)
-- 
2.10.0



[PATCH v5 09/20] selftests/powerpc: Move VMX stack frame macros to header file

2016-09-23 Thread Cyril Bur
Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/math/vmx_asm.S | 85 +-
 tools/testing/selftests/powerpc/vmx_asm.h  | 98 ++
 2 files changed, 99 insertions(+), 84 deletions(-)
 create mode 100644 tools/testing/selftests/powerpc/vmx_asm.h

diff --git a/tools/testing/selftests/powerpc/math/vmx_asm.S 
b/tools/testing/selftests/powerpc/math/vmx_asm.S
index 1b8c248..fd74da4 100644
--- a/tools/testing/selftests/powerpc/math/vmx_asm.S
+++ b/tools/testing/selftests/powerpc/math/vmx_asm.S
@@ -8,90 +8,7 @@
  */
 
 #include "../basic_asm.h"
-
-# POS MUST BE 16 ALIGNED!
-#define PUSH_VMX(pos,reg) \
-   li  reg,pos; \
-   stvxv20,reg,sp; \
-   addireg,reg,16; \
-   stvxv21,reg,sp; \
-   addireg,reg,16; \
-   stvxv22,reg,sp; \
-   addireg,reg,16; \
-   stvxv23,reg,sp; \
-   addireg,reg,16; \
-   stvxv24,reg,sp; \
-   addireg,reg,16; \
-   stvxv25,reg,sp; \
-   addireg,reg,16; \
-   stvxv26,reg,sp; \
-   addireg,reg,16; \
-   stvxv27,reg,sp; \
-   addireg,reg,16; \
-   stvxv28,reg,sp; \
-   addireg,reg,16; \
-   stvxv29,reg,sp; \
-   addireg,reg,16; \
-   stvxv30,reg,sp; \
-   addireg,reg,16; \
-   stvxv31,reg,sp;
-
-# POS MUST BE 16 ALIGNED!
-#define POP_VMX(pos,reg) \
-   li  reg,pos; \
-   lvx v20,reg,sp; \
-   addireg,reg,16; \
-   lvx v21,reg,sp; \
-   addireg,reg,16; \
-   lvx v22,reg,sp; \
-   addireg,reg,16; \
-   lvx v23,reg,sp; \
-   addireg,reg,16; \
-   lvx v24,reg,sp; \
-   addireg,reg,16; \
-   lvx v25,reg,sp; \
-   addireg,reg,16; \
-   lvx v26,reg,sp; \
-   addireg,reg,16; \
-   lvx v27,reg,sp; \
-   addireg,reg,16; \
-   lvx v28,reg,sp; \
-   addireg,reg,16; \
-   lvx v29,reg,sp; \
-   addireg,reg,16; \
-   lvx v30,reg,sp; \
-   addireg,reg,16; \
-   lvx v31,reg,sp;
-
-# Carefull this will 'clobber' vmx (by design)
-# Don't call this from C
-FUNC_START(load_vmx)
-   li  r5,0
-   lvx v20,r5,r3
-   addir5,r5,16
-   lvx v21,r5,r3
-   addir5,r5,16
-   lvx v22,r5,r3
-   addir5,r5,16
-   lvx v23,r5,r3
-   addir5,r5,16
-   lvx v24,r5,r3
-   addir5,r5,16
-   lvx v25,r5,r3
-   addir5,r5,16
-   lvx v26,r5,r3
-   addir5,r5,16
-   lvx v27,r5,r3
-   addir5,r5,16
-   lvx v28,r5,r3
-   addir5,r5,16
-   lvx v29,r5,r3
-   addir5,r5,16
-   lvx v30,r5,r3
-   addir5,r5,16
-   lvx v31,r5,r3
-   blr
-FUNC_END(load_vmx)
+#include "../vmx_asm.h"
 
 # Should be safe from C, only touches r4, r5 and v0,v1,v2
 FUNC_START(check_vmx)
diff --git a/tools/testing/selftests/powerpc/vmx_asm.h 
b/tools/testing/selftests/powerpc/vmx_asm.h
new file mode 100644
index 000..461845dd
--- /dev/null
+++ b/tools/testing/selftests/powerpc/vmx_asm.h
@@ -0,0 +1,98 @@
+/*
+ * Copyright 2015, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+#include "basic_asm.h"
+
+/* POS MUST BE 16 ALIGNED! */
+#define PUSH_VMX(pos,reg) \
+   li  reg,pos; \
+   stvxv20,reg,%r1; \
+   addireg,reg,16; \
+   stvxv21,reg,%r1; \
+   addireg,reg,16; \
+   stvxv22,reg,%r1; \
+   addireg,reg,16; \
+   stvxv23,reg,%r1; \
+   addireg,reg,16; \
+   stvxv24,reg,%r1; \
+   addireg,reg,16; \
+   stvxv25,reg,%r1; \
+   addireg,reg,16; \
+   stvxv26,reg,%r1; \
+   addireg,reg,16; \
+   stvxv27,reg,%r1; \
+   addireg,reg,16; \
+   stvxv28,reg,%r1; \
+   addireg,reg,16; \
+   stvxv29,reg,%r1; \
+   addireg,reg,16; \
+   stvxv30,reg,%r1; \
+   addireg,reg,16; \
+   stvxv31,reg,%r1;
+
+/* POS MUST BE 16 ALIGNED! */
+#define POP_VMX(pos,reg) \
+   li  reg,pos; \
+   lvx v20,reg,%r1; \
+   addireg,reg,16; \
+   lvx v21,reg,%r1; \
+   addireg,reg,16; \
+   lvx v22,reg,%r1; \
+   addireg,reg,16; \
+   lvx v23,reg,%r1; \
+   addireg,reg,16; \
+   lvx v24,reg,%r1; \
+   addireg,reg,16; \
+   lvx v25,reg,%r1; \
+   addireg,reg,16; \
+   lvx v26,reg,%r1; \
+   addireg,reg,16; \
+   lvx v27,reg,%r1; \
+   addireg,reg,16; \
+   lvx v28,reg,%r1; \
+   addireg,reg,16; \
+  

[PATCH v5 07/20] selftests/powerpc: Check for VSX preservation across userspace preemption

2016-09-23 Thread Cyril Bur
Ensure the kernel correctly switches VSX registers correctly. VSX
registers are all volatile, and despite the kernel preserving VSX
across syscalls, it doesn't have to. Test that during interrupts and
timeslices ending the VSX regs remain the same.

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/math/Makefile  |   4 +-
 tools/testing/selftests/powerpc/math/vsx_asm.S |  61 +
 tools/testing/selftests/powerpc/math/vsx_preempt.c | 147 +
 tools/testing/selftests/powerpc/vsx_asm.h  |  71 ++
 4 files changed, 282 insertions(+), 1 deletion(-)
 create mode 100644 tools/testing/selftests/powerpc/math/vsx_asm.S
 create mode 100644 tools/testing/selftests/powerpc/math/vsx_preempt.c
 create mode 100644 tools/testing/selftests/powerpc/vsx_asm.h

diff --git a/tools/testing/selftests/powerpc/math/Makefile 
b/tools/testing/selftests/powerpc/math/Makefile
index 5b88875..aa6598b 100644
--- a/tools/testing/selftests/powerpc/math/Makefile
+++ b/tools/testing/selftests/powerpc/math/Makefile
@@ -1,4 +1,4 @@
-TEST_PROGS := fpu_syscall fpu_preempt fpu_signal vmx_syscall vmx_preempt 
vmx_signal
+TEST_PROGS := fpu_syscall fpu_preempt fpu_signal vmx_syscall vmx_preempt 
vmx_signal vsx_preempt
 
 all: $(TEST_PROGS)
 
@@ -13,6 +13,8 @@ vmx_syscall: vmx_asm.S
 vmx_preempt: vmx_asm.S
 vmx_signal: vmx_asm.S
 
+vsx_preempt: vsx_asm.S
+
 include ../../lib.mk
 
 clean:
diff --git a/tools/testing/selftests/powerpc/math/vsx_asm.S 
b/tools/testing/selftests/powerpc/math/vsx_asm.S
new file mode 100644
index 000..a110dd8
--- /dev/null
+++ b/tools/testing/selftests/powerpc/math/vsx_asm.S
@@ -0,0 +1,61 @@
+/*
+ * Copyright 2015, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+#include "../basic_asm.h"
+#include "../vsx_asm.h"
+
+#long check_vsx(vector int *r3);
+#This function wraps storeing VSX regs to the end of an array and a
+#call to a comparison function in C which boils down to a memcmp()
+FUNC_START(check_vsx)
+   PUSH_BASIC_STACK(32)
+   std r3,STACK_FRAME_PARAM(0)(sp)
+   addi r3, r3, 16 * 12 #Second half of array
+   bl store_vsx
+   ld r3,STACK_FRAME_PARAM(0)(sp)
+   bl vsx_memcmp
+   POP_BASIC_STACK(32)
+   blr
+FUNC_END(check_vsx)
+
+# int preempt_vmx(vector int *varray, int *threads_starting,
+# int *running);
+# On starting will (atomically) decrement threads_starting as a signal
+# that the VMX have been loaded with varray. Will proceed to check the
+# validity of the VMX registers while running is not zero.
+FUNC_START(preempt_vsx)
+   PUSH_BASIC_STACK(512)
+   std r3,STACK_FRAME_PARAM(0)(sp) # vector int *varray
+   std r4,STACK_FRAME_PARAM(1)(sp) # int *threads_starting
+   std r5,STACK_FRAME_PARAM(2)(sp) # int *running
+
+   bl load_vsx
+   nop
+
+   sync
+   # Atomic DEC
+   ld r3,STACK_FRAME_PARAM(1)(sp)
+1: lwarx r4,0,r3
+   addi r4,r4,-1
+   stwcx. r4,0,r3
+   bne- 1b
+
+2: ld r3,STACK_FRAME_PARAM(0)(sp)
+   bl check_vsx
+   nop
+   cmpdi r3,0
+   bne 3f
+   ld r4,STACK_FRAME_PARAM(2)(sp)
+   ld r5,0(r4)
+   cmpwi r5,0
+   bne 2b
+
+3: POP_BASIC_STACK(512)
+   blr
+FUNC_END(preempt_vsx)
diff --git a/tools/testing/selftests/powerpc/math/vsx_preempt.c 
b/tools/testing/selftests/powerpc/math/vsx_preempt.c
new file mode 100644
index 000..6387f03
--- /dev/null
+++ b/tools/testing/selftests/powerpc/math/vsx_preempt.c
@@ -0,0 +1,147 @@
+/*
+ * Copyright 2015, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ * This test attempts to see if the VSX registers change across preemption.
+ * There is no way to be sure preemption happened so this test just
+ * uses many threads and a long wait. As such, a successful test
+ * doesn't mean much but a failure is bad.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include "utils.h"
+
+/* Time to wait for workers to get preempted (seconds) */
+#define PREEMPT_TIME 20
+/*
+ * Factor by which to multiply number of online CPUs for total number of
+ * worker threads
+ */
+#define THREAD_FACTOR 8
+
+/*
+ * Ensure there is twice the number of non-volatile VMX regs!
+ * check_vmx() is going to use the other half as space to put the live
+ * registers before calling vsx_memcmp()
+ */
+__thread vector int varray[24] = {
+   {1, 2, 3, 4 }, {5, 6, 7, 8 }, {9, 10,11,12},
+   {13,14,15,16}, {17,18,19,20}, {21,22,23,24},
+  

[PATCH v5 15/20] selftests/powerpc: Add checks for transactional FPUs in signal contexts

2016-09-23 Thread Cyril Bur
If a thread receives a signal while transactional the kernel creates a
second context to show the transactional state of the process. This
test loads some known values and waits for a signal and confirms that
the expected values are in the signal context.

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/tm/Makefile|  2 +-
 .../powerpc/tm/tm-signal-context-chk-fpu.c | 92 ++
 2 files changed, 93 insertions(+), 1 deletion(-)
 create mode 100644 
tools/testing/selftests/powerpc/tm/tm-signal-context-chk-fpu.c

diff --git a/tools/testing/selftests/powerpc/tm/Makefile 
b/tools/testing/selftests/powerpc/tm/Makefile
index 2b6fe8f..103648f 100644
--- a/tools/testing/selftests/powerpc/tm/Makefile
+++ b/tools/testing/selftests/powerpc/tm/Makefile
@@ -1,4 +1,4 @@
-SIGNAL_CONTEXT_CHK_TESTS := tm-signal-context-chk-gpr
+SIGNAL_CONTEXT_CHK_TESTS := tm-signal-context-chk-gpr tm-signal-context-chk-fpu
 
 TEST_PROGS := tm-resched-dscr tm-syscall tm-signal-msr-resv tm-signal-stack \
tm-vmxcopy tm-fork tm-tar tm-tmspr $(SIGNAL_CONTEXT_CHK_TESTS)
diff --git a/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-fpu.c 
b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-fpu.c
new file mode 100644
index 000..c760deb
--- /dev/null
+++ b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-fpu.c
@@ -0,0 +1,92 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ *
+ * Test the kernel's signal frame code.
+ *
+ * The kernel sets up two sets of ucontexts if the signal was to be
+ * delivered while the thread was in a transaction.
+ * Expected behaviour is that the checkpointed state is in the user
+ * context passed to the signal handler. The speculated state can be
+ * accessed with the uc_link pointer.
+ *
+ * The rationale for this is that if TM unaware code (which linked
+ * against TM libs) installs a signal handler it will not know of the
+ * speculative nature of the 'live' registers and may infer the wrong
+ * thing.
+ */
+
+#include 
+#include 
+#include 
+#include 
+
+#include 
+
+#include "utils.h"
+#include "tm.h"
+
+#define MAX_ATTEMPT 50
+
+#define NV_FPU_REGS 18
+
+long tm_signal_self_context_load(pid_t pid, long *gprs, double *fps, vector 
int *vms, vector int *vss);
+
+/* Be sure there are 2x as many as there are NV FPU regs (2x18) */
+static double fps[] = {
+1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18,
+   -1,-2,-3,-4,-5,-6,-7,-8,-9,-10,-11,-12,-13,-14,-15,-16,-17,-18
+};
+
+static sig_atomic_t fail;
+
+static void signal_usr1(int signum, siginfo_t *info, void *uc)
+{
+   int i;
+   ucontext_t *ucp = uc;
+   ucontext_t *tm_ucp = ucp->uc_link;
+
+   for (i = 0; i < NV_FPU_REGS && !fail; i++) {
+   fail = (ucp->uc_mcontext.fp_regs[i + 14] != fps[i]);
+   fail |= (tm_ucp->uc_mcontext.fp_regs[i + 14] != fps[i + 
NV_FPU_REGS]);
+   if (fail)
+   printf("Failed on %d FP %g or %g\n", i, 
ucp->uc_mcontext.fp_regs[i + 14], tm_ucp->uc_mcontext.fp_regs[i + 14]);
+   }
+}
+
+static int tm_signal_context_chk_fpu()
+{
+   struct sigaction act;
+   int i;
+   long rc;
+   pid_t pid = getpid();
+
+   SKIP_IF(!have_htm());
+
+   act.sa_sigaction = signal_usr1;
+   sigemptyset(_mask);
+   act.sa_flags = SA_SIGINFO;
+   if (sigaction(SIGUSR1, , NULL) < 0) {
+   perror("sigaction sigusr1");
+   exit(1);
+   }
+
+   i = 0;
+   while (i < MAX_ATTEMPT && !fail) {
+   rc = tm_signal_self_context_load(pid, NULL, fps, NULL, NULL);
+   FAIL_IF(rc != pid);
+   i++;
+   }
+
+   return fail;
+}
+
+int main(void)
+{
+   return test_harness(tm_signal_context_chk_fpu, 
"tm_signal_context_chk_fpu");
+}
-- 
2.10.0



[PATCH v5 16/20] selftests/powerpc: Add checks for transactional VMXs in signal contexts

2016-09-23 Thread Cyril Bur
If a thread receives a signal while transactional the kernel creates a
second context to show the transactional state of the process. This
test loads some known values and waits for a signal and confirms that
the expected values are in the signal context.

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/tm/Makefile|   3 +-
 .../powerpc/tm/tm-signal-context-chk-vmx.c | 110 +
 2 files changed, 112 insertions(+), 1 deletion(-)
 create mode 100644 
tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vmx.c

diff --git a/tools/testing/selftests/powerpc/tm/Makefile 
b/tools/testing/selftests/powerpc/tm/Makefile
index 103648f..06c44aa 100644
--- a/tools/testing/selftests/powerpc/tm/Makefile
+++ b/tools/testing/selftests/powerpc/tm/Makefile
@@ -1,4 +1,5 @@
-SIGNAL_CONTEXT_CHK_TESTS := tm-signal-context-chk-gpr tm-signal-context-chk-fpu
+SIGNAL_CONTEXT_CHK_TESTS := tm-signal-context-chk-gpr 
tm-signal-context-chk-fpu \
+   tm-signal-context-chk-vmx
 
 TEST_PROGS := tm-resched-dscr tm-syscall tm-signal-msr-resv tm-signal-stack \
tm-vmxcopy tm-fork tm-tar tm-tmspr $(SIGNAL_CONTEXT_CHK_TESTS)
diff --git a/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vmx.c 
b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vmx.c
new file mode 100644
index 000..f0ee55f
--- /dev/null
+++ b/tools/testing/selftests/powerpc/tm/tm-signal-context-chk-vmx.c
@@ -0,0 +1,110 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ *
+ * Test the kernel's signal frame code.
+ *
+ * The kernel sets up two sets of ucontexts if the signal was to be
+ * delivered while the thread was in a transaction.
+ * Expected behaviour is that the checkpointed state is in the user
+ * context passed to the signal handler. The speculated state can be
+ * accessed with the uc_link pointer.
+ *
+ * The rationale for this is that if TM unaware code (which linked
+ * against TM libs) installs a signal handler it will not know of the
+ * speculative nature of the 'live' registers and may infer the wrong
+ * thing.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include 
+
+#include "utils.h"
+#include "tm.h"
+
+#define MAX_ATTEMPT 50
+
+#define NV_VMX_REGS 12
+
+long tm_signal_self_context_load(pid_t pid, long *gprs, double *fps, vector 
int *vms, vector int *vss);
+
+static sig_atomic_t fail;
+
+vector int vms[] = {
+   {1, 2, 3, 4 },{5, 6, 7, 8 },{9, 10,11,12},
+   {13,14,15,16},{17,18,19,20},{21,22,23,24},
+   {25,26,27,28},{29,30,31,32},{33,34,35,36},
+   {37,38,39,40},{41,42,43,44},{45,46,47,48},
+   {-1, -2, -3, -4}, {-5, -6, -7, -8}, {-9, -10,-11,-12},
+   {-13,-14,-15,-16},{-17,-18,-19,-20},{-21,-22,-23,-24},
+   {-25,-26,-27,-28},{-29,-30,-31,-32},{-33,-34,-35,-36},
+   {-37,-38,-39,-40},{-41,-42,-43,-44},{-45,-46,-47,-48}
+};
+
+static void signal_usr1(int signum, siginfo_t *info, void *uc)
+{
+   int i;
+   ucontext_t *ucp = uc;
+   ucontext_t *tm_ucp = ucp->uc_link;
+
+   for (i = 0; i < NV_VMX_REGS && !fail; i++) {
+   fail = memcmp(ucp->uc_mcontext.v_regs->vrregs[i + 20],
+   [i], sizeof(vector int));
+   fail |= memcmp(tm_ucp->uc_mcontext.v_regs->vrregs[i + 20],
+   [i + NV_VMX_REGS], sizeof (vector int));
+
+   if (fail) {
+   int j;
+
+   fprintf(stderr, "Failed on %d vmx 0x", i);
+   for (j = 0; j < 4; j++)
+   fprintf(stderr, "%04x", 
ucp->uc_mcontext.v_regs->vrregs[i + 20][j]);
+   fprintf(stderr, " vs 0x");
+   for (j = 0 ; j < 4; j++)
+   fprintf(stderr, "%04x", 
tm_ucp->uc_mcontext.v_regs->vrregs[i + 20][j]);
+   fprintf(stderr, "\n");
+   }
+   }
+}
+
+static int tm_signal_context_chk()
+{
+   struct sigaction act;
+   int i;
+   long rc;
+   pid_t pid = getpid();
+
+   SKIP_IF(!have_htm());
+
+   act.sa_sigaction = signal_usr1;
+   sigemptyset(_mask);
+   act.sa_flags = SA_SIGINFO;
+   if (sigaction(SIGUSR1, , NULL) < 0) {
+   perror("sigaction sigusr1");
+   exit(1);
+   }
+
+   i = 0;
+   while (i < MAX_ATTEMPT && !fail) {
+   rc = tm_signal_self_context_load(pid, NULL, NULL, vms, NULL);
+   FAIL_IF(rc != pid);
+   i++;
+   }
+
+   return fail;
+}
+
+int main(void)
+{
+   return test_harness(tm_signal_context_chk, "tm_signal_context_chk_vmx");
+}
-- 
2.10.0



[PATCH v5 08/20] selftests/powerpc: Rework FPU stack placement macros and move to header file

2016-09-23 Thread Cyril Bur
The FPU regs are placed at the top of the stack frame. Currently the
position expected to be passed to the macro. The macros now should be
passed the stack frame size and from there they can calculate where to
put the regs, this makes the use simpler.

Also move them to a header file to be used in an different area of the
powerpc selftests

Signed-off-by: Cyril Bur 
---
 tools/testing/selftests/powerpc/fpu_asm.h  | 81 ++
 tools/testing/selftests/powerpc/math/fpu_asm.S | 73 ++-
 2 files changed, 86 insertions(+), 68 deletions(-)
 create mode 100644 tools/testing/selftests/powerpc/fpu_asm.h

diff --git a/tools/testing/selftests/powerpc/fpu_asm.h 
b/tools/testing/selftests/powerpc/fpu_asm.h
new file mode 100644
index 000..24061b8
--- /dev/null
+++ b/tools/testing/selftests/powerpc/fpu_asm.h
@@ -0,0 +1,81 @@
+/*
+ * Copyright 2016, Cyril Bur, IBM Corp.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+#ifndef _SELFTESTS_POWERPC_FPU_ASM_H
+#define _SELFTESTS_POWERPC_FPU_ASM_H
+#include "basic_asm.h"
+
+#define PUSH_FPU(stack_size) \
+   stfdf31,(stack_size + STACK_FRAME_MIN_SIZE)(%r1); \
+   stfdf30,(stack_size + STACK_FRAME_MIN_SIZE - 8)(%r1); \
+   stfdf29,(stack_size + STACK_FRAME_MIN_SIZE - 16)(%r1); \
+   stfdf28,(stack_size + STACK_FRAME_MIN_SIZE - 24)(%r1); \
+   stfdf27,(stack_size + STACK_FRAME_MIN_SIZE - 32)(%r1); \
+   stfdf26,(stack_size + STACK_FRAME_MIN_SIZE - 40)(%r1); \
+   stfdf25,(stack_size + STACK_FRAME_MIN_SIZE - 48)(%r1); \
+   stfdf24,(stack_size + STACK_FRAME_MIN_SIZE - 56)(%r1); \
+   stfdf23,(stack_size + STACK_FRAME_MIN_SIZE - 64)(%r1); \
+   stfdf22,(stack_size + STACK_FRAME_MIN_SIZE - 72)(%r1); \
+   stfdf21,(stack_size + STACK_FRAME_MIN_SIZE - 80)(%r1); \
+   stfdf20,(stack_size + STACK_FRAME_MIN_SIZE - 88)(%r1); \
+   stfdf19,(stack_size + STACK_FRAME_MIN_SIZE - 96)(%r1); \
+   stfdf18,(stack_size + STACK_FRAME_MIN_SIZE - 104)(%r1); \
+   stfdf17,(stack_size + STACK_FRAME_MIN_SIZE - 112)(%r1); \
+   stfdf16,(stack_size + STACK_FRAME_MIN_SIZE - 120)(%r1); \
+   stfdf15,(stack_size + STACK_FRAME_MIN_SIZE - 128)(%r1); \
+   stfdf14,(stack_size + STACK_FRAME_MIN_SIZE - 136)(%r1);
+
+#define POP_FPU(stack_size) \
+   lfd f31,(stack_size + STACK_FRAME_MIN_SIZE)(%r1); \
+   lfd f30,(stack_size + STACK_FRAME_MIN_SIZE - 8)(%r1); \
+   lfd f29,(stack_size + STACK_FRAME_MIN_SIZE - 16)(%r1); \
+   lfd f28,(stack_size + STACK_FRAME_MIN_SIZE - 24)(%r1); \
+   lfd f27,(stack_size + STACK_FRAME_MIN_SIZE - 32)(%r1); \
+   lfd f26,(stack_size + STACK_FRAME_MIN_SIZE - 40)(%r1); \
+   lfd f25,(stack_size + STACK_FRAME_MIN_SIZE - 48)(%r1); \
+   lfd f24,(stack_size + STACK_FRAME_MIN_SIZE - 56)(%r1); \
+   lfd f23,(stack_size + STACK_FRAME_MIN_SIZE - 64)(%r1); \
+   lfd f22,(stack_size + STACK_FRAME_MIN_SIZE - 72)(%r1); \
+   lfd f21,(stack_size + STACK_FRAME_MIN_SIZE - 80)(%r1); \
+   lfd f20,(stack_size + STACK_FRAME_MIN_SIZE - 88)(%r1); \
+   lfd f19,(stack_size + STACK_FRAME_MIN_SIZE - 96)(%r1); \
+   lfd f18,(stack_size + STACK_FRAME_MIN_SIZE - 104)(%r1); \
+   lfd f17,(stack_size + STACK_FRAME_MIN_SIZE - 112)(%r1); \
+   lfd f16,(stack_size + STACK_FRAME_MIN_SIZE - 120)(%r1); \
+   lfd f15,(stack_size + STACK_FRAME_MIN_SIZE - 128)(%r1); \
+   lfd f14,(stack_size + STACK_FRAME_MIN_SIZE - 136)(%r1);
+
+/*
+ * Careful calling this, it will 'clobber' fpu (by design)
+ * Don't call this from C
+ */
+FUNC_START(load_fpu)
+   lfd f14,0(r3)
+   lfd f15,8(r3)
+   lfd f16,16(r3)
+   lfd f17,24(r3)
+   lfd f18,32(r3)
+   lfd f19,40(r3)
+   lfd f20,48(r3)
+   lfd f21,56(r3)
+   lfd f22,64(r3)
+   lfd f23,72(r3)
+   lfd f24,80(r3)
+   lfd f25,88(r3)
+   lfd f26,96(r3)
+   lfd f27,104(r3)
+   lfd f28,112(r3)
+   lfd f29,120(r3)
+   lfd f30,128(r3)
+   lfd f31,136(r3)
+   blr
+FUNC_END(load_fpu)
+
+#endif /* _SELFTESTS_POWERPC_FPU_ASM_H */
+
diff --git a/tools/testing/selftests/powerpc/math/fpu_asm.S 
b/tools/testing/selftests/powerpc/math/fpu_asm.S
index f3711d8..241f067 100644
--- a/tools/testing/selftests/powerpc/math/fpu_asm.S
+++ b/tools/testing/selftests/powerpc/math/fpu_asm.S
@@ -8,70 +8,7 @@
  */
 
 #include "../basic_asm.h"
-
-#define PUSH_FPU(pos) \
-   stfdf14,pos(sp); \
-   stfdf15,pos+8(sp); \
-   stfdf16,pos+16(sp); \
-   stfdf17,pos+24(sp); \
-