2 Copyright (C) 2003 - 2010 Chaskiel Grundman
5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions
9 1. Redistributions of source code must retain the above copyright
10 notice, this list of conditions and the following disclaimer.
12 2. Redistributions in binary form must reproduce the above copyright
13 notice, this list of conditions and the following disclaimer in the
14 documentation and/or other materials provided with the distribution.
16 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18 OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19 IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 #include <afsconfig.h>
28 #include <afs/param.h>
32 #include <afs/vlserver.h>
33 #include <afs/vldbint.h>
35 #include <afs/unified_afs.h>
37 #include "afscp_internal.h"
40 afscp_CreateFile(const struct afscp_venusfid
*dir
, char *name
,
41 struct AFSStoreStatus
*sst
, struct afscp_venusfid
**ret
)
44 struct AFSFid df
= dir
->fid
;
45 struct afscp_volume
*vol
;
46 struct AFSFetchStatus dfst
, fst
;
48 struct AFSCallBack cb
;
50 struct afscp_server
*server
;
51 struct rx_connection
*c
;
54 if (dir
== NULL
|| name
== NULL
|| sst
== NULL
) {
56 "afscp_CreateFile called with NULL args, cannot continue\n");
59 vol
= afscp_VolumeById(dir
->cell
, dir
->fid
.Volume
);
65 for (i
= 0; i
< vol
->nservers
; i
++) {
66 server
= afscp_ServerByIndex(vol
->servers
[i
]);
67 if (server
&& server
->naddrs
> 0) {
68 for (j
= 0; j
< server
->naddrs
; j
++) {
69 c
= afscp_ServerConnection(server
, j
);
74 code
= RXAFS_CreateFile(c
, &df
, name
, sst
, &ff
,
75 &fst
, &dfst
, &cb
, &vs
);
90 _StatStuff(dir
, &dfst
);
91 afscp_AddCallBack(server
, &ff
, &fst
, &cb
, now
);
93 *ret
= afscp_MakeFid(vol
->cell
, ff
.Volume
, ff
.Vnode
, ff
.Unique
);
98 afscp_MakeDir(const struct afscp_venusfid
*dir
, char *name
,
99 struct AFSStoreStatus
*sst
, struct afscp_venusfid
**ret
)
102 struct AFSFid df
= dir
->fid
;
103 struct afscp_volume
*vol
;
104 struct AFSFetchStatus dfst
, fst
;
105 struct AFSVolSync vs
;
106 struct AFSCallBack cb
;
108 struct afscp_server
*server
;
109 struct rx_connection
*c
;
112 vol
= afscp_VolumeById(dir
->cell
, dir
->fid
.Volume
);
114 afscp_errno
= ENOENT
;
118 for (i
= 0; i
< vol
->nservers
; i
++) {
119 server
= afscp_ServerByIndex(vol
->servers
[i
]);
120 if (server
&& server
->naddrs
> 0) {
121 for (j
= 0; j
< server
->naddrs
; j
++) {
122 c
= afscp_ServerConnection(server
, j
);
126 code
= RXAFS_MakeDir(c
, &df
, name
, sst
, &ff
,
127 &fst
, &dfst
, &cb
, &vs
);
136 _StatInvalidate(dir
);
140 _StatStuff(dir
, &dfst
);
141 afscp_AddCallBack(server
, &ff
, &fst
, &cb
, now
);
143 *ret
= afscp_MakeFid(vol
->cell
, ff
.Volume
, ff
.Vnode
, ff
.Unique
);
148 afscp_Symlink(const struct afscp_venusfid
*dir
, char *name
,
149 char *target
, struct AFSStoreStatus
*sst
)
152 struct AFSFid df
= dir
->fid
;
153 struct afscp_volume
*vol
;
154 struct AFSFetchStatus dfst
, fst
;
155 struct AFSVolSync vs
;
157 struct afscp_server
*server
;
158 struct rx_connection
*c
;
160 vol
= afscp_VolumeById(dir
->cell
, dir
->fid
.Volume
);
162 afscp_errno
= ENOENT
;
166 for (i
= 0; i
< vol
->nservers
; i
++) {
167 server
= afscp_ServerByIndex(vol
->servers
[i
]);
168 if (server
&& server
->naddrs
> 0) {
169 for (j
= 0; j
< server
->naddrs
; j
++) {
170 c
= afscp_ServerConnection(server
, j
);
173 code
= RXAFS_Symlink(c
, &df
, name
, target
, sst
,
174 &ff
, &fst
, &dfst
, &vs
);
183 _StatInvalidate(dir
);
187 _StatStuff(dir
, &dfst
);
193 afscp_Lock(const struct afscp_venusfid
*fid
, int locktype
)
196 struct AFSFid ff
= fid
->fid
;
197 struct afscp_volume
*vol
;
198 struct AFSVolSync vs
;
199 struct afscp_server
*server
;
200 struct rx_connection
*c
;
202 vol
= afscp_VolumeById(fid
->cell
, fid
->fid
.Volume
);
204 afscp_errno
= ENOENT
;
208 for (i
= 0; i
< vol
->nservers
; i
++) {
209 server
= afscp_ServerByIndex(vol
->servers
[i
]);
210 if (server
&& server
->naddrs
> 0) {
211 for (j
= 0; j
< server
->naddrs
; j
++) {
212 c
= afscp_ServerConnection(server
, j
);
215 if (locktype
== LockRelease
)
216 code
= RXAFS_ReleaseLock(c
, &ff
, &vs
);
217 /* read, write, extend */
218 else if (locktype
< LockRelease
)
219 code
= RXAFS_SetLock(c
, &ff
, locktype
, &vs
);
228 if ((code
== EAGAIN
) || (code
== UAEWOULDBLOCK
) || (code
== UAEAGAIN
))
238 afscp_RemoveFile(const struct afscp_venusfid
*dir
, char *name
)
241 struct AFSFid df
= dir
->fid
;
242 struct afscp_volume
*vol
;
243 struct AFSFetchStatus dfst
;
244 struct AFSVolSync vs
;
245 struct afscp_server
*server
;
246 struct rx_connection
*c
;
248 vol
= afscp_VolumeById(dir
->cell
, dir
->fid
.Volume
);
250 afscp_errno
= ENOENT
;
254 for (i
= 0; i
< vol
->nservers
; i
++) {
255 server
= afscp_ServerByIndex(vol
->servers
[i
]);
256 if (server
&& server
->naddrs
> 0) {
257 for (j
= 0; j
< server
->naddrs
; j
++) {
258 c
= afscp_ServerConnection(server
, j
);
261 code
= RXAFS_RemoveFile(c
, &df
, name
, &dfst
, &vs
);
270 _StatInvalidate(dir
);
274 _StatStuff(dir
, &dfst
);
279 afscp_RemoveDir(const struct afscp_venusfid
*dir
, char *name
)
282 struct AFSFid df
= dir
->fid
;
283 struct afscp_volume
*vol
;
284 struct AFSFetchStatus dfst
;
285 struct AFSVolSync vs
;
286 struct afscp_server
*server
;
287 struct rx_connection
*c
;
289 vol
= afscp_VolumeById(dir
->cell
, dir
->fid
.Volume
);
291 afscp_errno
= ENOENT
;
295 for (i
= 0; i
< vol
->nservers
; i
++) {
296 server
= afscp_ServerByIndex(vol
->servers
[i
]);
297 if (server
&& server
->naddrs
> 0) {
298 for (j
= 0; j
< server
->naddrs
; j
++) {
299 c
= afscp_ServerConnection(server
, j
);
302 code
= RXAFS_RemoveDir(c
, &df
, name
, &dfst
, &vs
);
311 _StatInvalidate(dir
);
315 _StatStuff(dir
, &dfst
);