HPlogo 900 Series HP 3000 Computer Systems: MPE/iX Architected Interface Facility: Operating System Reference Manual > Chapter 3 Architected Interface Descriptions

AIFPORTOPEN

» 

Technical documentation

Complete book in PDF
» Feedback

 » Table of Contents

 » Index

Creates and/or opens a port. The port can be opened to allow for the asynchronous receipt of incoming messages by enabling a user specified handler.

Syntax

 I32                         REC          CA16         CA16

port_id := AIFPORTOPEN (overall_status, port_name, port_password,

                             I32      I32       I32A          @64A

                        access_mode, user_id, itemnum_array, item_array,

                                RECA

                        itemstatus_array);

Functional Return

port_id

32-bit signed integer by reference (required)

Returns a unique identifier, a port ID, to be used with other port AIFs to manage the opened port. The maximum number of open AIF ports is 2048.

If the call to AIFPORTOPEN is unsuccessful, port_id is undefined. Check overall_status to determine which error occurred.

Parameters

overall_status

record by reference (required)

Returns the overall status of the call. A zero indicates a successful call. A negative value indicates an error in the overall call, not specific to any particular item. A positive value indicates the last element in itemstatus_array, signaling an error condition. Refer to appendix A for meanings of status values.

Record type: status_type (Refer to appendix B.)

port_name

character array by reference (required)

Passes name used to identify this particular port. This name must be unique across the entire system. It should be padded on the right with blanks if it is fewer than 16 characters. The name will be upshifted, so it is not case sensitive.

If a totally blank port name is specified, a unique name is established, a port with that name is created, and the name is returned in the port_name parameter.

Array type: pac16 (Refer to appendix B.)

port_password

character array by reference (required)

Passes a password to associate with the port being opened. This password can be up to 16 characters in length. It should be padded on the right with blanks if it is fewer than 16 characters. The password will be upshifted, so it is not case sensitive. The first open of a port establishes the password, which must be matched by all subsequent opens.

Array type: pac16 (Refer to appendix B.)

access_mode

32-bit signed integer by value (required)

Passes a value determining the access mode for the port being opened.

Values and their meanings are as follows:

1

Receive access

2

Send access

3

Both receive and send access

user_id

32-bit signed integer by value (optional)

The user ID assigned to a vendor at the time of purchase of the Architected Interface Facility: Operating System product. If it is not passed, the caller must have previously called AIFACCESSON.

Default: 0

itemnum_array

32-bit signed integer array by reference (optional)

This is an array of integers, terminated by an element containing the value zero, used to define the corresponding option given in the item_array parameter. If this optional parameter is specified, the item_array parameter and the itemstatus_array parameter must both be supplied.

Default: nil

item_array

64-bit address array by reference (optional)

An array with the same number of elements as the itemnum_array parameter, each of which is a globalanyptr that points to the appropriate type needed by each particular item number. The value used for each option is taken from, or returned to, the location pointed to by the globalanyptr in this array. When this parameter is supplied, the itemnum_array parameter and the itemstatus_array parameter must both be supplied.

Array type: globalanyptr

Default: nil

itemstatus_array

record array by reference (optional)

If problems are detected with specific items, an error status is placed in the corresponding element of this array for each item with an error. The overall status parameter indicates whether any individual items contained errors, and the element of the last detected error. This array must contain as many elements as are contained in the itemnum_array and item_array parameters.

A non-zero value indicates an error, but a valid option does not set the value to zero, so this array should be initialized to all zeros before making the call.

Array type: status_type (Refer to appendix B.)

Default: nil

Operation Notes

The AIF Port Facility is an application interface that provides a fast means of interprocess communication by sending messages from one process to another. Messages can be received in a synchronous or asynchronous fashion. The ability to receive messages asynchronously is determined when the port is created.

The remaining notes will reference details from the AIFPORTOPEN item descriptions (Table 3-16). Please review the item descriptions before reading further.

Opening An AIF Port

The first time that AIFPORTOPEN is called for a named port that does not exist, it is created by default. If the named port already exists, it is opened. AIFPORTOPEN returns an integer value that must be supplied to all other port AIFs to identify the port being referenced. The default AIFPORTOPEN creates the port as temporary and does not allow for the asynchronous receipt of messages.

An asynchronous port is a port that provides the capability of interrupting the creator upon receipt of a message and transfers control to a user specified handler. To create an asynchronous port specific items must be passed to the AIFPORTOPEN routine. The following example illustrates the creation of an asynchronous port.

readln (user_id);

portname          := 'aifport1        ';

portpass          := 'aifpass1        ';

accessmode        := 1;          { receive access }

itemnum_ports     := Init_Itemnum_Array; { zero array }

item_ports        := Init_Item_Array;

item_status_ports := Init_Item_Status_Array;

createoptions     := 2;          { create new     }

itemnum_ports [1] := 11201;

item_ports [1]    := ADDR(createoptions);

maxmsgsize        := 80;         { message size   }

itemnum_ports [2] := 11202;

item_ports [2]    := ADDR(maxmsgsize);

proc_name         := '#PORTHANDLER#';

proc_file         := '#ASYNC1#';



HPGETPROCPLABEL (proc_name, createhandler, 

	         overall_status, proc_file, False);

if overall_status.all <> 0 then

  ERROR_IN_CALL('HPGETPROCPLABEL',overall_status);



itemnum_ports [3] := 11206;

item_ports [3]    := addr(createhandler); { handler address }

createstate       := True;

itemnum_ports [4] := 11207;  { next element initialized to 0 }  

item_ports [4]    := addr(createstate); { enabled }



portid1 := AIFPORTOPEN(overall_status, portname, portpass, 

		       accessmode,,itemnum_ports, 

		       item_ports, item_status_ports);

if overall_status.all <> 0 then

  ERROR_IN_CALL('AIFPORTOPEN',overall_status,

		 item_status_ports);

The creator of an asynchronous port is the only process that may receive messages from this port, and must provide the handler address when opening the port. If the creating process abnormally terminates, subsequent sends to the port will return an error.

AIF ports that do NOT specify a handler at creation time, receive messages synchronously and allow multiple receivers. In addition, synchronous ports can be permanent, however, asynchronous ports are always temporary.

Handlers

Handlers for asynchronous ports must be coded to certain conventions in order to function properly. The address of the handler can be acquired by calling the intrinsic HPGETPROCLABEL as shown in the previous example.

When defining the handler routine, the calling sequence must have one parameter. This parameter will contain the portid of the AIF port which received the asynchronous message.

In Pascal/iX, a handler is declared as follows:

procedure INT_HANDLER ( port_id : integer );

In C/iX, it would be:

void INT_HANDLER ( int portid )

Handlers should do only what is absolutely necessary. It is NOT a good idea to do the AIFPORTRECEIVE using the "all ports" option, as this can result in unnecessary delays. When using item 11003 of AIFPORTRECEIVE to retrieve envelope information, be sure to do the actual receive of the message, otherwise the message will remain queued to the port. Also, consider potential traps and escapes and do not allow your handler to be exited in this fashion. If a handler does escape, it will be caught by AIF ports code and will NOT be propagated out to the user.

Finally, a handler may never call AIFPORTCLOSE to close an asynchronous port. This will result in unpredictable behavior, and possible system failure. Handlers that are written in C, may not use the longjump function and must have a return-type of void. Handlers execute at ring level 2 or privileged mode. Calls to GETUSERMODE are not allowed inside the handler, this will cause an IMEM protection trap, which results in a process abort.

Special Considerations

The asynchronous receipt of incoming messages has been implemented through Process Interrupts. A process interrupt is generated to signal the arrival of a message on an asynchronous port. The process interrupt will "interrupt" the creator process transferring control to the user supplied interrupt handler. As with other types of process interrupts (eg., Break, Cntrl Y), control will not be transferred to the user's handler until the creator process is in the appropriate state. For asynchronous port interrupts, the process interrupt will be postponed if the creator is critical, in system code, or executing at ring level 0 or 1. This is done to protect critical system operations from being interrupted by the user application.

A waited receive against an asynchronous port takes precedence over notification by a process interrupt. Therefore, a process which blocks, waiting for a message from its asynchronous port has effectively disabled process interrupt notification. Several possible uses of asynchronous ports are described to illustrate the systems behavior.

Example 1

A process opens an asynchronous port with port interrupt handling enabled. The handler does a nowait receive to get the message and it does not access any global data.

When a send is issued against the port the message is queued by the send request. Messages sent to a process NOT blocked on an asynchronous port receive, will result in a process interrupt. When the receiving process is in the appropriate state (ring level 2 or 3) the user handler will be invoked. It is possible for the user interrupt handler to nest multiple levels deep if additional process interrupts occur. In this case, the user should do a single receive against the port for each call of the handler. The user should also handle error messages appropriately.

However, if the receiver chooses to explicitly wait for the arrival of a message on an asynchronous port, when the send is issued, the dispatcher is notified to unblock the process. When the receiver process is awoken, it will complete the receive operation on a single message. It is possible for multiple messages to queue while the process is blocked. If a user waits on an asynchronous port in this fashion, they are responsible for checking for multiple messages once the receive completes.

Example 2

The user opens an asynchronous port. AIFPORTINT is called to disable port interrupt handling around critical areas in the user code. Also AIFPORTINT is used in the handler to disable interrupt handling after entry, and later re-enabled before exiting the handling routine.

Again, the message is queued to the port when the send request is issued. If the receiver is not currently waiting on the port, the process interrupt will occur. Further process interrupts will nest until the user calls AIFPORTINT inside their handler. Once interrupt handling is disable, additional messages which arrive will cause a pending count to be incremented and the handler invokation will be delayed. When AIFPORTINT is called to re-enable interrupt handling, the user handler will be called once for each time the pending count was incremented. This is repeated until the pending interrupts have been serviced.

If the user is sitting in a waited receive, multiple messages can be sent, and the receiver will unblock. The receive will return the first message, but the user is responsible for clearing the port. If the user calls AIFPORTINT around the waited receive, it is possible the user can clear messages from the port, and when AIFPORTINT is called to enable interrupt handling, the handler could get invoked for messages which have already been read. Therefore, the handler should be coded to handle the case where no messages exist on the port.

AIFPORTOPEN Item Descriptions

The following table provides detailed descriptions of item numbers and corresponding items associated with AIFPORTOPEN.

Table 3-23 AIFPORTOPEN Item Descriptions

Item NumberItem Name (Data Type) Release First Available Description
11201

Create option (I32); Release 3.0

Passes a port creation option. Values and their meanings are as follows:

1

Create a new port if the named port does not exist; otherwise, open the existing port.

2

Create a new port and open it. Return an error if the port already exists.

3

Open an existing port. Return an error if it does not exist.

Default: 1

11202

Maximum message size (I32); Release 3.0

Passes the maximum message size, in bytes, to allow through this port. An error is returned if an attempt is made to send a message larger than this value.

Default: 256 bytes Maximum: 8144

11203

Normal message size (I32); Release 3.0

Passes the normal message size, in bytes. When this number is multiplied by the maximum number of normal messages, the result must be greater than or equal to the maximum message size.

Default: 64 bytes

11204

Maximum # of normal messages (I32); Release 3.0

Passes the maximum number of normal-sized messages (refer to item number 11203) to allow in this port. When this number is multiplied by the normal message size, the result must be greater than or equal to the maximum message size (refer to item number 11202).

The absolute maximum number of normal messages is 32,767; however, this value may be smaller based on the following calculation:

Maximum # of normal messages = 1,048,256 words / ( maximum message size rounded up in words + 16 words)

NOTE: The system allocates message pools based on the message size and number of normal messages when the port is created. These resources should be allocated sparingly since they are allocated out of system space. Shortages of system space can result in a system failure.

Default: 32

11205

Make permanent (B); Release 3.0

Passes a value specifying the final disposition of the port (whether permanent or removed) after the last process has done a close on it. If the port is to remain after the last process has done a close on it, a value of true must be passed with this parameter for all opens of the port. The last open of the port establishes the final permanence of the port. If the last opener passes this option with a true value, the port is permanent.

If the last opener does not specify this option, or specifies it and passes a false value, the port is removed after the last process closes it. To remove a permanent port from the system, all that is required is for a process to open the port without specifying this parameter, or specifying this parameter as false; the port is then destroyed when the last accessor closes the port.

An asynchronous port is always temporary. When an asynchronous port is opened, an error is returned if this option is specified as permanent.

Default: FALSE (port is temporary)

11206

Handler address (@32); Release 4.0

Passes the handler address for an asynchronous port. The address of the user defined handler can be acquired by calling the intrinsic HPGETPROCLABEL. See the operational notes for handler requirements. This item can only be specified when the port is first created (refer to item 11201). Any attempt to pass this item to an already open port results in an error. An asynchronous port may not be permanent. (Refer to item 11205.)

Default: nil

11207

Interrupt handler state (B); Release 4.0

Passes a Boolean that enables or disables the port interrupt handler at creation time. A value of TRUE means that the interrupt handler is enabled upon return from AIFPORTOPEN, while FALSE means that the interrupt handler is disabled and a call to AIFPORTINT is required to enable it.

Default: FALSE

 

Feedback to webmaster