send tensor over queue instead of aoa object

This commit is contained in:
Christos Falas 2025-01-02 11:27:10 +00:00
parent efe8923c51
commit 81c7b04fe7
No known key found for this signature in database
5 changed files with 25 additions and 20 deletions

View File

@ -32,12 +32,10 @@ receivers = [
# Start injecting CSI frames # Start injecting CSI frames
transmitter = ingest.FeitTransmitter() transmitter = ingest.FeitTransmitter()
webapp_queue: "mp.Queue[aoa.AoA]" = manager.Queue(config.SAMPLE_RATE) webapp_queue: "mp.Queue[aoa.AoA]" = mp.Queue(config.SAMPLE_RATE)
visualise.aoa_queue = webapp_queue
# Start webapp in background process # Start webapp in background process
webapp = mp.Process(target=visualise.start) webapp = mp.Process(target=visualise.start, args=(webapp_queue,))
webapp.start() webapp.start()
receiver_processes = [ receiver_processes = [

View File

@ -48,7 +48,7 @@ class AoA:
return H_sm return H_sm
def update(self, data: torch.Tensor): def update(self, data: torch.Tensor) -> torch.Tensor:
self.timestamp = datetime.now() self.timestamp = datetime.now()
H_sm = self.smooth(data) H_sm = self.smooth(data)
@ -74,9 +74,10 @@ class AoA:
# and the largest span the signal subspace. # and the largest span the signal subspace.
eigvals, eigvecs = torch.linalg.eigh(R) eigvals, eigvecs = torch.linalg.eigh(R)
logging.debug(f"Eigenvalues: {eigvals}") logging.debug(f"Eigenvalues: {eigvals}")
self.E_n = eigvecs[:, torch.abs(eigvals) < config.EIGVAL_THRESHOLD] return eigvecs[:, torch.abs(eigvals) < config.EIGVAL_THRESHOLD]
def steering_vector(self, theta: float, tof: float): @staticmethod
def steering_vector(theta: float, tof: float):
omega_t = torch.exp( omega_t = torch.exp(
torch.tensor([-2j * torch.pi * config.DELTA_F * tof], dtype=torch.complex64) torch.tensor([-2j * torch.pi * config.DELTA_F * tof], dtype=torch.complex64)
) )
@ -97,24 +98,23 @@ class AoA:
omega_t = torch.unsqueeze(omega_t, dim=-1) omega_t = torch.unsqueeze(omega_t, dim=-1)
phi_theta = torch.unsqueeze(phi_theta, dim=-1) phi_theta = torch.unsqueeze(phi_theta, dim=-1)
antenna_v = omega_t ** torch.arange(self.N_subcarriers // 2) antenna_v = omega_t ** torch.arange((config.N_SUBCARRIERS - 2) // 2)
phis = phi_theta ** torch.arange(self.N_rx // 2) phis = phi_theta ** torch.arange((len(config.ANTENNA_ORDER)) // 2)
antenna_v = torch.unsqueeze(antenna_v, dim=-1) antenna_v = torch.unsqueeze(antenna_v, dim=-1)
print(antenna_v.shape, phis.shape) print(antenna_v.shape, phis.shape)
steering = antenna_v[0] * phis steering = antenna_v[0] * phis
print(steering.shape) print(steering.shape)
return steering.T.reshape(-1) return steering.T.reshape(-1)
def evaluate(self, theta: float, tof: float): @staticmethod
def evaluate(E_n: torch.Tensor, theta: float, tof: float):
try: try:
steering = self.steering_vector(theta, tof) steering = AoA.steering_vector(theta, tof)
steering_h = torch.conj(steering).T steering_h = torch.conj(steering).T
except Exception as e: except Exception as e:
logger.exception(e) logger.exception(e)
return 0 return 0
assert isinstance(self.E_n, torch.Tensor)
E_n = self.E_n
E_n_H = torch.conj(E_n).T E_n_H = torch.conj(E_n).T
c = 1 / (0.001 + (steering_h @ E_n @ E_n_H @ steering)) c = 1 / (0.001 + (steering_h @ E_n @ E_n_H @ steering))
return torch.abs(c.real) return torch.abs(c.real)

View File

@ -34,3 +34,5 @@ C = 299_792_458 # m/s
VISUALISE_RAW = False VISUALISE_RAW = False
HEATMAP_FPS = 10 HEATMAP_FPS = 10
N_SUBCARRIERS = 56

View File

@ -100,10 +100,10 @@ class CSIProcessor:
processed = preprocess.preprocess(all_data) processed = preprocess.preprocess(all_data)
processed_tensor = torch.tensor(processed, device=device) processed_tensor = torch.tensor(processed, device=device)
# visualise.add_data(all_data_tensor, processed) # visualise.add_data(all_data_tensor, processed)
aoa.update(processed_tensor) E_n = aoa.update(processed_tensor)
logger.info("Processed data") logger.info("Processed data")
if not webserver.full(): if not webserver.full():
webserver.put(aoa) webserver.put(E_n)
@staticmethod @staticmethod
def process_forever( def process_forever(

View File

@ -5,8 +5,10 @@ import numpy.typing as npt
from simple_websocket import Server from simple_websocket import Server
import time import time
from datetime import datetime from datetime import datetime
import multiprocessing as mp import torch.multiprocessing as mp
import torch
from functools import partial
import matplotlib.pyplot as plt import matplotlib.pyplot as plt
import io import io
import logging import logging
@ -92,7 +94,7 @@ def add_data(
del subscriber_settings[subscriber] del subscriber_settings[subscriber]
def make_heatmap(aoa: AoA, max_tof: float): def make_heatmap(aoa_E_n: torch.Tensor, max_tof: float):
logger.info(f"Making heatmap with aoa of {aoa.timestamp}") logger.info(f"Making heatmap with aoa of {aoa.timestamp}")
fig = plt.figure() fig = plt.figure()
ax = fig.add_axes([0, 0, 1, 1], polar=True) ax = fig.add_axes([0, 0, 1, 1], polar=True)
@ -101,7 +103,8 @@ def make_heatmap(aoa: AoA, max_tof: float):
R, Theta = np.meshgrid(r, theta) # Create a 2D grid of r and theta R, Theta = np.meshgrid(r, theta) # Create a 2D grid of r and theta
# Compute the function values # Compute the function values
Z = np.log(np.vectorize(aoa.evaluate)(Theta, R)) eval_func = partial(AoA.evaluate, aoa_E_n)
Z = np.log(np.vectorize(eval_func)(Theta, R))
ax.pcolormesh(Theta, R, Z, edgecolors="face") ax.pcolormesh(Theta, R, Z, edgecolors="face")
buf = io.BytesIO() buf = io.BytesIO()
@ -119,11 +122,11 @@ def gather_aoa(max_tof: float):
while True: while True:
while (datetime.now() - prev_frame).total_seconds() < 1 / config.HEATMAP_FPS: while (datetime.now() - prev_frame).total_seconds() < 1 / config.HEATMAP_FPS:
time.sleep(0.01) time.sleep(0.01)
while not aoa_queue.empty(): while not aoa_queue.empty():
logger.debug("Receiving from aoa pipe") logger.debug("Receiving from aoa pipe")
aoa = aoa_queue.get() aoa = aoa_queue.get()
prev_frame = datetime.now() prev_frame = datetime.now()
logger.debug(f"Generating heatmap of time {aoa.timestamp}")
buf = make_heatmap(aoa, max_tof) buf = make_heatmap(aoa, max_tof)
yield (b"--frame\r\nContent-Type: image/jpeg\r\n\r\n" + buf.read() + b"\r\n") yield (b"--frame\r\nContent-Type: image/jpeg\r\n\r\n" + buf.read() + b"\r\n")
buf.close() buf.close()
@ -141,5 +144,7 @@ def aoa_tof():
) )
def start(): def start(queue: "mp.Queue[torch.Tensor]"):
global aoa_queue
aoa_queue = queue
app.run(debug=True, use_reloader=False, host="0.0.0.0") app.run(debug=True, use_reloader=False, host="0.0.0.0")