1#!/bin/bash 2# SPDX-License-Identifier: GPL-2.0 3# Copyright (C) 2018 Joe Lawrence <joe.lawrence@redhat.com> 4 5. $(dirname $0)/functions.sh 6 7MOD_LIVEPATCH=test_klp_callbacks_demo 8MOD_LIVEPATCH2=test_klp_callbacks_demo2 9MOD_TARGET=test_klp_callbacks_mod 10MOD_TARGET_BUSY=test_klp_callbacks_busy 11 12setup_config 13 14 15# TEST: target module before livepatch 16# 17# Test a combination of loading a kernel module and a livepatch that 18# patches a function in the first module. Load the target module 19# before the livepatch module. Unload them in the same order. 20# 21# - On livepatch enable, before the livepatch transition starts, 22# pre-patch callbacks are executed for vmlinux and $MOD_TARGET (those 23# klp_objects currently loaded). After klp_objects are patched 24# according to the klp_patch, their post-patch callbacks run and the 25# transition completes. 26# 27# - Similarly, on livepatch disable, pre-patch callbacks run before the 28# unpatching transition starts. klp_objects are reverted, post-patch 29# callbacks execute and the transition completes. 30 31echo -n "TEST: target module before livepatch ... " 32dmesg -C 33 34load_mod $MOD_TARGET 35load_lp $MOD_LIVEPATCH 36disable_lp $MOD_LIVEPATCH 37unload_lp $MOD_LIVEPATCH 38unload_mod $MOD_TARGET 39 40check_result "% modprobe $MOD_TARGET 41$MOD_TARGET: ${MOD_TARGET}_init 42% modprobe $MOD_LIVEPATCH 43livepatch: enabling patch '$MOD_LIVEPATCH' 44livepatch: '$MOD_LIVEPATCH': initializing patching transition 45$MOD_LIVEPATCH: pre_patch_callback: vmlinux 46$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 47livepatch: '$MOD_LIVEPATCH': starting patching transition 48livepatch: '$MOD_LIVEPATCH': completing patching transition 49$MOD_LIVEPATCH: post_patch_callback: vmlinux 50$MOD_LIVEPATCH: post_patch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 51livepatch: '$MOD_LIVEPATCH': patching complete 52% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 53livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 54$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 55$MOD_LIVEPATCH: pre_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 56livepatch: '$MOD_LIVEPATCH': starting unpatching transition 57livepatch: '$MOD_LIVEPATCH': completing unpatching transition 58$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 59$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 60livepatch: '$MOD_LIVEPATCH': unpatching complete 61% rmmod $MOD_LIVEPATCH 62% rmmod $MOD_TARGET 63$MOD_TARGET: ${MOD_TARGET}_exit" 64 65 66# TEST: module_coming notifier 67# 68# This test is similar to the previous test, but (un)load the livepatch 69# module before the target kernel module. This tests the livepatch 70# core's module_coming handler. 71# 72# - On livepatch enable, only pre/post-patch callbacks are executed for 73# currently loaded klp_objects, in this case, vmlinux. 74# 75# - When a targeted module is subsequently loaded, only its 76# pre/post-patch callbacks are executed. 77# 78# - On livepatch disable, all currently loaded klp_objects' (vmlinux and 79# $MOD_TARGET) pre/post-unpatch callbacks are executed. 80 81echo -n "TEST: module_coming notifier ... " 82dmesg -C 83 84load_lp $MOD_LIVEPATCH 85load_mod $MOD_TARGET 86disable_lp $MOD_LIVEPATCH 87unload_lp $MOD_LIVEPATCH 88unload_mod $MOD_TARGET 89 90check_result "% modprobe $MOD_LIVEPATCH 91livepatch: enabling patch '$MOD_LIVEPATCH' 92livepatch: '$MOD_LIVEPATCH': initializing patching transition 93$MOD_LIVEPATCH: pre_patch_callback: vmlinux 94livepatch: '$MOD_LIVEPATCH': starting patching transition 95livepatch: '$MOD_LIVEPATCH': completing patching transition 96$MOD_LIVEPATCH: post_patch_callback: vmlinux 97livepatch: '$MOD_LIVEPATCH': patching complete 98% modprobe $MOD_TARGET 99livepatch: applying patch '$MOD_LIVEPATCH' to loading module '$MOD_TARGET' 100$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 101$MOD_LIVEPATCH: post_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 102$MOD_TARGET: ${MOD_TARGET}_init 103% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 104livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 105$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 106$MOD_LIVEPATCH: pre_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 107livepatch: '$MOD_LIVEPATCH': starting unpatching transition 108livepatch: '$MOD_LIVEPATCH': completing unpatching transition 109$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 110$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 111livepatch: '$MOD_LIVEPATCH': unpatching complete 112% rmmod $MOD_LIVEPATCH 113% rmmod $MOD_TARGET 114$MOD_TARGET: ${MOD_TARGET}_exit" 115 116 117# TEST: module_going notifier 118# 119# Test loading the livepatch after a targeted kernel module, then unload 120# the kernel module before disabling the livepatch. This tests the 121# livepatch core's module_going handler. 122# 123# - First load a target module, then the livepatch. 124# 125# - When a target module is unloaded, the livepatch is only reverted 126# from that klp_object ($MOD_TARGET). As such, only its pre and 127# post-unpatch callbacks are executed when this occurs. 128# 129# - When the livepatch is disabled, pre and post-unpatch callbacks are 130# run for the remaining klp_object, vmlinux. 131 132echo -n "TEST: module_going notifier ... " 133dmesg -C 134 135load_mod $MOD_TARGET 136load_lp $MOD_LIVEPATCH 137unload_mod $MOD_TARGET 138disable_lp $MOD_LIVEPATCH 139unload_lp $MOD_LIVEPATCH 140 141check_result "% modprobe $MOD_TARGET 142$MOD_TARGET: ${MOD_TARGET}_init 143% modprobe $MOD_LIVEPATCH 144livepatch: enabling patch '$MOD_LIVEPATCH' 145livepatch: '$MOD_LIVEPATCH': initializing patching transition 146$MOD_LIVEPATCH: pre_patch_callback: vmlinux 147$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 148livepatch: '$MOD_LIVEPATCH': starting patching transition 149livepatch: '$MOD_LIVEPATCH': completing patching transition 150$MOD_LIVEPATCH: post_patch_callback: vmlinux 151$MOD_LIVEPATCH: post_patch_callback: $MOD_TARGET -> [MODULE_STATE_LIVE] Normal state 152livepatch: '$MOD_LIVEPATCH': patching complete 153% rmmod $MOD_TARGET 154$MOD_TARGET: ${MOD_TARGET}_exit 155$MOD_LIVEPATCH: pre_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 156livepatch: reverting patch '$MOD_LIVEPATCH' on unloading module '$MOD_TARGET' 157$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 158% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 159livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 160$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 161livepatch: '$MOD_LIVEPATCH': starting unpatching transition 162livepatch: '$MOD_LIVEPATCH': completing unpatching transition 163$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 164livepatch: '$MOD_LIVEPATCH': unpatching complete 165% rmmod $MOD_LIVEPATCH" 166 167 168# TEST: module_coming and module_going notifiers 169# 170# This test is similar to the previous test, however the livepatch is 171# loaded first. This tests the livepatch core's module_coming and 172# module_going handlers. 173# 174# - First load the livepatch. 175# 176# - When a targeted kernel module is subsequently loaded, only its 177# pre/post-patch callbacks are executed. 178# 179# - When the target module is unloaded, the livepatch is only reverted 180# from the $MOD_TARGET klp_object. As such, only pre and 181# post-unpatch callbacks are executed when this occurs. 182 183echo -n "TEST: module_coming and module_going notifiers ... " 184dmesg -C 185 186load_lp $MOD_LIVEPATCH 187load_mod $MOD_TARGET 188unload_mod $MOD_TARGET 189disable_lp $MOD_LIVEPATCH 190unload_lp $MOD_LIVEPATCH 191 192check_result "% modprobe $MOD_LIVEPATCH 193livepatch: enabling patch '$MOD_LIVEPATCH' 194livepatch: '$MOD_LIVEPATCH': initializing patching transition 195$MOD_LIVEPATCH: pre_patch_callback: vmlinux 196livepatch: '$MOD_LIVEPATCH': starting patching transition 197livepatch: '$MOD_LIVEPATCH': completing patching transition 198$MOD_LIVEPATCH: post_patch_callback: vmlinux 199livepatch: '$MOD_LIVEPATCH': patching complete 200% modprobe $MOD_TARGET 201livepatch: applying patch '$MOD_LIVEPATCH' to loading module '$MOD_TARGET' 202$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 203$MOD_LIVEPATCH: post_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 204$MOD_TARGET: ${MOD_TARGET}_init 205% rmmod $MOD_TARGET 206$MOD_TARGET: ${MOD_TARGET}_exit 207$MOD_LIVEPATCH: pre_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 208livepatch: reverting patch '$MOD_LIVEPATCH' on unloading module '$MOD_TARGET' 209$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 210% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 211livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 212$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 213livepatch: '$MOD_LIVEPATCH': starting unpatching transition 214livepatch: '$MOD_LIVEPATCH': completing unpatching transition 215$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 216livepatch: '$MOD_LIVEPATCH': unpatching complete 217% rmmod $MOD_LIVEPATCH" 218 219 220# TEST: target module not present 221# 222# A simple test of loading a livepatch without one of its patch target 223# klp_objects ever loaded ($MOD_TARGET). 224# 225# - Load the livepatch. 226# 227# - As expected, only pre/post-(un)patch handlers are executed for 228# vmlinux. 229 230echo -n "TEST: target module not present ... " 231dmesg -C 232 233load_lp $MOD_LIVEPATCH 234disable_lp $MOD_LIVEPATCH 235unload_lp $MOD_LIVEPATCH 236 237check_result "% modprobe $MOD_LIVEPATCH 238livepatch: enabling patch '$MOD_LIVEPATCH' 239livepatch: '$MOD_LIVEPATCH': initializing patching transition 240$MOD_LIVEPATCH: pre_patch_callback: vmlinux 241livepatch: '$MOD_LIVEPATCH': starting patching transition 242livepatch: '$MOD_LIVEPATCH': completing patching transition 243$MOD_LIVEPATCH: post_patch_callback: vmlinux 244livepatch: '$MOD_LIVEPATCH': patching complete 245% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 246livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 247$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 248livepatch: '$MOD_LIVEPATCH': starting unpatching transition 249livepatch: '$MOD_LIVEPATCH': completing unpatching transition 250$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 251livepatch: '$MOD_LIVEPATCH': unpatching complete 252% rmmod $MOD_LIVEPATCH" 253 254 255# TEST: pre-patch callback -ENODEV 256# 257# Test a scenario where a vmlinux pre-patch callback returns a non-zero 258# status (ie, failure). 259# 260# - First load a target module. 261# 262# - Load the livepatch module, setting its 'pre_patch_ret' value to -19 263# (-ENODEV). When its vmlinux pre-patch callback executes, this 264# status code will propagate back to the module-loading subsystem. 265# The result is that the insmod command refuses to load the livepatch 266# module. 267 268echo -n "TEST: pre-patch callback -ENODEV ... " 269dmesg -C 270 271load_mod $MOD_TARGET 272load_failing_mod $MOD_LIVEPATCH pre_patch_ret=-19 273unload_mod $MOD_TARGET 274 275check_result "% modprobe $MOD_TARGET 276$MOD_TARGET: ${MOD_TARGET}_init 277% modprobe $MOD_LIVEPATCH pre_patch_ret=-19 278livepatch: enabling patch '$MOD_LIVEPATCH' 279livepatch: '$MOD_LIVEPATCH': initializing patching transition 280test_klp_callbacks_demo: pre_patch_callback: vmlinux 281livepatch: pre-patch callback failed for object 'vmlinux' 282livepatch: failed to enable patch '$MOD_LIVEPATCH' 283livepatch: '$MOD_LIVEPATCH': canceling patching transition, going to unpatch 284livepatch: '$MOD_LIVEPATCH': completing unpatching transition 285livepatch: '$MOD_LIVEPATCH': unpatching complete 286modprobe: ERROR: could not insert '$MOD_LIVEPATCH': No such device 287% rmmod $MOD_TARGET 288$MOD_TARGET: ${MOD_TARGET}_exit" 289 290 291# TEST: module_coming + pre-patch callback -ENODEV 292# 293# Similar to the previous test, setup a livepatch such that its vmlinux 294# pre-patch callback returns success. However, when a targeted kernel 295# module is later loaded, have the livepatch return a failing status 296# code. 297# 298# - Load the livepatch, vmlinux pre-patch callback succeeds. 299# 300# - Set a trap so subsequent pre-patch callbacks to this livepatch will 301# return -ENODEV. 302# 303# - The livepatch pre-patch callback for subsequently loaded target 304# modules will return failure, so the module loader refuses to load 305# the kernel module. No post-patch or pre/post-unpatch callbacks are 306# executed for this klp_object. 307# 308# - Pre/post-unpatch callbacks are run for the vmlinux klp_object. 309 310echo -n "TEST: module_coming + pre-patch callback -ENODEV ... " 311dmesg -C 312 313load_lp $MOD_LIVEPATCH 314set_pre_patch_ret $MOD_LIVEPATCH -19 315load_failing_mod $MOD_TARGET 316disable_lp $MOD_LIVEPATCH 317unload_lp $MOD_LIVEPATCH 318 319check_result "% modprobe $MOD_LIVEPATCH 320livepatch: enabling patch '$MOD_LIVEPATCH' 321livepatch: '$MOD_LIVEPATCH': initializing patching transition 322$MOD_LIVEPATCH: pre_patch_callback: vmlinux 323livepatch: '$MOD_LIVEPATCH': starting patching transition 324livepatch: '$MOD_LIVEPATCH': completing patching transition 325$MOD_LIVEPATCH: post_patch_callback: vmlinux 326livepatch: '$MOD_LIVEPATCH': patching complete 327% echo -19 > /sys/module/$MOD_LIVEPATCH/parameters/pre_patch_ret 328% modprobe $MOD_TARGET 329livepatch: applying patch '$MOD_LIVEPATCH' to loading module '$MOD_TARGET' 330$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 331livepatch: pre-patch callback failed for object '$MOD_TARGET' 332livepatch: patch '$MOD_LIVEPATCH' failed for module '$MOD_TARGET', refusing to load module '$MOD_TARGET' 333modprobe: ERROR: could not insert '$MOD_TARGET': No such device 334% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 335livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 336$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 337livepatch: '$MOD_LIVEPATCH': starting unpatching transition 338livepatch: '$MOD_LIVEPATCH': completing unpatching transition 339$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 340livepatch: '$MOD_LIVEPATCH': unpatching complete 341% rmmod $MOD_LIVEPATCH" 342 343 344# TEST: multiple target modules 345# 346# Test loading multiple targeted kernel modules. This test-case is 347# mainly for comparing with the next test-case. 348# 349# - Load a target "busy" kernel module which kicks off a worker function 350# that immediately exits. 351# 352# - Proceed with loading the livepatch and another ordinary target 353# module. Post-patch callbacks are executed and the transition 354# completes quickly. 355 356echo -n "TEST: multiple target modules ... " 357dmesg -C 358 359load_mod $MOD_TARGET_BUSY block_transition=N 360load_lp $MOD_LIVEPATCH 361load_mod $MOD_TARGET 362unload_mod $MOD_TARGET 363disable_lp $MOD_LIVEPATCH 364unload_lp $MOD_LIVEPATCH 365unload_mod $MOD_TARGET_BUSY 366 367check_result "% modprobe $MOD_TARGET_BUSY block_transition=N 368$MOD_TARGET_BUSY: ${MOD_TARGET_BUSY}_init 369$MOD_TARGET_BUSY: busymod_work_func enter 370$MOD_TARGET_BUSY: busymod_work_func exit 371% modprobe $MOD_LIVEPATCH 372livepatch: enabling patch '$MOD_LIVEPATCH' 373livepatch: '$MOD_LIVEPATCH': initializing patching transition 374$MOD_LIVEPATCH: pre_patch_callback: vmlinux 375$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET_BUSY -> [MODULE_STATE_LIVE] Normal state 376livepatch: '$MOD_LIVEPATCH': starting patching transition 377livepatch: '$MOD_LIVEPATCH': completing patching transition 378$MOD_LIVEPATCH: post_patch_callback: vmlinux 379$MOD_LIVEPATCH: post_patch_callback: $MOD_TARGET_BUSY -> [MODULE_STATE_LIVE] Normal state 380livepatch: '$MOD_LIVEPATCH': patching complete 381% modprobe $MOD_TARGET 382livepatch: applying patch '$MOD_LIVEPATCH' to loading module '$MOD_TARGET' 383$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 384$MOD_LIVEPATCH: post_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 385$MOD_TARGET: ${MOD_TARGET}_init 386% rmmod $MOD_TARGET 387$MOD_TARGET: ${MOD_TARGET}_exit 388$MOD_LIVEPATCH: pre_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 389livepatch: reverting patch '$MOD_LIVEPATCH' on unloading module '$MOD_TARGET' 390$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 391% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 392livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 393$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 394$MOD_LIVEPATCH: pre_unpatch_callback: $MOD_TARGET_BUSY -> [MODULE_STATE_LIVE] Normal state 395livepatch: '$MOD_LIVEPATCH': starting unpatching transition 396livepatch: '$MOD_LIVEPATCH': completing unpatching transition 397$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 398$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET_BUSY -> [MODULE_STATE_LIVE] Normal state 399livepatch: '$MOD_LIVEPATCH': unpatching complete 400% rmmod $MOD_LIVEPATCH 401% rmmod $MOD_TARGET_BUSY 402$MOD_TARGET_BUSY: ${MOD_TARGET_BUSY}_exit" 403 404 405# TEST: busy target module 406# 407# A similar test as the previous one, but force the "busy" kernel module 408# to block the livepatch transition. 409# 410# The livepatching core will refuse to patch a task that is currently 411# executing a to-be-patched function -- the consistency model stalls the 412# current patch transition until this safety-check is met. Test a 413# scenario where one of a livepatch's target klp_objects sits on such a 414# function for a long time. Meanwhile, load and unload other target 415# kernel modules while the livepatch transition is in progress. 416# 417# - Load the "busy" kernel module, this time make its work function loop 418# 419# - Meanwhile, the livepatch is loaded. Notice that the patch 420# transition does not complete as the targeted "busy" module is 421# sitting on a to-be-patched function. 422# 423# - Load a second target module (this one is an ordinary idle kernel 424# module). Note that *no* post-patch callbacks will be executed while 425# the livepatch is still in transition. 426# 427# - Request an unload of the simple kernel module. The patch is still 428# transitioning, so its pre-unpatch callbacks are skipped. 429# 430# - Finally the livepatch is disabled. Since none of the patch's 431# klp_object's post-patch callbacks executed, the remaining 432# klp_object's pre-unpatch callbacks are skipped. 433 434echo -n "TEST: busy target module ... " 435dmesg -C 436 437load_mod $MOD_TARGET_BUSY block_transition=Y 438load_lp_nowait $MOD_LIVEPATCH 439 440# Wait until the livepatch reports in-transition state, i.e. that it's 441# stalled on $MOD_TARGET_BUSY::busymod_work_func() 442loop_until 'grep -q '^1$' /sys/kernel/livepatch/$MOD_LIVEPATCH/transition' || 443 die "failed to stall transition" 444 445load_mod $MOD_TARGET 446unload_mod $MOD_TARGET 447disable_lp $MOD_LIVEPATCH 448unload_lp $MOD_LIVEPATCH 449unload_mod $MOD_TARGET_BUSY 450 451check_result "% modprobe $MOD_TARGET_BUSY block_transition=Y 452$MOD_TARGET_BUSY: ${MOD_TARGET_BUSY}_init 453$MOD_TARGET_BUSY: busymod_work_func enter 454% modprobe $MOD_LIVEPATCH 455livepatch: enabling patch '$MOD_LIVEPATCH' 456livepatch: '$MOD_LIVEPATCH': initializing patching transition 457$MOD_LIVEPATCH: pre_patch_callback: vmlinux 458$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET_BUSY -> [MODULE_STATE_LIVE] Normal state 459livepatch: '$MOD_LIVEPATCH': starting patching transition 460% modprobe $MOD_TARGET 461livepatch: applying patch '$MOD_LIVEPATCH' to loading module '$MOD_TARGET' 462$MOD_LIVEPATCH: pre_patch_callback: $MOD_TARGET -> [MODULE_STATE_COMING] Full formed, running module_init 463$MOD_TARGET: ${MOD_TARGET}_init 464% rmmod $MOD_TARGET 465$MOD_TARGET: ${MOD_TARGET}_exit 466livepatch: reverting patch '$MOD_LIVEPATCH' on unloading module '$MOD_TARGET' 467$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET -> [MODULE_STATE_GOING] Going away 468% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 469livepatch: '$MOD_LIVEPATCH': reversing transition from patching to unpatching 470livepatch: '$MOD_LIVEPATCH': starting unpatching transition 471livepatch: '$MOD_LIVEPATCH': completing unpatching transition 472$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 473$MOD_LIVEPATCH: post_unpatch_callback: $MOD_TARGET_BUSY -> [MODULE_STATE_LIVE] Normal state 474livepatch: '$MOD_LIVEPATCH': unpatching complete 475% rmmod $MOD_LIVEPATCH 476% rmmod $MOD_TARGET_BUSY 477$MOD_TARGET_BUSY: busymod_work_func exit 478$MOD_TARGET_BUSY: ${MOD_TARGET_BUSY}_exit" 479 480 481# TEST: multiple livepatches 482# 483# Test loading multiple livepatches. This test-case is mainly for comparing 484# with the next test-case. 485# 486# - Load and unload two livepatches, pre and post (un)patch callbacks 487# execute as each patch progresses through its (un)patching 488# transition. 489 490echo -n "TEST: multiple livepatches ... " 491dmesg -C 492 493load_lp $MOD_LIVEPATCH 494load_lp $MOD_LIVEPATCH2 495disable_lp $MOD_LIVEPATCH2 496disable_lp $MOD_LIVEPATCH 497unload_lp $MOD_LIVEPATCH2 498unload_lp $MOD_LIVEPATCH 499 500check_result "% modprobe $MOD_LIVEPATCH 501livepatch: enabling patch '$MOD_LIVEPATCH' 502livepatch: '$MOD_LIVEPATCH': initializing patching transition 503$MOD_LIVEPATCH: pre_patch_callback: vmlinux 504livepatch: '$MOD_LIVEPATCH': starting patching transition 505livepatch: '$MOD_LIVEPATCH': completing patching transition 506$MOD_LIVEPATCH: post_patch_callback: vmlinux 507livepatch: '$MOD_LIVEPATCH': patching complete 508% modprobe $MOD_LIVEPATCH2 509livepatch: enabling patch '$MOD_LIVEPATCH2' 510livepatch: '$MOD_LIVEPATCH2': initializing patching transition 511$MOD_LIVEPATCH2: pre_patch_callback: vmlinux 512livepatch: '$MOD_LIVEPATCH2': starting patching transition 513livepatch: '$MOD_LIVEPATCH2': completing patching transition 514$MOD_LIVEPATCH2: post_patch_callback: vmlinux 515livepatch: '$MOD_LIVEPATCH2': patching complete 516% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH2/enabled 517livepatch: '$MOD_LIVEPATCH2': initializing unpatching transition 518$MOD_LIVEPATCH2: pre_unpatch_callback: vmlinux 519livepatch: '$MOD_LIVEPATCH2': starting unpatching transition 520livepatch: '$MOD_LIVEPATCH2': completing unpatching transition 521$MOD_LIVEPATCH2: post_unpatch_callback: vmlinux 522livepatch: '$MOD_LIVEPATCH2': unpatching complete 523% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH/enabled 524livepatch: '$MOD_LIVEPATCH': initializing unpatching transition 525$MOD_LIVEPATCH: pre_unpatch_callback: vmlinux 526livepatch: '$MOD_LIVEPATCH': starting unpatching transition 527livepatch: '$MOD_LIVEPATCH': completing unpatching transition 528$MOD_LIVEPATCH: post_unpatch_callback: vmlinux 529livepatch: '$MOD_LIVEPATCH': unpatching complete 530% rmmod $MOD_LIVEPATCH2 531% rmmod $MOD_LIVEPATCH" 532 533 534# TEST: atomic replace 535# 536# Load multiple livepatches, but the second as an 'atomic-replace' 537# patch. When the latter loads, the original livepatch should be 538# disabled and *none* of its pre/post-unpatch callbacks executed. On 539# the other hand, when the atomic-replace livepatch is disabled, its 540# pre/post-unpatch callbacks *should* be executed. 541# 542# - Load and unload two livepatches, the second of which has its 543# .replace flag set true. 544# 545# - Pre and post patch callbacks are executed for both livepatches. 546# 547# - Once the atomic replace module is loaded, only its pre and post 548# unpatch callbacks are executed. 549 550echo -n "TEST: atomic replace ... " 551dmesg -C 552 553load_lp $MOD_LIVEPATCH 554load_lp $MOD_LIVEPATCH2 replace=1 555disable_lp $MOD_LIVEPATCH2 556unload_lp $MOD_LIVEPATCH2 557unload_lp $MOD_LIVEPATCH 558 559check_result "% modprobe $MOD_LIVEPATCH 560livepatch: enabling patch '$MOD_LIVEPATCH' 561livepatch: '$MOD_LIVEPATCH': initializing patching transition 562$MOD_LIVEPATCH: pre_patch_callback: vmlinux 563livepatch: '$MOD_LIVEPATCH': starting patching transition 564livepatch: '$MOD_LIVEPATCH': completing patching transition 565$MOD_LIVEPATCH: post_patch_callback: vmlinux 566livepatch: '$MOD_LIVEPATCH': patching complete 567% modprobe $MOD_LIVEPATCH2 replace=1 568livepatch: enabling patch '$MOD_LIVEPATCH2' 569livepatch: '$MOD_LIVEPATCH2': initializing patching transition 570$MOD_LIVEPATCH2: pre_patch_callback: vmlinux 571livepatch: '$MOD_LIVEPATCH2': starting patching transition 572livepatch: '$MOD_LIVEPATCH2': completing patching transition 573$MOD_LIVEPATCH2: post_patch_callback: vmlinux 574livepatch: '$MOD_LIVEPATCH2': patching complete 575% echo 0 > /sys/kernel/livepatch/$MOD_LIVEPATCH2/enabled 576livepatch: '$MOD_LIVEPATCH2': initializing unpatching transition 577$MOD_LIVEPATCH2: pre_unpatch_callback: vmlinux 578livepatch: '$MOD_LIVEPATCH2': starting unpatching transition 579livepatch: '$MOD_LIVEPATCH2': completing unpatching transition 580$MOD_LIVEPATCH2: post_unpatch_callback: vmlinux 581livepatch: '$MOD_LIVEPATCH2': unpatching complete 582% rmmod $MOD_LIVEPATCH2 583% rmmod $MOD_LIVEPATCH" 584 585 586exit 0 587