Index: src/Common/Stats/Time.cc
===================================================================
--- src/Common/Stats/Time.cc	(revision 79eaeb7d2f415bedb0599880c26d345dd4696cd4)
+++ src/Common/Stats/Time.cc	(revision 3c0d4cdd403fcf9c68de3106b67c7b21967ae61f)
@@ -33,7 +33,9 @@
 			typedef  std::chrono::time_point<std::chrono::high_resolution_clock> point_t;
 			std::chrono::duration<double> total;
-			std::chrono::duration<double> parent;
 
 			point_t global_begin;
+
+			size_t prevl = 0;
+			size_t currl = 0;
 
 			template<typename T>
@@ -85,9 +87,21 @@
 
 				virtual void print(std::ostream & os) override {
+					if(currl > prevl) {
+						parents.push(last);
+					} else if(currl < prevl) {
+						parents.pop();
+					} else {
+						last = end - begin;
+					}
+
 					assert(finished);
 					std::chrono::duration<double> diff = end - begin;
 					os << diff << " | ";
-					os << std::setw(7) << std::setprecision(0);
-					os << size_t(100.0 * diff.count() / total.count()) << "% | ";
+					if(parents.empty()) {
+						os << "     N/A | ";
+					} else {
+						os << std::setw(7) << std::setprecision(0);
+						os << size_t(100.0 * diff.count() / parents.top().count()) << "% | ";
+					}
 					os << std::setw(5) << std::setprecision(0);
 					os << size_t(100.0 * diff.count() / total.count()) << "% ";
@@ -111,7 +125,13 @@
 				point_t begin;
 				point_t end;
+
+				static std::chrono::duration<double> last;
+				static std::stack<std::chrono::duration<double>> parents;
 			};
 
 			std::stack<TimerNode *> nodes;
+
+			std::chrono::duration<double> TimerNode::last = {};
+			std::stack<std::chrono::duration<double>> TimerNode::parents = {};
 
 			void StartGlobal() {
@@ -139,5 +159,4 @@
 				auto global_end = std::chrono::high_resolution_clock::now();
 				total = global_end - global_begin;
-				parent = total;
 
 				size_t nc = 0;
@@ -161,4 +180,5 @@
 
 				Base::ForAll(top, 0, [&](Base::TreeImpl * node, size_t level) {
+					currl = level;
 					std::cerr << std::string(level * 4, ' ');
 					std::cerr << node->name;
@@ -168,4 +188,5 @@
 					std::cerr << " |";
 					std::cerr << '\n';
+					prevl = level;
 				}, true);
 
Index: src/SymTab/Validate.cc
===================================================================
--- src/SymTab/Validate.cc	(revision 79eaeb7d2f415bedb0599880c26d345dd4696cd4)
+++ src/SymTab/Validate.cc	(revision 3c0d4cdd403fcf9c68de3106b67c7b21967ae61f)
@@ -304,35 +304,53 @@
 		PassVisitor<FixQualifiedTypes> fixQual;
 
-		Stats::Heap::newPass("validate-A");
-		acceptAll( translationUnit, hoistDecls );
-		ReplaceTypedef::replaceTypedef( translationUnit );
-		ReturnTypeFixer::fix( translationUnit ); // must happen before autogen
-		acceptAll( translationUnit, epc ); // must happen before VerifyCtorDtorAssign, because void return objects should not exist; before LinkReferenceToTypes because it is an indexer and needs correct types for mangling
-		Stats::Heap::newPass("validate-B");
-		acceptAll( translationUnit, lrt ); // must happen before autogen, because sized flag needs to propagate to generated functions
-		mutateAll( translationUnit, fixQual ); // must happen after LinkReferenceToTypes, because aggregate members are accessed
-		HoistStruct::hoistStruct( translationUnit ); // must happen after EliminateTypedef, so that aggregate typedefs occur in the correct order
-		EliminateTypedef::eliminateTypedef( translationUnit ); //
-		Stats::Heap::newPass("validate-C");
-		acceptAll( translationUnit, genericParams );  // check as early as possible - can't happen before LinkReferenceToTypes
-		VerifyCtorDtorAssign::verify( translationUnit );  // must happen before autogen, because autogen examines existing ctor/dtors
-		ReturnChecker::checkFunctionReturns( translationUnit );
-		InitTweak::fixReturnStatements( translationUnit ); // must happen before autogen
-		Stats::Heap::newPass("validate-D");
-		Concurrency::applyKeywords( translationUnit );
-		acceptAll( translationUnit, fpd ); // must happen before autogenerateRoutines, after Concurrency::applyKeywords because uniqueIds must be set on declaration before resolution
-		ControlStruct::hoistControlDecls( translationUnit );  // hoist initialization out of for statements; must happen before autogenerateRoutines
-		autogenerateRoutines( translationUnit ); // moved up, used to be below compoundLiteral - currently needs EnumAndPointerDecay
-		Stats::Heap::newPass("validate-E");
-		Concurrency::implementMutexFuncs( translationUnit );
-		Concurrency::implementThreadStarter( translationUnit );
-		mutateAll( translationUnit, compoundliteral );
-		ResolvExpr::resolveWithExprs( translationUnit ); // must happen before FixObjectType because user-code is resolved and may contain with variables
-		Stats::Heap::newPass("validate-F");
-		FixObjectType::fix( translationUnit );
-		ArrayLength::computeLength( translationUnit );
-		acceptAll( translationUnit, finder ); // xxx - remove this pass soon
-		mutateAll( translationUnit, labelAddrFixer );
-		Validate::handleAttributes( translationUnit );
+		{
+			Stats::Heap::newPass("validate-A");
+			Stats::Time::BlockGuard guard("validate-A");
+			acceptAll( translationUnit, hoistDecls );
+			ReplaceTypedef::replaceTypedef( translationUnit );
+			ReturnTypeFixer::fix( translationUnit ); // must happen before autogen
+			acceptAll( translationUnit, epc ); // must happen before VerifyCtorDtorAssign, because void return objects should not exist; before LinkReferenceToTypes because it is an indexer and needs correct types for mangling
+		}
+		{
+			Stats::Heap::newPass("validate-B");
+			Stats::Time::BlockGuard guard("validate-B");
+			acceptAll( translationUnit, lrt ); // must happen before autogen, because sized flag needs to propagate to generated functions
+			mutateAll( translationUnit, fixQual ); // must happen after LinkReferenceToTypes, because aggregate members are accessed
+			HoistStruct::hoistStruct( translationUnit ); // must happen after EliminateTypedef, so that aggregate typedefs occur in the correct order
+			EliminateTypedef::eliminateTypedef( translationUnit ); //
+		}
+		{
+			Stats::Heap::newPass("validate-C");
+			Stats::Time::BlockGuard guard("validate-C");
+			acceptAll( translationUnit, genericParams );  // check as early as possible - can't happen before LinkReferenceToTypes
+			VerifyCtorDtorAssign::verify( translationUnit );  // must happen before autogen, because autogen examines existing ctor/dtors
+			ReturnChecker::checkFunctionReturns( translationUnit );
+			InitTweak::fixReturnStatements( translationUnit ); // must happen before autogen
+		}
+		{
+			Stats::Heap::newPass("validate-D");
+			Stats::Time::BlockGuard guard("validate-D");
+			Concurrency::applyKeywords( translationUnit );
+			acceptAll( translationUnit, fpd ); // must happen before autogenerateRoutines, after Concurrency::applyKeywords because uniqueIds must be set on declaration before resolution
+			ControlStruct::hoistControlDecls( translationUnit );  // hoist initialization out of for statements; must happen before autogenerateRoutines
+			autogenerateRoutines( translationUnit ); // moved up, used to be below compoundLiteral - currently needs EnumAndPointerDecay
+		}
+		{
+			Stats::Heap::newPass("validate-E");
+			Stats::Time::BlockGuard guard("validate-E");
+			Concurrency::implementMutexFuncs( translationUnit );
+			Concurrency::implementThreadStarter( translationUnit );
+			mutateAll( translationUnit, compoundliteral );
+			ResolvExpr::resolveWithExprs( translationUnit ); // must happen before FixObjectType because user-code is resolved and may contain with variables
+		}
+		{
+			Stats::Heap::newPass("validate-F");
+			Stats::Time::BlockGuard guard("validate-F");
+			FixObjectType::fix( translationUnit );
+			ArrayLength::computeLength( translationUnit );
+			acceptAll( translationUnit, finder ); // xxx - remove this pass soon
+			mutateAll( translationUnit, labelAddrFixer );
+			Validate::handleAttributes( translationUnit );
+		}
 	}
 
Index: src/main.cc
===================================================================
--- src/main.cc	(revision 79eaeb7d2f415bedb0599880c26d345dd4696cd4)
+++ src/main.cc	(revision 3c0d4cdd403fcf9c68de3106b67c7b21967ae61f)
@@ -194,6 +194,7 @@
 		} // if
 
+		Stats::Time::StartGlobal();
 		NewPass("Parse");
-		Stats::Time::StartGlobal();
+		Stats::Time::StartBlock("Parse");
 
 		// read in the builtins, extras, and the prelude
@@ -247,4 +248,5 @@
 		// works okay for now.
 		CodeTools::fillLocations( translationUnit );
+		Stats::Time::StopBlock();
 
 		// add the assignment statement after the initialization of a type parameter
