Skip to content

Commit 499fdaf

Browse files
committed
mod_asterisk_ami: Add ability to associate Softmodem sessions.
Using a new AMI command added to the Softmodem application, we can query the Asterisk server to determine the identity of the caller associated with the modem session - in particular, the Caller ID Number and Name. This is possible because we can use the TCP port to associate the session with a channel on the Asterisk server. We can determine if an incoming TCP connection did, in fact, originate from the Asterisk server, and if so, what the Caller ID is. This allows us to extract caller information from the BBS, similar to how an application running on a PC with a modem connected to it would be able to get Caller ID from the incoming call prior to answering. This association has to be done manually in this sort of way since the TCP connection itself doesn't contain any of this information. The end result is a new API that allows BBS applications to simply query a node for the associated Caller ID.
1 parent d0e11c7 commit 499fdaf

File tree

2 files changed

+70
-1
lines changed

2 files changed

+70
-1
lines changed

include/mod_asterisk_ami.h

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@
2323
*
2424
* This can be NULL for the default connection.
2525
*
26-
* Currently, only connection is supported so this argument
26+
* Currently, only one connection is supported so this argument
2727
* is ignored, but if in the future multiple sessions
2828
* were supported (see [LBBS-111]), then it would be used. */
2929

@@ -36,6 +36,21 @@ int bbs_ami_action_redirect(const char *session, const char *channel, const char
3636
#define bbs_ami_action_axfer(sess, chan, exten, context) bbs_ami_action(sess, "Atxfer", "Channel:%s\r\nExten:%s\r\nContext:%s", chan, exten, context)
3737
#define bbs_ami_action_cancel_axfer(sess, chan) bbs_ami_action(sess, "CancelAtxfer", "Channel:%s", chan)
3838

39+
/* Forward declaration for modules that don't need to include <cami/cami.h> */
40+
struct ami_event;
41+
42+
/*!
43+
* \brief Get Caller ID information for the caller associated with an incoming softmodem call via TCP
44+
* \param node
45+
* \param[out] numberbuf Buffer for Caller ID number. May be empty.
46+
* \param num_len Length of numberbuf. Should be at least 16.
47+
* \param[out] namebuf Buffer for Caller ID name. May be empty.
48+
* \param num_len Length of namebuf. Should be at least 16.
49+
* \retval 0 on success (successfully retrieved a session with associated Caller ID information)
50+
* \retval -1 No Softmodem session corresponds with this TCP connection
51+
*/
52+
int bbs_ami_softmodem_get_callerid(struct bbs_node *node, char *numberbuf, size_t num_len, char *namebuf, size_t name_len);
53+
3954
int __bbs_ami_callback_register(int (*callback)(struct ami_event *event, const char *eventname), void *mod);
4055

4156
/*!

modules/mod_asterisk_ami.c

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,8 @@
4040
#include "include/alertpipe.h"
4141
#include "include/linkedlists.h"
4242
#include "include/cli.h"
43+
#include "include/node.h"
44+
#include "include/utils.h"
4345

4446
#include "include/mod_asterisk_ami.h"
4547

@@ -162,6 +164,58 @@ int bbs_ami_action_redirect(const char *session, const char *channel, const char
162164
return res;
163165
}
164166

167+
int bbs_ami_softmodem_get_callerid(struct bbs_node *node, char *numberbuf, size_t num_len, char *namebuf, size_t name_len)
168+
{
169+
int i;
170+
const char *number = NULL, *name = NULL;
171+
struct ami_response *resp;
172+
173+
*numberbuf = '\0';
174+
*namebuf = '\0';
175+
176+
/*
177+
* The sender is not sent as part of the payload itself via TCP.
178+
* We need to query the phone system for the caller's number/name.
179+
* If the Asterisk softmodem is being used, we need to figure this out from Asterisk.
180+
*
181+
* We can correlate the sessions because on our end, we know the TCP port number on the client side,
182+
* as opened by the Softmodem application. The Softmodem application can therefore save this
183+
* information on the channel, and we can look for a channel that has the correct port number saved.
184+
*
185+
* If we cannot determine the caller information, the application can reject the connection.
186+
* In that sense, it also functions as a partial security check, since it requires the connecting port
187+
* to be used by the softmodem (though the IP address itself is not checked here).
188+
*/
189+
resp = bbs_ami_action(NULL, "SoftmodemSessions", "Port:%u", node->rport);
190+
if (!resp || !resp->success) {
191+
bbs_warning("Failed to get caller info\n");
192+
if (resp) {
193+
ami_resp_free(resp);
194+
}
195+
return -1;
196+
}
197+
198+
/* Since we applied a filter for only port node->rport, we'll only get back one session, at most */
199+
for (i = 1; i < resp->size - 1; i++) {
200+
struct ami_event *e = resp->events[i];
201+
const char *event = ami_keyvalue(e, "Event");
202+
if (!strcmp(event, "SoftmodemSession")) {
203+
number = ami_keyvalue(e, "CallerIDNumber");
204+
name = ami_keyvalue(e, "CallerIDName");
205+
break;
206+
}
207+
}
208+
bbs_debug(5, "Softmodem caller: %s (%s)\n", S_IF(number), S_IF(name));
209+
if (strlen_zero(number)) {
210+
safe_strncpy(numberbuf, number, num_len);
211+
}
212+
if (!strlen_zero(name)) {
213+
safe_strncpy(namebuf, name, name_len);
214+
}
215+
ami_resp_free(resp);
216+
return 0;
217+
}
218+
165219
static void set_ami_status(int up)
166220
{
167221
asterisk_up = up;

0 commit comments

Comments
 (0)