private void notifyNamespace(PnfsId pnfsid, FileAttributes fileAttributes) throws InterruptedException { while (true) { try { pnfs.fileFlushed(pnfsid, fileAttributes); break; } catch (CacheException e) { if (e.getRc() == CacheException.FILE_NOT_FOUND || e.getRc() == CacheException.NOT_IN_TRASH) { /* In case the file was deleted, we are presented * with the problem that the file is now on tape, * however the location has not been registered * centrally. Hence the copy on tape will not be * removed by the HSM cleaner. The sensible thing * seems to be to remove the file from tape here. * For now we ignore this issue (REVISIT). */ break; } /* The message to the PnfsManager failed. There are several * possible reasons for this; we may have lost the * connection to the PnfsManager; the PnfsManager may have * lost its connection to the namespace or otherwise be in * trouble; bugs; etc. * * We keep retrying until we succeed. This will effectively * block this thread from flushing any other files, which * seems sensible when we have trouble talking to the * PnfsManager. If the pool crashes or gets restarted while * waiting here, we will end up flushing the file again. We * assume that the nearline storage is able to eliminate the * duplicate; or at least tolerate the duplicate (given that * this situation should be rare, we can live with a little * bit of wasted tape). */ LOGGER.error( "Error notifying pnfsmanager about a flushed file: {} ({})", e.getMessage(), e.getRc()); } TimeUnit.MINUTES.sleep(2); } }
public void fail(T msg, Exception e) { if (e instanceof CacheException) { CacheException ce = (CacheException) e; fail(msg, ce.getRc(), ce.getMessage()); } else if (e instanceof IllegalArgumentException) { fail(msg, CacheException.INVALID_ARGS, e.getMessage()); } else { fail(msg, CacheException.UNEXPECTED_SYSTEM_EXCEPTION, e); } }
/** * ask pool manager for a file * * <p>On successful reply from pool manager corresponding O request will be sent to the pool to * start a NFS mover. * * @throws ChimeraNFSException in case of NFS friendly errors ( like ACCESS ) * @throws IOException in case of any other errors */ @Override public Layout layoutGet(CompoundContext context, Inode nfsInode, int ioMode, stateid4 stateid) throws IOException { FsInode inode = _fileFileSystemProvider.inodeFromBytes(nfsInode.getFileId()); CDC cdc = CDC.reset(_cellName, _domainName); try { NDC.push(inode.toString()); NDC.push(context.getRpcCall().getTransport().getRemoteSocketAddress().toString()); deviceid4 deviceid; if (inode.type() != FsInodeType.INODE || inode.getLevel() != 0) { /* * all non regular files ( AKA pnfs dot files ) provided by door itself. */ deviceid = MDS_ID; } else { final InetSocketAddress remote = context.getRpcCall().getTransport().getRemoteSocketAddress(); final PnfsId pnfsId = new PnfsId(inode.toString()); final NFS4ProtocolInfo protocolInfo = new NFS4ProtocolInfo(remote, new org.dcache.chimera.nfs.v4.xdr.stateid4(stateid)); Transfer.initSession(); NfsTransfer transfer = _ioMessages.get(stateid); if (transfer == null) { transfer = new NfsTransfer(_pnfsHandler, context.getRpcCall().getCredential().getSubject()); transfer.setProtocolInfo(protocolInfo); transfer.setCellName(this.getCellName()); transfer.setDomainName(this.getCellDomainName()); transfer.setBillingStub(_billingStub); transfer.setPoolStub(_poolManagerStub); transfer.setPoolManagerStub(_poolManagerStub); transfer.setPnfsId(pnfsId); transfer.setClientAddress(remote); transfer.readNameSpaceEntry(); _ioMessages.put(stateid, transfer); PoolDS ds = getPool(transfer, ioMode); deviceid = ds.getDeviceId(); } else { PoolDS ds = transfer.waitForRedirect(NFS_RETRY_PERIOD); deviceid = ds.getDeviceId(); } } nfs_fh4 fh = new nfs_fh4(nfsInode.toNfsHandle()); // -1 is special value, which means entire file layout4 layout = Layout.getLayoutSegment(deviceid, fh, ioMode, 0, nfs4_prot.NFS4_UINT64_MAX); return new Layout(true, stateid, new layout4[] {layout}); } catch (FileInCacheException e) { cleanStateAndKillMover(stateid); throw new ChimeraNFSException(nfsstat.NFSERR_IO, e.getMessage()); } catch (CacheException e) { cleanStateAndKillMover(stateid); /* * error 243: file is broken on tape. * can't do a much. Tell it to client. */ int status = e.getRc() == CacheException.BROKEN_ON_TAPE ? nfsstat.NFSERR_IO : nfsstat.NFSERR_LAYOUTTRYLATER; throw new ChimeraNFSException(status, e.getMessage()); } catch (InterruptedException e) { cleanStateAndKillMover(stateid); throw new ChimeraNFSException(nfsstat.NFSERR_LAYOUTTRYLATER, e.getMessage()); } finally { cdc.close(); } }