nfs-ganesha 1.4
|
00001 /* 00002 * vim:expandtab:shiftwidth=8:tabstop=8: 00003 * 00004 * Copyright CEA/DAM/DIF (2008) 00005 * contributeur : Philippe DENIEL philippe.deniel@cea.fr 00006 * Thomas LEIBOVICI thomas.leibovici@cea.fr 00007 * 00008 * 00009 * This program is free software; you can redistribute it and/or 00010 * modify it under the terms of the GNU Lesser General Public 00011 * License as published by the Free Software Foundation; either 00012 * version 3 of the License, or (at your option) any later version. 00013 * 00014 * This program is distributed in the hope that it will be useful, 00015 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00016 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00017 * Lesser General Public License for more details. 00018 * 00019 * You should have received a copy of the GNU Lesser General Public 00020 * License along with this library; if not, write to the Free Software 00021 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 00022 * 00023 * --------------------------------------- 00024 */ 00025 00036 #ifdef HAVE_CONFIG_H 00037 #include "config.h" 00038 #endif 00039 00040 #ifdef _SOLARIS 00041 #include "solaris_port.h" 00042 #endif 00043 00044 #include <stdio.h> 00045 #include <string.h> 00046 #include <pthread.h> 00047 #include <fcntl.h> 00048 #include <sys/file.h> /* for having FNDELAY */ 00049 #include "HashData.h" 00050 #include "HashTable.h" 00051 #include "log.h" 00052 #include "ganesha_rpc.h" 00053 #include "nfs4.h" 00054 #include "nfs_core.h" 00055 #include "nfs_proto_functions.h" 00056 #include "nfs_tools.h" 00057 #include "nfs_exports.h" 00058 #include "nfs_file_handle.h" 00059 #include "cache_inode.h" 00060 00061 int nfs4_Set_Fh_Referral(nfs_fh4 * pfh) 00062 { 00063 file_handle_v4_t *pfhandle4; 00064 00065 if(pfh == NULL) 00066 return 0; 00067 00068 pfhandle4 = (file_handle_v4_t *) (pfh->nfs_fh4_val); 00069 00070 pfhandle4->refid = 1; 00071 00072 return 1; 00073 } 00074 00075 int nfs4_referral_str_To_Fattr_fs_location(char *input_str, char *buff, u_int *plen) 00076 { 00077 char str[MAXPATHLEN]; 00078 char local_part[MAXPATHLEN]; 00079 char *local_comp[MAXNAMLEN]; 00080 char remote_part[MAXPATHLEN]; 00081 char *remote_comp[MAXNAMLEN]; 00082 char server_part[MAXPATHLEN]; 00083 00084 u_int nb_comp_local = 1; 00085 u_int nb_comp_remote = 1; 00086 u_int lastoff = 0; 00087 u_int tmp_int = 0; 00088 u_int i = 0; 00089 u_int delta_xdr = 0; 00090 00091 char *ptr = NULL; 00092 00093 if(!plen || !buff || !input_str) 00094 return 0; 00095 00096 strncpy(str, input_str, MAXPATHLEN); 00097 00098 /* Find the ":" in the string */ 00099 for(ptr = str; *ptr != ':'; ptr++) ; 00100 *ptr = '\0'; 00101 ptr += 1; 00102 00103 memset( local_part, 0, MAXPATHLEN ) ; 00104 strncpy(local_part, str, MAXPATHLEN); 00105 00106 memset( remote_part, 0, MAXPATHLEN ) ; 00107 strncpy(remote_part, ptr, MAXPATHLEN); 00108 00109 /* Each part should not start with a leading slash */ 00110 if(local_part[0] == '/') 00111 strncpy(local_part, str + 1, MAXPATHLEN); 00112 00113 if(remote_part[0] == '/') 00114 strncpy(remote_part, ptr + 1, MAXPATHLEN); 00115 00116 /* Find the "@" in the remote_part */ 00117 for(ptr = remote_part; *ptr != '@'; ptr++) ; 00118 *ptr = '\0'; 00119 ptr += 1; 00120 00121 memset( server_part, 0 , MAXPATHLEN ) ; 00122 strncpy(server_part, ptr, MAXPATHLEN); 00123 00124 local_comp[0] = local_part; 00125 for(ptr = local_part; *ptr != '\0'; ptr++) 00126 if(*ptr == '/') 00127 { 00128 local_comp[nb_comp_local] = ptr + 1; 00129 nb_comp_local += 1; 00130 } 00131 for(tmp_int = 0; tmp_int < nb_comp_local; tmp_int++) 00132 { 00133 ptr = local_comp[tmp_int] - 1; 00134 *ptr = '\0'; 00135 } 00136 00137 remote_comp[0] = remote_part; 00138 for(ptr = remote_part; *ptr != '\0'; ptr++) 00139 if(*ptr == '/') 00140 { 00141 remote_comp[nb_comp_remote] = ptr + 1; 00142 nb_comp_remote += 1; 00143 } 00144 for(tmp_int = 0; tmp_int < nb_comp_remote; tmp_int++) 00145 { 00146 ptr = remote_comp[tmp_int] - 1; 00147 *ptr = '\0'; 00148 } 00149 00150 /* This attributes is equivalent to a "mount" command line, 00151 * To understand what's follow, imagine that you do kind of "mount refer@server nfs_ref" */ 00152 00153 LogFullDebug(COMPONENT_NFS_V4_REFERRAL, "--> %s", input_str); 00154 00155 LogFullDebug(COMPONENT_NFS_V4_REFERRAL, " %u comp local", nb_comp_local); 00156 for(tmp_int = 0; tmp_int < nb_comp_local; tmp_int++) 00157 LogFullDebug(COMPONENT_NFS_V4_REFERRAL, " #%s#", local_comp[tmp_int]); 00158 00159 LogFullDebug(COMPONENT_NFS_V4_REFERRAL, " %u comp remote", nb_comp_remote); 00160 for(tmp_int = 0; tmp_int < nb_comp_remote; tmp_int++) 00161 LogFullDebug(COMPONENT_NFS_V4_REFERRAL, " #%s#", remote_comp[tmp_int]); 00162 00163 LogFullDebug(COMPONENT_NFS_V4_REFERRAL, " server = #%s#", server_part); 00164 00165 /* 1- Number of component in local path */ 00166 tmp_int = htonl(nb_comp_local); 00167 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00168 lastoff += sizeof(u_int); 00169 00170 /* 2- each component in local path */ 00171 for(i = 0; i < nb_comp_local; i++) 00172 { 00173 /* The length for the string */ 00174 tmp_int = htonl(strlen(local_comp[i])); 00175 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00176 lastoff += sizeof(u_int); 00177 00178 /* the string itself */ 00179 memcpy((char *)(buff + lastoff), local_comp[i], strlen(local_comp[i])); 00180 lastoff += strlen(local_comp[i]); 00181 00182 /* The XDR padding : strings must be aligned to 32bits fields */ 00183 if((strlen(local_comp[i]) % 4) == 0) 00184 delta_xdr = 0; 00185 else 00186 { 00187 delta_xdr = 4 - (strlen(local_comp[i]) % 4); 00188 memset((char *)(buff + lastoff), 0, delta_xdr); 00189 lastoff += delta_xdr; 00190 } 00191 } 00192 00193 /* 3- there is only one fs_location in the fs_locations array */ 00194 tmp_int = htonl(1); 00195 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00196 lastoff += sizeof(u_int); 00197 00198 /* 4- Only ine server in fs_location entry */ 00199 tmp_int = htonl(1); 00200 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00201 lastoff += sizeof(u_int); 00202 00203 /* 5- the len for the server's adress */ 00204 tmp_int = htonl(strlen(server_part)); 00205 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00206 lastoff += sizeof(u_int); 00207 00208 /* 6- the server's string */ 00209 memcpy((char *)(buff + lastoff), server_part, strlen(server_part)); 00210 lastoff += strlen(server_part); 00211 00212 /* 7- XDR padding for server's string */ 00213 if((strlen(server_part) % 4) == 0) 00214 delta_xdr = 0; 00215 else 00216 { 00217 delta_xdr = 4 - (strlen(server_part) % 4); 00218 memset((char *)(buff + lastoff), 0, delta_xdr); 00219 lastoff += delta_xdr; 00220 } 00221 00222 /* 8- Number of component in remote path */ 00223 tmp_int = htonl(nb_comp_remote); 00224 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00225 lastoff += sizeof(u_int); 00226 00227 /* 9- each component in local path */ 00228 for(i = 0; i < nb_comp_remote; i++) 00229 { 00230 /* The length for the string */ 00231 tmp_int = htonl(strlen(remote_comp[i])); 00232 memcpy((char *)(buff + lastoff), &tmp_int, sizeof(u_int)); 00233 lastoff += sizeof(u_int); 00234 00235 /* the string itself */ 00236 memcpy((char *)(buff + lastoff), remote_comp[i], strlen(remote_comp[i])); 00237 lastoff += strlen(remote_comp[i]); 00238 00239 /* The XDR padding : strings must be aligned to 32bits fields */ 00240 if((strlen(remote_comp[i]) % 4) == 0) 00241 delta_xdr = 0; 00242 else 00243 { 00244 delta_xdr = 4 - (strlen(remote_comp[i]) % 4); 00245 memset((char *)(buff + lastoff), 0, delta_xdr); 00246 lastoff += delta_xdr; 00247 } 00248 } 00249 00250 /* Set the len then return */ 00251 *plen = lastoff; 00252 00253 return 1; 00254 } /* nfs4_referral_str_To_Fattr_fs_location */