diff --git a/ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java b/ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java index 3b74abacf3..b3060846c9 100644 --- a/ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java +++ b/ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java @@ -14638,39 +14638,43 @@ private boolean checkResultsCache(QueryResultsCache.LookupInfo lookupInfo) { } // Don't increment the reader count for explain queries. boolean isExplainQuery = (ctx.getExplainConfig() != null); - QueryResultsCache.CacheEntry cacheEntry = QueryResultsCache.getInstance().lookup(lookupInfo); - if (cacheEntry != null) { - // Potentially wait on the cache entry if entry is in PENDING status - // Blocking here can potentially be dangerous - for example if the global compile lock - // is used this will block all subsequent queries that try to acquire the compile lock, - // so it should not be done unless parallel compilation is enabled. - // We might not want to block for explain queries as well. - if (cacheEntry.getStatus() == QueryResultsCache.CacheEntryStatus.PENDING) { - if (!isExplainQuery && - conf.getBoolVar(HiveConf.ConfVars.HIVE_QUERY_RESULTS_CACHE_WAIT_FOR_PENDING_RESULTS) && - conf.getBoolVar(HiveConf.ConfVars.HIVE_SERVER2_PARALLEL_COMPILATION)) { - if (!cacheEntry.waitForValidStatus()) { - LOG.info("Waiting on pending cacheEntry, but it failed to become valid"); + do { + QueryResultsCache.CacheEntry cacheEntry = QueryResultsCache.getInstance().lookup(lookupInfo); + if (cacheEntry != null) { + // Potentially wait on the cache entry if entry is in PENDING status + // Blocking here can potentially be dangerous - for example if the global compile lock + // is used this will block all subsequent queries that try to acquire the compile lock, + // so it should not be done unless parallel compilation is enabled. + // We might not want to block for explain queries as well. + if (cacheEntry.getStatus() == QueryResultsCache.CacheEntryStatus.PENDING) { + if (!isExplainQuery && + conf.getBoolVar(HiveConf.ConfVars.HIVE_QUERY_RESULTS_CACHE_WAIT_FOR_PENDING_RESULTS) && + conf.getBoolVar(HiveConf.ConfVars.HIVE_SERVER2_PARALLEL_COMPILATION)) { + if (!cacheEntry.waitForValidStatus()) { + LOG.info("Waiting on pending cacheEntry, but it failed to become valid"); + // The pending query we were waiting on failed, but there might still be another + // pending or completed entry in the cache that can satisfy this query. Lookup again. + continue; + } + } else { + LOG.info("Not waiting for pending cacheEntry"); return false; } - } else { - LOG.info("Not waiting for pending cacheEntry"); - return false; } - } - if (cacheEntry.getStatus() == QueryResultsCache.CacheEntryStatus.VALID) { - if (!isExplainQuery) { - if (!cacheEntry.addReader()) { - return false; + if (cacheEntry.getStatus() == QueryResultsCache.CacheEntryStatus.VALID) { + if (!isExplainQuery) { + if (!cacheEntry.addReader()) { + return false; + } } + // Use the cache rather than full query execution. + // At this point the caller should return from semantic analysis. + useCachedResult(cacheEntry); + return true; } - // Use the cache rather than full query execution. - // At this point the caller should return from semantic analysis. - useCachedResult(cacheEntry); - return true; } - } + } while (false); return false; }