mt_spm_rc_api.c 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171
  1. /*
  2. * Copyright (c) 2023, MediaTek Inc. All rights reserved.
  3. *
  4. * SPDX-License-Identifier: BSD-3-Clause
  5. */
  6. #include <lpm/mt_lpm_smc.h>
  7. #include <mt_spm.h>
  8. #include "mt_spm_rc_api.h"
  9. #include "mt_spm_rc_internal.h"
  10. int spm_rc_condition_modifier(unsigned int id, unsigned int act,
  11. const void *val,
  12. enum mt_spm_rm_rc_type dest_rc_id,
  13. struct mt_spm_cond_tables * const tlb)
  14. {
  15. unsigned int rc_id, cond_id, cond;
  16. int res = 0;
  17. spin_lock(&spm_lock);
  18. rc_id = SPM_RC_UPDATE_COND_RC_ID_GET(id);
  19. cond_id = SPM_RC_UPDATE_COND_ID_GET(id);
  20. do {
  21. if ((dest_rc_id != rc_id) || (val == NULL) || (tlb == NULL)) {
  22. res = -1;
  23. break;
  24. }
  25. cond = *((unsigned int *)val);
  26. if (cond_id < PLAT_SPM_COND_MAX) {
  27. if ((act & MT_LPM_SMC_ACT_SET) > 0U) {
  28. SPM_RC_BITS_SET(tlb->table_cg[cond_id], cond);
  29. } else if ((act & MT_LPM_SMC_ACT_CLR) > 0U) {
  30. SPM_RC_BITS_CLR(tlb->table_cg[cond_id], cond);
  31. } else {
  32. res = -1;
  33. }
  34. } else if ((cond_id - PLAT_SPM_COND_MAX) < PLAT_SPM_COND_PLL_MAX) {
  35. unsigned int pll_idx = cond_id - PLAT_SPM_COND_MAX;
  36. cond = !!cond;
  37. if ((act & MT_LPM_SMC_ACT_SET) > 0U) {
  38. SPM_RC_BITS_SET(tlb->table_pll, (cond << pll_idx));
  39. } else if ((act & MT_LPM_SMC_ACT_CLR) > 0U) {
  40. SPM_RC_BITS_CLR(tlb->table_pll, (cond << pll_idx));
  41. } else {
  42. res = -1;
  43. }
  44. } else {
  45. res = -1;
  46. }
  47. } while (0);
  48. spin_unlock(&spm_lock);
  49. return res;
  50. }
  51. int spm_rc_constraint_status_get(unsigned int id, unsigned int type,
  52. unsigned int act,
  53. enum mt_spm_rm_rc_type dest_rc_id,
  54. struct constraint_status * const src,
  55. struct constraint_status * const dest)
  56. {
  57. if (((id != MT_RM_CONSTRAINT_ID_ALL) && (id != dest_rc_id)) || (dest == NULL) ||
  58. (src == NULL)) {
  59. return -1;
  60. }
  61. spin_lock(&spm_lock);
  62. switch (type) {
  63. case CONSTRAINT_GET_ENTER_CNT:
  64. if (id == MT_RM_CONSTRAINT_ID_ALL) {
  65. dest->enter_cnt += src->enter_cnt;
  66. } else {
  67. dest->enter_cnt = src->enter_cnt;
  68. }
  69. break;
  70. case CONSTRAINT_GET_VALID:
  71. dest->is_valid = src->is_valid;
  72. break;
  73. case CONSTRAINT_COND_BLOCK:
  74. dest->is_cond_block = src->is_cond_block;
  75. dest->all_pll_dump = src->all_pll_dump;
  76. break;
  77. case CONSTRAINT_GET_COND_BLOCK_DETAIL:
  78. dest->cond_res = src->cond_res;
  79. break;
  80. case CONSTRAINT_GET_RESIDNECY:
  81. dest->residency = src->residency;
  82. if (act & MT_LPM_SMC_ACT_CLR) {
  83. src->residency = 0;
  84. }
  85. break;
  86. default:
  87. break;
  88. }
  89. spin_unlock(&spm_lock);
  90. return 0;
  91. }
  92. int spm_rc_constraint_status_set(unsigned int id, unsigned int type,
  93. unsigned int act,
  94. enum mt_spm_rm_rc_type dest_rc_id,
  95. struct constraint_status * const src,
  96. struct constraint_status * const dest)
  97. {
  98. if (((id != MT_RM_CONSTRAINT_ID_ALL) && (id != dest_rc_id)) || (dest == NULL)) {
  99. return -1;
  100. }
  101. spin_lock(&spm_lock);
  102. switch (type) {
  103. case CONSTRAINT_UPDATE_VALID:
  104. if (src != NULL) {
  105. if ((act & MT_LPM_SMC_ACT_SET) > 0U) {
  106. SPM_RC_BITS_SET(dest->is_valid, src->is_valid);
  107. } else if ((act & MT_LPM_SMC_ACT_CLR) > 0U) {
  108. SPM_RC_BITS_CLR(dest->is_valid, src->is_valid);
  109. }
  110. }
  111. break;
  112. case CONSTRAINT_RESIDNECY:
  113. if (act & MT_LPM_SMC_ACT_CLR) {
  114. dest->residency = 0;
  115. }
  116. break;
  117. default:
  118. break;
  119. }
  120. spin_unlock(&spm_lock);
  121. return 0;
  122. }
  123. int spm_rc_constraint_valid_set(enum mt_spm_rm_rc_type id,
  124. enum mt_spm_rm_rc_type dest_rc_id,
  125. unsigned int valid,
  126. struct constraint_status * const dest)
  127. {
  128. if (((id != MT_RM_CONSTRAINT_ID_ALL) && (id != dest_rc_id)) || (dest == NULL)) {
  129. return -1;
  130. }
  131. spin_lock(&spm_lock);
  132. SPM_RC_BITS_SET(dest->is_valid, valid);
  133. spin_unlock(&spm_lock);
  134. return 0;
  135. }
  136. int spm_rc_constraint_valid_clr(enum mt_spm_rm_rc_type id,
  137. enum mt_spm_rm_rc_type dest_rc_id,
  138. unsigned int valid,
  139. struct constraint_status * const dest)
  140. {
  141. if (((id != MT_RM_CONSTRAINT_ID_ALL) && (id != dest_rc_id)) || (dest == NULL)) {
  142. return -1;
  143. }
  144. spin_lock(&spm_lock);
  145. SPM_RC_BITS_CLR(dest->is_valid, valid);
  146. spin_unlock(&spm_lock);
  147. return 0;
  148. }