예제 #1
0
  static XaMessageRequest createXaMessageRequest(ByteQueue queue) throws ModbusTransportException {
    // Remove the XA header
    int transactionId = ModbusUtils.popShort(queue);
    int protocolId = ModbusUtils.popShort(queue);
    if (protocolId != ModbusUtils.IP_PROTOCOL_ID)
      throw new ModbusTransportException("Unsupported IP protocol id: " + protocolId);
    ModbusUtils.popShort(queue); // Length, which we don't care about.

    // Create the modbus response.
    ModbusRequest request = ModbusRequest.createModbusRequest(queue);
    return new XaMessageRequest(request, transactionId);
  }
예제 #2
0
  @Override
  public synchronized ModbusResponse sendImpl(ModbusRequest request)
      throws ModbusTransportException {

    if (!connected) {
      LOG.debug("No connection in Port: " + ipParameters.getPort());
      throw new ModbusTransportException(
          new Exception("TCP Listener has no active connection!"), request.getSlaveId());
    }

    if (!initialized) {
      LOG.debug("Listener already terminated " + ipParameters.getPort());
      return null;
    }

    // Wrap the modbus request in a ip request.
    OutgoingRequestMessage ipRequest;
    if (ipParameters.isEncapsulated()) {
      ipRequest = new EncapMessageRequest(request);
      StringBuilder sb = new StringBuilder();
      for (byte b :
          Arrays.copyOfRange(ipRequest.getMessageData(), 0, ipRequest.getMessageData().length)) {
        sb.append(String.format("%02X ", b));
      }
      LOG.debug("Encap Request: " + sb.toString());
    } else {
      ipRequest = new XaMessageRequest(request, getNextTransactionId());
      StringBuilder sb = new StringBuilder();
      for (byte b :
          Arrays.copyOfRange(ipRequest.getMessageData(), 0, ipRequest.getMessageData().length)) {
        sb.append(String.format("%02X ", b));
      }
      LOG.debug("Xa Request: " + sb.toString());
    }

    // Send the request to get the response.
    IpMessageResponse ipResponse;
    try {
      // Send data via handler!
      handler.conn.DEBUG = true;
      ipResponse = (IpMessageResponse) handler.conn.send(ipRequest);
      if (ipResponse == null) {
        throw new ModbusTransportException(
            new Exception("No valid response from slave!"), request.getSlaveId());
      }
      StringBuilder sb = new StringBuilder();
      for (byte b :
          Arrays.copyOfRange(ipResponse.getMessageData(), 0, ipResponse.getMessageData().length)) {
        sb.append(String.format("%02X ", b));
      }
      LOG.debug("Response: " + sb.toString());
      return ipResponse.getModbusResponse();
    } catch (Exception e) {
      LOG.debug(
          e.getLocalizedMessage() + ",  Port: " + ipParameters.getPort() + ", retries: " + retries);
      if (retries < 10 && !e.getLocalizedMessage().contains("Broken")) {
        retries++;
      } else {
        /*
         * To recover from a Broken Pipe, the only way is to restart serverSocket
         */
        LOG.debug("Restarting Socket,  Port: " + ipParameters.getPort() + ", retries: " + retries);

        // Close the serverSocket first to prevent new messages.
        try {
          if (serverSocket != null) serverSocket.close();
        } catch (IOException e2) {
          LOG.debug("Error closing socket" + e2.getLocalizedMessage(), e);
          getExceptionHandler().receivedException(e2);
        }

        // Close all open connections.
        if (handler != null) {
          handler.closeConnection();
          terminateListener();
        }

        if (!initialized) {
          LOG.debug("Listener already terminated " + ipParameters.getPort());
          return null;
        }

        executorService = Executors.newCachedThreadPool();
        try {
          startListener();
        } catch (Exception e2) {
          LOG.warn("Error trying to restart socket" + e2.getLocalizedMessage(), e);
          throw new ModbusTransportException(e2, request.getSlaveId());
        }
        retries = 0;
      }
      LOG.warn(
          "Error sending request,  Port: " + ipParameters.getPort() + ", msg: " + e.getMessage());
      // Simple send error!
      throw new ModbusTransportException(e, request.getSlaveId());
    }
  }