From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 28974 invoked by alias); 22 May 2008 20:04:15 -0000 Received: (qmail 28913 invoked by uid 367); 22 May 2008 20:04:14 -0000 Date: Thu, 22 May 2008 20:04:00 -0000 Message-ID: <20080522200414.28895.qmail@sourceware.org> From: cagney@sourceware.org To: frysk-cvs@sourceware.org Subject: [SCM] master: Implement jni/PipePair. X-Git-Refname: refs/heads/master X-Git-Reftype: branch X-Git-Oldrev: bdd9bad5f20ab08bd3f23c1db6db0c43e46b40a0 X-Git-Newrev: 9a7034197f14ad2d56254fc9c1ad74a395e98a46 Mailing-List: contact frysk-cvs-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Post: List-Help: , Sender: frysk-cvs-owner@sourceware.org Reply-To: frysk@sourceware.org X-SW-Source: 2008-q2/txt/msg00272.txt.bz2 The branch, master has been updated via 9a7034197f14ad2d56254fc9c1ad74a395e98a46 (commit) from bdd9bad5f20ab08bd3f23c1db6db0c43e46b40a0 (commit) Those revisions listed above that are new to this repository have not appeared on any other notification email. - Log ----------------------------------------------------------------- commit 9a7034197f14ad2d56254fc9c1ad74a395e98a46 Author: Andrew Cagney Date: Thu May 22 16:02:47 2008 -0400 Implement jni/PipePair. frysk-core/frysk/proc/ChangeLog 2008-05-22 Andrew Cagney * TestBreakpoints.java: Update, use PipePair.daemon. * TestSyscallRunning.java: Ditto. * TestSyscallSignal.java: Ditto. frysk-sys/ChangeLog 2008-05-22 Andrew Cagney * Makefile.am (JniRunner): Add frysk.sys.TestPipePair. frysk-sys/frysk/sys/ChangeLog 2008-05-22 Andrew Cagney * PipePair.java (daemon, child): New factory methods. * cni/PipePair.cxx: New. * jni/PipePair.cxx: New. * DaemonPipePair.java: Delete. * ChildPipePair.java: Delete. * TestPipePair.java: Update. ----------------------------------------------------------------------- Summary of changes: frysk-core/frysk/proc/ChangeLog | 6 ++ frysk-core/frysk/proc/TestBreakpoints.java | 9 +- frysk-core/frysk/proc/TestSyscallRunning.java | 9 +- frysk-core/frysk/proc/TestSyscallSignal.java | 10 +-- frysk-sys/ChangeLog | 2 + frysk-sys/Makefile.am | 1 + frysk-sys/frysk/sys/ChangeLog | 7 ++ frysk-sys/frysk/sys/PipePair.java | 85 +++++++++----------- frysk-sys/frysk/sys/TestPipePair.java | 14 ++-- .../sys/{DaemonPipePair.java => cni/PipePair.cxx} | 75 ++++++++++++++---- .../sys/{ChildPipePair.java => jni/PipePair.cxx} | 85 +++++++++++++++----- 11 files changed, 195 insertions(+), 108 deletions(-) rename frysk-sys/frysk/sys/{DaemonPipePair.java => cni/PipePair.cxx} (56%) rename frysk-sys/frysk/sys/{ChildPipePair.java => jni/PipePair.cxx} (55%) First 500 lines of diff: diff --git a/frysk-core/frysk/proc/ChangeLog b/frysk-core/frysk/proc/ChangeLog index d5b5a7f..47e0c51 100644 --- a/frysk-core/frysk/proc/ChangeLog +++ b/frysk-core/frysk/proc/ChangeLog @@ -1,3 +1,9 @@ +2008-05-22 Andrew Cagney + + * TestBreakpoints.java: Update, use PipePair.daemon. + * TestSyscallRunning.java: Ditto. + * TestSyscallSignal.java: Ditto. + 2008-05-13 Phil Muldoon * TestTaskObserverWatchpoint.java (testAddFailed): Add alignment test. diff --git a/frysk-core/frysk/proc/TestBreakpoints.java b/frysk-core/frysk/proc/TestBreakpoints.java index 97514d7..3e6e2ff 100644 --- a/frysk-core/frysk/proc/TestBreakpoints.java +++ b/frysk-core/frysk/proc/TestBreakpoints.java @@ -47,8 +47,8 @@ import java.io.InputStreamReader; import java.io.IOException; import frysk.testbed.TestLib; import frysk.testbed.TearDownProcess; +import frysk.sys.PipePair; import frysk.config.Prefix; -import frysk.sys.DaemonPipePair; public class TestBreakpoints extends TestLib @@ -85,10 +85,9 @@ public class TestBreakpoints installInstructionObserver = false; // Create a process that we will communicate with through stdin/out. - DaemonPipePair process - = new DaemonPipePair(new String[] { - Prefix.pkgLibFile("funit-breakpoints").getPath() - }); + PipePair process = PipePair.daemon(new String[] { + Prefix.pkgLibFile("funit-breakpoints").getPath() + }); TearDownProcess.add(process.pid); in = new BufferedReader(new InputStreamReader(process.in.getInputStream())); out = new DataOutputStream(process.out.getOutputStream()); diff --git a/frysk-core/frysk/proc/TestSyscallRunning.java b/frysk-core/frysk/proc/TestSyscallRunning.java index 2f04ada..266f455 100644 --- a/frysk-core/frysk/proc/TestSyscallRunning.java +++ b/frysk-core/frysk/proc/TestSyscallRunning.java @@ -50,7 +50,7 @@ import frysk.event.Event; import frysk.testbed.TestLib; import frysk.testbed.TearDownProcess; import frysk.config.Prefix; -import frysk.sys.DaemonPipePair; +import frysk.sys.PipePair; import frysk.isa.syscalls.SyscallTable; import frysk.isa.syscalls.SyscallTableFactory; import frysk.testbed.IsaTestbed; @@ -81,10 +81,9 @@ public class TestSyscallRunning super.setUp(); // Create a process that we will communicate with through stdin/out. - DaemonPipePair process - = new DaemonPipePair(new String[] { - Prefix.pkgLibFile("funit-syscall-running").getPath() - }); + PipePair process = PipePair.daemon(new String[] { + Prefix.pkgLibFile("funit-syscall-running").getPath() + }); TearDownProcess.add(process.pid); in = new BufferedReader(new InputStreamReader(process.in.getInputStream())); diff --git a/frysk-core/frysk/proc/TestSyscallSignal.java b/frysk-core/frysk/proc/TestSyscallSignal.java index dc5c779..dca055a 100644 --- a/frysk-core/frysk/proc/TestSyscallSignal.java +++ b/frysk-core/frysk/proc/TestSyscallSignal.java @@ -45,7 +45,7 @@ import java.io.DataOutputStream; import java.io.IOException; import java.io.InputStreamReader; import frysk.sys.Signal; -import frysk.sys.DaemonPipePair; +import frysk.sys.PipePair; import frysk.testbed.TestLib; import frysk.isa.syscalls.Syscall; import frysk.isa.syscalls.SyscallTable; @@ -82,11 +82,9 @@ public class TestSyscallSignal super.setUp(); // Create a process that we will communicate with through stdin/out. - DaemonPipePair process - = new DaemonPipePair(new String[] { - Prefix.pkgLibFile("funit-syscall-signal") - .getPath() - }); + PipePair process = PipePair.daemon(new String[] { + Prefix.pkgLibFile("funit-syscall-signal").getPath() + }); pid = process.pid; TearDownProcess.add(pid); in = new BufferedReader(new InputStreamReader(process.in.getInputStream())); diff --git a/frysk-sys/ChangeLog b/frysk-sys/ChangeLog index 5dd0474..3be6951 100644 --- a/frysk-sys/ChangeLog +++ b/frysk-sys/ChangeLog @@ -1,5 +1,7 @@ 2008-05-22 Andrew Cagney + * Makefile.am (JniRunner): Add frysk.sys.TestPipePair. + * Makefile.am (JniRunner): Add frysk.testbed. * Makefile.am (JniRunner): Add TestStatelessFile and diff --git a/frysk-sys/Makefile.am b/frysk-sys/Makefile.am index dbc9742..d65e207 100644 --- a/frysk-sys/Makefile.am +++ b/frysk-sys/Makefile.am @@ -99,6 +99,7 @@ JniRunner: | frysk-sys.jar libfrysk-sys-jni.so echo " frysk.rsl \\" >> $@.tmp echo " frysk.sys.proc \\" >> $@.tmp echo " frysk.sys.termios \\" >> $@.tmp + echo " frysk.sys.TestPipePair \\" >> $@.tmp echo " frysk.sys.TestProcessIdentifier \\" >> $@.tmp echo " frysk.sys.TestPseudoTerminal \\" >> $@.tmp echo " frysk.sys.TestSignal \\" >> $@.tmp diff --git a/frysk-sys/frysk/sys/ChangeLog b/frysk-sys/frysk/sys/ChangeLog index 887b67c..8e0b43d 100644 --- a/frysk-sys/frysk/sys/ChangeLog +++ b/frysk-sys/frysk/sys/ChangeLog @@ -1,5 +1,12 @@ 2008-05-22 Andrew Cagney + * PipePair.java (daemon, child): New factory methods. + * cni/PipePair.cxx: New. + * jni/PipePair.cxx: New. + * DaemonPipePair.java: Delete. + * ChildPipePair.java: Delete. + * TestPipePair.java: Update. + * jni/Fork.hxx (class redirect_nostdin): New. * cni/Fork.hxx (class redirect_nostdin): New. diff --git a/frysk-sys/frysk/sys/PipePair.java b/frysk-sys/frysk/sys/PipePair.java index daaddf9..c150f02 100644 --- a/frysk-sys/frysk/sys/PipePair.java +++ b/frysk-sys/frysk/sys/PipePair.java @@ -47,8 +47,7 @@ package frysk.sys; * The child process is created using the method spawn. */ -public abstract class PipePair -{ +public abstract class PipePair { /** * Write to this file descriptor. */ @@ -64,67 +63,61 @@ public abstract class PipePair /** * Create a pipe-pair and then wire it up. * - * this > out.out|out.in > child > in.out|in.in > this + * this.out > [ out.out | out.in > child > in.out | in.in ] > this.in * * Spawn is parameterized with the Object o, allowing custom * behavior. The child must close to.out and from.in. */ - protected PipePair (Execute execute) - { - final Pipe out = new Pipe (); - final Pipe in = new Pipe (); - // Wire: this.out > to.out + protected PipePair(String[] args) { + Pipe out = new Pipe (); + Pipe in = new Pipe (); + // Wire: this.out > out.out this.out = out.out; - // Wire: from.in > this.in + // Wire: in.in > this.in this.in = in.in; // Wire: out.in > child > to.out - pid = spawn (new RedirectPipes (out, in), execute); - } - - private static class RedirectPipes - extends Redirect - { - private Pipe out; - private Pipe in; - RedirectPipes (Pipe out, Pipe in) - { - this.out = out; - this.in = in; - } - /** - * Executed by the child process - re-direct child's end of - * pipes to STDIN and STDOUT. - */ - protected void reopen () - { - FileDescriptor.in.dup (out.in); - FileDescriptor.out.dup (in.out); - in.close (); - out.close (); - } - /** - * Executed by the parent process (this) - close child's ends - * of pipes. - */ - protected void close () - { - out.in.close (); - in.out.close (); - } + pid = ProcessIdentifierFactory.create(spawn(args, in, out)); + // Close the child's end of the FDs. + out.in.close(); + in.out.close(); } /** * Called from the context of the child process. */ - protected abstract ProcessIdentifier spawn (Redirect redirect, - Execute exec); + abstract int spawn(String[] args, Pipe in, Pipe out); /** * Shut down the pipes. */ - public void close () - { + public void close() { in.close (); out.close (); } + + public static PipePair daemon(String[] args) { + return new PipePair(args) { + int spawn(String[] args, Pipe in, Pipe out) { + return PipePair.daemon(args[0], args, + in.in.getFd(), in.out.getFd(), + out.in.getFd(), out.out.getFd()); + } + }; + } + private static native int daemon(String exe, String[] args, + int in_in, int in_out, + int out_in, int out_out); + + public static PipePair child(String[] args) { + return new PipePair(args) { + int spawn(String[] args, Pipe in, Pipe out) { + return PipePair.child(args[0], args, + in.in.getFd(), in.out.getFd(), + out.in.getFd(), out.out.getFd()); + } + }; + } + private static native int child(String exe, String[] args, + int in_in, int in_out, + int out_in, int out_out); } diff --git a/frysk-sys/frysk/sys/TestPipePair.java b/frysk-sys/frysk/sys/TestPipePair.java index e5a6daf..4b182e6 100644 --- a/frysk-sys/frysk/sys/TestPipePair.java +++ b/frysk-sys/frysk/sys/TestPipePair.java @@ -97,14 +97,12 @@ public class TestPipePair extends TestCase { /** * Test a daemon Pipe pair. */ - public void testDaemonTee () - { - pipe = new DaemonPipePair (tee); + public void testDaemonTee() { + pipe = PipePair.daemon(tee); verifyIO (); } - public void testChildTee () - { - pipe = new ChildPipePair (tee); + public void testChildTee() { + pipe = PipePair.child(tee); verifyIO (); } @@ -124,7 +122,7 @@ public class TestPipePair extends TestCase { assertTrue("SIGHUP masked", new SignalSet().getProcMask().contains(Signal.HUP)); fine.log("Creating funit-procmask to check the mask"); - pipe = new DaemonPipePair(funitProcMask); + pipe = PipePair.daemon(funitProcMask); // For a daemon, it isn't possible to capture the processes // exit status; instead read the output and check for the word // "absent". @@ -143,7 +141,7 @@ public class TestPipePair extends TestCase { assertTrue("SIGHUP masked", new SignalSet().getProcMask().contains(Signal.HUP)); fine.log("Creating funit-procmask to check the mask"); - pipe = new ChildPipePair(funitProcMask); + pipe = PipePair.child(funitProcMask); // Capture the child's output (look for class ExitStatus extends UnhandledWaitBuilder { ProcessIdentifier pid; diff --git a/frysk-sys/frysk/sys/DaemonPipePair.java b/frysk-sys/frysk/sys/cni/PipePair.cxx similarity index 56% rename from frysk-sys/frysk/sys/DaemonPipePair.java rename to frysk-sys/frysk/sys/cni/PipePair.cxx index b040b3c..8ffdd96 100644 --- a/frysk-sys/frysk/sys/DaemonPipePair.java +++ b/frysk-sys/frysk/sys/cni/PipePair.cxx @@ -1,6 +1,6 @@ // This file is part of the program FRYSK. // -// Copyright 2007, Red Hat Inc. +// Copyright 2008 Red Hat Inc. // // FRYSK is free software; you can redistribute it and/or modify it // under the terms of the GNU General Public License as published by @@ -37,22 +37,65 @@ // version and license this file solely under the GPL without // exception. -package frysk.sys; +#include +#include +#include -/** - * A pair of pipes wired to a daemon process. - */ +#include -public class DaemonPipePair extends PipePair { - protected ProcessIdentifier spawn(Redirect redirect, - Execute exec) { - return DaemonFactory.create(redirect, exec); - } - public DaemonPipePair(String[] argv) { - super(new Exec (argv)); - } +#include "frysk/sys/cni/Errno.hxx" +#include "frysk/sys/cni/Fork.hxx" +#include "frysk/sys/PipePair.h" - public DaemonPipePair(Execute exec) { - super(exec); - } +class redirect_inout : public redirect { +private: + int in_in; + int in_out; + int out_in; + int out_out; +public: + redirect_inout(int in_in, int in_out, int out_in, int out_out) { + this->in_in = in_in; + this->in_out = in_out; + this->out_in = out_in; + this->out_out = out_out; + } + // this.out > [ out.out | out.in > child > in.out | in.in ] > this.in + void reopen() { + // Rewire: out.in > child's in + ::dup2(out_in, 0); + // Rewire: in.out > child's out + ::dup2(in_out, 1); + // Close the pipes. + ::close(in_in); + ::close(in_out); + ::close(out_in); + ::close(out_out); + } +}; + +static jint +spawn(enum tracing trace, jstring exe, + jstringArray args, + jint in_in, jint in_out, + jint out_in, jint out_out) { + redirect_inout inout = redirect_inout(in_in, in_out, out_in, out_out); + exec_program program = exec_program(exe, args, 0); + return ::spawn(trace, inout, program); +} + +jint +frysk::sys::PipePair::child(jstring exe, + jstringArray args, + jint in_in, jint in_out, + jint out_in, jint out_out) { + return ::spawn(CHILD, exe, args, in_in, in_out, out_in, out_out); +} + +jint +frysk::sys::PipePair::daemon(jstring exe, + jstringArray args, + jint in_in, jint in_out, + jint out_in, jint out_out) { + return ::spawn(DAEMON, exe, args, in_in, in_out, out_in, out_out); } diff --git a/frysk-sys/frysk/sys/ChildPipePair.java b/frysk-sys/frysk/sys/jni/PipePair.cxx similarity index 55% rename from frysk-sys/frysk/sys/ChildPipePair.java rename to frysk-sys/frysk/sys/jni/PipePair.cxx index bbe62c9..edc3a84 100644 --- a/frysk-sys/frysk/sys/ChildPipePair.java +++ b/frysk-sys/frysk/sys/jni/PipePair.cxx @@ -1,6 +1,6 @@ // This file is part of the program FRYSK. // -// Copyright 2007, Red Hat Inc. +// Copyright 2008 Red Hat Inc. // // FRYSK is free software; you can redistribute it and/or modify it // under the terms of the GNU General Public License as published by @@ -37,25 +37,66 @@ // version and license this file solely under the GPL without // exception. -package frysk.sys; - -/** - * An abstract class for creating a pair of pipes wired up to a child - * process, with OUT wired to the child's STDIN, and IN wired to the - * child's stdout. - * - * The child process is created using the method spawn. - */ - -public class ChildPipePair extends PipePair { - protected ProcessIdentifier spawn(Redirect redirect, - Execute exec) { - return ChildFactory.create(redirect, exec); - } - public ChildPipePair(String[] argv) { - super(new Exec(argv)); - } - public ChildPipePair(Execute exec) { - super(exec); - } +#include +#include +#include + +#include "jni.hxx" + +#include "jnixx/elements.hxx" +#include "frysk/sys/jni/Fork.hxx" + +using namespace java::lang; + +class redirect_inout : public redirect { +private: + int in_in; + int in_out; + int out_in; + int out_out; +public: + redirect_inout(int in_in, int in_out, int out_in, int out_out) { + this->in_in = in_in; + this->in_out = in_out; + this->out_in = out_in; + this->out_out = out_out; + } + // this.out > [ out.out | out.in > child > in.out | in.in ] > this.in + void reopen() { + // Rewire: out.in > child's in + ::dup2(out_in, 0); + // Rewire: in.out > child's out + ::dup2(in_out, 1); + // Close the pipes. + ::close(in_in); + ::close(in_out); + ::close(out_in); + ::close(out_out); + } +}; + +static jint +spawn(jnixx::env env, enum tracing trace, String exe, + jnixx::array args, + jint in_in, jint in_out, + jint out_in, jint out_out) { + redirect_inout inout = redirect_inout(in_in, in_out, out_in, out_out); + exec_program program = exec_program(env, exe, args, 0); + return ::spawn(env, trace, inout, program); +} + +jint +frysk::sys::PipePair::child(jnixx::env env, String exe, + jnixx::array args, + jint in_in, jint in_out, + jint out_in, jint out_out) { + return ::spawn(env, CHILD, exe, args, in_in, in_out, out_in, out_out); +} + +jint +frysk::sys::PipePair::daemon(jnixx::env env, String exe, + jnixx::array args, + jint in_in, jint in_out, + jint out_in, jint out_out) { + return ::spawn(env, DAEMON, exe, args, in_in, in_out, out_in, out_out); } hooks/post-receive -- frysk system monitor/debugger