extern struct vfs *afs_globalVFS;
#endif
+
/* copy out attributes from cache entry */
int
afs_CopyOutAttrs(register struct vcache *avc, register struct vattr *attrs)
{
afs_int32 code;
struct vrequest treq;
- extern struct unixuser *afs_FindUser();
struct unixuser *au;
int inited = 0;
OSI_VC_CONVERT(avc);
#elif defined(AFS_AIX_ENV)
/* Boy, was this machine dependent bogosity hard to swallow????.... */
if (av->va_mode != -1) {
-#elif defined(AFS_LINUX22_ENV)
+#elif defined(AFS_LINUX22_ENV) || defined(UKERNEL)
if (av->va_mask & ATTR_MODE) {
#elif defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (av->va_mask & AT_MODE) {
}
#if defined(AFS_DARWIN80_ENV)
if (VATTR_IS_ACTIVE(av, va_gid)) {
-#elif defined(AFS_LINUX22_ENV)
+#elif defined(AFS_LINUX22_ENV) || defined(UKERNEL)
if (av->va_mask & ATTR_GID) {
#elif defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (av->va_mask & AT_GID) {
}
#if defined(AFS_DARWIN80_ENV)
if (VATTR_IS_ACTIVE(av, va_uid)) {
-#elif defined(AFS_LINUX22_ENV)
+#elif defined(AFS_LINUX22_ENV) || defined(UKERNEL)
if (av->va_mask & ATTR_UID) {
#elif defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (av->va_mask & AT_UID) {
}
#if defined(AFS_DARWIN80_ENV)
if (VATTR_IS_ACTIVE(av, va_modify_time)) {
-#elif defined(AFS_LINUX22_ENV)
+#elif defined(AFS_LINUX22_ENV) || defined(UKERNEL)
if (av->va_mask & ATTR_MTIME) {
#elif defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (av->va_mask & AT_MTIME) {
*/
#if defined(AFS_DARWIN80_ENV)
if (VATTR_IS_ACTIVE(attrs, va_data_size)) {
-#elif defined(AFS_LINUX22_ENV)
+#elif defined(AFS_LINUX22_ENV) || defined(UKERNEL)
if (attrs->va_mask & ATTR_SIZE) {
#elif defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (attrs->va_mask & AT_SIZE) {
}
}
- if (AFS_IS_DISCONNECTED && !AFS_IS_LOGGING) {
+ if (AFS_IS_DISCONNECTED && !AFS_IS_DISCON_RW) {
code = ENETDOWN;
goto done;
}
#endif
#if defined(AFS_DARWIN80_ENV)
if (VATTR_IS_ACTIVE(attrs, va_data_size)) {
-#elif defined(AFS_LINUX22_ENV)
+#elif defined(AFS_LINUX22_ENV) || defined(UKERNEL)
if (attrs->va_mask & ATTR_SIZE) {
#elif defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (attrs->va_mask & AT_SIZE) {
#elif defined(AFS_OSF_ENV) || defined(AFS_XBSD_ENV)
if (attrs->va_size != VNOVAL) {
-#else
+#elif defined(AFS_AIX41_ENV)
if (attrs->va_size != -1) {
+#else
+ if (attrs->va_size != ~0) {
#endif
afs_size_t tsize = attrs->va_size;
ObtainWriteLock(&avc->lock, 128);
avc->states |= CDirty;
+
code = afs_TruncateAllSegments(avc, tsize, &treq, acred);
+#ifdef AFS_LINUX_26_ENV
+ /* We must update the Linux kernel's idea of file size as soon as
+ * possible, to avoid racing with delayed writepages delivered by
+ * pdflush */
+ if (code == 0)
+ i_size_write(AFSTOV(avc), tsize);
+#endif
/* if date not explicitly set by this call, set it ourselves, since we
* changed the data */
if (!(astat.Mask & AFS_SETMODTIME)) {
astat.Mask |= AFS_SETMODTIME;
astat.ClientModTime = osi_Time();
}
+
if (code == 0) {
if (((avc->execsOrWriters <= 0) && (avc->states & CCreating) == 0)
|| (avc->execsOrWriters == 1 && AFS_NFSXLATORREQ(acred))) {
- code = afs_StoreAllSegments(avc, &treq, AFS_ASYNC);
- if (!code)
- avc->states &= ~CDirty;
+
+ /* Store files now if not disconnected. */
+ /* XXX: AFS_IS_DISCON_RW handled. */
+ if (!AFS_IS_DISCONNECTED) {
+ code = afs_StoreAllSegments(avc, &treq, AFS_ASYNC);
+ if (!code)
+ avc->states &= ~CDirty;
+ }
}
} else
avc->states &= ~CDirty;
osi_dnlc_purgedp(avc);
/* error? erase any changes we made to vcache entry */
}
+
+#if defined(AFS_DISCON_ENV)
} else {
- /* Must be logging - but not implemented yet ... */
- code = ENETDOWN;
- }
+
+ ObtainSharedLock(&avc->lock, 712);
+ /* Write changes locally. */
+ code = afs_WriteVCacheDiscon(avc, &astat, attrs);
+ ReleaseSharedLock(&avc->lock);
+#endif
+ } /* if (!AFS_IS_DISCONNECTED) */
+
#if defined(AFS_SUN5_ENV) || defined(AFS_SGI_ENV)
if (AFS_NFSXLATORREQ(acred)) {
avc->execsOrWriters--;