fsal_status_t MFSL_truncate(mfsl_object_t * filehandle, /* IN */ fsal_op_context_t * p_context, /* IN */ mfsl_context_t * p_mfsl_context, /* IN */ fsal_size_t length, /* IN */ fsal_file_t * file_descriptor, /* INOUT */ fsal_attrib_list_t * object_attributes /* [ IN/OUT ] */ ) { return FSAL_truncate(&filehandle->handle, p_context, length, file_descriptor, object_attributes); } /* MFSL_truncate */
/** * * MFSL_truncate_async_op: Callback for asynchronous truncate. * * Callback for asynchronous truncate. * * @param popasyncdes [INOUT] asynchronous operation descriptor * * @return the status of the performed FSAL_truncate. */ fsal_status_t MFSL_truncate_async_op(mfsl_async_op_desc_t * popasyncdesc) { fsal_status_t fsal_status; LogDebug(COMPONENT_MFSL, "Making asynchronous FSAL_truncate for async op %p", popasyncdesc); P(popasyncdesc->op_args.truncate.pmobject->lock); fsal_status = FSAL_truncate(&(popasyncdesc->op_args.truncate.pmobject->handle), &popasyncdesc->fsal_op_context, popasyncdesc->op_args.truncate.size, NULL, /* deprecated parameter */ &popasyncdesc->op_res.truncate.attr); V(popasyncdesc->op_args.truncate.pmobject->lock); return fsal_status; } /* MFSL_truncate_async_op */
fsal_status_t MFSL_truncate(mfsl_object_t * filehandle, /* IN */ fsal_op_context_t * p_context, /* IN */ mfsl_context_t * p_mfsl_context, /* IN */ fsal_size_t length, /* IN */ mfsl_file_t * file_descriptor, /* INOUT */ fsal_attrib_list_t * object_attributes, /* [ IN/OUT ] */ void * pextra ) { struct timeval start, stop, delta ; fsal_status_t fsal_status = { ERR_FSAL_NO_ERROR, 0 } ; gettimeofday( &start, 0 ) ; fsal_status = FSAL_truncate(&filehandle->handle, p_context, length, &file_descriptor->fsal_file, object_attributes); gettimeofday( &stop, 0 ) ; delta = mfsl_timer_diff( &stop, &start ) ; LogFullDebug( COMPONENT_MFSL, "%s: duration=%ld.%06ld", __FUNCTION__, delta.tv_sec, delta.tv_usec ) ; return fsal_status ; } /* MFSL_truncate */
/** * * cache_inode_setattrs: set the attributes for an entry located in the cache by its address. * * Sets the attributes for an entry located in the cache by its address. Attributes are provided * with compliance to the underlying FSAL semantics. Attributes that are set are returned in "*pattr". * * @param pentry_parent [IN] entry for the parent directory to be managed. * @param pattr [INOUT] attributes for the entry that we have found. Out: attributes set. * @param ht [INOUT] hash table used for the cache, unused in this call. * @param pclient [INOUT] ressource allocated by the client for the nfs management. * @param pcontext [IN] FSAL credentials * @param pstatus [OUT] returned status. * * @return CACHE_INODE_SUCCESS if operation is a success \n * @return CACHE_INODE_LRU_ERROR if allocation error occured when validating the entry * */ cache_inode_status_t cache_inode_setattr(cache_entry_t * pentry, fsal_attrib_list_t * pattr, hash_table_t * ht, /* Unused, kept for protototype's homogeneity */ cache_inode_client_t * pclient, fsal_op_context_t * pcontext, cache_inode_status_t * pstatus) { fsal_handle_t *pfsal_handle = NULL; fsal_status_t fsal_status; fsal_attrib_list_t *p_object_attributes = NULL; fsal_attrib_list_t result_attributes; fsal_attrib_list_t truncate_attributes; /* Set the return default to CACHE_INODE_SUCCESS */ *pstatus = CACHE_INODE_SUCCESS; /* stat */ pclient->stat.nb_call_total += 1; pclient->stat.func_stats.nb_call[CACHE_INODE_SETATTR] += 1; /* Lock the entry */ P_w(&pentry->lock); switch (pentry->internal_md.type) { case REGULAR_FILE: pfsal_handle = &pentry->object.file.handle; break; case SYMBOLIC_LINK: assert(pentry->object.symlink); pfsal_handle = &pentry->object.symlink->handle; break; case FS_JUNCTION: case DIRECTORY: pfsal_handle = &pentry->object.dir.handle; break; case CHARACTER_FILE: case BLOCK_FILE: case SOCKET_FILE: case FIFO_FILE: pfsal_handle = &pentry->object.special_obj.handle; break; case UNASSIGNED: case RECYCLED: LogCrit(COMPONENT_CACHE_INODE, "WARNING: unknown source pentry type: internal_md.type=%d, line %d in file %s", pentry->internal_md.type, __LINE__, __FILE__); *pstatus = CACHE_INODE_BAD_TYPE; return *pstatus; } /* Call FSAL to set the attributes */ /* result_attributes.asked_attributes = pattr->asked_attributes ; */ /* mod Th.Leibovici on 2006/02/13 * We ask back all standard attributes, in case they have been modified * by another program (pftp, rcpd...) */ memset(&result_attributes, 0, sizeof(fsal_attrib_list_t)); result_attributes.asked_attributes = pclient->attrmask; /* end of mod */ #ifdef _USE_MFSL fsal_status = MFSL_setattrs(&pentry->mobject, pcontext, &pclient->mfsl_context, pattr, &result_attributes, NULL); #else fsal_status = FSAL_setattrs(pfsal_handle, pcontext, pattr, &result_attributes); #endif if(FSAL_IS_ERROR(fsal_status)) { *pstatus = cache_inode_error_convert(fsal_status); V_w(&pentry->lock); /* stat */ pclient->stat.func_stats.nb_err_unrecover[CACHE_INODE_SETATTR] += 1; if(fsal_status.major == ERR_FSAL_STALE) { cache_inode_status_t kill_status; LogEvent(COMPONENT_CACHE_INODE, "cache_inode_setattr: Stale FSAL File Handle detected for pentry = %p", pentry); if(cache_inode_kill_entry(pentry, NO_LOCK, ht, pclient, &kill_status) != CACHE_INODE_SUCCESS) LogCrit(COMPONENT_CACHE_INODE, "cache_inode_setattr: Could not kill entry %p, status = %u", pentry, kill_status); *pstatus = CACHE_INODE_FSAL_ESTALE; } return *pstatus; } if(pattr->asked_attributes & FSAL_ATTR_SIZE) { truncate_attributes.asked_attributes = pclient->attrmask; fsal_status = FSAL_truncate(pfsal_handle, pcontext, pattr->filesize, NULL, &truncate_attributes); if(FSAL_IS_ERROR(fsal_status)) { *pstatus = cache_inode_error_convert(fsal_status); V_w(&pentry->lock); /* stat */ pclient->stat.func_stats.nb_err_unrecover[CACHE_INODE_SETATTR] += 1; if(fsal_status.major == ERR_FSAL_STALE) { cache_inode_status_t kill_status; LogEvent(COMPONENT_CACHE_INODE, "cache_inode_setattr: Stale FSAL File Handle detected for pentry = %p", pentry); if(cache_inode_kill_entry(pentry, NO_LOCK, ht, pclient, &kill_status) != CACHE_INODE_SUCCESS) LogCrit(COMPONENT_CACHE_INODE, "cache_inode_setattr: Could not kill entry %p, status = %u", pentry, kill_status); *pstatus = CACHE_INODE_FSAL_ESTALE; } return *pstatus; } } /* Keep the new attribute in cache */ switch (pentry->internal_md.type) { case REGULAR_FILE: p_object_attributes = &(pentry->object.file.attributes); break; case SYMBOLIC_LINK: assert(pentry->object.symlink); p_object_attributes = &(pentry->object.symlink->attributes); break; case FS_JUNCTION: case DIRECTORY: p_object_attributes = &(pentry->object.dir.attributes); break; case CHARACTER_FILE: case BLOCK_FILE: case SOCKET_FILE: case FIFO_FILE: p_object_attributes = &(pentry->object.special_obj.attributes); break; case UNASSIGNED: case RECYCLED: LogCrit(COMPONENT_CACHE_INODE, "WARNING: unknown source pentry type: internal_md.type=%d, line %d in file %s", pentry->internal_md.type, __LINE__, __FILE__); *pstatus = CACHE_INODE_BAD_TYPE; return *pstatus; } /* Update the cached attributes */ if((result_attributes.asked_attributes & FSAL_ATTR_SIZE) || (result_attributes.asked_attributes & FSAL_ATTR_SPACEUSED)) { if(pentry->internal_md.type == REGULAR_FILE) { if(pentry->object.file.pentry_content == NULL) { /* Operation on a non data cached file */ p_object_attributes->filesize = result_attributes.filesize; p_object_attributes->spaceused = result_attributes.filesize; /* Unclear hook here. BUGAZOMEU */ } else { /* Data cached file */ /* Do not set the p_object_attributes->filesize and p_object_attributes->spaceused in this case * This will lead to a situation where (for example) untar-ing a file will produced invalid files * with a size of 0 despite the fact that they are not empty */ LogFullDebug(COMPONENT_CACHE_INODE, "cache_inode_setattr with FSAL_ATTR_SIZE on data cached entry"); } } else if(pattr->asked_attributes & FSAL_ATTR_SIZE) LogCrit(COMPONENT_CACHE_INODE, "WARNING !!! cache_inode_setattr tried to set size on a non REGULAR_FILE type=%d", pentry->internal_md.type); } if(result_attributes.asked_attributes & (FSAL_ATTR_MODE | FSAL_ATTR_OWNER | FSAL_ATTR_GROUP)) { if(result_attributes.asked_attributes & FSAL_ATTR_MODE) p_object_attributes->mode = result_attributes.mode; if(result_attributes.asked_attributes & FSAL_ATTR_OWNER) p_object_attributes->owner = result_attributes.owner; if(result_attributes.asked_attributes & FSAL_ATTR_GROUP) p_object_attributes->group = result_attributes.group; } if(result_attributes.asked_attributes & (FSAL_ATTR_ATIME | FSAL_ATTR_CTIME | FSAL_ATTR_MTIME)) { if(result_attributes.asked_attributes & FSAL_ATTR_ATIME) p_object_attributes->atime = result_attributes.atime; if(result_attributes.asked_attributes & FSAL_ATTR_CTIME) p_object_attributes->ctime = result_attributes.ctime; if(result_attributes.asked_attributes & FSAL_ATTR_MTIME) p_object_attributes->mtime = result_attributes.mtime; } #ifdef _USE_NFS4_ACL if(result_attributes.asked_attributes & FSAL_ATTR_ACL) { LogDebug(COMPONENT_CACHE_INODE, "cache_inode_setattr: old acl = %p, new acl = %p", p_object_attributes->acl, result_attributes.acl); /* Release previous acl entry. */ if(p_object_attributes->acl) { fsal_acl_status_t status; nfs4_acl_release_entry(p_object_attributes->acl, &status); if(status != NFS_V4_ACL_SUCCESS) LogEvent(COMPONENT_CACHE_INODE, "cache_inode_setattr: Failed to release old acl:" " status = %d", status); } /* Update with new acl entry. */ p_object_attributes->acl = result_attributes.acl; } #endif /* _USE_NFS4_ACL */ /* Return the attributes as set */ *pattr = *p_object_attributes; /* validate the entry */ *pstatus = cache_inode_valid(pentry, CACHE_INODE_OP_SET, pclient); /* Release the entry */ V_w(&pentry->lock); /* stat */ if(*pstatus != CACHE_INODE_SUCCESS) pclient->stat.func_stats.nb_err_retryable[CACHE_INODE_SETATTR] += 1; else pclient->stat.func_stats.nb_success[CACHE_INODE_SETATTR] += 1; return *pstatus; } /* cache_inode_setattr */
fsal_status_t MFSL_truncate(mfsl_object_t * filehandle, /* IN */ fsal_op_context_t * p_context, /* IN */ mfsl_context_t * p_mfsl_context, /* IN */ fsal_size_t length, /* IN */ mfsl_file_t * file_descriptor, /* INOUT */ fsal_attrib_list_t * object_attributes, /* [ IN/OUT ] */ void * pextra ) { int pnfs_status ; fsal_status_t fsal_status ; pnfs_file_t * ppnfs_file = NULL ; pnfs_fileloc_t pnfs_location ; fsal_status = FSAL_truncate(&filehandle->handle, p_context, length, &file_descriptor->fsal_file, object_attributes); if( FSAL_IS_ERROR( fsal_status ) ) return fsal_status ; if( pextra == NULL ) /* Not a regular file */ return fsal_status ; ppnfs_file = (pnfs_file_t *)pextra ; if( ppnfs_file->ds_file.allocated == FALSE ) { if(! pnfs_get_location( &p_mfsl_context->pnfsclient, &filehandle->handle, NULL, &pnfs_location ) ) { LogDebug(COMPONENT_MFSL, "LOOKUP PNFS support : can't build pnfs_location" ) ; fsal_status.major = ERR_FSAL_IO ; fsal_status.minor = 0 ; return fsal_status ; } if((pnfs_status = pnfs_lookup_file( &p_mfsl_context->pnfsclient, &pnfs_location, ppnfs_file ) ) != NFS4_OK ) { LogDebug(COMPONENT_MFSL, "LOOKUP PNFS support : can't build pnfs_location" ) ; fsal_status.major = ERR_FSAL_IO ; fsal_status.minor = 0 ; return fsal_status ; } ppnfs_file->ds_file.allocated = TRUE ; } if((pnfs_status = pnfs_truncate_file( &p_mfsl_context->pnfsclient, length, ppnfs_file ) ) != NFS4_OK ) { LogDebug(COMPONENT_MFSL, "OPEN PNFS TRUNCATE DS FILE : Error %u", pnfs_status ) ; fsal_status.major == ERR_FSAL_IO ; fsal_status.minor == 0 ; return fsal_status ; } fsal_status.major == ERR_FSAL_NO_ERROR ; fsal_status.minor == 0 ; return fsal_status ; } /* MFSL_truncate */