SIGSEGV during Exception handling in Solaris 10/Sunstudio 11
Hi all,
In our application we are encountering random crashes in our ACE/TAO framework code. The crash happens mostly when we convert our local data type to a CORBA datatype.
There is some exception handling in this area and crashes seem to happen randomly.
The stack always has a call to impl::ex_free and I saw other forums reportign this problem much earlier.
We are using a machine which has a pretty old patch for compilation. Acutally it was a Beta patch delivered for allowing clearcase installation.
The machine details are:
SunOS amsbuild8-1 5.10 ws.10.6198523 sun4u sparc SUNW,Sun-Fire-V440
The machine on which our appln runs has the details as:
SunOS sol-890perf1 5.10 Generic_127127-11 sun4u sparc SUNW,Sun-Fire-V890
What I would like to know is, has there been any known issue on Sunstudio11 related to Exception Handling in C++ and if there are any patches which came with the fix.
I know I could use the latest patches and test to see if it occurs, but it would be nice if we know our issue is the same, as we have little test time on our hands.
The stack looks like this:
f7d60a4c free (64646f36, 7a123, 136fc, 7a11b, 7a0fb, f7d74228) + 158
edb3802c __1cJ_ODI_free6Fpc_v_ (7a123, 3cc0, 21b190, eda8ca0c, edd53128, 3c00) + a0
eda8cb80 __1c2K6Fpv_v_ (7a123, 0, 0, 0, 0, 0) + 4
ed717828 __1cFCORBALstring_free6Fpc_v_ (7a123, 0, 0, 0, 0, 0) + 4
feb711a4 __1cDTAOHdetailsSstring_traits_base4Cc_Hrelease6Fpc_v_ (7a123, f7d7424c, f7d74248, 1b,
cd2f30, baddc800) + c
feb6f9f8 __1cDTAOKString_var4Cc_2T5B6M_v_ (2aef0c, ec6cdbe0, 1, 150ceb0, ff00, e9940) + 10
ed6b02d4 __1cFCORBAJException2T5B6M_v_ (2aef08, 300030, ed7a9fa8, ed799be8, 3a0, 0) + 30
ed73cb5c __1cFCORBANUserException2T5B6M_v_ (2aef08, feadff43, ed7b8c38, ed799be8, 250, 0) + 28
ec69e4a8 __1cFCORBAITypeCodeHBadKind2T6M_v_ (2aef08, 1, 2aeec0, ec69e4a4, 1, eb8fbbbc) + 4
*00235c0c __1cH__CimplHex_free6F_v_* (2b2f04, 1, 2aeec0, 298968, 62dc4, 2ff2648) + 6c
ec69d5b8 __1cFCORBAITypeCodeKequivalent6kMp1_b_ (1, ec6e2794, ec1f3700, feaf319c, 2ff2a00, eb8f
bc8c) + 218
fead7e60 __1cDTAOPAny_Dual_Impl_T4nGEvtSvcMIdlEventList__Hextract6FrknFCORBADAny_pFpv_vpn0EITyp
eCode_rpkn0C__b_ (cd2fd8, feac9710, feaf319c, eb8fbe9c, edd53128, 3c00) + 60
feacb1c4 __1c2R6FrknFCORBADAny_rpknGEvtSvcMIdlEventList__b_ (cd2fd8, eb8fbe9c, 5b524, feb6a7f4,
f1795e78, 1e39bb4) + 54
feb93a58 __1cSEvtEventDispatcherKpullEvents6Fkpkc_v_ (febc4b04, feb937c0, effecb34, effdde64, 3
78, 0) + 298
eff49698 __1cVACE_OS_Thread_AdapterGinvoke6M_pv_ (ac88d8, effee0c0, feb937c0, febc4b04, efdc0a0
0, 1) + 5c
eff06b58 ace_thread_adapter (ac88d8, eb8fc000, 0, 0, eff4963c, effee0c0) + c
Thanks in Advance,
Chenthil
There have been some exception-handling bugs fixed, most of which are in the C++ runtime library.
Be sure you have the latest runtime library patch. For Solaris 10 on sparc, that would be 119963-10.
To find out whether you have this patch, run the command
showrev -p | grep 119963and see if you have the -10 update.
I recommend upgrading to Sun Studio 12, since you are on Solaris 10. It has bug fixes and improvements not available in Studio 11. You should be able to drop in the new compiler and continue development. You don't have to rebuild all your binaries, but everyone must upgrade to the new compiler. You can download Studio 12 here:
[http://developers.sun.com/sunstudio/]
Whether you upgrade to Sun Studio 12 or stay with Studio 11, get the current patches here:
[http://developers.sun.com/sunstudio/downloads/patches/index.jsp]
(You can find the C++ runtime library patches here too.)
Finally, just because the runtime library is in the stack trace doesn't mean you have run into a bug in the library. The bug could be in your own code. For example, if you throw a deleted object, the segfault will probably occur in the runtime library when it tries to access the invalid object.
Running under dbx with RTC (run-time checking) enabled will help to find the source of the problem, especially if it is in your code. In dbx, try "help rtc" for more information, or refer to the dbx manual.
Here is a quick start guide:
% dbx myprog
(dbx) check -all
(dbx) run
Similar Messages
-
SIGSEGV in exception destruction (new)
I have an application that runs in: SunOS goldeni 5.8 Generic_117350-28 sun4u sparc SUNW,Netra-T12
The application crashed during the destruction of exception object. Following is the stack trace.
RWThreadImp_entry(0x3bbbda0, 0xf830dd38, 0x0, 0x5, 0x1, 0xfe401000)
RWThreadImp::exec(0x3bbbda0, 0x0, 0x0, 0x0, 0x0, 0x0)
RWRunnableImp::exec(0x3bbbda0, 0xf7101c50, 0xf7101c50, 0xf7101c4c, 0x1,
0x3bbbe78)
RWThreadFunctionImp::run(0x3bbbda0, 0x0, 0x1093888, 0x2e, 0x1, 0x0)
RWFunctor0::operator()(0xf7101bac, 0x3bbbea8, 0x0, 0x0, 0x0, 0x0)
RWTFunctor0MA1Imp::run(0x3bbbd50, 0x3bbbd50, 0x3bbbdb0, 0x0, 0x0, 0x0)
Task::taskThread(0x3bb51d8, 0x3bb51d8, 0xf7101a00, 0x1, 0x1, 0x0)
rv_MainLoop(0x3bb5da8, 0x1, 0x3bbbdb0, 0x3bbbe80, 0xff26a538, 0x8)
_rvevm_MainLoop(0x3bb5960, 0x3bb5680, 0xf7101a90, 0x1, 0x2e, 0x0)
dispatchEvents(0x45766e74, 0x3bb5e00, 0x0, 0x0, 0x3bb5da8, 0x3bb2b38)
drainQueue(0x3bb1c90, 0x0, 0x1, 0xe70, 0x3befcf8, 0xf7100ce0)
DaemonReceiveCallback(0x3befcf8, 0x3bb1c90, 0x3bb5da8, 0x9955eeaa, 0x1,
0x8)
_rv_ProcessMessageFromDaemon(0x0, 0x0, 0x3bb1c90, 0x1ca1bbe8, 0x0,
0x3bb1c90)
Distribute(0x0, 0x3bb5e3c, 0x0, 0x1, 0x1, 0x3bb5da8)
listenerCB(0x132c5db8, 0x3bb77f0, 0x132c5db8, 0x11be9528, 0xf710158c,
0x1ca1bc2e)
SubscriptionManager::onData(this = 0x3bb77f0, pRvSubject = 0xf710158c
"RDF.REC.PINOX.NaE", replySender = (nil), data = CLASS, invoker =
0x11be9528)
QuoteListenerImpl::onData(this = 0x11bea190, pRvSubject = 0xf710158c
"RDF.REC.PINOX.NaE", _ARG3 = (nil), data = CLASS, _ARG5 = 0x11be9528)
__Cimpl::ex_free(0xff26ef2c, 0x1, 0xff26e808, 0x4572726f, 0xff26a538,
0xff26e808)I have seen a topic with a similar issue in the following link. http://forum.sun.com/jive/thread.jspa?threadID=71170&start=0
The only difference is that my exception object doesn't have a deque, instead it has just a char* to store the error.
I'm unable to reproduce the crash with my application and also with the modified version (replaced deque with char*) of the program found in the above link.
Following are my system information:
%uname -a
SunOS fpsadpuat001 5.8 Generic_117350-28 sun4u sparc SUNW,Netra-T12
%showrev -p | grep -i sunwlibc
Patch: 108434-12 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-13 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-17 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-18 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-20 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108435-12 Obsoletes: Requires: 108434-12 Incompatibles: Packages: SUNWlibCx
Patch: 108435-13 Obsoletes: Requires: 108434-13 Incompatibles: Packages: SUNWlibCx
Patch: 108435-17 Obsoletes: Requires: 108434-17 Incompatibles: Packages: SUNWlibCx
Patch: 108435-18 Obsoletes: Requires: 108434-17 Incompatibles: Packages: SUNWlibCx
Patch: 108435-20 Obsoletes: Requires: 108434-20 Incompatibles: Packages: SUNWlibCx
From the above results, the version of SUNWlibC is 108434-20 and the version of SUNWlibCx is 108435-20.
I believe that as per the following link, the bug 6339010 is fixed in 108434-21.
http://sunsolve.sun.com/search/advsearch.do?collection=PATCH&type=collections&max=50&language=en&toDocument=yes&queryKey5=108434
Eventhough I don't have a deque in my exception object, is it safe to assume that the changes in 108434-21 will fix my problem ?
Since I'm unable to reproduce the crash using 108434-20, I won't be able to test the fix using 108434-21. But, have to just wait and see if this problem goes away.
Thanks for any help in advance.I am also experiencing a SIGSEGV issue which appears to be related to the other C++ exception handling issues described here. My version details are as follows:
uname -a
SunOS machineXYZ 5.8 Generic_117350-36 sun4u sparc SUNW,Ultra-80
CC -V
CC: Sun WorkShop 6 update 2 C++ 5.3 Patch 111685-24 2006/11/03
showrev -p | grep -i sunwlibc
Patch: 108434-08 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-17 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-18 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-20 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108434-21 Obsoletes: Requires: 109147-07 Incompatibles: Packages: SUNWlibC
Patch: 108435-08 Obsoletes: Requires: 108434-08 Incompatibles: Packages: SUNWlibCx
Patch: 108435-17 Obsoletes: Requires: 108434-17 Incompatibles: Packages: SUNWlibCx
Patch: 108435-18 Obsoletes: Requires: 108434-17 Incompatibles: Packages: SUNWlibCx
Patch: 108435-20 Obsoletes: Requires: 108434-20 Incompatibles: Packages: SUNWlibCx
Patch: 108435-21 Obsoletes: Requires: 108434-21 Incompatibles: Packages: SUNWlibCx
The exception class in question contains two "char *" members and subclasses another exception class that contains a "char*" and an integer code. The exception is part of a third party library whose code is not available to the debugger when analysing the core file.
The stacktrace details are:
[1] 0xfece4648(0xff24b0d0, 0x0, 0x1, 0xff24b080, 0xfece4648, 0x1), at 0xfece4647
[2] __Cimpl::ex_free(0xff24f0ec, 0xff24b080, 0xff24b080, 0x0, 0xb546bc, 0xff24a780), at 0xff2343a4
=>[3] WebAdapterRequestThread::threadFunc(this = 0xd5a720), line 273 in "WebAdapterRequestThread.cpp"
[4] WebAdapterRequestThread::staticThreadFunc(inst = 0xd5a720), line 31 in "WebAdapterRequestThread.cpp"
[5] handlerThread(inst = 0xd5a720), line 24 in "WebAdapterRequestThread.cpp"
I believe that the SEGV is related to the cleanup of the exception object invoked via __Cimpl::ex_free.
I notice that my system is at patch version 108434-21and the latest version is 108434-22. Perhaps that version may resolve my issue although the fix descriptions between 21 and 22 don't seem exactly relevant:
6319635 void stream_rmutex::rmutex_init() should call pthread_mutexattr_destroy()
6393170 Purify reporting "array bound writes" on deque template in libCstd
6406049 libCstd: acquiring a mutex on a deleted locale object causes core dump
6421790 Throwing an exception causing SIGABRT on Solaris 8 with patch 108434-20/108435-20
Is it possible that my issue is related to but slightly different to the issues that have already been discussed / resolved? I have not yet been able to reproduce the issue in a small sample piece of code. However, I think the following quote (from http://forum.java.sun.com/thread.jspa?threadID=5098599) is significant:
"f the crash occurs in __1cH__CimplHex_free6F_v_ == void __Cimpl::ex_free() it is probably a bug in the C++ exception handling. At least two bugs are already fixed in C++ runtime library patches (Solaris SUNWlibC patch)."
Please recommend OS / compiler patches that should be applied. -
PL/SQL 101 : Exception Handling
Frequently I see questions and issues around the use of Exception/Error Handling in PL/SQL. More often than not the issue comes from the questioners misunderstanding about how PL/SQL is constructed and executed, so I thought I'd write a small article covering the key concepts to give a clear picture of how it all hangs together. (Note: the examples are just showing examples of the exception handling structure, and should not be taken as truly valid code for ways of handling things)
Exception Handling
Contents
1. Understanding Execution Blocks (part 1)
2. Execution of the Execution Block
3. Exceptions
4. Understanding Execution Blocks (part 2)
5. How to continue exection of statements after an exception
6. User defined exceptions
7. Line number of exception
8. Exceptions within code within the exception block
1. Understanding Execution Blocks (part 1)
The first thing that one needs to understand is almost taking us back to the basics of PL/SQL... how a PL/SQL execution block is constructed.
Essentially an execution block is made of 3 sections...
+---------------------------+
| Declaration Section |
+---------------------------+
| Statements Section |
+---------------------------+
| Exception Section |
+---------------------------+
The Declaration section is the part defined between the PROCEDURE/FUNCTION header or the DECLARE keyword (for anonymous blocks) and the BEGIN keyword. (Optional section)
The Statements section is where your code goes and lies between the BEGIN keyword and the EXCEPTION keyword (or END keyword if there is no EXCEPTION section). (Mandatory section)
The Exception section is where any exception handling goes and lies between the EXCEPTION keyword at the END keyword. (Optional section)
Example of an anonymous block...
DECLARE
.. declarative statements go here ..
BEGIN
.. code statements go here ..
EXCEPTION
.. exception handlers go here ..
END;
Example of a procedure/function block...
[CREATE OR REPLACE] (PROCEDURE|FUNCTION) <proc or fn name> [(<parameters>)] [RETURN <datatype>] (IS|AS)
.. declarative statements go here ..
BEGIN
.. code statements go here ..
EXCEPTION
.. exception handlers go here ..
END;
(Note: The same can also be done for packages, but let's keep it simple)
2. Execution of the Execution Block
This may seem a simple concept, but it's surprising how many people have issues showing they haven't grasped it. When an Execution block is entered, the declaration section is processed, creating a scope of variables, types , cursors, etc. to be visible to the execution block and then execution enters into the Statements section. Each statment in the statements section is executed in turn and when the execution completes the last statment the execution block is exited back to whatever called it.
3. Exceptions
Exceptions generally happen during the execution of statements in the Statements section. When an exception happens the execution of statements jumps immediately into the exception section. In this section we can specify what exceptions we wish to 'capture' or 'trap' and do one of the two following things...
(Note: The exception section still has access to all the declared items in the declaration section)
3.i) Handle the exception
We do this when we recognise what the exception is (most likely it's something we expect to happen) and we have a means of dealing with it so that our application can continue on.
Example...
(without the exception handler the exception is passed back to the calling code, in this case SQL*Plus)
SQL> ed
Wrote file afiedt.buf
1 declare
2 v_name VARCHAR2(20);
3 begin
4 select ename
5 into v_name
6 from emp
7 where empno = &empno;
8 dbms_output.put_line(v_name);
9* end;
SQL> /
Enter value for empno: 123
old 7: where empno = &empno;
new 7: where empno = 123;
declare
ERROR at line 1:
ORA-01403: no data found
ORA-06512: at line 4
(with an exception handler, we capture the exception, handle it how we want to, and the calling code is happy that there is no error for it to report)
SQL> ed
Wrote file afiedt.buf
1 declare
2 v_name VARCHAR2(20);
3 begin
4 select ename
5 into v_name
6 from emp
7 where empno = &empno;
8 dbms_output.put_line(v_name);
9 exception
10 when no_data_found then
11 dbms_output.put_line('There is no employee with this employee number.');
12* end;
SQL> /
Enter value for empno: 123
old 7: where empno = &empno;
new 7: where empno = 123;
There is no employee with this employee number.
PL/SQL procedure successfully completed.
3.ii) Raise the exception
We do this when:-
a) we recognise the exception, handle it but still want to let the calling code know that it happened
b) we recognise the exception, wish to log it happened and then let the calling code deal with it
c) we don't recognise the exception and we want the calling code to deal with it
Example of b)
SQL> ed
Wrote file afiedt.buf
1 declare
2 v_name VARCHAR2(20);
3 v_empno NUMBER := &empno;
4 begin
5 select ename
6 into v_name
7 from emp
8 where empno = v_empno;
9 dbms_output.put_line(v_name);
10 EXCEPTION
11 WHEN no_data_found THEN
12 INSERT INTO sql_errors (txt)
13 VALUES ('Search for '||v_empno||' failed.');
14 COMMIT;
15 RAISE;
16* end;
SQL> /
Enter value for empno: 123
old 3: v_empno NUMBER := &empno;
new 3: v_empno NUMBER := 123;
declare
ERROR at line 1:
ORA-01403: no data found
ORA-06512: at line 15
SQL> select * from sql_errors;
TXT
Search for 123 failed.
SQL>
Example of c)
SQL> ed
Wrote file afiedt.buf
1 declare
2 v_name VARCHAR2(20);
3 v_empno NUMBER := &empno;
4 begin
5 select ename
6 into v_name
7 from emp
8 where empno = v_empno;
9 dbms_output.put_line(v_name);
10 EXCEPTION
11 WHEN no_data_found THEN
12 INSERT INTO sql_errors (txt)
13 VALUES ('Search for '||v_empno||' failed.');
14 COMMIT;
15 RAISE;
16 WHEN others THEN
17 RAISE;
18* end;
SQL> /
Enter value for empno: 'ABC'
old 3: v_empno NUMBER := &empno;
new 3: v_empno NUMBER := 'ABC';
declare
ERROR at line 1:
ORA-06502: PL/SQL: numeric or value error: character to number conversion error
ORA-06512: at line 3
SQL> select * from sql_errors;
TXT
Search for 123 failed.
SQL>
As you can see from the sql_errors log table, no log was written so the WHEN others exception was the exception that raised the error to the calling code (SQL*Plus)
4. Understanding Execution Blocks (part 2)
Ok, so now we understand the very basics of an execution block and what happens when an exception happens. Let's take it a step further...
Execution blocks are not just a single simple block in most cases. Often, during our statements section we have a need to call some reusable code and we do that by calling a procedure or function. Effectively this nests the procedure or function's code as another execution block within the current statement section so, in terms of execution, we end up with something like...
+---------------------------------+
| Declaration Section |
+---------------------------------+
| Statements Section |
| . |
| +---------------------------+ |
| | Declaration Section | |
| +---------------------------+ |
| | Statements Section | |
| +---------------------------+ |
| | Exception Section | |
| +---------------------------+ |
| . |
+---------------------------------+
| Exception Section |
+---------------------------------+
Example... (Note: log_trace just writes some text to a table for tracing)
SQL> create or replace procedure a as
2 v_dummy NUMBER := log_trace('Procedure A''s Declaration Section');
3 begin
4 v_dummy := log_trace('Procedure A''s Statement Section');
5 v_dummy := 1/0; -- cause an exception
6 exception
7 when others then
8 v_dummy := log_trace('Procedure A''s Exception Section');
9 raise;
10 end;
11 /
Procedure created.
SQL> create or replace procedure b as
2 v_dummy NUMBER := log_trace('Procedure B''s Declaration Section');
3 begin
4 v_dummy := log_trace('Procedure B''s Statement Section');
5 a; -- HERE the execution passes to the declare/statement/exception sections of A
6 exception
7 when others then
8 v_dummy := log_trace('Procedure B''s Exception Section');
9 raise;
10 end;
11 /
Procedure created.
SQL> exec b;
BEGIN b; END;
ERROR at line 1:
ORA-01476: divisor is equal to zero
ORA-06512: at "SCOTT.B", line 9
ORA-06512: at line 1
SQL> select * from code_trace;
TXT
Procedure B's Declaration Section
Procedure B's Statement Section
Procedure A's Declaration Section
Procedure A's Statement Section
Procedure A's Exception Section
Procedure B's Exception Section
6 rows selected.
SQL>
Likewise, execution blocks can be nested deeper and deeper.
5. How to continue exection of statements after an exception
One of the common questions asked is how to return execution to the statement after the one that created the exception and continue on.
Well, firstly, you can only do this for statements you expect to raise an exception, such as when you want to check if there is no data found in a query.
If you consider what's been shown above you could put any statement you expect to cause an exception inside it's own procedure or function with it's own exception section to handle the exception without raising it back to the calling code. However, the nature of procedures and functions is really to provide a means of re-using code, so if it's a statement you only use once it seems a little silly to go creating individual procedures for these.
Instead, you nest execution blocks directly, to give the same result as shown in the diagram at the start of part 4 of this article.
SQL> ed
Wrote file afiedt.buf
1 create or replace procedure b (p_empno IN VARCHAR2) as
2 v_dummy NUMBER := log_trace('Procedure B''s Declaration Section');
3 begin
4 v_dummy := log_trace('Procedure B''s Statement Section');
5 -- Here we start another execution block nested in the first one...
6 declare
7 v_dummy NUMBER := log_trace('Nested Block Declaration Section');
8 begin
9 v_dummy := log_trace('Nested Block Statement Section');
10 select empno
11 into v_dummy
12 from emp
13 where empno = p_empno; -- Note: the parameters and variables from
parent execution block are available to use!
14 exception
15 when no_data_found then
16 -- This is an exception we can handle so we don't raise it
17 v_dummy := log_trace('No employee was found');
18 v_dummy := log_trace('Nested Block Exception Section - Exception Handled');
19 when others then
20 -- Other exceptions we can't handle so we raise them
21 v_dummy := log_trace('Nested Block Exception Section - Exception Raised');
22 raise;
23 end;
24 -- ...Here endeth the nested execution block
25 -- As the nested block handled it's exception we come back to here...
26 v_dummy := log_trace('Procedure B''s Statement Section Continued');
27 exception
28 when others then
29 -- We'll only get to here if an unhandled exception was raised
30 -- either in the nested block or in procedure b's statement section
31 v_dummy := log_trace('Procedure B''s Exception Section');
32 raise;
33* end;
SQL> /
Procedure created.
SQL> exec b(123);
PL/SQL procedure successfully completed.
SQL> select * from code_trace;
TXT
Procedure B's Declaration Section
Procedure B's Statement Section
Nested Block Declaration Section
Nested Block Statement Section
No employee was found
Nested Block Exception Section - Exception Handled
Procedure B's Statement Section Continued
7 rows selected.
SQL> truncate table code_trace;
Table truncated.
SQL> exec b('ABC');
BEGIN b('ABC'); END;
ERROR at line 1:
ORA-01722: invalid number
ORA-06512: at "SCOTT.B", line 32
ORA-06512: at line 1
SQL> select * from code_trace;
TXT
Procedure B's Declaration Section
Procedure B's Statement Section
Nested Block Declaration Section
Nested Block Statement Section
Nested Block Exception Section - Exception Raised
Procedure B's Exception Section
6 rows selected.
SQL>
You can see from this that, very simply, the code that we expected may have an exception was able to either handle the exception and return to the outer execution block to continue execution, or if an unexpected exception occurred then it was able to be raised up to the outer exception section.
6. User defined exceptions
There are three sorts of 'User Defined' exceptions. There are logical situations (e.g. business logic) where, for example, certain criteria are not met to complete a task, and there are existing Oracle errors that you wish to give a name to in order to capture them in the exception section. The third is raising your own exception messages with our own exception numbers. Let's look at the first one...
Let's say I have tables which detail stock availablility and reorder levels...
SQL> select * from reorder_level;
ITEM_ID STOCK_LEVEL
1 20
2 20
3 10
4 2
5 2
SQL> select * from stock;
ITEM_ID ITEM_DESC STOCK_LEVEL
1 Pencils 10
2 Pens 2
3 Notepads 25
4 Stapler 5
5 Hole Punch 3
SQL>
Now, our Business has told the administrative clerk to check stock levels and re-order anything that is below the re-order level, but not to hold stock of more than 4 times the re-order level for any particular item. As an IT department we've been asked to put together an application that will automatically produce the re-order documents upon the clerks request and, because our company is so tight-ar*ed about money, they don't want to waste any paper with incorrect printouts so we have to ensure the clerk can't order things they shouldn't.
SQL> ed
Wrote file afiedt.buf
1 create or replace procedure re_order(p_item_id NUMBER, p_quantity NUMBER) is
2 cursor cur_stock_reorder is
3 select s.stock_level
4 ,r.stock_level as reorder_level
5 ,(r.stock_level*4) as reorder_limit
6 from stock s join reorder_level r on (s.item_id = r.item_id)
7 where s.item_id = p_item_id;
8 --
9 v_stock cur_stock_reorder%ROWTYPE;
10 begin
11 OPEN cur_stock_reorder;
12 FETCH cur_stock_reorder INTO v_stock;
13 IF cur_stock_reorder%NOTFOUND THEN
14 RAISE no_data_found;
15 END IF;
16 CLOSE cur_stock_reorder;
17 --
18 IF v_stock.stock_level >= v_stock.reorder_level THEN
19 -- Stock is not low enough to warrant an order
20 DBMS_OUTPUT.PUT_LINE('Stock has not reached re-order level yet!');
21 ELSE
22 IF v_stock.stock_level + p_quantity > v_stock.reorder_limit THEN
23 -- Required amount is over-ordering
24 DBMS_OUTPUT.PUT_LINE('Quantity specified is too much. Max for this item: '
||to_char(v_stock.reorder_limit-v_stock.stock_level));
25 ELSE
26 DBMS_OUTPUT.PUT_LINE('Order OK. Printing Order...');
27 -- Here goes our code to print the order
28 END IF;
29 END IF;
30 --
31 exception
32 WHEN no_data_found THEN
33 CLOSE cur_stock_reorder;
34 DBMS_OUTPUT.PUT_LINE('Invalid Item ID.');
35* end;
SQL> /
Procedure created.
SQL> exec re_order(10,100);
Invalid Item ID.
PL/SQL procedure successfully completed.
SQL> exec re_order(3,40);
Stock has not reached re-order level yet!
PL/SQL procedure successfully completed.
SQL> exec re_order(1,100);
Quantity specified is too much. Max for this item: 70
PL/SQL procedure successfully completed.
SQL> exec re_order(2,50);
Order OK. Printing Order...
PL/SQL procedure successfully completed.
SQL>
Ok, so that code works, but it's a bit messy with all those nested IF statements. Is there a cleaner way perhaps? Wouldn't it be nice if we could set up our own exceptions...
SQL> ed
Wrote file afiedt.buf
1 create or replace procedure re_order(p_item_id NUMBER, p_quantity NUMBER) is
2 cursor cur_stock_reorder is
3 select s.stock_level
4 ,r.stock_level as reorder_level
5 ,(r.stock_level*4) as reorder_limit
6 from stock s join reorder_level r on (s.item_id = r.item_id)
7 where s.item_id = p_item_id;
8 --
9 v_stock cur_stock_reorder%ROWTYPE;
10 --
11 -- Let's declare our own exceptions for business logic...
12 exc_not_warranted EXCEPTION;
13 exc_too_much EXCEPTION;
14 begin
15 OPEN cur_stock_reorder;
16 FETCH cur_stock_reorder INTO v_stock;
17 IF cur_stock_reorder%NOTFOUND THEN
18 RAISE no_data_found;
19 END IF;
20 CLOSE cur_stock_reorder;
21 --
22 IF v_stock.stock_level >= v_stock.reorder_level THEN
23 -- Stock is not low enough to warrant an order
24 RAISE exc_not_warranted;
25 END IF;
26 --
27 IF v_stock.stock_level + p_quantity > v_stock.reorder_limit THEN
28 -- Required amount is over-ordering
29 RAISE exc_too_much;
30 END IF;
31 --
32 DBMS_OUTPUT.PUT_LINE('Order OK. Printing Order...');
33 -- Here goes our code to print the order
34 --
35 exception
36 WHEN no_data_found THEN
37 CLOSE cur_stock_reorder;
38 DBMS_OUTPUT.PUT_LINE('Invalid Item ID.');
39 WHEN exc_not_warranted THEN
40 DBMS_OUTPUT.PUT_LINE('Stock has not reached re-order level yet!');
41 WHEN exc_too_much THEN
42 DBMS_OUTPUT.PUT_LINE('Quantity specified is too much. Max for this item: '
||to_char(v_stock.reorder_limit-v_stock.stock_level));
43* end;
SQL> /
Procedure created.
SQL> exec re_order(10,100);
Invalid Item ID.
PL/SQL procedure successfully completed.
SQL> exec re_order(3,40);
Stock has not reached re-order level yet!
PL/SQL procedure successfully completed.
SQL> exec re_order(1,100);
Quantity specified is too much. Max for this item: 70
PL/SQL procedure successfully completed.
SQL> exec re_order(2,50);
Order OK. Printing Order...
PL/SQL procedure successfully completed.
SQL>
That's better. And now we don't have to use all those nested IF statements and worry about it accidently getting to code that will print the order out as, once one of our user defined exceptions is raised, execution goes from the Statements section into the Exception section and all handling of errors is done in one place.
Now for the second sort of user defined exception...
A new requirement has come in from the Finance department who want to have details shown on the order that show a re-order 'indicator' based on the formula ((maximum allowed stock - current stock)/re-order quantity), so this needs calculating and passing to the report...
SQL> ed
Wrote file afiedt.buf
1 create or replace procedure re_order(p_item_id NUMBER, p_quantity NUMBER) is
2 cursor cur_stock_reorder is
3 select s.stock_level
4 ,r.stock_level as reorder_level
5 ,(r.stock_level*4) as reorder_limit
6 ,(((r.stock_level*4)-s.stock_level)/p_quantity) as finance_factor
7 from stock s join reorder_level r on (s.item_id = r.item_id)
8 where s.item_id = p_item_id;
9 --
10 v_stock cur_stock_reorder%ROWTYPE;
11 --
12 -- Let's declare our own exceptions for business logic...
13 exc_not_warranted EXCEPTION;
14 exc_too_much EXCEPTION;
15 begin
16 OPEN cur_stock_reorder;
17 FETCH cur_stock_reorder INTO v_stock;
18 IF cur_stock_reorder%NOTFOUND THEN
19 RAISE no_data_found;
20 END IF;
21 CLOSE cur_stock_reorder;
22 --
23 IF v_stock.stock_level >= v_stock.reorder_level THEN
24 -- Stock is not low enough to warrant an order
25 RAISE exc_not_warranted;
26 END IF;
27 --
28 IF v_stock.stock_level + p_quantity > v_stock.reorder_limit THEN
29 -- Required amount is over-ordering
30 RAISE exc_too_much;
31 END IF;
32 --
33 DBMS_OUTPUT.PUT_LINE('Order OK. Printing Order...');
34 -- Here goes our code to print the order, passing the finance_factor
35 --
36 exception
37 WHEN no_data_found THEN
38 CLOSE cur_stock_reorder;
39 DBMS_OUTPUT.PUT_LINE('Invalid Item ID.');
40 WHEN exc_not_warranted THEN
41 DBMS_OUTPUT.PUT_LINE('Stock has not reached re-order level yet!');
42 WHEN exc_too_much THEN
43 DBMS_OUTPUT.PUT_LINE('Quantity specified is too much. Max for this item: '
||to_char(v_stock.reorder_limit-v_stock.stock_level));
44* end;
SQL> /
Procedure created.
SQL> exec re_order(2,40);
Order OK. Printing Order...
PL/SQL procedure successfully completed.
SQL> exec re_order(2,0);
BEGIN re_order(2,0); END;
ERROR at line 1:
ORA-01476: divisor is equal to zero
ORA-06512: at "SCOTT.RE_ORDER", line 17
ORA-06512: at line 1
SQL>
Hmm, there's a problem if the person specifies a re-order quantity of zero. It raises an unhandled exception.
Well, we could put a condition/check into our code to make sure the parameter is not zero, but again we would be wrapping our code in an IF statement and not dealing with the exception in the exception handler.
We could do as we did before and just include a simple IF statement to check the value and raise our own user defined exception but, in this instance the error is standard Oracle error (ORA-01476) so we should be able to capture it inside the exception handler anyway... however...
EXCEPTION
WHEN ORA-01476 THEN
... is not valid. What we need is to give this Oracle error a name.
This is done by declaring a user defined exception as we did before and then associating that name with the error number using the PRAGMA EXCEPTION_INIT statement in the declaration section.
SQL> ed
Wrote file afiedt.buf
1 create or replace procedure re_order(p_item_id NUMBER, p_quantity NUMBER) is
2 cursor cur_stock_reorder is
3 select s.stock_level
4 ,r.stock_level as reorder_level
5 ,(r.stock_level*4) as reorder_limit
6 ,(((r.stock_level*4)-s.stock_level)/p_quantity) as finance_factor
7 from stock s join reorder_level r on (s.item_id = r.item_id)
8 where s.item_id = p_item_id;
9 --
10 v_stock cur_stock_reorder%ROWTYPE;
11 --
12 -- Let's declare our own exceptions for business logic...
13 exc_not_warranted EXCEPTION;
14 exc_too_much EXCEPTION;
15 --
16 exc_zero_quantity EXCEPTION;
17 PRAGMA EXCEPTION_INIT(exc_zero_quantity, -1476);
18 begin
19 OPEN cur_stock_reorder;
20 FETCH cur_stock_reorder INTO v_stock;
21 IF cur_stock_reorder%NOTFOUND THEN
22 RAISE no_data_found;
23 END IF;
24 CLOSE cur_stock_reorder;
25 --
26 IF v_stock.stock_level >= v_stock.reorder_level THEN
27 -- Stock is not low enough to warrant an order
28 RAISE exc_not_warranted;
29 END IF;
30 --
31 IF v_stock.stock_level + p_quantity > v_stock.reorder_limit THEN
32 -- Required amount is over-ordering
33 RAISE exc_too_much;
34 END IF;
35 --
36 DBMS_OUTPUT.PUT_LINE('Order OK. Printing Order...');
37 -- Here goes our code to print the order, passing the finance_factor
38 --
39 exception
40 WHEN exc_zero_quantity THEN
41 DBMS_OUTPUT.PUT_LINE('Quantity of 0 (zero) is invalid.');
42 WHEN no_data_found THEN
43 CLOSE cur_stock_reorder;
44 DBMS_OUTPUT.PUT_LINE('Invalid Item ID.');
45 WHEN exc_not_warranted THEN
46 DBMS_OUTPUT.PUT_LINE('Stock has not reached re-order level yet!');
47 WHEN exc_too_much THEN
48 DBMS_OUTPUT.PUT_LINE('Quantity specified is too much. Max for this item: '
||to_char(v_stock.reorder_limit-v_stock.stock_level));
49* end;
SQL> /
Procedure created.
SQL> exec re_order(2,0);
Quantity of 0 (zero) is invalid.
PL/SQL procedure successfully completed.
SQL>
Lastly, let's look at raising our own exceptions with our own exception numbers...
SQL> ed
Wrote file afiedt.buf
1 create or replace procedure re_order(p_item_id NUMBER, p_quantity NUMBER) is
2 cursor cur_stock_reorder is
3 select s.stock_level
4 ,r.stock_level as reorder_level
5 ,(r.stock_level*4) as reorder_limit
6 ,(((r.stock_level*4)-s.stock_level)/p_quantity) as finance_factor
7 from stock s join reorder_level r on (s.item_id = r.item_id)
8 where s.item_id = p_item_id;
9 --
10 v_stock cur_stock_reorder%ROWTYPE;
11 --
12 exc_zero_quantity EXCEPTION;
13 PRAGMA EXCEPTION_INIT(exc_zero_quantity, -1476);
14 begin
15 OPEN cur_stock_reorder;
16 FETCH cur_stock_reorder INTO v_stock;
17 IF cur_stock_reorder%NOTFOUND THEN
18 RAISE no_data_found;
19 END IF;
20 CLOSE cur_stock_reorder;
21 --
22 IF v_stock.stock_level >= v_stock.reorder_level THEN
23 -- Stock is not low enough to warrant an order
24 [b]RAISE_APPLICATION_ERROR(-20000, 'Stock has not reached re-order level yet!');[/b]
25 END IF;
26 --
27 IF v_stock.stock_level + p_quantity > v_stock.reorder_limit THEN
28 -- Required amount is over-ordering
29its nice article, have put up this one the blog
site,Nah, I don't have time to blog, but if one of the other Ace's/Experts wants to copy it to a blog with reference back to here (and all due credit given ;)) then that's fine by me.
I'd go for a book like "Selected articles by OTN members" or something. Does anybody have a list of links of all those mentioned articles?Just these ones I've bookmarked...
Introduction to regular expressions ... by CD
When your query takes too long ... by Rob van Wijk
How to pipeline a function with a dynamic number of columns? by ascheffer
PL/SQL 101 : Exception Handling by BluShadow -
Exception handling is not working in GCC compile shared object
Hello,
I am facing very strange issue on Solaris x86_64 platform with C++ code compiled usging gcc.3.4.3.
I have compiled shared object that load into web server process space while initialization. Whenever any exception generate in code base, it is not being caught by exception handler. Even though exception handlers are there. Same code is working fine since long time but on Solaris x86, Sparc arch, Linux platform
With Dbx, I am getting following stack trace.
Stack trace is
dbx: internal error: reference through NULL pointer at line 973 in file symbol.cc
[1] 0x11335(0x1, 0x1, 0x474e5543432b2b00, 0x59cb60, 0xfffffd7fffdff2b0, 0x11335), at 0x11335
---- hidden frames, use 'where -h' to see them all ----
=>[4] __cxa_throw(obj = (nil), tinfo = (nil), dest = (nil), , line 75 in "eh_throw.cc"
[5] OBWebGate_Authent(r = 0xfffffd7fff3fb300), line 86 in "apache.cpp"
[6] ap_run_post_config(0x0, 0x0, 0x0, 0x0, 0x0, 0x0), at 0x444624
[7] main(0x0, 0x0, 0x0, 0x0, 0x0, 0x0), at 0x42c39a
I am using following link options.
Compile option is
/usr/sfw/bin/g++ -c -I/scratch/ashishas/view_storage/build/coreid1014/palantir/apache22/solaris-x86_64/include -m64 -fPIC -D_REENTRANT -Wall -g -o apache.o apache.cpp
Link option is
/usr/sfw/bin/g++ -shared -m64 -o apache.so apache.o -lsocket -lnsl -ldl -lpthread -lthread
At line 86, we are just throwing simple exception which have catch handlers in place. Also we do have catch(...) handler as well.
Surpursing things are..same issue didn't observe if we make it as executable.
Issue only comes if this is shared object loaded on webserver. If this is plain shared object, opened by anyother exe, it works fine.
Can someone help me out. This is completly blocking issue for us. Using Solaris Sun Studio compiler is no option as of now.shared object that load into web server process space
... same issue didn't observe if we make it as executable.When you "inject" your shared object into some other process a well-being of your exception handling depends on that other process.
Mechanics of x64 stack traversing (unwind) performed when you throw the exception is quite complicated,
particularly involving a "nearly-standartized" Unwind interface (say, Unwind_RaiseException).
When we are talking about g++ on Solaris there are two implementations of unwind interface, one in libc and one in libgcc_s.so.
When you g++-compile the executable you get it directly linked with libgcc_s.so and Unwind stuff resolves into libgccs.
When g++-compiled shared object is loaded into non-g++-compiled executable's process _Unwind calls are most likely already resolved into Solaris libc.
Thats why you might see the difference.
Now, what exactly causes this difference can vary, I can only speculate.
All that would not be a problem if _Unwind interface was completely standartized and properly implemented.
However there are two issues currently:
* gcc (libstdc++ in particular) happens to use additional non-standard _Unwind calls which are not present in Solaris libc
naturally, implementation details of Unwind implementation in libc differs to that of libgccs, so when all the standard _Unwind
routines are resolved into Solaris version and one non-standard _Unwind routine is resolved into gcc version you get a problem
(most likely that is what happens with you)
* libc Unwind sometimes is unable to decipher the code generated by gcc.
However that is likely to happen with modern gcc (say, 4.4+) and not that likely with 3.4.3
Btw, you can check your call frame to see where _Unwind calls come from:
where -h -lIf you indeed stomped on "mixed _Unwind" problem then the only chance for you is to play with linker
so it binds Unwind stuff from your library directly into libgccs.
Not tried it myself though.
regards,
__Fedor. -
Exception handling in in insert statemnt
i am inserting values in to a table in a procedure.for insert statemnt what are the possible exceptions that may occur.
how to handle exceptions for that insert statement(other than when others)user639995 wrote:
is there any possiblity to use if sql%rowcount = 0 then
RAISE e1;
like thisNot for an insert statement, no.
sql%rowcount returns the number of rows effected by a DML statement.
For any of the statements you can only check sql%rowcount after the DML statement successfully executes, and it will only return a 0 if no rows were effected by that DML statement e.g. if an update effected no rows or an insert ... select ... actually inserted no rows etc.
If an exception occurs during a DML statement then execution will pass directly to the exception handler so you won't have the opportunity to test for sql%rowcount after the statement.
You should have an exception handler for expected exceptions.
If an exception is not expected then you should let your code raise it up so it is seen and not handled.
example of defining exceptions for non-named error numbers...
SQL> create table x (x number);
Table created.
SQL> insert into x values ('x');
insert into x values ('x')
ERROR at line 1:
ORA-01722: invalid number
SQL> set serverout on
SQL> declare
2 ex_not_number exception;
3 pragma exception_init(ex_not_number, -1722);
4 begin
5 insert into x values (1);
6 commit;
7 insert into x values ('A');
8 commit;
9 exception
10 when ex_not_number then
11 dbms_output.put_line('An attempt to insert a value that is not a number was made.');
12 end;
13 /
An attempt to insert a value that is not a number was made.
PL/SQL procedure successfully completed.
SQL> select * from x;
X
1
SQL>Further details on exception handling here:
[PL/SQL 101 : Exception Handling|http://forums.oracle.com/forums/thread.jspa?threadID=697262&tstart=50] -
Exception handling for mis-addressed messages
We are using ebXML messaging in WLI. In many of our workflows we start new conversations with trading partners based on the contents of address fields in the messages. Now and again during development a message comes in which is addressed to a TP who doesn't exist. The message fails to be sent and rolls back repeatedly. Is there a simple way to remove these messages from the WLI hub? Can exception handling be used to move messages which are failing to enter the workflows to a special queue automatically?
thanks
BenHi Holger,
I will not translate the coding into VB. So if you want to do this it is OK with me.
An idea would be after some testing by the community to provide the functionality as a DLL. This way it could also easily be added to a VB project.
However I assume that some developers prefer to integrate the coding themselves so that they might add additional customer specific functionlity.
For example not to raise an exception if a specific error is in the return parameter because they want to ignore it.
Best regards,
Andre -
Exception Handling in bounded taskflows - expected behaviour
Hi,
I'm currently reviewing exception handling in bounded task flows and some things does not seems to be very clear for me.
(q1) Does it make sense that a bounded task flow calls a method (via a method activity) defined on the page definition of another page (outside of the BTF) by using a #{data.xxxmyPageDef.myMethodName.execute} EL expression?
(q2) Is is correct to expect the application to execute the method marked as ExceptionHandler in the taskflow, whenever an exception occurs?
(q3) I created 5 different scenarios where I call a service method which throws an exception, from within a page fragment of the BTF.
(q3 – sc1) Call a service method through the binding layer of the current page (by using #{bindings.xxx.execute})
Result: A dialog containing the exception message appears.
This is what I expected. Althought, the exception handler method does not seems to be invoked.(q3 – sc2) Call a service method through a task flow method activity using #{bindings.xxx.execute}
Result: A dialog containing the exception message appears.
This is what I expected. Althought, the exception handler method does not seems to be invoked.(q3 – sc3) Call a service method through a task flow method activity using #{data.myPageFragementPagedef.xxx.execute} (accessing the pageDef of the page fragment)
Result: Nothing happens.
This is not what I expected. Although, the exception handler method does nog seems to be invoked, I expect the ADF Error Handler to create a FacesMessage.(q3 – sc4) Call a service method through a task flow method activity using #{data.myPageContainingThePageFragmentPageDef.xxx.execute} (accessing the page containing the BTF region)
Result: Nothing happens.
This is not what I expected. Although, the exception handler method does nog seems to be invoked, I expect the ADF Error Handler to create a FacesMessage. (q3 – sc5) Call a service method through a task flow method activity using #{data.aPageOutsideTheBTFPageDef.xxx.execute} (accessing a page outside the BTW)
Result: Nothing happens.
This is not what I expected. Although, the exception handler method does nog seems to be invoked, I expect the ADF Error Handler to create a FacesMessage. (q4) How can it be possible that – without an exception handler – exceptions occur when calling method activities, without the exceptions being translated to FacesMessages?
Thanks in advance,
Koen Verhulst
JDeveloper 11.1.1.4Koen,
+(q1) Does it make sense that a bounded task flow calls a method (via a method activity) defined on the page definition of another page (outside of the BTF) by using a #{data.xxxmyPageDef.myMethodName.execute} EL expression?+
No. Exceptions should be handled locally.
+(q2) Is is correct to expect the application to execute the method marked as ExceptionHandler in the taskflow, whenever an exception occurs?+
Only for exceptions that are before Render Response. The Render Response Phase is not handled in ADFc. So exceptions that occur in managed beans may fall through
+(q3) I created 5 different scenarios where I call a service method which throws an exception, from within a page fragment of the BTF.+
+(q3 – sc1) Call a service method through the binding layer of the current page (by using #{bindings.xxx.execute}) Result: A dialog containing the exception message appears.+
This is what I expected. Althought, the exception handler method does not seems to be invoked.
The binding layer has an error handler you can override in the DataBinings.cpx file
+(q3 – sc2) Call a service method through a task flow method activity using #{bindings.xxx.execute}+
Result: A dialog containing the exception message appears.
This is what I expected. Althought, the exception handler method does not seems to be invoked.
Again, you use the binding layer to invoke the service
+(q3 – sc3) Call a service method through a task flow method activity using #{data.myPageFragementPagedef.xxx.execute} (accessing the pageDef of the page fragment)+
Result: Nothing happens.
This is not what I expected. Although, the exception handler method does nog seems to be invoked, I expect the ADF Error Handler to create a FacesMessage.
Never use such a call. Its bad practice as there is no guarantee the container you reference is active. Always have the method call activity have its own binding defined when accessing a method call activity. I know there are lots of example floating aroundthat you #{data ...} and many are from 10.1.3. This should be avoided alltogether though
+(q3 – sc4) Call a service method through a task flow method activity using #{data.myPageContainingThePageFragmentPageDef.xxx.execute} (accessing the page containing the BTF region)+
Result: Nothing happens.
This is not what I expected. Although, the exception handler method does not seems to be invoked, I expect the ADF Error Handler to create a FacesMessage.
Again, this is not a proper use of the ADF framework.
+(q3 – sc5) Call a service method through a task flow method activity using #{data.aPageOutsideTheBTFPageDef.xxx.execute} (accessing a page outside the BTW)+
Result: Nothing happens. This is not what I expected. Although, the exception handler method does nog seems to be invoked, I expect the ADF Error Handler to create a FacesMessage.
accessing a page outside the BTW (!!!) This should ring a worst practices alarm on your laptop (obviously doesn't do it either)
+(q4) How can it be possible that – without an exception handler – exceptions occur when calling method activities, without the exceptions being translated to FacesMessages?+
Exceptions are not handled in a single place but stacked. The business service raises an exception and passes it to the binding layer if not handled. The binding layer handles the exception and if it can't passes it to ADFc. ADFc can handle this exception if it is not during Render Response.
Bottom line: There is no single point of exception handling. So as a recommendation for best practices
- Catch and handle exceptions as close as possible to their origins
- If things can go wrong, thy will - use try/catch blocks in managed beans
- Use an exception handling activity in all bounded task flows. In the case of task flow call activities being used exceptions can bubble up to the caller. However, this would take users out of their current application context
- Exceptions not handled in ADFc can be intercepted by overriding the application task flow exception handler (used by the exception handler activities). This would give you a chance e.g. to handle issues during Render Response
- Never fight the framework, never bend the framework: Don't use out of scope access to page definitions and resources. Exception handling is not a replacement for bad code practices (sorry for saying this, its not meant to be rude) :-)
Though I don't have a qualified numbers of bugs open for exception handling in ADF between 11.1.1.4 and now (and some that are open), but there are issues reported in this area. If there is something that really feels wrong, please go ahead and file a bug and provide a test case for development to have a look. The Render Response issue, for example is something we are aware of and that is in discussion (afaik knows, there is a change in exception handling in JSF 2 that may have an impact to what we can do in ADFc).
thanks
Frank -
Exception Handling in Web Center for UI related Errors not working.
Hi Guys,
I have implemented Error Handling in ADF Application with Custom Model Exception Handler ( which is "CustomExceptionHandler extends DCErrorHandlerImpl") to catch all Model Layer Exception and to customize those error messages.
I have implemented Error Handling in ADF Application with Custom View Exception Handler ( which is "CustomViewErrorHandler extends oracle.adf.view.rich.context.ExceptionHandler";) to catch all View Layer Exception and to customize those error messages.
The design for this is , in Model Custom Exception Handler i find the exception message in "public String getDisplayMessage(BindingContext bindingContext,Exception exception) " method and throw RuntimeException to pass this exception to Custom View Layer Exception , so that i can handle all the exception @ View Layer it self .
In the View Layer Exception Handler i am navigating to specific error page using
String contextPath = ((HttpServletRequest)FacesContext.getCurrentInstance().getExternalContext().getRequest()).getContextPath();
ExternalContext ectx = facesContext.getExternalContext();
ectx.redirect.
All these things absolutly working in ADF Application for all the exception ( Model , View ) and i am successfully navigating to error page.
Problem :
When i implement the same thing in Webcenter Application ( Model Custom Exception Handler and View Custom Exception Handler), Model Part is working as expected , but View Custom Exception Handler is not all calling .
i am assuming that ,this View Custom Exception Handler (CustomViewErrorHandler extends oracle.adf.view.rich.context.ExceptionHandler) works only for JSF Life cycle
"Allows frameworks to intercept otherwise unhandled exceptions thrown during the JSF lifecycle. ExceptionHandlers can be registered by adding a service file with a class name at META-INF/services/oracle.adf.view.rich.context.ExceptionHandler." from http://jdevadf.oracle.com/adf-richclient-demo/docs/apidocs/oracle/adf/view/rich/context/ExceptionHandler.html";
As Webcenter Portal uses ADF Life Cycle this Exception Handler is not calling , i am not sure.
if any one has any idea please let me know .
Thanks
Annapareddy Srinivasrao
Edited by: Srinivasrao Annapareddy on May 22, 2013 12:06 PMi used runtime exception along with the wdwsmodel exception
-
Exception Handling in C++ generate core
Hello ,
I have a shared lib which is having some code for exception handling ,till the point of exception thrown program is running fine but after the exception get thrown the program is crasing and creating the core .
I am using Solaris 5.9 on intel(x86) using compiler CC (CC: Sun C++ 5.5 2003/03/12 )
I am specifing the Makefile here . If any one have faced the same kind of problem then please help me out.
***********************Makefile *****************************
SHARED_LIBS = \
/opt/SUNWspro/prod/lib/libp/libgc.a \
/usr/lib/libCrun.so.1 \
/opt/SUNWspro/prod/lib/CC4/libC.a \
$(WLESSL)/lib/libgp.a \
$(WLESSL)/lib/sslplus.a
LIB=$(OBJ) $(SHARED_LIBS)
LIB128=$(OBJ128) $(SHARED_LIBS)
LIB_20=$(OBJ_20) $(SHARED_LIBS)
CC_20=/opt/SUNWspro/bin/CC
cc_20=/opt/SUNWspro/bin/cc
CC_OUT_20=-w -KPIC -mt -lpthread -c $< -o $@
# compile defintions
DEF=-DAPACHE -DSOLARIS -DEAPI -D_POSIX_PTHREAD_SEMANTICS -D_PTHREAD -D_REENTRANT
DOMFLAG=-DDOMESTIC_STRENGTH_ENABLED
# this is not needed if apache20/bin/apxs is working properly
APXS_CFLAGS_20=-mt -lpthread
COMPILE=$(cc_20) $(APXS_CFLAGS_20) $(STD_20_INC) $(VER2) -c $(SRC) -o $(OBJDIR_20)/abc_w.o
LOAD=$(cc_20) -G -z lazyload -o $(OBJDIR)/abc_wl_20.so $(LIB_20) $(OBJDIR_20)/abc.o
LOAD128=$(cc_20) -G -o $(OBJDIR)/abc_wl128_20.so $(LIB128_20) $(OBJDIR_20)/abc.o
# the DSO and objs should be placed in this directory
OBJDIR=sol_x86
OBJDIR_20=sol_x86/a20
# WLE include files include tmmach which are platform specific
WLESSLINC=$(WLESSL)/sysincludeHi Santinu,
I saw your question and thought of replying you, but I guess you might have got the solution by now as because the post date of your question is around a year back.
You need to change $LOAD so that id uses CC instead of cc. There's a compatibility issue.
LOAD=$(CC_20) -G -z lazyload -o $(OBJDIR)/mod_wl_20.so $(LIB_20) $(OBJDIR_20)/mod_weblogic.o
LOAD128=$(CC_20) -G -o $(OBJDIR)/mod_wl128_20.so $(LIB128_20) $(OBJDIR_20)/mod_weblogic.o
Hope this Helps.
Thanks
Somak -
It takes long time to invoke the Exception handler code
In our setup there is firewall between the Appserver that is using toplink and the database.The firewall terminates idle connection on any port if the connection is idle for 1 hr.So i have implemented an exception handler to reconnect when the connection is broken.The code works fine but It takes 15 mins for the exception handler code to be invoked.
The database is Oracle and the driver is thin driver,OS is solaris.No external connection pool
I had registered the exceptionhandler to the serversession,should i register it with each ClientSession?yes ,15 mins is the time taken before the server session's exception handler code is invoked.
The following is the exception handler code on the sever session.Any thing wrong?
server.setExceptionHandler(new ExceptionHandler()
public Object handleException(RuntimeException ex)
{//This method is executed only after 15 min ,if the connection is broken
String mess=ex.getMessage();
System.out.println("In handler excep mess is "+mess);
if ((ex instanceof DatabaseException) && (mess.equals("connection reset by peer.")||(mess.indexOf("IOException :Broken pipe")!=-1)))
DatabaseException dbex = (DatabaseException) ex;
dbex.getAccessor().reestablishConnection (dbex.getSession());
return dbex.getSession().executeQuery(dbex.getQuery());
return null;
What could be wrong ?
I tried Oracle's connection cache Impl created a connection pool using the same thin driver and on the same env.SQLException is thrown immediately on using the broken connection.so I feel the driver is not causing any problem.
Is there any way in toplink to keep the connections active?or Is there any way to poll all connections in the connection pool and check If they are connected instead of waiting until the exception gets thrown and handle it? -
BPM Process - Exception handling or timeout issues?
Hi Guys,
I have a BPM process as below.
1. Receive step: Receive the file with multiple transactions.
2. Transformation step: Split the file into individual transactions
3 Block step which includes -- par for each mode
1. Send Step (Synchronus): Each individual transaction needs to contact the 3rd party system and get the response. -- Do i need to handle any exceptions here ?
2. Container : Collect all the responses
Block ends
4. Transformation: combine all the responses in to a single file
5. Send Step: synchronus -- send the above single file and get the response back
6. Transformation : Transform the above response into the target structure.
7. Send: send the message asynchronusly to the target system
I need suggestion regarding the exceptional handling or any time out issues, i need to take care of.
any suggestions would be really appreciated
Thanks,
Raj
Edited by: raj reddy on Feb 12, 2009 10:12 PMHi,
I) For the Block holding the Sync Send, create an Exception Block. (right click on Sync Send -> Insert -> Exception Branch)
II) Name the Exception block (ex: exceptionHandler).
III) in the Sync Send step ->Properties -> Exceptions -> in System Error - add exceptionHandler.
IV) Now within the Exception handler block you can create containers to hold values from payload, throw exception as email etc).
This will cover your sync send step incase there is an error while sending the request of a timeout during receiving the response.
You can also do the same for the Step 7) Asycn send - if required.
Another suggestion in your question Step 6) can be done outside the bpm, when you do the interface determination for that Asycn Send you can add the Interface mapping that will map the responses to the target structure.
Doing this will reduce one step in your BPM. For further information in how more you can fine tune your bpm, read this blog - https://www.sdn.sap.com/irj/scn/weblogs?blog=/pub/wlg/5113. [original link is broken] [original link is broken] [original link is broken]
All the best.
Regards,
Balaji.M -
Hi all,
I'm trying to specify a method activity as an exception handler in the adfc-config. The problem is if I specify a view activity or a bounded task flow as the exception handler then it works fine, but if the exception handler is a method activity then it is not recognized. What could be the cause?. I need to execute a method when an exception occurs.
Version: 11.1.2.0
Edited by: NewBee on Apr 23, 2013 10:37 AMHi,
there should not be a problem with this and I recently did the same with JDeveloper 11g R2 (not sure which version of JDeveloper you use because you did not share this information). I assume you just marked the method activity as an exception handler without any other configuration? If so then set a break point to the managed bean method that you access from the method activity to see if it actually stops there. Also note that not all exceptions are handled by the controller exception handler. E.g an exception during render response phase (typically an exception in a managed bean) is not handled by the controller. Also you need to avoid the managed bean that handles the exception to itself throw one. This however you will see when debugging the bean.
Frank -
FORALL Exception handling problem
Hi All,
I have one doubt in forall exception handling. I have gone through the SAVE EXCEPTION for bulk collect but i have one more query
BEGIN
FORALL j IN l_tab.first .. l_tab.last
INSERT INTO exception_test
VALUES (l_tab(i));
EXCEPTION
END;
My requirement is when an exception occurs, i ant to print the values of the collection.
e.g. say l_tab (j).emp_number, l_tab (j).emp_id.
How is that possible?
Thanks
Samarth
Edited by: 950810 on Mar 12, 2013 7:28 PM>
I have one doubt in forall exception handling. I have gone through the SAVE EXCEPTION for bulk collect but i have one more query
BEGIN
FORALL j IN l_tab.first .. l_tab.last
INSERT INTO exception_test
VALUES (l_tab(i));
EXCEPTION
END;
My requirement is when an exception occurs, i ant to print the values of the collection.
e.g. say l_tab (j).emp_number, l_tab (j).emp_id.
How is that possible?
>
Post the code you are using. You didn't post the FORALL that is using SAVE EXCEPTIONS.
The SQL%BULK_EXCEPTIONS associative array that you get has the INDEX of the collection element that caused the exception.
So you need to use those indexes to index into the original collection to get whatever values are in it.
One index from the exception array is:
SQL%BULK_EXCEPTIONS(i).error_index So if your original collection is named 'myCollection' you would reference that collection value as:
myCollection(SQL%BULK_EXCEPTIONS(i).error_index); See 'Handling FORALL Exceptions (%BULK_EXCEPTIONS Attribute)' in the PL/SQL Language doc
http://docs.oracle.com/cd/B28359_01/appdev.111/b28370/tuning.htm#i49099
>
All exceptions raised during the execution are saved in the cursor attribute %BULK_EXCEPTIONS, which stores a collection of records. Each record has two fields:
%BULK_EXCEPTIONS(i).ERROR_INDEX holds the iteration of the FORALL statement during which the exception was raised.
%BULK_EXCEPTIONS(i).ERROR_CODE holds the corresponding Oracle Database error code.
The values stored by %BULK_EXCEPTIONS always refer to the most recently executed FORALL statement. The number of exceptions is saved in %BULK_EXCEPTIONS.COUNT. Its subscripts range from 1 to COUNT.
The individual error messages, or any substitution arguments, are not saved, but the error message text can looked up using ERROR_CODE with SQLERRM as shown in Example 12-9.
You might need to work backward to determine which collection element was used in the iteration that caused an exception. For example, if you use the INDICES OF clause to process a sparse collection, you must step through the elements one by one to find the one corresponding to %BULK_EXCEPTIONS(i).ERROR_INDEX. If you use the VALUES OF clause to process a subset of elements, you must find the element in the index collection whose subscript matches %BULK_EXCEPTIONS(i).ERROR_INDEX, and then use that element's value as the subscript to find the erroneous element in the original collection. -
Bounded Taskflow Exception Handler not working with Page Fragements
I have one bounded - taskflow task-flow-definition
<?xml version="1.0" encoding="windows-1252" ?>
<adfc-config xmlns="http://xmlns.oracle.com/adf/controller" version="1.2">
<task-flow-definition id="task-flow-definition">
<default-activity>view1</default-activity>
<managed-bean>
<managed-bean-name>backing_main</managed-bean-name>
<managed-bean-class>view.backing.Main</managed-bean-class>
<managed-bean-scope>pageFlow</managed-bean-scope>
</managed-bean>
<managed-bean>
<managed-bean-name>backing_view1</managed-bean-name>
<managed-bean-class>view.backing.View1</managed-bean-class>
<managed-bean-scope>pageFlow</managed-bean-scope>
</managed-bean>
<managed-bean>
<managed-bean-name>backing_view2</managed-bean-name>
<managed-bean-class>view.backing.View2</managed-bean-class>
<managed-bean-scope>pageFlow</managed-bean-scope>
</managed-bean>
<exception-handler>view2</exception-handler>
<view id="view1">
<page>/view1.jsff</page>
</view>
<view id="view2">
<page>/view2.jsff</page>
</view>
<use-page-fragments/>
</task-flow-definition>
</adfc-config>view1.jsff contains one command button, which calls one ActionListener
<?xml version='1.0' encoding='windows-1252'?>
<jsp:root xmlns:jsp="http://java.sun.com/JSP/Page" version="2.1"
xmlns:af="http://xmlns.oracle.com/adf/faces/rich">
<af:commandButton text="commandButton 1" actionListener="#{pageFlowScope.backing_view1.callMyFunction}"
binding="#{pageFlowScope.backing_view1.commandButton1}"
id="commandButton1"/>
<!--oracle-jdev-comment:auto-binding-backing-bean-name:backing_view1-->
</jsp:root>view1.java callMyFunction throws an Exception
public void callMyFunction(ActionEvent event) throws Exception{
throw new Exception();
}view2.jsff is an exception handler
<?xml version='1.0' encoding='windows-1252'?>
<jsp:root xmlns:jsp="http://java.sun.com/JSP/Page" version="2.1"
xmlns:af="http://xmlns.oracle.com/adf/faces/rich">
<af:activeOutputText value="Exception Occured"
binding="#{pageFlowScope.backing_view2.activeOutputText1}"
id="activeOutputText1"
inlineStyle="font-size:xx-large; color:red;"/>
<!--oracle-jdev-comment:auto-binding-backing-bean-name:backing_view2-->
</jsp:root>above taskflow is dragged-drop as a Region in one file main.jspx
<?xml version='1.0' encoding='windows-1252'?>
<jsp:root xmlns:jsp="http://java.sun.com/JSP/Page" version="2.1"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:af="http://xmlns.oracle.com/adf/faces/rich">
<jsp:directive.page contentType="text/html;charset=windows-1252"/>
<f:view>
<af:document binding="#{pageFlowScope.backing_main.document1}"
id="document1">
<af:form binding="#{pageFlowScope.backing_main.form1}" id="form1">
<af:region value="#{bindings.taskflowdefinition1.regionModel}"
id="taskf1"
binding="#{pageFlowScope.backing_main.taskf1}"/>
</af:form>
</af:document>
</f:view>
<!--oracle-jdev-comment:auto-binding-backing-bean-name:backing_main-->
</jsp:root>*pressing a commandButton on view1.jsff throws an Exception as expected but does not go to exceptionHandler [view2.jsff]*
However, this does work with Bounded Task-Flow without page fragments , view1.jspx contains one button, calling one method which throws an Exception,
view2.jspx is an Exception Handler, and in this case it redirects to the view2.jspx [error page]
any ideas?
thanksHi,
Pretty much. However, you got the event part wrong, which is mostly my fault here. First, let put down some general JSF facts about event handling.
1. http://java.sun.com/javaee/5/docs/api/javax/faces/component/UIComponent.html#queueEvent(javax.faces.event.FacesEvent)
2. So, basically, queuing an event on a component means queuing it on its parent until you reach the UIViewRoot that will really actually queue it. That strategy allows iterating components to intercept event queued on their children to record the row index as well so that the data model can be synchronized correctly during the broadcast phase (see http://java.sun.com/javaee/5/docs/api/javax/faces/component/UIData.html#queueEvent(javax.faces.event.FacesEvent) and http://java.sun.com/javaee/5/docs/api/javax/faces/component/UIData.html#broadcast(javax.faces.event.FacesEvent))
3. Exceptions that aren't handled by the exception handler are thrown during broadcast or various process* methods.
So, the catch component must leverage these facts to intercept events queued on its children (by overriding queueEvent method) wrapping the original event in a custom on that flag the catch component itself as the source of the event. The result will be that the broadcast method of the catch component will be called to handle the event. The broadcast method must then unwrap the event (to get the original event), gets the original source, then call originalSource.broadcast(originalEvent) within a try-catch block.
Does it make any more sense put that way? Note that it's an obscure part of JSF so I cannot make it incredibly simple either.
Regards,
~ Simon -
Exception Handling for Array Binding
Hi
1)
I am using a Stored Procedure.
I am using array binding and if i am sending an array of count 10 to be inserted in a table and only 9 got inserted,i deliberatly inserted one errorneous record in array, the count returned by ExecuteNonQuery() is 10.Why ?
How can i come to know exact number of rows inserted in table, how can i use Output variables, because the array bind count is 10 so if i add an output parameter it gives error ArrayBind count is wrong....
2)
Is it possible to roll back all the inserts if error occurs in any of the insert by Oracle engine.What it does is it inserts all correct records and leaves the errorneous record and doesn't even throw any exception or any message.
Answer - This can be achieved by using OracleTransaction and don't use Exception handling in procedure otherwise there wont be any exception thrown by procedure which is necessary to detect if an error occured during insert.If you use exception handling OracleEngine will insert correct rows and leave errorneous record and return count of inserted + non inserted records which is wrong.
Please help.
Message was edited by:
user556446
Message was edited by:
user556446You'll need to encapsulate your validation within it's own block as described below:
-- this will die on the first exception
declare
TYPE T_BADDATA_TEST IS TABLE OF VARCHAR2(1000) INDEX BY binary_integer ;
tbt T_BADDATA_TEST ;
aBadTypeFound exception ;
begin
tbt(0) := 'a';
tbt(1) := 'b';
tbt(2) := 'c';
for idx in tbt.first..tbt.last loop
if tbt(idx) = 'b' then
raise aBadTypeFound ;
else
dbms_output.put_line(tbt(idx));
end if ;
end loop ;
end ;--encapsulate the exception area in a begin/end block to handle the exception but continue on
declare
TYPE T_BADDATA_TEST IS TABLE OF VARCHAR2(1000) INDEX BY binary_integer ;
tbt T_BADDATA_TEST ;
aBadTypeFound exception ;
begin
tbt(0) := 'a';
tbt(1) := 'b';
tbt(2) := 'c';
for idx in tbt.first..tbt.last loop
BEGIN
if tbt(idx) = 'b' then
raise aBadTypeFound ;
else
dbms_output.put_line(tbt(idx));
end if ;
EXCEPTION
WHEN aBadTypeFound THEN
dbms_output.put_line(tbt(idx) || ' is bad data');
WHEN OTHERS THEN
dbms_output.put_line('exception');
END ;
end loop ;
end ;
output:
a
b is bad data
c
***/
Maybe you are looking for
-
How to route the Idoc to Two Different Locations based on the Plant Values
Hi All, We will generate single Idoc, in that we will have 2 E1MARCM segments, one will have UK plant and another will have US plant. Now in XI, receiver determination i need to route the idoc to corresponding folders. How can we do this, because in
-
I get this error message when i plug my ipod into my computer "iTunes cannot read the contents of the iPod "(my ipod's name)". Use the iPod Software Updater application to restore the iPod to factory settings." I don't want to go through the hassle o
-
I have charges on bill in question.How do I find out what they are
I have charges on my bill in question. How do I find out what they are. COULD "NO" find any help on website.
-
HT4337 Can you relocate OS, data to an external SSD,
I am running Lion on an early 2009 iMac. I use two external drives, one for Time Machine and the other for LR4 files. Can I relocate OS, date to an external ssd. I am told that this solution willl marked speed up the machine. Thanks David
-
Hi, friends i completed ODI training and i know SQLPLSQL and OBIEE 10G can i expect more calls on ODI,how is market for odi present,please share your valuable suggessions thanks raju