Add UNIX Domain Sockets internals to PFS. Contributed by Thomas Cort
This commit is contained in:
parent
ecc8a52f82
commit
ea19830de1
18 changed files with 2949 additions and 76 deletions
|
@ -1,10 +1,11 @@
|
||||||
# Makefile for Pipe File System (PFS)
|
# Makefile for Pipe File System (PFS)
|
||||||
PROG= pfs
|
PROG= pfs
|
||||||
SRCS= open.c table.c inode.c main.c super.c link.c \
|
SRCS= open.c table.c inode.c main.c super.c link.c \
|
||||||
buffer.c read.c misc.c utility.c stadir.c
|
buffer.c read.c misc.c utility.c stadir.c \
|
||||||
|
uds.c dev_uds.c
|
||||||
|
|
||||||
DPADD+= ${LIBSYS}
|
DPADD+= ${LIBDRIVER} ${LIBSYS}
|
||||||
LDADD+= -lsys
|
LDADD+= -ldriver -lsys
|
||||||
|
|
||||||
MAN=
|
MAN=
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,11 @@
|
||||||
|
|
||||||
#define NR_INODES 256 /* # slots in "in core" inode table */
|
#define NR_INODES 256 /* # slots in "in core" inode table */
|
||||||
|
|
||||||
|
/* Size of descriptor table for unix domain sockets. This should be
|
||||||
|
* equal to the maximum number of minor devices (currently 256).
|
||||||
|
*/
|
||||||
|
#define NR_FDS 256
|
||||||
|
|
||||||
#define INODE_HASH_LOG2 7 /* 2 based logarithm of the inode hash size */
|
#define INODE_HASH_LOG2 7 /* 2 based logarithm of the inode hash size */
|
||||||
#define INODE_HASH_SIZE ((unsigned long)1<<INODE_HASH_LOG2)
|
#define INODE_HASH_SIZE ((unsigned long)1<<INODE_HASH_LOG2)
|
||||||
#define INODE_HASH_MASK (((unsigned long)1<<INODE_HASH_LOG2)-1)
|
#define INODE_HASH_MASK (((unsigned long)1<<INODE_HASH_LOG2)-1)
|
||||||
|
@ -31,5 +36,8 @@
|
||||||
#define FS_BITCHUNK_BITS (usizeof(bitchunk_t) * CHAR_BIT)
|
#define FS_BITCHUNK_BITS (usizeof(bitchunk_t) * CHAR_BIT)
|
||||||
#define FS_BITS_PER_BLOCK(b) (FS_BITMAP_CHUNKS(b) * FS_BITCHUNK_BITS)
|
#define FS_BITS_PER_BLOCK(b) (FS_BITMAP_CHUNKS(b) * FS_BITCHUNK_BITS)
|
||||||
|
|
||||||
|
#define FS_CALL_VEC_SIZE 31
|
||||||
|
#define DEV_CALL_VEC_SIZE 25
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
1191
servers/pfs/dev_uds.c
Normal file
1191
servers/pfs/dev_uds.c
Normal file
File diff suppressed because it is too large
Load diff
|
@ -15,6 +15,7 @@
|
||||||
#include <minix/const.h>
|
#include <minix/const.h>
|
||||||
#include <minix/type.h>
|
#include <minix/type.h>
|
||||||
#include <minix/dmap.h>
|
#include <minix/dmap.h>
|
||||||
|
#include <minix/vfsif.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <minix/syslib.h>
|
#include <minix/syslib.h>
|
||||||
|
|
|
@ -12,10 +12,8 @@
|
||||||
/* The following variables are used for returning results to the caller. */
|
/* The following variables are used for returning results to the caller. */
|
||||||
EXTERN int err_code; /* temporary storage for error number */
|
EXTERN int err_code; /* temporary storage for error number */
|
||||||
|
|
||||||
EXTERN _PROTOTYPE (int (*fs_call_vec[]), (void) ); /* fs call table */
|
EXTERN _PROTOTYPE (int (*fs_call_vec[]), (message *fs_m_in, message *fs_m_out) ); /* fs call table */
|
||||||
|
EXTERN _PROTOTYPE (int (*dev_call_vec[]), (message *fs_m_in, message *fs_m_out) ); /* dev call table */
|
||||||
EXTERN message fs_m_in;
|
|
||||||
EXTERN message fs_m_out;
|
|
||||||
|
|
||||||
EXTERN uid_t caller_uid;
|
EXTERN uid_t caller_uid;
|
||||||
EXTERN gid_t caller_gid;
|
EXTERN gid_t caller_gid;
|
||||||
|
|
|
@ -4,8 +4,13 @@
|
||||||
|
|
||||||
#define VERBOSE 0 /* display diagnostics */
|
#define VERBOSE 0 /* display diagnostics */
|
||||||
|
|
||||||
|
#include <net/ioctl.h>
|
||||||
|
|
||||||
#include <ansi.h>
|
#include <ansi.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
|
#include <sys/select.h>
|
||||||
|
#include <sys/socket.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <signal.h>
|
#include <signal.h>
|
||||||
|
@ -13,6 +18,7 @@
|
||||||
|
|
||||||
#include <minix/callnr.h>
|
#include <minix/callnr.h>
|
||||||
#include <minix/config.h>
|
#include <minix/config.h>
|
||||||
|
#include <minix/dmap.h>
|
||||||
#include <minix/type.h>
|
#include <minix/type.h>
|
||||||
#include <minix/const.h>
|
#include <minix/const.h>
|
||||||
#include <minix/com.h>
|
#include <minix/com.h>
|
||||||
|
|
|
@ -26,7 +26,7 @@ FORWARD _PROTOTYPE( void unhash_inode, (struct inode * const node) );
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* fs_putnode *
|
* fs_putnode *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int fs_putnode()
|
PUBLIC int fs_putnode(message *fs_m_in, message *fs_m_out)
|
||||||
{
|
{
|
||||||
/* Find the inode specified by the request message and decrease its counter.*/
|
/* Find the inode specified by the request message and decrease its counter.*/
|
||||||
|
|
||||||
|
@ -35,15 +35,15 @@ PUBLIC int fs_putnode()
|
||||||
dev_t dev;
|
dev_t dev;
|
||||||
ino_t inum;
|
ino_t inum;
|
||||||
|
|
||||||
rip = find_inode( (ino_t) fs_m_in.REQ_INODE_NR);
|
rip = find_inode( (ino_t) fs_m_in->REQ_INODE_NR);
|
||||||
|
|
||||||
if(!rip) {
|
if(!rip) {
|
||||||
printf("%s:%d put_inode: inode #%ld dev: %d not found\n", __FILE__,
|
printf("%s:%d put_inode: inode #%ld dev: %d not found\n", __FILE__,
|
||||||
__LINE__, fs_m_in.REQ_INODE_NR, (dev_t) fs_m_in.REQ_DEV);
|
__LINE__, fs_m_in->REQ_INODE_NR, (dev_t) fs_m_in->REQ_DEV);
|
||||||
panic("fs_putnode failed");
|
panic("fs_putnode failed");
|
||||||
}
|
}
|
||||||
|
|
||||||
count = fs_m_in.REQ_COUNT;
|
count = fs_m_in->REQ_COUNT;
|
||||||
if (count <= 0) {
|
if (count <= 0) {
|
||||||
printf("%s:%d put_inode: bad value for count: %d\n", __FILE__,
|
printf("%s:%d put_inode: bad value for count: %d\n", __FILE__,
|
||||||
__LINE__, count);
|
__LINE__, count);
|
||||||
|
|
|
@ -6,18 +6,18 @@
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* fs_ftrunc *
|
* fs_ftrunc *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int fs_ftrunc(void)
|
PUBLIC int fs_ftrunc(message *fs_m_in, message *fs_m_out)
|
||||||
{
|
{
|
||||||
struct inode *rip;
|
struct inode *rip;
|
||||||
off_t start, end;
|
off_t start, end;
|
||||||
ino_t inumb;
|
ino_t inumb;
|
||||||
|
|
||||||
inumb = (ino_t) fs_m_in.REQ_INODE_NR;
|
inumb = (ino_t) fs_m_in->REQ_INODE_NR;
|
||||||
|
|
||||||
if( (rip = find_inode(inumb)) == NULL) return(EINVAL);
|
if( (rip = find_inode(inumb)) == NULL) return(EINVAL);
|
||||||
|
|
||||||
start = fs_m_in.REQ_TRC_START_LO;
|
start = fs_m_in->REQ_TRC_START_LO;
|
||||||
end = fs_m_in.REQ_TRC_END_LO;
|
end = fs_m_in->REQ_TRC_END_LO;
|
||||||
|
|
||||||
return truncate_inode(rip, start);
|
return truncate_inode(rip, start);
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,6 +6,7 @@
|
||||||
#include <minix/vfsif.h>
|
#include <minix/vfsif.h>
|
||||||
#include "buf.h"
|
#include "buf.h"
|
||||||
#include "inode.h"
|
#include "inode.h"
|
||||||
|
#include "uds.h"
|
||||||
|
|
||||||
FORWARD _PROTOTYPE(void get_work, (message *m_in) );
|
FORWARD _PROTOTYPE(void get_work, (message *m_in) );
|
||||||
|
|
||||||
|
@ -23,7 +24,9 @@ PUBLIC int main(int argc, char *argv[])
|
||||||
* three major activities: getting new work, processing the work, and
|
* three major activities: getting new work, processing the work, and
|
||||||
* sending the reply. The loop never terminates, unless a panic occurs.
|
* sending the reply. The loop never terminates, unless a panic occurs.
|
||||||
*/
|
*/
|
||||||
int error, ind;
|
int ind;
|
||||||
|
message pfs_m_in;
|
||||||
|
message pfs_m_out;
|
||||||
|
|
||||||
/* SEF local startup. */
|
/* SEF local startup. */
|
||||||
env_setargs(argc, argv);
|
env_setargs(argc, argv);
|
||||||
|
@ -33,31 +36,36 @@ PUBLIC int main(int argc, char *argv[])
|
||||||
endpoint_t src;
|
endpoint_t src;
|
||||||
|
|
||||||
/* Wait for request message. */
|
/* Wait for request message. */
|
||||||
get_work(&fs_m_in);
|
get_work(&pfs_m_in);
|
||||||
|
|
||||||
src = fs_m_in.m_source;
|
src = pfs_m_in.m_source;
|
||||||
error = OK;
|
|
||||||
caller_uid = INVAL_UID; /* To trap errors */
|
caller_uid = INVAL_UID; /* To trap errors */
|
||||||
caller_gid = INVAL_GID;
|
caller_gid = INVAL_GID;
|
||||||
req_nr = fs_m_in.m_type;
|
req_nr = pfs_m_in.m_type;
|
||||||
|
|
||||||
if (req_nr < VFS_BASE) {
|
if (IS_DEV_RQ(req_nr)) {
|
||||||
fs_m_in.m_type += VFS_BASE;
|
ind = req_nr - DEV_RQ_BASE;
|
||||||
req_nr = fs_m_in.m_type;
|
if (ind < 0 || ind >= DEV_CALL_VEC_SIZE) {
|
||||||
printf("PFS: bad request (no VFS_BASE) %d\n", req_nr);
|
printf("pfs: bad DEV request %d\n", req_nr);
|
||||||
}
|
pfs_m_out.m_type = EINVAL;
|
||||||
ind = req_nr - VFS_BASE;
|
|
||||||
|
|
||||||
if (ind < 0 || ind >= NREQS) {
|
|
||||||
printf("pfs: bad request %d\n", req_nr);
|
|
||||||
error = EINVAL;
|
|
||||||
} else {
|
} else {
|
||||||
error = (*fs_call_vec[ind])();
|
(*dev_call_vec[ind])(&pfs_m_in, &pfs_m_out);
|
||||||
|
}
|
||||||
|
} else if (IS_VFS_RQ(req_nr)) {
|
||||||
|
ind = req_nr - VFS_BASE;
|
||||||
|
if (ind < 0 || ind >= FS_CALL_VEC_SIZE) {
|
||||||
|
printf("pfs: bad FS request %d\n", req_nr);
|
||||||
|
pfs_m_out.m_type = EINVAL;
|
||||||
|
} else {
|
||||||
|
pfs_m_out.m_type =
|
||||||
|
(*fs_call_vec[ind])(&pfs_m_in, &pfs_m_out);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
printf("pfs: bad request %d\n", req_nr);
|
||||||
|
pfs_m_out.m_type = EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
fs_m_out.m_type = error;
|
reply(src, &pfs_m_out);
|
||||||
reply(src, &fs_m_out);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
return(OK);
|
return(OK);
|
||||||
}
|
}
|
||||||
|
@ -98,10 +106,13 @@ PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
|
||||||
}
|
}
|
||||||
|
|
||||||
init_inode_cache();
|
init_inode_cache();
|
||||||
|
uds_init();
|
||||||
|
|
||||||
SELF_E = getprocnr();
|
SELF_E = getprocnr();
|
||||||
buf_pool();
|
buf_pool();
|
||||||
|
|
||||||
|
driver_announce();
|
||||||
|
|
||||||
return(OK);
|
return(OK);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -122,12 +133,13 @@ PRIVATE void sef_cb_signal_handler(int signo)
|
||||||
PRIVATE void get_work(m_in)
|
PRIVATE void get_work(m_in)
|
||||||
message *m_in; /* pointer to message */
|
message *m_in; /* pointer to message */
|
||||||
{
|
{
|
||||||
int r, srcok = 0;
|
int r, srcok = 0, status;
|
||||||
endpoint_t src;
|
endpoint_t src;
|
||||||
|
|
||||||
do {
|
do {
|
||||||
if ((r = sef_receive(ANY, m_in)) != OK) /* wait for message */
|
/* wait for a message */
|
||||||
panic("sef_receive failed: %d", r);
|
if ((r = sef_receive_status(ANY, m_in, &status)) != OK)
|
||||||
|
panic("sef_receive_status failed: %d", r);
|
||||||
src = m_in->m_source;
|
src = m_in->m_source;
|
||||||
|
|
||||||
if(src == VFS_PROC_NR) {
|
if(src == VFS_PROC_NR) {
|
||||||
|
@ -148,4 +160,3 @@ message *m_out; /* report result */
|
||||||
if (OK != send(who, m_out)) /* send the message */
|
if (OK != send(who, m_out)) /* send the message */
|
||||||
printf("PFS(%d) was unable to send reply\n", SELF_E);
|
printf("PFS(%d) was unable to send reply\n", SELF_E);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* fs_sync *
|
* fs_sync *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int fs_sync()
|
PUBLIC int fs_sync(message *fs_m_in, message *fs_m_out)
|
||||||
{
|
{
|
||||||
/* Perform the sync() system call. No-op on this FS. */
|
/* Perform the sync() system call. No-op on this FS. */
|
||||||
|
|
||||||
|
|
|
@ -8,17 +8,17 @@
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* fs_newnode *
|
* fs_newnode *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int fs_newnode()
|
PUBLIC int fs_newnode(message *fs_m_in, message *fs_m_out)
|
||||||
{
|
{
|
||||||
register int r = OK;
|
register int r = OK;
|
||||||
mode_t bits;
|
mode_t bits;
|
||||||
struct inode *rip;
|
struct inode *rip;
|
||||||
dev_t dev;
|
dev_t dev;
|
||||||
|
|
||||||
caller_uid = (uid_t) fs_m_in.REQ_UID;
|
caller_uid = (uid_t) fs_m_in->REQ_UID;
|
||||||
caller_gid = (gid_t) fs_m_in.REQ_GID;
|
caller_gid = (gid_t) fs_m_in->REQ_GID;
|
||||||
bits = (mode_t) fs_m_in.REQ_MODE;
|
bits = (mode_t) fs_m_in->REQ_MODE;
|
||||||
dev = (dev_t) fs_m_in.REQ_DEV;
|
dev = (dev_t) fs_m_in->REQ_DEV;
|
||||||
|
|
||||||
/* Try to allocate the inode */
|
/* Try to allocate the inode */
|
||||||
if( (rip = alloc_inode(dev, bits) ) == NULL) return(err_code);
|
if( (rip = alloc_inode(dev, bits) ) == NULL) return(err_code);
|
||||||
|
@ -40,12 +40,12 @@ PUBLIC int fs_newnode()
|
||||||
free_inode(rip);
|
free_inode(rip);
|
||||||
} else {
|
} else {
|
||||||
/* Fill in the fields of the response message */
|
/* Fill in the fields of the response message */
|
||||||
fs_m_out.RES_INODE_NR = rip->i_num;
|
fs_m_out->RES_INODE_NR = rip->i_num;
|
||||||
fs_m_out.RES_MODE = rip->i_mode;
|
fs_m_out->RES_MODE = rip->i_mode;
|
||||||
fs_m_out.RES_FILE_SIZE_LO = rip->i_size;
|
fs_m_out->RES_FILE_SIZE_LO = rip->i_size;
|
||||||
fs_m_out.RES_UID = rip->i_uid;
|
fs_m_out->RES_UID = rip->i_uid;
|
||||||
fs_m_out.RES_GID = rip->i_gid;
|
fs_m_out->RES_GID = rip->i_gid;
|
||||||
fs_m_out.RES_DEV = dev;
|
fs_m_out->RES_DEV = dev;
|
||||||
}
|
}
|
||||||
|
|
||||||
return(r);
|
return(r);
|
||||||
|
|
|
@ -6,6 +6,7 @@
|
||||||
/* Structs used in prototypes must be declared as such first. */
|
/* Structs used in prototypes must be declared as such first. */
|
||||||
struct buf;
|
struct buf;
|
||||||
struct inode;
|
struct inode;
|
||||||
|
struct sockaddr_un;
|
||||||
|
|
||||||
/* buffer.c */
|
/* buffer.c */
|
||||||
_PROTOTYPE( struct buf *get_block, (dev_t dev, ino_t inum) );
|
_PROTOTYPE( struct buf *get_block, (dev_t dev, ino_t inum) );
|
||||||
|
@ -19,7 +20,7 @@ _PROTOTYPE( struct inode *alloc_inode, (dev_t dev, mode_t mode) );
|
||||||
_PROTOTYPE( void dup_inode, (struct inode *ip) );
|
_PROTOTYPE( void dup_inode, (struct inode *ip) );
|
||||||
_PROTOTYPE( struct inode *find_inode, (ino_t numb) );
|
_PROTOTYPE( struct inode *find_inode, (ino_t numb) );
|
||||||
_PROTOTYPE( void free_inode, (struct inode *rip) );
|
_PROTOTYPE( void free_inode, (struct inode *rip) );
|
||||||
_PROTOTYPE( int fs_putnode, (void) );
|
_PROTOTYPE( int fs_putnode, (message *fs_m_in, message *fs_m_out) );
|
||||||
_PROTOTYPE( void init_inode_cache, (void) );
|
_PROTOTYPE( void init_inode_cache, (void) );
|
||||||
_PROTOTYPE( struct inode *get_inode, (dev_t dev, ino_t numb) );
|
_PROTOTYPE( struct inode *get_inode, (dev_t dev, ino_t numb) );
|
||||||
_PROTOTYPE( void put_inode, (struct inode *rip) );
|
_PROTOTYPE( void put_inode, (struct inode *rip) );
|
||||||
|
@ -27,7 +28,7 @@ _PROTOTYPE( void update_times, (struct inode *rip) );
|
||||||
_PROTOTYPE( void wipe_inode, (struct inode *rip) );
|
_PROTOTYPE( void wipe_inode, (struct inode *rip) );
|
||||||
|
|
||||||
/* link.c */
|
/* link.c */
|
||||||
_PROTOTYPE( int fs_ftrunc, (void) );
|
_PROTOTYPE( int fs_ftrunc, (message *fs_m_in, message *fs_m_out) );
|
||||||
_PROTOTYPE( int truncate_inode, (struct inode *rip, off_t newsize) );
|
_PROTOTYPE( int truncate_inode, (struct inode *rip, off_t newsize) );
|
||||||
|
|
||||||
|
|
||||||
|
@ -35,23 +36,63 @@ _PROTOTYPE( int truncate_inode, (struct inode *rip, off_t newsize) );
|
||||||
_PROTOTYPE( void reply, (endpoint_t who, message *m_out) );
|
_PROTOTYPE( void reply, (endpoint_t who, message *m_out) );
|
||||||
|
|
||||||
/* misc.c */
|
/* misc.c */
|
||||||
_PROTOTYPE( int fs_sync, (void) );
|
_PROTOTYPE( int fs_sync, (message *fs_m_in, message *fs_m_out) );
|
||||||
|
|
||||||
/* open.c */
|
/* open.c */
|
||||||
_PROTOTYPE( int fs_newnode, (void) );
|
_PROTOTYPE( int fs_newnode, (message *fs_m_in, message *fs_m_out) );
|
||||||
|
|
||||||
/* read.c */
|
/* read.c */
|
||||||
_PROTOTYPE( int fs_readwrite, (void) );
|
_PROTOTYPE( int fs_readwrite, (message *fs_m_in, message *fs_m_out) );
|
||||||
|
|
||||||
/* utility.c */
|
/* utility.c */
|
||||||
_PROTOTYPE( time_t clock_time, (void) );
|
_PROTOTYPE( time_t clock_time, (void) );
|
||||||
_PROTOTYPE( int no_sys, (void) );
|
_PROTOTYPE( int no_sys, (message *pfs_m_in, message *pfs_m_out) );
|
||||||
|
|
||||||
/* stadir.c */
|
/* stadir.c */
|
||||||
_PROTOTYPE( int fs_stat, (void) );
|
_PROTOTYPE( int fs_stat, (message *fs_m_in, message *fs_m_out) );
|
||||||
|
|
||||||
/* super.c */
|
/* super.c */
|
||||||
_PROTOTYPE( bit_t alloc_bit, (void) );
|
_PROTOTYPE( bit_t alloc_bit, (void) );
|
||||||
_PROTOTYPE( void free_bit, (bit_t bit_returned) );
|
_PROTOTYPE( void free_bit, (bit_t bit_returned) );
|
||||||
|
|
||||||
|
/* dev_uds.c */
|
||||||
|
_PROTOTYPE( int uds_open, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_close, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_read, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_write, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_ioctl, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_select, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_status, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int uds_cancel, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
|
||||||
|
/* uds.c */
|
||||||
|
_PROTOTYPE( void uds_init, (void) );
|
||||||
|
_PROTOTYPE( int do_accept, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_connect, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_listen, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_socket, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_bind, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_getsockname, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_getpeername, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_shutdown, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_socketpair, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_getsockopt_sotype,
|
||||||
|
(message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_getsockopt_peercred,
|
||||||
|
(message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_getsockopt_sndbuf,
|
||||||
|
(message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_setsockopt_sndbuf,
|
||||||
|
(message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_getsockopt_rcvbuf,
|
||||||
|
(message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_setsockopt_rcvbuf,
|
||||||
|
(message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_sendto, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int do_recvfrom, (message *dev_m_in, message *dev_m_out) );
|
||||||
|
_PROTOTYPE( int perform_connection,
|
||||||
|
(message *dev_m_in, message *dev_m_out,
|
||||||
|
struct sockaddr_un *addr, int minorx,
|
||||||
|
int minory) );
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* fs_readwrite *
|
* fs_readwrite *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int fs_readwrite(void)
|
PUBLIC int fs_readwrite(message *fs_m_in, message *fs_m_out)
|
||||||
{
|
{
|
||||||
int r, rw_flag;
|
int r, rw_flag;
|
||||||
struct buf *bp;
|
struct buf *bp;
|
||||||
|
@ -20,7 +20,7 @@ PUBLIC int fs_readwrite(void)
|
||||||
|
|
||||||
r = OK;
|
r = OK;
|
||||||
cum_io = 0;
|
cum_io = 0;
|
||||||
inumb = (ino_t) fs_m_in.REQ_INODE_NR;
|
inumb = (ino_t) fs_m_in->REQ_INODE_NR;
|
||||||
|
|
||||||
/* Find the inode referred */
|
/* Find the inode referred */
|
||||||
if ((rip = find_inode(inumb)) == NULL) return(EINVAL);
|
if ((rip = find_inode(inumb)) == NULL) return(EINVAL);
|
||||||
|
@ -30,10 +30,10 @@ PUBLIC int fs_readwrite(void)
|
||||||
f_size = rip->i_size;
|
f_size = rip->i_size;
|
||||||
|
|
||||||
/* Get the values from the request message */
|
/* Get the values from the request message */
|
||||||
rw_flag = (fs_m_in.m_type == REQ_READ ? READING : WRITING);
|
rw_flag = (fs_m_in->m_type == REQ_READ ? READING : WRITING);
|
||||||
gid = (cp_grant_id_t) fs_m_in.REQ_GRANT;
|
gid = (cp_grant_id_t) fs_m_in->REQ_GRANT;
|
||||||
position = fs_m_in.REQ_SEEK_POS_LO;
|
position = fs_m_in->REQ_SEEK_POS_LO;
|
||||||
nrbytes = (unsigned) fs_m_in.REQ_NBYTES;
|
nrbytes = (unsigned) fs_m_in->REQ_NBYTES;
|
||||||
|
|
||||||
/* We can't read beyond the max file position */
|
/* We can't read beyond the max file position */
|
||||||
if (nrbytes > MAX_FILE_POS) return(EFBIG);
|
if (nrbytes > MAX_FILE_POS) return(EFBIG);
|
||||||
|
@ -64,7 +64,7 @@ PUBLIC int fs_readwrite(void)
|
||||||
cum_io += nrbytes;
|
cum_io += nrbytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
fs_m_out.RES_SEEK_POS_LO = position; /* It might change later and the VFS
|
fs_m_out->RES_SEEK_POS_LO = position; /* It might change later and the VFS
|
||||||
has to know this value */
|
has to know this value */
|
||||||
|
|
||||||
/* On write, update file size and access time. */
|
/* On write, update file size and access time. */
|
||||||
|
@ -81,7 +81,7 @@ PUBLIC int fs_readwrite(void)
|
||||||
bp->b_bytes = position;
|
bp->b_bytes = position;
|
||||||
if (rw_flag == READING) rip->i_update |= ATIME;
|
if (rw_flag == READING) rip->i_update |= ATIME;
|
||||||
if (rw_flag == WRITING) rip->i_update |= CTIME | MTIME;
|
if (rw_flag == WRITING) rip->i_update |= CTIME | MTIME;
|
||||||
fs_m_out.RES_NBYTES = (size_t) cum_io;
|
fs_m_out->RES_NBYTES = (size_t) cum_io;
|
||||||
put_inode(rip);
|
put_inode(rip);
|
||||||
put_block(rip->i_dev, rip->i_num);
|
put_block(rip->i_dev, rip->i_num);
|
||||||
|
|
||||||
|
|
|
@ -47,14 +47,14 @@ PRIVATE int stat_inode(
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* fs_stat *
|
* fs_stat *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int fs_stat()
|
PUBLIC int fs_stat(message *fs_m_in, message *fs_m_out)
|
||||||
{
|
{
|
||||||
register int r; /* return value */
|
register int r; /* return value */
|
||||||
register struct inode *rip; /* target inode */
|
register struct inode *rip; /* target inode */
|
||||||
|
|
||||||
if( (rip = find_inode(fs_m_in.REQ_INODE_NR)) == NULL) return(EINVAL);
|
if( (rip = find_inode(fs_m_in->REQ_INODE_NR)) == NULL) return(EINVAL);
|
||||||
get_inode(rip->i_dev, rip->i_num); /* mark inode in use */
|
get_inode(rip->i_dev, rip->i_num); /* mark inode in use */
|
||||||
r = stat_inode(rip, fs_m_in.m_source, (cp_grant_id_t) fs_m_in.REQ_GRANT);
|
r = stat_inode(rip, fs_m_in->m_source, (cp_grant_id_t) fs_m_in->REQ_GRANT);
|
||||||
put_inode(rip); /* release the inode */
|
put_inode(rip); /* release the inode */
|
||||||
return(r);
|
return(r);
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,8 +8,12 @@
|
||||||
#include "fs.h"
|
#include "fs.h"
|
||||||
#include "inode.h"
|
#include "inode.h"
|
||||||
#include "buf.h"
|
#include "buf.h"
|
||||||
|
#include "uds.h"
|
||||||
|
|
||||||
|
/* File System Handlers (pfs) */
|
||||||
|
PUBLIC _PROTOTYPE (int (*fs_call_vec[]),
|
||||||
|
(message *fs_m_in, message *fs_m_out) ) = {
|
||||||
|
|
||||||
PUBLIC _PROTOTYPE (int (*fs_call_vec[]), (void) ) = {
|
|
||||||
no_sys, /* 0 not used */
|
no_sys, /* 0 not used */
|
||||||
no_sys, /* 1 */
|
no_sys, /* 1 */
|
||||||
fs_putnode, /* 2 */
|
fs_putnode, /* 2 */
|
||||||
|
@ -45,3 +49,34 @@ PUBLIC _PROTOTYPE (int (*fs_call_vec[]), (void) ) = {
|
||||||
no_sys, /* 32 */
|
no_sys, /* 32 */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* Device Handlers (/dev/uds) */
|
||||||
|
PUBLIC _PROTOTYPE (int (*dev_call_vec[]),
|
||||||
|
(message *dev_m_in, message *dev_m_out) ) = {
|
||||||
|
|
||||||
|
uds_cancel, /* 0 */
|
||||||
|
no_sys, /* 1 */
|
||||||
|
no_sys, /* 2 */
|
||||||
|
no_sys, /* 3 */
|
||||||
|
no_sys, /* 4 */
|
||||||
|
no_sys, /* 5 */
|
||||||
|
uds_open, /* 6 */
|
||||||
|
uds_close, /* 7 */
|
||||||
|
no_sys, /* 8 */
|
||||||
|
no_sys, /* 9 */
|
||||||
|
no_sys, /* 10 */
|
||||||
|
no_sys, /* 11 */
|
||||||
|
uds_select, /* 12 */
|
||||||
|
uds_status, /* 13 */
|
||||||
|
uds_open, /* 14 */
|
||||||
|
no_sys, /* 15 */
|
||||||
|
no_sys, /* 16 */
|
||||||
|
no_sys, /* 17 */
|
||||||
|
no_sys, /* 18 */
|
||||||
|
no_sys, /* 19 */
|
||||||
|
uds_read, /* 20 */
|
||||||
|
uds_write, /* 21 */
|
||||||
|
no_sys, /* 22 */
|
||||||
|
no_sys, /* 23 */
|
||||||
|
uds_ioctl, /* 24 */
|
||||||
|
no_sys, /* 25 */
|
||||||
|
};
|
||||||
|
|
1354
servers/pfs/uds.c
Normal file
1354
servers/pfs/uds.c
Normal file
File diff suppressed because it is too large
Load diff
227
servers/pfs/uds.h
Normal file
227
servers/pfs/uds.h
Normal file
|
@ -0,0 +1,227 @@
|
||||||
|
#ifndef __PFS_UDS_H__
|
||||||
|
#define __PFS_UDS_H__
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Unix Domain Sockets Implementation (PF_UNIX, PF_LOCAL)
|
||||||
|
*
|
||||||
|
* Also See...
|
||||||
|
*
|
||||||
|
* dev_uds.c, table.c, uds.c
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <sys/un.h>
|
||||||
|
|
||||||
|
#include <minix/endpoint.h>
|
||||||
|
|
||||||
|
/* max connection backlog for incoming connections */
|
||||||
|
#define UDS_SOMAXCONN 64
|
||||||
|
|
||||||
|
/* UDS FD state Flags */
|
||||||
|
#define UDS_CONNECTING 0x10
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Internal State Information for a socket descriptor.
|
||||||
|
*/
|
||||||
|
struct uds_fd {
|
||||||
|
|
||||||
|
/* Flags */
|
||||||
|
|
||||||
|
enum UDS_STATE {
|
||||||
|
/* This file descriptor is UDS_FREE and can be allocated. */
|
||||||
|
UDS_FREE = 0,
|
||||||
|
|
||||||
|
/* OR it is UDS_INUSE and can't be allocated. */
|
||||||
|
UDS_INUSE = 1
|
||||||
|
|
||||||
|
/* state is set to UDS_INUSE in uds_open(). state is Set to
|
||||||
|
* UDS_FREE in uds_init() and uds_close(). state should be
|
||||||
|
* checked prior to all operations.
|
||||||
|
*/
|
||||||
|
} state;
|
||||||
|
|
||||||
|
/* Owner Info */
|
||||||
|
|
||||||
|
/* Socket Owner */
|
||||||
|
endpoint_t owner;
|
||||||
|
|
||||||
|
/* endpoint for suspend/resume */
|
||||||
|
endpoint_t endpoint;
|
||||||
|
|
||||||
|
/* Pipe Housekeeping */
|
||||||
|
|
||||||
|
/* inode number on PFS -- each descriptor is backed by 1
|
||||||
|
* PIPE which is allocated in uds_open() and freed in
|
||||||
|
* uds_close(). Data is sent/written to a peer's PIPE.
|
||||||
|
* Data is recv/read from this PIPE.
|
||||||
|
*/
|
||||||
|
ino_t inode_nr;
|
||||||
|
|
||||||
|
|
||||||
|
/* position in the PIPE where the data starts */
|
||||||
|
off_t pos;
|
||||||
|
|
||||||
|
/* size of data in the PIPE */
|
||||||
|
size_t size;
|
||||||
|
|
||||||
|
/* control read/write, set by uds_open() and shutdown(2).
|
||||||
|
* Can be set to S_IRUSR|S_IWUSR, S_IRUSR, S_IWUSR, or 0
|
||||||
|
* for read and write, read only, write only, or neither.
|
||||||
|
* default is S_IRUSR|S_IWUSR.
|
||||||
|
*/
|
||||||
|
mode_t mode;
|
||||||
|
|
||||||
|
/* Socket Info */
|
||||||
|
|
||||||
|
|
||||||
|
/* socket type - SOCK_STREAM, SOCK_DGRAM, or SOCK_SEQPACKET
|
||||||
|
* Set by uds_ioctl(NWIOSUDSTYPE). It defaults to -1 in
|
||||||
|
* uds_open(). Any action on a socket with type -1 besides
|
||||||
|
* uds_ioctl(NWIOSUDSTYPE) and uds_close() will result in
|
||||||
|
* an error.
|
||||||
|
*/
|
||||||
|
int type;
|
||||||
|
|
||||||
|
/* queue of pending connections for server sockets.
|
||||||
|
* connect(2) inserts and accept(2) removes from the queue
|
||||||
|
*/
|
||||||
|
int backlog[UDS_SOMAXCONN];
|
||||||
|
|
||||||
|
/* requested connection backlog size. Set by listen(2)
|
||||||
|
* Bounds (0 <= backlog_size <= UDS_SOMAXCONN)
|
||||||
|
* Defaults to UDS_SOMAXCONN which is defined above.
|
||||||
|
*/
|
||||||
|
unsigned char backlog_size;
|
||||||
|
|
||||||
|
/* index of peer in uds_fd_table for connected sockets.
|
||||||
|
* -1 is used to mean no peer. Assumptions: peer != -1 means
|
||||||
|
* connected.
|
||||||
|
*/
|
||||||
|
int peer;
|
||||||
|
|
||||||
|
/* index of child (client sd returned by accept(2))
|
||||||
|
* -1 is used to mean no child.
|
||||||
|
*/
|
||||||
|
int child;
|
||||||
|
|
||||||
|
/* address -- the address the socket is bound to.
|
||||||
|
* Assumptions: addr.sun_family == AF_UNIX means its bound.
|
||||||
|
*/
|
||||||
|
struct sockaddr_un addr;
|
||||||
|
|
||||||
|
/* target -- where DGRAMs are sent to on the next uds_write(). */
|
||||||
|
struct sockaddr_un target;
|
||||||
|
|
||||||
|
/* source -- address where DGRAMs are from. used to fill in the
|
||||||
|
* from address in recvfrom(2) and recvmsg(2).
|
||||||
|
*/
|
||||||
|
struct sockaddr_un source;
|
||||||
|
|
||||||
|
/* Flag (1 or 0) - listening for incoming connections.
|
||||||
|
* Default to 0. Set to 1 by do_listen()
|
||||||
|
*/
|
||||||
|
int listening;
|
||||||
|
|
||||||
|
/* Holds an errno. This is set when a connected socket is
|
||||||
|
* closed and we need to pass ECONNRESET on to a suspended
|
||||||
|
* peer.
|
||||||
|
*/
|
||||||
|
int err;
|
||||||
|
|
||||||
|
/* Suspend/Revive Housekeeping */
|
||||||
|
|
||||||
|
|
||||||
|
/* SUSPEND State Flags */
|
||||||
|
enum UDS_SUSPENDED {
|
||||||
|
|
||||||
|
/* Socket isn't blocked. */
|
||||||
|
UDS_NOT_SUSPENDED = 0,
|
||||||
|
|
||||||
|
/* Socket is blocked on read(2) waiting for data to read. */
|
||||||
|
UDS_SUSPENDED_READ = 1,
|
||||||
|
|
||||||
|
/* Socket is blocked on write(2) for space to write data. */
|
||||||
|
UDS_SUSPENDED_WRITE = 2,
|
||||||
|
|
||||||
|
/* Socket is blocked on connect(2) waiting for the server. */
|
||||||
|
UDS_SUSPENDED_CONNECT = 4,
|
||||||
|
|
||||||
|
/* Socket is blocked on accept(2) waiting for clients. */
|
||||||
|
UDS_SUSPENDED_ACCEPT = 8
|
||||||
|
} suspended;
|
||||||
|
|
||||||
|
/* Flag (1 or 0) - thing socket was waiting for is ready.
|
||||||
|
* If 1, then uds_status() will attempt the operation that
|
||||||
|
* the socket was blocked on.
|
||||||
|
*/
|
||||||
|
int ready_to_revive;
|
||||||
|
|
||||||
|
/* i/o grant, saved for later use by suspended procs */
|
||||||
|
cp_grant_id_t io_gr;
|
||||||
|
|
||||||
|
/* is of i/o grant, saved for later use by suspended procs */
|
||||||
|
size_t io_gr_size;
|
||||||
|
|
||||||
|
/* Save the call number so that uds_cancel() can unwind the
|
||||||
|
* call properly.
|
||||||
|
*/
|
||||||
|
int call_nr;
|
||||||
|
|
||||||
|
/* Save the IOCTL so uds_cancel() knows what got cancelled. */
|
||||||
|
int ioctl;
|
||||||
|
|
||||||
|
/* Flag (1 or 0) - the system call completed.
|
||||||
|
* A doc I read said DEV_CANCEL might be called even though
|
||||||
|
* the operation is finished. We use this variable to
|
||||||
|
* determine if we should rollback the changes or not.
|
||||||
|
*/
|
||||||
|
int syscall_done;
|
||||||
|
|
||||||
|
/* select() */
|
||||||
|
|
||||||
|
/* Flag (1 or 0) - the process blocked on select(2). When
|
||||||
|
* selecting is 1 and I/O happens on this socket, then
|
||||||
|
* select_proc should be notified.
|
||||||
|
*/
|
||||||
|
int selecting;
|
||||||
|
|
||||||
|
/* when a select is in progress, we notify() this endpoint
|
||||||
|
* of new data.
|
||||||
|
*/
|
||||||
|
endpoint_t select_proc;
|
||||||
|
|
||||||
|
/* Options (SEL_RD, SEL_WR, SEL_ERR) that are requested. */
|
||||||
|
int sel_ops_in;
|
||||||
|
|
||||||
|
/* Options that are available for this socket. */
|
||||||
|
int sel_ops_out;
|
||||||
|
|
||||||
|
/* Flag (1 or 0) to be set to one before calling notify().
|
||||||
|
* uds_status() will use the flag to locate this descriptor.
|
||||||
|
*/
|
||||||
|
int status_updated;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct uds_fd uds_fd_t;
|
||||||
|
|
||||||
|
/* File Descriptor Table -- Defined in uds.c */
|
||||||
|
EXTERN uds_fd_t uds_fd_table[NR_FDS];
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Take message m and get the index in uds_fd_table.
|
||||||
|
*/
|
||||||
|
#define uds_minor(m) (minor((dev_t) m->DEVICE) & BYTE)
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Fill in a reply message.
|
||||||
|
*/
|
||||||
|
#define uds_set_reply(msg,type,endpoint,io_gr,status) \
|
||||||
|
do { \
|
||||||
|
msg->m_type = type; \
|
||||||
|
msg->REP_ENDPT = endpoint; \
|
||||||
|
msg->REP_IO_GRANT = io_gr; \
|
||||||
|
msg->REP_STATUS = status; \
|
||||||
|
} while (0)
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
|
@ -4,10 +4,10 @@
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* no_sys *
|
* no_sys *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int no_sys()
|
PUBLIC int no_sys(message *pfs_m_in, message *pfs_m_out)
|
||||||
{
|
{
|
||||||
/* Somebody has used an illegal system call number */
|
/* Somebody has used an illegal system call number */
|
||||||
printf("no_sys: invalid call %d\n", req_nr);
|
printf("no_sys: invalid call 0x%x to pfs\n", req_nr);
|
||||||
return(EINVAL);
|
return(EINVAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue