jvm在试图声明一台javapos-epson热敏打印机时崩溃

ffx8fchx  于 2021-07-04  发布在  Java
关注(0)|答案(1)|浏览(545)

我正在使用epson_javapos_adk_11414_for_linux_x64安装带有PC的javapos( sh installJavaPOSFull-64.sh )
我在不同的shell中一个接一个地运行这个程序,第二个进程由于某种原因崩溃:

import jpos.JposException;
import jpos.POSPrinter;
import jpos.util.JposPropertiesConst;

import java.time.Duration;
import java.time.Instant;

public class POSPrinterClaimTest {
  static POSPrinter posPrinter;

  private static Boolean isOpen = false;
  private static Boolean isClaimed = false;
  private static Boolean isEnabled = false;

  static {
    System.setProperty(
        JposPropertiesConst.JPOS_POPULATOR_FILE_PROP_NAME, "jpos.xml");
  }

  public static void main(String[] args) {
    try {
      posPrinter = new POSPrinter();
      Instant start = Instant.now();
      Instant finish = null;
      Long timeElapsed = null;
      openConnection("POSPrinter1");
      finish = Instant.now();
      timeElapsed = Duration.between(start, finish).toMillis();
      System.out.println("Time taken to connect : " + timeElapsed.toString());
      Thread.sleep(100000L);
      terminate();
      System.out.println("terminated from try block");
    } catch (JposException | InterruptedException e) {
      e.printStackTrace();
      try {
        terminate();
        System.out.println("terminated from catch block");
        Thread.sleep(5000);
      } catch (JposException | InterruptedException jposException) {
        jposException.printStackTrace();
      }
    } catch(Throwable t){
      t.printStackTrace();
    } finally {
      posPrinter = null;
    }
  }

  private static void openConnection(String printerName) throws JposException {
    try {

      String printerNamesss = printerName;
      /**
       * open the printer object according to the device logical name defined in jpos.xml
       */
      posPrinter.open(printerName);
      isOpen = true;
      System.out.println("opened");
      /**
       * Get the exclusive control right for the opened device.
       * Then the device is disable from other application.
       * */
      posPrinter.claim(3000);
      isClaimed = true;
      System.out.println("claimed");
      /**
       *  enable the device for input and output
       */
      posPrinter.setDeviceEnabled(true);
      isEnabled = true;
      System.out.println("enabled");

    } catch (JposException jposException) {
      System.out.println("jpos exception in open : " + jposException.getMessage());
      throw jposException;
    } catch(Throwable t) {
      System.out.println("unknown throwable open: " + t.getMessage());
    }
  }

  public static void terminate() throws JposException {
    try {
        if(isOpen && isClaimed) {
          posPrinter.clearOutput();
          System.out.println("cleared output");
        }

        if(isEnabled) {
          posPrinter.setDeviceEnabled(false);
          isEnabled = false;
          System.out.println("setDeviceEnabled false");
        }

        if(isClaimed) {
          posPrinter.release();
          isClaimed = false;
          System.out.println("released");
        }

        if(isOpen) {
          posPrinter.close();
          isOpen = false;
          System.out.println("closed");
        }
    } catch (JposException jposException) {
      jposException.printStackTrace();
      throw jposException;
    } catch(Throwable t) {
      System.out.println("unknown throwable terminate: " + t.getMessage());
    }
  }
}

第一过程输出

opened
claimed
enabled
Time taken to connect : 7928 --> now I start the second process.
cleared output
setDeviceEnabled false
released
closed
terminated from try block

第二过程输出

opened
jpos exception in open : The port is already open.
jpos.JposException: The port is already open.
    at jp.co.epson.upos.core.v1_14_0001.pntr.CommonUPOSExceptionCreator.createJposException(CommonUPOSExceptionCreator.java:138)
    at jp.co.epson.upos.core.v1_14_0001.pntr.CommonUPOSExceptionCreator.createJposException(CommonUPOSExceptionCreator.java:99)
    at jp.co.epson.upos.core.v1_14_0001.pntr.CommonPrinterService.openPort(CommonPrinterService.java:3341)
    at jp.co.epson.upos.core.v1_14_0001.pntr.CommonPrinterService.claim(CommonPrinterService.java:3103)
    at jpos.BaseJposControl.claim(Unknown Source)
    at POSPrinterClaimTestThreads.openConnection(POSPrinterClaimTestThreads.java:73)
    at POSPrinterClaimTestThreads.test(POSPrinterClaimTestThreads.java:36)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
    at java.lang.Thread.run(Thread.java:748)
closed
terminated from catch block

# 

# A fatal error has been detected by the Java Runtime Environment:

# 

# SIGSEGV (0xb) at pc=0x00007f43880ea9df, pid=12119, tid=0x00007f43690b0700

# 

# JRE version: OpenJDK Runtime Environment (8.0_252-b09) (build 1.8.0_252-b09)

# Java VM: OpenJDK 64-Bit Server VM (25.252-b09 mixed mode linux-amd64 compressed oops)

# Problematic frame:

# C  [libethernetio31.so+0x1f9df]  CCommonPort::PortEvent(unsigned int, unsigned int, unsigned int*, unsigned int, unsigned char*)+0xf

# 

# Failed to write core dump. Core dumps have been disabled. To enable core dumping, try "ulimit -c unlimited" before starting Java again

# 

# An error report file with more information is saved as:

# /POSPrinterTest/JavaPOS/hs_err_pid12119.log

# 

# If you would like to submit a bug report, please visit:

# http://bugreport.java.com/bugreport/crash.jsp

# 

Aborted

如果您看到第二个进程抛出一个jposexception,然后它启动catch并关闭连接。然后它突然崩溃而不是睡5秒。
有什么帮助吗?

t5fffqht

t5fffqht1#

似乎javapos服务对象的独占控制处理没有很好地工作。
您应该得到一个超时错误,而不是端口已经打开的错误。
不过,你的程序也不好。
一试,一抓的范围太大了。
jposexception采用异常的形式,但它实际上只是一个错误代码通知。
发出jposexception信号并不意味着它崩溃。
大多数情况下,如果您消除错误的原因并重试,它将工作。
为了正确起见,请尝试捕获每个方法调用和属性访问。
epson\u javapos\u adk示例程序应该是这样做的。
请编写与示例程序相同的代码。
此外:
你看到的不同吗?
对于每个方法和属性,它都会尝试以小的单位进行捕获,并且不会使用throw将其传播到顶部。
我掌握的一些信息来源是:
来自“epson\u javapos\u adk\u 11414\u for \u linux\u x64\sample\samples\printer\printersample\u step15\src\printersample\u step15\step15frame.java”

// JavaPOS's code for Step7
// Set OutputCompleteEvent listener
ptr.addOutputCompleteListener(this);
// JavaPOS's code for Step7--END

// JavaPOS's code for Step10
try {
    //Open the device.
    //Use the name of the device that connected with your computer.
    ptr.open("POSPrinter");

}
catch(JposException ex){
    JOptionPane.showMessageDialog(this, "This device has not been registered, or cannot use.",
            "",JOptionPane.WARNING_MESSAGE);
    //Nothing can be used.
    changeButtonStatus();
    return;
}

try {
    //Get the exclusive control right for the opened device.
    //Then the device is disable from other application.
    ptr.claim(1000);
    bCoverSensor = ptr.getCapCoverSensor();
}
catch(JposException ex){
    JOptionPane.showMessageDialog(this, "Fails to get the exclusive access for the device.",
            "",JOptionPane.WARNING_MESSAGE);
    //Nothing can be used.
    changeButtonStatus();
    return;
}

从评论和帖子中提取情况:
好吧,索赔报告的错误可能是错误的,那么为什么不联系爱普生支持部门,提供有关这种情况的详细信息呢?
从op:
已经这么做了,但我们不知道他们是否会回应。所以在这里试图找到答案;某地:d
从op:
我在一个进程中运行同一个程序,在两个脉冲中运行多个线程。我现在确实得到了你说的超时错误。只是在不同的情况下,我会崩溃
如果是这样,javapos服务对象的进程间独占控制可能有问题。这就是它的问题所在,但是崩溃可能是异常结束时的清理问题,正如我之前所评论的。当claim方法中发生异常时,不是通过传播异常来结束进程,而是调用close方法并尝试其他清理以正常结束。
从op:
我在claim-catch块中编写了posprinter.close()。当使用两个进程和单个线程时,它工作正常,崩溃频率显著降低。但车祸还是发生了一两次。但是在两个进程中,每个进程有10个线程试图声明打印机,结果一个进程能够声明,另一个进程崩溃。 try{ posPrinter.claim(3000); } catch(JposException ex) { posPrinter.close();} 似乎epson的javapos服务对象的独占控制问题仍然存在。请根据这些调查信息向爱普生进行额外查询。

相关问题