From 013d5abbc4cc5a98ab1a66eb9fab01e35acf6d27 Mon Sep 17 00:00:00 2001 From: Chas Williams Date: Wed, 17 Oct 2001 22:07:49 +0000 Subject: [PATCH] sgi-ip20-work-around-cvt-bug-20011017 "apparently the rev 1 r5000 chips implement 'cvt' incorrectly. the irix kernel works around this problem by checking each text page mapped into memory and doing a fixup on the cvt instructions. it tries to maintain a hash of these pages using fid2() or fid() if fid2() returns ENOSYS. afs, in an effort to prevent people from doing checkpoints on an afs filesystem, makes fid2() return EINVAL. this also keeps the kernel from mapping executables that are in afs space on the broken r5000's. this is the patch i have been using for the past couple years while waiting for an official fix. it makes fid2() return ENOSYS, so you now need to have to have v_ckpt. however i disabled the rest of the CKPT code since i have no idea how well that code actually works. additionally, this behavior is only functional on machines with the 'broken' r5000 h/w. i cant think of a better way to fix this problem since i cant change the irix kernel." --- src/afs/IRIX/osi_vfs.h | 3 +++ src/afs/IRIX/osi_vfsops.c | 4 ++-- src/afs/IRIX/osi_vnodeops.c | 13 ++++++++++++- src/libafs/MakefileProto.IRIX.in | 2 +- 4 files changed, 18 insertions(+), 4 deletions(-) diff --git a/src/afs/IRIX/osi_vfs.h b/src/afs/IRIX/osi_vfs.h index 2c061c91d..0847b80a1 100644 --- a/src/afs/IRIX/osi_vfs.h +++ b/src/afs/IRIX/osi_vfs.h @@ -291,6 +291,9 @@ typedef struct vnode1 { #ifdef VNODE_TRACING struct ktrace *v_trace; /* trace header structure */ #endif +#ifdef CKPT + ckpt_handle_t v_ckpt; /* ckpt lookup info */ +#endif } vnode1_t; extern struct pfdat *vnode_get_dpages(vnode_t*); diff --git a/src/afs/IRIX/osi_vfsops.c b/src/afs/IRIX/osi_vfsops.c index df0c57a0a..7d3e74af6 100644 --- a/src/afs/IRIX/osi_vfsops.c +++ b/src/afs/IRIX/osi_vfsops.c @@ -523,7 +523,7 @@ afs_vget(OSI_VFS_DECL(afsp), vnode_t **avcp, struct fid *fidp) register afs_int32 code = 0; afs_int32 ret; -#if defined(AFS_SGI64_ENV) && defined(CKPT) +#if defined(AFS_SGI64_ENV) && defined(CKPT) && !defined(_R5000_CVT_WAR) afs_fid2_t *afid2; #endif @@ -533,7 +533,7 @@ afs_vget(OSI_VFS_DECL(afsp), vnode_t **avcp, struct fid *fidp) *avcp = NULL; -#if defined(AFS_SGI64_ENV) && defined(CKPT) +#if defined(AFS_SGI64_ENV) && defined(CKPT) && !defined(_R5000_CVT_WAR) afid2 = (afs_fid2_t*)fidp; if (afid2->af_len == sizeof(afs_fid2_t) - sizeof(afid2->af_len)) { /* It's a checkpoint restart fid. */ diff --git a/src/afs/IRIX/osi_vnodeops.c b/src/afs/IRIX/osi_vnodeops.c index 0952e9961..ef5fbdb80 100644 --- a/src/afs/IRIX/osi_vnodeops.c +++ b/src/afs/IRIX/osi_vnodeops.c @@ -1258,7 +1258,7 @@ int afs_rwlock_nowait(vnode_t *vp, AFS_RWLOCK_T flag) return 0; } -#if defined(AFS_SGI64_ENV) && defined(CKPT) +#if defined(AFS_SGI64_ENV) && defined(CKPT) && !defined(_R5000_CVT_WAR) int afs_fid2(OSI_VC_DECL(avc), struct fid *fidp) { struct cell *tcell; @@ -1283,10 +1283,21 @@ int afs_fid2(OSI_VC_DECL(avc), struct fid *fidp) * return of ENOSYS would make the code fail over to VOP_FID. We can't let * that happen, since we do a VN_HOLD there in the expectation that * posthandle will be called to release the vnode. + * + * afs_fid2 is used to support the R5000 workarounds (_R5000_CVT_WAR) */ int afs_fid2(OSI_VC_DECL(avc), struct fid *fidp) { +#if defined(_R5000_CVT_WAR) + extern int R5000_cvt_war; + + if (R5000_cvt_war) + return ENOSYS; + else + return EINVAL; +#else return EINVAL; +#endif } #endif /* AFS_SGI64_ENV && CKPT */ diff --git a/src/libafs/MakefileProto.IRIX.in b/src/libafs/MakefileProto.IRIX.in index 76f9afa9b..6e3aaa341 100644 --- a/src/libafs/MakefileProto.IRIX.in +++ b/src/libafs/MakefileProto.IRIX.in @@ -182,7 +182,7 @@ KDEFS_64 = -64 -D_PAGESZ=16384 -D_MIPS3_ADDRSPACE -mips4 IP19_KDEFS = -DIP19 -DEVEREST -DMP -DR4000 \ -mips3 -D_PAGESZ=16384 -D_MIPS3_ADDRSPACE -64 IP20_KDEFS = -DIP20 -DR4000 -DJUMP_WAR -DBADVA_WAR -DTRITON -DUSE_PCI_PIO \ - $(KDEFS_32) + -D_R5000_CVT_WAR=1 -DCKPT -D_MTEXT_VFS $(KDEFS_32) IP21_KDEFS = -DIP21 -DEVEREST -DMP -DTFP -TARG:processor=r8000 $(KDEFS_64) IP25_KDEFS = -DIP25 -DEVEREST -DMP -DR10000 -TARG:processor=r10000 $(KDEFS_64) IP26_KDEFS = -DIP26 -DTFP -TARG:sync=off -TARG:processor=r8000 $(KDEFS_64) -- 2.39.5