# DIGITAL TCP/IP Services for OpenVMS
System Services and C Socket Programming

Previous | Contents

Figure 3-1 shows the I/O status block (iosb) for the IO$_SETMODE, IO$_SENSEMODE, IO$_READVBLK, IO$_WRITEVBLK functions, and Table 3-5 describes each field.

Figure 3-1 I/O Status Block

Table 3-5 I/O Status Block Fields
Field | Description
--- | ---
OpenVMS completion status field | The final status of the operation. A standard OpenVMS system service status (that is, SS$_xx).
DIGITAL UNIX completion status field | The UNIX equivalent of the OpenVMS completion status code field. A word-length completion value returned to IO$_SETMODE and IO$_SENSEMODE, or on all I/O functions that are completed with an error. The UNIX completion values are defined in the <errno.h> file provided with DEC C and in the UCX$INETDEF symbol definition file. The word-length status value is returned by the $QIO system service when the I/O operation has been completed.
Parameter address | Address of the parameter or error.
Transfer size | Number of bytes transferred during a read or write operation.
| Read/write operations that complete with an error return the UNIX completion status instead of the transfer size.
Buffer address | Address of the buffer where the data was transferred.

## 3.4.2 Function-Dependent $QIO Arguments

Specify the p1, p2, p3, p4, p5, and p6 arguments. You can pass a parameter as a value, a reference to the address of a value, or a descriptor address. Table 3-6 lists arguments p1 through p6 for the $QIO system service calls.

Table 3-6 Function-Dependent$QIO Arguments
$QIO | p1 | p2 | p3 | p4 | p5 | p6
--- | --- | --- | --- | --- | --- | ---
IO$_ACCESS | Not used | Not used | Remote socket name² | Not used | Not used | Not used
IO$_ACCESS|IO$M_ACCEPT | Not used | Not used | Returned remote socket name 4 | Channel number (word)³ | Not used | Not used
IO$_DEACCESS | Not used | Not used | Not used | Not used | Not used | Not used
IO$_DEACCESS|IO$M_SHUTDOWN | Not used | Not used | Not used | Shutdown flags¹ | Not used | Not used
IO$_READVBLK | Buffer³ | Buffer size¹ | Remote socket name 4 | Flags¹ | Not used | Output buffer list²
IO$_READVBLK|IO$M_INTERRUPT | Buffer³ | Buffer size¹ | Not used | Not used | Not used | Not used
IO$_WRITEVBLK | Buffer³ | Buffer size¹ | Remote socket name² | Flags¹ | Input buffer list² | Not used
IO$_WRITEVBLK|IO$M_INTERRUPT | Buffer³ | Buffer size¹ | Not used | Not used | Not used | Not used
IO$_SETMODE | Socket char³ | Not used | Local socket name² | Backlog limit¹ | Input parameter list² | Not used
IO$_SENSEMODE | Not used | Not used | Local socket name 4 | Remote socket name 4 | Not used | Output parameter list², 4

¹By value
²Address of a UCX item_list_2 descriptor
³By reference
4Address of a UCX item_list_3 descriptor

# 3.5 Item Lists and Item List Descriptors

An item list is a contiguous block of memory that contains item list descriptors. An item list descriptor points to parameters and contains fields that describe the data. UCX uses two item list formats:

- The item_list_2 descriptor sets a parameter.
- The item_list_3 descriptor gets parameter information.

These formats do not necessarily correspond to formats used elsewhere in OpenVMS programming.

The function you call determines which format is required. When you specify a item_list_2 descriptor, it either passes a parameter to the system or returns a parameter from the system (depending on the function's requirements). When a item_list_2 descriptor returns the parameter from the system, the system returns only that parameter.

When you specify an item_list_3 descriptor, it returns a parameter from the system. In addition to the parameter itself, the system also returns the length of the parameter.

# 3.6 Specifying an Input Parameter List

Use the p5 argument with the IO$_WRITEVBLK and IO$_SETMODE functions to specify input parameter lists. The p5 argument contains the address of a descriptor that points to, and specifies the contents of, a UCX item list descriptor. Figure 3-2 illustrates how the p5 argument specifies the UCX item list.

Figure 3-2 Specifying an Input Parameter List

Table 3-7 defines the descriptor fields, which also apply to buffer lists where indicated.

Table 3-7 p5 Descriptor Fields
Field | Description
--- | ---
length | A word specifying the length (in bytes) of the requested UCX item list (also applies to buffer lists).
parameter type | A user-supplied, word-length symbolic code that specifies the type or class of parameter to set. The parameter types are:
| UCX$C_DATA or zero to specify read or write buffers (for buffer lists only)
| UCX$C_SOCKOPT to specify socket options (for parameter lists only)
| UCX$C_TCPOPT to specify TCP/IP options (for parameter lists only)
| UCX$C_IPOPT to specify raw IP options (for parameter lists only)
| UCX$C_IOCTL to specify I/O control options (for parameter lists only)
| With the IO$_SENSEMODE function, use either UCX$C_SOCKOPT or UCX$C_IOCTL parameter types.
| The UCX$INETDEF symbol definition file defines the parameter type, which applies to all the UCX descriptors in a list. See the $QIO routine descriptions in this chapter for details about the parameter types.
address | A longword that specifies the starting address of the UCX item list (also applies to buffer lists).

The rest of this chapter explains how to use parameters to describe specific information. This chapter also contains a sample DEC C program that specifies IOCTL parameters. There are additional sample programs in UCX$EXAMPLES that contain the different functions and parameters.

# 3.7 Specifying an Output Parameter List

Use the p6 argument with the IO$_READVBLK or the IO$_SENSEMODE function to specify an output parameter list. The p6 argument passes the address of a descriptor that points to, and specifies the contents of, a UCX descriptor list. The list consists of contiguous blocks of memory that contain one or more UCX descriptors.

Figure 3-3 illustrates how the p6 argument specifies the UCX item_list.

Figure 3-3 Specifying an Output Parameter List

Table 3-8 defines the descriptor fields, which also apply to buffer lists where indicated.

Table 3-8 p6 Descriptor Fields
Field | Description
--- | ---
length | A word that specifies the length (in bytes) of the buffer into which the service writes the information. You supply the integer for this value. The length needed depends on the parameter name specified in the parameter name field of the UCX descriptor on the list. If the value of the buffer length is too small, the service truncates the data (also applies to buffer lists.)
parameter type | A user-supplied, word-length symbolic code that specifies the type or class of parameter to get. The parameter types are: UCX$C_DATA or zero for read or write buffers (for buffer lists only) UCX$C_SOCKOPT to specify socket options (for parameter lists only) UCX$C_TCPOPT to specify TCP/IP options (for parameter lists only) UCX$C_IPOPT specify raw IP options (for parameter lists only) UCX$C_IOCTL to specify I/O control options (for parameter lists only) With the IO$_SENSEMODE function, use either UCX$C_SOCKOPT or UCX$C_IOCTL parameter types. The UCX$INETDEF symbol definition file defines the parameter type, which applies to all the UCX descriptors in a list. See the $QIO routine descriptions in this chapter for details about the parameter types.
address | A longword from which the service reads the starting address of the user buffer containing data (also applies to buffer lists).

# 3.8 Specifying the Socket Name

You specify the socket name with the p3 or p4 argument with the IO$_ACCESS, IO$_READVBLK, IO$_WRITEVBLK, IO$_SENSEMODE, and IO$_SETMODE functions. This parameter takes the form of an address of a UCX item_list_2 or a UCX item_list_3 descriptor.

Figure 3-4 illustrates how the p3 and p4 arguments specify the local and remote socket names.

The parameter name for p4 is UCX$C_SOCK_NAME, which is defined in the UCX$INETDEF symbol definition file.

The p3 argument must contain a UCX item_list_2 descriptor, unless you use GETSOCKETNAME. In this case, p3 must contain a UCX item_list_3 descriptor.

Figure 3-4 Specifying the Local or Remote Socket Name

The descriptor that the p3 and p4 arguments specify points to a 16-byte data structure called sockaddr_in. This data structure consists of the address domain (2 bytes), port number (2 bytes), host internet address (4 bytes), and unused bytes (8 bytes). Table 3-9 describes the sockaddr_in fields.

Table 3-9 sockaddr_in Fields
Field | Description
--- | ---
address domain | The INET domain (set by default).
port number | An integer in the range 0 to 65,535. Port numbers 1 to 1023 require either system UIC or BYPASS privileges when assigned. If you specify zero when binding a socket name, the system assigns an available port.
host internet address | A longword 4-byte integer.

# 3.9 Specifying Socket Options, Protocol Options, and I/O Control Parameters

Use UCX item_list_2 descriptors when setting the socket options. Figure 3-5 shows how to specify socket options.

Figure 3-5 Specifying Socket Options

The UCX$INETDEF symbol definition file defines the UCX$C_SOCKOPT parameter name for the socket options. For the TCP protocol options, the name of the parameter is UCX$C_TCPOPT. For IP options, the name is UCX$C_IPOPT.

Figure 3-6 illustrates how to specify I/O Control (IOCTL) functions.

Figure 3-6 Specifying IOCTL Functions

The UCX$INETDEF symbol definition file specifies the UCX$C_IOCTL name. You specify the I/O control (IOCTL) parameters with a UCX item_list_2 descriptor that lists its specifications. Each parameter field contains two longwords: the first is the IOCTL command value defined by the $SIOCDEF macro; the second is an IOCTL parameter structure address. During startup, the UCX$INETDEF symbol definition file specifies the values for the $SIOCDEF macro.

Use UCX item_list_3 descriptors when getting socket and protocol options. Figure 3-7 illustrates how to specify socket options.

Figure 3-8 illustrates how to specify IOCTL functions.

Figure 3-7 Specifying Socket Options

Figure 3-8 Specifying IOCTL Parameters

Example 3-1 shows how to specify IOCTL parameters.

Example 3-1 Specifying IOCTL Parameters

    #include <stdio.h>
    #include <iodef.h>
    #include  <ucx$inetdef.h>

       .
       .
       .
    *
    *        MACRO DEFINITIONS
    *
    */
    #ifndef _IO
    #define IOCPARM_MASK  0x7f            /* Parameters are < 128 bytes  */
    #define IOC_VOID      (int)0x20000000 /* No parameters               */
    #define IOC_OUT       (int)0x40000000 /* Copy out parameters         */
    #define IOC_IN        (int)i0x80000000/* Copy in parameters          */
    #define IOC_INOUT     (int)(IOC_IN|IOC_OUT)
    #define _IO(x,y)      (int)(IOC_VOID|('x'<<8)|y)
    #define _IOR(x,y,t)   (int)(IOC_OUT|((sizeof(t)&IOCPARM_MASK)<<16)|('x'<<8)|y)
    #define _IOW(x,y,t)   (int)(IOC_IN|((sizeof(t)&IOCPARM_MASK)<<16)|('x'<<8)|y)
    #define _IOWR(x,y,t)  (int)(IOC_INOUT|((sizeof(t)&IOCPARM_MASK)<<16)|('x'<<8)
    #endif _IO

    #define VMSOK(s) (s & 01)

    /*------------------------------------------------------------*/
    int ioctl(d, request, argp)
    int d, request;
    char *argp;
    {
        int ef;                        /* Event flag number */
        int sdc;                       /* Device socket channel */
        unsigned short fun;            /* Qiow function code  */
        unsigned short iosb[4];        /* Io status block */
        char *p5, *p6;                 /* Args p5 & p6 of qiow */
        struct comm
        {
            int command;
            char *addr;
        } ioctl_comm;                /* Qiow ioctl commands. */
        struct it2
        {
            unsigned short len;
            unsigned short opt;
            struct comm *addr;
        } ioctl_desc;                /* Qiow ioctl commands descriptor */
        int status;

        /*
         * Gets an event flag for qio
         */
        status = LIB$GET_EF(&ef);
        if (!VMSOK(status))
        {
            /* No ef available. Use 0 */
            ef = 0;
        }

        /*
         * Get the device socket channel number.
         */
        sdc = vaxc$get_sdc(d);
        if (sdc == 0)
        {
            /* Not an open socket descriptor. */
            errno = EBADF;
            return -1;
        }

        /*
         * Fill in ioctl descriptor.
         */
        ioctl_desc.opt = UCX$C_IOCTL;
        ioctl_desc.len = sizeof(struct comm);
        ioctl_desc.addr = &ioctl_comm;

        /*
         * Decide qio function code and in/out parameter.
         */
        if (request & IOC_OUT)
        {
            fun = IO$_SENSEMODE;
            p5 = 0;
            (struct it2 *)p6 = &ioctl_desc;
        }
        else
        {
            fun = IO$_SETMODE;
            (struct it2 *)p5 = &ioctl_desc;
            p6 = 0;
        }

        /*
         * Fill in ioctl command.
         */
        ioctl_comm.command = request;
        ioctl_comm.addr = argp;

        /*
         * Do ioctl.
         */
        status = SYS$QIOW(ef, sdc, fun, iosb, 0, 0,
                          0, 0, 0, 0,                /* p1 - p4: not used*/
                          p5, p6);

        if (!VMSOK(status))
        {
    #ifdef DEBUG
            printf("ioctl failed: status = %d\n", status);
    #endif DEBUG
            errno = status;
            return -1;
        }

        if (!VMSOK(iosb[0]))
        {
    #ifdef DEBUG
            printf("ioctl failed: status = %x, %x, %x%x\n", iosb[0], iosb[1],
                   iosb[3], iosb[2]);
    #endif DEBUG
            errno = iosb[0];
            return -1;
        }

        status = LIB$FREE_EF(&ef);
        return 0;
    }

# Chapter 4
OpenVMS System Services Reference

This chapter provides detailed use and reference information about the OpenVMS system services used to write internet applications. The chapter also describes the Internet I/O function codes.

The descriptions of the system services and I/O function codes in this chapter are written specifically for internet programmers. For a general description of these system services and I/O function codes, see the OpenVMS System Services Reference manual.

Table 4-1 lists the equivalent C Socket routine for each service and I/O function code in this chapter. See Chapter 6 for descriptions of C Socket routines.

Table 4-1 OpenVMS System Service and Equivalent C Socket Call
OpenVMS System Service | C Socket Call
--- | ---
$ASSIGN | open()
$CANCEL | close()
$DASSGN | close()
$GETDVI | getpeername(), getsockname(), getsockopt()
$QIO | bind(), listen()
IO$_ACCESS | connect(), accept()
IO$_ACPCONTROL | gethostbyname(), gethostbyaddr(), getnetbyname(), getnetbyaddr()
IO$_DEACCESS | close(), shutdown()
IO$_READVBLK | recv*(), read()
IO$_SENSEMODE | getsockopt(), or a call to the ioctl program
IO$_SENSECHAR | getsockopt(), or a call to the ioctl program
IO$_SETMODE | socket(), bind(), listen(), setsockopt(), or a call to the ioctl program
IO$_SETCHAR | socket(), bind(), listen(), setsockopt(), or a call to the ioctl program
IO$_WRITEVBLK | recv*(), send*(), sendto(), write(), sendmsg()

# 4.1 System Service Descriptions

This section describes the OpenVMS system service routines used to write internet applications.

# $ASSIGN

> The Assign I/O Channel service provides a calling process with an I/O channel. This makes it possible for the calling process to do I/O operations on the internet pseudodevice.

## Format

> ### SYS$ASSIGN devnam, chan, [acmode], [mbxnam]

## Returns

> OpenVMS usage: | longword (unsigned)
> type: | write only
> access: | by value
> mechanism: | 0

Longword condition value. All system services return (by immediate value) a condition value in R0. Condition values that can be returned by this service are listed under Condition Values Returned.

## ARGUMENTS

> ### devnam

> OpenVMS usage: | device_name
> type: | character-coded text string
> access: | read only
> mechanism: | by fixed-length string descriptor

> Name of the device to which $ASSIGN is to assign a channel. The devnam argument specifies the address of a character string descriptor pointing to the pseudodevice name string. The character string contains UCX$DEVICE:.

> ### chan

> OpenVMS usage: | channel
> type: | word (unsigned)
> access: | write only
> mechanism: | by reference

> Number of the channel that is assigned. The chan argument is the address of a word into which $ASSIGN writes the channel number.

> ### acmode

> OpenVMS usage: | access_mode
> type: | longword (unsigned)
> access: | read only
> mechanism: | by value

> Access mode to be associated with the channel. The acmode argument specifies the access mode. I/O operations on the channel can be performed only from equal and more privileged access modes.

> ### mbxnam

> OpenVMS usage: | device_name
> type: | character-coded text string
> access: | read only
> mechanism: | by descriptor---fixed length string descriptor

> This argument is not used.

## DESCRIPTION

> The $ASSIGN system service establishes a path to a device but does not check whether the calling process has the capability to do I/O operations to the device. The device drivers may apply privilege and protection restrictions. The calling process must have NETMBX privilege to assign a channel.

> System dynamic memory is required for the target device and the I/O byte-limit quota from the process buffer is used.

> When a channel is assigned to UCX$DEVICE:, the internet software creates a new pseudodevice called BGn, where n is a unique unit number. The corresponding channel number is used in any subsequent operation requests for that device.

> Channels remain assigned either until they are explicitly deassigned with the Deassign I/O Channel ($DASSGN) service, or, if they are user-mode channels, until the image that assigned the channel exits.

> Two programming examples for the $ASSIGN routine follow this command description. Example 4-1 uses the MACRO-32 programming language and Example 4-2 uses the C programming language.

## Condition Values Returned

> SS$_NORMAL | Service successfully completed.
> SS$_ACCVIO | The caller cannot read the device string or string descriptor, or the caller cannot write the channel number.
> SS$_DEVALLOC | The device is allocated to another process.
> SS$_EXQUOTA | The process has exceeded its buffered I/O byte limit (BIOLM) quota.
> SS$_IVDEVNAM | No device name was specified, the logical name translation failed, or the device name string contains invalid characters.
> SS$_IVLOGNAM | The device name string has a length of zero or has more than 63 characters.
> SS$_NOIOCHAN | No I/O channel is available for assignment.
> SS$_NOSUCHDEV | This warning code indicates that the specified device does not exist.

Example 4-1 $ASSIGN System Service (MACRO-32)

            .title  Assign
            .ident  /01/

            $inetsymdef             ; INET symbols

    dev:    .ascid  /ucx$device:/           ; INET device name
    channel:        .word   0       ; INET channel

            .entry   start,^m<>
    ;
    ;       Assign an INET  device
    ;
            $assign_s       devnam=dev, chan=channel
            .
            .
            .
            .end start

Previous | Next | Contents