[Git][NTPsec/ntpsec][master] 2 commits: Cleaned up and updated comments

Ian Bruene gitlab at mg.gitlab.com
Mon Oct 30 20:00:59 UTC 2017


Ian Bruene pushed to branch master at NTPsec / ntpsec


Commits:
6eabd1a7 by Ian Bruene at 2017-10-30T14:31:34-05:00
Cleaned up and updated comments

- - - - -
1af3c8fc by Ian Bruene at 2017-10-30T14:59:45-05:00
Added slots for agentx write callbacks

- - - - -


3 changed files:

- ntpclients/ntpsnmpd
- pylib/agentx.py
- tests/pylib/test_agentx.py


Changes:

=====================================
ntpclients/ntpsnmpd
=====================================
--- a/ntpclients/ntpsnmpd
+++ b/ntpclients/ntpsnmpd
@@ -37,187 +37,197 @@ class DataSource:  # This may be broken up in future to be less NTP-specific
         # certain edge cases
         # OIDs are relative from ntp root
         # ntpEntNotifications
-        self.oidTree = {0: (None,
+        self.oidTree = {0: (None, None,
                             # ntpEntNotifModeChange
-                            {1: (None, None),
+                            {1: (None, None, None),
                              # ntpEntNotifStratumChange
-                             2: (None, None),
+                             2: (None, None, None),
                              # ntpEntNotifSyspeerChange
-                             3: (None, None),
+                             3: (None, None, None),
                              # ntpEntNotifAddAssociation
-                             4: (None, None),
+                             4: (None, None, None),
                              # ntpEntNotifRemoveAsociation
-                             5: (None, None),
+                             5: (None, None, None),
                              # ntpEntNotifConfigChanged
-                             6: (None, None),
+                             6: (None, None, None),
                              # ntpEntNotifLeapSecondAnnounced
-                             7: (None, None),
+                             7: (None, None, None),
                              # ntpEntNotifHeartbeat
-                             8: (None, None)}),
+                             8: (None, None, None)}),
                         # ntpSnmpMIBObjects
-                        1: (None,
+                        1: (None, None,
                             # ntpEntInfo
-                            {1: (None,
+                            {1: (None, None,
                                  # ntpNetSoftwareName utf8str
                                  {1: ((lambda oid:
                                        self.cb_systemInfo(oid, "name")),
-                                      None),
+                                      None, None),
                                   # ntpEntSoftwareVersion utf8str
                                   2: ((lambda oid:
                                        self.cb_systemInfo(oid, "version")),
-                                      None),
+                                      None, None),
                                   # ntpEntSoftwareVendor utf8str
                                   3: ((lambda oid:
                                        self.cb_systemInfo(oid, "vendor")),
-                                      None),
+                                      None, None),
                                   # ntpEntSystemType utf8str
                                   4: ((lambda oid:
                                        self.cb_systemInfo(oid, "system")),
-                                      None),
+                                      None, None),
                                   # ntpEntTimeResolution uint32
-                                  5: (self.cb_timeResolution, None),
+                                  5: (self.cb_timeResolution, None, None),
                                   # ntpEntTimePrecision int32
-                                  6: (self.cb_timePrecision, None),
+                                  6: (self.cb_timePrecision, None, None),
                                   # ntpEntTimeDistance DisplayString
-                                  7: (self.cb_timeDistance, None)}),
+                                  7: (self.cb_timeDistance, None, None)}),
                              # ntpEntStatus
-                             2: (None,
+                             2: (None, None,
                                  # ntpEntStatusCurrentMode INTEGER {...}
-                                 {1: (self.cb_statusCurrentMode, None),
+                                 {1: (self.cb_statusCurrentMode, None, None),
                                   # ntpEntStatusStratum NtpStratum
-                                  2: (self.cb_statusStratum, None),
+                                  2: (self.cb_statusStratum, None, None),
                                   # ntpEntStatusActiveRefSourceId
                                   #  uint32 (0..99999)
-                                  3: (self.cb_statusActiveRefSourceID, None),
+                                  3: (self.cb_statusActiveRefSourceID,
+                                      None, None),
                                   # ntpEntStatusActiveRefSourceName utf8str
-                                  4: (self.cb_statusActiveRefSourceName, None),
+                                  4: (self.cb_statusActiveRefSourceName,
+                                      None, None),
                                   # ntpEntStatusActiveOffset DisplayString
-                                  5: (self.cb_statusActiveOffset, None),
+                                  5: (self.cb_statusActiveOffset, None, None),
                                   # ntpEntStatusNumberOfRefSources
                                   #  unit32 (0..99)
-                                  6: (self.cb_statusNumRefSources, None),
+                                  6: (self.cb_statusNumRefSources, None, None),
                                   # ntpEntStatusDispersion DisplayString
-                                  7: (self.cb_statusDispersion, None),
+                                  7: (self.cb_statusDispersion, None, None),
                                   # ntpEntStatusEntityUptime TimeTicks
-                                  8: (self.cb_statusEntityUptime, None),
+                                  8: (self.cb_statusEntityUptime, None, None),
                                   # ntpEntStatusDateTime NtpDateTime
-                                  9: (self.cb_statusDateTime, None),
+                                  9: (self.cb_statusDateTime, None, None),
                                   # ntpEntStatusLeapSecond NtpDateTime
-                                  10: (self.cb_statusLeapSecond, None),
+                                  10: (self.cb_statusLeapSecond, None, None),
                                   # ntpEntStatusLeapSecondDirection
                                   #  int32 (-1..1)
-                                  11: (self.cb_statusLeapSecDirection, None),
+                                  11: (self.cb_statusLeapSecDirection,
+                                       None, None),
                                   # ntpEntStatusInPkts Counter32
-                                  12: (self.cb_statusInPkts, None),
+                                  12: (self.cb_statusInPkts, None, None),
                                   # ntpEntStatusOutPkts Counter32
-                                  13: (self.cb_statusOutPkts, None),
+                                  13: (self.cb_statusOutPkts, None, None),
                                   # ntpEntStatusBadVersion Counter32
-                                  14: (self.cb_statusBadVersion, None),
+                                  14: (self.cb_statusBadVersion, None, None),
                                   # ntpEntStatusProtocolError Counter32
-                                  15: (self.cb_statusProtocolError, None),
+                                  15: (self.cb_statusProtocolError, None, None),
                                   # ntpEntStatusNotifications Counter32
-                                  16: (self.cb_statusNotifications, None),
+                                  16: (self.cb_statusNotifications, None, None),
                                   # ntpEntStatPktModeTable
                                   #  SEQUENCE of NtpEntStatPktModeEntry
-                                  17: (None,
+                                  17: (None, None,
                                        # ntpEntStatPktModeEntry SEQUENCE {...}
-                                       {1: (None,
+                                       {1: (None, None,
                                             # ntpEntStatPktMode INTEGER {...}
-                                            {1: (None, None),
+                                            {1: (None, None, None),
                                              # ntpEntStatPktSent Counter32
-                                             2: (None, None),
+                                             2: (None, None, None),
                                              # ntpEntStatPktRecived Counter32
-                                             3: (None, None)})})}),
+                                             3: (None, None, None)})})}),
                              # ntpAssociation
-                             3: (None,
+                             3: (None, None,
                                  # ntpAssociationTable
                                  #  SEQUENCE of NtpAssociationEntry
-                                 {1: (None,
+                                 {1: (None, None,
                                       # ntpAssociationEntry SEQUENCE {...}
-                                      {1: (None,
+                                      {1: (None, None,
                                            # ntpAssocId uint32 (1..99999)
-                                           {1: (self.cb_assocID, None),
+                                           {1: (self.cb_assocID, None, None),
                                             # ntpAssocName utf8str
-                                            2: (self.cb_assocName, None),
+                                            2: (self.cb_assocName, None, None),
                                             # ntpAssocRefId DisplayString
-                                            3: (self.cb_assocRefID, None),
+                                            3: (self.cb_assocRefID, None, None),
                                             # ntpAssocAddressType
                                             #  InetAddressType
-                                            4: (self.cb_assocAddrType, None),
+                                            4: (self.cb_assocAddrType,
+                                                None, None),
                                             # ntpAssocAddress
                                             #  InetAddress SIZE (4|8|16|20)
-                                            5: (self.cb_assocAddr, None),
+                                            5: (self.cb_assocAddr, None, None),
                                             # ntpAssocOffset DisplayString
-                                            6: (self.cb_assocOffset, None),
+                                            6: (self.cb_assocOffset,
+                                                None, None),
                                             # ntpAssocStratum NtpStratum
-                                            7: (self.cb_assocStratum, None),
+                                            7: (self.cb_assocStratum,
+                                                None, None),
                                             # ntpAssocStatusJitter DisplayString
                                             8: (self.cb_assocStatusJitter,
-                                                None),
+                                                None, None),
                                             # ntpAssocStatusDelay DisplayString
-                                            9: (self.cb_assocStatusDelay, None),
+                                            9: (self.cb_assocStatusDelay,
+                                                None, None),
                                             # ntpAssocStatusDispersion
                                             #  DisplayString
                                             10: (self.cb_assocStatusDisp,
-                                                 None)})}),
+                                                 None, None)})}),
                                   # ntpAssociationStatisticsTable
                                   #  SEQUENCE of ntpAssociationStatisticsEntry
-                                  2: (None,
+                                  2: (None, None,
                                       # ntpAssociationStatisticsEntry
                                       #  SEQUENCE {...}
-                                      {1: (None,
+                                      {1: (None, None,
                                            # ntpAssocStatInPkts Counter32
-                                           {1: (self.cb_assocStatInPkts, None),
+                                           {1: (self.cb_assocStatInPkts,
+                                                None, None),
                                             # ntpAssocStatOutPkts Counter32
                                             2: (self.cb_assocStatOutPkts,
-                                                None),
+                                                None, None),
                                             # ntpAssocStatProtocolError
                                             #  Counter32
                                             3: (self.cb_assocStatProtoErr,
-                                                None)})})}),
+                                                None, None)})})}),
                              # ntpEntControl
-                             4: (None,
+                             4: (None, None,
                                  # ntpEntHeartbeatInterval unit32
-                                 {1: (self.cb_entHeartbeatInterval, None),
+                                 {1: (self.cb_entHeartbeatInterval,
+                                      None, None),
                                   # ntpEntNotifBits BITS {...}
-                                  2: (self.cb_entNotifBits, None)}),
+                                  2: (self.cb_entNotifBits, None, None)}),
                              # ntpEntNotifObjects
-                             5: (None,
+                             5: (None, None,
                                  # ntpEntNotifMessage utf8str
-                                 {1: (self.cb_entNotifMessage, None)})}),
+                                 {1: (self.cb_entNotifMessage, None, None)})}),
                         # ntpEntConformance
-                        2: (None,
+                        2: (None, None,
                             # ntpEntCompliances
-                            {1: (None,
+                            {1: (None, None,
                                  # ntpEntNTPCompliance
-                                 {1: (None, None),
+                                 {1: (None, None, None),
                                   # ntpEntSNTPCompliance
-                                  2: (None, None)}),
+                                  2: (None, None, None)}),
                              # ntpEntGroups
-                             2: (None,
+                             2: (None, None,
                                  # ntpEntObjectsGroup1 OBJECTS {...}
-                                 {1: (None, None),
+                                 {1: (None, None, None),
                                   # ntpEntObjectsGroup2 OBJECTS {...}
-                                  2: (None, None),
+                                  2: (None, None, None),
                                   # ntpEntNotifGroup NOTIFICATIONS {...}
-                                  3: (None, None)})})}
+                                  3: (None, None, None)})})}
         self.oidList = ntp.agentx.mibTree2List(self.oidTree, ntpRootOID)
 
     def getOID(self, oid, acceptNext=False):
         "Get the requested OID, or the next lexographical OID"
         for node in self.oidList:
-            if node[0] is None:
+            if node[0] is None:  # No read callback
                 continue  # skip over not yet implemented OIDs
-            if (node[1] == oid):
+            if (node[2] == oid):
                 return node  # (callback, oid)
-            elif (node[1] > oid) and (acceptNext is True):
+            elif (node[2] > oid) and (acceptNext is True):
                 return node
         # Nothing in the list
         return (None, None)
 
     def getNextOID(self, oid):
+        "Get the next lexographical OID"
         for pos in range(len(self.oidList)):
-            callback, current = self.oidList[pos]
+            read_callback, write_callback, current = self.oidList[pos]
             if callback is None:
                 continue  # skip over not yet implemented OIDs
             if current <= oid:
@@ -225,19 +235,20 @@ class DataSource:  # This may be broken up in future to be less NTP-specific
             else:
                 return self.oidList[pos]
         # Nothing after the supplied oid
-        return (None, None)
+        return (None, None, None)
 
     def getOIDsInRange(self, oidrange, firstOnly=False):
+        "Get a list of every (optionally the first) OID in a range"
         oids = []
         for node in self.oidList:
-            if node[0] is None:  # No callback
+            if node[0] is None:  # No read callback
                 continue  # skip over not yet implemented OIDs
-            elif node[1] > oidrange.start:  # Past the start, in the body
-                if (oidrange.end is not None) and (node[1] >= oidrange.end):
+            elif node[2] > oidrange.start:  # Past the start, in the body
+                if (oidrange.end is not None) and (node[2] >= oidrange.end):
                     break  # Past the end of a bounded range
                 else:
                     oids.append(node)  # Found a match
-            elif (node[1].subids == oidrange.start.subids) and \
+            elif (node[2].subids == oidrange.start.subids) and \
                  (oidrange.start.include is True):
                 oids.append(node)  # Inclusive search and a match at the start
             else:
@@ -246,8 +257,10 @@ class DataSource:  # This may be broken up in future to be less NTP-specific
                 break
         return oids
 
+    # =============================================================
     # Data retrevial callbacks start here
     # comment divider lines represent not yet implemented callbacks
+    # =============================================================
 
     #########################
 
@@ -470,21 +483,20 @@ class PacketControl:
         dolog("Sent open packet\n", 1)
         response = self.waitForResponse(openpkt, True)
         self.sessionID = response.sessionID
-        # Register the tree, just random crap for testing right now
-        fooregister = ntp.agentx.RegisterPDU(True, self.sessionID, 1, 1,
-                                             self.timeout, 1, ntpRootOID)
-        self.sendPacket(fooregister, False)
-        dolog("Sent register\n", 1)
-        response = self.waitForResponse(fooregister, True)
+        # Register the tree
+        register = ntp.agentx.RegisterPDU(True, self.sessionID, 1, 1,
+                                          self.timeout, 1, ntpRootOID)
+        self.sendPacket(register, False)
+        dolog("Sent registration\n", 1)
+        response = self.waitForResponse(register, True)
 
     def waitForResponse(self, opkt, ignoreSID=False):
+        "Wait for a response to a specific packet, dropping everything else"
         while True:
             self.packetEater()
             while len(self.recievedPackets) > 0:
                 packet = self.recievedPackets.pop(0)
                 dolog("Waiting, got packet: " + repr(packet) + "\n\n", 3)
-                # This will drop anything that is not the response
-                #  but if this method is being called we don't care
                 if packet.__class__ != ntp.agentx.ResponsePDU:
                     continue
                 haveit = (opkt.transactionID == packet.transactionID) and \
@@ -496,6 +508,7 @@ class PacketControl:
             time.sleep(self.spinGap)
 
     def packetEater(self):
+        "Slurps data from the input buffer and tries to parse packets from it"
         self.pollSocket()
         while True:
             datalen = len(self.recievedData)
@@ -511,7 +524,7 @@ class PacketControl:
             except (ax.ParseVersionError, ax.ParsePDUTypeError,
                     ax.ParseError) as e:
                 if e.header["type"] != ax.PDU_RESPONSE:
-                    # Response errors are silently dropped
+                    # Response errors are silently dropped, per RFC
                     # Everything else sends an error response
                     resp = ax.ResponsePDU(e.header["flags"]["bigEndian"],
                                           e.header["session_id"],
@@ -520,6 +533,8 @@ class PacketControl:
                                           0, ax.RSPERR_PARSE_ERROR, 0)
                     self.sendPacket(resp, False)
                 # *Hopefully* the packet length was correct.....
+                #  if not, all packets will be scrambled. Maybe dump the
+                #  whole buffer if too many failures in a row?
                 self.receivedData = e.remainingData
 
     def sendPacket(self, packet, expectsReply):
@@ -533,7 +548,7 @@ class PacketControl:
             self.packetLog[index] = packet
 
     def pollSocket(self):
-        "Reads all currently available data from sock, non-blocking"
+        "Reads all currently available data from the socket, non-blocking"
         data = ""
         while True:
             tmp = select.select([self.socket], [], [], 0)[0]
@@ -548,17 +563,19 @@ class PacketControl:
                 break
         self.recievedData += data
 
+    # ==========================
     # Packet handlers start here
+    # ==========================
 
     def handle_GetPDU(self, packet):
         binds = []
         for oidr in packet.oidranges:
             target = oidr.start
-            callback, oid = self.database.getOID(target, False)
-            if (oid != target) or (callback is None):
+            r_clbk, w_clbk, oid = self.database.getOID(target, False)
+            if (oid != target) or (r_clbk is None):
                 binds.append(ax.Varbind(ax.VALUE_NO_SUCH_OBJECT, target))
             else:
-                binds.append(callback(oid))
+                binds.append(r_clbk(oid))
             # There should also be a situation that leads to noSuchInstance
             #  but I do not understand the requirements for that
         # Need to implement genError
@@ -573,8 +590,8 @@ class PacketControl:
             if len(oids) == 0:  # Nothing found
                 binds.append(ax.Varbind(ax.VALUE_END_OF_MIB_VIEW, oidr.start))
             else:
-                callback, oid = oids[0]
-                binds.append(callback(oid))
+                r_clbk, w_clbk, oid = oids[0]
+                binds.append(r_clbk(oid))
         # Need to implement genError
         resp = ax.ResponsePDU(True, self.sessionID, packet.transactionID,
                               packet.packetID, 0, ax.ERR_NOERROR, 0, binds)
@@ -590,8 +607,8 @@ class PacketControl:
             if len(oids) == 0:  # Nothing found
                 binds.append(ax.Varbind(ax.VALUE_END_OF_MIB_VIEW, oidr.start))
             else:
-                callback, oid = oids[0]
-                binds.append(callback(oid))
+                r_clbk, w_clbk, oid = oids[0]
+                binds.append(r_clbk(oid))
             binds.append(varbind)
         # Handle repeaters
         for oidr in repeats:
@@ -599,8 +616,8 @@ class PacketControl:
             if len(oids) == 0:  # Nothing found
                 binds.append(ax.Varbind(ax.VALUE_END_OF_MIB_VIEW, oidr.start))
             else:
-                for callback, oid in oids[:packet.maxReps]:
-                    binds.append(callback(oid))
+                for r_clbk, w_clbk, oid in oids[:packet.maxReps]:
+                    binds.append(r_clbk(oid))
         resp = ax.ResponsePDU(True, self.sessionID, packet.transactionID,
                               packet.packetID, 0, ax.ERR_NOERROR, 0, binds)
         self.sendPacket(resp, False)


=====================================
pylib/agentx.py
=====================================
--- a/pylib/agentx.py
+++ b/pylib/agentx.py
@@ -1308,8 +1308,10 @@ def mibTree2List(mibtree, currentPath=()):
     branches = list(mibtree.keys())
     branches.sort()
     for branch in branches:
-        callback, tree = mibtree[branch]
-        paths.append((callback, OID(currentPath + (branch,))))
+        read_callback, write_callback, tree = mibtree[branch]
+        paths.append((read_callback,
+                      write_callback,
+                      OID(currentPath + (branch,))))
         branchPath = currentPath + (branch,)
         paths += mibTree2List(tree, branchPath)
     return tuple(paths)
@@ -1317,9 +1319,10 @@ def mibTree2List(mibtree, currentPath=()):
 
 def mibList2Tree(miblist, rootPath=()):
     "Takes a list of OIDs and inflates it into a tree"
+    # Tree node format: (read callback, write callback, sub-nodes)
     tree = {}
     for mibnode in miblist:
-        callback, oid = mibnode[0], mibnode[1].subids
+        read_clbk, write_clbk, oid = mibnode[0], mibnode[1], mibnode[2].subids
         rootlen = len(rootPath)
         if oid[:rootlen] != rootPath:  # OID not decended from the root, bail
             raise ValueError("Node %s does not have root %s" %
@@ -1331,10 +1334,10 @@ def mibList2Tree(miblist, rootPath=()):
         while oidPos < oidSize:
             subid = oid[oidPos]
             if subid not in branch:  # First time at this position
-                branch[subid] = (callback, None)  # might be a leaf
-            elif branch[subid][1] is None:  # It isn't a leaf
-                branch[subid] = (branch[subid][0], {})
-            branch = branch[subid][1]
+                branch[subid] = (read_clbk, write_clbk, None)  # might be a leaf
+            elif branch[subid][2] is None:  # It isn't a leaf
+                branch[subid] = (branch[subid][0], branch[subid][1], {})
+            branch = branch[subid][2]
             oidPos += 1
     return tree
 


=====================================
tests/pylib/test_agentx.py
=====================================
--- a/tests/pylib/test_agentx.py
+++ b/tests/pylib/test_agentx.py
@@ -2507,35 +2507,41 @@ class TestNtpclientsNtpsnmpd(unittest.TestCase):
         # Test empty tree
         self.assertEqual(f({}), ())
         # Test flat tree
-        self.assertEqual(f({0: (None, None), 1: (None, None),
-                            3: (None, None), 4: (None, None)}),
-                         ((None, x.OID((0,))), (None, x.OID((1,))),
-                          (None, x.OID((3,))), (None, x.OID((4,)))))
+        self.assertEqual(f({0: (None, None, None), 1: (None, None, None),
+                            3: (None, None, None), 4: (None, None, None)}),
+                         ((None, None, x.OID((0,))),
+                          (None, None, x.OID((1,))),
+                          (None, None, x.OID((3,))),
+                          (None, None, x.OID((4,)))))
         # Test flat tree with root path
-        self.assertEqual(f({0: (None, None), 1: (None, None),
-                            3: (None, None), 4: (None, None)},
+        self.assertEqual(f({0: (None, None, None), 1: (None, None, None),
+                            3: (None, None, None), 4: (None, None, None)},
                            (42, 23)),
-                         ((None, x.OID((42, 23, 0))),
-                          (None, x.OID((42, 23, 1))),
-                          (None, x.OID((42, 23, 3))),
-                          (None, x.OID((42, 23, 4)))))
+                         ((None, None, x.OID((42, 23, 0))),
+                          (None, None, x.OID((42, 23, 1))),
+                          (None, None, x.OID((42, 23, 3))),
+                          (None, None, x.OID((42, 23, 4)))))
         # Test nested tree
-        self.assertEqual(f({0: (None, None),
-                            2: (None,
-                                {0: (None, None), 1: (None, None)}),
-                            3: (None,
-                                {5: (None,
-                                     {0: (None, None), 2: (None, None)}),
-                                 6: (None, None)}),
-                            4: (None, None)}),
-                         ((None, x.OID((0,))),
-                          (None, x.OID((2,))),
-                          (None, x.OID((2, 0))), (None, x.OID((2, 1))),
-                          (None, x.OID((3,))),
-                          (None, x.OID((3, 5))),
-                          (None, x.OID((3, 5, 0))), (None, x.OID((3, 5, 2))),
-                          (None, x.OID((3, 6))),
-                          (None, x.OID((4,)))))
+        self.assertEqual(f({0: (None, None, None),
+                            2: (None, None,
+                                {0: (None, None, None),
+                                 1: (None, None, None)}),
+                            3: (None, None,
+                                {5: (None, None,
+                                     {0: (None, None, None),
+                                      2: (None, None, None)}),
+                                 6: (None, None, None)}),
+                            4: (None, None, None)}),
+                         ((None, None, x.OID((0,))),
+                          (None, None, x.OID((2,))),
+                          (None, None, x.OID((2, 0))),
+                          (None, None, x.OID((2, 1))),
+                          (None, None, x.OID((3,))),
+                          (None, None, x.OID((3, 5))),
+                          (None, None, x.OID((3, 5, 0))),
+                          (None, None, x.OID((3, 5, 2))),
+                          (None, None, x.OID((3, 6))),
+                          (None, None, x.OID((4,)))))
 
     def test_mibList2Tree(self):
         x = ntp.agentx
@@ -2544,35 +2550,40 @@ class TestNtpclientsNtpsnmpd(unittest.TestCase):
         # Test empty tree
         self.assertEqual(f(tuple()), {})
         # Test flat tree
-        self.assertEqual(f(((None, x.OID((0,))), (None, x.OID((1,))),
-                            (None, x.OID((3,))), (None, x.OID((4,))))),
-                         {0: (None, None), 1: (None, None),
-                          3: (None, None), 4: (None, None)})
+        self.assertEqual(f(((None, None, x.OID((0,))),
+                            (None, None, x.OID((1,))),
+                            (None, None, x.OID((3,))),
+                            (None, None, x.OID((4,))))),
+                         {0: (None, None, None), 1: (None, None, None),
+                          3: (None, None, None), 4: (None, None, None)})
         # Test flat tree with root path
-        self.assertEqual(f(((None, x.OID((42, 23, 0))),
-                            (None, x.OID((42, 23, 1))),
-                            (None, x.OID((42, 23, 3))),
-                            (None, x.OID((42, 23, 4)))),
+        self.assertEqual(f(((None, None, x.OID((42, 23, 0))),
+                            (None, None, x.OID((42, 23, 1))),
+                            (None, None, x.OID((42, 23, 3))),
+                            (None, None, x.OID((42, 23, 4)))),
                            (42, 23)),
-                         {0: (None, None), 1: (None, None),
-                          3: (None, None), 4: (None, None)})
+                         {0: (None, None, None), 1: (None, None, None),
+                          3: (None, None, None), 4: (None, None, None)})
         # Test nested tree
-        self.assertEqual(f(((None, x.OID((0,))),
-                            (None, x.OID((2,))),
-                            (None, x.OID((2, 0))), (None, x.OID((2, 1))),
-                            (None, x.OID((3,))),
-                            (None, x.OID((3, 5))),
-                            (None, x.OID((3, 5, 0))), (None, x.OID((3, 5, 2))),
-                            (None, x.OID((3, 6))),
-                            (None, x.OID((4,))))),
-                         {0: (None, None),
-                          2: (None,
-                              {0: (None, None), 1: (None, None)}),
-                          3: (None,
-                              {5: (None,
-                                   {0: (None, None), 2: (None, None)}),
-                               6: (None, None)}),
-                          4: (None, None)})
+        self.assertEqual(f(((None, None, x.OID((0,))),
+                            (None, None, x.OID((2,))),
+                            (None, None, x.OID((2, 0))),
+                            (None, None, x.OID((2, 1))),
+                            (None, None, x.OID((3,))),
+                            (None, None, x.OID((3, 5))),
+                            (None, None, x.OID((3, 5, 0))),
+                            (None, None, x.OID((3, 5, 2))),
+                            (None, None, x.OID((3, 6))),
+                            (None, None, x.OID((4,))))),
+                         {0: (None, None, None),
+                          2: (None, None,
+                              {0: (None, None, None), 1: (None, None, None)}),
+                          3: (None, None,
+                              {5: (None, None,
+                                   {0: (None, None, None),
+                                    2: (None, None, None)}),
+                               6: (None, None, None)}),
+                          4: (None, None, None)})
 
 
 if __name__ == "__main__":



View it on GitLab: https://gitlab.com/NTPsec/ntpsec/compare/ca83d4ecde8e47a178bc9713ce01ec48cbcaa4f5...1af3c8fc5b77671142dad048f7024e819344c058

---
View it on GitLab: https://gitlab.com/NTPsec/ntpsec/compare/ca83d4ecde8e47a178bc9713ce01ec48cbcaa4f5...1af3c8fc5b77671142dad048f7024e819344c058
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/20171030/ad171017/attachment.html>


More information about the vc mailing list