Skip to content

Commit

Permalink
Build kernel with KFT instrumentation (#1393)
Browse files Browse the repository at this point in the history
  • Loading branch information
franciscozdo authored Nov 22, 2023
1 parent 0833084 commit 8950128
Show file tree
Hide file tree
Showing 43 changed files with 326 additions and 125 deletions.
11 changes: 0 additions & 11 deletions .gdbinit
Original file line number Diff line number Diff line change
@@ -1,14 +1,3 @@
# some generic settings
set output-radix 0x10
set pagination off
set confirm off
set verbose off

# make extra commands available
python import os, sys
python sys.path.append(os.path.join(os.getcwd(), 'sys'))
python import debug

# favorite set of breakpoints
break kernel_init
break halt
Expand Down
10 changes: 10 additions & 0 deletions .gdbinit-common
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# some generic settings
set output-radix 0x10
set pagination off
set confirm off
set verbose off

# make extra commands available
python import os, sys
python sys.path.append(os.path.join(os.getcwd(), 'sys'))
python import debug
29 changes: 29 additions & 0 deletions .gdbinit-kftrace
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# Command to easily append KFT events to specified file
define dump-kft
printf "Appending %d entries to file `dump.kft`\n", kft_used
append memory dump.kft kft_event_list kft_event_list+kft_used
end

set $kft_flush_count = 0

break kft_flush
commands
silent
printf "kft_flush(%d): ", $kft_flush_count++
dump-kft
continue
end

break ktest_success
commands
printf "ktest_success: "
dump-kft
end

break halt
commands
printf "halt: "
dump-kft
end

continue
12 changes: 0 additions & 12 deletions .gdbinit-test
Original file line number Diff line number Diff line change
@@ -1,15 +1,3 @@
# some generic settings
set output-radix 0x10
set pagination off
set confirm off
set verbose off
handle SIGINT stop

# make extra commands available
python import os, sys
python sys.path.append(os.path.join(os.getcwd(), 'sys'))
python import debug

define post-mortem
add-symbol-file bin/utest/utest.uelf 0x400000
echo \n*** REGISTERS ***\n\n
Expand Down
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -83,3 +83,6 @@ mimiker-env/

#
contrib/*/build/

# kft dump
dump.kft
3 changes: 2 additions & 1 deletion build/build.kern.mk
Original file line number Diff line number Diff line change
Expand Up @@ -25,11 +25,12 @@ include $(TOPDIR)/config.mk
SOURCES_ALL = $(SOURCES)
SOURCES_ALL += $(foreach var, $(CONFIG_OPTS), $(value SOURCES-$(var)))

include $(TOPDIR)/build/flags.kern.mk

SOURCES += $(foreach var, $(CONFIG_OPTS), \
$(if $(subst 0,,$(value $(var))), \
$(value SOURCES-$(var)),))

include $(TOPDIR)/build/flags.kern.mk
include $(TOPDIR)/build/compile.mk
include $(TOPDIR)/build/common.mk

Expand Down
2 changes: 1 addition & 1 deletion build/common.mk
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ $(BUILDDIR)%.S: %.c

$(BUILDDIR)%.o: %.c
@echo "[CC] $(SRCPATH) -> $(DSTPATH)"
$(CC) $(CFLAGS) $(CFLAGS.$*.c) $(CFLAGS_KASAN) $(CFLAGS_KCSAN) $(CFLAGS_KGPROF) $(CPPFLAGS) $(WFLAGS) \
$(CC) $(CFLAGS) $(CFLAGS.$*.c) $(CFLAGS_KASAN) $(CFLAGS_KCSAN) $(CFLAGS_KFI) $(CPPFLAGS) $(WFLAGS) \
-c -o $@ $(realpath $<)

$(BUILDDIR)%.o: %.S
Expand Down
14 changes: 11 additions & 3 deletions build/flags.kern.mk
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ include $(TOPDIR)/build/flags.mk

CFLAGS += -fno-builtin -nostdinc -nostdlib -ffreestanding
CPPFLAGS += -I$(TOPDIR)/include -I$(TOPDIR)/sys/contrib -D_KERNEL
CPPFLAGS += -DLOCKDEP=$(LOCKDEP) -DKASAN=$(KASAN) -DKGPROF=$(KGPROF) -DKCSAN=$(KCSAN)
CPPFLAGS += -DLOCKDEP=$(LOCKDEP) -DKASAN=$(KASAN) -DKCSAN=$(KCSAN) -DKFI=$(KFI)
LDFLAGS += -nostdlib

ifeq ($(KCSAN), 1)
Expand Down Expand Up @@ -44,8 +44,16 @@ ifeq ($(KASAN), 1)
-wrap=strlen
endif

ifeq ($(KGPROF), 1)
CFLAGS_KGPROF = -finstrument-functions
ifeq ($(KFI),ftrace)
CFLAGS_KFI += -finstrument-functions
CPPFLAGS += -DKFTRACE
KFTRACE = 1
endif

ifeq ($(KFI),gprof)
CFLAGS_KFI += -finstrument-functions
CPPFLAGS += -DKGPROF
KGPROF = 1
endif

KERNEL := 1
5 changes: 3 additions & 2 deletions config.mk
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
# build system for given platform.
#

CONFIG_OPTS := KASAN LOCKDEP KGPROF MIPS AARCH64 RISCV KCSAN
CONFIG_OPTS := KASAN LOCKDEP KGPROF MIPS AARCH64 RISCV KCSAN KFTRACE

BOARD ?= rpi3

Expand Down Expand Up @@ -40,6 +40,7 @@ VERBOSE ?= 0
LLVM ?= 1
LOCKDEP ?= 0
KASAN ?= 0
KGPROF ?= 0
KCSAN ?= 0
# Kernel function instrumentation options: ftrace, gprof
KFI ?=
TRAP_USER_ACCESS ?= 0
9 changes: 9 additions & 0 deletions include/aarch64/kftrace.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#ifndef __AARCH64_KFTRACE_H__
#define __AARCH64_KFTRACE_H__

#include <aarch64/armreg.h>

#define KFT_EVENT_MAX 0x100000
#define kft_get_time() READ_SPECIALREG(cntpct_el0)

#endif /* __AARCH64_KFTRACE_H__ */
19 changes: 10 additions & 9 deletions include/aarch64/pmap.h
Original file line number Diff line number Diff line change
Expand Up @@ -49,13 +49,13 @@ typedef struct pmap_md {
* Page directory.
*/

static inline bool pde_valid_p(pde_t *pdep) {
static __no_profile inline bool pde_valid_p(pde_t *pdep) {
return pdep && PTE_FRAME_ADDR(*pdep) != 0;
}

void *phys_to_dmap(paddr_t addr);

static inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
static __no_profile inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
pde_t *pde = phys_to_dmap(pd_pa);
if (lvl == 0)
return pde + L0_INDEX(va);
Expand All @@ -70,15 +70,15 @@ static inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
* Page table.
*/

static inline paddr_t pte_frame(pte_t pte) {
static __no_profile inline paddr_t pte_frame(pte_t pte) {
return PTE_FRAME_ADDR(pte);
}

static inline bool pte_valid_p(pte_t *ptep) {
static __no_profile inline bool pte_valid_p(pte_t *ptep) {
return ptep && (pte_frame(*ptep) != 0);
}

static inline bool pte_access(pte_t pte, vm_prot_t prot) {
static __no_profile inline bool pte_access(pte_t pte, vm_prot_t prot) {
switch (prot) {
case VM_PROT_READ:
return pte & ATTR_SW_READ;
Expand All @@ -95,16 +95,17 @@ static inline bool pte_access(pte_t pte, vm_prot_t prot) {
* Physical map management.
*/

static inline void pmap_md_setup(pmap_t *pmap) {
static __no_profile inline void pmap_md_setup(pmap_t *pmap) {
}

static inline void pmap_md_delete(pmap_t *pmap) {
static __no_profile inline void pmap_md_delete(pmap_t *pmap) {
}

static inline void pmap_md_growkernel(vaddr_t old_kva, vaddr_t new_kva) {
static __no_profile inline void pmap_md_growkernel(vaddr_t old_kva,
vaddr_t new_kva) {
}

static inline void pmap_md_update(pmap_t *pmap) {
static __no_profile inline void pmap_md_update(pmap_t *pmap) {
}

#endif /* !_AARCH64_PMAP_H_ */
13 changes: 13 additions & 0 deletions include/mips/kftrace.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
#ifndef __MIPS_KFTRACE_H__
#define __MIPS_KFTRACE_H__

#define _MACHDEP

#include <mips/m32c0.h>

#define KFT_EVENT_MAX 0x4000
#define kft_get_time() mips32_getcount()

#undef _MACHDEP

#endif /* __MIPS_KFTRACE_H__ */
17 changes: 9 additions & 8 deletions include/mips/pmap.h
Original file line number Diff line number Diff line change
Expand Up @@ -77,13 +77,13 @@ typedef struct pmap_md {
* Page directory.
*/

static inline bool pde_valid_p(pde_t *pdep) {
static __no_profile inline bool pde_valid_p(pde_t *pdep) {
return pdep && (*pdep & PDE_VALID);
}

void *phys_to_dmap(paddr_t addr);

static inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
static __no_profile inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
pde_t *pde = phys_to_dmap(pd_pa);
if (lvl == 0)
return pde + PDE_INDEX(va);
Expand All @@ -94,15 +94,15 @@ static inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
* Page table.
*/

static inline paddr_t pte_frame(pte_t pte) {
static __no_profile inline paddr_t pte_frame(pte_t pte) {
return PTE_FRAME_ADDR(pte);
}

static inline bool pte_valid_p(pte_t *ptep) {
static __no_profile inline bool pte_valid_p(pte_t *ptep) {
return ptep && (pte_frame(*ptep) != 0);
}

static inline bool pte_access(pte_t pte, vm_prot_t prot) {
static __no_profile inline bool pte_access(pte_t pte, vm_prot_t prot) {
switch (prot) {
case VM_PROT_READ:
return pte & PTE_SW_READ;
Expand All @@ -119,13 +119,14 @@ static inline bool pte_access(pte_t pte, vm_prot_t prot) {
* Physical map management.
*/

static inline void pmap_md_delete(pmap_t *pmap) {
static __no_profile inline void pmap_md_delete(pmap_t *pmap) {
}

static inline void pmap_md_growkernel(vaddr_t old_kva, vaddr_t new_kva) {
static __no_profile inline void pmap_md_growkernel(vaddr_t old_kva,
vaddr_t new_kva) {
}

static inline void pmap_md_update(pmap_t *pmap) {
static __no_profile inline void pmap_md_update(pmap_t *pmap) {
}

#endif /* __ASSEMBLER__ */
Expand Down
9 changes: 9 additions & 0 deletions include/riscv/kftrace.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#ifndef __RISCV_KFTRACE_H__
#define __RISCV_KFTRACE_H__

#include <riscv/cpufunc.h>

#define KFT_EVENT_MAX 0x100000
#define kft_get_time() rdtime()

#endif /* __RISCV_KFTRACE_H__ */
12 changes: 6 additions & 6 deletions include/riscv/pmap.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,13 +46,13 @@ typedef struct pmap_md {
* Page directory.
*/

static inline bool pde_valid_p(pde_t *pdep) {
static __no_profile inline bool pde_valid_p(pde_t *pdep) {
return pdep && VALID_PDE_P(*pdep);
}

void *phys_to_dmap(paddr_t addr);

static inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
static __no_profile inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
pde_t *pde = phys_to_dmap(pd_pa);
if (lvl == 0)
return pde + L0_INDEX(va);
Expand All @@ -69,15 +69,15 @@ static inline pde_t *pde_ptr(paddr_t pd_pa, int lvl, vaddr_t va) {
* Page table.
*/

static inline paddr_t pte_frame(pte_t pte) {
static __no_profile inline paddr_t pte_frame(pte_t pte) {
return PTE_TO_PA(pte);
}

static inline bool pte_valid_p(pte_t *ptep) {
static __no_profile inline bool pte_valid_p(pte_t *ptep) {
return ptep && VALID_PTE_P(*ptep);
}

static inline bool pte_access(pte_t pte, vm_prot_t prot) {
static __no_profile inline bool pte_access(pte_t pte, vm_prot_t prot) {
switch (prot) {
case VM_PROT_READ:
return pte & PTE_SW_READ;
Expand All @@ -94,7 +94,7 @@ static inline bool pte_access(pte_t pte, vm_prot_t prot) {
* Physical map management.
*/

static inline void pmap_md_delete(pmap_t *pmap) {
static __no_profile inline void pmap_md_delete(pmap_t *pmap) {
}

#endif /* !_RISCV_PMAP_H_ */
2 changes: 1 addition & 1 deletion include/sys/cdefs.h
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@
#define __no_sanitize \
__attribute__((no_sanitize("address", "thread", "undefined")))
#define __no_instrument_function __attribute__((no_instrument_function))
#ifdef KGPROF
#if defined(KFI)
#define __no_profile __no_instrument_function
#else
#define __no_profile
Expand Down
4 changes: 2 additions & 2 deletions include/sys/interrupt.h
Original file line number Diff line number Diff line change
Expand Up @@ -37,11 +37,11 @@ bool intr_disabled(void) __no_profile;

/* Two following functions are workaround to make interrupt disabling work with
* scoped and with statement. */
static inline void __intr_disable(void *data) {
static __no_profile inline void __intr_disable(void *data) {
intr_disable();
}

static inline void __intr_enable(void *data) {
static __no_profile inline void __intr_enable(void *data) {
intr_enable();
}

Expand Down
11 changes: 11 additions & 0 deletions include/sys/kftrace.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#ifndef __KFTRACE_H__
#define __KFTRACE_H__

#if KFTRACE
#include <machine/kftrace.h>
void init_kftrace(void);
#else
#define init_kftrace() __nothing
#endif

#endif /* __KFTRACE_H__ */
2 changes: 1 addition & 1 deletion include/sys/mimiker.h
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ bool intr_disabled(void) __no_profile;

#define CLEANUP_FUNCTION(func) __CONCAT(__cleanup_, func)
#define DEFINE_CLEANUP_FUNCTION(type, func) \
static inline void __cleanup_##func(type *ptr) { \
static __no_profile inline void __cleanup_##func(type *ptr) { \
if (*ptr) \
func(*ptr); \
} \
Expand Down
4 changes: 2 additions & 2 deletions include/sys/mutex.h
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ bool mtx_owned(mtx_t *m);
/*! \brief Fetch mutex owner.
*
* \note The function is used by some tests. */
static inline thread_t *mtx_owner(mtx_t *m) {
static __no_profile inline thread_t *mtx_owner(mtx_t *m) {
return (thread_t *)(m->m_owner & ~MTX_FLAGMASK);
}

Expand All @@ -93,7 +93,7 @@ void _mtx_lock(mtx_t *m, const void *waitpt) __no_profile;
/*! \brief Locks sleep mutex.
*
* If mutex is already owned, then the thread is inserted into turnstile. */
static inline void mtx_lock(mtx_t *m) {
static __no_profile inline void mtx_lock(mtx_t *m) {
_mtx_lock(m, __caller(0));
}

Expand Down
Loading

0 comments on commit 8950128

Please sign in to comment.