1fcace290SJake Freeland#- 2fcace290SJake Freeland# SPDX-License-Identifier: BSD-2-Clause 3fcace290SJake Freeland# 4fcace290SJake Freeland# Copyright (c) 2021, 2023 The FreeBSD Foundation 5fcace290SJake Freeland# 6fcace290SJake Freeland# This software was developed by Mark Johnston under sponsorship from 7fcace290SJake Freeland# the FreeBSD Foundation. 8fcace290SJake Freeland# 9fcace290SJake Freeland# This software was developed by Jake Freeland under sponsorship from 10fcace290SJake Freeland# the FreeBSD Foundation. 11fcace290SJake Freeland# 12fcace290SJake Freeland 13fcace290SJake Freeland# Tests to-do: 14fcace290SJake Freeland# actions: hostname, users 15fcace290SJake Freeland 16fcace290SJake Freelandreadonly SYSLOGD_UDP_PORT="5140" 17fcace290SJake Freelandreadonly SYSLOGD_CONFIG="${PWD}/syslog.conf" 18fcace290SJake Freelandreadonly SYSLOGD_LOCAL_SOCKET="${PWD}/log.sock" 19fcace290SJake Freelandreadonly SYSLOGD_PIDFILE="${PWD}/syslogd.pid" 20fcace290SJake Freelandreadonly SYSLOGD_LOCAL_PRIVSOCKET="${PWD}/logpriv.sock" 21fcace290SJake Freeland 22fcace290SJake Freeland# Start a private syslogd instance. 23fcace290SJake Freelandsyslogd_start() 24fcace290SJake Freeland{ 25fcace290SJake Freeland syslogd \ 26fcace290SJake Freeland -b ":${SYSLOGD_UDP_PORT}" \ 27fcace290SJake Freeland -C \ 28fcace290SJake Freeland -d \ 29fcace290SJake Freeland -f "${SYSLOGD_CONFIG}" \ 30fcace290SJake Freeland -H \ 31fcace290SJake Freeland -p "${SYSLOGD_LOCAL_SOCKET}" \ 32fcace290SJake Freeland -P "${SYSLOGD_PIDFILE}" \ 33fcace290SJake Freeland -S "${SYSLOGD_LOCAL_PRIVSOCKET}" \ 34fcace290SJake Freeland $@ \ 35fcace290SJake Freeland & 36fcace290SJake Freeland 37fcace290SJake Freeland # Give syslogd a bit of time to spin up. 38fcace290SJake Freeland while [ "$((i+=1))" -le 20 ]; do 39fcace290SJake Freeland [ -S "${SYSLOGD_LOCAL_SOCKET}" ] && return 40fcace290SJake Freeland sleep 0.1 41fcace290SJake Freeland done 42fcace290SJake Freeland atf_fail "timed out waiting for syslogd to start" 43fcace290SJake Freeland} 44fcace290SJake Freeland 45fcace290SJake Freeland# Simple logger(1) wrapper. 46fcace290SJake Freelandsyslogd_log() 47fcace290SJake Freeland{ 48fcace290SJake Freeland atf_check -s exit:0 -o empty -e empty logger $* 49fcace290SJake Freeland} 50fcace290SJake Freeland 51fcace290SJake Freeland# Make syslogd reload its configuration file. 52fcace290SJake Freelandsyslogd_reload() 53fcace290SJake Freeland{ 54fcace290SJake Freeland pkill -HUP -F "${SYSLOGD_PIDFILE}" 55fcace290SJake Freeland} 56fcace290SJake Freeland 57fcace290SJake Freeland# Stop a private syslogd instance. 58fcace290SJake Freelandsyslogd_stop() 59fcace290SJake Freeland{ 60fcace290SJake Freeland pid=$(cat "${SYSLOGD_PIDFILE}") 61fcace290SJake Freeland if pkill -F "${SYSLOGD_PIDFILE}"; then 62fcace290SJake Freeland wait "${pid}" 63fcace290SJake Freeland rm -f "${SYSLOGD_PIDFILE}" "${SYSLOGD_LOCAL_SOCKET}" \ 64fcace290SJake Freeland "${SYSLOGD_LOCAL_PRIVSOCKET}" 65fcace290SJake Freeland fi 66fcace290SJake Freeland} 67fcace290SJake Freeland 68fcace290SJake Freelandatf_test_case "basic" "cleanup" 69fcace290SJake Freelandbasic_head() 70fcace290SJake Freeland{ 71fcace290SJake Freeland atf_set descr "Messages are logged via supported transports" 72fcace290SJake Freeland} 73fcace290SJake Freelandbasic_body() 74fcace290SJake Freeland{ 75fcace290SJake Freeland logfile="${PWD}/basic.log" 76fcace290SJake Freeland printf "user.debug\t${logfile}\n" > "${SYSLOGD_CONFIG}" 77fcace290SJake Freeland syslogd_start 78fcace290SJake Freeland 79fcace290SJake Freeland syslogd_log -p user.debug -t basic -h "${SYSLOGD_LOCAL_SOCKET}" \ 80fcace290SJake Freeland "hello, world (unix)" 81fcace290SJake Freeland atf_check -s exit:0 -o match:"basic: hello, world \(unix\)" \ 82fcace290SJake Freeland tail -n 1 "${logfile}" 83fcace290SJake Freeland 84fcace290SJake Freeland # Grab kernel configuration file. 85fcace290SJake Freeland sysctl kern.conftxt > conf.txt 86fcace290SJake Freeland 87fcace290SJake Freeland # We have INET transport; make sure we can use it. 88fcace290SJake Freeland if grep -qw "INET" conf.txt; then 89fcace290SJake Freeland syslogd_log -4 -p user.debug -t basic -h 127.0.0.1 -P "${SYSLOGD_UDP_PORT}" \ 90fcace290SJake Freeland "hello, world (v4)" 91fcace290SJake Freeland atf_check -s exit:0 -o match:"basic: hello, world \(v4\)" \ 92fcace290SJake Freeland tail -n 1 "${logfile}" 93fcace290SJake Freeland fi 94fcace290SJake Freeland # We have INET6 transport; make sure we can use it. 95fcace290SJake Freeland if grep -qw "INET6" conf.txt; then 96fcace290SJake Freeland syslogd_log -6 -p user.debug -t basic -h ::1 -P "${SYSLOGD_UDP_PORT}" \ 97fcace290SJake Freeland "hello, world (v6)" 98fcace290SJake Freeland atf_check -s exit:0 -o match:"basic: hello, world \(v6\)" \ 99fcace290SJake Freeland tail -n 1 "${logfile}" 100fcace290SJake Freeland fi 101fcace290SJake Freeland} 102fcace290SJake Freelandbasic_cleanup() 103fcace290SJake Freeland{ 104fcace290SJake Freeland syslogd_stop 105fcace290SJake Freeland} 106fcace290SJake Freeland 107fcace290SJake Freelandatf_test_case "reload" "cleanup" 108fcace290SJake Freelandreload_head() 109fcace290SJake Freeland{ 110fcace290SJake Freeland atf_set descr "SIGHUP correctly refreshes configuration" 111fcace290SJake Freeland} 112fcace290SJake Freelandreload_body() 113fcace290SJake Freeland{ 114fcace290SJake Freeland logfile="${PWD}/reload.log" 115fcace290SJake Freeland printf "user.debug\t/${logfile}\n" > "${SYSLOGD_CONFIG}" 116fcace290SJake Freeland syslogd_start 117fcace290SJake Freeland 118fcace290SJake Freeland syslogd_log -p user.debug -t reload -h "${SYSLOGD_LOCAL_SOCKET}" \ 119fcace290SJake Freeland "pre-reload" 120fcace290SJake Freeland atf_check -s exit:0 -o match:"reload: pre-reload" tail -n 1 "${logfile}" 121fcace290SJake Freeland 122fcace290SJake Freeland # Override the old rule. 123fcace290SJake Freeland truncate -s 0 "${logfile}" 124fcace290SJake Freeland printf "news.debug\t${logfile}\n" > "${SYSLOGD_CONFIG}" 125fcace290SJake Freeland syslogd_reload 126fcace290SJake Freeland 127fcace290SJake Freeland syslogd_log -p user.debug -t reload -h "${SYSLOGD_LOCAL_SOCKET}" \ 128fcace290SJake Freeland "post-reload user" 129fcace290SJake Freeland syslogd_log -p news.debug -t reload -h "${SYSLOGD_LOCAL_SOCKET}" \ 130fcace290SJake Freeland "post-reload news" 131fcace290SJake Freeland atf_check -s exit:0 -o not-match:"reload: post-reload user" cat ${logfile} 132fcace290SJake Freeland atf_check -s exit:0 -o match:"reload: post-reload news" cat ${logfile} 133fcace290SJake Freeland} 134fcace290SJake Freelandreload_cleanup() 135fcace290SJake Freeland{ 136fcace290SJake Freeland syslogd_stop 137fcace290SJake Freeland} 138fcace290SJake Freeland 139fcace290SJake Freelandatf_test_case "prog_filter" "cleanup" 140fcace290SJake Freelandprog_filter_head() 141fcace290SJake Freeland{ 142fcace290SJake Freeland atf_set descr "Messages are only received from programs in the filter" 143fcace290SJake Freeland} 144fcace290SJake Freelandprog_filter_body() 145fcace290SJake Freeland{ 146fcace290SJake Freeland logfile="${PWD}/prog_filter.log" 147fcace290SJake Freeland printf "!prog1,prog2\nuser.debug\t${logfile}\n" > "${SYSLOGD_CONFIG}" 148fcace290SJake Freeland syslogd_start 149fcace290SJake Freeland 150fcace290SJake Freeland for i in 1 2 3; do 151fcace290SJake Freeland syslogd_log -p user.debug -t "prog${i}" -h "${SYSLOGD_LOCAL_SOCKET}" \ 152fcace290SJake Freeland "hello this is prog${i}" 153fcace290SJake Freeland done 154fcace290SJake Freeland atf_check -s exit:0 -o match:"prog1: hello this is prog1" cat "${logfile}" 155fcace290SJake Freeland atf_check -s exit:0 -o match:"prog2: hello this is prog2" cat "${logfile}" 156fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prog3: hello this is prog3" cat "${logfile}" 157fcace290SJake Freeland 158fcace290SJake Freeland # Override the old rule. 159fcace290SJake Freeland truncate -s 0 ${logfile} 160fcace290SJake Freeland printf "!-prog1,prog2\nuser.debug\t${logfile}\n" > "${SYSLOGD_CONFIG}" 161fcace290SJake Freeland syslogd_reload 162fcace290SJake Freeland 163fcace290SJake Freeland for i in 1 2 3; do 164fcace290SJake Freeland syslogd_log -p user.debug -t "prog${i}" -h "${SYSLOGD_LOCAL_SOCKET}" \ 165fcace290SJake Freeland "hello this is prog${i}" 166fcace290SJake Freeland done 167fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prog1: hello this is prog1" cat "${logfile}" 168fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prog2: hello this is prog2" cat "${logfile}" 169fcace290SJake Freeland atf_check -s exit:0 -o match:"prog3: hello this is prog3" cat "${logfile}" 170fcace290SJake Freeland} 171fcace290SJake Freelandprog_filter_cleanup() 172fcace290SJake Freeland{ 173fcace290SJake Freeland syslogd_stop 174fcace290SJake Freeland} 175fcace290SJake Freeland 176fcace290SJake Freelandatf_test_case "host_filter" "cleanup" 177fcace290SJake Freelandhost_filter_head() 178fcace290SJake Freeland{ 179fcace290SJake Freeland atf_set descr "Messages are only received from hostnames in the filter" 180fcace290SJake Freeland} 181fcace290SJake Freelandhost_filter_body() 182fcace290SJake Freeland{ 183fcace290SJake Freeland logfile="${PWD}/host_filter.log" 184fcace290SJake Freeland printf "+host1,host2\nuser.debug\t${logfile}\n" > "${SYSLOGD_CONFIG}" 185fcace290SJake Freeland syslogd_start 186fcace290SJake Freeland 187fcace290SJake Freeland for i in 1 2 3; do 188fcace290SJake Freeland syslogd_log -p user.debug -t "host${i}" -H "host${i}" \ 189fcace290SJake Freeland -h "${SYSLOGD_LOCAL_SOCKET}" "hello this is host${i}" 190fcace290SJake Freeland done 191fcace290SJake Freeland atf_check -s exit:0 -o match:"host1: hello this is host1" cat "${logfile}" 192fcace290SJake Freeland atf_check -s exit:0 -o match:"host2: hello this is host2" cat "${logfile}" 193fcace290SJake Freeland atf_check -s exit:0 -o not-match:"host3: hello this is host3" cat "${logfile}" 194fcace290SJake Freeland 195fcace290SJake Freeland # Override the old rule. 196fcace290SJake Freeland truncate -s 0 ${logfile} 197fcace290SJake Freeland printf "\-host1,host2\nuser.debug\t${logfile}\n" > "${SYSLOGD_CONFIG}" 198fcace290SJake Freeland syslogd_reload 199fcace290SJake Freeland 200fcace290SJake Freeland for i in 1 2 3; do 201fcace290SJake Freeland syslogd_log -p user.debug -t "host${i}" -H "host${i}" \ 202fcace290SJake Freeland -h "${SYSLOGD_LOCAL_SOCKET}" "hello this is host${i}" 203fcace290SJake Freeland done 204fcace290SJake Freeland atf_check -s exit:0 -o not-match:"host1: hello this is host1" cat "${logfile}" 205fcace290SJake Freeland atf_check -s exit:0 -o not-match:"host2: hello this is host2" cat "${logfile}" 206fcace290SJake Freeland atf_check -s exit:0 -o match:"host3: hello this is host3" cat "${logfile}" 207fcace290SJake Freeland} 208fcace290SJake Freelandhost_filter_cleanup() 209fcace290SJake Freeland{ 210fcace290SJake Freeland syslogd_stop 211fcace290SJake Freeland} 212fcace290SJake Freeland 213fcace290SJake Freelandatf_test_case "prop_filter" "cleanup" 214fcace290SJake Freelandprop_filter_head() 215fcace290SJake Freeland{ 216fcace290SJake Freeland atf_set descr "Messages are received based on conditions in the propery based filter" 217fcace290SJake Freeland} 218fcace290SJake Freelandprop_filter_body() 219fcace290SJake Freeland{ 220fcace290SJake Freeland logfile="${PWD}/prop_filter.log" 221fcace290SJake Freeland printf ":msg,contains,\"FreeBSD\"\nuser.debug\t${logfile}\n" \ 222fcace290SJake Freeland > "${SYSLOGD_CONFIG}" 223fcace290SJake Freeland syslogd_start 224fcace290SJake Freeland 225fcace290SJake Freeland syslogd_log -p user.debug -t "prop1" -h "${SYSLOGD_LOCAL_SOCKET}" "FreeBSD" 226fcace290SJake Freeland syslogd_log -p user.debug -t "prop2" -h "${SYSLOGD_LOCAL_SOCKET}" "freebsd" 227fcace290SJake Freeland atf_check -s exit:0 -o match:"prop1: FreeBSD" cat "${logfile}" 228fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prop2: freebsd" cat "${logfile}" 229fcace290SJake Freeland 230fcace290SJake Freeland truncate -s 0 ${logfile} 231fcace290SJake Freeland printf ":msg,!contains,\"FreeBSD\"\nuser.debug\t${logfile}\n" \ 232fcace290SJake Freeland > "${SYSLOGD_CONFIG}" 233fcace290SJake Freeland syslogd_reload 234fcace290SJake Freeland 235fcace290SJake Freeland syslogd_log -p user.debug -t "prop1" -h "${SYSLOGD_LOCAL_SOCKET}" "FreeBSD" 236fcace290SJake Freeland syslogd_log -p user.debug -t "prop2" -h "${SYSLOGD_LOCAL_SOCKET}" "freebsd" 237fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prop1: FreeBSD" cat "${logfile}" 238fcace290SJake Freeland atf_check -s exit:0 -o match:"prop2: freebsd" cat "${logfile}" 239fcace290SJake Freeland 240fcace290SJake Freeland truncate -s 0 ${logfile} 241fcace290SJake Freeland printf ":msg,icase_contains,\"FreeBSD\"\nuser.debug\t${logfile}\n" \ 242fcace290SJake Freeland > "${SYSLOGD_CONFIG}" 243fcace290SJake Freeland syslogd_reload 244fcace290SJake Freeland 245fcace290SJake Freeland syslogd_log -p user.debug -t "prop1" -h "${SYSLOGD_LOCAL_SOCKET}" "FreeBSD" 246fcace290SJake Freeland syslogd_log -p user.debug -t "prop2" -h "${SYSLOGD_LOCAL_SOCKET}" "freebsd" 247fcace290SJake Freeland atf_check -s exit:0 -o match:"prop1: FreeBSD" cat "${logfile}" 248fcace290SJake Freeland atf_check -s exit:0 -o match:"prop2: freebsd" cat "${logfile}" 249fcace290SJake Freeland 250fcace290SJake Freeland truncate -s 0 ${logfile} 251fcace290SJake Freeland printf ":msg,!icase_contains,\"FreeBSD\"\nuser.debug\t${logfile}\n" \ 252fcace290SJake Freeland > "${SYSLOGD_CONFIG}" 253fcace290SJake Freeland syslogd_reload 254fcace290SJake Freeland 255fcace290SJake Freeland syslogd_log -p user.debug -t "prop1" -h "${SYSLOGD_LOCAL_SOCKET}" "FreeBSD" 256fcace290SJake Freeland syslogd_log -p user.debug -t "prop2" -h "${SYSLOGD_LOCAL_SOCKET}" "freebsd" 257fcace290SJake Freeland syslogd_log -p user.debug -t "prop3" -h "${SYSLOGD_LOCAL_SOCKET}" "Solaris" 258fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prop1: FreeBSD" cat "${logfile}" 259fcace290SJake Freeland atf_check -s exit:0 -o not-match:"prop2: freebsd" cat "${logfile}" 260fcace290SJake Freeland atf_check -s exit:0 -o match:"prop3: Solaris" cat "${logfile}" 261fcace290SJake Freeland} 262fcace290SJake Freelandprop_filter_cleanup() 263fcace290SJake Freeland{ 264fcace290SJake Freeland syslogd_stop 265fcace290SJake Freeland} 266fcace290SJake Freeland 267fcace290SJake Freelandatf_test_case "pipe_action" "cleanup" 268fcace290SJake Freelandpipe_action_head() 269fcace290SJake Freeland{ 270fcace290SJake Freeland atf_set descr "The pipe action evaluates provided command in sh(1)" 271fcace290SJake Freeland} 272fcace290SJake Freelandpipe_action_body() 273fcace290SJake Freeland{ 274fcace290SJake Freeland logfile="${PWD}/pipe_action.log" 275fcace290SJake Freeland printf "\"While I'm digging in the tunnel, the elves will often come to me \ 276fcace290SJake Freeland with solutions to my problem.\"\n-Saymore Crey" > ${logfile} 277fcace290SJake Freeland 278fcace290SJake Freeland printf "!pipe\nuser.debug\t| sed -i '' -e 's/Saymore Crey/Seymour Cray/g' \ 279fcace290SJake Freeland ${logfile}\n" > "${SYSLOGD_CONFIG}" 280fcace290SJake Freeland syslogd_start 281fcace290SJake Freeland 282fcace290SJake Freeland syslogd_log -p user.debug -t "pipe" -h "${SYSLOGD_LOCAL_SOCKET}" \ 283fcace290SJake Freeland "fix spelling error" 284fcace290SJake Freeland atf_check -s exit:0 -o match:"Seymour Cray" cat "${logfile}" 285fcace290SJake Freeland} 286fcace290SJake Freelandpipe_action_cleanup() 287fcace290SJake Freeland{ 288fcace290SJake Freeland syslogd_stop 289fcace290SJake Freeland} 290fcace290SJake Freeland 291fcace290SJake Freelandatf_init_test_cases() 292fcace290SJake Freeland{ 293fcace290SJake Freeland atf_add_test_case "basic" 294fcace290SJake Freeland atf_add_test_case "reload" 295fcace290SJake Freeland atf_add_test_case "prog_filter" 296fcace290SJake Freeland atf_add_test_case "host_filter" 297fcace290SJake Freeland atf_add_test_case "prop_filter" 298fcace290SJake Freeland atf_add_test_case "pipe_action" 299fcace290SJake Freeland} 300