Home | History | Annotate | Download | only in sockfs
      1 /*
      2  * CDDL HEADER START
      3  *
      4  * The contents of this file are subject to the terms of the
      5  * Common Development and Distribution License (the "License").
      6  * You may not use this file except in compliance with the License.
      7  *
      8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
      9  * or http://www.opensolaris.org/os/licensing.
     10  * See the License for the specific language governing permissions
     11  * and limitations under the License.
     12  *
     13  * When distributing Covered Code, include this CDDL HEADER in each
     14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
     15  * If applicable, add the following below this CDDL HEADER, with the
     16  * fields enclosed by brackets "[]" replaced with your own identifying
     17  * information: Portions Copyright [yyyy] [name of copyright owner]
     18  *
     19  * CDDL HEADER END
     20  */
     21 
     22 /*
     23  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
     24  * Use is subject to license terms.
     25  */
     26 
     27 #ifndef _SOCKFS_SOCKTPI_H
     28 #define	_SOCKFS_SOCKTPI_H
     29 
     30 #include <inet/kssl/ksslapi.h>
     31 
     32 #ifdef	__cplusplus
     33 extern "C" {
     34 #endif
     35 
     36 /*
     37  * Internal representation used for addresses.
     38  */
     39 struct soaddr {
     40 	struct sockaddr	*soa_sa;	/* Actual address */
     41 	t_uscalar_t	soa_len;	/* Length in bytes for kmem_free */
     42 	t_uscalar_t	soa_maxlen;	/* Allocated length */
     43 };
     44 /* Maximum size address for transports that have ADDR_size == 1 */
     45 #define	SOA_DEFSIZE	128
     46 
     47 struct sonode;
     48 
     49 /*
     50  * TPI Sockets
     51  * ======================
     52  *
     53  * A TPI socket can be created by the TPI socket module, or as a
     54  * result of fallback. In either case, the TPI related information is
     55  * stored in a sotpi_info_t. Sockets that are TPI based from the
     56  * beginning will use a sotpi_sonode_t, but fallback case the
     57  * sotpi_info_t will be allocated when needed. However, the so_priv
     58  * field in the sonode will always point to the sotpi_info_t, and the
     59  * structure should only be accessed via so_priv. Use SOTOTPI().
     60  *
     61  * A TPI socket always corresponds to a VCHR stream representing the
     62  * transport provider (e.g. /dev/tcp). This information is retrieved
     63  * from the kernel socket configuration table and accessible via
     64  * so_sockparams->sp_sdev_info.  sockfs uses this to perform
     65  * VOP_ACCESS checks before allowing an open of the transport
     66  * provider.
     67  *
     68  * AF_UNIX Sockets
     69  * -------------------------
     70  *
     71  * When an AF_UNIX socket is bound to a pathname the sockfs creates a
     72  * VSOCK vnode in the underlying file system. However, the vnodeops
     73  * etc in this VNODE remain those of the underlying file system.
     74  * Sockfs uses the v_stream pointer in the underlying file system
     75  * VSOCK node to find the sonode bound to the pathname. The bound
     76  * pathname vnode is accessed through sti_ux_vp.
     77  *
     78  * Out of Band Data Handling
     79  * -------------------------
     80  *
     81  * The counts (sti_oobcnt and sti_oobsigcnt) track the number of
     82  * urgent indicates that are (logically) queued on the stream head
     83  * read queue. The urgent data is queued on the stream head
     84  * as follows.
     85  *
     86  * In the normal case the SIGURG is not generated until
     87  * the T_EXDATA_IND arrives at the stream head. However, transports
     88  * that have an early indication that urgent data is pending
     89  * (e.g. TCP receiving a "new" urgent pointer value) can send up
     90  * an M_PCPROTO/SIGURG message to generate the signal early.
     91  *
     92  * The mark is indicated by either:
     93  *  - a T_EXDATA_IND (with no M_DATA b_cont) with MSGMARK set.
     94  *    When this message is consumed by sorecvmsg the socket layer
     95  *    sets SS_RCVATMARK until data has been consumed past the mark.
     96  *  - a message with MSGMARKNEXT set (indicating that the
     97  *    first byte of the next message constitutes the mark). When
     98  *    the last byte of the MSGMARKNEXT message is consumed in
     99  *    the stream head the stream head sets STRATMARK. This flag
    100  *    is cleared when at least one byte is read. (Note that
    101  *    the MSGMARKNEXT messages can be of zero length when there
    102  *    is no previous data to which the marknext can be attached.)
    103  *
    104  * While the T_EXDATA_IND method is the common case which is used
    105  * with all TPI transports, the MSGMARKNEXT method is needed to
    106  * indicate the mark when e.g. the TCP urgent byte has not been
    107  * received yet but the TCP urgent pointer has made TCP generate
    108  * the M_PCSIG/SIGURG.
    109  *
    110  * The signal (the M_PCSIG carrying the SIGURG) and the mark
    111  * indication can not be delivered as a single message, since
    112  * the signal should be delivered as high priority and any mark
    113  * indication must flow with the data. This implies that immediately
    114  * when the SIGURG has been delivered if the stream head queue is
    115  * empty it is impossible to determine if this will be the position
    116  * of the mark. This race condition is resolved by using MSGNOTMARKNEXT
    117  * messages and the STRNOTATMARK flag in the stream head. The
    118  * SIOCATMARK code calls the stream head to wait for either a
    119  * non-empty queue or one of the STR*ATMARK flags being set.
    120  * This implies that any transport that is sending M_PCSIG(SIGURG)
    121  * should send the appropriate MSGNOTMARKNEXT message (which can be
    122  * zero length) after sending an M_PCSIG to prevent SIOCATMARK
    123  * from sleeping unnecessarily.
    124  */
    125 
    126 #define	SOTPI_INFO_MAGIC	0x12345678
    127 
    128 /*
    129  * Information used by TPI/STREAMS sockets
    130  */
    131 typedef struct sotpi_info {
    132 	/*
    133 	 * These fields are initialized once.
    134 	 */
    135 	uint32_t	sti_magic;	/* always set to SOTPI_INFO_MAGIC */
    136 	dev_t		sti_dev;	/* device the sonode represents */
    137 
    138 	struct sockparams *sti_orig_sp;	/* in case of fallback; the orig sp */
    139 
    140 	kmutex_t	sti_plumb_lock;	/* serializes plumbs, and the related */
    141 					/* so_pushcnt */
    142 	short		sti_pushcnt;	/* Number of modules above "sockmod" */
    143 
    144 	kcondvar_t	sti_ack_cv;	/* wait for TPI acks */
    145 
    146 	uint8_t
    147 		sti_laddr_valid : 1,	/* sti_laddr valid for user */
    148 		sti_faddr_valid : 1,	/* sti_faddr valid for user */
    149 		sti_faddr_noxlate : 1,	/* No xlation of faddr for AF_UNIX */
    150 
    151 		sti_direct : 1,		/* transport is directly below */
    152 
    153 		sti_pad_to_bit7 : 4;
    154 
    155 	mblk_t	*sti_ack_mp;		/* TPI ack received from below */
    156 	mblk_t	*sti_unbind_mp;		/* Preallocated T_UNBIND_REQ message */
    157 
    158 	time_t  sti_atime;		/* time of last access */
    159 	time_t  sti_mtime;		/* time of last modification */
    160 	time_t  sti_ctime;		/* time of last attributes change */
    161 
    162 	ushort_t sti_delayed_error;	/* From T_uderror_ind */
    163 	mblk_t	*sti_eaddr_mp;		/* for so_delayed_error */
    164 					/* put here for delayed processing  */
    165 
    166 	mblk_t	*sti_conn_ind_head;	/* b_next list of T_CONN_IND */
    167 	mblk_t	*sti_conn_ind_tail;
    168 
    169 	uint_t	sti_oobsigcnt;		/* Number of SIGURG generated */
    170 	uint_t	sti_oobcnt;		/* Number of T_EXDATA_IND queued */
    171 
    172 	/* From T_info_ack */
    173 	t_uscalar_t	sti_tsdu_size;
    174 	t_uscalar_t	sti_etsdu_size;
    175 	t_scalar_t	sti_addr_size;
    176 	t_uscalar_t	sti_opt_size;
    177 	t_uscalar_t	sti_tidu_size;
    178 	t_scalar_t	sti_serv_type;
    179 
    180 	/* From T_capability_ack */
    181 	t_uscalar_t	sti_acceptor_id;
    182 
    183 	/* Internal provider information */
    184 	struct tpi_provinfo	*sti_provinfo;
    185 
    186 	/*
    187 	 * The local and remote addresses have multiple purposes
    188 	 * but one of the key reasons for their existence and careful
    189 	 * tracking in sockfs is to support getsockname and getpeername
    190 	 * when the transport does not handle the TI_GET*NAME ioctls
    191 	 * and caching when it does (signalled by valid bits in so_state).
    192 	 * When all transports support the new TPI (with T_ADDR_REQ)
    193 	 * we can revisit this code.
    194 	 *
    195 	 * The other usage of sti_faddr is to keep the "connected to"
    196 	 * address for datagram sockets.
    197 	 *
    198 	 * Finally, for AF_UNIX both local and remote addresses are used
    199 	 * to record the sockaddr_un since we use a separate namespace
    200 	 * in the loopback transport.
    201 	 */
    202 	struct soaddr sti_laddr;	/* Local address */
    203 	struct soaddr sti_faddr;	/* Peer address */
    204 #define	sti_laddr_sa		sti_laddr.soa_sa
    205 #define	sti_faddr_sa		sti_faddr.soa_sa
    206 #define	sti_laddr_len		sti_laddr.soa_len
    207 #define	sti_faddr_len		sti_faddr.soa_len
    208 #define	sti_laddr_maxlen	sti_laddr.soa_maxlen
    209 #define	sti_faddr_maxlen	sti_faddr.soa_maxlen
    210 
    211 	/*
    212 	 * For AF_UNIX sockets:
    213 	 *
    214 	 * sti_ux_laddr/faddr records the internal addresses used with the
    215 	 * transport. sti_ux_vp and v_stream->sd_vnode form the
    216 	 * cross-linkage between the underlying fs vnode corresponding
    217 	 * to the bound sockaddr_un and the socket node.
    218 	 */
    219 	struct so_ux_addr sti_ux_laddr; /* laddr bound with the transport */
    220 	struct so_ux_addr sti_ux_faddr; /* temporary peer address */
    221 	struct vnode	*sti_ux_bound_vp; /* bound AF_UNIX file system vnode */
    222 	struct sonode	*sti_next_so; 	/* next sonode on socklist	*/
    223 	struct sonode	*sti_prev_so;	/* previous sonode on socklist	*/
    224 	mblk_t	*sti_discon_ind_mp;	/* T_DISCON_IND received from below */
    225 
    226 	/*
    227 	 * For NL7C sockets:
    228 	 *
    229 	 * sti_nl7c_flags	the NL7C state of URL processing.
    230 	 *
    231 	 * sti_nl7c_rcv_mp	mblk_t chain of already received data to be
    232 	 *			passed up to the app after NL7C gives up on
    233 	 *			a socket.
    234 	 *
    235 	 * sti_nl7c_rcv_rval	returned rval for last mblk_t from above.
    236 	 *
    237 	 * sti_nl7c_uri		the URI currently being processed.
    238 	 *
    239 	 * sti_nl7c_rtime	URI request gethrestime_sec().
    240 	 *
    241 	 * sti_nl7c_addr	pointer returned by nl7c_addr_lookup().
    242 	 */
    243 	uint64_t	sti_nl7c_flags;
    244 	mblk_t		*sti_nl7c_rcv_mp;
    245 	int64_t		sti_nl7c_rcv_rval;
    246 	void		*sti_nl7c_uri;
    247 	time_t		sti_nl7c_rtime;
    248 	void		*sti_nl7c_addr;
    249 
    250 	/* For sockets acting as an in-kernel SSL proxy */
    251 	kssl_endpt_type_t	sti_kssl_type;	/* is proxy/is proxied/none */
    252 	kssl_ent_t		sti_kssl_ent;	/* SSL config entry */
    253 	kssl_ctx_t		sti_kssl_ctx;	/* SSL session context */
    254 
    255 	/*
    256 	 * The mblks below are only allocated and used during fallback.
    257 	 */
    258 	mblk_t	*sti_exdata_mp;		/* T_EXDATA_IND or SIGURG */
    259 	mblk_t	*sti_urgmark_mp;	/* mark indication */
    260 } sotpi_info_t;
    261 
    262 struct T_capability_ack;
    263 
    264 extern sonodeops_t sotpi_sonodeops;
    265 
    266 extern int	socktpi_init(void);
    267 extern int	sotpi_convert_sonode(struct sonode *, struct sockparams *,
    268 		    boolean_t *, queue_t **, struct cred *);
    269 extern void	sotpi_revert_sonode(struct sonode *, struct cred *);
    270 extern void	sotpi_update_state(struct sonode *, struct T_capability_ack *,
    271 		    struct sockaddr *, socklen_t, struct sockaddr *, socklen_t,
    272 		    short);
    273 
    274 extern sotpi_info_t 	*sotpi_sototpi(struct sonode *);
    275 #ifdef DEBUG
    276 #define	SOTOTPI(so)	(sotpi_sototpi(so))
    277 #else
    278 #define	SOTOTPI(so)	((sotpi_info_t *)(so)->so_priv)
    279 #endif
    280 
    281 /* for consumers outside sockfs */
    282 #define	_SOTOTPI(so)	((sotpi_info_t *)(so)->so_priv)
    283 
    284 #ifdef	__cplusplus
    285 }
    286 #endif
    287 
    288 #endif /* _SOCKFS_SOCKTPI_H */
    289