module (..., package.seeall) require("format") require("date") require("fs") require("posix") local ntpdconfig = "/etc/ntpd.conf" local ntpdconfd = "/etc/conf.d/ntpd" local progname = "openntpd" local function config_content( f ) local config = {} config.name = f local conf_file = fs.read_file_as_array ( config.name ) for i=1,table.maxn(conf_file) do local l = conf_file[i] -- Filter out commented lines if not string.find ( l, "^[;#].*" ) then local a,b,c = string.match ( l, "^%s*(%S+)%s*(%S*)%s*(%S*).*$" ) if (a) then if not (config[string.lower(a)]) then config[string.lower(a)] = {} end if (string.lower(a) == "listen") then table.insert (config[string.lower(a)], {value=c} ) else table.insert (config[string.lower(a)], {value=b} ) end end end end return config end local function file_info ( path ) require("posix") local filedetails = posix.stat(path) filedetails["owner"]=rawget((posix.getpasswd(filedetails["uid"])),"name") filedetails["group"]=rawget((posix.getgroup(filedetails["gid"])),"name") filedetails["atimelong"]=os.date("%c", filedetails["atime"]) filedetails["mtimelong"]=os.date("%c", filedetails["mtime"]) filedetails["longname"]=path filedetails["name"]=basename(path) if ( filedetails["size"] > 1073741824 ) then filedetails["size"]=((filedetails["size"]/1073741824) - (filedetails["size"]/1073741824%0.1)) .. "G" elseif ( filedetails["size"] > 1048576 ) then filedetails["size"]=((filedetails["size"]/1048576) - (filedetails["size"]/1048576%0.1)) .. "M" elseif ( filedetails["size"] > 1024 ) then filedetails["size"]=((filedetails["size"]/1024) - (filedetails["size"]/1024%0.1)) .. "k" else filedetails["size"]=filedetails["size"] end return filedetails end local function get_version () local f,error = io.popen("/sbin/apk_version -v -s openntpd") local programversion = f:read("*a") f:close() return programversion end local is_running = function( process ) local statusreport = nil local cmdoutput = {} local cmd, error = io.popen("pidof " .. process ,r) local cmdoutput = string.gsub(cmd:read("*a"), "%s", "") cmd:close() if (cmdoutput ~= "") then statusreport = "Running" else statusreport = "Stopped" end return statusreport end local last_time_change = function() local cmdoutput = {} local cmd, error = io.popen("cat /var/log/messages | grep ntpd | grep adjusting | tail -1" ,r) local cmdoutput1,cmdoutput2 = string.match(cmd:read("*a"), "^%s*(%S+%s+%S+%s+%S+%s+).*: (.*)$") cmd:close() cmdoutput1 = cmdoutput1 or "(Have no data on updates)" cmdoutput2 = cmdoutput2 or "" return cmdoutput1 .. cmdoutput2 end local get_confdopts = function(search) local opts = {} local searchresult = nil local conf_file = fs.read_file_as_array ( ntpdconfd ) for i=1,table.maxn(conf_file) do local l = conf_file[i] -- Filter out commented lines if not string.find ( l, "^[;#].*" ) then local a = string.match ( l, "^%s*(%S+)%=" ) if (a) then if not (opts[string.lower(a)]) then opts[string.lower(a)] = {} end local b = string.gsub(string.match ( l, '^%s*%S+%=(.*)' ), '"', '') for i=1,table.maxn(format.string_to_table(" ", b)) do local option = rawget(format.string_to_table(" ", b),i) table.insert (opts[string.lower(a)], i, option) if (option == search) then searchresult = "Yes" end end end end end return opts,searchresult end -- This function needs: -- addremove = [add|remove] -- file = Path to the file -- variable = e.g. "NTPD_OPTS" -- option = What value to look for to add or remove from the variable. local addremove_opts = function ( addremove, file, variable, option ) if (string.lower(addremove) == "remove" ) then cmdtxt = "/bin/sed -i 's/\\(" .. variable .. ".*\\)" .. option .. "/\\1/' " .. file local cmd, error = io.popen ( cmdtxt ) local cmdoutput = cmd:read("*a") cmd:close() -- Cleanup the variable by removing unneccesary blanks cmdtxt = "/bin/sed -i 's/\\\"\\ /\\\"/g' " .. file cmdtxt = cmdtxt .. ";/bin/sed -i 's/\\ \\\"/\\\"/g' " .. file local cmd, error = io.popen ( cmdtxt ) cmd:close() elseif (string.lower(addremove) == "add" ) then cmdtxt = "/bin/sed -i 's/\\(" .. variable .. ".*\\)\\\"/\\1" .. option .. " \\\"/' " .. file local cmd, error = io.popen ( cmdtxt ) local cmdoutput = cmd:read("*a") cmd:close() end return cmdtxt end local addremove_config = function ( addremove, file, variable ) -- Notes on known/unknown bugs: Remove 'server www.test.org' wont work if config has multiple space/tab e.g. 'server www.test.org' -- FIXME: Make num-space unsensetive. -- FIXME: Can hold multiple rows with same values (when deleting... every equal row is deleted) if (string.lower(addremove) == "delete" ) then cmdtxt = "/bin/sed -i '/" .. variable .. "/d' " .. file local cmd, error = io.popen ( cmdtxt ) local cmdoutput = cmd:read("*a") cmd:close() elseif (string.lower(addremove) == "add" ) then cmdtxt = "/bin/echo '" .. variable .. "' >> " .. file local cmd, error = io.popen ( cmdtxt ) local cmdoutput = cmd:read("*a") cmd:close() end return cmdtxt end -- ################################################################################ -- PUBLIC FUNCTIONS function startstop_service ( self, state ) local status = {} -- This is a strange hack to get the init.d script working local f,err = io.popen("PATH=/usr/local/bin:/usr/bin:/bin:/usr/local/sbin:/usr/sbin:/sbin /etc/init.d/ntpd " .. state) local config = f:read("*a") f:close() if (config == "") then config = "OK!" end status.status = config return status end function modify_config (self, addremove, file, variable, opts) if (file == nil) then file = ntpdconfig end -- See to that only *my* configs are modyfied. if (file == ntpdconfig) or (file == ntpdconfd) then return addremove_config(addremove, file, variable) end end function modify_opts (self, addremove, file, variable, opts) -- See to that only *my* configs are modyfied. if (file == ntpdconfig) or (file == ntpdconfd) then -- See to that the variable/option only exists once if (addremove == "add") then local remove = addremove_opts( "remove", file, variable, opts ) end local remove = addremove_opts( addremove, file, variable, opts ) end end function get () local path = ntpdconfig local config = {} if not (fs.is_file(path)) then local file_result,err = fs.write_file(path, "") end local startstop = is_running ("ntpd") local config = config_content ( path ) if (config["listen"]) then server = "Yes" else server = "No" end config["version"] = string.match(get_version(), "^(%S*)" ) config["date"] = os.date() config["status"] = startstop config["confd"],config["setstimeonstartup"] = get_confdopts("-s") config["listenstate"] = server config["timechanged"] = last_time_change() config["timezone"] = date.what_tz() return config end function get_logfile () local me = {} local cmdtxt = "cat /var/log/messages | grep ntpd" local cmd, error = io.popen(cmdtxt ,r) local cmdoutput = cmd:read("*a") cmd:close() me.value = cmdoutput me.cmd = cmdtxt return me end function get_filecontent (self) local path = ntpdconfig local file_content = get() if (fs.is_file(path)) then local filedetails = file_info(path) local configstatus = get() local file = io.open( path ) local file_result = file:read("*a") or "unknown" file_content["filedetails"]=filedetails file_content["value"]=file_result file:close() else file_content = {value="", errtxt="File is missing, but will be created when you save your new settings",filedetails={longname=path, size="0", mtimelong=""}} end return file_content end function update_filecontent (self, modifications) local path = ntpdconfig local file_result,err = fs.write_file(path, format.dostounix(modifications)) file_content = get_filecontent() return file_content end