Results 1 to 6 of 6
I'm doing the shell history audit logging using syslog to gather the command history. I'm using this well publicized method using trap and logger:
declare -r REAL_LOGNAME=`/usr/bin/who am i | ...
- 10-22-2010 #1Just Joined!
- Join Date
- Dec 2007
- Posts
- 3
What signal emitted with CTL+D in Bash?
I'm doing the shell history audit logging using syslog to gather the command history. I'm using this well publicized method using trap and logger:
declare -r REAL_LOGNAME=`/usr/bin/who am i | cut -d" " -f1`
function log2syslog {
declare command
command=`fc -ln -0`
logger -p local1.notice -t bash -i ": $REAL_LOGNAME as $LOGNAME :$command"
}
trap log2syslog DEBUG TERM
The problem is that the trap on DEBUG will catch the next to last command executed (by virtue of the "fc" command) which is not the current command executed. TERM will catch that "next to last" command on exit, thus completing the logging of each command executed during that session.
However, CTL+D doesn't seem to emit a SIGTERM signal. What signal is actually being emitted and can it be trapped? I guess another question would be whether there is a way to trap history after command line execution? Moving to Bash 4.1 isn't possible in our "supported" multi-platform environment
Thanks.Last edited by onthego; 10-22-2010 at 02:39 PM. Reason: add additional comment
- 10-23-2010 #2
So without fully understanding your code, I'll at least answer the Ctrl-D question.
Ctrl-D does not emit a signal. Instead, it counts as an input of EOF. EOF causes the program to think that there is no more input, so in this case, Bash decides to exit.
I'm not sure exactly how to catch that condition super well, unfortunately.DISTRO=Arch
Registered Linux User #388732
- 10-23-2010 #3Linux Guru
- Join Date
- Apr 2009
- Location
- I can be found either 40 miles west of Chicago, or in a galaxy far, far away.
- Posts
- 8,974
As Cabhan said, a Ctrl-D doesn't generate a signal. It is effectively the same behavior as the "exit" command. Your attempt to trap the TERM signal won't work in such a case as it is not generating a signal.
Sometimes, real fast is almost as good as real time.
Just remember, Semper Gumbi - always be flexible!
- 10-25-2010 #4
I just went poking through the bash man page, and I came across this environment variable:
This does not cause bash to ignore EOF, but means that EOF must be typed multiple times. You could set this variable to a high number, and in the documentation for your script say that EOF is not supported when running your program and that you must run "exit" to quit.Code:IGNOREEOF Controls the action of an interactive shell on receipt of an EOF character as the sole input. If set, the value is the number of consecutive EOF characters which must be typed as the first characters on an input line before bash exits. If the variable exists but does not have a numeric value, or has no value, the default value is 10. If it does not exist, EOF signifies the end of input to the shell.DISTRO=Arch
Registered Linux User #388732
- 10-26-2010 #5Just Joined!
- Join Date
- Dec 2007
- Posts
- 3
Makes sense
Thanks guys for the advise. I'm only command line logging a handful of shared non-user/administrative accounts that the identity is assumed using "sudo su -". That type of exception won't be far reaching.
Though EOF is not a true Unix signal, it is an event that is detected by the running shell and a section of code is invoked to act on based on that event. The builtin "exit" command itself isn't a true signal, but results in the signal being emitted.
The method for IGNOREEOF is interesting workaround and worth giving a shot. It will be interesting to see how it affects inline reads and such. I'll post back with the results.Last edited by onthego; 10-26-2010 at 03:57 PM. Reason: correct spelling
- 10-28-2010 #6Just Joined!
- Join Date
- Dec 2007
- Posts
- 3
Appears to be a suitable solution
I set the IGNOREEOF=1 without exporting it and seems to be suitable (though not optional) in order to capture the last command executed before exit.
The fallout comes when you perform in-line reads (aka here-documents) directly from that login shell. For each line directed from STDIN you log a redundant command line execution (from history) for that loop instance. When executing a standalone bash script with a looped in-line read, you only get the script executed once in the log (since the variable is unexported). Logically, if exported, any bash script executed will inherit the IGNOREEOF. The fallout here is the added clutter in the log for what appears to be redundant shell script executions you really don't care to see, again one shell script execution from history per loop iteration in that script.
Hope this makes sense. Thanks for the tip.


Reply With Quote