Commit ed0a5f6a authored by Ramon Nou's avatar Ramon Nou
Browse files

initial commit

parents
Loading
Loading
Loading
Loading
+69 −0
Original line number Diff line number Diff line
################################################################################
# Copyright 2018-2024, Barcelona Supercomputing Center (BSC), Spain            #
# Copyright 2015-2024, Johannes Gutenberg Universitaet Mainz, Germany          #
#                                                                              #
# This software was partially supported by the                                 #
# EC H2020 funded project NEXTGenIO (Project ID: 671951, www.nextgenio.eu).    #
#                                                                              #
# This software was partially supported by the                                 #
# ADA-FS project under the SPPEXA project funded by the DFG.                   #
#                                                                              #
# This file is part of GekkoFS.                                                #
#                                                                              #
# GekkoFS 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 3 of the License, or            #
# (at your option) any later version.                                          #
#                                                                              #
# GekkoFS is distributed in the hope that it will be useful,                   #
# but WITHOUT ANY WARRANTY; without even the implied warranty of               #
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                #
# GNU General Public License for more details.                                 #
#                                                                              #
# You should have received a copy of the GNU General Public License            #
# along with GekkoFS.  If not, see <https://www.gnu.org/licenses/>.            #
#                                                                              #
# SPDX-License-Identifier: GPL-3.0-or-later                                    #
################################################################################

find_package(PkgConfig)
pkg_check_modules(PC_Syscall_intercept QUIET libsyscall_intercept)

find_path(Syscall_intercept_INCLUDE_DIR
    NAMES libsyscall_intercept_hook_point.h
    PATHS ${PC_Syscall_intercept_INCLUDE_DIRS}
)

find_library(Syscall_intercept_LIBRARY
    NAMES syscall_intercept
    PATHS ${PC_Syscall_intercept_LIBRARY_DIRS}
)

include(FindPackageHandleStandardArgs)
find_package_handle_standard_args(
    Syscall_intercept
    DEFAULT_MSG
    Syscall_intercept_INCLUDE_DIR
    Syscall_intercept_LIBRARY
)

if (Syscall_intercept_FOUND)
    set(Syscall_intercept_LIBRARIES ${Syscall_intercept_LIBRARY})
    set(Syscall_intercept_INCLUDE_DIRS ${Syscall_intercept_INCLUDE_DIR})
    set(Syscall_intercept_DEFINITIONS ${PC_Syscall_intercept_CFLAGS_OTHER})

    if (NOT TARGET Syscall_intercept::Syscall_intercept)
        add_library(Syscall_intercept::Syscall_intercept UNKNOWN IMPORTED)
        set_target_properties(Syscall_intercept::Syscall_intercept PROPERTIES
            IMPORTED_LOCATION "${Syscall_intercept_LIBRARY}"
            INTERFACE_COMPILE_OPTIONS "${PC_Syscall_intercept_CFLAGS_OTHER}"
            INTERFACE_INCLUDE_DIRECTORIES "${Syscall_intercept_INCLUDE_DIR}"
        )
    endif ()
endif ()


mark_as_advanced(
    Syscall_intercept_INCLUDE_DIR
    Syscall_intercept_LIBRARY
)

CMakeLists.txt

0 → 100644
+68 −0
Original line number Diff line number Diff line
cmake_minimum_required(VERSION 3.13)

project(
    "eval"
    VERSION 1.0
    LANGUAGES CXX
)

set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

SET(CMAKE_INSTALL_RPATH_USE_LINK_PATH TRUE)

include(CheckCXXSourceCompiles)
include(CMakeDependentOption)
include(GNUInstallDirs)
include(FeatureSummary)

if (NOT CMAKE_BUILD_TYPE)
    set(CMAKE_BUILD_TYPE Release
        CACHE STRING "Choose the type of build: Debug Release Memcheck" FORCE)
ENDIF (NOT CMAKE_BUILD_TYPE)
message(STATUS "[${PROJECT_NAME}] Build type: ${CMAKE_BUILD_TYPE}")

set(CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/CMake" ${CMAKE_MODULE_PATH})

message(STATUS "[${PROJECT_NAME}] Checking for syscall_intercept")
find_package(Syscall_intercept REQUIRED)


set(INCLUDE_DIR "${CMAKE_SOURCE_DIR}/include")
include_directories(
    ${INCLUDE_DIR}
    ${CMAKE_BINARY_DIR}/include
    /usr/include
)


add_library(eval_intercept SHARED)
add_executable(opendevnull)
target_sources(eval_intercept
    PRIVATE
        src/eval.cpp
)

target_sources(opendevnull
    PRIVATE
        src/opendevnull.cpp
)

target_link_libraries(
    eval_intercept
    Syscall_intercept::Syscall_intercept
)



install(
    TARGETS eval_intercept
    LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
    ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
)

install(
    TARGETS opendevnull
    LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
    ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
)

src/eval.cpp

0 → 100644
+64 −0
Original line number Diff line number Diff line
#include <fcntl.h>
#include <libsyscall_intercept_hook_point.h>
#include <sys/syscall.h>
#include <sys/types.h>
void start_interception() __attribute__((constructor));
void stop_interception() __attribute__((destructor));

int hook_openat(int dirfd, const char *cpath, int flags, mode_t mode) {

  return syscall_no_intercept(SYS_openat, dirfd, cpath, flags, mode);
}

inline int hook(long syscall_number, long arg0, long arg1, long arg2, long arg3,
                long arg4, long arg5, long *result) {

  switch (syscall_number) {

#ifdef SYS_open
  case SYS_open:
    *result = hook_openat(AT_FDCWD, reinterpret_cast<char *>(arg0),
                          static_cast<int>(arg1), static_cast<mode_t>(arg2));
    break;
#endif
  case SYS_openat:
    *result = hook_openat(static_cast<int>(arg0),
                          reinterpret_cast<const char *>(arg1),
                          static_cast<int>(arg2), static_cast<mode_t>(arg3));
    break;
  default:
    // ignore any other syscalls, i.e.: pass them on to the kernel
    // (syscalls forwarded to the kernel that return are logged in
    // hook_forwarded_syscall())

    return 1;
  }

  return 0;
}

int hook_guard_wrapper(long syscall_number, long arg0, long arg1, long arg2,
                       long arg3, long arg4, long arg5,
                       long *syscall_return_value) {

  int was_hooked = 1;

  if (syscall_number == SYS_openat)
    was_hooked = hook(syscall_number, arg0, arg1, arg2, arg3, arg4, arg5,
                      syscall_return_value);

  return was_hooked;
}

void start_interception() {

  // Set up the callback function pointer
  intercept_hook_point = hook_guard_wrapper;
}

void stop_interception() {

  // Reset callback function pointer
  intercept_hook_point = nullptr;
}
 No newline at end of file

src/opendevnull.cpp

0 → 100644
+40 −0
Original line number Diff line number Diff line

#include <fcntl.h>
#include <iostream>
#include <sys/syscall.h>
#include <unistd.h>

int main() {
  // measure time to run in microseconds
  struct timespec start, end;
  clock_gettime(CLOCK_MONOTONIC, &start);
  // open /dev/null 100000 times

  for (int j = 0; j < 1000; j++) {
    for (int i = 0; i < 100000; i++) {
      int fd = openat(AT_FDCWD, "/dev/null", O_RDWR, 0);

      close(fd);
    }
  }
  clock_gettime(CLOCK_MONOTONIC, &end);
  double time_taken =
      (end.tv_sec - start.tv_sec) * 1e6 + (end.tv_nsec - start.tv_nsec) / 1e3;
  std::cout << "Time taken: " << time_taken << " microseconds" << std::endl;
  // mean of the time for a syscall (10000000)

  std::cout << "Mean time taken: " << time_taken / 10000000.0 << " microseconds"
            << std::endl;
  // Calculate single syscall ()
  clock_gettime(CLOCK_MONOTONIC, &start);
  int fd = openat(AT_FDCWD, "/dev/null", O_RDWR, 0);
  close(fd);
  clock_gettime(CLOCK_MONOTONIC, &end);
  std::cout << "Time taken for single syscall: "
            << (end.tv_sec - start.tv_sec) * 1e6 +
                   (end.tv_nsec - start.tv_nsec) / 1e3
            << " microseconds" << std::endl;

  return 0;
}
 No newline at end of file