[Git][NTPsec/ntpsec][master] Fixed ntpsnmpd config file parser.
Ian Bruene
gitlab at mg.gitlab.com
Tue Mar 27 21:56:29 UTC 2018
Ian Bruene pushed to branch master at NTPsec / ntpsec
Commits:
5fa48ed0 by Ian Bruene at 2018-03-27T21:55:08Z
Fixed ntpsnmpd config file parser.
- - - - -
3 changed files:
- ntpclients/ntpsnmpd.py
- pylib/util.py
- tests/pylib/test_util.py
Changes:
=====================================
ntpclients/ntpsnmpd.py
=====================================
--- a/ntpclients/ntpsnmpd.py
+++ b/ntpclients/ntpsnmpd.py
@@ -825,7 +825,7 @@ class DataSource(ntp.agentx.MIBControl):
return
def boolify(d, k):
- return True if d[k] == "True" else False
+ return True if d[k][0][1] == "True" else False
optionList = ("notify-mode-change", "notify-stratum-change",
"notify-syspeer-change", "notify-add-association",
"notify-rm-association", "notify-leap-announced",
@@ -849,7 +849,7 @@ class DataSource(ntp.agentx.MIBControl):
elif key == "notify-heartbeat":
self.notifyHeartbeat = boolify(settings, key)
elif key == "heartbeat-interval":
- self.heartbeatInterval = int(settings[key])
+ self.heartbeatInterval = settings[key][0][1]
def misc_storeDynamicSettings(self):
if self.settingsFilename is None:
@@ -1079,19 +1079,11 @@ def loadSettings(filename, optionList):
options = {}
with open(filename) as f:
data = f.read()
- parser = shlex.shlex(data)
- parser.wordchars += "-.:"
- data = [x for x in parser]
- i = 0
- dataLen = len(data)
- while i < dataLen:
- if data[i] in optionList:
- arg = data[i+1]
- if arg[0] in "\"'":
- arg = arg[1:-1]
- options[data[i]] = arg
- i += 1
- i += 1
+ lines = ntp.util.parseConf(data)
+ for line in lines:
+ isQuote, token = line[0]
+ if token in optionList:
+ options[token] = line[1:]
return options
@@ -1152,7 +1144,7 @@ if __name__ == "__main__":
if conf is not None:
for key in conf.keys():
if key == "master-addr": # Address of the SNMP master daemon
- val = conf[key]
+ val = conf[key][0][1]
if ":" in val:
host, port = val.split(":")
port = int(port)
@@ -1160,12 +1152,12 @@ if __name__ == "__main__":
else:
masterAddr = val
elif key == "logfile":
- logfile = conf[key]
+ logfile = conf[key][0][1]
elif key == "ntp-addr": # Address of the NTP daemon
- hostname = conf[key]
+ hostname = conf[key][0][1]
elif key == "loglevel":
errmsg = "Error: loglevel parameter '%s' not a number\n"
- debug = ntp.util.safeargcast(conf[key], int, errmsg, usage)
+ debug = conf[key][0][1]
fileLogging = False
for (switch, val) in options:
=====================================
pylib/util.py
=====================================
--- a/pylib/util.py
+++ b/pylib/util.py
@@ -10,6 +10,7 @@ import os
import re
import shutil
import socket
+import string
import sys
import time
import ntp.ntpc
@@ -157,6 +158,75 @@ def portsplit(hostname):
return (hostname, portsuffix)
+def parseConf(text):
+ inQuote = False
+ quoteStarter = ""
+ lines = []
+ tokens = []
+ current = []
+
+ def pushToken():
+ token = "".join(current)
+ if inQuote is False: # Attempt type conversion
+ try:
+ token = int(token)
+ except ValueError:
+ try:
+ token = float(token)
+ except ValueError:
+ pass
+ wrapper = (inQuote, token)
+ tokens.append(wrapper)
+ current[:] = []
+
+ def pushLine():
+ if len(current) > 0:
+ pushToken()
+ if len(tokens) > 0:
+ lines.append(tokens[:])
+ tokens[:] = []
+
+ i = 0
+ tlen = len(text)
+ while i < tlen:
+ if inQuote is True:
+ if text[i] == quoteStarter: # Ending a text string
+ pushToken()
+ quoteStarter = ""
+ inQuote = False
+ elif text[i] == "\\": # Starting an escape sequence
+ i += 1
+ if text[i] in "'\"n\\":
+ print(repr(text[i]))
+ current.append(eval("\'\\" + text[i] + "\'"))
+ else:
+ current.append(text[i])
+ else:
+ if text[i] == "#": # Comment
+ while (i < tlen) and (text[i] != "\n"):
+ i += 1 # Advance to end of line...
+ i -= 1 # ...and back up so we don't skip the newline
+ elif text[i] in "'\"": # Starting a text string
+ inQuote = True
+ quoteStarter = text[i]
+ if len(current) > 0:
+ pushToken()
+ elif text[i] == "\\": # Linebreak escape
+ i += 1
+ if text[i] != "\n":
+ raise SyntaxError
+ elif text[i] == "\n": # EOL: break the lines
+ pushLine()
+ elif text[i] in string.whitespace:
+ if len(current) > 0:
+ pushToken()
+ else:
+ current.append(text[i])
+ i += 1
+ pushLine()
+ return lines
+
+
def stringfilt(data):
"Pretty print string of space separated numbers"
parts = data.split()
=====================================
tests/pylib/test_util.py
=====================================
--- a/tests/pylib/test_util.py
+++ b/tests/pylib/test_util.py
@@ -151,6 +151,17 @@ class TestPylibUtilMethods(unittest.TestCase):
"[0000:1111:2222:3333:4444:5555:6666:7777]:123"),
("0000:1111:2222:3333:4444:5555:6666:7777", ":123"))
+ def test_parseConf(self):
+ data = """foo bar 42 #blah blah blah
+ "abcd" poi? 3.14
+ "\\"\\n\\\\foo\\c" \\
+ poi! """
+ parsed = ntp.util.parseConf(data)
+ self.assertEqual(parsed,
+ [[(False, "foo"), (False, "bar"), (False, 42)],
+ [(True, "abcd"), (False, "poi?"), (False, 3.14)],
+ [(True, "\"\n\\foo"), (False, "poi!")]])
+
def test_stringfilt(self):
f = ntp.util.stringfilt
View it on GitLab: https://gitlab.com/NTPsec/ntpsec/commit/5fa48ed012d328ffd08a2d256ff37e85052188ac
---
View it on GitLab: https://gitlab.com/NTPsec/ntpsec/commit/5fa48ed012d328ffd08a2d256ff37e85052188ac
You're receiving this email because of your account on gitlab.com.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.ntpsec.org/pipermail/vc/attachments/20180327/f3036b20/attachment.html>
More information about the vc
mailing list