2
* Copyright 2000, International Business Machines Corporation and others.
5
* This software has been released under the terms of the IBM Public
6
* License. For details, see the LICENSE file in the top-level source
7
* directory or online at http://www.openafs.org/dl/license10.html
11
* SOLARIS inode operations
16
#include <afsconfig.h>
17
#include "../afs/param.h"
19
RCSID("$Header: /afs/sipb.mit.edu/project/openafs/debian/cvs/openafs/src/afs/SOLARIS/osi_inode.c,v 1.1.1.8 2002/05/10 23:44:12 hartmans Exp $");
21
#include "../afs/sysincludes.h" /* Standard vendor system headers */
22
#include "../afs/afsincludes.h" /* Afs-based standard headers */
23
#include "../afs/osi_inode.h"
24
#include "../afs/afs_stats.h" /* statistics stuff */
26
extern int (*ufs_iallocp)(), (*ufs_iupdatp)(), (*ufs_igetp)(),
27
(*ufs_itimes_nolockp)();
29
#define AFS_ITIMES(ip) { \
30
mutex_enter(&(ip)->i_tlock); \
31
(*ufs_itimes_nolockp)(ip); \
32
mutex_exit(&(ip)->i_tlock); \
35
#define AFS_ITIMES_NOLOCK(ip) \
36
(*ufs_itimes_nolockp)(ip);
38
getinode(vfsp, dev, inode, ipp, credp,perror)
40
struct AFS_UCRED *credp;
47
register afs_int32 code;
51
struct ufsvfs *ufsvfsp;
53
AFS_STATCNT(getinode);
58
#if !defined(AFS_SUN58_ENV)
59
&& !(vfsp = vfs_devsearch(dev))
61
&& !(vfsp = vfs_dev2vfsp(dev))
66
ufsvfsp = (struct ufsvfs *)vfsp->vfs_data;
68
#ifdef HAVE_VFS_DQRWLOCK
69
rw_enter(&ufsvfsp->vfs_dqrwlock, RW_READER);
71
code = (*ufs_igetp)(vfsp, inode, &ip, credp);
72
#ifdef HAVE_VFS_DQRWLOCK
73
rw_exit(&ufsvfsp->vfs_dqrwlock);
84
/* get an existing inode. Common code for iopen, iread/write, iinc/dec. */
85
igetinode(vfsp, dev, inode, ipp, credp,perror)
86
struct AFS_UCRED *credp;
93
struct inode *pip, *ip;
94
extern struct osi_dev cacheDev;
95
register int code = 0;
99
AFS_STATCNT(igetinode);
101
code = getinode(vfsp, dev, inode, &ip, credp,perror);
105
rw_enter(&ip->i_contents, RW_READER);
107
if (ip->i_mode == 0) {
108
/* Not an allocated inode */
109
rw_exit(&ip->i_contents);
114
if (ip->i_nlink == 0 || (ip->i_mode&IFMT) != IFREG) {
116
rw_exit(&ip->i_contents);
121
/* On VFS40 systems, iput does major synchronous write action, but only
122
when the reference count on the vnode goes to 0. Normally, Sun users
123
don't notice this because the DNLC keep references for them, but we
124
notice 'cause we don't. So, we make a fake dnlc entry which gets
125
cleaned up by iget when it needs the space. */
126
if (dev != cacheDev.dev) {
128
* Don't call dnlc for the cm inodes since it's a big performance
131
dnlc_enter(ITOV(ip), "a", ITOV(ip), (struct AFS_UCRED *) 0);
135
rw_exit(&ip->i_contents);
141
afs_syscall_icreate(dev, near_inode, param1, param2, param3, param4, rvp, credp)
143
struct AFS_UCRED *credp;
144
long near_inode, param1, param2, param3, param4;
148
struct inode *ip, *newip;
151
struct ufsvfs *ufsvfsp;
153
AFS_STATCNT(afs_syscall_icreate);
155
if (!afs_suser(credp))
158
/** Code to convert a 32 bit dev_t into a 64 bit dev_t
159
* This conversion is needed only for the 64 bit OS.
162
#ifdef AFS_SUN57_64BIT_ENV
163
newdev = expldev( (dev32_t) dev);
168
code = getinode(0, (dev_t)newdev, 2, &ip, credp,&dummy);
173
ufsvfsp = ip->i_ufsvfs;
174
rw_enter(&ip->i_rwlock, RW_WRITER);
175
#ifdef HAVE_VFS_DQRWLOCK
176
rw_enter(&ufsvfsp->vfs_dqrwlock, RW_READER);
178
rw_enter(&ip->i_contents, RW_WRITER);
179
code = (*ufs_iallocp)(ip, near_inode, 0, &newip, credp);
180
AFS_ITIMES_NOLOCK(ip);
181
rw_exit(&ip->i_contents);
182
#ifdef HAVE_VFS_DQRWLOCK
183
rw_exit(&ufsvfsp->vfs_dqrwlock);
185
rw_exit(&ip->i_rwlock);
191
rw_enter(&newip->i_contents, RW_WRITER);
192
newip->i_flag |= IACC|IUPD|ICHG;
194
#if defined(AFS_SUN56_ENV)
195
newip->i_vicemagic = VICEMAGIC;
201
newip->i_mode = IFREG;
202
newip->i_vnode.v_type = VREG;
204
newip->i_vicep1 = param1;
205
if (param2 == 0x1fffffff/*INODESPECIAL*/) {
206
newip->i_vicep2 = ((0x1fffffff << 3) + (param4 & 0x3));
207
newip->i_vicep3 = param3;
209
newip->i_vicep2 = (((param2 >> 16) & 0x1f) << 27) +
210
(((param4 >> 16) & 0x1f) << 22) +
212
newip->i_vicep3 = ((param4 << 16) + (param2 & 0xffff));
214
#ifdef AFS_SUN57_64BIT_ENV
215
rvp->r_vals = newip->i_number;
217
rvp->r_val1 = newip->i_number;
221
* We're being conservative and sync to the disk
224
(*ufs_iupdatp)(newip, 1);
225
AFS_ITIMES_NOLOCK(newip);
226
rw_exit(&newip->i_contents);
227
VN_RELE(ITOV(newip));
231
afs_syscall_iopen(dev, inode, usrmod, rvp, credp)
233
struct AFS_UCRED *credp;
239
struct vnode *vp = (struct vnode *)0;
245
AFS_STATCNT(afs_syscall_iopen);
247
if (!afs_suser(credp))
250
/** Code to convert a 32 bit dev_t into a 64 bit dev_t
251
* This conversion is needed only for the 64 bit OS.
254
#ifdef AFS_SUN57_64BIT_ENV
255
newdev = expldev( (dev32_t) dev);
260
code = igetinode(0, (dev_t)newdev, (ino_t)inode, &ip, credp,&dummy);
264
code = falloc((struct vnode *)NULL, FWRITE|FREAD, &fp, &fd);
266
rw_enter(&ip->i_contents, RW_READER);
268
rw_exit(&ip->i_contents);
273
/* fp->f_count, f_audit_data are set by falloc */
274
fp->f_vnode = ITOV(ip);
276
fp->f_flag = (usrmod+1) & (FMASK);
278
/* fp->f_count, f_msgcount are set by falloc */
280
/* fp->f_offset zeroed by falloc */
281
/* f_cred set by falloc */
283
* falloc returns the fp write locked
285
mutex_exit(&fp->f_tlock);
287
* XXX We should set the fp to null since we don't need it in the icalls
290
#ifdef AFS_SUN57_64BIT_ENV
301
afs_syscall_iincdec(dev, inode, inode_p1, amount, rvp, credp)
303
struct AFS_UCRED *credp;
304
int inode, inode_p1, amount;
309
register afs_int32 code;
312
if (!afs_suser(credp))
315
/** Code to convert a 32 bit dev_t into a 64 bit dev_t
316
* This conversion is needed only for the 64 bit OS.
319
#ifdef AFS_SUN57_64BIT_ENV
320
newdev = expldev( (dev32_t) dev);
325
code = igetinode(0, (dev_t)newdev, (ino_t)inode, &ip, credp,&dummy);
329
if (!IS_VICEMAGIC(ip)) {
331
rw_enter(&ip->i_contents, RW_READER);
333
rw_exit(&ip->i_contents);
336
rw_enter(&ip->i_contents, RW_WRITER);
337
ip->i_nlink += amount;
338
if (ip->i_nlink == 0) {
339
/* remove the "a" name added by igetinode so that the space is reclaimed. */
340
dnlc_remove(ITOV(ip), "a");
344
/* We may want to force the inode to the disk in case of crashes, other references, etc. */
346
(*ufs_iupdatp)(ip, 1);
347
AFS_ITIMES_NOLOCK(ip);
348
rw_exit(&ip->i_contents);