@@ -2204,3 +2204,191 @@ int yfs_fs_inline_bulk_status(struct afs_fs_cursor *fc,
22042204	afs_make_call (& fc -> ac , call , GFP_NOFS );
22052205	return  afs_wait_for_call_to_complete (call , & fc -> ac );
22062206}
2207+ 
2208+ /* 
2209+  * Deliver reply data to an YFS.FetchOpaqueACL. 
2210+  */ 
2211+ static  int  yfs_deliver_fs_fetch_opaque_acl (struct  afs_call  * call )
2212+ {
2213+ 	struct  afs_volsync  * volsync  =  call -> reply [2 ];
2214+ 	struct  afs_vnode  * vnode  =  call -> reply [1 ];
2215+ 	struct  yfs_acl  * yacl  =   call -> reply [0 ];
2216+ 	struct  afs_acl  * acl ;
2217+ 	const  __be32  * bp ;
2218+ 	unsigned int   size ;
2219+ 	int  ret ;
2220+ 
2221+ 	_enter ("{%u}" , call -> unmarshall );
2222+ 
2223+ 	switch  (call -> unmarshall ) {
2224+ 	case  0 :
2225+ 		afs_extract_to_tmp (call );
2226+ 		call -> unmarshall ++ ;
2227+ 
2228+ 		/* Extract the file ACL length */ 
2229+ 	case  1 :
2230+ 		ret  =  afs_extract_data (call , true);
2231+ 		if  (ret  <  0 )
2232+ 			return  ret ;
2233+ 
2234+ 		size  =  call -> count2  =  ntohl (call -> tmp );
2235+ 		size  =  round_up (size , 4 );
2236+ 
2237+ 		if  (yacl -> flags  &  YFS_ACL_WANT_ACL ) {
2238+ 			acl  =  kmalloc (struct_size (acl , data , size ), GFP_KERNEL );
2239+ 			if  (!acl )
2240+ 				return  - ENOMEM ;
2241+ 			yacl -> acl  =  acl ;
2242+ 			acl -> size  =  call -> count2 ;
2243+ 			afs_extract_begin (call , acl -> data , size );
2244+ 		} else  {
2245+ 			iov_iter_discard (& call -> iter , READ , size );
2246+ 		}
2247+ 		call -> unmarshall ++ ;
2248+ 
2249+ 		/* Extract the file ACL */ 
2250+ 	case  2 :
2251+ 		ret  =  afs_extract_data (call , true);
2252+ 		if  (ret  <  0 )
2253+ 			return  ret ;
2254+ 
2255+ 		afs_extract_to_tmp (call );
2256+ 		call -> unmarshall ++ ;
2257+ 
2258+ 		/* Extract the volume ACL length */ 
2259+ 	case  3 :
2260+ 		ret  =  afs_extract_data (call , true);
2261+ 		if  (ret  <  0 )
2262+ 			return  ret ;
2263+ 
2264+ 		size  =  call -> count2  =  ntohl (call -> tmp );
2265+ 		size  =  round_up (size , 4 );
2266+ 
2267+ 		if  (yacl -> flags  &  YFS_ACL_WANT_VOL_ACL ) {
2268+ 			acl  =  kmalloc (struct_size (acl , data , size ), GFP_KERNEL );
2269+ 			if  (!acl )
2270+ 				return  - ENOMEM ;
2271+ 			yacl -> vol_acl  =  acl ;
2272+ 			acl -> size  =  call -> count2 ;
2273+ 			afs_extract_begin (call , acl -> data , size );
2274+ 		} else  {
2275+ 			iov_iter_discard (& call -> iter , READ , size );
2276+ 		}
2277+ 		call -> unmarshall ++ ;
2278+ 
2279+ 		/* Extract the volume ACL */ 
2280+ 	case  4 :
2281+ 		ret  =  afs_extract_data (call , true);
2282+ 		if  (ret  <  0 )
2283+ 			return  ret ;
2284+ 
2285+ 		afs_extract_to_buf (call ,
2286+ 				   sizeof (__be32 ) *  2  + 
2287+ 				   sizeof (struct  yfs_xdr_YFSFetchStatus ) + 
2288+ 				   sizeof (struct  yfs_xdr_YFSVolSync ));
2289+ 		call -> unmarshall ++ ;
2290+ 
2291+ 		/* extract the metadata */ 
2292+ 	case  5 :
2293+ 		ret  =  afs_extract_data (call , false);
2294+ 		if  (ret  <  0 )
2295+ 			return  ret ;
2296+ 
2297+ 		bp  =  call -> buffer ;
2298+ 		yacl -> inherit_flag  =  ntohl (* bp ++ );
2299+ 		yacl -> num_cleaned  =  ntohl (* bp ++ );
2300+ 		ret  =  yfs_decode_status (call , & bp , & vnode -> status , vnode ,
2301+ 					& call -> expected_version , NULL );
2302+ 		if  (ret  <  0 )
2303+ 			return  ret ;
2304+ 		xdr_decode_YFSVolSync (& bp , volsync );
2305+ 
2306+ 		call -> unmarshall ++ ;
2307+ 
2308+ 	case  6 :
2309+ 		break ;
2310+ 	}
2311+ 
2312+ 	_leave (" = 0 [done]" );
2313+ 	return  0 ;
2314+ }
2315+ 
2316+ void  yfs_free_opaque_acl (struct  yfs_acl  * yacl )
2317+ {
2318+ 	if  (yacl ) {
2319+ 		kfree (yacl -> acl );
2320+ 		kfree (yacl -> vol_acl );
2321+ 		kfree (yacl );
2322+ 	}
2323+ }
2324+ 
2325+ static  void  yfs_destroy_fs_fetch_opaque_acl (struct  afs_call  * call )
2326+ {
2327+ 	yfs_free_opaque_acl (call -> reply [0 ]);
2328+ 	afs_flat_call_destructor (call );
2329+ }
2330+ 
2331+ /* 
2332+  * YFS.FetchOpaqueACL operation type 
2333+  */ 
2334+ static  const  struct  afs_call_type  yfs_RXYFSFetchOpaqueACL  =  {
2335+ 	.name 		=  "YFS.FetchOpaqueACL" ,
2336+ 	.op 		=  yfs_FS_FetchOpaqueACL ,
2337+ 	.deliver 	=  yfs_deliver_fs_fetch_opaque_acl ,
2338+ 	.destructor 	=  yfs_destroy_fs_fetch_opaque_acl ,
2339+ };
2340+ 
2341+ /* 
2342+  * Fetch the YFS advanced ACLs for a file. 
2343+  */ 
2344+ struct  yfs_acl  * yfs_fs_fetch_opaque_acl (struct  afs_fs_cursor  * fc ,
2345+ 					unsigned int   flags )
2346+ {
2347+ 	struct  afs_vnode  * vnode  =  fc -> vnode ;
2348+ 	struct  afs_call  * call ;
2349+ 	struct  yfs_acl  * yacl ;
2350+ 	struct  afs_net  * net  =  afs_v2net (vnode );
2351+ 	__be32  * bp ;
2352+ 
2353+ 	_enter (",%x,{%llx:%llu},," ,
2354+ 	       key_serial (fc -> key ), vnode -> fid .vid , vnode -> fid .vnode );
2355+ 
2356+ 	call  =  afs_alloc_flat_call (net , & yfs_RXYFSFetchOpaqueACL ,
2357+ 				   sizeof (__be32 ) *  2  + 
2358+ 				   sizeof (struct  yfs_xdr_YFSFid ),
2359+ 				   sizeof (__be32 ) *  2  + 
2360+ 				   sizeof (struct  yfs_xdr_YFSFetchStatus ) + 
2361+ 				   sizeof (struct  yfs_xdr_YFSVolSync ));
2362+ 	if  (!call )
2363+ 		goto nomem ;
2364+ 
2365+ 	yacl  =  kzalloc (sizeof (struct  yfs_acl ), GFP_KERNEL );
2366+ 	if  (!yacl )
2367+ 		goto nomem_call ;
2368+ 
2369+ 	yacl -> flags  =  flags ;
2370+ 	call -> key  =  fc -> key ;
2371+ 	call -> reply [0 ] =  yacl ;
2372+ 	call -> reply [1 ] =  vnode ;
2373+ 	call -> reply [2 ] =  NULL ; /* volsync */ 
2374+ 	call -> ret_reply0  =  true;
2375+ 
2376+ 	/* marshall the parameters */ 
2377+ 	bp  =  call -> request ;
2378+ 	bp  =  xdr_encode_u32 (bp , YFSFETCHOPAQUEACL );
2379+ 	bp  =  xdr_encode_u32 (bp , 0 ); /* RPC flags */ 
2380+ 	bp  =  xdr_encode_YFSFid (bp , & vnode -> fid );
2381+ 	yfs_check_req (call , bp );
2382+ 
2383+ 	call -> cb_break  =  fc -> cb_break ;
2384+ 	afs_use_fs_server (call , fc -> cbi );
2385+ 	trace_afs_make_fs_call (call , & vnode -> fid );
2386+ 	afs_make_call (& fc -> ac , call , GFP_KERNEL );
2387+ 	return  (struct  yfs_acl  * )afs_wait_for_call_to_complete (call , & fc -> ac );
2388+ 
2389+ nomem_call :
2390+ 	afs_put_call (call );
2391+ nomem :
2392+ 	fc -> ac .error  =  - ENOMEM ;
2393+ 	return  ERR_PTR (- ENOMEM );
2394+ }
0 commit comments