cdev-1.7.2n
This commit is contained in:
BIN
extensions/ScriptService/doc/cdevScriptService.book
Executable file
BIN
extensions/ScriptService/doc/cdevScriptService.book
Executable file
Binary file not shown.
BIN
extensions/ScriptService/doc/cdevScriptService.doc
Executable file
BIN
extensions/ScriptService/doc/cdevScriptService.doc
Executable file
Binary file not shown.
BIN
extensions/ScriptService/doc/cdevScriptServiceLOF.doc
Executable file
BIN
extensions/ScriptService/doc/cdevScriptServiceLOF.doc
Executable file
Binary file not shown.
BIN
extensions/ScriptService/doc/cdevScriptServiceTITLE.doc
Executable file
BIN
extensions/ScriptService/doc/cdevScriptServiceTITLE.doc
Executable file
Binary file not shown.
BIN
extensions/ScriptService/doc/cdevScriptServiceTOC.doc
Executable file
BIN
extensions/ScriptService/doc/cdevScriptServiceTOC.doc
Executable file
Binary file not shown.
BIN
extensions/ScriptService/doc/html/bullet.jpg
Executable file
BIN
extensions/ScriptService/doc/html/bullet.jpg
Executable file
Binary file not shown.
|
After Width: | Height: | Size: 948 B |
948
extensions/ScriptService/doc/html/cdevScriptService.html
Executable file
948
extensions/ScriptService/doc/html/cdevScriptService.html
Executable file
@@ -0,0 +1,948 @@
|
||||
<! This document generated using mif2html Version 1.0 - Walt Akers - 1996 !>
|
||||
<head>
|
||||
<title>CDEV Script Service</title>
|
||||
</head>
|
||||
|
||||
<body bgcolor="#E0E0FF">
|
||||
|
||||
<body>
|
||||
<! ************************ FILE : cdevScriptServiceTITLE.mif *****************************!>
|
||||
<br><hr><br>
|
||||
<table width=100%>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start ADDRESS-VERSION ***!><font size=+2 color=Black>
|
||||
CDEV Script Service
|
||||
</p>
|
||||
|
||||
</p>
|
||||
A Tool for Using Interactive Scripts from CDEV
|
||||
</p>
|
||||
|
||||
</p>
|
||||
Walt Akers
|
||||
</p>
|
||||
|
||||
</p>
|
||||
Version 1.0 February 11, 1997
|
||||
</p>
|
||||
|
||||
</p>
|
||||
TJNAF - Thomas Jefferson National Accelerator Facility
|
||||
</p>
|
||||
|
||||
<!*** Finish ADDRESS-VERSION ***!></p></font>
|
||||
</td></tr>
|
||||
</table>
|
||||
<! *************************** TABLE OF CONTENTS ****************************!>
|
||||
<br><hr><br>
|
||||
<table width=100%>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top align=center>
|
||||
<!*** Start CLASS-TOC-TITLE ***!><font size=+3><strong>
|
||||
Table of Contents
|
||||
<!*** Finish CLASS-TOC-TITLE ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<table>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
1.
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF1">Script Service Fundamentals</a>
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF2">Overview of the Script Service</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF3">Features of the Script Service</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
2.
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF4">Building the Script Service</a>
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF5">Location of Files</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF6">Steps to Building Service</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
3.
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF7">Structure of Data Provided to the Script</a>
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF8">General Form of Data String</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF9">Representation of Scalar Data</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF10">Representation of Array Data</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
4.
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF11">Structure of Data Returned from the Script</a>
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF12">Returning Data to the Calling CDEV Application</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF13">General Form of String Data </a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF14">Returning a Single Result Packet </a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF15">Returning Multiple Result Packets </a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF16">Special Considerations</a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
5.
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF17">DDL Entries for the Script Service</a>
|
||||
<!*** Finish HEADING1TOC ***!><br></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start UHEADING2TOC ***!><font size=+1 color=Black>
|
||||
<a href="cdevScriptService.html#TOCREF18">Setting Up the DDL </a>
|
||||
<!*** Finish UHEADING2TOC ***!><br></font>
|
||||
</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
</table>
|
||||
<! **************************** LIST OF FIGURES *****************************!>
|
||||
<br><hr><br>
|
||||
<table width=100%>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top align=center>
|
||||
<!*** Start CLASS-LOF-TITLE ***!><font size=+3><strong>
|
||||
List of Figures
|
||||
<!*** Finish CLASS-LOF-TITLE ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start FIGURELOF ***!><font size=+1 color=Black>
|
||||
Figure 7:
|
||||
<a href="cdevScriptService.html#LOFREF1">General form of string representation of cdevData</a>
|
||||
<!*** Finish FIGURELOF ***!><br></font>
|
||||
<!*** Start FIGURELOF ***!><font size=+1 color=Black>
|
||||
Figure 8:
|
||||
<a href="cdevScriptService.html#LOFREF2">String representation of scalar data in a cdevData object</a>
|
||||
<!*** Finish FIGURELOF ***!><br></font>
|
||||
<!*** Start FIGURELOF ***!><font size=+1 color=Black>
|
||||
Figure 9:
|
||||
<a href="cdevScriptService.html#LOFREF3">String representation of array data</a>
|
||||
<!*** Finish FIGURELOF ***!><br></font>
|
||||
<!*** Start FIGURELOF ***!><font size=+1 color=Black>
|
||||
Figure 10:
|
||||
<a href="cdevScriptService.html#LOFREF4">Returning a single result packet to the CDEV application</a>
|
||||
<!*** Finish FIGURELOF ***!><br></font>
|
||||
<!*** Start FIGURELOF ***!><font size=+1 color=Black>
|
||||
Figure 11:
|
||||
<a href="cdevScriptService.html#LOFREF5">Returning a multiple result packets to the CDEV application</a>
|
||||
<!*** Finish FIGURELOF ***!><br></font>
|
||||
<!*** Start FIGURELOF ***!><font size=+1 color=Black>
|
||||
Figure 12:
|
||||
<a href="cdevScriptService.html#LOFREF6">Simple DDL file for the Script Service</a>
|
||||
<!*** Finish FIGURELOF ***!><br></font>
|
||||
</td></tr>
|
||||
</table>
|
||||
<! ************************ FILE : ./cdevScriptService.mif *****************************!>
|
||||
<br><hr><br>
|
||||
<table width=100%>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
1.
|
||||
<!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
<a name="TOCREF1">
|
||||
Script Service Fundamentals
|
||||
</a> <!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF2">
|
||||
Overview of the
|
||||
Script Service
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
The CDEV Script Service is designed to allow a a CDEV application to execute an
|
||||
external script to process a message. The output that is produced by the executable
|
||||
will be returned to the caller in the form of a cdevData. The CDEV Script Service
|
||||
meets the following requirements.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF3">
|
||||
Features of the
|
||||
Script Service
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<table>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
The filename of the script is associated with a CDEV device/message
|
||||
combination by using the "filename" field of the class-data in the CDEV DDL file.
|
||||
Syntax is described later in this document.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
A new process will be spawned for the script each time it is executed. Its standard
|
||||
output (stdout) file descriptor will be redirected to return data to the main CDEV
|
||||
application, allowing the script to return results to the parent process.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
The external executable file can be any form of user shell, batch file or binary
|
||||
application that is supported on the host platform.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
The Script Service supports all of CDEV's send mechanisms; "send",
|
||||
"sendNoBlock" and "sendCallback". Because of limits imposed on the number of
|
||||
active processes, the user is advised to use the synchronous "send" method
|
||||
whenever practical.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
When called by CDEV, the script will receive three arguments; the name of the
|
||||
CDEV device associated with the request, the message string that was submitted
|
||||
to the device, and a string that describes the contents of the outbound cdevData
|
||||
object.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
The reply that is written to the standard output by the script must have a specific
|
||||
format as described later in this document. A script may return more than one
|
||||
reply packet to the caller.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
The script notifies CDEV that it has written its last reply packet by writing "done"
|
||||
alone on a line to the standard output.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
If the script is to return multiple results, it should write "end" alone on a line to the
|
||||
standard output between each packet, and write "done" alone on a line following
|
||||
the last packet.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
If the script returns a value in the "status" tag of its reply packet, this will be
|
||||
provided to the caller as the completion code of the message. Traditionally a
|
||||
status of 0 indicates success, and all other values indicated an error occurred.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
<img src="bullet.jpg">
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BULLETED ***!><font size=+1 color=Black>
|
||||
Because the callback mechanism of the Script Service is triggered by output from
|
||||
the script, the script developer should at least write "done" to the standard output
|
||||
even if the application returns no output.
|
||||
<!*** Finish BULLETED ***!></p></font>
|
||||
</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
2.
|
||||
<!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
<a name="TOCREF4">
|
||||
Building the Script Service
|
||||
</a> <!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF5">
|
||||
Location of Files
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
The source code for the Script Service is provided with the CDEV distribution starting
|
||||
with version 1.5. The source code is located in the directory $CDEV/extensions/
|
||||
ScriptService. The following steps should be taken to build the ScriptService.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF6">
|
||||
Steps to Building
|
||||
Service
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<table>
|
||||
<tr><td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
1.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
Obtain and install the CDEV distribution - Version 1.5 or higher.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
2.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
Follow the installation steps to build CDEV on your system. This includes setting
|
||||
all of the environment variables required by CDEV.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
3.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
Change directories to <em>$CDEV/extensions/ScriptService/src</em>.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
4.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
There is a collection of platform specific makefiles in the directory <em>$CDEV/
|
||||
extensions/cdevGenericServer/include/makeinclude</em>. Link the makefile that is
|
||||
appropriate to your architecture to the file Makefile.OS.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
<!*** Start INDENTED ***!><font size=+1 color=Black>
|
||||
For example, to link to the makefile for HP-UX, you would type the following
|
||||
command.
|
||||
</p>
|
||||
|
||||
</p>
|
||||
<em>ln -s Makefile.hpux Makefile.OS</em>
|
||||
</p>
|
||||
|
||||
<!*** Finish INDENTED ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
5.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start NUMBERED ***!><font size=+1 color=Black>
|
||||
Type make to compile and link the Script Service shared object. Note that you
|
||||
must be using GNU make in order to build this distribution.
|
||||
<!*** Finish NUMBERED ***!></p></font>
|
||||
</td></tr>
|
||||
</table>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
Upon completion the Makefile will generate the shared object for the Script Service
|
||||
and will install it into your CDEVSHOBJ directory. At this point you are ready to use
|
||||
the Script Service.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
3.
|
||||
<!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
<a name="TOCREF7">
|
||||
Structure of Data Provided to the Script
|
||||
</a> <!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF8">
|
||||
General Form of
|
||||
Data String
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
When a developer makes a CDEV send call, he may provide outbound data in the
|
||||
form of a cdevData object. Before calling the script, this data is converted into a string
|
||||
and provided as the third argument to the application (the first argument is the device
|
||||
name and the second is the message). The structure of the outbound data string is of
|
||||
the following form.
|
||||
</p>
|
||||
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
<!*** Start FIGURE ***!><font size=+0 color=Black><em>
|
||||
Figure 7:
|
||||
<a name="LOFREF1">
|
||||
General form of string representation of cdevData
|
||||
<table border=1><tr><td>
|
||||
<table>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start PROGRAM ***!><pre><font size=+0 color=Black><strong><em>
|
||||
tag1="string value"
|
||||
tag2=1.00
|
||||
<!*** Finish PROGRAM ***!></strong></em></font></pre>
|
||||
</td></tr>
|
||||
</table>
|
||||
</tr></td></table>
|
||||
<AFrame 13>
|
||||
</a> <!*** Finish FIGURE ***!></p></em></font>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF9">
|
||||
Representation of
|
||||
Scalar Data
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
The above example shows two data entries of the form <em>tag=value</em>. Each entry is
|
||||
separated by a carriage return. The first entry has a tag name of <em>'tag1'</em> and a value of
|
||||
<em>'string value'</em>. You will note that <em>'string value'</em> is enclosed in double quotes in the
|
||||
example. This is used to notify the script that the value is a non-numeric character
|
||||
string. In the second data entry the value <em>'1.0' </em>is not enclosed in quotes, indicating that
|
||||
the value is a number.
|
||||
</p>
|
||||
The following example illustrates how scalar values stored in a cdevData object would
|
||||
look when they are passed to the script.
|
||||
</p>
|
||||
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
<!*** Start FIGURE ***!><font size=+0 color=Black><em>
|
||||
Figure 8:
|
||||
<a name="LOFREF2">
|
||||
String representation of scalar data in a cdevData object
|
||||
<table border=1><tr><td>
|
||||
<table>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start PROGRAM ***!><pre><font size=+0 color=Black><strong><em>
|
||||
Data stored in cdevData object:
|
||||
Tag: value
|
||||
Data Type: character string
|
||||
Value: Test
|
||||
|
||||
Tag: status
|
||||
Data Type: integer
|
||||
Value: 0
|
||||
|
||||
Tag: controlHigh
|
||||
Data Type: double
|
||||
Value: 1.001
|
||||
|
||||
String representation provided to script:
|
||||
value="Test"\\n
|
||||
status=0\\n
|
||||
controlHigh=1.001\\n
|
||||
<!*** Finish PROGRAM ***!></strong></em></font></pre>
|
||||
</td></tr>
|
||||
</table>
|
||||
</tr></td></table>
|
||||
<AFrame 1>
|
||||
</a> <!*** Finish FIGURE ***!></p></em></font>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF10">
|
||||
Representation of
|
||||
Array Data
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
If array data is stored in the outbound cdevData object, it too can be provided to the
|
||||
script. The data is structured in the standard C format where opening and closing
|
||||
braces mark the beginning and end (respectively) of each array bound. The following
|
||||
example illustrates how various arrays would be represented as strings.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
<!*** Start FIGURE ***!><font size=+0 color=Black><em>
|
||||
Figure 9:
|
||||
<a name="LOFREF3">
|
||||
String representation of array data
|
||||
<table border=1><tr><td>
|
||||
<table>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start PROGRAM ***!><pre><font size=+0 color=Black><strong><em>
|
||||
Data stored in cdevData object:
|
||||
Tag: value
|
||||
Data Type: character string [3]
|
||||
Value: "value1" "value2" "value3"
|
||||
|
||||
String representation provided to script:
|
||||
value={"value1","value2","value3"}\\n
|
||||
|
||||
<AFrame 5>
|
||||
|
||||
Data stored in cdevData object:
|
||||
Tag: value
|
||||
Data Type: double [3]
|
||||
Value: 1.0, 2.0, 3.01
|
||||
|
||||
String representation provided to script:
|
||||
value={1,2,3.01}\\n
|
||||
|
||||
<AFrame 6>
|
||||
|
||||
Data stored in cdevData object:
|
||||
Tag: value
|
||||
Data Type: double [3][2]
|
||||
Value: 1.0, 2.0, 3.0, 4.0, 5.0, 6.0
|
||||
|
||||
String representation provided to script:
|
||||
value={{1,2},{3,4},{5,6}}\\n
|
||||
<!*** Finish PROGRAM ***!></strong></em></font></pre>
|
||||
</td></tr>
|
||||
</table>
|
||||
</tr></td></table>
|
||||
<AFrame 3>
|
||||
</a> <!*** Finish FIGURE ***!></p></em></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
4.
|
||||
<!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
<a name="TOCREF11">
|
||||
Structure of Data Returned from the Script
|
||||
</a> <!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF12">
|
||||
Returning Data to
|
||||
the Calling CDEV
|
||||
Application
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
Before CDEV starts the script, it creates a pipe that is used to pass data between the
|
||||
script and the CDEV application. One end of this pipe is maintained by the application
|
||||
and the other end of the pipe is provided to the script as its standard output. This
|
||||
means that anytime the script uses the "echo" command or the "printf" command, the
|
||||
data that it output's will be transmitted through the pipe to the parent application.
|
||||
</p>
|
||||
The script is responsible for formatting the data into a collection of character strings
|
||||
that can be recognized by the CDEV application.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF13">
|
||||
General Form of
|
||||
String Data
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
In general, the data that is returned from a script is of the same form as described in
|
||||
the preceding section, "<em>Structure of Data Provided to the Script</em>". The most notable
|
||||
difference is that the script must terminate the list by providing a character string that
|
||||
indicates that the group of data items is complete; the string "<em>end</em>" or "<em>done</em>" alone on
|
||||
a line.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF14">
|
||||
Returning a
|
||||
Single Result
|
||||
Packet
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
If the script is going to return exactly one result packet (<em>a group of tags and values that
|
||||
will be used to populate the result cdevData</em>), then it should write the string "<em>done</em>" on
|
||||
a line by itself immediately following the output data. This will notify the Script Service
|
||||
that no more data will be returned from the script.
|
||||
</p>
|
||||
The following example shows how a single result will be returned from a script. Note
|
||||
that the "status" tag contains the completion code that will be returned to the CDEV
|
||||
application.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
<!*** Start FIGURE ***!><font size=+0 color=Black><em>
|
||||
Figure 10:
|
||||
<a name="LOFREF4">
|
||||
Returning a single result packet to the CDEV application
|
||||
<table border=1><tr><td>
|
||||
<table>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start PROGRAM ***!><pre><font size=+0 color=Black><strong><em>
|
||||
#\\! /bin/csh -f
|
||||
|
||||
echo value=\\"Test\\"
|
||||
echo status=0
|
||||
echo controlLow=1.5
|
||||
echo controlHigh=25.1
|
||||
echo done
|
||||
<!*** Finish PROGRAM ***!></strong></em></font></pre>
|
||||
</td></tr>
|
||||
</table>
|
||||
</tr></td></table>
|
||||
<AFrame 7>
|
||||
</a> <!*** Finish FIGURE ***!></p></em></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF15">
|
||||
Returning
|
||||
Multiple Result
|
||||
Packets
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
Returning multiple results from a single script execution is not generally advised.
|
||||
However, If the script is going to return more than one result packet, then each interim
|
||||
packet should be terminated by the "<em>end</em>" keyword on a line by itself. The "<em>done</em>"
|
||||
keyword should follow the last entry.
|
||||
</p>
|
||||
The following example shows how two results will be returned from a script.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
<!*** Start FIGURE ***!><font size=+0 color=Black><em>
|
||||
Figure 11:
|
||||
<a name="LOFREF5">
|
||||
Returning a multiple result packets to the CDEV application
|
||||
<table border=1><tr><td>
|
||||
<table>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start PROGRAM ***!><pre><font size=+0 color=Black><strong><em>
|
||||
#\\! /bin/csh -f
|
||||
|
||||
echo value=\\"Start Result 1\\"
|
||||
echo status=0
|
||||
echo end
|
||||
echo value=\\"Start Result 2\\"
|
||||
echo status=-1
|
||||
echo done
|
||||
<!*** Finish PROGRAM ***!></strong></em></font></pre>
|
||||
</td></tr>
|
||||
</table>
|
||||
</tr></td></table>
|
||||
<AFrame 9>
|
||||
</a> <!*** Finish FIGURE ***!></p></em></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF16">
|
||||
Special
|
||||
Considerations
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
If the script that is being executed will not return a result, then the developer should
|
||||
still write "<em>done"</em> to the standard output in order to notify the CDEV application that it
|
||||
should no longer wait for output. If the script is not returning a result, it may write the
|
||||
terminating <em>"done"</em> at the beginning of the script or at the end. Because synchronous
|
||||
calls will block until a reply is received, the developer should return a result to the
|
||||
CDEV application as quickly as possible.
|
||||
</p>
|
||||
If the developer never writes anything to the standard output, then the user specified
|
||||
CDEV callback will never be executed... therefore, it is crucial to notify the CDEV
|
||||
application when the script has completed.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top align=right>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
5.
|
||||
<!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start HEADING1 ***!><font size=+3 color=Black><strong>
|
||||
<a name="TOCREF17">
|
||||
DDL Entries for the Script Service
|
||||
</a> <!*** Finish HEADING1 ***!></p></strong></font>
|
||||
</td></tr>
|
||||
<tr><td valign=top>
|
||||
<!*** Start UHEADING2 ***!><font size=+1 color=Black><strong>
|
||||
<a name="TOCREF18">
|
||||
Setting Up the
|
||||
DDL
|
||||
</a> <!*** Finish UHEADING2 ***!></p></strong></font>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
The following example illustrates how to add a service entry to identify the Script
|
||||
Service and how to use the class-data to specify the filename that the Script Service
|
||||
will execute to service a message.
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
<!*** Start FIGURE ***!><font size=+0 color=Black><em>
|
||||
Figure 12:
|
||||
<a name="LOFREF6">
|
||||
Simple DDL file for the Script Service
|
||||
<table border=1><tr><td>
|
||||
<table>
|
||||
<tr><td>
|
||||
<! ***** Empty Column ***** !>
|
||||
</td>
|
||||
<td valign=top>
|
||||
<!*** Start PROGRAM ***!><pre><font size=+0 color=Black><strong><em>
|
||||
/*
|
||||
* This is the service definition, it tells CDEV that there is
|
||||
* a service named Script and that it will use the cdevData
|
||||
* tag 'filename' to read configuration information from the
|
||||
* DDL file entries.
|
||||
*/
|
||||
service Script
|
||||
{
|
||||
tags {filename}
|
||||
}
|
||||
|
||||
/*
|
||||
* This class definition identifies the class scriptClass which
|
||||
* supports the "get and "set" commands on attributes "attrib0"
|
||||
* and "attrib1". Note that attrib0 will call script /bin/ouch
|
||||
* and attrib1 will call script /bin/wammo.
|
||||
*/
|
||||
class scriptClass
|
||||
{
|
||||
verbs {get, set}
|
||||
attributes
|
||||
{
|
||||
attrib0 Script {filename = /bin/ouch};
|
||||
attrib1 Script {filename = /bin/wammo};
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Finally, the CDEV DDL identifies two devices that are of type
|
||||
* scriptClass. Any time one of the supported messages is passed
|
||||
* to one of these devices it will activate the corresponding
|
||||
* script.
|
||||
*/
|
||||
scriptClass : device0, device1;
|
||||
|
||||
<!*** Finish PROGRAM ***!></strong></em></font></pre>
|
||||
</td></tr>
|
||||
</table>
|
||||
</tr></td></table>
|
||||
<AFrame 11>
|
||||
</a> <!*** Finish FIGURE ***!></p></em></font>
|
||||
<!*** Start BODY ***!><font size=+1 color=Black>
|
||||
|
||||
<!*** Finish BODY ***!></p></font>
|
||||
</td></tr>
|
||||
</table>
|
||||
</body>
|
||||
21
extensions/ScriptService/doc/makehtml
Executable file
21
extensions/ScriptService/doc/makehtml
Executable file
@@ -0,0 +1,21 @@
|
||||
#! /bin/csh
|
||||
|
||||
if( -f fmbatch.dat) rm fmbatch.dat
|
||||
if( -d html) rm -rf html
|
||||
mkdir -p html
|
||||
cp $CDEV/doc/bullet.jpg html
|
||||
|
||||
foreach x (`find . -name \*.doc -a ! -name \*TOC.doc -a ! -name \*LOF.doc`)
|
||||
echo "Open $x" >> fmbatch.dat
|
||||
echo "SaveAs ma $x html/`basename $x .doc`.mif" >> fmbatch.dat
|
||||
end
|
||||
|
||||
fmbatch fmbatch.dat
|
||||
|
||||
cd html
|
||||
|
||||
foreach x (`find . -name \*.mif -a ! -name \*TITLE.mif`)
|
||||
mif2html -t 'CDEV Script Service' -o `basename $x .mif`.html `basename $x .mif`TITLE.mif \-TOC \-LOF $x
|
||||
end
|
||||
|
||||
rm *.mif
|
||||
BIN
extensions/ScriptService/src/.shobj/Linux/ScriptRequestObject.o
Normal file
BIN
extensions/ScriptService/src/.shobj/Linux/ScriptRequestObject.o
Normal file
Binary file not shown.
BIN
extensions/ScriptService/src/.shobj/Linux/ScriptService.o
Normal file
BIN
extensions/ScriptService/src/.shobj/Linux/ScriptService.o
Normal file
Binary file not shown.
46
extensions/ScriptService/src/Makefile
Executable file
46
extensions/ScriptService/src/Makefile
Executable file
@@ -0,0 +1,46 @@
|
||||
ARCH = OS
|
||||
SHOBJ = YES
|
||||
|
||||
include $(CDEV)/extensions/cdevGenericServer/include/makeinclude/Makefile.$(ARCH)
|
||||
|
||||
APPNAME = "CDEV/ACE Script Service"
|
||||
CXXINCLUDES = -I./
|
||||
BASEBIN = ./
|
||||
SO_LIBS = $(OSLIBS)
|
||||
SO_SRCS = ScriptService.cc \
|
||||
ScriptRequestObject.cc \
|
||||
ScriptList.cc
|
||||
OBJS = $(OBJDIR)/ScriptService.o \
|
||||
$(OBJDIR)/ScriptRequestObject.o \
|
||||
$(OBJDIR)/ScriptList.o
|
||||
|
||||
# ******************************************************************************
|
||||
# * The BINARIES definition names all of the binary files that should be deleted
|
||||
# * whenever "make clean" is executed.
|
||||
# ******************************************************************************
|
||||
BINARIES = $(CDEVLIB)/libScriptService.a \
|
||||
$(CDEVSHOBJ)/$(CDEVVERSION)/ScriptService.so
|
||||
|
||||
ifeq ($(SHOBJ), YES)
|
||||
LIBS = $(CDEVLIBS) $(OSLIBS)
|
||||
TARGETS = $(CDEVSHOBJ)/$(CDEVVERSION)/ScriptService.so
|
||||
else
|
||||
LIBS = $(CDEVLIBS) -lScriptService $(OSLIBS)
|
||||
TARGETS = $(CDEVLIB)/libScriptService.a
|
||||
endif
|
||||
|
||||
targets : $(TARGETS)
|
||||
|
||||
$(CDEVSHOBJ)/$(CDEVVERSION)/ScriptService.so : $(OBJS)
|
||||
@rm -f $@
|
||||
@$(SOBUILD)
|
||||
@mkdir -p $(CDEVSHOBJ)/$(CDEVVERSION)
|
||||
@echo "<= Done...\n"
|
||||
|
||||
$(CDEVLIB)/libScriptService.a : $(OBJS)
|
||||
@rm -f $@
|
||||
@echo "=> Building archive library $(@F)"
|
||||
@echo " => Linking $(@F) from objects"
|
||||
@$(LINK.a) $@ $^
|
||||
@$(RANLIB) $@ > /dev/null
|
||||
@echo "<= Done...\n"
|
||||
958
extensions/ScriptService/src/ScriptList.cc
Executable file
958
extensions/ScriptService/src/ScriptList.cc
Executable file
@@ -0,0 +1,958 @@
|
||||
// -----------------------------------------------------------------------------
|
||||
// Copyright (c) 1995 Southeastern Universities Research Association,
|
||||
// Continuous Electron Beam Accelerator Facility
|
||||
//
|
||||
// This software was developed under a United States Government license
|
||||
// described in the NOTICE file included as part of this distribution.
|
||||
//
|
||||
// -----------------------------------------------------------------------------
|
||||
//
|
||||
// Description:
|
||||
// This header file contains the class definitions for the classes
|
||||
// associated with the construction of a script service.
|
||||
//
|
||||
// Author: Walt Akers
|
||||
//
|
||||
// Revision History:
|
||||
// ScriptList.cc,v
|
||||
// Revision 1.3 1997/02/14 20:43:40 akers
|
||||
// Ongoing improvement
|
||||
//
|
||||
// Revision 1.2 1997/02/14 20:06:32 akers
|
||||
// Ongoing improvement
|
||||
//
|
||||
// Revision 1.1 1997/02/11 17:37:22 akers
|
||||
// Directory restructure
|
||||
//
|
||||
// Revision 1.7 1997/02/10 20:31:23 akers
|
||||
// Ongoing improvement
|
||||
//
|
||||
// Revision 1.6 1997/02/07 16:19:43 akers
|
||||
// Ongoing development
|
||||
//
|
||||
// Revision 1.5 1997/02/06 20:27:48 akers
|
||||
// Ongoing development
|
||||
//
|
||||
// Revision 1.4 1997/01/31 21:09:58 akers
|
||||
// Ongoing Development
|
||||
//
|
||||
// Revision 1.3 1997/01/31 18:51:26 akers
|
||||
// Ongoing development
|
||||
//
|
||||
// Revision 1.2 1997/01/31 16:21:22 akers
|
||||
// Ongoing development
|
||||
//
|
||||
// Revision 1.1 1997/01/30 20:35:33 akers
|
||||
// Initial installation of Script Service
|
||||
//
|
||||
// -----------------------------------------------------------------------------
|
||||
#include <ScriptList.h>
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptData::ScriptData :
|
||||
// * Constructor for the class...
|
||||
// *****************************************************************************
|
||||
ScriptData::ScriptData ( cdevTranObj & Xobj )
|
||||
: next(NULL), data(new cdevData),
|
||||
xobj(&Xobj), inputBuf(NULL),
|
||||
inputBufLen(0), amntRead(0),
|
||||
process(0), finished(0), callbackCount(0)
|
||||
{
|
||||
// *********************************************************************
|
||||
// * Attempt to create the pipe that will be used to return
|
||||
// * the result to the class.
|
||||
// *********************************************************************
|
||||
if(pipe((int *)&sp)!=0)
|
||||
{
|
||||
sp.readFD = -1;
|
||||
sp.writeFD = -1;
|
||||
}
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptData::data2Buffer :
|
||||
// * This method is used to convert a cdevData object into a
|
||||
// * series of strings that can be used by the script.
|
||||
// *****************************************************************************
|
||||
int ScriptData::data2Buffer ( cdevData & data, char *& buf, int &bufLen)
|
||||
{
|
||||
cdevDataIterator iter(&data);
|
||||
int i;
|
||||
int idx = 0;
|
||||
struct DataPack
|
||||
{
|
||||
char * tag;
|
||||
char ** ptr;
|
||||
double * dPtr;
|
||||
size_t ptrCnt;
|
||||
int quoted;
|
||||
cdevBounds * bounds;
|
||||
size_t boundsCnt;
|
||||
} dataPack[256];
|
||||
|
||||
memset(dataPack, 0, sizeof(dataPack));
|
||||
|
||||
// *********************************************************************
|
||||
// * Iterate through the cdevData object and collect the data
|
||||
// * that is stored into an array of character strings.
|
||||
// *********************************************************************
|
||||
for(bufLen=0, iter.init(); !iter && idx<256; idx++)
|
||||
{
|
||||
// *************************************************************
|
||||
// * Get the tag string and add the length of that plus
|
||||
// * the length of a seperating equals sign (=) to the
|
||||
// * buffer length.
|
||||
// *************************************************************
|
||||
data.tagI2C(iter.tag(), dataPack[idx].tag);
|
||||
bufLen+=strlen(dataPack[idx].tag)+2;
|
||||
|
||||
// *************************************************************
|
||||
// * Get the number of elements in the array.
|
||||
// *************************************************************
|
||||
data.getElems(dataPack[idx].tag, &dataPack[idx].ptrCnt);
|
||||
|
||||
// *************************************************************
|
||||
// * If the data object is a string, add two times the
|
||||
// * number of elements to the buffer length (to account
|
||||
// * for double quotes around each entry.)
|
||||
// *************************************************************
|
||||
if(data.getType(dataPack[idx].tag)==CDEV_STRING ||
|
||||
data.getType(dataPack[idx].tag)==CDEV_TIMESTAMP)
|
||||
{
|
||||
dataPack[idx].quoted = 1;
|
||||
bufLen+=(2*dataPack[idx].ptrCnt);
|
||||
|
||||
// *****************************************************
|
||||
// * Allocate an array of character strings to
|
||||
// * be used to extract the array as a
|
||||
// * collection of strings and increase the
|
||||
// * buffer length to accomodate all of the
|
||||
// * items.
|
||||
// *****************************************************
|
||||
dataPack[idx].ptr = new char * [dataPack[idx].ptrCnt];
|
||||
data.get(dataPack[idx].tag, dataPack[idx].ptr);
|
||||
for(i=0; i<dataPack[idx].ptrCnt; i++)
|
||||
{
|
||||
bufLen+=strlen(dataPack[idx].ptr[i]);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// *****************************************************
|
||||
// * Allocate an array of doubles to
|
||||
// * be used to extract the array as a
|
||||
// * collection and increase the buffer length
|
||||
// * to accomodate all of the items.
|
||||
// *****************************************************
|
||||
dataPack[idx].dPtr = new double [dataPack[idx].ptrCnt];
|
||||
data.get(dataPack[idx].tag, dataPack[idx].dPtr);
|
||||
bufLen += 21*dataPack[idx].ptrCnt;
|
||||
}
|
||||
// *************************************************************
|
||||
// * Add 1 character for each entry to account for
|
||||
// * commas between entries.
|
||||
// *************************************************************
|
||||
bufLen += dataPack[idx].ptrCnt;
|
||||
|
||||
// *************************************************************
|
||||
// * Get the number of dimensions in the tagged data
|
||||
// * item.
|
||||
// *************************************************************
|
||||
data.getDim(dataPack[idx].tag, &dataPack[idx].boundsCnt);
|
||||
|
||||
// *************************************************************
|
||||
// * If the data is an array or vector, then calculate
|
||||
// * the amount of space that will have to be used
|
||||
// * to store the separating brace characters (and commas).
|
||||
// *************************************************************
|
||||
if(dataPack[idx].boundsCnt!=0)
|
||||
{
|
||||
int braceCount = 1;
|
||||
|
||||
dataPack[idx].bounds = new cdevBounds[dataPack[idx].boundsCnt];
|
||||
data.getBounds(dataPack[idx].tag, dataPack[idx].bounds, dataPack[idx].boundsCnt);
|
||||
|
||||
for(i=0; i<dataPack[idx].boundsCnt-1; i++)
|
||||
{
|
||||
if(i==0) braceCount +=
|
||||
dataPack[idx].bounds[i].length;
|
||||
else braceCount +=
|
||||
dataPack[idx].bounds[i-1].length*
|
||||
dataPack[idx].bounds[i].length;
|
||||
}
|
||||
bufLen += braceCount*3;
|
||||
}
|
||||
|
||||
// *************************************************************
|
||||
// * Add space for the separating carriage return.
|
||||
// *************************************************************
|
||||
bufLen+=1;
|
||||
|
||||
// *************************************************************
|
||||
// * Move to the next item in the list.
|
||||
// *************************************************************
|
||||
++iter;
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * Allocate a buffer of sufficient size to hold the result
|
||||
// * plus a NULL terminating character and an opening and closing
|
||||
// * single quote.
|
||||
// *********************************************************************
|
||||
if(idx) {
|
||||
buf = new char [bufLen+1+2];
|
||||
*buf = 0;
|
||||
}
|
||||
else {
|
||||
buf = NULL;
|
||||
bufLen = 0;
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * Walk through each item in the list and place it in the
|
||||
// * data buffer.
|
||||
// *********************************************************************
|
||||
int max = idx;
|
||||
for(idx=0; idx<max; idx++)
|
||||
{
|
||||
char * ptr = buf+strlen(buf);
|
||||
sprintf(ptr, "%s=", dataPack[idx].tag);
|
||||
|
||||
if(!dataPack[idx].boundsCnt)
|
||||
{
|
||||
if(dataPack[idx].quoted)
|
||||
sprintf(ptr+strlen(ptr), "\"%s\"\n", dataPack[idx].ptr[0]);
|
||||
else sprintf(ptr+strlen(ptr), "%g\n", dataPack[idx].dPtr[0]);
|
||||
}
|
||||
else {
|
||||
size_t ptrIdx = 0;
|
||||
strcat(ptr, "{");
|
||||
if(dataPack[idx].quoted)
|
||||
{
|
||||
dataArray2Buffer(ptr+strlen(ptr),
|
||||
dataPack[idx].ptr,
|
||||
ptrIdx,
|
||||
dataPack[idx].bounds,
|
||||
dataPack[idx].boundsCnt,
|
||||
0);
|
||||
}
|
||||
else
|
||||
{
|
||||
dataArray2Buffer(ptr+strlen(ptr),
|
||||
dataPack[idx].dPtr,
|
||||
ptrIdx,
|
||||
dataPack[idx].bounds,
|
||||
dataPack[idx].boundsCnt,
|
||||
0);
|
||||
}
|
||||
strcat(ptr, "}\n");
|
||||
}
|
||||
|
||||
// *************************************************************
|
||||
// * Delete the allocated contents of the dataPack once
|
||||
// * it is no longer needed.
|
||||
// *************************************************************
|
||||
if(dataPack[idx].quoted)
|
||||
{
|
||||
for(int j=0; j<dataPack[idx].ptrCnt; j++)
|
||||
{
|
||||
delete dataPack[idx].ptr[j];
|
||||
}
|
||||
delete dataPack[idx].ptr;
|
||||
}
|
||||
else delete dataPack[idx].dPtr;
|
||||
delete dataPack[idx].bounds;
|
||||
}
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::dataArray2Buffer :
|
||||
// * This is a method that is called recursively to dump the contents
|
||||
// * of a string array to the buffer.
|
||||
// *****************************************************************************
|
||||
void ScriptData::dataArray2Buffer (char * output,
|
||||
char ** ptr,
|
||||
size_t & ptrIdx,
|
||||
cdevBounds * bounds,
|
||||
size_t nBounds,
|
||||
size_t boundsIdx)
|
||||
{
|
||||
for(int i=0; i<bounds[boundsIdx].length; i++)
|
||||
{
|
||||
if(boundsIdx<nBounds-1)
|
||||
{
|
||||
strcat(output, "{");
|
||||
dataArray2Buffer(output+strlen(output), ptr, ptrIdx, bounds, nBounds, boundsIdx+1);
|
||||
if(i+1<bounds[boundsIdx].length) strcat(output, "},");
|
||||
else strcat(output, "}");
|
||||
}
|
||||
else {
|
||||
output+=strlen(output);
|
||||
if(i+1<bounds[boundsIdx].length) sprintf(output, "\"%s\",", ptr[ptrIdx++]);
|
||||
else sprintf(output, "\"%s\"", ptr[ptrIdx++]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::dataArray2Buffer :
|
||||
// * This is a method that is called recursively to dump the contents
|
||||
// * of a double array to the buffer.
|
||||
// *****************************************************************************
|
||||
void ScriptData::dataArray2Buffer (char * output,
|
||||
double * ptr,
|
||||
size_t & ptrIdx,
|
||||
cdevBounds * bounds,
|
||||
size_t nBounds,
|
||||
size_t boundsIdx)
|
||||
{
|
||||
for(int i=0; i<bounds[boundsIdx].length; i++)
|
||||
{
|
||||
if(boundsIdx<nBounds-1)
|
||||
{
|
||||
strcat(output, "{");
|
||||
dataArray2Buffer(output+strlen(output), ptr, ptrIdx, bounds, nBounds, boundsIdx+1);
|
||||
if(i+1<bounds[boundsIdx].length) strcat(output, "},");
|
||||
else strcat(output, "}");
|
||||
}
|
||||
else {
|
||||
output+=strlen(output);
|
||||
if(i+1<bounds[boundsIdx].length) sprintf(output, "%g,", ptr[ptrIdx++]);
|
||||
else sprintf(output, "%g", ptr[ptrIdx++]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptData::buffer2Data :
|
||||
// * This method allows the ScriptData class to read the inbound
|
||||
// * results of the script inot a cdevData buffer.
|
||||
// *
|
||||
// * Each line of the result should be structured as such.
|
||||
// *
|
||||
// * Tag value\n
|
||||
// *
|
||||
// * All results are assumed to be doubles unless they are enclosed
|
||||
// * in double quotes (").
|
||||
// *
|
||||
// * If an array of items is returned, it should be enclosed in
|
||||
// * braces as described below.
|
||||
// *
|
||||
// * 1) Returning a string:
|
||||
// *
|
||||
// * value="Test"\n
|
||||
// * status "Running very well"\n
|
||||
// *
|
||||
// * 2) Returning a double:
|
||||
// * value=10.01\n
|
||||
// * status=1\n
|
||||
// *
|
||||
// * 3) Returning an array of strings
|
||||
// * value={"John","Jacob","Jingleheimer","Schmidt"}\n
|
||||
// *
|
||||
// * 4) Returning a two dimensional array of doubles: ie x[2][3]
|
||||
// * value={{1.0,2.0,3.0}{4.0,5.0,6.0}}\n
|
||||
// *
|
||||
// *****************************************************************************
|
||||
int ScriptData::buffer2Data ( char * &buf, cdevData & data )
|
||||
{
|
||||
int done = 0;
|
||||
char * ptr = buf;
|
||||
|
||||
while(ptr && *ptr)
|
||||
{
|
||||
while(isspace(*ptr)) ptr++;
|
||||
char * tag = ptr;
|
||||
|
||||
// *************************************************************
|
||||
// * Find the end of the tag and remove any trailing
|
||||
// * spaces that are associated with it.
|
||||
// *************************************************************
|
||||
if(*tag) ptr = strchr(ptr, '=');
|
||||
|
||||
// *************************************************************
|
||||
// * If the pointer does not point to a valid line, jump to
|
||||
// * the next line and continue from the top of the loop.
|
||||
// *************************************************************
|
||||
if(!ptr || !(*ptr))
|
||||
{
|
||||
ptr = strchr(ptr, '\n');
|
||||
continue;
|
||||
}
|
||||
else {
|
||||
char *temp = ptr-1;
|
||||
*(ptr++) = 0;
|
||||
while(isspace(*temp)) *(temp--)=0;
|
||||
}
|
||||
|
||||
// *************************************************************
|
||||
// * Find the beginning of the data.
|
||||
// *************************************************************
|
||||
while(*ptr && isspace(*ptr)) ptr++;
|
||||
|
||||
// *************************************************************
|
||||
// * Beginning of an array of things.
|
||||
// *************************************************************
|
||||
if(*ptr=='{')
|
||||
{
|
||||
cdevDataTypes dataType = CDEV_DOUBLE;
|
||||
char ** strData = NULL;
|
||||
double * dblData = NULL;
|
||||
char * tPtr = ptr;
|
||||
cdevBounds * bounds;
|
||||
int nDim = 0;
|
||||
int dimIdx = 0;
|
||||
int itmCnt = 0;
|
||||
int itmIdx = 0;
|
||||
int chkSum = 1;
|
||||
|
||||
// *****************************************************
|
||||
// * Count the number of opening braces, this will
|
||||
// * indicate the number of dimensions in the array.
|
||||
// *****************************************************
|
||||
while(*(tPtr++)=='{') nDim++;
|
||||
bounds = new cdevBounds[nDim];
|
||||
for(dimIdx=0; dimIdx<nDim; dimIdx++)
|
||||
{
|
||||
bounds[dimIdx].offset = 0;
|
||||
bounds[dimIdx].length = 0;
|
||||
}
|
||||
|
||||
// *****************************************************
|
||||
// * Now count the number of the dimensions in the array
|
||||
// *****************************************************
|
||||
for(tPtr=ptr+1, dimIdx=0; dimIdx>=0 && *tPtr; tPtr++)
|
||||
{
|
||||
if(*tPtr=='"')
|
||||
{
|
||||
tPtr = strchr(tPtr+1, '"');
|
||||
dataType = CDEV_STRING;
|
||||
}
|
||||
else if(*tPtr=='}')
|
||||
{
|
||||
if(dimIdx==nDim-1) bounds[dimIdx].length++;
|
||||
dimIdx--;
|
||||
}
|
||||
else if(*tPtr=='{')
|
||||
{
|
||||
bounds[dimIdx++].length++;
|
||||
}
|
||||
else if(*tPtr==',' && dimIdx==nDim-1)
|
||||
{
|
||||
bounds[dimIdx].length++;
|
||||
}
|
||||
}
|
||||
|
||||
// *****************************************************
|
||||
// * At this point, the last element of the bounds
|
||||
// * array will contain the total count of items.
|
||||
// *****************************************************
|
||||
itmCnt = bounds[nDim-1].length;
|
||||
|
||||
// *****************************************************
|
||||
// * To set each bounds element to its actual array
|
||||
// * dimension, it will be necessary to divide it by
|
||||
// * the size of its predecessor - working backwards.
|
||||
// *****************************************************
|
||||
for(dimIdx = nDim-2; dimIdx>=0; dimIdx--)
|
||||
{
|
||||
bounds[dimIdx+1].length /= bounds[dimIdx].length;
|
||||
}
|
||||
for(dimIdx = 0; dimIdx<nDim; dimIdx++)
|
||||
{
|
||||
chkSum*=bounds[dimIdx].length;
|
||||
}
|
||||
|
||||
if(chkSum==itmCnt && chkSum>0)
|
||||
{
|
||||
// *****************************************************
|
||||
// * Allocate a buffer of the correct type to hold the
|
||||
// * data.
|
||||
// *****************************************************
|
||||
if(dataType == CDEV_STRING) strData = new char *[itmCnt];
|
||||
else dblData = new double [itmCnt];
|
||||
|
||||
// *****************************************************
|
||||
// * Walk through the data and accumulate the items
|
||||
// * into the array.
|
||||
// *****************************************************
|
||||
tPtr = ptr;
|
||||
dimIdx = -1;
|
||||
|
||||
do {
|
||||
if(*tPtr=='{')
|
||||
{
|
||||
int jumpTheComma = 0;
|
||||
|
||||
dimIdx++;
|
||||
tPtr++;
|
||||
|
||||
if(*tPtr && dimIdx==nDim-1) do
|
||||
{
|
||||
if(*tPtr==',' && jumpTheComma) tPtr++;
|
||||
|
||||
while(isspace(*tPtr)) tPtr++;
|
||||
if(dataType==CDEV_DOUBLE)
|
||||
{
|
||||
dblData[itmIdx++] = atof(tPtr);
|
||||
while(*tPtr && *tPtr!=',' && *tPtr!='}') tPtr++;
|
||||
}
|
||||
else {
|
||||
char oldEndVal;
|
||||
char * ePtr;
|
||||
if(*tPtr=='"')
|
||||
{
|
||||
tPtr++;
|
||||
ePtr = strchr(tPtr, '"');
|
||||
}
|
||||
else for(ePtr=tPtr; *ePtr && *ePtr!=',' && *ePtr!='}'; ePtr++);
|
||||
|
||||
if(ePtr)
|
||||
{
|
||||
oldEndVal = *ePtr;
|
||||
*ePtr = 0;
|
||||
}
|
||||
|
||||
strData[itmIdx++] = strdup(tPtr);
|
||||
|
||||
if(ePtr)
|
||||
{
|
||||
*ePtr = oldEndVal;
|
||||
tPtr = (*ePtr=='"')?ePtr+1:ePtr;
|
||||
}
|
||||
else tPtr = tPtr+strlen(tPtr);
|
||||
}
|
||||
jumpTheComma = (*tPtr==',')?1:0;
|
||||
} while(*tPtr!='}' && *tPtr);
|
||||
}
|
||||
else if(*tPtr=='}')
|
||||
{
|
||||
dimIdx--;
|
||||
tPtr++;
|
||||
}
|
||||
else tPtr++;
|
||||
} while (*tPtr && itmIdx<itmCnt && dimIdx>=0);
|
||||
|
||||
if(dataType==CDEV_STRING)
|
||||
{
|
||||
data.insert(tag, strData, itmCnt, nDim);
|
||||
for(int x=0; x<itmCnt; x++) delete strData[x];
|
||||
delete strData;
|
||||
}
|
||||
else {
|
||||
data.insert(tag, dblData, itmCnt, nDim);
|
||||
delete dblData;
|
||||
}
|
||||
|
||||
data.setBounds(tag, bounds, nDim);
|
||||
}
|
||||
|
||||
delete bounds;
|
||||
for(ptr=tPtr; *ptr && *ptr!='\n'; ptr++);
|
||||
}
|
||||
// *************************************************************
|
||||
// * Beginning of a string.
|
||||
// *************************************************************
|
||||
else if(*ptr=='"')
|
||||
{
|
||||
ptr++;
|
||||
char * temp = ptr;
|
||||
while(*temp!='"') temp++;
|
||||
if(*temp=='"')
|
||||
{
|
||||
*(temp++)=0;
|
||||
data.insert(tag, ptr);
|
||||
}
|
||||
for(ptr = temp; *ptr && *ptr!='\n'; ptr++);
|
||||
}
|
||||
// *************************************************************
|
||||
// * Beginning of a double.
|
||||
// *************************************************************
|
||||
else if(*ptr)
|
||||
{
|
||||
data.insert(tag, atof(ptr));
|
||||
while(*ptr && *ptr!='\n') ptr++;
|
||||
}
|
||||
}
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptData::fireCallback :
|
||||
// * Deploys the callback associated with the class instance.
|
||||
// *****************************************************************************
|
||||
void ScriptData::fireCallback ( int result, void * arg, cdevRequestObject &req, cdevData & data, int partial)
|
||||
{
|
||||
// *********************************************************************
|
||||
// * Fire the user provided callback and increment the counter.
|
||||
// *********************************************************************
|
||||
xobj->userCallback_->fireCallback ( result, arg, req, data, partial );
|
||||
callbackCount++;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptData::dispatch :
|
||||
// * This method is responsible for collecting data from the
|
||||
// * read file descriptor, and executing the callback associated
|
||||
// * with it.
|
||||
// *
|
||||
// * This method will return the number of messages that it handled.
|
||||
// *****************************************************************************
|
||||
int ScriptData::dispatch ( void )
|
||||
{
|
||||
int nHandled = 0;
|
||||
if(!finished)
|
||||
{
|
||||
int count = 0;
|
||||
int stat_val;
|
||||
// *************************************************************
|
||||
// * Find out how many bytes are ready to read.
|
||||
// *************************************************************
|
||||
while(ioctl(sp.readFD, FIONREAD, &count)==0 && count>0)
|
||||
{
|
||||
// *****************************************************
|
||||
// * If the input buffer has not already been
|
||||
// * allocated, then allocate a new one that
|
||||
// * is of sufficient size in increments of
|
||||
// * 1024 bytes.
|
||||
// *****************************************************
|
||||
if(inputBufLen==0)
|
||||
{
|
||||
inputBufLen = (count/1024+1)*1024;
|
||||
inputBuf = (char *)malloc(inputBufLen);
|
||||
}
|
||||
// *****************************************************
|
||||
// * If the existing buffer is not sufficiently
|
||||
// * large, then allocate a new one that is
|
||||
// * of sufficient size in increments of
|
||||
// * 1024 bytes.
|
||||
// *********************************************
|
||||
else if(amntRead + count > inputBufLen)
|
||||
{
|
||||
inputBufLen = ((amntRead+count)/1024+1)*1024;
|
||||
inputBuf = (char *)realloc(inputBuf, inputBufLen);
|
||||
}
|
||||
|
||||
// *****************************************************
|
||||
// * Read the data that is ready into the buffer
|
||||
// *****************************************************
|
||||
amntRead += read(sp.readFD, inputBuf+amntRead, count);
|
||||
|
||||
// *****************************************************
|
||||
// * NULL terminate the buffer to prevent memory
|
||||
// * overruns while performing string operations
|
||||
// *****************************************************
|
||||
inputBuf[amntRead] = 0;
|
||||
|
||||
int done = 0;
|
||||
|
||||
// *****************************************************
|
||||
// * Search the data for the "done" or "end" keywords
|
||||
// * on a line by themselves... Either of these
|
||||
// * keywords indicate the end of a data transmission.
|
||||
// *****************************************************
|
||||
do {
|
||||
char * ePtr = NULL;
|
||||
|
||||
if (strncmp(inputBuf, "end\n", 4)==0 ||
|
||||
strncmp(inputBuf, "done\n", 5)==0)
|
||||
{
|
||||
ePtr = inputBuf;
|
||||
}
|
||||
else if((ePtr = strstr(inputBuf, "\nend\n"))!=NULL ||
|
||||
(ePtr = strstr(inputBuf, "\ndone\n"))!=NULL)
|
||||
{
|
||||
ePtr++;
|
||||
}
|
||||
else done = 1;
|
||||
|
||||
if(ePtr && *ePtr)
|
||||
{
|
||||
if(*ePtr=='d')
|
||||
{
|
||||
*ePtr = 0;
|
||||
ePtr += 5;
|
||||
finished = 1;
|
||||
}
|
||||
else {
|
||||
*ePtr = 0;
|
||||
ePtr += 4;
|
||||
}
|
||||
|
||||
buffer2Data (inputBuf, *data);
|
||||
strcpy(inputBuf, ePtr);
|
||||
amntRead = strlen(inputBuf);
|
||||
|
||||
// *************************************
|
||||
// * If no more data is ready,
|
||||
// * determine if the process
|
||||
// * is still alive.
|
||||
// *************************************
|
||||
stat_val = 0;
|
||||
if(waitpid(process, &stat_val, WNOHANG)==process &&
|
||||
(errno==ECHILD || WIFEXITED(stat_val)))
|
||||
{
|
||||
finished = 1;
|
||||
}
|
||||
|
||||
// *************************************
|
||||
// * Transfer the data from the
|
||||
// * temporary data object into
|
||||
// * the user-defined result
|
||||
// * data object.
|
||||
// *************************************
|
||||
if(xobj->resultData_==NULL)
|
||||
xobj->resultData_ = data;
|
||||
else *(xobj->resultData_) = *data;
|
||||
|
||||
// *************************************
|
||||
// * Fire the user provided
|
||||
// * callback and increment the
|
||||
// * callback counter. The status as
|
||||
// * returned in the cdevData object
|
||||
// * is the status for the request.
|
||||
// *************************************
|
||||
int status = CDEV_SUCCESS;
|
||||
xobj->resultData_->get("status", &status);
|
||||
fireCallback
|
||||
(
|
||||
status,
|
||||
xobj->userCallback_->userarg(),
|
||||
*xobj->reqObj_,
|
||||
*xobj->resultData_,
|
||||
!finished);
|
||||
nHandled++;
|
||||
}
|
||||
} while(!done && !finished);
|
||||
}
|
||||
|
||||
// *************************************************************
|
||||
// * When no more data is ready, determine if the process is
|
||||
// * still alive.
|
||||
// *************************************************************
|
||||
if(!finished && waitpid(process, &stat_val, WNOHANG)==process &&
|
||||
(errno==ECHILD || WIFEXITED(stat_val)))
|
||||
{
|
||||
finished = 1;
|
||||
}
|
||||
}
|
||||
return nHandled;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptData::~ScriptData :
|
||||
// * The destructor is protected to prevent it from being deleted by
|
||||
// * anyone except the ScriptList class.
|
||||
// *****************************************************************************
|
||||
ScriptData::~ScriptData ( void )
|
||||
{
|
||||
static int killCount = 0;
|
||||
if(callbackCount==0)
|
||||
{
|
||||
data->remove();
|
||||
fireCallback (
|
||||
CDEV_SUCCESS,
|
||||
xobj->userCallback_->userarg(),
|
||||
*xobj->reqObj_,
|
||||
*data);
|
||||
}
|
||||
|
||||
if(inputBuf) delete inputBuf;
|
||||
if(sp.readFD != -1) close(sp.readFD);
|
||||
if(sp.writeFD != -1) close(sp.writeFD);
|
||||
if(data) delete data;
|
||||
if(xobj)
|
||||
{
|
||||
xobj->removeFromGrps();
|
||||
delete xobj;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::ScriptList :
|
||||
// * This is the constructor for the ScriptList class. It
|
||||
// * initializes the internals of the class to 0.
|
||||
// *****************************************************************************
|
||||
ScriptList::ScriptList ( void ) : scripts(NULL), fdList(NULL), fdCount(0), fdMax(0)
|
||||
{
|
||||
};
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::ScriptList :
|
||||
// * This method will walk through the list of ScriptData objects and
|
||||
// * will delete each of them in sequence.
|
||||
// *
|
||||
// * Note that is no callbacks have been delivered for the specified
|
||||
// * ScriptData object, it will deliver a single callback with
|
||||
// * CDEV_ERROR as the status prior to terminating.
|
||||
// *****************************************************************************
|
||||
ScriptList::~ScriptList ( void )
|
||||
{
|
||||
ScriptData * curr;
|
||||
while(scripts!=NULL)
|
||||
{
|
||||
curr = scripts;
|
||||
scripts = scripts->next;
|
||||
delete curr;
|
||||
}
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::find :
|
||||
// * This method allows the caller to locate the ScriptData object
|
||||
// * that is associated with a specified file descriptor.
|
||||
// *****************************************************************************
|
||||
ScriptData * ScriptList::find ( int fd )
|
||||
{
|
||||
ScriptData * curr = scripts;
|
||||
while(curr->sp.readFD != fd && curr!=NULL)
|
||||
{
|
||||
curr = curr->next;
|
||||
}
|
||||
return curr;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::insert :
|
||||
// * This method allows the caller to insert a new ScriptData object
|
||||
// * into the list of scripts that is managed by this list. Once
|
||||
// * added to the list the file descriptor associated with the
|
||||
// * ScriptData object will be placed on the list of file
|
||||
// * descriptors that will be polled by the cdevSystem object.
|
||||
// *****************************************************************************
|
||||
void ScriptList::insert ( ScriptData & script )
|
||||
{
|
||||
script.next = scripts;
|
||||
scripts = &script;
|
||||
|
||||
if(fdCount >= fdMax)
|
||||
{
|
||||
fdMax = (fdMax>1)?(fdMax*2):16;
|
||||
fdList = (int *)realloc(fdList, fdMax*sizeof(int));
|
||||
}
|
||||
if(fdCount==0) fdList[fdCount++] = selector.readfd();
|
||||
fdList[fdCount++] = script.sp.readFD;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::remove :
|
||||
// * This method calls the remove(fd) method to remove the ScriptData
|
||||
// * object that is specified by the caller.
|
||||
// *****************************************************************************
|
||||
void ScriptList::remove ( ScriptData & script )
|
||||
{
|
||||
remove(script.sp.readFD);
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::remove :
|
||||
// * This method will walk through all scripts in the list until it
|
||||
// * locates the file descriptor specified by fd. The method will
|
||||
// * then remove the ScriptData object that is associated with that
|
||||
// * file descriptor.
|
||||
// *
|
||||
// * The fdList and fdCount variables will be updated once the dead
|
||||
// * file descriptor has been removed.
|
||||
// *****************************************************************************
|
||||
void ScriptList::remove ( int fd )
|
||||
{
|
||||
ScriptData * prev = NULL;
|
||||
ScriptData * curr = scripts;
|
||||
|
||||
while(curr!=NULL && curr->sp.readFD!=fd)
|
||||
{
|
||||
prev = curr;
|
||||
curr = prev->next;
|
||||
}
|
||||
if(curr!=NULL)
|
||||
{
|
||||
if(prev!=NULL) prev->next = curr->next;
|
||||
else scripts = curr->next;
|
||||
delete curr;
|
||||
|
||||
for(fdCount=0, curr = scripts; curr!=NULL; curr=curr->next)
|
||||
{
|
||||
fdList[fdCount++] = curr->sp.readFD;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::getFd :
|
||||
// * This method allows the caller to obtain the list of file
|
||||
// * descriptors that are in use in all scripts. These descriptors
|
||||
// * will be used to perform ending at the cdevSystem level.
|
||||
// *
|
||||
// * Note that this list is updated and maintained each time the
|
||||
// * user calls "insert" to add a new file descriptor of "remove" to
|
||||
// * extract an old one.
|
||||
// *****************************************************************************
|
||||
int ScriptList::getFd ( int * &fd, int & numFd )
|
||||
{
|
||||
fd = fdList;
|
||||
numFd = fdCount;
|
||||
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptList::poll :
|
||||
// * This method is called to poll for events on a list of scripts
|
||||
// * that are currently executing. This method will return the
|
||||
// * count of callbacks that were dispatched during this pass through
|
||||
// * poll.
|
||||
// *****************************************************************************
|
||||
int ScriptList::poll ( void )
|
||||
{
|
||||
int nHandled = 0;
|
||||
ScriptData * prev = NULL;
|
||||
ScriptData * curr = scripts;
|
||||
|
||||
// *********************************************************************
|
||||
// * Clear any events that might be stored in the selector object.
|
||||
// *********************************************************************
|
||||
selector.purge();
|
||||
|
||||
// *********************************************************************
|
||||
// * Walk through each script and call the dispatch method to
|
||||
// * fire callbacks for all file descriptors that have data
|
||||
// * ready.
|
||||
// *********************************************************************
|
||||
for(curr=scripts; curr!=NULL; curr = curr->next)
|
||||
{
|
||||
nHandled+=curr->dispatch();
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * Walk through the list of scripts again. This time, check
|
||||
// * the finished flag to determine if each script has run to
|
||||
// * completion. If so, remove the script from the list of
|
||||
// * scripts and delete it.
|
||||
// *********************************************************************
|
||||
for(prev=NULL, curr=scripts; curr!=NULL; )
|
||||
{
|
||||
if(curr->finished)
|
||||
{
|
||||
int deadFd = curr->sp.readFD;
|
||||
curr = curr->next;
|
||||
remove(deadFd);
|
||||
}
|
||||
else {
|
||||
prev = curr;
|
||||
curr = prev->next;
|
||||
}
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * Return the total number of callbacks that were fired. This
|
||||
// * value will be used to allow for polling until at least one
|
||||
// * event has been processed.
|
||||
// *********************************************************************
|
||||
return nHandled;
|
||||
}
|
||||
|
||||
|
||||
|
||||
113
extensions/ScriptService/src/ScriptList.h
Executable file
113
extensions/ScriptService/src/ScriptList.h
Executable file
@@ -0,0 +1,113 @@
|
||||
/*
|
||||
* -----------------------------------------------------------------------------
|
||||
* Copyright (c) 1995 Southeastern Universities Research Association,
|
||||
* Continuous Electron Beam Accelerator Facility
|
||||
*
|
||||
* This software was developed under a United States Government license
|
||||
* described in the NOTICE file included as part of this distribution.
|
||||
*
|
||||
* -----------------------------------------------------------------------------
|
||||
*
|
||||
* Description:
|
||||
* This header file contains the class definitions for the classes
|
||||
* associated with the construction of a script service.
|
||||
*
|
||||
* Author: Walt Akers
|
||||
*
|
||||
* -----------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/wait.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <ctype.h>
|
||||
#include <cdevData.h>
|
||||
#include <cdevTranObj.h>
|
||||
#include <cdevSelector.h>
|
||||
// *****************************************************************************
|
||||
// * class ScriptData :
|
||||
// * This contains the information associated with a single script. A list
|
||||
// * of ScriptData objects is maintained and accessed through the ScriptList
|
||||
// * object.
|
||||
// *
|
||||
// * Note: because this object is only accessed through the ScriptList
|
||||
// * object, all data items have been made public to improve performance.
|
||||
// *****************************************************************************
|
||||
class ScriptData
|
||||
{
|
||||
public:
|
||||
typedef struct {
|
||||
int readFD;
|
||||
int writeFD;
|
||||
} SocketPair;
|
||||
|
||||
|
||||
ScriptData * next;
|
||||
SocketPair sp;
|
||||
cdevTranObj * xobj;
|
||||
cdevData * data;
|
||||
char * inputBuf;
|
||||
int inputBufLen;
|
||||
int amntRead;
|
||||
pid_t process;
|
||||
int finished;
|
||||
int callbackCount;
|
||||
|
||||
ScriptData ( cdevTranObj & Xobj );
|
||||
~ScriptData (void);
|
||||
static int data2Buffer (cdevData & data, char *& buf, int &bufLen);
|
||||
static void dataArray2Buffer (char * output,
|
||||
char ** ptr,
|
||||
size_t & ptrIdx,
|
||||
cdevBounds * bounds,
|
||||
size_t nBounds,
|
||||
size_t boundsIdx);
|
||||
static void dataArray2Buffer (char * output,
|
||||
double * ptr,
|
||||
size_t & ptrIdx,
|
||||
cdevBounds * bounds,
|
||||
size_t nBounds,
|
||||
size_t boundsIdx);
|
||||
static int buffer2Data (char * &buf, cdevData & data );
|
||||
void fireCallback (int result,
|
||||
void * arg,
|
||||
cdevRequestObject &req,
|
||||
cdevData & data,
|
||||
int partial=0);
|
||||
int dispatch (void);
|
||||
};
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * class ScriptList:
|
||||
// * This class maintains a list of ScriptData objects that represent all
|
||||
// * of the scripts that are currently being run by the ScriptService. The
|
||||
// * ScriptService object will use the methods of this object to perform
|
||||
// * operations on the items in the list.
|
||||
// *
|
||||
// * Because this class is only accessible through the ScriptService, its
|
||||
// * internals have been made public to improve performance.
|
||||
// *****************************************************************************
|
||||
class ScriptList
|
||||
{
|
||||
public:
|
||||
static cdevSelector selector;
|
||||
|
||||
ScriptData * scripts;
|
||||
int * fdList;
|
||||
int fdCount;
|
||||
int fdMax;
|
||||
|
||||
ScriptList (void);
|
||||
~ScriptList (void);
|
||||
ScriptData * find ( int fd );
|
||||
void insert ( ScriptData & script );
|
||||
void remove ( ScriptData & script );
|
||||
void remove ( int fd );
|
||||
int getFd ( int * &fd, int & numFd );
|
||||
int poll ( void );
|
||||
};
|
||||
|
||||
|
||||
|
||||
134
extensions/ScriptService/src/ScriptRequestObject.cc
Executable file
134
extensions/ScriptService/src/ScriptRequestObject.cc
Executable file
@@ -0,0 +1,134 @@
|
||||
//-----------------------------------------------------------------------------
|
||||
// Copyright (c) 1995 Southeastern Universities Research Association,
|
||||
// Continuous Electron Beam Accelerator Facility
|
||||
//
|
||||
// This software was developed under a United States Government license
|
||||
// described in the NOTICE file included as part of this distribution.
|
||||
//
|
||||
//-----------------------------------------------------------------------------
|
||||
//
|
||||
// Description:
|
||||
// This header file contains the class definitions for the classes
|
||||
// associated with the construction of a model request object.
|
||||
//
|
||||
// Author: Walt Akers
|
||||
//
|
||||
// Revision History:
|
||||
// ScriptRequestObject.cc,v
|
||||
// Revision 1.1 1997/02/11 17:37:24 akers
|
||||
// Directory restructure
|
||||
//
|
||||
// Revision 1.1 1997/01/30 20:35:34 akers
|
||||
// Initial installation of Script Service
|
||||
//
|
||||
//-----------------------------------------------------------------------------
|
||||
//
|
||||
|
||||
#include <ScriptService.h>
|
||||
#include <ScriptRequestObject.h>
|
||||
#include <cdevClock.h>
|
||||
|
||||
int ScriptRequestObject::syncCode = 0;
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::ScriptRequestObject :
|
||||
// * This constructor initializes the internals of a device/message
|
||||
// * pair associated with the model server.
|
||||
// *
|
||||
// * Returns nothing.
|
||||
// *********************************************************************
|
||||
ScriptRequestObject::ScriptRequestObject ( char * device, char * message, cdevSystem & system)
|
||||
: cdevRequestObject(device, message, system), syncFinished(0)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptRequestObject::sendNoBlock :
|
||||
// * This function allows the caller to submit an asynchronous message to the
|
||||
// * server for processing.
|
||||
// *****************************************************************************
|
||||
int ScriptRequestObject::sendNoBlock (cdevData * in, cdevData * out)
|
||||
{
|
||||
ScriptService * svc = (ScriptService *)service_;
|
||||
cdevTranObj * xobj = new cdevTranObj(&system_, this, out, &svc->asyncCallback);
|
||||
cdevData * Data = ((in==NULL)?new cdevData:new cdevData(*in));
|
||||
|
||||
return svc->submit(*xobj, *Data);
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptRequestObject::sendCallback :
|
||||
// * This function allows the caller to submit an asynchronous message to the
|
||||
// * server for processing.
|
||||
// *****************************************************************************
|
||||
int ScriptRequestObject::sendCallback (cdevData * in, cdevCallback & callback)
|
||||
{
|
||||
ScriptService * svc = (ScriptService *)service_;
|
||||
cdevTranObj * xobj = new cdevTranObj(&system_, this, NULL, new cdevCallback(callback));
|
||||
cdevData * Data = ((in==NULL)?new cdevData:new cdevData(*in));
|
||||
|
||||
xobj->enableDeleteCbk();
|
||||
return svc->submit(*xobj, *Data);
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptRequestObject::send :
|
||||
// * The send interface is used to provide synchronous I/O with the service.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *****************************************************************************
|
||||
int ScriptRequestObject::send ( cdevData * in, cdevData * out )
|
||||
{
|
||||
int status = CDEV_SUCCESS;
|
||||
ScriptService * svc = (ScriptService *)service_;
|
||||
cdevCallback * cb = new cdevCallback(ScriptService::syncCallbackFunc, (void *)++syncCode);
|
||||
cdevTranObj * xobj = new cdevTranObj(&system_, this, out, cb);
|
||||
cdevData * Data = ((in==NULL)?new cdevData:new cdevData(*in));
|
||||
|
||||
xobj->enableDeleteCbk();
|
||||
if((status = svc->submit(*xobj, *Data))==CDEV_SUCCESS)
|
||||
{
|
||||
// *************************************************************
|
||||
// * I used to wait for a response here only if the outbound
|
||||
// * cdevData object was non-null. However, that provided
|
||||
// * unexpected behavior to the client. Now I wait whether
|
||||
// * output data is expected or not.
|
||||
// *************************************************************
|
||||
cdevTimeValue t((double)SEND_WAIT_PERIOD);
|
||||
cdevClock timer;
|
||||
timer.schedule(NULL,t);
|
||||
|
||||
// *************************************************************
|
||||
// * WAITING WITH system_.pend():
|
||||
// * Previously I was using system_.pend() to process events
|
||||
// * while waiting for the service to respond. This resulted
|
||||
// * in a lock-up when the connection could not be
|
||||
// * established or if the connection collapsed while in use.
|
||||
// *
|
||||
// * WAITING WITH system_.poll():
|
||||
// * When in a heavy inbound traffic situation, the calls from other
|
||||
// * services will trample all over the inbound data coming from the
|
||||
// * model service. This results in unreliable delivery and
|
||||
// * processing of messages from the model server.
|
||||
// *
|
||||
// * WAITING WITH service_.poll():
|
||||
// * So far so good.
|
||||
// *************************************************************
|
||||
for(syncFinished=0; !syncFinished && !timer.expired(); svc->poll());
|
||||
if (!syncFinished)
|
||||
{
|
||||
status = CDEV_ERROR;
|
||||
system_.reportError(
|
||||
CDEV_SEVERITY_ERROR,
|
||||
"cdevRequestObject",
|
||||
this,
|
||||
"Transaction wasn't processed after %i seconds",
|
||||
SEND_WAIT_PERIOD);
|
||||
}
|
||||
else status = syncStatus;
|
||||
}
|
||||
return status;
|
||||
}
|
||||
121
extensions/ScriptService/src/ScriptRequestObject.h
Executable file
121
extensions/ScriptService/src/ScriptRequestObject.h
Executable file
@@ -0,0 +1,121 @@
|
||||
/*
|
||||
*-----------------------------------------------------------------------------
|
||||
* Copyright (c) 1995 Southeastern Universities Research Association,
|
||||
* Continuous Electron Beam Accelerator Facility
|
||||
*
|
||||
* This software was developed under a United States Government license
|
||||
* described in the NOTICE file included as part of this distribution.
|
||||
*
|
||||
*-----------------------------------------------------------------------------
|
||||
*
|
||||
* Description:
|
||||
* This header file contains the class definitions for the classes
|
||||
* associated with the construction of a request object.
|
||||
*
|
||||
* Author: Walt Akers
|
||||
*
|
||||
*-----------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#if !defined (_SCRIPT_REQUEST_OBJECT_H_)
|
||||
#define _SCRIPT_REQUEST_OBJECT_H_
|
||||
|
||||
#include <cdevRequestObject.h>
|
||||
#include <cdevTranObj.h>
|
||||
#include <cdevGroup.h>
|
||||
#include <cdevErrCode.h>
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptRequestObject:
|
||||
// * The ScriptRequestObject class provides the interface for sending
|
||||
// * messages to a server. All device/message commands are routed
|
||||
// * through a ScriptRequestObject either directly or indirectly.
|
||||
// *****************************************************************************
|
||||
class ScriptRequestObject : public cdevRequestObject
|
||||
{
|
||||
friend class ScriptService;
|
||||
|
||||
public:
|
||||
// *********************************************************************
|
||||
// * This is how long the system will wait for a reply to be returned
|
||||
// * from a send.
|
||||
// *********************************************************************
|
||||
enum { SEND_WAIT_PERIOD=30 };
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::ScriptRequestObject :
|
||||
// * This constructor initializes the internals of a device/message
|
||||
// * pair associated with the server.
|
||||
// *
|
||||
// * Returns nothing.
|
||||
// *********************************************************************
|
||||
ScriptRequestObject ( char * device, char * message,
|
||||
cdevSystem & system = cdevSystem::defaultSystem() );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::~ScriptRequestObject :
|
||||
// * This destructor performs any deallocation or shutdown operations
|
||||
// * necessary, prior to the destruction of the object.
|
||||
// *
|
||||
// * Returns nothing.
|
||||
// *********************************************************************
|
||||
virtual ~ScriptRequestObject ( void ) {}
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::send :
|
||||
// * The send interface is used to provide synchronous I/O with the
|
||||
// * service.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int send ( cdevData & in, cdevData & out )
|
||||
{ return send(&in, &out); }
|
||||
int send ( cdevData * in, cdevData & out )
|
||||
{ return send(in, &out); }
|
||||
int send ( cdevData & in, cdevData * out )
|
||||
{ return send(&in, out); }
|
||||
int send ( cdevData * in, cdevData * out );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::sendNoBlock :
|
||||
// * The sendNoBlock interface is used in conjunction with cdevGroup
|
||||
// * or cdevSystem to execute a series of operations. During the
|
||||
// * early implementation of this product, these functions will be
|
||||
// * linked directly to the send call.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int sendNoBlock (cdevData & in, cdevData & out)
|
||||
{ return sendNoBlock(&in, &out); }
|
||||
int sendNoBlock (cdevData * in, cdevData & out)
|
||||
{ return sendNoBlock(in, &out); }
|
||||
int sendNoBlock (cdevData & in, cdevData * out)
|
||||
{ return sendNoBlock(&in, out); }
|
||||
int sendNoBlock (cdevData * in, cdevData * out);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::sendCallback :
|
||||
// * The sendCallback interface provides asynchronous communications
|
||||
// * with the server. During the early implementation of this
|
||||
// * product, these functions will be linked directly to the send
|
||||
// * call.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int sendCallback (cdevData & in, cdevCallback & callback)
|
||||
{ return sendCallback(&in, callback); }
|
||||
int sendCallback (cdevData * in, cdevCallback & callback);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptRequestObject::className :
|
||||
// * This function returns the name of the class as a constant string
|
||||
// *********************************************************************
|
||||
const char * className ( void ) const { return "ScriptRequestObject"; }
|
||||
|
||||
private:
|
||||
int syncFinished;
|
||||
int syncStatus;
|
||||
static int syncCode;
|
||||
};
|
||||
|
||||
#endif /* _SCRIPT_REQUEST_OBJECT_H_ */
|
||||
381
extensions/ScriptService/src/ScriptService.cc
Executable file
381
extensions/ScriptService/src/ScriptService.cc
Executable file
@@ -0,0 +1,381 @@
|
||||
// -----------------------------------------------------------------------------
|
||||
// Copyright (c) 1995 Southeastern Universities Research Association,
|
||||
// Continuous Electron Beam Accelerator Facility
|
||||
//
|
||||
// This software was developed under a United States Government license
|
||||
// described in the NOTICE file included as part of this distribution.
|
||||
//
|
||||
// -----------------------------------------------------------------------------
|
||||
//
|
||||
// Description:
|
||||
// This header file contains the class definitions for the classes
|
||||
// associated with the construction of a script service.
|
||||
//
|
||||
// Author: Walt Akers
|
||||
//
|
||||
// Revision History:
|
||||
// ScriptService.cc,v
|
||||
// Revision 1.3 1997/02/14 20:43:41 akers
|
||||
// Ongoing improvement
|
||||
//
|
||||
// Revision 1.2 1997/02/14 20:06:32 akers
|
||||
// Ongoing improvement
|
||||
//
|
||||
// Revision 1.1 1997/02/11 17:37:27 akers
|
||||
// Directory restructure
|
||||
//
|
||||
// Revision 1.3 1997/01/31 18:51:27 akers
|
||||
// Ongoing development
|
||||
//
|
||||
// Revision 1.2 1997/01/31 16:21:24 akers
|
||||
// Ongoing development
|
||||
//
|
||||
// Revision 1.1 1997/01/30 20:35:35 akers
|
||||
// Initial installation of Script Service
|
||||
//
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
#include <signal.h>
|
||||
|
||||
#include "ScriptService.h"
|
||||
#include "cdevDirectory.h"
|
||||
#include "cdevClock.h"
|
||||
#include "ScriptList.h"
|
||||
|
||||
cdevSelector ScriptList::selector;
|
||||
|
||||
// ****************************************************************************
|
||||
// * This function is an interrupt handler that will be executed whenever the
|
||||
// * program receives a SIGCHLD signal. When called it will execute the poll
|
||||
// * method of the default server, in order to remove any dead Script Service
|
||||
// * processes.
|
||||
// ****************************************************************************
|
||||
static void SIGCHLD_handler (int)
|
||||
{
|
||||
ScriptList::selector.insertEvent();
|
||||
}
|
||||
|
||||
|
||||
// *********************************************************************
|
||||
// * newScriptService :
|
||||
// * This method is called by the cdevSystem object to load the
|
||||
// * initial instance of the ScriptService.
|
||||
// *********************************************************************
|
||||
cdevService * newScriptService ( char * name, cdevSystem * system )
|
||||
{
|
||||
signal(SIGCHLD, SIGCHLD_handler);
|
||||
return new ScriptService(name, *system);
|
||||
}
|
||||
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::ScriptService :
|
||||
// * This is the constructor for the script service. It determines
|
||||
// * the tag number for the "filename" tag if it does not already
|
||||
// * exist and allocates the ScriptList object that will be used
|
||||
// * to hold the individual script instances.
|
||||
// *********************************************************************
|
||||
ScriptService::ScriptService ( char * name, cdevSystem & system )
|
||||
: cdevService(name, system),
|
||||
FILENAME_TAG(1000),
|
||||
asyncCallback(asyncCallbackFunc, NULL)
|
||||
{
|
||||
scripts = new ScriptList;
|
||||
|
||||
while(cdevData::tagC2I("filename", &FILENAME_TAG)!=CDEV_SUCCESS)
|
||||
{
|
||||
cdevData::insertTag(++FILENAME_TAG, "filename");
|
||||
}
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::~ScriptService :
|
||||
// * This is the destructor for the script service,it does nothing
|
||||
// * but act as a placeholder for the virtual destructor.
|
||||
// *********************************************************************
|
||||
ScriptService::~ScriptService ( void )
|
||||
{
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::getRequestObject :
|
||||
// * This is the interface that cdev objects will use to obtain a
|
||||
// * ScriptRequestObject object. The ScriptRequestObject
|
||||
// * represents a combined device and message pair that is associated
|
||||
// * with the ScriptService.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int ScriptService::getRequestObject ( char * device, char * message, cdevRequestObject * &req)
|
||||
{
|
||||
req = new ScriptRequestObject (device, message, system_);
|
||||
return (req ? CDEV_SUCCESS : CDEV_ERROR);
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptService::getFd
|
||||
// * This function will return the list of file descriptors that the
|
||||
// * ScriptService is using. This will allow the file descriptors to be
|
||||
// * used in global select and poll calls performed at the cdevSystem class
|
||||
// * level.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *****************************************************************************
|
||||
int ScriptService::getFd ( int * &fd, int & numFd )
|
||||
{
|
||||
fd = scripts->fdList;
|
||||
numFd = scripts->fdCount;
|
||||
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::flush :
|
||||
// * This function flushes all communications buffers that the
|
||||
// * service may have open.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int ScriptService::flush ( void )
|
||||
{
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptService::poll :
|
||||
// * This function polls the file descriptors used by the service
|
||||
// * until one of them becomes active or a discrete amount of time
|
||||
// * has expired.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *****************************************************************************
|
||||
int ScriptService::poll ( void )
|
||||
{
|
||||
if(scripts->fdCount>0) scripts->poll();
|
||||
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptService::pend :
|
||||
// * Pends until the named file descriptor (or any file descriptor
|
||||
// * if fd = -1) is ready. Will pend forever if the descriptor does
|
||||
// * not become active.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *****************************************************************************
|
||||
int ScriptService::pend ( int )
|
||||
{
|
||||
while(scripts->fdCount>0 && scripts->poll()==0);
|
||||
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptService::pend :
|
||||
// * Pends until the named file descriptor (or any file descriptor
|
||||
// * if fd = -1) is ready. Will pend for no longer than the user
|
||||
// * specified number of seconds.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *****************************************************************************
|
||||
int ScriptService::pend ( double seconds, int )
|
||||
{
|
||||
if(scripts->fdCount > 0)
|
||||
{
|
||||
int nHandled = 0;
|
||||
cdevTimeValue sec = seconds;
|
||||
cdevClock timer;
|
||||
|
||||
timer.schedule(NULL, sec);
|
||||
|
||||
do {
|
||||
nHandled = scripts->poll();
|
||||
} while(!nHandled &&
|
||||
!timer.expired() &&
|
||||
scripts->fdCount>0);
|
||||
}
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptService::submit :
|
||||
// * This is the mechanism that the request object will use to submit a
|
||||
// * message to the service. It is important to note that all of the
|
||||
// * data provided to this object becomes the property of the service and
|
||||
// * must not be accessed afterwords.
|
||||
// *****************************************************************************
|
||||
int ScriptService::submit ( cdevTranObj &xobj, cdevData &data )
|
||||
{
|
||||
int status = CDEV_SUCCESS;
|
||||
|
||||
// *********************************************************************
|
||||
// * Attempt to read the script filename from the DDL file.
|
||||
// *********************************************************************
|
||||
ScriptData *script = new ScriptData(xobj);
|
||||
cdevData temp;
|
||||
char DDL_request[256];
|
||||
|
||||
sprintf (DDL_request,
|
||||
"resolveServiceData %s %s",
|
||||
xobj.reqObj_->device().name(),
|
||||
xobj.reqObj_->message());
|
||||
|
||||
if((system_.nameServer()).send(DDL_request, NULL, &temp)==CDEV_SUCCESS)
|
||||
{
|
||||
*DDL_request = 0;
|
||||
temp.get (FILENAME_TAG, DDL_request, 256);
|
||||
}
|
||||
else *DDL_request = 0;
|
||||
|
||||
// *********************************************************************
|
||||
// * If the script file was loaded, then begin the process of creating
|
||||
// * a pipe to retrieve the output of the script, and forking off an
|
||||
// * additional process to handle execution.
|
||||
// *********************************************************************
|
||||
if(*DDL_request)
|
||||
{
|
||||
char * parms = NULL;
|
||||
int bufLen = 0;
|
||||
|
||||
// *************************************************************
|
||||
// * Extract the data from the user provided output cdevData
|
||||
// * object into a string that can be passed to the script.
|
||||
// *************************************************************
|
||||
ScriptData::data2Buffer(data, parms, bufLen);
|
||||
|
||||
// *************************************************************
|
||||
// * Make a copy standard output for later use to restore the
|
||||
// * standard output file descriptor in the main thread...
|
||||
// * This is because the behaviour of vfork on some systems
|
||||
// * will leave the file descriptor in the main thread modified.
|
||||
// *************************************************************
|
||||
int fd = dup(1);
|
||||
|
||||
// *************************************************************
|
||||
// * Set the standard output file descriptor to the write file
|
||||
// * descriptor of the socket pair.
|
||||
// *************************************************************
|
||||
dup2(script->sp.writeFD, 1);
|
||||
|
||||
// *************************************************************
|
||||
// * Fork the process to allow the user application to continue
|
||||
// * running in the original branch, and the script to be
|
||||
// * executed in the new (child) process.
|
||||
// *************************************************************
|
||||
switch((script->process = vfork()))
|
||||
{
|
||||
// *****************************************************
|
||||
// * 0 Indicates that we are in the new child process.
|
||||
// *****************************************************
|
||||
case 0:
|
||||
{
|
||||
if(bufLen)
|
||||
{
|
||||
execl(DDL_request,
|
||||
DDL_request,
|
||||
xobj.reqObj_->device().name(),
|
||||
xobj.reqObj_->message(),
|
||||
parms, NULL);
|
||||
}
|
||||
else {
|
||||
execl(DDL_request,
|
||||
DDL_request,
|
||||
xobj.reqObj_->device().name(),
|
||||
xobj.reqObj_->message(),
|
||||
NULL);
|
||||
}
|
||||
exit(-1);
|
||||
}
|
||||
break;
|
||||
|
||||
// *****************************************************
|
||||
// * -1 Indicates that a new process could not be
|
||||
// * forked.
|
||||
// *****************************************************
|
||||
case -1:
|
||||
{
|
||||
// *********************************************
|
||||
// * Restore the standard output file descriptor
|
||||
// *********************************************
|
||||
dup2(fd, 1);
|
||||
close(fd);
|
||||
|
||||
system_.reportError(
|
||||
CDEV_SEVERITY_ERROR,
|
||||
"ScriptService",
|
||||
xobj.reqObj_,
|
||||
"Failed to fork a new process");
|
||||
|
||||
script->fireCallback(CDEV_ERROR,
|
||||
xobj.userCallback_->userarg(),
|
||||
*xobj.reqObj_,
|
||||
*script->data);
|
||||
|
||||
status = CDEV_ERROR;
|
||||
delete script;
|
||||
}
|
||||
break;
|
||||
|
||||
// *****************************************************
|
||||
// * Any other value indicates that we are in the parent
|
||||
// * and the value is the process ID of the new child.
|
||||
// *****************************************************
|
||||
default:
|
||||
{
|
||||
// *********************************************
|
||||
// * Restore the standard output file descriptor
|
||||
// *********************************************
|
||||
dup2(fd, 1);
|
||||
close(fd);
|
||||
|
||||
// *********************************************
|
||||
// * Insert the script into the list.
|
||||
// *********************************************
|
||||
scripts->insert(*script);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
// *************************************************************
|
||||
// * Delete parameters (if any).
|
||||
// *************************************************************
|
||||
if(bufLen) delete parms;
|
||||
}
|
||||
else {
|
||||
system_.reportError(
|
||||
CDEV_SEVERITY_ERROR,
|
||||
"ScriptService",
|
||||
xobj.reqObj_,
|
||||
"No filename specified for request %s %s",
|
||||
xobj.reqObj_->device().name(),
|
||||
xobj.reqObj_->message());
|
||||
|
||||
script->fireCallback(CDEV_ERROR,
|
||||
xobj.userCallback_->userarg(),
|
||||
*xobj.reqObj_,
|
||||
*script->data);
|
||||
status = CDEV_ERROR;
|
||||
delete script;
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
// *****************************************************************************
|
||||
// * ScriptService::getNameServer :
|
||||
// * This function should obtain the default name server for this object.
|
||||
// * It does nothing for now.
|
||||
// *****************************************************************************
|
||||
int ScriptService::getNameServer(cdevDevice * &ns)
|
||||
{
|
||||
ns = 0;
|
||||
return CDEV_SUCCESS;
|
||||
}
|
||||
166
extensions/ScriptService/src/ScriptService.h
Executable file
166
extensions/ScriptService/src/ScriptService.h
Executable file
@@ -0,0 +1,166 @@
|
||||
/*
|
||||
*-----------------------------------------------------------------------------
|
||||
* Copyright (c) 1995 Southeastern Universities Research Association,
|
||||
* Continuous Electron Beam Accelerator Facility
|
||||
*
|
||||
* This software was developed under a United States Government license
|
||||
* described in the NOTICE file included as part of this distribution.
|
||||
*
|
||||
*-----------------------------------------------------------------------------
|
||||
*
|
||||
* Description:
|
||||
* This header file contains the class definitions for the classes
|
||||
* associated with the construction of a script service.
|
||||
*
|
||||
* Author: Walt Akers
|
||||
*
|
||||
*-----------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#if !defined (_SCRIPT_SERVICE_H_)
|
||||
#define _SCRIPT_SERVICE_H_
|
||||
|
||||
#include <cdevService.h>
|
||||
#include "ScriptRequestObject.h"
|
||||
|
||||
extern "C" cdevService *newScriptService ( char * name, cdevSystem * system );
|
||||
|
||||
class ScriptService : public cdevService
|
||||
{
|
||||
friend class ScriptRequestObject;
|
||||
|
||||
public:
|
||||
// *********************************************************************
|
||||
// * ScriptService::ScriptService :
|
||||
// * This constructor is responsible for performing all service
|
||||
// * initialization.
|
||||
// *********************************************************************
|
||||
ScriptService ( char * name, cdevSystem & system );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::~ScriptService :
|
||||
// * The destructor is protected to prevent it from being called
|
||||
// * directly. The destructor performs any clean-up or shutdown
|
||||
// * operations.
|
||||
// *
|
||||
// * Returns nothing.
|
||||
// *********************************************************************
|
||||
~ScriptService ( void );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::installTags :
|
||||
// * Installs the tags that the service and service applications
|
||||
// * will use. This function is static to allow servers to setup
|
||||
// * the necessary tags without having to instanciate a
|
||||
// * ScriptService object.
|
||||
// *********************************************************************
|
||||
void installTags ( void );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::getRequestObject :
|
||||
// * This is the interface that cdev objects will use to obtain a
|
||||
// * cdevSimpleRequestObject object. The cdevSimpleRequestObject
|
||||
// * represents a combined device and message pair that is associated
|
||||
// * with the ScriptService.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int getRequestObject (char *, char *, cdevRequestObject * &);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::getFd
|
||||
// * This function will return the list of file descriptors that the
|
||||
// * ScriptService is using. This will allow the file
|
||||
// * descriptors to be used in global select and poll calls performed
|
||||
// * at the cdevSystem class level.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int getFd ( int * &fd, int & numFd );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::flush :
|
||||
// * This function flushes all communications buffers that the
|
||||
// * service may have open.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int flush ( void );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::poll :
|
||||
// * This function polls the file descriptors used by the service
|
||||
// * until one of them becomes active or a discrete amount of time
|
||||
// * has expired.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int poll ( void );
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::pend :
|
||||
// * Pends until the named file descriptor (or any file descriptor
|
||||
// * if fd = -1) is ready. Will pend for no longer than the user
|
||||
// * specified number of seconds.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int pend ( double seconds, int = -1);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::pend :
|
||||
// * Pends until the named file descriptor (or any file descriptor
|
||||
// * if fd = -1) is ready. Will pend forever if the descriptor does
|
||||
// * not become active.
|
||||
// *
|
||||
// * Returns CDEV_SUCCESS on success or CDEV_ERROR on error.
|
||||
// *********************************************************************
|
||||
int pend ( int = -1);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::submit :
|
||||
// * This is the mechanism that the request object will use to submit
|
||||
// * a message to the service. It is important to note that all of
|
||||
// * the data provided to this object becomes the property of the
|
||||
// * service and must not be accessed afterwords.
|
||||
// *********************************************************************
|
||||
int submit (cdevTranObj &, cdevData &);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::getNameServer :
|
||||
// * This function should obtain the default name server for this
|
||||
// * object. It does nothing for now.
|
||||
// *********************************************************************
|
||||
int getNameServer(cdevDevice * &ns);
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::asyncCallback :
|
||||
// * This method is called in response to a sendNoBlock reply.
|
||||
// *********************************************************************
|
||||
static void asyncCallbackFunc (int, void *, cdevRequestObject &, cdevData &)
|
||||
{
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// * ScriptService::syncCallback :
|
||||
// * This method is called whenever a send is requested from a
|
||||
// * ScriptRequestObject.
|
||||
// *********************************************************************
|
||||
static void syncCallbackFunc ( int status, void *arg, cdevRequestObject &req, cdevData &)
|
||||
{
|
||||
ScriptRequestObject * sReq = (ScriptRequestObject *)&req;
|
||||
int syncCode = (int)arg;
|
||||
|
||||
if(syncCode == sReq->syncCode)
|
||||
{
|
||||
sReq->syncFinished = 1;
|
||||
sReq->syncStatus = status;
|
||||
}
|
||||
}
|
||||
protected:
|
||||
int FILENAME_TAG;
|
||||
class ScriptList * scripts;
|
||||
cdevCallback asyncCallback;
|
||||
};
|
||||
|
||||
#endif /* _SCRIPT_SERVICE_H_ */
|
||||
BIN
extensions/ScriptService/test/.shobj/Linux/TestProgram.o
Normal file
BIN
extensions/ScriptService/test/.shobj/Linux/TestProgram.o
Normal file
Binary file not shown.
BIN
extensions/ScriptService/test/.shobj/Linux/TestProgram2.o
Normal file
BIN
extensions/ScriptService/test/.shobj/Linux/TestProgram2.o
Normal file
Binary file not shown.
39
extensions/ScriptService/test/Makefile
Executable file
39
extensions/ScriptService/test/Makefile
Executable file
@@ -0,0 +1,39 @@
|
||||
ARCH = OS
|
||||
SHOBJ = YES
|
||||
|
||||
include $(CDEV)/extensions/cdevGenericServer/include/makeinclude/Makefile.$(ARCH)
|
||||
|
||||
APPNAME = "CDEV/ACE Script Service Tests"
|
||||
CXXINCLUDES = -I./
|
||||
BASEBIN = ./
|
||||
SO_LIBS = $(OSLIBS)
|
||||
|
||||
# ******************************************************************************
|
||||
# * The BINARIES definition names all of the binary files that should be deleted
|
||||
# * whenever "make clean" is executed.
|
||||
# ******************************************************************************
|
||||
BINARIES = $(BASEBIN)/TestProgram $(BASEBIN)/TestProgram2
|
||||
|
||||
ifeq ($(SHOBJ), YES)
|
||||
LIBS = $(CDEVLIBS) $(OSLIBS)
|
||||
TARGETS = $(BASEBIN)/TestProgram \
|
||||
$(BASEBIN)/TestProgram2
|
||||
else
|
||||
LIBS = $(CDEVLIBS) -lScriptService $(OSLIBS)
|
||||
TARGETS = $(BASEBIN)/TestProgram \
|
||||
$(BASEBIN)/TestProgram2
|
||||
endif
|
||||
|
||||
targets : $(TARGETS)
|
||||
|
||||
$(BASEBIN)/TestProgram : $(OBJDIR)/TestProgram.o
|
||||
@rm -f $@
|
||||
@echo "=> $(CXX) -o $(@F) $(^F)"
|
||||
@$(LINK.cc) $^ -o $@ $(LIBS)
|
||||
@echo "<= Done...\n"
|
||||
|
||||
$(BASEBIN)/TestProgram2 : $(OBJDIR)/TestProgram2.o
|
||||
@rm -f $@
|
||||
@echo "=> $(CXX) -o $(@F) $(^F)"
|
||||
@$(LINK.cc) $^ -o $@ $(LIBS)
|
||||
@echo "<= Done...\n"
|
||||
27
extensions/ScriptService/test/Script.ddl
Executable file
27
extensions/ScriptService/test/Script.ddl
Executable file
@@ -0,0 +1,27 @@
|
||||
service Script
|
||||
{
|
||||
tags {filename}
|
||||
}
|
||||
|
||||
class scriptClass
|
||||
{
|
||||
verbs {get, set, monitorOn, monitorOff}
|
||||
attributes
|
||||
{
|
||||
attrib0 Script {filename = <>.attrib0};
|
||||
attrib1 Script {filename = <>.attrib1};
|
||||
attrib2 Script {filename = <>.attrib2};
|
||||
attrib3 Script {filename = <>.attrib3};
|
||||
attrib4 Script {filename = <>.attrib4};
|
||||
attrib5 Script {filename = <>.attrib5};
|
||||
attrib6 Script {filename = <>.attrib6};
|
||||
attrib7 Script {filename = <>.attrib7};
|
||||
attrib8 Script {filename = <>.attrib8};
|
||||
attrib9 Script;
|
||||
}
|
||||
}
|
||||
|
||||
scriptClass :
|
||||
device0, device1, device2, device3, device4,
|
||||
device5, device6, device7, device8, device9
|
||||
;
|
||||
BIN
extensions/ScriptService/test/TestProgram
Executable file
BIN
extensions/ScriptService/test/TestProgram
Executable file
Binary file not shown.
76
extensions/ScriptService/test/TestProgram.cc
Executable file
76
extensions/ScriptService/test/TestProgram.cc
Executable file
@@ -0,0 +1,76 @@
|
||||
#include <cdevSystem.h>
|
||||
#include <cdevRequestObject.h>
|
||||
#include <cdevCallback.h>
|
||||
#include <cdevGroup.h>
|
||||
|
||||
void callback (int, void *arg, cdevRequestObject &, cdevData &)
|
||||
{
|
||||
static int totalCount = 0;
|
||||
int * resultCount = (int *)arg;
|
||||
(*resultCount)++;
|
||||
|
||||
fprintf(stdout, "Total count = %i\n", ++totalCount);
|
||||
}
|
||||
|
||||
char * data[2][2][3] =
|
||||
{
|
||||
{{"1", "2", "3"}, {"4", "5", "6"}},
|
||||
{{"1", "2", "3"}, {"4", "5", "6"}},
|
||||
};
|
||||
|
||||
double dData[2][2][3] =
|
||||
{
|
||||
{{1.1, 2.2, 3.3}, {4.4, 5.5, 6.6}},
|
||||
{{1.7, 2.8, 3.9}, {4.11, 5.12, 6.13}}
|
||||
};
|
||||
|
||||
cdevBounds bounds[3] =
|
||||
{{0, 2},
|
||||
{0, 2},
|
||||
{0, 3}};
|
||||
|
||||
int main ( void )
|
||||
{
|
||||
int resultCount = 0;
|
||||
cdevData in;
|
||||
cdevRequestObject & req = cdevRequestObject::attachRef("device0", "get attrib0");
|
||||
cdevCallback cb (callback, &resultCount);
|
||||
|
||||
in.insert("value", (char **)data, 12, 3);
|
||||
in.setBounds("value", bounds, 3);
|
||||
in.insert("severity", (double*)dData, 12, 3);
|
||||
in.setBounds("severity", bounds, 3);
|
||||
in.insert("status", "Testing");
|
||||
|
||||
for(int i=0; i<10; i++)
|
||||
{
|
||||
resultCount = 0;
|
||||
|
||||
for(int j=0; j<20; j++)
|
||||
{
|
||||
req.sendCallback(in, cb);
|
||||
}
|
||||
while(resultCount<26) cdevSystem::defaultSystem().poll();
|
||||
}
|
||||
}
|
||||
/*
|
||||
#include "ScriptList.cc"
|
||||
|
||||
int main()
|
||||
{
|
||||
cdevData in, out;
|
||||
char * buf;
|
||||
int bufLen;
|
||||
|
||||
in.insert("value", (char **)data, 12, 3);
|
||||
in.setBounds("value", bounds, 3);
|
||||
in.insert("severity", (double*)dData, 12, 3);
|
||||
in.setBounds("severity", bounds, 3);
|
||||
in.insert("status", "Testing");
|
||||
|
||||
ScriptData::data2Buffer(in, buf, bufLen);
|
||||
ScriptData::buffer2Data(buf, out);
|
||||
out.asciiDump();
|
||||
delete buf;
|
||||
}
|
||||
*/
|
||||
BIN
extensions/ScriptService/test/TestProgram2
Executable file
BIN
extensions/ScriptService/test/TestProgram2
Executable file
Binary file not shown.
27
extensions/ScriptService/test/TestProgram2.cc
Executable file
27
extensions/ScriptService/test/TestProgram2.cc
Executable file
@@ -0,0 +1,27 @@
|
||||
#include <cdevSystem.h>
|
||||
#include <cdevRequestObject.h>
|
||||
#include <cdevCallback.h>
|
||||
#include <cdevGroup.h>
|
||||
|
||||
int done = 0;
|
||||
|
||||
void callback (int, void *, cdevRequestObject &, cdevData &data)
|
||||
{
|
||||
static int resultCount = 0;
|
||||
done = cdevCallback::isTransactionDone();
|
||||
fprintf(stdout, "Result count %i - %s done...\n", ++resultCount, done?" ":"NOT");
|
||||
if(done) data.asciiDump();
|
||||
}
|
||||
|
||||
int main ( void )
|
||||
{
|
||||
cdevData in;
|
||||
cdevRequestObject & req = cdevRequestObject::attachRef("device0", "get attrib0");
|
||||
cdevCallback cb (callback, NULL);
|
||||
|
||||
req.sendCallback(in, cb);
|
||||
while(!done)
|
||||
{
|
||||
cdevSystem::defaultSystem().pend();
|
||||
}
|
||||
}
|
||||
386
extensions/ScriptService/test/device0.attrib0
Executable file
386
extensions/ScriptService/test/device0.attrib0
Executable file
@@ -0,0 +1,386 @@
|
||||
#! /bin/csh -f
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value=1\nseverity="GOOD"\nstatus=0\nend\n'
|
||||
printf 'value={{1,2,3},{4,5,6}}\nseverity="NOT so GOOD"\nstatus=0\ncontrolLow={1, 2, 3}\ndone\n'
|
||||
1
extensions/ScriptService/test/device0.attrib1
Executable file
1
extensions/ScriptService/test/device0.attrib1
Executable file
@@ -0,0 +1 @@
|
||||
#! /bin/csh
|
||||
15
extensions/ScriptService/test/odebug.txt
Executable file
15
extensions/ScriptService/test/odebug.txt
Executable file
@@ -0,0 +1,15 @@
|
||||
load /lib/milli.a
|
||||
load /lib/libc.sl
|
||||
load /usr/csite4/CenterLine/pa-hpux8/lib/libC.a
|
||||
load -G /usr/csite/cdev/1.5/lib/hpux-09.XX/libcdev.a
|
||||
load -D_OS_MAJOR_=9 \
|
||||
-D_OS_MINOR_=7 \
|
||||
-I/usr/csite/cdev/1.5/include \
|
||||
-g -D_HAS_CA -pta \
|
||||
-I./ -I../src\
|
||||
../src/ScriptList.cc \
|
||||
../src/ScriptService.cc \
|
||||
../src/ScriptRequestObject.cc \
|
||||
TestProgram2.cc \
|
||||
-ly -ll -L/lib -lm
|
||||
link
|
||||
Reference in New Issue
Block a user