union_vnops.c (06be2aaa8320ba839a837d20e35f35c3efdf7587) | union_vnops.c (fa288043e2c7d1d75b1bdae82704af2eace72de7) |
---|---|
1/* 2 * Copyright (c) 1992, 1993, 1994, 1995 Jan-Simon Pendry. 3 * Copyright (c) 1992, 1993, 1994, 1995 4 * The Regents of the University of California. All rights reserved. 5 * 6 * This code is derived from software contributed to Berkeley by 7 * Jan-Simon Pendry. 8 * --- 1210 unchanged lines hidden (view full) --- 1219 } 1220 union_unlock_upper(upperdvp, td); 1221 return (error); 1222} 1223 1224/* 1225 * union_link: 1226 * | 1/* 2 * Copyright (c) 1992, 1993, 1994, 1995 Jan-Simon Pendry. 3 * Copyright (c) 1992, 1993, 1994, 1995 4 * The Regents of the University of California. All rights reserved. 5 * 6 * This code is derived from software contributed to Berkeley by 7 * Jan-Simon Pendry. 8 * --- 1210 unchanged lines hidden (view full) --- 1219 } 1220 union_unlock_upper(upperdvp, td); 1221 return (error); 1222} 1223 1224/* 1225 * union_link: 1226 * |
1227 * tdvp will be locked on entry, vp will not be locked on entry. 1228 * tdvp should remain locked on return and vp should remain unlocked | 1227 * tdvp and vp will be locked on entry. 1228 * tdvp and vp should remain locked on return. |
1229 * on return. 1230 */ 1231 1232static int 1233union_link(ap) 1234 struct vop_link_args /* { 1235 struct vnode *a_tdvp; 1236 struct vnode *a_vp; --- 8 unchanged lines hidden (view full) --- 1245 int error = 0; 1246 1247 if (ap->a_tdvp->v_op != ap->a_vp->v_op) { 1248 vp = ap->a_vp; 1249 } else { 1250 struct union_node *tun = VTOUNION(ap->a_vp); 1251 1252 if (tun->un_uppervp == NULLVP) { | 1229 * on return. 1230 */ 1231 1232static int 1233union_link(ap) 1234 struct vop_link_args /* { 1235 struct vnode *a_tdvp; 1236 struct vnode *a_vp; --- 8 unchanged lines hidden (view full) --- 1245 int error = 0; 1246 1247 if (ap->a_tdvp->v_op != ap->a_vp->v_op) { 1248 vp = ap->a_vp; 1249 } else { 1250 struct union_node *tun = VTOUNION(ap->a_vp); 1251 1252 if (tun->un_uppervp == NULLVP) { |
1253 vn_lock(ap->a_vp, LK_EXCLUSIVE | LK_RETRY, td); | |
1254#if 0 1255 if (dun->un_uppervp == tun->un_dirvp) { 1256 if (dun->un_flags & UN_ULOCK) { 1257 dun->un_flags &= ~UN_ULOCK; 1258 VOP_UNLOCK(dun->un_uppervp, 0, td); 1259 } 1260 } 1261#endif 1262 error = union_copyup(tun, 1, cnp->cn_cred, td); 1263#if 0 1264 if (dun->un_uppervp == tun->un_dirvp) { 1265 vn_lock(dun->un_uppervp, 1266 LK_EXCLUSIVE | LK_RETRY, td); 1267 dun->un_flags |= UN_ULOCK; 1268 } 1269#endif | 1253#if 0 1254 if (dun->un_uppervp == tun->un_dirvp) { 1255 if (dun->un_flags & UN_ULOCK) { 1256 dun->un_flags &= ~UN_ULOCK; 1257 VOP_UNLOCK(dun->un_uppervp, 0, td); 1258 } 1259 } 1260#endif 1261 error = union_copyup(tun, 1, cnp->cn_cred, td); 1262#if 0 1263 if (dun->un_uppervp == tun->un_dirvp) { 1264 vn_lock(dun->un_uppervp, 1265 LK_EXCLUSIVE | LK_RETRY, td); 1266 dun->un_flags |= UN_ULOCK; 1267 } 1268#endif |
1270 VOP_UNLOCK(ap->a_vp, 0, td); | 1269 if (error) 1270 return (error); |
1271 } 1272 vp = tun->un_uppervp; | 1271 } 1272 vp = tun->un_uppervp; |
1273 vn_lock(vp, LK_EXCLUSIVE | LK_RETRY, td); |
|
1273 } 1274 | 1274 } 1275 |
1275 if (error) 1276 return (error); 1277 | |
1278 /* 1279 * Make sure upper is locked, then unlock the union directory we were 1280 * called with to avoid a deadlock while we are calling VOP_LINK on 1281 * the upper (with tdvp locked and vp not locked). Our ap->a_tdvp 1282 * is expected to be locked on return. 1283 */ 1284 1285 if ((tdvp = union_lock_upper(dun, td)) == NULLVP) 1286 return (EROFS); 1287 1288 VOP_UNLOCK(ap->a_tdvp, 0, td); /* unlock calling node */ 1289 error = VOP_LINK(tdvp, vp, cnp); /* call link on upper */ 1290 1291 /* | 1276 /* 1277 * Make sure upper is locked, then unlock the union directory we were 1278 * called with to avoid a deadlock while we are calling VOP_LINK on 1279 * the upper (with tdvp locked and vp not locked). Our ap->a_tdvp 1280 * is expected to be locked on return. 1281 */ 1282 1283 if ((tdvp = union_lock_upper(dun, td)) == NULLVP) 1284 return (EROFS); 1285 1286 VOP_UNLOCK(ap->a_tdvp, 0, td); /* unlock calling node */ 1287 error = VOP_LINK(tdvp, vp, cnp); /* call link on upper */ 1288 1289 /* |
1290 * Unlock tun->un_uppervp if we locked it above. 1291 */ 1292 if (ap->a_tdvp->v_op == ap->a_vp->v_op) 1293 VOP_UNLOCK(vp, 0, td); 1294 /* |
|
1292 * We have to unlock tdvp prior to relocking our calling node in | 1295 * We have to unlock tdvp prior to relocking our calling node in |
1293 * order to avoid a deadlock. | 1296 * order to avoid a deadlock. We also have to unlock ap->a_vp 1297 * before relocking the directory, but then we have to relock 1298 * ap->a_vp as our caller expects. |
1294 */ | 1299 */ |
1300 VOP_UNLOCK(ap->a_vp, 0, td); |
|
1295 union_unlock_upper(tdvp, td); 1296 vn_lock(ap->a_tdvp, LK_EXCLUSIVE | LK_RETRY, td); | 1301 union_unlock_upper(tdvp, td); 1302 vn_lock(ap->a_tdvp, LK_EXCLUSIVE | LK_RETRY, td); |
1303 vn_lock(ap->a_vp, LK_EXCLUSIVE | LK_RETRY, td); |
|
1297 return (error); 1298} 1299 1300static int 1301union_rename(ap) 1302 struct vop_rename_args /* { 1303 struct vnode *a_fdvp; 1304 struct vnode *a_fvp; --- 657 unchanged lines hidden --- | 1304 return (error); 1305} 1306 1307static int 1308union_rename(ap) 1309 struct vop_rename_args /* { 1310 struct vnode *a_fdvp; 1311 struct vnode *a_fvp; --- 657 unchanged lines hidden --- |