1a9643ea8Slogwang /*- 2a9643ea8Slogwang * Copyright (c) 1996 John S. Dyson 3a9643ea8Slogwang * All rights reserved. 4a9643ea8Slogwang * 5a9643ea8Slogwang * Redistribution and use in source and binary forms, with or without 6a9643ea8Slogwang * modification, are permitted provided that the following conditions 7a9643ea8Slogwang * are met: 8a9643ea8Slogwang * 1. Redistributions of source code must retain the above copyright 9a9643ea8Slogwang * notice immediately at the beginning of the file, without modification, 10a9643ea8Slogwang * this list of conditions, and the following disclaimer. 11a9643ea8Slogwang * 2. Redistributions in binary form must reproduce the above copyright 12a9643ea8Slogwang * notice, this list of conditions and the following disclaimer in the 13a9643ea8Slogwang * documentation and/or other materials provided with the distribution. 14a9643ea8Slogwang * 3. Absolutely no warranty of function or purpose is made by the author 15a9643ea8Slogwang * John S. Dyson. 16a9643ea8Slogwang * 4. This work was done expressly for inclusion into FreeBSD. Other use 17a9643ea8Slogwang * is allowed if this notation is included. 18a9643ea8Slogwang * 5. Modifications may be freely made to this file if the above conditions 19a9643ea8Slogwang * are met. 20a9643ea8Slogwang * 21a9643ea8Slogwang * $FreeBSD$ 22a9643ea8Slogwang */ 23a9643ea8Slogwang 24a9643ea8Slogwang #ifndef _SYS_PIPE_H_ 25a9643ea8Slogwang #define _SYS_PIPE_H_ 26a9643ea8Slogwang 27a9643ea8Slogwang #ifndef _KERNEL 28*22ce4affSfengbojiang #error "no user-serviceable parts inside" 29a9643ea8Slogwang #endif 30a9643ea8Slogwang 31a9643ea8Slogwang /* 32a9643ea8Slogwang * Pipe buffer size, keep moderate in value, pipes take kva space. 33a9643ea8Slogwang */ 34a9643ea8Slogwang #ifndef PIPE_SIZE 35a9643ea8Slogwang #define PIPE_SIZE 16384 36a9643ea8Slogwang #endif 37a9643ea8Slogwang 38a9643ea8Slogwang #ifndef BIG_PIPE_SIZE 39a9643ea8Slogwang #define BIG_PIPE_SIZE (64*1024) 40a9643ea8Slogwang #endif 41a9643ea8Slogwang 42a9643ea8Slogwang #ifndef SMALL_PIPE_SIZE 43a9643ea8Slogwang #define SMALL_PIPE_SIZE PAGE_SIZE 44a9643ea8Slogwang #endif 45a9643ea8Slogwang 46a9643ea8Slogwang /* 47a9643ea8Slogwang * PIPE_MINDIRECT MUST be smaller than PIPE_SIZE and MUST be bigger 48a9643ea8Slogwang * than PIPE_BUF. 49a9643ea8Slogwang */ 50a9643ea8Slogwang #ifndef PIPE_MINDIRECT 51a9643ea8Slogwang #define PIPE_MINDIRECT 8192 52a9643ea8Slogwang #endif 53a9643ea8Slogwang 54a9643ea8Slogwang #define PIPENPAGES (BIG_PIPE_SIZE / PAGE_SIZE + 1) 55a9643ea8Slogwang 56a9643ea8Slogwang /* 57a9643ea8Slogwang * See sys_pipe.c for info on what these limits mean. 58a9643ea8Slogwang */ 59a9643ea8Slogwang extern long maxpipekva; 60a9643ea8Slogwang extern struct fileops pipeops; 61a9643ea8Slogwang 62a9643ea8Slogwang /* 63a9643ea8Slogwang * Pipe buffer information. 64a9643ea8Slogwang * Separate in, out, cnt are used to simplify calculations. 65a9643ea8Slogwang * Buffered write is active when the buffer.cnt field is set. 66a9643ea8Slogwang */ 67a9643ea8Slogwang struct pipebuf { 68a9643ea8Slogwang u_int cnt; /* number of chars currently in buffer */ 69a9643ea8Slogwang u_int in; /* in pointer */ 70a9643ea8Slogwang u_int out; /* out pointer */ 71a9643ea8Slogwang u_int size; /* size of buffer */ 72a9643ea8Slogwang caddr_t buffer; /* kva of buffer */ 73a9643ea8Slogwang }; 74a9643ea8Slogwang 75a9643ea8Slogwang /* 76a9643ea8Slogwang * Information to support direct transfers between processes for pipes. 77a9643ea8Slogwang */ 78a9643ea8Slogwang struct pipemapping { 79a9643ea8Slogwang vm_size_t cnt; /* number of chars in buffer */ 80a9643ea8Slogwang vm_size_t pos; /* current position of transfer */ 81a9643ea8Slogwang int npages; /* number of pages */ 82a9643ea8Slogwang vm_page_t ms[PIPENPAGES]; /* pages in source process */ 83a9643ea8Slogwang }; 84a9643ea8Slogwang 85a9643ea8Slogwang /* 86a9643ea8Slogwang * Bits in pipe_state. 87a9643ea8Slogwang */ 88a9643ea8Slogwang #define PIPE_ASYNC 0x004 /* Async? I/O. */ 89a9643ea8Slogwang #define PIPE_WANTR 0x008 /* Reader wants some characters. */ 90a9643ea8Slogwang #define PIPE_WANTW 0x010 /* Writer wants space to put characters. */ 91a9643ea8Slogwang #define PIPE_WANT 0x020 /* Pipe is wanted to be run-down. */ 92a9643ea8Slogwang #define PIPE_SEL 0x040 /* Pipe has a select active. */ 93a9643ea8Slogwang #define PIPE_EOF 0x080 /* Pipe is in EOF condition. */ 94a9643ea8Slogwang #define PIPE_LOCKFL 0x100 /* Process has exclusive access to pointers/data. */ 95a9643ea8Slogwang #define PIPE_LWANT 0x200 /* Process wants exclusive access to pointers/data. */ 96a9643ea8Slogwang #define PIPE_DIRECTW 0x400 /* Pipe direct write active. */ 97a9643ea8Slogwang #define PIPE_DIRECTOK 0x800 /* Direct mode ok. */ 98*22ce4affSfengbojiang 99*22ce4affSfengbojiang /* 100*22ce4affSfengbojiang * Bits in pipe_type. 101*22ce4affSfengbojiang */ 102*22ce4affSfengbojiang #define PIPE_TYPE_NAMED 0x001 /* Is a named pipe. */ 103a9643ea8Slogwang 104a9643ea8Slogwang /* 105a9643ea8Slogwang * Per-pipe data structure. 106a9643ea8Slogwang * Two of these are linked together to produce bi-directional pipes. 107a9643ea8Slogwang */ 108a9643ea8Slogwang struct pipe { 109a9643ea8Slogwang struct pipebuf pipe_buffer; /* data storage */ 110*22ce4affSfengbojiang struct pipemapping pipe_pages; /* wired pages for direct I/O */ 111a9643ea8Slogwang struct selinfo pipe_sel; /* for compat with select */ 112a9643ea8Slogwang struct timespec pipe_atime; /* time of last access */ 113a9643ea8Slogwang struct timespec pipe_mtime; /* time of last modify */ 114a9643ea8Slogwang struct timespec pipe_ctime; /* time of status change */ 115a9643ea8Slogwang struct sigio *pipe_sigio; /* information for async I/O */ 116a9643ea8Slogwang struct pipe *pipe_peer; /* link with other direction */ 117a9643ea8Slogwang struct pipepair *pipe_pair; /* container structure pointer */ 118*22ce4affSfengbojiang u_short pipe_state; /* pipe status info */ 119*22ce4affSfengbojiang u_char pipe_type; /* pipe type info */ 120*22ce4affSfengbojiang u_char pipe_present; /* still present? */ 121*22ce4affSfengbojiang int pipe_waiters; /* pipelock waiters */ 122a9643ea8Slogwang int pipe_busy; /* busy flag, mostly to handle rundown sanely */ 123a9643ea8Slogwang int pipe_wgen; /* writer generation for named pipe */ 124a9643ea8Slogwang ino_t pipe_ino; /* fake inode for stat(2) */ 125a9643ea8Slogwang }; 126a9643ea8Slogwang 127a9643ea8Slogwang /* 128a9643ea8Slogwang * Values for the pipe_present. 129a9643ea8Slogwang */ 130a9643ea8Slogwang #define PIPE_ACTIVE 1 131a9643ea8Slogwang #define PIPE_CLOSING 2 132a9643ea8Slogwang #define PIPE_FINALIZED 3 133a9643ea8Slogwang 134a9643ea8Slogwang /* 135a9643ea8Slogwang * Container structure to hold the two pipe endpoints, mutex, and label 136a9643ea8Slogwang * pointer. 137a9643ea8Slogwang */ 138a9643ea8Slogwang struct pipepair { 139a9643ea8Slogwang struct pipe pp_rpipe; 140a9643ea8Slogwang struct pipe pp_wpipe; 141a9643ea8Slogwang struct mtx pp_mtx; 142a9643ea8Slogwang struct label *pp_label; 143a9643ea8Slogwang }; 144a9643ea8Slogwang 145a9643ea8Slogwang #define PIPE_MTX(pipe) (&(pipe)->pipe_pair->pp_mtx) 146a9643ea8Slogwang #define PIPE_LOCK(pipe) mtx_lock(PIPE_MTX(pipe)) 147a9643ea8Slogwang #define PIPE_UNLOCK(pipe) mtx_unlock(PIPE_MTX(pipe)) 148a9643ea8Slogwang #define PIPE_LOCK_ASSERT(pipe, type) mtx_assert(PIPE_MTX(pipe), (type)) 149a9643ea8Slogwang 150a9643ea8Slogwang void pipe_dtor(struct pipe *dpipe); 151*22ce4affSfengbojiang int pipe_named_ctor(struct pipe **ppipe, struct thread *td); 152a9643ea8Slogwang void pipeselwakeup(struct pipe *cpipe); 153a9643ea8Slogwang #endif /* !_SYS_PIPE_H_ */ 154