Script to guess Red Hat machine's build date.
[profile.git] / opt / bin / ktmux_helper
index e62b4a5..e2b58a5 100755 (executable)
@@ -1,16 +1,22 @@
 #!/usr/bin/perl
 #
 # ktmux_helper: Run krenew in the background for tmux.
+# Usage: ktmux_helper [options]
+# Options: -I <path>   Specify path to kinit.
+#          -L <path>   Specify path to klist.
+#          -R <path>   Specify path to krenew.
+#          -T <path>   Specify path to tmux.
 # Notes: Doesn't handle multiple sessions properly.
 #
 
 use FindBin;
+use Getopt::Std;
 use POSIX ":sys_wait_h";
 
 my $PROG = $FindBin::Script;
 
 # Ensure tmux is our parent and find its PID.
-my $tmux_pid = &get_tmux_pid;
+our $tmux_pid = &get_tmux_pid;
 unless ($tmux_pid) {
   print STDERR "$PROG: Not a child of tmux!\n";
   exit 100;
@@ -19,6 +25,17 @@ unless ($tmux_pid) {
 # Ensure there isn't already a helper running for this tmux.
 my $tmux_helper = &get_tmux_helper;
 exit 0 if $tmux_helper;
+$tmux_helper = $$;
+
+my %opts;
+getopts('I:L:R:T:', \%opts);
+
+my $kinit = $opts{'I'} || "kinit";
+my $klist = $opts{'L'} || "klist";
+my $krenew = $opts{'R'} || "krenew";
+my $tmux = $opts{'T'} || "tmux";
+
+my $avoid_race = 0;
 
 my $exitasap = 0;
 my $pid = 0;
@@ -26,6 +43,7 @@ my $pid = 0;
 $SIG{INT} = \&cleanup;
 $SIG{QUIT} = \&cleanup;
 $SIG{TERM} = \&cleanup;
+$SIG{USR1} = \&want_credentials;
 
 LOOP: while (&ping_tmux) {
   $pid = fork;
@@ -39,12 +57,13 @@ LOOP: while (&ping_tmux) {
     }
 
     # tmux is dead so kill krenew.
-    kill 3, $pid;
+    kill QUIT, $pid;
     waitpid $pid, 0;
     exit 0;
   }
   else {
-    exec "krenew", "-K", "60";
+    exit 1 if &check_credentials;
+    exec $krenew, "-K", "60";
     print "$PROG: Can't run krenew: $!\n";
     exit 111;
   }
@@ -57,6 +76,13 @@ sub get_tmux_pid {
   return undef;
 }
 
+sub check_kinit_child {
+  foreach my $pid (`/bin/ps -o ppid= -C kinit`) {
+    return 1 if $pid =~ /^\s*$tmux_pid\s*$/;
+  }
+  return 0;
+}
+
 sub get_tmux_helper {
   my $pid = undef;
   if (open IN, "pgrep -x -P $tmux_pid $PROG | ") {
@@ -76,6 +102,25 @@ sub ping_tmux {
   return kill 0, $tmux_pid;
 }
 
+# Try to check existing Kerberos credentials.
+sub check_credentials {
+  system $klist, "-s";
+  return 1 if $? < 0;
+  return 0 unless $?;
+  kill USR1, $tmux_helper;
+  return 111;
+}
+
+# We were signalled by our child which noticed that our credentials expired.
+sub want_credentials {
+  return sleep 1 if $avoid_race;
+  $avoid_race = 1;
+  # Do we already know?
+  system $tmux, "new-window", "-n", "Renew Kerberos credentials", "exec $kinit" unless &check_kinit_child;
+  sleep 1;
+  $avoid_race = 0;
+}
+
 sub cleanup {
   unless ($exitasap) {
     $exitasap = 1;