Merge branch 'master' of git.freeswitch.org:freeswitch

This commit is contained in:
unknown 2010-04-09 12:30:43 -04:00
commit c423c10864
20 changed files with 1774 additions and 1106 deletions

View File

@ -179,10 +179,26 @@ void MainWindow::debugConsoleTriggered()
}
void MainWindow::applyPreprocessors(QStringList cmds)
{
if (g_FSHost.getCurrentActiveCall().isNull()) return;
QString uuid = g_FSHost.getCurrentActiveCall().data()->getUuid();
foreach(QString cmd, cmds)
{
switch_stream_handle_t stream = { 0 };
SWITCH_STANDARD_STREAM(stream);
switch_api_execute("uuid_preprocess", QString("%1 %2").arg(uuid, cmd).toAscii().data(), NULL, &stream);
switch_safe_free(stream.data);
}
}
void MainWindow::prefTriggered()
{
if (!preferences)
{
preferences = new PrefDialog();
connect(preferences, SIGNAL(preprocessorsApplied(QStringList)), this, SLOT(applyPreprocessors(QStringList)));
}
preferences->raise();
preferences->show();

View File

@ -85,6 +85,7 @@ private slots:
void updateCallTimers();
void debugConsoleTriggered();
void debugEventsTriggered();
void applyPreprocessors(QStringList);
private:
Ui::MainWindow *ui;

View File

@ -15,6 +15,7 @@ PrefDialog::PrefDialog(QWidget *parent) :
_pref_accounts = new PrefAccounts(ui);
_mod_portaudio = new PrefPortaudio(ui, this);
connect(_mod_portaudio, SIGNAL(preprocessorsApplied(QStringList)), this, SIGNAL(preprocessorsApplied(QStringList)));
_mod_sofia = new PrefSofia(ui, this);
readConfig();
}

View File

@ -26,6 +26,9 @@ protected:
private slots:
void writeConfig();
signals:
void preprocessorsApplied(QStringList);
private:
void readConfig();
QSettings *_settings;

File diff suppressed because it is too large Load Diff

View File

@ -15,6 +15,28 @@ PrefPortaudio::PrefPortaudio(Ui::PrefDialog *ui, QObject *parent) :
connect(_ui->PaRingdevTestBtn, SIGNAL(clicked()), this, SLOT(ringdevTest()));
connect(_ui->PaLoopTestBtn, SIGNAL(clicked()), this, SLOT(loopTest()));
connect(_ui->PaRefreshDevListBtn, SIGNAL(clicked()), this, SLOT(refreshDevList()));
connect(_ui->btnApplyPreprocessor, SIGNAL(toggled(bool)), this, SLOT(applyPreprocessors(bool)));
}
void PrefPortaudio::applyPreprocessors(bool state)
{
QStringList cmds;
if (!state)
{
cmds.append("stop");
}
else
{
if (_ui->checkAECRead->isChecked()) cmds.append(QString("recho_cancel=%1").arg(_ui->spinAECTail->value()));
if (_ui->checkAECWrite->isChecked()) cmds.append(QString("wecho_cancel=%1").arg(_ui->spinAECTail->value()));
if (_ui->checkESRead->isChecked()) cmds.append(QString("recho_suppress=%1").arg(_ui->spinESDb->value()));
if (_ui->checkESWrite->isChecked()) cmds.append(QString("wecho_suppress=%1").arg(_ui->spinESDb->value()));
if (_ui->checkNSRead->isChecked()) cmds.append(QString("rnoise_suppress=%1").arg(_ui->spinNSDb->value()));
if (_ui->checkNSWrite->isChecked()) cmds.append(QString("wnoise_suppress=%1").arg(_ui->spinNSDb->value()));
if (_ui->checkAGCRead->isChecked()) cmds.append(QString("ragc=%1").arg(_ui->spinAGC->value()));
if (_ui->checkAGCWrite->isChecked()) cmds.append(QString("wagc=%1").arg(_ui->spinAGC->value()));
}
emit preprocessorsApplied(cmds);
}
void PrefPortaudio::ringdevTest()

View File

@ -24,6 +24,11 @@ private slots:
void ringdevTest();
void loopTest();
void refreshDevList();
void applyPreprocessors(bool);
signals:
void preprocessorsApplied(QStringList);
private:
void getPaDevlist(void);
QSettings *_settings;

76
scripts/setup-git.sh Executable file
View File

@ -0,0 +1,76 @@
#!/bin/bash
##### -*- mode:shell-script; indent-tabs-mode:nil; sh-basic-offset:2 -*-
##### setup git properly for FreeSWITCH
if [ ! -d .git ]; then
echo "error: must be run from within the top level of a FreeSWITCH git tree." 1>&2
exit 1;
fi
err () {
echo "error: $1" 1>&2
exit 1
}
if ! git config user.name >/dev/null 2>&1; then
name=$(git config user.name)
[ -z "$name" ] \
&& [ -n "$NAME" ] && name="$NAME" || name=""
echo -n "What is your name? [$name]: "
read name_
[ -n "$name_" ] && name="$name_"
[ -z "$name" ] && err "Your name is required."
git config --global user.name "$name"
fi
if ! git config user.email >/dev/null 2>&1; then
email=$(git config user.email)
[ -z "$email" ] \
&& [ -n "$EMAIL" ] && email="$EMAIL" || email=""
echo -n "What is your email? [$email]: "
read email_
[ -n "$email_" ] && email="$email_"
[ -z "$email" ] && err "Your email is required."
git config --global user.email "$email"
fi
git config branch.master.rebase true
cat 1>&2 <<EOF
----------------------------------------------------------------------
Git has been configured for FS successfully.
branch.master.rebase has been set to true
This means that when you do a 'git pull' to fetch remote changes,
your local changes will be rebased on top of the remote changes.
This does NOT rewrite history on the remote FS repo, but it does
change the commit hashes in your local tree.
If you really want to merge rather than rebasing, run:
git merge <commit>
See 'man git-config' for more information.
EOF
[ -n "$name" ] \
&& cat 1>&2 <<EOF
Your name has been set to: $name
via 'git config --global user.name "$name"
EOF
[ -n "$name" ] \
&& cat 1>&2 <<EOF
Your email has been set to: $email
via 'git config --global user.email "$email"
EOF
cat 1>&2 <<EOF
----------------------------------------------------------------------
EOF

View File

@ -186,10 +186,14 @@ static void tts_commandline_speech_flush_tts(switch_speech_handle_t *sh)
{
tts_commandline_t *info = (tts_commandline_t *) sh->private_info;
assert(info != NULL);
switch_core_file_close(info->fh);
if (unlink(info->file) != 0) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Sound file [%s] delete failed\n", info->file);
if (info->fh != NULL && info->fh->file_interface != NULL) {
switch_core_file_close(info->fh);
}
if (switch_file_exists(info->file, NULL) == SWITCH_STATUS_SUCCESS) {
if (unlink(info->file) != 0) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Sound file [%s] delete failed\n", info->file);
}
}
}

View File

@ -6,26 +6,25 @@ package Net::Skinny;
use strict;
use warnings;
use IO::Socket;
require IO::Socket;
use Net::Skinny::Protocol qw/:all/;
our(@ISA);
@ISA = qw(IO::Socket::INET);
our @ISA = qw(IO::Socket::INET);
sub new {
shift->SUPER::new(PeerPort => 2000, @_);
}
sub send_data
sub send_raw
{
my $self = shift;
my $type = shift;
my $data = shift;
my $len = length($data)+4;
my $raw = shift;
my $len = length($raw)+4;
printf "Sending message (length=%d, type=%s (%X))", $len, Net::Skinny::Protocol::skinny_message_type2str($type), $type;
$self->send(
pack("VVV", $len, 0, $type).
$data);
$self->send(pack("VVV", $len, 0, $type).$raw);
printf ".\n";
}
@ -33,11 +32,8 @@ sub send_message
{
my $self = shift;
my $type = shift;
return Net::Skinny::Message->new(
$self,
$type,
@_
)->send();
my $message = Net::Skinny::Message->new($type, @_);
return $self->send_raw($message->type(), $message->raw());
}
sub receive_message
@ -58,20 +54,26 @@ sub receive_message
printf "type=%s (%X))", Net::Skinny::Protocol::skinny_message_type2str($type), $type;
if($len > 4) {
$self->recv($buf, $len-4);
} else {
$buf = '';
}
printf ".\n";
return Net::Skinny::Message->new_raw($type, $buf);
}
sub sleep
{
my $self = shift;
my $t = shift;
my %args = @_;
$args{'quiet'} = 0 if not $args{'quiet'};
printf "Sleeping %d seconds", $t;
while(--$t){
sleep(1);
printf "." if $t % 10;
printf "_" unless $t % 10;
if(!$args{'quiet'}) {
printf "." if $t % 10;
printf "_" unless $t % 10;
}
}
printf ".\n";
}

View File

@ -0,0 +1,94 @@
# Copyright (c) 2010 Mathieu Parent <math.parent@gmail.com>.
# All rights reserved. This program is free software; you can redistribute it
# and/or modify it under the same terms as Perl itself.
package Net::Skinny::Client;
use strict;
use warnings;
use Config;
use threads;
use threads::shared;
use Thread::Queue;
require Net::Skinny;
use Net::Skinny::Protocol qw/:all/;
use Net::Skinny::Message;
our(@ISA);
@ISA = qw(Net::Skinny);
my $keep_alive_thread;
my $keep_alives :shared;
our $kept_self;
my $messages_send_queue;
my $messages_receive_queue;
$Config{useithreads} or die('Recompile Perl with threads to run this program.');
sub new {
$kept_self = shift->SUPER::new(@_);
$messages_send_queue = Thread::Queue->new();
$messages_receive_queue = Thread::Queue->new();
threads->create(\&send_messages_thread_func);
threads->create(\&receive_messages_thread_func);
return $kept_self;
}
sub send_message {
my $self = shift;
$messages_send_queue->enqueue(\@_);
}
sub receive_message {
my $self = shift;
my $message = $messages_receive_queue->dequeue();
if($message->type() == 0x100) {#keepaliveack
if(1) {
lock($keep_alives);
$keep_alives--;
}
$message = $messages_receive_queue->dequeue();
}
return $message;
}
sub launch_keep_alive_thread
{
if(!$keep_alive_thread) {
$keep_alive_thread = threads->create(\&keep_alive_thread_func);
} else {
print "keep-alive thread is already running\n";
}
return $keep_alive_thread;
}
sub keep_alive_thread_func
{
while($kept_self) {
if(1) {
lock($keep_alives);
$keep_alives++;
$kept_self->send_message(KEEP_ALIVE_MESSAGE);
} #mutex unlocked
$kept_self->sleep(30, quiet => 0);
}
}
sub send_messages_thread_func
{
while(my $message = $messages_send_queue->dequeue()) {
my $type = shift @$message;
$kept_self->SUPER::send_message($type, @$message);
}
}
sub receive_messages_thread_func
{
while(1) {
$messages_receive_queue->enqueue($kept_self->SUPER::receive_message());
}
}
1;

View File

@ -7,54 +7,96 @@ package Net::Skinny::Message;
use strict;
use warnings;
use threads;
use threads::shared;
use Net::Skinny::Protocol qw/:all/;
use Data::Dumper;
require Exporter;
our @ISA = qw(Exporter);
our @EXPORT = qw(send);
sub new {
sub new_empty {
my $class = shift;
my $self = {};
bless $self, $class;
$self->{'socket'} = shift;
$self->{'type'} = shift;
%{$self->{'data'}} = @_;
return $ self;
$self->{'type'} = undef;
$self->{'data'} = undef;
$self->{'raw'} = undef;
return $self;
}
sub send {
sub new {
my $self = shift->new_empty();
$self->type(shift);
$self->data(@_) if @_;
return $self;
}
sub new_raw {
my $self = shift->new_empty();
$self->type(shift);
$self->raw(shift);
return $self;
}
sub type
{
my $self = shift;
my $struct = Net::Skinny::Protocol::skinny_message_struct($self->{'type'});
my $raw = '';
my $parsed_count = 0;
for my $info ( @$struct) {
last if !defined($self->{'data'}{@$info[1]});
if(@$info[0] eq 'char') {
$raw .= pack("a".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'uint32_t') {
$raw .= pack("V".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'uint16_t') {
$raw .= pack("n".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'struct in_addr') {
$raw .= pack("V".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'struct station_capabilities') {
$raw .= $self->{'data'}{@$info[1]};
} else {
printf "Unknown type: %s\n", @$info[0];
return;
}
$parsed_count++;
my $type = @_ ? shift : undef;
if(defined($type)) {
$self->{'type'} = $type;
}
if($parsed_count != scalar(keys %{$self->{'data'}})) {
printf "Incomplete message (type=%s (%X)) %d out of %d\n", Net::Skinny::Protocol::skinny_message_type2str($self->{'type'}), $self->{'type'},
$parsed_count, scalar(keys %{$self->{'data'}});
print Dumper(@$struct);
return;
return $self->{'type'};
}
sub data
{
my $self = shift;
my @data = @_;
if(@data) {
%{$self->{'data'}} = @data;
$self->{'raw'} = undef;
} elsif(!defined($self->{'data'})) {
printf "Conversion from raw to data not implemented\n";
}
$self->{'socket'}->send_data($self->{'type'}, $raw);
return $self->{'data'};
}
sub raw
{
my $self = shift;
my $raw = shift || undef;
if(defined($raw)) {
$self->{'raw'} = $raw;
$self->{'data'} = undef;
}
if(!defined($self->{'raw'})) {
my $struct = Net::Skinny::Protocol::skinny_message_struct($self->{'type'});
my $raw = '';
my $parsed_count = 0;
for my $info ( @$struct) {
last if !defined($self->{'data'}{@$info[1]});
if(@$info[0] eq 'char') {
$raw .= pack("a".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'uint32_t') {
$raw .= pack("V".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'uint16_t') {
$raw .= pack("n".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'struct in_addr') {
$raw .= pack("V".@$info[2], $self->{'data'}{@$info[1]});
} elsif(@$info[0] eq 'struct station_capabilities') {
$raw .= $self->{'data'}{@$info[1]};
} else {
printf "Unknown type: %s\n", @$info[0];
return;
}
$parsed_count++;
}
if($parsed_count != scalar(keys %{$self->{'data'}})) {
printf "Incomplete message (type=%s (%X)) %d out of %d\n", Net::Skinny::Protocol::skinny_message_type2str($self->{'type'}), $self->{'type'},
$parsed_count, scalar(keys %{$self->{'data'}});
return;
}
$self->{'raw'} = $raw;
}
return $self->{'raw'};
}
1;

View File

@ -8,7 +8,6 @@ use strict;
no strict "refs";
use warnings;
use Carp;
use Data::Dumper;
require Exporter;
our @ISA = qw(Exporter);
@ -69,7 +68,6 @@ sub _find {
printf "Unparsed line '%s' in %s\n", $_, $struct_name;
}
}
#print "$name: ".Dumper($struct{$name});
}
}
@sub{@_};
@ -77,6 +75,7 @@ sub _find {
sub skinny_message_type2str {
my $message_type = shift;
return "UndefinedTypeMessage" if !defined($message_type);
keys %const;
while (my ($key, $value) = each %const) {

View File

@ -221,7 +221,7 @@ char * skinny_profile_find_session_uuid(skinny_profile_t *profile, listener_t *l
"SELECT channel_uuid, line_instance "
"FROM skinny_active_lines "
"WHERE %s AND %s AND %s "
"ORDER BY channel_uuid DESC",
"ORDER BY call_state, channel_uuid", /* off hook first */
device_condition, line_instance_condition, call_id_condition
))) {
skinny_execute_sql_callback(profile, profile->sql_mutex, sql,
@ -235,14 +235,22 @@ char * skinny_profile_find_session_uuid(skinny_profile_t *profile, listener_t *l
return helper.channel_uuid;
}
#ifdef SWITCH_DEBUG_RWLOCKS
switch_core_session_t * skinny_profile_perform_find_session(skinny_profile_t *profile, listener_t *listener, uint32_t *line_instance_p, uint32_t call_id, const char *file, const char *func, int line)
#else
switch_core_session_t * skinny_profile_find_session(skinny_profile_t *profile, listener_t *listener, uint32_t *line_instance_p, uint32_t call_id)
#endif
{
char *uuid;
switch_core_session_t *result = NULL;
uuid = skinny_profile_find_session_uuid(profile, listener, line_instance_p, call_id);
if(!zstr(uuid)) {
#ifdef SWITCH_DEBUG_RWLOCKS
result = switch_core_session_perform_locate(uuid, file, func, line);
#else
result = switch_core_session_locate(uuid);
#endif
if(!result) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING,
"Unable to find session %s on %s:%d, line %d\n",
@ -357,7 +365,9 @@ struct skinny_line_get_state_helper {
int skinny_line_get_state_callback(void *pArg, int argc, char **argv, char **columnNames)
{
struct skinny_line_get_state_helper *helper = pArg;
helper->call_state = atoi(argv[0]);
if (helper->call_state == -1) {
helper->call_state = atoi(argv[0]);
}
return 0;
}
@ -383,10 +393,12 @@ uint32_t skinny_line_get_state(listener_t *listener, uint32_t line_instance, uin
}
switch_assert(call_id_condition);
helper.call_state = -1;
if ((sql = switch_mprintf(
"SELECT call_state FROM skinny_active_lines "
"WHERE device_name='%s' AND device_instance=%d "
"AND %s AND %s",
"AND %s AND %s "
"ORDER BY call_state, channel_uuid", /* off hook first */
listener->device_name, listener->device_instance,
line_instance_condition, call_id_condition
))) {
@ -531,6 +543,7 @@ void tech_init(private_t *tech_pvt, skinny_profile_t *profile, switch_core_sessi
switch_mutex_init(&tech_pvt->mutex, SWITCH_MUTEX_NESTED, switch_core_session_get_pool(session));
switch_mutex_init(&tech_pvt->flag_mutex, SWITCH_MUTEX_NESTED, switch_core_session_get_pool(session));
tech_pvt->call_id = ++profile->next_call_id;
tech_pvt->party_id = tech_pvt->call_id;
tech_pvt->profile = profile;
switch_core_session_set_private(session, tech_pvt);
tech_pvt->session = session;
@ -633,16 +646,7 @@ int channel_on_hangup_callback(void *pArg, int argc, char **argv, char **columnN
send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_OFF);
send_clear_prompt_status(listener, line_instance, call_id);
if(call_state == SKINNY_CONNECTED) { /* calling parties */
send_close_receive_channel(listener,
call_id, /* uint32_t conference_id, */
helper->tech_pvt->party_id, /* uint32_t pass_thru_party_id, */
call_id /* uint32_t conference_id2, */
);
send_stop_media_transmission(listener,
call_id, /* uint32_t conference_id, */
helper->tech_pvt->party_id, /* uint32_t pass_thru_party_id, */
call_id /* uint32_t conference_id2, */
);
skinny_session_stop_media(helper->tech_pvt->session, listener, line_instance);
}
skinny_line_set_state(listener, line_instance, call_id, SKINNY_ON_HOOK);
@ -650,7 +654,6 @@ int channel_on_hangup_callback(void *pArg, int argc, char **argv, char **columnN
/* TODO: DefineTimeDate */
send_set_speaker_mode(listener, SKINNY_SPEAKER_OFF);
send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, 0, call_id);
}
return 0;
}
@ -1229,6 +1232,9 @@ static void *SWITCH_THREAD_FUNC listener_run(switch_thread_t *thread, void *obj)
switch_clear_flag_locked(listener, LFLAG_RUNNING);
break;
}
if (!listener_is_ready(listener)) {
break;
}
if (!request) {
continue;
@ -1473,7 +1479,7 @@ static switch_status_t load_skinny_config(void)
}
profile = switch_core_alloc(profile_pool, sizeof(skinny_profile_t));
profile->pool = profile_pool;
profile->name = profile_name;
profile->name = switch_core_strdup(profile->pool, profile_name);
switch_mutex_init(&profile->listener_mutex, SWITCH_MUTEX_NESTED, profile->pool);
switch_mutex_init(&profile->sql_mutex, SWITCH_MUTEX_NESTED, profile->pool);
switch_mutex_init(&profile->sock_mutex, SWITCH_MUTEX_NESTED, profile->pool);

View File

@ -189,7 +189,12 @@ switch_status_t skinny_profile_dump(const skinny_profile_t *profile, switch_stre
switch_status_t skinny_profile_find_listener_by_device_name(skinny_profile_t *profile, const char *device_name, listener_t **listener);
switch_status_t skinny_profile_find_listener_by_device_name_and_instance(skinny_profile_t *profile, const char *device_name, uint32_t device_instance, listener_t **listener);
char * skinny_profile_find_session_uuid(skinny_profile_t *profile, listener_t *listener, uint32_t *line_instance_p, uint32_t call_id);
#ifdef SWITCH_DEBUG_RWLOCKS
switch_core_session_t * skinny_profile_perform_find_session(skinny_profile_t *profile, listener_t *listener, uint32_t *line_instance_p, uint32_t call_id, const char *file, const char *func, int line);
#define skinny_profile_find_session(profile, listener, line_instance_p, call_id) skinny_profile_perform_find_session(profile, listener, line_instance_p, call_id, __FILE__, __SWITCH_FUNC__, __LINE__)
#else
switch_core_session_t * skinny_profile_find_session(skinny_profile_t *profile, listener_t *listener, uint32_t *line_instance_p, uint32_t call_id);
#endif
switch_status_t dump_device(skinny_profile_t *profile, const char *device_name, switch_stream_handle_t *stream);
/*****************************************************************************/

View File

@ -446,19 +446,20 @@ switch_status_t skinny_create_ingoing_session(listener_t *listener, uint32_t *li
line_instance = *line_instance_p;
if((nsession = skinny_profile_find_session(listener->profile, listener, line_instance_p, 0))) {
switch_core_session_rwunlock(nsession);
if(skinny_line_get_state(listener, *line_instance_p, 0) == SKINNY_OFF_HOOK) {
/* Reuse existing session */
*session = nsession;
return SWITCH_STATUS_SUCCESS;
}
skinny_session_hold_line(nsession, listener, *line_instance_p);
switch_core_session_rwunlock(nsession);
}
*line_instance_p = line_instance;
if(*line_instance_p == 0) {
*line_instance_p = 1;
}
skinny_hold_active_calls(listener);
skinny_line_get(listener, *line_instance_p, &button);
if (!button || !button->shortname) {
@ -494,7 +495,11 @@ switch_status_t skinny_create_ingoing_session(listener_t *listener, uint32_t *li
"Error Creating Session thread\n");
goto error;
}
if (switch_core_session_read_lock(nsession) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(nsession), SWITCH_LOG_CRIT,
"Error Locking Session\n");
goto error;
}
if (!(tech_pvt->caller_profile = switch_caller_profile_new(switch_core_session_get_pool(nsession),
NULL, listener->profile->dialplan,
button->shortname, button->name,
@ -543,6 +548,49 @@ done:
return SWITCH_STATUS_SUCCESS;
}
struct skinny_session_process_dest_helper {
private_t *tech_pvt;
listener_t *listener;
uint32_t line_instance;
};
int skinny_session_process_dest_callback(void *pArg, int argc, char **argv, char **columnNames)
{
struct skinny_session_process_dest_helper *helper = pArg;
listener_t *listener = NULL;
char *device_name = argv[0];
uint32_t device_instance = atoi(argv[1]);
/* uint32_t position = atoi(argv[2]); */
uint32_t line_instance = atoi(argv[3]);
/* char *label = argv[4]; */
/* char *value = argv[5]; */
/* char *caller_name = argv[6]; */
/* uint32_t ring_on_idle = atoi(argv[7]); */
/* uint32_t ring_on_active = atoi(argv[8]); */
/* uint32_t busy_trigger = atoi(argv[9]); */
/* char *forward_all = argv[10]; */
/* char *forward_busy = argv[11]; */
/* char *forward_noanswer = argv[12]; */
/* uint32_t noanswer_duration = atoi(argv[13]); */
/* char *channel_uuid = argv[14]; */
/* uint32_t call_id = atoi(argv[15]); */
/* uint32_t call_state = atoi(argv[16]); */
skinny_profile_find_listener_by_device_name_and_instance(helper->tech_pvt->profile, device_name, device_instance, &listener);
if(listener) {
if(!strcmp(device_name, helper->listener->device_name)
&& (device_instance == helper->listener->device_instance)
&& (line_instance == helper->line_instance)) {/* the calling line */
/* nothing */
} else {
/* TODO: capture and check what should happen here*/
skinny_line_set_state(listener, line_instance, helper->tech_pvt->call_id, SKINNY_IN_USE_REMOTELY);
}
}
return 0;
}
switch_status_t skinny_session_process_dest(switch_core_session_t *session, listener_t *listener, uint32_t line_instance, char *dest, char append_dest, uint32_t backspace)
{
switch_channel_t *channel = NULL;
@ -555,31 +603,43 @@ switch_status_t skinny_session_process_dest(switch_core_session_t *session, list
channel = switch_core_session_get_channel(session);
tech_pvt = switch_core_session_get_private(session);
if(!dest) {
if(append_dest == '\0') {/* no digit yet */
send_start_tone(listener, SKINNY_TONE_DIALTONE, 0, line_instance, tech_pvt->call_id);
} else {
if(strlen(tech_pvt->caller_profile->destination_number) == 0) {/* first digit */
send_stop_tone(listener, line_instance, tech_pvt->call_id);
send_select_soft_keys(listener, line_instance, tech_pvt->call_id,
SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT, 0xffff);
}
if (!dest) {
if (backspace) { /* backspace */
*tech_pvt->caller_profile->destination_number++ = '\0';
}
if (append_dest != '\0' && !backspace) {/* append digit */
tech_pvt->caller_profile->destination_number = switch_core_sprintf(tech_pvt->caller_profile->pool,
"%s%c", tech_pvt->caller_profile->destination_number, append_dest);
}
if (strlen(tech_pvt->caller_profile->destination_number) == 0) {/* no digit yet */
send_start_tone(listener, SKINNY_TONE_DIALTONE, 0, line_instance, tech_pvt->call_id);
if(backspace) {
send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_OFF_HOOK, 0xffff);
/* TODO: How to clear the screen? */
}
} else if (strlen(tech_pvt->caller_profile->destination_number) == 1) {/* first digit */
send_stop_tone(listener, line_instance, tech_pvt->call_id);
send_select_soft_keys(listener, line_instance, tech_pvt->call_id,
SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT, 0xffff);
}
} else {
tech_pvt->caller_profile->destination_number = switch_core_strdup(tech_pvt->caller_profile->pool,
dest);
}
/* TODO Number is complete -> check against dialplan */
if((strlen(tech_pvt->caller_profile->destination_number) >= 4) || dest) {
if ((strlen(tech_pvt->caller_profile->destination_number) >= 4) || dest) {
struct skinny_session_process_dest_helper helper = {0};
send_dialed_number(listener, tech_pvt->caller_profile->destination_number, line_instance, tech_pvt->call_id);
skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_PROCEED);
skinny_send_call_info(session, listener, line_instance);
skinny_session_start_media(session, listener, line_instance);
}
switch_core_session_rwunlock(session);
skinny_session_start_media(session, listener, line_instance);
helper.tech_pvt = tech_pvt;
helper.listener = listener;
helper.line_instance = line_instance;
skinny_session_walk_lines(tech_pvt->profile, switch_core_session_get_uuid(session), skinny_session_process_dest_callback, &helper);
}
return SWITCH_STATUS_SUCCESS;
}
@ -603,8 +663,6 @@ switch_status_t skinny_session_ring_out(switch_core_session_t *session, listener
line_instance, tech_pvt->call_id);
skinny_send_call_info(session, listener, line_instance);
switch_core_session_rwunlock(session);
return SWITCH_STATUS_SUCCESS;
}
@ -643,16 +701,14 @@ int skinny_session_answer_callback(void *pArg, int argc, char **argv, char **col
if(!strcmp(device_name, helper->listener->device_name)
&& (device_instance == helper->listener->device_instance)
&& (line_instance == helper->line_instance)) {/* the answering line */
send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, 0, helper->tech_pvt->call_id);
send_set_speaker_mode(listener, SKINNY_SPEAKER_ON);
/* nothing */
} else {
send_define_current_time_date(listener);
send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON);
skinny_line_set_state(listener, line_instance, helper->tech_pvt->call_id, SKINNY_OFF_HOOK);
/* send_select_soft_keys(listener, line_instance, helper->tech_pvt->call_id, SKINNY_KEY_SET_OFF_HOOK, 0xffff); */
/* display_prompt_status(listener, 0, "\200\000",
line_instance, tech_pvt->call_id); */
send_activate_call_plane(listener, line_instance);
skinny_line_set_state(listener, line_instance, helper->tech_pvt->call_id, SKINNY_IN_USE_REMOTELY);
send_select_soft_keys(listener, line_instance, helper->tech_pvt->call_id, 10, 0x0002);
send_display_prompt_status(listener, 0, "\200\037", line_instance, helper->tech_pvt->call_id);
send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, 0, helper->tech_pvt->call_id);
}
}
return 0;
@ -671,6 +727,12 @@ switch_status_t skinny_session_answer(switch_core_session_t *session, listener_t
channel = switch_core_session_get_channel(session);
tech_pvt = switch_core_session_get_private(session);
send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, 0, tech_pvt->call_id);
send_set_speaker_mode(listener, SKINNY_SPEAKER_ON);
send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON);
skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_OFF_HOOK);
send_activate_call_plane(listener, line_instance);
helper.tech_pvt = tech_pvt;
helper.listener = listener;
helper.line_instance = line_instance;
@ -679,8 +741,6 @@ switch_status_t skinny_session_answer(switch_core_session_t *session, listener_t
skinny_session_start_media(session, listener, line_instance);
switch_core_session_rwunlock(session);
return SWITCH_STATUS_SUCCESS;
}
@ -717,8 +777,6 @@ switch_status_t skinny_session_start_media(switch_core_session_t *session, liste
tech_pvt->call_id);
skinny_send_call_info(session, listener, line_instance);
switch_core_session_rwunlock(session);
return SWITCH_STATUS_SUCCESS;
}
@ -734,22 +792,129 @@ switch_status_t skinny_session_hold_line(switch_core_session_t *session, listene
channel = switch_core_session_get_channel(session);
tech_pvt = switch_core_session_get_private(session);
/* TODO */
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Hold is not implemented yet. Hanging up the line.\n");
skinny_session_stop_media(session, listener, line_instance);
switch_ivr_hold(session, NULL, 1);
switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING);
switch_core_session_rwunlock(session);
send_define_current_time_date(listener);
send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_WINK);
skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_HOLD);
send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_ON_HOLD, 0xffff);
send_display_prompt_status(listener, 0, "\200\003",
line_instance, tech_pvt->call_id);
skinny_send_call_info(tech_pvt->session, listener, line_instance);
send_set_speaker_mode(listener, SKINNY_SPEAKER_OFF);
send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, 0, tech_pvt->call_id);
return SWITCH_STATUS_SUCCESS;
}
switch_status_t skinny_session_unhold_line(switch_core_session_t *session, listener_t *listener, uint32_t line_instance)
{
/* TODO */
switch_channel_t *channel = NULL;
private_t *tech_pvt = NULL;
switch_assert(session);
switch_assert(listener);
switch_assert(listener->profile);
channel = switch_core_session_get_channel(session);
tech_pvt = switch_core_session_get_private(session);
skinny_hold_active_calls(listener);
send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, 0, tech_pvt->call_id);
send_set_speaker_mode(listener, SKINNY_SPEAKER_ON);
send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_RING_OUT, 0xffff);
skinny_session_start_media(session, listener, line_instance);
switch_ivr_unhold(session);
send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON);
return SWITCH_STATUS_SUCCESS;
}
switch_status_t skinny_session_stop_media(switch_core_session_t *session, listener_t *listener, uint32_t line_instance)
{
switch_channel_t *channel = NULL;
private_t *tech_pvt = NULL;
switch_assert(session);
switch_assert(listener);
switch_assert(listener->profile);
channel = switch_core_session_get_channel(session);
tech_pvt = switch_core_session_get_private(session);
send_close_receive_channel(listener,
tech_pvt->call_id, /* uint32_t conference_id, */
tech_pvt->party_id, /* uint32_t pass_thru_party_id, */
tech_pvt->call_id /* uint32_t conference_id2, */
);
send_stop_media_transmission(listener,
tech_pvt->call_id, /* uint32_t conference_id, */
tech_pvt->party_id, /* uint32_t pass_thru_party_id, */
tech_pvt->call_id /* uint32_t conference_id2, */
);
return SWITCH_STATUS_SUCCESS;
}
struct skinny_hold_active_calls_helper {
listener_t *listener;
};
int skinny_hold_active_calls_callback(void *pArg, int argc, char **argv, char **columnNames)
{
struct skinny_hold_active_calls_helper *helper = pArg;
switch_core_session_t *session;
/* char *device_name = argv[0]; */
/* uint32_t device_instance = atoi(argv[1]); */
/* uint32_t position = atoi(argv[2]); */
uint32_t line_instance = atoi(argv[3]);
/* char *label = argv[4]; */
/* char *value = argv[5]; */
/* char *caller_name = argv[6]; */
/* uint32_t ring_on_idle = atoi(argv[7]); */
/* uint32_t ring_on_active = atoi(argv[8]); */
/* uint32_t busy_trigger = atoi(argv[9]); */
/* char *forward_all = argv[10]; */
/* char *forward_busy = argv[11]; */
/* char *forward_noanswer = argv[12]; */
/* uint32_t noanswer_duration = atoi(argv[13]); */
/* char *channel_uuid = argv[14]; */
uint32_t call_id = atoi(argv[15]);
/* uint32_t call_state = atoi(argv[16]); */
session = skinny_profile_find_session(helper->listener->profile, helper->listener, &line_instance, call_id);
if(session) {
skinny_session_hold_line(session, helper->listener, line_instance);
switch_core_session_rwunlock(session);
}
return 0;
}
switch_status_t skinny_hold_active_calls(listener_t *listener)
{
struct skinny_hold_active_calls_helper helper = {0};
char *sql;
helper.listener = listener;
if ((sql = switch_mprintf(
"SELECT skinny_lines.*, channel_uuid, call_id, call_state "
"FROM skinny_active_lines "
"INNER JOIN skinny_lines "
"ON skinny_active_lines.device_name = skinny_lines.device_name "
"AND skinny_active_lines.device_instance = skinny_lines.device_instance "
"AND skinny_active_lines.line_instance = skinny_lines.line_instance "
"WHERE skinny_lines.device_name='%s' AND skinny_lines.device_instance=%d AND call_state=%d",
listener->device_name, listener->device_instance, SKINNY_CONNECTED))) {
skinny_execute_sql_callback(listener->profile, listener->profile->sql_mutex, sql, skinny_hold_active_calls_callback, &helper);
switch_safe_free(sql);
}
return SWITCH_STATUS_SUCCESS;
}
/*****************************************************************************/
/* SKINNY BUTTONS */
/*****************************************************************************/
@ -1480,6 +1645,9 @@ switch_status_t skinny_handle_register(listener_t *listener, skinny_message_t *r
}
}
}
if (xroot) {
switch_xml_free(xroot);
}
status = SWITCH_STATUS_SUCCESS;
@ -1789,10 +1957,26 @@ switch_status_t skinny_handle_soft_key_set_request(listener_t *listener, skinny_
message->data.soft_key_set.total_soft_key_set_count = 11;
/* TODO fill the set */
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOOK].soft_key_template_index[0] = SOFTKEY_REDIAL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOOK].soft_key_template_index[1] = SOFTKEY_NEWCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOOK].soft_key_template_index[0] = SOFTKEY_NEWCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOOK].soft_key_template_index[1] = SOFTKEY_REDIAL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_OFF_HOOK].soft_key_template_index[1] = SOFTKEY_REDIAL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_OFF_HOOK].soft_key_template_index[2] = SOFTKEY_ENDCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT].soft_key_template_index[0] = SOFTKEY_BACKSPACE;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT].soft_key_template_index[2] = SOFTKEY_ENDCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_CONNECTED].soft_key_template_index[0] = SOFTKEY_ENDCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_RING_IN].soft_key_template_index[0] = SOFTKEY_ENDCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_CONNECTED].soft_key_template_index[1] = SOFTKEY_HOLD;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_CONNECTED].soft_key_template_index[2] = SOFTKEY_NEWCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_RING_IN].soft_key_template_index[0] = SOFTKEY_ANSWER;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_RING_IN].soft_key_template_index[1] = SOFTKEY_ENDCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_RING_IN].soft_key_template_index[2] = SOFTKEY_NEWCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOLD].soft_key_template_index[0] = SOFTKEY_NEWCALL;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOLD].soft_key_template_index[1] = SOFTKEY_RESUME;
message->data.soft_key_set.soft_key_set[SKINNY_KEY_SET_ON_HOLD].soft_key_template_index[2] = SOFTKEY_ENDCALL;
skinny_send_reply(listener, message);
@ -1931,7 +2115,6 @@ switch_status_t skinny_handle_soft_key_event_message(listener_t *listener, skinn
case SOFTKEY_NEWCALL:
status = skinny_create_ingoing_session(listener, &line_instance, &session);
tech_pvt = switch_core_session_get_private(session);
assert(tech_pvt != NULL);
skinny_session_process_dest(session, listener, line_instance, NULL, '\0', 0);
break;
@ -1942,6 +2125,13 @@ switch_status_t skinny_handle_soft_key_event_message(listener_t *listener, skinn
status = skinny_session_hold_line(session, listener, line_instance);
}
break;
case SOFTKEY_BACKSPACE:
session = skinny_profile_find_session(listener->profile, listener, &line_instance, request->data.soft_key_event.call_id);
if(session) {
skinny_session_process_dest(session, listener, line_instance, NULL, '\0', 1);
}
break;
case SOFTKEY_ENDCALL:
session = skinny_profile_find_session(listener->profile, listener, &line_instance, request->data.soft_key_event.call_id);
@ -1967,7 +2157,7 @@ switch_status_t skinny_handle_soft_key_event_message(listener_t *listener, skinn
break;
default:
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING,
"Unknown SoftKeyEvent type while busy: %d.\n", request->data.soft_key_event.event);
"Unknown SoftKeyEvent type: %d.\n", request->data.soft_key_event.event);
}
if(session) {
@ -2002,6 +2192,11 @@ switch_status_t skinny_handle_off_hook_message(listener_t *listener, skinny_mess
skinny_session_process_dest(session, listener, line_instance, NULL, '\0', 0);
}
if(session) {
switch_core_session_rwunlock(session);
}
return SWITCH_STATUS_SUCCESS;
}
@ -2037,6 +2232,11 @@ switch_status_t skinny_handle_stimulus_message(listener_t *listener, skinny_mess
default:
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Unknown Stimulus Type Received [%d]\n", request->data.stimulus.instance_type);
}
if(session) {
switch_core_session_rwunlock(session);
}
return SWITCH_STATUS_SUCCESS;
}
@ -2118,9 +2318,13 @@ switch_status_t skinny_handle_open_receive_channel_ack_message(listener_t *liste
}
switch_channel_mark_answered(channel);
switch_core_session_rwunlock(session);
}
end:
if(session) {
switch_core_session_rwunlock(session);
}
return status;
}
@ -2171,6 +2375,9 @@ switch_status_t skinny_handle_keypad_button_message(listener_t *listener, skinny
switch_channel_queue_dtmf(channel, &dtmf);
}
}
}
if(session) {
switch_core_session_rwunlock(session);
}
@ -2195,9 +2402,12 @@ switch_status_t skinny_handle_on_hook_message(listener_t *listener, skinny_messa
channel = switch_core_session_get_channel(session);
switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING);
}
if(session) {
switch_core_session_rwunlock(session);
}
return status;
}

View File

@ -630,6 +630,8 @@ switch_status_t skinny_session_answer(switch_core_session_t *session, listener_t
switch_status_t skinny_session_start_media(switch_core_session_t *session, listener_t *listener, uint32_t line_instance);
switch_status_t skinny_session_hold_line(switch_core_session_t *session, listener_t *listener, uint32_t line_instance);
switch_status_t skinny_session_unhold_line(switch_core_session_t *session, listener_t *listener, uint32_t line_instance);
switch_status_t skinny_session_stop_media(switch_core_session_t *session, listener_t *listener, uint32_t line_instance);
switch_status_t skinny_hold_active_calls(listener_t *listener);
void skinny_line_get(listener_t *listener, uint32_t instance, struct line_stat_res_message **button);
void skinny_speed_dial_get(listener_t *listener, uint32_t instance, struct speed_dial_stat_res_message **button);

View File

@ -15,6 +15,7 @@ use Sys::Hostname;
use Net::Skinny;
use Net::Skinny::Protocol qw/:all/;
use Net::Skinny::Message;
use Net::Skinny::Client;
#Config
my $skinny_server = hostname;
@ -23,13 +24,13 @@ my $device_ip = 10+256*(11+256*(12+256*13)); # 10.11.12.13
#======
$| = 1;
my $socket = Net::Skinny->new(
my $socket = Net::Skinny::Client->new(
PeerAddr => $skinny_server,
PeerPort => 2000,
);
if(!$socket) {
print "Unable to connect to server\n";
printf "Unable to connect to server %s\n", $skinny_server;
exit 1;
}
# =============================================================================
@ -84,11 +85,8 @@ $socket->send_message(
count => 2
);
for(my $i = 0; $i < 1; $i++) {
$socket->sleep(5);
$socket->send_message(KEEP_ALIVE_MESSAGE);
$socket->receive_message(); # keepaliveack
}
$socket->launch_keep_alive_thread();
$socket->sleep(5);
#NewCall

View File

@ -21403,21 +21403,36 @@ SWIGEXPORT char * SWIGSTDCALL CSharp_switch_channel_get_variable_partner(void *
}
SWIGEXPORT int SWIGSTDCALL CSharp_switch_channel_export_variable_var_check(void * jarg1, char * jarg2, char * jarg3, int jarg4, int jarg5) {
SWIGEXPORT int SWIGSTDCALL CSharp_switch_channel_export_variable_var_check(void * jarg1, char * jarg2, char * jarg3, int jarg4) {
int jresult ;
switch_channel_t *arg1 = (switch_channel_t *) 0 ;
char *arg2 = (char *) 0 ;
char *arg3 = (char *) 0 ;
switch_bool_t arg4 ;
switch_bool_t arg5 ;
switch_status_t result;
arg1 = (switch_channel_t *)jarg1;
arg2 = (char *)jarg2;
arg3 = (char *)jarg3;
arg4 = (switch_bool_t)jarg4;
arg5 = (switch_bool_t)jarg5;
result = (switch_status_t)switch_channel_export_variable_var_check(arg1,(char const *)arg2,(char const *)arg3,arg4,arg5);
result = (switch_status_t)switch_channel_export_variable_var_check(arg1,(char const *)arg2,(char const *)arg3,arg4);
jresult = result;
return jresult;
}
SWIGEXPORT int SWIGSTDCALL CSharp_switch_channel_export_variable_printf(void * jarg1, char * jarg2, char * jarg3) {
int jresult ;
switch_channel_t *arg1 = (switch_channel_t *) 0 ;
char *arg2 = (char *) 0 ;
char *arg3 = (char *) 0 ;
void *arg4 = 0 ;
switch_status_t result;
arg1 = (switch_channel_t *)jarg1;
arg2 = (char *)jarg2;
arg3 = (char *)jarg3;
result = (switch_status_t)switch_channel_export_variable_printf(arg1,(char const *)arg2,(char const *)arg3,arg4);
jresult = result;
return jresult;
}

View File

@ -2904,8 +2904,13 @@ public class freeswitch {
return ret;
}
public static switch_status_t switch_channel_export_variable_var_check(SWIGTYPE_p_switch_channel channel, string varname, string value, switch_bool_t var_check, switch_bool_t nolocal) {
switch_status_t ret = (switch_status_t)freeswitchPINVOKE.switch_channel_export_variable_var_check(SWIGTYPE_p_switch_channel.getCPtr(channel), varname, value, (int)var_check, (int)nolocal);
public static switch_status_t switch_channel_export_variable_var_check(SWIGTYPE_p_switch_channel channel, string varname, string value, switch_bool_t var_check) {
switch_status_t ret = (switch_status_t)freeswitchPINVOKE.switch_channel_export_variable_var_check(SWIGTYPE_p_switch_channel.getCPtr(channel), varname, value, (int)var_check);
return ret;
}
public static switch_status_t switch_channel_export_variable_printf(SWIGTYPE_p_switch_channel channel, string varname, string fmt) {
switch_status_t ret = (switch_status_t)freeswitchPINVOKE.switch_channel_export_variable_printf(SWIGTYPE_p_switch_channel.getCPtr(channel), varname, fmt);
return ret;
}
@ -10215,7 +10220,10 @@ class freeswitchPINVOKE {
public static extern string switch_channel_get_variable_partner(HandleRef jarg1, string jarg2);
[DllImport("mod_managed", EntryPoint="CSharp_switch_channel_export_variable_var_check")]
public static extern int switch_channel_export_variable_var_check(HandleRef jarg1, string jarg2, string jarg3, int jarg4, int jarg5);
public static extern int switch_channel_export_variable_var_check(HandleRef jarg1, string jarg2, string jarg3, int jarg4);
[DllImport("mod_managed", EntryPoint="CSharp_switch_channel_export_variable_printf")]
public static extern int switch_channel_export_variable_printf(HandleRef jarg1, string jarg2, string jarg3);
[DllImport("mod_managed", EntryPoint="CSharp_switch_channel_get_variable_dup")]
public static extern string switch_channel_get_variable_dup(HandleRef jarg1, string jarg2, int jarg3);