如何保护java中的方法(溢出等)

时间:2011-08-09 11:52:20

标签: java watchdog

我必须在Java中编写一个“WatchDog”,它确保Threads的执行时间不会太长。随着对象的初始化没有问题,我创建了一个类,它使用run()方法中的反射来调用WatchDog和构造函数。

线程很容易停止,但我如何才能保证对象的常规方法? 例如,我调用Object的方法,这个方法执行无限循环,你会怎么做?

谢谢

3 个答案:

答案 0 :(得分:4)

首先,我应该指出停止线程很容易。事实上,在一般情况下,线程无法安全停止:

  • 您可以在要停止的线程上调用Thread.interrupt(),但无法保证线程会注意到中断,更不用说实际停止了。

  • 您可以调用已弃用的Thread.stop()方法,但此方法不安全。如果你在一个不幸的时刻调用它,你可以让数据结构处于半更新状态,让其他线程等待(永远)等待无法到达的信号,等等。


以下是我为方法执行实现监视程序的方法。

首先我修改方法,向看门狗服务添加两个调用;例如

public void someMethod(...) {
    Watchdog.startMethod(maxTime);
    // do stuff
    Watchdog.endMethod();
}

接下来,我将使用在到期时间排序的优先级队列实现Watchdog:

  1. startMethod(maxTime)会在队列中添加一个条目,其到期时间为now + maxTime。该条目将包括对当前线程的引用(当调用该方法时。
  2. endMethod()将查找当前线程的(队列)条目,如果找到则将其删除。
  3. 监视程序线程会定期查看第一个队列条目。如果该条目的到期时间小于“现在”,则监视程序将删除该条目,停止其线程并检查下一个条目。重复,直到下一个条目尚未过期。
  4. 需要考虑数据结构,并处理跳过endMethod调用的情况。 (实际上,由于方法调用可能因异常而终止,因此endMethod()调用确实需要在finally块中完成。)

    请注意,startMethodendMethod调用可以(也可能应该)由注释处理器或类似内容插入。


    鉴于复杂性以及您无法保证(安全地)停止线程的事实,我会想到一些不涉及方法监视器的解决方案。

答案 1 :(得分:3)

对象的常规方法正在某些线程上运行。它可能是AWT事件调度程序或其所谓的任何调度程序。或者它可能是控制台应用程序的主要线程。

它们与使用新Thread()调用的线程没有区别。

我想你的看门狗需要查看虚拟机中的所有线程,并寻找利用率> =某个阈值的线程。

到目前为止,你有什么代码?

答案 2 :(得分:1)

尝试使用@Timeable中的jcabi-aspects注释:

public class Resource {
  @Timeable(limit = 5, unit = TimeUnit.SECONDS)
  public String load(URL url) {
    return url.openConnection().getContent();
  }
}

您的方法将在超时时中断。