Hibernate + MySQL + C3p0: Problema com "Too many connections"

Boa tarde pessoal,

estou sofrendo com esse problema já faz umas semanas, e não consegui resolvê-lo. Então deixei de lado e agora estou voltando para
tentar resolver, mas não consegui de forma alguma. Vamos ao X da questão:

Possuo um sistema criado em Struts 2+Hibernate 3+MySQL. Esse sistema está mapeado corretamente, pois todos os meus CRUDs funcionam
perfeitamente. O problema acontece depois que eu executo várias operações na aplicação, com isso minha pool de conexões estoura e recebo
a seguinte excessão:

Unable to instantiate Action, br.com.jm.actions.EleitorAction,  defined for 'eleitor' in namespace '/'Could not open connection
	com.opensymphony.xwork2.DefaultActionInvocation.createAction(DefaultActionInvocation.java:318)
	com.opensymphony.xwork2.DefaultActionInvocation.init(DefaultActionInvocation.java:399)
	com.opensymphony.xwork2.DefaultActionProxy.prepare(DefaultActionProxy.java:198)
	org.apache.struts2.impl.StrutsActionProxy.prepare(StrutsActionProxy.java:63)
	org.apache.struts2.impl.StrutsActionProxyFactory.createActionProxy(StrutsActionProxyFactory.java:39)
	com.opensymphony.xwork2.DefaultActionProxyFactory.createActionProxy(DefaultActionProxyFactory.java:58)
	org.apache.struts2.dispatcher.Dispatcher.serviceAction(Dispatcher.java:500)
	org.apache.struts2.dispatcher.FilterDispatcher.doFilter(FilterDispatcher.java:434)

root cause

org.hibernate.exception.JDBCConnectionException: Could not open connection
	org.hibernate.exception.internal.SQLExceptionTypeDelegate.convert(SQLExceptionTypeDelegate.java:68)
	org.hibernate.exception.internal.StandardSQLExceptionConverter.convert(StandardSQLExceptionConverter.java:49)
	org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:125)
	org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:110)
	org.hibernate.engine.jdbc.internal.LogicalConnectionImpl.obtainConnection(LogicalConnectionImpl.java:304)
	org.hibernate.engine.jdbc.internal.LogicalConnectionImpl.getConnection(LogicalConnectionImpl.java:169)
	org.hibernate.engine.transaction.internal.jdbc.JdbcTransaction.doBegin(JdbcTransaction.java:67)
	org.hibernate.engine.transaction.spi.AbstractTransactionImpl.begin(AbstractTransactionImpl.java:160)
	org.hibernate.internal.SessionImpl.beginTransaction(SessionImpl.java:1309)
	br.com.jm.config.HibernateUtil.getSession(HibernateUtil.java:31)
	br.com.jm.dao.GenericDAO.getSession(GenericDAO.java:14)
	br.com.jm.dao.ExperienciaDAO.<init>(ExperienciaDAO.java:12)
	br.com.jm.factory.EleitorFactory.<init>(EleitorFactory.java:17)
	br.com.jm.actions.EleitorAction.<init>(EleitorAction.java:32)
	...
	org.apache.struts2.dispatcher.Dispatcher.serviceAction(Dispatcher.java:500)
	org.apache.struts2.dispatcher.FilterDispatcher.doFilter(FilterDispatcher.java:434)
root cause

[color=red]com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Data source rejected establishment of connection,  message from server: "Too many connections"[/color]
	sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
	sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source)
	sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source)
	java.lang.reflect.Constructor.newInstance(Unknown Source)
	...

Pesquisei na internet e fui informado que isso ocorria geralmente pelo fato do desenvolvedor não usar o session.close() em seus métodos DAO. Pois muito bem, coloquei session.close() em todo
metodo de minha aplicação, mas com isso, obtive um outro erro, que foi um erro acusando que minha sessão estava fechada e a aplicação não poderia recuperar os objetos solicitados. Isso
ocorreu porque eu tinha vários fetchs em meus relacionamentos que eram do tipo LAZY, assim, quando eles ia carregar preguiçosamente os objetos, a sessão não existia mais. Então, resolvi
alterar todos os meus fetchs para o tipo EAGER, isso iria, teoriamente, causar uma certa lentidão na recuperação de alguns dados, mas, TEORICAMENTE, resolveria meu problema.

O problema foi que eu obtive mais um glorioso erro ao tentar executar isso, o nosso caríssimo “cannot fetch multiple bags simultaneously”. Isso quer dizer que por algum motivo que desconheço,
eu não posso sair atribuindo FetchType.EAGER por aí à torto e à direita.

Acabou que voltei ao meu problema inicial: eu não poderia usar o session.close(), eu tería que descobrir uma forma de, ao solicitar uma sessão (hibernate), verificar se uma delas já não existe.
O problema é: como vou fazer isso?

Até que me deram um toque pra eu pesquisar sobre o C3P0 pooling, me disseram que esse cara vai controlar isso pra mim, vai matar minhas conexões ociosas, e vai controlar tudo isso pra mim.
Fui atrás disso, pesquisei, e vi que com 1 .jar, e 5 linhas de configuração no arquivo hibernate.cgf.xml, eu resolveria meu problema (sonha). Ao definir as configurações, eu notei que em algumas
chamadas que faço ao servidor, pelo firebug, noto que ele fica esperando uma resposta do servidor, mas essa resposta não chega, e depois de um longo tempo de espera, ele acusa um
NullPointerException que não faço idéia de onde seja.

Preciso realmente de uma ajuda com isso, seja com uma nova forma de organização de meus métodos e classes DAO, seja com nova configuração do hibernate ou do C3P0, ou de qualquer outro componente que possa me ajudar à resolver isso. Estou aberto à sugestões!

Seguem minhas classes:

CampanhaDAO
Percebam que na linha eu uso o método getSession(), se não me engano, é esse cara que abre uma nova conexão toda vez.

package br.com.jm.dao;

import java.util.List;

import org.hibernate.Query;
import org.hibernate.Session;

import br.com.jm.beans.Campanha;

public class CampanhaDAO extends GenericDAO{
	Session session = getSession();
	
	@SuppressWarnings("unchecked")
	public List<Campanha> all(){
		Query query = session.createQuery("from Campanha");
		List<Campanha> listaCampanhas = query.list();
		return listaCampanhas;
	}
	
	public Campanha one(Campanha cam){
		Campanha Campanha = (Campanha) session.get(Campanha.class, cam.getIdCampanha());
		return Campanha;
	}
	
	public void insert(Campanha cam){
		session.save(cam);
		session.getTransaction().commit();
	}
	
	public void delete(Campanha cam){
		session.delete(cam);
		session.getTransaction().commit();
	}
}

GenericDAO
Essa é a classe que toda classe DAO extende, estou seguindo um modelo passado por video aulas do site DevMedia

package br.com.jm.dao;

import org.hibernate.Session;

import br.com.jm.config.HibernateUtil;

public abstract class GenericDAO {
	
	public GenericDAO(){
		
	}
	
	protected static Session getSession(){
		return HibernateUtil.getInstance().getSession();
	}
}

HibernateUtil
Essa é a classe onde o MAL acontece, tenho quase certeza de que tem coisa errada aí, mas não sei concertar.

package br.com.jm.config;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.service.ServiceRegistryBuilder;


public class HibernateUtil{

    private static HibernateUtil me;
    private SessionFactory sessionFactory;
    private static ServiceRegistry serviceRegistry;
    private Session toReturn;
    
    private HibernateUtil(){
    	try {
    		Configuration configuration = new Configuration();
    		configuration.configure();
    		serviceRegistry = new ServiceRegistryBuilder().applySettings(
    		configuration.getProperties()).buildServiceRegistry();
    		sessionFactory = configuration.buildSessionFactory(serviceRegistry);
		} catch (Throwable ex) {
    		System.err.println("Failed to create sessionFactory object." + ex);
    		throw new ExceptionInInitializerError(ex);
		}
    }
    public Session getSession() {
    	toReturn = sessionFactory.openSession();
        toReturn.beginTransaction();
        return toReturn;
    }


    public static HibernateUtil getInstance() {
        if (me== null){
            me = new HibernateUtil();
        }
        return me;
    }

}

hibernate.cgf.xml
Arquivo de configuração, SEM as [color=red]linhas entre os pontilhados[/color], continuo explodindo minha pool, COM elas, eu não recebo resposta do servidor.

<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD//EN"
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">

<hibernate-configuration>
	<session-factory>
		<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
		<property name="hibernate.connection.url">jdbc:mysql://localhost:3306/genix</property>
		<property name="hibernate.connection.username">root</property>
		<property name="hibernate.connection.password">root</property>
		<property name="hibernate.connection.pool_size">0</property>
		<property name="show_sql">false</property>
-------------------------------------------------------------------------------------------------------------------------
		<property name="c3p0.acquire_increment">1</property> 
		<property name="c3p0.idle_test_period">100</property> <!-- seconds --> 
		<property name="c3p0.max_size">100</property> 
		<property name="c3p0.max_statements">0</property> 
		<property name="c3p0.min_size">10</property> 
		<property name="c3p0.timeout">100</property> <!-- seconds -->
-------------------------------------------------------------------------------------------------------------------------
		<property name="dialect">org.hibernate.dialect.MySQL5Dialect</property>
		<property name="hibernate.current_session_context_class">thread</property>
		<mapping class="br.com.jm.beans.Usuario"/>
		<mapping class="br.com.jm.beans.Perfil"/>
		<mapping class="br.com.jm.beans.Setor"/>
		<mapping class="br.com.jm.beans.Profissao"/>
		<mapping class="br.com.jm.beans.Mensagem"/>
		<mapping class="br.com.jm.beans.LogFile"/>
		<mapping class="br.com.jm.beans.Eleitor"/>
		<mapping class="br.com.jm.beans.Demanda"/>
		<mapping class="br.com.jm.beans.Curso"/>
		<mapping class="br.com.jm.beans.Cidade"/>
		<mapping class="br.com.jm.beans.Campanha"/>
		<mapping class="br.com.jm.beans.Atividade"/>
		<mapping class="br.com.jm.beans.Ocorrencia"/>
		<mapping class="br.com.jm.beans.CampanhasEleitor"/>
		<mapping class="br.com.jm.beans.Experiencia"/>
	</session-factory>
</hibernate-configuration>

Espero que possam me ajudar.