Museum

Home

Lab Overview

Retrotechnology Articles

Online Manuals

⇒ appletalk(7) — A/UX 0.7

Media Vault

Software Library

Restoration Projects

Artifacts Sought

Related Articles

creat(2)

open(2)

dup(2)

fcntl(2)



     appletalk(7)                                         appletalk(7)



     NAME
          appletalk - general AppleTalk socket interface

     DESCRIPTION
          This section describes particular special files and the
          general nature of the AppleTalk interface.

          The 254 special files /dev/appletalk/socket1 through
          /dev/appletalk/socket254 provide access to the 254 sockets
          that the AppleTalk DDP (DataGram Delivery Protocol) provides
          on each node.

          The AppleTalk I/O driver itself is accessed by the special
          file /dev/appletalk/control, socket 1 is accessed by
          /dev/appletalk/socket1, and so on.

          The standard system calls read(2) and write(2) are used to
          read and write DataGrams to and from sockets.

        Opening Sockets
              Sockets correspond one to one to Oreo files.  To open a
              socket, you open a file on the filename of the socket,
              for example:

              fildes = open("/dev/appletalk/socket1",1);

          However, in AppleTalk, there are two kinds of sockets.
          Static sockets and dynamic sockets. Static sockets are
          opened just as described above.  To open a dynamic socket,
          you must first ask the AppleTalk I/O driver to give you a
          random socket number. Once you have that socket number, you
          can use it to create the special file filename for opening
          the dynamic socket with.

          To open a dynamic socket, the following code can be used:

          int         control_file;
          int         socket_file;
          int         socket_number;
          char        buffer[64];

          control_file  = open("/dev/appletalk/control",0);
          ioctl(control_file,AT_GET_DYNAMIC_SOCKET,&socket_number);
          sprintf(buffer,"/dev/appletalk/socket%d",socket_number);
          socket_file = open(buffer,open_mode);

          The use of the ioctl(2) system call is explained later in
          the document.

        Open Errors
              [ENETDOWN]    The network is down.




     Page 1                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



              [ENOTCONN]    Dynamic open attempted on a socket that
                            was not previously the subject of an
                            ATGETDYNAMICSOCKET ioctl(2) system
                            call.

              [ENOTDIR]     A component of the path prefix is not a
                            directory.

              [ENOENT]      OCREAT is not set and the named file does
                            not exist.

              [EACCES]      A component of the path prefix denies
                            search permission.

              [EACCES]      Oflag permission is denied for the named
                            file.

              [EISDIR]      The named file is a directory and oflag is
                            write or read/write.

              [EEXIST]      The file is opened with the OCREAT
                            and OEXCL option and exists already.

              [EMFILE]      Twenty (20) file descriptors are currently
                            open.

              [ENXIO]       The named file is a character special or
                            block special file, and the device
                            associated with this special file does not
                            exist.

              [EFAULT]      Path points outside the allocated address
                            space of the process.

              [EINTR]       A signal was caught during the open system
                            call.

              [ENFILE]      The system file table is full.

              [EBUSY]       An already opened socket is being opened
                            again exclusively.

              [ENOTSOCK]    The file specified in the open system call
                            does not refer to a socket.


        ioctl(2) and DataGram control
        ioctl
          performs a variety of special functions on the AppleTalk I/O
          driver. The general format of an ioctl(2) system call is as
          follows:




     Page 2                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



          int   control_file;
          int   request;
          int   arg;

          control_file  = open("/dev/appletalk/control",0);
          ioctl(control_file,request,arg);

          fildes is the file descriptor obtained from a creat(2),
          open(2), dup(2), fcntl(2), or pipe(2) system call on an
          AppleTalk socket.

          request is the ioctl request type to the AppleTalk I/O
          driver.

        ioctl(2) Requests
          The following requests are supported. The value for each of
          the requests is defined in the appletalk.h header file.  For
          most of the requests, the file descriptor in the first
          argument should be for the AppleTalk control file.  Some of
          the requests are "special", in the sense that the file
          descriptor for those requests will be the file descriptor of
          a socket. Those requests determine in which mode the socket
          associated with the descriptor will be used, the default
          being the DDP (Datagram) mode. They are:

          AT_SET_DDP_PROTOCOL
               Sets the mode of a specific socket to be DDP. This
               socket can now only be used for receiving and sending
               datagrams on it.

          AT_SET_ATP_TREQ_PROTOCOL
               Sets the mode of a specific socket to be ATP Request.
               This socket can now only be used for sending ATP
               requests and for receiving ATP responses on it.

          AT_SET_ATP_TRES_PROTOCOL
               Sets the mode of a specific socket to be ATP Response.
               This socket can now only be used for receiving ATP
               requests and for sending ATP responses on it.

          Those modes affect the way in which the user can use the
          read and write system calls. See the description of those
          calls for the differences.

          The following requests are more general i.e. they are
          independent of the socket mode:

          FIONREAD
               See ``Pending DataGrams'' under ``Reading DataGrams''.

          AT_GET_CONFIGURATION
               Gets the configuration table from the I/O driver.  arg



     Page 3                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



               must be a pointer to an atcfg structure, as defined in
               appletalk.h.

          AT_GET_DYNAMIC_SOCKET
               Gets a dynamic socket number.  arg must be a pointer to
               an int data type.

          AT_RTMP_AGE_A_BRIDGE
               This call returns no value nor does it exppect a value.
               It ages the a bridge node address.  If no RTMP packet
               has been received from a bridge since this ioctl was
               issued last, the bridge address will be set to zero.

          AT_SET_CONFIGURATION
               Sets the configuration table in the I/O driver.  arg
               must be a pointer to an atcfg structure, as defined in
               appletalk.h.  The following fields from the atcfg
               structure are copied into appropriate values in the I/O
               driver:
                 at_cfg_initial_node_address
               \  at_cfg_rts_attempts
                  (only if non-zero)

          All others field in atcfg are ignored.

          AT_SHUTDOWN
               Shuts the network down.  All sockets become inoperative
               immediately.  The node address will still be defended
               though.

          AT_STARTUP
               Resets and starts up the net. All buffers, trace table,
               are reset. One needs to be superuser to perform this
               function.

          AT_TESTWRITE
               Internal debugging use. Do not use.

          AT_TRACEDUMP
               Internal debugging use. Do not use.

          AT__ Internal debugging use. Do not use.

        ioctl Errors
              [EALREADY]        An attempt was made to start a network
                                that is already up.

              [ENETDOWN]        A shutdown was attempted on a network
                                that was not started.

              [ECONNABORTED]    Attempted to AT_GET_DYNAMIC_SOCKET on
                                a non-zero minor number.  That is, the



     Page 4                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



                                ioctl(2) AT_GET_DYNAMIC_SOCKET
                                operation was attempted on a file
                                descriptor that was opened on a socket
                                rather than /dev/appletalk/control.

              [ENOTCONN]        No dynamic sockets are available. All
                                127 are already dynamically assigned.

              [EFAULT]          An illegal address was given for the
                                argument, or a non supported request
                                was specified.

              [EAFNOSUPPORT]    The initial node address specified
                                with the AT_SET_CONFIGURATION request
                                is out of range.

              [ENOTSOCK]        An illegal socket file descriptor was
                                specified with the AT_SET_*_PROTOCOL
                                request.

              [ENETRESET]       The network has gone down and has been
                                brought up again, so all previously
                                accessed sockets are now closed.

              [EACCES]          The user starting up the network or
                                resetting its configuration is not
                                superuser.

              [EINVAL]          An illegal value was specified for the
                                number of attempts with the
                                AT_SET_CONFIGURATION request.

        Reading DataGrams
              The data read from the socket is always the entire LAP
              packet.  Packets of types not corresponding to the
              socket protocol they are intended for get thrown away
              silently, e.g. from a socket with TReq protocol, only
              TReq packets can be read.  A read(2) system call will
              return the length of data read, from 3 bytes (minimum
              length of a LAP packet) to 603 bytes (maximum length of
              a LAP packet). If the LAP packet length is greater than
              the maximum length specified in the read(2) system call,
              the bytes not read from the LAP packet will be silently
              (i.e., no indication of error) thrown away.

              The read will always block until a packet is received
              for the socket.

        Reading Pending DataGrams
              The length of the next (if any) DataGram may be
              determined by using an ioctl(2) call as follows:




     Page 5                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



              int  status;
              int  next_datagram_length;

              status = ioctl(fildes,FIONREAD,&next_datagram_length);

          Where fildes is the file descriptor obtained from a
          creat(2), open(2), dup(2), fcntl(2), or pipe(2) system call,
          FIONREAD is a constant value defined in the include header
          file <sys/ioctl.h>, and iptr is a pointer to an int variable
          in which the number of bytes of the next DataGram to be read
          will be returned in. If no DataGram exists for the socket, a
          value of zero will be placed in iptr .

        Read Return Value
              Upon sucessful completion a non-negative integer is
              returned indicating the number of bytes actually read.
              Otherwise, a -1 is returned, and errno is set to
              indicate the error.

        Read Errors
              [EBADF]     The file descriptor is not valid or is not
                          open for reading.

              [EFAULT]    The buffer address to write is not a valid
                          logical address for the process

              [EINTR]     A signal was caught during the read(2)
                          system call.

              [ENOPROTOOPT]
                          A request was read from the socket, the user
                          is not responding to it but is trying to
                          read another request instead.

              [ENETDOWN]  The network is down.

        Writing DataGrams on a DDP socket
              The data written to the socket is the entire LAP packet.
              At least 3 bytes, (minimum length of a LAP packet), and
              no more than 603 bytes (maximum length of a LAP packet),
              may be written.

        Write Buffer Manipulation
              The following fields in the LAP packet and DataGram will
              be filled in by the Oreo driver:

              Source address with the current node number.

              DataGram length with the computed length.

              Source socket with the actual socket number.




     Page 6                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



              DDP checksum with checksum of the DataGram (extended DDP
              headers only). This will be optional in the next
              release, but the additional ioctl(2) system call
              definition didn't make it into this release.

              Source node with the current node number (extended DDP
              headers only).

              Source network number with the current network number
              (extended DDP headers only).

        Write Return Value
              Upon successful completion a non-negative integer is
              returned indicating the number of bytes written.
              Otherwise, a -1 is returned, and errno is set to
              indicate the error.

        Write Errors
              [EMSGSIZE]        The length of the packet is too small
                                (< 3) or too big (> 603).

              [EPROTOTYPE]      The packet is not a DDP packet (i.e.,
                                a value of 0x01 or 0x02 is not in the
                                3rd byte of the LAP header).

              [EBADF]           The file descriptor is not valid or is
                                not open for writing.

              [EFAULT ]         The buffer address to write is not a
                                valid logical address for the process.

              [ERANGE]          The length of the data being written
                                is less than 3 bytes or more than 603
                                bytes.

              [EINTR]           A signal was caught during the
                                write(2) system call.

              [EADDRNOTAVAIL]   The destination node number is 0.

              [ENOTSOCK]        The destination socket number is out
                                of range (<1 or >254).

              [EHOSTUNREACH]    The request to send was never
                                acknowledged; the destination node
                                went down or an invalid destination
                                address was specified.

        Writing Transaction Requests on a TReq socket
              The data written to the socket is a structure of the
              type atatpreq, as described in <appletalk.h>.  All
              fields of the structure must be filled in by the user,



     Page 7                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



              except for atatpreqtrespuserbytes,
              atatpreqtresplengths, atatpreqtrespeomseqno,
              atatpreqtrespbitmap, atatpreqtid and
              atatpreqgottrel.  The length specified to the write()
              call should be sizeof(atatpreq).

        Write Return Value
              Upon successful completion a non-negative integer is
              returned indicating the number of bytes written.
              Otherwise, a -1 is returned, and errno is set to
              indicate the error. The packets received in response to
              the request will be stored in the atatpreq structure.
              The user bytes will be stored in the
              atatpreqtrespuserbytes field, the data will be
              stored at the addresses provided by the user in the
              atatpreqtrespdata fields, and the lengths of the
              packets will be in the atatpreqtresplengths fields.
              The bitmap in the atatpreqtrespbitmap will indicate
              which packets were received, and the
              atatpreqtrespeomseqno field which packet is the last
              one.

        Write Errors
              [EBADF]           The file descriptor is not valid or is
                                not open for writing.

              [EFAULT ]         The address of the atatpreq
                                structure, or one of the addresses
                                specified in that structure is not a
                                valid logical address for the process.

              [ERANGE]          The length of the data to be written
                                as specified in the atatpreq
                                structure is out of range (> 578 or
                                <0).

              [EINVAL]          The length specified in the write()
                                call is not sizeof(atatpreq).

              [EINTR]           A signal was caught during the
                                write(2) system call.

              [EOPNOTSUPP]      The request type specified in the
                                atatpreq structure is not
                                AT_ATP_CMD_TREQ.

              [ENOSP]           There is no more internal buffer space
                                available.

              [EHOSTUNREACH]    The request to send was never
                                acknowledged; the destination node
                                went down or an invalid destination



     Page 8                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



                                address was specified.

              [ETIMEDOUT]       All response packets could not be
                                obtained within the time interval and
                                with the number of tries specified by
                                the user.

              [ENETDOWN]        The network is down.
          Writing Transaction Responses on a TResp socket
              The data written to the socket is a structure of the
              type atatpreq, as described in <appletalk.h>.  All
              fields of the structure must be filled in by the user,
              except for
              atatpreqtrequserbytes,atatpreqtreqdata,
              atatpreqtreqlength,
              atatpreqretrytimeout,atatpreqmaximumretries and
              atatpreqgottrel.  The length specified to the write()
              call should be sizeof(atatpreq).

        Write Return Value
              Upon successful completion a non-negative integer is
              returned indicating the number of bytes written.
              Otherwise, a -1 is returned, and errno is set to
              indicate the error. The atatpreqgottrel field will
              indicate (for an exactly_once transaction) whether a
              TRel packet was received from the requestor or whether a
              timeout occurred.

        Write Errors
              [EBADF]           The file descriptor is not valid or is
                                not open for writing.

              [EFAULT ]         The address of the atatpreq
                                structure, or one of the addresses
                                specified in that structure is not a
                                valid logical address for the process.

              [ERANGE]          The length of the data to be written
                                as specified in the atatpreq
                                structure is out of range (> 578 or
                                <0).

              [EINVAL]          The length specified in the write()
                                call is not sizeof(atatpreq).

              [EINTR]           A signal was caught during the
                                write(2) system call.

              [EOPNOTSUPP]      The request type specified in the
                                atatpreq structure is not
                                ATATPCMDTREQ.




     Page 9                                        (last mod. 1/15/87)





     appletalk(7)                                         appletalk(7)



              [ENOSP]           There is no more internal buffer space
                                available.

              [EHOSTUNREACH]    The request to send was never
                                acknowledged; the destination node
                                went down or an invalid destination
                                address was specified.

              [ECONNREFUSED]    A response is being written without
                                having read the request first.

              [ENETDOWN]        The network is down.

     EXAMPLE
          #include <stdio.h>

          #include "appletalk.h"

          main()
            {
            at_dg   datagram;
            int     i;
            int     fildes;
            int     length;

            datagram.lap.at_lap_dst_addr = 0x82;
            datagram.lap.at_lap_type = AT_LAP_TYPE_DDP_S_HDR;
            datagram.ddp.at_ddp_datagram_len = AT_DDP_DATA_MAX;
            for (i = 0;  i < AT_DDP_DATA_MAX;  i++)
                {
                datagram.buf[i] = 0x57;
                }
            fildes = open("/dev/appletalk/socket5",2);
            length = sizeof(at_lap_hdr) + sizeof(at_ddp_hdr) + AT_DDP_DATA_MAX;
            write(fildes,&datagram,length);
            }

     FILES
          /dev/appletalk/socket1
          /dev/appletalk/socket2
               ...     ...
               ...     ...
          /dev/appletalk/socket254

     SEE ALSO
          creat(2), open(2), dup(2), fcntl(2).









     Page 10                                       (last mod. 1/15/87)



Typewritten Software • bear@typewritten.org • Edmonds, WA 98026