return 0;
 }
 
+static int hns_roce_query_func_info(struct hns_roce_dev *hr_dev)
+{
+       struct hns_roce_cmq_desc desc;
+       int ret;
+
+       if (hr_dev->pci_dev->revision < PCI_REVISION_ID_HIP09)
+               return 0;
+
+       hns_roce_cmq_setup_basic_desc(&desc, HNS_ROCE_OPC_QUERY_FUNC_INFO,
+                                     true);
+       ret = hns_roce_cmq_send(hr_dev, &desc, 1);
+       if (ret)
+               return ret;
+
+       hr_dev->cong_algo_tmpl_id = le32_to_cpu(desc.func_info.own_mac_id);
+
+       return 0;
+}
+
 static int hns_roce_config_global_param(struct hns_roce_dev *hr_dev)
 {
        struct hns_roce_cfg_global_param *req;
                return ret;
        }
 
+       ret = hns_roce_query_func_info(hr_dev);
+       if (ret) {
+               dev_err(hr_dev->dev, "Query function info fail, ret = %d.\n",
+                       ret);
+               return ret;
+       }
+
        ret = hns_roce_config_global_param(hr_dev);
        if (ret) {
                dev_err(hr_dev->dev, "Configure global param fail, ret = %d.\n",
 
        HNS_ROCE_OPC_CFG_EXT_LLM                        = 0x8403,
        HNS_ROCE_OPC_CFG_TMOUT_LLM                      = 0x8404,
        HNS_ROCE_OPC_QUERY_PF_TIMER_RES                 = 0x8406,
+       HNS_ROCE_OPC_QUERY_FUNC_INFO                    = 0x8407,
        HNS_ROCE_OPC_QUERY_PF_CAPS_NUM                  = 0x8408,
        HNS_ROCE_OPC_CFG_ENTRY_SIZE                     = 0x8409,
        HNS_ROCE_OPC_CFG_SGID_TB                        = 0x8500,
        __le16 flag;
        __le16 retval;
        __le16 rsv;
-       __le32 data[6];
+       union {
+               __le32 data[6];
+               struct {
+                       __le32 rsv1;
+                       __le32 own_mac_id;
+                       __le32 rsv2[4];
+               } func_info;
+       };
+
 };
 
 #define HNS_ROCE_V2_GO_BIT_TIMEOUT_MSECS       10000