git: 05296a0ff615 - main - ktrace: Record syscall violations with KTR_CAPFAIL
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Sun, 07 Apr 2024 23:57:08 UTC
The branch main has been updated by jfree:
URL: https://cgit.FreeBSD.org/src/commit/?id=05296a0ff615566d25c77c5e6619b08724d2eecb
commit 05296a0ff615566d25c77c5e6619b08724d2eecb
Author: Jake Freeland <jfree@FreeBSD.org>
AuthorDate: 2024-04-06 18:31:18 +0000
Commit: Jake Freeland <jfree@FreeBSD.org>
CommitDate: 2024-04-07 23:52:51 +0000
ktrace: Record syscall violations with KTR_CAPFAIL
Report syscalls that are not allowed in capability mode with
CAPFAIL_SYSCALL.
Reviewed by: markj
Approved by: markj (mentor)
MFC after: 1 month
Differential Revision: https://reviews.freebsd.org/D40678
---
sys/amd64/amd64/sys_machdep.c | 52 +++++++++++++++++++++----------------------
sys/arm/arm/sys_machdep.c | 27 ++++++++++------------
sys/i386/i386/sys_machdep.c | 34 +++++++++++++---------------
sys/kern/kern_descrip.c | 2 ++
sys/kern/kern_sig.c | 12 +++++++---
sys/kern/subr_syscall.c | 11 +++++----
6 files changed, 71 insertions(+), 67 deletions(-)
diff --git a/sys/amd64/amd64/sys_machdep.c b/sys/amd64/amd64/sys_machdep.c
index dd4eef610147..b626925e1ea1 100644
--- a/sys/amd64/amd64/sys_machdep.c
+++ b/sys/amd64/amd64/sys_machdep.c
@@ -187,35 +187,33 @@ sysarch(struct thread *td, struct sysarch_args *uap)
* explicitly indicate whether or not the operation is safe to
* perform in capability mode.
*/
- if (IN_CAPABILITY_MODE(td)) {
- switch (uap->op) {
- case I386_GET_LDT:
- case I386_SET_LDT:
- case I386_GET_IOPERM:
- case I386_GET_FSBASE:
- case I386_SET_FSBASE:
- case I386_GET_GSBASE:
- case I386_SET_GSBASE:
- case I386_GET_XFPUSTATE:
- case I386_SET_PKRU:
- case I386_CLEAR_PKRU:
- case AMD64_GET_FSBASE:
- case AMD64_SET_FSBASE:
- case AMD64_GET_GSBASE:
- case AMD64_SET_GSBASE:
- case AMD64_GET_XFPUSTATE:
- case AMD64_SET_PKRU:
- case AMD64_CLEAR_PKRU:
- break;
+ switch (uap->op) {
+ case I386_GET_LDT:
+ case I386_SET_LDT:
+ case I386_GET_IOPERM:
+ case I386_GET_FSBASE:
+ case I386_SET_FSBASE:
+ case I386_GET_GSBASE:
+ case I386_SET_GSBASE:
+ case I386_GET_XFPUSTATE:
+ case I386_SET_PKRU:
+ case I386_CLEAR_PKRU:
+ case AMD64_GET_FSBASE:
+ case AMD64_SET_FSBASE:
+ case AMD64_GET_GSBASE:
+ case AMD64_SET_GSBASE:
+ case AMD64_GET_XFPUSTATE:
+ case AMD64_SET_PKRU:
+ case AMD64_CLEAR_PKRU:
+ break;
- case I386_SET_IOPERM:
- default:
-#ifdef KTRACE
- if (KTRPOINT(td, KTR_CAPFAIL))
- ktrcapfail(CAPFAIL_SYSCALL, NULL, NULL);
-#endif
+ case I386_SET_IOPERM:
+ default:
+ if (CAP_TRACING(td))
+ ktrcapfail(CAPFAIL_SYSCALL, &uap->op);
+ if (IN_CAPABILITY_MODE(td))
return (ECAPMODE);
- }
+ break;
}
#endif
diff --git a/sys/arm/arm/sys_machdep.c b/sys/arm/arm/sys_machdep.c
index bf738ed77a67..50cdc4158517 100644
--- a/sys/arm/arm/sys_machdep.c
+++ b/sys/arm/arm/sys_machdep.c
@@ -175,22 +175,19 @@ sysarch(struct thread *td, struct sysarch_args *uap)
* explicitly indicate whether or not the operation is safe to
* perform in capability mode.
*/
- if (IN_CAPABILITY_MODE(td)) {
- switch (uap->op) {
- case ARM_SYNC_ICACHE:
- case ARM_DRAIN_WRITEBUF:
- case ARM_SET_TP:
- case ARM_GET_TP:
- case ARM_GET_VFPSTATE:
- break;
-
- default:
-#ifdef KTRACE
- if (KTRPOINT(td, KTR_CAPFAIL))
- ktrcapfail(CAPFAIL_SYSCALL, NULL, NULL);
-#endif
+ switch (uap->op) {
+ case ARM_SYNC_ICACHE:
+ case ARM_DRAIN_WRITEBUF:
+ case ARM_SET_TP:
+ case ARM_GET_TP:
+ case ARM_GET_VFPSTATE:
+ break;
+
+ default:
+ if (CAP_TRACING(td))
+ ktrcapfail(CAPFAIL_SYSCALL, &uap->op);
+ if (IN_CAPABILITY_MODE(td))
return (ECAPMODE);
- }
}
#endif
diff --git a/sys/i386/i386/sys_machdep.c b/sys/i386/i386/sys_machdep.c
index 2da60bd438d1..e29d98a61cb9 100644
--- a/sys/i386/i386/sys_machdep.c
+++ b/sys/i386/i386/sys_machdep.c
@@ -152,26 +152,24 @@ sysarch(struct thread *td, struct sysarch_args *uap)
* explicitly indicate whether or not the operation is safe to
* perform in capability mode.
*/
- if (IN_CAPABILITY_MODE(td)) {
- switch (uap->op) {
- case I386_GET_LDT:
- case I386_SET_LDT:
- case I386_GET_IOPERM:
- case I386_GET_FSBASE:
- case I386_SET_FSBASE:
- case I386_GET_GSBASE:
- case I386_SET_GSBASE:
- case I386_GET_XFPUSTATE:
- break;
+ switch (uap->op) {
+ case I386_GET_LDT:
+ case I386_SET_LDT:
+ case I386_GET_IOPERM:
+ case I386_GET_FSBASE:
+ case I386_SET_FSBASE:
+ case I386_GET_GSBASE:
+ case I386_SET_GSBASE:
+ case I386_GET_XFPUSTATE:
+ break;
- case I386_SET_IOPERM:
- default:
-#ifdef KTRACE
- if (KTRPOINT(td, KTR_CAPFAIL))
- ktrcapfail(CAPFAIL_SYSCALL, NULL, NULL);
-#endif
+ case I386_SET_IOPERM:
+ default:
+ if (CAP_TRACING(td))
+ ktrcapfail(CAPFAIL_SYSCALL, &uap->op);
+ if (IN_CAPABILITY_MODE(td))
return (ECAPMODE);
- }
+ break;
}
#endif
diff --git a/sys/kern/kern_descrip.c b/sys/kern/kern_descrip.c
index 7f9318a7ceda..f626f5a38ca8 100644
--- a/sys/kern/kern_descrip.c
+++ b/sys/kern/kern_descrip.c
@@ -875,6 +875,8 @@ revert_f_setfl:
case F_KINFO:
#ifdef CAPABILITY_MODE
+ if (CAP_TRACING(td))
+ ktrcapfail(CAPFAIL_SYSCALL, &cmd);
if (IN_CAPABILITY_MODE(td)) {
error = ECAPMODE;
break;
diff --git a/sys/kern/kern_sig.c b/sys/kern/kern_sig.c
index a2ca74ac9183..8fa0942a5496 100644
--- a/sys/kern/kern_sig.c
+++ b/sys/kern/kern_sig.c
@@ -2677,10 +2677,16 @@ ptrace_syscallreq(struct thread *td, struct proc *p,
&td->td_proc->p_cowgen)))
thread_cow_update(td);
+ td->td_sa = tsr->ts_sa;
+
#ifdef CAPABILITY_MODE
- if (IN_CAPABILITY_MODE(td) && (se->sy_flags & SYF_CAPENABLED) == 0) {
- tsr->ts_ret.sr_error = ECAPMODE;
- return;
+ if ((se->sy_flags & SYF_CAPENABLED) == 0) {
+ if (CAP_TRACING(td))
+ ktrcapfail(CAPFAIL_SYSCALL, NULL);
+ if (IN_CAPABILITY_MODE(td)) {
+ tsr->ts_ret.sr_error = ECAPMODE;
+ return;
+ }
}
#endif
diff --git a/sys/kern/subr_syscall.c b/sys/kern/subr_syscall.c
index 8948cc0517a5..22bc35774e70 100644
--- a/sys/kern/subr_syscall.c
+++ b/sys/kern/subr_syscall.c
@@ -118,10 +118,13 @@ syscallenter(struct thread *td)
* In capability mode, we only allow access to system calls
* flagged with SYF_CAPENABLED.
*/
- if (__predict_false(IN_CAPABILITY_MODE(td) &&
- (se->sy_flags & SYF_CAPENABLED) == 0)) {
- td->td_errno = error = ECAPMODE;
- goto retval;
+ if ((se->sy_flags & SYF_CAPENABLED) == 0) {
+ if (CAP_TRACING(td))
+ ktrcapfail(CAPFAIL_SYSCALL, NULL);
+ if (IN_CAPABILITY_MODE(td)) {
+ td->td_errno = error = ECAPMODE;
+ goto retval;
+ }
}
#endif