📄 session.cpp
字号:
// Copyright (C) 2000 Open Source Telecom Corporation.// // This program is free software; you can redistribute it and/or modify// it under the terms of the GNU General Public License as published by// the Free Software Foundation; either version 2 of the License, or// (at your option) any later version.// // This program is distributed in the hope that it will be useful,// but WITHOUT ANY WARRANTY; without even the implied warranty of// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the// GNU General Public License for more details.// // You should have received a copy of the GNU General Public License// along with this program; if not, write to the Free Software // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.#include <config.h>#include <fcntl.h>#include "server.h"#include "trunk.h"#include "session.h"Trunk **Session::trunks = NULL;Session::Session(int count, int pri) : Sessionmap(), Thread(NULL, pri){ long flags; trunks = (Trunk **)new Trunk *[count]; pipe(fd); FD_ZERO(&events); FD_ZERO(&pending); FD_ZERO(&exiting); FD_SET(fd[0], &pending); flags = fcntl(fd[0], F_GETFL); fcntl(fd[0], F_SETFL, flags | O_NDELAY); hiwater = fd[0] + 1;}Session::~Session() { Terminate(); delete[] trunks;}void Session::setBusy(int id){ EventRecord er; Trunk *trunk = getPhoneTrunk(id); if(!trunk) return; er.event = UM_EVENT_MAKE_BUSY; er.p1 = er.p2 = 0; SendMessage(trunk, &er);}void Session::setIdle(int id){ EventRecord er; Trunk *trunk = getPhoneTrunk(id); if(!trunk) return; er.event = UM_EVENT_MAKE_IDLE; er.p1 = er.p2 = 0; SendMessage(trunk, &er);}void Session::exitTGI(int id, int excode){ EventRecord er; Trunk *trunk = getPhoneTrunk(id); if(!trunk) return; er.event = UM_EVENT_EXIT_SHELL; er.p1 = excode; er.p2 = 0; SendMessage(trunk, &er);}void Session::ringTrunk(int id){ EventRecord er; Trunk *trunk = getPhoneTrunk(id); if(!trunk) return; er.event = UM_EVENT_RING_LINE; er.p1 = er.p2 = 0; SendMessage(trunk, &er);}void Session::callTrunk(int id, char *scr){ bool search = false; EventRecord er; Trunk *trunk; if(!id) { id = getDriverPorts(); search = true; } trunk = getPhoneTrunk(id); if(!trunk) return; if(search) er.p1 = id; else er.p1 = 0; SendMessage(trunk, &er);}void Session::Update(char buf){ ::write(fd[1], &buf, 1);}void Session::Exiting(int dev){ FD_SET(dev, &exiting); Update(1);}void Session::Initial(void){ int port, dev; Trunk *trunk; for(port = 0; port < getDriverPorts(); ++port) { trunk = trunks[port]; if(!trunk) continue; dev = trunk->getDevice(); if(dev >= hiwater) hiwater = dev + 1; FD_SET(dev, &events); }}void Session::Run(void){ time_t now; struct tm *dt; long timer, expires; char buf; struct timeval timeout; int port; int dev; Trunk *trunk; fd_set inp, out, err; EventRecord er; union telephony_exception event; FD_ZERO(&out); FD_ZERO(&inp); FD_ZERO(&err); setCancel(THREAD_CANCEL_DEFERRED); for(;;) { time(&now); dt = localtime(&now); debug(9, "service thread wakeup %02d:%02d:%02d", dt->tm_hour, dt->tm_min, dt->tm_sec); timer = 3600000; while(1 == ::read(fd[0], &buf, 1)) { switch(buf) { case 0: setCancel(THREAD_CANCEL_IMMEDIATE); Sleep(60000); Exit(); } } for(port = 0; port < getDriverPorts(); ++port) { er.p1 = er.p2 = 0; trunk = trunks[port]; if(!trunk) continue; dev = trunk->getDevice(); if(FD_ISSET(dev, &err)) { event.bytes = ioctl(dev, PHONE_EXCEPTION); debug(9, "service event bits %08x", event.bytes); if(event.bits.pstn_ring) { er.event = PH_EVENT_LINE_RINGING; SendMessage(trunk, &er); } if(event.bits.pstn_wink) { er.event = PH_EVENT_LINE_WINKING; SendMessage(trunk, &er); } if(event.bits.dtmf_ready) { er.event = PH_EVENT_DTMF_DIGIT; er.p1 = ioctl(dev, PHONE_GET_DTMF_ASCII); SendMessage(trunk, &er); er.p1 = 0; } if(event.bits.hookstate) { if(ioctl(dev, PHONE_HOOKSTATE)) er.event = PH_EVENT_OFF_HOOK; else er.event = PH_EVENT_ON_HOOK; SendMessage(trunk, &er); } if(event.bits.caller_id) { er.event = PH_EVENT_CALLER_ID; SendMessage(trunk, &er); } } if(FD_ISSET(dev, &inp)) { er.event = PH_EVENT_INPUT_PENDING; SendMessage(trunk, &er); } if(FD_ISSET(dev, &exiting)) { er.event = PH_EVENT_SERVICE_ENDING; SendMessage(trunk, &er); FD_CLR(dev, &exiting); } expires = trunk->getTimer(); if(expires > 0) if(expires < timer) timer = expires; if(!expires) { er.event = PH_EVENT_TIMER_EXPIRED; SendMessage(trunk, &er); } } debug(9, "service thread waiting %ld msec", timer); memcpy(&err, &events, sizeof(err)); memcpy(&inp, &pending, sizeof(inp)); timeout.tv_sec = timer / 1000; timeout.tv_usec = (timer % 1000) * 1000; select(hiwater, &inp, &out, &err, &timeout); }}Trunk* getPhoneTrunk(int id){ if(id < 1 || id > getDriverPorts()) return NULL; return Session::trunks[--id];}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -