Beispiel #1
0
int srslte_chest_ul_estimate_pucch(srslte_chest_ul_t *q, cf_t *input, cf_t *ce, 
                                   srslte_pucch_format_t format, uint32_t n_pucch, uint32_t sf_idx, 
                                   uint8_t *pucch2_ack_bits) 
{
  if (!q->dmrs_signal_configured) {
    fprintf(stderr, "Error must call srslte_chest_ul_set_cfg() before using the UL estimator\n");
    return SRSLTE_ERROR; 
  }
    
  int n_rs = srslte_refsignal_dmrs_N_rs(format, q->cell.cp);
  if (!n_rs) {
    fprintf(stderr, "Error computing N_rs\n");
    return SRSLTE_ERROR; 
  }
  int nrefs_sf = SRSLTE_NRE*n_rs*2; 
  
  /* Get references from the input signal */
  srslte_refsignal_dmrs_pucch_get(&q->dmrs_signal, format, n_pucch, input, q->pilot_recv_signal);
  
  /* Generate known pilots */
  uint8_t pucch2_bits[2] = {0, 0};
  if (format == SRSLTE_PUCCH_FORMAT_2A || format == SRSLTE_PUCCH_FORMAT_2B) {
    float max = -1e9;
    int i_max = 0; 
    
    int m = 0; 
    if (format == SRSLTE_PUCCH_FORMAT_2A) {
      m = 2; 
    } else {
      m = 4; 
    }
    
    for (int i=0;i<m;i++) {
      pucch2_bits[0] = i%2;
      pucch2_bits[1] = i/2;
      srslte_refsignal_dmrs_pucch_gen(&q->dmrs_signal, format, n_pucch, sf_idx, pucch2_bits, q->pilot_known_signal);
      srslte_vec_prod_conj_ccc(q->pilot_recv_signal, q->pilot_known_signal, q->pilot_estimates_tmp[i], nrefs_sf);
      float x = cabsf(srslte_vec_acc_cc(q->pilot_estimates_tmp[i], nrefs_sf));
      if (x >= max) {
        max = x; 
        i_max = i; 
      }      
    }
    memcpy(q->pilot_estimates, q->pilot_estimates_tmp[i_max], nrefs_sf*sizeof(cf_t));
    pucch2_ack_bits[0] = i_max%2;
    pucch2_ack_bits[1] = i_max/2;
  } else {
    srslte_refsignal_dmrs_pucch_gen(&q->dmrs_signal, format, n_pucch, sf_idx, pucch2_bits, q->pilot_known_signal);
    /* Use the known DMRS signal to compute Least-squares estimates */
    srslte_vec_prod_conj_ccc(q->pilot_recv_signal, q->pilot_known_signal, q->pilot_estimates, nrefs_sf);
  }
  
  if (ce != NULL) {
    /* FIXME: Currently averaging entire slot, performance good enough? */
    for (int ns=0;ns<2;ns++) {
      // Average all slot 
      for (int i=1;i<n_rs;i++) {
        srslte_vec_sum_ccc(&q->pilot_estimates[ns*n_rs*SRSLTE_NRE], &q->pilot_estimates[(i+ns*n_rs)*SRSLTE_NRE], 
                           &q->pilot_estimates[ns*n_rs*SRSLTE_NRE], 
                           SRSLTE_NRE);
      }
      srslte_vec_sc_prod_ccc(&q->pilot_estimates[ns*n_rs*SRSLTE_NRE], (float) 1.0/n_rs, 
                             &q->pilot_estimates[ns*n_rs*SRSLTE_NRE], 
                             SRSLTE_NRE);
      
      // Average in freq domain
      srslte_chest_average_pilots(&q->pilot_estimates[ns*n_rs*SRSLTE_NRE], &q->pilot_recv_signal[ns*n_rs*SRSLTE_NRE], 
                                  q->smooth_filter, SRSLTE_NRE, 1, q->smooth_filter_len);
      
      // Determine n_prb
      uint32_t n_prb = srslte_pucch_n_prb(&q->dmrs_signal.pucch_cfg, format, n_pucch, q->cell.nof_prb, q->cell.cp, ns); 

      // copy estimates to slot 
      for (int i=0;i<SRSLTE_CP_NSYMB(q->cell.cp);i++) {
        memcpy(&ce[SRSLTE_RE_IDX(q->cell.nof_prb, i+ns*SRSLTE_CP_NSYMB(q->cell.cp), n_prb*SRSLTE_NRE)], 
               &q->pilot_recv_signal[ns*n_rs*SRSLTE_NRE], sizeof(cf_t)*SRSLTE_NRE);
      }
    }
  }
  
  return 0;
}
Beispiel #2
0
int main(int argc, char **argv) {
  srslte_pucch_t pucch;
  srslte_pucch_cfg_t pucch_cfg;
  srslte_refsignal_ul_t dmrs;
  uint8_t bits[SRSLTE_PUCCH_MAX_BITS];
  uint8_t pucch2_bits[2]; 
  cf_t *sf_symbols = NULL;
  cf_t pucch_dmrs[2*SRSLTE_NRE*3];
  int ret = -1;
  
  parse_args(argc,argv);

  if (srslte_pucch_init(&pucch, cell)) {
    fprintf(stderr, "Error creating PDSCH object\n");
    goto quit;
  }
  if (srslte_refsignal_ul_init(&dmrs, cell)) {
    fprintf(stderr, "Error creating PDSCH object\n");
    goto quit;
  }
  
  bzero(&pucch_cfg, sizeof(srslte_pucch_cfg_t));
  
  for (int i=0;i<SRSLTE_PUCCH_MAX_BITS;i++) {
    bits[i] = i%2;
  }
        
  for (int i=0;i<2;i++) {
    pucch2_bits[i] = i%2;
  }
  
  if (srslte_pucch_set_crnti(&pucch, 11)) {
    fprintf(stderr, "Error setting C-RNTI\n");
    goto quit; 
  }
  
  sf_symbols = srslte_vec_malloc(sizeof(cf_t) * SRSLTE_SF_LEN_RE(cell.nof_prb, cell.cp));
  if (!sf_symbols) {
    goto quit; 
  }

  srslte_pucch_format_t format; 
  for (format=0;format<=SRSLTE_PUCCH_FORMAT_2B;format++) {
    for (uint32_t d=1;d<=3;d++) {
      for (uint32_t ncs=0;ncs<8;ncs+=d) {
        for (uint32_t n_pucch=1;n_pucch<130;n_pucch+=50) {
        
          struct timeval t[3]; 
          
          pucch_cfg.delta_pucch_shift = d; 
          bool group_hopping_en = false; 
          pucch_cfg.N_cs = ncs; 
          pucch_cfg.n_rb_2 = 0; 
    
          gettimeofday(&t[1], NULL);
          if (!srslte_pucch_set_cfg(&pucch, &pucch_cfg, group_hopping_en)) {
            fprintf(stderr, "Error setting PUCCH config\n");
            goto quit; 
          }
          
          if (srslte_pucch_encode(&pucch, format, n_pucch, subframe, bits, sf_symbols)) {
            fprintf(stderr, "Error encoding PUCCH\n");
            goto quit; 
          }
          
          srslte_refsignal_dmrs_pusch_cfg_t pusch_cfg; 
          pusch_cfg.group_hopping_en = group_hopping_en; 
          pusch_cfg.sequence_hopping_en = false; 
          srslte_refsignal_ul_set_cfg(&dmrs, &pusch_cfg, &pucch_cfg, NULL);
          
          if (srslte_refsignal_dmrs_pucch_gen(&dmrs, format, n_pucch, subframe, pucch2_bits, pucch_dmrs)) {
            fprintf(stderr, "Error encoding PUCCH\n");
            goto quit; 
          }
          if (srslte_refsignal_dmrs_pucch_put(&dmrs, format, n_pucch, pucch_dmrs, sf_symbols)) {
            fprintf(stderr, "Error encoding PUCCH\n");
            goto quit; 
          }     
          gettimeofday(&t[2], NULL);
          get_time_interval(t);
          INFO("format %d, n_pucch: %d, ncs: %d, d: %d, t_exec=%d us\n", format, n_pucch, ncs, d, t[0].tv_usec);
        }
      }
    }    
  }

  ret = 0;
quit:
  srslte_pucch_free(&pucch);
  srslte_refsignal_ul_free(&dmrs);
  
  if (sf_symbols) {
    free(sf_symbols);
  }
  if (ret) {
    printf("Error\n");
  } else {
    printf("Ok\n");
  }
  exit(ret);
}