On 01.05.2017 16:19, Rick McGuire wrote:
> If the parsing event handler is storing references to any of the proxy 
> objects in other ooRexx
> objects (arrays, etc.), those objects will still be anchored. The uninits are 
> definitely
> interleaved with execution in the sample program, so problems from this point 
> are probably in how
> the code in question is managing the object references.
No, there are no references on the ooRexx side that would keep them referenced 
(cf. the short demo
Rexx program is enclosed). The native code does not refer to them either beyond 
the
AttachThread/DetachThread section (the Java arguments are turned into Rexx 
arguments which get
stored in a RexxArray and supplied in the SendMessage call).

---

I re-ran the SAX test program after noticing that running the 
test01.rex/test_gc.dll combo, no
uninits are run while being in native code and while creating 100,000 to 
1,000,000 ABC objects that
immediately turn into garbage. As each ABC object gets created in a single 
AttachThread/DetachThread
section, the created ABC object should turn to garbage after the DetachThread 
call as neither the
Rexx test script nor the native code would refer to it anymore.

The AttachThread/DetachThread invocations in native code occur in the same 
thread that invoked the
external Rexx function ("call CreateABCObjects nr"). And it seems that only 
upon return from the
CreaetABCObjects-call (or probably after ending the Rexx program) the ABC 
uninits start to run.

---rony


>
> On Mon, May 1, 2017 at 10:14 AM, Rony G. Flatscher <rony.flatsc...@wu.ac.at
> <mailto:rony.flatsc...@wu.ac.at>> wrote:
>
>     Retested today quite exhaustively (see below), and indeed I cannot create 
> any Rexx crashes
>     anymore, which is *really* great!
>
>     ---
>
>     However, retesting today, I just realized, that all the uninits only 
> start to run *after* the
>     test script ends!
>
>     Running the test script on the patched interpreter with "test01.rex 2>&1 
> | gvim -" will yield
>     (the "duration:" output is the last statement of the program):
>
>       * 100.000 ABC objects created in native code
>
>         ... InitializeRII(): gRI=[7DBA8178] started: 
> 2017-05-01T14:57:18.003000 ... about to
>         create [100000] ABC objects by native code... *ended:* 
> 2017-05-01T14:57:33.703000
>         duration: 00:00:15.700000 *** ::UNINIT:
>         [ABC-from_native_createTestObject-88726]@[FFFFFFFFFF95351217] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-89421]@[FFFFFFFFFF9526FCC7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-90116]@[FFFFFFFFFF9518E777] ... cut 
> ...
>
>       * 250.000 ABC objects created in native code
>
>         ... InitializeRII(): gRI=[7DBA8178] started: 
> 2017-05-01T14:51:54.135000 ... about to
>         create [250000] ABC objects by native code... ended: 
> 2017-05-01T14:53:42.775000 duration:
>         00:01:48.640000 *** ::UNINIT:
>         [ABC-from_native_createTestObject-42126]@[FFFFFFFFFF879A4AE7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-195246]@[FFFFFFFFFFA7279DCF] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-12005]@[FFFFFFFFFF829BF5F7] ... cut 
> ...
>
>       * 500.000 ABC objects created in native code
>
>         ... InitializeRII(): gRI=[7DBA8178] started: 
> 2017-05-01T14:57:46.935000 ... about to
>         create [500000] ABC objects by native code... ended: 
> 2017-05-01T15:04:06.482000 duration:
>         00:06:19.547000 *** ::UNINIT:
>         [ABC-from_native_createTestObject-42126]@[FFFFFFFFFF879A4AE7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-120397]@[FFFFFFFFFF9A8F9EC7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-195246]@[FFFFFFFFFFA7279DCF]... cut 
> ...
>
>       * 750.000 ABC objects created in native code
>
>         ... InitializeRII(): gRI=[7DBA8178] started: 
> 2017-05-01T15:05:09.713000 ... about to
>         create [750000] ABC objects by native code... ended: 
> 2017-05-01T15:25:33.533000 duration:
>         00:20:23.820000 *** ::UNINIT:
>         [ABC-from_native_createTestObject-166273]@[FFFFFFFFFF9DD3FCF7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-416933]@[FFFFFFFFFFC109519F] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-516807]@[FFFFFFFFFFCE93FC07] ... 
> cut...
>
>       * 1.000.000 ABC objects created in native code
>
>         ... InitializeRII(): gRI=[7DBA8178] started: 
> 2017-05-01T15:28:40.547000 ... about to
>         create [1000000] ABC objects by native code... ended: 
> 2017-05-01T15:58:49.271000 duration:
>         00:30:08.724000 *** ::UNINIT:
>         [ABC-from_native_createTestObject-795014]@[FFFFFFFFFFFAFEA5D7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-520973]@[FFFFFFFFFFCAA6A6C7] *** 
> ::UNINIT:
>         [ABC-from_native_createTestObject-240938]@[FFFFFFFFFFAD9AA757]
>
>     (In all tests the number of uninits that ran upon program completion 
> corresponds to the number
>     of ABC objects created except for the last one where two uninits are 
> missing.)
>
>     Re-running the original program (using a Java SAX parser that causes 
> callbacks into ooRexx via
>     JNI/native code) that caused the "Error 5: System resources exhausted" on 
> the 32-bit ooRexx
>     interpreter still causes the error (around parsing the 84900th XML 
> element).
>
>     ---rony
>
>     On 30.04.2017 22:18, Rony G. Flatscher wrote:
>>
>>     Applying your patch and re-running the problematic test-cases, it seems 
>> to be indeed the case
>>     that the problem is solved! Many thanks!
>>
>>     ---rony
>>
>>     On 30.04.2017 13:00, Rony G. Flatscher wrote:
>>>     On 30.04.2017 12:53, Rick McGuire wrote:
>>>>     I want to verify something first. In this scenario, Rexx code makes a 
>>>> call to a Java method
>>>>     (i.e., the parser) which then makes a lot of callbacks all on the same 
>>>> thread?
>>>     Yes.
>>>>     If so, then I think I might see where the problem could be. The code 
>>>> that handles nested
>>>>     thread attaches (that is, attaching to a thread that already exists) 
>>>> appears to hold on to
>>>>     any allocated objects until it returns to the original exit point (in 
>>>> your case, the
>>>>     initial call to the parser). 
>>>>     This may take a little while to figure out the details of a fix, but I 
>>>> at least know where
>>>>     to start. You might want to open a bug indicating there appears to be 
>>>> an
>>>>     AttachThread()/DetachThread() memory leak.
>>>     Opened a bug: <https://sourceforge.net/p/oorexx/bugs/1445/>
>>>     <https://sourceforge.net/p/oorexx/bugs/1445/>. ---rony
>>>>     On Sun, Apr 30, 2017 at 6:38 AM, Rony G. Flatscher 
>>>> <rony.flatsc...@wu.ac.at
>>>>     <mailto:rony.flatsc...@wu.ac.at>> wrote:
>>>>
>>>>         Having slept I went over the debug statements, just to learn that 
>>>> I concluded wrongly
>>>>         yesterday: the reference decreases did not come from the Rexx 
>>>> objects with uninits, but
>>>>         from the Java side! :(
>>>>
>>>>         With new debug statements on the Rexx side (in the destructores) 
>>>> it is clear that no
>>>>         proxy Rexx object turns into garbage before the program gets 
>>>> interrupted with a syntax
>>>>         error.
>>>>
>>>>         Will start over analyzing the codepaths, creating debug programs 
>>>> and report back, once
>>>>         I am done, which might take a day or two.
>>>>
>>>>         ---rony
>>>>         On 29.04.2017 21:53, Rick McGuire wrote:
>>>>>         On Sat, Apr 29, 2017 at 3:43 PM, Rony G. Flatscher 
>>>>> <rony.flatsc...@wu.ac.at
>>>>>         <mailto:rony.flatsc...@wu.ac.at>> wrote:
>>>>>
>>>>>             The class object (for the BSF class and also its subclasses) 
>>>>> is (get) created in
>>>>>             the BSF.CLS package, which gets required. So it (and its 
>>>>> subclasses) should get
>>>>>             created only once in this test case. The ooRexx peer objects 
>>>>> are instances of the
>>>>>             .BSF class, which defines an uninit method. Ad interpreter 
>>>>> safepoints:
>>>>>
>>>>>               * in this case there is a pending external Rexx function 
>>>>> call that kicks of the
>>>>>                 SAX parser's parsing and only will return after the SAX 
>>>>> parser concluded its work,
>>>>>               * in the meantime each callback from the SAX parser will 
>>>>> cause a call via JNI to
>>>>>                 Rexx, where each such callback will do an AttachThread() 
>>>>> in native code and
>>>>>                 before returning a DetachThread().
>>>>>
>>>>>             The uninits run, so these interpreter safepoints should be 
>>>>> reached.
>>>>>
>>>>>         The return from the ooRexx code at the end of the event call is 
>>>>> one safepoint, but the
>>>>>         arguments you passed will still be protected at this point. 
>>>>> However, these objects
>>>>>         will not be processed until the next time a garbage collection is 
>>>>> required and then
>>>>>         not until the next uninit point is hit. 
>>>>>          
>>>>>
>>>>>             --- Maybe one more thing: the ooRexx peer objects that get 
>>>>> created in native code
>>>>>             are stored in a RexxArray object as they server as arguments 
>>>>> for the SendMessage()
>>>>>             function. So I assume (pure speculation!) that first the 
>>>>> RexxArray object needs to
>>>>>             get destroyed in order for its contained objects to become 
>>>>> eligible for
>>>>>             destruction. Maybe that explains why the Rexx peer objects 
>>>>> currently do not get
>>>>>             their uninits run at a much faster pace.
>>>>>
>>>>>         I doubt this causes much of the delay, since these objects don't 
>>>>> get moved to the
>>>>>         uninit queue until the next time it is necessary to run the 
>>>>> garbage collector. It is
>>>>>         highly unlikely that more than a few objects would be affected  
>>>>> by this, but you might
>>>>>         give it a try and see what happens. 
>>>>>         Rick
>>>>>          
>>>>>
>>>>>             ---rony
>>>>>
>>>>>             On 29.04.2017 21:32, Rick McGuire wrote:
>>>>>>             Running the garbage collector will not force the uninit 
>>>>>> methods to be run. When
>>>>>>             the garbage collector runs, any newly dead objects with 
>>>>>> uninit methods are marked
>>>>>>             as being ready to have the uninit method run. At some later 
>>>>>> time, when the
>>>>>>             interpreter is at a safe point, then the objects with 
>>>>>> pending uninit methods will
>>>>>>             be processed. These are major boundaries such as return from 
>>>>>> a method or call or
>>>>>>             thread termination. 
>>>>>>             Since you are creating class objects, things can get delayed 
>>>>>> even further since
>>>>>>             the class object will not become "dead" until all of its 
>>>>>> instances are first
>>>>>>             "dead". It then gets moved to the uninit queue for 
>>>>>> processing. 
>>>>>>             Rick
>>>>>>             On Sat, Apr 29, 2017 at 3:11 PM, Rony G. Flatscher 
>>>>>> <rony.flatsc...@wu.ac.at
>>>>>>             <mailto:rony.flatsc...@wu.ac.at>> wrote:
>>>>>>
>>>>>>                 Today, I have started to analyze the code-paths through 
>>>>>> BSF4ooRexx (Java,
>>>>>>                 c++, ooRexx-package BSF.CLS).
>>>>>>
>>>>>>                 As I have not found any "obvious" cause for the observed 
>>>>>> behaviour yet, I
>>>>>>                 have started to analyse the changes in the Java registry 
>>>>>> (that I have full
>>>>>>                 control of).
>>>>>>
>>>>>>                 Maybe first a sketch, how Java objects get proxied by 
>>>>>> ooRexx objects:
>>>>>>
>>>>>>                   * a Java object that is to be sent to ooRexx as a 
>>>>>> return or argument value
>>>>>>                     will get stored together with a reference counter in 
>>>>>> a Java registry
>>>>>>                     (using a ConcurrentHashMap), the index is a string 
>>>>>> which will get passed
>>>>>>                     on to Rexx instead of the Java object,
>>>>>>                   * the Rexx side will create an instance of the class 
>>>>>> .BSF (or a subclass of
>>>>>>                     it) supplying the Java object's index string which 
>>>>>> is used as the
>>>>>>                     objecname for the ooRexx peer object
>>>>>>                       o The BSF class has a destructor method (uninit) 
>>>>>> which will cause a
>>>>>>                         call to the Java side to reduce the Java 
>>>>>> object's reference counter;
>>>>>>                         if the Java reference counter drops to 0 the 
>>>>>> Java object will be
>>>>>>                         removed from the Java registry
>>>>>>
>>>>>>                 Running the SAX-example serving as the test case until 
>>>>>> 250 startElement
>>>>>>                 SAX-callbacks (each callback from Java to Rexx will 
>>>>>> cause an AttachThread(),
>>>>>>                 creating the ooRexx peer objects for the arguments, 
>>>>>> sending the Rexx message,
>>>>>>                 upon return doing a DetachThread()) have been carried 
>>>>>> out (in addition there
>>>>>>                 are plenty of other SAX-callbacks) and using debug 
>>>>>> statements for adding and
>>>>>>                 removing entries to/from the Java registry, this is what 
>>>>>> I can observe:
>>>>>>
>>>>>>                   * the ooRexx destructors run,
>>>>>>                   * *however* the rate of new ooRexx peer objects that 
>>>>>> get created (by Java
>>>>>>                     objects that are sent to Rexx) is much higher than 
>>>>>> the rate of ooRexx
>>>>>>                     peer objects that get garbage collected by ooRexx, 
>>>>>> which causes a
>>>>>>                     continuous increase in Rexx objects over time
>>>>>>                       o indeed, the ooRexx peer objects get destroyed 
>>>>>> eventually, causing the
>>>>>>                         Java refcounters to be decreased
>>>>>>                           + it seems that not all ooRexx peer objects 
>>>>>> that have turned into
>>>>>>                             garbage get destroyed in the garbage 
>>>>>> collection runs
>>>>>>                       o still (hence), the amount of ooRexx peer objects 
>>>>>> increases quickly at
>>>>>>                         runtime as the flux of callbacks from Java 
>>>>>> continues
>>>>>>                   * at the end of the program (in this case forcing an 
>>>>>> error to stop it by
>>>>>>                     issuing a 'say 1/0') all uninits run the reference 
>>>>>> counters on the Java
>>>>>>                     objects in the Java registry drop to 0!
>>>>>>
>>>>>>                 Is there a way in ooRexx to have the garbage collector 
>>>>>> be run (like in Java's
>>>>>>                 System.gc() or Runtime.getRuntime.gc())?
>>>>>>
>>>>>>                 Such a possibility might help to debug/tame this 
>>>>>> "run-away" scenario.
>>>>>>
>>>>>>                 ---rony
>>>>>>
>>>>>>                 On 27.04.2017 16:56, Rony G. Flatscher wrote:
>>>>>>>
>>>>>>>                 Thank you! Will report back, once I concluded the 
>>>>>>> analysis, which may take a
>>>>>>>                 while.
>>>>>>>
>>>>>>>                 ---rony
>>>>>>>
>>>>>>>                 On 27.04.2017 16:53, Rick McGuire wrote:
>>>>>>>>                 The memory manager will force any pending uninits to 
>>>>>>>> be run before it gives
>>>>>>>>                 up and issues the out of resources error messages. I 
>>>>>>>> really suspect
>>>>>>>>                 something in the way your code is creating the proxies 
>>>>>>>> and tracking them is
>>>>>>>>                 preventing the objects from being identified as dead 
>>>>>>>> objects, so these
>>>>>>>>                 objects will just keep accumulating. The more live 
>>>>>>>> objects locked in
>>>>>>>>                 memory, the longer a GC cycle will take because there 
>>>>>>>> is a larger live set
>>>>>>>>                 to mark. 
>>>>>>>>                 Rick
>>>>>>>>                 On Thu, Apr 27, 2017 at 10:34 AM, Rony G. Flatscher
>>>>>>>>                 <rony.flatsc...@wu.ac.at 
>>>>>>>> <mailto:rony.flatsc...@wu.ac.at>> wrote:
>>>>>>>>
>>>>>>>>                     Further information, using the initial e-mail to 
>>>>>>>> keep all relevant
>>>>>>>>                     information in one e-mail.
>>>>>>>>
>>>>>>>>                     Today I uninstalled the 32-bit ooRexx 5.0beta and 
>>>>>>>> installed the 64-bit
>>>>>>>>                     ooRexx 5.0beta (both from SourceForge, downloaded 
>>>>>>>> February 4th 2017).
>>>>>>>>
>>>>>>>>                     This time the program ran successfully to the end:
>>>>>>>>
>>>>>>>>                       * there were more than 247,000 XML elements 
>>>>>>>> processed
>>>>>>>>                           o as already mentioned this may translate 
>>>>>>>> into million(s) call
>>>>>>>>                             backs from Java to Rexx as all SAX events 
>>>>>>>> will cause callbacks
>>>>>>>>                             to Rexx
>>>>>>>>                               + some of these callbacks carry Java 
>>>>>>>> objects as arguments
>>>>>>>>                                 which will get wrapped as a peer 
>>>>>>>> ooRexx object (ultimately
>>>>>>>>                                 an instance of the class .BSF that has 
>>>>>>>> an uninit method
>>>>>>>>                                 defined), namely the Java types: 
>>>>>>>> "char[]", "Attributes",
>>>>>>>>                                 "Local" from the callbacks 
>>>>>>>>                                 
>>>>>>>> <https://docs.oracle.com/javase/7/docs/api/org/xml/sax/ContentHandler.html
>>>>>>>>                                 
>>>>>>>> <https://docs.oracle.com/javase/7/docs/api/org/xml/sax/ContentHandler.html>>
>>>>>>>>                               + there are no return values (all 
>>>>>>>> callbacks are defined to be
>>>>>>>>                                 void)
>>>>>>>>                       * it took a total of 2:37 hours to SAX-parse a 
>>>>>>>> 10MB XML file,
>>>>>>>>                           o the SAX-parsing was over after 1:45 hours
>>>>>>>>                               + the program constantly slowed down and 
>>>>>>>> in between paused
>>>>>>>>                                 for a while (which got longer and 
>>>>>>>> longer over time)
>>>>>>>>                           o after the SAX-parseing was over the Rexx 
>>>>>>>> program needed
>>>>>>>>                             another  0:52 hours to complete
>>>>>>>>                               + speculating/assuming that in this time 
>>>>>>>> all the uninits got
>>>>>>>>                                 executed (which is fine)
>>>>>>>>                       * it consumed 8.7GB of memory
>>>>>>>>                           o ProcessExplorer reports a
>>>>>>>>                               + Physical Memory "PeekWorking Set" of 
>>>>>>>> 8.795.796 K
>>>>>>>>                               + Virtual Memory "Virtual Size" of 
>>>>>>>> 13.404.424 K with "Peak
>>>>>>>>                                 Private Bytes" of 9.138.664 K
>>>>>>>>                       * it used 24% of the CPU over all 2:37 hours
>>>>>>>>                           o ProcessExplorer reports a
>>>>>>>>                               + "Kernel Time" of 0:01:10.184
>>>>>>>>                               + "User Time" of 2.32.57.960
>>>>>>>>                               + "Total Time" of  2:34:08.144
>>>>>>>>                               + "Cycles": 23.898.290.997.693
>>>>>>>>
>>>>>>>>                     Will check the BSF4ooRexx call and code paths. 
>>>>>>>> ---rony
>>>>>>>>
>>>>>>>>                     On 26.04.2017 20:28, Rony G. Flatscher wrote:
>>>>>>>>>
>>>>>>>>>                     A student is using BSF4ooRexx to parse a huge XML 
>>>>>>>>> file using Java's
>>>>>>>>>                     SAX parser.
>>>>>>>>>
>>>>>>>>>                     The SAX (simple API for XML) works with a 
>>>>>>>>> callback concept. In order
>>>>>>>>>                     to be eligible for these SAX callbacks the 
>>>>>>>>> ContentHandler interface
>>>>>>>>>                     
>>>>>>>>> <https://docs.oracle.com/javase/7/docs/api/org/xml/sax/ContentHandler.html>
>>>>>>>>>                     
>>>>>>>>> <https://docs.oracle.com/javase/7/docs/api/org/xml/sax/ContentHandler.html>
>>>>>>>>>                     must be implemented, which the Rexx program does 
>>>>>>>>> with the help of
>>>>>>>>>                     BSF4ooRexx.
>>>>>>>>>
>>>>>>>>>                     As a result each single SAX event will cause an 
>>>>>>>>> appropriate Rexx
>>>>>>>>>                     message to be generated and dispatched.  The Rexx 
>>>>>>>>> message is named
>>>>>>>>>                     after the ContentHandler method name and will 
>>>>>>>>> receive all arguments
>>>>>>>>>                     documented there. All arguments are processed in 
>>>>>>>>> native code, a Rexx
>>>>>>>>>                     array object will get created from the Java 
>>>>>>>>> arguments.
>>>>>>>>>
>>>>>>>>>                     This works and was presented on one of the 
>>>>>>>>> International Rexx
>>>>>>>>>                     symposiums and has become part of my lecture 
>>>>>>>>> using Java camouflaged as
>>>>>>>>>                     ooRexx with the help of BSF4ooRexx. Here is a 
>>>>>>>>> link to the symposium
>>>>>>>>>                     which contains links to the slides:
>>>>>>>>>                     <http://rexxla.org/events/2013/schedule.html>
>>>>>>>>>                     <http://rexxla.org/events/2013/schedule.html>.
>>>>>>>>>
>>>>>>>>>                     Now, a student is in the need to parse a rather 
>>>>>>>>> huge XML file (10 MB)
>>>>>>>>>                     and uses the SAX parser. She always hits the Rexx 
>>>>>>>>> "Error 5: System
>>>>>>>>>                     resources exhausted"! I asked her to come up with 
>>>>>>>>> a very small program
>>>>>>>>>                     to demonstrate the error and I am able to 
>>>>>>>>> reproduce it reliably! Here
>>>>>>>>>                     is the rather short Rexx program:
>>>>>>>>>                     --- #!/usr/bin/rexx parse arg xmlFile if 
>>>>>>>>> xmlFile="" then
>>>>>>>>>                     XMLFile="..\LB-HB.onlb" if 
>>>>>>>>> sysFileExists(xmlFile)=.false then do say
>>>>>>>>>                     "File" pp(xmlFile) "does not exist, aborting." 
>>>>>>>>> exit -1 end
>>>>>>>>>                     rexxObject=.saxHandler~new();
>>>>>>>>>                     
>>>>>>>>> javaProxy=BSFCreateRexxProxy(rexxObject,,"org.xml.sax.ContentHandler")
>>>>>>>>>                     
>>>>>>>>> parser=bsf.loadClass("org.xml.sax.helpers.XMLReaderFactory")~createXMLReader
>>>>>>>>>                     parser~setContentHandler(javaProxy) 
>>>>>>>>> eh=.errorHandler~new
>>>>>>>>>                     
>>>>>>>>> javaEH=BsfCreateRexxProxy(eh,,"org.xml.sax.ErrorHandler")
>>>>>>>>>                     parser~setErrorHandler(javaEH) signal on syntax 
>>>>>>>>> start=.dateTime~new
>>>>>>>>>                     say pp(start)": start of parsing" 
>>>>>>>>> parser~parse(XMLFile)
>>>>>>>>>                     end=.dateTime~new say pp(end)": end of parsing" 
>>>>>>>>> say "done, needed:"
>>>>>>>>>                     pp(end-start) exit syntax: say "error at" 
>>>>>>>>> rexxObject~nrOfElements
>>>>>>>>>                     "element" co=condition('o') say ppCondition2(co) 
>>>>>>>>> ::requires "BSF.CLS"
>>>>>>>>>                     /* get the Java support */ ::requires 
>>>>>>>>> "rgf_util2.rex" ::CLASS
>>>>>>>>>                     "SaxHandler" -- a Rexx content handler 
>>>>>>>>> ("org.xml.sax.ContentHandler")
>>>>>>>>>                     ::attribute nrOfElements ::METHOD init --ooRexx 
>>>>>>>>> constructor expose
>>>>>>>>>                     nrOfElements nrOfElements=0 ::METHOD startElement 
>>>>>>>>> expose nrOfElements
>>>>>>>>>                     USE ARG uri, localName, qName, attributes 
>>>>>>>>> nrOfElements+=1 if
>>>>>>>>>                     nrOfElements//1000=0 then say nrOfElements 
>>>>>>>>> "elements so far ..."
>>>>>>>>>                     ::METHOD characters -- the callback method for 
>>>>>>>>> characters (text) USE
>>>>>>>>>                     ARG charArray, start, length ::METHOD endElement 
>>>>>>>>> USE ARG uri,
>>>>>>>>>                     localName, qName, attributes ::method unknown 
>>>>>>>>> ::class ErrorHandler
>>>>>>>>>                     ::method unknown use arg methName, argArray 
>>>>>>>>> exception=argArray[1]s
>>>>>>>>>                     .error~say(methName": " 
>>>>>>>>> "line="exception~getLineNumber
>>>>>>>>>                     ",col="exception~getColumnNumber": " 
>>>>>>>>> pp(exception~getMessage)) ---
>>>>>>>>>                     As you might see, there is nothing "special" 
>>>>>>>>> going on here, other than
>>>>>>>>>                     being able to supply a Rexx object as the 
>>>>>>>>> callback object for the Java
>>>>>>>>>                     implemented SAX parser! It seems that running all 
>>>>>>>>> these callback from
>>>>>>>>>                     Java to Rexx will cause eventually that ooRexx 
>>>>>>>>> gets exhausted of
>>>>>>>>>                     system resources. While running the program it 
>>>>>>>>> can be observed that
>>>>>>>>>                     from time to time there are little lags as if 
>>>>>>>>> some garbage collecting
>>>>>>>>>                     takes place. Eventually the error 5 is thrown, 
>>>>>>>>> while executing in
>>>>>>>>>                     native code:
>>>>>>>>>
>>>>>>>>>                         result_obj=rtc->SendMessage(ro, c_msg, ra); 
>>>>>>>>> // with arguments
>>>>>>>>>
>>>>>>>>>                     Please note that the following error message only 
>>>>>>>>> gives the numbers of
>>>>>>>>>                     XML elements that the SAX parser reported. In 
>>>>>>>>> reality, *all* callbacks
>>>>>>>>>                     are carried out from Java to Rexx, the 
>>>>>>>>> unprocessed ones will be
>>>>>>>>>                     intercepted by the Rexx UNKNOWN method. So there 
>>>>>>>>> is a flurry of
>>>>>>>>>                     context switches and creation of Rexx array 
>>>>>>>>> objects for the arguments
>>>>>>>>>                     and the like. Here is the error message on my 
>>>>>>>>> system.
>>>>>>>>>                     --- 83000 elements so far ... 84000 elements so 
>>>>>>>>> far ... error at 84926
>>>>>>>>>                     element [ADDITIONAL] =[an Array (2 items) 
>>>>>>>>> id#_-1457160369]
>>>>>>>>>                     ["BSF4ooRexx/routine/BSF(), error 3: Java 
>>>>>>>>> exception occurred:
>>>>>>>>>                     [org.rexxla.bsf.engines.rexx.RexxException:
>>>>>>>>>                     
>>>>>>>>> BSF4ooRexx/routine/jniRexxSendMessageToRexxObject(), error 4:" ||
>>>>>>>>>                     "0A"x || " *-* Compiled method ""OBJECTNAME="" 
>>>>>>>>> with scope ""Object""."
>>>>>>>>>                     || "0A"x || "Error 5 running C:\Program Files 
>>>>>>>>> (x86)\BSF4ooRexx\BSF.CLS
>>>>>>>>>                     line 2644: System resources exhausted." || "0A"x 
>>>>>>>>> || "Error 5.0:
>>>>>>>>>                     message n/a]"] 
>>>>>>>>> [org.rexxla.bsf.engines.rexx.RexxException@182d820
>>>>>>>>>                     id#_-1478994985] [CODE] =[40.900] [CONDITION] 
>>>>>>>>> =[SYNTAX]
>>>>>>>>>                     [DESCRIPTION]=[] [ERRORTEXT] =[Incorrect call to 
>>>>>>>>> routine.]
>>>>>>>>>                     [INSTRUCTION]=[SIGNAL] [MESSAGE] 
>>>>>>>>> =["BSF4ooRexx/routine/BSF(), error 3:
>>>>>>>>>                     Java exception occurred: 
>>>>>>>>> [org.rexxla.bsf.engines.rexx.RexxException:
>>>>>>>>>                     
>>>>>>>>> BSF4ooRexx/routine/jniRexxSendMessageToRexxObject(), error 4:" ||
>>>>>>>>>                     "0A"x || " *-* Compiled method ""OBJECTNAME="" 
>>>>>>>>> with scope ""Object""."
>>>>>>>>>                     || "0A"x || "Error 5 running C:\Program Files 
>>>>>>>>> (x86)\BSF4ooRexx\BSF.CLS
>>>>>>>>>                     line 2644: System resources exhausted." || "0A"x 
>>>>>>>>> || "Error 5.0:
>>>>>>>>>                     message n/a]."] [PACKAGE] =[a Package 
>>>>>>>>> id#_-2109388833] [POSITION]
>>>>>>>>>                     =[25] [PROGRAM] 
>>>>>>>>> =[F:\tmp\orx\kirisits\20170425\SAX_noAlerts.rxj]
>>>>>>>>>                     [PROPAGATED] =[1] [RC] =[40] [STACKFRAMES]=[a 
>>>>>>>>> List (4 items)
>>>>>>>>>                     id#_-1467321073] [ *-* Compiled routine "BSF". 
>>>>>>>>> id#_-1939043649] [ 1811
>>>>>>>>>                     *-* res=BSF( "invoke", 
>>>>>>>>> "com.sun.org.apache.xerces.int
>>>>>>>>>                     
>>>>>>>>> <http://com.sun.org.apache.xerces.int>ernal.parsers.SAXParser@117ae12",
>>>>>>>>>                     "PARSE" , a.1 ) id#_-1938526417] [ 1813 *-* 
>>>>>>>>> interpret code ")" --
>>>>>>>>>                     execute this dynamically created Rexx string 
>>>>>>>>> id#_-1937397361] [ 25 *-*
>>>>>>>>>                     parser~parse(XMLFile) id#_-1936143753] 
>>>>>>>>> [TRACEBACK] =[a List (4 items)
>>>>>>>>>                     id#_-1458379065] [ *-* Compiled routine "BSF".] [ 
>>>>>>>>> 1811 *-* res=BSF(
>>>>>>>>>                     "invoke", "com.sun.org.apache.xerces.int
>>>>>>>>>                     
>>>>>>>>> <http://com.sun.org.apache.xerces.int>ernal.parsers.SAXParser@117ae12",
>>>>>>>>>                     "PARSE" , a.1 )] [ 1813 *-* interpret code ")" -- 
>>>>>>>>> execute this
>>>>>>>>>                     dynamically created Rexx string] [ 25 *-* 
>>>>>>>>> parser~parse(XMLFile)] ---
>>>>>>>>>                     The traceback points to the invocation of the SAX 
>>>>>>>>> parser from Rexx
>>>>>>>>>                     which only returns upon completion of the Java 
>>>>>>>>> parse method, or in
>>>>>>>>>                     this case when an error interrupts the program. 
>>>>>>>>> --- So now my
>>>>>>>>>                     question/request: how to debug this 
>>>>>>>>> problem/error? How can I get more
>>>>>>>>>                     information from the ooRexx interpreter? How can 
>>>>>>>>> one determine what
>>>>>>>>>                     kind of "system resources" got exhausted and what 
>>>>>>>>> the cause would be?
>>>>>>>>>                     Can one e.g. determine how many Rexx objects 
>>>>>>>>> there are and how many
>>>>>>>>>                     are dead, in the need of getting garbage 
>>>>>>>>> collected? In this case
>>>>>>>>>                     whenever (on each SAX callback) the Java side 
>>>>>>>>> invokes the native code
>>>>>>>>>                     which then sends the message to the Rexx object 
>>>>>>>>> there will be an
>>>>>>>>>                     AttachThread() followed by a DetachThread(). 
>>>>>>>>> Please advise! ---rony 
#!/usr/bin/rexx

parse arg xmlFile
if xmlFile="" then 
   XMLFile="..\LB-HB.onlb"

if sysFileExists(xmlFile)=.false then
do
   say "File" pp(xmlFile) "does not exist, aborting."
   exit -1
end

rexxObject=.saxHandler~new();

javaProxy=BSFCreateRexxProxy(rexxObject,,"org.xml.sax.ContentHandler")
parser=bsf.loadClass("org.xml.sax.helpers.XMLReaderFactory")~createXMLReader
parser~setContentHandler(javaProxy)
eh=.errorHandler~new
javaEH=BsfCreateRexxProxy(eh,,"org.xml.sax.ErrorHandler")
parser~setErrorHandler(javaEH)

signal on syntax
start=.dateTime~new
say pp(start)": start of parsing"
parser~parse(XMLFile)
end=.dateTime~new
say pp(end)": end of parsing"
say "done, needed:" pp(end-start)
exit

syntax:
  say "error at" rexxObject~nrOfElements "element"
  co=condition('o')
  say ppCondition2(co)

::requires "BSF.CLS"    /* get the Java support    */
::requires "rgf_util2.rex"


::CLASS "SaxHandler" -- a Rexx content handler ("org.xml.sax.ContentHandler")

::attribute nrOfElements

::METHOD init --ooRexx constructor
  expose nrOfElements
  nrOfElements=0

::METHOD startElement
  expose nrOfElements
  USE ARG uri, localName, qName, attributes
  nrOfElements+=1
  if nrOfElements//1000=0 then say nrOfElements "elements so far ..."
/*
  if nrOfElements>250 then
  do
     say self": nrOfElements="nrOfElements", aborting by doing a 1/0..."
     say "1/0:" 1/0
  end
*/


::METHOD characters -- the callback method for characters (text)
  USE ARG charArray, start, length


::METHOD endElement
  USE ARG uri, localName, qName, attributes


::method unknown



::class ErrorHandler
	::method unknown
	use arg methName, argArray
		 exception=argArray[1]s
		 .error~say(methName": " "line="exception~getLineNumber ",col="exception~getColumnNumber": " pp(exception~getMessage))

------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
_______________________________________________
Oorexx-devel mailing list
Oorexx-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/oorexx-devel

Reply via email to