From 618811f0a0449915a840fd6ec3641385fc9f00b1 Mon Sep 17 00:00:00 2001 From: Christos Falas Date: Thu, 15 May 2025 00:23:03 +0100 Subject: [PATCH] try to fix music --- examples/music.py | 68 ++++++++++++++++++++++++++++++++++++++ where_fi/config/models.py | 2 +- where_fi/processing/aoa.py | 8 ++--- 3 files changed, 73 insertions(+), 5 deletions(-) create mode 100644 examples/music.py diff --git a/examples/music.py b/examples/music.py new file mode 100644 index 0000000..fc32b5a --- /dev/null +++ b/examples/music.py @@ -0,0 +1,68 @@ +import logging + +import numpy as np +import torch + +from where_fi.application import CSIApplication +from where_fi.collection import CSIMatrix +from where_fi.collection.ingest import RealtimeCSIProducer +from where_fi.config import config +from where_fi.processing import aoa +from where_fi.visualise import server as visualise + +producer = RealtimeCSIProducer() +app = CSIApplication(producer, visualise_raw=True) +visualise.figures.all_figures["median"] = visualise.figures.RandomVariable( + "Median Phase" +) +visualise.figures.all_figures["magn"] = visualise.figures.RandomVariable( + "Median Magnitude" +) + +logging.basicConfig(level=logging.INFO) + +T = 500 + +N_sub1 = config.antennas.count // 2 +N_sub2 = config.subcarriers // 2 +L2 = config.subcarriers - N_sub2 + 1 +L1 = config.antennas.count - N_sub1 + 1 +N_sensors = config.subcarriers * config.antennas.count +historical = torch.zeros(T, N_sensors, N_sensors, dtype=torch.complex64) + +cnt = 0 + + +@app.on_sample +def _(sample: CSIMatrix) -> None: + global cnt + sample = sample.T.reshape(-1, 1) + sample_tensor = torch.tensor(sample) + historical[cnt] = sample_tensor @ torch.conj(sample_tensor).T + cnt = (cnt + 1) % T + + +aoa = aoa.AoA() + + +@app.on_process +def _(_: CSIMatrix) -> None: + R: torch.Tensor = torch.mean(historical, axis=0) + Rss = torch.zeros(N_sub1 * N_sub2, N_sub1 * N_sub2, dtype=torch.complex64) + for i in range(L1): + for j in range(L2): + Rss += R[i : i + N_sub1 * N_sub2, j : j + N_sub1 * N_sub2] + Rss /= L1 * L2 + + aoa.historical_autocorr = torch.unsqueeze(Rss, 0) + aoa.heatmap(app.visualise_data) + # eigvals, eigvecs = torch.linalg.eig(Rss) + # app.visualise_data(eigvals.numpy(), visualise.figures.Figure.MUSIC_EIGENVALUES) + # E_n = eigvecs[:, torch.abs(eigvals) < config.music.eigval_threshold] + + # print(E_n) + # c: torch.Tensor = 1 / (steering_h @ E_n @ E_n_H @ steering) + # return torch.abs(c)[:, 0, 0] + + +app.start() diff --git a/where_fi/config/models.py b/where_fi/config/models.py index 3e8fb58..df86b24 100644 --- a/where_fi/config/models.py +++ b/where_fi/config/models.py @@ -23,7 +23,7 @@ class Preprocessing(BaseModel): class MUSIC(BaseModel): - eigval_threshold: int + eigval_threshold: float window_size: int class Heatmap(BaseModel): diff --git a/where_fi/processing/aoa.py b/where_fi/processing/aoa.py index a70a5c1..70cb7fa 100644 --- a/where_fi/processing/aoa.py +++ b/where_fi/processing/aoa.py @@ -18,8 +18,8 @@ torch.set_default_device(device) class AoA: def __init__(self) -> None: self.historical_autocorr = torch.tensor([], dtype=torch.complex64) - self.N_subcarriers = -1 - self.N_rx = -1 + self.N_subcarriers = config.subcarriers + self.N_rx = config.antennas.count self.timestamp = datetime.now() pass @@ -84,7 +84,7 @@ class AoA: * np.pi * config.central_freq_hz * config.antennas.spacing - * (1 - torch.cos(theta)) + * (torch.sin(theta)) / 299_792_458 ) assert omega_t.shape == phi_theta.shape == (N,) @@ -133,7 +133,7 @@ class AoA: logger.debug(f"Eigenvalues: {eigvals}") E_n = eigvecs[:, torch.abs(eigvals) < config.music.eigval_threshold] - logger.debug(f"Signal subspace: {E_n.shape}") + logger.info(f"Signal subspace: {E_n.shape}") steering = torch.unsqueeze(self.steering_vector(theta, tof), dim=-1) steering_h = torch.conj(steering).permute(0, 2, 1)