src/java.base/share/classes/sun/net/www/http/KeepAliveStreamCleaner.java
branchJDK-8229867-branch
changeset 57968 8595871a5446
parent 47216 71c04702a3d5
equal deleted inserted replaced
57966:e89c7aaf2906 57968:8595871a5446
     1 /*
     1 /*
     2  * Copyright (c) 2005, 2008, Oracle and/or its affiliates. All rights reserved.
     2  * Copyright (c) 2005, 2019, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.  Oracle designates this
     7  * published by the Free Software Foundation.  Oracle designates this
    28 import java.io.IOException;
    28 import java.io.IOException;
    29 import java.util.LinkedList;
    29 import java.util.LinkedList;
    30 import sun.net.NetProperties;
    30 import sun.net.NetProperties;
    31 import java.security.AccessController;
    31 import java.security.AccessController;
    32 import java.security.PrivilegedAction;
    32 import java.security.PrivilegedAction;
       
    33 import java.util.concurrent.locks.Condition;
       
    34 import java.util.concurrent.locks.ReentrantLock;
    33 
    35 
    34 /**
    36 /**
    35  * This class is used to cleanup any remaining data that may be on a KeepAliveStream
    37  * This class is used to cleanup any remaining data that may be on a KeepAliveStream
    36  * so that the connection can be cached in the KeepAliveCache.
    38  * so that the connection can be cached in the KeepAliveCache.
    37  * Instances of this class can be used as a FIFO queue for KeepAliveCleanerEntry objects.
    39  * Instances of this class can be used as a FIFO queue for KeepAliveCleanerEntry objects.
    76                 }}).intValue();
    78                 }}).intValue();
    77         MAX_CAPACITY = maxCapacity;
    79         MAX_CAPACITY = maxCapacity;
    78 
    80 
    79     }
    81     }
    80 
    82 
       
    83     final ReentrantLock queueLock = new ReentrantLock();
       
    84     final Condition waiter = queueLock.newCondition();
    81 
    85 
    82     @Override
    86     @Override
    83     public boolean offer(KeepAliveCleanerEntry e) {
    87     public boolean offer(KeepAliveCleanerEntry e) {
    84         if (size() >= MAX_CAPACITY)
    88         if (size() >= MAX_CAPACITY)
    85             return false;
    89             return false;
    92     {
    96     {
    93         KeepAliveCleanerEntry kace = null;
    97         KeepAliveCleanerEntry kace = null;
    94 
    98 
    95         do {
    99         do {
    96             try {
   100             try {
    97                 synchronized(this) {
   101                 queueLock.lock();
       
   102                 try {
    98                     long before = System.currentTimeMillis();
   103                     long before = System.currentTimeMillis();
    99                     long timeout = TIMEOUT;
   104                     long timeout = TIMEOUT;
   100                     while ((kace = poll()) == null) {
   105                     while ((kace = poll()) == null) {
   101                         this.wait(timeout);
   106                         waiter.wait(timeout);
   102 
   107 
   103                         long after = System.currentTimeMillis();
   108                         long after = System.currentTimeMillis();
   104                         long elapsed = after - before;
   109                         long elapsed = after - before;
   105                         if (elapsed > timeout) {
   110                         if (elapsed > timeout) {
   106                             /* one last try */
   111                             /* one last try */
   108                             break;
   113                             break;
   109                         }
   114                         }
   110                         before = after;
   115                         before = after;
   111                         timeout -= elapsed;
   116                         timeout -= elapsed;
   112                     }
   117                     }
       
   118                 } finally {
       
   119                     queueLock.unlock();
   113                 }
   120                 }
   114 
   121 
   115                 if(kace == null)
   122                 if(kace == null)
   116                     break;
   123                     break;
   117 
   124 
   118                 KeepAliveStream kas = kace.getKeepAliveStream();
   125                 KeepAliveStream kas = kace.getKeepAliveStream();
   119 
   126 
   120                 if (kas != null) {
   127                 if (kas != null) {
   121                     synchronized(kas) {
   128                     final ReentrantLock readLock = kas.readLock();
       
   129                     readLock.lock();
       
   130                     try {
   122                         HttpClient hc = kace.getHttpClient();
   131                         HttpClient hc = kace.getHttpClient();
   123                         try {
   132                         try {
   124                             if (hc != null && !hc.isInKeepAliveCache()) {
   133                             if (hc != null && !hc.isInKeepAliveCache()) {
   125                                 int oldTimeout = hc.getReadTimeout();
   134                                 int oldTimeout = hc.getReadTimeout();
   126                                 hc.setReadTimeout(TIMEOUT);
   135                                 hc.setReadTimeout(TIMEOUT);
   145                         } catch (IOException ioe) {
   154                         } catch (IOException ioe) {
   146                             hc.closeServer();
   155                             hc.closeServer();
   147                         } finally {
   156                         } finally {
   148                             kas.setClosed();
   157                             kas.setClosed();
   149                         }
   158                         }
       
   159                     } finally {
       
   160                         readLock.unlock();
   150                     }
   161                     }
   151                 }
   162                 }
   152             } catch (InterruptedException ie) { }
   163             } catch (InterruptedException ie) { }
   153         } while (kace != null);
   164         } while (kace != null);
   154     }
   165     }