How to get MAC address of connected Access point? - python-2.7

I am using Scapy to sniff access point(AP) beacon packets and also getting all AP beacon packets and it's MAC address nearby AP but I need exact MAC address of connected AP then How to sniff only connected AP beacon frame or How to filter connected AP beacon frame using scapy or any alternate idea.
*I am doing it in python 2.7

Assuming the beacon frame is called pkt. pkt.addr1 is the destination MAC, pkt.addr2 is the source MAC and pkt.addr3 is the MAC address of the AP. You could write something like:
from scapy.all import *
def ap_mac(pkt):
if pkt.haslayer(Dot11)
if pkt.type == 0 and pkt.subtype == 8:
print('SSID: '+%s+' MAC:'+%s)(pk.info,pkt.addr3)
else: pass
else: pass
sniff(prn=ap_mac)
to print out all the AP MACs from beacon frames. Then you could use something like:
from scapy.all import *
def sniff_ap(pkt):
if pkt.haslayer(Dot11):
if pkt.add3 == 'xx.xx.xx.xx.xx.xx': ## AP MAC
print(pkt.summary())
else: pass
else: pass
sniff(prn=sniff_ap)
Here is a good link re: beacon frames. https://www.4armed.com/blog/forging-wifi-beacon-frames-using-scapy/

I choose alternate method i.e using command in python program
Code snippet
def Check_connected_ap():
cmd =["nmcli -f BSSID,ACTIVE dev wifi list | awk '$2 ~ /yes/ {print $1}'"]
address = subprocess.Popen(cmd, stdout=subprocess.PIPE, shell=True)
(out, err) = address.communicate()
print out

Related

how do i store the result of ICMP Reply Packet into variable for further use?

I am new to python. As a beginner i am facing a problem that how to store the result of ICMP reply in to variable so that it can be further used in the script in python ? i am using scapy tool along with python for packet creation.
My script is-
#!/usr/bin/python
from scapy.all import *
mac=”3c:97:0e:57:00:f1”
def build_req():
For v in range(2, 4094):
Pkt = sendp(Ether(src=”ff:ff:ff:ff:ff:ff”)/Dot1Q(vlan=v)/ARP(hwsrc=mac, psrc=”192.168.1.108”,pdst=”192.168.1.107”)/ICMP()/Padding(load=”x”*10),iface=”enp0s25”)
If response is None:
Print “vlan id is not found”
Else:
Print “vlan id found’
Sys.exit(1)
Return pkt
{ I want to store the icmp response coming from vlan id in a variable and use that response to send the packet }
You are only sending packets, but not trying to get the response. Scapy documentation tells you how to do so:
https://scapy.readthedocs.io/en/latest/usage.html#send-and-receive-packets-sr

Programmatically Connect to Wifi device python Raspberry

I am working with Raspberry PI 3.
Here I have a task to create Custom GUI to view all the available wifi connections and to connect selected wifi using python.
I am able to get all the Wifi connections through following code.
import subprocess
results = subprocess.check_output(["netsh", "wlan", "show", "network"])
print(results)
results = results.decode("ascii") # needed in python 3
results = results.replace("\r","")
ls = results.split("\n")
ls = ls[4:]
ssids = []
x = 0
while x < len(ls):
if x % 5 == 0:
ssids.append(ls[x])
x += 1
#print(ssids)
But, I am not able to get apis to connect to particular wifi.
Kindly provide me good tutorial for that If any.
Thank you guys

How to use regular expressions to pull something from a terminal output?

I'm attempting to use the re module to look through some terminal output. When I ping a server through terminal using ping -n 1 host (I'm using Windows), it gives me much more information than I want. I want just the amount of time that it takes to get a reply from the server, which in this case is always denoted by an integer and then the letters 'ms'. The error I get explains that the output from the terminal is not a string, so I cannot use regular expressions on it.
from os import system as system_call
import re
def ping(host):
return system_call("ping -n 1 " + host) == 0
host = input("Select a host to ping: ")
regex = re.compile(r"\w\wms")
final_ping = regex.search(ping(host))
print(final_ping)
system returns 0, not anything too useful. However, if we were to do subprocess, we can get teh output, and store it to a variable, out, then we can regex search that.
import subprocess
import re
def ping(host):
ping = subprocess.Popen(["ping", "-n", "1", host], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
out, error = ping.communicate()
return str(out)
host = input("Select a host to ping: ")
final_ping = re.findall("\d+ms",ping(host))[0]
print(final_ping)
Output:
22ms
There are two problems with your code:
Your ping function doesn't return the terminal output. It only returns a bool that reports if the ping succeeded. The ping output is directly forwarded to the terminal that runs the Python script.
Python 3 differentiates between strings (for text, consisting of Unicode codepoints) and bytes (for any data, consisting of bytes). As Python cannot know that ping only outputs ASCII text, you will get a bytes object if you don't specify which text encoding is in use.
It would be the best to use the subprocess module instead of os.system. This is also suggested by the Python documentation.
One possible way is to use subprocess.check_output with the encoding parameter to get a string instead of bytes:
from subprocess import check_output
import sys
def ping(host):
return check_output(
"ping -n 1 " + host,
shell=True,
encoding=sys.getdefaultencoding()
)
...
EDIT: The encoding parameter is only supported since Python 3.6. If you are using an older version, try this:
from subprocess import check_output
import sys
def ping(host):
return check_output(
"ping -n 1 " + host,
shell=True
).decode()
...

socket.gaierror: [Errno -2] Name or service not known No DNS issue

I am trying to learn network scripting via Python. I am trying to extract device names from file "Device_List" and then ssh to the device, executing a command on it and printing the output.
It works fine when I use IP address in the file however it does not if I use a hostname. I tried this on an Ubuntu Trusty as well as Mac OSX.
I get the following error:
FWIP = socket.gethostbyname(name)
socket.gaierror: [Errno -2] Name or service not known
I am able to resolve the hostname on both machines so it is not a DNS issue.
Moreover, if I input the device name from keyboard instead of file, it works fine.
Could you please help me find the issue?
My Code:
import datetime
import paramiko
import socket
import time
import sys
import getpass
with open("Device_List") as dev:
for name in dev:
ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
Uname = raw_input("Username : ")
Pw = getpass.getpass()
print "Connected to ", name
FWIP = socket.gethostbyname(name)
ssh.connect(FWIP, username=Uname,password=Pw)
remote_conn = ssh.invoke_shell()
remote_conn.send("set cli pager off\n")
sys.stdout.flush()
command = raw_input("Enter Command to run : ")
remote_conn.send(command + "\n")
time.sleep(2)
output = remote_conn.recv(65534)
print output
print "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++"
print "Moving Onto Next Device..."
print "Device List Over"
When you iterate over lines in a text file, e.g. your
with open("Device_List") as dev:
for name in dev:
the default I/O subsystem always includes the '\n' line ending character. One reason is that this way you can tell when a text file ends without ending the final line.
Get used to using (e.g.) dev.rstrip() when you don't want that.

Getting list of audio Input devices in Python

How do I get the list of audio input devices in linux using python in this format as hw:0,1 ?
I've tried the following using pyaudio :
def getaudiodevices():
p = pyaudio.PyAudio()
print p.get_default_input_device_info()
for i in range(p.get_device_count()):
print ''#p.get_device_info_by_index(i)
I'm also able to retrieve using "arecord -l" but I need to just get it like
hw:0,1
hw:0,2
I need it in this format. Do you have any suggestions?
Thanks.
If the name stored by the PaDeviceInfo structure is sufficient, then you could just access the 'name' from the dict returned by get_device_info_by_index(), and then perhaps slice the information off the end:
import pyaudio
def getaudiodevices():
p = pyaudio.PyAudio()
for i in range(p.get_device_count()):
print p.get_device_info_by_index(i).get('name')
gives me
HDA Intel HDMI: 0 (hw:0,3)
HDA Intel HDMI: 1 (hw:0,7)
HDA Intel HDMI: 2 (hw:0,8)
HDA Intel PCH: CS4208 Analog (hw:1,0)
HDA Intel PCH: CS4208 Digital (hw:1,1)
hdmi
default
But this doesn't give you what you want with the default devices, the name seems to be stored as "default". In that case, executing "arecord -l" in Python can work, if that's what you're looking for. Of course, you can do the same thing for "aplay -l".
import os
def getaudiodevices():
devices = os.popen("arecord -l")
device_string = devices.read()
device_string = device_string.split("\n")
for line in device_string:
if(line.find("card") != -1):
print "hw:" + line[line.find("card")+5] + "," +\
line[line.find("device")+7]
outputs
hw:1,0