fman_sp.c 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142
  1. // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0-or-later
  2. /*
  3. * Copyright 2008 - 2015 Freescale Semiconductor Inc.
  4. */
  5. #include "fman_sp.h"
  6. #include "fman.h"
  7. void fman_sp_set_buf_pools_in_asc_order_of_buf_sizes(struct fman_ext_pools
  8. *fm_ext_pools,
  9. u8 *ordered_array,
  10. u16 *sizes_array)
  11. {
  12. u16 buf_size = 0;
  13. int i = 0, j = 0, k = 0;
  14. /* First we copy the external buffers pools information
  15. * to an ordered local array
  16. */
  17. for (i = 0; i < fm_ext_pools->num_of_pools_used; i++) {
  18. /* get pool size */
  19. buf_size = fm_ext_pools->ext_buf_pool[i].size;
  20. /* keep sizes in an array according to poolId
  21. * for direct access
  22. */
  23. sizes_array[fm_ext_pools->ext_buf_pool[i].id] = buf_size;
  24. /* save poolId in an ordered array according to size */
  25. for (j = 0; j <= i; j++) {
  26. /* this is the next free place in the array */
  27. if (j == i)
  28. ordered_array[i] =
  29. fm_ext_pools->ext_buf_pool[i].id;
  30. else {
  31. /* find the right place for this poolId */
  32. if (buf_size < sizes_array[ordered_array[j]]) {
  33. /* move the pool_ids one place ahead
  34. * to make room for this poolId
  35. */
  36. for (k = i; k > j; k--)
  37. ordered_array[k] =
  38. ordered_array[k - 1];
  39. /* now k==j, this is the place for
  40. * the new size
  41. */
  42. ordered_array[k] =
  43. fm_ext_pools->ext_buf_pool[i].id;
  44. break;
  45. }
  46. }
  47. }
  48. }
  49. }
  50. EXPORT_SYMBOL(fman_sp_set_buf_pools_in_asc_order_of_buf_sizes);
  51. int fman_sp_build_buffer_struct(struct fman_sp_int_context_data_copy *
  52. int_context_data_copy,
  53. struct fman_buffer_prefix_content *
  54. buffer_prefix_content,
  55. struct fman_sp_buf_margins *buf_margins,
  56. struct fman_sp_buffer_offsets *buffer_offsets,
  57. u8 *internal_buf_offset)
  58. {
  59. u32 tmp;
  60. /* Align start of internal context data to 16 byte */
  61. int_context_data_copy->ext_buf_offset = (u16)
  62. ((buffer_prefix_content->priv_data_size & (OFFSET_UNITS - 1)) ?
  63. ((buffer_prefix_content->priv_data_size + OFFSET_UNITS) &
  64. ~(u16)(OFFSET_UNITS - 1)) :
  65. buffer_prefix_content->priv_data_size);
  66. /* Translate margin and int_context params to FM parameters */
  67. /* Initialize with illegal value. Later we'll set legal values. */
  68. buffer_offsets->prs_result_offset = (u32)ILLEGAL_BASE;
  69. buffer_offsets->time_stamp_offset = (u32)ILLEGAL_BASE;
  70. buffer_offsets->hash_result_offset = (u32)ILLEGAL_BASE;
  71. /* Internally the driver supports 4 options
  72. * 1. prsResult/timestamp/hashResult selection (in fact 8 options,
  73. * but for simplicity we'll
  74. * relate to it as 1).
  75. * 2. All IC context (from AD) not including debug.
  76. */
  77. /* This case covers the options under 1 */
  78. /* Copy size must be in 16-byte granularity. */
  79. int_context_data_copy->size =
  80. (u16)((buffer_prefix_content->pass_prs_result ? 32 : 0) +
  81. ((buffer_prefix_content->pass_time_stamp ||
  82. buffer_prefix_content->pass_hash_result) ? 16 : 0));
  83. /* Align start of internal context data to 16 byte */
  84. int_context_data_copy->int_context_offset =
  85. (u8)(buffer_prefix_content->pass_prs_result ? 32 :
  86. ((buffer_prefix_content->pass_time_stamp ||
  87. buffer_prefix_content->pass_hash_result) ? 64 : 0));
  88. if (buffer_prefix_content->pass_prs_result)
  89. buffer_offsets->prs_result_offset =
  90. int_context_data_copy->ext_buf_offset;
  91. if (buffer_prefix_content->pass_time_stamp)
  92. buffer_offsets->time_stamp_offset =
  93. buffer_prefix_content->pass_prs_result ?
  94. (int_context_data_copy->ext_buf_offset +
  95. sizeof(struct fman_prs_result)) :
  96. int_context_data_copy->ext_buf_offset;
  97. if (buffer_prefix_content->pass_hash_result)
  98. /* If PR is not requested, whether TS is
  99. * requested or not, IC will be copied from TS
  100. */
  101. buffer_offsets->hash_result_offset =
  102. buffer_prefix_content->pass_prs_result ?
  103. (int_context_data_copy->ext_buf_offset +
  104. sizeof(struct fman_prs_result) + 8) :
  105. int_context_data_copy->ext_buf_offset + 8;
  106. if (int_context_data_copy->size)
  107. buf_margins->start_margins =
  108. (u16)(int_context_data_copy->ext_buf_offset +
  109. int_context_data_copy->size);
  110. else
  111. /* No Internal Context passing, STartMargin is
  112. * immediately after private_info
  113. */
  114. buf_margins->start_margins =
  115. buffer_prefix_content->priv_data_size;
  116. /* align data start */
  117. tmp = (u32)(buf_margins->start_margins %
  118. buffer_prefix_content->data_align);
  119. if (tmp)
  120. buf_margins->start_margins +=
  121. (buffer_prefix_content->data_align - tmp);
  122. buffer_offsets->data_offset = buf_margins->start_margins;
  123. return 0;
  124. }
  125. EXPORT_SYMBOL(fman_sp_build_buffer_struct);