Skip to content

Commit

Permalink
changes to support the new Sis class
Browse files Browse the repository at this point in the history
  • Loading branch information
giumas committed Apr 10, 2021
1 parent f5807ae commit 5d5f385
Show file tree
Hide file tree
Showing 18 changed files with 234 additions and 593 deletions.
32 changes: 0 additions & 32 deletions examples/soundspeed/listener/ex_sis5.py

This file was deleted.

2 changes: 1 addition & 1 deletion examples/soundspeed/server/ex_server.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
logger = logging.getLogger(__name__)

lib = SoundSpeedLibrary()
lib.listen_sis4()
lib.listen_sis()
time.sleep(3) # for SIS emulator

server = Server(prj=lib)
Expand Down
1 change: 0 additions & 1 deletion hyo2/soundspeed/base/callbacks/abstract_callbacks.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ class GeneralAbstractCallbacks(metaclass=ABCMeta):

def __init__(self) -> None:
self.sis_listener = None
self.kctrl_listener = None

@abstractmethod
def ask_number(self, title: Optional[str] = "", msg: Optional[str] = "Enter number", default: Optional[float] = 0.0,
Expand Down
4 changes: 4 additions & 0 deletions hyo2/soundspeed/base/setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,10 @@ def __init__(self, release_folder, use_setup_name=None):
self.release_folder = release_folder
self.load_from_db()

@property
def use_sis(self) -> bool:
return self.use_sis4 or self.use_sis5

@property
def db(self):
"""Usually the data_folder is set when the project is instantiated, so this is safe"""
Expand Down
22 changes: 4 additions & 18 deletions hyo2/soundspeed/client/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -103,30 +103,16 @@ def _transmit(self, tx_data: Union[bytes, str]) -> bool:
sock_out.close()
return True

def request_profile_from_sis4(self, prj: 'SoundSpeedLibrary') -> None:
if self.protocol != "SIS":
def request_profile_from_sis(self, prj: 'SoundSpeedLibrary') -> None:
if self.protocol not in ["SIS", "KCTRL"]:
return

prj.listeners.sis4.request_cur_profile(ip=self.ip, port=self.port)
prj.listeners.sis.request_cur_profile(ip=self.ip, port=self.port)
wait = prj.setup.rx_max_wait_time
count = 0
quantum = 2
logger.info("Waiting ..")
while (count < wait) and (not prj.listeners.sis4.ssp):
time.sleep(quantum)
count += quantum
logger.info(".. %s sec" % count)

def request_profile_from_sis5(self, prj: 'SoundSpeedLibrary') -> None:
if self.protocol != "KCTRL":
return

prj.listeners.sis5.request_cur_profile(ip=self.ip, port=self.port)
wait = prj.setup.rx_max_wait_time
count = 0
quantum = 2
logger.info("Waiting ..")
while (count < wait) and (not prj.listeners.sis5.svp):
while (count < wait) and (not prj.listeners.sis.ssp):
time.sleep(quantum)
count += quantum
logger.info(".. %s sec" % count)
38 changes: 8 additions & 30 deletions hyo2/soundspeed/client/clientlist.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import numpy as np
import time
import logging
from typing import TYPE_CHECKING, Union
from typing import TYPE_CHECKING

from hyo2.soundspeed.client.client import Client
if TYPE_CHECKING:
Expand Down Expand Up @@ -31,10 +31,8 @@ def transmit_ssp(self, prj: 'SoundSpeedLibrary', server_mode: bool = False):
for client in self.clients:

# clean previously received profile from SIS
if client.protocol == "SIS":
prj.listeners.sis4.ssp = None
elif client.protocol == "KCTRL":
prj.listeners.sis5.svp = None
if client.protocol in ["SIS", "KCTRL"]:
prj.listeners.sis.ssp = None

prj.progress.add(prog_quantum)

Expand Down Expand Up @@ -62,7 +60,7 @@ def transmit_ssp(self, prj: 'SoundSpeedLibrary', server_mode: bool = False):
wait_max = prj.setup.rx_max_wait_time
# For multiple SIS clients, make sure the client IP match with the sender IP.
while True:
if (wait > wait_max) or (prj.listeners.sis4.ssp is not None) or (prj.listeners.sis5.svp is not None):
if (wait > wait_max) or (prj.listeners.sis.ssp is not None):
break

time.sleep(1)
Expand All @@ -74,17 +72,17 @@ def transmit_ssp(self, prj: 'SoundSpeedLibrary', server_mode: bool = False):
logger.info("canceled by user")
wait = wait_max

if (client.protocol == "SIS") and prj.listeners.sis4.ssp:
if client.protocol in ["SIS", "KCTRL"] and prj.listeners.sis.ssp:
# The KM .all SVP datagrams have a bug in their time reporting and
# have a 100 second granularity so can't compare times
# to ensure it's the same profile. Comparing the sound speeds instead
d_tx = prj.cur.sis.depth[prj.cur.sis_thinned]
s_tx = prj.cur.sis.speed[prj.cur.sis_thinned]
# print(d_tx, s_tx)
s_rx = np.interp(d_tx, prj.listeners.sis4.ssp.depth, prj.listeners.sis4.ssp.speed)
s_rx = np.interp(d_tx, prj.listeners.sis.ssp.depth, prj.listeners.sis.ssp.speed)
max_diff = max(abs(s_tx - s_rx))
if max_diff < 0.2:
self.last_tx_time = prj.listeners.sis4.ssp.acquisition_time
self.last_tx_time = prj.listeners.sis.ssp.acquisition_time
logger.debug("reception confirmed: %s" % self.last_tx_time.strftime("%d/%m/%Y, %H:%M:%S"))
if not server_mode:
prj.cb.msg_tx_sis_confirmed(name=client.name)
Expand All @@ -96,30 +94,10 @@ def transmit_ssp(self, prj: 'SoundSpeedLibrary', server_mode: bool = False):
success = False
continue

elif (client.protocol == "KCTRL") and prj.listeners.sis5.svp:
# Comparing the sound speeds instead
d_tx = prj.cur.sis.depth[prj.cur.sis_thinned]
s_tx = prj.cur.sis.speed[prj.cur.sis_thinned]
# print(d_tx, s_tx)
s_rx = np.interp(d_tx, prj.listeners.sis5.svp.depth, prj.listeners.sis5.svp.speed)
max_diff = max(abs(s_tx - s_rx))
if max_diff < 0.2:
self.last_tx_time = prj.listeners.sis5.svp.acquisition_time
logger.debug("reception confirmed: %s" % self.last_tx_time.strftime("%d/%m/%Y, %H:%M:%S"))
if not server_mode:
prj.cb.msg_tx_sis_confirmed(name=client.name)
continue
else:
logger.info("casts differ by %.2f m/s" % max_diff)
if not server_mode:
prj.cb.msg_tx_sis_not_confirmed(name=client.name, port=prj.setup.sis5_listen_port)
success = False
continue

else:
logger.warning("reception NOT confirmed: unable to catch the back datagram")
if not server_mode:
prj.cb.msg_tx_sis_not_confirmed(name=client.name, port=prj.setup.sis5_listen_port)
prj.cb.msg_tx_sis_not_confirmed(name=client.name, port=prj.setup.sis_listen_port)
success = False

prj.progress.end()
Expand Down
3 changes: 1 addition & 2 deletions hyo2/soundspeed/formats/kmall.py
Original file line number Diff line number Diff line change
Expand Up @@ -118,8 +118,7 @@ def __init__(self, data, debug: bool = False):
# logger.debug('TSS: %s m/s' % (self.tss, ))
z_water_level_re_ref_point_m = ping_info[38]
# logger.debug('RP-WL distance: %s m' % (z_water_level_re_ref_point_m, ))
# TODO: change the semantic for this measure
self.transducer_draft = z_water_level_re_ref_point_m
self.transducer_depth = z_water_level_re_ref_point_m
# vrp_latitude = ping_info[45]
# vrp_longitude = ping_info[46]
# logger.debug('VRP pos: %s, %s' % (vrp_latitude, vrp_longitude))
Expand Down
74 changes: 29 additions & 45 deletions hyo2/soundspeed/listener/listeners.py
Original file line number Diff line number Diff line change
@@ -1,115 +1,99 @@
import time
import logging
from typing import TYPE_CHECKING

from hyo2.soundspeed.listener.sis.sis4 import Sis4
from hyo2.soundspeed.listener.sis.sis5 import Sis5
from hyo2.soundspeed.listener.sis.sis import Sis
from hyo2.soundspeed.listener.sippican.sippican import Sippican
from hyo2.soundspeed.listener.mvp.mvp import Mvp
if TYPE_CHECKING:
from hyo2.soundspeed.soundspeed import SoundSpeedLibrary

logger = logging.getLogger(__name__)


class Listeners:
"""A collection of listening processes"""

def __init__(self, prj):
def __init__(self, prj: 'SoundSpeedLibrary'):
super(Listeners, self).__init__()
# data folder
self.prj = prj

# available listeners
self.sis4 = Sis4(port=self.prj.setup.sis_listen_port, datagrams=[0x50, 0x52, 0x55, 0x58],
timeout=self.prj.setup.sis_listen_timeout)
self.sis5 = Sis5(ip="localhost", port=self.prj.setup.sis_listen_port,
datagrams=[b'#MRZ', b'#SPO', b'#SVP'],
timeout=self.prj.setup.sis_listen_timeout)
self.sis = Sis(port=self.prj.setup.sis_listen_port,
timeout=self.prj.setup.sis_listen_timeout,
use_sis5=self.prj.setup.use_sis5)
self.sippican = Sippican(port=self.prj.setup.sippican_listen_port, prj=prj)
self.mvp = Mvp(port=self.prj.setup.mvp_listen_port, prj=prj)

@property
def sippican_to_process(self):
def sippican_to_process(self) -> bool:
return self.sippican.new_ssp.is_set()

@sippican_to_process.setter
def sippican_to_process(self, to_process):
def sippican_to_process(self, to_process: bool) -> None:
if not to_process:
self.sippican.new_ssp.clear()

@property
def mvp_to_process(self):
def mvp_to_process(self) -> bool:
return self.mvp.new_ssp.is_set()

@mvp_to_process.setter
def mvp_to_process(self, to_process):
def mvp_to_process(self, to_process: bool) -> None:
if not to_process:
self.mvp.new_ssp.clear()

def listen_sis4(self):
if not self.sis4.is_alive():
self.sis4.start()
def listen_sis(self) -> bool:
if not self.sis.is_alive():
self.sis.start()
time.sleep(0.1)
logger.debug("start")
return self.sis4.is_alive()
return self.sis.is_alive()

def stop_listen_sis4(self):
if self.sis4.is_alive():
self.sis4.stop()
self.sis4.join(2)
def stop_listen_sis(self) -> bool:
if self.sis.is_alive():
self.sis.stop()
self.sis.join(2)
logger.debug("stop")
return not self.sis4.is_alive()
return not self.sis.is_alive()

def listen_sis5(self):
if not self.sis5.is_alive():
self.sis5.start()
time.sleep(0.1)
logger.debug("start")
return self.sis5.is_alive()

def stop_listen_sis5(self):
if self.sis5.is_alive():
self.sis5.stop()
self.sis5.join(2)
logger.debug("stop")
return not self.sis5.is_alive()

def listen_sippican(self):
def listen_sippican(self) -> bool:
if not self.sippican.is_alive():
self.sippican.start()
time.sleep(0.1)
logger.debug("start")
return self.sippican.is_alive()

def stop_listen_sippican(self):
def stop_listen_sippican(self) -> bool:
if self.sippican.is_alive():
self.sippican.stop()
self.sippican.join(2)
logger.debug("stop")
return not self.sippican.is_alive()

def listen_mvp(self):
def listen_mvp(self) -> bool:
if not self.mvp.is_alive():
self.mvp.start()
time.sleep(0.1)
logger.debug("start")
return self.mvp.is_alive()

def stop_listen_mvp(self):
def stop_listen_mvp(self) -> bool:
if self.mvp.is_alive():
self.mvp.stop()
self.mvp.join(2)
logger.debug("stop")
return not self.mvp.is_alive()

def stop(self):
self.stop_listen_sis4()
self.stop_listen_sis5()
def stop(self) -> None:
self.stop_listen_sis()
self.stop_listen_sippican()
self.stop_listen_mvp()

def __repr__(self):
def __repr__(self) -> str:
msg = "<Listeners>\n"
msg += "%s" % self.sis4
msg += "%s" % self.sis5
msg += "%s" % self.sis
msg += "%s" % self.sippican
msg += "%s" % self.mvp
return msg
Loading

0 comments on commit 5d5f385

Please sign in to comment.