diff --git a/scapy/arch/pcapdnet.py b/scapy/arch/pcapdnet.py
old mode 100644
new mode 100755
index 94673d7d284695cfa9569e41d67646301a250f19..c3333b0f28e1106504b6add31d78f9a5a4fdb5ef
--- a/scapy/arch/pcapdnet.py
+++ b/scapy/arch/pcapdnet.py
@@ -16,9 +16,307 @@ from scapy.utils import warning
 from scapy.supersocket import SuperSocket
 from scapy.error import Scapy_Exception
 import scapy.arch
+import socket
 
 
+if conf.use_winpcapy:
+  #mostly code from https://github.com/phaethon/scapy translated to python2.X
+  try:
+    from .winpcapy import *
+    def winpcapy_get_if_list():
+      err = create_string_buffer(PCAP_ERRBUF_SIZE)
+      devs = POINTER(pcap_if_t)()
+      ret = []
+      if pcap_findalldevs(byref(devs), err) < 0:
+        return ret
+      try:
+        p = devs
+        while p:
+          ret.append(p.contents.name.decode('ascii'))
+          p = p.contents.next
+        return ret
+      finally:
+        pcap_freealldevs(devs)
 
+  except OSError as e:
+    if conf.interactive:
+      log_loading.error("Unable to import libpcap library: %s" % e)
+      conf.use_winpcapy = False
+    else:
+      raise
+
+  # From BSD net/bpf.h
+  #BIOCIMMEDIATE=0x80044270
+  BIOCIMMEDIATE=-2147204496
+
+  class PcapTimeoutElapsed(Scapy_Exception):
+      pass
+
+  def get_if_raw_hwaddr(iff):
+    err = create_string_buffer(PCAP_ERRBUF_SIZE)
+    devs = POINTER(pcap_if_t)()
+    ret = "\0\0\0\0\0\0"
+    
+    if pcap_findalldevs(byref(devs), err) < 0:
+      return ret
+    try:
+      p = devs
+      while p:
+        if p.contents.name.endswith(iff):
+          a = p.contents.addresses
+          while a:
+            if hasattr(socket, 'AF_LINK') and a.contents.addr.contents.sa_family == socket.AF_LINK:
+              ap = a.contents.addr
+              val = cast(ap, POINTER(sockaddr_dl))
+              ret = str(val.contents.sdl_data[ val.contents.sdl_nlen : val.contents.sdl_nlen + val.contents.sdl_alen ])
+            a = a.contents.next
+          break
+        p = p.contents.next
+      return ret
+    finally:
+      pcap_freealldevs(devs)
+  def get_if_raw_addr(iff):
+    err = create_string_buffer(PCAP_ERRBUF_SIZE)
+    devs = POINTER(pcap_if_t)()
+    ret = "\0\0\0\0"
+
+    if pcap_findalldevs(byref(devs), err) < 0:
+      return ret
+    try:
+      p = devs
+      while p:
+        if p.contents.name.endswith(iff):
+          a = p.contents.addresses
+          while a:
+            if a.contents.addr.contents.sa_family == socket.AF_INET:
+              ap = a.contents.addr
+              val = cast(ap, POINTER(sockaddr_in))
+              #ret = bytes(val.contents.sin_addr[:4])
+              ret = "".join([chr(x) for x in val.contents.sin_addr[:4]])
+            a = a.contents.next
+          break
+        p = p.contents.next
+      return ret
+    finally:
+      pcap_freealldevs(devs)
+  get_if_list = winpcapy_get_if_list
+  def in6_getifaddr():
+    err = create_string_buffer(PCAP_ERRBUF_SIZE)
+    devs = POINTER(pcap_if_t)()
+    ret = []
+    if pcap_findalldevs(byref(devs), err) < 0:
+      return ret
+    try:
+      p = devs
+      ret = []
+      while p:
+        a = p.contents.addresses
+        while a:
+          if a.contents.addr.contents.sa_family == socket.AF_INET6:
+            ap = a.contents.addr
+            val = cast(ap, POINTER(sockaddr_in6))
+            addr = socket.inet_ntop(socket.AF_INET6, str(val.contents.sin6_addr[:]))
+            scope = scapy.utils6.in6_getscope(addr)
+            ret.append((addr, scope, p.contents.name.decode('ascii')))
+          a = a.contents.next
+        p = p.contents.next
+      return ret
+    finally:
+      pcap_freealldevs(devs)
+
+  from ctypes import POINTER, byref, create_string_buffer
+  class _PcapWrapper_pypcap:
+      def __init__(self, device, snaplen, promisc, to_ms):
+          self.errbuf = create_string_buffer(PCAP_ERRBUF_SIZE)
+          self.iface = create_string_buffer(device)
+          self.pcap = pcap_open_live(self.iface, snaplen, promisc, to_ms, self.errbuf)
+          self.header = POINTER(pcap_pkthdr)()
+          self.pkt_data = POINTER(c_ubyte)()
+          self.bpf_program = bpf_program()
+      def next(self):
+          c = pcap_next_ex(self.pcap, byref(self.header), byref(self.pkt_data))
+          if not c > 0:
+              return
+          ts = self.header.contents.ts.tv_sec
+          pkt = "".join([ chr(i) for i in self.pkt_data[:self.header.contents.len] ])
+          #pkt = bytes(self.pkt_data[:self.header.contents.len])
+          return ts, pkt
+      def datalink(self):
+          return pcap_datalink(self.pcap)
+      def fileno(self):
+          if sys.platform.startswith("win"):
+            error("Cannot get selectable PCAP fd on Windows")
+            return 0
+          return pcap_get_selectable_fd(self.pcap) 
+      def setfilter(self, f):
+          filter_exp = create_string_buffer(f)
+          if pcap_compile(self.pcap, byref(self.bpf_program), filter_exp, 0, -1) == -1:
+            error("Could not compile filter expression %s" % f)
+            return False
+          else:
+            if pcap_setfilter(self.pcap, byref(self.bpf_program)) == -1:
+              error("Could not install filter %s" % f)
+              return False
+          return True
+      def setnonblock(self, i):
+          pcap_setnonblock(self.pcap, i, self.errbuf)
+      def send(self, x):
+          pcap_sendpacket(self.pcap, x, len(x))
+      def close(self):
+          pcap_close(self.pcap)
+  open_pcap = lambda *args,**kargs: _PcapWrapper_pypcap(*args,**kargs)
+  class PcapTimeoutElapsed(Scapy_Exception):
+      pass
+
+  class L2pcapListenSocket(SuperSocket):
+      desc = "read packets at layer 2 using libpcap"
+      def __init__(self, iface = None, type = ETH_P_ALL, promisc=None, filter=None):
+          self.type = type
+          self.outs = None
+          self.iface = iface
+          if iface is None:
+              iface = conf.iface
+          if promisc is None:
+              promisc = conf.sniff_promisc
+          self.promisc = promisc
+          self.ins = open_pcap(iface, 1600, self.promisc, 100)
+          try:
+              ioctl(self.ins.fileno(),BIOCIMMEDIATE,struct.pack("I",1))
+          except:
+              pass
+          if type == ETH_P_ALL: # Do not apply any filter if Ethernet type is given
+              if conf.except_filter:
+                  if filter:
+                      filter = "(%s) and not (%s)" % (filter, conf.except_filter)
+                  else:
+                      filter = "not (%s)" % conf.except_filter
+              if filter:
+                  self.ins.setfilter(filter)
+  
+      def close(self):
+          self.ins.close()
+          
+      def recv(self, x=MTU):
+          ll = self.ins.datalink()
+          if ll in conf.l2types:
+              cls = conf.l2types[ll]
+          else:
+              cls = conf.default_l2
+              warning("Unable to guess datalink type (interface=%s linktype=%i). Using %s" % (self.iface, ll, cls.name))
+  
+          pkt = None
+          while pkt is None:
+              pkt = self.ins.next()
+              if pkt is not None:
+                  ts,pkt = pkt
+              if scapy.arch.WINDOWS and pkt is None:
+                  raise PcapTimeoutElapsed
+          try:
+              pkt = cls(pkt)
+          except KeyboardInterrupt:
+              raise
+          except:
+              if conf.debug_dissector:
+                  raise
+              pkt = conf.raw_layer(pkt)
+          pkt.time = ts
+          return pkt
+  
+      def send(self, x):
+          raise Scapy_Exception("Can't send anything with L2pcapListenSocket")
+  
+
+  conf.L2listen = L2pcapListenSocket
+  class L2pcapSocket(SuperSocket):
+      desc = "read/write packets at layer 2 using only libpcap"
+      def __init__(self, iface = None, type = ETH_P_ALL, filter=None, nofilter=0):
+          if iface is None:
+              iface = conf.iface
+          self.iface = iface
+          self.ins = open_pcap(iface, 1600, 0, 100)
+          try:
+              ioctl(self.ins.fileno(),BIOCIMMEDIATE,struct.pack("I",1))
+          except:
+              pass
+          if nofilter:
+              if type != ETH_P_ALL:  # PF_PACKET stuff. Need to emulate this for pcap
+                  filter = "ether proto %i" % type
+              else:
+                  filter = None
+          else:
+              if conf.except_filter:
+                  if filter:
+                      filter = "(%s) and not (%s)" % (filter, conf.except_filter)
+                  else:
+                      filter = "not (%s)" % conf.except_filter
+              if type != ETH_P_ALL:  # PF_PACKET stuff. Need to emulate this for pcap
+                  if filter:
+                      filter = "(ether proto %i) and (%s)" % (type,filter)
+                  else:
+                      filter = "ether proto %i" % type
+          if filter:
+              self.ins.setfilter(filter)
+      def send(self, x):
+          sx = str(x)
+          if hasattr(x, "sent_time"):
+              x.sent_time = time.time()
+          return self.ins.send(sx)
+
+      def recv(self,x=MTU):
+          ll = self.ins.datalink()
+          if ll in conf.l2types:
+              cls = conf.l2types[ll]
+          else:
+              cls = conf.default_l2
+              warning("Unable to guess datalink type (interface=%s linktype=%i). Using %s" % (self.iface, ll, cls.name))
+  
+          pkt = self.ins.next()
+          if pkt is not None:
+              ts,pkt = pkt
+          if pkt is None:
+              return
+          
+          try:
+              pkt = cls(pkt)
+          except KeyboardInterrupt:
+              raise
+          except:
+              if conf.debug_dissector:
+                  raise
+              pkt = conf.raw_layer(pkt)
+          pkt.time = ts
+          return pkt
+  
+      def nonblock_recv(self):
+          self.ins.setnonblock(1)
+          p = self.recv(MTU)
+          self.ins.setnonblock(0)
+          return p
+  
+      def close(self):
+          if hasattr(self, "ins"):
+              self.ins.close()
+          if hasattr(self, "outs"):
+              self.outs.close()
+
+  class L3pcapSocket(L2pcapSocket):
+      #def __init__(self, iface = None, type = ETH_P_ALL, filter=None, nofilter=0):
+      #    L2pcapSocket.__init__(self, iface, type, filter, nofilter)
+      def recv(self, x = MTU):
+          r = L2pcapSocket.recv(self, x) 
+          if r:
+            return r.payload
+          else:
+            return
+      def send(self, x):
+          cls = conf.l2types[1]
+          sx = str(cls()/x)
+          if hasattr(x, "sent_time"):
+              x.sent_time = time.time()
+          return self.ins.send(sx)
+  conf.L2socket=L2pcapSocket
+  conf.L3socket=L3pcapSocket
+    
 if conf.use_pcap:    
 
 
diff --git a/scapy/arch/windows/__init__.py b/scapy/arch/windows/__init__.py
index 4fbed76cb80fa13377f1148fe960d2b6e3179fbd..c66a933537ca4c50a05187086336c28a3e2674ab 100755
--- a/scapy/arch/windows/__init__.py
+++ b/scapy/arch/windows/__init__.py
@@ -7,19 +7,33 @@
 Customizations needed to support Microsoft Windows.
 """
 
-import os,re,sys,socket,time
+import os,re,sys,socket,time, itertools
+import subprocess as sp
 from glob import glob
 from scapy.config import conf,ConfClass
 from scapy.error import Scapy_Exception,log_loading,log_runtime
-from scapy.utils import atol, inet_aton, inet_ntoa, PcapReader
+from scapy.utils import atol, itom, inet_aton, inet_ntoa, PcapReader
 from scapy.base_classes import Gen, Net, SetGen
 import scapy.plist as plist
 from scapy.sendrecv import debug, srp1
 from scapy.layers.l2 import Ether, ARP
 from scapy.data import MTU, ETHER_BROADCAST, ETH_P_ARP
 
-conf.use_pcap = 1
-conf.use_dnet = 1
+conf.use_pcap = False
+conf.use_dnet = False
+conf.use_winpcapy = True
+
+
+#hot-patching socket for missing variables on Windows
+import socket
+if not hasattr(socket, 'IPPROTO_IPIP'):
+    socket.IPPROTO_IPIP=4
+if not hasattr(socket, 'IPPROTO_AH'):
+    socket.IPPROTO_AH=51
+if not hasattr(socket, 'IPPROTO_ESP'):
+    socket.IPPROTO_ESP=50
+
+
 from scapy.arch import pcapdnet
 from scapy.arch.pcapdnet import *
 
@@ -69,120 +83,137 @@ class WinProgPath(ConfClass):
 
 conf.prog = WinProgPath()
 
-
-
-import _winreg
-
-
-    
 class PcapNameNotFoundError(Scapy_Exception):
     pass    
-
+import platform
+
+def is_interface_valid(iface):
+    if "guid" in iface and iface["guid"]:
+        return True
+    return False
+def get_windows_if_list():
+    if platform.release()=="post2008Server" or platform.release()=="8":
+        # This works only starting from Windows 8/2012 and up. For older Windows another solution is needed
+        ps = sp.Popen(['powershell', 'Get-NetAdapter', '|', 'select Name, InterfaceIndex, InterfaceDescription, InterfaceGuid, MacAddress', '|', 'fl'], stdout = sp.PIPE, universal_newlines = True)
+    else:
+        ps = sp.Popen(['powershell', 'Get-WmiObject', 'Win32_NetworkAdapter', '|', 'select Name, InterfaceIndex, InterfaceDescription, GUID, MacAddress', '|', 'fl'], stdout = sp.PIPE, universal_newlines = True)
+	#no solution implemented for xp
+
+    stdout, stdin = ps.communicate()
+    current_interface = None
+    interface_list = []
+    for i in stdout.split('\n'):
+        if not i.strip():
+            continue
+        if i.find(':')<0:
+            continue
+        name, value = [ j.strip() for j in i.split(':',1) ]
+        if name == 'Name':
+            if current_interface and is_interface_valid(current_interface):
+                interface_list.append(current_interface)
+            current_interface = {}
+            current_interface['name'] = value
+        elif name == 'InterfaceIndex':
+            current_interface['win_index'] = int(value)
+        elif name == 'InterfaceDescription':
+            current_interface['description'] = value
+        elif name == 'InterfaceGuid':
+            current_interface['guid'] = value
+        elif name == 'GUID':
+            current_interface['guid'] = value
+        elif name == 'MacAddress':
+            current_interface['mac'] = ':'.join([ j for j in value.split('-')])    
+    if current_interface and is_interface_valid(current_interface):
+        interface_list.append(current_interface)
+
+    return interface_list
+def get_ip_from_name(ifname, v6=False):
+    ps = sp.Popen(['powershell', 'Get-WmiObject', 'Win32_NetworkAdapterConfiguration', '|', 'select Description, IPAddress', '|', 'fl'], stdout = sp.PIPE, universal_newlines = True)
+    stdout, stdin = ps.communicate()
+    selected=False
+    for i in stdout.split('\n'):
+        if not i.strip():
+            continue
+        if i.find(':')<0:
+            continue
+        name, value = [ j.strip() for j in i.split(':',1) ]
+        if name=="Description" and value.strip()==ifname.strip():
+            selected=True
+        elif selected:
+            if v6:
+                return value.split(",",1)[1].strip('{}').strip()
+            else:
+                return value.split(",",1)[0].strip('{}').strip()
+        
 class NetworkInterface(object):
     """A network interface of your local host"""
     
-    def __init__(self, dnetdict=None):
+    def __init__(self, data=None):
         self.name = None
         self.ip = None
         self.mac = None
         self.pcap_name = None
-        self.win_name = None
-        self.uuid = None
-        self.dnetdict = dnetdict
-        if dnetdict is not None:
-            self.update(dnetdict)
+        self.description = None
+        self.data = data
+        if data is not None:
+            self.update(data)
         
-    def update(self, dnetdict):
+    def update(self, data):
         """Update info about network interface according to given dnet dictionary"""
-        self.name = dnetdict["name"]
+        self.name = data["name"]
+        self.description = data['description']
+        self.win_index = data['win_index']
         # Other attributes are optional
+        self._update_pcapdata()
+
         try:
-            self.ip = socket.inet_ntoa(dnetdict["addr"].ip)
+            self.ip = socket.inet_ntoa(get_if_raw_addr(data['guid']))
         except (KeyError, AttributeError, NameError):
             pass
+
         try:
-            self.mac = dnetdict["link_addr"]
+            if not self.ip:
+                self.ip=get_ip_from_name(data['name'])
+        except (KeyError, AttributeError, NameError) as e:
+            print e
+        try:
+            self.mac = data['mac']
         except KeyError:
             pass
-        self._update_pcapdata()
-    
+
     def _update_pcapdata(self):
-        """Supplement more info from pypcap and the Windows registry"""
-        
-        # XXX: We try eth0 - eth29 by bruteforce and match by IP address, 
-        # because only the IP is available in both pypcap and dnet.
-        # This may not work with unorthodox network configurations and is
-        # slow because we have to walk through the Windows registry.
-        for n in xrange(30):
-            guess = "eth%s" % n
-            win_name = pcapdnet.pcap.ex_name(guess)
-            if win_name.endswith("}"):
-                try:
-                    uuid = win_name[win_name.index("{"):win_name.index("}")+1]
-                    keyname = r"SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\Interfaces\%s" % uuid
-                    try:
-                        key = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE, keyname)
-                    except WindowsError:
-                        log_loading.debug("Couldn't open 'HKEY_LOCAL_MACHINE\\%s' (for guessed pcap iface name '%s')." % (keyname, guess))
-                        continue
-                    try:    
-                        fixed_ip = _winreg.QueryValueEx(key, "IPAddress")[0][0].encode("utf-8")
-                    except (WindowsError, UnicodeDecodeError, IndexError):
-                        fixed_ip = None
-                    try:
-                        dhcp_ip = _winreg.QueryValueEx(key, "DhcpIPAddress")[0].encode("utf-8")
-                    except (WindowsError, UnicodeDecodeError, IndexError):
-                        dhcp_ip = None
-                    # "0.0.0.0" or None means the value is not set (at least not correctly).
-                    # If both fixed_ip and dhcp_ip are set, fixed_ip takes precedence 
-                    if fixed_ip is not None and fixed_ip != "0.0.0.0":
-                        ip = fixed_ip
-                    elif dhcp_ip is not None and dhcp_ip != "0.0.0.0":
-                        ip = dhcp_ip
-                    else:
-                        continue
-                except IOError:
-                    continue
-                else:
-                    if ip == self.ip:
-                        self.pcap_name = guess
-                        self.win_name = win_name
-                        self.uuid = uuid
-                        break
-        else:
-            raise PcapNameNotFoundError
-    
+        for i in winpcapy_get_if_list():
+            if i.endswith(self.data['guid']):
+                self.pcap_name = i
+                return
+
+        raise PcapNameNotFoundError
+
     def __repr__(self):
-        return "<%s: %s %s %s pcap_name=%s win_name=%s>" % (self.__class__.__name__,
-                     self.name, self.ip, self.mac, self.pcap_name, self.win_name)
+        return "<%s: %s %s %s pcap_name=%s description=%s>" % (self.__class__.__name__,
+                     self.name, self.ip, self.mac, repr(self.pcap_name), repr(self.description))
 
-from UserDict import IterableUserDict
+from UserDict import UserDict
 
-class NetworkInterfaceDict(IterableUserDict):
+class NetworkInterfaceDict(UserDict):
     """Store information about network interfaces and convert between names""" 
-    
-    def load_from_dnet(self):
-        """Populate interface table via dnet"""
-        for i in pcapdnet.dnet.intf():
+    def load_from_powershell(self):
+        for i in get_windows_if_list():
             try:
-                # XXX: Only Ethernet for the moment: localhost is not supported by dnet and pcap
-                # We only take interfaces that have an IP address, because the IP
-                # is used for the mapping between dnet and pcap interface names
-                # and this significantly improves Scapy's startup performance
-                if i["name"].startswith("eth") and "addr" in i:
-                    self.data[i["name"]] = NetworkInterface(i)
+                interface = NetworkInterface(i)
+                self.data[interface.name] = interface
             except (KeyError, PcapNameNotFoundError):
                 pass
+        
         if len(self.data) == 0:
-            log_loading.warning("No match between your pcap and dnet network interfaces found. "
+            log_loading.warning("No match between your pcap and windows network interfaces found. "
                                 "You probably won't be able to send packets. "
-                                "Deactivating unneeded interfaces and restarting Scapy might help.")
+                                "Deactivating unneeded interfaces and restarting Scapy might help."
+                                "Check your winpcap and powershell installation, and access rights.")
     
     def pcap_name(self, devname):
-        """Return pypcap device name for given libdnet/Scapy device name
-        
-        This mapping is necessary because pypcap numbers the devices differently."""
-        
+        """Return pcap device name for given Windows device name."""
+
         try:
             pcap_name = self.data[devname].pcap_name
         except KeyError:
@@ -191,30 +222,37 @@ class NetworkInterfaceDict(IterableUserDict):
             return pcap_name
             
     def devname(self, pcap_name):
-        """Return libdnet/Scapy device name for given pypcap device name
-        
-        This mapping is necessary because pypcap numbers the devices differently."""
+        """Return Windows device name for given pcap device name."""
         
         for devname, iface in self.items():
             if iface.pcap_name == pcap_name:
                 return iface.name
         raise ValueError("Unknown pypcap network interface %r" % pcap_name)
     
+    def devname_from_index(self, if_index):
+        """Return interface name from interface index"""
+        for devname, iface in self.items():
+            if iface.win_index == if_index:
+                return iface.name
+        raise ValueError("Unknown network interface index %r" % if_index)
+
     def show(self, resolve_mac=True):
         """Print list of available network interfaces in human readable form"""
-        print "%s  %s  %s" % ("IFACE".ljust(5), "IP".ljust(15), "MAC")
+        print "%s  %s  %s  %s" % ("INDEX".ljust(5), "IFACE".ljust(35), "IP".ljust(15), "MAC")
         for iface_name in sorted(self.data.keys()):
             dev = self.data[iface_name]
-            mac = str(dev.mac)
+            mac = dev.mac
             if resolve_mac:
                 mac = conf.manufdb._resolve_MAC(mac)
-            print "%s  %s  %s" % (str(dev.name).ljust(5), str(dev.ip).ljust(15), mac)     
+            print "%s  %s  %s  %s" % (str(dev.win_index).ljust(5), str(dev.name).ljust(35), str(dev.ip).ljust(15), mac)
             
 ifaces = NetworkInterfaceDict()
-ifaces.load_from_dnet()
+ifaces.load_from_powershell()
 
 def pcap_name(devname):
     """Return pypcap device name for given libdnet/Scapy device name"""  
+    if type(devname) is NetworkInterface:
+        return devname.pcap_name
     try:
         pcap_name = ifaces.pcap_name(devname)
     except ValueError:
@@ -225,6 +263,10 @@ def pcap_name(devname):
 def devname(pcap_name):
     """Return libdnet/Scapy device name for given pypcap device name"""
     return ifaces.devname(pcap_name)
+
+def devname_from_index(if_index):
+    """Return Windows adapter name for given Windows interface index"""
+    return ifaces.devname_from_index(if_index)
     
 def show_interfaces(resolve_mac=True):
     """Print list of available network interfaces"""
@@ -233,99 +275,102 @@ def show_interfaces(resolve_mac=True):
 _orig_open_pcap = pcapdnet.open_pcap
 pcapdnet.open_pcap = lambda iface,*args,**kargs: _orig_open_pcap(pcap_name(iface),*args,**kargs)
 
+_orig_get_if_raw_hwaddr = pcapdnet.get_if_raw_hwaddr
+pcapdnet.get_if_raw_hwaddr = lambda iface,*args,**kargs: (ARPHDR_ETHER,''.join([ chr(int(i, 16)) for i in ifaces[iface].mac.split(':') ]))
+get_if_raw_hwaddr = pcapdnet.get_if_raw_hwaddr
+
+
+def read_routes_7():
+    routes=[]
+    ps = sp.Popen(['powershell', 'Get-WmiObject', 'win32_IP4RouteTable', '|', 'select Name,Mask,NextHop,InterfaceIndex', '|', 'fl'], stdout = sp.PIPE, universal_newlines = True)
+    stdout, stdin = ps.communicate()
+    dest=None
+    mask=None
+    gw=None
+    ifIndex=None
+    for i in stdout.split('\n'):
+        if not i.strip():
+            continue
+        if i.find(':')<0:
+            continue
+        name, value = [ j.strip().lower() for j in i.split(':',1) ]
+        if name=="name":
+            dest=atol(value)
+        elif name=="mask":
+            mask=atol(value)
+        elif name=="nexthop":
+            gw=value
+        elif name=="interfaceindex":
+            ifIndex=value
+            try:
+                iface = devname_from_index(int(ifIndex))
+            except ValueError:
+                continue
+            addr = ifaces[iface].ip
+            routes.append((dest, mask, gw, iface, addr))
+    return routes
+
 def read_routes():
-    ok = 0
+    routes=[]
+    try:
+        if platform.release()=="post2008Server" or platform.release()=="8":
+            routes=read_routes_post2008()
+        else:
+            routes=read_routes_7()
+    except Exception as e:    
+        log_loading.warning("Error building scapy routing table : %s"%str(e))
+    else:
+        if not routes:
+            log_loading.warning("No default IPv4 routes found. Your Windows release may no be supported and you have to enter your routes manually")
+    return routes
+       
+def read_routes_post2008():
     routes = []
-    ip = '(\d+\.\d+\.\d+\.\d+)'
-    # On Vista and Windows 7 the gateway can be IP or 'On-link'.
-    # But the exact 'On-link' string depends on the locale, so we allow any text.
-    gw_pattern = '(.+)'
+    if_index = '(\d+)'
+    dest = '(\d+\.\d+\.\d+\.\d+)/(\d+)'
+    next_hop = '(\d+\.\d+\.\d+\.\d+)'
     metric_pattern = "(\d+)"
     delim = "\s+"        # The columns are separated by whitespace
-    netstat_line = delim.join([ip, ip, gw_pattern, ip, metric_pattern])
+    netstat_line = delim.join([if_index, dest, next_hop, metric_pattern])
     pattern = re.compile(netstat_line)
-    f=os.popen("netstat -rn")
-    for l in f.readlines():
+    # This works only starting from Windows 8/2012 and up. For older Windows another solution is needed
+    ps = sp.Popen(['powershell', 'Get-NetRoute', '-AddressFamily IPV4', '|', 'select ifIndex, DestinationPrefix, NextHop, RouteMetric'], stdout = sp.PIPE, universal_newlines = True)
+    stdout, stdin = ps.communicate()
+    for l in stdout.split('\n'):
         match = re.search(pattern,l)
         if match:
-            dest   = match.group(1)
-            mask   = match.group(2)
-            gw     = match.group(3)
-            netif  = match.group(4)
-            metric = match.group(5)
             try:
-                intf = pcapdnet.dnet.intf().get_dst(pcapdnet.dnet.addr(type=2, addrtxt=dest))
-            except OSError:
-                log_loading.warning("Building Scapy's routing table: Couldn't get outgoing interface for destination %s" % dest)
-                continue               
-            if not intf.has_key("addr"):
-                break
-            addr = str(intf["addr"])
-            addr = addr.split("/")[0]
-            
-            dest = atol(dest)
-            mask = atol(mask)
-            # If the gateway is no IP we assume it's on-link
-            gw_ipmatch = re.search('\d+\.\d+\.\d+\.\d+', gw)
-            if gw_ipmatch:
-                gw = gw_ipmatch.group(0)
-            else:
-                gw = netif
-            routes.append((dest,mask,gw, str(intf["name"]), addr))
-    f.close()
+                iface = devname_from_index(int(match.group(1)))
+                addr = ifaces[iface].ip
+            except:
+                continue
+            dest = atol(match.group(2))
+            mask = itom(int(match.group(3)))
+            gw = match.group(4)
+            # try:
+            #     intf = pcapdnet.dnet.intf().get_dst(pcapdnet.dnet.addr(type=2, addrtxt=dest))
+            # except OSError:
+            #     log_loading.warning("Building Scapy's routing table: Couldn't get outgoing interface for destination %s" % dest)
+            #     continue               
+            routes.append((dest, mask, gw, iface, addr))
     return routes
 
 def read_routes6():
     return []
 
-def getmacbyip(ip, chainCC=0):
-    """Return MAC address corresponding to a given IP address"""
-    if isinstance(ip,Net):
-        ip = iter(ip).next()
-    tmp = map(ord, inet_aton(ip))
-    if (tmp[0] & 0xf0) == 0xe0: # mcast @
-        return "01:00:5e:%.2x:%.2x:%.2x" % (tmp[1]&0x7f,tmp[2],tmp[3])
-    iff,a,gw = conf.route.route(ip)
-    if ( (iff == LOOPBACK_NAME) or (ip == conf.route.get_if_bcast(iff)) ):
-        return "ff:ff:ff:ff:ff:ff"
-    # Windows uses local IP instead of 0.0.0.0 to represent locally reachable addresses
-    ifip = str(pcapdnet.dnet.intf().get(iff)['addr'])
-    if gw != ifip.split('/')[0]:
-        ip = gw
-
-    mac = conf.netcache.arp_cache.get(ip)
-    if mac:
-        return mac
-
-    res = srp1(Ether(dst=ETHER_BROADCAST)/ARP(op="who-has", pdst=ip),
-               type=ETH_P_ARP,
-               iface = iff,
-               timeout=2,
-               verbose=0,
-               chainCC=chainCC,
-               nofilter=1)
-    if res is not None:
-        mac = res.payload.hwsrc
-        conf.netcache.arp_cache[ip] = mac
-        return mac
-    return None
-
-import scapy.layers.l2
-scapy.layers.l2.getmacbyip = getmacbyip
-
-try:
-    import readline
-    console = readline.GetOutputFile()
-except (ImportError, AttributeError):
-    log_loading.info("Could not get readline console. Will not interpret ANSI color codes.") 
-else:
-    conf.readfunc = readline.rl.readline
-    orig_stdout = sys.stdout
-    sys.stdout = console
-
-
-
-
+if conf.interactive_shell != 'ipython':
+    try:
+        __IPYTHON__
+    except NameError:
+        try:
+            import readline
+            console = readline.GetOutputFile()
+        except (ImportError, AttributeError):
+            log_loading.info("Could not get readline console. Will not interpret ANSI color codes.") 
+        else:
+            conf.readfunc = readline.rl.readline
+            orig_stdout = sys.stdout
+            sys.stdout = console
 
 def sndrcv(pks, pkt, timeout = 2, inter = 0, verbose=None, chainCC=0, retry=0, multi=0):
     if not isinstance(pkt, Gen):
@@ -395,7 +440,6 @@ def sndrcv(pks, pkt, timeout = 2, inter = 0, verbose=None, chainCC=0, retry=0, m
                 else:
                     stoptime = 0
                 remaintime = None
-                inmask = [pks.ins.fd]
                 try:
                     try:
                         while 1:
@@ -442,9 +486,9 @@ def sndrcv(pks, pkt, timeout = 2, inter = 0, verbose=None, chainCC=0, retry=0, m
         finally:
             pass
 
-        remain = reduce(list.__add__, hsent.values(), [])
+        remain = list(itertools.chain(*[ i for i in hsent.values() ]))
         if multi:
-            remain = filter(lambda p: not hasattr(p, '_answered'), remain);
+            remain = [ p for p in remain if not hasattr(p, '_answered')]
             
         if autostop and len(remain) > 0 and len(remain) != len(tobesent):
             retry = autostop
@@ -475,7 +519,7 @@ scapy.sendrecv.sndrcv = sndrcv
 def sniff(count=0, store=1, offline=None, prn = None, lfilter=None, L2socket=None, timeout=None, *arg, **karg):
     """Sniff packets
 sniff([count=0,] [prn=None,] [store=1,] [offline=None,] [lfilter=None,] + L2ListenSocket args) -> list of packets
-
+Select interface to sniff by setting conf.iface. Use show_interfaces() to see interface names.
   count: number of packets to capture. 0 means infinity
   store: wether to store sniffed packets or discard them
     prn: function to apply to each packet. If something is returned,
@@ -491,6 +535,7 @@ L2socket: use the provided L2socket
     c = 0
 
     if offline is None:
+        log_runtime.info('Sniffing on %s' % conf.iface)
         if L2socket is None:
             L2socket = conf.L2listen
         s = L2socket(type=ETH_P_ALL, *arg, **karg)
@@ -533,11 +578,17 @@ L2socket: use the provided L2socket
 import scapy.sendrecv
 scapy.sendrecv.sniff = sniff
 
-def get_if_list():
-    return sorted(ifaces.keys())
-        
 def get_working_if():
     try:
-        return devname(pcap.lookupdev())
-    except Exception:
-        return 'lo0'
+        if 'Ethernet' in ifaces and ifaces['Ethernet'].ip != '0.0.0.0':
+            return 'Ethernet'
+        elif 'Wi-Fi' in ifaces and ifaces['Wi-Fi'].ip != '0.0.0.0':
+            return 'Wi-Fi'
+        elif len(ifaces) > 0:
+            return ifaces[list(ifaces.keys())[0]]
+        else:
+            return LOOPBACK_NAME
+    except:
+        return LOOPBACK_NAME
+
+conf.iface = get_working_if()
diff --git a/scapy/config.py b/scapy/config.py
old mode 100644
new mode 100755
index 14d024abfebea7e61a528e826381bd116bd2b847..39d476b69f5ee09336e82ce0083ee4ce04cd8740
--- a/scapy/config.py
+++ b/scapy/config.py
@@ -360,6 +360,7 @@ extensions_paths: path or list of paths where extensions are to be looked for
     emph = Emphasize()
     use_pcap = False
     use_dnet = False
+    use_winpcapy = False
     ipv6_enabled = socket.has_ipv6
     ethertypes = ETHER_TYPES
     protocols = IP_PROTOS