Re: Win32 talking to *nix question

From: M. Said (muneers_at_xmail.com)
Date: 02/17/04


Date: Tue, 17 Feb 2004 14:30:10 -0600

Ok, here is something I did a while ago in perl (should be available on most
*nix system, and windows, and ....)

Please read the code carefuly, and change it to get it to do what YOU want
it to do.
THIS CODE WAS NOT WRITTEN TO BE SECURE, YOU CAN RUN ANYTHING WITH IT. YOUR
SYSTEM IS WIDE OPEN.

run cmd_server.pl on the server
run do_cmd.pl <hostname> "command" on the client

If you can open a socket in delphi, you should be able to get this to work
for you.

do_cmd.pl:
--------------------------------------------------------------------
#!/usr/local/bin/perl

use IO::Socket;

$host = $ARGV[0];
$cmd = $ARGV[1];

if ($#ARGV != 1) {
 print "Incorrect number of arguments.\n";
 print "Syntax: do_cmd.pl [host] \"[command]\"\n";
 exit;
}
$socket = IO::Socket::INET->new(PeerAddr => $host,
    PeerPort => '9888',
    Proto => 'tcp');
if ($socket) {
 $socket->autoflush(1);
 send($socket,$cmd . "\n", 0);
 $socket->flush();
 print ">>>> $host: RESPONSE:\n";
 while ($res = <$socket>) {
  print $res;
 }
 print ">>>> END.\n";
 close($socket);
} else {
 print "Error Connecting to cmd_server on $host\n";
}
----------------------------------------------------------------------------

cmd_server.pl:
---------------------------------------------------------------------------
#!/usr/local/bin/perl
use strict;
use POSIX qw(setsid);
use IO::Socket;

my($port) = 9888;
my($run) = 1;
my($server_socket);
my($log_file) = "/tmp/cmd_server.log";

my(%weekday) =(
  "0" => "Sun",
  "1" => "Mon",
  "2" => "Tue",
  "3" => "Wed",
  "4" => "Thu",
  "5" => "Fri",
  "6" => "Sat");

sub time_stamp {
  my($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst);
  my($ret_val);

  ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst)=localtime(time);
  $ret_val = sprintf("%3s %02d/%02d/%04d at %02d:%02d:%02d",
        $weekday{"$wday"},
        $mon+1,$mday,(1900 + $year),
        $hour,$min,$sec);

  return($ret_val);
}

sub log_msg {
 my($msg) = @_;

 open(LOG,">> $log_file");
 print LOG time_stamp() . ": " . $msg . "\n";
 close(LOG);
}

sub start_server {

 $server_socket = IO::Socket::INET->new(
   Proto=>"tcp",
   LocalPort=>$port,
   Listen=>"20") or die "Can't start server socket!\n";
}

sub do_cmd {
 my($command) = join(' ',@_);
 my($res,$line);
 $res = "";
 log_msg("Executing: $command");
 if (! open(CMD,"$command |" ) ) {
  log_msg("ERROR: Could not execute command: $command");
 }
 while ($line = <CMD>) {
  $res = $res . $line;
 }
 close(CMD);
 return($res);
}

sub daemonize {
    chdir '/' or die "Can't chdir to /: $!";
    open STDIN, '/dev/null' or die "Can't read /dev/null: $!";
    open STDOUT, '>>/dev/null' or die "Can't write to /dev/null: $!";
    open STDERR, '>>/dev/null' or die "Can't write to /dev/null: $!";
    defined(my $pid = fork) or die "Can't fork: $!";
    exit if $pid;
    setsid or die "Can't start a new session: $!";
    # umask 0;
}

sub main {
 log_msg "Starting Server ...";
 start_server();
 log_msg "Started.";
 while ($run) {
  my($remote_socket) = $server_socket->accept();
  # Is it a valid socket. In case signal unblocks accept
  if ($remote_socket) {
   $remote_socket->autoflush(1);
   my($c) = $remote_socket->peerhost ;
   my($len) = 1024;
   my($cmd);
   recv($remote_socket,$cmd,$len,0);
   my($res) = "\n";

   # Resolve IP to hostname
   my($port,$iaddr) = sockaddr_in(getpeername($remote_socket));
   my($n) = gethostbyaddr($iaddr,AF_INET);
   if ( $n eq "") {
    $n = $c;
   }
   my($res) = do_cmd($cmd);
   send($remote_socket, $res. "\n", 0);
   close($remote_socket);
  }

 }
 close($server_socket);
 exit(0);
}

daemonize();
main();

----------------------- END ---------------------------

"Davids" <nowhere@nowthere.com> wrote in message
news:403168F1.4A594799@nowthere.com...
> I have a small Delphi app that runs under Windows. It uses FTP to fetch a
file
> from a remote Linux system, do some processing on it, and save the results
> locally.
>
> The file it grabs is output by running a process on the Linux box first.
I'd
> really like to have this app trigger that process when the user runs it,
rather
> than have it run as a cron job or manually run via SSH. Is it possible to
run a
> shell script via FTP? Or is there another way to do it simply?
>
> I've got the script file that runs it set up with SetUID perms, so all I
need to
> do is run it with a command that specifies an output file name -- or, even
> better, suck the standard output (which is text) directly into the Windows
app.
>
> Suggestions?
>
> TIA
> -David
>



Relevant Pages

  • Overriding the "X" control and using WndProc
    ... I have an application that should run in the system tray while open. ... the "X" button is pushed on the form...but without closing the app. ... > Private Sub frmMain_Closing(ByVal sender As Object, ... and windows can't shutdown without closing my app first. ...
    (microsoft.public.dotnet.languages.vb)
  • Re: recv blocks although socket is ready
    ... IRIX, IRIX64, Linux, OSF1, SunOS and Windows. ... Running the same app on the same hardware under Linux ... Another point which seems worth noting is, ... frequently when there is some UDP traffic on another socket. ...
    (microsoft.public.win32.programmer.networks)
  • Re: correct way to use an I/O thread to emulate old blocking hook behavior?
    ... If you've ever seen a "hung" app, ... So, instead, the "blocking hook" was created. ... because of course it makes your Windows ... socket operations completing. ...
    (microsoft.public.win32.programmer.networks)
  • Re: Info on Tcls channel system (specifically file events) needed
    ... >I don't know a thing about windows, so the following may be utterly ... but in unix I would simply open a domain socket and use ... I do know that there are other means than shared memory to have 2 apps ... One app is of course Tcl based, but the other need not be. ...
    (comp.lang.tcl)
  • Re: Sub Main
    ... >> In my Windows Forms app, I tried using a Sub Main as my startup object. ... > Public Class AppMain ...
    (microsoft.public.dotnet.languages.vb)