mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2026-09-27 00:34:57 +08:00
GP-6912 Added task monitor to Block Stream methods
This commit is contained in:
+9
-4
@@ -22,6 +22,8 @@ import java.util.zip.Deflater;
|
||||
import java.util.zip.InflaterInputStream;
|
||||
|
||||
import db.buffers.*;
|
||||
import ghidra.util.MonitoredInputStream;
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
|
||||
/**
|
||||
* <code>RemoteInputBlockStreamHandle</code> provides a serializable handle to a
|
||||
@@ -56,11 +58,11 @@ public class RemoteInputBlockStreamHandle extends RemoteBlockStreamHandle<InputB
|
||||
private class ClientInputBlockStream implements InputBlockStream {
|
||||
|
||||
private final Socket socket;
|
||||
private final InputStream in;
|
||||
private InputStream in;
|
||||
|
||||
private int blocksRemaining = getBlockCount();
|
||||
|
||||
ClientInputBlockStream(Socket socket) throws IOException {
|
||||
ClientInputBlockStream(Socket socket, TaskMonitor monitor) throws IOException {
|
||||
this.socket = socket;
|
||||
if (compressed) {
|
||||
// Uses default Inflater with nowrap=false
|
||||
@@ -68,6 +70,7 @@ public class RemoteInputBlockStreamHandle extends RemoteBlockStreamHandle<InputB
|
||||
} else {
|
||||
in = socket.getInputStream();
|
||||
}
|
||||
in = new MonitoredInputStream(in, monitor);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -121,12 +124,12 @@ public class RemoteInputBlockStreamHandle extends RemoteBlockStreamHandle<InputB
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputBlockStream openBlockStream() throws IOException {
|
||||
public InputBlockStream openBlockStream(TaskMonitor monitor) throws IOException {
|
||||
|
||||
Socket socket = connect();
|
||||
socket.setReceiveBufferSize(getPreferredBufferSize());
|
||||
|
||||
return new ClientInputBlockStream(socket);
|
||||
return new ClientInputBlockStream(socket, monitor);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -150,6 +153,8 @@ public class RemoteInputBlockStreamHandle extends RemoteBlockStreamHandle<InputB
|
||||
|
||||
// Perform final handshake before close (uncompressed)
|
||||
writeStreamEnd(socket);
|
||||
|
||||
// TODO: Investigate use of timeout if both sides are trying to do a read
|
||||
readStreamEnd(socket, false);
|
||||
}
|
||||
catch (SocketException e) {
|
||||
|
||||
+9
-8
@@ -21,6 +21,8 @@ import java.net.SocketException;
|
||||
import java.util.zip.*;
|
||||
|
||||
import db.buffers.*;
|
||||
import ghidra.util.MonitoredOutputStream;
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
|
||||
/**
|
||||
* <code>RemoteOutputBlockStreamHandle</code> provides a serializable handle to a
|
||||
@@ -39,7 +41,7 @@ public class RemoteOutputBlockStreamHandle extends RemoteBlockStreamHandle<Outpu
|
||||
* @param server block stream server instance
|
||||
* @param blockCount number of blocks to be read by server and written by client
|
||||
* @param blockSize buffer file block size
|
||||
* @throws IOException
|
||||
* @throws IOException if an IO error occurs
|
||||
*/
|
||||
public RemoteOutputBlockStreamHandle(BlockStreamServer server, int blockCount, int blockSize)
|
||||
throws IOException {
|
||||
@@ -54,16 +56,15 @@ public class RemoteOutputBlockStreamHandle extends RemoteBlockStreamHandle<Outpu
|
||||
private class ClientOutputBlockStream implements OutputBlockStream {
|
||||
|
||||
private final Socket socket;
|
||||
private final OutputStream out;
|
||||
private OutputStream out;
|
||||
|
||||
private int blocksRemaining = getBlockCount();
|
||||
|
||||
ClientOutputBlockStream(Socket socket) throws IOException {
|
||||
ClientOutputBlockStream(Socket socket, TaskMonitor monitor) throws IOException {
|
||||
this.socket = socket;
|
||||
out = new MonitoredOutputStream(socket.getOutputStream(), monitor);
|
||||
if (compressed) {
|
||||
out = new RemoteDeflaterOutputStream(socket.getOutputStream(), Deflater.BEST_SPEED);
|
||||
} else {
|
||||
out = socket.getOutputStream();
|
||||
out = new RemoteDeflaterOutputStream(out, Deflater.BEST_SPEED);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -106,12 +107,12 @@ public class RemoteOutputBlockStreamHandle extends RemoteBlockStreamHandle<Outpu
|
||||
}
|
||||
|
||||
@Override
|
||||
public OutputBlockStream openBlockStream() throws IOException {
|
||||
public OutputBlockStream openBlockStream(TaskMonitor monitor) throws IOException {
|
||||
|
||||
Socket socket = connect();
|
||||
socket.setSendBufferSize(getPreferredBufferSize());
|
||||
|
||||
return new ClientOutputBlockStream(socket);
|
||||
return new ClientOutputBlockStream(socket, monitor);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -4,9 +4,9 @@
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
@@ -17,14 +17,17 @@ package db.buffers;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
|
||||
public interface BlockStreamHandle<T extends BlockStream> {
|
||||
|
||||
/**
|
||||
* Invoked by client to establish the remote connection and return
|
||||
* the opened block stream.
|
||||
* @param monitor monitor which will allow cancellation of transfer
|
||||
* @return connected/open block stream
|
||||
* @throws IOException
|
||||
* @throws IOException if an IO error occurs
|
||||
*/
|
||||
public T openBlockStream() throws IOException;
|
||||
public T openBlockStream(TaskMonitor monitor) throws IOException;
|
||||
|
||||
}
|
||||
|
||||
@@ -20,6 +20,7 @@ import java.rmi.*;
|
||||
import java.util.NoSuchElementException;
|
||||
|
||||
import ghidra.util.Msg;
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
|
||||
/**
|
||||
* <code>BufferFileAdapter</code> provides a BufferFile implementation which
|
||||
@@ -148,10 +149,11 @@ public class BufferFileAdapter implements BufferFile {
|
||||
|
||||
/**
|
||||
* Obtain a direct stream to read all blocks of this buffer file
|
||||
* @param monitor task monitor
|
||||
* @return input block stream
|
||||
* @throws IOException
|
||||
* @throws IOException if an IO error occurs
|
||||
*/
|
||||
InputBlockStream getInputBlockStream() throws IOException {
|
||||
InputBlockStream getInputBlockStream(TaskMonitor monitor) throws IOException {
|
||||
// NOTE: This may need to change in the future if other
|
||||
// non-RMI implementation require the use of InputBlockStreamHandle
|
||||
if (isRemote()) {
|
||||
@@ -159,7 +161,7 @@ public class BufferFileAdapter implements BufferFile {
|
||||
// obtain InputBlockStream via InputBlockStreamHandle
|
||||
BlockStreamHandle<InputBlockStream> inputBlockStreamHandle =
|
||||
bufferFileHandle.getInputBlockStreamHandle();
|
||||
return inputBlockStreamHandle.openBlockStream();
|
||||
return inputBlockStreamHandle.openBlockStream(monitor);
|
||||
}
|
||||
return bufferFileHandle.getInputBlockStream();
|
||||
}
|
||||
@@ -167,10 +169,11 @@ public class BufferFileAdapter implements BufferFile {
|
||||
/**
|
||||
* Obtain a direct stream to write blocks to this buffer file
|
||||
* @param blockCount number of blocks to be written
|
||||
* @param monitor task monitor
|
||||
* @return output block stream
|
||||
* @throws IOException
|
||||
* @throws IOException if an IO error occurs
|
||||
*/
|
||||
OutputBlockStream getOutputBlockStream(int blockCount) throws IOException {
|
||||
OutputBlockStream getOutputBlockStream(int blockCount, TaskMonitor monitor) throws IOException {
|
||||
// NOTE: This may need to change in the future if other
|
||||
// non-RMI implementation require the use of InputBlockStreamHandle
|
||||
if (isRemote()) {
|
||||
@@ -178,7 +181,7 @@ public class BufferFileAdapter implements BufferFile {
|
||||
// obtain OutputBlockStream via OutputBlockStreamHandle
|
||||
BlockStreamHandle<OutputBlockStream> outputBlockStreamHandle =
|
||||
bufferFileHandle.getOutputBlockStreamHandle(blockCount);
|
||||
return outputBlockStreamHandle.openBlockStream();
|
||||
return outputBlockStreamHandle.openBlockStream(monitor);
|
||||
}
|
||||
return bufferFileHandle.getOutputBlockStream(blockCount);
|
||||
}
|
||||
|
||||
@@ -737,7 +737,8 @@ public class BufferMgr {
|
||||
Msg.trace(BufferMgr.this, "Pre-cache started...");
|
||||
int cacheCount = 0;
|
||||
BufferFileAdapter sourceAdapter = (BufferFileAdapter) sourceFile;
|
||||
try (InputBlockStream inputBlockStream = sourceAdapter.getInputBlockStream()) {
|
||||
try (InputBlockStream inputBlockStream =
|
||||
sourceAdapter.getInputBlockStream(TaskMonitor.DUMMY)) {
|
||||
BufferFileBlock block;
|
||||
while (!Thread.interrupted() && (block = inputBlockStream.readBlock()) != null) {
|
||||
DataBuffer buf = LocalBufferFile.getDataBuffer(block);
|
||||
@@ -2000,7 +2001,8 @@ public class BufferMgr {
|
||||
monitor.initialize(indexCnt);
|
||||
|
||||
// write/update all non-empty buffers
|
||||
try (OutputBlockStream out = LocalBufferFile.getOutputBlockStream(outFile, bufCount)) {
|
||||
try (OutputBlockStream out =
|
||||
LocalBufferFile.getOutputBlockStream(outFile, bufCount, monitor)) {
|
||||
for (int id = 0; id < indexCnt; id++) {
|
||||
monitor.checkCancelled();
|
||||
monitor.setProgress(id);
|
||||
|
||||
@@ -939,14 +939,16 @@ public class LocalBufferFile implements BufferFile {
|
||||
* for the specified read-only bufferFile. Input stream may not supply header block in which case
|
||||
* free list and file parameters may need to be set separately.
|
||||
* @param bufferFile buffer file opened read-only
|
||||
* @param monitor task monitor
|
||||
* @return input block stream object
|
||||
* @throws IOException if an I/O error occurs
|
||||
*/
|
||||
private static InputBlockStream getInputBlockStream(BufferFile bufferFile) throws IOException {
|
||||
private static InputBlockStream getInputBlockStream(BufferFile bufferFile, TaskMonitor monitor)
|
||||
throws IOException {
|
||||
// This method is used so we can utilize a package method and avoid putting
|
||||
// it on the BufferFile interface
|
||||
if (bufferFile instanceof BufferFileAdapter) {
|
||||
return ((BufferFileAdapter) bufferFile).getInputBlockStream();
|
||||
return ((BufferFileAdapter) bufferFile).getInputBlockStream(monitor);
|
||||
}
|
||||
if (bufferFile instanceof LocalBufferFile) {
|
||||
return ((LocalBufferFile) bufferFile).getInputBlockStream();
|
||||
@@ -961,18 +963,21 @@ public class LocalBufferFile implements BufferFile {
|
||||
* to select which buffer should be transferred. Input stream may not supply header block
|
||||
* in which case free list and file parameters may need to be set separately.
|
||||
* @param bufferFile buffer file opened read-only
|
||||
* @param monitor task monitor
|
||||
* @return input block stream object
|
||||
* @throws IOException if an I/O error occurs
|
||||
*/
|
||||
private static InputBlockStream getInputBlockStream(BufferFile bufferFile, ChangeMap changeMap)
|
||||
private static InputBlockStream getInputBlockStream(BufferFile bufferFile, ChangeMap changeMap,
|
||||
TaskMonitor monitor)
|
||||
throws IOException {
|
||||
if (changeMap == null) {
|
||||
return getInputBlockStream(bufferFile);
|
||||
return getInputBlockStream(bufferFile, monitor);
|
||||
}
|
||||
// This method is used so we can utilize a package method and avoid putting
|
||||
// it on the BufferFile interface
|
||||
if (bufferFile instanceof ManagedBufferFileAdapter) {
|
||||
return ((ManagedBufferFileAdapter) bufferFile).getInputBlockStream(changeMap.getData());
|
||||
return ((ManagedBufferFileAdapter) bufferFile).getInputBlockStream(changeMap.getData(),
|
||||
monitor);
|
||||
}
|
||||
if (bufferFile instanceof LocalManagedBufferFile) {
|
||||
return ((LocalManagedBufferFile) bufferFile).getInputBlockStream(changeMap.getData());
|
||||
@@ -987,15 +992,17 @@ public class LocalBufferFile implements BufferFile {
|
||||
* @param bufferFile write-able buffer file
|
||||
* @param blockCount number of blocks to be written. This should be available from
|
||||
* the corresponding {@link InputBlockStream}.
|
||||
* @param monitor task monitor
|
||||
* @return output block stream object
|
||||
* @throws IOException if an I/O error occurs
|
||||
*/
|
||||
static OutputBlockStream getOutputBlockStream(BufferFile bufferFile, int blockCount)
|
||||
static OutputBlockStream getOutputBlockStream(BufferFile bufferFile, int blockCount,
|
||||
TaskMonitor monitor)
|
||||
throws IOException {
|
||||
// This method is used so we can utilize a package method and avoid putting
|
||||
// it on the BufferFile interface
|
||||
if (bufferFile instanceof BufferFileAdapter) {
|
||||
return ((BufferFileAdapter) bufferFile).getOutputBlockStream(blockCount);
|
||||
return ((BufferFileAdapter) bufferFile).getOutputBlockStream(blockCount, monitor);
|
||||
}
|
||||
if (bufferFile instanceof LocalBufferFile) {
|
||||
return ((LocalBufferFile) bufferFile).getOutputBlockStream(blockCount);
|
||||
@@ -1030,11 +1037,12 @@ public class LocalBufferFile implements BufferFile {
|
||||
int srcBlockCnt;
|
||||
boolean headerTransferRequired;
|
||||
|
||||
try (InputBlockStream in = getInputBlockStream(srcFile, changeMap)) {
|
||||
try (InputBlockStream in = getInputBlockStream(srcFile, changeMap, monitor)) {
|
||||
headerTransferRequired = !in.includesHeaderBlock();
|
||||
srcBlockCnt = in.getBlockCount();
|
||||
monitor.initialize(srcBlockCnt + 2);
|
||||
try (OutputBlockStream out = getOutputBlockStream(destFile, in.getBlockCount())) {
|
||||
try (OutputBlockStream out =
|
||||
getOutputBlockStream(destFile, in.getBlockCount(), monitor)) {
|
||||
completeBlockStreamTransfer(in, out, monitor);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,9 +4,9 @@
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
@@ -18,6 +18,8 @@ package db.buffers;
|
||||
import java.io.IOException;
|
||||
import java.rmi.Remote;
|
||||
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
|
||||
/**
|
||||
* <code>ManagedBufferFileAdapter</code> provides a ManagedBufferFile implementation which
|
||||
* wraps a ManagedBufferFileHandle.
|
||||
@@ -86,7 +88,8 @@ public class ManagedBufferFileAdapter extends BufferFileAdapter implements Manag
|
||||
* @return input block stream
|
||||
* @throws IOException
|
||||
*/
|
||||
InputBlockStream getInputBlockStream(byte[] changeMapData) throws IOException {
|
||||
InputBlockStream getInputBlockStream(byte[] changeMapData, TaskMonitor monitor)
|
||||
throws IOException {
|
||||
// NOTE: This may need to change in the future if other
|
||||
// non-RMI implementation require the use of InputBlockStreamHandle
|
||||
if (managedBufferFileHandle instanceof Remote) {
|
||||
@@ -94,7 +97,7 @@ public class ManagedBufferFileAdapter extends BufferFileAdapter implements Manag
|
||||
// obtain InputBlockStream via InputBlockStreamHandle
|
||||
BlockStreamHandle<InputBlockStream> inputBlockStreamHandle =
|
||||
managedBufferFileHandle.getInputBlockStreamHandle(changeMapData);
|
||||
return inputBlockStreamHandle.openBlockStream();
|
||||
return inputBlockStreamHandle.openBlockStream(monitor);
|
||||
}
|
||||
return managedBufferFileHandle.getInputBlockStream(changeMapData);
|
||||
}
|
||||
|
||||
+12
-3
@@ -385,12 +385,21 @@ public abstract class LocalFileSystem implements FileSystem {
|
||||
}
|
||||
ItemPropertyFile propertyFile = itemStorage.getPropertyFile();
|
||||
if (propertyFile.exists()) {
|
||||
return LocalFolderItem.getFolderItem(this, propertyFile);
|
||||
LocalFolderItem item = LocalFolderItem.getFolderItem(this, propertyFile);
|
||||
if (item != null) {
|
||||
return item;
|
||||
}
|
||||
Msg.warn(this, "Attempting item cleanup due to invalid state: " +
|
||||
new File(propertyFile.getParentStorageDirectory(),
|
||||
propertyFile.getStorageName()));
|
||||
}
|
||||
else {
|
||||
Msg.warn(this, "Attempting item cleanup due to missing property file: " +
|
||||
new File(propertyFile.getParentStorageDirectory(),
|
||||
propertyFile.getStorageName()));
|
||||
}
|
||||
|
||||
// force cleanup of bad storage allocation
|
||||
Msg.warn(this, "Attempting item cleanup due to missing property file: " +
|
||||
new File(propertyFile.getParentStorageDirectory(), propertyFile.getStorageName()));
|
||||
itemDeleted(folderPath, name);
|
||||
}
|
||||
catch (InvalidObjectException e) {
|
||||
|
||||
Reference in New Issue
Block a user