Ho fana ka boiketsetso ho Yealink T19 + buka ea liaterese e matla

Ha ke tlil'o sebeletsa k'hamphani ena, ke ne ke se ke ntse ke e-na le boitsebiso bo itseng ba lisebelisoa tsa IP, li-server tse 'maloa tse nang le asterisk le patch ka mokhoa oa FreeBPX. Ntle le moo, analogue PBX Samsung IDCS500 e ne e sebetsa ka mokhoa o ts'oanang mme, ka kakaretso, e ne e le sistimi e kholo ea puisano k'hamphaning; IP telephony e ne e sebetsa feela bakeng sa lefapha la thekiso. 'Me ntho e' ngoe le e 'ngoe e ka be e ile ea tsoela pele ho pheha ka tsela ena, empa ka letsatsi le leng ho ile ha fanoa ka taelo ea hore motho e mong le e mong a fetisetsoe ho IP telephony, ho ile ha lumellanoa ka linako tse behiloeng, thepa e ile ea rekoa 'me morero oa ho fetisetsa khoebo lekholong la bo21 la lilemo oa qala ho kenngoa ts'ebetsong.
Ntho ea pele e qalang ho tšoenyeha boemong bo joalo ke palo e ntseng e eketseha ka potlako ea lisebelisoa tsa thelefono tse hlokang ho laoloa ka tsela e itseng, ntho ea bobeli e neng e tšoenya haholo ke buka ea fono. Haeba Endpoint Manager a ka re thusa ka ea pele (eo, ka tsela, e ileng ea khaoloa liphetolelong tsa morao-rao tsa FreePBX), joale lipotso tse ling li ile tsa hlaha ka buka:

  • Taba ea pele, u ka etsa bonnete ba hore e nepahetse ha sebaka / metsi a basebelisi a lula a fetoha?
  • Taba ea bobeli, mokhoa oa ho nyenyefatsa lifono ka botlalo. Mme ha o tlatse lebitso la motho ka mong nako le nako?

Bothata bo ne bo thahasellisa, tharollo ha ea ka ea nka nako e telele ho fihla. Joale ke tla fana ka lethathamo le felletseng, ebe joale re tla le sheba ka tatellano.

from scapy.all import sniff
from scapy.layers.inet import IP
import mysql.connector
import ldap
import getpass
import tftpy
import requests
import os
import time
from string import replace

def conn_ldap(login):
    ad = ldap.initialize('ldap://***.local')
    ad.simple_bind_s('voip@***.local', 'password')
    basedn = 'OU=IT,DC=***,DC=LOCAL'
    basedn_user = 'OU=***,OU=***,DC=***,DC=LOCAL'
    scope = ldap.SCOPE_SUBTREE
    filterexp = "(&(sAMAccountName=" + login + ")(ObjectClass=person))"
    filterexp2 = "(&(ObjectClass=organizationUnit))"
    attrlist = ['cn']
    attrlist2 = ['OU']
    search = ad.search_s(basedn, scope, filterexp, attrlist)
    adname = search[0][1]['cn'][0].decode('utf-8')
    if adname == ' ':
        search = ad.search_s(basedn_user, scope, filterexp2, attrlist2)
        for i in range(1, len(search)+1):
            group = search[i][1]['ou'][0]
            basedn_user2 = 'OU='+group+','+basedn_user
            search = ad.search_s(basedn_user2, scope, filterexp, attrlist)
            adname = search[0][1]['cn'][0].decode('utf-8')
            if adname != ' ':
                return adname
        adname = search[0][1]['cn'][0].decode('utf-8')
    ad.unbind_s()
    return adname


def tftp_file_change(config,place,adname,current_account,current_account_password):

    client = tftpy.TftpClient("192.168.0.3", 69)
    client.download('template.cfg', place)
    fileread = open(place, 'r')
    line = fileread.readlines()
    fileread.close()
    line[5] = (('account.1.label = ').encode('utf-8') + adname.encode('utf-8') + 'n')
    line[2] = (('account.1.auth_name = ').encode('utf-8') + current_account.encode('utf-8') + 'n')
    line[3] = (('account.1.display_name = ').encode('utf-8') + current_account.encode('utf-8') + 'n')
    line[6] = (('account.1.password = ').encode('utf-8') + current_account_password[0][0] + 'n')
    filewrite = open(place, 'w')
    for i in line:
      filewrite.write(i)
    filewrite.close()
    print place
    print config
    client.upload(config,place)


def get_phone_inform(ipaddr):
    fileconf = requests.get('http://admin:admin@'+ipaddr+'/servlet?phonecfg=get[&accounts=1]')
    conf = fileconf.text.split('|')
    current_account = conf[2]
    return current_account


def sniff_frame():
    pcapf = sniff(count=1, timeout=70, filter="dst host 192.168.0.3 and port 5060")
    if len(pcapf) == 0:
        exit()
    frame = pcapf[0]
    macaddr = frame.src
    print macaddr[:8]
    if macaddr[:8] != '80:5e:c0':
        exit()
    ipaddr = frame[0][IP].src
    return macaddr, ipaddr


def conn_mysql(query,fquery,macaddr,qwery2):
    connect = mysql.connector.connect(host='192.168.0.3', database='voip', user='voip_wr', password='***')
    cursor = connect.cursor()
    cursor.execute(fquery)
    state = cursor.fetchall()
    state = bool(state[0][0])
    if state == True:
        cursor.execute(qwery2)
        connect.commit()
        connect.close()
    else:
        cursor.execute(query)
        connect.commit()
        connect.close()


def check_account(current_account):
    connect = mysql.connector.connect(host='192.168.0.3', database='asterisk', user='voip_wr', password='***')
    cursor = connect.cursor()
    qwery = 'select data from sip where id=' + current_account + ' and keyword="secret";'
    cursor.execute(qwery)
    password = cursor.fetchall()
    if password == ' ':
        exit()
    else:
        return password


if __name__ == '__main__':
    macaddr, ipaddr = sniff_frame()
    current_account = get_phone_inform(ipaddr)
    current_account_password = check_account(current_account)
    macaddr = macaddr.replace(':', '')
    ipaddr = ipaddr.decode('utf-8')
    adname = conn_ldap(getpass.getuser())
    query = 'INSERT INTO station (mac, ip, name, number) VALUES (' + '"' + macaddr + '",' + '"' + ipaddr + '",' + '"' + adname + '",' + '"' + get_phone_inform(ipaddr) + '"' + ')'
    qwery2 = 'UPDATE station SET ip=' + '"' + ipaddr + '"' + ', name=' + '"' + adname + '"' + ', number=' + '"' + get_phone_inform(ipaddr) + '"' + ' WHERE mac=' + '"' + macaddr + '"'
    fquery = 'SELECT EXISTS(SELECT mac FROM voip.station WHERE mac=' + '"' + macaddr + '")'
    query = query.encode('utf-8')
    fquery = fquery.encode('utf-8')
    config = macaddr + '.cfg'
    place = os.path.expanduser("~") + "" + "AppDataLocal" + config
    conn_mysql(query,fquery,macaddr,qwery2)
    tftp_file_change(config,place,adname,current_account,current_account_password)
    requests.get('http://admin:admin@'+ipaddr+'/cgi-bin/ConfigManApp.com?key=AutoP')
    requests.get('http://admin:admin@'+ipaddr+'/cgi-bin/ConfigManApp.com?key=Reboot')

Lenaneo le sebetsa komporong ea mosebelisi mme le sebetsa ha feela komporo e hokahane le marang-rang ka mohala, kaha Yealink T19 e ke ke ea sebetsa joalo ka heke.

Taba ea pele, re hloka ho utloisisa hore na e hokahane? le hore na mac le ip fono ea rona e na le eng.

def sniff_frame():
    pcapf = sniff(count=1, timeout=70, filter="dst host 192.168.0.3 and port 5060")
    if len(pcapf) == 0:
        exit()
    frame = pcapf[0]
    macaddr = frame.src
    print macaddr[:8]
    if macaddr[:8] != '80:5e:c0':
        exit()
    ipaddr = frame[0][IP].src
    return macaddr, ipaddr

Mona re sebelisa ts'ebetso ea sniff ho tloha moralo oa scapy, ka thuso ea eona re fumana pakete ea udp e reriloeng esale pele, emela metsotsoana e 70 mme haeba re sa tšoase letho, rea tsoa.

count=1, timeout=70, filter="dst host 192.168.0.3 and port 5060"

Ka mor'a moo, re etsa bonnete ba hore sesebelisoa ke Yealink 'me re khutlisetsa litekanyetso tse hlokahalang (ip le mac).

Re sebelisa kopo e khethehileng, re fumana akhaonto ea morao-rao fonong. Ho etsa sena, tlhophiso ea hajoale e jarollwa fonong ebe e arolwa.

def get_phone_inform(ipaddr):
    fileconf = requests.get('http://admin:admin@'+ipaddr+'/servlet?phonecfg=get[&accounts=1]')
    conf = fileconf.text.split('|')
    current_account = conf[2]
    return current_account

Fumana phasewete ea akhaonto ena. Ho etsa sena, re retelehela tafoleng ea asterisk.sip le tšimo ea data ho eona.

def check_account(current_account):
    connect = mysql.connector.connect(host='192.168.0.3', database='asterisk', user='voip_wr', password='***')
    cursor = connect.cursor()
    qwery = 'select data from sip where id=' + current_account + ' and keyword="secret";'
    cursor.execute(qwery)
    password = cursor.fetchall()
    if password == ' ':
        exit()
    else:
        return password

Che, molemong oa ho qetela re hokela ho ldap AD le ho sebelisa sAMAccountName e fumanoeng ka ts'ebetso getpass.getuser() nka cn ea mosebelisi oa hajoale (eo hangata e nang le lebitso le felletseng la mosebelisi).

def conn_ldap(login):
    ad = ldap.initialize('ldap://***.local')
    ad.simple_bind_s('voip@***.local', 'password')
    basedn = 'OU=***,DC=***,DC=LOCAL'
    basedn_user = 'OU=***,OU=***,DC=***,DC=LOCAL'
    scope = ldap.SCOPE_SUBTREE
    filterexp = "(&(sAMAccountName=" + login + ")(ObjectClass=person))"
    filterexp2 = "(&(ObjectClass=organizationUnit))"
    attrlist = ['cn']
    attrlist2 = ['OU']
    search = ad.search_s(basedn, scope, filterexp, attrlist)
    adname = search[0][1]['cn'][0].decode('utf-8')
    if adname == ' ':
        search = ad.search_s(basedn_user, scope, filterexp2, attrlist2)
        for i in range(1, len(search)+1):
            group = search[i][1]['ou'][0]
            basedn_user2 = 'OU='+group+','+basedn_user
            search = ad.search_s(basedn_user2, scope, filterexp, attrlist)
            adname = search[0][1]['cn'][0].decode('utf-8')
            if adname != ' ':
                return adname
        adname = search[0][1]['cn'][0].decode('utf-8')
    ad.unbind_s()
    return adname

Re hokela tafoleng e entsoeng esale pele ho database (ke e bōpile moo) ebe re kenya ntho e 'ngoe le e' ngoe eo re ithutileng eona, e leng: ip, mac, username.

def conn_mysql(query,fquery,macaddr,qwery2):
    connect = mysql.connector.connect(host='192.168.0.3', database='voip', user='voip_wr', password='***')
    cursor = connect.cursor()
    cursor.execute(fquery)
    state = cursor.fetchall()
    state = bool(state[0][0])
    if state == True:
        cursor.execute(qwery2)
        connect.commit()
        connect.close()
    else:
        cursor.execute(query)
        connect.commit()
        connect.close()

Re ka emisa mona, hobane re se re thehile buka ea liaterese e matla, u ka botsa, empa ke ile ka fetela pele mme ka eketsa tlhahiso ea lisebelisoa tsa lisebelisoa mona.

Ho etsa sena, tlhophiso ea template e kopitsoa ho tsoa ho seva sa tftp se seng se lokiselitsoe, moo re etsang liphetoho le ho e boloka joalo ka mac.cfg. Ke hore, bakeng sa Yealink ho na le mefuta e 'meli ea tlhophiso, e' ngoe ke ea lefats'e, 'me ea bobeli e sebetsa ho fono e itseng' me e lokela ho ba ea mofuta oa mac_phone.cfg.

Ka mor'a liphetoho tsohle tse faeleng le ho e boloka ho seva sa tftp, re fana ka taelo ho fono ho fana le ho tsosolosa sesebelisoa.

def tftp_file_change(config,place,adname,current_account,current_account_password):

    client = tftpy.TftpClient("192.168.0.3", 69)
    client.download('template.cfg', place)
    fileread = open(place, 'r')
    line = fileread.readlines()
    fileread.close()
    line[5] = (('account.1.label = ').encode('utf-8') + adname.encode('utf-8') + 'n')
    line[2] = (('account.1.auth_name = ').encode('utf-8') + current_account.encode('utf-8') + 'n')
    line[3] = (('account.1.display_name = ').encode('utf-8') + current_account.encode('utf-8') + 'n')
    line[6] = (('account.1.password = ').encode('utf-8') + current_account_password[0][0] + 'n')
    filewrite = open(place, 'w')
    for i in line:
      filewrite.write(i)
    filewrite.close()
    print place
    print config
    client.upload(config,place)

requests.get('http://admin:admin@'+ipaddr+'/cgi-bin/ConfigManApp.com?key=AutoP')
requests.get('http://admin:admin@'+ipaddr+'/cgi-bin/ConfigManApp.com?key=Reboot')

Kamora ho qala sesebelisoa hape, re fumana lebitso la rona le felletseng skrineng sa mohala + buka ea liaterese e tlatsitsoeng ka nepo ka mokhoa oa polokelo ea litaba, ebe se setseng ke ho eketsa XML le PHP e nyane ho bonts'a litaba ka matla. Ho na le mehlala e mengata e joalo, esita le YEALINK ka boeona e na le eona.

PS: Bakeng sa scalability e kholoanyane, o ka tsamaisa litlhophiso tsa mantlha (li-variable) ho faele e arohaneng.

Source: www.habr.com

Eketsa ka tlhaloso