Chapter 2. Programming Notes for Character Device API

This chapter describes how to interface an application to the IRIS HIPPI subsystem through the character device (ioctl()-based) application programming interface (API). A reference section containing an alphabetical listing of all the ioctl() calls is included under the heading “API Reference”. Code examples are provided in Appendix B, “Sample Programs.”

Maximum Size for write()s and read()s

The variables max_write_size and max_read_size are used throughout these notes. The maximum size value you can use for these variables depends on the installed hardware, as summarized below.

  • max_xxx_size = 2 megabytes when the hardware is a copper-based HIO board

  • max_xxx_size = 16 megabytes when the hardware is a fiber-optics XIO board

To create a program that will behave correctly, regardless of which hardware is installed, include code that retrieves status from the hardware to determine the hardware type and sets the max_xxx_size appropriately. In the following example, max_len is used for both max_write_size and max_read_size:

/* verify which platform  */
if ( ioctl( fd_i, HIPIOC_GET_STATS, &hipstats ) < 0 ) {
    if ( errno == ENODEV ) fprintf(stderr,
        “%s: HIPPI board is down\n”, argv[0]), exit(1);
    else
        perror(“hipcntl: ioctl HIPIOC_GET_STATS failed”),exit(1);
    }

/* set the maximum length for reads and writes */
/* HST_FORMAT_ID_MASK and HST_XIO are defined in hippi.h */
max_len = ( (hipstats.hst_flags & HST_FORMAT_ID_MASK) == HST_XIO) ? (0x1000000 + 8) : (0x200000 + 8);

Programming for the HIPPI-PH Access Method

This section describes how to program a module that accesses the HIPPI subsystem at the HIPPI-PH signalling layer. This access method does not use an intermediate protocol such as the HIPPI Framing Protocol. This API does not support sharing the subsystem with other APIs (for example, HIPPI-FP access mode or IRIX sockets). A sample program is provided under the heading “HIPPI-PH Example”.


Note: The interface described in this section is applicable for use with either the copper-based IRIS HIPPI-800 physical layer or the fiber optic-based HIPPI-Serial physical layer. The HIPPI-PH references within this section refer to only the signalling protocol that is common to these two HIPPI implementations.


Includes

The following file must be included in any program using the IRIS HIPPI API:

#include <sys/hippi.h>

Special Instructions

For maximum throughput, DMA between the HIPPI board and the host application occurs directly to/from user application space. Because of this, and the fact that the DMA component (ASIC) has a 64-bit interface, all application read()s and write()s must specify buffers that are 8-byte word–aligned, and the data bytecount must be a multiple of 8. (See the memalign(3C) reference page for a method of allocating 8-byte aligned memory).

Opening and Binding to the Device

An application can open a HIPPI device (for example, /dev/hippi0 or /dev/hippi1) for read-only, write-only, or read-and-write access. The acronym fd_hippi#, in the examples below, refers to the file descriptor for the opened HIPPI device. Multiple applications can successfully open() a HIPPI device, although contention will occur if two or more try to write() at the same time.


Note: With a HIPPI-Serial physical layer, simultaneous connections to separate endpoints (for example, simultaneous use of a write-only file descriptor and a read-only one) requires the use of a HIPPI switch between the source and final destination.

It is important that the application open the HIPPI device with only the read/write flag settings that it needs. For example, if an application is not going to be doing read()s, it should set only the WRITE flag. When the READ flag is set, the HIPPI subsystem is told to expect HIPPI packets, so incoming packets are always accepted by the HIPPI device. The HIPPI subsystem holds each accepted packet until an application reads it. If no application consumes the incoming packets, the HIPPI device stalls for lack of buffer space.


Tip: This API does not provide a timeout or interrupt for read()s or write()s that do not complete. If you want your program to be interrupted when one of these calls fails to complete in a certain length of time, use the alarm mechanism. (See the alarm(2) reference page).

To set up an application as a HIPPI-PH user, use one of the following sets of calls at the “beginning of time”:

  • For a transmit-only connection:

    fd_hippi0=open (“/dev/hippi0”, O_WRONLY);
    ioctl (fd_hippi#, HIPIOC_BIND_ULP, HIPPI_ULP_PH);
    

  • For a receive-only connection:

    fd_hippi0=open (“/dev/hippi0”, O_RDONLY);
    ioctl (fd_hippi#, HIPIOC_BIND_ULP, HIPPI_ULP_PH);
    

  • For a transmit and receive connection:

    fd_hippi0=open (“/dev/hippi0”, O_RDWR); 
    ioctl (fd_hippi#, HIPIOC_BIND_ULP, HIPPI_ULP_PH);
    

Transmitting

For an application to transmit over its HIPPI-PH connection, a set (scenario) of calls must be made. The four possible scenarios are explained in the paragraphs that follow, and are illustrated in Figure 2-1. The order of the calls is unimportant except for the initial write() call, which actually allocates the resources and starts sending the data. Four functionality scenarios are supported. (See Table 1-1 for an overview of the four transmission functionality scenarios.)

Many of the ioctl() calls used in these scenarios write or set a value for a stored FDO parameter. These values are not cleared when a transmission completes, so prior settings can be reused with subsequent write() calls without resetting. All the calls should be made for the first transmission (since the device was opened) in order to initialize them to non-default values.

All application write()s must specify buffers that are 8-byte word–aligned, must use a maximum size as defined in “Maximum Size for write()s and read()s”, and must have a data bytecount that is a multiple of 8. (See the memalign(3C) reference page).

Notice the following:

  1. When the HIPIOCW_CONNECT call is used, the HIPPI subsystem sets up a “permanent” connection. In contrast, when the HIPIOCW_CONNECT call is not used, the connection is disconnected as soon as the packet has been sent.

  2. When the HIPIOCW_START_PKT call is used, many write()s may make up one packet. In contrast, when the HIPIOCW_START_PKT call is not used, one write() is a single packet.

    Figure 2-1. The Four Transmission Scenarios

    Figure 2-1 The Four Transmission Scenarios

Functionality Scenario 1

This scenario describes transmission of one small packet (less than max_write_size, as described in section “Maximum Size for write()s and read()s”) that uses one write() for the packet. The connection disconnects automatically when the packet has been completely sent.

The application makes an ioctl() call to specify the I-field, then makes the write() call. The maximum sized packet with this method is max_write_size. The packet and connection are both terminated when the data from the single write() call has completed.

ioctl (fd_hippi#, HIPIOCW_I, I-fieldValue); 
/* I-field does not need to be reset for each pkt */ 
write (fd_hippi#, buffer, size); 
/* PACKET line goes low (false) after one write */
/* connection is dropped after one write */

Functionality Scenario 2

This scenario describes transmission of many small packets (each no larger than max_write_size, as described in section “Maximum Size for write()s and read()s”) that use only one write() for each packet. The connection is kept open between packets.

The application makes an ioctl() call to specify the I-field for its “permanent” connection, then makes a write() call to send the first packet. The maximum–sized packet with this method is max_write_size. The PACKET signal is dropped automatically when the write() call completes. The connection, however, is not terminated, so the next packet can be another single-write in which the packet is terminated automatically, or a multiple-write (Functionality Scenario #4).

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue);
write (fd_hippi#, buffer, size); /* first packet*/
/* PKT line goes low after one write. Connection is not dropped */
write (fd_hippi#, buffer, size); /* second packet*/
/* PKT line goes low after one write. Connection is not dropped */
/* When application wants connection to be torn down, */
/* it tells the HIPPI subsystem to disconnect: */
ioctl (fd_hippi#, HIPIOCW_DISCONN);


Note: With HIPPI–Serial hardware, for the duration of this long-term connection, no packets are received from any source other than the endpoint (destination) of this long-term connection.


Functionality Scenario 3

This scenario describes transmission of a large packet that requires many write() calls and where the connection disconnects automatically when the packet has been completely sent.

The application makes an ioctl() call to specify the I-field, and one to define the size (bytecount) of the packet. It then makes the first write() call; subsequent write() calls are treated as part of the same packet until the bytecount is reached. The PACKET and REQUEST signals are automatically dropped after the specified number of bytes have been sent. This scheme allows an application to send very large packets. It also allows some data gathering on output. (Note, however, that if packets are formed using small-sized write() calls, performance degrades considerably.)

ioctl (fd_hippi#, HIPIOCW_I, I-fieldValue);
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /* only if size is changing */
ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount); 
write (fd_hippi#, buffer, size);   /* buffer can point to FPheader + D1 data */
write (fd_hippi#, buffer, size);  /* size=only a part of the complete pkt*/
write (fd_hippi#, buffer, size);  /* max size for each write is max_write_size*/
write (fd_hippi#, buffer, size);
etc.
/* connection is dropped when packet is completely sent */

Functionality Scenario 4

This scenario describes transmission of many large packets that require many write() calls for each packet and where the connection is kept open.

The application makes an ioctl() call to specify the I-field for its “permanent” connection and one to specify the size (bytecount) of the packet. Each write() is treated as part of the same packet, until the bytecount is satisfied, at which time the packet is ended. When the application wants to terminate the connection, it makes an ioctl() call to disconnect.

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue);
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /* only if size is changing */
ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount); 
write (fd_hippi#, buffer, size); /* buffer can point to FPheader + D1 data */
write (fd_hippi#, buffer, size); /* size=only a part of the complete pkt*/
write (fd_hippi#, buffer, size); /* max size for each write is max_write_size */
etc.
/*when pkt's bytecount is complete, PKT line goes low*/
/*connection is not dropped*/
/* Optional: if the application wishes to start another packet, 
/* it does this: */
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /* only if size is changing */
ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount);
...
/* When the application wants the connection to be torn down, */
/* it tells the HIPPI subsystem to disconnect */
ioctl (fd_hippi#, HIPIOCW_DISCONN); 


Note: With HIPPI–Serial hardware, for the duration of this “permanent” connection, no packets are received from any source other than the endpoint (destination) of this “permanent” connection.


Special Use of Functionality Scenario 4

Scenario 4 can be used to send one infinite-sized packet on a long-term (“permanent”) connection.

The application makes an ioctl() call to specify the I-field for its “permanent” connection and one to specify the bytecount of the packet. The bytecount is specified as HIPPI_D2SIZE_INFINITY. All write() calls are then treated as one “infinite-sized” packet (that is, the PACKET signal is not deasserted), until the packet is specifically terminated by the application with a special ioctl() call. The connection is not dropped until the application disconnects it.

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue);
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /* only if size is changing */
ioctl (fd_hippi#, HIPIOCW_START_PKT, HIPPI_D2SIZE_INFINITY);
/*infinity=0xFFFFFFFF) */
write (fd_hippi#, buffer, size);  /*max size for each write is max_write_size*/
write (fd_hippi#, buffer, size);
etc.
/* Optional: if the application wishes to terminate this packet, it does this */
ioctl (fd_hippi#, HIPIOCW_END_PKT);
/* Optional: if the application wishes to start another packet, 
/* it does one of these: */
ioctl (fd_hippi#, HIPIOCW_START_PKT, HIPPI_D2SIZE_INFINITY);
/* or */

ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount);
/* When the application wishes to tear down the connection, */
/* it does one of these: */
ioctl (fd_hippi#, HIPIOCW_END_PKT);
ioctl (fd_hippi#, HIPIOCW_DISCONN);
/* or */
ioctl (fd_hippi#, HIPIOCW_DISCONN);


Note: With HIPPI–Serial hardware, for the duration of this “permanent” connection, no packets are received from any source other than the endpoint (destination) of this “permanent” connection.


About Blocking on write()

IRIS HIPPI uses the first write() on each connection as the trigger for allocating/obtaining the hardware resources. For example, the REQUEST and PACKET signals are not asserted until the first write() call is made for a connection. This means that any number of open()s, HIPIOCW_CONNECT, and HIPIOCW_START_PKT calls can successfully be made in rapid succession for the same device; the HIPPI subsystem resources become unavailable (to other users) only when the first write() call is made for one of these open file descriptors. After the first successful write(), and as long as the connection for that write() remains active (that is, the REQUEST signal is asserted), write()s from other connections block. Once a connection is finished (that is, the REQUEST and CONNECT signals are deasserted), blocked write()s are serviced.

Receiving

In HIPPI-PH mode, all incoming data is accepted when the device file is opened for reading. The HIPPI subsystem does not reject any connection requests.

To retrieve its data, the application uses the calls below. All read()s retrieve sequentially received data. If an incoming packet contains an FP header and D1 data, the HIPPI subsystem does not interpret them and does not separate them from the D2 data, so the first read() may contain FP header, D1 data, and/or D2 data. To determine packet boundaries, the application can use an ioctl() call to retrieve the current offset (received bytecount) for the packet. When the returned value is 0, the next read() retrieves the first bytes from a new packet.

All application read()s must specify buffers that are 8-byte word–aligned, must use a maximum size as defined in “Maximum Size for write()s and read()s”, and must have a data bytecount that is a multiple of 8. (See the memalign(3C) reference page).

offset = ioctl (fd_hippi#, HIPIOCR_PKT_OFFSET); /*when 0, nxt read is new pkt*/
read (fd_hippi#, buffer, size); /*max size is max_write_size*/
offset = ioctl (fd_hippi#, HIPIOCR_PKT_OFFSET); /*when 0, nxt read is new pkt*/
read (fd_hippi#, buffer, size);
etc.

When the application wishes to stop receiving data, it closes the file descriptor using the following call:

close (fd_hippi#);

Programming for the HIPPI-FP Access Method

This section describes how to program a module that uses the HIPPI Framing Protocol over the IRIS HIPPI subsystem. This API supports sharing the receive and/or transmit channels through the HIPPI subsystem with other upper layer protocols (ULPs). A sample program for this API is provided under the heading “HIPPI-FP Example”.


Note: Multiple applications can bind to a HIPPI file descriptor (for example, /dev/hippi1) without affecting other applications that have opened the same device.

Using a HIPPI ioctl() call, the application “binds” itself to one ULPO and FDO. This action associates the application with one set of HIPPI information that is then used by the HIPPI subsystem whenever it services that application's read/write requests. The application specifies which ULPO by specifying the ULPO's 8-bit identifier.

It is important that the application open the HIPPI device with only the read/write flag settings that it needs. For example, if an application is not going to be doing read()s, it should set only the WRITE flag. When the READ flag is set, the HIPPI device is told to accept HIPPI packets on that ULP-id. All incoming packets for that ULP-id are accepted by the HIPPI device. The HIPPI subsystem holds each accepted packet until an application reads it. If no application consumes the incoming packets, the HIPPI device stalls for lack of buffer space.

Includes

The following files must be included in any program using the HIPPI API:

#include <sys/hippi.h>

Special Instructions

For maximum throughput, DMA between the HIPPI board and the host application occurs directly to/from user application space. Because of this, and the fact that the DMA component (ASIC) has a 64-bit interface, all application read()s and write()s must specify buffers that are 8-byte word–aligned, and the data bytecount must be a multiple of 8. (See the memalign(3C) reference page).

Opening and Binding to the Device

An application can open a HIPPI device (for example, /dev/hippi0 or /dev/hippi1) for read-only, write-only, or read-and-write access. The acronym fd_hippi#, in the examples below, refers to the file descriptor for the opened HIPPI device.


Note: When the physical layer is IRIS HIPPI-Serial, simultaneous use of read-only and write-only files (for the same device) to different endpoints requires the use of a HIPPI switch between the source and the final destination.

To set up an application as a HIPPI-FP user, use one of the following sets of calls at the “beginning of time.” Within the calls in these examples, the ULP-id is a positive number in the range 0-255 decimal (inclusive), where 4 is reserved for the IRIX 8802.2 Link Encapsulation (HIPPI-LE) ULP, and 6 and 7 are reserved for HIPPI–IPI3 implementations. Each ULP's identification must be unique among the ULPs that are bound to that HIPPI board.

  • For a transmit-only connection:

    fd_hippi0=open (“/dev/hippi0”, O_WRONLY);
    

    ioctl (fd_hippi#, HIPIOC_BIND_ULP, ULP-id);
    

  • For a receive-only connection:

    fd_hippi0=open (“/dev/hippi0”, O_RDONLY);
    

    ioctl (fd_hippi#, HIPIOC_BIND_ULP, ULP-id);
    

  • For a transmit and receive connection:

    fd_hippi0=open (“/dev/hippi0”, O_RDWR);
    

    ioctl (fd_hippi#, HIPIOC_BIND_ULP, ULP-id);
    

  • For a monitoring connection to a HIPPI driver that has bypass functionality:

    fd_hippibp0=open (“/dev/hippibp0”, O_RDONLY);
    

    ioctl (fd_hippibp#, HIPIOC_BIND_ULP, ULP-id);
    <only the HIPIOC_GET_BPSTATS is available>
    


Tip: The IRIS HIPPI API does not provide a timeout or interrupt for read()s or write()s that do not complete. If you want your program to be interrupted when one of these calls fails to complete in a certain length of time, use the alarm mechanism. (See the man page for alarm(2) reference page).


Transmitting

For a HIPPI-FP application to transmit over its HIPPI connection, one of the sets of calls documented below in the “Functionality Scenarios” must be made. The order of the calls is unimportant except for the initial write() call, which actually starts sending the data. Four functionality scenarios are supported. (See Table 1-1 for details on the four transmission functionality scenarios.)

Many of the ioctl() calls write or set a value for a stored ULPO or FDO parameter. These values are not cleared when a transmission completes, so prior settings can be reused with subsequent write() calls without resetting. All the calls should be made for the first transmission (since the device was opened) in order to initialize them to non-default values.

All application write()s must specify buffers that are 8-byte word–aligned, must use a maximum size as defined in “Maximum Size for write()s and read()s”, and must have a data bytecount that is a multiple of 8. (See the memalign(3C) reference page).

Notice the following:

  1. When the HIPIOCW_CONNECT call is used, the HIPPI subsystem sets up a “permanent” connection. In contrast, when the HIPIOCW_CONNECT call is not used, the connection is disconnected as soon as the packet has been sent.

  2. When the HIPIOCW_START_PKT call is used, many write()s may make up one packet. In contrast, when the HIPIOCW_START_PKT call is not used, one write() is a single packet.

Functionality Scenario 1

This scenario describes transmission of one small packet (less than max_write_size, as described on page 23), using one write() for the packet. The connection disconnects when the packet has been completely sent.

The application makes an ioctl() call to specify the I-field, then makes the write() call. The maximum sized packet with this method is max_write_size. The packet and connection are both terminated when the data from the single write() call has completed.

ioctl (fd_hippi#, HIPIOCW_I, I-fieldValue); 
/* I-field does not need to be reset for each pkt */ 
ioctl (fd_hippi#, HIPIOCW_D1_SIZE, bytecount);   /* only if size is changing*/
write (fd_hippi#, buffer, size);   /*max size for each write is max_write_size*/
/* PKT line goes low (false) after one write */
/* connection is dropped after one write */

Functionality Scenario 2

This scenario describes transmission of many small packets (each no larger than max_write_size, as described on page 23) that use one write() for each packet. The connection is kept open between packets.

The application makes an ioctl() call to specify the I-field for its “permanent” connection, then makes a write() call to send the first packet. The maximum sized packet with this method is max_write_size. The PACKET signal is automatically dropped when the write() call completes. The connection, however, is not terminated, so the next packet can be another single-write or a multiple-write one (Functionality Scenario #4).

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue);
ioctl (fd_hippi#, HIPIOCW_D1_SIZE, bytecount);  /* only if size is changing*/
write (fd_hippi#, buffer, size);     /* first packet; max size = max_write_size*/
/* PKT line goes low after one write. Connection is not dropped */
write (fd_hippi#, buffer, size);     /* second packet; max size = max_write_size*/
/* PKT line goes low after one write. Connection is not dropped */
/* When application wants connection to be torn down, */
/* it tells the HIPPI subsystem to disconnect: */
ioctl (fd_hippi#, HIPIOCW_DISCONN);


Note: With HIPPI–Serial hardware or with IRIS HIPPI configured to support the IP suite of protocols, for the duration of this long-term connection, no packets are received from a source other than the endpoint (destination) of this long-term connection.


Functionality Scenario 3

This scenario describes the transmission of one large packet that requires many write() calls for the packet and where the connection disconnects when the packet has been completely sent.

The application makes an ioctl() call to specify the I-field, and another call to define the size (bytecount) of the packet. It then makes the first write() call; subsequent write() calls are treated as part of the same packet until the bytecount is reached. The PACKET and REQUEST signals are automatically dropped after the specified number of bytes have been sent. This scheme allows an application to send very large packets. It also allows some data gathering on output. (Note, however, that if packets are formed using small-sized write() calls, performance degrades considerably.)

ioctl (fd_hippi#, HIPIOCW_I, I-fieldValue);
ioctl (fd_hippi#, HIPIOCW_D1_SIZE, bytecount);  /* only if size is changing*/
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /*only if burst_1 is changing*/
ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount); 
write (fd_hippi#, buffer, size);   /* buffer can include D1 data */
write (fd_hippi#, buffer, size); /* size=only part of pkt and up to max_write_size*/
write (fd_hippi#, buffer, size);  /* max size for each write is max_write_size*/
write (fd_hippi#, buffer, size);
etc.
/* connection is dropped when pkt is completely sent */

Functionality Scenario 4

This scenario describes transmission of many large packets that require many write() calls for each packet and where the connection is kept open.

The application makes an ioctl() call to specify the I-field for its “permanent” connection, and another call to specify the size (bytecount) of the packet. Each write() is treated as part of the same packet, until the bytecount is satisfied, at which time the packet is ended. When the application wants to terminate the connection, it makes an ioctl() call to disconnect.

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue); 
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /*only if burst_1 is changing*/
ioctl (fd_hippi#, HIPIOCW_D1_SIZE, bytecount);  /* only if size is changing*/
ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount); 
write (fd_hippi#, buffer, size); /* buffer can include D1 data */
write (fd_hippi#, buffer, size); /* size=only a part of the complete pkt*/
write (fd_hippi#, buffer, size); /* max size for each write is max_write_size */
etc.
/*when pkt completes, PKT line goes low*/
/*connection is not dropped*/
/* When the application wants the connection to be torn down, */
/* it tells the HIPPI subsystem to disconnect */
ioctl (fd_hippi#, HIPIOCW_DISCONN);

Special Use of Functionality Scenario 4

For an infinite-sized packet on a long-term (“permanent”) connection.

The application makes an ioctl() call to specify the I-field for its “permanent” connection, and another call to specify the bytecount of the packet. The bytecount is specified as HIPPI_D2SIZE_INFINITY. All write() calls are then treated as one “infinite-sized” packet (that is, the PACKET signal is not deasserted), until the connection is specifically disconnected by the application.

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue);
ioctl (fd_hippi#, HIPIOCW_SHBURST, firstburstsize); /*only if burst_1 is changing*/
ioctl (fd_hippi#, HIPIOCW_D1_SIZE, bytecount);  /* only if size is changing*/
ioctl (fd_hippi#, HIPIOCW_START_PKT, HIPPI_D2SIZE_INFINITY);
/*infinity=0xFFFFFFFF) */
write (fd_hippi#, buffer, size);  /*max size for each write is max_write_size*/
write (fd_hippi#, buffer, size);
etc.
/* Optional: if the application wishes to terminate this packet 
/* and start another without dropping the connection, it does this: */
ioctl (fd_hippi#, HIPIOCW_END_PKT);
ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount);
etc.
/* When the application wishes to tear down the connection */
ioctl (fd_hippi#, HIPIOCW_END_PKT);
ioctl (fd_hippi#, HIPIOCW_DISCONN);


Note: With HIPPI–Serial hardware or with IRIS HIPPI configured to support the IP suite of protocols, for the duration of this “permanent” connection, no packets are received from any source other than the endpoint (destination) of this “permanent” connection.


About Blocking on write()

IRIS HIPPI uses the first write() on each connection as the trigger for allocating/obtaining the hardware resources. For example, the REQUEST and PACKET signals are not asserted until the first write() call is made for a connection. This means that any number of open()s, HIPIOCW_CONNECT, and HIPIOCW_START_PKT calls can successfully be made in rapid succession for the same device; the HIPPI subsystem resources become unavailable (to other users) only when the first write() call is made for one of these open file descriptors. After the first successful write(), and as long as the connection for that write() remains active (that is, the REQUEST signal is asserted), write()s from other connections block. Once a connection is finished (that is, the REQUEST and CONNECT signals are deasserted), blocked write()s are serviced.

Receiving

To receive data, the application uses the calls below. The first read() of a ULP's queue retrieves a packet's FP header and D1 area. Subsequent read() calls retrieve D2 data. When the HIPIOCR_PKT_OFFSET returns zero, the next read() will retrieve a new packet's header and D1 area.

All application read()s must specify buffers that are 8-byte word–aligned, must use a maximum size as defined in “Maximum Size for write()s and read()s”, and must have a data bytecount that is a multiple of 8. (See the memalign(3C) reference page).

read (fd_hippi#, buffer, size); /* FPheader and D1 data */
read (fd_hippi#, buffer, size); /* D2 data */
read (fd_hippi#, buffer, size); /* D2 data */
offset = ioctl (fd_hippi#, HIPIOCR_PKT_OFFSET); /*when 0, nxt read is new pkt*/

When the application wishes to stop receiving data, it closes the file descriptor using the following call:

close (fd_hippi#);

API Reference

This section describes the HIPPI ioctl calls that comprise the API to the IRIS HIPPI subsystem. These calls are defined in the sys/hippi.h file. Each application program that wants to use the services of the HIPPI connection uses these calls to define its ULPO and FDO values, to set up its connection(s), and to transmit or receive data. The API calls are listed in Table 2-1.

Table 2-1. IRIS HIPPI API Summary

Purpose

API Call

Page

Device Management:

 

 

Bind an upper-layer application

HIPIOC_BIND_ULP

41

Enable/disable IRIS HIPPI board

HIPPI_SETONOFF

66

Connection Management:

 

 

Start/stop accepting connections

HIPIOC_ACCEPT_FLAG

40

Set timeout for source's connection

HIPIOC_STIMEO

53

Prepare to open a single-packet connection

HIPIOCW_I

62

Prepare to open a long-term connection

HIPIOCW_CONNECT

56

Terminate a long-term connection

HIPIOCW_DISCONN

59

Packet Control:

 

 

Received packet's bytecount

HIPIOCR_PKT_OFFSET

55

Send a single-write packet

After setting the I-field (with HIPIOCW_I), no additional call is necessary, other than the write().

 

Send a multiple-write packet

HIPIOCW_START_PKT

65

Define first burst of a multiple-write packet

HIPIOCW_SHBURST

63

Terminate a packet

HIPIOCW_END_PKT

60

Retrieve errors from failed read() and write() calls

HIPIOCR_ERRS
HIPIOCW_ERR

54
61

Define HIPPI-FP Fields:

 

 

Define D1 Area Size and set P-bit

HIPIOCW_D1_SIZE

58

Collect Statistics or Monitor Connection:

 

 

Obtain standard statistics

HIPIOC_GET_STATS

44

Obtain bypass statistics

HIPIOC_GET_BPSTATS

42


HIPIOC_ACCEPT_FLAG

HIPIOC_ACCEPT_FLAG configures the HIPPI board to accept or refuse connection requests.


Note: After each execution of /usr/etc/hipcntl startup, /etc/init.d/network, or each restart of the system, the IRIS HIPPI software sets this flag ON (accept).

Usage

HIPPI device control for HIPPI-FP and HIPPI-PH.

ioctl (fd_hippi#, HIPIOCW_ACCEPT_FLAG, value);

The arg

The value is any non–zero value (including negative values) to accept connection requests, and 0 to reject connection requests.

Failures and Errors

This call fails for the following reasons:

  • The IRIS HIPPI board is shutdown (for example, hipcntl shutdown or HIPPI_SETONOFF has been called).

HIPIOC_BIND_ULP

HIPIOC_BIND_ULP is used to bind an application's open file descriptor (/dev/hippi0, /dev/hippi1, etc.) to a ULPO or FDO. If an application wishes to both transmit and receive, it can bind once to a read-and-write file descriptor, or it can make this call twice (once to a write-only file descriptor and once to a read-only one). This call prepares for a connection; it does not open the connection.

  • When the HIPPI-FP access method is used, up to 32 different applications can be bound simultaneously.

  • When the HIPPI-FP access method is used, up to eight different ULPOs can be bound to each HIPPI subsystem.

  • When the HIPPI-PH method is used, only one ULPO (that being, HIPPI_ULP_PH) can be bound for the receive HIPPI channel and one FDO for the transmit channel.

Usage

Initialization of HIPPI-FP.

ioctl (fd_hippi#, HIPIOC_BIND_ULP, ULP-id);

Initialization of HIPPI-PH.

ioctl (fd_hippi#, HIPIOC_BIND_ULP, HIPPI_ULP_PH);

The arg

For HIPPI-FP, the arg is the identification for the ULPO or FDO that the application uses (range 0-255 decimal inclusive), where 4 is reserved for the IRIX 8802.2 Link Encapsulation (HIPPI-LE), 6 and 7 are reserved for HIPPI-IPI, 12 is reserved for the IRIS ST Protocol stack, and 144 is used (by default) by the optional IRIS Bypass module. Each ULPO/FDO implementation must have an identification, and each identification must be unique among the ULPOs and FDOs that are open (bound) for the particular HIPPI board (device).

For HIPPI-PH, the arg is HIPPI_ULP_PH.

Failures and Errors

This call fails for the following reasons:

  • The maximum number of FDOs and ULPOs are already bound to the HIPPI device.

  • A HIPPI-PH object (FDO or ULPO) is already bound for this type of access (read or write) to this file descriptor.

HIPIOC_GET_BPSTATS

HIPIOC_GET_BPSTATS is used to obtain statistics about the HIPPI bypass functionality.

Usage

Monitoring the HIPPI bypass functionality.

ioctl (fd_hippibp#, HIPIOC_GET_BPSTATS, &hippibp_stats);

The arg

The arg is a pointer to a hippibp_stats structure.

The hippibp_stats structure, from the hippi.h file, is provided below for reference:

typedef struct hippibp_stats {
/* BYPASS STATE */
  u_int   hst_bp_job_vec;         /* bypass job enable vector */
                                /* job 0 is in bit 31, job 7 bit 24*/
  u_int   hst_bp_ulp;            /* ulp used by bypass */

/* SOURCE STATISTICS */
  u_int   hst_s_bp_descs;        /* total bypass desc processed */
  u_int   hst_s_bp_packets;      /* total bypass packets sent */
  _uint64_t hst_s_bp_byte_count; /* total bypass bytes sent */

/* SOURCE ERRORS */
  /* descriptor errors */
  u_int   hst_s_bp_desc_hostx_err;     /* hostx is out of bounds*/
  u_int   hst_s_bp_desc_bufx_err;      /* buffer index out of bounds*/
  u_int   hst_s_bp_desc_opcode_err;    /* invalid opcode */
  u_int   hst_s_bp_desc_addr_err;      /* packet length + offset */
                                     /* would cross a page boundary*/
  u_int   hst_s_bp_resvd[6];          /* future expansion */

/* DESTINATION STATISTICS */
  u_int   hst_d_bp_descs;          /* total dest desc processed */
  u_int   hst_d_bp_packets;        /* total bypass packets received */
  __uint64_t hst_d_bp_byte_count;   /* total bypass bytes received */

/* DESTINATION ERRORS */
  /* descriptor errors */ 
  u_int   hst_d_bp_port_err;       /* port not enabled or port */
                                  /* or port too large */
  u_int   hst_d_bp_job_err;     /* job not enabled */
  u_int   hst_d_bp_no_pgs_err;   /* no longer used */
  u_int   hst_d_bp_bufx_err;    /* destination bufx not in bounds */
  u_int   hst_d_bp_auth_err;    /* received authentication did */
                               /* not match job authentication
                               /* for destination port */
  u_int   hst_d_bp_off_err;     /* offset plus packet length */
                               /* would cross a page boundary 
                               /* or not aligned properly*/
  u_int   hst_d_bp_opcode_err;  /* received opcode was invalid */
  u_int   hst_d_bp_vers_err;    /* received version number invalid */
  u_int   hst_d_bp_seq_err;     /* sequence number for multi-pkt */
                               /* opcode was out of sequence */
  u_int   hst_d_bp_resvd[4];

} hippibp_stats_t;

Failures and Errors

This call fails for the following reasons:

  • The driver is unable to copy the statistics from the board.

  • The IRIS HIPPI board is shutdown (for example, hipcntl shutdown or HIPPI_SETONOFF has be called).

HIPIOC_GET_STATS

HIPIOC_GET_STATS is used to obtain statistics about the HIPPI board. The HIPPI product ships with a utility (hipcntl) for doing this kind of monitoring, so this ioctl call is not usually needed by customer-developed applications.

Usage

Monitoring of HIPPI-PH and HIPPI-FP devices and connections.

ioctl (fd_hippi#, HIPIOC_GET_STATS, &hippi_stats);

The arg

The arg is a pointer to a hippi_stats structure, described in Table 2-2. The structure is the same across all IRIS HIPPI implementations; however, the specific information varies from hardware to hardware. Refer to the table that is appropriate for your hardware.

Table 2-2. Information Retrieved by HIPIOC_GET_STATS

Field

Type

Description

hst_flags;

u_int

The value of bits 31-28 indicates the type of hardware:
 0x0 = IRIS HIPPI HIO Mezzanine,
 0x1 = IRIS HIPPI-Serial XIO

Bits 27-0 contain flags that indicate the currently active states. See

Table 2-3 or Table 2-4 for the specific flags associated with each hardware implementation.

 

 

Source statistics.

 hst_s_conns;

u_int

Total connections attempted by local SRC.

 hst_s_packets;

u_int

Total packets sent by local SRC.

 sf.
  data[14];

union
u_int

Array containing either a hip_p (described in Table 2-3) or hip_s (described in Table 2-4) structure, depending on the specific hardware.

 

 

Destination statistics.

 hst_d_conns;

u_int

Total connections accepted.

 hst_d_packets;

u_int

Total packets received.

 df.
  data[14];

union
u_int

Array containing either a hip_p (described in Table 2-3) or hip_s (described in Table 2-4) structure, depending on the specific hardware.


  

Table 2-3. Status Information Retrieved From Copper-based HIPPI HIO Mezzanine Board

Field

Value or Type

Description

Status flags:

 

 

 HST_FLAG_DSIC

0x0001

Local SRC sees inbound INTERCONNECT signal

 HST_FLAG_SDIC

0x0002

Local DST sees inbound INTERCONNECT signal

 HST_FLAG_DST_ACCEPT

0x0010

Local DST is accepting connections

 HST_FLAG_DST_PKTIN

0x0020

Local DST: PACKET input signal is asserted

 HST_FLAG_DST_REQIN

0x0040

DST: inbound REQUEST signal is asserted

 HST_FLAG_SRC_REQOUT

0x0100

Local SRC: outbound REQUEST signal is asserted

 HST_FLAG_SRC_CONIN

0x0200

Local SRC: CONNECT input signal is asserted

hip_p

struct

Source error counts

 rejects;

u_int

connection attempts rejected

 dm_seqerrs;

u_int

count of sequence errors from SRC's data state machine

 cd_seqerrs;

u_int

count of invalid sequencing of inbound control signals at the SRC's connection state machine

 cs_seqerrs;

u_int

count of sequence errors detected within SRC's connection state machine

 dsic_lost;

u_int

inbound INTERCONNECT signal was deasserted before local SRC terminated connection

 timeo;

u_int

timed out connection attempts

 connls;

u_int

connections dropped by other side

 par_err;

u_int

source parity error

 resvd[6];

u_int

reserved for future compatibility

hip_p

struct

Destination error counts

 badulps;

u_int

packets dropped due to unknown ULP-id

 ledrop;

u_int

HIPPI-LE packets dropped

 llrc;

u_int

connections dropped due to LLRC error

 par_err;

u_int

connections dropped due to parity errors

 seq_err;

u_int

connections dropped due to sequence errors

 sync;

u_int

synchronization errors

 illbrst;

u_int

packets with illegal burst sizes

 sdic_lost;

u_int

connections dropped due to loss of inbound INTERCONNECT signal

 nullconn;

u_int

connections with zero packets

 resvd[5];

u_int

reserved for future compatibility


 

Table 2-4. Status Information Retrieved From Fiber Optics-based HIPPI-Serial XIO Board

Field

Value or Type

Description

Status flags:

 

 

 HST_FLAG_LOOPBACK

0x0004

Board's internal loopback mode is enabled

 HST_FLAG_DST_ACCEPT

0x0010

Local DST is accepting connections

 HST_FLAG_DST_PKTIN

0x0020

Local DST: PACKET signal input is asserted

 HST_FLAG_DST_REQIN

0x0040

Local DST: REQUEST signal input is asserted

 HST_FLAG_SRC_REQOUT

0x0100

Local SRC: REQUEST signal is asserted

 HST_FLAG_SRC_CONIN

0x0200

Local SRC: CONNECT input signal is asserted

 HST_FLAG_DST_LNK_RDY

0x00010000

Local SERIAL DST: the on-board HIPPI processor is in its operational state (that is, it is in state 2 of the “link reset state machine”). This flag is absent (not set) only if the DST state machine transitions to state 0 or 1, caused by losing contact with the HIPPI-Serial (G-link) chip on the board or the fiber connection.

 HST_FLAG_DST_FLAG_SYNC

0x00020000

Local SERIAL DST: the alternating flag within the incoming data frame is correct (that is, it is synchronized)

 HST_FLAG_DST_OH8_SYNC

0x00040000

Local SERIAL DST: the OH8 (framing) overhead bit from the incoming data stream is correct

 HST_FLAG_DST_SIG_DET

0x00080000

Local SERIAL DST: incoming signal on fiber is detected

hip_s

struct

Source error counts

 rejects;

u_int

Connection REQUESTs that were rejected

 resvd0[2];

u_int

reserved

 glink_resets;

u_int

Times that the firmware reset both the HIPPI-Serial (G-link) chips. A reset occurs when the firmware believes one of the HIPPI-Serial (G-link) chips is not responding. However, a reset can be caused by faulty cabling, ODLs, or connectors since the firmware cannot identify the true cause for an unresponsive HIPPI-Serial portion of the board.

 glink_err;

u_int

Count of times that the firmware fails to see any one of the following flags for more than half a second: DST_OH8_SYNC, DST_FLAG_SYNC, DST_LNK_RDY, or DST_SIG_DET. This event can be counted, at maximum, 50 times per second (at 25MHz).

 timeo;

u_int

Count of connection attempts by SRC that timed out.

 connls;

u_int

Count of connections made by SRC that were dropped by the other side.

 par_err;

u_int

Count of SRC parity errors. This error indicates that a local parity error (for example, on the IRIS HIPPI board) resulted in the transmission of invalid data.

 resvd1[4];

u_int

reserved

 numbytes_hi;

u_int

Most significant digits for total count of bytes sent.

 numbytes_lo;

u_int

Least significant digits for total count of bytes sent.

hip_s

struct

Destination error counts.

 badulps;

u_int

Packets dropped due to unknown ULP-id.

 ledrop;

u_int

HIPPI-LE packets dropped.

 llrc;

u_int

Connections dropped due to LLRC errors.

 par_err;

u_int

Connections dropped due to parity errors.

 frame_state_err;

u_int

Count of framing (OH8 overhead bit) errors that occurred while PACKET signal was asserted or HIPPI state transition errors. Examples of state transition errors include:

 no_REQUEST —> PACKET
 no_REQUEST —> BURST
 REQUEST —> BURST
 BURST —> REQUEST
 BURST —>
no_REQUEST

 flag_err;

u_int

Count of data–frame alternating–flag–bit synchronizations that were lost while PACKET signal was asserted.

 illbrst;

u_int

Packets with illegal burst sizes.

 pkt_lnklost_err;

u_int

Count of packets that were aborted due to the DST_FLAG_SYNC, DST_OH8_SYNC, or DST_LNK_RDY flag becoming unset (not true) when the PACKET signal was asserted.

 nullconn;

u_int

Connections with zero packets.

 rdy_err;

u_int

Count of bursts received for which no READYs had been sent.

 bad_pkt_st_err;

u_int

Number of packets that started improperly. For example, a sequence of PACKET-no_BURST- deasserted_PACKET (that is, a null packet), or a faulty FP packet (BURST followed by less than 12 bytes and a deasserted PACKET signal).

 resvd;

u_int

reserved

 numbytes_hi;

u_int

Most significant digits for total count of bytes received.

 numbytes_lo;

u_int

Least significant digits for total count of bytes received.

The hippi_stats structure, from the hippi.h file, is provided below for reference.

typedef struct hippi_stats {
     u_int hst_flags;	/* status flags */
/* Used by HIO™ board on Challenge™ or Onyx® systems only */
#define HST_FLAG_DSIC 0x0001           /* SRC sees IC */
#define HST_FLAG_SDIC 0x0002           /* DST sees IC */

/* Used only by HIPPI-Serial XIO™ board */
#define HST_FLAG_LOOPBACK 0x0004        /* internal loopback enabled */

/* HIPPI flags used by all types of hardwre */
#define HST_FLAG_DST_ACCEPT 0x0010          /* DST is accepting connections */
#define HST_FLAG_DST_PKTIN 0x0020           /* DST: PACKET input is high */
#define HST_FLAG_DST_REQIN 0x0040           /* DST: REQUEST input is high */
#define HST_FLAG_SRC_REQOUT 0x0100          /* SRC: REQUEST is asserted */
#define HST_FLAG_SRC_CONIN 0x0200           /* SRC: CONNECT input is high */

/* HIPPI-Serial flags used only with HIPPI-Serial */
#define HST_FLAG_DST_LNK_RDY 0x00010000
#define HST_FLAG_DST_FLAG_SYNC 0x00020000 /* SERIAL DST: alternating flg sync'd*/
#define HST_FLAG_DST_OH8_SYNC 0x00040000
#define HST_FLAG_DST_SIG_DET 0x00080000  /* SERIAL DST: signal detect at DST */

/* Error statistics are different for Hippi Parallel (HP) vs. Hippi Serial (HS).
*  In an effort to keep some binary compatibility, some fields
*  defined originally for Hippi Parallel are re-used for Hippi Serial.
*/
/* Source statistics */
   u_int hst_s_conns;             /* total connections attempted */
   u_int hst_s_packets;           /* total packets sent */

union {
  u_int     data[14];
  struct {
   u_int rejects;                /* connection attempts rejected */
   u_int dm_seqerrs;             /* data sm sequence error */
   u_int cd_seqerrs;             /* conn sm sequence error, dst */
   u_int cs_seqerrs;             /* conn sm sequence error, src */
   u_int dsic_lost;
   u_int timeo;                  /* timed out connection attempts*/
   u_int connls;                 /* connections dropped by other side*/
   u_int par_err;                /* source parity error */
   u_int   resvd[6];	/* reserved for future compatibility */
  } hip_p;	/* parrallel hippi */

  struct {
     u_int   rejects;             /* connection attempts rejected */
     u_int   resvd0[2];           /* reserved for future compatibility */
     u_int   glink_resets;        /* times firmware reset glink */
     u_int   glink_err;           /* glink error count */
     u_int   timeo;               /* connection attempts timed out */
     u_int   connls;              /* connections dropped by other side */
     u_int   par_err;             /* source parity error */
     u_int   resvd1[4];           /* reserved for future compatibility */
     u_int   numbytes_hi;         /* number of bytes sent */
     u_int   numbytes_lo;         /* number of bytes sent */
  } hip_s;                       /* serial hippi */

} sf;                           /* source format, system specific */


/* Destination statistics */
   u_int hst_d_conns;            /* total connections accepted */
   u_int hst_d_packets;          /* total packets received */

  union {
    u_int       data[14];
    struct {

   u_int badulps;          /* pkts dropped due to unknown ULP*/
   u_int ledrop;           /* HIPPI-LE packets dropped */
   u_int llrc;             /* conns dropped due to llrc error */
   u_int par_err;          /* conns dropped due to parity err */
   u_int seq_err;          /* conns dropped due to sequence err */
   u_int sync;             /* sync errors */
   u_int illbrst;          /* packets with illegal burst sizes */
   u_int sdic_lost;        /* conns dropped due to sdic lost */
   u_int nullconn;         /* connections with zero packets */
   u_int resvd[5];         /* reserved for future compatibility*/
  } hip_p;

  struct {
     u_int   badulps;           /* packets dropped due to unknown ULP */
     u_int   ledrop;            /* HIPPI-LE packets dropped */
     u_int   llrc;              /* conns dropped due to llrc error */
     u_int   par_err;           /* conns dropped due to parity error */
     u_int   frame_state_err;    /* framing err or state transition err; eg: */
                                    * no request -> packet
                                    * no request -> burst
                                    * request -> burst
                                    * burst -> request
                                    * burst -> no request
     u_int   flag_err;          /* flag sync lost during packet */
     u_int   illbrst;           /* packets with illegal burst sizes */
     u_int   pkt_lnklost_err;   /* lost linkready when PACKET asserted */
     u_int   nullconn;          /* connections with zero packets */
     u_int   rdy_err;           /* data received when no readys sent */
     u_int   bad_pkt_st_err;     /* packet got off to a bad start 	*/
     u_int   resvd;
     u_int   numbytes_hi;        /* number bytes received */
     u_int   numbytes_lo;        /* number bytes received */
     } hip_s;

  } df;                        /* destination format, system specific */

} hippi_stats_t;

Failures and Errors

This call fails for the following reasons:

  • The driver is unable to copy the statistics from the board.

  • The IRIS HIPPI board is shutdown (for example, hipcntl shutdown or HIPPI_SETONOFF has be called).

HIPIOC_STIMEO

HIPIOC_STIMEO sets the period of time for which the IRIS HIPPI source channel waits for a CONNECT or READY signal before aborting the connection. With the Challenge/Onyx HIO board, the granularity for this timeout is 250 milliseconds; IRIS HIPPI rounds the user-specified value to the nearest 250 millisecond interval. With the Origin/Onyx2 XIO board, the granularity is 1 millisecond.

Usage

Transmission for HIPPI-FP and HIPPI-PH.

ioctl (fd_hippi#, HIPIOC_STIMEO, milliseconds);

The arg

The range of valid values for milliseconds is 1 to FFFFFFFF inclusive (hexadecimal notation).

Failures and Errors

This call fails for the following reasons:

  • IRIS HIPPI board is shutdown (for example, hipcntl shutdown or HIPPI_SETONOFF has be called).

  • The value used for the milliseconds argument is out of range.

HIPIOCR_ERRS

HIPIOCR_ERRS returns the error status from the last read() call for the indicated file descriptor.

Usage

Error monitoring for reception with HIPPI-FP and HIPPI-PH.

error = ioctl (fd_hippi#, HIPIOCR_ERRS);

The arg

There is no arg for this call.

Returned Value

The returned error is a 6-bit vector indicating the errors that occurred on the last read(), as summarized in Table 2-5.

Table 2-5. Errors for Failed read() Calls

Bit Position

Hex Mask

Error

0

0x01

HIP_DSTERR_PARITY: Destination parity error.

1

0x02

HIP_DSTERR_LLRC: Destination LLRC error.

2

0x04

HIP_DSTERR_SEQ: Destination sequence error. Causes the SDIC lost error also.

3

0x08

HIP_DSTERR_SYNC: Destination synchronization error.

4

0x10

HIP_DSTERR_ILBURST: Destination illegal burst error.

5

0x20

HIP_DSTERR_SDIC: Destination SDIC lost error.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • If the returned error is a negative value, then an error occurred while making the ioctl() call, and none of the bits should be interpreted.

HIPIOCR_PKT_OFFSET

HIPIOCR_PKT_OFFSET retrieves the offset for the packet being received.

Usage

Reception for HIPPI-FP and HIPPI-PH.

offset = ioctl (fd_hippi#, HIPIOCR_PKT_OFFSET);

The arg

There is no arg for this call.

Returned Value

The returned offset is an integer indicating the current offset (number of bytes received so far) for the packet in the next read(). When the offset is 0, the next read() starts a new packet.

When the returned offset reaches 0x7FFFFFFF, the counter sticks (that is, does not count any higher and does not roll over to zero). However, the counter will again return true count values when the next packet arrives.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • The file descriptor has not been opened for reading by this application.

HIPIOCW_CONNECT

HIPIOCW_CONNECT causes a long-term (many-packet) connection to be established with the next write(). The argument sets the value for the I-field that will be used on the connection request. Once this call has been made, the HIPPI-subsystem sets up a connection with the next write() call, and does not tear the connection down until the HIPIOCW_DISCONN call is invoked. Multiple applications can call HIPIOCW_CONNECT for the same device successfully; however, once one application does a write(), the HIPPI subsystem's resources are unavailable for other applications' write()s.


Note: For single-packet connections, use HIPIOCW_I.

Usage

Transmission for HIPPI-FP and HIPPI-PH.

ioctl (fd_hippi#, HIPIOCW_CONNECT, I-fieldValue);

The arg

The I-fieldValue is a 32-bit number used as the I-field. IRIS HIPPI does not verify, alter, or interpret the I-field value.

For a HIPPI-SC compliant I-field, bit 31 of the I-field must be set to 0 and the remaining bits (30:0) must be partitioned into fields, as summarized in Table 2-6. (For more details about the I-field, see Figure A-2.)

“Locally-administered” schemes are legal and supported. For a locally-administered scheme, bit 31 must be set to 1 and bits 30:0 can be set to comply with any locally-defined protocol or can be set to zero (for example, I-field value = 80000000 hex).


Note: Using a “locally-administered” I-field severely limits interoperability, especially in the areas of routing and HIPPI switch control.  


Table 2-6. IRIS HIPPI Support for Fields in I-Field

 

Valid Values for
IRIS HIPPI (binary)

 

 

Bits in I-field


Locally-Defined


HIPPI-SC Compliant


Comments

31

1

0

Both I-field formats (local and HIPPI-SC) are supported.

30:29

anything

anything

 

28

anything

0

IRIS HIPPI hardware currently supports only 800 Mbits/second. It is the application's responsibility to set this correctly.

27

anything

0 / 1

It is the application's responsibility to set the direction bit correctly.

26:25

anything

00 / 01/11

All addressing schemes are supported.

24

anything

0 / 1

It is the application's responsibility to set the camp-on bit correctly.

23:0

anything

anything

All addressing schemes are supported.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • The application has not disconnected from a long-term connection that was established with HIPIOCW_CONNECT prior to this request. (If no data has ever been sent, the connection is not necessarily open at the physical layer.)

HIPIOCW_D1_SIZE

HIPIOCW_D1_SIZE is used to set the size of the D1_Area and set the P-bit in a HIPPI-FP FDO. This call specifies a D1 area size that is placed in the FP header of all subsequently transmitted packets.

This call has the following characteristics:

  • The size must be zero or a multiple of 8.

  • When the D1 area size is greater than 0, the P-bit in the FP header is set to 1.

To send its D1 data, the application can concatenate the D2 data to the D1 data so that the first burst contains both kinds of data, or it can use HIPIOCW_SHBURST to place only the FP header and the D1 data in the first burst. The HIPPI subsystem uses all of this information to correctly calculate the values for the FP header, as explained in “How HIPPI Protocol Items Are Handled With the HIPPI-FP Access Method”.

Usage

Transmission for HIPPI-FP.

ioctl (fd_hippi#, HIPIOCW_D1_SIZE, bytecount);

The arg

The bytecount is the size in bytes to be placed in the D1_Area_Size field of the HIPPI-FP header of subsequent packets. Valid sizes fall within the range of 0-1016 (decimal), inclusive, and must be evenly divisible by 8.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • The bound FDO is HIPPI-PH.

  • The bytecount is not valid.

HIPIOCW_DISCONN

HIPIOCW_DISCONN is used for terminating a permanent connection that was opened with the HIPIOCW_CONNECT call. This call causes the HIPPI subsystem to tear down the connection immediately.


Note: To terminate a packet without tearing down the connection, use HIPIOCW_END_PKT.

Usage

Transmission for HIPPI-FP and HIPPI-PH.

ioctl (fd_hippi#, HIPIOCW_DISCONN);

The arg

There is no arg for this call.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • No long-term (permanent) connection has been set up; there is nothing to disconnect.

HIPIOCW_END_PKT

HIPIOCW_END_PKT terminates the current packet (that is, causes the HIPPI subsystem to drive the PACKET signal false). This call is required only when the packet length was specified as infinite.

Usage

Transmission for HIPPI-FP and HIPPI-PH.

ioctl (fd_hippi#, HIPIOCW_END_PKT);

The arg

There is no arg for this call.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • There is no inprogress packet; that is, this call has not been preceded by a HIPIOCW_START_PKT call.

HIPIOCW_ERR

HIPIOCW_ERR returns the error status from the last write() call for the indicated file descriptor.

Usage

Error monitoring for transmission with HIPPI-FP and HIPPI-PH.

error = ioctl (fd_hippi#, HIPIOCW_ERR);

The arg

There is no arg for this call.

Returned Value

The returned error is an integer, as summarized in Table 2-7.  

Table 2-7. Errors for Failed write() Calls

Hex Value

Error

0

HIP_SRCERR_NONE: No error occurred on last write().

1

HIP_SRCERR_SEQ: Source sequence error.

2

HIP_SRCERR_DSIC: Source lost DSIC error.

3

HIP_SRCERR_TIMEO: Source timed out connection.

4

HIP_SRCERR_CONNLS: Source lost inbound CONNECT signal during transmission.

5

HIP_SRCERR_REJ: Source's connection REQUEST was rejected.

6

HIP_SRCERR_SHUT: Interface is shut down.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

HIPIOCW_I

HIPIOCW_I prepares the HIPPI subsystem to set up a single-packet connection. The command specifies a new value for the HIPPI I-field in the application's FDO. (The I-field is also known as CCI.) The HIPPI subsystem uses this value as the I-field for all subsequent connection requests (that is, at each write call), until HIPIOCW_I is called again. The HIPPI subsystem does not alter or interpret the I-field contents. The HIPPI subsystem drops each connection as soon as the data from the write() call is sent.


Note: For a long-term (many-packet) connection, use the HIPIOCW_CONNECT call.

Usage

Transmission for HIPPI-PH and HIPPI-FP.

ioctl (fd_hippi#, HIPIOCW_I, I-fieldValue);

The arg

The I-fieldValue is a 32-bit number. IRIS HIPPI does not verify, alter, or interpret the I-field value.

For a HIPPI-SC compliant I-field, bit 31 of the I-field must be set to 0 and the remaining bits (30:0) must be partitioned into fields, as summarized in Table 2-6. (For more details about the I-field, see Figure A-2.)

“Locally-administered” schemes are legal and supported. For a locally-administered scheme, bit 31 must be set to 1 and bits 30:0 can be set to comply with any locally-defined protocol or can be set to zero (for example, I-field value = 80000000 hex).


Note: Using a “locally-administered” I-field severely limits interoperability, especially in the areas of routing and HIPPI switch control.

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

HIPIOCW_SHBURST

HIPIOCW_SHBURST defines the size of the first burst for all subsequent packets. The size may be shorter than a standard burst, or full-sized. The IRIS HIPPI subsystem's functionality is slightly different for HIPPI-PH and HIPPI-FP applications, as explained below.


Note: If the first burst is short, it is the responsibility of the application to pad out the D2 data to a multiple of 256 words, so that all the non-first bursts are full-sized. The IRIS HIPPI software does not verify the data size nor pad the final burst.

For a HIPPI-PH application, the call causes the HIPPI subsystem to “break off” the indicated number of bytes from the data provided by the first write() call, and send these bytes as the first burst. When the desired first burst consists of 256 words, it is not necessary to make this call. When HIPIOCW_SHBURST is called with a bytecount of 0, the IRIS HIPPI subsystem creates standard-sized first bursts.

For a HIPPI-FP application, the call causes the IRIS HIPPI subsystem to create a first burst that contains only the FP header and D1 data and to set the B-bit in the FP header. When HIPIOCW_SHBURST is called with the following bytecounts, the first burst is created as described:

  • With a bytecount of 0, the first burst is standard-sized and contains the FP header and 1016 bytes of data from the write() call. The B-bit is set to 0.

  • With a bytecount of 8, the first burst is short and contains only the FP header. The B-bit is set to 1.

  • When the bytecount is larger than 8 but smaller than 1024, the first burst is short; it contains 8 bytes of FP header and [bytecount minus 8] of D1 data. The HIPPI subsystem “breaks off” the D1 data bytes from the data provided with the first write() call. The B-bit is set to 1.


    Note: When D1 data is included, it is the application's responsibility to also call HIPIOCW_D1_SIZE to ensure a properly filled–in FP header.


  • When the bytecount is 1024, the first burst is standard-sized; it contains 8 bytes of FP header and 1016 bytes of D1 data. The HIPPI subsystem “breaks off” the D1 data bytes from the data provided with the first write() call. The B-bit is set to 1.

Usage

Transmission of multiple-write packets for HIPPI-FP and HIPPI-PH. Once called, the setting applies to all packets, until called again.

ioctl (fd_hippi#, HIPIOCW_SHBURST, bytecount);

The arg

For HIPPI-PH, the bytecount can be any value from 0-1024 decimal (inclusive) that is evenly divisible by 8.

For HIPPI-FP, the bytecount can be any value from 0-1024 decimal (inclusive) that is evenly divisible by 8. The minimum bytecount for a short first burst is 8 (that is, large enough to include the FP header) and, if HIPIOCW_D1_SIZE has been called, it must be [8 + D1_Area_Size].

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • The packet has not been setup as a multiple-write packet, using the HIPIOCW_START_PKT command.

  • The size of bytecount is not valid.

HIPIOCW_START_PKT

HIPIOCW_START_PKT controls the HIPPI subsystem's PACKET signal. The signal is held high (PACKET = true) for the bytecount provided in the call's argument (or for HIPPI-FP, the bytecount plus 8, thus including the FP header). The bytecount should be so large that a number of write() calls are required to send it. This call must be made for each multiple-write packet.

Usage

Transmission for HIPPI-FP and HIPPI-PH.

ioctl (fd_hippi#, HIPIOCW_START_PKT, bytecount);

The arg

The bytecount is either the actual bytecount of the D1 and D2 areas of the packet or a value indicating “infinite.” (Infinite packets are supported only when the connection is permanent or long-term.)

  • The range of valid values for an actual bytecount is multiples of 8 between 0 and 0xFFFFFFF8 hexadecimal, inclusive. The maximum actual length for any packet is 4 gigabytes less 8 bytes.

  • An “infinite” or indeterminate packet is defined by a bytecount of HIPPI_D2SIZE_INFINITY (which is 0xFFFFFFFF).

Failures and Errors

This call fails for the following reasons:

  • The application is not bound.

  • A packet is currently in progress. For example, for an infinite packet, the HIPIOCW_END_PKT call has not terminated the current packet.

HIPPI_SETONOFF

HIPPI_SETONOFF does shutdown and bringup of the IRIS HIPPI board. ON (bringup) initializes everything on the board, leaving the board in the UP state. OFF (shutdown) completes inprogress work with errors, turns everything off, resets the onboard CPU, and transitions to the DOWN state. This command is intended for administration and maintenance purposes only; hence, it is only available to superuser (root).

Usage

Board shutdown and bringup. Only available to superuser (root).

ioctl (fd_hippi#, HIPPI_SETONOFF, arg);

The arg

The arg is 1 for ON (bringup) and 0 for OFF (shutdown). Multiple, sequential calls for OFF while the board is down results in multiple resets of the board's CPU, as described in Table 2-8.

Table 2-8. Actions Caused by HIPPI_SETONOFF

 

Board = DOWN

Board = UP

Command = OFF (0)

reset onboard CPU

shutdown, which includes CPU reset

Command = ON (1)

bringup

error

Failures and Errors

This call fails for the following reasons:

  • The application is not superuser (root).

  • The file descriptor is bound. Closing the file descriptor will unbind it.

  • For ON, there are other open (cloned) file descriptors that must be closed before the board can be brought up.