#!/usr/bin/wish set root "/etc" set backupdir "/tmp/tksysv" set version "0.8" set lib "/usr/lib/tksysv" set about $lib/about.txt set tksysv $lib/tksysv.txt set sysvinit $lib/sysvinit.txt exec rm -rf $backupdir exec mkdir -p $backupdir exec cp -arf $root/rc.d $backupdir if {[exec id -un] != "root"} { if {[tk_dialog .new "Wrong User" "You aren't the superuser. You must \ be root to run this program." "" "0" "Ok"] == "0"} { exit 0 } } if {$argv == "" } { set levels "0 1 2 3 4 5 6" } elseif {$argv == "--help"} { puts "\n\tUsage: tksysv \[0|1|2|3|4|5|6\] \[--help\]" puts "\n\tRun 'tksysv' with no args to view and edit all runlevels." puts "\tRun 'tksysv 0 1 2' to view and edit runlevels 0, 1, and 2.\n" exit 0 } else { set levels $argv } set number "" wm title . "SYSV Runlevel Manager, v$version" frame .top -relief raised -borderwidth 2 pack .top -side top -padx 1 -pady 1 -fill x menubutton .top.helpbutton -text Help -underline 0 -menu \ .top.helpbutton.filemenu menubutton .top.filebutton -text File -underline 0 -menu \ .top.filebutton.filemenu menu .top.filebutton.filemenu .top.filebutton.filemenu add command -label "Rescan rc.d" -command {readrc} .top.filebutton.filemenu add separator .top.filebutton.filemenu add command -label " Quit " -command {exit 0} menu .top.helpbutton.filemenu .top.helpbutton.filemenu add command -label "About" -command {showit $about} .top.helpbutton.filemenu add separator .top.helpbutton.filemenu add command -label "SYSV Init" -command {showit $sysvinit} .top.helpbutton.filemenu add command -label "tksysv" -command {showit $tksysv} pack .top.filebutton -side left pack .top.helpbutton -side right focus .top.filebutton.filemenu frame .left -relief groove -borderwidth 3 pack .left -side left -padx 3 -pady 3 -fill y frame .right pack .right -side left frame .right.top -relief groove -borderwidth 3 pack .right.top -side top -padx 3 -pady 3 frame .right.top.lab pack .right.top.lab -side left label .right.top.lab.label1 -text "S" -width 2 -justify center label .right.top.lab.label2 -text "t" -width 2 -justify center label .right.top.lab.label3 -text "a" -width 2 -justify center label .right.top.lab.label4 -text "r" -width 2 -justify center label .right.top.lab.label5 -text "t" -width 2 -justify center pack .right.top.lab.label1 -side top pack .right.top.lab.label2 -side top pack .right.top.lab.label3 -side top pack .right.top.lab.label4 -side top pack .right.top.lab.label5 -side top frame .right.bottom -relief groove -borderwidth 3 pack .right.bottom -side top -padx 3 -pady 3 frame .right.bottom.lab pack .right.bottom.lab -side left label .right.bottom.lab.label1 -text "S" -width 2 -justify center label .right.bottom.lab.label2 -text "t" -width 2 -justify center label .right.bottom.lab.label3 -text "o" -width 2 -justify center label .right.bottom.lab.label4 -text "p" -width 2 -justify center pack .right.bottom.lab.label1 -side top pack .right.bottom.lab.label2 -side top pack .right.bottom.lab.label3 -side top pack .right.bottom.lab.label4 -side top foreach loc "$levels" { frame .right.top.$loc pack .right.top.$loc -side left frame .right.bottom.$loc pack .right.bottom.$loc -side left frame .right.bottom.$loc.top pack .right.bottom.$loc.top -side top label .right.top.$loc.label -text "$loc" pack .right.top.$loc.label -side top listbox .right.top.$loc.list -height 10 -width 10 -yscrollcommand \ ".right.top.$loc.scroll set" scrollbar .right.top.$loc.scroll -command \ ".right.top.$loc.list yview" -width 10 listbox .right.bottom.$loc.top.list -height 10 -width 10 \ -yscrollcommand ".right.bottom.$loc.top.scroll set" scrollbar .right.bottom.$loc.top.scroll -command \ ".right.bottom.$loc.top.list yview" -width 10 # button .right.bottom.addstart$loc -text "Add Start" -command \ # {addstart} -width 10 # button .right.bottom.addstop$loc -text "Add Stop" -command \ # {addstop $loc} -width 10 # button .right.bottom.edit$loc -text "Edit" -command \ # {edit $loc} -width 10 # button .right.bottom.remove$loc -text "Remove" -command \ # {remove $loc} -width 10 pack .right.top.$loc.list -side left -in .right.top.$loc pack .right.top.$loc.scroll -side right -fill y -in .right.top.$loc pack .right.bottom.$loc.top.list -side left -in .right.bottom.$loc.top pack .right.bottom.$loc.top.scroll -side right -fill y -in \ .right.bottom.$loc.top # pack .right.bottom.addstart$loc -in .right.bottom.$loc -side top # pack .right.bottom.addstop$loc -in .right.bottom.$loc -side top # pack .right.bottom.edit$loc -in .right.bottom.$loc -side top # pack .right.bottom.remove$loc -in .right.bottom.$loc -side top } frame .left.top pack .left.top -in .left -side top label .left.top.label -text "Available:" -justify left pack .left.top.label -side top button .left.add -text "Add" -command {addit} -width 14 pack .left.add -side top button .left.remove -text "Remove" -command {removeit} -width 14 pack .left.add -side top button .left.edit -text "Edit" -command {editit} -width 14 pack .left.add .left.remove .left.edit -side top button .left.execute -text "Execute" -command {execute} -width 14 pack .left.add .left.execute .left.edit -side top listbox .left.top.available -height 14 -width 10 -yscrollcommand \ ".left.top.availablescroll set" scrollbar .left.top.availablescroll -command ".left.top.available yview" \ -width 10 pack .left.top.available -side left -in .left.top pack .left.top.availablescroll -side right -in .left.top -fill y pack .left -side left pack .right -side left pack .right.top -side top pack .right.bottom -side top # button .left.quit -text "Quit" -command {exit} -width 10 # pack .left.quit -side bottom -in .left foreach n [lsort [glob -nocomplain "$root/rc.d/init.d/*"]] { regsub (.*/) "$n" "" a if {![regexp "$a" "functions" ]} { if {![regexp "$a" "skeleton"]} { .left.top.available insert end "$a" } } } proc findit {} { global topstring top global bottomstring global runnumber global levels global leftstring set topstring "" set bottomstring "" set runnumber "" set leftstring "" foreach n "$levels" { set topselect [.right.top.$n.list curselection] if {$topselect != ""} { set topstring $topselect set runnumber $n set top "0" return 0 } set bottomselect [.right.bottom.$n.top.list curselection] if {$bottomselect != ""} { set bottomstring $bottomselect set runnumber $n set top "1" return 0 } } if {$bottomstring == "" && $topstring == ""} { set leftselect [.left.top.available curselection] if {$leftselect != ""} { set leftstring $leftselect return 2 } } if {$bottomstring == "" && $topstring == "" && $leftstring == ""} { return 1 } } proc execute {} { global topstring top global bottomstring global runnumber global leftstring levels global addtolevel leftselect if {[findit] != "2"} { tk_dialog .new "Select Something" "Please select something from the Available window." "" "0" "Ok" } elseif {$topstring != "" || $bottomstring != ""} { # puts "select something from the \"Available\" window please." } elseif {$leftstring != ""} { set leftselect [.left.top.available get $leftstring] toplevel .executeit focus .executeit wm title .executeit "Excute $leftselect" label .executeit.label -text "$leftselect" -justify center -width 20 \ -relief groove -borderwidth 2 button .executeit.start -text "Start" -command {runcom start} button .executeit.stop -text "Stop" -command {runcom stop} #button .executeit.restart -text "Restart" -command {runcom restart} button .executeit.canc -text "Cancel" -command {destroy .executeit} pack .executeit.label -side top #pack .executeit.start .executeit.stop .executeit.restart -side top -fill x pack .executeit.start .executeit.stop -side top -fill x pack .executeit.canc -side top -fill x } } proc runcom {what} { global topstring top root global bottomstring global runnumber global leftstring levels global addtolevel leftselect destroy .executeit toplevel .result focus .result wm title .result "Result from \`$leftselect $what\`" frame .result.top pack .result.top -side top text .result.top.text -relief sunken -borderwidth 2 -width 60 \ -height 10 -yscrollcommand ".result.top.scroll set" scrollbar .result.top.scroll -command ".result.top.text yview" \ -width 10 pack .result.top.text .result.top.scroll -side left -fill y button .result.quit -text "Done" -command {destroy .result} pack .result.quit -side top -fill x -padx 2 -pady 2 update idletasks set f [open "|$root/rc.d/init.d/$leftselect $what" r] while {[gets $f line] >= 0} { update idletasks .result.top.text insert end $line } close $f } proc addit {} { global topstring top global bottomstring global runnumber global leftstring levels global addtolevel leftselect if {[findit] == "1"} { tk_dialog .new "Nothing Selected" "You didn't select anything.\ Please select something to add/remove." "" "0" "Ok" } elseif {$topstring != "" || $bottomstring != ""} { # puts "select something from the \"Available\" window please." tk_dialog .new "Select Something" "Please select something from the Available window." "" "0" "Ok" } elseif {$leftstring != ""} { toplevel .addwin focus .addwin frame .addwin.box -relief groove -borderwidth 2 frame .addwin.box.top frame .addwin.box.bottom set leftselect [.left.top.available get $leftstring] wm title .addwin "Add $leftselect" # label .addwin.label -text "Add $leftselect to which runlevel:" # entry .addwin.entry -textvar addtolevel -width 4 # pack .addwin.label .addwin.entry -side top # pack .addwin.label -side top frame .addwin.two -relief groove -borderwidth 2 set addtolevel [lindex $levels 0] foreach n "$levels" { frame .addwin.two.$n label .addwin.two.$n.label -text "$n" checkbutton .addwin.two.$n.button -onvalue $n \ -variable addtolevel pack .addwin.two.$n.label .addwin.two.$n.button -side left pack .addwin.two.$n -side top } pack .addwin.box -side top -padx 3 -pady 3 -fill x label .addwin.label -text "in runlevel:" pack .addwin.label -side top pack .addwin.two -side top -padx 3 -pady 3 -fill x label .addwin.box.top.checkstart -text "Start $leftselect" checkbutton .addwin.box.top.startcheck -onvalue "0" \ -offvalue "1" -variable top pack .addwin.box.top .addwin.box.bottom -side top pack .addwin.box.top.checkstart .addwin.box.top.startcheck -side left label .addwin.box.bottom.checkstop -text "Stop $leftselect" checkbutton .addwin.box.bottom.stopcheck -onvalue "1" -offvalue \ "0" -variable top pack .addwin.box.bottom.checkstop .addwin.box.bottom.stopcheck -side left button .addwin.quit -text "Done" -command {addto} button .addwin.can -text "Cancel" -command {destroy .addwin} pack .addwin.quit .addwin.can -fill x -side top if {$top == "1"} { set label "Stop" } } else { # puts "nothing selected to add" } readrc } proc removeit {} { global topstring global bottomstring global runnumber root global leftstring if {[findit] == "1"} { tk_dialog .new "Nothing Selected" "You didn't select anything.\ Please select something to add/remove." "" "0" "Ok" } elseif {$topstring != ""} { set stringis [.right.top.$runnumber.list get $topstring] regsub (.*/) \ [glob -nocomplain "$root/rc.d/rc$runnumber.d/S*$stringis"] "" a exec rm -f "$root/rc.d/rc$runnumber.d/$a" } elseif {$bottomstring != ""} { set stringis [.right.bottom.$runnumber.top.list get $bottomstring] regsub (.*/) \ [glob -nocomplain "$root/rc.d/rc$runnumber.d/K*$stringis"] "" a exec rm -f "$root/rc.d/rc$runnumber.d/$a" } else { # puts "nothing selected that is removable" } readrc } proc readrc {} { global levels root foreach level "$levels" { .right.top.$level.list delete 0 end .right.bottom.$level.top.list delete 0 end } foreach level "$levels" { foreach n [lsort [glob -nocomplain "$root/rc.d/rc$level.d/S*"]] { regsub (.*/...) "$n" "" a .right.top.$level.list insert end "$a" } foreach n [lsort [glob -nocomplain "$root/rc.d/rc$level.d/K*"]] { regsub (.*/...) "$n" "" a .right.bottom.$level.top.list insert end "$a" } } } readrc proc addto {} { global root addtolevel leftselect var global number global top destroy .addwin toplevel .whereat focus .whereat # wm title . "Place $leftselect" frame .whereat.top pack .whereat.top -side top listbox .whereat.top.list -height 10 -width 20 \ -yscrollcommand ".whereat.top.scroll set" scrollbar .whereat.top.scroll -command ".whereat.top.list yview" pack .whereat.top.list -side left pack .whereat.top.scroll -side right -fill y label .whereat.label -text "The Number for $leftselect is:" entry .whereat.entry -textvar number -width 10 pack .whereat.label .whereat.entry -side top button .whereat.add -text "Add" -command {addthis;destroy .whereat} button .whereat.quit -text "Done" -command {destroy .whereat} pack .whereat.add .whereat.quit -side top -fill x if {$top == "0"} { set var "S" } else { set var "K" } loadlevel } proc loadlevel {} { global addtolevel root var .whereat.top.list delete 0 end foreach n [lsort [glob -nocomplain "$root/rc.d/rc$addtolevel.d/$var*"]] { regsub (.*/.) "$n" "" a set b [string range "$a" 0 1] set a [string range "$a" 2 end] .whereat.top.list insert end "$b - $a" } if {[lsort [glob -nocomplain "$root/rc.d/rc$addtolevel.d/$var*"]] == ""} { .whereat.top.list insert end "** Runlevel Empty **" } } proc addthis {} { global root addtolevel leftselect global top number set base "$leftselect" set base [string trimright $base ".init"] if {$top == "0"} { # puts "Adding S$number$leftselect to runlevel $addtolevel" exec ln -sf "$root/rc.d/init.d/$leftselect" \ "$root/rc.d/rc$addtolevel.d/S$number$base" } else { # puts "Adding K$number$leftselect to runlevel $addtolevel" exec ln -sf "$root/rc.d/init.d/$leftselect" \ "$root/rc.d/rc$addtolevel.d/K$number$base" } loadlevel readrc } proc editit {} { global topstring top global bottomstring global runnumber global leftstring levels global addtolevel leftselect findit # If you select the available box only if {$topstring == "" && $bottomstring == "" && $leftstring != ""} { # puts "Can't pick that stuff" whichlevel # if you pick something in the runlevel boxes } elseif {$leftstring == "" && ($topstring != "" || $bottomstring != "")} { editlevel $runnumber # if you didn't pick anything } else { whichlevel } } proc whichlevel {} { global topstring top global bottomstring global runnumber global leftstring levels global addtolevel leftselect toplevel .which focus .which wm title .which "Which Runlevel?" label .which.label -text "Which Runlevel?" frame .which.box pack .which.box -side top frame .which.box.top pack .which.box.top -side top frame .which.box.bottom pack .which.box.bottom -side top label .which.box.top.label -text Start checkbutton .which.box.top.button -onvalue "0" \ -offvalue "1" -variable top label .which.box.bottom.label -text Stop checkbutton .which.box.bottom.button -onvalue "1" \ -offvalue "0" -variable top pack .which.box.top.label .which.box.top.button -side left pack .which.box.bottom.label .which.box.bottom.button -side left pack .which.label -side top frame .which.top pack .which.top -side top set runnumber [lindex "$levels" 0] foreach n "$levels" { frame .which.top.$n pack .which.top.$n -side top label .which.top.$n.label -text "$n" checkbutton .which.top.$n.button -onvalue $n -variable runnumber pack .which.top.$n.label .which.top.$n.button -side left } button .which.done -text "Done" -command {destroy .which;editlevel $runnumber} button .which.cancel -text "Cancel" -command {destroy .which} pack .which.done .which.cancel -fill x -side top } proc editlevel {level} { global topstring top global bottomstring global runnumber var global leftstring levels global addtolevel leftselect change toplevel .edit wm title .edit "Edit Window" focus .edit frame .edit.top pack .edit.top -side top label .edit.top.label -text "Select an entry to change:" listbox .edit.top.list -width 20 -height 14 -yscrollcommand ".edit.top.scroll set" scrollbar .edit.top.scroll -command ".edit.top.list yview" pack .edit.top.label -side top pack .edit.top.list .edit.top.scroll -side left -fill y if {$top == "0"} { set var "S" } else { set var "K" } reloadedit $level label .edit.label -text "Change selected item's number to:" entry .edit.entry -width 4 -textvar change pack .edit.label .edit.entry -side top button .edit.apply -text "Apply" -command {changeit} button .edit.done -text "Cancel" -command {destroy .edit} pack .edit.apply .edit.done -side top -fill x focus .edit.entry } proc reloadedit {level} { global topstring top root global bottomstring global runnumber global leftstring levels global addtolevel leftselect var foreach n [lsort [glob -nocomplain "$root/rc.d/rc$level.d/$var*"]] { regsub (.*/.) "$n" "" a set b [string range "$a" 0 1] set a [string range "$a" 2 end] .edit.top.list insert end "$b - $a" } if {[lsort [glob -nocomplain "$root/rc.d/rc$level.d/$var*"]] == ""} { .edit.top.list insert end "" .edit.top.list insert end " Nothing to edit." .edit.top.list insert end " Press Cancel." } } proc changeit {} { global topstring top root global bottomstring global runnumber var global leftstring levels global addtolevel leftselect change set temp "[.edit.top.list curselection]" if {$temp == ""} { # puts "nothing selected" tk_dialog .new "Nothing Selected" "You must select something to change." "" "0" "Ok" } else { if {![regexp {^[0-9][0-9]$} "$change"]} { puts "error -- $change doesn't match regex" return } set line [.edit.top.list get $temp] # puts " changing $change to $line " set selectnum [string range $line 0 1] set selectwhat [string range $line 5 end] set select "$var$selectnum$selectwhat" # puts $select set base "$selectwhat" set base [string trimright $base ".init"] set linkto [file readlink "$root/rc.d/rc$runnumber.d/$var$selectnum$selectwhat"] exec rm -f "$root/rc.d/rc$runnumber.d/$var$selectnum$selectwhat" exec ln -sf "$linkto" "$root/rc.d/rc$runnumber.d/$var$change$base" destroy .edit } readrc } proc showit {text} { global version toplevel .showit focus .showit wm title .showit "Help" frame .showit.top text .showit.top.text -relief raised -bd 3 -yscrollcommand ".showit.top.scroll set" -font -*-helvetica-bold-r-*-*-12-*-*-*-*-*-*-* scrollbar .showit.top.scroll -command ".showit.top.text yview" pack .showit.top.scroll -side right -fill y pack .showit.top.text -side left pack .showit.top -side top button .showit.button -text "Done" -command {destroy .showit} pack .showit.button -side top -fill both set w .showit focus $w set x [expr [winfo screenwidth $w]/2 - [winfo reqwidth $w]/2 \ - [winfo vrootx [winfo parent $w]]] set y [expr [winfo screenheight $w]/2 - [winfo reqheight $w]/2 \ - [winfo vrooty [winfo parent $w]]] wm geom $w +$x+$y .showit.top.text delete 1.0 end set f [open $text] while {![eof $f]} { .showit.top.text insert end [read $f 1000] } close $f }