Voice Server

This project implements a TCP/IP client and server using Perl and links the server to a voice synthesiser.


Click here to check out other projects.

Click to search the Acacia site
Click to search using Google

It allows you to type

	say "Hello there"

on one PC and have the voice server speak the words.

Impress your friends, intimidate burglars or adapt it to other uses - up to you!

Hardware

The following hardware is required:

Software

The software listed below is needed:

Ideas

Code

The server code:

#!/usr/bin/perl
#---------------------------------------------------------------
# TCP/IP Server
#
# Based on sample server p988 of Perl Black Book.
#
# Written 9/9/01: G.Collett
#---------------------------------------------------------------
# To do...
# - log data
# - handle piped data
#---------------------------------------------------------------

#---------------------------------------------------------------
# Initialisation
#---------------------------------------------------------------

# Use the socket library
use IO::Socket;

# Determine the current date and time
$now = `date +%Y%m%d%H%M%S`;
chop($now);

# Automatically flush output
$| = 1;

# Catch signals
$SIG{HUP} = \&CloseUp; #-1
$SIG{INT} = \&CloseUp; #-2
$SIG{QUIT} = \&CloseUp; #-3
$SIG{TRAP} = \&CloseUp; #-5
$SIG{KILL} = \&CloseUp; #-9
$SIG{TERM} = \&CloseUp; #-15
$SIG{STOP} = \&CloseUp; #-17

# Open a file to log all output
open(LOG, ">>server.log") or die "Unable to open log file\n";
print LOG "\n\n";
print LOG "-------------------------------------------\n";
print LOG "Starting server at $now...\n";
LOG->flush;



#---------------------------------------------------------------
# Start a listener on the local host port 8888 for 5 clients max
#---------------------------------------------------------------
$sock = new IO::Socket::INET->new
(
	LocalAddr => '192.16.16.16',
	LocalPort => 8888,
	Proto     => 'tcp',
	Reuse     => 1,
	Listen    => 5
) or die "Unable to start server: $!\n";
$sock->autoflush(1);
# Determine the current date and time
$now = `date +%Y%m%d%H%M%S`;
chop($now);

print LOG "Server started at $now\n\n";
LOG->flush;



#---------------------------------------------------------------
# Accept client connections
#---------------------------------------------------------------
while ($client = $sock->accept())
{
	#---------------------------------------------------------------
	# Now fork a thread to handle the client connection
	#---------------------------------------------------------------
	$| = 1;
	$client_addr = $client->peerhost;
	#print LOG "Client has connected from $client_addr\n";
	LOG->flush;
	unless (defined($child_pid = fork()))
		{
		die "Cannot fork\n";
		}


	#---------------------------------------------------------------
	# Child thread (handles client connections)
	#---------------------------------------------------------------
	if ($child_pid)
	{
		$| = 1;
		while ($line = <$client>)
		{
			chop($line);
			# Determine the current date and time
			$now = `date +%Y%m%d%H%M%S`;
			chop($now);

			print LOG "$now|$client_addr|$line\n";
			LOG->flush;

			&ProcessCmd($client_addr, $line);
		}
		LOG->flush;
		$client->flush;
		close($client);
#		print LOG "Child ended\n";
#		LOG->flush;
		exit;
	}


	# Parent thread just loops back and listen for more connections
}

&CloseUp;
exit;



#---------------------------------------------------------------
# Catch all signals and shutdown gracefully.
#---------------------------------------------------------------
sub CloseUp
{
	my $signal = shift;

	print LOG "Server received signal [$signal].  Shutting down.\n";
	close($client);
	close($sock);
	close(LOG);
	exit;
}



#---------------------------------------------------------------
# Process commands from authorised hosts
#---------------------------------------------------------------
sub ProcessCmd
{
	local ($client_addr, $line) = @_;

	if ($client_addr eq '192.16.16.17')
		{
		if ($line eq 'FIREWALLUP')
			{
				$msg = "ADSL Connection is back on line at $now.";
			  `echo "$msg" | smbclient -M TERMINATOR`;
				`echo "$msg" | smbclient -M GCLT2`;
				`echo "$msg" | smbclient -M BRAD`;
				`echo "$msg" | smbclient -M ERIN`;
				`echo "$msg" | smbclient -M PEGASUS`;
			}
		if ($line eq 'FIREWALLDOWN')
			{
				$msg = "ADSL Connection has dropped out at $now.  Please reset the modem.";
			  `echo "$msg" | smbclient -M TERMINATOR`;
				`echo "$msg" | smbclient -M GCLT2`;
				`echo "$msg" | smbclient -M BRAD`;
				`echo "$msg" | smbclient -M ERIN`;
				`echo "$msg" | smbclient -M PEGASUS`;
			}
		}
	else
		{
		print LOG "Client $client_addr not authorised\n";
		}
}

The client code:

#!/usr/bin/perl
#---------------------------------------------------------------
# TCP/IP Client
#
# Based on sample server p988 of Perl Black Book.
#
# Written 9/9/01: G.Collett
#---------------------------------------------------------------


#---------------------------------------------------------------
# Initialisation
#---------------------------------------------------------------

# Use the socket library
use IO::Socket;

# Automatically flush output
$| = 1;

# Catch signals
$SIG{HUP} = \&CloseUp; #-1
$SIG{INT} = \&CloseUp; #-2
$SIG{QUIT} = \&CloseUp; #-3
$SIG{TRAP} = \&CloseUp; #-5
$SIG{KILL} = \&CloseUp; #-9
$SIG{TERM} = \&CloseUp; #-15
$SIG{STOP} = \&CloseUp; #-17



#---------------------------------------------------------------
# Start a connection to the server
#---------------------------------------------------------------
print "Connecting to server....\n";
$sock = new IO::Socket::INET->new
(
  PeerAddr => '192.16.16.16',
  PeerPort => 8888,
  Proto     => 'tcp',
  Reuse     => 1,
  Timeout   => 5,
  Type    => SOCK_STREAM
) or die "Unable to connect to server: $!";
$sock->autoflush(1);
print "Connected\n\n";



#---------------------------------------------------------------
# Send all STDIN to the server
#---------------------------------------------------------------
STDIN->autoflush(1);
until (eof(STDIN))
{
  $line = ;
  chop($line);

  # Write STDIN to the socket
  print $sock "$line\n";
  print "Sent [$line]\n";
}

ALLDONE:
  # input complete so close up and exit
  $sock->flush;
  close($sock);


exit;



#---------------------------------------------------------------
# Catch all signals and shutdown gracefully.
#---------------------------------------------------------------
sub CloseUp
{
  my $signal = shift;

  print "Server received signal [$signal].  Shutting down.\n";
  close($sock);
  exit;
}


Client utilities: Application: "say"

#!/usr/local/bin/perl
$msg  = $ARGV[0];
print `echo "$msg" |  voice_client.pl`;
exit;

Click here to check out the list of other projects.

You may also like to click here to check out the list of Artificial Intelligence projects.

If you would like to get any further information on this or any of the other projects shown on this web site, please send an email to Acacia Lateral Technologies. or place a comment in our Guest Book

You might also like to submit your idea to our Free Ideas page for the benefit of other like-minded soles.