Skip to content

Commit 51f4214

Browse files
ldxldx
authored andcommitted
Only check xtables major version once.
1 parent 42babcd commit 51f4214

File tree

4 files changed

+29
-56
lines changed

4 files changed

+29
-56
lines changed

iptc/ip4tc.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ class IPTCError(Exception):
8383
"""
8484

8585

86-
_libiptc = find_library("ip4tc", "iptc") # old iptables versions use iptc
86+
_libiptc, _ = find_library("ip4tc", "iptc") # old iptables versions use iptc
8787

8888

8989
class iptc(object):

iptc/ip6tc.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ class ip6t_entry(ct.Structure):
8181
("elems", ct.c_ubyte * 0)] # the matches then the target
8282

8383

84-
_libiptc = find_library("ip6tc", "iptc") # old iptables versions use iptc
84+
_libiptc, _ = find_library("ip6tc", "iptc") # old iptables versions use iptc
8585

8686

8787
class ip6tc(object):

iptc/util.py

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import re
12
import ctypes
23
import ctypes.util
34
from subprocess import Popen, PIPE
@@ -63,4 +64,11 @@ def find_library(*names):
6364
lib = _find_library(name)
6465
if lib is not None:
6566
break
66-
return lib
67+
if lib:
68+
major = 0
69+
m = re.match("libxtables.so.(\d+)", lib._name)
70+
if m:
71+
major = int(m.group(1))
72+
return lib, major
73+
else:
74+
return None, None

iptc/xtables.py

Lines changed: 18 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# -*- coding: utf-8 -*-
22

33
import ctypes as ct
4-
import re
4+
import sys
55
import weakref
66
import version
77

@@ -684,13 +684,13 @@ class XTablesError(Exception):
684684
"""Raised when an xtables call fails for some reason."""
685685

686686

687-
_libc = find_library("c")
687+
_libc, _ = find_library("c")
688688
_optind = ct.c_long.in_dll(_libc, "optind")
689689
_optarg = ct.c_char_p.in_dll(_libc, "optarg")
690690

691-
_lib_xtables = find_library("xtables")
691+
_lib_xtables, _xtables_version = find_library("xtables")
692692

693-
_lib_xtwrapper = find_library("xtwrapper")
693+
_lib_xtwrapper, _ = find_library("xtwrapper")
694694

695695
_throw = _lib_xtwrapper.throw_exception
696696

@@ -783,6 +783,16 @@ def _xtinit(self, proto):
783783
self._xt_globals.opts = None
784784
self._xt_globals.exit_err = _xt_exit
785785

786+
thismodule = sys.modules[__name__]
787+
matchname = "_xtables_match_v%d" % (_xtables_version)
788+
targetname = "_xtables_target_v%d" % (_xtables_version)
789+
try:
790+
self._match_struct = getattr(thismodule, matchname)
791+
self._target_struct = getattr(thismodule, targetname)
792+
except:
793+
raise XTablesError("unknown xtables version %d" %
794+
(_xtables_version))
795+
786796
self._loaded_exts = []
787797

788798
# make sure we're initializing with clean state
@@ -828,15 +838,6 @@ def _restore_globals(self):
828838
xtables._xtables_targets.value = self._targets
829839
xtables._xtables_pending_targets.value = self._pending_targets
830840

831-
@classmethod
832-
def _get_xtables_version(cls, version):
833-
version_match = re.match("libxtables.so.(\d+)", version)
834-
835-
if version_match:
836-
return int(version_match.group(1))
837-
else:
838-
raise RuntimeError("Xtables returned unknown version format")
839-
840841
def _check_extname(self, name):
841842
if name in ["", "ACCEPT", "DROP", "QUEUE", "RETURN"]:
842843
name = "standard"
@@ -893,26 +894,8 @@ def find_match(self, name):
893894
if not match:
894895
return match
895896
self._loaded(name)
896-
version = xtables._get_xtables_version(match.contents.v1.version)
897-
898-
if 1 == version:
899-
return ct.cast(match, ct.POINTER(_xtables_match_v1))
900-
elif 2 == version:
901-
return ct.cast(match, ct.POINTER(_xtables_match_v2))
902-
elif 4 == version:
903-
return ct.cast(match, ct.POINTER(_xtables_match_v4))
904-
elif 5 == version:
905-
return ct.cast(match, ct.POINTER(_xtables_match_v5))
906-
elif 6 == version:
907-
return ct.cast(match, ct.POINTER(_xtables_match_v6))
908-
elif 7 == version:
909-
return ct.cast(match, ct.POINTER(_xtables_match_v7))
910-
elif 9 == version:
911-
return ct.cast(match, ct.POINTER(_xtables_match_v9))
912-
elif 10 <= version:
913-
return ct.cast(match, ct.POINTER(_xtables_match_v10))
914-
else:
915-
raise Exception("Match object casting failed")
897+
898+
return ct.cast(match, ct.POINTER(self._match_struct))
916899

917900
@preserve_globals
918901
def find_target(self, name):
@@ -924,26 +907,8 @@ def find_target(self, name):
924907
if not target:
925908
return target
926909
self._loaded(name)
927-
version = xtables._get_xtables_version(target.contents.v1.version)
928-
929-
if 1 == version:
930-
return ct.cast(target, ct.POINTER(_xtables_target_v1))
931-
elif 2 == version:
932-
return ct.cast(target, ct.POINTER(_xtables_target_v2))
933-
elif 4 == version:
934-
return ct.cast(target, ct.POINTER(_xtables_target_v4))
935-
elif 5 == version:
936-
return ct.cast(target, ct.POINTER(_xtables_target_v5))
937-
elif 6 == version:
938-
return ct.cast(target, ct.POINTER(_xtables_target_v6))
939-
elif 7 == version:
940-
return ct.cast(target, ct.POINTER(_xtables_target_v7))
941-
elif 9 == version:
942-
return ct.cast(target, ct.POINTER(_xtables_target_v9))
943-
elif 10 <= version:
944-
return ct.cast(target, ct.POINTER(_xtables_target_v10))
945-
else:
946-
raise Exception("Target object casting failed")
910+
911+
return ct.cast(target, ct.POINTER(self._target_struct))
947912

948913
@preserve_globals
949914
def save(self, module, ip, ptr):

0 commit comments

Comments
 (0)