0% found this document useful (1 vote)
3K views615 pages

WebSphere MQ Application Programming Guide

This edition of the book applies to the following: v IBM WebSphere MQ, Version 7. V IBM WebSphere MQ for z / os, Version 7. And to any subsequent releases and modifications until otherwise indicated in new editions.

Uploaded by

Ramasamy Ramar
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (1 vote)
3K views615 pages

WebSphere MQ Application Programming Guide

This edition of the book applies to the following: v IBM WebSphere MQ, Version 7. V IBM WebSphere MQ for z / os, Version 7. And to any subsequent releases and modifications until otherwise indicated in new editions.

Uploaded by

Ramasamy Ramar
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 615

WebSphere MQ 򔻐򗗠򙳰

Application Programming Guide


Version 7.0

SC34-6939-00
WebSphere MQ 򔻐򗗠򙳰

Application Programming Guide


Version 7.0

SC34-6939-00
Note
Before using this information and the product it supports, be sure to read the general information under notices at the back
of this book.

First edition (April 2008)


This edition of the book applies to the following:
v IBM WebSphere MQ, Version 7.0
v IBM WebSphere MQ for z/OS, Version 7.0
and to any subsequent releases and modifications until otherwise indicated in new editions.
© Copyright International Business Machines Corporation 1993, 2008. All rights reserved.
US Government Users Restricted Rights – Use, duplication or disclosure restricted by GSA ADP Schedule Contract
with IBM Corp.
Contents
Figures . . . . . . . . . . . . . . vii Rules for naming WebSphere MQ objects . . . 61
Handling program errors . . . . . . . . . . 62
Tables . . . . . . . . . . . . . . . ix Locally determined errors . . . . . . . . 63
Using report messages for problem determination 65
Remotely determined errors . . . . . . . . 66
Chapter 1. Designing applications that
use WebSphere MQ . . . . . . . . . . 1 Chapter 2. Writing a WebSphere MQ
Introduction to message queuing . . . . . . . 1
application . . . . . . . . . . . . . 69
What is message queuing? . . . . . . . . . 1
Introducing the Message Queue Interface . . . . 69
What is a message? . . . . . . . . . . . 2
What is in the MQI? . . . . . . . . . . 69
What is a message queue? . . . . . . . . . 2
Parameters common to all the calls . . . . . 77
What is a queue manager? . . . . . . . . . 3
Specifying buffers . . . . . . . . . . . 78
What is a cluster? . . . . . . . . . . . . 3
Programming language considerations . . . . 79
What is a shared queue, a queue-sharing group,
z/OS batch considerations . . . . . . . . 87
and intra-group queuing? . . . . . . . . . 4
UNIX signal handling . . . . . . . . . . 88
What is a WebSphere MQ client? . . . . . . 4
Connecting to and disconnecting from a queue
What is publish/subscribe? . . . . . . . . 4
manager . . . . . . . . . . . . . . . 91
Main features of message queuing . . . . . . 4
Connecting to a queue manager using the
Benefits of message queuing to the application
MQCONN call . . . . . . . . . . . . 92
designer and developer . . . . . . . . . . 7
Connecting to a queue manager using the
What can you do with WebSphere MQ products? 7
MQCONNX call . . . . . . . . . . . . 94
Overview of application design . . . . . . . . 9
Disconnecting programs from a queue manager
Planning your design . . . . . . . . . . 9
using MQDISC . . . . . . . . . . . . 98
Using WebSphere MQ objects . . . . . . . 10
Opening and closing objects . . . . . . . . . 99
Designing your messages . . . . . . . . . 11
Opening objects using the MQOPEN call . . . 100
WebSphere MQ techniques . . . . . . . . 12
Creating dynamic queues . . . . . . . . 107
Application programming . . . . . . . . 14
Opening remote queues . . . . . . . . . 107
Testing WebSphere MQ applications . . . . . 16
Closing objects using the MQCLOSE call . . . 108
WebSphere MQ messages . . . . . . . . . . 16
Putting messages on a queue . . . . . . . . 109
Message descriptor . . . . . . . . . . . 17
Putting messages on a local queue using the
Types of message . . . . . . . . . . . 17
MQPUT call . . . . . . . . . . . . . 109
Format of message control information and
Putting messages on a remote queue . . . . 115
message data . . . . . . . . . . . . . 23
Setting properties of a message . . . . . . 115
Message priorities . . . . . . . . . . . 26
Controlling context information . . . . . . 115
Message properties . . . . . . . . . . . 26
Putting one message on a queue using the
Selecting messages from queues . . . . . . 31
MQPUT1 call . . . . . . . . . . . . 117
Asynchronous consumption of WebSphere MQ
Distribution lists . . . . . . . . . . . 119
messages . . . . . . . . . . . . . . 41
Some cases where the put calls fail . . . . . 124
Message groups . . . . . . . . . . . . 43
Getting messages from a queue . . . . . . . 125
Message persistence . . . . . . . . . . 44
Getting messages from a queue using the
Messages that fail to be delivered . . . . . . 45
MQGET call . . . . . . . . . . . . . 125
Messages that are backed out . . . . . . . 45
The order in which messages are retrieved from
Reply-to queue and queue manager . . . . . 46
a queue . . . . . . . . . . . . . . 131
Message context . . . . . . . . . . . . 46
Getting a particular message . . . . . . . 138
WebSphere MQ objects . . . . . . . . . . 48
Improving performance of non-persistent
Queue managers . . . . . . . . . . . 49
messages . . . . . . . . . . . . . . 140
Queue-sharing groups . . . . . . . . . . 50
Type of index . . . . . . . . . . . . 142
Queues . . . . . . . . . . . . . . . 50
Handling messages greater than 4 MB long . . 143
Administrative topic objects . . . . . . . . 58
Waiting for messages . . . . . . . . . . 149
Namelists . . . . . . . . . . . . . . 59
Signaling . . . . . . . . . . . . . . 150
Process definitions . . . . . . . . . . . 59
Skipping backout . . . . . . . . . . . 152
Authentication information objects . . . . . 59
Application data conversion . . . . . . . 154
Channels . . . . . . . . . . . . . . 59
Browsing messages on a queue . . . . . . 156
Storage classes . . . . . . . . . . . . 60
Some cases where the MQGET call fails . . . 162
Listeners . . . . . . . . . . . . . . 60
Writing data-conversion exits . . . . . . . . 163
Services . . . . . . . . . . . . . . 60

© Copyright IBM Corp. 1993, 2008 iii


Invoking the data-conversion exit . . . . . 164 IMS and IMS Bridge applications on WebSphere
Writing a data-conversion exit program . . . 165 MQ for z/OS . . . . . . . . . . . . . 323
Writing a data-conversion exit program for Writing IMS applications using WebSphere MQ 323
WebSphere MQ for i5/OS . . . . . . . . 170 Writing WebSphere MQ-IMS bridge applications 327
Writing a data-conversion exit program for Object-oriented programming with WebSphere MQ 336
WebSphere MQ for z/OS . . . . . . . . 171 What is in the WebSphere MQ Object Model? 336
Writing a data-conversion exit for WebSphere Programming language considerations . . . . 338
MQ on UNIX systems . . . . . . . . . 172
Writing a data-conversion exit for WebSphere Chapter 3. Building a WebSphere MQ
MQ for Windows . . . . . . . . . . . 178 application . . . . . . . . . . . . 339
Exit and switch load files on Windows
Building your application on AIX . . . . . . 339
operating systems . . . . . . . . . . . 179
Preparing C programs . . . . . . . . . 339
Inquiring about and setting object attributes . . . 180
Preparing COBOL programs . . . . . . . 340
Inquiring about the attributes of an object . . . 181
Preparing CICS programs . . . . . . . . 342
Some cases where the MQINQ call fails . . . 182
Building your application on HP-UX . . . . . 344
Setting queue attributes . . . . . . . . . 182
Preparing C programs . . . . . . . . . 344
Committing and backing out units of work . . . 183
Preparing COBOL programs . . . . . . . 348
Syncpoint considerations in WebSphere MQ
Preparing CICS programs . . . . . . . . 349
applications . . . . . . . . . . . . . 184
Address Space models supported by WebSphere
Syncpoints in WebSphere MQ for z/OS
MQ for HP-UX on IA64 (IPF) . . . . . . . 351
applications . . . . . . . . . . . . . 186
Building your application on Linux . . . . . . 352
Syncpoints in CICS for i5/OS applications. . . 188
Preparing C programs . . . . . . . . . 352
Syncpoints in WebSphere MQ for Windows,
Preparing COBOL programs . . . . . . . 355
WebSphere MQ for i5/OS, and WebSphere MQ
Building your application on i5/OS . . . . . . 356
on UNIX systems . . . . . . . . . . . 189
Preparing C programs . . . . . . . . . 357
Interfaces to the i5/OS external syncpoint
Preparing COBOL programs . . . . . . . 357
manager . . . . . . . . . . . . . . 193
Preparing CICS programs . . . . . . . . 358
Starting WebSphere MQ applications using triggers 195
Preparing RPG programs . . . . . . . . 359
What is triggering? . . . . . . . . . . 195
SQL programming considerations . . . . . 359
Prerequisites for triggering . . . . . . . . 199
i5/OS programming considerations . . . . . 360
Conditions for a trigger event . . . . . . . 201
Building your application on Solaris . . . . . . 360
Controlling trigger events . . . . . . . . 205
Preparing C programs . . . . . . . . . 360
Designing an application that uses triggered
Preparing COBOL programs . . . . . . . 363
queues . . . . . . . . . . . . . . 208
Preparing CICS programs . . . . . . . . 364
Trigger monitors . . . . . . . . . . . 209
Building your application on Windows systems 365
Properties of trigger messages . . . . . . . 213
Building 64-bit applications on Windows . . . 366
When triggering does not work . . . . . . 215
Preparing C programs . . . . . . . . . 366
Using and writing API exits . . . . . . . . 216
Preparing COBOL programs . . . . . . . 368
Introducing API exits . . . . . . . . . . 216
Preparing Visual Basic programs . . . . . . 370
Compiling API exits . . . . . . . . . . 218
SSPI security exit . . . . . . . . . . . 370
Reference information . . . . . . . . . 223
Building your application on z/OS . . . . . . 372
Using and writing applications on WebSphere MQ
Preparing your program to run . . . . . . 373
for z/OS . . . . . . . . . . . . . . . 269
Dynamically calling the WebSphere MQ stub 377
Environment-dependent WebSphere MQ for
Debugging your programs . . . . . . . . 382
z/OS functions . . . . . . . . . . . . 269
Using lightweight directory access protocol services
Program debugging facilities . . . . . . . 270
with WebSphere MQ for Windows . . . . . . 385
Syncpoint support . . . . . . . . . . . 270
What is a directory service? . . . . . . . 385
Recovery support . . . . . . . . . . . 271
What is LDAP? . . . . . . . . . . . . 386
The WebSphere MQ for z/OS interface with the
Using LDAP with WebSphere MQ . . . . . 386
application environment . . . . . . . . . 271
LDAP sample program . . . . . . . . . 387
Writing z/OS UNIX System Services
applications . . . . . . . . . . . . . 276
The API-crossing exit for z/OS . . . . . . 277 Chapter 4. Sample WebSphere MQ
WebSphere MQ Workflow . . . . . . . . 281 programs . . . . . . . . . . . . . 395
Application programming with shared queues 282 Sample programs (all platforms except z/OS) . . 395
Using and writing WebSphere MQ-CICS bridge Features demonstrated in the sample programs 396
applications for z/OS. . . . . . . . . . . 285 Preparing and running the sample programs 401
Distributed program link applications . . . . 286 The Put sample programs . . . . . . . . 404
3270 applications . . . . . . . . . . . 293 The Distribution List sample program . . . . 405
Information applicable to both DPL and 3270 317 The Browse sample programs . . . . . . . 406
The Browser sample program . . . . . . . 408

iv WebSphere MQ: Application Programming Guide


The Get sample programs . . . . . . . . 409 Putting a message using MQPUT . . . . . . . 530
The Reference Message sample programs . . . 410 Putting a message using MQPUT1 . . . . . . 531
The Request sample programs . . . . . . . 418 Getting a message . . . . . . . . . . . . 532
The Inquire sample programs . . . . . . . 423 Getting a message using the wait option . . . . 534
The Set sample programs . . . . . . . . 425 Getting a message using signaling . . . . . . 536
The Echo sample programs . . . . . . . . 426 Inquiring about the attributes of an object . . . . 538
The Data-Conversion sample program . . . . 427 Setting the attributes of a queue . . . . . . . 540
The Triggering sample programs . . . . . . 428
The Asynchronous Put sample program . . . 429 Chapter 7. System/390
Running the samples using remote queues . . 430 assembler-language examples . . . . 543
Database coordination samples . . . . . . 430
Connecting to a queue manager . . . . . . . 543
The CICS transaction sample . . . . . . . 437
Disconnecting from a queue manager . . . . . 544
TUXEDO samples . . . . . . . . . . . 437
Creating a dynamic queue . . . . . . . . . 545
Encina sample program . . . . . . . . . 449
Opening an existing queue . . . . . . . . . 546
Dead-letter queue handler sample . . . . . 449
Closing a queue . . . . . . . . . . . . 547
The Connect sample program . . . . . . . 450
Putting a message using MQPUT . . . . . . . 548
The API exit sample program . . . . . . . 451
Putting a message using MQPUT1 . . . . . . 549
Using the SSPI security exit on Windows
Getting a message . . . . . . . . . . . . 551
systems . . . . . . . . . . . . . . 452
Getting a message using the wait option . . . . 552
Sample programs for WebSphere MQ for z/OS . . 452
Getting a message using signaling . . . . . . 554
Features demonstrated in the sample
Inquiring about and setting the attributes of a
applications . . . . . . . . . . . . . 453
queue . . . . . . . . . . . . . . . . 556
Preparing and running sample applications for
the batch environment . . . . . . . . . 457
Preparing sample applications for the TSO Chapter 8. PL/I examples . . . . . . 559
environment . . . . . . . . . . . . . 459 Connecting to a queue manager . . . . . . . 559
Preparing the sample applications for the CICS Disconnecting from a queue manager . . . . . 560
environment . . . . . . . . . . . . . 461 Creating a dynamic queue . . . . . . . . . 560
Preparing the sample application for the IMS Opening an existing queue . . . . . . . . . 561
environment . . . . . . . . . . . . . 464 Closing a queue . . . . . . . . . . . . 562
The Put samples . . . . . . . . . . . 465 Putting a message using MQPUT . . . . . . . 563
The Get samples . . . . . . . . . . . 467 Putting a message using MQPUT1 . . . . . . 564
The Browse sample . . . . . . . . . . 470 Getting a message . . . . . . . . . . . . 565
The Print Message sample . . . . . . . . 472 Getting a message using the wait option . . . . 567
The Queue Attributes sample . . . . . . . 476 Getting a message using signaling . . . . . . 568
The Mail Manager sample . . . . . . . . 477 Inquiring about the attributes of an object . . . . 571
The Credit Check sample . . . . . . . . 485 Setting the attributes of a queue . . . . . . . 572
The Message Handler sample . . . . . . . 499
Chapter 9. WebSphere MQ data
Chapter 5. C language examples . . . 505 definition files . . . . . . . . . . . 575
Connecting to a queue manager . . . . . . . 505 C language include files . . . . . . . . . . 576
Disconnecting from a queue manager . . . . . 506 Visual Basic module files . . . . . . . . . 576
Creating a dynamic queue . . . . . . . . . 506 COBOL copy files . . . . . . . . . . . . 576
Opening an existing queue . . . . . . . . . 507 System/390 assembler-language macros . . . . 578
Closing a queue . . . . . . . . . . . . 508 PL/I include files . . . . . . . . . . . . 578
Putting a message using MQPUT . . . . . . . 509
Putting a message using MQPUT1 . . . . . . 510 Chapter 10. Coding standards on 64
Getting a message . . . . . . . . . . . . 511 bit platforms . . . . . . . . . . . . 579
Getting a message using the wait option . . . . 512 Preferred data types . . . . . . . . . . . 579
Getting a message using signaling . . . . . . 514 Standard data types . . . . . . . . . . . 579
Inquiring about the attributes of an object . . . . 516 32-bit UNIX applications . . . . . . . . 579
Setting the attributes of a queue . . . . . . . 517 64-bit UNIX applications . . . . . . . . 579
Retrieving status information with MQSTAT . . . 518 Windows 64–bit applications . . . . . . . 580

Chapter 6. COBOL examples . . . . . 525 Notices . . . . . . . . . . . . . . 583


Connecting to a queue manager . . . . . . . 525
Disconnecting from a queue manager . . . . . 526
Creating a dynamic queue . . . . . . . . . 526
Index . . . . . . . . . . . . . . . 587
Opening an existing queue . . . . . . . . . 528
Closing a queue . . . . . . . . . . . . 529 Sending your comments to IBM . . . 599

Contents v
vi WebSphere MQ: Application Programming Guide
Figures
1. Message queuing compared with traditional 30. Dynamic linking using COBOL in the IMS
communication . . . . . . . . . . . . 5 environment . . . . . . . . . . . . 379
2. Representation of a message . . . . . . . 16 31. Dynamic linking using assembler language in
3. Selection using MQSUB call . . . . . . . 33 the batch environment . . . . . . . . 380
4. Selection using MQOPEN call . . . . . . 34 32. Dynamic linking using assembler language in
5. Standard Message Driven application the CICS environment . . . . . . . . 380
consuming from two queues . . . . . . . 42 33. Dynamic linking using assembler language in
6. Single Threaded Message Driven application the IMS environment . . . . . . . . . 380
consuming from two queues . . . . . . . 43 34. Dynamic linking using C language in the
7. Group of logical messages . . . . . . . 43 batch environment . . . . . . . . . . 380
8. Segmented messages . . . . . . . . . 44 35. Dynamic linking using C language in the
9. How distribution lists work . . . . . . . 120 CICS environment . . . . . . . . . . 380
10. Opening a distribution list in C . . . . . 122 36. Dynamic linking using C language in the IMS
11. Opening a distribution list in COBOL 122 environment . . . . . . . . . . . . 381
12. Putting a message to a distribution list in C 124 37. Dynamic linking using PL/I in the batch
13. Putting a message to a distribution list in environment . . . . . . . . . . . . 381
COBOL . . . . . . . . . . . . . 124 38. Dynamic linking using PL/I in the IMS
14. Logical order on a queue . . . . . . . 132 environment . . . . . . . . . . . . 381
15. Physical order on a queue . . . . . . . 133 39. Running the Reference Message samples 412
16. Skipping backout using 40. Request and Inquire samples using triggering 420
MQGMO_MARK_SKIP_BACKOUT . . . . 153 41. Sample i5/OS Client/Server (Echo) program
17. Sample JCL used to invoke the CSQUCVX flowchart . . . . . . . . . . . . . 423
utility . . . . . . . . . . . . . . 167 42. The database coordination samples . . . . 431
18. Flow of application and trigger messages 197 43. Example of ubbstxcn.cfg file for WebSphere
19. Relationship of queues within triggering 199 MQ for Windows . . . . . . . . . . 444
20. Setting of key fields for many CICS user 44. Sample TUXEDO makefile for WebSphere
programs in a unit of work viewed from the MQ for Windows . . . . . . . . . . 445
perspective of the bridge . . . . . . . . 292 45. Example of ubbstxcn.cfg file for WebSphere
21. Setting of key fields: WebSphere MQ - MQ for Windows . . . . . . . . . . 446
pseudo-conversational 3270 transaction 46. Sample TUXEDO makefile for WebSphere
viewed from the perspective of the bridge MQ for Windows . . . . . . . . . . 447
prior to CICS TS 2.2 . . . . . . . . . 315 47. How TUXEDO samples work together 448
22. Setting of key fields: WebSphere MQ - 48. Example of a report from the Print Message
conversational 3270 transaction viewed from sample application . . . . . . . . . . 474
the perspective of the bridge . . . . . . 317 49. Programs and panels for the TSO versions of
23. User program abends (only program in the the Mail Manager . . . . . . . . . . 481
unit of work) . . . . . . . . . . . 319 50. Programs and panels for the CICS version of
24. Fragments of JCL to link-edit the object the Mail Manager . . . . . . . . . . 482
module in the batch environment, using 51. Example of a panel showing a list of waiting
single-phase commit . . . . . . . . . 374 messages . . . . . . . . . . . . . 483
25. Fragments of JCL to link-edit the object 52. Example of a panel showing the contents of a
module in the batch environment, using message . . . . . . . . . . . . . 484
two-phase commit . . . . . . . . . . 374 53. Immediate Inquiry panel for the Credit Check
26. Fragments of JCL to link-edit the object sample application . . . . . . . . . . 487
module in the CICS environment . . . . . 375 54. Programs and queues for the Credit Check
27. Fragments of JCL to link-edit the object sample application (COBOL programs only) . 489
module in the IMS environment . . . . . 376 55. Initial screen for Message Handler sample 500
28. Dynamic linking using COBOL in the batch 56. Message list screen for Message Handler
environment . . . . . . . . . . . . 379 sample . . . . . . . . . . . . . . 500
29. Dynamic linking using COBOL in the CICS 57. Chosen message is displayed . . . . . . 501
environment . . . . . . . . . . . . 379

© Copyright IBM Corp. 1993, 2008 vii


viii WebSphere MQ: Application Programming Guide
Tables
1. Boolean operator outcome when logic is A 24. Call names for dynamic linking . . . . . 377
AND B . . . . . . . . . . . . . . 40 25. CICS adapter trace entries . . . . . . . 383
2. Boolean operator outcome when logic is A OR 26. WebSphere MQ on UNIX sample programs
B . . . . . . . . . . . . . . . . 40 demonstrating use of the MQI (C and
3. Boolean operator outcome when logic is NOT COBOL) . . . . . . . . . . . . . 396
A . . . . . . . . . . . . . . . . 40 27. WebSphere MQ for Windows sample
4. The MQ_CONNECT_TYPE environment programs demonstrating use of the MQI (C
variable . . . . . . . . . . . . . . 97 and COBOL) . . . . . . . . . . . . 398
5. Resolving queue names when using 28. WebSphere MQ for Windows sample
MQOPEN . . . . . . . . . . . . . 101 programs demonstrating use of the MQI
6. How queue attributes and options of the (Visual Basic) . . . . . . . . . . . 400
MQOPEN call affect access to queues . . . 105 29. WebSphere MQ for i5/OS sample programs
7. Using message and correlation identifiers 138 demonstrating use of the MQI (C and
8. Using the group identifier . . . . . . . 139 COBOL) . . . . . . . . . . . . . 400
9. MQGET options and read ahead . . . . . 141 30. Where to find the samples for WebSphere
10. Skeleton source files . . . . . . . . . 166 MQ on UNIX systems . . . . . . . . 402
11. MQXR_BEFORE exit processing . . . . . 228 31. Where to find the samples for WebSphere
12. Valid combinations of function identifiers and MQ for Windows . . . . . . . . . . 402
ExitReasons . . . . . . . . . . . . 236 32. Source for the distributed queuing exit
13. API exit errors and appropriate actions to samples . . . . . . . . . . . . . 457
take . . . . . . . . . . . . . . . 265 33. Source for the data conversion exit samples
14. z/OS environmental features . . . . . . 270 (assembler language only) . . . . . . . 457
15. When to use a shared-initiation queue 285 34. Batch Put and Get samples . . . . . . . 458
16. Mapping WebSphere MQ messages to IMS 35. Batch Browse sample . . . . . . . . . 458
transaction types . . . . . . . . . . 328 36. Batch Print Message sample (C language
17. Essential code for CICS applications (AIX) 342 only) . . . . . . . . . . . . . . 459
18. Essential code for CICS applications (HP-UX) 350 37. TSO Mail Manager sample . . . . . . . 460
19. Example of CRTPGM in the nonthreaded 38. TSO Message Handler sample . . . . . . 460
environment . . . . . . . . . . . . 357 39. CICS Put and Get samples . . . . . . . 462
20. Example of CRTPGM in the threaded 40. CICS Queue Attributes sample . . . . . . 462
environment . . . . . . . . . . . . 357 41. CICS Mail Manager sample (COBOL only) 463
21. Essential code for CICS applications (Solaris) 364 42. CICS Credit Check sample . . . . . . . 463
22. Location of WebSphere MQ libraries . . . . 366 43. Source and JCL for the Credit Check IMS
23. Context initiators and their associated context sample (C only) . . . . . . . . . . . 465
acceptors . . . . . . . . . . . . . 371

© Copyright IBM Corp. 1993, 2008 ix


x WebSphere MQ: Application Programming Guide
Chapter 1. Designing applications that use WebSphere MQ
Introduction to message queuing
The WebSphere® MQ products enable programs to communicate with one another
across a network of unlike components (processors, operating systems, subsystems,
and communication protocols) using a consistent application programming
interface.

Applications designed and written using this interface are known as message
queuing applications, because they use the messaging and queuing style:

Messaging Programs communicate by sending each other data in messages rather


than calling each other directly.
Queuing Messages are placed on queues in storage, allowing programs to run
independently of each other, at different speeds and times, in different
locations, and without having a logical connection between them.

This chapter introduces messaging and queuing concepts, under these headings:
v “What is message queuing?”
v “What is a message?” on page 2
v “What is a message queue?” on page 2
v “What is a queue manager?” on page 3
v “What is a cluster?” on page 3
v “What is a WebSphere MQ client?” on page 4
v “Main features of message queuing” on page 4
v “Benefits of message queuing to the application designer and developer” on
page 7
v “What can you do with WebSphere MQ products?” on page 7

What is message queuing?


Message queuing has been used in data processing for many years. It is most
commonly used today in electronic mail. Without queuing, sending an electronic
message over long distances requires every node on the route to be available for
forwarding messages, and the addressees to be logged on and conscious of the fact
that you are trying to send them a message. In a queuing system, messages are
stored at intermediate nodes until the system is ready to forward them. At their
final destination they are stored in an electronic mailbox until the addressee is
ready to read them.

Even so, many complex business transactions are processed today without
queuing. In a large network, the system might be maintaining many thousands of
connections in a ready-to-use state. If one part of the system suffers a problem,
many parts of the system become unusable.

You can think of message queuing as being electronic mail for programs. In a
message queuing environment, each program from the set that makes up an
application suite is designed to perform a well-defined, self-contained function in
response to a specific request. To communicate with another program, a program

© Copyright IBM Corp. 1993, 2008 1


must put a message on a predefined queue. The other program retrieves the
message from the queue, and processes the requests and information contained in
the message. So message queuing is a style of program-to-program communication.

Queuing is the mechanism by which messages are held until an application is


ready to process them. Queuing allows you to:
v Communicate between programs (which might each be running in different
environments) without having to write the communication code.
v Select the order in which a program processes messages.
v Balance loads on a system by arranging for more than one program to service a
queue when the number of messages exceeds a threshold.
v Increase the availability of your applications by arranging for an alternative
system to service the queues if your primary system is unavailable.

What is a message?
In message queuing, a message is a collection of data sent by one program and
intended for another program.

WebSphere MQ defines four types of message:

Datagram A simple message for which no reply is expected


Request A message for which a reply is expected
Reply A reply to a request message
Report A message that describes an event such as the occurrence of an
error

See “Types of message” on page 17 for more information about these message
types.

Message descriptor
A WebSphere MQ message consists of control information and application data.

The control information is defined in a message descriptor structure (MQMD) and


contains such things as:
v The type of the message
v An identifier for the message
v The priority for delivery of the message
The structure and content of the application data is determined by the
participating programs, not by WebSphere MQ.

Message channel agent


A message channel agent moves messages from one queue manager to another.

References are made to them in this book when dealing with report messages and
you will need to consider them when designing your application. See WebSphere
MQ Intercommunications for more information.

What is a message queue?


A message queue, known simply as a queue, is a named destination to which
messages can be sent. Messages accumulate on queues until they are retrieved by
programs that service those queues.

2 WebSphere MQ: Application Programming Guide


Queues reside in, and are managed by, a queue manager (see “What is a queue
manager?”). The physical nature of a queue depends on the operating system on
which the queue manager is running. A queue can either be a volatile buffer area
in the memory of a computer, or a data set on a permanent storage device (such as
a disk). The physical management of queues is the responsibility of the queue
manager and is not made apparent to the participating application programs.

Programs access queues only through the external services of the queue manager.
They can open a queue, put messages on it, get messages from it, and close the
queue. They can also set, and inquire about, the attributes of queues.

What is a queue manager?


A queue manager is a system program that provides queuing services to
applications.

It provides an application programming interface so that programs can put


messages on, and get messages from, queues. A queue manager provides
additional functions so that administrators can create new queues, alter the
properties of existing queues, and control the operation of the queue manager.

For WebSphere MQ message queuing services to be available on a system, there


must be a queue manager running. You can have more than one queue manager
running on a single system (for example, to separate a test system from a live
system). To an application, each queue manager is identified by a connection handle
(Hconn).

Many different applications can use the queue manager’s services at the same time
and these applications can be entirely unrelated. For a program to use the services
of a queue manager, it must establish a connection to that queue manager.

For applications to send messages to applications that are connected to other queue
managers, the queue managers must be able to communicate among themselves.
WebSphere MQ implements a store-and-forward protocol to ensure the safe delivery
of messages between such applications.

What is a cluster?
A cluster is a network of queue managers that are logically associated in some way.
Clustering is available to queue managers on all WebSphere MQ V7.0 platforms.

In a WebSphere MQ network using distributed queuing without clustering, every


queue manager is independent. If one queue manager needs to send messages to
another it must have defined a transmission queue and a channel to the remote
queue manager.

If you group queue managers in a cluster, the queue managers can make the
queues that they host available to every other queue manager in the cluster. Then,
assuming that you have the necessary network infrastructure in place, any queue
manager can send a message to any other queue manager in the same cluster
without the need for explicit channel definitions, remote queue definitions, or
transmission queues.

There are two different reasons for using clusters: to reduce system administration
and to improve availability and workload balancing.

Chapter 1. Designing applications that use WebSphere MQ 3


As soon as you establish even the smallest cluster you will benefit from simplified
system administration. Queue managers that are part of a cluster need fewer
definitions and so the risk of making an error in your definitions is reduced.

For details of all aspects of clustering, see WebSphere MQ Queue Manager


Clusters.

What is a shared queue, a queue-sharing group, and


intra-group queuing?
Shared queues, queue-sharing groups, and intra-group queuing are available
only on WebSphere MQ for z/OS®.

A shared queue is a type of local queue whose messages can be accessed by one or
more queue managers that are in a sysplex. (This is not the same as a queue being
shared by more than one application, using the same queue manager.)

The queue managers that can access the same set of shared queues form a group
called a queue-sharing group (QSG). They communicate with each other by means of
a coupling facility (CF) that stores the shared queues. See the WebSphere MQ for
z/OS Concepts and Planning Guide for a full discussion of queue-sharing groups.

Queue managers in a queue-sharing group can communicate using normal


channels or you can use a technique called intra-group queuing (IGQ), which lets
you perform fast message transfer without defining channels.

What is a WebSphere MQ client?


WebSphere MQ clients are independently installable components of WebSphere MQ
products. A client allows you to run WebSphere MQ applications, by means of a
communications protocol, to interact with one or more Message Queue Interface
(MQI) servers on other platforms and to connect to their queue managers.

For full details on how to install and use WebSphere MQ client components, see
WebSphere MQ Clients.

What is publish/subscribe?
Publish/subscribe messaging allows you to decouple the provider of information
from the consumers of that information. The sending application (publisher) and
receiving application (subscriber) do not need to know anything about each other
for the information to be sent and received.

Main features of message queuing


The main features of applications that use message queuing techniques are:
v There are no direct connections between programs.
v Communication between programs can be time-independent.
v Work can be carried out by small, self-contained programs.
v Communication can be driven by events.
v Applications can assign a priority to a message.
v Security.
v Data integrity.
v Recovery support.

4 WebSphere MQ: Application Programming Guide


No direct connections between programs
Message queuing is a technique for indirect program-to-program
communication. It can be used within any application where programs
communicate with each other. Communication occurs by one program
putting messages on a queue (owned by a queue manager) and another
program getting the messages from the queue.
Programs can get messages that were put on a queue by other programs.
The other programs can be connected to the same queue manager as the
receiving program, or to another queue manager. This other queue
manager might be on another system, a different computer system, or even
within a different business or enterprise.
There are no physical connections between programs that communicate
using message queues. A program sends messages to a queue owned by a
queue manager, and another program retrieves messages from the queue
(see Figure 1).

Traditional communication between programs

Program A Program B

Comms code Comms code

Networking software

Communication by message queuing

Program A Program B

WebSphere MQ
comms code
(Queue Manager)

Networking software

Figure 1. Message queuing compared with traditional communication

As with electronic mail, the individual messages that are part of a


transaction travel through a network on a store-and-forward basis. If a link
between nodes fails, the message is kept until the link is restored, or the
operator or program redirects the message.
The mechanism by which a message moves from queue to queue is hidden
from the programs. Therefore the programs are simpler.
Time-independent communication
Programs requesting others to do work do not have to wait for the reply to
a request. They can do other work, and process the reply either when it
arrives or at a later time. When writing a messaging application, you need
not know (or be concerned) when a program sends a message, or when the
target is able to receive the message. The message is not lost; it is retained

Chapter 1. Designing applications that use WebSphere MQ 5


by the queue manager until the target is ready to process it. The message
stays on the queue until it is removed by a program.
Small programs
Message queuing allows you to exploit the advantages of using small,
self-contained programs. Instead of a single, large program performing all
the parts of a job sequentially, you can spread the job over several smaller,
independent programs. The requesting program sends messages to each of
the separate programs, asking them to perform their function; when each
program is complete, the results are sent back as one or more messages.
Event-driven processing
Programs can be controlled according to the state of queues. For example,
you can arrange for a program to start as soon as a message arrives on a
queue, or you can specify that the program does not start until there are,
for example, 10 messages above a certain priority on the queue, or 10
messages of any priority on the queue.
Message priority
A program can assign a priority to a message when it puts the message on
a queue. This determines the position in the queue at which the new
message is added.
Programs can get messages from a queue either in the order in which the
messages appear in the queue, or by getting a specific message. (A
program might want to get a specific message if it is looking for the reply
to a request that it sent earlier.)
Security
Authorization checks are carried out on each resource, using the tables that
are set up and maintained by the WebSphere MQ administrator.
v Use Security Server (formerly known as RACF®) or other external
security managers on WebSphere MQ for z/OS.
v On WebSphere MQ on UNIX® systems, Windows® systems, and i5/OS®,
a security manager called the Object Authority Manager (OAM) is
provided as an installable service. By default, the OAM is active.
Data integrity
Data integrity is provided by units of work. The synchronization of the
start and end of units of work is fully supported as an option on each
MQGET or MQPUT, allowing the results of the unit of work to be
committed or rolled back. Syncpoint support operates either internally or
externally to WebSphere MQ depending on the form of syncpoint
coordination selected for the application.
Recovery support
For recovery to be possible, all persistent WebSphere MQ updates are
logged. In the event that recovery is necessary, all persistent messages are
restored, all in-flight transactions are rolled back, and any syncpoint
commit and backouts are handled in the normal way of the syncpoint
manager in control. For more information on persistent messages, see
“Message persistence” on page 44.

WebSphere MQ clients and servers


You do not have to change a server application to support additional WebSphere
MQ clients on new platforms.

Similarly, the WebSphere MQ client can, without change, function with additional
types of server. See WebSphere MQ Clients for more information.

6 WebSphere MQ: Application Programming Guide


Benefits of message queuing to the application designer and
developer
Some of the benefits of message queuing are:
v You can design applications using small programs that you can share between
many applications.
v You can quickly build new applications by reusing these building blocks.
v Applications written to use message queuing techniques are not affected by
changes in the way that queue managers work.
v You do not need to use any communication protocols. The queue manager deals
with all aspects of communication for you.
v Programs that receive messages need not be running at the time that messages
are sent to them. The messages are retained on queues.

Designers can reduce the cost of their applications because development is faster,
fewer developers are needed, and demands on programming skill are lower than
those for applications that do not use message queuing.

What can you do with WebSphere MQ products?


WebSphere MQ products are queue managers and application enablers. They
support the IBM® Message Queue Interface (MQI) through which programs can
put messages on a queue and get messages from a queue.

WebSphere MQ for z/OS


With WebSphere MQ for z/OS you can write applications that:
v Use message queuing within CICS® or IMS™.
v Send messages between batch, CICS, and IMS applications, selecting the most
appropriate environment for each function.
v Send messages to applications that run on other WebSphere MQ platforms.
v Process several messages together as a single unit of work that can be
committed or backed out.
v Send messages to, and interact with, IMS applications by means of the IMS
bridge.
v Participate in units of work coordinated by RRS.

Each environment within z/OS has its own characteristics, advantages, and
disadvantages. The advantage of WebSphere MQ for z/OS is that applications are
not tied to any one environment, but can be distributed to take advantage of the
benefits of each environment. For example, you can develop end-user interfaces
using TSO or CICS, you can run processing-intensive modules in z/OS batch, and
you can run database applications in IMS or CICS. In all cases, the various parts of
the application can communicate using messages and queues.

Designers of WebSphere MQ applications must be aware of the differences and


limitations imposed by these environments. For example:
v WebSphere MQ provides facilities that allow intercommunication between queue
managers (this is known as distributed queuing).
v Methods of committing and backing out changes differ between the batch and
CICS environments.

Chapter 1. Designing applications that use WebSphere MQ 7


v WebSphere MQ for z/OS provides support in the IMS environment for online
message processing programs (MPPs), interactive fast path programs (IFPs), and
batch message processing programs (BMPs). If you are writing batch DL/I
programs, follow the guidance given in this book for z/OS batch programs.
v Although multiple instances of WebSphere MQ for z/OS can exist on a single
z/OS system, a CICS region can connect to only one queue manager at a time.
However, more than one CICS region can be connected to the same queue
manager. In the IMS and z/OS batch environments, programs can connect to
more than one queue manager.
v WebSphere MQ for z/OS allows local queues to be shared by a group of queue
managers, giving improved throughput and availability. Such queues are called
shared queues, and the queue managers form a queue-sharing group, which can
process messages on the same shared queues. Batch applications can connect to
one of several queue managers within a queue-sharing group by specifying the
queue-sharing group name, instead of a particular queue manager name. This is
known as group batch attach, or more simply group attach. See the WebSphere MQ
for z/OS Concepts and Planning Guide for a full discussion of queue-sharing
groups.

The differences between the supported environments, and their limitations, are
discussed further in “Using and writing applications on WebSphere MQ for z/OS”
on page 269.

WebSphere MQ for non-z/OS platforms


With WebSphere MQ for non-z/OS platforms you can write applications that:
v Send messages to other applications running under the same operating systems.
The applications can be on either the same or another system.
v Send messages to applications that run on other WebSphere MQ platforms.
v Use message queuing from within CICS for i5/OS, TXSeries® for AIX®, TXSeries
for HP-UX, TXSeries for Solaris, and TXSeries for Windows systems applications.
v Use message queuing from within Encina® for AIX, HP-UX, Solaris, and
Windows systems.
v Use message queuing from within Tuxedo for AIX, AT&T, HP-UX, Solaris, and
Windows systems.
v Use WebSphere MQ as a transaction manager, coordinating updates made by
external resource managers within WebSphere MQ units of work. The following
external resource managers are supported and comply with the X/OPEN XA
interface
– DB2®
– Informix®
– Oracle
– Sybase
v Process several messages together as a single unit of work that can be
committed or backed out.
v Run from a full WebSphere MQ environment, or run from a WebSphere MQ
client environment on the following platforms:
– i5/OS (Java™ client only)
– UNIX systems
– VM/ESA®
– Windows 2000, Windows 2003, or Windows XP

8 WebSphere MQ: Application Programming Guide


Overview of application design
This chapter introduces the design of WebSphere MQ applications, under these
headings:
v “Planning your design”
v “Using WebSphere MQ objects” on page 10
v “Designing your messages” on page 11
v “WebSphere MQ techniques” on page 12
v “Application programming” on page 14
v “Testing WebSphere MQ applications” on page 16

These subjects are discussed in greater detail in the remaining chapters of this
book.

Planning your design


When you have decided how your applications can take advantage of the
platforms and environments available to you, you need to decide how to use the
features offered by WebSphere MQ.

Some of the key aspects are:


What types of queue should you use?
Do you want to create a queue each time that you need one, or do you
want to use queues that have already been set up? Do you want to delete
a queue when you have finished using it, or is it going to be used again?
Do you want to use alias queues for application independence? To see
what types of queues are supported, refer to “Queues” on page 50.
Should you use shared queues and queue-sharing groups (WebSphere MQ for
z/OS only)?
You might want to take advantage of the increased availability, scalability,
and workload balancing that are possible when you use shared queues
with queue-sharing groups. See the WebSphere MQ for z/OS Concepts and
Planning Guide for a full discussion of this topic.
Should you use queue manager clusters?
You might want to take advantage of the simplified system administration,
and increased availability, scalability, and workload balancing that are
possible when you use clusters. See WebSphere MQ Queue Manager Clusters
for a full discussion of this topic.
What types of message should you use?
You might want to use datagrams for simple messages, but request
messages (for which you expect replies) for other situations. You might
want to assign different priorities to some of your messages.
Should you use publish/subscribe or point-to-point messaging?
Using publish/subscribe messaging, a sending application sends the
information that it wants to share in a WebSphere MQ message to a
standard destination managed by WebSphere MQ publish/subscribe, and
lets WebSphere MQ handle the distribution of that information. The target
application does not have to know anything about the source of the
information it receives, it just registers an interest in one or more topics
and receives that information when it is available. For more information
about publish/subscribe messaging, see WebSphere MQ Publish/Subscribe
User’s Guide.

Chapter 1. Designing applications that use WebSphere MQ 9


Using point-to-point messaging, a sending application sends a message to
a specific queue, from where it knows a receiving application will retrieve
it. A receiving application gets messages from a specific queue and acts on
their contents. An application will often function both as a sender and a
receiver, sending a query to another application and receiving a response.
How can you control your WebSphere MQ programs?
You might want to start some programs automatically or make programs
wait until a particular message arrives on a queue (using the WebSphere
MQ triggering feature, see “Starting WebSphere MQ applications using
triggers” on page 195). Alternatively, you might want to start up another
instance of an application when the messages on a queue are not getting
processed fast enough (using the WebSphere MQ instrumentation events
feature as described in WebSphere MQ Monitoring).
Will your application run on a WebSphere MQ client?
The full MQI is supported in the client environment and this enables
almost any WebSphere MQ application to be relinked to run on a
WebSphere MQ client. Link the application on the WebSphere MQ client to
the MQIC library, rather than to the MQI library. Get(signal) on z/OS is
not supported.

Note: An application running on a WebSphere MQ client can connect to


more than one queue manager concurrently, or use a queue manager name
with an asterisk (*) on an MQCONN or MQCONNX call. Change the
application if you want to link to the queue manager libraries instead of
the client libraries, as this function will not be available.
See WebSphere MQ Clients for more information.
How can you secure your data and maintain its integrity?
You can use the context information that is passed with a message to test
that the message has been sent from an acceptable source. You can use the
syncpointing facilities provided by WebSphere MQ or your operating
system to ensure that your data remains consistent with other resources
(see “Committing and backing out units of work” on page 183 for further
details). You can use the persistence feature of WebSphere MQ messages to
assure the delivery of important messages.
How should you handle exceptions and errors?
You need to consider how to process messages that cannot be delivered,
and how to resolve error situations that are reported to you by the queue
manager. For some reports, you must set report options on MQPUT.

The remainder of this chapter introduces the features and techniques that
WebSphere MQ provides to help you answer questions like these.

Using WebSphere MQ objects


The MQI uses the following types of object:
v Queue managers
v Queues
v Administrative topic objects
v Namelists
v Services
v Listeners

10 WebSphere MQ: Application Programming Guide


v Process definitions
v Channels
v Storage classes (WebSphere MQ for z/OS only)
v Authentication information objects

These objects, and queue-sharing groups (which are only supported on WebSphere
MQ for z/OS and which are not strictly objects), are discussed in “WebSphere MQ
objects” on page 48.

With the exception of dynamic queues, these objects must be defined to the queue
manager before you can work with them.

You define objects using:


v The PCF commands described in WebSphere MQ Programmable Command Formats
and Administration Interface
v The MQSC commands described in WebSphere MQ Script (MQSC) Command
Reference
v The WebSphere MQ for z/OS operations and control panels, described in the
WebSphere MQ for z/OS System Administration Guide
v The WebSphere MQ Explorer (Windows, UNIX, and Linux® for Intel® systems
only)

You can also display or alter the attributes of objects, or delete the objects.

Alternatively, for sequences of WebSphere MQ for z/OS commands that you use
regularly, you can write administration programs that create messages containing
commands and that put these messages on the system-command input queue. The
queue manager processes the messages on this queue in the same way that it
processes commands entered from the command line or from the operations and
control panels. This technique is described in the z/OS System Administration Guide,
and demonstrated in the Mail Manager sample application delivered with
WebSphere MQ for z/OS. For a description of this sample, see “Sample programs
for WebSphere MQ for z/OS” on page 452.

For sequences of WebSphere MQ for i5/OS commands that you use regularly you
can write CL programs.

For sequences of WebSphere MQ commands on Windows systems and UNIX


systems, you can use the MQSC facility to run a series of commands held in a file.
For information on how to do this, see the WebSphere MQ Script (MQSC) Command
Reference.

Designing your messages


Ask yourself these questions to help you to design the messages.

You create a message when you use an MQI call to put the message on a queue.
As input to the call, you supply some control information in a message descriptor
(MQMD) and the data that you want to send to another program. But at the
design stage, you need to consider the following questions, because they affect the
way that you create your messages:
What type of message should I use?
Are you designing a simple application in which you can send a message,
then take no further action? Or are you asking for a reply to a question? If

Chapter 1. Designing applications that use WebSphere MQ 11


you are asking a question, you might include in the message descriptor the
name of the queue on which you want to receive the reply.
Do you want your request and reply messages to be synchronous? This
implies that you set a timeout period for the reply to answer your request,
and if you do not receive the reply within that period, it is treated as an
error.
Or would you prefer to work asynchronously, so that your processes do
not have to depend upon the occurrence of specific events, such as
common timing signals?
Another consideration is whether you have all your messages inside a unit
of work.
Should I assign different priorities to some of the messages that I create?
You can assign a priority value to each message, and define the queue so
that it maintains its messages in order of their priority. If you do this,
when another program retrieves a message from the queue, it always gets
the message with the highest priority. If the queue does not maintain its
messages in priority order, a program that retrieves messages from the
queue will retrieve them in the order in which they were added to the
queue.
Programs can also select a message using the identifier that the queue
manager assigned when the message was put on the queue. Alternatively,
you can generate your own identifiers for each of your messages.
Will my messages be discarded when the queue manager restarts?
The queue manager preserves all persistent messages, recovering them
when necessary from the WebSphere MQ log files, when it is restarted.
Nonpersistent messages and temporary dynamic queues are not preserved.
Any messages that you do not want discarded must be defined as
persistent when they are created. When writing an application for
WebSphere MQ for Windows or WebSphere MQ on UNIX systems, make
sure that you know how your system has been set up in respect of log file
allocation to reduce the risk of designing an application that will run to the
log file limits.
Because messages on shared queues (only available on WebSphere MQ for
z/OS) are held in the Coupling Facility (CF), nonpersistent messages are
preserved across restarts of a queue manager as long as the CF remains
available. If the CF fails, nonpersistent messages are lost.
Do I want to give information about myself to the recipient of my messages?
Usually, the queue manager sets the user ID, but suitably authorized
applications can also set this field, so that you can include your own user
ID and other information that the receiving program can use for
accounting or security purposes.
How many queues will receive my messages?
If a message might need to be put on several queues, you can use a
distribution list (not on z/OS), or publish to a topic.

WebSphere MQ techniques
For a simple WebSphere MQ application, you need to decide which WebSphere
MQ objects to use in your application, and which types of message you want to
use. For a more advanced application, you might want to use some of the
techniques introduced in the following sections.

12 WebSphere MQ: Application Programming Guide


Waiting for messages
A program that is serving a queue can await messages by:
v Waiting until either a message arrives, or a specified time interval expires (see
“Waiting for messages” on page 149).
v Setting a signal so that the program is informed when a message arrives
(WebSphere MQ for z/OS only). For information about this, see “Signaling” on
page 150.
v Establish a call back exit to be driven when a message arrives; see
“Asynchronous consumption of WebSphere MQ messages” on page 41.
v Making periodic calls on the queue to see whether a message has arrived
(polling). This is not recommended because of the extra overhead.

Correlating replies
In WebSphere MQ applications, when a program receives a message that asks it to
do some work, the program usually sends one or more reply messages to the
requester.

To help the requester to associate these replies with its original request, an
application can set a correlation identifier field in the descriptor of each message.
Programs then copy the message identifier of the request message into the
correlation identifier field of their reply messages.

Setting and using context information


Context information is used for associating messages with the user who generated
them, and for identifying the application that generated the message. Such
information is useful for security, accounting, auditing, and problem determination.

When you create a message, you can specify an option that requests that the queue
manager associates default context information with your message.

For more information on using and setting context information, see “Message
context” on page 46.

Starting WebSphere MQ programs automatically


Use WebSphere MQ triggering to start a program automatically when messages
arrive on a queue.

You can set trigger conditions on a queue so that a program starts to process that
queue:
v Every time that a message arrives on the queue
v When the first message arrives on the queue
v When the number of messages on the queue reaches a predefined number

For more information on triggering, see “Starting WebSphere MQ applications


using triggers” on page 195. Triggering is just one way of starting a program
automatically. For example, you can start a program automatically on a timer using
non-WebSphere MQ facilities.

On platforms other than z/OS, WebSphere MQ can define service objects to start
WebSphere MQ programs when the queue manager starts; see WebSphere MQ
Migration Information.

Chapter 1. Designing applications that use WebSphere MQ 13


Generating WebSphere MQ reports
You can request the following reports within an application:
v Exception reports
v Expiry reports
v Confirm-on-arrival (COA) reports
v Confirm-on-delivery (COD) reports
v Positive action notification (PAN) reports
v Negative action notification (NAN) reports

These are described in “Report messages” on page 19.

Clusters and message affinities


Before starting to use clusters with multiple definitions for the same queue,
examine your applications to see whether there are any that require an exchange of
related messages.

Within a cluster, a message can be routed to any queue manager that hosts an
instance of the appropriate queue. Therefore, the logic of applications with
message affinities can be upset.

For example, you might have two applications that rely on a series of messages
flowing between them in the form of questions and answers. It might be important
that all the questions are sent to the same queue manager and that all the answers
are sent back to the other queue manager. In this situation, it is important that the
workload management routine does not send the messages to any queue manager
that just happens to host an instance of the appropriate queue.

Where possible, remove the affinities. Removing message affinities improves the
availability and scalability of applications.

For more information see WebSphere MQ Queue Manager Clusters.

Application programming
WebSphere MQ supports the IBM Message Queue Interface (MQI). The MQI
includes a set of calls with which you can send and receive messages, and
manipulate WebSphere MQ objects.

Call interface
Use MQI calls to:
v Connect programs to, and disconnect programs from, a queue manager.
v Open and close objects (such as queues, queue managers, namelists, and
processes).
v Put messages on queues and topics.
v Receive messages from a queue, or browse them (leaving them on the queue).
v Subscribe to topics.
v Inquire about the attributes (or properties) of WebSphere MQ objects, and set
some of the attributes of queues.
v Commit and back out changes made within a unit of work, in environments
where there is no natural syncpoint support, for example, UNIX systems.

14 WebSphere MQ: Application Programming Guide


v Coordinate queue manager updates and updates made by other resource
managers.

The MQI provides structures (groups of fields) with which you supply input to,
and get output from, the calls. It also provides a large set of named constants to
help you supply options in the parameters of the calls. The definitions of the calls,
structures, and named constants are supplied in data definition files for each of the
supported programming languages. Also, default values are set within the MQI
calls.

Design for performance: hints and tips


Here are a few ideas to help you to design efficient applications:
v Design your application so that processing goes on in parallel with a user’s
thinking time:
– Display a panel and allow the user to start typing while the application is still
initializing.
– Get the data that you need in parallel from different servers.
v Keep connections and queues open if you are going to reuse them instead of
repeatedly opening and closing, connecting and disconnecting.
v However, a server application that is putting only one message should use
MQPUT1.
v Queue managers are optimized for messages between 4 KB and 100 KB in size.
Very large messages are inefficient; it is probably better to send 100 messages of
1 MB each than a single 100 MB message. Very small messages are also
inefficient. The queue manager does the same amount of work for a single-byte
message as for a 4 KB message.
v Keep your messages within a unit of work, so that they can be committed or
backed out simultaneously.
v Use the nonpersistent option for messages that do not need to be recoverable.
v If you need to send a message to a number of target queues, consider using a
distribution list.

Programming platforms
For details of supported programming platforms, refer to the product
announcements at
http://www.ibm.com/software/integration/wmq/requirements

Applications for more than one platform


Will your application run on more than one platform? Do you have a strategy to
move to a different platform from the one that you use today? If the answer to
either of these questions is yes, ensure that you code your programs for platform
independence.

If you are using C, code in ANSI standard C. Use a standard C library function
rather than an equivalent platform-specific function even if the platform-specific
function is faster or more efficient. The exception is when efficiency in the code is
paramount, when you should code for both situations using #ifdef. For example:
#ifdef _AIX
AIX specific code
#else
generic code
#endif

Chapter 1. Designing applications that use WebSphere MQ 15


When you want to move the code to another platform, search the source for #ifdef
with the platform specific identifiers, in this example _AIX, and add or change
code as necessary.

Keep portable code in separate source files from the platform-specific code, and
use a simple naming convention to split the categories.

Testing WebSphere MQ applications


The application development environment for WebSphere MQ programs is no
different from that for any other application, so you can use the same development
tools as well as the WebSphere MQ trace facilities.

When testing CICS applications with WebSphere MQ for z/OS, you can use the
CICS Execution Diagnostic Facility (CEDF). CEDF traps the entry and exit of every
MQI call as well as calls to all CICS services. Also, in the CICS environment, you
can write an API-crossing exit program to provide diagnostic information before
and after every MQI call. For information on how to do this, see “Using and
writing applications on WebSphere MQ for z/OS” on page 269.

When testing i5/OS applications, you can use the standard Debugger. To start this,
use the STRDBG command.

WebSphere MQ messages
WebSphere MQ messages are made up of two parts:
v Message properties
v Application data
Figure 2 represents a message and shows how it is logically divided into message
properties and application data.

Message properties Application data

Message description
(MQMD)

Message ID ARM correlator Address


Persistence ... Customer number Claim details ...

Figure 2. Representation of a message

The application data carried in a WebSphere MQ message is not changed by a


queue manager unless data conversion is carried out on it. Also, WebSphere MQ
does not put any restrictions on the content of this data. The length of the data in
each message cannot exceed the value of the MaxMsgLength attribute of both the
queue and queue manager.

On WebSphere MQ for AIX, WebSphere MQ for i5/OS, WebSphere MQ for HP-UX,


WebSphere MQ for Linux, WebSphere MQ for Solaris, and WebSphere MQ for
Windows, the MaxMsgLength defaults to 100 MB (104 857 600 bytes).

16 WebSphere MQ: Application Programming Guide


Note: If you are intending to use WebSphere MQ messages greater than 15 MB on
i5/OS, see “Building your application on i5/OS” on page 356.

On WebSphere MQ for z/OS, the MaxMsgLength attribute of the queue manager is


fixed at 100 MB and the MaxMsgLength attribute of the queue defaults to 4 MB (4
194 304 bytes) which you can change up to a maximum of 100 MB if required.

Make your messages slightly shorter than the value of the MaxMsgLength attribute
in some circumstances. See “The data in your message” on page 113 for more
information.

You create a message when you use the MQPUT or MQPUT1 MQI calls. As input
to these calls, you supply the control information (such as the priority of the
message and the name of a reply queue) and your data , and the call then puts the
message on a queue. See the WebSphere MQ Application Programming Reference for
more information on these calls.

This chapter introduces WebSphere MQ messages, under these headings:


v “Message descriptor”
v “Types of message”
v “Format of message control information and message data” on page 23
v “Message priorities” on page 26
v “Message properties and message length” on page 26
v “Property names” on page 28
v “Message groups” on page 43
v “Message persistence” on page 44
v “Getting a specific message using MsgId and CorrelId” on page 31
v “Messages that fail to be delivered” on page 45
v “Messages that are backed out” on page 45
v “Reply-to queue and queue manager” on page 46
v “Message context” on page 46

Message descriptor
You can access message control information using the MQMD structure, which
defines the message descriptor.

For a full description of the MQMD structure, see the WebSphere MQ Application
Programming Reference.

See “Message context” on page 46 for a description of how to use the fields within
the MQMD that contain information about the origin of the message.

There are different versions of the message descriptor. Additional information for
grouping and segmenting messages (see “Message groups” on page 43) is
provided in Version 2 of the message descriptor (or the MQMDE). This is the same
as the Version 1 message descriptor but has additional fields. These are described
in the WebSphere MQ Application Programming Reference.

Types of message
There are four types of message defined by WebSphere MQ:
v Datagram

Chapter 1. Designing applications that use WebSphere MQ 17


v Request
v Reply
v Report

Applications can use the first three types of messages to pass information between
themselves. The fourth type, report, is for applications and queue managers to use
to report information about events such as the occurrence of an error.

Each type of message is identified by an MQMT_* value. You can also define your
own types of message. For the range of values you can use, see the description of
the MsgType field in the WebSphere MQ Application Programming Reference.

Datagrams
Use a datagram when you do not require a reply from the application that receives
the message (that is, gets the message from the queue).

An example of an application that could use datagrams is one that displays flight
information in an airport lounge. A message could contain the data for a whole
screen of flight information. Such an application is unlikely to request an
acknowledgement for a message because it probably does not matter if a message
is not delivered. The application sends an update message after a short period of
time.

Request messages
Use a request message when you want a reply from the application that receives the
message.

An example of an application that could use request messages is one that displays
the balance of a checking account. The request message could contain the number
of the account, and the reply message would contain the account balance.

If you want to link your reply message with your request message, there are two
options:
v Make the application that handles the request message responsible for ensuring
that it puts information into the reply message that relates to the request
message.
v Use the report field in the message descriptor of your request message to specify
the content of the MsgId and CorrelId fields of the reply message:
– You can request that either the MsgId or the CorrelId of the original message
is to be copied into the CorrelId field of the reply message (the default action
is to copy MsgId).
– You can request that either a new MsgId is generated for the reply message, or
that the MsgId of the original message is to be copied into the MsgId field of
the reply message (the default action is to generate a new message identifier).

Reply messages
Use a reply message when you reply to another message.

When you create a reply message, respect any options that were set in the message
descriptor of the message to which you are replying. Report options specify the
content of the message identifier (MsgId) and correlation identifier (CorrelId) fields.
These fields allow the application that receives the reply to correlate the reply with
its original request.

18 WebSphere MQ: Application Programming Guide


Report messages
Report messages inform applications about events such as the occurrence of an error
when processing a message.

They can be generated by:


v A queue manager,
v A message channel agent (for example, if they cannot deliver the message), or
v An application (for example, if it cannot use the data in the message).

Report messages can be generated at any time, and might arrive on a queue when
your application is not expecting them.

Types of report message:

When you put a message on a queue, you can select to receive:


v An exception report message. This is sent in response to a message with the
exceptions flag set. It is generated by the message channel agent (MCA) or the
application.
v An expiry report message. This indicates that an application attempted to retrieve
a message that had reached its expiry threshold; the message is marked to be
discarded. This type of report is generated by the queue manager.
v A confirmation of arrival (COA) report message. This indicates that the message has
reached its target queue. It is generated by the queue manager.
v A confirmation of delivery (COD) report message. This indicates that the message
has been retrieved by a receiving application. It is generated by the queue
manager.
v A positive action notification (PAN) report message. This indicates that a request has
been successfully serviced (that is, the action requested in the message has been
performed successfully). This type of report is generated by the application.
v A negative action notification (NAN) report message. This indicates that a request
has not been successfully serviced (that is, the action requested in the message
has not been performed successfully). This type of report is generated by the
application.

Note: Each type of report message contains one of the following:


v The entire original message
v The first 100 bytes of data in the original message
v No data from the original message

You can request more than one type of report message when you put a message on
a queue. If you select the delivery confirmation report message and the exception
report message options, in the event that the message fails to be delivered, you
receive an exception report message. However, if you select only the delivery
confirmation report message option and the message fails to be delivered, you do
not get an exception report message.

The report messages that you request, when the criteria for generating a particular
message are met, are the only ones that you receive.

Report message options:

Chapter 1. Designing applications that use WebSphere MQ 19


You can discard a message after an exception has arisen. If you select the discard
option, and have requested an exception report message, the report message goes
to the ReplyToQ and ReplyToQMgr, and the original message is discarded.

Note: A benefit of this is that you can reduce the number of messages going to the
dead-letter queue. However, it does mean that your application, unless it sends
only datagram messages, has to deal with returned messages. When an exception
report message is generated, it inherits the persistence of the original message.

If a report message cannot be delivered (if the queue is full, for instance), the
report message is placed on the dead-letter queue.

If you want to receive a report message, specify the name of your reply-to queue
in the ReplyToQ field; otherwise the MQPUT or MQPUT1 of your original message
fails with MQRC_MISSING_REPLY_TO_Q.

You can use other report options in the message descriptor (MQMD) of a message
to specify the content of the MsgId and CorrelId fields of any report messages that
are created for the message:
v You can request that either the MsgId or the CorrelId of the original message is
to be copied into the CorrelId field of the report message. The default action is
to copy the message identifier. Use MQRO_COPY_MSG_ID_TO_CORRELID
because it enables the sender of a message to correlate the reply or report
message with the original message. The correlation identifier of the reply or
report message will be identical to the message identifier of the original
message.
v You can request that either a new MsgId is generated for the report message, or
that the MsgId of the original message is to be copied into the MsgId field of the
report message. The default action is to generate a new message identifier. Use
MQRO_NEW_MSG_ID because it ensures that each message in the system has a
different message identifier, and can be distinguished unambiguously from all
other messages in the system.
v Specialized applications might need to use MQRO_PASS_MSG_ID or
MQRO_PASS_CORREL_ID. However, you need to design the application that
reads the messages from the queue to ensure that it works correctly when, for
example, the queue contains multiple messages with the same message
identifier.
Server applications must check the settings of these flags in the request message,
and set the MsgId and CorrelId fields in the reply or report message
appropriately.
Applications that act as intermediaries between a requester application and a
server application should not need to check the settings of these flags. This is
because these applications usually need to forward the message to the server
application with the MsgId, CorrelId, and Report fields unchanged. This allows
the server application to copy the MsgId from the original message in the
CorrelId field of the reply message.
When generating a report about a message, server applications must test to see if
any of these options have been set.

For more information on how to use report messages, see the description of the
Report field in the WebSphere MQ Application Programming Guide.

To indicate the nature of the report, queue managers use a range of feedback
codes. They put these codes in the Feedback field of the message descriptor of a

20 WebSphere MQ: Application Programming Guide


report message. Queue managers can also return MQI reason codes in the Feedback
field. WebSphere MQ defines a range of feedback codes for applications to use.

For more information on feedback and reason codes, see the description of the
Feedback field in the WebSphere MQ Application Programming Guide.

An example of a program that could use a feedback code is one that monitors the
workloads of other programs serving a queue. If there is more than one instance of
a program serving a queue, and the number of messages arriving on the queue no
longer justifies this, such a program can send a report message (with the feedback
code MQFB_QUIT) to one of the serving programs to indicate that the program
should terminate its activity. (A monitoring program could use the MQINQ call to
find out how many programs are serving a queue.)

Reports and segmented messages


Not supported on WebSphere MQ for z/OS.

If a message is segmented (see “Message segmentation” on page 144 for a


description of this) and you ask for reports to be generated, you might receive
more reports than you would have done had the message not been segmented.

For reports generated by WebSphere MQ:

If you segment your messages or allow the queue manager to do so, there is only
one case in which you can expect to receive a single report for the entire message.
This is when you have requested only COD reports, and you have specified
MQGMO_COMPLETE_MSG on the getting application.

In other cases your application must be prepared to deal with several reports;
usually one for each segment.

Note: If you segment your messages, and you need only the first 100 bytes of the
original message data to be returned, change the setting of the report options to
ask for reports with no data for segments that have an offset of 100 or more. If you
do not do this, and you leave the setting so that each segment requests 100 bytes
of data, and you retrieve the report messages with a single MQGET specifying
MQGMO_COMPLETE_MSG, the reports assemble into a large message containing
100 bytes of read data at each appropriate offset. If this happens, you need a large
buffer or you need to specify MQGMO_ACCEPT_TRUNCATED_MSG.

For reports generated by applications:

If your application generates reports, always copy the WebSphere MQ headers that
are present at the start of the original message data to the report message data.

Then add none, 100 bytes, or all of the original message data (or whatever other
amount you would usually include) to the report message data.

You can recognize the WebSphere MQ headers that must be copied by looking at
the successive Format names, starting with the MQMD and continuing through
any headers present. The following Format names indicate these WebSphere MQ
headers:
v MQMDE
v MQDLH
v MQXQH

Chapter 1. Designing applications that use WebSphere MQ 21


v MQIIH
v MQH*
MQH* means any name that starts with the characters MQH.

The Format name occurs at specific positions for MQDLH and MQXQH, but for the
other WebSphere MQ headers it occurs at the same position. The length of the
header is contained in a field that also occurs at the same position for MQMDE,
MQIMS, and all MQH* headers.

If you are using a Version 1 MQMD, and you are reporting on a segment, or a
message in a group, or a message for which segmentation is allowed, the report
data must start with an MQMDE. Set the OriginalLength field to the length of the
original message data excluding the lengths of any WebSphere MQ headers that
you find.

Retrieval of reports:

If you ask for COA or COD reports, you can ask for them to be reassembled for
you with MQGMO_COMPLETE_MSG.

An MQGET with MQGMO_COMPLETE_MSG is satisfied when enough report


messages (of a single type, for example COA, and with the same GroupId) are
present on the queue to represent one complete original message. This is true even
if the report messages themselves do not contain the complete original data; the
OriginalLength field in each report message gives the length of original data
represented by that report message, even if the data itself is not present.

You can use this technique even if there are several different report types present
on the queue (for example, both COA and COD), because an MQGET with
MQGMO_COMPLETE_MSG reassembles report messages only if they have the
same Feedback code. However, you cannot usually use this technique for exception
reports, because, in general, these have different Feedback codes.

You can use this technique to get a positive indication that the entire message has
arrived. However, in most circumstances you need to cater for the possibility that
some segments arrive while others might generate an exception (or expiry, if you
have allowed this). You cannot use MQGMO_COMPLETE_MSG in this case,
because, in general, you might get different Feedback codes for different segments
and, as noted above, you might get more than one report for a given segment. You
can, however, use MQGMO_ALL_SEGMENTS_AVAILABLE.

To allow for this you might need to retrieve reports as they arrive, and build up a
picture in your application of what happened to the original message. You can use
the GroupId field in the report message to correlate reports with the GroupId of the
original message, and the Feedback field to identify the type of each report
message. The way in which you do this depends on your application requirements.

One approach is as follows:


v Ask for COD reports and exception reports.
v After a specific time, check whether a complete set of COD reports has been
received using MQGMO_COMPLETE_MSG. If so, your application knows that
the entire message has been processed.
v If not, and exception reports relating to this message are present, handle the
problem as for unsegmented messages, but ensure that you clean up orphan
segments at some point.
22 WebSphere MQ: Application Programming Guide
v If there are segments for which there are no reports of any kind, the original
segments (or the reports) might be waiting for a channel to be reconnected, or
the network might be overloaded at some point. If no exception reports at all
have been received (or if you think that the ones you have might be temporary
only), you might decide to let your application wait a little longer.
As before, this is similar to the considerations you have when dealing with
unsegmented messages, except that you must also consider the possibility of
cleaning up orphan segments.
If the original message is not critical (for example, if it is a query, or a message that
can be repeated later), set an expiry time to ensure that orphan segments are
removed.

Back-level queue managers:

When a report is generated by a queue manager that supports segmentation, but is


received on a queue manager that does not support segmentation, the MQMDE
structure (which identifies the Offset and OriginalLength represented by the
report) is always included in the report data, in addition to zero, 100 bytes, or all
of the original data in the message.

However, if a segment of a message passes through a queue manager that does not
support segmentation, if a report is generated there, the MQMDE structure in the
original message is treated purely as data. It is not therefore included in the report
data if zero bytes of the original data have been requested. Without the MQMDE,
the report message might not be useful.

Request at least 100 bytes of data in reports if there is a possibility that the
message might travel through a back-level queue manager.

Format of message control information and message data


The queue manager is only interested in the format of the control information
within a message, whereas applications that handle the message are interested in
the format of both the control information and the data.

Format of message control information


Control information in the character-string fields of the message descriptor must be
in the character set used by the queue manager.

The CodedCharSetId attribute of the queue manager object defines this character
set. Control information must be in this character set because, when applications
pass messages from one queue manager to another, message channel agents that
transmit the messages use the value of this attribute to determine what data
conversion to perform.

Format of message data


You can specify any of the following:
v The format of the application data
v The character set of the character data
v The format of numeric data

To do this, use these fields:

Chapter 1. Designing applications that use WebSphere MQ 23


Format
This indicates to the receiver of a message the format of the application
data in the message.
When the queue manager creates a message, in some circumstances it uses
the Format field to identify the format of that message. For example, when
a queue manager cannot deliver a message, it puts the message on a
dead-letter (undelivered message) queue. It adds a header (containing
more control information) to the message, and changes the Format field to
show this.
The queue manager has a number of built-in formats with names beginning
MQ, for example MQFMT_STRING. If these do not meet your needs, you
can define your own formats (user-defined formats), but you must not use
names beginning with MQ for these.
When you create and use your own formats, you must write a
data-conversion exit to support a program getting the message using
MQGMO_CONVERT.
CodedCharSetId
This defines the character set of character data in the message. If you want
to set this character set to that of the queue manager, you can set this field
to the constant MQCCSI_Q_MGR or MQCCSI_INHERIT.
When you get a message from a queue, compare the value of the
CodedCharSetId field with the value that your application is expecting. If
the two values differ, you might need to convert any character data in the
message or use a data-conversion message exit if one is available.
Encoding
This describes the format of numeric message data that contains binary
integers, packed-decimal integers, and floating point numbers. It is usually
encoded according to the particular machine on which the queue manager
is running.
When you put a message on a queue, you usually specify the constant
MQENC_NATIVE in the Encoding field. This means that the encoding of
your message data is the same as that of the machine on which your
application is running.
When you get a message from a queue, compare the value of the Encoding
field in the message descriptor with the value of the constant
MQENC_NATIVE on your machine. If the two values differ, you might
need to convert any numeric data in the message or use a data-conversion
message exit if one is available.

Application data conversion


Application data might need to be converted to the character set and the encoding
required by another application where different platforms are concerned.

It can be converted at the sending queue manager, or at the receiving queue


manager. If the library of built-in formats does not meet your needs, you can
define your own. The type of conversion depends on the message format that is
specified in the format field of the message descriptor, MQMD.

Note: Messages with MQFMT_NONE specified are not converted.

Conversion at the sending queue manager:

24 WebSphere MQ: Application Programming Guide


Set the CONVERT channel attribute to YES if you need the sending message
channel agent (MCA) to convert the application data.

The conversion is performed at the sending queue manager for certain built-in
formats and for user-defined formats if a suitable user exit is supplied.

Built-in formats:

These include:
v Messages that are all characters (using the format name MQFMT_STRING)
v WebSphere MQ defined messages, for example Programmable Command
Formats
WebSphere MQ uses Programmable Command Format messages for
administration messages and events (the format name used is MQFMT_ADMIN
in this case). You can use the same format (using the format name
MQFMT_PCF) for your own messages, and take advantage of the built-in data
conversion.

The queue manager built-in formats all have names beginning with MQFMT. They
are listed and described in the WebSphere MQ Application Programming Reference
under the Format field of the Message descriptor (MQMD).

Application-defined formats:

For user-defined formats, application data conversion must be performed by a


data-conversion exit program (for more information, see “Writing data-conversion
exits” on page 163). In a client-server environment, the exit is loaded at the server
and conversion takes place there.

Conversion at the receiving queue manager:

Application message data can be converted by the receiving queue manager for
both built-in and user-defined formats.

The conversion is performed during the processing of an MQGET call if you


specify the MQGMO_CONVERT option. For details, see the WebSphere MQ
Application Programming Reference.

Coded character sets:

WebSphere MQ products support the coded character sets that are provided by the
underlying operating system.

When you create a queue manager, the queue manager coded character set ID
(CCSID) used is based on that of the underlying environment. If this is a mixed
code page, WebSphere MQ uses the SBCS part of the mixed code page as the
queue manager CCSID.

For general data conversion, if the underlying operating system supports DBCS
code pages, WebSphere MQ can use it.

See the documentation for your operating system for details of the coded character
sets that it supports.

You need to consider application data conversion, format names, and user exits
when writing applications that span multiple platforms. For details of the MQGET
Chapter 1. Designing applications that use WebSphere MQ 25
call, the Convert characters call, the MQGMO_CONVERT option, and the built-in
formats, see the WebSphere MQ Application Programming Reference. See “Writing
data-conversion exits” on page 163 for information about invoking and writing
data-conversion exits.

Message priorities
You set the priority of a message (in the Priority field of the MQMD structure)
when you put the message on a queue. You can set a numeric value for the
priority, or you can let the message take the default priority of the queue.

The MsgDeliverySequence attribute of the queue determines whether messages on


the queue are stored in FIFO (first in, first out) sequence, or in FIFO within priority
sequence. If this attribute is set to MQMDS_PRIORITY, messages are enqueued
with the priority specified in the Priority field of their message descriptors; but if
it is set to MQMDS_FIFO, messages are enqueued with the default priority of the
queue. Messages of equal priority are stored on the queue in order of arrival.

The DefPriority attribute of a queue sets the default priority value for messages
being put on that queue. This value is set when the queue is created, but it can be
changed afterwards. Alias queues, and local definitions of remote queues, can have
different default priorities from the base queues to which they resolve. If there is
more than one queue definition in the resolution path (see “Name resolution” on
page 101), the default priority is taken from the value (at the time of the put
operation) of the DefPriority attribute of the queue specified in the open
command.

The value of the MaxPriority attribute of the queue manager is the maximum
priority that you can assign to a message processed by that queue manager. You
cannot change the value of this attribute. In WebSphere MQ, the attribute has the
value 9; you can create messages having priorities between 0 (the lowest) and 9
(the highest).

Message properties
Use message properties to allow an application to select messages to process, or to
retrieve information about a message without accessing MQMD or MQRFH2
headers. They also facilitate communication between Websphere MQ and JMS
applications.

A message property is data associated with a message, consisting of a textual name


and a value of a particular type. Message properties are used by message selectors
to filter publications to topics or to selectively get messages from queues. Message
properties can be used to include business data or state information without
having to store it in the application data. Applications do not have to access data
in the MQ Message Descriptor (MQMD) or MQRFH2 headers because fields in
these data structures can be accessed as message properties using Message Queue
Interface (MQI) function calls.

The use of message properties in WebSphere MQ mimics the use of properties in


JMS. This means that you can set properties in a JMS application and retrieve them
in a procedural WebSphere MQ application, or the other way round.

Message properties and message length


Use the queue manager attribute MaxPropertiesLength to control the size of the
properties that can flow with any message in a WebSphere MQ queue manager.

26 WebSphere MQ: Application Programming Guide


In general, when you use MQSETMP to set properties, the size of a property is the
length of the property name in bytes, plus the length of the property value in bytes
as passed into the MQSETMP call. It is possible for the character set of the
property name and the property value to change during transmission of the
message to its destination because these can be converted into Unicode; in this case
the size of the property might change.

On an MQPUT or MQPUT1 call, properties of the message do not count towards


the length of the message for the queue and the queue manager, but they do count
towards the length of the properties as perceived by the queue manager (whether
they were set using the message property MQI calls or not).

If the size of the properties exceeds the maximum properties length, the message is
rejected with MQRC_PROPERTIES_TOO_BIG. Because the size of the properties is
dependent on its representation, you should set the maximum properties length at
a gross level.

It is possible that an application could successfully put a message with a buffer


larger than the value of MaxMsgLength when the buffer includes properties. This is
because, even when represented as MQRFH2 elements, message properties do not
count towards the length of the message. The MQRFH2 header fields themselves
add to the properties length only if there are one or more folders contained and
every folder in the header contains properties. Otherwise the header fields count
towards the message length.

On an MQGET call, properties of the message do not count towards the length of
the message as far as the queue and the queue manager are concerned. However,
because the properties are counted separately it is possible that the buffer returned
by an MQGET call is larger than the value of the MaxMsgLength attribute.

Do not have your applications query the value of MaxMsgLength and then allocate
a buffer of this size before calling MQGET; instead, allocate a buffer you consider
large enough. If the MQGET fails, allocate a buffer guided by the size of the
DataLength parameter.

The DataLength parameter of the MQGET call now returns the length in bytes of
the application data and any properties returned in the buffer you have provided,
if a message handle is not specified in the MQGMO structure.

The Buffer parameter of the MQPUT call now contains the application message
data to be sent and any properties represented in the message data.

When flowing to a queue manager that is prior to Version 7.0 of the product,
properties of the message, except those in the message descriptor, count towards
the length of the message. Therefore, you should either raise the value of the
MaxMsgLength attribute of channels going to a system prior to Version 7.0 as
necessary, to compensate for the fact that more data might be sent for each
message. Alternatively, you can lower the queue or queue manager MaxMsgLength,
so that the overall level of data being sent around the system remains the same.

There is a length limit of 100 MB for message properties, excluding the message
descriptor or extension for each message.

The size of a property in its internal representation is the length of the name, plus
the size of its value, plus some control data for the property. There is also some
control data for the set of properties after one property is added to the message.

Chapter 1. Designing applications that use WebSphere MQ 27


Property names
A property name is a character string. Certain restrictions apply to its length and
the set of characters that can be used.

A property name is a case-sensitive character string, limited to +4095 characters


unless otherwise restricted by the context. This limit is contained in the
MQ_MAX_PROPERTY_NAME_LENGTH constant.

If you exceed this maximum length when using a message property MQI call, the
call fails with reason code MQRC_PROPERTY_NAME_LENGTH_ERR.

Because there is no maximum property name length in JMS, it is possible for a JMS
application to set a valid JMS property name that is not a valid WebSphere MQ
MQ property name when stored in an MQRFH2 structure.

In this case, when parsed, only the first 4095 characters of the property name are
used; the following characters are truncated. This could cause an application using
selectors to fail to match a selection string, or to match a string when not expecting
to, since more than one property might truncate to the same name. When a
property name is truncated, MQ issues an error log message.

All property names must follow the rules defined by the Java Language
Specification for Java Identifiers, with the exception that Unicode character U+002E
(“.”) is permitted as part of the name - but not the start. The rules for Java
Identifiers equate to those contained in the JMS specification for property names.

White space characters and comparison operators are prohibited. Embedded nulls
are allowed in a property name but not recommended. If you use embedded nulls,
this prevents the use of the MQVS_NULL_TERMINATED constant when used
with the MQCHARV structure to specify variable length strings.

Keep property names simple because applications can select messages based on the
property names and the conversion between the character set of the name and of
the selector might cause the selection to fail unexpectedly.

WebSphere MQ property names use character U+002E (“.”) for logical grouping of
properties. This divides up the namespace for properties. The properties with the
following prefixes, in any mixture of lower or upper case are reserved for use by
the product:
v mcd
v jms
v usr
v mq
v sib
v wmq
v Root
v Body

A good way to avoid name clashes is to ensure that all applications prefix their
message properties with their Internet domain name. For example, if you are
developing an application using domain name “ourcompany.com” you could name
all properties with the prefix “com.ourcompany”. This naming convention also

28 WebSphere MQ: Application Programming Guide


allows for easy selection of properties; for example, an application can inquire on
all message properties starting “com.ourcompany.%”.

See Property name restrictions for further information about the use of property
names.

Property name restrictions:

When you name a property, you must observe certain rules.

The following restrictions apply to property names:


1. A property must not begin with the following strings:
v ″JMS″ - these are reserved for use by WebSphere MQ classes for JMS.
v ″usr.JMS″ - these are not valid.
The only exceptions to this are the following properties providing synonyms
for JMS properties:

Property Synonym for


JMSCorrelationID Root.MQMD.CorrelId or jms.Cid
JMSDeliveryMode Root.MQMD.Persistence or jms.Dlv
JMSDestination jms.Dst
JMSExpiration Root.MQMD.Expiry or jms.Exp
JMSMessageID Root.MQMD.MsgId
JMSPriority Root.MQMD.Priority or jms.Pri
JMSRedelivered Root.MQMD.BackoutCount
JMSReplyTo (a string Root.MQMD.ReplyToQ or Root.MQMD.ReplyToQMgr or
encoded as a URI) jms.Rto
JMSTimestamp Root.MQMD.PutDate or Root.MQMD.PutTime or jms.Tms
JMSType mcd.Type or mcd.Set or mcd.Fmt
JMSXAppID Root.MQMD.PutApplName
JMSXDeliveryCount Root.MQMD.BackoutCount
JMSXGroupID Root.MQMD.GroupId or jms.Gid
JMSXGroupSeq Root.MQMD.MsgSeqNumber or jms.Seq
JMSXUserID Root.MQMD.UserIdentifier

These synonyms allow an MQI application to access JMS properties in a similar


fashion to a WebSphere MQ classes for JMS client application. Of these
properties, only JMSCorrelationID, JMSReplyTo, JMSType, JMSXGroupID, and
JMSXGroupSeq can be set using the MQI.
Note that the JMS_IBM_* properties available from within WebSphere MQ
classes for JMS are not available using the MQI. The fields that the JMS_IBM_*
properties reference can be accessed in other ways by MQI applications.
2. A property must not be called, in any mixture of lower or uppercase, “NULL”,
“TRUE”, “FALSE”, “NOT”, “AND”, “OR”, “BETWEEN”, “LIKE”, “IN”, “IS”
and “ESCAPE”. These are the names of SQL keywords used in selection strings.
3. A property beginning “mq” (except “mq_usr”), “jms”, “mcd”, “usr”, or “sib”
(in any mixture of lower or uppercase) can only contain a single “.” character
(U+002E).

Chapter 1. Designing applications that use WebSphere MQ 29


4. Two “.” characters must contain other characters in between; you cannot have
an empty point in the hierarchy. Similarly a property name cannot end in a “.”
character.
5. If an application sets the property “a.b” and then the property “a.b.c”, it is
unclear whether in the hierarchy “b” contains a value or another logical
grouping. Such a hierarchy is “mixed content” and this is not supported.
Setting a property that causes mixed content is not allowed.

These restrictions are enforced by the validation mechanism as follows:


v Property names are validated when setting a property using the MQSETMP call,
if validation was requested when the message handle was created. If an attempt
to validate a property is undertaken and fails due to an error in the specification
of the property name, the completion code is MQCC_FAILED with reason:
– MQRC_PROPERTY_NAME_ERROR for reasons 1-4.
– MQRC_MIXED_CONTENT_NOT_ALLOWED for reason 5.
v The names of properties specified directly as MQRFH2 elements are not
guaranteed to be validated by the MQPUT call.

Message descriptor fields as properties:

Most message descriptor fields can be treated as properties. The property name is
constructed by adding a prefix to the message descriptor field’s name.

If an MQI application wants to identify a message property contained in a message


descriptor field, for example, in a selector string or using the message property
APIs, use the following syntax:

Property name Message descriptor field


Root.MQMD.<Field> <Field>

Specify <Field> with the same case as for the MQMD structure fields in the C
language declaration. For example, the property name Root.MQMD.AccountingToken
accesses the AccountingToken field of the message descriptor.

The StrucId and Version fields of the message descriptor are not accessible using
the above syntax.

Message descriptor fields are never represented in an MQRFH2 header as for other
properties.

If the message data starts with an MQMDE that is honored by the queue manager,
the MQMDE fields can be accessed using the Root.MQMD.<Field> notation
described above. In this case the MQMDE fields are treated as logically part of the
MQMD from a properties perspective. See the section “MQMDE specified on
MQPUT and MQPUT1 calls” in Overview of MQMDE.

Property data types and values


A property can be a boolean, a byte string, a character string, or a floating-point or
integer number. The property can store any valid value in the range of the data
type unless otherwise restricted by the context.

The data type of a property value must be one of the following values:
v MQBOOL

30 WebSphere MQ: Application Programming Guide


v MQBYTE[ ]
v MQCHAR[ ]
v MQFLOAT32
v MQFLOAT64
v MQINT8
v MQINT16
v MQINT32
v MQINT64

A property can exist but have no defined value; it is a null property. A null
property is different from a byte or character string property (MQBYTE[ ] and
MQCHAR[ ] respectively) that has a defined but empty value, that is, one with a
zero-length value.

Byte string is not a valid property data type in JMS or XMS. You are advised not to
use byte string properties in the <usr> folder.

Selecting messages from queues


You can select messages from queues using the MsgId and CorrelId fields on an
MQGET call, or by using a SelectionString on an MQOPEN or MQSUB call.

Getting a specific message using MsgId and CorrelId


To get a particular message from a queue, use the MsgId and CorrelId fields of the
message descriptor. If you specify Version 2 of the MQMD, you can also use the
GroupId, MsgSeqNumber, and Offset fields.

A globally unique message identifier is ideally generated by the queue manager


when a message is first put on a queue. Globally unique MsgIds improve
serviceability because you can track messages across queue managers and locate
messages in recovery logs for example. However, a WebSphere MQ application can
specify a particular value for the message identifier, and although it is strongly
recommended that application-generated MsgIds are unique identifiers, it is
possible for an application to specify a non-unique MsgId.

You can use the correlation identifier in any way that you like. One intended use
of this field is for applications to copy the message identifier of a request message
into the CorrelId field of a reply message. Where possible use the CorrelId in
preference to the MsgId if you want to associate an application-provided identity
with a message. When retrieving a specific message on the distributed platforms,
the queue manager is then optimized for retrieving messages by CorrelId (rather
than by MsgId).

The group identifier is usually generated by the queue manager when the first
message of a group is put onto a queue. The MsgSeqNumber field identifies the
position of the message within the group and the Offset field identifies the
segments within the message.

Where more than one message meets the combined selection criteria, the
MsgDeliverySequence attribute of the queue determines whether messages are
selected in FIFO (first in, first out) or priority order. When messages have equal
priority, they are selected in FIFO order. For more information, see “The order in
which messages are retrieved from a queue” on page 131.

Chapter 1. Designing applications that use WebSphere MQ 31


For an example of an application that uses correlation identifiers, see “The Credit
Check sample” on page 485.

Selectors
A message selector is a variable-length string used by an application to register its
interest in only those messages whose properties satisfy the Structured Query
Language (SQL) query that the selection string represents.

Selection using the MQSUB and MQOPEN function calls

You use the SelectionString, which is a structure of type MQCHARV, to make


selections using the MQSUB and MQOPEN calls.

The SelectionString structure is used to pass a variable-length selection string to


the queue manager.

The CCSID associated with the selector string is set via the VSCCSID field of the
MQCHARV structure. The value used must be a CCSID that is supported for
selector strings. The code pages supported are listed within the Code Page
Conversion topic in the WebSphere MQ Application Programming Reference.

Specifying a CCSID for which there is no WebSphere MQ supported Unicode


conversion, results in an error of MQRC_SOURCE_CCSID_ERROR. This error is
returned at the time that the selector is presented to the queue manager, that is, on
the MQSUB, MQOPEN, or MQPUT1 call.

The default value for the VSCCSID field is MQCCSI_APPL, which indicates that the
CCSID of the selection string is equal to the queue manager CCSID, or the client
CCSID if connected through a client. The MQCCSI_APPL constant can however be
overridden by an application redefining it before compiling.

If the MQCHARV selector represents a NULL string, no selection takes place for
that message consumer and messages are delivered as if a selector had not been
used.

The maximum length of a selection string is limited only by what can be described
by the MQCHARV field VSLength.

The SelectionString is returned on the output from an MQSUB call using the
MQSO_RESUME subscribe option, if you have provided a buffer and there is a
positive buffer length in VSBufSize. If you do not provide a buffer, only the length
of the selection string is returned in the VSLength field of the MQCHARV. If the
buffer provided is smaller than the space required to return the field, only
VSBufSize bytes are returned in the provided buffer.

An application cannot alter a selection string without first closing either the handle
to the queue (for MQOPEN), or subscription (for MQSUB). A new selection string
can then be specified on a subsequent MQOPEN or MQSUB call.
MQOPEN
Use MQCLOSE to close the opened handle, then specify a new selection
string on a subsequent MQOPEN call.
MQSUB
Use MQCLOSE to close the returned subscription handle (hSub), then
specify a new selection string on a subsequent MQSUB call.

32 WebSphere MQ: Application Programming Guide


Figure 3 shows the process of selection using the MQSUB call.

MQOPEN
(APP 1)
ObjectName = "MyDestQ"
hObj MyDestQ

MQSUB
(APP 1)
SelectionString = "Sport = 'Football'"
hObj ResultsTopic
TopicString = "ResultsTopic" MyDestQ

DELIVERED
ResultsTopic
League = 'Premiership'
MyDestQ Sport = 'Football'

Message

NOT DELIVERED
ResultsTopic

League = 'Premiership'
MyDestQ Sport = 'Cricket'

Message

DELIVERED
ResultsTopic
League = 'Div 2'
Sport = 'Football'
MyDestQ
Message
MQGET
(APP 1) hObj

DELIVERED

League = 'Premiership'
Sport = 'Football'
MyDestQ
Message

DELIVERED

League = 'Div 2'


Sport = 'Football'
MyDestQ
Message

Figure 3. Selection using MQSUB call

A selector can be passed in on the call to MQSUB by using the SelectionString


field in the MQSD structure. The effect of passing in a selector on the MQSUB is
that only those messages published to the topic being subscribed to, that match a
supplied selection string, are made available on the destination queue.

Figure 4 on page 34 shows the process of selection using the MQOPEN call.

Chapter 1. Designing applications that use WebSphere MQ 33


MQOPEN
(APP 1)

SelectorString = "League = 'Premiership'"


ObjectName = "SportQ" SportQ
hObj

MQPUT
Application 2
League = 'Div 2'
Sport = 'Football'
SportQ
Message

MQPUT
Application 2
League = 'Premiership'
Sport = 'Football'
SportQ
Message
MQGET
(APP 1) hObj
NOT DELIVERED

League = 'Div 2'


Sport = 'Football'
SportQ
Message

DELIVERED

League = 'Premiership'
Sport = 'Football'
SportQ
Message

MQRC_NO_MSG_AVAILABLE

SportQ

Figure 4. Selection using MQOPEN call

A selector can be passed in on the call to MQOPEN by using the SelectionString


field in the MQOD structure. The effect of passing in a selector on the MQOPEN
call is that only those messages on the opened queue, that match a selector, are
delivered to the message consumer.

The main use for the selector on the MQOPEN call is for the point-to-point case
where an application can elect to receive only those messages on a queue that
match a selector. The example above shows a simple scenario where two messages
are put to a queue opened by MQOPEN but only one is received by the
application getting it, as it is the only one that matches a selector.

Note that subsequent MQGET calls result in MQRC_NO_MSG_AVAILABLE as no


further messages exist on the queue that match the given selector.

Selection behavior:

34 WebSphere MQ: Application Programming Guide


Overview of WebSphere MQ selection behavior.

The fields in an MQMDE structure are considered to be the message properties for
the corresponding message descriptor properties if the MQMD:
v Has format MQFMT_MD_EXTENSION
v Is immediately followed by a valid MQMDE structure
v Is version one or contains the default version two fields only

It is possible for a selection string to resolve to either TRUE or FALSE before any
matching against message properties takes place. This might be the case if, for
instance, the selection string is set to, for example:
"TRUE <>FALSE"

Such early evaluation is guaranteed to take place only when there are no message
property references in the selection string.

If a selection string resolves to TRUE before any message properties are


considered, all messages published to the topic subscribed to by the consumer are
delivered. If a selection string resolves to FALSE before any message properties are
considered, a reason code of MQRC_SELECTOR_ALWAYS_FALSE, and completion
code MQCC_FAILED are returned on the function call that presented the selector.

Even if a message contains no message properties (other than header properties)


then it may still be eligible for selection. If a selection string references a message
property that does not exist, this property is assumed to have the value of NULL
or ‘Unknown’.

For example, a message might still satisfy a selection string like ‘Color IS NULL’,
where ’Color’ does not exist as a message property in the message.

Note that selection can be performed only on the properties associated with a
message, not the message itself.

Each message property has a type associated with it, and when you perform a
selection, you must ensure that the values used in expressions to test message
properties are of the correct type. If a type mismatch occurs, the expression in
question resolves to FALSE.

It is your responsibility to ensure that the selection string and message properties
use compatible types.

Selection criteria continue to be applied on behalf of inactive durable subscribers,


so that only messages that match the selection string that was originally supplied
are kept.

Selection strings are non-alterable when a durable subscription is resumed with


alter (MQSO_ALTER). If a different selection string is presented when a durable
subscriber resumes activity, then MQRC_SELECTOR_NOT_ALTERABLE is
returned to the application.

Applications receive a return code of MQRC_NO_MSG_AVAILABLE if there is no


message on a queue that meets the selection criteria.

If an application has specified a selection string containing property values then


only those messages that contain matching properties are eligible for selection. As

Chapter 1. Designing applications that use WebSphere MQ 35


an example, if a subscriber specifies a selection string of “a = 3” and a message is
published containing no properties, or properties where ‘a’ does not exist or is not
equal to 3, then the subscriber will not receive that message to its destination
queue.

Message selector syntax:

A WebSphere MQ message selector is a String, whose syntax is based on a subset


of the SQL92 conditional expression syntax.

The order in which a message selector is evaluated is from left to right within a
precedence level. You can use parentheses to change this order. Predefined selector
literals and operator names are written here in upper case; however, they are not
case-sensitive.

WebSphere MQ verifies the syntactic correctness of a message selector at the time


it is presented. If the syntax of the selection string is incorrect or a property name
is not valid, a MQRC_SELECTOR_SYNTAX_ERROR is returned to the application.
If property name validation was disabled when the property was set (by setting
MQSMPO_NONE instead of MQSMPO_VALIDATE) and an application
subsequently puts a message with in invalid property name, this message will
never be selected.

A selector can contain:


v Literals:
– String literals are enclosed in single quotes. A doubled single quote represents
a single quote. Examples are ’literal’ and ’literal’’s’. Like Java string literals,
these use the Unicode character encoding. You cannot use double quotes to
enclose a string literal. Any sequence of bytes can be used between the
quotes.
– A byte string is one or more pair of hex characters enclosed in double quotes
and prefixed by 0x. Examples are ″0x2F1C″ or ″0XD43A″. The length of a byte
string must be at least one byte. When matching a selector byte string to a
message property of type MQTYPE_BYTE_STRING no special action taken on
leading or trailing zero, they are simply treated as another character.
Endianness is also not considered. The length of both selector and property
byte strings should therefore be equal and the sequence of bytes should be
exactly the same.
Examples of byte string selection (assume myBytes = 0AFC23) are:
- “myBytes = “0x0AFC23”” = TRUE
- “myBytes = “0xAFC23”” = MQRC_SELECTOR_SYNTAX_ERROR (because
number of bytes is not multiple of two)
- “myBytes = “0x0AFC2300”” = FALSE (because the trailing zero is
significant in the comparison)
- “myBytes = “0x000AFC23”” = FALSE (because leading zero is significant in
the comparison)
- “myBytes = “0x23FC0A”” = FALSE (because endianness is not considered)
– Hex numbers begin with a zero, followed by an upper or lowercase ’x’. The
remainder of the literal contains one or more valid hex characters. Examples
are 0xA, 0xAF, 0X2020.
– A leading zero followed by one or more digits in the range 0-7 is always
interpreted as being the start of an octal number. You cannot represent a

36 WebSphere MQ: Application Programming Guide


zero-prefixed decimal number like this, for example, ’09’ returns a syntax
error because 9 is not a valid octal digit. Examples of octal numbers are 0177,
0713.
– An exact numeric literal is a numeric value without a decimal point, such as
57, -957, and +62. An exact numeric literal can have a trailing upper or
lowercase ’L’ character, this does not affect how the number is stored or
interpreted. WebSphere MQ supports exact numerals in the range
-9,223,372,036,854,775,808 to 9,223,372,036,854,775,807.
– An approximate numeric literal is a numeric value in scientific notation, such
as 7E3 or -57.9E2, or a numeric value with a decimal, such as 7., -95.7, or +6.2.
WebSphere MQ supports numbers in the range -1.797693134862315E+308 to
1.797693134862315E+308.
The significand should follow an optional sign character (+ or -). The
significand should be either an integer or a fraction. A fractional part of the
significand need not have a leading digit.
An upper or lowercase ’E’ indicates the start of an optional exponent. The
exponent has a decimal radix and the number part of the exponent can be
prefixed by an optional sign character.
Approximate numeric literals can be terminated by an ’F’ or ’D’ (case
insensitive). This syntax exists to support the cross-language method of
tagging single or double precision numbers. These characters are optional and
do not affect how an approximate numeric literal is stored or processed.
These numbers are always stored and processed using double-precision.
– The boolean literals TRUE and FALSE.

Note: Non-finite IEEE-754 representations such as NaN, +Infinity, -Infinity are


not supported in selection strings. It is therefore not possible to use these values
as operands in an expression. Negative zero is treated the same as positive zero
for mathematical operations.
v Identifiers:
An identifier is a variable-length character sequence that must begin with a valid
identifier start character, followed by zero or more valid identifier part
characters. The rules for identifier names are the same as those for message
property names, see “Property names” on page 28 and “Property name
restrictions” on page 29 for more information.
Identifiers are either header field references or property references. The type of a
property value in a message selector must correspond to the type used to set the
property, although numeric promotion is performed where possible. If a type
mismatch occurs then the result of the expression is FALSE. If a property that
does not exist in a message is referenced, its value is NULL.
Type conversions that apply to the get methods for properties do not apply
when a property is used in a message selector expression. For example, if you
set a property as a string value and then use a selector to query it as a numeric
value, the expression returns FALSE.
JMS field and property names that map to property names or MQMD field
names are also valid identifiers in a selection string. WebSphere MQ maps the
recognized JMS field and property names to the message property values. See
Using Java for more information. As an example, the selection string ″JMSPriority
>= ″will select on the Pri property found in the jms folder of the current
message.
v Overflow/underflow:
For both decimal and approximate numeric numbers, the following are
undefined:

Chapter 1. Designing applications that use WebSphere MQ 37


– Specifying a number that is out of the defined range
– Specifying an arithmetic expression which would cause overflow or
underflow
No checks are performed for the above conditions.
v Whitespace:
Defined as a space, form-feed, new-line, carriage return, horizontal tab, or
vertical tab. The following Unicode characters are recognized as whitespace:
– \u0009 to \u000D
– \u0020
– \u001C
– \u001D
– \u001E
– \u001F
– \u1680
– \u180E
– \u2000 to \u200A
– \u2028
– \u2029
– \u202F
– \u205F
– \u3000
v Expressions:
– A selector is a conditional expression. A selector that evaluates to true
matches; a selector that evaluates to false or unknown does not match.
– Arithmetic expressions are composed of themselves, arithmetic operations,
identifiers (whose value is treated as a numeric literal), and numeric literals.
– Conditional expressions are composed of themselves, comparison operations,
and logical operations.
v Standard bracketing (), to set the order in which expressions are evaluated, is
supported.
v Logical operators in precedence order: NOT, AND, OR.
v Comparison operators: =, >, >=, <, <=, <> (not equal).
– Two byte strings are equal only if the strings are of the same length and the
sequence of bytes is equal.
– Only values of the same type can be compared. One exception is that it is
valid to compare exact numeric values and approximate numeric values, (the
type conversion required is defined by the rules of Java numeric promotion).
If there is an attempt to compare different types, the selector is always false.
– String and boolean comparison is restricted to = and <>. Two strings are
equal only if they contain the same sequence of characters.
v Arithmetic operators in precedence order:
– +, - unary.
– *, /, multiplication, and division.
– +, -, addition, and subtraction.
– Arithmetic operations on a NULL value are not supported. If they are
attempted, the complete selector is always false.
– Arithmetic operations must use Java numeric promotion.

38 WebSphere MQ: Application Programming Guide


v arithmetic-expr1 [NOT] BETWEEN arithmetic-expr2 and arithmetic-expr3
comparison operator:
– Age BETWEEN 15 and 19 is equivalent to age >= 15 AND age <= 19.
– Age NOT BETWEEN 15 and 19 is equivalent to age < 15 OR age > 19.
– If any of the expressions of a BETWEEN operation are NULL, the value of the
operation is false. If any of the expressions of a NOT BETWEEN operation are
NULL, the value of the operation is true.
v identifier [NOT] IN (string-literal1, string-literal2,...) comparison operator where
identifier has a String or NULL value.
– Country IN (’UK’, ’US’, ’France’) is true for ’UK’ and false for ’Peru’. It is
equivalent to the expression (Country = ’UK’) OR (Country = ’US’) OR
(Country = ’France’).
– Country NOT IN (’UK’, ’US’, ’France’) is false for ’UK’ and true for ’Peru’. It
is equivalent to the expression NOT ((Country = ’UK’) OR (Country = ’US’)
OR (Country = ’France’)).
– If the identifier of an IN or NOT IN operation is NULL, the value of the
operation is unknown.
v identifier [NOT] LIKE pattern-value [ESCAPE escape-character] comparison
operator, where identifier has a string value. pattern-value is a string literal,
where _ stands for any single character and % stands for any sequence of
characters (including the empty sequence). All other characters stand for
themselves. The optional escape-character is a single character string literal,
whose character is used to escape the special meaning of the _ and % in
pattern-value.
– phone LIKE ’12%3’ is true for 123 and 12993 and false for 1234.
– word LIKE ’l_se’ is true for lose and false for loose.
– underscored LIKE ’\_%’ ESCAPE ’\’ is true for _foo and false for bar.
– phone NOT LIKE ’12%3’ is false for 123 and 12993 and true for 1234.
– If the identifier of a LIKE or NOT LIKE operation is NULL, the value of the
operation is unknown.
v identifier IS NULL comparison operator tests for a null header field value, or a
missing property value.
– prop_name IS NULL.
v identifier IS NOT NULL comparison operator tests for the existence of a
non-null header field value or a property value.
– prop_name IS NOT NULL.
v Null values
The evaluation of selector expressions that contain NULL values is defined by
SQL 92 NULL semantics, in summary:
– SQL treats a NULL value as unknown.
– Comparison or arithmetic with an unknown value always yields an unknown
value.
– The IS NULL and IS NOT NULL operators convert an unknown value into
the respective TRUE and FALSE values.
The boolean operators use three-valued logic (T=TRUE, F=FALSE,
U=UNKNOWN)

Chapter 1. Designing applications that use WebSphere MQ 39


Table 1. Boolean operator outcome when logic is A AND B
Operator A Operator B Outcome (A AND B)
T F F
T U U
T T T
F T F
F U F
F F F
U T U
U U U
U F F

Table 2. Boolean operator outcome when logic is A OR B


Operator A Operator B Outcome (A OR B)
T F T
T U T
T T T
F T T
F U U
F F F
U T T
U U U
U F U

Table 3. Boolean operator outcome when logic is NOT A


Operator A Outcome (A AND B)
T F
F T
U U

The following message selector selects messages with a message type of car, color
of blue, and weight greater than 2500 lbs:
"JMSType = ’car’ AND color = ’blue’ AND weight > 250"

Although SQL supports fixed decimal comparison and arithmetic, message


selectors do not. This is why exact numeric literals are restricted to those without a
decimal. It is also why there are numerics with a decimal as an alternate
representation for an approximate numeric value.

SQL comments are not supported.

Selection string rules and restrictions:

Familiarize yourself with these rules about how selection strings are interpreted
and character restrictions to avoid potential problems when using selectors.

40 WebSphere MQ: Application Programming Guide


v Equivalence is tested using a single equals character, for example, “a == b” is
incorrect, whereas “a = b” is correct.
v An operator used by many programming languages to represent ‘not-equals’ is
‘!=’. This representation is not a valid synonym for ‘<>’, for example, “a != b” is
not valid, whereas “a <> b” is valid.
v Care must be taken to ensure that the correct type of quotes are used to contain
selectors. Single quotes are recognized only if the ‘ (U+0039) character is used,
not, ` (U+0145), for example is not recognized. Similarly, double quotes are valid
only when used to enclose byte-strings, they are not valid for other strings.
v The symbols &, &&, | and || are not synonyms for logical
conjunction/disjunction, for example. “a && b” should be specifies as “a AND
b”.
v The wildcard characters * and ? are not synonyms for % and _.
v Selectors containing compound expressions such as “20 < b < 30” are not valid.
Because where operators have the same precedence, the parser will evaluate
from left to right, so the example would become “(20 < b) < 30”, which does not
make sense. Instead the expression must be written as (b > 20) AND (b < 30).
v Byte strings must be enclosed in double quotes, if single quotes are used, the
byte string will be taken to be a string literal. The number of characters (not the
number which the characters represent) following the “0x” must be a multiple of
two.
v The keyword ‘IS’ is not a synonym for =. Thus the selection strings “a IS 3” and
“b IS ‘red’” are not valid. The ‘IS’ keyword exists only to support ‘IS NULL’ and
‘IS NOT NULL’.

Asynchronous consumption of WebSphere MQ messages


Asynchronous consumption uses a set of Message Queue Interface (MQI)
extensions that allow an MQI application to be written to consume messages from
a set of queues. Messages are delivered to the application by invoking a ‘unit of
code’, identified by the application passing either the message, or a token
representing the message.

In the most straightforward of application environments, the ‘unit of code’ is


defined by a function pointer, however in other environments the ‘unit of code’
can be defined by a program or module name.

In asynchronous consumption of messages, the following terms are used:


Message consumer
A programming construct that allows you to define a program, or function,
to be invoked with a message when one which matches the applications
requirement becomes available.
Event handler
A programming construct that allows you to define a program or function
to invoke when an asynchronous event, such as queue manager quiescing,
occurs.
Call back
A generic term used to refer to either Message Consumer or an Event
Handler routine.

This process provides a new programming style that can simplify the design and
implementation of new applications, especially those that process multiple input
queues or subscriptions.

Chapter 1. Designing applications that use WebSphere MQ 41


The following illustrations give an example of how you can use this function.

Figure 5 shows a multithreaded application consuming messages from two queues.


The example shows all of the messages being delivered to a single function.

MQCONN

OPEN (QUEUE1, &hObj1)

OPEN (QUEUE2, &hObj2)

MQCB(hObj1, func1)

MQCB(hObj2, func1)

Func1(...)
MQCTL(CONSUME_START)

Process message
Pause, perform non MQ
function. or use a
different hConn.
MQPUT1(md.ReplyQ, ...)

MQCTL(CONSUME_STOP)
return

MQDISC

Figure 5. Standard Message Driven application consuming from two queues

Figure 6 on page 43 This sample flow shows a single threaded application


consuming messages from two queues. The example shows all of the messages
being delivered to a single function.

The difference from the asynchronous case is that control doesn’t return to the
issuer of MQCTL until all of the consumers have deactivated themselves; that is
one consumer has issued an MQCTL STOP request or the queue manager quiesces.

42 WebSphere MQ: Application Programming Guide


MQCONN

OPEN (QUEUE1, &hObj1)

OPEN (QUEUE2, &hObj2)

Func1(...)
MQCB(hObj1, func1)

MQCB(hObj2, func1) Process message

MQCTL(CONSUME_START-WAIT) MQPUT1(md.ReplyQ, ...)

MQDISC return

Figure 6. Single Threaded Message Driven application consuming from two queues

Message groups
Segmentation is not supported on WebSphere MQ for z/OS.

Messages can occur within groups. This allows ordering of messages (see “Logical
and physical ordering” on page 131), and, except on WebSphere MQ for z/OS,
segmentation of large messages (see “Message segmentation” on page 144) within
the same group.

The hierarchy within a group is as follows:


Group This is the highest level in the hierarchy and is identified by a GroupId. It
consists of one or more messages that contain the same GroupId. These
messages can be stored anywhere on the queue.

Note: The term message is used here to denote one item on a queue, such
as would be returned by a single MQGET that does not specify
MQGMO_COMPLETE_MSG.
Figure 7 shows a group of logical messages:

Group

LOGMSG1 LOGMSG2 LOGMSG3

Figure 7. Group of logical messages

Chapter 1. Designing applications that use WebSphere MQ 43


Logical message
Logical messages within a group are identified by the GroupId and
MsgSeqNumber fields. The MsgSeqNumber starts at 1 for the first message
within a group, and if a message is not in a group, the value of the field is
1.
Use logical messages within a group to:
v Ensure ordering (if this is not guaranteed under the circumstances in
which the message is transmitted).
v Allow applications to group together similar messages (for example,
those that must all be processed by the same server instance).
Each message within a group consists of one physical message, unless it is
split into segments. Each message is logically a separate message, and only
the GroupId and MsgSeqNumber fields in the MQMD need bear any
relationship to other messages in the group. Other fields in the MQMD are
independent; some might be identical for all messages in the group
whereas others might be different. For example, messages in a group can
have different format names, CCSIDs, encodings, and so on.
Segment
Segments are used to handle messages that are too large for either the
putting or getting application or the queue manager (including intervening
queue managers through which the message passes). For more information
about this, see “Message segmentation” on page 144.
A segment of a message is identified by the GroupId, MsgSeqNumber, and
Offset fields. The Offset field starts at zero for the first segment within a
message.
Each segment consists of one physical message that might belong to a
group (Figure 8 shows an example of messages within a group). A segment
is logically part of a single message, so only the MsgId, Offset, and
SegmentFlag fields in the MQMD should differ between separate segments
of the same message.
Figure 8 shows a group of logical messages, some of which are segmented:

Group

LOGMSG1 LOGMSG2 LOGMSG3

SEG1 SEG2 SEG1 SEG2 SEG3

Figure 8. Segmented messages

For a description of logical and physical messages, see “Logical and physical
ordering” on page 131. For further information about segmenting messages, see
“Message segmentation” on page 144.

Message persistence
Persistent messages are written to logs and queue data files.

If a queue manager is restarted after a failure, it recovers these persistent messages


as necessary from the logged data. Messages that are not persistent are discarded if

44 WebSphere MQ: Application Programming Guide


a queue manager stops, whether the stoppage is as a result of an operator
command or because of the failure of some part of your system. Nonpersistent
messages for WebSphere MQ for z/OS stored in a coupling facility (CF) are an
exception to this. They persist as long as the CF remains available.

When you create a message, if you initialize the message descriptor (MQMD)
using the defaults, the persistence for the message is taken from the
DefPersistence attribute of the queue specified in the MQOPEN command.
Alternatively, you can set the persistence of the message using the Persistence
field of the MQMD structure to define the message as persistent or nonpersistent.

The performance of your application is affected when you use persistent messages;
the extent of the effect depends on the performance characteristics of the machine’s
I/O subsystem and how you use the syncpoint options on each platform:
v A persistent message, outside the current unit of work, is written to disk on
every put and get operation. See “Committing and backing out units of work”
on page 183.
v In WebSphere MQ on UNIX systems, WebSphere MQ for z/OS, and WebSphere
MQ for Windows, a persistent message within the current unit of work is logged
only when the unit of work is committed (and the unit of work could contain
many queue operations).

Nonpersistent messages can be used for fast messaging. See the WebSphere MQ
Application Programming Reference and WebSphere MQ Intercommunications for further
information about fast messages.

Messages that fail to be delivered


When a queue manager cannot put a message on a queue, you have various
options.

You can:
v Attempt to put the message on the queue again.
v Request that the message is returned to the sender.
v Put the message on the dead-letter queue.

See “Handling program errors” on page 62 for more information.

Messages that are backed out


When processing messages from a queue under the control of a unit of work, the
unit of work can consist of one or more messages. If a backout occurs, the
messages that were retrieved from the queue are reinstated on the queue, and they
can be processed again in another unit of work. If the processing of a particular
message is causing the problem, the unit of work is backed out again. This can
cause a processing loop. Messages that were put to a queue are removed from the
queue.

An application can detect messages that are caught up in such a loop by testing
the BackoutCount field of MQMD. The application can either correct the situation,
or issue a warning to an operator.

In WebSphere MQ for z/OS, to ensure that the backout count for private queues
survives restarts of the queue manager, set the HardenGetBackout attribute to
MQQA_BACKOUT_HARDENED; otherwise, if the queue manager has to restart, it

Chapter 1. Designing applications that use WebSphere MQ 45


does not maintain an accurate backout count for each message. Setting the
attribute this way adds the penalty of extra processing.

On WebSphere MQ for i5/OS, WebSphere MQ for Windows, WebSphere MQ on


UNIX systems, and shared queues on z/OS, the backout count always survives
restarts of the queue manager. Any change to the HardenGetBackout attribute is
ignored.

For more information on committing and backing out messages, see “Committing
and backing out units of work” on page 183.

Reply-to queue and queue manager


There are occasions when you might receive messages in response to a message
you send:
v A reply message in response to a request message
v A report message about an unexpected event or expiry
v A report message about a COA (Confirmation Of Arrival) or a COD
(Confirmation Of Delivery) event
v A report message about a PAN (Positive Action Notification) or a NAN
(Negative Action Notification) event

Using the MQMD structure, specify the name of the queue to which you want
reply and report messages sent, in the ReplyToQ field. Specify the name of the
queue manager that owns the reply-to queue in the ReplyToQMgr field.

If you leave the ReplyToQMgr field blank, the queue manager sets the contents of
the following fields in the message descriptor on the queue:
ReplyToQ
If ReplyToQ is a local definition of a remote queue, the ReplyToQ field is set
to the name of the remote queue; otherwise this field is not changed.
ReplyToQMgr
If ReplyToQ is a local definition of a remote queue, the ReplyToQMgr field is
set to the name of the queue manager that owns the remote queue;
otherwise the ReplyToQMgr field is set to the name of the queue manager to
which your application is connected.

Note: You can request that a queue manager makes more than one attempt to
deliver a message, and you can request that the message is discarded if it fails. If
the message, after failing to be delivered, is not to be discarded, the remote queue
manager puts the message on its dead-letter (undelivered message) queue (see
“Using the dead-letter (undelivered message) queue” on page 66).

Message context
Message context information allows the application that retrieves the message to
find out about the originator of the message.

The retrieving application might want to:


v Check that the sending application has the correct level of authority
v Perform some accounting function so that it can charge the sending application
for any work that it has to perform
v Keep an audit trail of all the messages that it has worked with

46 WebSphere MQ: Application Programming Guide


When you use the MQPUT or MQPUT1 call to put a message on a queue, you can
specify that the queue manager is to add some default context information to the
message descriptor. Applications that have the appropriate level of authority can
add extra context information. For more information on how to specify context
information, see “Controlling context information” on page 115.

All context information is stored in the context fields of the message descriptor.
The type of information falls into identity, origin, and user context information.

Identity context
Identity context information identifies the user of the application that first put the
message on a queue:
v The queue manager fills the UserIdentifier field with a name that identifies the
user; the way that the queue manager can do this depends on the environment
in which the application is running.
v The queue manager fills the AccountingToken field with a token or number that
it determined from the application that put the message.
v Applications can use the ApplIdentityData field for any extra information that
they want to include about the user (for example, an encrypted password).

Suitably authorized applications can set the above fields.

A Windows systems security identifier (SID) is stored in the AccountingToken field


when a message is created under WebSphere MQ for Windows. The SID can be
used to supplement the UserIdentifier field and to establish the credentials of a
user.

For information on how the queue manager fills the UserIdentifier and
AccountingToken fields, see the descriptions of these fields in the WebSphere MQ
Application Programming Reference.

Applications that pass messages from one queue manager to another should also
pass on the identity context information so that other applications know the
identity of the originator of the message.

Origin context
Origin context information describes the application that put the message on the
queue on which the message is currently stored. The message descriptor contains
the following fields for origin context information:

PutApplType The type of application that put the message (for example, a CICS
transaction).
PutApplName The name of the application that put the message (for example, the
name of a job or transaction).
PutDate The date on which the message was put on the queue.
PutTime The time at which the message was put on the queue.
ApplOriginData Any extra information that an application wants to include about
the origin of the message. For example, it could be set by suitably
authorized applications to indicate whether the identity data is
trusted.

Chapter 1. Designing applications that use WebSphere MQ 47


Origin context information is usually supplied by the queue manager. Greenwich
Mean Time (GMT) is used for the PutDate and PutTime fields. See the descriptions
of these fields in the WebSphere MQ Application Programming Reference.

An application with enough authority can provide its own context. This allows
accounting information to be preserved when a single user has a different user ID
on each of the systems that process a message that they have originated.

User context
User context allows an application to pass properties around a queue manager
network without direct support of message handles on all the intermediate
applications.

You can include any message property in the user context, by setting the Context
field of the message property descriptor (MQPD) when you make the MQSETMP
call.

WebSphere MQ objects
The WebSphere MQ objects are:
v Queue managers
v Queue-sharing groups (WebSphere MQ for z/OS only), although these are not
strictly objects.
v Queues
v Administrative topic objects
v Namelists
v Process definitions
v Authentication information objects
v Channels
v Storage classes (WebSphere MQ for z/OS only)
v Listeners
v Services (not WebSphere MQ for z/OS)
Queue managers define the properties (known as attributes) of these objects. The
values of these attributes affect the way in which WebSphere MQ processes these
objects. From your applications, you use the Message Queue Interface (MQI) to
control these objects. Objects are identified by an object descriptor (MQOD) when
addressed from a program.

When you use WebSphere MQ commands to define, alter, or delete objects, for
example, the queue manager checks that you have the required level of authority
to perform these operations. Similarly, when an application uses the MQOPEN call
to open an object, the queue manager checks that the application has the required
level of authority before it allows access to that object. The checks are made on the
name of the object being opened.

This chapter introduces WebSphere MQ objects, under these headings:


v “Queue managers” on page 49
v “Queue-sharing groups” on page 50
v “Queues” on page 50
v “Administrative topic objects” on page 58

48 WebSphere MQ: Application Programming Guide


v “Namelists” on page 59
v “Process definitions” on page 59
v “Authentication information objects” on page 59
v “Channels” on page 59
v “Storage classes” on page 60
v “Listeners” on page 60
v “Services” on page 60
v “Rules for naming WebSphere MQ objects” on page 61

Queue managers
A queue manager supplies an application with WebSphere MQ services.

A program must have a connection to a queue manager before it can use the
services of that queue manager. A program can make this connection explicitly
(using the MQCONN or MQCONNX call), or the connection might be made
implicitly (this depends on the platform and the environment in which the
program is running).

Queues belong to queue managers, but programs can send messages to queues
that belong to any queue manager.

Attributes of queue managers


Associated with each queue manager is a set of attributes (or properties) that
define its characteristics. Some of the attributes of a queue manager are fixed when
it is created; you can change others using the WebSphere MQ commands. You can
inquire about the values of all the attributes, except those used for Secure Sockets
Layer (SSL) encryption, using the MQINQ call.

The fixed attributes include:


v The name of the queue manager
v The platform on which the queue manager runs (for example, z/OS)
v The level of system control commands that the queue manager supports
v The maximum priority that you can assign to messages processed by the queue
manager
v The name of the queue to which programs can send WebSphere MQ commands
v The maximum length of messages the queue manager can process (fixed only in
WebSphere MQ for z/OS)
v Whether the queue manager supports syncpointing when programs put and get
messages

The changeable attributes include:


v A text description of the queue manager
v The identifier of the character set the queue manager uses for character strings
when it processes MQI calls
v The time interval that the queue manager uses to restrict the number of trigger
messages
v The time interval that the queue manager uses to determine how often queues
are to be scanned for expired messages (WebSphere MQ for z/OS only)
v The name of the queue manager’s dead-letter (undelivered message) queue
v The name of the queue manager’s default transmission queue

Chapter 1. Designing applications that use WebSphere MQ 49


v The maximum number of open handles for any one connection
v The enabling and disabling of various categories of event reporting
v The maximum number of uncommitted messages within a unit of work

For a full description of all the attributes, see the WebSphere MQ Application
Programming Reference.

Queue managers and workload management


You can set up a cluster of queue managers that has more than one definition for
the same queue (for example, the queue managers in the cluster could be clones of
each other). Messages for a particular queue can be handled by any queue
manager that hosts an instance of the queue. A workload-management algorithm
decides which queue manager handles the message and so spreads the workload
between your queue managers. See WebSphere MQ Queue Manager Clusters for
further information.

Queue-sharing groups
Supported only on WebSphere MQ for z/OS.

Queue-sharing groups are not strictly objects, but are mentioned here for
convenience.

Queue managers that can access the same set of shared queues form a group called
a queue-sharing group (QSG), and they communicate with each other by means of a
coupling facility (CF) that stores the shared queues. A shared queue is a type of local
queue whose messages can be accessed by one or more queue managers that are in
a queue-sharing group. (This is not the same as a queue being shared by more than
one application, using the same queue manager.) See the WebSphere MQ for z/OS
Concepts and Planning Guide for a full discussion of shared queues and
queue-sharing groups.

Queues
A WebSphere MQ queue is a named object on which applications can put messages,
and from which applications can get messages.

Messages are stored on a queue, so that if the putting application is expecting a


reply to its message, it is free to do other work while waiting for that reply.
Applications access a queue by using the Message Queue Interface (MQI),
described in “Introducing the Message Queue Interface” on page 69.

Before a message can be put on a queue, the queue must have already been
created. A queue is owned by a queue manager, and that queue manager can own
many queues. However, each queue must have a name that is unique within that
queue manager.

A queue is maintained through a queue manager. In most cases, each queue is


physically managed by its queue manager but this is transparent to an application
program. WebSphere MQ for z/OS shared queues can be managed by any queue
manager in the queue-sharing group.

To create a queue you can use WebSphere MQ commands (MQSC), PCF


commands, or platform-specific interfaces such as the WebSphere MQ for z/OS
operations and control panels.

50 WebSphere MQ: Application Programming Guide


You can create local queues for temporary jobs dynamically from your application.
For example, you can create reply-to queues (which are not needed after an
application ends). For more information, see “Dynamic queues” on page 55.

Before using a queue, you must open the queue, specifying what you want to do
with it. For example, you can open a queue for:
v Browsing messages only (not retrieving them)
v Retrieving messages (and either sharing the access with other programs, or with
exclusive access)
v Putting messages on the queue
v Inquiring about the attributes of the queue
v Setting the attributes of the queue

For a complete list of the options that you can specify when you open a queue, see
the description of the MQOPEN call in the WebSphere MQ Application Programming
Reference.

Types of queue
The types of queue that WebSphere MQ supports for applications to use are:
Local and remote queues
A queue is known to a program as local if it is owned by the queue
manager to which the program is connected; the queue is known as remote
if it is owned by a different queue manager. The important difference
between these two types of queue is that you can get messages only from
local queues. (You can put messages on both types of queue.)
The queue definition object, created when you define a local queue, holds
the definition information of the queue as well as the physical messages
put on the queue. The queue definition object, created when you define a
remote queue, only holds the information necessary for the local queue
manager to locate the queue to which you want your message to go. This
object is known as the local definition of a remote queue. All the attributes of
the remote queue are held by the queue manager that owns it, because it is
a local queue to that queue manager.
Shared queues
Shared queues are available only on WebSphere MQ for z/OS.
A shared queue is a type of local queue whose messages can be accessed by
one or more queue managers that are in a queue-sharing group. (This is
not the same as a queue being shared by more than one application, using
the same queue manager.) Shared queues are held by a coupling facility
(CF), and are accessible by any queue manager in the queue-sharing group.
Each shared queue in a queue-sharing group must have a name that is
unique within that group. See the WebSphere MQ for z/OS Concepts and
Planning Guide for a full discussion of shared queues and queue-sharing
groups.
Alias queues
To your program, an alias queue appears to be a queue, but it is really a
WebSphere MQ object that you can use to access another queue or a topic.
This means that more than one program can work with the same queue,
accessing it using different names. For more information about topic
aliases, see WebSphere MQ Publish/Subscribe User’s Guide.

Chapter 1. Designing applications that use WebSphere MQ 51


Model and dynamic queues
A model queue is a template of a queue definition used only when you
want to create a dynamic local queue.
You can create a local queue dynamically from a WebSphere MQ program,
naming the model queue that you want to use as the template for the
queue attributes. At that point you can change some attributes of the new
queue. However, you cannot change the DefinitionType. If, for example, you
require a permanent queue, select a model queue with the definition type
set to permanent. Some conversational applications can use dynamic
queues to hold replies to their queries because they probably do not need
to maintain these queues after they have processed the replies.
Cluster queues
A cluster queue is a queue that is hosted by a cluster queue manager and
made available to other queue managers in the cluster.
The cluster queue manager makes a local queue definition for the queue
specifying the name of the cluster that the queue is to be available in. This
definition has the effect of advertising the queue to the other queue
managers in the cluster. The other queue managers in the cluster can put
messages to a cluster queue without needing a corresponding
remote-queue definition. A cluster queue can be advertised in more than
one cluster. See “What is a cluster?” on page 3 and WebSphere MQ Queue
Manager Clusters for further information.

Types of local queue:

Each queue manager can have some local queues that it uses for special purposes:
Transmission queues
A transmission queue is a local queue that holds messages destined for a
remote queue. The messages are forwarded to their destination queue by
WebSphere MQ when a communication program and link are available.
Initiation queues
An initiation queue is a local queue on which the queue manager puts a
message to start an application when certain conditions (such as more than
10 messages arriving, for example) are met on a local queue.
Dead-letter (undelivered message) queue
The dead-letter queue is a local queue on which the queue manager and
applications put messages they cannot deliver. You need to process any
messages that arrive on this queue.
System command queue
The system command queue is a queue to which suitably authorized
applications can send WebSphere MQ commands.
System default queues
When you create a queue (other than a dynamic queue), WebSphere MQ
uses the queue definitions stored in the system default queues.
Channel queues
Channel queues are used for distributed queue management.
Event queues
Event queues hold event messages. These messages are reported by the
queue manager or a channel.

These special queues are described in greater detail in the following sections.

52 WebSphere MQ: Application Programming Guide


Attributes of queues
Some of the attributes of a queue are specified when the queue is defined, and
cannot be changed afterwards (for example, the type of the queue). Other
attributes of queues can be grouped into those that can be changed:
v By the queue manager during the processing of the queue (for example, the
current depth of a queue)
v Only by commands (for example, the text description of the queue)
v By applications, using the MQSET call (for example, whether or not put
operations are allowed on the queue)

You can find the values of all the attributes using the MQINQ call.

The attributes that are common to more than one type of queue are:
QName Name of the queue
QType Type of the queue
QDesc Text description of the queue
InhibitGet
Whether or not programs are allowed to get messages from the queue
(although you can never get messages from remote queues)
InhibitPut
Whether or not programs are allowed to put messages on the queue
DefPriority
Default priority for messages put on the queue
DefPersistence
Default persistence for messages put on the queue
Scope (not supported on z/OS)
Controls whether an entry for this queue also exists in a name service

For a full description of these attributes, see the WebSphere MQ Application


Programming Reference.

Remote queues
To a program, a queue is remote if it is owned by a different queue manager to the
one to which the program is connected.

Where a communication link has been established, a program can send a message
to a remote queue. A program can never get a message from a remote queue.

When opening a remote queue, to identify the queue you must specify either:
v The name of the local definition that defines the remote queue.
To create a local definition of a remote queue use the DEFINE QREMOTE
command; on WebSphere MQ for i5/OS, use the CRTMQMQ command.
From the viewpoint of an application, this is the same as opening a local queue.
An application does not need to know if a queue is local or remote.
v The name of the remote queue manager and the name of the queue as it is
known to that remote queue manager.

Local definitions of remote queues have three attributes in addition to the common
attributes described in “Attributes of queues.” These are RemoteQName (the name

Chapter 1. Designing applications that use WebSphere MQ 53


that the queue’s owning queue manager knows it by), RemoteQMgrName (the name
of the owning queue manager), and XmitQName (the name of the local transmission
queue that is used when forwarding messages to other queue managers). For a
fuller description of these attributes, see the WebSphere MQ Application Programming
Reference.

If you use the MQINQ call against the local definition of a remote queue, the
queue manager returns the attributes of the local definition only, that is the remote
queue name, the remote queue manager name, and the transmission queue name,
not the attributes of the matching local queue in the remote system.

See also “Transmission queues” on page 57.

Alias queues
An alias queue is a WebSphere MQ object that you can use to access another queue
or a topic.

The queue resulting from the resolution of an alias name (known as the base
queue) can be a local queue, the local definition of a remote queue, or a shared
queue (a type of local queue only available on WebSphere MQ for z/OS). It can
also be either a predefined queue or a dynamic queue, as supported by the
platform.

An alias name can also resolve to a topic. If an application currently puts messages
onto a queue, it can be made to publish to a topic by making the queue name an
alias for the topic. No change to the application code is necessary. For more
information about topic aliases, see WebSphere MQ Publish/Subscribe User’s Guide.

Note: An alias cannot resolve to another alias.

An example of the use of alias queues is for a system administrator to give


different access authorities to the base queue name (that is, the queue to which the
alias resolves) and to the alias queue name. This means that a program or user can
be authorized to use the alias queue, but not the base queue.

Alternatively, authorization can be set to inhibit put operations for the alias name,
but allow them for the base queue.

In some applications, the use of alias queues means that system administrators can
easily change the definition of an alias queue object without having to get the
application changed.

WebSphere MQ makes authorization checks against the alias name when programs
try to use that name. It does not check that the program is authorized to access the
name to which the alias resolves. A program can therefore be authorized to access
an alias queue name, but not the resolved queue name.

In addition to the general queue attributes described in “Attributes of queues” on


page 53, alias queues have a BaseQName attribute. This is the name of the base
queue to which the alias name resolves. For a fuller description of this attribute,
see the WebSphere MQ Application Programming Reference.

The InhibitGet and InhibitPut attributes (see “Attributes of queues” on page 53)
of alias queues belong to the alias name. For example, if the alias-queue name

54 WebSphere MQ: Application Programming Guide


ALIAS1 resolves to the base-queue name BASE, inhibitions on ALIAS1 affect
ALIAS1 only and BASE is not inhibited. However, inhibitions on BASE also affect
ALIAS1.

The DefPriority and DefPersistence attributes also belong to the alias name. So,
for example, you can assign different default priorities to different aliases of the
same base queue. Also, you can change these priorities without having to change
the applications that use the aliases.

Model queues
A model queue is a template of a queue definition that you use when creating a
dynamic queue.

You specify the name of a model queue in the object descriptor (MQOD) of your
MQOPEN call. Using the attributes of the model queue, the queue manager
dynamically creates a local queue for you.

You can specify a name (in full) for the dynamic queue, or the stem of a name (for
example, ABC) and let the queue manager add a unique part to this, or you can let
the queue manager assign a complete unique name for you. If the queue manager
assigns the name, it puts it in the MQOD structure.

You cannot issue an MQPUT1 call directly to a model queue , but you can issue an
MQPUT1 to the dynamic queue that has been created by opening a model queue.

The attributes of a model queue are a subset of those of a local queue. For a fuller
description, see the WebSphere MQ Application Programming Reference.

Dynamic queues
When an application program issues an MQOPEN call to open a model queue, the
queue manager dynamically creates an instance of a local queue with the same
attributes as the model queue.

Depending on the value of the DefinitionType field of the model queue, the queue
manager creates either a temporary or permanent dynamic queue (See “Creating
dynamic queues” on page 107).

Properties of temporary dynamic queues:

Temporary dynamic queues have the following properties:


v They cannot be shared queues, accessible from queue managers in a
queue-sharing group (only available on WebSphere MQ for z/OS).
v They hold nonpersistent messages only.
v They are non-recoverable.
v They are deleted when the queue manager is started.
v They are deleted when the application that issued the MQOPEN call that created
the queue closes the queue or terminates.
– If there are any committed messages on the queue, they are deleted.
– If there are any uncommitted MQGET, MQPUT, or MQPUT1 calls outstanding
against the queue at this time, the queue is marked as being logically deleted,
and is only physically deleted (after these calls have been committed) as part
of close processing, or when the application terminates.

Chapter 1. Designing applications that use WebSphere MQ 55


– If the queue is in use at this time (by the creating, or another application), the
queue is marked as being logically deleted, and is only physically deleted
when closed by the last application using the queue.
– Attempts to access a logically deleted queue (other than to close it) fail with
reason code MQRC_Q_DELETED.
– MQCO_NONE, MQCO_DELETE and MQCO_DELETE_PURGE are all treated
as MQCO_NONE when specified on an MQCLOSE call for the corresponding
MQOPEN call that created the queue.

Properties of permanent dynamic queues:

Permanent dynamic queues have the following properties:


v They hold persistent or nonpersistent messages.
v They are recoverable in the event of system failures.
v They are deleted when an application (not necessarily the one that issued the
MQOPEN call that created the queue) successfully closes the queue using the
MQCO_DELETE or MQCO_DELETE_PURGE option.
– A close request with the MQCO_DELETE option fails if there are any
messages (committed or uncommitted) still on the queue. A close request with
the MQCO_DELETE_PURGE option succeeds even if there are committed
messages on the queue (the messages being deleted as part of the close), but
fails if there are any uncommitted MQGET, MQPUT, or MQPUT1 calls
outstanding against the queue.
– If the delete request is successful, but the queue happens to be in use (by the
creating, or another application), the queue is marked as being logically
deleted and is only physically deleted when closed by the last application
using the queue.
v They are not deleted if closed by an application that is not authorized to delete
the queue, unless the closing application issued the MQOPEN call that created
the queue. Authorization checks are performed against the user identifier (or
alternate user identifier if MQOO_ALTERNATE_USER_AUTHORITY was
specified) that was used to validate the corresponding MQOPEN call.
v They can be deleted in the same way as a normal queue.

Uses of dynamic queues:

You can use dynamic queues for:


v Applications that do not require queues to be retained after the application has
terminated.
v Applications that require replies to messages to be processed by another
application. Such applications can dynamically create a reply-to queue by
opening a model queue. For example, a client application can:
1. Create a dynamic queue.
2. Supply its name in the ReplyToQ field of the message descriptor structure of
the request message.
3. Place the request on a queue being processed by a server.

The server can then place the reply message on the reply-to queue. Finally, the
client could process the reply, and close the reply-to queue with the delete option.

Recommendations for uses of dynamic queues:

Consider the following points when using dynamic queues:

56 WebSphere MQ: Application Programming Guide


v In a client-server model, each client must create and use its own dynamic
reply-to queue. If a dynamic reply-to queue is shared between more than one
client, deleting the reply-to queue might be delayed because there is
uncommitted activity outstanding against the queue, or because the queue is in
use by another client. Additionally, the queue might be marked as being
logically deleted, and inaccessible for subsequent API requests (other than
MQCLOSE).
v If your application environment requires that dynamic queues must be shared
between applications, ensure that the queue is only closed (with the delete
option) when all activity against the queue has been committed. This should be
by the last user. This ensures that deletion of the queue is not delayed, and
minimizes the period that the queue is inaccessible because it has been marked
as being logically deleted.

Transmission queues
When an application sends a message to a remote queue, the local queue manager
stores the message in a special local queue, called a transmission queue.

A message channel agent (channel program), or intra-group queuing agent when using
intra-group queuing on WebSphere MQ for z/OS, is associated with the
transmission queue and the remote queue manager, and this delivers the message.
When the message has been delivered, it is deleted from the transmission queue.

The message might have to pass through many queue managers (or nodes) on its
journey to its final destination. There must be a transmission queue defined at each
queue manager along the route, each holding messages waiting to be transmitted
to the next node. (A shared transmission queue is used when using intra-group
queuing on WebSphere MQ for z/OS.) There can be several transmission queues
defined at a particular queue manager. A given transmission queue holds messages
whose next destination is the same queue manager, although the messages might
have different eventual destinations. There might also be several transmission
queues for the same remote queue manager, with each one being used for a
different type of service, for example.

Transmission queues can be used to trigger a message channel agent to send


messages onward. For information about this, see “Starting WebSphere MQ
applications using triggers” on page 195. These attributes are defined in the
transmission queue definition (for triggered channels) or the process definition
object (see “Process definitions” on page 59).

Initiation queues
An initiation queue is a local queue on which the queue manager puts a trigger
message when a trigger event occurs on an application queue.

A trigger event is an event (for example, more than 10 messages arriving) that an
application designer intends the queue manager to use as a cue, or trigger, to start
a program to process the queue. For more information on how triggering works,
see “Starting WebSphere MQ applications using triggers” on page 195.

Dead-letter (undelivered message) queues


A dead-letter (undelivered message) queue is a local queue on which the queue
manager puts messages that it cannot deliver.

When the queue manager puts a message on the dead-letter queue, it adds a
header to the message. This includes such information as the intended destination

Chapter 1. Designing applications that use WebSphere MQ 57


of the original message, the reason that the queue manager put the message on the
dead-letter queue, and the date and time that it did this.

Applications can also use the queue for messages that they cannot deliver. For
more information, see “Using the dead-letter (undelivered message) queue” on
page 66.

System command queues


These queues receive the PCF, MQSC, and CL commands, as supported on your
platform, in readiness for the queue manager to action them.

On WebSphere MQ for z/OS the queue is known as the


SYSTEM.COMMAND.INPUT.QUEUE; on other platforms it is known as the
SYSTEM.ADMIN.COMMAND.QUEUE. The commands accepted vary by
platform. See WebSphere MQ Programmable Command Formats and Administration
Interface for details.

System default queues


The system default queues contain the initial definitions of the queues for your
system. When you create a new queue, the queue manager copies the definition
from the appropriate system default queue.

Administrative topic objects


An administrative topic object is a WebSphere MQ object that allows you to assign
specific, non-default attributes to topics.

A topic is defined by an application publishing or subscribing to a particular topic


string. A topic string can specify a hierarchy of topics by separating them with a
forward slash character (/). This can be visualized by a topic tree. For example, if
an application publishes to the topic strings /Sport/American Football and
/Sport/Soccer, a topic tree will be created that has a parent node Sport with two
children, American Football, and Soccer.

Topics inherit their attributes from the first parent administrative node found in
their topic tree. If there are no administrative topic nodes in a particular topic tree,
then all topics will inherit their attributes from the base topic object,
SYSTEM.BASE.TOPIC.

You can create an administrative topic object at any node in a topic tree by
specifying that node’s topic string in the TOPICSTR attribute of the administrative
topic object. You can also define other attributes for the administrative topic node.
For more information about these attributes, see the WebSphere MQ Script (MQSC)
Command Reference, or the WebSphere MQ Programmable Command Formats and
Administration Interface. Each administrative topic object will, by default, inherit its
attributes from its closest parent administrative topic node.

Administrative topic objects can also be used to hide the full topic tree from
application developers. If an administrative topic object named FOOTBALL.US is
created for the topic /Sport/American Football, an application can publish or
subscribe to the object name FOOTBALL.US instead of the string /Sport/American
Football with the same result.

If you enter a #, +, /, or * character within a topic string on a topic object, the


character is treated as a normal character within the string, and is considered to be
part of the topic string associated with an administrative topic object.

58 WebSphere MQ: Application Programming Guide


For more information about administrative topic objects, see the WebSphere MQ
Publish/Subscribe User’s Guide.

Namelists
A namelist is a WebSphere MQ object that contains a list of cluster names, queue
names or authentication information object names. In a cluster, it can be used to
identify a list of clusters for which the queue manager holds the repositories.

You can define and modify namelists only using the operations and control panels
of WebSphere MQ for z/OS or MQSC commands.

Programs can use the MQI to find out which queues are included in these
namelists. The organization of the namelists is the responsibility of the application
designer and system administrator.

For a full description of the attributes of namelists, see the WebSphere MQ


Application Programming Reference.

Process definitions
To allow an application to be started without the need for operator intervention
(described in “Starting WebSphere MQ applications using triggers” on page 195),
the attributes of the application must be known to the queue manager. These
attributes are defined in a process definition object.

The ProcessName attribute is fixed when the object is created; you can change the
others using the WebSphere MQ commands or the WebSphere MQ for z/OS
operations and control panels. You can inquire about the values of all the attributes
using the MQINQ call.

For a full description of the attributes of process definitions, see the WebSphere MQ
Application Programming Reference.

Authentication information objects


An authentication information object contains authentication information used in
Secure Sockets Layer (SSL) encrypted transport of information.

An authentication information object of AUTHTYPE CRLLDAP provides the


definitions required to perform Certificate Revocation List (CRL) checking using
LDAP servers. CRLs allow Certification Authorities to revoke certificates that can
no longer be trusted.

For a full description of the attributes of authentication information objects, see the
WebSphere MQ Application Programming Reference. For more information about SSL,
see WebSphere MQ Security.

Channels
A channel is a communication link used by distributed queue managers.

There are two categories of channel in WebSphere MQ:


v Message channels, which are unidirectional, and transfer messages from one
queue manager to another.

Chapter 1. Designing applications that use WebSphere MQ 59


v MQI channels, which are bidirectional, and transfer MQI calls from a WebSphere
MQ client to a queue manager, and responses from a queue manager to a
WebSphere MQ client.

You need to consider these when designing your application, but programs are
unaware of WebSphere MQ channel objects. For more information, see WebSphere
MQ Intercommunications and WebSphere MQ Clients.

Storage classes
Supported only on WebSphere MQ for z/OS.

A storage class maps one or more queues to a page set. This means that messages
for that queue are stored (subject to buffering) on that page set.

For further information about storage classes, see the WebSphere MQ for z/OS
Concepts and Planning Guide.

Listeners
Listeners are processes that accept network requests from other queue managers, or
client applications, and start associated channels.

Listener processes can be started using the runmqlsr control command. Listeners
are available on all platforms.

Listener objects are WebSphere MQ objects that allow you to manage the starting
and stopping of listener processes from within the scope of a queue manager.
Listener objects are not supported on WebSphere MQ for z/OS. By defining
attributes of a listener object you do the following:
v Configure the listener process.
v Specify whether the listener process automatically starts and stops when the
queue manager starts and stops.

Services
Service objects are a way of defining programs to be executed when a queue
manager starts or stops.

Not supported on WebSphere MQ for z/OS.

The programs can be split into the following types:


Servers
A server is a service object that has the parameter SERVTYPE specified as
SERVER. A server service object is the definition of a program that will be
executed when a specified queue manager is started. Only one instance of
a server process can be executed concurrently. While running, the status of
a server process can be monitored using the MQSC command, DISPLAY
SVSTATUS. Typically server service objects are definitions of programs
such as dead letter handlers or trigger monitors, however the programs
that can be run are not limited to those supplied with WebSphere MQ.
Additionally, a server service object can be defined to include a command
that will be run when the specified queue manager is shutdown to end the
program.

60 WebSphere MQ: Application Programming Guide


Commands
A command is a service object that has the parameter SERVTYPE specified
as COMMAND. A command service object is the definition of a program
that will be executed when a specified queue manager is started or
stopped. Multiple instances of a command process can be executed
concurrently. Command service objects differ from server service objects in
that once the program is executed the queue manager will not monitor the
program. Typically command service objects are definitions of programs
that are short lived and will perform a specific task such as starting one, or
more, other tasks.

Rules for naming WebSphere MQ objects


A WebSphere MQ queue, process definition, namelist, and channel can all have the
same name. However, a WebSphere MQ object cannot have the same name as any
other object of the same type. Names in WebSphere MQ are case sensitive.

The character set to use for naming all WebSphere MQ objects is as follows:
v Uppercase A–Z
v Lowercase a–z (but there are restrictions on the use of lowercase letters for z/OS
console support)
On systems using EBCDIC Katakana you cannot use lowercase characters.
v Numerics 0–9
v Period (.)
v Forward slash (/)
v Underscore (_)
v Percent sign (%)

Note:
1. Leading or embedded blanks are not allowed.
2. Avoid using names with leading or trailing underscores, because they cannot
be handled by the WebSphere MQ for z/OS operations and control panels.
3. Any name that is less than the full field length can be padded to the right with
blanks. All short names that are returned by the queue manager are always
padded to the right with blanks.
4. Any structure to the names (for example, the use of the period or underscore)
is not significant to the queue manager.
5. On i5/OS systems, within CL, lowercase a-z, forward slash (/), and percent (%)
are special characters. If you use any of these characters in a name, enclose the
name in quotation marks. Lowercase a-z characters are changed to uppercase if
the name is not enclosed in quotation marks.
6. On Windows systems, the first character of a queue manager name cannot be a
forward slash (/).

Queue names
The name of a queue has two parts:
v The name of a queue manager
v The local name of the queue as it is known to that queue manager

Each part of the queue name is 48 characters long.

Chapter 1. Designing applications that use WebSphere MQ 61


To refer to a local queue, you can omit the name of the queue manager (by
replacing it with blank characters or using a leading null character). However, all
queue names returned to a program by WebSphere MQ contain the name of the
queue manager.

A shared queue, accessible to any queue manager in its queue-sharing group,


cannot have the same name as any non-shared local queue in the same
queue-sharing group. This restriction avoids the possibility of an application
mistakenly opening a shared queue when it intended to open a local queue, or vice
versa. Shared queues and queue-sharing groups are only available on WebSphere
MQ for z/OS.

To refer to a remote queue, a program must include the name of the queue
manager in the full queue name, or there must be a local definition of the remote
queue.

When an application uses a queue name, that name can be either the name of a
local queue (or an alias to one) or the name of a local definition of a remote queue,
but the application does not need to know which, unless it needs to get a message
from the queue (when the queue must be local). When the application opens the
queue object, the MQOPEN call performs a name resolution function to determine
on which queue to perform subsequent operations. The significance of this is that
the application has no built-in dependency on particular queues being defined at
particular locations in a network of queue managers. Therefore, if a system
administrator relocates queues in the network, and changes their definitions, the
applications that use those queues do not need to be changed.

Process definition, authentication information object, and


namelist names
Process definitions, authentication information objects, and namelists can have
names up to 48 characters long.

Channel names
Channels can have names up to 20 characters long.

See WebSphere MQ Intercommunications for further information on channels.

Reserved object names


Names that start with SYSTEM. are reserved for objects defined by the queue
manager.

Handling program errors


Your application can encounter errors associated with its MQI calls either when it
makes a call or when its message is delivered to its final destination:
v Whenever possible, the queue manager returns any errors as soon as an MQI
call is made. These are locally determined errors.
v When sending messages to a remote queue, errors might not be apparent when
the MQI call is made. In this case, the queue manager that identifies the errors
reports them by sending another message to the originating program. These are
remotely determined errors.

This chapter gives advice on how to handle both types of error, under these
headings:
v “Locally determined errors” on page 63

62 WebSphere MQ: Application Programming Guide


v “Using report messages for problem determination” on page 65
v “Remotely determined errors” on page 66

Locally determined errors


The three most common causes of errors that the queue manager can report
immediately are:
v Failure of an MQI call; for example, because a queue is full
v An interruption to the running of some part of the system on which your
application depends; for example, the queue manager
v Messages containing data that cannot be processed successfully

If you are using the asynchronous put facility, errors are not reported immediately.
Use the MQSTAT call to retrieve status information about previous asynchronous
put operations.

Failure of an MQI call


The queue manager can report immediately any errors in the coding of an MQI
call. It does this using a set of predefined return codes. These are divided into
completion codes and reason codes.

To show whether or not a call is successful, the queue manager returns a completion
code when the call completes. There are three completion codes, indicating success,
partial completion, and failure of the call. The queue manager also returns a reason
code that indicates the reason for the partial completion or the failure of the call.

The completion and reason codes for each call are listed with the description of
that call in the WebSphere MQ Application Programming Reference. For more detailed
information, including ideas for corrective action, see:
v WebSphere MQ for z/OS Messages and Codes for WebSphere MQ for z/OS
v WebSphere MQ Messages for all other WebSphere MQ platforms
Design your programs to handle all the return codes that can arise from each call.

System interruptions
Your application might be unaware of any interruption if the queue manager to
which it is connected has to recover from a system failure. However, you must
design your application to ensure that your data is not lost if such an interruption
occurs.

The methods that you can use to make sure that your data remains consistent
depends on the platform on which your queue manager is running:
z/OS In the CICS and IMS environments, you can make MQPUT and MQGET
calls within units of work that are managed by CICS or IMS. In the batch
environment, you can make MQPUT and MQGET calls in the same way,
but you must declare syncpoints using:
v The WebSphere MQ for z/OS MQCMIT and MQBACK calls (see
“Committing and backing out units of work” on page 183), or
v The z/OS Transaction Management and Recoverable Resource Manager
Services (RRS) to provide two-phase syncpoint support. RRS allows you
to update both WebSphere MQ and other RRS-enabled product
resources, such as DB2 stored procedure resources, within a single

Chapter 1. Designing applications that use WebSphere MQ 63


logical unit of work. For information on RRS syncpoint support see
“Transaction management and recoverable resource manager services”
on page 187.
i5/OS You can make your MQPUT and MQGET calls within global units of work
that are managed by i5/OS commitment control. You can declare
syncpoints by using the native i5/OS COMMIT and ROLLBACK
commands or the language-specific commands. Local units of work are
managed by WebSphere MQ using the MQCMIT and MQBACK calls.
UNIX systems and Windows systems
In these environments, you can make your MQPUT and MQGET calls in
the usual way, but you must declare syncpoints by using the MQCMIT and
MQBACK calls (see “Committing and backing out units of work” on page
183). In the CICS environment, MQCMIT and MQBACK commands are
disabled, because you can make your MQPUT and MQGET calls within
units of work that are managed by CICS.

Use persistent messages for carrying all data that you cannot afford to lose.
Persistent messages are reinstated on queues if the queue manager has to recover
from a failure. With WebSphere MQ on UNIX systems and WebSphere MQ for
Windows, an MQGET or MQPUT call within your application will fail at the point
of filling all the log files, with the message MQRC_RESOURCE_PROBLEM. For
more information on log files on AIX, HP-UX, Linux, Solaris, and Windows
systems, see the WebSphere MQ System Administration Guide; for z/OS see the
WebSphere MQ for z/OS Concepts and Planning Guide.

If the queue manager is stopped by an operator while an application is running,


the quiesce option is usually used. The queue manager enters a quiescing state in
which applications can continue to do work, but they must terminate as soon as
convenient. Small, quick applications can probably ignore the quiescing state and
continue until they terminate as normal. Longer running applications, or ones that
wait for messages to arrive, should use the fail if quiescing option when they use
the MQOPEN, MQPUT, MQPUT1, and MQGET calls. These options mean that the
calls fail when the queue manager quiesces, but the application might still have
time to terminate cleanly by issuing calls that ignore the quiescing state. Such
applications could also commit, or back out, changes that they have made, and
then terminate.

If the queue manager is forced to stop (that is, stop without quiescing),
applications will receive the MQRC_CONNECTION_BROKEN reason code when
they make MQI calls. At this point, exit the application or, alternatively, on
WebSphere MQ for i5/OS, WebSphere MQ on UNIX systems, and WebSphere MQ
for Windows, issue an MQDISC call.

Messages containing incorrect data


When you use units of work in your application, if a program cannot successfully
process a message that it retrieves from a queue, the MQGET call is backed out.

The queue manager maintains a count (in the BackoutCount field of the message
descriptor) of the number of times that happens. It maintains this count in the
descriptor of each message that is affected. This count can provide valuable
information about the efficiency of an application. Messages whose backout counts
are increasing over time are being repeatedly rejected; design your application so
that it analyzes the reasons for this and handles such messages accordingly.

64 WebSphere MQ: Application Programming Guide


On WebSphere MQ for z/OS, to make the backout count survive restarts of the
queue manager, set the HardenGetBackout attribute to
MQQA_BACKOUT_HARDENED; otherwise, if the queue manager has to restart, it
does not maintain an accurate backout count for each message. Setting the
attribute this way adds the penalty of extra processing.

On WebSphere MQ for i5/OS, WebSphere MQ for Windows, and WebSphere MQ


on UNIX systems, the backout count always survives restarts of the queue
manager.

Also, on WebSphere MQ for z/OS, when you remove messages from a queue
within a unit of work, you can mark one message so that it is not made available
again if the unit of work is backed out by the application. The marked message is
treated as if it has been retrieved under a new unit of work. You mark the message
that is to skip backout using the MQGMO_MARK_SKIP_BACKOUT option (in the
MQGMO structure) when you use the MQGET call. See “Skipping backout” on
page 152 for more information about this technique.

Using report messages for problem determination


The remote queue manager cannot report errors such as failing to put a message
on a queue when you make your MQI call, but it can send you a report message
to say how it has processed your message.

Within your application you can create (MQPUT) report messages as well as select
the option to receive them (in which case they are sent by either another
application or by a queue manager).

Creating report messages


Report messages enable an application to tell another application that it cannot
deal with the message that was sent.

However, the Report field must initially be analyzed to determine whether the
application that sent the message is interested in being informed of any problems.
Having determined that a report message is required, you have to decide:
v Whether you want to include the entire original message, just the first 100 bytes
of data, or none of the original message.
v What to do with the original message. You can discard it or let it go to the
dead-letter queue.
v Whether the contents of the MsgId and CorrelId fields are needed as well.

Use the Feedback field to indicate the reason for the report message being
generated. Put your report messages on an application’s reply-to queue. Refer to
the WebSphere MQ Application Programming Reference for further information.

Requesting and receiving (MQGET) report messages:

When you send a message to another application, you are not informed of any
problems unless you complete the Report field to indicate the feedback that you
require. The options available to you are in the WebSphere MQ Application
Programming Reference.

Queue managers always put report messages on an application’s reply-to queue


and it is recommended that your own applications do the same. When you use the
report message facility, specify the name of your reply-to queue in the message
descriptor of your message; otherwise, the MQPUT call fails.

Chapter 1. Designing applications that use WebSphere MQ 65


Your application must contain procedures that monitor your reply-to queue and
process any messages that arrive on it. Remember that a report message can
contain all the original message, the first 100 bytes of the original message, or none
of the original message.

The queue manager sets the Feedback field of the report message to indicate the
reason for the error; for example, the target queue does not exist. Your programs
should do the same.

For more information on report messages, see “Report messages” on page 19.

Remotely determined errors


When you send messages to a remote queue, even when the local queue manager
has processed your MQI call without finding an error, other factors can influence
how your message is handled by a remote queue manager.

For example, the queue that you are targeting might be full, or might not even
exist. If your message has to be handled by other intermediate queue managers on
the route to the target queue, any of these could find an error.

Problems delivering a message


When an MQPUT call fails, you can try to put the message on the queue again,
return it to the sender, or put it on the dead-letter queue.

Each option has its merits, but you might not want to retry putting a message if
the reason that the MQPUT failed was because the destination queue was full. In
this instance, putting it on the dead-letter queue allows you to deliver it to the
correct destination queue later on.

Retry message delivery:

Before the message is put on a dead-letter queue, a remote queue manager


attempts to put the message on the queue again if the attributes MsgRetryCount
and MsgRetryInterval have been set for the channel, or if there is a retry exit
program for it to use (the name of which is held in the channel attribute
MsgRetryExitId field).

If the MsgRetryExitId field is blank, the values in the attributes MsgRetryCount and
MsgRetryInterval are used.

If the MsgRetryExitId field is not blank, the exit program of this name runs. For
more information on using your own exit programs, see WebSphere MQ
Intercommunications.

Return message to sender:

You return a message to the sender by requesting a report message to be generated


to include all of the original message.

See “Report messages” on page 19 for details on report message options.

Using the dead-letter (undelivered message) queue


When a queue manager cannot deliver a message, it attempts to put the message
on its dead-letter queue. This queue should be defined when the queue manager is
installed.

66 WebSphere MQ: Application Programming Guide


Your programs can use the dead-letter queue in the same way that the queue
manager uses it. You can find the name of the dead-letter queue by opening the
queue manager object (using the MQOPEN call) and inquiring about the
DeadLetterQName attribute (using the MQINQ call).

When the queue manager puts a message on this queue, it adds a header to the
message, the format of which is described by the dead-letter header (MQDLH)
structure, in the WebSphere MQ Application Programming Reference. This header
includes the name of the target queue and the reason that the message was put on
the dead-letter queue. It must be removed and the problem must be resolved
before the message is put on the intended queue. Also, the queue manager changes
the Format field of the message descriptor (MQMD) to indicate that the message
contains an MQDLH structure.

MQDLH structure

You are recommended to add an MQDLH structure to all messages that you put
on the dead-letter queue; however, if you intend to use the dead-letter handler
provided by certain WebSphere MQ products, you must add an MQDLH structure
to your messages.

The addition of the header to a message might make the message too long for the
dead-letter queue, so always make sure that your messages are shorter than the
maximum size allowed for the dead-letter queue, by at least the value of the
MQ_MSG_HEADER_LENGTH constant. The maximum size of messages allowed
on a queue is determined by the value of the MaxMsgLength attribute of the queue.
For the dead-letter queue, make sure that this attribute is set to the maximum
allowed by the queue manager. If your application cannot deliver a message, and
the message is too long to be put on the dead-letter queue, follow the advice given
in the description of the MQDLH structure.

Ensure that the dead-letter queue is monitored, and that any messages arriving on
it get processed. The dead-letter queue handler runs as a batch utility and can be
used to perform various actions on selected messages on the dead-letter queue. For
further details, see WebSphere MQ System Administration Guide for WebSphere MQ
for AIX, HP-UX, Linux, Solaris, and Windows systems; for WebSphere MQ for
z/OS see WebSphere MQ for z/OS System Administration Guide; for i5/OS see
WebSphere MQ for i5/OS System Administration Guide.

If data conversion is necessary, the queue manager converts the header information
when you use the MQGMO_CONVERT option on the MQGET call. If the process
putting the message is an MCA, the header is followed by all the text of the
original message.

Messages put on the dead-letter queue might be truncated if they are too long for
this queue. A possible indication of this situation is the messages on the dead-letter
queue being the same length as the value of the MaxMsgLength attribute of the
queue.

Dead-letter queue processing:

The rest of this chapter contains general-use programming interface information.

Dead-letter queue processing depends on local system requirements, but consider


the following when you draw up the specification:

Chapter 1. Designing applications that use WebSphere MQ 67


v The message can be identified as having a dead-letter queue header because the
value of the format field in the MQMD, is MQFMT_DEAD_LETTER_HEADER.
v On WebSphere MQ for z/OS using CICS, if an MCA puts this message to the
dead-letter queue, the PutApplType field is MQAT_CICS, and the PutApplName
field is the ApplId of the CICS system followed by the transaction name of the
MCA.
v The reason for the message to be routed to the dead-letter queue is contained in
the Reason field of the dead-letter queue header.
v The dead-letter queue header contains details of the destination queue name and
queue manager name.
v The dead-letter queue header contains fields that have to be reinstated in the
message descriptor before the message is put to the destination queue. These
are:
1. Encoding
2. CodedCharSetId
3. Format
v The message descriptor is the same as PUT by the original application, except
for the three fields shown above.

Your dead-letter queue application must do one or more of the following:


v Examine the Reason field. A message might have been put by an MCA for the
following reasons:
– The message was longer than the maximum message size for the channel
The reason is MQRC_MSG_TOO_BIG_FOR_CHANNEL (or
MQRC_MSG_TOO_BIG_FOR_Q_MGR if you are using CICS for distributed
queuing on WebSphere MQ for z/OS)
– The message could not be put to its destination queue
The reason is any MQRC_* reason code that can be returned by an MQPUT
operation
– A user exit has requested this action
The reason code is that supplied by the user exit, or the default
MQRC_SUPPRESSED_BY_EXIT
v Try to forward the message to its intended destination, where this is possible.
v Retain the message for a certain length of time before discarding when the
reason for the diversion is determined, but not immediately correctable.
v Give instructions to administrators correct problems where these have been
determined.
v Discard messages that are corrupted or otherwise not processible.

There are two ways to deal with the messages that you have recovered from the
dead-letter queue:
1. If the message is for a local queue:
v Carry out any code translations required to extract the application data
v Carry out code conversions on that data if this is a local function
v Put the resulting message on the local queue with all the detail of the
message descriptor restored
2. If the message is for a remote queue, put the message on the queue.

For information on how undelivered messages are handled in a distributed


queuing environment, see WebSphere MQ Intercommunications.

68 WebSphere MQ: Application Programming Guide


Chapter 2. Writing a WebSphere MQ application
Introducing the Message Queue Interface
This chapter introduces the features of the Message Queue Interface (MQI).

The remaining chapters in this part of the book describe how to use these features.
Detailed descriptions of the calls, structures, data types, return codes, and
constants are given in the WebSphere MQ Application Programming Reference.

The MQI is introduced under these headings:


v “What is in the MQI?”
v “Parameters common to all the calls” on page 77
v “Specifying buffers” on page 78
v “Programming language considerations” on page 79
v “z/OS batch considerations” on page 87
v “UNIX signal handling” on page 88

What is in the MQI?


The Message Queue Interface consists of the following:
v Calls through which programs can access the queue manager and its facilities
v Structures that programs use to pass data to, and get data from, the queue
manager
v Elementary data types for passing data to, and getting data from, the queue
manager

WebSphere MQ for z/OS also supplies:


v Two extra calls through which z/OS batch programs can commit and back out
changes.
v Data definition files (sometimes known as copy files, macros, include files, and
header files) that define the values of constants supplied with WebSphere MQ
for z/OS.
v Stub programs to link-edit to your applications.
v A suite of sample programs that demonstrate how to use the MQI on the z/OS
platform. For further information about these samples, see “Sample programs
for WebSphere MQ for z/OS” on page 452.

WebSphere MQ for i5/OS also supplies:


v Data definition files (sometimes known as copy files, macros, include files, and
header files) that define the values of constants supplied with WebSphere MQ
for i5/OS.
v Three stub programs to link-edit to your ILE C, ILE COBOL, and ILE RPG
applications.
v A suite of sample programs that demonstrate how to use the MQI on the i5/OS
platform. For further information about these samples, see “Sample programs
(all platforms except z/OS)” on page 395.

WebSphere MQ for Windows and WebSphere MQ on UNIX systems also supply:

© Copyright IBM Corp. 1993, 2008 69


v Calls through which WebSphere MQ for Windows and WebSphere MQ on UNIX
systems programs can commit and back out changes.
v Include files that define the values of constants supplied on these platforms.
v Library files to link your applications.
v A suite of sample programs that demonstrate how to use the MQI on these
platforms.
v Sample source and executable code for bindings to external transaction
managers.

Calls
The calls in the MQI can be grouped as follows:
MQCONN, MQCONNX, and MQDISC
Use these calls to connect a program to (with or without options), and
disconnect a program from, a queue manager. If you write CICS programs
for z/OS, you do not need to use these calls. However, you are
recommended to use them if you want to port your application to other
platforms.
MQOPEN and MQCLOSE
Use these calls to open and close an object, such as a queue.
MQPUT and MQPUT1
Use these calls to put a message on a queue.
MQGET
Use this call to browse messages on a queue, or to remove messages from
a queue.
MQSUB, MQSUBRQ
Use these calls to register a subscription to a topic, and to request
publications matching the subscription.
MQINQ
Use this call to inquire about the attributes of an object.
MQSET
Use this call to set some of the attributes of a queue. You cannot set the
attributes of other types of object.
MQBEGIN, MQCMIT, and MQBACK
Use these calls when WebSphere MQ is the coordinator of a unit of work.
MQBEGIN starts the unit of work. MQCMIT and MQBACK end the unit
of work, either committing or rolling back the updates made during the
unit of work. i5/OS commitment controller is used to coordinate global
units of work on i5/OS. Native start commitment control, commit, and
rollback commands are used.
MQCRTMH, MQBUFMH, MQMHBUF, MQDLTMH
Use these calls to create a message handle, to convert a message handle to
a buffer or a buffer to a message handle, and to delete a message handle.
MQSETMP, MQINQMP, MQDLTMP
Use these calls to set a message property on a message handle, inquire on
a message property, and delete a property from a message handle.
MQCB, MQCB_FUNCTION, MQCTL
Use these calls to register and control a callback function.

70 WebSphere MQ: Application Programming Guide


MQSTAT
Use this call to retrieve status information about previous asynchronous
put operations.

The MQI calls are described fully in the WebSphere MQ Application Programming
Reference

Syncpoint calls
Syncpoint calls are available as follows:

WebSphere MQ for z/OS calls:

WebSphere MQ for z/OS provides the MQCMIT and MQBACK calls.

Use these calls in z/OS batch programs to tell the queue manager that all the
MQGET and MQPUT operations since the last syncpoint are to be made
permanent (committed) or are to be backed out. To commit and back out changes
in other environments:
CICS Use commands such as EXEC CICS SYNCPOINT and EXEC CICS
SYNCPOINT ROLLBACK.
IMS Use the IMS syncpoint facilities, such as the GU (get unique) to the IOPCB,
CHKP (checkpoint), and ROLB (rollback) calls.
RRS Use MQCMIT and MQBACK or SRRCMIT and SRRBACK as appropriate.
(See “Transaction management and recoverable resource manager services”
on page 187.)

Note: SRRCMIT and SRRBACK are native RRS commands, they are not
MQI calls.

For backward compatibility, the CSQBCMT and CSQBBAK calls are available as
synonyms for MQCMIT and MQBACK. These are described in the WebSphere MQ
Application Programming Reference.

i5/OS calls:

WebSphere MQ for i5/OS provides the MQCMIT and MQBACK commands. You
can also use the i5/OS COMMIT and ROLLBACK commands, or any other
commands or calls that initiate the i5/OS commitment control facilities (for
example, EXEC CICS SYNCPOINT).

WebSphere MQ calls on other platforms:

The following products provide the MQCMIT and MQBACK calls:


v WebSphere MQ for Windows
v WebSphere MQ on UNIX systems

Use syncpoint calls in programs to tell the queue manager that all the MQGET and
MQPUT operations since the last syncpoint are to be made permanent (committed)
or are to be backed out. To commit and back out changes in the CICS environment,
use commands such as EXEC CICS SYNCPOINT and EXEC CICS SYNCPOINT
ROLLBACK.

Chapter 2. Writing a WebSphere MQ application 71


Data conversion
The MQXCNVC (convert characters) call converts message character data from one
character set to another. Except on WebSphere MQ for z/OS, this call is used only
from a data-conversion exit.

See the WebSphere MQ Application Programming Reference for the syntax used with
the MQXCNVC call, and “Writing data-conversion exits” on page 163 for guidance
on writing and invoking data conversion exits.

Structures
Structures, used with the MQI calls listed in “Calls” on page 70, are supplied in
data definition files for each of the supported programming languages. WebSphere
MQ for z/OS and WebSphere MQ for i5/OS supply files that contain constants for
you to use when filling in some of the fields of these structures. For more
information on these, see “WebSphere MQ data definitions.”

All the structures are described in the WebSphere MQ Application Programming


Reference.

Elementary data types


For the supported programming languages, the MQI provides elementary data
types or unstructured fields.

These data types are described fully in the WebSphere MQ Application Programming
Reference.

WebSphere MQ data definitions


WebSphere MQ for z/OS supplies data definitions in the form of COBOL copy
files, assembler-language macros, a single PL/I include file, a single C language
include file, and C++ language include files.

WebSphere MQ for i5/OS supplies data definitions in the form of COBOL copy
files, RPG copy files, C language include files, and C++ language include files.

The data definition files supplied with WebSphere MQ contain:


v Definitions of all the WebSphere MQ constants and return codes
v Definitions of the WebSphere MQ structures and data types
v Constant definitions for initializing the structures
v Function prototypes for each of the calls (for PL/I and the C language only)

For a full description of WebSphere MQ data definition files, see Chapter 9,


“WebSphere MQ data definition files,” on page 575.

WebSphere MQ stub programs and library files


The stub programs and library files provided are listed here, for each platform.

For more information about how to use stub programs and library files when you
build an executable application, see Chapter 3, “Building a WebSphere MQ
application,” on page 339. For information about linking to C++ library files, see
WebSphere MQ Using C++.

WebSphere MQ for z/OS:

72 WebSphere MQ: Application Programming Guide


Before you can run a program written with WebSphere MQ for z/OS, you must
link-edit it to the stub program supplied with WebSphere MQ for z/OS for the
environment in which you are running the application.

The stub program provides the first stage of the processing of your calls into
requests that WebSphere MQ for z/OS can process.

WebSphere MQ for z/OS supplies the following stub programs:

CSQBSTUB Stub program for z/OS batch programs


CSQBRRSI Stub program for z/OS batch programs using RRS via the MQI
CSQBRSTB Stub program for z/OS batch programs using RRS directly
CSQCSTUB Stub program for CICS programs
CSQQSTUB Stub program for IMS programs
CSQXSTUB Stub program for distributed queuing non-CICS exits
CSQASTUB Stub program for data-conversion exits

Note: If you use the CSQBRSTB stub program, link-edit with ATRSCSS from
SYS1.CSSLIB. (SYS1.CSSLIB is also known as the Callable Services Library). For more
information about RRS see “Transaction management and recoverable resource
manager services” on page 187.

Alternatively, you can dynamically call the stub from within your program. This
technique is described in “Dynamically calling the WebSphere MQ stub” on page
377.

In IMS, you might also need to use a special language interface module that is
supplied by WebSphere MQ.

WebSphere MQ for i5/OS:

In WebSphere MQ for i5/OS, link your program to the MQI library files supplied
for the environment in which you are running your application, in addition to
those provided by the operating system.

For non-threaded applications:

AMQZSTUB Server service program provided for compatibility with releases


before V5R1M0
AMQVSTUB Data conversion service program provided for compatibility with
releases before V5R1M0
LIBMQM Server service program
LIBMQIC Client service program
IMQB23I4 C++ base service program
IMQS23I4 C++ server service program
LIBMQMZF Installable exits for C

In a threaded application:

LIBMQM_R Server service program


IMQB23I4_R C++ base service program
IMQS23I4_R C++ server service program
LIBMQMZF_R Installable exits for C

Chapter 2. Writing a WebSphere MQ application 73


On WebSphere MQ for i5/OS you can write your applications in C++. To see how
to link your C++ applications, and for full details of all aspects of using C++, see
WebSphere MQ Using C++.

WebSphere MQ for Windows:

On WebSphere MQ for Windows, you must link your program to the MQI library
files supplied for the environment in which you are running your application, in
addition to those provided by the operating system:

Library file and location Purpose


install_location\Tools\Lib\ Server for C (32-bit)
mqm.lib
install_location\Tools\Lib\ Client for C (32-bit)
mqic.lib
install_location\Tools\Lib\ Server XA interface for C (32-bit)
mqmxa.lib
install_location\Tools\Lib\ Client XA interface for C (32-bit)
mqcxa.lib
install_location\Tools\Lib\ Client MTS for C (32-bit)
mqicxa.lib
install_location\Tools\Lib\ Server TXSeries CICS support for C (32-bit)
mqmcics4.lib
install_location\Tools\Lib\ Client TXSeries CICS support for C (32-bit)
mqccics4.lib
install_location\Tools\Lib\ Installable services exits for C (32-bit)
mqmzf.lib
install_location\Tools\Lib\ Server for IBM COBOL (32-bit)
mqmcbb.lib
install_location\Tools\Lib\ Server for Micro Focus COBOL (32-bit)
mqmcb.lib
install_location\Tools\Lib\ Client for IBM COBOL (32-bit)
mqiccbb.lib
install_location\Tools\Lib\ Client for Micro Focus COBOL (32-bit)
mqiccb.lib
install_location\Tools\Lib\ Server for C++ (32-bit)
imqs23vn.lib
install_location\Tools\Lib\ Client for C++ (32-bit)
imqc23vn.lib
install_location\Tools\Lib\ Base for C++ (32-bit)
imqb23vn.lib
install_location\Tools\Lib\ Client MTS for C++ (32-bit)
imqx23vn.lib
install_location\Tools\Lib64\ Server for C (64-bit)
mqm.lib
install_location\Tools\Lib64\ Client for C (64-bit)
mqic.lib
install_location\Tools\Lib64\ Server XA interface for C (64-bit)
mqmxa.lib
install_location\Tools\Lib64\ Client XA interface for C (64-bit)
mqcxa.lib
install_location\Tools\Lib64\ Client MTS for C (64-bit)
mqicxa.lib
install_location\Tools\Lib64\ Server for IBM COBOL (64-bit)
mqmcbb.lib
install_location\Tools\Lib64\ Server for Micro Focus COBOL (64-bit)
mqmcb.lib

74 WebSphere MQ: Application Programming Guide


install_location\Tools\Lib64\ Client for IBM COBOL (64-bit)
mqiccbb.lib
install_location\Tools\Lib64\ Client for Micro Focus COBOL (64-bit)
mqiccb.lib
install_location\Tools\Lib64\ Server for C++ (64-bit)
imqs23vn.lib
install_location\Tools\Lib64\ Client for C++ (64-bit)
imqc23vn.lib
install_location\Tools\Lib64\ Base for C++ (64-bit)
imqb23vn.lib
install_location\Tools\Lib64\ Client MTS for C++ (64-bit)
imqx23vn.lib

These files are shipped for compatibility with previous releases:


mqic32.lib
mqic32xa.lib

WebSphere MQ for AIX:

On WebSphere MQ for AIX, you must link your program to the MQI library files
supplied for the environment in which you are running your application, in
addition to those provided by the operating system.

In a non-threaded application:

libmqm.a Server for C


libmqic.a Client for C
libmqmzf.a Installable service exits for C
libmqmxa.a Server XA interface for C
libmqmxa64.a Server alternative XA interface for C
libmqcxa.a Client XA interface for C
libmqcxa64.a Client alternative XA interface for C
libmqmcbrt.o WebSphere MQ run-time library for Micro Focus COBOL support
libmqmcb.a Server for COBOL
libmqicb.a Client for COBOL
libimqc23ia.a Client for C++
libimqs23ia.a Server for C++

In a threaded application:

libmqm_r.a Server for C


libmqic_r.a Client for C
libmqmzf_r.a Installable service exits for C
libmqmxa_r.a Server XA interface for C
libmqmxa64_r.a Server alternative XA interface for C
libmqcxa_r.a Client XA interface for C
libmqcxa64_r.a Client alternative XA interface for C
libimqc23ia_r.a Client for C++
libimqs23ia_r.a Server for C++

WebSphere MQ for HP-UX:

Chapter 2. Writing a WebSphere MQ application 75


On WebSphere MQ for HP-UX, you must link your program to the MQI library
files supplied for the environment in which you are running your application, in
addition to those provided by the operating system.

PA-RISC platform:

In a non-threaded application:

libmqm.sl Server for C


libmqic.sl Client for C
libmqmzf.sl Installable service exits for C
libmqmxa.sl Server XA interface for C
libmqmxa64.sl Server alternative XA interface for C
libmqcxa.sl Client XA interface for C
libmqcxa64.sl Client alternative XA interface for C
libimqi23ah.sl C++
libmqmcbrt.o WebSphere MQ run-time library for Micro Focus COBOL support
libmqmcb.sl Server for COBOL
libmqicb.sl Client for COBOL

In a threaded application:

libmqm_r.sl Server for C


libmqmzf_r.sl Installable service exits for C
libmqmxa_r.sl Server XA interface for C
libmqmxa64_r.sl Server alternative XA interface for C
libmqcxa_r.sl Client XA interface for C
libmqcxa64_r.sl Client alternative XA interface for C
libimqi23ah_r.sl C++

IA64 (IPF) platform:

In a non-threaded application:

libmqm.so Server for C


libmqic.so Client for C
libmqmzf.so Installable service exits for C
libmqmxa.so Server XA interface for C
libmqmxa64.so Server alternative XA interface for C
libmqcxa.so Client XA interface for C
libmqcxa64.so Client alternative XA interface for C
libimqi23ah.so C++
libmqmcbrt.o WebSphere MQ run-time library for Micro Focus COBOL support
libmqmcb.so Server for COBOL
libmqicb.so Client for COBOL

In a threaded application:

libmqm_r.so Server for C


libmqmzf_r.so Installable service exits for C
libmqmxa_r.so Server XA interface for C
libmqmxa64_r.so Server alternative XA interface for C
libmqcxa_r.so Client XA interface for C
libmqcxa64_r.so Client alternative XA interface for C

76 WebSphere MQ: Application Programming Guide


libimqi23ah_r.so C++

WebSphere MQ for Linux:

On WebSphere MQ for Linux, you must link your program to the MQI library files
supplied for the environment in which you are running your application, in
addition to those provided by the operating system.

In a non-threaded application:

libmqm.so Server for C


libmqic.so Client for C
libmqmzf.so Installable service exits for C
libmqmxa.so Server XA interface for C
libmqmxa64.so Server alternative XA interface for C
libmqcxa.so Client XA interface for C
libmqcxa64.so Client alternative XA interface for C
libimqc23gl.so Client for C++
libimqs23gl.so Server for C++

In a threaded application:

libmqm_r.so Server for C


libmqic_r.so Client for C
libmqmzf_r.so Installable service exits for C
libmqmxa_r.so Server XA interface for C
libmqmxa64_r.so Server alternative XA interface for C
libmqcxa_r.so Client XA interface for C
libmqcxa64_r.so Client alternative XA interface for C
libimqc23gl_r.so Client for C++
libimqs23gl_r.so Server for C++

WebSphere MQ for Solaris:

On WebSphere MQ for Solaris, you must link your program to the MQI library
files supplied for the environment in which you are running your application in
addition to those provided by the operating system.

libmqm.so Server for C


libmqmzse.so For C
libmqic.so Client for C
libmqmcs.so Common services for C
libmqmzf.so Installable service exits for C
libmqmxa.so Server XA interface for C
libmqmxa64.so Server alternative XA interface for C
libmqcxa.so Client XA interface for C
libmqcxa64.so Client alternative XA interface for C
libimqc23as.a Client for C++
libimqs23as.a Server for C++

Parameters common to all the calls


There are two types of parameter common to all the calls: handles and return
codes.

Chapter 2. Writing a WebSphere MQ application 77


Using handles
All MQI calls use one or more handles. These identify the queue manager, queue or
other object, message, or subscription, as appropriate to the call.

For a program to communicate with a queue manager, the program must have a
unique identifier by which it knows that queue manager. This identifier is called a
connection handle, sometimes referred to as an Hconn. For CICS programs, the
connection handle is always zero. For all other platforms or styles of programs, the
connection handle is returned by the MQCONN or MQCONNX call when the
program connects to the queue manager. Programs pass the connection handle as
an input parameter when they use the other calls.

For a program to work with a WebSphere MQ object, the program must have a
unique identifier by which it knows that object. This identifier is called an object
handle, sometimes referred to as an Hobj. The handle is returned by the MQOPEN
call when the program opens the object to work with it. Programs pass the object
handle as an input parameter when they use subsequent MQPUT, MQGET,
MQINQ, MQSET, or MQCLOSE calls.

Similarly, the MQSUB call returns a subscription handle or Hsub, which is used to
identify the subscription in subsequent MQGET, MQCB or MQSUBRQ calls, and
certain calls processing message properties use a message handle or Hmsg.

Understanding return codes


A completion code and a reason code are returned as output parameters by each
call. These are known collectively as return codes.

To show whether or not a call is successful, each call returns a completion code
when the call is complete. The completion code is usually either MQCC_OK or
MQCC_FAILED, showing success and failure, respectively. Some calls can return
an intermediate state, MQCC_WARNING, indicating partial success.

Each call also returns a reason code that shows the reason for the failure, or partial
success, of the call. There are many reason codes, covering such circumstances as a
queue being full, get operations not being allowed for a queue, and a particular
queue not being defined for the queue manager. Programs can use the reason code
to decide how to proceed. For example, they can prompt users to change their
input data, then make the call again, or they can return an error message to the
user.

When the completion code is MQCC_OK, the reason code is always


MQRC_NONE.

The completion and reason codes for each call are listed with the description of
that call in WebSphere MQ Application Programming Reference. For more detailed
information, including ideas for corrective action, see:
v WebSphere MQ for z/OS Messages and Codes for WebSphere MQ for z/OS
v WebSphere MQ Messages for all other WebSphere MQ platforms

Specifying buffers
The queue manager refers to buffers only if they are required. If you do not
require a buffer on a call or the buffer is zero in length, you can use a null pointer
to a buffer.

Always use datalength when specifying the size of the buffer that you require.
78 WebSphere MQ: Application Programming Guide
When you use a buffer to hold the output from a call (for example, to hold the
message data for an MQGET call, or the values of attributes queried by the
MQINQ call), the queue manager attempts to return a reason code if the buffer
you specify is not valid or is in read-only storage. However, it might not always be
able to return a reason code.

Programming language considerations


WebSphere MQ provides support for the following programming languages:
v C
v C++ ( see WebSphere MQ Using C++ for information about coding WebSphere
MQ programs in C++)
v Visual Basic (Windows systems only)
v COBOL
v Assembler language (WebSphere MQ for z/OS only)
v RPG (WebSphere MQ for i5/OS only)
v PL/I (WebSphere MQ for z/OS only)

The call interface, and how you can code the calls in each of these languages, is
described in the WebSphere MQ Application Programming Reference.

WebSphere MQ provides data definition files to help you to write your


applications. For a full description, see Chapter 9, “WebSphere MQ data definition
files,” on page 575.

If you can choose which language to code your programs in, consider the
maximum length of the messages that your programs will process. If your
programs will process only messages of a known maximum length, you can code
them in any of the supported programming languages. But if you do not know the
maximum length of the messages that the programs will have to process, the
language you choose will depend on whether you are writing a CICS, IMS, or
batch application:
IMS and batch
Code the programs in C, PL/I, or assembler language to use the facilities
these languages offer for obtaining and releasing arbitrary amounts of
memory. Alternatively, you could code your programs in COBOL, but use
assembler language, PL/I, or C subroutines to get and release storage.
CICS Code the programs in any language supported by CICS. The EXEC CICS
interface provides the calls for managing memory, if necessary.

Coding in C
Note the information in the following sections when coding WebSphere MQ
programs in C.

Parameters of the MQI calls:

Parameters that are input-only and of type MQHCONN, MQHOBJ, MQHMSG, or


MQLONG are passed by value; for all other parameters, the address of the
parameter is passed by value.

Not all parameters that are passed by address need to be specified every time a
function is invoked. Where a particular parameter is not required, a null pointer

Chapter 2. Writing a WebSphere MQ application 79


can be specified as the parameter on the function invocation, in place of the
address of the parameter data. Parameters for which this is possible are identified
in the call descriptions.

No parameter is returned as the value of the function; in C terminology, this means


that all functions return void.

The attributes of the function are defined by the MQENTRY macro variable; the
value of this macro variable depends on the environment.

Parameters with undefined data type:

The MQGET, MQPUT, and MQPUT1 functions each have a Buffer parameter that
has an undefined data type. This parameter is used to send and receive the
application’s message data.

Parameters of this sort are shown in the C examples as arrays of MQBYTE. You
can declare the parameters in this way, but it is usually more convenient to declare
them as the structure that describes the layout of the data in the message. The
function parameter is declared as a pointer-to-void, and so the address of any sort
of data can be specified as the parameter on the function invocation.

Data types:

All data types are defined by means of the typedef statement.

For each data type, the corresponding pointer data type is also defined. The name
of the pointer data type is the name of the elementary or structure data type
prefixed with the letter P to denote a pointer. The attributes of the pointer are
defined by the MQPOINTER macro variable; the value of this macro variable
depends on the environment. The following illustrates how to declare pointer data
types:
#define MQPOINTER /* depends on environment */
...
typedef MQLONG MQPOINTER PMQLONG; /* pointer to MQLONG */
typedef MQMD MQPOINTER PMQMD; /* pointer to MQMD */

Manipulating binary strings:

Strings of binary data are declared as one of the MQBYTEn data types.

Whenever you copy, compare, or set fields of this type, use the C functions memcpy,
memcmp, or memset:
#include <string.h>
#include "cmqc.h"

MQMD MyMsgDesc;

memcpy(MyMsgDesc.MsgId, /* set "MsgId" field to nulls */


MQMI_NONE, /* ...using named constant */
sizeof(MyMsgDesc.MsgId));

memset(MyMsgDesc.CorrelId, /* set "CorrelId" field to nulls */


0x00, /* ...using a different method */
sizeof(MQBYTE24));

Do not use the string functions strcpy, strcmp, strncpy, or strncmp because these
do not work correctly with data declared as MQBYTE24.

80 WebSphere MQ: Application Programming Guide


Manipulating character strings:

When the queue manager returns character data to the application, the queue
manager always pads the character data with blanks to the defined length of the
field. The queue manager does not return null-terminated strings, but you can use
them in your input. Therefore, when copying, comparing, or concatenating such
strings, use the string functions strncpy, strncmp, or strncat.

Do not use the string functions that require the string to be terminated by a null
(strcpy, strcmp, and strcat). Also, do not use the function strlen to determine the
length of the string; use instead the sizeof function to determine the length of the
field.

Initial values for structures:

The include file <cmqc.h> defines various macro variables that you can use to
provide initial values for the structures when declaring instances of those
structures. These macro variables have names of the form MQxxx_DEFAULT,
where MQxxx represents the name of the structure. Use them like this:
MQMD MyMsgDesc = {MQMD_DEFAULT};
MQPMO MyPutOpts = {MQPMO_DEFAULT};

For some character fields, the MQI defines particular values that are valid (for
example, for the StrucId fields or for the Format field in MQMD). For each of the
valid values, two macro variables are provided:
v One macro variable defines the value as a string whose length, excluding the
implied null, matches exactly the defined length of the field. For example, (the
symbol  represents a blank character):
#define MQMD_STRUC_ID "MD"
#define MQFMT_STRING "MQSTR"

Use this form with the memcpy and memcmp functions.


v The other macro variable defines the value as an array of char; the name of this
macro variable is the name of the string form suffixed with _ARRAY. For
example:
#define MQMD_STRUC_ID_ARRAY ’M’,’D’,’’,’’
#define MQFMT_STRING_ARRAY ’M’,’Q’,’S’,’T’,’R’,’’,’’,’’

Use this form to initialize the field when an instance of the structure is declared
with values different from those provided by the MQMD_DEFAULT macro
variable.

Initial values for dynamic structures:

When a variable number of instances of a structure are required, the instances are
usually created in main storage obtained dynamically using the calloc or malloc
functions.

To initialize the fields in such structures, the following technique is recommended:


1. Declare an instance of the structure using the appropriate MQxxx_DEFAULT
macro variable to initialize the structure. This instance becomes the model for
other instances:
MQMD ModelMsgDesc = {MQMD_DEFAULT};
/* declare model instance */

Chapter 2. Writing a WebSphere MQ application 81


Code the static or auto keywords on the declaration to give the model instance
static or dynamic lifetime, as required.
2. Use the calloc or malloc functions to obtain storage for a dynamic instance of
the structure:
PMQMD InstancePtr;
InstancePtr = malloc(sizeof(MQMD));
/* get storage for dynamic instance */
3. Use the memcpy function to copy the model instance to the dynamic instance:
memcpy(InstancePtr,&ModelMsgDesc,sizeof(MQMD));
/* initialize dynamic instance */

Use from C++:

For the C++ programming language, the header files contain the following
additional statements that are included only when a C++ compiler is used:
#ifdef __cplusplus
extern "C" {
#endif

/* rest of header file */

#ifdef __cplusplus
}
#endif

Coding in COBOL
Note the information in the following sections when coding WebSphere MQ
programs in COBOL.

Named constants:

In this book, the names of constants are shown containing the underscore character
(_) as part of the name. In COBOL, you must use the hyphen character (-) in place
of the underscore.

Constants that have character-string values use the single quotation mark character
(’) as the string delimiter. To make the compiler accept this character, use the
compiler option APOST.

The copy file CMQV contains declarations of the named constants as level-10
items. To use the constants, declare the level-01 item explicitly, then use the COPY
statement to copy in the declarations of the constants:
WORKING-STORAGE SECTION.
01 MQM-CONSTANTS.
COPY CMQV.

However, this method causes the constants to occupy storage in the program even
if they are not referred to. If the constants are included in many separate programs
within the same run unit, multiple copies of the constants will exist; this might
result in a significant amount of main storage being used. You can avoid this by
adding the GLOBAL clause to the level-01 declaration:
* Declare a global structure to hold the constants
01 MQM-CONSTANTS GLOBAL.
COPY CMQV.

82 WebSphere MQ: Application Programming Guide


This allocates storage for only one set of constants within the run unit; the
constants, however, can be referred to by any program within the run unit, not just
the program that contains the level-01 declaration.

Coding in System/390 assembler language


Note the information in the following sections when coding WebSphere MQ for
z/OS programs in assembler language.

Names:

In this book, the names of parameters in the descriptions of calls, and the names of
fields in the descriptions of structures are shown in mixed case. In the
assembler-language macros supplied with WebSphere MQ, all names are in
uppercase.

Using the MQI calls:

The MQI is a call interface, so assembler-language programs must observe the OS


linkage convention.

In particular, before they issue an MQI call, assembler-language programs must


point register R13 at a save area of at least 18 full words. This save area provides
storage for the called program. It stores the registers of the caller before their
contents are destroyed, and restores the contents of the caller’s registers on return.

Note: This is important for CICS assembler-language programs that use the
DFHEIENT macro to set up their dynamic storage, but that choose to override the
default DATAREG from R13 to other registers. When the CICS Resource Manager
Interface receives control from the stub, it saves the current contents of the
registers at the address to which R13 is pointing. Failing to reserve a proper save
area for this purpose gives unpredictable results, and will probably cause an abend
in CICS.

Declaring constants:

Most constants are declared as equates in macro CMQA.

However, the following constants cannot be defined as equates, and these are not
included when you call the macro using default options:
v MQACT_NONE
v MQCI_NONE
v MQFMT_NONE
v MQFMT_ADMIN
v MQFMT_COMMAND_1
v MQFMT_COMMAND_2
v MQFMT_DEAD_LETTER_HEADER
v MQFMT_EVENT
v MQFMT_IMS
v MQFMT_IMS_VAR_STRING
v MQFMT_PCF
v MQFMT_STRING
v MQFMT_TRIGGER
v MQFMT_XMIT_Q_HEADER

Chapter 2. Writing a WebSphere MQ application 83


v MQMI_NONE
To include them, add the keyword EQUONLY=NO when you call the macro.

CMQA is protected against multiple declaration, so you can include it many times.
However, the keyword EQUONLY takes effect only the first time that the macro is
included.

Specifying the name of a structure:

To allow more than one instance of a structure to be declared, the macro that
generates the structure prefixes the name of each field with a user-specifiable string
and an underscore character (_).

Specify the string when you invoke the macro. If you do not specify a string, the
macro uses the name of the structure to construct the prefix:
* Declare two object descriptors
CMQODA Prefix used="MQOD_" (the default)
MY_MQOD CMQODA Prefix used="MY_MQOD_"

The structure declarations in the WebSphere MQ Application Programming Reference


show the default prefix.

Specifying the form of a structure:

The macros can generate structure declarations in one of two forms, controlled by
the DSECT parameter:

DSECT=YES An assembler-language DSECT instruction is used to start a new data


section; the structure definition immediately follows the DSECT
statement. No storage is allocated, so no initialization is possible. The
label on the macro invocation is used as the name of the data section; if
no label is specified, the name of the structure is used.
DSECT=NO Assembler-language DC instructions are used to define the structure at
the current position in the routine. The fields are initialized with values,
which you can specify by coding the relevant parameters on the macro
invocation. Fields for which no values are specified on the macro
invocation are initialized with default values.

DSECT=NO is assumed if the DSECT parameter is not specified.

Controlling the listing:

You can control the appearance of the structure declaration in the


assembler-language listing by means of the LIST parameter:

LIST=YES The structure declaration appears in the assembler-language listing.


LIST=NO The structure declaration does not appear in the assembler-language
listing. This is assumed if the LIST parameter is not specified.

Specifying initial values for fields:

You can specify the value to be used to initialize a field in a structure by coding
the name of that field (without the prefix) as a parameter on the macro invocation,
accompanied by the value required.

84 WebSphere MQ: Application Programming Guide


For example, to declare a message descriptor structure with the MsgType field
initialized with MQMT_REQUEST, and the ReplyToQ field initialized with the
string MY_REPLY_TO_QUEUE, use the following code:
MY_MQMD CMQMDA MSGTYPE=MQMT_REQUEST, X
REPLYTOQ=MY_REPLY_TO_QUEUE

If you specify a named constant (or equate) as a value on the macro invocation,
use the CMQA macro to define the named constant. You must not enclose in single
quotation marks (‘ ’) values that are character strings.

Writing reenterable programs:

WebSphere MQ uses its structures for both input and output. If you want your
program to remain reenterable:
1. Define working storage versions of the structures as DSECTs, or define the
structures inline within an already-defined DSECT. Then copy the DSECT to
storage that is obtained using:
v For batch and TSO programs, the STORAGE or GETMAIN z/OS assembler
macros
v For CICS, the working storage DSECT (DFHEISTG) or the EXEC CICS
GETMAIN command
To correctly initialize these working storage structures, copy a constant version
of the corresponding structure to the working storage version.

Note: The MQMD and MQXQH structures are each more than 256 bytes long.
To copy these structures to storage, use the MVCL assembler instruction.
2. Reserve space in storage by using the LIST form (MF=L) of the CALL macro.
When you use the CALL macro to make an MQI call, use the EXECUTE form
(MF=E) of the macro, using the storage reserved earlier, as shown in the example
under “Using CEDF.” For more examples of how to do this, see the assembler
language sample programs as shipped with WebSphere MQ.

Use the assembler language RENT option to help you to determine if your
program is reenterable.

For information on writing reenterable programs, see MVS/ESA Application


Development Guide: Assembler Language Programs, GC28-1644.

Using CEDF:

If you want to use the CICS-supplied transaction, CEDF (CICS Execution


Diagnostic Facility) to help you to debug your program, add the ,VL keyword to
each CALL statement, for example:
CALL MQCONN,(NAME,HCONN,COMPCODE,REASON),MF=(E,PARMAREA),VL

The above example is reenterable assembler-language code where PARMAREA is an


area in the working storage that you specified.

Coding in RPG
Supported only on WebSphere MQ for i5/OS.

In this book, the parameters of calls, the names of data types, the fields of
structures, and the names of constants are described using their long names. In
RPG, these names are abbreviated to six or fewer uppercase characters. For

Chapter 2. Writing a WebSphere MQ application 85


example, the field MsgType becomes MDMT in RPG. For more information, see the
WebSphere MQ for i5/OS Application Programming Reference.

Coding in PL/I
PL/I is supported on z/OS only.

Note the information in the following sections when coding WebSphere MQ for
z/OS programs in PL/I.

Structures:

Structures are declared with the BASED attribute, and so do not occupy any
storage unless the program declares one or more instances of a structure.

An instance of a structure can be declared using the like attribute, for example:
dcl my_mqmd like MQMD; /* one instance */
dcl my_other_mqmd like MQMD; /* another one */

The structure fields are declared with the INITIAL attribute; when the like
attribute is used to declare an instance of a structure, that instance inherits the
initial values defined for that structure. You need to set only those fields where the
value required is different from the initial value.

PL/I is not sensitive to case, and so the names of calls, structure fields, and
constants can be coded in lowercase, uppercase, or mixed case.

Named constants:

The named constants are declared as macro variables; as a result, named constants
that are not referred to by the program do not occupy any storage in the compiled
procedure.

However, the compiler option that causes the source to be processed by the macro
preprocessor must be specified when the program is compiled.

All the macro variables are character variables, even the ones that represent
numeric values. Although this might seem counter intuitive, it does not result in
any data-type conflict after the macro variables have been substituted by the macro
processor, for example:
%dcl MQMD_STRUC_ID char;
%MQMD_STRUC_ID = ’’’MD ’’’;

%dcl MQMD_VERSION_1 char;


%MQMD_VERSION_1 = ’1’;

Coding in Visual Basic


Note: Outside the .NET environment, support for Visual Basic (VB) in WebSphere
MQ has been stabilized at the V6.0 level. Most new function added to WebSphere
MQ 7.0 or later is not available to VB applications. If you are programming in
VB.NET, use the WebSphere MQ .NET classes. For more information, see WebSphere
MQ Using .NET.

Visual Basic is supported only on Windows.

86 WebSphere MQ: Application Programming Guide


To avoid unintended translation of binary data passing between Visual Basic and
WebSphere MQ, use an MQBYTE definition instead of MQSTRING. CMQB.BAS
defines several new MQBYTE types that are equivalent to a C byte definition and
uses these within WebSphere MQ structures. For example, for the MQMD
(message descriptor) structure, MsgId (message identifier) is defined as
MQBYTE24.

Visual Basic does not have a pointer datatype, so references to other WebSphere
MQ data structures are by offset rather than pointer. Declare a compound structure
consisting of the two component structures, and specify the compound structure
on the call. WebSphere MQ support for Visual Basic provides an MQCONNXAny
call to make this possible and allow client applications to specify the channel
properties on a client connection. It accepts an untyped structure (MQCNOCD) in
place of the usual MQCNO structure.

The MQCNOCD structure is a compound structure consisting of an MQCNO


followed by an MQCD. This structure is declared in the exits header file CMQXB.
Use the routine MQCNOCD_DEFAULTS to initialize an MQCNOCD structure. A
sample making MQCONNX calls is provided (amqscnxb.vbp).

MQCONNXAny has the same parameters as MQCONNX, except that the


ConnectOpts parameter is declared as being of Any datatype rather than of
MQCNO datatype. This allows the function to accept either the MQCNO or the
MQCNOCD structure. This function is declared in the main header file CMQB.

z/OS batch considerations


z/OS batch programs that call the MQI can be in either supervisor or problem
state.

However, they must meet the following conditions:


v They must be in task mode, not service request block (SRB) mode.
v They must be in Primary address space control (ASC) mode (not Access Register
ASC mode).
v They must not be in cross-memory mode. The primary address space number
(ASN) must be equal to the secondary ASN and the home ASN.
v They must not be used as MPF exit programs.
v No z/OS locks can be held.
v There can be no function recovery routines (FRRs) on the FRR stack.
v Any program status word (PSW) key can be in force for the MQCONN or
MQCONNX call (provided the key is compatible with using storage that is in
the TCB key), but subsequent calls that use the connection handle returned by
MQCONN or MQCONNX:
– Must have the same PSW key that was used on the MQCONN or
MQCONNX call
– Must have parameters accessible (for write, where appropriate) under the
same PSW key
– Must be issued under the same task (TCB), but not in any subtask of the task
v They can be in either 24-bit or 31-bit addressing mode. However, if 24-bit
addressing mode is in force, parameter addresses must be interpreted as valid
31-bit addresses.
If any of these conditions is not met, a program check might occur. In some cases
the call will fail and a reason code will be returned.

Chapter 2. Writing a WebSphere MQ application 87


UNIX signal handling
This section does not apply to WebSphere MQ for z/OS or WebSphere MQ for
Windows.

In general, UNIX and i5/OS systems have moved from a nonthreaded (process)
environment to a multithreaded environment. In the nonthreaded environment,
some functions could be implemented only by using signals, though most
applications did not need to be aware of signals and signal handling. In the
multithreaded environment, thread-based primitives support some of the functions
that used to be implemented in the nonthreaded environments using signals.

In many instances, signals and signal handling, although supported, do not fit well
into the multithreaded environment and various restrictions exist. This can be
particularly problematic when you are integrating application code with different
middleware libraries (running as part of the application) in a multithreaded
environment where each is trying to handle signals. The traditional approach of
saving and restoring signal handlers (defined per process), which worked when
there was only one thread of execution within a process, does not work in a
multithreaded environment. This is because many threads of execution could be
trying to save and restore a process-wide resource, with unpredictable results.

Unthreaded applications
(Not applicable on Solaris as all applications are considered threaded even if they
use only a single thread.)

Each MQI function sets up its own signal handler for the signals:
SIGALRM
SIGBUS
SIGFPE
SIGSEGV
SIGILL

Users’ handlers for these are replaced for the duration of the MQI function call.
Other signals can be caught in the normal way by user-written handlers. If you do
not install a handler, the default actions (for example, ignore, core dump, or exit)
are left in place.

After WebSphere MQ handles a synchronous signal (SIGSEGV, SIGBUS, SIGFPE,


SIGILL), it attempts to pass the signal to any registered signal handler before
making the MQI function call.

Threaded applications
A thread is considered to be connected to WebSphere MQ from MQCONN (or
MQCONNX) until MQDISC.

Synchronous signals:

Synchronous signals arise in a specific thread.

UNIX safely allows the setting up of a signal handler for such signals for the
whole process. However, WebSphere MQ sets up its own handler for the following
signals, in the application process, while any thread is connected to WebSphere
MQ:
SIGBUS

88 WebSphere MQ: Application Programming Guide


SIGFPE
SIGSEGV
SIGILL

If you are writing multithreaded applications, there is only one process-wide signal
handler for each signal. When WebSphere MQ sets up its own synchronous signal
handlers it saves any previously registered handlers for each signal. After
WebSphere MQ handles one of the signals listed above, WebSphere MQ attempts
to call the signal handler that was in effect at the time of the first WebSphere MQ
connection within the process. The previously-registered handlers are restored
when all application threads have disconnected from WebSphere MQ.

Because signal handlers are saved and restored by WebSphere MQ, application
threads ideally should not establish signal handlers for these signals while there is
any possibility that another thread of the same process is also connected to
WebSphere MQ.

Note: When an application, or a middleware library (running as part of an


application), establishes a signal handler while a thread is connected to WebSphere
MQ, the application’s signal handler must call the corresponding WebSphere MQ
handler during the processing of that signal.

When establishing and restoring signal handlers, the general principle is that the
last signal handler to be saved must be the first to be restored:
v When an application establishes a signal handler after connecting to WebSphere
MQ, the previous signal handler must be restored before the application
disconnects from WebSphere MQ.
v When an application establishes a signal handler before connecting to
WebSphere MQ, the application must disconnect from WebSphere MQ before
restoring its signal handler.

Note: Failure to observe the general principle that the last signal handler to be
saved must be the first to be restored can result in unexpected signal handling in
the application and, potentially, the loss of signals by the application.

Asynchronous signals:

WebSphere MQ does not use any asynchronous signals in threaded applications


unless they are client applications.

Additional considerations for threaded client applications:

WebSphere MQ handles the following signals during I/O to a server. These signals
are defined by the communications stack. The application must not establish a
signal handler for these signals while a thread is connected to a queue manager:
SIGPIPE (for TCP/IP)

Additional considerations
Fastpath (trusted) applications:

Fastpath applications run in the same process as WebSphere MQ and so are


running in the multithreaded environment.

In this environment WebSphere MQ handles the synchronous signals SIGSEGV,


SIGBUS, SIGFPE, and SIGILL. All other signals must not be delivered to the

Chapter 2. Writing a WebSphere MQ application 89


Fastpath application while it is connected to WebSphere MQ. Instead they must be
blocked or handled by the application. If a Fastpath application intercepts such an
event, the queue manager must be stopped and restarted, or it may be left in an
undefined state. For a full list of the restrictions for Fastpath applications under
MQCONNX see “Connecting to a queue manager using the MQCONNX call” on
page 94.

MQI function calls within signal handlers:

While you are in a signal handler, do not call an MQI function.

If you try to call an MQI function from a signal handler while another MQI
function is active, MQRC_CALL_IN_PROGRESS is returned. If you try to call an
MQI function from a signal handler while no other MQI function is active, it is
likely to fail sometime during the operation because of the operating system
restrictions where only selective calls can be issued from, or within, a handler.

In the case of C++ destructor methods, which may be called automatically during
program exit, you might not be able to stop the MQI functions from being called.
Ignore any errors about MQRC_CALL_IN_PROGRESS. If a signal handler calls
exit(), WebSphere MQ backs out uncommitted messages in syncpoint as usual and
closes any open queues.

Signals during MQI calls:

MQI functions do not return the code EINTR or any equivalent to application
programs.

If a signal occurs during an MQI call, and the handler calls return, the call
continues to run as if the signal had not happened. In particular, MQGET cannot
be interrupted by a signal to return control immediately to the application. If you
want to break out of an MQGET, set the queue to GET_DISABLED; alternatively,
use a loop around a call to MQGET with a finite time expiry (MQGMO_WAIT
with gmo.WaitInterval set), and use your signal handler (in a nonthreaded
environment) or equivalent function in a threaded environment to set a flag which
breaks the loop.

In the AIX environment, WebSphere MQ requires that system calls interrupted by


signals are restarted. When establishing your own signal handler with sigaction(2),
set the SA_RESTART flag in the sa_flags field of the new action structure otherwise
WebSphere MQ might be unable to complete any call interrupted by a signal.

User exits and installable services:

User exits and installable services that run as part of a WebSphere MQ process in a
multithreaded environment have the same restrictions as for fastpath applications.
They should be considered as permanently connected to WebSphere MQ and so do
not use signals or non-threadsafe operating system calls.

VMS exit handlers:

Users can install exit handlers for an MQ application using the SYS$DCLEXH
system service.

The exit handler receives control when an image exits. An image exit will normally
occur when you call the Exit ($EXIT) or Force Exit ($FORCEX) service. The

90 WebSphere MQ: Application Programming Guide


$FORCEX will interrupt the target process in user mode. Then all user-mode exit
handlers (established via $DCLEXH) will begin to execute in reverse order of
establishment. For more details on exit handlers and $FORCEX, please refer to the
VMS Programming Concepts Manual and the VMS System Services Manual.

If you call an MQI function from within an exit handler, the behavior of the
function depends on the way the image was terminated. If the image was
terminated while another MQI function is active, an MQRC_CALL_IN_PROGRESS will be
returned.

It is possible to call an MQI function from within an exit handler if no other MQI
function is active and upcalls are disabled for the MQ application. If upcalls are
enabled for the MQ application, it will fail with the reason code MQRC_HCONN_ERROR.

The scope of an MQCONN or MQCONNX call is usually the thread that issued it.
If upcalls are enabled, the exit handler will be run as a separate thread and the
connection handles can not be shared.

Exit handlers are invoked within the interrupted context of the target process. It is
up to the application to ensure that actions taken by a handler are safe and
reliable, for the asynchronously interrupted context they are called from.

Connecting to and disconnecting from a queue manager


To use WebSphere MQ programming services, a program must have a connection
to a queue manager.

The way that this connection is made depends on the platform and the
environment in which the program is operating:
z/OS batch, WebSphere MQ for i5/OS, WebSphere MQ on UNIX systems, and
WebSphere MQ for Windows
Programs that run in these environments can use the MQCONN MQI call
to connect to, and the MQDISC call to disconnect from, a queue manager.
Alternatively, programs can use the MQCONNX call. This chapter
describes how to use these calls.
z/OS batch programs can connect, consecutively or concurrently, to
multiple queue managers on the same TCB.
IMS The IMS control region is connected to one or more queue managers when
it starts. This connection is controlled by IMS commands. (For information
on how to control the IMS adapter of WebSphere MQ for z/OS, see the
WebSphere MQ for z/OS System Administration Guide.) However, writers of
message queuing IMS programs must use the MQCONN MQI call to
specify the queue manager to which they want to connect. They can use
the MQDISC call to disconnect from that queue manager. This chapter
describes how writers of such programs should use these calls.
Before the IMS adapter processes a message for another user following a
Get Unique call from the IOPCB, or one implied by a checkpoint call, the
adapter ensures that the application closes handles and disconnects from
the queue manager.
IMS programs can connect, consecutively or concurrently, to multiple
queue managers on the same TCB.
CICS Transaction Server for OS/390® and CICS for MVS/ESA™
CICS programs do not need to do any work to connect to a queue

Chapter 2. Writing a WebSphere MQ application 91


manager because the CICS system itself is connected. This connection is
usually made automatically at initialization, but you can also use the
CKQC transaction, which is supplied with WebSphere MQ for z/OS.
CKQC is discussed in the WebSphere MQ for z/OS System Administration
Guide.
CICS tasks can connect only to the queue manager to which the CICS
region, itself, is connected.

Note: CICS programs can also use the MQI connect and disconnect calls
(MQCONN and MQDISC). You might want to do this so that you can port
these applications to non-CICS environments with a minimum of recoding.
However, these calls always complete successfully in a CICS environment.
This means that the return code might not reflect the true state of the
connection to the queue manager.
TXSeries for Windows and Open Systems
These programs do not need to do any work to connect to a queue
manager because the CICS system itself is connected. Therefore, only one
connection at a time is supported. CICS applications must issue an
MQCONN call to obtain a connection handle, and an MQDISC call before
they exit.

This chapter introduces connecting to and disconnecting from a queue manager,


under these headings:
v “Connecting to a queue manager using the MQCONN call”
v “Connecting to a queue manager using the MQCONNX call” on page 94
v “Disconnecting programs from a queue manager using MQDISC” on page 98

Connecting to a queue manager using the MQCONN call


In general, you can connect either to a specific queue manager, or to the default
queue manager:
v For WebSphere MQ for z/OS, in the batch environment, the default queue
manager is specified in the CSQBDEFV module.
v For WebSphere MQ for i5/OS, and WebSphere MQ on UNIX systems, the
default queue manager is specified in the mqs.ini file.
v For WebSphere MQ for Windows, the default queue manager is specified in the
registry.

Alternatively, in the z/OS MVS™ batch, TSO, and RRS environments you can
connect to any one queue manager within a queue-sharing group. The MQCONN
or MQCONNX request selects any one of the active members of the group.

The queue manager that you connect to must be local to the task. This means that
it must belong to the same system as the WebSphere MQ application.

In the IMS environment, the queue manager must be connected to the IMS control
region and to the dependent region that the program uses. The default queue
manager is specified in the CSQQDEFV module when WebSphere MQ for z/OS is
installed.

With the TXSeries CICS environment, and TXSeries for Windows and AIX, the
queue manager must be defined as an XA resource to CICS.

92 WebSphere MQ: Application Programming Guide


To connect to the default queue manager, call MQCONN, specifying a name
consisting entirely of blanks or starting with a null (X’00’) character.

Within WebSphere MQ on UNIX systems, an application must be authorized for it


to successfully connect to a queue manager. For more information, see the the
WebSphere MQ System Administration Guide.

The output from MQCONN is:


v A connection handle (Hconn)
v A completion code
v A reason code

Use the connection handle on subsequent MQI calls.

If the reason code indicates that the application is already connected to that queue
manager, the connection handle that is returned is the same as the one that was
returned when the application first connected. The application should not issue the
MQDISC call in this situation because the calling application will expect to remain
connected.

The scope of the connection handle is the same as that of the object handle (see
“Opening objects using the MQOPEN call” on page 100).

Descriptions of the parameters are given in the description of the MQCONN call in
the WebSphere MQ Application Programming Reference.

The MQCONN call fails if the queue manager is in a quiescing state when you
issue the call, or if the queue manager is shutting down.

Scope of MQCONN or MQCONNX


Within WebSphere MQ for i5/OS, WebSphere MQ on UNIX systems, and
WebSphere MQ for Windows, the scope of an MQCONN or MQCONNX call is
usually the thread that issued it.

That is, the connection handle returned from the call is valid only within the
thread that issued the call. Only one call can be made at any one time using the
handle. If it is used from a different thread, it is rejected as invalid. If you have
multiple threads in your application and each wants to use WebSphere MQ calls,
each one must issue MQCONN or MQCONNX. Alternatively, consider “Shared
(thread independent) connections with MQCONNX” on page 96.1

On WebSphere MQ for i5/OS, WebSphere MQ on UNIX systems, and WebSphere


MQ for Windows, each thread in an application can connect to different queue
managers; on other systems, all concurrent connections within a process must be to
the same queue manager.

If your application is running as a client, it can connect to more than one queue
manager within a thread.

1. When using multithreaded applications with WebSphere MQ on UNIX systems you need to ensure that the applications have a
sufficient stack size for the threads. You are recommended to use a stack size of 256KB, or larger, when multithreaded
applications are making MQI calls, either by themselves or, with other signal handlers (for example, CICS).

Chapter 2. Writing a WebSphere MQ application 93


Connecting to a queue manager using the MQCONNX call
The MQCONNX call is similar to the MQCONN call, but includes options to
control the way that the call works.

As input to MQCONNX, you can supply a queue manager name, or a


queue-sharing group name on z/OS shared queue systems. The output from
MQCONNX is:
v A connection handle (Hconn)
v A completion code
v A reason code
You use the connection handle on subsequent MQI calls.

A description of all the parameters of MQCONNX is given in the WebSphere MQ


Application Programming Reference. The Options field allows you to set
STANDARD_BINDING, FASTPATH_BINDING, SHARED_BINDING, or
ISOLATED_BINDING for any version of MQCNO. You can also make shared
(thread independent) connections using a MQCONNX call. See “Shared (thread
independent) connections with MQCONNX” on page 96 for more information
about these.
MQCNO_STANDARD_BINDING
By default, MQCONNX (like MQCONN) implies two logical threads
where the WebSphere MQ application and the local queue manager agent
run in separate processes. The WebSphere MQ application requests the
WebSphere MQ operation and the local queue manager agent services the
request. This is defined by the MQCNO_STANDARD_BINDING option on
the MQCONNX call.

Note: This default maintains the integrity of the queue manager (that is, it
makes the queue manager immune to errant programs), but impairs the
performance of the MQI calls.
MQCNO_FASTPATH_BINDING
Trusted applications imply that the WebSphere MQ application and the local
queue manager agent become the same process. Because the agent process
no longer needs to use an interface to access the queue manager, these
applications become an extension of the queue manager. This is defined by
the MQCNO_FASTPATH_BINDING option on the MQCONNX call.
You need to link trusted applications to the threaded WebSphere MQ
libraries. For instructions on how to set up a WebSphere MQ application to
run as trusted, see the WebSphere MQ Application Programming Reference.

Note: This option compromises the integrity of the queue manager:


there is no protection from overwriting its storage. This also applies if
the application contains errors that can be exposed to messages and
other data in the queue manager too. Consider these issues before using
this option.
MQCNO_SHARED_BINDING
Specify this option to make the application and the local queue manager
agent run in separate processes. This maintains the integrity of the queue
manager, that is, it protects the queue manager from errant programs.
However, the application and the local-queue-manager agent share some
resources.

94 WebSphere MQ: Application Programming Guide


MQCNO_SHARED_BINDING is ignored if the queue manager does not
support this type of binding. Processing continues as though the option
had not been specified.
MQCNO_ISOLATED_BINDING
Specify this option to make the application and the local queue manager
agent run in separate processes, as for MQCNO_SHARED_BINDING. In
this case, however, the application process and the local-queue-manager
agent are isolated from each other in that they do not share resources.
MQCNO_ISOLATED_BINDING is ignored if the queue manager does not
support this type of binding. Processing continues as though the option
had not been specified.

On z/OS these options are tolerated, but only a standard bound connection is
performed. MQCNO Version 3, for z/OS, allows four alternative options:
MQCNO_SERIALIZE_CONN_TAG_QSG
This allows an application to request that only one instance of an
application runs at any one time in a queue-sharing group. This is
achieved by registering the use of a connection tag, whose value is
specified or derived by the application. The tag is a 128 byte character
string specified in the Version 3 MQCNO.
MQCNO_RESTRICT_CONN_TAG_QSG
This is used where an application consists of more than one process (or a
TCB), each of which can connect to a queue manager. Connection is
permitted only if there is no current use of the tag, or the requesting
application is within the same processing scope. This is MVS address space
within the same queue-sharing group as the tag owner.
MQCNO_SERIALIZE_CONN_TAG_Q_MGR
This is similar to MQCNO_SERIALIZE_CONN_TAG_QSG, but only the
local queue manager is interrogated to see if the requested tag is already in
use.
MQCNO_RESTRICT_CONN_TAG_Q_MGR
This is similar to MQCNO_RESTRICT_CONN_TAG_QSG, but only the
local queue manager is interrogated to see if the requested tag is already in
use.

Restrictions for trusted applications


The following restrictions apply to trusted applications:
v You must explicitly disconnect trusted applications from the queue manager.
v You must stop trusted applications before ending the queue manager with the
endmqm command.
v You must not use asynchronous signals and timer interrupts (such as sigkill)
with MQCNO_FASTPATH_BINDING.
v On all platforms, a thread within a trusted application cannot connect to a queue
manager while another thread in the same process is connected to a different
queue manager.
v On WebSphere MQ on UNIX systems you must use mqm as the effective userID
and groupID for all MQI calls. You can change these IDs before making a

Chapter 2. Writing a WebSphere MQ application 95


non-MQI call requiring authentication (for example, opening a file), but you
must change it back to mqm before making the next MQI call.
v On WebSphere MQ for i5/OS:
1. Trusted applications must run under the QMQM user profile. It is not
sufficient that the user profile be a member of the QMQM group or that the
program adopt QMQM authority. It might not be possible for the QMQM
user profile to be used to sign on to interactive jobs, or to be specified in the
job description for jobs running trusted applications. In this case one
approach is to use the i5/OS profile swapping API functions, QSYGETPH,
QWTSETP, and QSYRLSPH to temporarily change the current user of the job
to QMQM while the MQ programs run. Details of these functions, together
with an example of their use, is provided in the Security APIs section of the
i5/OS System API Reference.
2. Do not cancel trusted applications using System-Request Option 2, or by
ending the jobs in which they are running using ENDJOB.
v On WebSphere MQ for HP-UX, multithreaded fast-path applications are likely to
need to set a larger stack size than the default. Use a size of 256 KB.
v On WebSphere MQ for Windows trusted 64-bit applications are not supported. If
you try to run a trusted 64-bit application, it will be downgraded to a standard
bound connection.
v On WebSphere MQ on UNIX systems trusted 32-bit applications are not
supported. If you try to run a trusted 32-bit application, it will be downgraded
to a standard bound connection.

Shared (thread independent) connections with MQCONNX


Not supported on WebSphere MQ for z/OS.

On WebSphere MQ platforms other than WebSphere MQ for z/OS, a connection


made with MQCONN is available only to the thread that made the connection.
Options on the MQCONNX call allow you to create a connection that can be
shared by all the threads in a process.

Use one of the following options to make a thread independent or shared


connection:

MQCNO_HANDLE_SHARE_BLOCK Creates a shared connection on which, if the


connection is currently in use by another
thread, an MQI call waits until the current
MQI call has completed
MQCNO_HANDLE_SHARE_NO_BLOCK Creates a shared connection on which, if the
connection is currently in use by another
thread, an MQI call fails immediately with a
reason of MQRC_CALL_IN_PROGRESS
MQCNO_HANDLE_SHARE_NONE Creates a standard non-shared connection

In the normal MQI environment the default value is


MQCNO_HANDLE_SHARE_NONE. In the MTS environment the default value is
MQCNO_HANDLE_SHARE_BLOCK.

A connection handle (Hconn) is returned from the MQCONNX call in the usual
way. This can be used by subsequent MQI calls from any thread in the process,
associating those calls with the Hconn returned from the MQCONNX. MQI calls
using a single shared Hconn are serialized across threads.

96 WebSphere MQ: Application Programming Guide


For example, the following sequence of activity is possible with a shared Hconn:
1. Thread 1 issues MQCONNX and gets a shared Hconn h1
2. Thread 1 opens a queue and issues a get request using h1
3. Thread 2 issues a put request using h1
4. Thread 3 issues a put request using h1
5. Thread 2 issues MQDISC using h1

While the Hconn is in use by any thread, access to the connection is unavailable to
other threads. In circumstances where it is acceptable that a thread waits for any
previous call from another thread to complete, use MQCONNX with the option
MQCNO_HANDLE_SHARE_BLOCK.

However this can cause difficulties. Suppose that in step 2 above, the thread issues
a get request that waits for messages that might not have yet arrived (a get with
wait). In this case, threads 2 and 3 are also left waiting (blocked) for as long as the
get request takes. If you prefer that your application is notified of calls that are
already running on the Hconn, use MQCONNX with the option
MQCNO_HANDLE_SHARE_NO_BLOCK.

Shared connection usage notes:


1. Any object handles (Hobj) created by opening an object are associated with an
Hconn; so for a shared Hconn, the Hobjs are also shared and usable by any
thread using the Hconn. Similarly, any unit of work started under an Hconn is
associated with that Hconn; so this too is shared across threads with the shared
Hconn.
2. Any thread can call MQDISC to disconnect a shared Hconn, not just the thread
that called the corresponding MQCONNX. The MQDISC terminates the Hconn
making it unavailable to all threads.
3. A single thread can use multiple shared Hconns serially, for example use
MQPUT to put one message under one shared Hconn then put another
message using another shared Hconn, with each operation being under a
different local unit of work.
4. Shared Hconns cannot be used within a global unit of work.

MQCONNX environment variable


On WebSphere MQ for i5/OS, WebSphere MQ for Windows, and WebSphere MQ
on UNIX systems, you can use the environment variable, MQ_CONNECT_TYPE in
combination with the type of binding specified in the Options field. This
environment variable allows you to execute the application with the
STANDARD_BINDING if any problems occur with the FASTPATH_BINDING. You
specify the environment variable with the value FASTPATH or STANDARD to
select the type of binding required. However, the FASTPATH binding is used only
if the connect option is appropriately specified as shown in Table 4:
Table 4. The MQ_CONNECT_TYPE environment variable
MQCONNX call option MQ_CONNECT_TYPE Result
environment variable
STANDARD UNDEFINED STANDARD
FASTPATH UNDEFINED FASTPATH
STANDARD STANDARD STANDARD
FASTPATH STANDARD STANDARD

Chapter 2. Writing a WebSphere MQ application 97


Table 4. The MQ_CONNECT_TYPE environment variable (continued)
MQCONNX call option MQ_CONNECT_TYPE Result
environment variable
STANDARD FASTPATH STANDARD
FASTPATH FASTPATH FASTPATH

So, to run a trusted application, either:


1. Specify the MQCNO_FASTPATH_BINDING option on the MQCONNX call and
the FASTPATH environment variable, or
2. Specify the MQCNO_FASTPATH_BINDING option on the MQCONNX call and
leave the environment variable undefined.

If neither MQCNO_STANDARD_BINDING nor MQCNO_FASTPATH_BINDING is


specified, you can use MQCNO_NONE, which defaults to
MQCNO_STANDARD_BINDING.

Disconnecting programs from a queue manager using


MQDISC
When a program that has connected to a queue manager using the MQCONN or
MQCONNX call has finished all interaction with the queue manager, it breaks the
connection using the MQDISC call, except:
v On CICS Transaction Server for z/OS applications, where the call is optional
unless MQCONNX was used and you want to drop the connection tag before
the application ends.
v On WebSphere MQ for i5/OS where, when you sign off from the operating
system, an implicit MQDISC call is made.

As input to the MQDISC call, you must supply the connection handle (Hconn) that
was returned by MQCONN or MQCONNX when you connected to the queue
manager.

Except on CICS on z/OS, after MQDISC is called the connection handle (Hconn) is
no longer valid, and you cannot issue any further MQI calls until you call
MQCONN or MQCONNX again. MQDISC does an implicit MQCLOSE for any
objects that are still open using this handle.

If you use MQCONNX to connect on WebSphere MQ for z/OS, MQDISC also ends
the scope of the connection tag established by the MQCONNX. However, in a
CICS, IMS, or RRS application, if there is an active unit of recovery associated with
a connection tag, the MQDISC is rejected with a reason code of
MQRC_CONN_TAG_NOT_RELEASED.

Descriptions of the parameters are given in the description of the MQDISC call in
the WebSphere MQ Application Programming Reference.

When no MQDISC is issued


A standard, non-shared connection (Hconn) is cleaned up when the creating thread
terminates. A shared connection is only implicitly backed out and disconnected
when the whole process terminates. If the thread that created the shared Hconn
terminates while the Hconn still exists the Hconn is still usable.

98 WebSphere MQ: Application Programming Guide


Authority checking
The MQCLOSE and MQDISC calls usually perform no authority checking.

In the normal course of events a job that has the authority to open or connect to a
WebSphere MQ object closes or disconnect from that object. Even if the authority
of a job that has connected to or opened a WebSphere MQ object is revoked, the
MQCLOSE and MQDISC calls are accepted.

Opening and closing objects


To perform any of the following operations, you must first open the relevant
WebSphere MQ object:
v Put messages on a queue
v Get (browse or retrieve) messages from a queue
v Set the attributes of an object
v Inquire about the attributes of any object

Use the MQOPEN call to open the object, using the options of the call to specify
what you want to do with the object. The only exception is if you want to put a
single message on a queue, then close the queue immediately. In this case, you can
bypass the opening stage by using the MQPUT1 call (see “Putting one message on a
queue using the MQPUT1 call” on page 117).

Before you open an object using the MQOPEN call, you must connect your
program to a queue manager. This is explained in detail, for all environments, in
“Connecting to and disconnecting from a queue manager” on page 91.

There are four types of WebSphere MQ object that you can open:
v Queue
v Namelist
v Process definition
v Queue manager
You open all these objects in a similar way using the MQOPEN call. For more
information about WebSphere MQ objects, see “WebSphere MQ objects” on page
48.

You can open the same object more than once, and each time you get a new object
handle. You might want to browse messages on a queue using one handle, and
remove messages from the same queue using another handle. This saves using up
resources to close and reopen the same object. You can also open a queue for
browsing and removing messages at the same time.

Moreover, you can open multiple objects with a single MQOPEN and close them
using MQCLOSE. See “Distribution lists” on page 119 for information about how
to do this.

When you attempt to open an object, the queue manager checks that you are
authorized to open that object for the options that you specify in the MQOPEN
call.

Objects are closed automatically when a program disconnects from the queue
manager. In the IMS environment, disconnection is forced when a program starts

Chapter 2. Writing a WebSphere MQ application 99


processing for a new user following a GU (get unique) IMS call. On the i5/OS
platform, objects are closed automatically when a job ends.

It is good programming practice to close objects you have opened. Use the
MQCLOSE call to do this.

This chapter introduces opening and closing WebSphere MQ objects, under these
headings:
v “Opening objects using the MQOPEN call”
v “Creating dynamic queues” on page 107
v “Opening remote queues” on page 107
v “Closing objects using the MQCLOSE call” on page 108

Opening objects using the MQOPEN call


As input to the MQOPEN call, you must supply:
v A connection handle. For CICS applications on z/OS, you can specify the
constant MQHC_DEF_HCONN (which has the value zero), or use the
connection handle returned by the MQCONN or MQCONNX call. For other
programs, always use the connection handle returned by the MQCONN or
MQCONNX call.
v A description of the object that you want to open, using the object descriptor
structure (MQOD).
v One or more options that control the action of the call.

The output from MQOPEN is:


v An object handle that represents your access to the object. Use this on input to
any subsequent MQI calls.
v A modified object-descriptor structure, if you are creating a dynamic queue (and
it is supported on your platform).
v A completion code.
v A reason code.

Scope of an object handle


The scope of an object handle (Hobj) is the same as the scope of a connection
handle (Hconn).

This is covered in “Scope of MQCONN or MQCONNX” on page 93 and “Shared


(thread independent) connections with MQCONNX” on page 96. However, there
are additional considerations in some environments :
CICS In a CICS program, you can use the handle only within the same CICS
task from which you made the MQOPEN call.
IMS and z/OS batch
In the IMS and batch environments, you can use the handle within the
same task, but not within any subtasks.

Descriptions of the parameters of the MQOPEN call are given in the WebSphere MQ
Application Programming Reference.

The following sections describe the information that you must supply as input to
MQOPEN.

100 WebSphere MQ: Application Programming Guide


Identifying objects (the MQOD structure)
Use the MQOD structure to identify the object that you want to open. This
structure is an input parameter for the MQOPEN call. (The structure is modified
by the queue manager when you use the MQOPEN call to create a dynamic
queue.)

For full details of the MQOD structure see MQOD - Object descriptor.

For information about using the MQOD structure for distribution lists, see “Using
the MQOD structure” on page 120 under “Distribution lists” on page 119.

Name resolution
How the MQOPEN call resolves queue and queue manager names.

Note: A Queue manager alias is a remote queue definition without an RNAME field.

When you open a WebSphere MQ queue, the MQOPEN call performs a name
resolution function on the queue name that you specify. This determines on which
queue the queue manager performs subsequent operations. This means that when
you specify the name of an alias queue or a remote queue in your object descriptor
(MQOD), the call resolves the name either to a local queue or to a transmission
queue. If a queue is opened for any type of input, browse, or set, it resolves to a
local queue if there is one, and fails if there is not one. It resolves to a nonlocal
queue only if it is opened for output only, inquire only, or output and inquire only.
See Table 5 for an overview of the name resolution process. The name that you
supply in ObjectQMgrName is resolved before that in ObjectName.

Table 5 also shows how you can use a local definition of a remote queue to define
an alias for the name of a queue manager. This allows you to select which
transmission queue is used when you put messages on a remote queue, so you
could, for example, use a single transmission queue for messages destined for
many remote queue managers.

To use the following table, first read down the two left-hand columns, under the
heading Input to MQOD, and select the appropriate case. Then read across the
corresponding row, following any instructions. Following the instructions in the
Resolved names columns, you can either return to the Input to MQOD columns
and insert values as directed, or you can exit the table with the results supplied.
For example, you might be required to input ObjectName.
Table 5. Resolving queue names when using MQOPEN
Input to MQOD Resolved names
ObjectQMgrName ObjectName ObjectQMgrName ObjectName Transmission queue
Blank or local queue Local queue Local queue manager Input Not applicable (local
manager with no ObjectName queue used)
CLUSTER
attribute
Blank queue manager Local queue Workload management Input SYSTEM.CLUSTER.
with CLUSTER selected cluster queue ObjectName TRANSMIT.QUEUE and
attribute manager or specific local queue used
cluster queue manager
selected on PUT SYSTEM.QSG.
TRANSMIT.QUEUE (see
note)

Chapter 2. Writing a WebSphere MQ application 101


Table 5. Resolving queue names when using MQOPEN (continued)
Input to MQOD Resolved names
ObjectQMgrName ObjectName ObjectQMgrName ObjectName Transmission queue
Local queue manager Local queue Local queue manager Input Not applicable (local
with CLUSTER ObjectName queue used)
attribute
Blank or local queue Model queue Local queue manager Generated name Not applicable (local
manager queue used)
Blank or local queue Alias queue Perform name resolution
manager again with
ObjectQMgrName
unchanged, and input
ObjectName set to the
BaseQName in the alias
queue definition object.
Must not resolve to an
alias queue.
Local queue manager Alias queue with The alias must not
CLUSTER resolve to a cluster queue
attribute that is not locally
defined, or a cluster
queue that has the same
ObjectName as the alias.
Blank queue manager Alias queue with The alias can resolve to a
CLUSTER cluster queue with same
attribute ObjectName as the alias.
Blank or local queue Local definition Perform name resolution Name of XmitQName
manager of a remote again with attribute, if non-blank;
queue ObjectQMgrName set to otherwise
RemoteQMgrName, and RemoteQMgrName in the
ObjectName set to remote queue definition
RemoteQName. Must not object.
resolve remote queues
SYSTEM.QSG.
TRANSMIT.QUEUE (see
note)
Blank queue manager No matching Workload management Input SYSTEM.CLUSTER.
local object; selected cluster queue ObjectName TRANSMIT.QUEUE
cluster queue manager or specific
found cluster queue manager SYSTEM.QSG.
selected on PUT TRANSMIT.QUEUE (see
note)
Blank or local queue No matching Error, queue not Not applicable
manager local object; found
cluster queue
not found
Name of queue manager Local shared Local queue manager Input Not applicable
in same queue sharing queue ObjectName
group as local queue
manager
Name of a local (Not resolved) Input ObjectQMgrName Input Input ObjectQMgrName
transmission queue ObjectName
SYSTEM.QSG.
TRANSMIT.QUEUE (see
note)

102 WebSphere MQ: Application Programming Guide


Table 5. Resolving queue names when using MQOPEN (continued)
Input to MQOD Resolved names
ObjectQMgrName ObjectName ObjectQMgrName ObjectName Transmission queue
Queue manager alias (Not resolved, Perform name resolution Input Name of XmitQName
definition remote queue) again with ObjectName attribute, if non-blank;
(RemoteQMgrName may ObjectQMgrName set to otherwise
be the local queue RemoteQMgrName. Must RemoteQMgrName in the
manager) not resolve to remote remote queue definition
queues object.

SYSTEM.QSG.
TRANSMIT.QUEUE (see
note)
Queue manager is not (Not resolved) ObjectQMgrName or Input SYSTEM.CLUSTER.
the name of any local specific cluster queue ObjectName TRANSMIT.QUEUE
object; cluster queue manager selected on PUT
managers or queue SYSTEM.QSG.
manager alias found TRANSMIT.QUEUE (see
note)
Queue manager is not (Not resolved) Input ObjectQMgrName Input DefXmitQName attribute
the name of any local ObjectName of the queue manager
object; no cluster objects where DefXmitQName is
found supported.

SYSTEM.QSG.
TRANSMIT.QUEUE (see
note)
Note: The SYSTEM.QSG.TRANSMIT.QUEUE is used if local and remote queue managers are in the same
queue-sharing group; intra-group queuing is enabled.

Note:
1. BaseQName is the name of the base queue from the definition of the alias queue.
2. RemoteQName is the name of the remote queue from the local definition of the
remote queue.
3. RemoteQMgrName is the name of the remote queue manager from the local
definition of the remote queue.
4. XmitQName is the name of the transmission queue from the local definition of
the remote queue.
5. When using WebSphere MQ for z/OS queue managers that are part of a
queue-sharing group (QSG), the name of the QSG can be used instead of the
local queue manager name in Table 5 on page 101.
6. In the ObjectName column of the table, CLUSTER refers to both the CLUSTER
and CLUSNL attributes of the queue.

Opening an alias queue also opens the base queue to which the alias resolves, and
opening a remote queue also opens the transmission queue. Therefore you cannot
delete either the queue that you specify or the queue to which it resolves while the
other one is open.

The resolved queue name and the resolved queue manager name are stored in the
ResolvedQName and ResolvedQMgrName fields in the MQOD.

For more information about name resolution in a distributed queuing environment


see WebSphere MQ Intercommunications.

Chapter 2. Writing a WebSphere MQ application 103


Using the options of the MQOPEN call
In the Options parameter of the MQOPEN call, you must choose one or more
options to control the access that you are given to the object that you are opening.
With these options you can:
v Open a queue and specify that all messages put to that queue must be directed
to the same instance of it
v Open a queue to allow you to put messages on it
v Open a queue to allow you to browse messages on it
v Open a queue to allow you to remove messages from it
v Open an object to allow you to inquire about and set its attributes (but you can
set the attributes of queues only)
v Open a topic or topic string to publish messages to it
v Associate context information with a message
v Nominate an alternate user identifier to be used for security checks
v Control the call if the queue manager is in a quiescing state

MQOPEN option for cluster queue:

To route all messages put to a queue using MQPUT to the same queue manager by
the same route, use the MQOO_BIND_ON_OPEN option on the MQOPEN call.

To specify that a destination is to be selected at MQPUT time, that is, on a


message-by-message basis, use the MQOO_BIND_NOT_FIXED option on the
MQOPEN call. If you specify neither of these options the default,
MQOO_BIND_AS_Q_DEF, is used. In this case the binding used for the queue
handle is taken from the DefBind queue attribute, which can take the value
MQBND_BIND_ON_OPEN or MQBND_BIND_NOT_FIXED.

If the queue that you open is not a cluster queue, the MQOO_BIND_* options are
ignored. If you specify the name of the local queue manager in the MQOD, the
local instance of the cluster queue is selected. If the queue manager name is blank,
any instance can be selected. See WebSphere MQ Queue Manager Clusters for more
information.

MQOPEN option for putting messages:

To open a queue or topic to put messages on it, use the MQOO_OUTPUT option.

MQOPEN option for browsing messages:

To open a queue so that you can browse the messages on it, use the MQOPEN call
with the MQOO_BROWSE option.

This creates a browse cursor that the queue manager uses to identify the next
message on the queue. For more information, see “Browsing messages on a queue”
on page 156.

Note:
1. You cannot browse messages on a remote queue; do not open a remote queue
using the MQOO_BROWSE option.
2. You cannot specify this option when opening a distribution list. For further
information about distribution lists, see “Distribution lists” on page 119.

104 WebSphere MQ: Application Programming Guide


3. Use the MQOO_CO_OP in conjunction with MQOO_BROWSE if you are using
cooperative browsing; see Options (MQLONG)

MQOPEN options for removing messages:

Three options control the opening of a queue to remove messages from it.

You can use only one of them in any MQOPEN call. These options define whether
your program has exclusive or shared access to the queue. Exclusive access means
that, until you close the queue, only you can remove messages from it. If another
program attempts to open the queue to remove messages, its MQOPEN call fails.
Shared access means that more than one program can remove messages from the
queue.

The most advisable approach is to accept the type of access that was intended for
the queue when the queue was defined. The queue definition involved the setting
of the Shareability and the DefInputOpenOption attributes. To accept this access,
use the MQOO_INPUT_AS_Q_DEF option. Refer to Table 6 to see how the setting
of these attributes affects the type of access that you will be given when you use
this option.
Table 6. How queue attributes and options of the MQOPEN call affect access to queues
Queue attributes Type of access with MQOPEN options
Shareability DefInputOpenOption AS_Q_DEF SHARED EXCLUSIVE
SHAREABLE SHARED shared shared exclusive
SHAREABLE EXCLUSIVE exclusive shared exclusive
NOT_SHAREABLE* SHARED* exclusive exclusive exclusive
NOT_SHAREABLE EXCLUSIVE exclusive exclusive exclusive
Note: * Although you can define a queue to have this combination of attributes, the
default input open option is overridden by the shareability attribute.

Alternatively:
v If you know that your application can work successfully even if other programs
can remove messages from the queue at the same time, use the
MQOO_INPUT_SHARED option. Table 6 shows how, in some cases you will be
given exclusive access to the queue, even with this option.
v If you know that your application can work successfully only if other programs
are prevented from removing messages from the queue at the same time, use the
MQOO_INPUT_EXCLUSIVE option.

Note:
1. You cannot remove messages from a remote queue. Therefore you cannot open
a remote queue using any of the MQOO_INPUT_* options.
2. You cannot specify this option when opening a distribution list. For further
information, see “Distribution lists” on page 119.

MQOPEN options for setting and inquiring about attributes:

To open a queue so that you can set its attributes, use the MQOO_SET option.

You cannot set the attributes of any other type of object (see “Inquiring about and
setting object attributes” on page 180).

Chapter 2. Writing a WebSphere MQ application 105


To open an object so that you can inquire about its attributes, use the
MQOO_INQUIRE option.

Note: You cannot specify this option when opening a distribution list.

MQOPEN options relating to message context:

If you want to be able to associate context information with a message when you
put it on a queue, you must use one of the message context options when you
open the queue.

The options allow you to differentiate between context information that relates to
the user who originated the message, and that which relates to the application that
originated the message. Also, you can opt to set the context information when you
put the message on the queue, or you can opt to have the context taken
automatically from another queue handle.

For more information about the subject of message context, see “Message context”
on page 46.

MQOPEN option for alternate user authority:

When you attempt to open an object using the MQOPEN call, the queue manager
checks that you have the authority to open that object. If you are not authorized,
the call fails.

However, server programs might want the queue manager to check the
authorization of the user on whose behalf they are working, rather than the
server’s own authorization. To do this, they must use the
MQOO_ALTERNATE_USER_AUTHORITY option of the MQOPEN call, and
specify the alternate user ID in the AlternateUserId field of the MQOD structure.
Typically, the server would get the user ID from the context information in the
message it is processing.

MQOPEN option for queue manager quiescing:

In the CICS environment on z/OS, if you use the MQOPEN call when the queue
manager is in a quiescing state, the call always fails.

In other z/OS environments, i5/OS, Windows systems and in UNIX systems


environments, the call fails when the queue manager is quiescing only if you use
the MQOO_FAIL_IF_QUIESCING option of the MQOPEN call.

MQOPEN option for resolving local queue names:

When you open a local, alias or model queue, the local queue is returned.

However, when you open a remote queue or cluster queue, the ResolvedQName and
ResolvedQMgrName fields of the MQOD structure are filled with the names of the
remote queue and remote queue manger found in the remote queue definition, or
with the chosen remote cluster queue.

Use the MQOO_RESOLVE_LOCAL_Q option of the MQOPEN call to fill the


ResolvedQName in the MQOD structure with the name of the local queue that was
opened. The ResolvedQMgrName is similarly filled with the name of the local queue
manager hosting the local queue. This field is available only with Version 3 of the

106 WebSphere MQ: Application Programming Guide


MQOD structure; if the structure is less than Version 3,
MQOO_RESOLVE_LOCAL_Q is ignored without an error being returned.

If you specify MQOO_RESOLVE_LOCAL_Q when opening, for example, a remote


queue, ResolvedQName is the name of the transmission queue to which messages
will be put. ResolvedQMgrNameis the name of the local queue manager hosting the
transmission queue.

Creating dynamic queues


Use a dynamic queue when you do not need the queue after your application
ends.

For example, you could use a dynamic queue for your reply-to queue. You specify
the name of the reply-to queue in the ReplyToQ field of the MQMD structure when
you put a message on a queue (see “Defining messages using the MQMD
structure” on page 110).

To create a dynamic queue, you use a template known as a model queue, together
with the MQOPEN call. You create a model queue using the WebSphere MQ
commands or the operations and control panels. The dynamic queue that you
create takes the attributes of the model queue.

When you call MQOPEN, specify the name of the model queue in the ObjectName
field of the MQOD structure. When the call completes, the ObjectName field is set
to the name of the dynamic queue that is created. Also, the ObjectQMgrName field is
set to the name of the local queue manager.

You can specify the name of the dynamic queue that you create in three ways:
v Give the full name that you want in the DynamicQName field of the MQOD
structure.
v Specify a prefix (fewer than 33 characters) for the name, and allow the queue
manager to generate the rest of the name. This means that the queue manager
generates a unique name, but you still have some control (for example, you
might want each user to use a certain prefix, or you might want to give a special
security classification to queues with a certain prefix in their name). To use this
method, specify an asterisk (*) for the last non-blank character of the
DynamicQName field. Do not specify a single asterisk (*) for the dynamic queue
name.
v Allow the queue manager to generate the full name. To use this method, specify
an asterisk (*) in the first character position of the DynamicQName field.

For more information about these methods, see the description of the DynamicQName
field in the WebSphere MQ Application Programming Reference.

There is more information on dynamic queues in “Dynamic queues” on page 55.

Opening remote queues


A remote queue is a queue that is owned by a queue manager other than the one
to which the application is connected.

To open a remote queue, use the MQOPEN call as for a local queue. You can
specify the name of the queue as follows:
1. In the ObjectName field of the MQOD structure, specify the name of the remote
queue as known to the local queue manager.

Chapter 2. Writing a WebSphere MQ application 107


Note: Leave the ObjectQMgrName field blank in this case.
2. In the ObjectName field of the MQOD structure, specify the name of the remote
queue, as known to the remote queue manager. In the ObjectQMgrName field,
specify either:
v The name of the transmission queue that has the same name as the remote
queue manager. The name and case (uppercase, lowercase or a mixture) must
match exactly.
v The name of a queue manager alias object that resolves to the destination
queue manager or the transmission queue.
This tells the queue manager the destination of the message as well as the
transmission queue that it needs to be put on to get there.
3. If DefXmitQname is supported, in the ObjectName field of the MQOD structure,
specify the name of the remote queue as known by the remote queue manager.

Note: Set the ObjectQMgrName field to the name of the remote queue manager
(it cannot be left blank in this case).

Only local names are validated when you call MQOPEN; the last check is for the
existence of the transmission queue to be used.

These methods are summarized in Table 5 on page 101.

Closing objects using the MQCLOSE call


To close an object, use the MQCLOSE call.

If the object is a queue, note the following:


v You do not need to empty a temporary dynamic queue before you close it.
When you close a temporary dynamic queue, the queue is deleted, along with
any messages that might still be on it. This is true even if there are uncommitted
MQGET, MQPUT, or MQPUT1 calls outstanding against the queue.
v On WebSphere MQ for z/OS, if you have any MQGET requests with an
MQGMO_SET_SIGNAL option outstanding for that queue, they are canceled.
v If you opened the queue using the MQOO_BROWSE option, your browse cursor
is destroyed.

Closure is unrelated to syncpoint, so you can close queues before or after


syncpoint.

As input to the MQCLOSE call, you must supply:


v A connection handle. Use the same connection handle used to open it, or
alternatively, for CICS applications on z/OS, you can specify the constant
MQHC_DEF_HCONN (which has the value zero).
v The handle of the object that you want to close. Get this from the output of the
MQOPEN call.
v MQCO_NONE in the Options field (unless you are closing a permanent
dynamic queue).
v The control option to determine whether the queue manager should delete the
queue even if there are still messages on it (when closing a permanent dynamic
queue).

The output from MQCLOSE is:


v A completion code

108 WebSphere MQ: Application Programming Guide


v A reason code
v The object handle, reset to the value MQHO_UNUSABLE_HOBJ

Descriptions of the parameters of the MQCLOSE call are given in the WebSphere
MQ Application Programming Reference.

Putting messages on a queue


Use the MQPUT call to put messages on the queue. You can use MQPUT
repeatedly to put many messages on the same queue, following the initial
MQOPEN call. Call MQCLOSE when you have finished putting all your messages
on the queue.

If you want to put a single message on a queue and close the queue immediately
afterwards, you can use the MQPUT1 call. MQPUT1 performs the same functions
as the following sequence of calls:
v MQOPEN
v MQPUT
v MQCLOSE

Generally however, if you have more than one message to put on the queue, it is
more efficient to use the MQPUT call. This depends on the size of the message and
the platform that you are working on.

This chapter introduces putting messages to a queue, under these headings:


v “Putting messages on a local queue using the MQPUT call”
v “Putting messages on a remote queue” on page 115
v “Controlling context information” on page 115
v “Putting one message on a queue using the MQPUT1 call” on page 117
v “Distribution lists” on page 119
v “Some cases where the put calls fail” on page 124

Putting messages on a local queue using the MQPUT call


As input to the MQPUT call, you must supply:
v A connection handle (Hconn).
v A queue handle (Hobj).
v A description of the message that you want to put on the queue. This is in the
form of a message descriptor structure (MQMD).
v Control information, in the form of a put-message options structure (MQPMO).
v The length of the data contained within the message (MQLONG).
v The message data itself.

The output from the MQPUT call is


v A reason code (MQLONG)
v A completion code (MQLONG)

If the call completes successfully, it also returns your options structure and your
message descriptor structure. The call modifies your options structure to show the
name of the queue and the queue manager to which the message was sent. If you

Chapter 2. Writing a WebSphere MQ application 109


request that the queue manager generates a unique value for the identifier of the
message you are putting (by specifying binary zero in the MsgId field of the
MQMD structure), the call inserts the value in the MsgId field before returning this
structure to you. Reset this value before you issue another MQPUT.

There is a description of the MQPUT call in the WebSphere MQ Application


Programming Reference.

The following sections describe the information that you must supply as input to
the MQPUT call.

Specifying handles
For the connection handle (Hconn) in CICS on z/OS applications, you can specify
the constant MQHC_DEF_HCONN (which has the value zero), or you can use the
connection handle returned by the MQCONN or MQCONNX call. For other
applications, always use the connection handle returned by the MQCONN or
MQCONNX call.

Whatever environment you are working in, use the same queue handle (Hobj) that
is returned by the MQOPEN call.

Defining messages using the MQMD structure


The message descriptor structure (MQMD) is an input/output parameter for the
MQPUT and MQPUT1 calls. Use it to define the message you are putting on a
queue.

If MQPRI_PRIORITY_AS_Q_DEF or MQPER_PERSISTENCE_AS_Q_DEF is
specified for the message and the queue is a cluster queue, the values used are
those of the queue to which the MQPUT resolves. If that queue is disabled for
MQPUT, the call will fail. See WebSphere MQ Queue Manager Clusters for more
information.

Note: Use MQPMO_NEW_MSG_ID and MQPMO_NEW_CORREL_ID before


putting a new message to ensure that the MsgId and CorrelId are unique. The
values in these fields are returned on a successful MQPUT.

There is an introduction to the message properties that MQMD describes in


“WebSphere MQ messages” on page 16, and there is a description of the structure
itself in the WebSphere MQ Application Programming Reference.

Specifying options using the MQPMO structure


Use the MQPMO (Put Message Option) structure to pass options to the MQPUT
and MQPUT1 calls.

The following sections give you help on filling in the fields of this structure. There
is a description of the structure in the WebSphere MQ Application Programming
Reference.

The fields of the structure include:


v StrucId
v Version
v Options
v Context
v ResolvedQName

110 WebSphere MQ: Application Programming Guide


v ResolvedQMgrName
These fields are described below.
StrucId
This identifies the structure as a put-message options structure. This is a
4-character field. Always specify MQPMO_STRUC_ID.
Version
This describes the version number of the structure. The default is
MQPMO_VERSION_1. If you enter MQPMO_VERSION_2, you can use
distribution lists (see “Distribution lists” on page 119). If you enter
MQPMO_VERSION_3, you can use message handles and message
properties. If you enter MQPMO_CURRENT_VERSION, your application is
set always to use the most recent level.
Options
This controls the following:
v Whether the put operation is included in a unit of work
v How much context information is associated with a message
v Where the context information is taken from
v Whether the call fails if the queue manager is in a quiescing state
v Whether grouping or segmentation is allowed
v Generation of a new message identifier and correlation identifier
v The order in which messages and segments are put on a queue
v Whether to resolve local queue names
If you leave the Options field set to the default value (MQPMO_NONE),
the message you put has default context information associated with it.
Also, the way that the call operates with syncpoints is determined by the
platform. The syncpoint control default is yes in z/OS; for other platforms,
it is no.
Context
This states the name of the queue handle that you want context
information to be copied from (if requested in the Options field).
For an introduction to message context, see “Message context” on page 46.
For information about using the MQPMO structure to control the context
information in a message, see “Controlling context information” on page
115.
ResolvedQName
This contains the name (after resolution of any alias name) of the queue
that was opened to receive the message. This is an output field.
ResolvedQMgrName
This contains the name (after resolution of any alias name) of the queue
manager that owns the queue in ResolvedQName. This is an output field.

The MQPMO can also accommodate fields required for distribution lists (see
“Distribution lists” on page 119). If you want to use this facility, Version 2 of the
MQPMO structure is used. This includes the following fields:
RecsPresent
This field contains the number of queues in the distribution list; that is, the
number of Put Message Records (MQPMR) and corresponding Response
Records (MQRR) present.

Chapter 2. Writing a WebSphere MQ application 111


The value that you enter can be the same as the number of Object Records
provided at MQOPEN. However, if the value is less than the number of
Object Records provided on the MQOPEN call, or if you provide no Put
Message Records, the values of the queues that are not defined are taken
from the default values provided by the message descriptor. Also, if the
value is greater than the number of Object Records provided, the excess
Put Message Records are ignored.
You are recommended to do one of the following:
v If you want to receive a report or reply from each destination, enter the
same value as appears in the MQOR structure and use MQPMRs
containing MsgId fields. Either initialize these MsgId fields to zeros or
specify MQPMO_NEW_MSG_ID.
When you have put the message to the queue, MsgId values that the
queue manager has created become available in the MQPMRs; you can
use these to identify which destination is associated with each report or
reply.
v If you do not want to receive reports or replies, choose one of the
following:
1. If you want to identify destinations that fail immediately, you might
still want to enter the same value in the RecsPresent field as appears
in the MQOR structure and provide MQRRs to identify these
destinations. Do not specify any MQPMRs.
2. If you do not want to identify failed destinations, enter zero in the
RecsPresent field and do not provide MQPMRs nor MQRRs.

Note: If you are using MQPUT1, the number of Response Record Pointers
and Response Record Offsets must be zero.
For a full description of Put Message Records (MQPMR) and Response
Records (MQRR), see the WebSphere MQ Application Programming Reference.
PutMsgRecFields
This indicates which fields are present in each Put Message Record
(MQPMR). For a list of these fields, see “Using the MQPMR structure” on
page 123.
PutMsgRecOffset and PutMsgRecPtr
Pointers (typically in C) and offsets (typically in COBOL) are used to
address the Put Message Records (see “Using the MQPMR structure” on
page 123 for an overview of the MQPMR structure).
Use the PutMsgRecPtr field to specify a pointer to the first Put Message
Record, or the PutMsgRecOffset field to specify the offset of the first Put
Message Record. This is the offset from the start of the MQPMO.
Depending on the PutMsgRecFields field, enter a nonnull value for either
PutMsgRecOffset or PutMsgRecPtr.
ResponseRecOffset and ResponseRecPtr
You also use pointers and offsets to address the Response Records (see
“Using the MQRR structure” on page 122 for further information about
Response Records).
Use the ResponseRecPtr field to specify a pointer to the first Response
Record, or the ResponseRecOffset field to specify the offset of the first
Response Record. This is the offset from the start of the MQPMO structure.
Enter a nonnull value for either ResponseRecOffset or ResponseRecPtr.

112 WebSphere MQ: Application Programming Guide


Note: If you are using MQPUT1 to put messages to a distribution list,
ResponseRecPtr must be null or zero and ResponseRecOffset must be zero.

Version 3 of the MQPMO structure additionally includes the following fields:


OriginalMsgHandle
The use you can make of this field depends on the value of the Action
field. If you are putting a new message with associated message properties,
set this field to the message handle you previously created and set
properties on. If you are forwarding, replying to, or generating a report in
response to a previously retrieved message, this field contains the message
handle of that message.
NewMsgHandle
If you specify a NewMsgHandle, any properties associated with the handle
override properties associated with the OriginalMsgHandle. For more
information, see WebSphere MQ Application Programming Reference.
Action
Use this field to specify the type of put being performed. Possible values
and their meanings are as follows:
MQACTP_NEW
This is a new message unrelated to any other.
MQACTP_FORWARD
This message was retrieved previously and is now being
forwarded.
MQACTP_REPLY
This message is a reply to a previously retrieved message.
MQACTP_REPORT
This message is a report generated as a result of a previously
retrieved message.

For more information, see WebSphere MQ Application Programming Reference.


PubLevel
If this message is a publication, you can set this field to determine which
subscriptions receive it. Only subscriptions with a SubLevel less than or
equal to this value will receive this publication. The default value is 9
which is the highest level and means that subscriptions with any SubLevel
can receive this publication.

The data in your message


Give the address of the buffer that contains your data in the Buffer parameter of
the MQPUT call. You can include anything in the data in your messages. The
amount of data in the messages, however, affects the performance of the
application that is processing them.

The maximum size of the data is determined by:


v The MaxMsgLength attribute of the queue manager
v The MaxMsgLength attribute of the queue on which you are putting the message
v The size of any message header added by WebSphere MQ (including the
dead-letter header, MQDLH and the distribution list header, MQDH)

Chapter 2. Writing a WebSphere MQ application 113


The MaxMsgLength attribute of the queue manager holds the size of message that
the queue manager can process. This has a default of 100 MB for all WebSphere
MQ products at V6 or higher.

To determine the value of this attribute, use the MQINQ call on the queue
manager object. For large messages, you can change this value.

The MaxMsgLength attribute of a queue determines the maximum size of message


that you can put on the queue. If you attempt to put a message with a size larger
than the value of this attribute, your MQPUT call fails. If you are putting a
message on a remote queue, the maximum size of message that you can
successfully put is determined by the MaxMsgLength attribute of the remote queue,
of any intermediate transmission queues that the message is put on along the route
to its destination, and of the channels used.

For an MQPUT operation, the size of the message must be smaller than or equal to
the MaxMsgLength attribute of both the queue and the queue manager. The values of
these attributes are independent, but you are recommended to set the
MaxMsgLength of the queue to a value less than or equal to that of the queue
manager.

WebSphere MQ adds header information to messages in the following


circumstances:
v When you put a message on a remote queue, WebSphere MQ adds a
transmission header structure (MQXQH) to the message. This structure includes
the name of the destination queue and its owning queue manager.
v If WebSphere MQ cannot deliver a message to a remote queue, it attempts to put
the message on the dead-letter (undelivered-message) queue. It adds an
MQDLH structure to the message. This structure includes the name of the
destination queue and the reason that the message was put on the dead-letter
queue.
v If you want to send a message to multiple destination queues, WebSphere MQ
adds an MQDH header to the message. This describes the data that is present in
a message, belonging to a distribution list, on a transmission queue. Consider
this when choosing an optimum value for the maximum message length.
v If the message is a segment or a message in a group, WebSphere MQ might add
an MQMDE.

These structures are described in the WebSphere MQ Application Programming


Reference.

If your messages are of the maximum size allowed for these queues, the addition
of these headers means that the put operations fail because the messages are now
too big. To reduce the possibility of the put operations failing:
v Make the size of your messages smaller than the MaxMsgLength attribute of the
transmission and dead-letter queues. Allow at least the value of the
MQ_MSG_HEADER_LENGTH constant (more for large distribution lists).
v Make sure that the MaxMsgLength attribute of the dead-letter queue is set to the
same as the MaxMsgLength of the queue manager that owns the dead-letter
queue.

The attributes for the queue manager and the message queuing constants are
described in the WebSphere MQ Application Programming Reference.

114 WebSphere MQ: Application Programming Guide


For information on how undelivered messages are handled in a distributed
queuing environment, see WebSphere MQ Intercommunications.

Putting messages: Using message handles


Two message handles are available in the MQPMO structure, OriginalMsgHandle
and NewMsgHandle. The relationship between these message handles is defined by
the value of the MQPMO Action field.

For full details see the description of the Action field in the WebSphere MQ
Application Programming Reference. A message handle is not necessarily required in
order to put a message. Its purpose is to associate properties with a message, so it
is required only if you are using message properties.

Putting messages on a remote queue


When you want to put a message on a remote queue (that is, a queue owned by a
queue manager other than the one to which your application is connected) rather
than a local queue, the only extra consideration is how you specify the name of the
queue when you open it. This is described in “Opening remote queues” on page
107. There is no change to how you use the MQPUT or MQPUT1 call for a local
queue.

For more information on using remote and transmission queues, see WebSphere MQ
Intercommunications.

Setting properties of a message


Call MQSETMP for each property you want to set. When you put the message set
the message handle and action fields of the MQPMO structure.

To associate properties with a message, the message must have a message handle.
Create a message handle using the MQCRTMH function call. Call MQSETMP
specifying this message handle for each property you want to set. A sample
program, amqsstma.c, is provided to illustrate the use of MQSETMP.

If this is a new message, when you put it to a queue, using MQPUT or MQPUT1,
set the OriginalMsgHandle field in the MQPMO to the value of this message
handle, and set the MQPMO Action field to MQACTP_NEW (this is the default
value).

If this is a message you have previously retrieved, and you are now forwarding or
replying to it or sending a report in response to it, put the original message handle
in the OriginalMsgHandle field of the MQPMO and the new message handle in
the NewMsgHandle field. Set the Action field to MQACTP_FORWARD,
MQACTP_REPLY, or MQACTP_REPORT, as appropriate.

For more information about the message handle and Action fields, see the
WebSphere MQ Application Programming Reference.

If you have properties in an MQRFH2 header from a message you have previously
retrieved, you can convert them to message handle properties using the
MQBUFMH call.

Controlling context information


To control context information, use the Options field in the MQPMO structure.

Chapter 2. Writing a WebSphere MQ application 115


If you do not, the queue manager overwrites context information that might
already be in the message descriptor with the identity and context information that
it has generated for your message. This is the same as specifying the
MQPMO_DEFAULT_CONTEXT option. You might want this default context
information when you create a new message (for example, when processing user
input from an inquiry screen).

If you want no context information associated with your message, use the
MQPMO_NO_CONTEXT option.

The following topics explain the use of identity context, user context and all
context.

Passing identity context


In general, programs should pass identity context information from message to
message around an application until the data reaches its final destination.

Programs should change the origin context information each time that they change
the data. However, applications that want to change or set any context information
must have the appropriate level of authority. The queue manager checks this
authority when the applications open the queues; they must have authority to use
the appropriate context options for the MQOPEN call.

If your application gets a message, processes the data from the message, then puts
the changed data into another message (possibly for processing by another
application), the application must pass the identity context information from the
original message to the new message. You can allow the queue manager to create
the origin context information.

To save the context information from the original message, use the
MQOO_SAVE_ALL_CONTEXT option when you open the queue for getting the
message. This is in addition to any other options you use with the MQOPEN call.
Note, however, that you cannot save context information if you only browse the
message.

When you create the second message:


v Open the queue using the MQOO_PASS_IDENTITY_CONTEXT option (in
addition to the MQOO_OUTPUT option).
v In the Context field of the put-message options structure, give the handle of the
queue from which you saved the context information.
v In the Options field of the put-message options structure, specify the
MQPMO_PASS_IDENTITY_CONTEXT option.

Passing user context


You cannot choose to pass only user context. To pass user context when putting a
message, specify MQPMO_PASS_ALL_CONTEXT. Any properties in the user
context are passed in the same way as the origin context.

When an MQPUT or MQPUT1 takes place and the context is being passed, all
properties in the user context are passed from the retrieved message to the put
message. Any user context properties that the putting application has altered are
put with their original values. Any user context properties that the putting
application has deleted are restored in the put message. Any user context
properties that the putting application has added to the message are retained.

116 WebSphere MQ: Application Programming Guide


Passing all context
If your application gets a message, and puts the message data (unchanged) into
another message, the application must pass all (identity, origin, and user) context
information from the original message to the new message. An example of an
application that might do this is a message mover, which moves messages from
one queue to another.

Follow the same procedure as for passing identity context, except that you use the
MQOPEN option MQOO_PASS_ALL_CONTEXT and the put-message option
MQPMO_PASS_ALL_CONTEXT.

Setting identity context


If you want to set the identity context information for a message:
v Open the queue using the MQOO_SET_IDENTITY_CONTEXT option.
v Put the message on the queue, specifying the
MQPMO_SET_IDENTITY_CONTEXT option. In the message descriptor, specify
whatever identity context information you require.

Note: When you set some (but not all) of the identity context fields using the
MQOO_SET_IDENTITY_CONTEXT and MQPMO_SET_IDENTITY_CONTEXT
options, it is important to realize that the queue manager does not set any of the
other fields.

Setting user context


To set a property in the user context, set the Context field of the message property
descriptor (MQPD) to MQPD_USER_CONTEXT when you make the MQSETMP
call..

You do not need any special authority to set a property in the user context. User
context has no MQOO_SET_* or MQPMO_SET_* context options

Setting all context


If you want to set both the identity and the origin context information for a
message:
1. Open the queue using the MQOO_SET_ALL_CONTEXT option.
2. Put the message on the queue, specifying the MQPMO_SET_ALL_CONTEXT
option. In the message descriptor, specify whatever identity and origin context
information you require.
Appropriate authority is needed for each type of context setting.

Putting one message on a queue using the MQPUT1 call


Use the MQPUT1 call when you want to close the queue immediately after you
have put a single message on it. For example, a server application is likely to use
the MQPUT1 call when it is sending a reply to each of the different queues.

MQPUT1 is functionally equivalent to calling MQOPEN followed by MQPUT,


followed by MQCLOSE. The only difference in the syntax for the MQPUT and
MQPUT1 calls is that for MQPUT you specify an object handle, whereas for
MQPUT1 you specify an object descriptor structure (MQOD) as defined in
MQOPEN (see “Identifying objects (the MQOD structure)” on page 101). This is
because you need to give information to the MQPUT1 call about the queue that it
has to open, whereas when you call MQPUT, the queue must already be open.
Chapter 2. Writing a WebSphere MQ application 117
As input to the MQPUT1 call, you must supply:
v A connection handle.
v A description of the object that you want to open. This is in the form of an
object descriptor structure (MQOD).
v A description of the message that you want to put on the queue. This is in the
form of a message descriptor structure (MQMD).
v Control information in the form of a put-message options structure (MQPMO).
v The length of the data contained within the message (MQLONG).
v The address of the message data.

The output from MQPUT1 is:


v A completion code
v A reason code

If the call completes successfully, it also returns your options structure and your
message descriptor structure. The call modifies your options structure to show the
name of the queue and the queue manager to which the message was sent. If you
request that the queue manager generate a unique value for the identifier of the
message that you are putting (by specifying binary zero in the MsgId field of the
MQMD structure), the call inserts the value in the MsgId field before returning this
structure to you.

Note: You cannot use MQPUT1 with a model queue name; however, once a model
queue has been opened, you can issue an MQPUT1 to the dynamic queue.

The six input parameters for MQPUT1 are:


Hconn This is a connection handle. For CICS applications, you can specify the
constant MQHC_DEF_HCONN (which has the value zero), or use the
connection handle returned by the MQCONN or MQCONNX call. For
other programs, always use the connection handle returned by the
MQCONN or MQCONNX call.
ObjDesc
This is an object descriptor structure (MQOD).
In the ObjectName and ObjectQMgrName fields, give the name of the queue
on which you want to put a message, and the name of the queue manager
that owns this queue.
The DynamicQName field is ignored for the MQPUT1 call because it cannot
use model queues.
Use the AlternateUserId field if you want to nominate an alternate user
identifier that is to be used to test authority to open the queue.
MsgDesc
This is a message descriptor structure (MQMD). As with the MQPUT call,
use this structure to define the message that you are putting on the queue.
PutMsgOpts
This is a put-message options structure (MQPMO). Use it as you would for
the MQPUT call (see “Specifying options using the MQPMO structure” on
page 110).
When the Options field is set to zero, the queue manager uses your own
user ID when it performs tests for authority to access the queue. Also, the

118 WebSphere MQ: Application Programming Guide


queue manager ignores any alternate user identifier given in the
AlternateUserId field of the MQOD structure.
BufferLength
This is the length of your message.
Buffer This is the buffer area that contains the text of your message.

When you use clusters, MQPUT1 operates as though MQOO_BIND_NOT_FIXED


is in effect. Applications must use the resolved fields in the MQPMO structure
rather than the MQOD structure to determine where the message was sent. See
WebSphere MQ Queue Manager Clusters for more information.

There is a description of the MQPUT1 call in the WebSphere MQ Application


Programming Reference.

Distribution lists
Not supported on WebSphere MQ for z/OS.

Distribution lists allow you to put a message to multiple destinations in a single


MQPUT or MQPUT1 call. Multiple queues can be opened using a single MQOPEN
and a message can then be put to each of those queues using a single MQPUT.
Some generic information from the MQI structures used for this process can be
superseded by specific information relating to the individual destinations included
in the distribution list.

When an MQOPEN call is issued, generic information is taken from the Object
Descriptor (MQOD). If you specify MQOD_VERSION_2 in the Version field and a
value greater than zero in the RecsPresent field, the Hobj can be defined as a
handle of a list (of one or more queues) rather than of a queue. In this case,
specific information is given through the object records (MQORs), which give
details of destination (that is, ObjectName and ObjectQMgrName).

The object handle (Hobj) is passed to the MQPUT call, allowing you to put to a list
rather than to a single queue.

When a message is put on the queues (MQPUT), generic information is taken from
the Put Message Option structure (MQPMO) and the Message Descriptor
(MQMD). Specific information is given in the form of Put Message Records
(MQPMRs).

Response Records (MQRR) can receive a completion code and reason code specific
to each destination queue.

Figure 9 on page 120 shows how distribution lists work.

Chapter 2. Writing a WebSphere MQ application 119


Local Remote
QMgr1 QMgr2

Local1 Local2 Remote1 Remote2


Setup Xmit2 queue queue queue queue

MQOpen
Put to distribution list

MQORs Local1 Remote1 Remote2


QName QMgrName
local1
local2 Local2
remote1 QMgr2 MQDH
remote2 QMgr2
XmitQ 1 message transmitted
through channel

Key:

Empty queue Queue containing one message

Figure 9. How distribution lists work. This diagram shows that one message is transmitted
through the channel and can be put on more than one remote queue.

Opening distribution lists


Use the MQOPEN call to open a distribution list, and use the options of the call to
specify what you want to do with the list.

As input to MQOPEN, you must supply:


v A connection handle (see “Putting messages on a queue” on page 109 for a
description)
v Generic information in the Object Descriptor structure (MQOD)
v The name of each queue that you want to open, using the Object Record
structure (MQOR)

The output from MQOPEN is:


v An object handle that represents your access to the distribution list
v A generic completion code
v A generic reason code
v Response Records (optional), containing a completion code and reason for each
destination

Using the MQOD structure:

Use the MQOD structure to identify the queues that you want to open.

To define a distribution list, you must specify MQOD_VERSION_2 in the Version


field, a value greater than zero in the RecsPresent field, and MQOT_Q in the
ObjectType field. See MQOD - Object descriptor for a description of all the fields of
the MQOD structure.

120 WebSphere MQ: Application Programming Guide


Using the MQOR structure:

Provide an MQOR structure for each destination.

The structure contains the destination queue and queue manager names. The
ObjectName and ObjectQMgrName fields in the MQOD are not used for distribution
lists. There must be one or more object records. If the ObjectQMgrName is left blank,
the local queue manager is used. See the WebSphere MQ Application Programming
Reference for further information about these fields.

You can specify the destination queues in two ways:


v By using the offset field ObjectRecOffset.
In this case, the application must declare its own structure containing an MQOD
structure, followed by the array of MQOR records (with as many array elements
as are needed), and set ObjectRecOffset to the offset of the first element in the
array from the start of the MQOD. Ensure that this offset is correct.
Use of built-in facilities provided by the programming language is
recommended, if these are available in all the environments in which the
application runs. The following illustrates this technique for the COBOL
programming language:
01 MY-OPEN-DATA.
02 MY-MQOD.
COPY CMQODV.
02 MY-MQOR-TABLE OCCURS 100 TIMES.
COPY CMQORV.
MOVE LENGTH OF MY-MQOD TO MQOD-OBJECTRECOFFSET.
Alternatively, use the constant MQOD_CURRENT_LENGTH if the programming
language does not support the necessary built-in facilities in all the
environments concerned. The following illustrates this technique:
01 MY-MQ-CONSTANTS.
COPY CMQV.
01 MY-OPEN-DATA.
02 MY-MQOD.
COPY CMQODV.
02 MY-MQOR-TABLE OCCURS 100 TIMES.
COPY CMQORV.
MOVE MQOD-CURRENT-LENGTH TO MQOD-OBJECTRECOFFSET.

However, this works correctly only if the MQOD structure and the array of
MQOR records are contiguous; if the compiler inserts skip bytes between the
MQOD and the MQOR array, these must be added to the value stored in
ObjectRecOffset.
Using ObjectRecOffset is recommended for programming languages that do not
support the pointer data type, or that implement the pointer data type in a way
that is not portable to different environments (for example, the COBOL
programming language).
v By using the pointer field ObjectRecPtr.
In this case, the application can declare the array of MQOR structures separately
from the MQOD structure, and set ObjectRecPtr to the address of the array. The
following illustrates this technique for the C programming language:
MQOD MyMqod;
MQOR MyMqor[100];
MyMqod.ObjectRecPtr = MyMqor;
Using ObjectRecPtr is recommended for programming languages that support
the pointer data type in a way that is portable to different environments (for
example, the C programming language).

Chapter 2. Writing a WebSphere MQ application 121


Whichever technique you choose, you must use one of ObjectRecOffset and
ObjectRecPtr; the call fails with reason code MQRC_OBJECT_RECORDS_ERROR if
both are zero, or both are nonzero.

Using the MQRR structure:

These structures are destination specific; each Response Record contains a CompCode
and Reason field for each queue of a distribution list. You must use this structure
to enable you to distinguish where any problems lie.

For example, if you receive a reason code of MQRC_MULTIPLE_REASONS and


your distribution list contains five destination queues, you will not know which
queues the problems apply to if you do not use this structure. However, if you
have a completion code and reason code for each destination, you can locate the
errors more easily.

See the WebSphere MQ Application Programming Reference for further information


about the MQRR structure.

Figure 10 shows how you can open a distribution list in C.

MQOD 2 n ptr ptr

MQOR MQRR
0 Q QMgr 0 CompCode Reason
Q QMgr CompCode Reason
n-1 Q QMgr n-1 CompCode Reason

Figure 10. Opening a distribution list in C. The MQOD uses pointers to the MQOR and MQRR structures.

Figure 11 shows how you can open a distribution list in COBOL.

0 x 0 n-1 y
MQOD 2 n offset offset Q QMgr Q QMgr Comp Comp
Code Reason Code R
x y

Figure 11. Opening a distribution list in COBOL. The MQOD uses offsets in COBOL.

Using the MQOPEN options:

You can specify the following options when opening a distribution list:
v MQOO_OUTPUT
v MQOO_FAIL_IF_QUIESCING (optional)
v MQOO_ALTERNATE_USER_AUTHORITY (optional)
v MQOO_*_CONTEXT (optional)

See “Opening and closing objects” on page 99 for a description of these options.

Putting messages to a distribution list


To put messages to a distribution list, you can use MQPUT or MQPUT1.

As input, you must supply:

122 WebSphere MQ: Application Programming Guide


v A connection handle (see “Putting messages on a queue” on page 109 for a
description).
v An object handle. If a distribution list is opened using MQOPEN, the Hobj
allows you only to put to the list.
v A message descriptor structure (MQMD). See the WebSphere MQ Application
Programming Reference for a description of this structure.
v Control information in the form of a put-message option structure (MQPMO).
See “Specifying options using the MQPMO structure” on page 110 for
information about filling in the fields of the MQPMO structure.
v Control information in the form of Put Message Records (MQPMR).
v The length of the data contained within the message (MQLONG).
v The message data itself.

The output is:


v A completion code
v A reason code
v Response Records (optional)

Using the MQPMR structure:

This structure is optional and gives destination-specific information for some fields
that you might want to identify differently from those already identified in the
MQMD.

For a description of these fields, see the WebSphere MQ Application Programming


Reference.

The content of each record depends on the information given in the


PutMsgRecFields field of the MQPMO. For example, in the sample program
AMQSPTL0.C (see “The Distribution List sample program” on page 405 for a
description) showing the use of distribution lists, the sample chooses to provide
values for MsgId and CorrelId in the MQPMR. This section of the sample program
looks like this:
typedef struct
{
MQBYTE24 MsgId;
MQBYTE24 CorrelId;
} PutMsgRec;...
/**********************
MQLONG PutMsgRecFields=MQPMRF_MSG_ID | MQPMRF_CORREL_ID;

This implies that MsgId and CorrelId are provided for each destination of a
distribution list. The Put Message Records are provided as an array.

Figure 12 on page 124 shows how you can put a message to a distribution list in C.

Chapter 2. Writing a WebSphere MQ application 123


MQPMO 2 f n ptr ptr

MQPMR MQRR
e.g. MsgId, CorrelId (depending
on f) CompCode Reason
CompCode Reason
CompCode Reason

Figure 12. Putting a message to a distribution list in C. The MQPMO uses pointers to the MQPMR and MQRR
structures.

Figure 13 shows how you can put a message to a distribution list in COBOL.

x y
MQPMO 2 f n offset1 offset2 MQPMR MQRR
x y

Figure 13. Putting a message to a distribution list in COBOL. The MQPMO uses offsets in COBOL.

Using MQPUT1:

If you are using MQPUT1, consider the following:


1. The values of the ResponseRecOffset and ResponseRecPtr fields must be null or
zero.
2. The Response Records, if required, must be addressed from the MQOD.

Some cases where the put calls fail


If certain attributes of a queue are changed using the FORCE option on a
command during the interval between you issuing an MQOPEN and an MQPUT
call, the MQPUT call fails and returns the MQRC_OBJECT_CHANGED reason
code.

The queue manager marks the object handle as being no longer valid. This also
happens if the changes are made while an MQPUT1 call is being processed, or if
the changes apply to any queue to which the queue name resolves. The attributes
that affect the handle in this way are listed in the description of the MQOPEN call
in the WebSphere MQ Application Programming Reference. If your call returns the
MQRC_OBJECT_CHANGED reason code, close the queue, reopen it, then try to
put a message again.

If put operations are inhibited for a queue on which you are attempting to put
messages (or any queue to which the queue name resolves), the MQPUT or
MQPUT1 call fails and returns the MQRC_PUT_INHIBITED reason code. You
might be able to put a message successfully if you attempt the call at a later time,
if the design of the application is such that other programs change the attributes of
queues regularly.

Furthemore, if the queue that you are trying to put your message on is full, the
MQPUT or MQPUT1 call fails and returns MQRC_Q_FULL.

If a dynamic queue (either temporary or permanent) has been deleted, MQPUT


calls using a previously-acquired object handle fail and return the
MQRC_Q_DELETED reason code. In this situation, it is good practice to close the
object handle as it is no longer of any use to you.

124 WebSphere MQ: Application Programming Guide


In the case of distribution lists, multiple completion codes and reason codes can
occur in a single request. These cannot be handled using only the CompCode and
Reason output fields on MQOPEN and MQPUT.

When you use distribution lists to put messages to multiple destinations, the
Response Records contain the specific CompCode and Reason for each destination. If
you receive a completion code of MQCC_FAILED, no message is put on any
destination queue successfully. If the completion code is MQCC_WARNING, the
message is successfully put on one or more of the destination queues. If you
receive a return code of MQRC_MULTIPLE_REASONS, the reason codes are not
all the same for every destination. Therefore, it is recommended to use the MQRR
structure so that you can determine which queue or queues caused an error and
the reasons for each.

Getting messages from a queue


You can get messages from a queue in two ways:
1. You can remove a message from the queue so that other programs can no longer
see it.
2. You can copy a message, leaving the original message on the queue. This is
known as browsing. You can remove the message once you have browsed it.
In both cases, you use the MQGET call, but first your application must be
connected to the queue manager, and you must use the MQOPEN call to open the
queue (for input, browse, or both). These operations are described in “Connecting
to and disconnecting from a queue manager” on page 91 and “Opening and
closing objects” on page 99.

When you have opened the queue, you can use the MQGET call repeatedly to
browse or remove messages on the same queue. Call MQCLOSE when you have
finished getting all the messages that you want from the queue.

This chapter introduces getting messages from a queue, under these headings:
v “Getting messages from a queue using the MQGET call”
v “The order in which messages are retrieved from a queue” on page 131
v “Getting a particular message” on page 138
v “Type of index” on page 142
v “Handling messages greater than 4 MB long” on page 143
v “Waiting for messages” on page 149
v “Signaling” on page 150
v “Skipping backout” on page 152
v “Application data conversion” on page 154
v “Browsing messages on a queue” on page 156
v “Browsing messages in logical order” on page 159
v “Some cases where the MQGET call fails” on page 162

Getting messages from a queue using the MQGET call


The MQGET call gets a message from an open local queue. It cannot get a message
from a queue on another system.

As input to the MQGET call, you must supply:


v A connection handle.
Chapter 2. Writing a WebSphere MQ application 125
v A queue handle.
v A description of the message that you want to get from the queue. This is in the
form of a message descriptor (MQMD) structure.
v Control information in the form of a Get Message Options (MQGMO) structure.
v The size of the buffer that you have assigned to hold the message (MQLONG).
v The address of the storage in which to put the message.

The output from MQGET is:


v A reason code
v A completion code
v The message in the buffer area that you specified, if the call completes
successfully
v Your options structure, modified to show the name of the queue from which the
message was retrieved
v Your message descriptor structure, with the contents of the fields modified to
describe the message that was retrieved
v The length of the message (MQLONG)

There is a description of the MQGET call in the WebSphere MQ Application


Programming Reference.

The following sections describe the information you must supply as input to the
MQGET call.

Specifying connection handles


For CICS on z/OS applications, you can specify the constant
MQHC_DEF_HCONN (which has the value zero), or use the connection handle
returned by the MQCONN or MQCONNX call. For other applications, always use
the connection handle returned by the MQCONN or MQCONNX call.

Use the queue handle (Hobj) that is returned when you call MQOPEN.

Describing messages using the MQMD structure and the MQGET


call
To identify the message that you want to get from a queue, use the message
descriptor structure (MQMD).

This is an input/output parameter for the MQGET call. There is an introduction to


the message properties that MQMD describes in “WebSphere MQ messages” on
page 16, and there is a description of the structure itself in the WebSphere MQ
Application Programming Reference.

If you know which message you want to get from the queue, see “Getting a
particular message” on page 138.

If you do not specify a particular message, MQGET retrieves the first message in
the queue. “The order in which messages are retrieved from a queue” on page 131
describes how the priority of a message, the MsgDeliverySequence attribute of the
queue, and the MQGMO_LOGICAL_ORDER option determine the order of the
messages in the queue.

126 WebSphere MQ: Application Programming Guide


Note: If you want to use MQGET more than once (for example, to step through
the messages in the queue), you must set the MsgId and CorrelId fields of this
structure to null after each call. This clears these fields of the identifiers of the
message that was retrieved.

However, if you want to group your messages, the GroupId must be the same for
messages in the same group, so that the call looks for a message having the same
identifiers as the previous message in order to make up the whole group.

Specifying MQGET options using the MQGMO structure


The MQGMO structure is an input/output variable for passing options to the
MQGET call. The following sections help you to complete some of the fields of this
structure.

There is a description of the MQGMO structure in the WebSphere MQ Application


Programming Reference.
StrucId
StrucId is a 4-character field used to identify the structure as a
get-message options structure. Always specify MQGMO_STRUC_ID.
Version
Version describes the version number of the structure.
MQGMO_VERSION_1 is the default. If you want to use the Version 2
fields or retrieve messages in logical order, specify MQGMO_VERSION_2.
If you want to use the Version 3 fields or retrieve messages in logical order,
specify MQGMO_VERSION_3. MQGMO_CURRENT_VERSION sets your
application to use the most recent level.
Options
Within your code, you can select the options in any order; each option is
represented by a bit in the Options field.
The Options field controls:
v Whether the MQGET call waits for a message to arrive on the queue
before it completes (see “Waiting for messages” on page 149)
v Whether the get operation is included in a unit of work.
v Whether a nonpersistent message is retrieved outside syncpoint,
allowing fast messaging
v On WebSphere MQ for z/OS, whether the message retrieved is marked
as skipping backout (see “Skipping backout” on page 152)
v Whether the message is removed from the queue, or merely browsed
v Whether to select a message by using a browse cursor or by other
selection criteria
v Whether the call succeeds even if the message is longer than your buffer
v On WebSphere MQ for z/OS, whether to allow the call to complete. This
option also sets a signal to indicate that you want to be notified when a
message arrives
v Whether the call fails if the queue manager is in a quiescing state
v On WebSphere MQ for z/OS, whether the call fails if the connection is
in a quiescing state
v Whether application message data conversion is required (see
“Application data conversion” on page 154)
v The order in which messages and (with the exception of WebSphere MQ
for z/OS) segments are retrieved from a queue

Chapter 2. Writing a WebSphere MQ application 127


v Except on WebSphere MQ for z/OS, whether complete, logical messages
only are retrievable
v Whether messages in a group can be retrieved only when all messages in
the group are available
v Except on WebSphere MQ for z/OS, whether segments in a logical
message can be retrieved only when all segments in the logical message
are available
If you leave the Options field set to the default value
(MQGMO_NO_WAIT), the MQGET call operates this way:
v If there is no message matching your selection criteria on the queue, the
call does not wait for a message to arrive, but completes immediately.
Also, in WebSphere MQ for z/OS, the call does not set a signal
requesting notification when such a message arrives.
v The way that the call operates with syncpoints is determined by the
platform:

Platform Under syncpoint control


i5/OS No
UNIX systems No
z/OS Yes
Windows systems No

v On WebSphere MQ for z/OS, the message retrieved is not marked as


skipping backout.
v The selected message is removed from the queue (not browsed).
v No application message data conversion is required.
v The call fails if the message is longer than your buffer.
WaitInterval
The WaitInterval field specifies the maximum time (in milliseconds) that
the MQGET call waits for a message to arrive on the queue when you use
the MQGMO_WAIT option. If no message arrives within the time specified
in WaitInterval, the call completes and returns a reason code showing that
there was no message that matched your selection criteria on the queue.
On WebSphere MQ for z/OS, if you use the MQGMO_SET_SIGNAL
option, the WaitInterval field specifies the time for which the signal is set.
For more information on these options, see “Waiting for messages” on
page 149 and “Signaling” on page 150.
Signal1
Signal1 is supported on WebSphere MQ for z/OS and MQSeries® for
Compaq NonStop Kernel only.
If you use the MQGMO_SET_SIGNAL option to request that your
application is notified when a suitable message arrives, you specify the
type of signal in the Signal1 field. In WebSphere MQ on all other
platforms, the Signal1 field is reserved and its value is not significant.
For more information, see “Signaling” on page 150.
Signal2
The Signal2 field is reserved on all platforms and its value is not
significant.

128 WebSphere MQ: Application Programming Guide


For more information, see “Signaling” on page 150.
ResolvedQName
ResolvedQName is an output field in which the queue manager returns the
name of the queue (after resolution of any alias) from which the message
was retrieved.
MatchOptions
MatchOptions controls the selection criteria for MQGET.
GroupStatus
GroupStatus indicates whether the message that you have retrieved is in a
group.
SegmentStatus
SegmentStatus indicates whether the item that you have retrieved is a
segment of a logical message.
Segmentation
Segmentation indicates whether segmentation is allowed for the message
retrieved.
MsgToken
MsgToken uniquely identifies a message.
For more information, see “WebSphere MQ Workflow” on page 281.
ReturnedLength
ReturnedLength is an output field in which the queue manager returns the
length of message data returned (in bytes).
MsgHandle
The handle to a message that is to be populated with the properties of the
message being retrieved from the queue. The handle has previously been
created by an MQCRTMH call. Any properties already associated with the
handle are cleared before retrieving a message.

Retrieving properties of a message


You can either retrieve message properties using a message handle or MQRFH2
headers. Use the MQGMO Options field to indicate how you want properties to be
returned. Use MQINQMP to return properties associated with a message handle to
your application.

If you set MQGMO_PROPERTIES_IN_HANDLE and set the MsgHandle in your


MQGET call to a valid value, the message properties are made available using that
message handle. If you set MQGMO_PROPERTIES_FORCE_MQRFH2, the message
properties are returned in MQRFH2 headers. If you set
MQGMO_PROPERTIES_AS_Q_DEF, properties are represented as defined by the
PropertyControl queue attribute; however, if a MsgHandle is provided this option
is ignored and the properties of the message are made available on the
MsgHandle, unless the value of the PropertyControl queue attribute is
MQPROP_FORCE_MQRFH2.

When you have associated the message properties with the message handle, you
can return each property to your application using MQINQMP. A sample program,
amqsiqma.c, is provided to illustrate the use of MQINQMP.

You should normally return properties using a message handle. If you already use
properties in MQRFH2 headers in applications using earlier versions of WebSphere
MQ, you can continue to do so by using

Chapter 2. Writing a WebSphere MQ application 129


MQGMO_PROPERTIES_FORCE_MQRFH2 or MQPROP_FORCE_MQRFH2. You
can also use the MQMHBUF call to convert properties from a message handle to
MQRFH2 format.

If you set properties using a message handle, an application connected to an earlier


version of Websphere MQ can retrieve them using MQRFH2 headers.

Websphere MQ Version 7.0 clients connected to queue managers at an earlier


version can retrieve properties using message handles, although those properties
were set using MQRFH2 headers.

Specifying the size of the buffer area


In the BufferLength parameter of the MQGET call, specify the size of the buffer
area to hold the message data that you retrieve. You decide how big this should be
in three ways:
1. You might already know what length of messages to expect from this program.
If so, specify a buffer of this size.
However, you can use the MQGMO_ACCEPT_TRUNCATED_MSG option in
the MQGMO structure if you want the MQGET call to complete even if the
message is too big for the buffer. In this case:
v The buffer is filled with as much of the message as it can hold
v The call returns a warning completion code
v The message is removed from the queue (discarding the remainder of the
message), or the browse cursor is advanced (if you are browsing the queue)
v The real length of the message is returned in DataLength
Without this option, the call still completes with a warning, but it does not
remove the message from the queue (or advance the browse cursor).
2. Estimate a size for the buffer (or even specify a size of zero bytes) and do not
use the MQGMO_ACCEPT_TRUNCATED_MSG option. If the MQGET call fails
(for example, because the buffer is too small), the length of the message is
returned in the DataLength parameter of the call. (The buffer is still filled with
as much of the message as it can hold, but the processing of the call is not
completed.) Store the MsgId of this message, then repeat the MQGET call,
specifying a buffer area of the correct size, and the MsgId that you noted from
the first call.
If your program is serving a queue that is also being served by other programs,
one of those other programs might remove the message that you want before
your program can issue another MQGET call. Your program could waste time
searching for a message that no longer exists. To avoid this, first browse the
queue until you find the message that you want, specifying a BufferLength of
zero and using the MQGMO_ACCEPT_TRUNCATED_MSG option. This
positions the browse cursor under the message that you want. You can then
retrieve the message by calling MQGET again, specifying the
MQGMO_MSG_UNDER_CURSOR option. If another program removes the
message between your browse and removal calls, your second MQGET fails
immediately (without searching the whole queue), because there is no message
under your browse cursor.
3. The MaxMsgLength queue attribute determines the maximum length of messages
accepted for that queue; the MaxMsgLength queue manager attribute determines
the maximum length of messages accepted for that queue manager. If you do

130 WebSphere MQ: Application Programming Guide


not know what length of message to expect, you can inquire about the
MaxMsgLength attribute (using the MQINQ call), then specify a buffer of this
size.
Try to make the buffer size as close as possible to the actual message size to
avoid reduced performance.
For further information about the MaxMsgLength attribute, see “Increasing the
maximum message length” on page 143.

The order in which messages are retrieved from a queue


You can control the order in which you retrieve messages from a queue. This
section looks at the options.

Priority
A program can assign a priority to a message when it puts the message on a queue
(see “Message priorities” on page 26). Messages of equal priority are stored in a
queue in order of arrival, not the order in which they are committed.

The queue manager maintains queues either in strict FIFO (first in, first out)
sequence, or in FIFO within priority sequence. This depends on the setting of the
MsgDeliverySequence attribute of the queue. When a message arrives on a queue, it
is inserted immediately following the last message that has the same priority.

Programs can either get the first message from a queue, or they can get a
particular message from a queue, ignoring the priority of those messages. For
example, a program might want to process the reply to a particular message that it
sent earlier. For more information, see “Getting a particular message” on page 138.

If an application puts a sequence of messages on a queue, another application can


retrieve those messages in the same order that they were put, provided:
v The messages all have the same priority
v The messages were all put within the same unit of work, or all put outside a
unit of work
v The queue is local to the putting application

If these conditions are not met, and the applications depend on the messages being
retrieved in a certain order, the applications must either include sequencing
information in the message data, or establish a means of acknowledging receipt of
a message before the next one is sent.

On WebSphere MQ for z/OS, you can use the queue attribute, IndexType, to
increase the speed of MQGET operations on the queue. For more information, see
“Type of index” on page 142.

Logical and physical ordering


Messages on queues can occur (within each priority level) in physical or logical
order.

Physical order is the order in which messages arrive on a queue. Logical order is
when all of the messages and segments within a group are in their logical
sequence, adjacent to each other, in the position determined by the physical
position of the first item belonging to the group.

For a description of groups, messages, and segments, see “Message groups” on


page 43. These physical and logical orders can differ because:
Chapter 2. Writing a WebSphere MQ application 131
v Groups can arrive at a destination at similar times from different applications,
therefore losing any distinct physical order.
v Even within a single group, messages can get out of order because of rerouting
or delay of some of the messages in the group.

For example, the logical order might look like Figure Figure 14:

Group Message Segment

Y1

Y2

Y3 (last)

Y3.1

Y3.2

Z1

Z2 (last)
B

Figure 14. Logical order on a queue

These messages would appear in the following logical order on a queue:


1. Message A (not in a group)
2. Logical message 1 of group Y
3. Logical message 2 of group Y
4. Segment 1 of (last) logical message 3 of group Y
5. (Last) segment 2 of (last) logical message 3 of group Y
6. Logical message 1 of group Z
7. (Last) logical message 2 of group Z
8. Message B (not in a group)

The physical order, however, might be entirely different. As stated in topic “Logical
and physical ordering” on page 131, the physical position of the first item within
each group determines the logical position of the whole group. For example, if
groups Y and Z arrived at similar times, and message 2 of group Z overtook
message 1 of the same group, the physical order would look like Figure Figure 15
on page 133:

132 WebSphere MQ: Application Programming Guide


Group Message Segment

Y1

Z2 (last)

Y2

Y3 (last)

Y3.1

Y3.2

Z1

Figure 15. Physical order on a queue

These messages appear in the following physical order on the queue:


1. Message A (not in a group)
2. Logical message 1 of group Y
3. Logical message 2 of group Z
4. Logical message 2 of group Y
5. Segment 1 of (last) logical message 3 of group Y
6. (Last) segment 2 of (last) logical message 3 of group Y
7. Logical message 1 of group Z
8. Message B (not in a group)

Note: On WebSphere MQ for z/OS, the physical order of messages on the queue
is not guaranteed if the queue is indexed by GROUPID.

When getting messages, you can specify MQGMO_LOGICAL_ORDER to retrieve


messages in logical rather than physical order.

If you issue an MQGET call with MQGMO_BROWSE_FIRST and


MQGMO_LOGICAL_ORDER, subsequent MQGET calls with
MQGMO_BROWSE_NEXT must also specify this option. Conversely, if the
MQGET with MQGMO_BROWSE_FIRST does not specify
MQGMO_LOGICAL_ORDER, neither must the following MQGETs with
MQGMO_BROWSE_NEXT.

Chapter 2. Writing a WebSphere MQ application 133


The group and segment information that the queue manager retains for MQGET
calls that browse messages on the queue is separate from the group and segment
information that the queue manager retains for MQGET calls that remove
messages from the queue. When you specify MQGMO_BROWSE_FIRST, the queue
manager ignores the group and segment information for browsing, and scans the
queue as though there were no current group and no current logical message.

Note: Take special care if you use an MQGET call to browse beyond the end of a
message group (or logical message not in a group) without specifying
MQGMO_LOGICAL_ORDER. For example, if the last message in the group
precedes the first message in the group on the queue, using
MQGMO_BROWSE_NEXT to browse beyond the end of the group, specifying
MQMO_MATCH_MSG_SEQ_NUMBER with MsgSeqNumber set to 1 (to find the first
message of the next group) returns again the first message in the group already
browsed. This could happen immediately, or a number of MQGET calls later (if
there are intervening groups).

Avoid the possibility of an infinite loop by opening the queue twice for browse:
v Use the first handle to browse only the first message in each group.
v Use the second handle to browse only the messages within a specific group.
v Use the MQMO_* options to move the second browse cursor to the position of
the first browse cursor, before browsing the messages in the group.
v Do not use the MQGMO_BROWSE_NEXT browse beyond the end of a group.
For further information about this, see the WebSphere MQ Application Programming
Reference.

For most applications you will probably choose either logical or physical ordering
when browsing. However, if you want to switch between these modes, remember
that when you first issue a browse with MQGMO_LOGICAL_ORDER, your
position within the logical sequence is established.

If the first item within the group is not present at this time, the group that you are
in is not considered to be part of the logical sequence.

Once the browse cursor is within a group, it can continue within the same group,
even if the first message is removed. Initially though, you can never move into a
group using MQGMO_LOGICAL_ORDER where the first item is not present.

Grouping logical messages:

There are two main reasons for using logical messages in a group:
v You might need to process the messages in a particular order
v You might need to process each message in a group in a related way.

In either case, retrieve the entire group with the same getting application instance.

For example, assume that the group consists of four logical messages. The putting
application looks like this:
PMO.Options = MQPMO_LOGICAL_ORDER | MQPMO_SYNCPOINT

MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP


MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP

134 WebSphere MQ: Application Programming Guide


MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_LAST_MSG_IN_GROUP

MQCMIT

The getting application chooses not to start processing any group until all the
messages within it have arrived. specify MQGMO_ALL_MSGS_AVAILABLE for
the first message in the group; the option is ignored for subsequent messages
within the group.

Once the first logical message of the group is retrieved, use


MQGMO_LOGICAL_ORDER to ensure that the remaining logical messages of the
group are retrieved in order.

So, the getting application looks like this:


/* Wait for the first message in a group, or a message not in a group */
GMO.Options = MQGMO_SYNCPOINT | MQGMO_WAIT
| MQGMO_ALL_MSGS_AVAILABLE | MQGMO_LOGICAL_ORDER
do while ( GroupStatus == MQGS_MSG_IN_GROUP )
MQGET
/* Process each remaining message in the group */
...

MQCMIT

For further examples of grouping messages, see “Application segmentation of


logical messages” on page 146 and “Putting and getting a group that spans units
of work.”

Putting and getting a group that spans units of work:

In the previous case, messages or segments cannot start to leave the node (if its
destination is remote) or start to be retrieved until the whole group has been put
and the unit of work is committed. This might not be what you want if it takes a
long time to put the whole group, or if queue space is limited on the node. To
overcome this, put the group in several units of work.

If the group is put within multiple units of work, it is possible for some of the
group to commit even when the putting application fails. The application must
therefore save status information, committed with each unit of work, which it can
use after a restart to resume an incomplete group. The simplest place to record this
information is in a STATUS queue. If a complete group has been successfully put,
the STATUS queue is empty.

If segmentation is involved, the logic is similar. In this case, the StatusInfo must
include the Offset.

Here is an example of putting the group in several units of work:


PMO.Options = MQPMO_LOGICAL_ORDER | MQPMO_SYNCPOINT

/* First UOW */

MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP


MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
StatusInfo = GroupId,MsgSeqNumber from MQMD
MQPUT (StatusInfo to STATUS queue) PMO.Options = MQPMO_SYNCPOINT
MQCMIT

Chapter 2. Writing a WebSphere MQ application 135


/* Next and subsequent UOWs */
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQGET (from STATUS queue) GMO.Options = MQGMO_SYNCPOINT
StatusInfo = GroupId,MsgSeqNumber from MQMD
MQPUT (StatusInfo to STATUS queue) PMO.Options = MQPMO_SYNCPOINT
MQCMIT

/* Last UOW */
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_LAST_MSG_IN_GROUP
MQGET (from STATUS queue) GMO.Options = MQGMO_SYNCPOINT
MQCMIT

If all the units of work have been committed, the entire group has been put
successfully, and the STATUS queue is empty. If not, the group must be resumed at
the point indicated by the status information. MQPMO_LOGICAL_ORDER cannot
be used for the first put, but can thereafter.

Restart processing looks like this:


MQGET (StatusInfo from STATUS queue) GMO.Options = MQGMO_SYNCPOINT
if (Reason == MQRC_NO_MSG_AVAILABLE)
/* Proceed to normal processing */
...

else
/* Group was terminated prematurely */
Set GroupId, MsgSeqNumber in MQMD to values from Status message
PMO.Options = MQPMO_SYNCPOINT
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP

/* Now normal processing is resumed.


Assume this is not the last message */
PMO.Options = MQPMO_LOGICAL_ORDER | MQPMO_SYNCPOINT
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP
StatusInfo = GroupId,MsgSeqNumber from MQMD
MQPUT (StatusInfo to STATUS queue) PMO.Options = MQPMO_SYNCPOINT
MQCMIT

From the getting application, you might want to start processing the messages in a
group before the whole group has arrived. This improves response times on the
messages within the group, and also means that storage is not required for the
entire group.

For recovery reasons, you must retrieve each message within a unit of work.
However, in order to realize the above benefits, use several units of work for each
group of messages.

As with the corresponding putting application, this requires status information to


be recorded somewhere automatically as each unit of work is committed. Again,
the simplest place to record this information is on a STATUS queue. If a complete
group has been successfully processed, the STATUS queue is empty.

Note: For intermediate units of work, you can avoid the MQGET calls from the
STATUS queue by specifying that each MQPUT to the status queue is a segment of
a message (that is, by setting the MQMF_SEGMENT flag), instead of putting a
complete new message for each unit of work. In the last unit of work, a final

136 WebSphere MQ: Application Programming Guide


segment is put to the status queue specifying MQMF_LAST_SEGMENT, and then
the status information is cleared with an MQGET specifying
MQGMO_COMPLETE_MSG.

During restart processing, instead of using a single MQGET to get a possible status
message, browse the status queue with MQGMO_LOGICAL_ORDER until you
reach the last segment (that is, until no further segments are returned). In the first
unit of work after restart, also specify the offset explicitly when putting the status
segment.

In the following example, we consider only messages within a group, assuming


that the application’s buffer is always large enough to hold the entire message,
whether or not the message has been segmented. MQGMO_COMPLETE_MSG is
therefore specified on each MQGET. The same principles apply if segmentation is
involved (in this case, the StatusInfo must include the Offset).

For simplicity, we assume that a maximum of 4 messages are retrieved within a


single UOW:
msgs = 0 /* Counts messages retrieved within UOW */
/* Should be no status message at this point */

/* Retrieve remaining messages in the group */


do while ( GroupStatus == MQGS_MSG_IN_GROUP )

/* Process up to 4 messages in the group */


GMO.Options = MQGMO_SYNCPOINT | MQGMO_WAIT
| MQGMO_LOGICAL_ORDER
do while ( (GroupStatus == MQGS_MSG_IN_GROUP) && (msgs < 4) )
MQGET
msgs = msgs + 1
/* Process this message */
...
/* end while

/* Have retrieved last message or 4 messages */


/* Update status message if not last in group */
MQGET (from STATUS queue) GMO.Options = MQGMO_SYNCPOINT
if ( GroupStatus == MQGS_MSG_IN_GROUP )
StatusInfo = GroupId,MsgSeqNumber from MQMD
MQPUT (StatusInfo to STATUS queue) PMO.Options = MQPMO_SYNCPOINT
MQCMIT
msgs = 0
/* end while

if ( msgs > 0 )
/* Come here if there was only 1 message in the group */
MQCMIT

If all the units of work have been committed, the entire group has been retrieved
successfully, and the STATUS queue is empty. If not, the group must be resumed at
the point indicated by the status information. MQGMO_LOGICAL_ORDER cannot
be used for the first retrieve, but can thereafter.

Restart processing looks like this:


MQGET (from STATUS queue) GMO.Options = MQGMO_SYNCPOINT
if (Reason == MQRC_NO_MSG_AVAILABLE)
/* Proceed to normal processing */
...

else
/* Group was terminated prematurely */

Chapter 2. Writing a WebSphere MQ application 137


/* The next message on the group must be retrieved by matching
the sequence number and group id with those retrieved from the
status information. */
GMO.Options = MQGMO_COMPLETE_MSG | MQGMO_SYNCPOINT | MQGMO_WAIT
MQGET GMO.MatchOptions = MQMO_MATCH_GROUP_ID | MQMO_MATCH_MSG_SEQ_NUMBER,
MQMD.GroupId = value from Status message,
MQMD.MsgSeqNumber = value from Status message plus 1
msgs = 1
/* Process this message */
...

/* Now normal processing is resumed */


/* Retrieve remaining messages in the group */
do while ( GroupStatus == MQGS_MSG_IN_GROUP )

/* Process up to 4 messages in the group */


GMO.Options = MQGMO_COMPLETE_MSG | MQGMO_SYNCPOINT | MQGMO_WAIT
| MQGMO_LOGICAL_ORDER
do while ( (GroupStatus == MQGS_MSG_IN_GROUP) && (msgs < 4) )
MQGET
msgs = msgs + 1
/* Process this message */
...

/* Have retrieved last message or 4 messages */


/* Update status message if not last in group */
MQGET (from STATUS queue) GMO.Options = MQGMO_SYNCPOINT
if ( GroupStatus == MQGS_MSG_IN_GROUP )
StatusInfo = GroupId,MsgSeqNumber from MQMD
MQPUT (StatusInfo to STATUS queue) PMO.Options = MQPMO_SYNCPOINT
MQCMIT
msgs = 0

Getting a particular message


There are a number of ways of getting a particular message from a queue. These
are: selecting on the MsgId and CorrelId, selecting on the GroupId,
MsgSeqNumber and Offset, and selecting on the MsgToken. You can also use a
selection string when you open the queue.

To get a particular message from a queue, use the MsgId and CorrelId fields of the
MQMD structure. However, applications can explicitly set these fields, so the
values that you specify might not identify a unique message. Table 7 shows which
message is retrieved for the possible settings of these fields. These fields are
ignored on input if you specify MQGMO_MSG_UNDER_CURSOR in the
GetMsgOpts parameter of the MQGET call.
Table 7. Using message and correlation identifiers
To retrieve ... MsgId CorrelId
First message in the queue MQMI_NONE MQCI_NONE
First message that matches MsgId Nonzero MQCI_NONE
First message that matches CorrelId MQMI_NONE Nonzero
First message that matches both MsgId and CorrelId Nonzero Nonzero

In each case, first means the first message that satisfies the selection criteria (unless
MQGMO_BROWSE_NEXT is specified, when it means the next message in the
sequence satisfying the selection criteria).

On return, the MQGET call sets the MsgId and CorrelId fields to the message and
correlation identifiers (respectively) of the message returned (if any).
138 WebSphere MQ: Application Programming Guide
If you set the Version field of the MQMD structure to 2, you can use the GroupId,
MsgSeqNumber, and Offset fields. Table 8 shows which message is retrieved for the
possible settings of these fields.
Table 8. Using the group identifier
To retrieve ... Match options
First message in the queue MQMO_NONE
First message that matches MsgId MQMO_MATCH_MSG_ID
First message that matches CorrelId MQMO_MATCH_CORREL_ID
First message that matches GroupId MQMO_MATCH_GROUP_ID
First message that matches MsgSeqNumber MQMO_MATCH_MSG_SEQ_NUMBER
First message that matches MsgToken MQMO_MATCH_MSG_TOKEN
First message that matches Offset MQMO_MATCH_OFFSET
Notes:
1. MQMO_MATCH_XXX implies that the XXX field in the MQMD structure is set to the
value to be matched.
2. The MQMO flags can be used in combination. For example,
MQMO_MATCH_GROUP_ID, MQMO_MATCH_MSG_SEQ_NUMBER, and
MQMO_MATCH_OFFSET can be used together to give the segment identified by the
GroupId, MsgSeqNumber, and Offset fields.
3. If you specify MQGMO_LOGICAL_ORDER, the message that you are trying to retrieve
is affected because the option depends on state information controlled for the queue
handle. For information about this, see “Logical and physical ordering” on page 131
and the WebSphere MQ Application Programming Reference.

The MQGET call usually retrieves the first message from a queue. If you specify a
particular message when you use the MQGET call, the queue manager has to
search the queue until it finds that message. This can affect the performance of
your application.

If you are using Version 2 or later of the MQGMO structure and do not specify the
MQMO_MATCH_MSG_ID or MQMO_MATCH_CORREL_ID flags, you do not
need to reset the MsgId or CorrelId fields respectively between MQGETs.

On WebSphere MQ for z/OS the queue attribute IndexType can be used to increase
the speed of MQGET operations on the queue. For more information, see “Type of
index” on page 142.

You can get a specific message from a queue by specifying its MsgToken and the
MatchOption MQMO_MATCH_MSG_TOKEN in the MQGMO structure. The
MsgToken is returned by the MQPUT call that originally put that message on the
queue, or by previous MQGET operations and remains constant unless the queue
manager is restarted.

If you are interested in only a subset of messages on the queue, you can specify
which messages you want to process by using a selection string with the
MQOPEN or MQSUB call. MQGET then retrieves the next message that satisfies
that selection string. For more information about selection strings, see “Selectors”
on page 32.

Chapter 2. Writing a WebSphere MQ application 139


Improving performance of non-persistent messages
When a client requires a message from a server, it sends a request to the server. It
sends a separate request for each of the messages it consumes. To improve the
performance of a client consuming non persistent messages by avoiding having to
send these request messages, a client can be configured to use read ahead. Read
ahead allows messages to be sent to a client without an application having to
request them.

When read ahead is enabled, messages are sent to an in memory buffer on the
client called the read ahead buffer. The client will have a read ahead buffer for each
queue it has open with read ahead enabled. The messages in the read ahead buffer
are not persisted. The client periodically updates the server with information about
the amount of data it has consumed.

If a client application is restarted, messages in the read ahead buffer can be lost.

Using read ahead can improve performance when consuming non persistent
messages from a client application. This performance improvement is available to
both MQI and JMS applications. Client applications using MQGET or
asynchronous consumption will benefit from the performance improvements when
consuming non-persistent messages.

Not all client application designs are suited to using read ahead as not all options
are supported for use with read ahead and some options are required to be
consistent between MQGET calls when read ahead is enabled. If a client alters its
selection criteria between MQGET calls, messages being stored in the read ahead
buffer will remain stranded in the client read ahead buffer.

If a backlog of stranded messages with the previous selection criteria are no longer
required, a configurable purge interval can be set on the client to automatically
purge these messages from the client. The purge interval is one of a group of read
ahead tuning options determined by the client. It is possible to tune these options
to meet your requirements.

Read ahead is only performed for client bindings. The attribute is ignored for all
other bindings.

Read ahead has no impact on triggering. No trigger message is generated when a


message is read ahead by the client. Read ahead does not generate accounting and
statistics information when it is enabled.

Using read ahead with publish subscribe messaging

When a subscribing application specifies a destination queue to which publications


are sent, the DEFREADA value of the specified queue is used as the default read
ahead value.

When a subscribing application requests that WebSphere MQ manages the


destination to which publications are sent, a managed queue is created as a
dynamic queue based upon a predefined model queue. It is the DEFREADA value
of the model queue that is used as the default read ahead value. The default model
queues SYSTEM.DURABLE.PUBLICATIONS.MODEL or
SYSTEM.NONDURABLE.PUBLICATIONS.MODEL are used unless a model queue
is defined for this or a parent topic.

140 WebSphere MQ: Application Programming Guide


MQGET options and read ahead
Not all MQGET options are supported when read ahead is enabled and some
options are required to be consistent between MQGET calls when read ahead is
enabled.

The following table indicates which options are supported for use with read ahead
and whether they can be altered between MQGET calls.
Table 9. MQGET options and read ahead
Permitted when read ahead is enabled and can Permitted when read ahead is enabled but MQGET Options that are not permitted
be altered between MQGET calls cannot be altered between MQGET calls1 when read ahead is enabled2
MQGET MQMD values MsgId3 Encoding
CorrelId3 CodedCharSetId
MQGET MQGMO v MQGMO_NO_WAIT v MQGMO_SYNCPOINT_IF _PERSISTENT v MQGMO_SET_SIGNAL
Options
v MQGMO_BROWSE_MESSAGE v MQGMO_NO_SYNCPOINT v MQGMO_SYNCPOINT
_UNDER_CURSOR v MQGMO_ACCEPT_TRUNCATED _MSG v MQGMO_MARK_SKIP _BACKOUT
v MQGMO_BROWSE_FIRST v MQGMO_CONVERT v MQGMO_MSG_UNDER _CURSOR4
v MQGMO_BROWSE_NEXT v MQGMO_LOCK
v MQGMO_FAIL_IF_QUIESCING
v MQGMO_UNLOCK
v MQGMO_LOGICAL_ORDER
v MQGMO_COMPLETE_MSG
v MQGMO_ALL_MSGS_AVAILABLE
v MQGMO_ALL_SEGMENTS_ AVAILABLE

Notes:
1. If these options are altered between MQGET calls an
MQRC_OPTIONS_CHANGED reason code will be returned.
2. If these options are specified on the first MQGET call then read ahead will be
disabled. If these options are specified on a subsequent MQGET call a reason
code MQRC_OPTIONS_ERROR will be returned.
3. The client applications needs to be aware that if the MsgId and CorrelId values
are altered between MQGET calls messages with the previous values may have
already been sent to the client and will remain in the client read ahead buffer
until consumed (or automatically purged).
4. MQGMO_MSG_UNDER_CURSOR is not possible with read ahead. Read ahead
is disabled when both MQOO_BROWSE and one of the
MQOO_INPUT_SHARED or MQOO_INPUT_EXCLUSIVE options are specified
when opening the queue.

If a client alters its selection criteria between MQGET calls, messages being stored
in the read ahead buffer that match the initial selection criteria will not be
consumed by the client application and remain stranded in the client read ahead
buffer. In situations where the client read ahead buffer contains a large number of
stranded messages the benefits associated with read ahead will be lost and a
separate request to the server required for each message consumed. To determine
whether read ahead is being used efficiently you can use the connection status
parameter, READA.

Read ahead can be inhibited when requested by an application due to


incompatible options specified on the first MQGET call. In this situation the
connection status will show read ahead as being inhibited.

If you decide that because of these restrictions on MQGET, that a client application
design is not suited to read ahead, specify the MQOPEN option
MQOO_READ_AHEAD_NO. Alternatively set the default read ahead value of the
queue being opened altered to either NO or DISABLED.

Chapter 2. Writing a WebSphere MQ application 141


Enabling and disabling read ahead
By default read ahead is disabled. You can enable read ahead at queue or
application level.

To enable read ahead:


v To configure read ahead at the queue level set the queue attribute, DEFREADA
to YES.
v To configure read ahead at the application level:
– to use read ahead wherever possible use the MQOO_READ_AHEAD option
on the MQOPEN function call. It will not be possible for the client application
to use read ahead if the DEFREADA queue attribute has been set to
DISABLED.
– to use read ahead only when read ahead is enabled on a queue, use the
MQOO_READ_AHEAD_AS_Q_DEF option on the MQOPEN function call.

If a client application design is not suited to read ahead you can disable it:
v at the queue level by setting the queue attribute, DEFREADA to NO if you do
not want read ahead to be used unless it is requested by a client application, or
DISABLED if you do not want read ahead to be used regardless of whether read
ahead is required by a client application.
v at the application level by using the MQOO_NO_READ_AHEAD option on the
MQOPEN function call.
Two MQCLOSE options allow you to configure what happens to any messages
that are being stored in the read ahead buffer if the queue is closed.
v Use MQCO_IMMEDIATE to discard messages in the read ahead buffer.
v Use MQCO_QUIESCE to ensure that messages in the read ahead buffer are
consumed by the application before the queue is closed. When MQCLOSE with
the MQCO_QUIESCE is issued and there are messages remaining on the read
ahead buffer, MQRC_READ_AHEAD_MSGS will be returned with
MQCC_WARNING.

Type of index
Supported only on WebSphere MQ for z/OS.

The queue attribute, IndexType, specifies the type of index that the queue manager
maintains to increase the speed of MQGET operations on the queue.

You have five options:

Value Description

NONE No index is maintained. Use this when retrieving messages sequentially (see “Priority” on
page 131).
GROUPID An index of group identifiers is maintained. You must use this index type if you want logical
ordering of message groups (see “Logical and physical ordering” on page 131).
MSGID An index of message identifiers is maintained. Use this when retrieving messages using the
MsgId field as a selection criterion on the MQGET call (see “Getting a particular message” on
page 138).
MSGTOKEN An index of message tokens is maintained.
CORRELID An index of correlation identifiers is maintained. Use this when retrieving messages using
the CorrelId field as a selection criterion on the MQGET call (see “Getting a particular
message” on page 138).

142 WebSphere MQ: Application Programming Guide


Note:
1. If you are indexing using the MSGID option or CORRELID option, set the
relative MsgId or CorrelId parameters in the MQMD. It is not beneficial to set
both.
2. Browse uses the index mechanism to find a message if a queue matches all the
following conditions:
v It has index type MSGID, CORRELID, or GROUPID
v It is browsed with the same type of id
v It has messages of only one priority
3. Avoid queues (indexed by MsgId or CorrelId) containing thousands of
messages because this affects restart time. (This does not apply to nonpersistent
messages as they are deleted at restart.)
4. MSGTOKEN is used to define queues managed by the z/OS workload
manager.

For a full description of the IndexType attribute, see the WebSphere MQ Application
Programming Reference. For conditions needed to change the IndexType attribute, see
the WebSphere MQ Script (MQSC) Command Reference.

Handling messages greater than 4 MB long


Messages can be too large for the application, queue, or queue manager.
Depending on the environment, WebSphere MQ provides a number of ways of
dealing with messages that are longer than 4 MB.

You can increase the MaxMsgLength attribute up to 100 MB on all WebSphere MQ


systems at V6 or later. Set this value to reflect the size of the messages using the
queue. On WebSphere MQ systems other than WebSphere MQ for z/OS, you can
also:
1. Use segmented messages. (Messages can be segmented by either the application
or the queue manager.)
2. Use reference messages.

Each of these approaches is described in the remainder of this section.

Increasing the maximum message length


The MaxMsgLength queue manager attribute defines the maximum length of a
message that can be handled by a queue manager. Similarly, the MaxMsgLength
queue attribute is the maximum length of a message that can be handled by a
queue. The default maximum message length supported depends on the
environment in which you are working.

If you are handling large messages, you can alter these attributes independently.
You can set the queue manager attribute value between 32768 bytes and 100 MB;
you can set the queue attribute value between 0 and 100 MB.

After changing one or both of the MaxMsgLength attributes, restart your applications
and channels to ensure that the changes take effect.

When these changes are made, the message length must be less than or equal to
both the queue and the queue manager MaxMsgLength attributes. However, existing
messages might be longer than either attribute.

Chapter 2. Writing a WebSphere MQ application 143


If the message is too big for the queue, MQRC_MSG_TOO_BIG_FOR_Q is
returned. Similarly, if the message is too big for the queue manager,
MQRC_MSG_TOO_BIG_FOR_Q_MGR is returned.

This method of handling large messages is easy and convenient. However,


consider the following factors before using it:
v Uniformity among queue managers is reduced. The maximum size of message
data is determined by the MaxMsgLength for each queue (including transmission
queues) on which the message will be put. This value is often defaulted to the
queue manager’s MaxMsgLength, especially for transmission queues. This makes it
difficult to predict whether a message is too large when it is to travel to a
remote queue manager.
v Usage of system resources is increased. For example, applications need larger
buffers, and on some platforms, there might be increased usage of shared
storage. Queue storage should be affected only if actually required for larger
messages.
v Channel batching is affected. A large message still counts as just one message
towards the batch count but needs longer to transmit, thereby increasing
response times for other messages.

Message segmentation
Not supported in WebSphere MQ for z/OS.

Increasing the maximum message length as discussed in topic “Increasing the


maximum message length” on page 143 has some negative implications. Also, it
can still result in the message being too large for the queue or queue manager. In
these cases, you can segment a message. For information about segments, see
“Message groups” on page 43.

The next sections look at common uses for segmenting messages. For putting and
destructively getting, it is assumed that the MQPUT or MQGET calls always
operate within a unit of work. We strongly recommend that you always use this
technique, to reduce the possibility of incomplete groups being present in the
network. Single-phase commit by the queue manager is assumed, but of course
other coordination techniques are equally valid.

Also, in the getting applications, it is assumed that if multiple servers are


processing the same queue, each server executes similar code, so that one server
never fails to find a message or segment that it expects to be there (because it had
specified MQGMO_ALL_MSGS_AVAILABLE or
MQGMO_ALL_SEGMENTS_AVAILABLE earlier).

Segmentation and reassembly by queue manager:

This is the simplest scenario, in which one application puts a message to be


retrieved by another. The message might be large: not too large for either the
putting or the getting application to handle in a single buffer, but too large for the
queue manager or a queue on which the message is to be put.

The only changes necessary for these applications are for the putting application to
authorize the queue manager to perform segmentation if necessary:
PMO.Options = (existing options)
MQPUT MD.MsgFlags = MQMF_SEGMENTATION_ALLOWED

144 WebSphere MQ: Application Programming Guide


and for the getting application to ask the queue manager to reassemble the
message if it has been segmented:
GMO.Options = MQGMO_COMPLETE_MSG | (existing options)
MQGET

The application buffer must be large enough to contain the reassembled message
(unless you include the MQGMO_ACCEPT_TRUNCATED_MSG option).

If data conversion is necessary, the getting application might have to do it by


specifying MQGMO_CONVERT. This should be straightforward because the data
conversion exit is presented with the complete message. Do not attempt to convert
data in a sender channel if the message is segmented, and the format of the data is
such that the data-conversion exit cannot carry out the conversion on incomplete
data.

Application segmentation:

Application segmentation is used for two main reasons:


1. Queue-manager segmentation alone is not adequate because the message is too
large to be handled in a single buffer by the applications.
2. Data conversion must be performed by sender channels, and the format is such
that the putting application needs to stipulate where the segment boundaries
are to be in order for conversion of an individual segment to be possible.

However, if data conversion is not an issue, or if the getting application always


uses MQGMO_COMPLETE_MSG, queue-manager segmentation can also be
allowed by specifying MQMF_SEGMENTATION_ALLOWED. In our example, the
application segments the message into four segments:
PMO.Options = MQPMO_LOGICAL_ORDER | MQPMO_SYNCPOINT

MQPUT MD.MsgFlags = MQMF_SEGMENT


MQPUT MD.MsgFlags = MQMF_SEGMENT
MQPUT MD.MsgFlags = MQMF_SEGMENT
MQPUT MD.MsgFlags = MQMF_LAST_SEGMENT

MQCMIT

If you do not use MQPMO_LOGICAL_ORDER, the application must set the Offset
and the length of each segment. In this case, logical state is not maintained
automatically.

The getting application cannot guarantee to have a buffer large enough to hold any
reassembled message. It must therefore be prepared to process segments
individually.

For messages that are segmented, this application does not want to start processing
one segment until all the segments that constitute the logical message are present.
MQGMO_ALL_SEGMENTS_AVAILABLE is therefore specified for the first
segment. If you specify MQGMO_LOGICAL_ORDER and there is a current logical
message, MQGMO_ALL_SEGMENTS_AVAILABLE is ignored.

Once the first segment of a logical message has been retrieved, use
MQGMO_LOGICAL_ORDER to ensure that the remaining segments of the logical
message are retrieved in order.

Chapter 2. Writing a WebSphere MQ application 145


No consideration is given to messages within different groups. If such messages
occur, they are processed in the order in which the first segment of each message
appears on the queue.
GMO.Options = MQGMO_SYNCPOINT | MQGMO_LOGICAL_ORDER
| MQGMO_ALL_SEGMENTS_AVAILABLE | MQGMO_WAIT
do while ( SegmentStatus == MQSS_SEGMENT )
MQGET
/* Process each remaining segment of the logical message */
...

MQCMIT

Application segmentation of logical messages:

The messages must be maintained in logical order in a group, and some or all of
them might be so large that they require application segmentation.

In our example, a group of four logical messages is to be put. All but the third
message are large, and require segmentation, which is performed by the putting
application:
PMO.Options = MQPMO_LOGICAL_ORDER | MQPMO_SYNCPOINT

MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP | MQMF_SEGMENT


MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP | MQMF_SEGMENT
MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP | MQMF_LAST_SEGMENT

MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP | MQMF_SEGMENT


MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP | MQMF_LAST_SEGMENT

MQPUT MD.MsgFlags = MQMF_MSG_IN_GROUP

MQPUT MD.MsgFlags = MQMF_LAST_MSG_IN_GROUP | MQMF_SEGMENT


MQPUT MD.MsgFlags = MQMF_LAST_MSG_IN_GROUP | MQMF_SEGMENT
MQPUT MD.MsgFlags = MQMF_LAST_MSG_IN_GROUP | MQMF_LAST_SEGMENT

MQCMIT

In the getting application, MQGMO_ALL_MSGS_AVAILABLE is specified on the


first MQGET. This means that no messages or segments of a group are retrieved
until the entire group is available. When the first physical message of a group has
been retrieved, MQGMO_LOGICAL_ORDER is used to ensure that the segments
and messages of the group are retrieved in order:
GMO.Options = MQGMO_SYNCPOINT | MQGMO_LOGICAL_ORDER
| MQGMO_ALL_MESSAGES_AVAILABLE | MQGMO_WAIT

do while ( (GroupStatus != MQGS_LAST_MSG_IN_GROUP) ||


(SegmentStatus != MQGS_LAST_SEGMENT) )
MQGET
/* Process a segment or complete logical message. Use the GroupStatus
and SegmentStatus information to see what has been returned */
...

MQCMIT

Note: If you specify MQGMO_LOGICAL_ORDER and there is a current group,


MQGMO_ALL_MSGS_AVAILABLE is ignored.

Putting and getting a segmented message that spans units of work:

You can put and get a segmented message that spans a unit of work in a similar
way to “Putting and getting a group that spans units of work” on page 135.

146 WebSphere MQ: Application Programming Guide


You cannot, however, put or get segmented messages in a global unit of work.

Reference messages
Not supported in WebSphere MQ for z/OS.

This method allows a large object to be transferred from one node to another
without storing the object on WebSphere MQ queues at either the source or the
destination nodes. This is of particular benefit when the data already exists in
another form, for example, for mail applications.

To do this, you specify a message exit at both ends of a channel. For information
on how to do this, see WebSphere MQ Intercommunications.

WebSphere MQ defines the format of a reference message header (MQRMH). See


the WebSphere MQ Application Programming Reference for a description of this. This
is recognized by means of a defined format name and might be followed by actual
data.

To initiate transfer of a large object, an application can put a message consisting of


a reference message header with no data following it. As this message leaves the
node, the message exit retrieves the object in an appropriate way and appends it to
the reference message. It then returns the message (now larger than before) to the
sending Message Channel Agent for transmission to the receiving MCA.

Another message exit is configured at the receiving MCA. When this message exit
sees one of these messages, it creates the object using the object data that was
appended and passes on the reference message without it. The reference message
can now be received by an application and this application knows that the object
(or at least the portion of it represented by this reference message) has been
created at this node.

The maximum amount of object data that a sending message exit can append to
the reference message is limited by the negotiated maximum message length for
the channel. The exit can return only a single message to the MCA for each
message that it is passed, so the putting application can put several messages to
cause one object to be transferred. Each message must identify the logical length
and offset of the object that is to be appended to it. However, in cases where it is
not possible to know the total size of the object or the maximum size allowed by
the channel, design the sending message exit so that the putting application just
puts a single message, and the exit itself puts the next message on the transmission
queue when it has appended as much data as it can to the message it has been
passed.

Before using this method of dealing with large messages, consider the following:
v The MCA and the message exit run under a WebSphere MQ user ID. The
message exit (and therefore, the user ID) needs to access the object to either
retrieve it at the sending end or create it at the receiving end; this might only be
feasible in cases where the object is universally accessible. This raises a security
issue.
v If the reference message with bulk data appended to it must travel through
several queue managers before reaching its destination, the bulk data is present
on WebSphere MQ queues at the intervening nodes. However, no special
support or exits need to be provided in these cases.

Chapter 2. Writing a WebSphere MQ application 147


v Designing your message exit is made difficult if rerouting or dead-letter queuing
is allowed. In these cases, the portions of the object might arrive out of order.
v When a reference message arrives at its destination, the receiving message exit
creates the object. However, this is not synchronized with the MCA’s unit of
work, so if the batch is backed out, another reference message containing this
same portion of the object will arrive in a later batch, and the message exit
might attempt to re-create the same portion of the object. If the object is, for
example, a series of database updates, this might be unacceptable. If so, the
message exit must keep a log of which updates have been applied; this might
require the use of a WebSphere MQ queue.
v Depending on the characteristics of the object type, the message exits and
applications might need to cooperate in maintaining use counts, so that the
object can be deleted when it is no longer needed. An instance identifier might
also be required; a field is provided for this in the reference message header (see
the WebSphere MQ Application Programming Reference).
v If a reference message is put as a distribution list, the object must be retrievable
for each resulting distribution list or individual destination at that node. You
might need to maintain use counts. Also consider the possibility that a given
node might be the final node for some of the destinations in the list, but an
intermediate node for others.
v Bulk data is not ususally converted. This is because conversion takes place before
the message exit is invoked. For this reason, conversion must not be requested
on the originating sender channel. If the reference message passes through an
intermediate node, the bulk data is converted when sent from the intermediate
node, if requested.
v Reference messages cannot be segmented.

Using the MQRMH and MQMD structures:

See the WebSphere MQ Application Programming Reference for a description of the


fields in the reference message header and the message descriptor.

In the MQMD structure, set the Format field to MQFMT_REF_MSG_HEADER. The


MQHREF format, when requested on MQGET, is converted automatically by
WebSphere MQ along with any bulk data that follows.

Here is an example of the use of the DataLogicalOffset and DataLogicalLength


fields of the MQRMH:

A putting application might put a reference message with:


v No physical data
v DataLogicalLength = 0 (this message represents the entire object)
v DataLogicalOffset = 0.

Assuming that the object is 70 000 bytes long, the sending message exit sends the
first 40 000 bytes along the channel in a reference message containing:
v 40 000 bytes of physical data following the MQRMH
v DataLogicalLength = 40000
v DataLogicalOffset = 0 (from the start of the object).

It then places another message on the transmission queue containing:


v No physical data

148 WebSphere MQ: Application Programming Guide


v DataLogicalLength = 0 (to the end of the object). You could specify a value of
30 000 here.
v DataLogicalOffset = 40000 (starting from this point).

When this message exit is seen by the sending message exit, the remaining 30,000
bytes of data is appended, and the fields are set to:
v 30,000 bytes of physical data following the MQRMH
v DataLogicalLength = 30000
v DataLogicalOffset = 40000 (starting from this point).

The MQRMHF_LAST flag is also set.

For a description of the sample programs provided for the use of reference
messages, see “Sample programs (all platforms except z/OS)” on page 395.

Waiting for messages


If you want a program to wait until a message arrives on a queue, specify the
MQGMO_WAIT option in the Options field of the MQGMO structure. Use the
WaitInterval field of the MQGMO structure to specify the maximum time (in
milliseconds) that you want an MQGET call to wait for a message to arrive on a
queue.

If the message does not arrive within this time, the MQGET call completes with
the MQRC_NO_MSG_AVAILABLE reason code.

You can specify an unlimited wait interval using the constant MQWI_UNLIMITED
in the WaitInterval field. However, events outside your control could cause your
program to wait for a long time, so use this constant with caution. IMS
applications must not specify an unlimited wait interval because this would
prevent the IMS system terminating. (When IMS terminates, it requires all
dependent regions to end.) Instead, IMS applications can specify a finite wait
interval; then, if the call completes without retrieving a message after that interval,
issue another MQGET call with the wait option.

Note: If more than one program is waiting on the same shared queue to remove a
message, only one program is activated by a message arriving. However, if more
than one program is waiting to browse a message, all the programs can be
activated. For more information, see the description of the Options field of the
MQGMO structure in the WebSphere MQ Application Programming Reference.

If the state of the queue or the queue manager changes before the wait interval
expires, the following actions occur:
v If the queue manager enters the quiescing state, and you used the
MQGMO_FAIL_IF_QUIESCING option, the wait is canceled and the MQGET
call completes with the MQRC_Q_MGR_QUIESCING reason code. Without this
option, the call remains waiting.
v On z/OS, if the connection (for a CICS or IMS application) enters the quiescing
state, and you used the MQGMO_FAIL_IF_QUIESCING option, the wait is
canceled and the MQGET call completes with the MQRC_CONN_QUIESCING
reason code. Without this option, the call remains waiting.
v If the queue manager is forced to stop, or is canceled, the MQGET call completes
with either the MQRC_Q_MGR_STOPPING or the
MQRC_CONNECTION_BROKEN reason code.

Chapter 2. Writing a WebSphere MQ application 149


v If the attributes of the queue (or a queue to which the queue name resolves) are
changed so that get requests are now inhibited, the wait is canceled and the
MQGET call completes with the MQRC_GET_INHIBITED reason code.
v If the attributes of the queue (or a queue to which the queue name resolves) are
changed in such a way that the FORCE option is required, the wait is canceled
and the MQGET call completes with the MQRC_OBJECT_CHANGED reason
code.

If you want your application to wait on more than one queue, use the signal
facility of WebSphere MQ for z/OS (see “Signaling”). For more information about
the circumstances in which these actions occur, see the WebSphere MQ Application
Programming Reference.

Signaling
Signaling is supported only on WebSphere MQ for z/OS.

Signaling is an option on the MQGET call to allow the operating system to notify
(or signal) a program when an expected message arrives on a queue. This is similar
to the get with wait function described in topic “Waiting for messages” on page 149
because it allows your program to continue with other work while waiting for the
signal. However, if you use signaling, you can free the application thread and rely
on the operating system to notify the program when a message arrives.

To set a signal
To set a signal, do the following in the MQGMO structure that you use on your
MQGET call:
1. Set the MQGMO_SET_SIGNAL option in the Options field.
2. Set the maximum life of the signal in the WaitInterval field. This sets the
length of time (in milliseconds) for which you want WebSphere MQ to monitor
the queue. Use the MQWI_UNLIMITED value to specify an unlimited life.

Note: IMS applications must not specify an unlimited wait interval because
this would prevent the IMS system from terminating. (When IMS terminates, it
requires all dependent regions to end.) Instead, IMS applications can examine
the state of the ECB at regular intervals (see step 3). A program can have
signals set on several queue handles at the same time:
3. Specify the address of the Event Control Block (ECB) in the Signal1 field. This
notifies you of the result of your signal. The ECB storage must remain available
until the queue is closed.

Note: You cannot use the MQGMO_SET_SIGNAL option in conjunction with the
MQGMO_WAIT option.

When the message arrives


When a suitable message arrives, a completion code is returned to the ECB.

The completion code describes one of the following:


v The message that you set the signal for has arrived on the queue. The message
is not reserved for the program that requested a signal, so the program must
issue an MQGET call again to get the message.

Note: Another application could get the message in the time between your
receiving the signal and issuing another MQGET call.

150 WebSphere MQ: Application Programming Guide


v The wait interval you set has expired and the message you set the signal for did
not arrive on the queue. WebSphere MQ has canceled the signal.
v The signal has been canceled. This happens, for example, if the queue manager
stops, or the attribute of the queue is changed, so that MQGET calls are no
longer allowed.

When a suitable message is already on the queue, the MQGET call completes in
the same way as an MQGET call without signaling. Also, if an error is detected
immediately, the call completes and the return codes are set.

When the call is accepted and no message is immediately available, control is


returned to the program so that it can continue with other work. None of the
output fields in the message descriptor are set, but the CompCode and Reason
parameters are set to MQCC_WARNING and
MQRC_SIGNAL_REQUEST_ACCEPTED, respectively.

For information on what WebSphere MQ can return to your application when it


makes an MQGET call using signaling, see the WebSphere MQ Application
Programming Reference.

If the program has no other work to do while it is waiting for the ECB to be
posted, it can wait for the ECB using:
v For a CICS Transaction Server for OS/390 program, the EXEC CICS WAIT
EXTERNAL command
v For batch and IMS programs, the z/OS WAIT macro

If the state of the queue or the queue manager changes while the signal is set (that
is, the ECB has not yet been posted), the following actions occur:
v If the queue manager enters the quiescing state, and you used the
MQGMO_FAIL_IF_QUIESCING option, the signal is canceled. The ECB is
posted with the MQEC_Q_MGR_QUIESCING completion code. Without this
option, the signal remains set.
v If the queue manager is forced to stop, or is canceled, the signal is canceled. The
signal is delivered with the MQEC_WAIT_CANCELED completion code.
v If the attributes of the queue (or a queue to which the queue name resolves) are
changed so that get requests are now inhibited, the signal is canceled. The signal
is delivered with the MQEC_WAIT_CANCELED completion code.

Note:
1. If more than one program has set a signal on the same shared queue to remove
a message, only one program is activated by a message arriving. However, if
more than one program is waiting to browse a message, all the programs can
be activated. The rules that the queue manager follows when deciding which
applications to activate are the same as those for waiting applications: for more
information, see the description of the Options field of the MQGMO structure
in the WebSphere MQ Application Programming Reference.
2. If there is more than one MQGET call waiting for the same message, with a
mixture of wait and signal options, each waiting call is considered equally. For
more information, see the description of the Options field of the MQGMO
structure in the WebSphere MQ Application Programming Reference.
3. Under some conditions, it is possible both for an MQGET call to retrieve a
message and for a signal (resulting from the arrival of the same message) to be

Chapter 2. Writing a WebSphere MQ application 151


delivered. This means that when your program issues another MQGET call
(because the signal was delivered), there could be no message available. Design
your program to test for this situation.

For information about how to set a signal, see the description of the
MQGMO_SET_SIGNAL option and the Signal1 field in the WebSphere MQ
Application Programming Reference.

Skipping backout
Supported only on WebSphere MQ for z/OS.

As part of a unit of work, an application program can issue one or more MQGET
calls to get messages from a queue. If the application program detects an error, it
can back out the unit of work. This restores all the resources updated during that
unit of work to the state that they were in before the unit of work started, and
reinstates the messages retrieved by the MQGET calls.

Once reinstated, these messages are available to subsequent MQGET calls issued
by the application program. In many cases, this does not cause a problem for the
application program. However, in cases where the error leading to the backout
cannot be circumvented, having the message reinstated on the queue can cause the
application program to enter an MQGET-error-backout loop.

To avoid this problem, specify the MQGMO_MARK_SKIP_BACKOUT option on


the MQGET call. This marks the MQGET request as not being involved in
application-initiated backout; that is, it should not be backed out. Use of this
option means that when a backout occurs, updates to other resources are backed
out as required, but the marked message is treated as if it had been retrieved
under a new unit of work.

The application program must issue a WebSphere MQ call either to commit the
new unit of work, or to back out the new unit of work. For example, the program
can perform exception handling, such as informing the originator that the message
has been discarded, and commit the unit of work so removing the message from
the queue, If the new unit of work is backed out (for any reason) the message is
reinstated on the queue.

Within a unit of work, there can be only one MQGET request marked as skipping
backout; however, there can be several other messages that are not marked as
skipping backout. Once a message has been marked as skipping backout, any
further MQGET calls within the unit of work that specify
MQGMO_MARK_SKIP_BACKOUT fail with reason code
MQRC_SECOND_MARK_NOT_ALLOWED.

Note:
1. The marked message skips backout only if the unit of work containing it is
terminated by an application request to back it out. If the unit of work is
backed out for any other reason, the message is backed out onto the queue in
the same way that it would be if it was not marked to skip backout.
2. Skip backout is not supported within DB2 stored procedures participating in
units of work controlled by RRS. For example, an MQGET call with the
MQGMO_MARK_SKIP_BACKOUT option will fail with the reason code
MQRC_OPTION_ENVIRONMENT_ERROR.

152 WebSphere MQ: Application Programming Guide


Figure 16 illustrates a typical sequence of steps that an application program might
contain when an MQGET request is required to skip backout.

Step 1.
Initial processing, including
MQOPEN of queue specifying
one MQOO INPUT * option

START-OF-UOW1

Step 2.
MQGET message, specifying
MQGMO MARK SKIP BACKOUT
and MQGMO SYNCPOINT

Step 3.
Other resource updates made
for UOW1

Yes No
OK?

Step 4. Step 5.
Commit (message Application requests
removed from queue) backout

Step 6.
Updates from Step 3
backed out

END-OF-UOW1
START-OF-UOW2

Step 7.
Message retrieved at
Step 2 skips backout
and enters new unit
of work

Step 8.
Exception handling.
This must include a
WebSphere MQ operation

Yes No
OK?

Step 9. Step 10.


Commit (message Application requests
removed from queue) backout (message
reinstated on queue)

END-OF-UOW2

Figure 16. Skipping backout using MQGMO_MARK_SKIP_BACKOUT

The steps in Figure 16 are:


Step 1 Initial processing occurs within the transaction, including an MQOPEN call
to open the queue (specifying one of the MQOO_INPUT_* options in order
to get messages from the queue in Step 2).
Step 2 MQGET is called, with MQGMO_SYNCPOINT and

Chapter 2. Writing a WebSphere MQ application 153


MQGMO_MARK_SKIP_BACKOUT. MQGMO_SYNCPOINT is required
because MQGET must be within a unit of work for
MQGMO_MARK_SKIP_BACKOUT to be effective. In Figure 16 on page
153 this unit of work is referred to as UOW1.
Step 3 Other resource updates are made as part of UOW1. These can include
further MQGET calls (issued without MQGMO_MARK_SKIP_BACKOUT).
Step 4 All updates from Steps 2 and 3 complete as required. The application
program commits the updates and UOW1 ends. The message retrieved in
Step 2 is removed from the queue.
Step 5 Some of the updates from Steps 2 and 3 do not complete as required. The
application program requests that the updates made during these steps are
backed out.
Step 6 The updates made in Step 3 are backed out.
Step 7 The MQGET request made in Step 2 skips backout and becomes part of a
new unit of work, UOW2.
Step 8 UOW2 performs exception handling in response to UOW1 being backed
out. (For example, an MQPUT call to another queue, indicating that a
problem occurred that caused UOW1 to be backed out.)
Step 9 Step 8 completes as required, the application program commits the activity,
and UOW2 ends. As the MQGET request is part of UOW2 (see Step 7), this
commit causes the message to be removed from the queue.
Step 10
Step 8 does not complete as required and the application program backs
out UOW2. Because the get message request is part of UOW2 (see Step 7),
it too is backed out and reinstated on the queue. It is now available to
further MQGET calls issued by this or another application program (in the
same way as any other message on the queue).

Application data conversion


When necessary, MCAs convert the message descriptor and header data into the
required character set and encoding. Either end of the link (that is, the local MCA
or the remote MCA) can do the conversion.

When an application puts messages on a queue, the local queue manager adds
control information to the message descriptors to facilitate the control of the
messages when they are processed by queue managers and MCAs. Depending on
the environment, the message header data fields are created in the character set
and encoding of the local system.

When you move messages between systems, you sometimes need to convert the
application data into the character set and encoding required by the receiving
system. This can be done either from within application programs on the receiving
system or by the MCAs on the sending system. If data conversion is supported on
the receiving system, use application programs to convert the application data,
rather than depending on the conversion having already occurred at the sending
system.

Application data is converted within an application program when you specify the
MQGMO_CONVERT option in the Options field of the MQGMO structure passed
to an MQGET call, and all the following are true:

154 WebSphere MQ: Application Programming Guide


v The CodedCharSetId or Encoding fields set in the MQMD structure associated
with the message on the queue differ from the CodedCharSetId or Encoding fields
set in the MQMD structure specified on the MQGET call.
v The Format field in the MQMD structure associated with the message is not
MQFMT_NONE.
v The BufferLength specified on the MQGET call is not zero.
v The message data length is not zero.
v The queue manager supports conversion between the CodedCharSetId and
Encoding fields specified in the MQMD structures associated with the message
and the MQGET call. See the WebSphere MQ Application Programming Reference
for details of the coded character set identifiers and machine encodings
supported.
v The queue manager supports conversion of the message format. If the Format
field of the MQMD structure associated with the message is one of the built-in
formats, the queue manager can convert the message. If the Format is not one of
the built-in formats, you need to write a data-conversion exit to convert the
message.

If the sending MCA is to convert the data, specify the CONVERT(YES) keyword on
the definition of each sender or server channel for which conversion is required. If
the data conversion fails, the message is sent to the DLQ at the sending queue
manager and the Feedback field of the MQDLH structure indicates the reason. If
the message cannot be put on the DLQ, the channel closes and the unconverted
message remains on the transmission queue. Data conversion within applications
rather than at sending MCAs avoids this situation.

As a general rule, data in the message that is described as character data by the
built-in format or data-conversion exit is converted from the coded character set
used by the message to that requested, and numeric fields are converted to the
encoding requested.

For further details of the conversion processing conventions used when converting
the built-in formats, and for information about writing your own data-conversion
exits, see “Writing data-conversion exits” on page 163. See also the WebSphere MQ
Application Programming Reference for information about the language support
tables and about the supported machine encodings.

Conversion of EBCDIC newline characters


If you need to ensure that the data that you send from an EBCDIC platform to an
ASCII one is identical to the data that you receive back again, you must control the
conversion of EBCDIC newline characters.

You can do this using a platform-dependent switch that forces WebSphere MQ to


use the unmodified conversion tables, but you must be aware of the inconsistent
behavior that might result.

The problem arises because the EBCDIC newline character is not converted
consistently across platforms or conversion tables. As a result, if the data is
displayed on an ASCII platform, the formatting might be incorrect. This would
make it difficult, for example, to administer an i5/OS system remotely from an
ASCII platform using RUNMQSC.

See the WebSphere MQ System Administration Guide for further information


about converting EBCDIC-format data to ASCII format.

Chapter 2. Writing a WebSphere MQ application 155


Browsing messages on a queue
To use the MQGET call to browse the messages on a queue:
1. Call MQOPEN to open the queue for browsing, specifying the
MQOO_BROWSE option.
2. To browse the first message on the queue, call MQGET with the
MQGMO_BROWSE_FIRST option. To find the message that you want, call
MQGET repeatedly with the MQGMO_BROWSE_NEXT option to step through
many messages.
You must set the MsgId and CorrelId fields of the MQMD structure to null after
each MQGET call in order to see all messages.
3. Call MQCLOSE to close the queue.

The browse cursor


When you open (MQOPEN) a queue for browsing, the call establishes a browse
cursor for use with MQGET calls that use one of the browse options. You can think
of the browse cursor as a logical pointer that is positioned before the first message
on the queue.

You can have more than one browse cursor active (from a single program) by
issuing several MQOPEN requests for the same queue.

When you call MQGET for browsing, use one of the following options in your
MQGMO structure:
MQGMO_BROWSE_FIRST
Gets a copy of the first message that satisfies the conditions specified in
your MQMD structure.
MQGMO_BROWSE_NEXT
Gets a copy of the next message that satisfies the conditions specified in
your MQMD structure.
MQGMO_BROWSE_MSG_UNDER_CURSOR
Gets a copy of the message currently pointed to by the cursor, that is, the
one that was last retrieved using either the MQGMO_BROWSE_FIRST or
the MQGMO_BROWSE_NEXT option.

In all cases, the message remains on the queue.

When you open a queue, the browse cursor is positioned logically just before the
first message on the queue. This means that if you make your MQGET call
immediately after your MQOPEN call, you can use the MQGMO_BROWSE_NEXT
option to browse the first message; you do not have to use the
MQGMO_BROWSE_FIRST option.

The order in which messages are copied from the queue is determined by the
MsgDeliverySequence attribute of the queue. (For more information, see “The order
in which messages are retrieved from a queue” on page 131.)

Queues in FIFO (first in, first out) sequence:

The first message in a queue in this sequence is the message that has been on the
queue the longest.

156 WebSphere MQ: Application Programming Guide


Use MQGMO_BROWSE_NEXT to read the messages sequentially in the queue.
You will see any messages put to the queue while you are browsing, as a queue in
this sequence has messages placed at the end. When the cursor recognizes that it
has reached the end of the queue, the browse cursor stays where it is and returns
with MQRC_NO_MSG_AVAILABLE. You can then either leave it there waiting for
further messages or reset it to the beginning of the queue with a
MQGMO_BROWSE_FIRST call.

Queues in priority sequence:

The first message in a queue in this sequence is the message that has been on the
queue the longest and that has the highest priority at the time that the MQOPEN
call is issued.

Use MQGMO_BROWSE_NEXT to read the messages in the queue.

The browse cursor points to the next message, working from the priority of the
first message to finish with the message at the lowest priority. It browses any
messages put to the queue during this time as long as they are of priority equal to,
or lower than, the message identified by the current browse cursor.

Any messages put to the queue of higher priority can be browsed only by:
v Opening the queue for browse again, at which point a new browse cursor is
established
v Using the MQGMO_BROWSE_FIRST option

Uncommitted messages:

An uncommitted message is never visible to a browse; the browse cursor skips


past it.

Messages within a unit-of-work cannot be browsed until the unit-of-work is


committed. Messages do not change their position on the queue when committed,
so skipped, uncommitted messages will not be seen, even when they are
committed, unless you use the MQGMO_BROWSE_FIRST option and work though
the queue again.

Change to queue sequence:

If the message delivery sequence is changed from priority to FIFO while there are
messages on the queue, the order of the messages that are already queued is not
changed. Messages added to the queue subsequently take the default priority of
the queue.

Using the queue’s index:

Supported only on WebSphere MQ for z/OS.

When you browse an indexed queue that contains only messages of a single
priority (either persistent or nonpersistent or both), the queue manager performs
the browse by making use of the index, when any of the following forms of
browse are used:
1. If the queue is indexed by MSGID, and the above condition is true, browse
requests that pass a MSGID in the MQMD structure are processed using the
index to find the target message.

Chapter 2. Writing a WebSphere MQ application 157


2. If the queue is indexed by CORRELID, and the above condition is true, browse
requests that pass a CORRELID in the MQMD structure are processed using
the index to find the target message.
3. If the queue is indexed by GROUPID, and the above condition is true, browse
requests that pass a GROUPID in the MQMD structure are processed using the
index to find the target message.

If the browse request does not pass a MSGID, CORRELID, or GROUPID in the
MQMD structure, the queue is indexed, and a message is returned, the index entry
for the message must be found, and information within it used to update the
browse cursor. If you use a wide selection of index values, this extra processing
adds little overhead to the browse request.

Browsing messages when the message length is unknown


To browse a message when you do not know the size of the message, and you do
not want to use the MsgId, CorrelId, or GroupId fields to locate the message, you
can use the MQGMO_BROWSE_MSG_UNDER_CURSOR option:
1. Issue an MQGET with:
v Either the MQGMO_BROWSE_FIRST or MQGMO_BROWSE_NEXT option
v The MQGMO_ACCEPT_TRUNCATED_MSG option
v Buffer length zero

Note: If another program is likely to get the same message, consider using the
MQGMO_LOCK option as well. MQRC_TRUNCATED_MSG_ACCEPTED
should be returned.
2. Use the returned DataLength to allocate the storage needed.
3. Issue an MQGET with the MQGMO_BROWSE_MSG_UNDER_CURSOR.

The message pointed to is the last one that was retrieved; the browse cursor will
not have moved. You can choose either to lock the message using the
MQGMO_LOCK option, or to unlock a locked message using MQGMO_UNLOCK
option.

The call fails if no MQGET with either the MQGMO_BROWSE_FIRST or


MQGMO_BROWSE_NEXT options has been issued successfully since the queue
was opened.

Removing a message that you have browsed


You can remove from the queue a message that you have already browsed
provided that you have opened the queue for removing messages as well as for
browsing. (You must specify one of the MQOO_INPUT_* options, as well as the
MQOO_BROWSE option, on your MQOPEN call.)

To remove the message, call MQGET again, but in the Options field of the
MQGMO structure, specify MQGMO_MSG_UNDER_CURSOR. In this case, the
MQGET call ignores the MsgId, CorrelId, and GroupId fields of the MQMD
structure.

In the time between your browsing and removal steps, another program might
have removed messages from the queue, including the message under your browse
cursor. In this case, your MQGET call returns a reason code to say that the
message is not available.

158 WebSphere MQ: Application Programming Guide


Browsing messages in logical order
“Logical and physical ordering” on page 131 discusses the difference between the
logical and physical order of messages on a queue. This distinction is particularly
important when browsing a queue, because, in general, messages are not being
deleted and browse operations do not necessarily start at the beginning of the
queue.

If an application browses through the various messages of one group (using logical
order), it is important that logical order should be followed to reach the start of the
next group, because the last message of one group might occur physically after the
first message of the next group. The MQGMO_LOGICAL_ORDER option ensures
that logical order is followed when scanning a queue.

Use MQGMO_ALL_MSGS_AVAILABLE (or


MQGMO_ALL_SEGMENTS_AVAILABLE) with care for browse operations.
Consider the case of logical messages with MQGMO_ALL_MSGS_AVAILABLE.
The effect of this is that a logical message is available only if all the remaining
messages in the group are also present. If they are not, the message is passed over.
This can mean that when the missing messages arrive subsequently, they are not
noticed by a browse-next operation.

For example, if the following logical messages are present,


Logical message 1 (not last) of group 123
Logical message 1 (not last) of group 456
Logical message 2 (last) of group 456

and a browse function is issued with MQGMO_ALL_MSGS_AVAILABLE, the first


logical message of group 456 is returned, leaving the browse cursor on this logical
message. If the second (last) message of group 123 now arrives:
Logical message 1 (not last) of group 123
Logical message 2 (last) of group 123
Logical message 1 (not last) of group 456 <=== browse cursor
Logical message 2 (last) of group 456

and the same browse-next function is issued, it is not noticed that group 123 is
now complete, because the first message of this group is before the browse cursor.

In some cases (for example, if messages are retrieved destructively when the group
is present in its entirety), you can use MQGMO_ALL_MSGS_AVAILABLE together
with MQGMO_BROWSE_FIRST. Otherwise, you must repeat the browse scan to
take note of newly-arrived messages that have been missed; just issuing
MQGMO_WAIT together with MQGMO_BROWSE_NEXT and
MQGMO_ALL_MSGS_AVAILABLE does not take account of them. (This also
happens to higher-priority messages that might arrive after scanning the messages
is complete.)

The next sections look at browsing examples that deal with unsegmented
messages; segmented messages follow similar principles.

Browsing messages in groups:

In this example, the application browses through each message on the queue, in
logical order.

Messages on the queue might be grouped. For grouped messages, the application
does not want to start processing any group until all the messages within it have
Chapter 2. Writing a WebSphere MQ application 159
arrived. MQGMO_ALL_MSGS_AVAILABLE is therefore specified for the first
message in the group; for subsequent messages in the group, this option is
unnecessary.

MQGMO_WAIT is used in this example. However, although the wait can be


satisfied if a new group arrives, for the reasons in “Browsing messages in logical
order” on page 159, it is not satisfied if the browse cursor has already passed the
first logical message in a group, and the remaining messages now arrive.
Nevertheless, waiting for a suitable interval ensures that the application does not
constantly loop while waiting for new messages or segments.

MQGMO_LOGICAL_ORDER is used throughout, to ensure that the scan is in


logical order. This contrasts with the destructive MQGET example, where because
each group is being removed, MQGMO_LOGICAL_ORDER is not used when
looking for the first (or only) message in a group.

It is assumed that the application’s buffer is always large enough to hold the entire
message, whether or not the message has been segmented.
MQGMO_COMPLETE_MSG is therefore specified on each MQGET.

The following gives an example of browsing logical messages in a group:


/* Browse the first message in a group, or a message not in a group */
GMO.Options = MQGMO_BROWSE_NEXT | MQGMO_COMPLETE_MSG | MQGMO_LOGICAL_ORDER
| MQGMO_ALL_MSGS_AVAILABLE | MQGMO_WAIT
MQGET GMO.MatchOptions = MQMO_MATCH_MSG_SEQ_NUMBER, MD.MsgSeqNumber = 1
/* Examine first or only message */
...

GMO.Options = MQGMO_BROWSE_NEXT | MQGMO_COMPLETE_MSG | MQGMO_LOGICAL_ORDER


do while ( GroupStatus == MQGS_MSG_IN_GROUP )
MQGET
/* Examine each remaining message in the group */
...

The above group is repeated until MQRC_NO_MSG_AVAILABLE is returned.

Browsing and retrieving destructively:

In this example, the application browses each of the logical messages within a
group, before deciding whether to retrieve that group destructively.

The first part of this example is similar to the previous one. However, in this case,
having browsed an entire group, we decide to go back and retrieve it destructively.

As each group is removed in this example, MQGMO_LOGICAL_ORDER is not


used when looking for the first or only message in a group.

The following gives an example of browsing and then retrieving destructively:


GMO.Options = MQGMO_BROWSE_NEXT | MQGMO_COMPLETE_MSG | MQGMO_LOGICAL_ORDER
| MQGMO_ALL_MESSAGES_AVAILABE | MQGMO_WAIT
do while ( GroupStatus == MQGS_MSG_IN_GROUP )
MQGET
/* Examine each remaining message in the group (or as many as
necessary to decide whether or not to get it destructively) */
...

if ( we want to retrieve the group destructively )

if ( GroupStatus == ’ ’ )

160 WebSphere MQ: Application Programming Guide


/* We retrieved an ungrouped message */
GMO.Options = MQGMO_MSG_UNDER_CURSOR | MQGMO_SYNCPOINT
MQGET GMO.MatchOptions = 0
/* Process the message */
...

else
/* We retrieved one or more messages in a group. The browse cursor */
/* will not normally be still on the first in the group, so we have */
/* to match on the GroupId and MsgSeqNumber = 1. */
/* Another way, which works for both grouped and ungrouped messages,*/
/* would be to remember the MsgId of the first message when it was */
/* browsed, and match on that. */
GMO.Options = MQGMO_COMPLETE_MSG | MQGMO_SYNCPOINT
MQGET GMO.MatchOptions = MQMO_MATCH_GROUP_ID
| MQMO_MATCH_MSG_SEQ_NUMBER,
(MQMD.GroupId = value already in the MD)
MQMD.MsgSeqNumber = 1
/* Process first or only message */
...

GMO.Options = MQGMO_COMPLETE_MSG | MQGMO_SYNCPOINT


| MQGMO_LOGICAL_ORDER
do while ( GroupStatus == MQGS_MSG_IN_GROUP )
MQGET
/* Process each remaining message in the group */
...

Avoiding repeated delivery of browsed messages


By using certain open options and get-message options, you can mark messages as
having been browsed so that they are not retrieved again by the current or other
cooperating applications. Messages can be unmarked explicitly or automatically to
make them available again for browsing.

If you browse messages on a queue, you might retrieve them in a different order to
the order in which you would retrieve them if you got them destructively. In
particular, you can browse the same message multiple times, which is not possible
if it is removed from the queue. To avoid this you can mark messages as they are
browsed, and avoid retrieving marked messages. This is sometimes referred to as
browse with mark. To mark browsed messages, use the get message option
MQGMO_MARK_BROWSE_HANDLE, and to retrieve only messages that are not
marked, use MQGMO_UNMARKED_BROWSE_MSG. If you use the combination
of options MQGMO_BROWSE_FIRST, MQGMO_UNMARKED_BROWSE_MSG,
and MQGMO_MARK_BROWSE_HANDLE, and issue repeated MQGETs, you will
retrieve each message on the queue in turn. This prevents repeated delivery of
messages even though MQGMO_BROWSE_FIRST is used to ensure that messages
are not skipped. This combination of options can be represented by the single
constant MQGMO_BROWSE_HANDLE. When there are no messages on the queue
that have not been browsed, MQRC_NO_MSG_AVAILABLE is returned.

If multiple applications are browsing the same queue, they can open the queue
with the options MQOO_CO_OP and MQOO_BROWSE. The object handle
returned by each MQOPEN is considered to be part of a cooperating group. Any
message returned by an MQGET call specifying the option
MQGMO_MARK_BROWSE_CO_OP is considered to be marked for this
cooperating set of handles.

If a message has been marked for some time, it can be automatically unmarked by
the queue manager and made available for browsing again. The queue manager
attribute MsgMarkBrowseInterval gives the time in milliseconds for which a

Chapter 2. Writing a WebSphere MQ application 161


message is to remain marked for the cooperating set of handles. A
MsgMarkBrowseInterval of -1 means that messages are never automatically
unmarked.

When the single process or set of cooperative processes marking messages stop,
any marked messages become unmarked.

Examples of cooperative browsing

You might run multiple copies of a dispatcher application to browse messages on a


queue and initiate a consumer based on the content of each message. In each
dispatcher, open the queue with MQOO_CO_OP. This indicates that the
dispatchers are cooperating and will be aware of each other’s marked messages.
Each dispatcher then makes repeated MQGET calls, specifying the options
MQGMO_BROWSE_FIRST, MQGMO_UNMARKED_BROWSE_MSG, and
MQGMO_MARK_BROWSE_CO_OP (you can use the single constant
MQGMO_BROWSE_CO_OP to represent this combination of options). Each
dispatcher application then retrieves only those messages that have not already
been marked by other cooperating dispatchers. The dispatcher initializes a
consumer and passes the MsgToken returned by the MQGET to the consumer,
which destructively gets the message from the queue. If the consumer backs out
the MQGET of the message, then the message is available for one of the browsers
to re-dispatch, because it is no longer marked. If the consumer does not do an
MQGET on the message, then after the MsgMarkBrowseInterval has passed, the
queue manager unmarks the message for the cooperating set of handles, and it can
be re-dispatched.

Rather than multiple copies of the same dispatcher application, you might have a
number of different dispatcher applications browsing the queue, each suitable for
processing a subset of the messages on the queue. In each dispatcher, open the
queue with MQOO_CO_OP. This indicates that the dispatchers are cooperating and
will be aware of each other’s marked messages.
v If the order of message processing for a single dispatcher is important, each
dispatcher makes repeated MQGET calls, specifying the options
MQGMO_BROWSE_FIRST, MQGMO_UNMARKED_BROWSE_MSG , and
MQGMO_MARK_BROWSE_HANDLE (or MQGMO_BROWSE_HANDLE). If the
browsed message is suitable for this dispatcher to process, it then makes an
MQGET call specifying MQMO_MATCH_MSG_TOKEN,
MQGMO_MARK_BROWSE_CO_OP, and the MsgToken returned by the
previous MQGET call. If the call succeeds, the dispatcher initializes the
consumer, passing the MsgToken to it.
v If the order of message processing is not important and the dispatcher is
expected to process most of the messages it encounters, use the options
MQGMO_BROWSE_FIRST, MQGMO_UNMARKED_BROWSE_MSG , and
MQGMO_MARK_BROWSE_CO_OP (or MQGMO_BROWSE_CO_OP). If the
dispatcher browses a message it cannot process, it unmarks the message by
calling MQGET with the option MQMO_MATCH_MSG_TOKEN,
MQGMO_UNMARK_BROWSE_CO_OP, and the MsgToken returned previously.

Some cases where the MQGET call fails


If certain attributes of a queue are changed using the FORCE option on a
command between issuing an MQOPEN and an MQGET call, the MQGET call fails
and returns the MQRC_OBJECT_CHANGED reason code.

162 WebSphere MQ: Application Programming Guide


The queue manager marks the object handle as being no longer valid. This also
happens if the changes apply to any queue to which the queue name resolves. The
attributes that affect the handle in this way are listed in the description of the
MQOPEN call in the WebSphere MQ Application Programming Reference. If your call
returns the MQRC_OBJECT_CHANGED reason code, close the queue, reopen it,
then try to get a message again.

If get operations are inhibited for a queue from which you are attempting to get
messages (or any queue to which the queue name resolves), the MQGET call fails
and returns the MQRC_GET_INHIBITED reason code. This happens even if you
are using the MQGET call for browsing. You might be able to get a message
successfully if you attempt the MQGET call at a later time, if the design of the
application is such that other programs change the attributes of queues regularly.

If a dynamic queue (either temporary or permanent) has been deleted, MQGET


calls using a previously-acquired object handle fail and return the
MQRC_Q_DELETED reason code.

Writing data-conversion exits


Not supported in MQSeries for VSE/ESA™.

When you do an MQPUT, your application creates the message descriptor


(MQMD) of the message. Because WebSphere MQ needs to be able to understand
the contents of the MQMD regardless of the platform it is created on, it is
converted automatically by the system.

Application data, however, is not converted automatically. If character data is being


exchanged between platforms where the CodedCharSetId and Encoding fields differ,
for example, between ASCII and EBCDIC, the application must arrange for
conversion of the message. Application data conversion can be performed by the
queue manager itself or by a user exit program, referred to as a data-conversion exit.
The queue manager can perform data conversion itself, using one of its built-in
conversion routines, if the application data is in one of the built-in formats (such as
MQFMT_STRING). This chapter discusses the data-conversion exit facility that
WebSphere MQ provides for when the application data is not in a built-in format.

Control can be passed to the data-conversion exit during an MQGET call. This
avoids converting across different platforms before reaching the final destination.
However, if the final destination is a platform that does not support data
conversion on the MQGET, you must specify CONVERT(YES) on the sender
channel that sends the data to its final destination. This ensures that WebSphere
MQ converts the data during transmission. In this case, your data-conversion exit
must reside on the system where the sender channel is defined.

The MQGET call is issued directly by the application. Set the CodedCharSetId and
Encoding fields in the MQMD to the character set and encoding required. If your
application uses the same character set and encoding as the queue manager, set
CodedCharSetId to MQCCSI_Q_MGR, and Encoding to MQENC_NATIVE. After the
MQGET call completes, these fields have the values appropriate to the message
data returned. These might differ from the values required if the conversion was
not successful. Your application should reset these fields to the values required
before each MQGET call.

Chapter 2. Writing a WebSphere MQ application 163


The conditions required for the data-conversion exit to be called are defined for the
MQGET call in the WebSphere MQ Application Programming Reference.

For a description of the parameters that are passed to the data-conversion exit, and
detailed usage notes, see the WebSphere MQ Application Programming Reference for
the MQ_DATA_CONV_EXIT call and the MQDXP structure.

Programs that convert application data between different machine encodings and
CCSIDs must conform to the WebSphere MQ data conversion interface (DCI).

This chapter introduces data-conversion exits, under these headings:


v “Invoking the data-conversion exit”
v “Writing a data-conversion exit program” on page 165
v “Writing a data-conversion exit program for WebSphere MQ for i5/OS” on page
170
v “Writing a data-conversion exit program for WebSphere MQ for z/OS” on page
171
v “Writing a data-conversion exit for WebSphere MQ on UNIX systems” on page
172
v “Writing a data-conversion exit for WebSphere MQ for Windows” on page 178

Invoking the data-conversion exit


A data-conversion exit is a user-written exit that receives control during the
processing of an MQGET call.

The exit is invoked if the following are true:


v The MQGMO_CONVERT option is specified on the MQGET call.
v Some or all of the message data is not in the requested character set or
encoding.
v The Format field in the MQMD structure associated with the message is not
MQFMT_NONE.
v The BufferLength specified on the MQGET call is not zero.
v The message data length is not zero.
v The message contains data that has a user-defined format. The user-defined
format can occupy the entire message, or be preceded by one or more built-in
formats. For example, the user-defined format might be preceded by an
MQFMT_DEAD_LETTER_HEADER format. The exit is invoked to convert only
the user-defined format; the queue manager converts any built-in formats that
precede the user-defined format.
A user-written exit can also be invoked to convert a built-in format, but this
happens only if the built-in conversion routines cannot convert the built-in
format successfully.

There are some other conditions, described fully in the usage notes of the
MQ_DATA_CONV_EXIT call in the WebSphere MQ Application Programming
Reference.

See the WebSphere MQ Application Programming Reference for details of the MQGET
call. Data-conversion exits cannot use MQI calls, other than MQXCNVC.

164 WebSphere MQ: Application Programming Guide


A new copy of the exit is loaded when an application attempts to retrieve the first
message that uses that Format since the application connected to the queue
manager. A new copy might also be loaded at other times if the queue manager
has discarded a previously-loaded copy.

The data-conversion exit runs in an environment similar to that of the program


that issued the MQGET call. As well as user applications, the program can be an
MCA (message channel agent) sending messages to a destination queue manager
that does not support message conversion. The environment includes address
space and user profile, where applicable. The exit cannot compromise the queue
manager’s integrity, because it does not run in the queue manager’s environment.

In a client-server environment, the exit is loaded at the server, and conversion


takes place there.

Data conversion on z/OS


On z/OS, be aware of the following:
v Exit programs can be written in assembler language only.
v Exit programs must be reentrant, and capable of running anywhere in storage.
v Exit programs must restore the environment on exit to that at entry, and must
free any storage obtained.
v Exit programs must not WAIT, or issue ESTAEs or SPIEs.
v Exit programs are usually invoked as if by z/OS LINK in:
– Non-authorized problem program state
– Primary address space control mode
– Non cross-memory mode
– Non access-register mode
– 31 bit addressing mode
– TCB-PRB mode
v When used by a CICS application, the exit is invoked by EXEC CICS LINK, and
must conform to the CICS programming conventions. The parameters are passed
by pointers (addresses) in the CICS communication area (COMMAREA).
Although not recommended, user exit programs can also use CICS API calls,
with the following caution:
– Do not issue syncpoints, as the results could influence units of work declared
by the MCA.
– Do not update any resources controlled by a resource manager other than
WebSphere MQ for z/OS, including those controlled by CICS Transaction
Server for OS/390.
v For distributed queuing without CICS, the exit is loaded from the data set
referenced by the CSQXLIB DD statement.
v For distributed queuing using CICS, data-conversion exits are not supported.

Writing a data-conversion exit program


For z/OS, you must write data-conversion exits in assembler language. For other
platforms, it is recommended that you use the C programming language.

To help you to create a data-conversion exit program, the following are supplied:
v A skeleton source file
v A convert characters call

Chapter 2. Writing a WebSphere MQ application 165


v A utility that creates a fragment of code that performs data conversion on data
type structures This utility takes C input only. On z/OS, it produces assembler
code.

These are described in subsequent sections.

For the procedure for writing the programs see:


v “Writing a data-conversion exit program for WebSphere MQ for i5/OS” on page
170
v “Writing a data-conversion exit program for WebSphere MQ for z/OS” on page
171
v “Writing a data-conversion exit for WebSphere MQ on UNIX systems” on page
172
v “Writing a data-conversion exit for WebSphere MQ for Windows” on page 178

Skeleton source file


These can be used as your starting point when writing a data-conversion exit
program.

The files supplied are listed in Table 10.


Table 10. Skeleton source files

Platform File

AIX amqsvfc0.c

i5/OS QMQMSAMP/QCSRC(AMQSVFC4)

HP-UX amqsvfc0.c

Linux amqsvfc0.c

z/OS CSQ4BAX8 (1)


CSQ4BAX9 (2)
CSQ4CAX9 (3)

Solaris amqsvfc0.c

Windows systems amqsvfc0.c


Notes:
1. Illustrates the MQXCVNC call.
2. A wrapper for the code fragments generated by the utility for use in all environments
except CICS.
3. A wrapper for the code fragments generated by the utility for use in the CICS
environment.

166 WebSphere MQ: Application Programming Guide


Convert characters call
Use the MQXCNVC (convert characters) call from within a data-conversion exit
program to convert character message data from one character set to another. For
certain multibyte character sets (for example, UCS2 character sets), the appropriate
options must be used.

No other MQI calls can be made from within the exit; an attempt to make such a
call fails with reason code MQRC_CALL_IN_PROGRESS.

See the WebSphere MQ Application Programming Reference for further information on


the MQXCNVC call and appropriate options.

Utility for creating conversion-exit code


The commands for creating conversion-exit code are:
i5/OS CVTMQMDTA (Convert WebSphere MQ Data Type)
Windows systems and UNIX systems
crtmqcvx (Create WebSphere MQ conversion-exit)
z/OS CSQUCVX

The command for your platform produces a fragment of code that performs data
conversion on data type structures, for use in your data-conversion exit program.
The command takes a file containing one or more C language structure definitions.
On z/OS, it then generates a data set containing assembler code fragments and
conversion functions. On other platforms, it generates a file with a C function to
convert each structure definition. On z/OS, the utility requires access to the
LE/370 run-time library SCEERUN.

Invoking the CSQUCVX utility on z/OS:

Figure 17 shows an example of the JCL used to invoke the CSQUCVX utility.

//CVX EXEC PGM=CSQUCVX


//STEPLIB DD DISP=SHR,DSN=thlqual.SCSQANLE
// DD DISP=SHR,DSN=thlqual.SCSQLOAD
// DD DISP=SHR,DSN=le370qual.SCEERUN
//SYSPRINT DD SYSOUT=*
//CSQUINP DD DISP=SHR,DSN=MY.MQSERIES.FORMATS(MSG1)
//CSQUOUT DD DISP=OLD,DSN=MY.MQSERIES.EXITS(MSG1)

Figure 17. Sample JCL used to invoke the CSQUCVX utility

z/OS data definition statements:

The CSQUCVX utility requires DD statements with the following DDnames:

SYSPRINT This specifies a data set or print spool class for reports and error messages.
CSQUINP This specifies the sequential data set containing the definitions of the data structures to be
converted.
CSQUOUT This specifies the sequential data set where the conversion code fragments are to be written.
The logical record length (LRECL) must be 80 and the record format (RECFM) must be FB.

Error messages in Windows systems, and UNIX systems:

Chapter 2. Writing a WebSphere MQ application 167


The crtmqcvx command returns messages in the range AMQ7953 through
AMQ7970.

These are listed in WebSphere MQ Messages.

There are two main types of error:


v Major errors, such as syntax errors, when processing cannot continue.
A message is displayed on the screen giving the line number of the error in the