Настройка FSK в Asterisk для определения номеров

Чтобы определялся номер, с аналоговых линий, нужно в контексте для транка каждого канала Dahdi указать:

usecallerid = yes
hidecallerid=no
cidstart = ring
cidsignalling = bell
callerid = asreceived

asreceived — означает что номер нужно передавать в виде, в каком он есть.
Я использовал китайскую плату TDM410P.
Также необходимо подать заявку оператору телефонной связи чтобы они включили не старый АОН, а CallerID, то есть FSK (Bellcore).
Я написал сообщение в техническую поддержку на сайта Укртелеком, и на следующий день на стационарный телефон перезвонил местный инженер.
Мы были подключены к АТС SI 3000, спустя еще день с нескольких попыток нам все же включили FSK и номера начали определяться еще до снятия трубки, мобильные, стационарные и т.д., хотя иногда бывали случаи что номер был не определен.

Если у провайдера телефонной связи не включен FSK, то в консоли Asterisk при звонках можно увидеть ошибки:

WARNING[21790][C-00000000]: chan_dahdi.c:1842 my_get_callerid: Failed to decode CallerID
ERROR[21790][C-00000000]: callerid.c:566 callerid_feed: No start bit found in fsk data.

Записать для анализа звук с канала телефонной линии можно командой:

dahdi_monitor 1 -v -r streamrx.wav

Также можно включить(on)/отключить(off) режим отладки звонков открыв консоль Asterisk и набрав команду:

sudo asterisk -rvvvvvv
sip set debug on
sip set debug off

Сгенерированный /etc/asterisk/dahdi-channels.conf я оставил без изменений (на всякий случай приведу его содержимое):

; Span 1: WCTDM/0 "Wildcard TDM410P" (MASTER)
;;; line="1 WCTDM/0/0 FXSKS"
signalling=fxs_ks
callerid=asreceived
group=0
context=from-pstn
channel => 1
callerid=
group=
context=default

;;; line="2 WCTDM/0/1 FXSKS"
signalling=fxs_ks
callerid=asreceived
group=0
context=from-pstn
channel => 2
callerid=
group=
context=default

;;; line="3 WCTDM/0/2 FXSKS"
signalling=fxs_ks
callerid=asreceived
group=0
context=from-pstn
channel => 3
callerid=
group=
context=default

;;; line="4 WCTDM/0/3 FXSKS"
signalling=fxs_ks
callerid=asreceived
group=0
context=from-pstn
channel => 4
callerid=
group=
context=default

Увеличение громкости звонков в Asterisk

Чтобы увеличить громкость разговора при звонках, необходимо в файле /etc/asterisk/extensions.conf, в начале каждого диалплана добавить пару строк (на которых нужно увеличить громкость):

exten => X.,1,Set(VOLUME(TX)=5)
exten => X.,n,Set(VOLUME(RX)=5)

Минимальное значение 0, а максимальное 10.

Если используется Dahdi, то можно усилить громкость на плате прописав в /etc/asterisk/chan_dahdi.conf или в контексте нужного транка:

rxgain=2.0
txgain=2.0

Тут стандартное значение 0.0, а максимальное 6.0, где rx (receive) — входящая громкость, tx (transmit) — исходящая от Asterisk.

Маршрутизация звонков по времени в Asterisk

Приведу пример маршрутизации звонков по времени в Asterisk.
Допустим в файле /etc/asterisk/extensions.conf есть настроенный контекст для транка со следующими параметрами:

[Trunk_2]
exten => s,1,DIAL(SIP/6004&SIP/6003,19)
exten => s,2,Hangup()

И чтобы разрулить звонки по времени на разные телефоны укажем для контекста этого транка только вложенные контексты:

[Trunk_2]
include => daytime,8:00-18:00,mon-sat,*,*
include => nighttime,18:00-8:00,mon-sun,*,*
include => sunday,8:00-22:00,sun,*,*

По сути daytime, nighttime, sunday это только названия контекстов, для которых прописано время в контексте [Trunk_2], их можно называть как угодно.

И потом в этих отдельных контекстах уже пропишем нужные екстеншены.
То есть, днем:

[daytime]
exten => s,1,DIAL(SIP/6004&SIP/6003,19)
exten => s,2,Hangup()

Ночью:

[nighttime]
exten => s,1,DIAL(SIP/6002,19)
exten => s,2,Hangup()

И в воскресенье:

[sunday]
exten => s,1,DIAL(SIP/6002,19)
exten => s,2,Hangup()

Можно также например создать контекст holiday с праздничными днями:

include => holiday,*,*,1,jan
include => holiday,*,*,8,mar

и т.д.

Для тех кто хочет расписать подробнее по дням, приведу список дней на английском:
mon — Monday — Понедельник
tue — Tuesday — Вторник
wed — Wednesday — Среда
thu — Thursday — Четверг
fri — Friday — Пятница
sat — Saturday — Суббота
sun — Sunday — Воскресенье

Аналогично сокращаются до трех букв и названия месяцев.

Решение ошибки при компиляции Asterisk «‘pjsip_tcp_transport_cfg’ has no member named ‘sockopt_params’»

Компилировал однажды Asterisk версии 13.13.1 и при выполнении make заметил следующую ошибку:

‘pjsip_tcp_transport_cfg’ has no member named ‘sockopt_params’

pjproject-2.2.1 уже был скомпилирован.

Решил проблему собрав поновее версию pjproject-2.4.5

cd /usr/src
wget http://www.pjsip.org/release/2.4.5/pjproject-2.4.5.tar.bz2
tar -xjvf pjproject-2.4.5.tar.bz2
cd pjproject-2.4.5
CFLAGS='-DPJ_HAS_IPV6=1' ./configure --prefix=/usr --enable-shared --disable-sound --disable-resample --disable-video --disable-opencore-amr
make dep
make
make install

После этого, ошибка исчезла.

Настройка TDM410P c asterisk

На тесте подключил китайскую плату TDM410P с четырьмя FXO-портами (красными) в PCI слот выключенного Ubuntu сервера.
Для удобства в Ubuntu на root пользователя можно переключится командой:

sudo -i

Включил сервер, выполнил команду которая отображает PCI устройства и шины:

lspci -v

В списке увидел установленную плату:

05:00.0 Ethernet controller: Digium, Inc. Wildcard TDM410 4-port analog card (rev 11)
Subsystem: Digium, Inc. Wildcard TDM410 4-port analog card
Physical Slot: 1
Flags: bus master, fast Back2Back, medium devsel, latency 64, IRQ 16
I/O ports at 1000 [size=256]
Memory at b1900000 (32-bit, non-prefetchable) [size=1K]
Expansion ROM at b1920000 [disabled] [size=128K]
Capabilities:
Kernel driver in use: wctdm24xxp
Kernel modules: wctdm24xxp

Зарегистрируем плату (параметры автоматически пропишутся в конфигурации /etc/dahdi/ и /etc/asterisk/dahdi-channels.conf):

dahdi_span_assignments -v auto
dahdi_genconf -v

Теперь плату можно увидеть командой:

dahdi_scan
dahdi_cfg -vvvv
lsdahdi

Если возникают ошибки при команде dahdi_cfg, то возможно не установлен dahdi, скомпилируем его например как я писал в статье указанной по ссылке ниже, тем более если китайская плата не имеет аппаратного шумоподавления то dahdi по любому придется собирать с Oslec.
Установка эхоподавителя Oslec и DAHDI

В файле /etc/dahdi/modules у меня указаны модули (последний wctdm24xxp как раз предназначен для TDM410P):

dahdi
dahdi_dummy
dahdi_transcode
wctdm24xxp

Подгрузить его можно командой:

modprobe wctdm24xxp

В файле /etc/dahdi/system.conf изменим зону на свою (она может сбросится после выполнения команды dahdi_genconf):

loadzone=ru
defaultzone=ru

В файле /etc/asterisk/modules.conf, в блоке [modules] должна быть строка для автозагрузки модуля chan_dahdi:

load => chan_dahdi.so

Из консоли asterisk его также можно загрузить, но он будет активен до перезапуска asterisk (первая команда открывает консоль asterisk, последняя выходит из него):

asterisk -rvv
module load chan_dahdi
quit

Перезапустить dahdi можно из консоли asterisk командой:

dahdi restart

Проверить статус можно командой (в списке должна быть Wildcard TDM410P):

dahdi show status

Я подключил к 1 порту платы провод с телефонным номером городской аналоговой линии (нумерация портов идет сверху вниз, порт что ближе к PCI слоту четвертый).
Теперь пропишем его в конце файла users.conf для первого порта (канала):

[trunk_1]
group = 1
context = DID_trunk_1
busydetect = yes
busycount = 3
busypattern = 500,500
ringtimeout = 8000
progzone = ru
usecallerid = yes
cidstart = ring
cidsignalling = bell
flash = 750
rxflash = 1250
callerid = asreceived
dahdichan = 1
trunkstyle = analog
allow = all
group = 1
pulsedial=yes
dialtone_detect=yes
signalling = fxs_ks
channel = 1

Замечу что без параметров pulsedial=yes, dialtone_detect=yes у меня не работали исходящие вызовы, а был слышен беспрерывный гудок линии (телефонные линии Укртелеком).

Добавим в конце файла /etc/asterisk/chan_dahdi.conf

context=DID_trunk_1
signalling=fxs_ks
group=1
channel => 1

Перезапустим asterisk чтобы применить изменения:

service asterisk restart

Подключимся к его консоли и посмотрим активен ли добавленный канал:

asterisk -vvr
dahdi show channels
dahdi show channel 1

Посмотреть уровень громкости и трафик на канале можно командой:

dahdi_monitor 1 -v

В файле extensions.conf укажем куда отправлять входящие звонки (в моём случае на IP телефон с номером 6001):

[DID_trunk_1]
exten => s,1,DIAL(SIP/6001,20)
exten => s,2,Hangup()

Также добавим к диалплану в котором настроены IP телефоны, строки с шаблонами номеров телефонов куда можно звонить (в первой строке например конкретно указан номер 21545, а во второй шаблон под который попадают все номера из пяти цифр начинающиеся на семерку, буква W означает паузу перед набором):

exten => _21545,1,Dial(DAHDI/1/W${EXTEN})
exten => _7XXXX,1,Dial(DAHDI/1/W${EXTEN})

Если необходимо дождаться паузы после набора 0 перед набором остальной части номера:

exten => _022XXXXXX,1,Dial(DAHDI/1/W0W${EXTEN:1},60)

Перезапустить asterisk можно командой:

service asterisk restart

Из консоли asterisk можно по отдельности подгружать конфиги, например sip и extensions:

asterisk -rvv
sip reload
dialplan reload
quit

Решение проблемы Asterisk — нет звука при звонке через NAT

Заметил недавно что нет звука при звонке с IP-телефона на другой IP-телефон которые оба находились за одним и тем же NAT (роутером).

По этому в конфигурации sip.conf для этих аккаунтов нужно указать что они за NAT, указав параметр:

nat=force_rport,comedia

Хочу заметить что значение yes для nat уже устарело начиная с версии Asterisk 11, по этому правильно будет как указанно выше.

И указать также на no для параметра directmedia, чтобы Asterisk не отправлял пакеты на тот же порт из которого их получил (что в моём случае и произошло, оба телефона подключались к Asterisk с одного IP, с одинаковыми портами):

directmedia=no

Все.

Установка эхоподавителя Oslec и DAHDI

Устанавливал как-то китайскую плату TDM410P для подключения аналоговых телефонных линий и связку Asterisk + Dahdi.
Так как плата не имеет аппаратного шумоподавления, пришлось ставить Oslec.
При звонках, со стороны аналогового телефона эха не было, а вот кто говорил в IP телефон — слышал сам себя.

Настраивал на Ubuntu Server, по этому переключимся сразу на пользователя root:

sudo -i

Следующими командами посмотрим установлен ли oslec и прочую информацию о dahdi и плате:

lsmod |grep oslec
lsmod |grep dahdi
updatedb
locate oslec | more
dahdi_cfg -vvvv

В моём случае первая команда ничего не показала, а последняя выдала в конце ошибку.
Это значит что Oslec не установлен, по этому будем собирать Dahdi вместе с Oslec.
Скачаем архив с исходниками ядра и распакуем их (командой ls посмотрим имя архива linux-source-*, в моём случае был линк на архив linux-source-3.13.0.tar.bz2):

cd /usr/src
aptitude install linux-source
tar xjf linux-source-3.13.0.tar.bz2

Скачаем исходники Dahdi и распакуем их в директорию /usr/src/dahdi/ (командой ls посмотри имя директории с распакованными файлами и последней командой переименуем её):

wget http://downloads.asterisk.org/pub/telephony/dahdi-linux-complete/dahdi-linux-complete-current.tar.gz
tar xvfz dahdi-linux-complete-current.tar.gz
rm -f dahdi-linux-complete-current.tar.gz
mv dahdi-linux-complete-2.11.1+2.11.1 dahdi

Создадим директорию для Oslec и скопируем нужные файлы из архива с исходниками ядра в директорию с исходниками Dahdi:

mkdir /usr/src/dahdi/linux/drivers/staging
cp -fR /usr/src/linux-source-3.13.0/drivers/staging/echo /usr/src/dahdi/linux/drivers/staging

Укажем в Kbuild что нужно собирать Dahdi вместе с Oslec:

sed -i "s|#obj-m += dahdi_echocan_oslec.o|obj-m += dahdi_echocan_oslec.o|" /usr/src/dahdi/linux/drivers/dahdi/Kbuild
sed -i "s|#obj-m += ../staging/echo/|obj-m += ../staging/echo/|" /usr/src/dahdi/linux/drivers/dahdi/Kbuild
echo 'obj-m += echo.o' > /usr/src/dahdi/linux/drivers/staging/echo/Kbuild

Приступим к компиляции и установке:

cd /usr/src/dahdi/linux
make
make install

На этом Dahdi с эхоподавителем Oslec установлены и готовы к работе. Замечу что если обновить систему командами apt-get update & upgrade и обновится ядро, то нужно будет снова скомпилировать dahdi.

Чтобы задействовать Oslec укажем его в файле /etc/dahdi/system.conf:

fxsks=1
echocanceller=oslec,1
fxoks=2
echocanceller=oslec,2
fxoks=3
echocanceller=oslec,3
fxoks=4
echocanceller=oslec,4

А также активируем в /etc/asterisk/chan_dahdi.conf:

echocancel=yes
echocancelwhenbriged=no
echotraining=no

Перезапустим Dadhi и Asterisk чтобы применить изменения в файлах конфигурации:

service asterisk restart
asterisk -rvv
dahdi restart
quit
modprobe dahdi
modprobe dahdi_dummy
modprobe dahdi_transcode
modprobe wctdm24xxp

В случае ошибок запуска dahdi, можно перезагрузить сервер.

Все, на тесте при звонке через аналоговую линию иногда в первую секунду со стороны IP телефона можно услышать себя, но потом эхо отлично подавляется.