diff --git a/src/ipa/ipa_rkisp1.cpp b/src/ipa/ipa_rkisp1.cpp
index 063b075d8358c30d..cc926867d6fde478 100644
--- a/src/ipa/ipa_rkisp1.cpp
+++ b/src/ipa/ipa_rkisp1.cpp
@@ -6,6 +6,7 @@
  */
 
 #include <algorithm>
+#include <math.h>
 #include <string.h>
 
 #include <linux/rkisp1-config.h>
@@ -112,8 +113,9 @@ void IPARkISP1::updateStatistics(const void *cookie, Buffer &statistics)
 	const rkisp1_stat_buffer *stats =
 		static_cast<rkisp1_stat_buffer *>(statistics.mem()->planes()[0].mem());
 	const cifisp_stat *params = &stats->params;
+	IPAMetaData metaData = {};
 
-	if ((stats->meas_type & CIFISP_STAT_AUTOEXP) && (statFrame_ % 2 == 0)) {
+	if (stats->meas_type & CIFISP_STAT_AUTOEXP) {
 		const cifisp_ae_stat *ae = &params->ae;
 
 		const unsigned int target = 60;
@@ -129,18 +131,28 @@ void IPARkISP1::updateStatistics(const void *cookie, Buffer &statistics)
 		value /= num;
 
 		double factor = (double)target / value;
-		double tmp;
 
-		tmp = factor * exposure_ * gain_ / minGain_;
-		exposure_ = utils::clamp<uint64_t>((uint64_t)tmp, minExposure_, maxExposure_);
+		if (statFrame_ % 3 == 0) {
+			double tmp;
 
-		tmp = tmp / exposure_ * minGain_;
-		gain_ = utils::clamp<uint64_t>((uint64_t)tmp, minGain_, maxGain_);
+			tmp = factor * exposure_ * gain_ / minGain_;
+			exposure_ = utils::clamp<uint64_t>((uint64_t)tmp, minExposure_, maxExposure_);
 
-		setControls();
+			tmp = tmp / exposure_ * minGain_;
+			gain_ = utils::clamp<uint64_t>((uint64_t)tmp, minGain_, maxGain_);
+
+			setControls();
+		}
+
+		metaData.aeState = fabs(factor - 1.0f) < 0.05f ?
+			AeState::Converged : AeState::Searching;
+	} else {
+		metaData.aeState = AeState::Inactive;
 	}
 
 	statFrame_++;
+
+	metaDataReady.emit(cookie, metaData);
 }
 
 /*
