MQRC 2018: Connection handle error
MQRC 2018 (MQRC_
Other names for this code
Also written as RC2018, reason code 2018, MQ 2018, MQ error 2018, MQRC_HCONN_ERROR, 07E2, 0x07E2, Hconn error, invalid connection handle MQ, MQJE001 Reason 2018.
What it means
Every MQI call after MQCONN or MQCONNX passes the connection handle that the connect call returned. The queue manager checks that handle first. If it doesn't recognise it, or the handle belongs to a different thread or has already been disconnected, the call fails with MQCC_
This is a programming or build problem, not a queue manager problem. The handle may be uninitialised, overwritten, freed by an earlier MQDISC, or used on the wrong thread. A connection handle belongs to the thread that created it unless the connection was made with MQCNO_
On z/OS a common cause is different. The program was link-edited with the wrong MQ stub for its environment, or with a stub from a newer MQ release than the queue manager it runs against. CICS, batch and IMS programs each need their own stub.
Common causes
- The program issues an MQI call after MQDISC, or after a failed MQCONN, so the handle variable holds a stale or empty value.
- A multithreaded program passes a handle to another thread when the connection wasn't made shareable with MQCNO_
HANDLE_ SHARE_ BLOCK or MQCNO_ HANDLE_ SHARE_ NO_ BLOCK. - One thread disconnects a shared handle while other threads are still using it.
- On z/OS, the program was linked with the wrong stub. CICS programs need CSQCSTUB, batch programs CSQBSTUB and IMS programs CSQQSTUB. A stub from a newer MQ release than the running queue manager also causes it.
- On CICS TS 3.2 and later, a data conversion exit that calls MQXCNVC isn't defined as OPENAPI. The task switches to the QR TCB and its MQ connection is no longer valid there.
- Storage overlay. The handle variable was overwritten by a buffer overrun or a mismatched parameter list.
How to find the problem
- Note which call returned 2018. If it is the first call after MQCONN, check that MQCONN returned MQCC_
OK and that the program kept the handle it returned. - On distributed MQ, take an MQ trace (
strmqtrcandendmqtrc) or turn on application activity trace. Both show each MQI call with its Hconn, so you can see where the handle changes or is used after MQDISC. - In multithreaded code, log the thread ID with each MQ call. A 2018 on a thread that didn't make the connection points to handle sharing.
- On z/OS, look at the link-edit map of the load module and confirm it includes CSQCSTUB, CSQBSTUB or CSQQSTUB to match where it runs. Compare the SCSQLOAD library used at link time with the queue manager's release.
- In CICS, check the program definition of any conversion exit with
CEMT INQUIRE PROGRAM(...)and look at its API and CONCURRENCY settings.
How to fix it
- Make sure every MQI call uses the handle from a successful MQCONN or MQCONNX, and that no call runs after MQDISC on that handle.
- Give each thread its own connection, or connect with a shared-handle option on MQCONNX and coordinate MQDISC so no thread disconnects while others are working.
- On z/OS, relink the program with the stub for its environment from the SCSQLOAD library of the release it runs on.
- On CICS TS 3.2 and later, define a conversion exit that calls MQXCNVC as OPENAPI (API(OPENAPI) on its PROGRAM definition).
- Treat an unexpected 2018 as a bug to fix rather than a condition to retry. Retrying with the same handle fails the same way.
IBM documentation
IBM documentation: MQRC 2018. Use the documentation for your installed release.
Related codes
Questions
Is MQRC 2018 a queue manager problem?
Almost never. The queue manager is rejecting a handle the program passed. Look at the application code, its threads or, on z/OS, the stub it was linked with.
What is the difference between 2018 and 2019?
2018 is a bad connection handle (Hconn). 2019 is a bad object handle (Hobj), the one MQOPEN returns for a queue or other object.
Why does 2018 appear only under load?
Threading bugs show up when several threads run at once. A handle shared between threads without the right MQCONNX option, or a disconnect racing with another thread's call, often works in testing and fails in production.