FAPI TM, WLS_LIB and ODULOW documentation
[o-du/phy.git] / fapi_5g / source / api / fapi2mac / p7 / nr5g_fapi_proc_rach_ind.c
1 /******************************************************************************
2 *
3 *   Copyright (c) 2019 Intel.
4 *
5 *   Licensed under the Apache License, Version 2.0 (the "License");
6 *   you may not use this file except in compliance with the License.
7 *   You may obtain a copy of the License at
8 *
9 *       http://www.apache.org/licenses/LICENSE-2.0
10 *
11 *   Unless required by applicable law or agreed to in writing, software
12 *   distributed under the License is distributed on an "AS IS" BASIS,
13 *   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 *   See the License for the specific language governing permissions and
15 *   limitations under the License.
16 *
17 *******************************************************************************/
18 /**
19  * @file
20  * This file consist of implementation of FAPI RACH.indication message.
21  *
22  **/
23
24 #include "nr5g_fapi_framework.h"
25 #include "gnb_l1_l2_api.h"
26 #include "nr5g_fapi_fapi2mac_api.h"
27 #include "nr5g_fapi_fapi2mac_p7_proc.h"
28 #include "nr5g_fapi_fapi2mac_p7_pvt_proc.h"
29
30  /** @ingroup group_source_api_p7_fapi2mac_proc
31  *
32  *  @param[in]  p_phy_ctx Pointer to PHY Context.
33  *  @param[in]  p_phy_rach_ind Pointer to FAPI RACH.indication message structure.
34  *  
35  *  @return     Returns ::SUCCESS and ::FAILURE.
36  *
37  *  @description
38  *  This message includes RACH PDU. 
39  *
40 **/
41 uint8_t nr5g_fapi_rach_indication(
42     p_nr5g_fapi_phy_ctx_t p_phy_ctx,
43     PRXRACHIndicationStruct p_phy_rach_ind)
44 {
45     uint8_t phy_id;
46
47     fapi_rach_indication_t *p_fapi_rach_ind;
48     p_fapi_api_queue_elem_t p_list_elem;
49     p_nr5g_fapi_phy_instance_t p_phy_instance = NULL;
50     nr5g_fapi_stats_t *p_stats;
51
52     if (NULL == p_phy_ctx) {
53         NR5G_FAPI_LOG(ERROR_LOG, ("[RACH.indication] Invalid " "phy context"));
54         return FAILURE;
55     }
56
57     if (NULL == p_phy_rach_ind) {
58         NR5G_FAPI_LOG(ERROR_LOG, ("[RACH.indication] Invalid handle to phy "
59                 "RACH indication"));
60         return FAILURE;
61     }
62
63     phy_id = p_phy_rach_ind->sSFN_Slot.nCarrierIdx;
64     p_phy_instance = &p_phy_ctx->phy_instance[phy_id];
65     if ((p_phy_instance->phy_id != phy_id)) {
66         NR5G_FAPI_LOG(ERROR_LOG, ("[RACH.indication] Invalid " "phy instance"));
67         return FAILURE;
68     }
69
70     p_stats = &p_phy_instance->stats;
71     p_stats->iapi_stats.iapi_rach_ind++;
72
73     p_list_elem =
74         nr5g_fapi_fapi2mac_create_api_list_elem(FAPI_RACH_INDICATION, 1,
75         sizeof(fapi_rach_indication_t));
76
77     if (!p_list_elem) {
78         NR5G_FAPI_LOG(ERROR_LOG, ("[RACH.indication] Unable to create "
79                 "list element. Out of memory!!!"));
80         return FAILURE;
81     }
82
83     p_fapi_rach_ind = (fapi_rach_indication_t *) (p_list_elem + 1);
84     p_fapi_rach_ind->header.msg_id = FAPI_RACH_INDICATION;
85     p_fapi_rach_ind->header.length = (uint16_t) sizeof(fapi_rach_indication_t);
86
87     if (nr5g_fapi_rach_indication_to_fapi_translation(p_phy_instance,
88             p_phy_rach_ind, p_fapi_rach_ind)) {
89         NR5G_FAPI_LOG(ERROR_LOG,
90             ("[RACH.indication] L1 to FAPI " "translation failed"));
91         return FAILURE;
92     }
93
94     nr5g_fapi_fapi2mac_add_api_to_list(phy_id, p_list_elem);
95
96     p_stats->fapi_stats.fapi_rach_ind++;
97     NR5G_FAPI_LOG(DEBUG_LOG, ("[RACH.indication][%d][%d,%d]",
98             p_phy_instance->phy_id,
99             p_phy_rach_ind->sSFN_Slot.nSFN, p_phy_rach_ind->sSFN_Slot.nSlot));
100
101     return SUCCESS;
102 }
103
104  /** @ingroup group_source_api_p7_fapi2mac_proc
105  *
106  *  @param[in]   slot_index Variable holding nStartSlotdx received in IAPI RACH.Indication.
107  *  @param[in]   freq_index Variable holding nFreqIdx received in IAPI RACH.Indication.
108  *  @param[in]   symbol_index Variable holding nSymbolIdx received in IAPI RACH.Indication.
109  *  @param[in]   num_pdus Variable holding the num_pdus filled in FAPI RACH.Indication till then.
110  *  @param[in]   p_fapi_rach_ind Pointer to FAPI RACH.indication structure.
111  *  
112  *  @return     Returns pdu_index at which slot_index and freq_index match occurs
113  *                         
114  *
115  *  @description
116  *  This function returns the pdu_index at which slot_index and freq_index match
117  *  occurs in FAPI RACH.Indication populated till then
118  *
119 **/
120 uint8_t nr5g_fapi_start_slot_freq_idx_occ(
121     uint8_t slot_index,
122     uint8_t freq_index,
123     uint8_t symbol_index,
124     uint8_t num_pdus,
125     fapi_rach_indication_t * p_fapi_rach_ind)
126 {
127     uint8_t i, pdu_index = 0xFF;
128
129     fapi_rach_pdu_t *p_fapi_rach_pdu;
130
131     for (i = 0; i < num_pdus; i++) {
132         p_fapi_rach_pdu = &p_fapi_rach_ind->rachPdu[i];
133         if ((slot_index == p_fapi_rach_pdu->slotIndex)
134             && (freq_index == p_fapi_rach_pdu->freqIndex)
135             && (symbol_index == p_fapi_rach_pdu->symbolIndex)) {
136             pdu_index = i;
137             break;
138         }
139     }
140     return pdu_index;
141 }
142
143  /** @ingroup group_source_api_p7_fapi2mac_proc
144  *
145  *  @param[in]  p_phy_instance Pointer to PHY instance.
146  *  @param[in]   p_phy_rach_ind Pointer to IAPI RACH.indication structure.
147  *  @param[out]  p_fapi_rach_ind Pointer to FAPI RACH.indication structure.
148  *  
149  *  @return     Returns ::SUCCESS and ::FAILURE.
150  *
151  *  @description
152  *  This function converts IAPI RACH.indication to FAPI RACH.indication
153  *  structure.
154  *
155 **/
156 uint8_t nr5g_fapi_rach_indication_to_fapi_translation(
157     p_nr5g_fapi_phy_instance_t p_phy_instance,
158     PRXRACHIndicationStruct p_phy_rach_ind,
159     fapi_rach_indication_t * p_fapi_rach_ind)
160 {
161     uint8_t num_preamble, num_pdus = 0, i;
162     uint8_t slot_no, preamble_no;
163     uint8_t slot_freq_idx_entry;
164     uint8_t slot_index, freq_index, symbol_index;
165     uint16_t frame_no;
166
167     fapi_rach_pdu_t *p_fapi_rach_pdu;
168     fapi_rach_pdu_t *p_fapi_rach_pdu_match;
169     fapi_preamble_info_t *p_fapi_preamble_info;
170     nr5g_fapi_ul_slot_info_t *p_ul_slot_info;
171     nr5g_fapi_stats_t *p_stats;
172     PreambleStruct *p_phy_preamble_struct;
173
174     p_stats = &p_phy_instance->stats;
175
176     frame_no = p_fapi_rach_ind->sfn = p_phy_rach_ind->sSFN_Slot.nSFN;
177     slot_no = p_fapi_rach_ind->slot = p_phy_rach_ind->sSFN_Slot.nSlot;
178
179     p_ul_slot_info =
180         nr5g_fapi_get_ul_slot_info(frame_no, slot_no, p_phy_instance);
181
182     if (p_ul_slot_info == NULL) {
183         NR5G_FAPI_LOG(ERROR_LOG, ("[RACH.indication] No Valid data available "
184                 "for frame :%d and slot: %d", frame_no, slot_no));
185         return FAILURE;
186     }
187
188     if (p_ul_slot_info->rach_presence == 0) {
189         NR5G_FAPI_LOG(ERROR_LOG, ("[RACHindication] RACH is not requested"
190                 "for frame :%d and slot: %d", frame_no, slot_no));
191         return FAILURE;
192     }
193
194     num_preamble = p_phy_rach_ind->nNrOfPreamb;
195     for (i = 0; i < num_preamble; i++) {
196         p_stats->iapi_stats.iapi_rach_preambles++;
197         p_phy_preamble_struct = &p_phy_rach_ind->sPreambleStruct[i];
198         slot_index = p_phy_preamble_struct->nStartSlotdx;
199         freq_index = p_phy_preamble_struct->nFreqIdx;
200         symbol_index = p_phy_preamble_struct->nStartSymbIdx;
201         //returns 0xFF if its a new preamble, else pdu index of p_fapi_rach_ind;
202         slot_freq_idx_entry = nr5g_fapi_start_slot_freq_idx_occ(slot_index,
203             freq_index, symbol_index, num_pdus, p_fapi_rach_ind);
204         if (slot_freq_idx_entry == 0xFF) {
205             p_fapi_rach_pdu = &p_fapi_rach_ind->rachPdu[i];
206             p_fapi_rach_pdu->phyCellId = p_ul_slot_info->rach_info.phy_cell_id;
207             p_fapi_rach_pdu->numPreamble = 0;
208             p_fapi_rach_pdu->symbolIndex = p_phy_preamble_struct->nStartSymbIdx;
209             p_fapi_rach_pdu->slotIndex = slot_index;
210             p_fapi_rach_pdu->freqIndex = freq_index;
211             p_fapi_rach_pdu->avgRssi = 0xFF;
212             p_fapi_rach_pdu->avgSnr = 0xFF;
213             preamble_no = p_fapi_rach_pdu->numPreamble++;
214             p_fapi_preamble_info = &p_fapi_rach_pdu->preambleInfo[preamble_no];
215             num_pdus++;
216             p_stats->fapi_stats.fapi_rach_ind_pdus++;
217         } else {
218             p_fapi_rach_pdu_match =
219                 &p_fapi_rach_ind->rachPdu[slot_freq_idx_entry];
220             preamble_no = p_fapi_rach_pdu_match->numPreamble++;
221             p_fapi_preamble_info =
222                 &p_fapi_rach_pdu_match->preambleInfo[preamble_no];
223         }
224         p_fapi_preamble_info->preambleIndex = p_phy_preamble_struct->nPreambIdx;
225         p_fapi_preamble_info->timingAdvance = p_phy_preamble_struct->nTa;
226         p_fapi_preamble_info->preamblePwr = p_phy_preamble_struct->nPreambPwr;
227     }
228     p_fapi_rach_ind->numPdus = num_pdus;
229
230     return SUCCESS;
231 }