1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * Ptrace test TM SPR registers
5 * Copyright (C) 2015 Anshuman Khandual, IBM Corporation.
10 /* Tracee and tracer shared data */
13 struct tm_spr_regs regs
;
18 struct shared
*cptr
, *pptr
;
23 #define TM_KVM_SCHED 0xe0000001ac000001
24 int validate_tm_spr(struct tm_spr_regs
*regs
)
26 FAIL_IF(regs
->tm_tfhar
!= tfhar
);
27 FAIL_IF((regs
->tm_texasr
== TM_KVM_SCHED
) && (regs
->tm_tfiar
!= 0));
34 unsigned long result
, texasr
;
37 cptr
= (struct shared
*)shmat(shm_id
, NULL
, 0);
38 cptr1
= (int *)shmat(shm_id1
, NULL
, 0);
44 /* TM failover handler should follow "tbegin.;" */
46 "bl 4f;" /* $ = TFHAR - 12 */
69 "mfspr %[texasr], %[sprn_texasr];"
72 : [tfhar
] "=r" (tfhar
), [res
] "=r" (result
),
73 [texasr
] "=r" (texasr
), [cptr1
] "=b" (cptr1
)
74 : [sprn_texasr
] "i" (SPRN_TEXASR
)
75 : "memory", "r0", "r8", "r31"
78 /* There are 2 32bit instructions before tbegin. */
85 ret
= validate_tm_spr((struct tm_spr_regs
*)&cptr
->regs
);
97 int trace_tm_spr(pid_t child
)
99 FAIL_IF(start_trace(child
));
100 FAIL_IF(show_tm_spr(child
, (struct tm_spr_regs
*)&pptr
->regs
));
102 printf("TFHAR: %lx TEXASR: %lx TFIAR: %lx\n", pptr
->regs
.tm_tfhar
,
103 pptr
->regs
.tm_texasr
, pptr
->regs
.tm_tfiar
);
106 FAIL_IF(stop_trace(child
));
111 int ptrace_tm_spr(void)
116 SKIP_IF_MSG(!have_htm(), "Don't have transactional memory");
117 SKIP_IF_MSG(htm_is_synthetic(), "Transactional memory is synthetic");
118 shm_id
= shmget(IPC_PRIVATE
, sizeof(struct shared
), 0777|IPC_CREAT
);
119 shm_id1
= shmget(IPC_PRIVATE
, sizeof(int), 0777|IPC_CREAT
);
122 perror("fork() failed");
130 pptr
= (struct shared
*)shmat(shm_id
, NULL
, 0);
131 pptr1
= (int *)shmat(shm_id1
, NULL
, 0);
134 asm volatile("" : : : "memory");
135 ret
= trace_tm_spr(pid
);
139 shmdt((void *)pptr1
);
140 shmctl(shm_id
, IPC_RMID
, NULL
);
141 shmctl(shm_id1
, IPC_RMID
, NULL
);
146 shmdt((void *)pptr1
);
148 shmctl(shm_id
, IPC_RMID
, NULL
);
149 shmctl(shm_id1
, IPC_RMID
, NULL
);
151 printf("Child's exit status not captured\n");
155 return (WIFEXITED(status
) && WEXITSTATUS(status
)) ? TEST_FAIL
:
161 int main(int argc
, char *argv
[])
163 return test_harness(ptrace_tm_spr
, "ptrace_tm_spr");