my dog learned polymorphism*
The moose likes Servlets and the fly likes Too many threads? Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Java » Servlets
Bookmark "Too many threads?" Watch "Too many threads?" New topic
Author

Too many threads?

James Hodgkiss
Ranch Hand

Joined: Jan 22, 2004
Posts: 401
Hope no-one minds, but I've also posted the following in the Apache/Tomcat forum. Not sure whether the problem is with the servlets or Tomcat, so I'm posting here as well...


The people that host my servlets have asked me the following question:

"When we restart Tomcat, for some reason the number of java processes starts off at about 20 but rises to over 100 over time? any idea why this is - I'm not too familiar with how java works to know if this is normal or not."

Is this normal behaviour?

They are hosting about 20 of my servlets and (as far as I know), no-one elses.

To help try and figure what might be going wrong, I have put the following code into one of my servlets:


code:
--------------------------------------------------------------------------------

int numThreads = Thread.activeCount(); Thread[] threads = new Thread[numThreads]; Thread.enumerate(threads); response.setContentType("text/html"); PrintWriter out = response.getWriter(); out.println("<html>"); out.println("<head>"); out.println("<title>Threads Test</title>"); out.println("</head>"); out.println("<body>"); out.println("<p><b>There are " + numThreads + " threads...</b></p>"); for(int i = 0; i < numThreads; i++) { try { out.println("<p>Thread" + i + ": " + threads[i].toString() + ". isAlive: " + threads[i].isAlive() + ". isDaemon: " + threads[i].isDaemon() + ". isInterrupted: " + threads[i].isInterrupted() + "</p>"); } catch(Exception ex) { out.println("<p>Exception occurred getting info for Thread " + i + ": " + ex.toString() + "</p>"); } } out.close();

--------------------------------------------------------------------------------



... which gives the following output (when I run it on my PC):


quote:
--------------------------------------------------------------------------------

There are 76 threads...

Thread0: Thread[main,5,main]. isAlive: true. isDaemon: false. isInterrupted: false

Thread1: Thread[Thread-2,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread2: Thread[ContainerBackgroundProcessor[StandardEngine[Catalina]],5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread3: Thread[http-8084-Processor1,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread4: Thread[http-8084-Processor2,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread5: Thread[http-8084-Processor3,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread6: Thread[http-8084-Processor4,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread7: Thread[http-8084-Processor5,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread8: Thread[http-8084-Processor6,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread9: Thread[http-8084-Processor7,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread10: Thread[http-8084-Processor8,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread11: Thread[http-8084-Processor9,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread12: Thread[http-8084-Processor10,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread13: Thread[http-8084-Processor11,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread14: Thread[http-8084-Processor12,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread15: Thread[http-8084-Processor13,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread16: Thread[http-8084-Processor14,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread17: Thread[http-8084-Processor15,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread18: Thread[http-8084-Processor16,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread19: Thread[http-8084-Processor17,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread20: Thread[http-8084-Processor18,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread21: Thread[http-8084-Processor19,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread22: Thread[http-8084-Processor20,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread23: Thread[http-8084-Processor21,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread24: Thread[http-8084-Processor22,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread25: Thread[http-8084-Processor23,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread26: Thread[http-8084-Processor24,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread27: Thread[http-8084-Processor25,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread28: Thread[http-8084-Monitor,5,main]. isAlive: true. isDaemon: false. isInterrupted: false

Thread29: Thread[TP-Processor1,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread30: Thread[TP-Processor2,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread31: Thread[TP-Processor3,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread32: Thread[TP-Processor4,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread33: Thread[TP-Monitor,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread34: Thread[http-8084-Processor26,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread35: Thread[http-8084-Processor27,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread36: Thread[http-8084-Processor28,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread37: Thread[http-8084-Processor29,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread38: Thread[http-8084-Processor30,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread39: Thread[http-8084-Processor31,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread40: Thread[http-8084-Processor32,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread41: Thread[http-8084-Processor33,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread42: Thread[http-8084-Processor34,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread43: Thread[http-8084-Processor35,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread44: Thread[http-8084-Processor36,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread45: Thread[http-8084-Processor37,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread46: Thread[http-8084-Processor38,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread47: Thread[http-8084-Processor39,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread48: Thread[http-8084-Processor40,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread49: Thread[http-8084-Processor41,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread50: Thread[http-8084-Processor42,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread51: Thread[http-8084-Processor43,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread52: Thread[http-8084-Processor44,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread53: Thread[http-8084-Processor45,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread54: Thread[http-8084-Processor46,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread55: Thread[http-8084-Processor47,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread56: Thread[http-8084-Processor48,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread57: Thread[http-8084-Processor49,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread58: Thread[http-8084-Processor50,5,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread59: Thread[Thread-61,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread60: Thread[Thread-62,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread61: Thread[Thread-64,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread62: Thread[Thread-65,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread63: Thread[Thread-67,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread64: Thread[Thread-69,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread65: Thread[Thread-72,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread66: Thread[Thread-73,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread67: Thread[Thread-76,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread68: Thread[Thread-77,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread69: Thread[Thread-78,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread70: Thread[Thread-80,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread71: Thread[Thread-90,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread72: Thread[Thread-91,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread73: Thread[Thread-92,1,main]. isAlive: true. isDaemon: true. isInterrupted: false

Thread 74 no longer exists

Thread 75 no longer exists

--------------------------------------------------------------------------------



I wasn't expecting so many threads either!...

As far as I'm aware, my servlets are ok - a couple of them do contain an inner class that extends Thread, but these are only instantiated once by each servlet in the init() method and they are daemon threads.

Also, it may be worth mentioning that about 4 of my servlets use contextlisteners, so maybe this has something to do with it.

Maybe nothing is wrong and all is normal, but I would appreciate any responses.

Many thanks,
James
James Carman
Ranch Hand

Joined: Feb 20, 2001
Posts: 580
James,

Why don't you try giving your daemon threads some sort of name so that you can figure out which ones are yours? Of course, the http-8084-Processor threads are Tomcat's.

James


James Carman, President<br />Carman Consulting, Inc.
James Hodgkiss
Ranch Hand

Joined: Jan 22, 2004
Posts: 401
Hiya James,

Thanks for the reply. I've now followed your suggestion. I also included a timestamp in the thread's name which has also proved useful.

The situation is that tomcat is frequently restarted in order to pick up any changes to my servlets. Problem is though that my daemon threads are staying alive when Tomcat is restarted, so I am getting extra instances of these daemon threads for every Tomcat restart...

So it seems like I will have to kill the threads off myself in a context listener...

Thanks again,
James
William Brogden
Author and all-around good cowpoke
Rancher

Joined: Mar 22, 2000
Posts: 12761
    
    5
Are you saying that you completely shutdown tomcat and restart it and find the daemon Threads are still there? That does not seem possible - what JVM are they living in?
Bill
James Carman
Ranch Hand

Joined: Feb 20, 2001
Posts: 580
I think he means that he's restarting the webapp, not the entire instance of Tomcat. That's definitely possible.
Jeroen Wenting
Ranch Hand

Joined: Oct 12, 2000
Posts: 5093
Calls for something to run on webapp shutdown that kills off any running daemon threads the webapp generated.


42
Ben Souther
Sheriff

Joined: Dec 11, 2004
Posts: 13410

Originally posted by Jeroen Wenting:
Calls for something to run on webapp shutdown that kills off any running daemon threads the webapp generated.


You shouldn't have to do that for daemon threads.
The server should bring them down automatically.


Java API J2EE API Servlet Spec JSP Spec How to ask a question... Simple Servlet Examples jsonf
Jeroen Wenting
Ranch Hand

Joined: Oct 12, 2000
Posts: 5093
it should, but it seems as if it may not be?
Of course a more likely cause is a problem in the threads themselves, maybe they're blocked waiting for some resource and thus can never terminate.
James Carman
Ranch Hand

Joined: Feb 20, 2001
Posts: 580
Originally posted by Ben Souther:


You shouldn't have to do that for daemon threads.
The server should bring them down automatically.


This is probably why you're not supposed to start your own threads inside the servlet container (I'm guilty of it too, though). Daemon threads will stop upon JVM shutdown (of course), but restarting a webapp does not invoke an entirely new JVM. It just re-establishes a new servlet context using a brand new classloader.
 
Consider Paul's rocket mass heater.
 
subject: Too many threads?
 
Similar Threads
Aboutt Daemon Threads
Servlet sessions
priority of garbage collector thread
main thread
Tomcat using too many processes?