|
Referencing Synergy .NET Assemblies
By David Barron, Sr. Systems Software Engineer, Synergy/DE
One of the exciting new features in Synergy/DE 9.5 is the ability to build and run Synergy Language applications within Microsoft’s .NET Framework. This feature is part of Synergy .NET, which provides built-in compile-time and runtime support for most Synergy Language statements, subroutines, and functions. This includes many of the Synergy Language APIs, such as the Synergy socket API and the Synergy windowing API, and if you install Synergy Language Integration for Visual Studio, you will see IntelliSense for Synergy statements and routines when typing in the Visual Studio 2010 editor.
Some features, however, aren’t automatically available. Synergy .NET allows you to access the Repository subroutine library, the Synergy XML API, and many UI Toolkit routines. But to access one of these APIs from within .NET, or to access Synergy data type classes from a non-Synergy project type, you must add a reference to an assembly:
- For the Repository subroutine library, add a reference to Synergex.SynergyDE.ddlib.
- For the Synergy XML API, add a reference to Synergex.SynergyDE.synxml.
- For UI Toolkit routines, add a reference to Synergex.SynergyDE.tklib.
- To access Synergy data type classes from a non-Synergy project type, add a reference to Synergex.SynergyDE.synrnt.
To add a reference to one of these assemblies, follow these steps from within your project:
-
Find Solution Explorer. By default, it is docked on the right edge of the Visual Studio IDE. If it’s not there, you can use the View > Solution Explorer menu entry to see it.
- Right-click on the References node of the tree in Solution Explorer. A context menu with a single entry, Add Reference, will open. Select this. The Add Reference dialog opens to allow you to select from a list of available assemblies. Select the .NET tab. It may take a few seconds to populate the list.
- Scroll down until you find the assembly you are looking for, and double-click it. This adds a reference to the assembly, which appears as an entry in the Reference branch of Solution Explorer.
If you’re like me and prefer to use the command line, you can add an assembly reference to the compilation using the -ref option for dblnet. It looks like this for the Repository subroutine library:
dblnet –ref=”C:\program files (x86)\Common Files\Synergex\CLR20\Synergex.SynergyDE.ddlib.dll” yourfile.dbl
Note that all of the assemblies listed above are in the same directory: C:\Program Files (x86)\Common Files\Synergex\CLR20 for 64-bit and C:\Program Files\Common Files\Synergex\CLR20 for 32-bit.
Once a reference has been added to one of these assemblies, you can use its functionality (routines and classes).
See the Repository User’s Guide, Synergy Language Reference Manual, and UI Toolkit Reference Manual for more information on the APIs mentioned above, and see chapter 7 of Getting Started with Synergy/DE for information on using Synergy data type classes in non-Synergy projects. Also note that not all UI Toolkit routines are supported. UI Toolkit will throw a trappable error (runtime error 507, $ERR_UNSUP) if any unsupported routine is called in your Synergy .NET application. See the Professional Series Portability Guide for the list of UI Toolkit routines supported in Synergy .NET.
For more information about Synergy/DE 9.5, see our website.
Calling a destructor from outside a shared image on OpenVMS
Question:
I have a class with a destructor on OpenVMS, and the class methods (including the destructor) are in a shared image. However, I’m getting the following error:
%DBL-F-RUNERR, Internal runtime failure: Undefined destructor NS.CLS.~CLS()
Why isn’t the destructor being found?
Answer:
For class methods to be called from outside the shared image, the methods must be in the vector list. The destructor is in a unique situation. None of the methods in the class need to be in the vector list when all of the class usage is entirely within the shared image, except that the destructor is not explicitly called. The destructor is called when the object goes out of scope or is destroyed. The calling of the destructor is performed from within the runtime, and the routine address is looked up when it is called. The Synergy runtime knows the names of all routines in the primary executable, but the routines in a shared image are hidden unless they are in the vector list, so the runtime does the same thing that an XSUBR call does: it looks first for a routine in its internal tables, and if the routine is not found, it looks for it in the vectors of any shared images it knows about. Because the runtime only knows about shared images that have been opened (either through OPENELB, XSUBR, or XADDR), if the shared image has not been opened, it is not searched.
This means that the destructor must be in the vector list of the shared image. However, when it is included, an error is generated:
%ILINK-F-OPTSYNERR, syntax error in options file
This problem occurs because of the tilde (~) in the name of the destructor. (All destructor names begin with a tilde.) The OpenVMS linker does not allow a routine name with a tilde in it to be specified in the vector list of an options file. The only way around this limitation is not to have a destructor in the classes that are placed in a shared image.
What if you need to do special processing before the object is destroyed? The only way to accomplish this is to write a special method that is not a destructor to do the special processing, and always explicitly call it before the object is destroyed. This is not the best situation, but until the OpenVMS linker is fixed to allow tildes in routine names in the vector list of an options file, it is the only workaround.
Synergy/DE pros, see if you can answer this question!
What keeps the following program from compiling in version 9.5.1 on all supported platforms?
namespace Justin
class Case
public virtual method doit, int
proc
mreturn TRUE
end
endclass
class Time extends Case
public override method Doit, int
proc
mreturn %cputime
end
endclass
endnamespace
main
record
t ,@Time
proc
t = new Justin.Time()
t.Doit()
end
a. TRUE is not defined
b. %CPUTIME is not supported on all platforms
c. The override method "Doit" differs in case from its base method
d. Nothing, this compiles fine everywhere
Read a selection of recent articles from around the web
|
|