use of org.apache.plc4x.java.s7.readwrite.context.S7DriverContext in project plc4x by apache.
the class S7Optimizer method processWriteRequest.
@Override
protected List<PlcRequest> processWriteRequest(PlcWriteRequest writeRequest, DriverContext driverContext) {
S7DriverContext s7DriverContext = (S7DriverContext) driverContext;
List<PlcRequest> processedRequests = new LinkedList<>();
// This calculates the size of the header for the request and response.
int curRequestSize = EMPTY_WRITE_REQUEST_SIZE;
// An empty response has the same size as an empty request.
int curResponseSize = EMPTY_WRITE_RESPONSE_SIZE;
// List of all items in the current request.
LinkedHashMap<String, FieldValueItem> curFields = new LinkedHashMap<>();
for (String fieldName : writeRequest.getFieldNames()) {
S7Field field = (S7Field) writeRequest.getField(fieldName);
PlcValue value = writeRequest.getPlcValue(fieldName);
int writeRequestItemSize = S7_ADDRESS_ANY_SIZE + 4;
if (field.getDataType() == TransportSize.BOOL) {
writeRequestItemSize += Math.ceil((double) field.getNumberOfElements() / 8);
} else {
writeRequestItemSize += (field.getNumberOfElements() * field.getDataType().getSizeInBytes());
}
// If it's an odd number of bytes, add one to make it even
if (writeRequestItemSize % 2 == 1) {
writeRequestItemSize++;
}
int writeResponseItemSize = 4;
// If adding the item would not exceed the sizes, add it to the current request.
if (((curRequestSize + writeRequestItemSize) <= s7DriverContext.getPduSize()) && ((curResponseSize + writeResponseItemSize) <= s7DriverContext.getPduSize())) {
// Increase the current request sizes.
curRequestSize += writeRequestItemSize;
curResponseSize += writeResponseItemSize;
// Add the item.
} else // If adding them would exceed, start a new request.
{
// Create a new PlcWriteRequest containing the current field item.
processedRequests.add(new DefaultPlcWriteRequest(((DefaultPlcWriteRequest) writeRequest).getWriter(), curFields));
// Reset the size and item lists.
curRequestSize = EMPTY_WRITE_REQUEST_SIZE + writeRequestItemSize;
curResponseSize = EMPTY_WRITE_RESPONSE_SIZE + writeResponseItemSize;
curFields = new LinkedHashMap<>();
// Splitting of huge fields not yet implemented, throw an exception instead.
if (((curRequestSize + writeRequestItemSize) > s7DriverContext.getPduSize()) && ((curResponseSize + writeResponseItemSize) > s7DriverContext.getPduSize())) {
throw new PlcRuntimeException("Field size exceeds maximum payload for one item.");
}
}
curFields.put(fieldName, new FieldValueItem(field, value));
}
// Create a new PlcWriteRequest from the remaining field items.
if (!curFields.isEmpty()) {
processedRequests.add(new DefaultPlcWriteRequest(((DefaultPlcWriteRequest) writeRequest).getWriter(), curFields));
}
return processedRequests;
}
use of org.apache.plc4x.java.s7.readwrite.context.S7DriverContext in project plc4x by apache.
the class S7Optimizer method processReadRequest.
@Override
protected List<PlcRequest> processReadRequest(PlcReadRequest readRequest, DriverContext driverContext) {
S7DriverContext s7DriverContext = (S7DriverContext) driverContext;
List<PlcRequest> processedRequests = new LinkedList<>();
// This calculates the size of the header for the request and response.
int curRequestSize = EMPTY_READ_REQUEST_SIZE;
// An empty response has the same size as an empty request.
int curResponseSize = EMPTY_READ_RESPONSE_SIZE;
// List of all items in the current request.
LinkedHashMap<String, PlcField> curFields = new LinkedHashMap<>();
for (String fieldName : readRequest.getFieldNames()) {
S7Field field = (S7Field) readRequest.getField(fieldName);
int readRequestItemSize = S7_ADDRESS_ANY_SIZE;
int readResponseItemSize = 4 + (field.getNumberOfElements() * field.getDataType().getSizeInBytes());
// If it's an odd number of bytes, add one to make it even
if (readResponseItemSize % 2 == 1) {
readResponseItemSize++;
}
// If adding the item would not exceed the sizes, add it to the current request.
if (((curRequestSize + readRequestItemSize) <= s7DriverContext.getPduSize()) && ((curResponseSize + readResponseItemSize) <= s7DriverContext.getPduSize())) {
// Increase the current request sizes.
curRequestSize += readRequestItemSize;
curResponseSize += readResponseItemSize;
// Add the item.
} else // If they would exceed, start a new request.
{
// Create a new PlcReadRequest containing the current field item.
processedRequests.add(new DefaultPlcReadRequest(((DefaultPlcReadRequest) readRequest).getReader(), curFields));
// Reset the size and item lists.
curRequestSize = EMPTY_READ_REQUEST_SIZE + readRequestItemSize;
curResponseSize = EMPTY_READ_RESPONSE_SIZE + readResponseItemSize;
curFields = new LinkedHashMap<>();
// Splitting of huge fields not yet implemented, throw an exception instead.
if (((curRequestSize + readRequestItemSize) > s7DriverContext.getPduSize()) && ((curResponseSize + readResponseItemSize) > s7DriverContext.getPduSize())) {
throw new PlcRuntimeException("Field size exceeds maximum payload for one item.");
}
}
curFields.put(fieldName, field);
}
// Create a new PlcReadRequest from the remaining field items.
if (!curFields.isEmpty()) {
processedRequests.add(new DefaultPlcReadRequest(((DefaultPlcReadRequest) readRequest).getReader(), curFields));
}
return processedRequests;
}
Aggregations