summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorpiotr <piotr@piotr-desktop.(none)>2009-06-05 21:01:11 +0200
committerpiotr <piotr@piotr-desktop.(none)>2009-06-05 21:01:11 +0200
commit58b281711e2000abe99aa4522a295ad9b97bc1f7 (patch)
tree0502648f06d346edfbc1cac2855c052adb07d7d2
parentba23d7efb87cd8ba624a1f9c577cf2bbea1b2fed (diff)
just next cleanup, move along
-rw-r--r--src/lib/gsm_constants.h48
-rw-r--r--src/lib/gsm_receiver_cf.cc53
-rw-r--r--src/lib/gsm_receiver_cf.h8
3 files changed, 79 insertions, 30 deletions
diff --git a/src/lib/gsm_constants.h b/src/lib/gsm_constants.h
index ded8cb4..520ff4f 100644
--- a/src/lib/gsm_constants.h
+++ b/src/lib/gsm_constants.h
@@ -22,10 +22,12 @@
#define FRAME_BITS (TS_PER_FRAME * TS_BITS + 2) // 156.25 * 8
#define FCCH_POS TAIL_BITS
#define SYNC_POS 39
-#define TRAIN_POS 58
-#define SAFETY_MARGIN 6
+#define TRAIN_POS TAIL_BITS + DATA_BITS + 5 //first 5 bits of a training sequence
+//aren't used for channel impulse response estimation
+#define TRAIN_BEGINNING 5
+#define SAFETY_MARGIN 6 //
-#define FCCH_HITS_NEEDED (USEFUL_BITS - 4)
+#define FCCH_HITS_NEEDED (USEFUL_BITS - 4)
#define FCCH_MAX_MISSES 1
#define FCCH_MAX_FREQ_OFFSET 100
@@ -38,9 +40,9 @@ static const unsigned char SYNC_BITS[] = {
0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 1, 1
};
-const unsigned FCCH_FRAMES[] = {0,10,20,30,40};
-const unsigned SCH_FRAMES[] = {1,11,21,31,41};
-const unsigned BCCH_FRAMES[] = {2,3,4,5, 12}; //remove 12
+const unsigned FCCH_FRAMES[] = {0, 10, 20, 30, 40};
+const unsigned SCH_FRAMES[] = {1, 11, 21, 31, 41};
+const unsigned BCCH_FRAMES[] = {2, 3, 4, 5};
// Sync : .+...++.+..+++.++++++.++++++....++.+..+.+.+++.+.+...+..++++..+..
// Diff Encoded Sync: .++..+.+++.+..++.....++.....+...+.+++.+++++..+++++..++.+...+.++.
@@ -91,6 +93,40 @@ static const unsigned char dummy_burst[] = {
1, 1, 1, 0, 1, 0, 1, 0
};
+
+/*
+ * The frequency correction burst is used for frequency synchronization
+ * of the mobile. This is broadcast in TS0 together with the SCH and
+ * BCCH.
+ *
+ * Modulating the bits below causes a spike at 62.5kHz above (below for
+ * COMPACT) the center frequency. One can use this spike with a narrow
+ * band filter to accurately determine the center of the channel.
+ */
+static const unsigned char fc_fb[] = { //I don't use this tables,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //I copied this here from burst_types.h because
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, //the description is very informative - p.krysik
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
+};
+
+static const unsigned char fc_compact_fb[] = {
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0
+};
+
//Diff encoded train_seq
//TSC0: +.++.+++..+...++..++.+++..
//TSC1: +.+++.++..++...+..++.+++..
diff --git a/src/lib/gsm_receiver_cf.cc b/src/lib/gsm_receiver_cf.cc
index c47e111..c1280f4 100644
--- a/src/lib/gsm_receiver_cf.cc
+++ b/src/lib/gsm_receiver_cf.cc
@@ -75,10 +75,10 @@ gsm_receiver_cf::gsm_receiver_cf(gr_feval_dd *tuner, int osr)
d_burst_nr(osr)
{
int i;
- gmsk_mapper(SYNC_BITS, N_SYNC_BITS, d_sch_training_seq, gr_complex(0.0,-1.0));
+ gmsk_mapper(SYNC_BITS, N_SYNC_BITS, d_sch_training_seq, gr_complex(0.0, -1.0));
for (i = 0; i < TRAIN_SEQ_NUM; i++) {
- gmsk_mapper(train_seq[i], N_TRAIN_BITS, d_norm_training_seq[i], gr_complex(1.0,0.0));
+ gmsk_mapper(train_seq[i], N_TRAIN_BITS, d_norm_training_seq[i], gr_complex(1.0, 0.0));
}
}
@@ -91,7 +91,7 @@ gsm_receiver_cf::~gsm_receiver_cf()
void gsm_receiver_cf::forecast(int noutput_items, gr_vector_int &ninput_items_required)
{
- ninput_items_required[0] = noutput_items * (TS_BITS + 2 * SAFETY_MARGIN) * d_OSR;
+ ninput_items_required[0] = noutput_items * floor((TS_BITS + 2 * GUARD_PERIOD) * d_OSR);
}
int
@@ -207,13 +207,11 @@ gsm_receiver_cf::general_work(int noutput_items,
case normal_burst:
burst_start = get_norm_chan_imp_resp(in, chan_imp_resp, TRAIN_SEARCH_RANGE);
detect_burst(in, &d_channel_imp_resp[0], burst_start, output_binary);
-// printf("burst = [ ");
-//
-// for (int i = 0; i < BURST_SIZE ; i++) {
-// printf(" %d", output_binary[i]);
-// }
-// printf("];\n");
-
+ printf("burst = [ ");
+ for (int i = 0; i < BURST_SIZE ; i++) {
+ printf(" %d", output_binary[i]);
+ }
+ printf("];\n");
break;
case rach_burst:
@@ -596,12 +594,13 @@ int gsm_receiver_cf::get_norm_chan_imp_resp(const gr_complex *in, gr_complex * c
int chan_imp_resp_center;
float max_correlation = 0;
float energy = 0;
-
- int search_start_pos = floor((TRAIN_POS + GUARD_PERIOD) * d_OSR);
- int search_stop_pos = search_start_pos + search_range * d_OSR;
+
+ int search_center = (int)((TRAIN_POS + GUARD_PERIOD) * d_OSR);
+ int search_start_pos = search_center+1;
+ int search_stop_pos = search_center + d_chan_imp_length * d_OSR + 2*d_OSR;
for (int ii = search_start_pos; ii < search_stop_pos; ii++) {
- gr_complex correlation = correlate_sequence(&d_norm_training_seq[d_bcc][5], &in[ii], N_TRAIN_BITS - 10);
+ gr_complex correlation = correlate_sequence(&d_norm_training_seq[d_bcc][TRAIN_BEGINNING], &in[ii], N_TRAIN_BITS - 10);
correlation_buffer.push_back(correlation);
power_buffer.push_back(pow(abs(correlation), 2));
@@ -615,24 +614,27 @@ int gsm_receiver_cf::get_norm_chan_imp_resp(const gr_complex *in, gr_complex * c
energy = 0;
for (int ii = 0; ii < (d_chan_imp_length)*d_OSR; ii++, iter_ii++) {
+// for (int ii = 0; ii < (d_chan_imp_length); ii++) {
if (iter_ii == power_buffer.end()) {
loop_end = true;
break;
}
energy += (*iter_ii);
+// iter_ii = iter_ii + d_OSR;
}
if (loop_end) {
break;
}
iter++;
+// std::cout << energy << "\n";
+
window_energy_buffer.push_back(energy);
}
-
-
+// std::cout << window_energy_buffer.size() << "\n";
strongest_window_nr = max_element(window_energy_buffer.begin(), window_energy_buffer.end()) - window_energy_buffer.begin();
d_channel_imp_resp.clear();
- strongest_window_nr = 36;
+// strongest_window_nr = 3;
max_correlation = 0;
for (int ii = 0; ii < (d_chan_imp_length)*d_OSR; ii++) {
@@ -644,9 +646,20 @@ int gsm_receiver_cf::get_norm_chan_imp_resp(const gr_complex *in, gr_complex * c
d_channel_imp_resp.push_back(correlation);
chan_imp_resp[ii] = correlation;
}
+//WE WANT TO USE THE FIRST SAMPLE OF THE IMPULSERESPONSE, AND THE
+// CORRESPONDING SAMPLES OF THE RECEIVED SIGNAL.
+// THE VARIABLE sync_w SHOULD CONTAIN THE BEGINNING OF THE USED PART OF
+// TRAINING SEQUENCE, WHICH IS 3+57+1+6=67 BITS INTO THE BURST. THAT IS
+// WE HAVE THAT sync_T16 EQUALS FIRST SAMPLE IN BIT NUMBER 67.
+
+
+ burst_start = search_start_pos + chan_imp_resp_center + strongest_window_nr - 66 * d_OSR - 2 * d_OSR + 2;
+// COMPENSATING FOR THE 2 Tb DELAY INTRODUCED IN THE GMSK MODULATOR.
+// EACH BIT IS STRECHED OVER A PERIOD OF 3 Tb WITH ITS MAXIMUM VALUE
+// IN THE LAST BIT PERIOD. HENCE, burst_start IS 2 * OSR
+//compute burst start
+ std::cout << " burst_start: " << (float)burst_start/(float)d_OSR<< " center: " << ((float)(search_start_pos + strongest_window_nr + chan_imp_resp_center))/d_OSR << " stronegest window nr: " << strongest_window_nr << "\n";
- std::cout << "center: " << strongest_window_nr + chan_imp_resp_center << " stronegest window nr: " << strongest_window_nr << "\n";
-
- burst_start = search_start_pos + strongest_window_nr + chan_imp_resp_center - 66 * d_OSR - 2 * d_OSR + 2;
return burst_start;
+
}
diff --git a/src/lib/gsm_receiver_cf.h b/src/lib/gsm_receiver_cf.h
index 978576b..e07eb60 100644
--- a/src/lib/gsm_receiver_cf.h
+++ b/src/lib/gsm_receiver_cf.h
@@ -164,6 +164,10 @@ class burst_counter
unsigned get_offset(){
return (unsigned)d_offset;
}
+ //!!
+ float get_first_sample_offset(){
+ return d_first_sample_offset;
+ }
};
class channel_configuration
@@ -255,10 +259,6 @@ class gsm_receiver_cf : public gr_block
//variables used to store result of the find_fcch_burst fuction
int d_fcch_start_pos;
float d_freq_offset;
-// double d_best_sum;
-
-// int d_fcch_count; //!!!
-// double d_x_temp, d_x2_temp, d_mean;//!!
burst_counter d_burst_nr;
channel_configuration d_channel_conf;
personal git repositories of Harald Welte. Your mileage may vary