15331Samw /* 25331Samw * CDDL HEADER START 35331Samw * 45331Samw * The contents of this file are subject to the terms of the 55331Samw * Common Development and Distribution License (the "License"). 65331Samw * You may not use this file except in compliance with the License. 75331Samw * 85331Samw * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 95331Samw * or http://www.opensolaris.org/os/licensing. 105331Samw * See the License for the specific language governing permissions 115331Samw * and limitations under the License. 125331Samw * 135331Samw * When distributing Covered Code, include this CDDL HEADER in each 145331Samw * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 155331Samw * If applicable, add the following below this CDDL HEADER, with the 165331Samw * fields enclosed by brackets "[]" replaced with your own identifying 175331Samw * information: Portions Copyright [yyyy] [name of copyright owner] 185331Samw * 195331Samw * CDDL HEADER END 205331Samw */ 215331Samw /* 22*11963SAfshin.Ardakani@Sun.COM * Copyright 2010 Sun Microsystems, Inc. All rights reserved. 235331Samw * Use is subject to license terms. 245331Samw */ 255331Samw 265331Samw /* 27*11963SAfshin.Ardakani@Sun.COM * Net DFS server side RPC service for managing DFS namespaces. 28*11963SAfshin.Ardakani@Sun.COM * 29*11963SAfshin.Ardakani@Sun.COM * For more details refer to following Microsoft specification: 30*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM] 31*11963SAfshin.Ardakani@Sun.COM * Distributed File System (DFS): Namespace Management Protocol Specification 325331Samw */ 335331Samw 34*11963SAfshin.Ardakani@Sun.COM #include <unistd.h> 35*11963SAfshin.Ardakani@Sun.COM #include <libgen.h> 365331Samw #include <strings.h> 37*11963SAfshin.Ardakani@Sun.COM #include <sys/sysmacros.h> 385331Samw 39*11963SAfshin.Ardakani@Sun.COM #include <smbsrv/ndl/netdfs.ndl> 405331Samw #include <smbsrv/nmpipes.h> 415331Samw #include <smbsrv/nterror.h> 42*11963SAfshin.Ardakani@Sun.COM #include <smbsrv/libmlsvc.h> 43*11963SAfshin.Ardakani@Sun.COM #include <dfs.h> 445331Samw 45*11963SAfshin.Ardakani@Sun.COM /* 46*11963SAfshin.Ardakani@Sun.COM * Depends on the information level requested around 4000 or more links 47*11963SAfshin.Ardakani@Sun.COM * can be provided with this buffer size. The limitation here is due 48*11963SAfshin.Ardakani@Sun.COM * to some problem in NDR and/or opipe layer so: 49*11963SAfshin.Ardakani@Sun.COM * 50*11963SAfshin.Ardakani@Sun.COM * - Do NOT increase the buffer size until that problem is fixed 51*11963SAfshin.Ardakani@Sun.COM * - The buffer size should be increased when the problem is fixed 52*11963SAfshin.Ardakani@Sun.COM * so the 4000 link limitation is removed. 53*11963SAfshin.Ardakani@Sun.COM */ 54*11963SAfshin.Ardakani@Sun.COM #define NETDFS_MAXBUFLEN (800 * 1024) 55*11963SAfshin.Ardakani@Sun.COM #define NETDFS_MAXPREFLEN ((uint32_t)(-1)) 565331Samw 57*11963SAfshin.Ardakani@Sun.COM typedef struct netdfs_enumhandle_t { 58*11963SAfshin.Ardakani@Sun.COM uint32_t de_level; /* level of detail being requested */ 59*11963SAfshin.Ardakani@Sun.COM uint32_t de_prefmaxlen; /* client MAX size buffer preference */ 60*11963SAfshin.Ardakani@Sun.COM uint32_t de_resume; /* client resume handle */ 61*11963SAfshin.Ardakani@Sun.COM uint32_t de_bavail; /* remaining buffer space in bytes */ 62*11963SAfshin.Ardakani@Sun.COM uint32_t de_ntotal; /* total number of objects */ 63*11963SAfshin.Ardakani@Sun.COM uint32_t de_nmax; /* MAX number of objects to return */ 64*11963SAfshin.Ardakani@Sun.COM uint32_t de_nitems; /* number of objects in buf */ 65*11963SAfshin.Ardakani@Sun.COM uint32_t de_nskip; /* number of objects to skip */ 66*11963SAfshin.Ardakani@Sun.COM void *de_entries; /* ndr buffer */ 67*11963SAfshin.Ardakani@Sun.COM } netdfs_enumhandle_t; 685331Samw 698334SJose.Borrego@Sun.COM static int netdfs_s_getver(void *, ndr_xa_t *); 708334SJose.Borrego@Sun.COM static int netdfs_s_add(void *, ndr_xa_t *); 718334SJose.Borrego@Sun.COM static int netdfs_s_remove(void *, ndr_xa_t *); 728334SJose.Borrego@Sun.COM static int netdfs_s_setinfo(void *, ndr_xa_t *); 738334SJose.Borrego@Sun.COM static int netdfs_s_getinfo(void *, ndr_xa_t *); 748334SJose.Borrego@Sun.COM static int netdfs_s_enum(void *, ndr_xa_t *); 758334SJose.Borrego@Sun.COM static int netdfs_s_move(void *, ndr_xa_t *); 768334SJose.Borrego@Sun.COM static int netdfs_s_rename(void *, ndr_xa_t *); 778334SJose.Borrego@Sun.COM static int netdfs_s_addstdroot(void *, ndr_xa_t *); 788334SJose.Borrego@Sun.COM static int netdfs_s_remstdroot(void *, ndr_xa_t *); 798334SJose.Borrego@Sun.COM static int netdfs_s_enumex(void *, ndr_xa_t *); 805331Samw 81*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_setinfo_100(dfs_path_t *, netdfs_info100_t *); 82*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_setinfo_101(dfs_path_t *, netdfs_info101_t *, 83*11963SAfshin.Ardakani@Sun.COM const char *, const char *); 84*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_setinfo_102(dfs_path_t *, netdfs_info102_t *); 85*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_setinfo_103(dfs_path_t *, netdfs_info103_t *); 86*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_setinfo_104(dfs_path_t *, netdfs_info104_t *, 87*11963SAfshin.Ardakani@Sun.COM const char *, const char *); 88*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_setinfo_105(dfs_path_t *, netdfs_info105_t *); 89*11963SAfshin.Ardakani@Sun.COM 90*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_1(netdfs_info1_t *, dfs_info_t *, ndr_xa_t *, 91*11963SAfshin.Ardakani@Sun.COM uint32_t *); 92*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_2(netdfs_info2_t *, dfs_info_t *, ndr_xa_t *, 93*11963SAfshin.Ardakani@Sun.COM uint32_t *); 94*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_3(netdfs_info3_t *, dfs_info_t *, ndr_xa_t *, 95*11963SAfshin.Ardakani@Sun.COM uint32_t *); 96*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_4(netdfs_info4_t *, dfs_info_t *, ndr_xa_t *, 97*11963SAfshin.Ardakani@Sun.COM uint32_t *); 98*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_5(netdfs_info5_t *, dfs_info_t *, ndr_xa_t *, 99*11963SAfshin.Ardakani@Sun.COM uint32_t *); 100*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_6(netdfs_info6_t *, dfs_info_t *, ndr_xa_t *, 101*11963SAfshin.Ardakani@Sun.COM uint32_t *); 102*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_100(netdfs_info100_t *, dfs_info_t *, ndr_xa_t *, 103*11963SAfshin.Ardakani@Sun.COM uint32_t *); 104*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_info_300(netdfs_info300_t *, dfs_info_t *, ndr_xa_t *, 105*11963SAfshin.Ardakani@Sun.COM uint32_t *); 106*11963SAfshin.Ardakani@Sun.COM 107*11963SAfshin.Ardakani@Sun.COM static uint32_t netdfs_enum_common(netdfs_enumhandle_t *, ndr_xa_t *); 108*11963SAfshin.Ardakani@Sun.COM 109*11963SAfshin.Ardakani@Sun.COM static void netdfs_path_create(const char *); 110*11963SAfshin.Ardakani@Sun.COM static void netdfs_path_remove(smb_unc_t *); 111*11963SAfshin.Ardakani@Sun.COM static boolean_t netdfs_guid_fromstr(char *, netdfs_uuid_t *); 112*11963SAfshin.Ardakani@Sun.COM 1138334SJose.Borrego@Sun.COM static ndr_stub_table_t netdfs_stub_table[] = { 1145331Samw { netdfs_s_getver, NETDFS_OPNUM_GETVER }, 1155331Samw { netdfs_s_add, NETDFS_OPNUM_ADD }, 1165331Samw { netdfs_s_remove, NETDFS_OPNUM_REMOVE }, 1175331Samw { netdfs_s_setinfo, NETDFS_OPNUM_SETINFO }, 1185331Samw { netdfs_s_getinfo, NETDFS_OPNUM_GETINFO }, 1195331Samw { netdfs_s_enum, NETDFS_OPNUM_ENUM }, 1205331Samw { netdfs_s_rename, NETDFS_OPNUM_RENAME }, 1215331Samw { netdfs_s_move, NETDFS_OPNUM_MOVE }, 1225331Samw { netdfs_s_addstdroot, NETDFS_OPNUM_ADDSTDROOT }, 1235331Samw { netdfs_s_remstdroot, NETDFS_OPNUM_REMSTDROOT }, 1245331Samw { netdfs_s_enumex, NETDFS_OPNUM_ENUMEX }, 1255331Samw {0} 1265331Samw }; 1275331Samw 1288334SJose.Borrego@Sun.COM static ndr_service_t netdfs_service = { 1295331Samw "NETDFS", /* name */ 1305331Samw "DFS", /* desc */ 131*11963SAfshin.Ardakani@Sun.COM "\\netdfs", /* endpoint */ 132*11963SAfshin.Ardakani@Sun.COM PIPE_NETDFS, /* sec_addr_port */ 1335331Samw NETDFS_ABSTRACT_UUID, NETDFS_ABSTRACT_VERS, 1345331Samw NETDFS_TRANSFER_UUID, NETDFS_TRANSFER_VERS, 1355331Samw 1365331Samw 0, /* no bind_instance_size */ 1375331Samw 0, /* no bind_req() */ 1385331Samw 0, /* no unbind_and_close() */ 1395331Samw 0, /* use generic_call_stub() */ 1405331Samw 1415331Samw &TYPEINFO(netdfs_interface), /* interface ti */ 1425331Samw netdfs_stub_table /* stub_table */ 1435331Samw }; 1445331Samw 1455331Samw /* 1465331Samw * Register the NETDFS RPC interface with the RPC runtime library. 1475331Samw * The service must be registered in order to use either the client 1485331Samw * side or the server side functions. 1495331Samw */ 1505331Samw void 1515331Samw netdfs_initialize(void) 1525331Samw { 1538334SJose.Borrego@Sun.COM (void) ndr_svc_register(&netdfs_service); 154*11963SAfshin.Ardakani@Sun.COM dfs_init(); 155*11963SAfshin.Ardakani@Sun.COM } 156*11963SAfshin.Ardakani@Sun.COM 157*11963SAfshin.Ardakani@Sun.COM void 158*11963SAfshin.Ardakani@Sun.COM netdfs_finalize(void) 159*11963SAfshin.Ardakani@Sun.COM { 160*11963SAfshin.Ardakani@Sun.COM dfs_fini(); 1615331Samw } 1625331Samw 1635331Samw /* 164*11963SAfshin.Ardakani@Sun.COM * Returns the version number of the DFS server in use on the server. 1655331Samw * 166*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsManagerGetVersion (Opnum 0) 1675331Samw */ 1685331Samw /*ARGSUSED*/ 1695331Samw static int 1708334SJose.Borrego@Sun.COM netdfs_s_getver(void *arg, ndr_xa_t *mxa) 1715331Samw { 1725331Samw struct netdfs_getver *param = arg; 1735331Samw 174*11963SAfshin.Ardakani@Sun.COM param->version = DFS_MANAGER_VERSION_NT4; 1758334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 1765331Samw } 1775331Samw 1785331Samw /* 179*11963SAfshin.Ardakani@Sun.COM * Creates a new DFS link or adds a new target to an existing link of a 180*11963SAfshin.Ardakani@Sun.COM * DFS namespace. 181*11963SAfshin.Ardakani@Sun.COM * 182*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsAdd (Opnum 1) 1835331Samw */ 1845331Samw static int 1858334SJose.Borrego@Sun.COM netdfs_s_add(void *arg, ndr_xa_t *mxa) 1865331Samw { 187*11963SAfshin.Ardakani@Sun.COM netdfs_add_t *param = arg; 188*11963SAfshin.Ardakani@Sun.COM dfs_path_t path; 189*11963SAfshin.Ardakani@Sun.COM uint32_t status; 190*11963SAfshin.Ardakani@Sun.COM const char *uncpath = (const char *)param->dfs_path; 191*11963SAfshin.Ardakani@Sun.COM const char *fspath = (const char *)path.p_fspath; 192*11963SAfshin.Ardakani@Sun.COM boolean_t newlink; 193*11963SAfshin.Ardakani@Sun.COM 194*11963SAfshin.Ardakani@Sun.COM if (!ndr_is_admin(mxa)) { 195*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_ACCESS_DENIED; 196*11963SAfshin.Ardakani@Sun.COM return (NDR_DRC_OK); 197*11963SAfshin.Ardakani@Sun.COM } 1985331Samw 199*11963SAfshin.Ardakani@Sun.COM if (param->server == NULL || param->share == NULL) { 200*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_INVALID_PARAMETER; 201*11963SAfshin.Ardakani@Sun.COM return (NDR_DRC_OK); 202*11963SAfshin.Ardakani@Sun.COM } 203*11963SAfshin.Ardakani@Sun.COM 204*11963SAfshin.Ardakani@Sun.COM switch (param->flags) { 205*11963SAfshin.Ardakani@Sun.COM case DFS_CREATE_VOLUME: 206*11963SAfshin.Ardakani@Sun.COM case DFS_ADD_VOLUME: 207*11963SAfshin.Ardakani@Sun.COM case DFS_RESTORE_VOLUME: 208*11963SAfshin.Ardakani@Sun.COM case (DFS_ADD_VOLUME | DFS_RESTORE_VOLUME): 209*11963SAfshin.Ardakani@Sun.COM break; 210*11963SAfshin.Ardakani@Sun.COM default: 2115331Samw param->status = ERROR_INVALID_PARAMETER; 2128334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 2135331Samw } 2145331Samw 215*11963SAfshin.Ardakani@Sun.COM status = dfs_path_parse(&path, uncpath, DFS_OBJECT_LINK); 216*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) { 217*11963SAfshin.Ardakani@Sun.COM param->status = status; 218*11963SAfshin.Ardakani@Sun.COM return (NDR_DRC_OK); 2195331Samw } 2205331Samw 221*11963SAfshin.Ardakani@Sun.COM status = smb_name_validate_rpath(path.p_unc.unc_path); 222*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) { 223*11963SAfshin.Ardakani@Sun.COM dfs_path_free(&path); 2245331Samw param->status = status; 2258334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 2265331Samw } 2275331Samw 228*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 229*11963SAfshin.Ardakani@Sun.COM 230*11963SAfshin.Ardakani@Sun.COM netdfs_path_create(fspath); 231*11963SAfshin.Ardakani@Sun.COM 232*11963SAfshin.Ardakani@Sun.COM status = dfs_link_add(fspath, (const char *)param->server, 233*11963SAfshin.Ardakani@Sun.COM (const char *)param->share, (const char *)param->comment, 234*11963SAfshin.Ardakani@Sun.COM param->flags, &newlink); 235*11963SAfshin.Ardakani@Sun.COM 236*11963SAfshin.Ardakani@Sun.COM if (newlink) 237*11963SAfshin.Ardakani@Sun.COM (void) dfs_cache_add_byname(path.p_unc.unc_share, 238*11963SAfshin.Ardakani@Sun.COM path.p_unc.unc_path, DFS_OBJECT_LINK); 239*11963SAfshin.Ardakani@Sun.COM 240*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 241*11963SAfshin.Ardakani@Sun.COM netdfs_path_remove(&path.p_unc); 242*11963SAfshin.Ardakani@Sun.COM 243*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 244*11963SAfshin.Ardakani@Sun.COM 245*11963SAfshin.Ardakani@Sun.COM dfs_path_free(&path); 246*11963SAfshin.Ardakani@Sun.COM param->status = status; 2478334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 2485331Samw } 2495331Samw 2505331Samw /* 251*11963SAfshin.Ardakani@Sun.COM * Removes a link or a link target from a DFS namespace. A link can be 252*11963SAfshin.Ardakani@Sun.COM * removed regardless of the number of targets associated with it. 2535331Samw * 254*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsRemove (Opnum 2) 2555331Samw */ 2565331Samw static int 2578334SJose.Borrego@Sun.COM netdfs_s_remove(void *arg, ndr_xa_t *mxa) 2585331Samw { 2595331Samw struct netdfs_remove *param = arg; 260*11963SAfshin.Ardakani@Sun.COM dfs_path_t path; 261*11963SAfshin.Ardakani@Sun.COM uint32_t status, stat; 262*11963SAfshin.Ardakani@Sun.COM const char *uncpath = (const char *)param->dfs_path; 263*11963SAfshin.Ardakani@Sun.COM const char *fspath = (const char *)path.p_fspath; 2645331Samw 265*11963SAfshin.Ardakani@Sun.COM if (!ndr_is_admin(mxa)) { 266*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_ACCESS_DENIED; 267*11963SAfshin.Ardakani@Sun.COM return (NDR_DRC_OK); 268*11963SAfshin.Ardakani@Sun.COM } 269*11963SAfshin.Ardakani@Sun.COM 270*11963SAfshin.Ardakani@Sun.COM /* both server and share must be NULL or non-NULL */ 271*11963SAfshin.Ardakani@Sun.COM if ((param->server == NULL && param->share != NULL) || 272*11963SAfshin.Ardakani@Sun.COM (param->server != NULL && param->share == NULL)) { 2735331Samw param->status = ERROR_INVALID_PARAMETER; 2748334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 2755331Samw } 2765331Samw 277*11963SAfshin.Ardakani@Sun.COM status = dfs_path_parse(&path, uncpath, DFS_OBJECT_LINK); 278*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) { 2795331Samw param->status = status; 2808334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 2815331Samw } 2825331Samw 283*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 284*11963SAfshin.Ardakani@Sun.COM 285*11963SAfshin.Ardakani@Sun.COM status = dfs_link_remove(fspath, (const char *)param->server, 286*11963SAfshin.Ardakani@Sun.COM (const char *)param->share); 287*11963SAfshin.Ardakani@Sun.COM 288*11963SAfshin.Ardakani@Sun.COM if (status == ERROR_SUCCESS) { 289*11963SAfshin.Ardakani@Sun.COM if (dfs_link_stat(fspath, &stat) == ERROR_SUCCESS) { 290*11963SAfshin.Ardakani@Sun.COM if (stat != DFS_STAT_ISDFS) 291*11963SAfshin.Ardakani@Sun.COM dfs_cache_remove(path.p_unc.unc_share, 292*11963SAfshin.Ardakani@Sun.COM path.p_unc.unc_path); 293*11963SAfshin.Ardakani@Sun.COM /* 294*11963SAfshin.Ardakani@Sun.COM * if link is removed then try to remove its 295*11963SAfshin.Ardakani@Sun.COM * empty parent directories if any 296*11963SAfshin.Ardakani@Sun.COM */ 297*11963SAfshin.Ardakani@Sun.COM if (stat == DFS_STAT_NOTFOUND) 298*11963SAfshin.Ardakani@Sun.COM netdfs_path_remove(&path.p_unc); 299*11963SAfshin.Ardakani@Sun.COM } 300*11963SAfshin.Ardakani@Sun.COM } 301*11963SAfshin.Ardakani@Sun.COM 302*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 303*11963SAfshin.Ardakani@Sun.COM 304*11963SAfshin.Ardakani@Sun.COM dfs_path_free(&path); 305*11963SAfshin.Ardakani@Sun.COM param->status = status; 3068334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 3075331Samw } 3085331Samw 3095331Samw /* 310*11963SAfshin.Ardakani@Sun.COM * Sets or modifies information relevant to a specific DFS root, DFS root 311*11963SAfshin.Ardakani@Sun.COM * target, DFS link, or DFS link target 3125331Samw * 313*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsSetInfo (Opnum 3) 3145331Samw */ 3155331Samw /*ARGSUSED*/ 3165331Samw static int 3178334SJose.Borrego@Sun.COM netdfs_s_setinfo(void *arg, ndr_xa_t *mxa) 3185331Samw { 319*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_t *param = arg; 320*11963SAfshin.Ardakani@Sun.COM dfs_path_t path; 321*11963SAfshin.Ardakani@Sun.COM uint32_t status, stat; 3225331Samw 323*11963SAfshin.Ardakani@Sun.COM /* both server and share must be NULL or non-NULL */ 324*11963SAfshin.Ardakani@Sun.COM if ((param->server == NULL && param->share != NULL) || 325*11963SAfshin.Ardakani@Sun.COM (param->server != NULL && param->share == NULL)) { 3265331Samw param->status = ERROR_INVALID_PARAMETER; 3278334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 3285331Samw } 3295331Samw 330*11963SAfshin.Ardakani@Sun.COM status = dfs_path_parse(&path, (const char *)param->dfs_path, 331*11963SAfshin.Ardakani@Sun.COM DFS_OBJECT_ANY); 332*11963SAfshin.Ardakani@Sun.COM 333*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) { 334*11963SAfshin.Ardakani@Sun.COM param->status = status; 335*11963SAfshin.Ardakani@Sun.COM return (NDR_DRC_OK); 3365331Samw } 3375331Samw 338*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 339*11963SAfshin.Ardakani@Sun.COM status = dfs_link_stat((const char *)path.p_fspath, &stat); 340*11963SAfshin.Ardakani@Sun.COM 341*11963SAfshin.Ardakani@Sun.COM if ((path.p_type == DFS_OBJECT_LINK) && (stat != DFS_STAT_ISDFS)) { 342*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 343*11963SAfshin.Ardakani@Sun.COM dfs_path_free(&path); 344*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_NOT_FOUND; 3458334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 3465331Samw } 3475331Samw 3485331Samw switch (param->info.level) { 3495331Samw case 100: 350*11963SAfshin.Ardakani@Sun.COM status = netdfs_setinfo_100(&path, param->info.iu.info100); 351*11963SAfshin.Ardakani@Sun.COM break; 3525331Samw case 101: 353*11963SAfshin.Ardakani@Sun.COM status = netdfs_setinfo_101(&path, param->info.iu.info101, 354*11963SAfshin.Ardakani@Sun.COM (const char *)param->server, (const char *)param->share); 355*11963SAfshin.Ardakani@Sun.COM break; 3565331Samw case 102: 357*11963SAfshin.Ardakani@Sun.COM status = netdfs_setinfo_102(&path, param->info.iu.info102); 3585331Samw break; 359*11963SAfshin.Ardakani@Sun.COM case 103: 360*11963SAfshin.Ardakani@Sun.COM status = netdfs_setinfo_103(&path, param->info.iu.info103); 361*11963SAfshin.Ardakani@Sun.COM break; 362*11963SAfshin.Ardakani@Sun.COM case 104: 363*11963SAfshin.Ardakani@Sun.COM status = netdfs_setinfo_104(&path, param->info.iu.info104, 364*11963SAfshin.Ardakani@Sun.COM (const char *)param->server, (const char *)param->share); 365*11963SAfshin.Ardakani@Sun.COM break; 366*11963SAfshin.Ardakani@Sun.COM case 105: 367*11963SAfshin.Ardakani@Sun.COM status = netdfs_setinfo_105(&path, param->info.iu.info105); 368*11963SAfshin.Ardakani@Sun.COM break; 3695331Samw default: 370*11963SAfshin.Ardakani@Sun.COM status = ERROR_INVALID_LEVEL; 371*11963SAfshin.Ardakani@Sun.COM break; 3725331Samw } 3735331Samw 374*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 375*11963SAfshin.Ardakani@Sun.COM dfs_path_free(&path); 376*11963SAfshin.Ardakani@Sun.COM param->status = status; 3778334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 3785331Samw } 3795331Samw 3805331Samw /* 381*11963SAfshin.Ardakani@Sun.COM * Returns information about a DFS root or a DFS link of the specified 382*11963SAfshin.Ardakani@Sun.COM * DFS namespace. 3835331Samw * 384*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsGetInfo (Opnum 4) 3855331Samw */ 3865331Samw static int 3878334SJose.Borrego@Sun.COM netdfs_s_getinfo(void *arg, ndr_xa_t *mxa) 3885331Samw { 389*11963SAfshin.Ardakani@Sun.COM netdfs_getinfo_t *param = arg; 390*11963SAfshin.Ardakani@Sun.COM netdfs_info1_t *info1; 391*11963SAfshin.Ardakani@Sun.COM netdfs_info2_t *info2; 392*11963SAfshin.Ardakani@Sun.COM netdfs_info3_t *info3; 393*11963SAfshin.Ardakani@Sun.COM netdfs_info4_t *info4; 394*11963SAfshin.Ardakani@Sun.COM netdfs_info5_t *info5; 395*11963SAfshin.Ardakani@Sun.COM netdfs_info6_t *info6; 396*11963SAfshin.Ardakani@Sun.COM netdfs_info100_t *info100; 397*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 398*11963SAfshin.Ardakani@Sun.COM dfs_path_t path; 399*11963SAfshin.Ardakani@Sun.COM uint32_t status, stat; 400*11963SAfshin.Ardakani@Sun.COM const char *fspath; 401*11963SAfshin.Ardakani@Sun.COM uint32_t level = param->level; 402*11963SAfshin.Ardakani@Sun.COM 403*11963SAfshin.Ardakani@Sun.COM status = dfs_path_parse(&path, (const char *)param->dfs_path, 404*11963SAfshin.Ardakani@Sun.COM DFS_OBJECT_ANY); 4055331Samw 406*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 407*11963SAfshin.Ardakani@Sun.COM goto getinfo_error; 408*11963SAfshin.Ardakani@Sun.COM 409*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 4105331Samw 411*11963SAfshin.Ardakani@Sun.COM fspath = path.p_fspath; 412*11963SAfshin.Ardakani@Sun.COM if (path.p_type == DFS_OBJECT_LINK) { 413*11963SAfshin.Ardakani@Sun.COM status = dfs_link_stat(fspath, &stat); 414*11963SAfshin.Ardakani@Sun.COM if ((status != ERROR_SUCCESS) || (stat != DFS_STAT_ISDFS)) { 415*11963SAfshin.Ardakani@Sun.COM status = ERROR_NOT_FOUND; 416*11963SAfshin.Ardakani@Sun.COM goto getinfo_error; 417*11963SAfshin.Ardakani@Sun.COM } 418*11963SAfshin.Ardakani@Sun.COM 419*11963SAfshin.Ardakani@Sun.COM status = dfs_link_getinfo(fspath, &info, param->level); 4205331Samw } else { 421*11963SAfshin.Ardakani@Sun.COM status = dfs_root_getinfo(fspath, &info, param->level); 4225331Samw } 4235331Samw 424*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 425*11963SAfshin.Ardakani@Sun.COM goto getinfo_error; 426*11963SAfshin.Ardakani@Sun.COM 427*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(info.i_uncpath, (char *)param->dfs_path, 428*11963SAfshin.Ardakani@Sun.COM sizeof (info.i_uncpath)); 4295331Samw 430*11963SAfshin.Ardakani@Sun.COM dfs_info_trace("netdfs_s_getinfo", &info); 431*11963SAfshin.Ardakani@Sun.COM 432*11963SAfshin.Ardakani@Sun.COM status = ERROR_NOT_ENOUGH_MEMORY; 433*11963SAfshin.Ardakani@Sun.COM 434*11963SAfshin.Ardakani@Sun.COM switch (level) { 4355331Samw case 1: 436*11963SAfshin.Ardakani@Sun.COM if ((info1 = NDR_NEW(mxa, netdfs_info1_t)) != NULL) { 437*11963SAfshin.Ardakani@Sun.COM param->info.iu.info1 = info1; 438*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_1(info1, &info, mxa, NULL); 439*11963SAfshin.Ardakani@Sun.COM } 440*11963SAfshin.Ardakani@Sun.COM break; 4415331Samw case 2: 442*11963SAfshin.Ardakani@Sun.COM if ((info2 = NDR_NEW(mxa, netdfs_info2_t)) != NULL) { 443*11963SAfshin.Ardakani@Sun.COM param->info.iu.info2 = info2; 444*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_2(info2, &info, mxa, NULL); 445*11963SAfshin.Ardakani@Sun.COM } 446*11963SAfshin.Ardakani@Sun.COM break; 4475331Samw case 3: 448*11963SAfshin.Ardakani@Sun.COM if ((info3 = NDR_NEW(mxa, netdfs_info3_t)) != NULL) { 449*11963SAfshin.Ardakani@Sun.COM param->info.iu.info3 = info3; 450*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_3(info3, &info, mxa, NULL); 451*11963SAfshin.Ardakani@Sun.COM } 452*11963SAfshin.Ardakani@Sun.COM break; 4535331Samw case 4: 454*11963SAfshin.Ardakani@Sun.COM if ((info4 = NDR_NEW(mxa, netdfs_info4_t)) != NULL) { 455*11963SAfshin.Ardakani@Sun.COM param->info.iu.info4 = info4; 456*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_4(info4, &info, mxa, NULL); 457*11963SAfshin.Ardakani@Sun.COM } 458*11963SAfshin.Ardakani@Sun.COM break; 459*11963SAfshin.Ardakani@Sun.COM case 5: 460*11963SAfshin.Ardakani@Sun.COM if ((info5 = NDR_NEW(mxa, netdfs_info5_t)) != NULL) { 461*11963SAfshin.Ardakani@Sun.COM param->info.iu.info5 = info5; 462*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_5(info5, &info, mxa, NULL); 463*11963SAfshin.Ardakani@Sun.COM } 464*11963SAfshin.Ardakani@Sun.COM break; 465*11963SAfshin.Ardakani@Sun.COM case 6: 466*11963SAfshin.Ardakani@Sun.COM if ((info6 = NDR_NEW(mxa, netdfs_info6_t)) != NULL) { 467*11963SAfshin.Ardakani@Sun.COM param->info.iu.info6 = info6; 468*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_6(info6, &info, mxa, NULL); 469*11963SAfshin.Ardakani@Sun.COM } 470*11963SAfshin.Ardakani@Sun.COM break; 4715331Samw case 100: 472*11963SAfshin.Ardakani@Sun.COM if ((info100 = NDR_NEW(mxa, netdfs_info100_t)) != NULL) { 473*11963SAfshin.Ardakani@Sun.COM param->info.iu.info100 = info100; 474*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_100(info100, &info, mxa, NULL); 475*11963SAfshin.Ardakani@Sun.COM } 4765331Samw break; 4775331Samw 4785331Samw default: 479*11963SAfshin.Ardakani@Sun.COM status = ERROR_INVALID_LEVEL; 480*11963SAfshin.Ardakani@Sun.COM break; 4815331Samw } 4825331Samw 483*11963SAfshin.Ardakani@Sun.COM dfs_info_free(&info); 484*11963SAfshin.Ardakani@Sun.COM 485*11963SAfshin.Ardakani@Sun.COM getinfo_error: 486*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 487*11963SAfshin.Ardakani@Sun.COM dfs_path_free(&path); 488*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 489*11963SAfshin.Ardakani@Sun.COM bzero(param, sizeof (netdfs_getinfo_t)); 490*11963SAfshin.Ardakani@Sun.COM 491*11963SAfshin.Ardakani@Sun.COM param->info.level = level; 492*11963SAfshin.Ardakani@Sun.COM param->status = status; 4938334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 4945331Samw } 4955331Samw 4965331Samw /* 497*11963SAfshin.Ardakani@Sun.COM * Enumerates the DFS root hosted on a server or the DFS links of the 498*11963SAfshin.Ardakani@Sun.COM * namespace hosted by a server. Depending on the information level, 499*11963SAfshin.Ardakani@Sun.COM * the targets of the root and links are also displayed. 5005331Samw * 501*11963SAfshin.Ardakani@Sun.COM * For unsupported levels, it should return ERROR_INVALID_LEVEL as 502*11963SAfshin.Ardakani@Sun.COM * Microsoft does for DFS server on Win2000 and NT. 503*11963SAfshin.Ardakani@Sun.COM * 504*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsEnum (Opnum 5) 5055331Samw */ 5065331Samw /*ARGSUSED*/ 5075331Samw static int 5088334SJose.Borrego@Sun.COM netdfs_s_enum(void *arg, ndr_xa_t *mxa) 5095331Samw { 510*11963SAfshin.Ardakani@Sun.COM netdfs_enum_t *param = arg; 511*11963SAfshin.Ardakani@Sun.COM netdfs_enumhandle_t de; 512*11963SAfshin.Ardakani@Sun.COM uint32_t level = param->level; 513*11963SAfshin.Ardakani@Sun.COM uint32_t status = ERROR_SUCCESS; 514*11963SAfshin.Ardakani@Sun.COM uint32_t nroot; 515*11963SAfshin.Ardakani@Sun.COM size_t entsize; 516*11963SAfshin.Ardakani@Sun.COM 517*11963SAfshin.Ardakani@Sun.COM if (param->info == NULL) { 518*11963SAfshin.Ardakani@Sun.COM status = ERROR_INVALID_PARAMETER; 519*11963SAfshin.Ardakani@Sun.COM goto enum_error; 520*11963SAfshin.Ardakani@Sun.COM } 521*11963SAfshin.Ardakani@Sun.COM 522*11963SAfshin.Ardakani@Sun.COM if ((nroot = dfs_namespace_count()) == 0) 523*11963SAfshin.Ardakani@Sun.COM status = ERROR_NOT_FOUND; 524*11963SAfshin.Ardakani@Sun.COM else if (nroot > 1) 525*11963SAfshin.Ardakani@Sun.COM status = ERROR_DEVICE_NOT_AVAILABLE; 526*11963SAfshin.Ardakani@Sun.COM 527*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 528*11963SAfshin.Ardakani@Sun.COM goto enum_error; 529*11963SAfshin.Ardakani@Sun.COM 530*11963SAfshin.Ardakani@Sun.COM bzero(&de, sizeof (netdfs_enumhandle_t)); 531*11963SAfshin.Ardakani@Sun.COM de.de_level = level; 532*11963SAfshin.Ardakani@Sun.COM de.de_ntotal = dfs_cache_num(); 533*11963SAfshin.Ardakani@Sun.COM 534*11963SAfshin.Ardakani@Sun.COM if (param->pref_max_len == NETDFS_MAXPREFLEN || 535*11963SAfshin.Ardakani@Sun.COM param->pref_max_len > NETDFS_MAXBUFLEN) 536*11963SAfshin.Ardakani@Sun.COM de.de_prefmaxlen = NETDFS_MAXBUFLEN; 537*11963SAfshin.Ardakani@Sun.COM else 538*11963SAfshin.Ardakani@Sun.COM de.de_prefmaxlen = param->pref_max_len; 539*11963SAfshin.Ardakani@Sun.COM 540*11963SAfshin.Ardakani@Sun.COM de.de_bavail = de.de_prefmaxlen; 541*11963SAfshin.Ardakani@Sun.COM 542*11963SAfshin.Ardakani@Sun.COM if (param->resume_handle != NULL) { 543*11963SAfshin.Ardakani@Sun.COM if (*param->resume_handle >= de.de_ntotal) { 544*11963SAfshin.Ardakani@Sun.COM status = ERROR_NO_MORE_ITEMS; 545*11963SAfshin.Ardakani@Sun.COM goto enum_error; 546*11963SAfshin.Ardakani@Sun.COM } 547*11963SAfshin.Ardakani@Sun.COM de.de_resume = *param->resume_handle; 548*11963SAfshin.Ardakani@Sun.COM de.de_nskip = de.de_resume; 549*11963SAfshin.Ardakani@Sun.COM *param->resume_handle = 0; 550*11963SAfshin.Ardakani@Sun.COM } 551*11963SAfshin.Ardakani@Sun.COM 552*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 553*11963SAfshin.Ardakani@Sun.COM 554*11963SAfshin.Ardakani@Sun.COM status = ERROR_NOT_ENOUGH_MEMORY; 555*11963SAfshin.Ardakani@Sun.COM 556*11963SAfshin.Ardakani@Sun.COM switch (level) { 557*11963SAfshin.Ardakani@Sun.COM case 1: 558*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info1_t); 559*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 560*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info1_t, de.de_nmax); 561*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 562*11963SAfshin.Ardakani@Sun.COM goto enum_error; 563*11963SAfshin.Ardakani@Sun.COM 564*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 565*11963SAfshin.Ardakani@Sun.COM param->info->iu.info1->info1 = de.de_entries; 566*11963SAfshin.Ardakani@Sun.COM param->info->iu.info1->count = de.de_nitems; 567*11963SAfshin.Ardakani@Sun.COM } 568*11963SAfshin.Ardakani@Sun.COM break; 569*11963SAfshin.Ardakani@Sun.COM case 2: 570*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info2_t); 571*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 572*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info2_t, de.de_nmax); 573*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 574*11963SAfshin.Ardakani@Sun.COM goto enum_error; 5755331Samw 576*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 577*11963SAfshin.Ardakani@Sun.COM param->info->iu.info2->info2 = de.de_entries; 578*11963SAfshin.Ardakani@Sun.COM param->info->iu.info2->count = de.de_nitems; 579*11963SAfshin.Ardakani@Sun.COM } 580*11963SAfshin.Ardakani@Sun.COM break; 5815331Samw case 3: 582*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info3_t) + 583*11963SAfshin.Ardakani@Sun.COM sizeof (netdfs_storage_info_t); 584*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 585*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info3_t, de.de_nmax); 586*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 587*11963SAfshin.Ardakani@Sun.COM goto enum_error; 588*11963SAfshin.Ardakani@Sun.COM 589*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 590*11963SAfshin.Ardakani@Sun.COM param->info->iu.info3->info3 = de.de_entries; 591*11963SAfshin.Ardakani@Sun.COM param->info->iu.info3->count = de.de_nitems; 592*11963SAfshin.Ardakani@Sun.COM } 593*11963SAfshin.Ardakani@Sun.COM break; 594*11963SAfshin.Ardakani@Sun.COM case 4: 595*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info4_t) + 596*11963SAfshin.Ardakani@Sun.COM sizeof (netdfs_storage_info_t); 597*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 598*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info4_t, de.de_nmax); 599*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 600*11963SAfshin.Ardakani@Sun.COM goto enum_error; 601*11963SAfshin.Ardakani@Sun.COM 602*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 603*11963SAfshin.Ardakani@Sun.COM param->info->iu.info4->info4 = de.de_entries; 604*11963SAfshin.Ardakani@Sun.COM param->info->iu.info4->count = de.de_nitems; 605*11963SAfshin.Ardakani@Sun.COM } 606*11963SAfshin.Ardakani@Sun.COM break; 607*11963SAfshin.Ardakani@Sun.COM 608*11963SAfshin.Ardakani@Sun.COM case 5: 609*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info5_t); 610*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 611*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info5_t, de.de_nmax); 612*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 613*11963SAfshin.Ardakani@Sun.COM goto enum_error; 614*11963SAfshin.Ardakani@Sun.COM 615*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 616*11963SAfshin.Ardakani@Sun.COM param->info->iu.info5->info5 = de.de_entries; 617*11963SAfshin.Ardakani@Sun.COM param->info->iu.info5->count = de.de_nitems; 618*11963SAfshin.Ardakani@Sun.COM } 619*11963SAfshin.Ardakani@Sun.COM break; 620*11963SAfshin.Ardakani@Sun.COM 621*11963SAfshin.Ardakani@Sun.COM case 6: 622*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info6_t) + 623*11963SAfshin.Ardakani@Sun.COM sizeof (netdfs_storage_info1_t); 624*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 625*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info6_t, de.de_nmax); 626*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 627*11963SAfshin.Ardakani@Sun.COM goto enum_error; 628*11963SAfshin.Ardakani@Sun.COM 629*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 630*11963SAfshin.Ardakani@Sun.COM param->info->iu.info6->info6 = de.de_entries; 631*11963SAfshin.Ardakani@Sun.COM param->info->iu.info6->count = de.de_nitems; 632*11963SAfshin.Ardakani@Sun.COM } 633*11963SAfshin.Ardakani@Sun.COM break; 634*11963SAfshin.Ardakani@Sun.COM 635*11963SAfshin.Ardakani@Sun.COM case 300: 636*11963SAfshin.Ardakani@Sun.COM entsize = sizeof (netdfs_info300_t); 637*11963SAfshin.Ardakani@Sun.COM de.de_nmax = MAX((de.de_prefmaxlen / entsize), 1); 638*11963SAfshin.Ardakani@Sun.COM de.de_entries = NDR_NEWN(mxa, netdfs_info300_t, de.de_nmax); 639*11963SAfshin.Ardakani@Sun.COM if (de.de_entries == NULL) 640*11963SAfshin.Ardakani@Sun.COM goto enum_error; 641*11963SAfshin.Ardakani@Sun.COM 642*11963SAfshin.Ardakani@Sun.COM if ((status = netdfs_enum_common(&de, mxa)) == ERROR_SUCCESS) { 643*11963SAfshin.Ardakani@Sun.COM param->info->iu.info300->info300 = de.de_entries; 644*11963SAfshin.Ardakani@Sun.COM param->info->iu.info300->count = de.de_nitems; 645*11963SAfshin.Ardakani@Sun.COM } 6465331Samw break; 6475331Samw 6485331Samw default: 649*11963SAfshin.Ardakani@Sun.COM status = ERROR_INVALID_PARAMETER; 650*11963SAfshin.Ardakani@Sun.COM break; 6515331Samw } 6525331Samw 653*11963SAfshin.Ardakani@Sun.COM if ((status == ERROR_SUCCESS) && (param->resume_handle != NULL)) 654*11963SAfshin.Ardakani@Sun.COM *param->resume_handle = de.de_resume; 655*11963SAfshin.Ardakani@Sun.COM 656*11963SAfshin.Ardakani@Sun.COM enum_error: 657*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 658*11963SAfshin.Ardakani@Sun.COM param->status = status; 6598334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 6605331Samw } 6615331Samw 6625331Samw /* 663*11963SAfshin.Ardakani@Sun.COM * Renames or moves a DFS link 664*11963SAfshin.Ardakani@Sun.COM * 665*11963SAfshin.Ardakani@Sun.COM * Does not need to be supported for DFS version 1 666*11963SAfshin.Ardakani@Sun.COM * 667*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsMove (Opnum 6) 6685331Samw */ 6695331Samw /*ARGSUSED*/ 6705331Samw static int 6718334SJose.Borrego@Sun.COM netdfs_s_move(void *arg, ndr_xa_t *mxa) 6725331Samw { 6735331Samw struct netdfs_move *param = arg; 6745331Samw 675*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_NOT_SUPPORTED; 6768334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 6775331Samw } 6785331Samw 6795331Samw /* 680*11963SAfshin.Ardakani@Sun.COM * According to [MS-DFSNM] spec this operation (opnum 7) is not 681*11963SAfshin.Ardakani@Sun.COM * used over the wire. 6825331Samw */ 6835331Samw /*ARGSUSED*/ 6845331Samw static int 6858334SJose.Borrego@Sun.COM netdfs_s_rename(void *arg, ndr_xa_t *mxa) 6865331Samw { 6875331Samw struct netdfs_rename *param = arg; 6885331Samw 689*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_NOT_SUPPORTED; 6908334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 6915331Samw } 6925331Samw 6935331Samw /* 694*11963SAfshin.Ardakani@Sun.COM * Creates a new standalone DFS namespace 695*11963SAfshin.Ardakani@Sun.COM * 696*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsAddStdRoot (Opnum 12) 6975331Samw */ 6985331Samw /*ARGSUSED*/ 6995331Samw static int 7008334SJose.Borrego@Sun.COM netdfs_s_addstdroot(void *arg, ndr_xa_t *mxa) 7015331Samw { 7025331Samw struct netdfs_addstdroot *param = arg; 703*11963SAfshin.Ardakani@Sun.COM const char *share = (const char *)param->share; 704*11963SAfshin.Ardakani@Sun.COM const char *comment = (const char *)param->comment; 7055331Samw 706*11963SAfshin.Ardakani@Sun.COM if (!ndr_is_admin(mxa)) { 707*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_ACCESS_DENIED; 708*11963SAfshin.Ardakani@Sun.COM return (NDR_DRC_OK); 709*11963SAfshin.Ardakani@Sun.COM } 710*11963SAfshin.Ardakani@Sun.COM 711*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 712*11963SAfshin.Ardakani@Sun.COM 713*11963SAfshin.Ardakani@Sun.COM /* For now only allow a single standalone namespace */ 714*11963SAfshin.Ardakani@Sun.COM if (dfs_namespace_count() == 0) 715*11963SAfshin.Ardakani@Sun.COM param->status = dfs_namespace_add(share, comment); 716*11963SAfshin.Ardakani@Sun.COM else 717*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_NOT_SUPPORTED; 718*11963SAfshin.Ardakani@Sun.COM 719*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 7208334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 7215331Samw } 7225331Samw 7235331Samw /* 724*11963SAfshin.Ardakani@Sun.COM * Deletes the specified stand-alone DFS namespace. The DFS namespace can be 725*11963SAfshin.Ardakani@Sun.COM * removed without first removing all of the links in it. 726*11963SAfshin.Ardakani@Sun.COM * 727*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM]: NetrDfsRemoveStdRoot (Opnum 13) 7285331Samw */ 7295331Samw /*ARGSUSED*/ 7305331Samw static int 7318334SJose.Borrego@Sun.COM netdfs_s_remstdroot(void *arg, ndr_xa_t *mxa) 7325331Samw { 7335331Samw struct netdfs_remstdroot *param = arg; 734*11963SAfshin.Ardakani@Sun.COM const char *share = (const char *)param->share; 7355331Samw 736*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_ON); 737*11963SAfshin.Ardakani@Sun.COM 738*11963SAfshin.Ardakani@Sun.COM if (ndr_is_admin(mxa)) 739*11963SAfshin.Ardakani@Sun.COM param->status = dfs_namespace_remove(share); 740*11963SAfshin.Ardakani@Sun.COM else 741*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_ACCESS_DENIED; 742*11963SAfshin.Ardakani@Sun.COM 743*11963SAfshin.Ardakani@Sun.COM dfs_setpriv(PRIV_OFF); 7448334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 7455331Samw } 7465331Samw 7475331Samw /* 748*11963SAfshin.Ardakani@Sun.COM * Enumerates the DFS roots hosted on a server, or DFS links of a namespace 749*11963SAfshin.Ardakani@Sun.COM * hosted by the server. Depending on the information level, the targets 750*11963SAfshin.Ardakani@Sun.COM * associated with the roots and links are also displayed 7515331Samw * 752*11963SAfshin.Ardakani@Sun.COM * Does not need to be supported for DFS version 1 753*11963SAfshin.Ardakani@Sun.COM * 754*11963SAfshin.Ardakani@Sun.COM * [MS-DFSNM] NetrDfsEnumEx (Opnum 21) 7555331Samw */ 756*11963SAfshin.Ardakani@Sun.COM /*ARGSUSED*/ 7575331Samw static int 7588334SJose.Borrego@Sun.COM netdfs_s_enumex(void *arg, ndr_xa_t *mxa) 7595331Samw { 7605331Samw struct netdfs_enumex *param = arg; 7615331Samw 7625331Samw bzero(param->info, sizeof (struct netdfs_enumex)); 763*11963SAfshin.Ardakani@Sun.COM param->status = ERROR_NOT_SUPPORTED; 7648334SJose.Borrego@Sun.COM return (NDR_DRC_OK); 7655331Samw } 7665331Samw 7675331Samw /* 768*11963SAfshin.Ardakani@Sun.COM * Sets the comment for the DFS link/root. 769*11963SAfshin.Ardakani@Sun.COM */ 770*11963SAfshin.Ardakani@Sun.COM static uint32_t 771*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_100(dfs_path_t *path, netdfs_info100_t *netinfo) 772*11963SAfshin.Ardakani@Sun.COM { 773*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 774*11963SAfshin.Ardakani@Sun.COM uint32_t status; 775*11963SAfshin.Ardakani@Sun.COM char *cmnt = (char *)netinfo->comment; 776*11963SAfshin.Ardakani@Sun.COM 777*11963SAfshin.Ardakani@Sun.COM bzero(&info, sizeof (dfs_info_t)); 778*11963SAfshin.Ardakani@Sun.COM if (cmnt != NULL) 779*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(info.i_comment, cmnt, sizeof (info.i_comment)); 780*11963SAfshin.Ardakani@Sun.COM 781*11963SAfshin.Ardakani@Sun.COM if (path->p_type == DFS_OBJECT_LINK) 782*11963SAfshin.Ardakani@Sun.COM status = dfs_link_setinfo(path->p_fspath, &info, 100); 783*11963SAfshin.Ardakani@Sun.COM else 784*11963SAfshin.Ardakani@Sun.COM status = dfs_root_setinfo(path->p_fspath, &info, 100); 785*11963SAfshin.Ardakani@Sun.COM 786*11963SAfshin.Ardakani@Sun.COM return (status); 787*11963SAfshin.Ardakani@Sun.COM } 788*11963SAfshin.Ardakani@Sun.COM 789*11963SAfshin.Ardakani@Sun.COM /* 790*11963SAfshin.Ardakani@Sun.COM * Sets the state for the DFS root/link or its target. 791*11963SAfshin.Ardakani@Sun.COM */ 792*11963SAfshin.Ardakani@Sun.COM static uint32_t 793*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_101(dfs_path_t *path, netdfs_info101_t *netinfo, 794*11963SAfshin.Ardakani@Sun.COM const char *t_server, const char *t_share) 795*11963SAfshin.Ardakani@Sun.COM { 796*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 797*11963SAfshin.Ardakani@Sun.COM dfs_target_t target; 798*11963SAfshin.Ardakani@Sun.COM uint32_t status; 799*11963SAfshin.Ardakani@Sun.COM 800*11963SAfshin.Ardakani@Sun.COM bzero(&info, sizeof (dfs_info_t)); 801*11963SAfshin.Ardakani@Sun.COM bzero(&target, sizeof (dfs_target_t)); 802*11963SAfshin.Ardakani@Sun.COM 803*11963SAfshin.Ardakani@Sun.COM if (t_server == NULL && t_share == NULL) { 804*11963SAfshin.Ardakani@Sun.COM info.i_state = netinfo->state; 805*11963SAfshin.Ardakani@Sun.COM } else { 806*11963SAfshin.Ardakani@Sun.COM target.t_state = netinfo->state; 807*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(target.t_server, t_server, 808*11963SAfshin.Ardakani@Sun.COM sizeof (target.t_server)); 809*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(target.t_share, t_share, 810*11963SAfshin.Ardakani@Sun.COM sizeof (target.t_share)); 811*11963SAfshin.Ardakani@Sun.COM info.i_targets = ⌖ 812*11963SAfshin.Ardakani@Sun.COM } 813*11963SAfshin.Ardakani@Sun.COM 814*11963SAfshin.Ardakani@Sun.COM if (path->p_type == DFS_OBJECT_LINK) 815*11963SAfshin.Ardakani@Sun.COM status = dfs_link_setinfo(path->p_fspath, &info, 101); 816*11963SAfshin.Ardakani@Sun.COM else 817*11963SAfshin.Ardakani@Sun.COM status = dfs_root_setinfo(path->p_fspath, &info, 101); 818*11963SAfshin.Ardakani@Sun.COM 819*11963SAfshin.Ardakani@Sun.COM return (status); 820*11963SAfshin.Ardakani@Sun.COM } 821*11963SAfshin.Ardakani@Sun.COM 822*11963SAfshin.Ardakani@Sun.COM /* 823*11963SAfshin.Ardakani@Sun.COM * Sets the timeout value of the DFS link/root. 824*11963SAfshin.Ardakani@Sun.COM */ 825*11963SAfshin.Ardakani@Sun.COM static uint32_t 826*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_102(dfs_path_t *path, netdfs_info102_t *netinfo) 827*11963SAfshin.Ardakani@Sun.COM { 828*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 829*11963SAfshin.Ardakani@Sun.COM uint32_t status; 830*11963SAfshin.Ardakani@Sun.COM 831*11963SAfshin.Ardakani@Sun.COM bzero(&info, sizeof (dfs_info_t)); 832*11963SAfshin.Ardakani@Sun.COM info.i_timeout = netinfo->timeout; 833*11963SAfshin.Ardakani@Sun.COM 834*11963SAfshin.Ardakani@Sun.COM if (path->p_type == DFS_OBJECT_LINK) 835*11963SAfshin.Ardakani@Sun.COM status = dfs_link_setinfo(path->p_fspath, &info, 102); 836*11963SAfshin.Ardakani@Sun.COM else 837*11963SAfshin.Ardakani@Sun.COM status = dfs_root_setinfo(path->p_fspath, &info, 102); 838*11963SAfshin.Ardakani@Sun.COM 839*11963SAfshin.Ardakani@Sun.COM return (status); 840*11963SAfshin.Ardakani@Sun.COM } 841*11963SAfshin.Ardakani@Sun.COM 842*11963SAfshin.Ardakani@Sun.COM /* 843*11963SAfshin.Ardakani@Sun.COM * Sets the property flags for the root or link. 844*11963SAfshin.Ardakani@Sun.COM */ 845*11963SAfshin.Ardakani@Sun.COM static uint32_t 846*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_103(dfs_path_t *path, netdfs_info103_t *netinfo) 847*11963SAfshin.Ardakani@Sun.COM { 848*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 849*11963SAfshin.Ardakani@Sun.COM uint32_t status; 850*11963SAfshin.Ardakani@Sun.COM 851*11963SAfshin.Ardakani@Sun.COM bzero(&info, sizeof (dfs_info_t)); 852*11963SAfshin.Ardakani@Sun.COM info.i_propflags = 853*11963SAfshin.Ardakani@Sun.COM netinfo->property_flags & netinfo->property_flag_mask; 854*11963SAfshin.Ardakani@Sun.COM 855*11963SAfshin.Ardakani@Sun.COM if (path->p_type == DFS_OBJECT_LINK) 856*11963SAfshin.Ardakani@Sun.COM status = dfs_link_setinfo(path->p_fspath, &info, 103); 857*11963SAfshin.Ardakani@Sun.COM else 858*11963SAfshin.Ardakani@Sun.COM status = dfs_root_setinfo(path->p_fspath, &info, 103); 859*11963SAfshin.Ardakani@Sun.COM 860*11963SAfshin.Ardakani@Sun.COM return (status); 861*11963SAfshin.Ardakani@Sun.COM } 862*11963SAfshin.Ardakani@Sun.COM 863*11963SAfshin.Ardakani@Sun.COM /* 864*11963SAfshin.Ardakani@Sun.COM * Sets the target priority rank and class for the root target or link target 865*11963SAfshin.Ardakani@Sun.COM */ 866*11963SAfshin.Ardakani@Sun.COM static uint32_t 867*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_104(dfs_path_t *path, netdfs_info104_t *netinfo, 868*11963SAfshin.Ardakani@Sun.COM const char *t_server, const char *t_share) 869*11963SAfshin.Ardakani@Sun.COM { 870*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 871*11963SAfshin.Ardakani@Sun.COM dfs_target_t target; 872*11963SAfshin.Ardakani@Sun.COM uint32_t status; 873*11963SAfshin.Ardakani@Sun.COM 874*11963SAfshin.Ardakani@Sun.COM if ((t_server == NULL) || (t_share == NULL)) 875*11963SAfshin.Ardakani@Sun.COM return (ERROR_INVALID_PARAMETER); 876*11963SAfshin.Ardakani@Sun.COM 877*11963SAfshin.Ardakani@Sun.COM bzero(&info, sizeof (dfs_info_t)); 878*11963SAfshin.Ardakani@Sun.COM bzero(&target, sizeof (dfs_target_t)); 879*11963SAfshin.Ardakani@Sun.COM 880*11963SAfshin.Ardakani@Sun.COM target.t_priority.p_class = netinfo->priority_class; 881*11963SAfshin.Ardakani@Sun.COM target.t_priority.p_rank = netinfo->priority_rank; 882*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(target.t_server, t_server, sizeof (target.t_server)); 883*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(target.t_share, t_share, sizeof (target.t_share)); 884*11963SAfshin.Ardakani@Sun.COM info.i_targets = ⌖ 885*11963SAfshin.Ardakani@Sun.COM 886*11963SAfshin.Ardakani@Sun.COM if (path->p_type == DFS_OBJECT_LINK) 887*11963SAfshin.Ardakani@Sun.COM status = dfs_link_setinfo(path->p_fspath, &info, 104); 888*11963SAfshin.Ardakani@Sun.COM else 889*11963SAfshin.Ardakani@Sun.COM status = dfs_root_setinfo(path->p_fspath, &info, 104); 890*11963SAfshin.Ardakani@Sun.COM 891*11963SAfshin.Ardakani@Sun.COM return (status); 892*11963SAfshin.Ardakani@Sun.COM } 893*11963SAfshin.Ardakani@Sun.COM 894*11963SAfshin.Ardakani@Sun.COM /* 895*11963SAfshin.Ardakani@Sun.COM * Sets the comment, state, time-out information, and property flags for the 896*11963SAfshin.Ardakani@Sun.COM * namespace root or link specified in DfsInfo. Does not apply to a root target 897*11963SAfshin.Ardakani@Sun.COM * or link target. 898*11963SAfshin.Ardakani@Sun.COM */ 899*11963SAfshin.Ardakani@Sun.COM static uint32_t 900*11963SAfshin.Ardakani@Sun.COM netdfs_setinfo_105(dfs_path_t *path, netdfs_info105_t *netinfo) 901*11963SAfshin.Ardakani@Sun.COM { 902*11963SAfshin.Ardakani@Sun.COM dfs_info_t info; 903*11963SAfshin.Ardakani@Sun.COM uint32_t status; 904*11963SAfshin.Ardakani@Sun.COM char *cmnt = (char *)netinfo->comment; 905*11963SAfshin.Ardakani@Sun.COM 906*11963SAfshin.Ardakani@Sun.COM bzero(&info, sizeof (dfs_info_t)); 907*11963SAfshin.Ardakani@Sun.COM 908*11963SAfshin.Ardakani@Sun.COM if (cmnt != NULL) 909*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(info.i_comment, cmnt, sizeof (info.i_comment)); 910*11963SAfshin.Ardakani@Sun.COM info.i_state = netinfo->state; 911*11963SAfshin.Ardakani@Sun.COM info.i_timeout = netinfo->timeout; 912*11963SAfshin.Ardakani@Sun.COM info.i_propflags = 913*11963SAfshin.Ardakani@Sun.COM netinfo->property_flags & netinfo->property_flag_mask; 914*11963SAfshin.Ardakani@Sun.COM 915*11963SAfshin.Ardakani@Sun.COM if (path->p_type == DFS_OBJECT_LINK) 916*11963SAfshin.Ardakani@Sun.COM status = dfs_link_setinfo(path->p_fspath, &info, 105); 917*11963SAfshin.Ardakani@Sun.COM else 918*11963SAfshin.Ardakani@Sun.COM status = dfs_root_setinfo(path->p_fspath, &info, 105); 919*11963SAfshin.Ardakani@Sun.COM 920*11963SAfshin.Ardakani@Sun.COM return (status); 921*11963SAfshin.Ardakani@Sun.COM } 922*11963SAfshin.Ardakani@Sun.COM 923*11963SAfshin.Ardakani@Sun.COM /* 924*11963SAfshin.Ardakani@Sun.COM * DFS_STORAGE_INFO: target information 925*11963SAfshin.Ardakani@Sun.COM */ 926*11963SAfshin.Ardakani@Sun.COM static uint32_t 927*11963SAfshin.Ardakani@Sun.COM netdfs_info_storage(netdfs_storage_info_t **sinfo, dfs_info_t *info, 928*11963SAfshin.Ardakani@Sun.COM ndr_xa_t *mxa, uint32_t *size) 929*11963SAfshin.Ardakani@Sun.COM { 930*11963SAfshin.Ardakani@Sun.COM netdfs_storage_info_t *storage; 931*11963SAfshin.Ardakani@Sun.COM dfs_target_t *target; 932*11963SAfshin.Ardakani@Sun.COM int i; 933*11963SAfshin.Ardakani@Sun.COM 934*11963SAfshin.Ardakani@Sun.COM *sinfo = NULL; 935*11963SAfshin.Ardakani@Sun.COM if (info->i_ntargets == 0) 936*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 937*11963SAfshin.Ardakani@Sun.COM 938*11963SAfshin.Ardakani@Sun.COM *sinfo = NDR_NEWN(mxa, netdfs_storage_info_t, info->i_ntargets); 939*11963SAfshin.Ardakani@Sun.COM if (*sinfo == NULL) 940*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 941*11963SAfshin.Ardakani@Sun.COM 942*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 943*11963SAfshin.Ardakani@Sun.COM *size += info->i_ntargets * sizeof (netdfs_storage_info_t); 944*11963SAfshin.Ardakani@Sun.COM 945*11963SAfshin.Ardakani@Sun.COM target = info->i_targets; 946*11963SAfshin.Ardakani@Sun.COM storage = *sinfo; 947*11963SAfshin.Ardakani@Sun.COM for (i = 0; i < info->i_ntargets; i++, target++, storage++) { 948*11963SAfshin.Ardakani@Sun.COM storage->state = target->t_state; 949*11963SAfshin.Ardakani@Sun.COM storage->server = NDR_STRDUP(mxa, target->t_server); 950*11963SAfshin.Ardakani@Sun.COM storage->share = NDR_STRDUP(mxa, target->t_share); 951*11963SAfshin.Ardakani@Sun.COM 952*11963SAfshin.Ardakani@Sun.COM if (storage->server == NULL || storage->share == NULL) 953*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 954*11963SAfshin.Ardakani@Sun.COM 955*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 956*11963SAfshin.Ardakani@Sun.COM *size += smb_wcequiv_strlen(target->t_server) + 957*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(target->t_share); 958*11963SAfshin.Ardakani@Sun.COM } 959*11963SAfshin.Ardakani@Sun.COM 960*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 961*11963SAfshin.Ardakani@Sun.COM } 962*11963SAfshin.Ardakani@Sun.COM 963*11963SAfshin.Ardakani@Sun.COM /* 964*11963SAfshin.Ardakani@Sun.COM * DFS_STORAGE_INFO_1: target information 965*11963SAfshin.Ardakani@Sun.COM */ 966*11963SAfshin.Ardakani@Sun.COM static uint32_t 967*11963SAfshin.Ardakani@Sun.COM netdfs_info_storage1(netdfs_storage_info1_t **sinfo, dfs_info_t *info, 968*11963SAfshin.Ardakani@Sun.COM ndr_xa_t *mxa, uint32_t *size) 969*11963SAfshin.Ardakani@Sun.COM { 970*11963SAfshin.Ardakani@Sun.COM netdfs_storage_info1_t *storage; 971*11963SAfshin.Ardakani@Sun.COM dfs_target_t *target; 972*11963SAfshin.Ardakani@Sun.COM int i; 973*11963SAfshin.Ardakani@Sun.COM 974*11963SAfshin.Ardakani@Sun.COM *sinfo = NULL; 975*11963SAfshin.Ardakani@Sun.COM if (info->i_ntargets == 0) 976*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 977*11963SAfshin.Ardakani@Sun.COM 978*11963SAfshin.Ardakani@Sun.COM *sinfo = NDR_NEWN(mxa, netdfs_storage_info1_t, info->i_ntargets); 979*11963SAfshin.Ardakani@Sun.COM if (*sinfo == NULL) 980*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 981*11963SAfshin.Ardakani@Sun.COM 982*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 983*11963SAfshin.Ardakani@Sun.COM *size += info->i_ntargets * sizeof (netdfs_storage_info1_t); 984*11963SAfshin.Ardakani@Sun.COM 985*11963SAfshin.Ardakani@Sun.COM target = info->i_targets; 986*11963SAfshin.Ardakani@Sun.COM storage = *sinfo; 987*11963SAfshin.Ardakani@Sun.COM for (i = 0; i < info->i_ntargets; i++, target++, storage++) { 988*11963SAfshin.Ardakani@Sun.COM storage->state = target->t_state; 989*11963SAfshin.Ardakani@Sun.COM storage->server = NDR_STRDUP(mxa, target->t_server); 990*11963SAfshin.Ardakani@Sun.COM storage->share = NDR_STRDUP(mxa, target->t_share); 991*11963SAfshin.Ardakani@Sun.COM storage->p_class = target->t_priority.p_class; 992*11963SAfshin.Ardakani@Sun.COM storage->p_rank = target->t_priority.p_rank; 993*11963SAfshin.Ardakani@Sun.COM storage->p_reserved = 0; 994*11963SAfshin.Ardakani@Sun.COM 995*11963SAfshin.Ardakani@Sun.COM if (storage->server == NULL || storage->share == NULL) 996*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 997*11963SAfshin.Ardakani@Sun.COM 998*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 999*11963SAfshin.Ardakani@Sun.COM *size += smb_wcequiv_strlen(target->t_server) + 1000*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(target->t_share); 1001*11963SAfshin.Ardakani@Sun.COM } 1002*11963SAfshin.Ardakani@Sun.COM 1003*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1004*11963SAfshin.Ardakani@Sun.COM } 1005*11963SAfshin.Ardakani@Sun.COM 1006*11963SAfshin.Ardakani@Sun.COM /* 1007*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_1 for get/enum response 1008*11963SAfshin.Ardakani@Sun.COM */ 1009*11963SAfshin.Ardakani@Sun.COM static uint32_t 1010*11963SAfshin.Ardakani@Sun.COM netdfs_info_1(netdfs_info1_t *info1, dfs_info_t *info, ndr_xa_t *mxa, 1011*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1012*11963SAfshin.Ardakani@Sun.COM { 1013*11963SAfshin.Ardakani@Sun.COM info1->entry_path = NDR_STRDUP(mxa, info->i_uncpath); 1014*11963SAfshin.Ardakani@Sun.COM if (info1->entry_path == NULL) 1015*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1016*11963SAfshin.Ardakani@Sun.COM 1017*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1018*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info1_t) + 1019*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath); 1020*11963SAfshin.Ardakani@Sun.COM 1021*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1022*11963SAfshin.Ardakani@Sun.COM } 1023*11963SAfshin.Ardakani@Sun.COM 1024*11963SAfshin.Ardakani@Sun.COM /* 1025*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_2 for get/enum response 1026*11963SAfshin.Ardakani@Sun.COM */ 1027*11963SAfshin.Ardakani@Sun.COM static uint32_t 1028*11963SAfshin.Ardakani@Sun.COM netdfs_info_2(netdfs_info2_t *info2, dfs_info_t *info, ndr_xa_t *mxa, 1029*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1030*11963SAfshin.Ardakani@Sun.COM { 1031*11963SAfshin.Ardakani@Sun.COM void *entry_path; 1032*11963SAfshin.Ardakani@Sun.COM void *comment; 1033*11963SAfshin.Ardakani@Sun.COM 1034*11963SAfshin.Ardakani@Sun.COM entry_path = NDR_STRDUP(mxa, info->i_uncpath); 1035*11963SAfshin.Ardakani@Sun.COM comment = NDR_STRDUP(mxa, info->i_comment); 1036*11963SAfshin.Ardakani@Sun.COM 1037*11963SAfshin.Ardakani@Sun.COM if (entry_path == NULL || comment == NULL) 1038*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1039*11963SAfshin.Ardakani@Sun.COM 1040*11963SAfshin.Ardakani@Sun.COM info2->entry_path = entry_path; 1041*11963SAfshin.Ardakani@Sun.COM info2->comment = comment; 1042*11963SAfshin.Ardakani@Sun.COM info2->state = info->i_state; 1043*11963SAfshin.Ardakani@Sun.COM info2->n_store = info->i_ntargets; 1044*11963SAfshin.Ardakani@Sun.COM 1045*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1046*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info2_t) + 1047*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath) + 1048*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_comment); 1049*11963SAfshin.Ardakani@Sun.COM 1050*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1051*11963SAfshin.Ardakani@Sun.COM } 1052*11963SAfshin.Ardakani@Sun.COM 1053*11963SAfshin.Ardakani@Sun.COM /* 1054*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_3 for get/enum response 1055*11963SAfshin.Ardakani@Sun.COM */ 1056*11963SAfshin.Ardakani@Sun.COM static uint32_t 1057*11963SAfshin.Ardakani@Sun.COM netdfs_info_3(netdfs_info3_t *info3, dfs_info_t *info, ndr_xa_t *mxa, 1058*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1059*11963SAfshin.Ardakani@Sun.COM { 1060*11963SAfshin.Ardakani@Sun.COM void *entry_path; 1061*11963SAfshin.Ardakani@Sun.COM void *comment; 1062*11963SAfshin.Ardakani@Sun.COM 1063*11963SAfshin.Ardakani@Sun.COM entry_path = NDR_STRDUP(mxa, info->i_uncpath); 1064*11963SAfshin.Ardakani@Sun.COM comment = NDR_STRDUP(mxa, info->i_comment); 1065*11963SAfshin.Ardakani@Sun.COM 1066*11963SAfshin.Ardakani@Sun.COM if (entry_path == NULL || comment == NULL) 1067*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1068*11963SAfshin.Ardakani@Sun.COM 1069*11963SAfshin.Ardakani@Sun.COM info3->entry_path = entry_path; 1070*11963SAfshin.Ardakani@Sun.COM info3->comment = comment; 1071*11963SAfshin.Ardakani@Sun.COM info3->state = info->i_state; 1072*11963SAfshin.Ardakani@Sun.COM info3->n_store = info->i_ntargets; 1073*11963SAfshin.Ardakani@Sun.COM 1074*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1075*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info3_t) + 1076*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath) + 1077*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_comment); 1078*11963SAfshin.Ardakani@Sun.COM 1079*11963SAfshin.Ardakani@Sun.COM return (netdfs_info_storage(&info3->si, info, mxa, size)); 1080*11963SAfshin.Ardakani@Sun.COM } 1081*11963SAfshin.Ardakani@Sun.COM 1082*11963SAfshin.Ardakani@Sun.COM /* 1083*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_4 for get/enum response 1084*11963SAfshin.Ardakani@Sun.COM */ 1085*11963SAfshin.Ardakani@Sun.COM static uint32_t 1086*11963SAfshin.Ardakani@Sun.COM netdfs_info_4(netdfs_info4_t *info4, dfs_info_t *info, ndr_xa_t *mxa, 1087*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1088*11963SAfshin.Ardakani@Sun.COM { 1089*11963SAfshin.Ardakani@Sun.COM void *entry_path; 1090*11963SAfshin.Ardakani@Sun.COM void *comment; 1091*11963SAfshin.Ardakani@Sun.COM 1092*11963SAfshin.Ardakani@Sun.COM entry_path = NDR_STRDUP(mxa, info->i_uncpath); 1093*11963SAfshin.Ardakani@Sun.COM comment = NDR_STRDUP(mxa, info->i_comment); 1094*11963SAfshin.Ardakani@Sun.COM 1095*11963SAfshin.Ardakani@Sun.COM if (entry_path == NULL || comment == NULL) 1096*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1097*11963SAfshin.Ardakani@Sun.COM 1098*11963SAfshin.Ardakani@Sun.COM if (!netdfs_guid_fromstr(info->i_guid, &info4->guid)) 1099*11963SAfshin.Ardakani@Sun.COM return (ERROR_INVALID_DATA); 1100*11963SAfshin.Ardakani@Sun.COM 1101*11963SAfshin.Ardakani@Sun.COM info4->entry_path = entry_path; 1102*11963SAfshin.Ardakani@Sun.COM info4->comment = comment; 1103*11963SAfshin.Ardakani@Sun.COM info4->state = info->i_state; 1104*11963SAfshin.Ardakani@Sun.COM info4->timeout = info->i_timeout; 1105*11963SAfshin.Ardakani@Sun.COM info4->n_store = info->i_ntargets; 1106*11963SAfshin.Ardakani@Sun.COM 1107*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1108*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info4_t) + 1109*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath) + 1110*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_comment); 1111*11963SAfshin.Ardakani@Sun.COM 1112*11963SAfshin.Ardakani@Sun.COM return (netdfs_info_storage(&info4->si, info, mxa, size)); 1113*11963SAfshin.Ardakani@Sun.COM } 1114*11963SAfshin.Ardakani@Sun.COM 1115*11963SAfshin.Ardakani@Sun.COM /* 1116*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_5 for get/enum response 1117*11963SAfshin.Ardakani@Sun.COM */ 1118*11963SAfshin.Ardakani@Sun.COM static uint32_t 1119*11963SAfshin.Ardakani@Sun.COM netdfs_info_5(netdfs_info5_t *info5, dfs_info_t *info, ndr_xa_t *mxa, 1120*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1121*11963SAfshin.Ardakani@Sun.COM { 1122*11963SAfshin.Ardakani@Sun.COM void *entry_path; 1123*11963SAfshin.Ardakani@Sun.COM void *comment; 1124*11963SAfshin.Ardakani@Sun.COM 1125*11963SAfshin.Ardakani@Sun.COM entry_path = NDR_STRDUP(mxa, info->i_uncpath); 1126*11963SAfshin.Ardakani@Sun.COM comment = NDR_STRDUP(mxa, info->i_comment); 1127*11963SAfshin.Ardakani@Sun.COM 1128*11963SAfshin.Ardakani@Sun.COM if (entry_path == NULL || comment == NULL) 1129*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1130*11963SAfshin.Ardakani@Sun.COM 1131*11963SAfshin.Ardakani@Sun.COM if (!netdfs_guid_fromstr(info->i_guid, &info5->guid)) 1132*11963SAfshin.Ardakani@Sun.COM return (ERROR_INVALID_DATA); 1133*11963SAfshin.Ardakani@Sun.COM 1134*11963SAfshin.Ardakani@Sun.COM info5->entry_path = entry_path; 1135*11963SAfshin.Ardakani@Sun.COM info5->comment = comment; 1136*11963SAfshin.Ardakani@Sun.COM info5->state = info->i_state; 1137*11963SAfshin.Ardakani@Sun.COM info5->timeout = info->i_timeout; 1138*11963SAfshin.Ardakani@Sun.COM info5->flags = info->i_propflags; 1139*11963SAfshin.Ardakani@Sun.COM info5->metadata_sz = 0; 1140*11963SAfshin.Ardakani@Sun.COM info5->n_store = info->i_ntargets; 1141*11963SAfshin.Ardakani@Sun.COM 1142*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1143*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info5_t) + 1144*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath) + 1145*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_comment); 1146*11963SAfshin.Ardakani@Sun.COM 1147*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1148*11963SAfshin.Ardakani@Sun.COM } 1149*11963SAfshin.Ardakani@Sun.COM 1150*11963SAfshin.Ardakani@Sun.COM /* 1151*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_6 for get/enum response 1152*11963SAfshin.Ardakani@Sun.COM */ 1153*11963SAfshin.Ardakani@Sun.COM static uint32_t 1154*11963SAfshin.Ardakani@Sun.COM netdfs_info_6(netdfs_info6_t *info6, dfs_info_t *info, ndr_xa_t *mxa, 1155*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1156*11963SAfshin.Ardakani@Sun.COM { 1157*11963SAfshin.Ardakani@Sun.COM void *entry_path; 1158*11963SAfshin.Ardakani@Sun.COM void *comment; 1159*11963SAfshin.Ardakani@Sun.COM 1160*11963SAfshin.Ardakani@Sun.COM entry_path = NDR_STRDUP(mxa, info->i_uncpath); 1161*11963SAfshin.Ardakani@Sun.COM comment = NDR_STRDUP(mxa, info->i_comment); 1162*11963SAfshin.Ardakani@Sun.COM 1163*11963SAfshin.Ardakani@Sun.COM if (entry_path == NULL || comment == NULL) 1164*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1165*11963SAfshin.Ardakani@Sun.COM 1166*11963SAfshin.Ardakani@Sun.COM if (!netdfs_guid_fromstr(info->i_guid, &info6->guid)) 1167*11963SAfshin.Ardakani@Sun.COM return (ERROR_INVALID_DATA); 1168*11963SAfshin.Ardakani@Sun.COM 1169*11963SAfshin.Ardakani@Sun.COM info6->entry_path = entry_path; 1170*11963SAfshin.Ardakani@Sun.COM info6->comment = comment; 1171*11963SAfshin.Ardakani@Sun.COM info6->state = info->i_state; 1172*11963SAfshin.Ardakani@Sun.COM info6->timeout = info->i_timeout; 1173*11963SAfshin.Ardakani@Sun.COM info6->flags = info->i_propflags; 1174*11963SAfshin.Ardakani@Sun.COM info6->metadata_sz = 0; 1175*11963SAfshin.Ardakani@Sun.COM info6->n_store = info->i_ntargets; 1176*11963SAfshin.Ardakani@Sun.COM 1177*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1178*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info6_t) + 1179*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath) + 1180*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_comment); 1181*11963SAfshin.Ardakani@Sun.COM 1182*11963SAfshin.Ardakani@Sun.COM return (netdfs_info_storage1(&info6->si, info, mxa, size)); 1183*11963SAfshin.Ardakani@Sun.COM } 1184*11963SAfshin.Ardakani@Sun.COM 1185*11963SAfshin.Ardakani@Sun.COM /* 1186*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_100 for Get response 1187*11963SAfshin.Ardakani@Sun.COM */ 1188*11963SAfshin.Ardakani@Sun.COM static uint32_t 1189*11963SAfshin.Ardakani@Sun.COM netdfs_info_100(netdfs_info100_t *info100, dfs_info_t *info, ndr_xa_t *mxa, 1190*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1191*11963SAfshin.Ardakani@Sun.COM { 1192*11963SAfshin.Ardakani@Sun.COM info100->comment = NDR_STRDUP(mxa, info->i_comment); 1193*11963SAfshin.Ardakani@Sun.COM if (info100->comment == NULL) 1194*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1195*11963SAfshin.Ardakani@Sun.COM 1196*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1197*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info100_t) + 1198*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_comment); 1199*11963SAfshin.Ardakani@Sun.COM 1200*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1201*11963SAfshin.Ardakani@Sun.COM } 1202*11963SAfshin.Ardakani@Sun.COM 1203*11963SAfshin.Ardakani@Sun.COM /* 1204*11963SAfshin.Ardakani@Sun.COM * Sets a DFS_INFO_300 for Enum response 1205*11963SAfshin.Ardakani@Sun.COM */ 1206*11963SAfshin.Ardakani@Sun.COM static uint32_t 1207*11963SAfshin.Ardakani@Sun.COM netdfs_info_300(netdfs_info300_t *info300, dfs_info_t *info, ndr_xa_t *mxa, 1208*11963SAfshin.Ardakani@Sun.COM uint32_t *size) 1209*11963SAfshin.Ardakani@Sun.COM { 1210*11963SAfshin.Ardakani@Sun.COM info300->dfsname = NDR_STRDUP(mxa, info->i_uncpath); 1211*11963SAfshin.Ardakani@Sun.COM if (info300->dfsname == NULL) 1212*11963SAfshin.Ardakani@Sun.COM return (ERROR_NOT_ENOUGH_MEMORY); 1213*11963SAfshin.Ardakani@Sun.COM 1214*11963SAfshin.Ardakani@Sun.COM info300->flavor = DFS_VOLUME_FLAVOR_STANDALONE; 1215*11963SAfshin.Ardakani@Sun.COM if (size != NULL) 1216*11963SAfshin.Ardakani@Sun.COM *size = sizeof (netdfs_info300_t) + 1217*11963SAfshin.Ardakani@Sun.COM smb_wcequiv_strlen(info->i_uncpath); 1218*11963SAfshin.Ardakani@Sun.COM 1219*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1220*11963SAfshin.Ardakani@Sun.COM } 1221*11963SAfshin.Ardakani@Sun.COM 1222*11963SAfshin.Ardakani@Sun.COM /* 1223*11963SAfshin.Ardakani@Sun.COM * Common enumeration function 1224*11963SAfshin.Ardakani@Sun.COM */ 1225*11963SAfshin.Ardakani@Sun.COM static uint32_t 1226*11963SAfshin.Ardakani@Sun.COM netdfs_enum_common(netdfs_enumhandle_t *de, ndr_xa_t *mxa) 1227*11963SAfshin.Ardakani@Sun.COM { 1228*11963SAfshin.Ardakani@Sun.COM netdfs_info1_t *info1 = de->de_entries; 1229*11963SAfshin.Ardakani@Sun.COM netdfs_info2_t *info2 = de->de_entries; 1230*11963SAfshin.Ardakani@Sun.COM netdfs_info3_t *info3 = de->de_entries; 1231*11963SAfshin.Ardakani@Sun.COM netdfs_info4_t *info4 = de->de_entries; 1232*11963SAfshin.Ardakani@Sun.COM netdfs_info5_t *info5 = de->de_entries; 1233*11963SAfshin.Ardakani@Sun.COM netdfs_info6_t *info6 = de->de_entries; 1234*11963SAfshin.Ardakani@Sun.COM netdfs_info300_t *info300 = de->de_entries; 1235*11963SAfshin.Ardakani@Sun.COM dfs_info_t dfsinfo; 1236*11963SAfshin.Ardakani@Sun.COM smb_cache_cursor_t cursor; 1237*11963SAfshin.Ardakani@Sun.COM dfs_nscnode_t nscnode; 1238*11963SAfshin.Ardakani@Sun.COM uint32_t status; 1239*11963SAfshin.Ardakani@Sun.COM uint32_t itemsz; 1240*11963SAfshin.Ardakani@Sun.COM 1241*11963SAfshin.Ardakani@Sun.COM dfs_cache_iterinit(&cursor); 1242*11963SAfshin.Ardakani@Sun.COM 1243*11963SAfshin.Ardakani@Sun.COM de->de_nitems = 0; 1244*11963SAfshin.Ardakani@Sun.COM while (dfs_cache_iterate(&cursor, &nscnode)) { 1245*11963SAfshin.Ardakani@Sun.COM if (de->de_nskip > 0) { 1246*11963SAfshin.Ardakani@Sun.COM de->de_nskip--; 1247*11963SAfshin.Ardakani@Sun.COM continue; 1248*11963SAfshin.Ardakani@Sun.COM } 1249*11963SAfshin.Ardakani@Sun.COM 1250*11963SAfshin.Ardakani@Sun.COM if (de->de_nitems == de->de_nmax) 1251*11963SAfshin.Ardakani@Sun.COM break; 1252*11963SAfshin.Ardakani@Sun.COM 1253*11963SAfshin.Ardakani@Sun.COM status = dfs_cache_getinfo(&nscnode, &dfsinfo, de->de_level); 1254*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 1255*11963SAfshin.Ardakani@Sun.COM continue; 1256*11963SAfshin.Ardakani@Sun.COM 1257*11963SAfshin.Ardakani@Sun.COM switch (de->de_level) { 1258*11963SAfshin.Ardakani@Sun.COM case 1: 1259*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_1(info1, &dfsinfo, mxa, &itemsz); 1260*11963SAfshin.Ardakani@Sun.COM info1++; 1261*11963SAfshin.Ardakani@Sun.COM break; 1262*11963SAfshin.Ardakani@Sun.COM case 2: 1263*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_2(info2, &dfsinfo, mxa, &itemsz); 1264*11963SAfshin.Ardakani@Sun.COM info2++; 1265*11963SAfshin.Ardakani@Sun.COM break; 1266*11963SAfshin.Ardakani@Sun.COM case 3: 1267*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_3(info3, &dfsinfo, mxa, &itemsz); 1268*11963SAfshin.Ardakani@Sun.COM info3++; 1269*11963SAfshin.Ardakani@Sun.COM break; 1270*11963SAfshin.Ardakani@Sun.COM case 4: 1271*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_4(info4, &dfsinfo, mxa, &itemsz); 1272*11963SAfshin.Ardakani@Sun.COM info4++; 1273*11963SAfshin.Ardakani@Sun.COM break; 1274*11963SAfshin.Ardakani@Sun.COM case 5: 1275*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_5(info5, &dfsinfo, mxa, &itemsz); 1276*11963SAfshin.Ardakani@Sun.COM info5++; 1277*11963SAfshin.Ardakani@Sun.COM break; 1278*11963SAfshin.Ardakani@Sun.COM case 6: 1279*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_6(info6, &dfsinfo, mxa, &itemsz); 1280*11963SAfshin.Ardakani@Sun.COM info6++; 1281*11963SAfshin.Ardakani@Sun.COM break; 1282*11963SAfshin.Ardakani@Sun.COM case 300: 1283*11963SAfshin.Ardakani@Sun.COM status = netdfs_info_300(info300, &dfsinfo, mxa, 1284*11963SAfshin.Ardakani@Sun.COM &itemsz); 1285*11963SAfshin.Ardakani@Sun.COM info300++; 1286*11963SAfshin.Ardakani@Sun.COM break; 1287*11963SAfshin.Ardakani@Sun.COM default: 1288*11963SAfshin.Ardakani@Sun.COM status = ERROR_INVALID_LEVEL; 1289*11963SAfshin.Ardakani@Sun.COM } 1290*11963SAfshin.Ardakani@Sun.COM 1291*11963SAfshin.Ardakani@Sun.COM dfs_info_free(&dfsinfo); 1292*11963SAfshin.Ardakani@Sun.COM 1293*11963SAfshin.Ardakani@Sun.COM if (status != ERROR_SUCCESS) 1294*11963SAfshin.Ardakani@Sun.COM return (status); 1295*11963SAfshin.Ardakani@Sun.COM 1296*11963SAfshin.Ardakani@Sun.COM if (de->de_nmax == 1) { 1297*11963SAfshin.Ardakani@Sun.COM de->de_nitems = 1; 1298*11963SAfshin.Ardakani@Sun.COM break; 1299*11963SAfshin.Ardakani@Sun.COM } 1300*11963SAfshin.Ardakani@Sun.COM 1301*11963SAfshin.Ardakani@Sun.COM if (itemsz > de->de_bavail) 1302*11963SAfshin.Ardakani@Sun.COM break; 1303*11963SAfshin.Ardakani@Sun.COM 1304*11963SAfshin.Ardakani@Sun.COM de->de_bavail -= itemsz; 1305*11963SAfshin.Ardakani@Sun.COM de->de_nitems++; 1306*11963SAfshin.Ardakani@Sun.COM } 1307*11963SAfshin.Ardakani@Sun.COM 1308*11963SAfshin.Ardakani@Sun.COM de->de_resume += de->de_nitems; 1309*11963SAfshin.Ardakani@Sun.COM return (ERROR_SUCCESS); 1310*11963SAfshin.Ardakani@Sun.COM } 1311*11963SAfshin.Ardakani@Sun.COM 1312*11963SAfshin.Ardakani@Sun.COM /* 1313*11963SAfshin.Ardakani@Sun.COM * Creates intermediate directories of a link from the root share path. 13145331Samw * 1315*11963SAfshin.Ardakani@Sun.COM * TODO: directories should be created by smbsrv to get Windows compatible 1316*11963SAfshin.Ardakani@Sun.COM * ACL inheritance. 13175331Samw */ 1318*11963SAfshin.Ardakani@Sun.COM static void 1319*11963SAfshin.Ardakani@Sun.COM netdfs_path_create(const char *path) 13205331Samw { 1321*11963SAfshin.Ardakani@Sun.COM char dirpath[DFS_PATH_MAX]; 1322*11963SAfshin.Ardakani@Sun.COM mode_t mode; 13235331Samw char *p; 13245331Samw 1325*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(dirpath, path, DFS_PATH_MAX); 13265331Samw 1327*11963SAfshin.Ardakani@Sun.COM /* drop the link itself from the path */ 1328*11963SAfshin.Ardakani@Sun.COM if ((p = strrchr(dirpath, '/')) != NULL) { 13295331Samw *p = '\0'; 1330*11963SAfshin.Ardakani@Sun.COM mode = umask(0); 1331*11963SAfshin.Ardakani@Sun.COM (void) mkdirp(dirpath, 0777); 1332*11963SAfshin.Ardakani@Sun.COM (void) umask(mode); 1333*11963SAfshin.Ardakani@Sun.COM } 1334*11963SAfshin.Ardakani@Sun.COM } 13355331Samw 1336*11963SAfshin.Ardakani@Sun.COM /* 1337*11963SAfshin.Ardakani@Sun.COM * Removes empty directories 1338*11963SAfshin.Ardakani@Sun.COM */ 1339*11963SAfshin.Ardakani@Sun.COM static void 1340*11963SAfshin.Ardakani@Sun.COM netdfs_path_remove(smb_unc_t *unc) 1341*11963SAfshin.Ardakani@Sun.COM { 1342*11963SAfshin.Ardakani@Sun.COM char rootdir[DFS_PATH_MAX]; 1343*11963SAfshin.Ardakani@Sun.COM char relpath[DFS_PATH_MAX]; 1344*11963SAfshin.Ardakani@Sun.COM char dir[DFS_PATH_MAX]; 1345*11963SAfshin.Ardakani@Sun.COM uint32_t status; 1346*11963SAfshin.Ardakani@Sun.COM char *p; 13475331Samw 1348*11963SAfshin.Ardakani@Sun.COM status = dfs_namespace_path(unc->unc_share, rootdir, DFS_PATH_MAX); 1349*11963SAfshin.Ardakani@Sun.COM if ((status == ERROR_SUCCESS) && (chdir(rootdir) == 0)) { 1350*11963SAfshin.Ardakani@Sun.COM (void) strlcpy(relpath, unc->unc_path, DFS_PATH_MAX); 1351*11963SAfshin.Ardakani@Sun.COM /* drop the link itself from the path */ 1352*11963SAfshin.Ardakani@Sun.COM if ((p = strrchr(relpath, '/')) != NULL) { 13535331Samw *p = '\0'; 1354*11963SAfshin.Ardakani@Sun.COM (void) rmdirp(relpath, dir); 13555331Samw } 13565331Samw } 1357*11963SAfshin.Ardakani@Sun.COM } 13585331Samw 1359*11963SAfshin.Ardakani@Sun.COM /* 1360*11963SAfshin.Ardakani@Sun.COM * Converts the guid string into binary format in network byte order. 1361*11963SAfshin.Ardakani@Sun.COM */ 1362*11963SAfshin.Ardakani@Sun.COM static boolean_t 1363*11963SAfshin.Ardakani@Sun.COM netdfs_guid_fromstr(char *guid_str, netdfs_uuid_t *guid) 1364*11963SAfshin.Ardakani@Sun.COM { 1365*11963SAfshin.Ardakani@Sun.COM uuid_t uuid; 13665331Samw 1367*11963SAfshin.Ardakani@Sun.COM if (uuid_parse(guid_str, uuid) != 0) 1368*11963SAfshin.Ardakani@Sun.COM return (B_FALSE); 1369*11963SAfshin.Ardakani@Sun.COM 1370*11963SAfshin.Ardakani@Sun.COM bcopy(&uuid, guid, sizeof (uuid_t)); 13715331Samw 1372*11963SAfshin.Ardakani@Sun.COM guid->data1 = htonl(guid->data1); 1373*11963SAfshin.Ardakani@Sun.COM guid->data2 = htons(guid->data2); 1374*11963SAfshin.Ardakani@Sun.COM guid->data3 = htons(guid->data3); 1375*11963SAfshin.Ardakani@Sun.COM 1376*11963SAfshin.Ardakani@Sun.COM return (B_TRUE); 13775331Samw } 1378