sdm: Add LTM support for dual displays

This patch adds object id in DRMDppsFeatureInfo, and use vector to
map this id and ltm buffers in order to support dual displays.

Change-Id: If04bc6944932646c80bb8b8a4738f96a60ae692b
diff --git a/libdrmutils/drm_interface.h b/libdrmutils/drm_interface.h
index 19ffe78..1a6ab91 100644
--- a/libdrmutils/drm_interface.h
+++ b/libdrmutils/drm_interface.h
@@ -735,6 +735,7 @@
 
 struct DRMDppsFeatureInfo {
   DRMDPPSFeatureID id;
+  uint32_t obj_id;
   uint32_t version;
   uint32_t payload_size;
   void *payload;
diff --git a/sde-drm/drm_dpps_mgr_imp.cpp b/sde-drm/drm_dpps_mgr_imp.cpp
index cd77fad..b870cdb 100644
--- a/sde-drm/drm_dpps_mgr_imp.cpp
+++ b/sde-drm/drm_dpps_mgr_imp.cpp
@@ -408,8 +408,11 @@
       return;
     } else {
       prop_info = &dpps_feature_[kFeatureLtmBufferCtrl];
-      prop_info->obj_id = crtc_id_;
-      prop_info->value = (uint64_t)&ltm_buffers_ctrl_;
+      prop_info->obj_id = info->obj_id;
+      for (const auto& it : ltm_buffers_ctrl_map_) {
+        if (it.first == info->obj_id)
+          prop_info->value = (uint64_t)&(it.second);
+      }
       dpps_dirty_prop_.push_back(*prop_info);
     }
   }
@@ -420,6 +423,8 @@
   uint32_t buffer_size, i = 0, bpp = 0;
   void* uva;
   struct DRMDppsLtmBuffers *buffers;
+  DRMDppsLtmBuffers ltm_buffers = {};
+  drm_msm_ltm_buffers_ctrl ltm_buffers_ctrl = {};
   struct drm_prime_handle prime_req;
   struct drm_mode_fb_cmd2 fb_obj;
   struct drm_gem_close gem_close;
@@ -429,9 +434,11 @@
     return -EINVAL;
   }
 
-  if (ltm_buffers_.num_of_buffers != 0) {
-    DRM_LOGE("LTM buffer already initialized");
-    return -EALREADY;
+  for (const auto& it : ltm_buffers_map_) {
+    if (it.first == info->obj_id) {
+      DRM_LOGE("LTM buffer already initialized, obj id %d", info->obj_id);
+      return -EALREADY;
+    }
   }
 
   if (!info->payload || info->payload_size != sizeof(struct DRMDppsLtmBuffers)) {
@@ -446,7 +453,10 @@
     return -EINVAL;
   }
 
-  ltm_buffers_.num_of_buffers = buffers->num_of_buffers;
+  std::memset(&ltm_buffers, 0, sizeof(ltm_buffers));
+  std::memset(&ltm_buffers_ctrl, 0, sizeof(ltm_buffers_ctrl));
+
+  ltm_buffers.num_of_buffers = buffers->num_of_buffers;
 
   buffer_size = sizeof(struct drm_msm_ltm_stats_data) + LTM_GUARD_BYTES;
   std::memset(&fb_obj, 0, sizeof(drm_mode_fb_cmd2));
@@ -469,7 +479,7 @@
       DRM_LOGE("failed get prime handle: %d", ret);
       break;
     }
-    ltm_buffers_.ion_buffer_fd[i] = buffers->ion_buffer_fd[i];
+    ltm_buffers.ion_buffer_fd[i] = buffers->ion_buffer_fd[i];
 
     fb_obj.handles[0] = prime_req.handle;
     ret = drmIoctl(drm_fd_, DRM_IOCTL_MODE_ADDFB2, &fb_obj);
@@ -478,8 +488,8 @@
       DRM_LOGE("return value from addFB2: %d", ret);
       break;
     }
-    ltm_buffers_.drm_fb_id[i] = buffers->drm_fb_id[i] = fb_obj.fb_id;
-    ltm_buffers_ctrl_.fds[i] = ltm_buffers_.drm_fb_id[i];
+    ltm_buffers.drm_fb_id[i] = buffers->drm_fb_id[i] = fb_obj.fb_id;
+    ltm_buffers_ctrl.fds[i] = ltm_buffers.drm_fb_id[i];
 
     /**
      * ADDFB2 will take reference to GEM handles,
@@ -501,19 +511,22 @@
       DRM_LOGE("failed to get uva: %d", ret);
       break;
     }
-    ltm_buffers_.uva[i] = buffers->uva[i] = uva;
+    ltm_buffers.uva[i] = buffers->uva[i] = uva;
   }
 
   if (!ret) {
     buffers->status = 0;
-    ltm_buffers_.buffer_size = buffers->buffer_size;
-    ltm_buffers_ctrl_.num_of_buffers = ltm_buffers_.num_of_buffers;
+    ltm_buffers.buffer_size = buffers->buffer_size;
+    ltm_buffers_ctrl.num_of_buffers = ltm_buffers.num_of_buffers;
     DRM_LOGV("InitLtmBuffers return successful");
   } else {
     DeInitLtmBuffers();
     buffers->status = ret;
+    return ret;
   }
 
+  ltm_buffers_map_.push_back(std::make_pair(info->obj_id, std::move(ltm_buffers)));
+  ltm_buffers_ctrl_map_.push_back(std::make_pair(info->obj_id, std::move(ltm_buffers_ctrl)));
   return ret;
 }
 
@@ -525,28 +538,38 @@
     return -EINVAL;
   }
 
-  for (i = 0; i < ltm_buffers_.num_of_buffers; i++) {
-    if (ltm_buffers_.uva[i]) {
-      drm_munmap(ltm_buffers_.uva[i], ltm_buffers_.buffer_size);
-      ltm_buffers_.uva[i] = NULL;
+  for (auto& it : ltm_buffers_map_) {
+    DRMDppsLtmBuffers& ltm_buffers = it.second;
+    for (i = 0; i < ltm_buffers.num_of_buffers; i++) {
+      if (ltm_buffers.uva[i]) {
+        drm_munmap(ltm_buffers.uva[i], ltm_buffers.buffer_size);
+        ltm_buffers.uva[i] = NULL;
+      }
+
+      if (ltm_buffers.drm_fb_id[i] >= 0) {
+#ifdef DRM_IOCTL_MSM_RMFB2
+        ret = drmIoctl(drm_fd_, DRM_IOCTL_MSM_RMFB2, &ltm_buffers.drm_fb_id[i]);
+        if (ret) {
+          ret = errno;
+          DRM_LOGE("RMFB2 failed for fb_id %d with error %d", ltm_buffers.drm_fb_id[i], ret);
+        }
+#endif
+        ltm_buffers.drm_fb_id[i] = -1;
+      }
+      ltm_buffers.ion_buffer_fd[i] = -1;
     }
 
-    if (ltm_buffers_.drm_fb_id[i] >= 0) {
-#ifdef DRM_IOCTL_MSM_RMFB2
-      ret = drmIoctl(drm_fd_, DRM_IOCTL_MSM_RMFB2, &ltm_buffers_.drm_fb_id[i]);
-      if (ret) {
-        ret = errno;
-        DRM_LOGE("RMFB2 failed for fb_id %d with error %d", ltm_buffers_.drm_fb_id[i], ret);
-      }
-#endif
-      ltm_buffers_.drm_fb_id[i] = -1;
-    }
-    ltm_buffers_.ion_buffer_fd[i] = -1;
+    ltm_buffers.num_of_buffers = 0;
+    ltm_buffers.buffer_size = 0;
   }
 
-  ltm_buffers_.num_of_buffers = 0;
-  ltm_buffers_.buffer_size = 0;
-  std::memset(&ltm_buffers_ctrl_, 0, sizeof(ltm_buffers_ctrl_));
+  for (auto& it : ltm_buffers_ctrl_map_) {
+    drm_msm_ltm_buffers_ctrl& ltm_buffers_ctrl = it.second;
+    std::memset(&ltm_buffers_ctrl, 0, sizeof(ltm_buffers_ctrl));
+  }
+
+  ltm_buffers_map_.clear();
+  ltm_buffers_ctrl_map_.clear();
   return 0;
 }
 
diff --git a/sde-drm/drm_dpps_mgr_imp.h b/sde-drm/drm_dpps_mgr_imp.h
index b7a2fb9..eefb213 100644
--- a/sde-drm/drm_dpps_mgr_imp.h
+++ b/sde-drm/drm_dpps_mgr_imp.h
@@ -71,8 +71,8 @@
   int conn_id_ = -1;
   int crtc_id_ = -1;
   int drm_fd_ = -1;
-  struct drm_msm_ltm_buffers_ctrl ltm_buffers_ctrl_ = {};
-  struct DRMDppsLtmBuffers ltm_buffers_ = {};
+  std::vector<std::pair<uint32_t, drm_msm_ltm_buffers_ctrl>> ltm_buffers_ctrl_map_;
+  std::vector<std::pair<uint32_t, DRMDppsLtmBuffers>> ltm_buffers_map_;
 };
 
 class DRMDppsManagerDummyImp : public DRMDppsManagerIntf {
diff --git a/sdm/libs/core/drm/hw_peripheral_drm.cpp b/sdm/libs/core/drm/hw_peripheral_drm.cpp
index f70984e..0aaeb93 100644
--- a/sdm/libs/core/drm/hw_peripheral_drm.cpp
+++ b/sdm/libs/core/drm/hw_peripheral_drm.cpp
@@ -276,6 +276,7 @@
     return kErrorParameters;
   }
   DRMDppsFeatureInfo *feature_info = reinterpret_cast<DRMDppsFeatureInfo *>(payload);
+  feature_info->obj_id = token_.crtc_id;
   drm_mgr_intf_->GetDppsFeatureInfo(feature_info);
   return kErrorNone;
 }