Ejemplo n.º 1
0
def altimeter_reading_loop(configuration: Configuration,
                           altimeter_value: AtomicValue):
    """Continually read the altimeter and set it to the atomic var"""
    try:
        bmp = init_altimeter(configuration)
        while bmp:
            try:
                altimeter_value.update(bmp._read())  # pylint: disable=protected-access
            except Exception as ex:  # pylint: disable=broad-except
                handle_exception("Altimeter reading failure", ex)
    except Exception as ex:  # pylint: disable=broad-except
        handle_exception("Altimeter setup failure", ex)
Ejemplo n.º 2
0
class BufferSessionStore:
    """Data capture session storage engine"""
    def __init__(self,
                 configuration: Configuration,
                 sql_file: str = "sessionstore.sqlite3"):
        """Create a new session store"""
        self.buffer = SafeBuffer()
        self.current_session = AtomicValue()
        self.output_dir = configuration.get("output_directory")
        self.sql_file = sql_file
        self.connection = None
        self.cursor = None

    def initialize(self):
        """Initialize the store. (Pins the SQLite connection to the calling thread)"""
        self.connection = sqlite3.connect(
            path.join(self.output_dir, self.sql_file))
        self.cursor = self.connection.cursor()
        self.cursor.execute(
            "CREATE TABLE IF NOT EXISTS sessions (timestamp NUMBER UNIQUE NOT NULL)"
        )
        self.connection.commit()
        self.create_new_session()

    def get_sessions(self) -> List[float]:
        """Get a list of saved sessions"""
        self.cursor.execute(
            "SELECT timestamp FROM sessions WHERE timestamp != ? ORDER BY timestamp DESC",
            (self.current_session.get_value(), ),
        )
        return [row[0] for row in self.cursor.fetchall()]

    def create_new_session(self) -> float:
        """Create and save a new session"""
        timestamp = int(time.time())
        self.current_session.update(timestamp)
        self.cursor.execute("INSERT INTO sessions (timestamp) VALUES (?)",
                            (timestamp, ))
        self.connection.commit()
        self.buffer.purge()
        return timestamp

    def load_session(self, session) -> List[List[float]]:
        """Load data from a given session"""
        with open(self.data_path_for_session(session), "r") as csvfile:
            reader = csv.reader(csvfile)
            return [[float(v) for v in r] for r in reader]

    def data_path_for_session(self, session=None) -> str:
        """Get the path to the given session's data"""
        if not session:
            session = self.current_session.get_value()
        return path.join(self.output_dir, f"telemetry_log_{session}.csv")
Ejemplo n.º 3
0
def take_gps_reading(sio, gps_value: AtomicValue) -> bool:
    """Grab the most recent data from GPS feed"""
    line = sio.readline()
    if line[0:6] == "$GPGGA":
        gps = pynmea2.parse(line)
        gps_value.update((
            gps.latitude if gps else 0.0,
            gps.longitude if gps else 0.0,
            gps.gps_qual if gps else 0.0,
            float(gps.num_sats) if gps else 0.0,
        ))
        return True
    return False
Ejemplo n.º 4
0
def magnetometer_accelerometer_reading_loop(
        configuration: Configuration,
        magnetometer_accelerometer_value: AtomicValue):
    """Continually read the accelerometer/magnetometer and set it to the atomic var"""
    try:
        mag, accel = init_magnetometer_accelerometer(configuration)
        while mag and accel:
            try:
                magnetometer_accelerometer_value.update(
                    (*accel.acceleration, *mag.magnetic))
            except Exception as ex:  # pylint: disable=broad-except
                handle_exception("Magnetometer/Accelerometer reading failure",
                                 ex)
    except Exception as ex:  # pylint: disable=broad-except
        handle_exception("Magnetometer/Accelerometer setup failure", ex)
Ejemplo n.º 5
0
def take_gps_reading(sio, gps_value: AtomicValue) -> bool:
    """Grab the most recent data from GPS feed"""
    line = sio.readline()
    gps = pynmea2.parse(line)
    if isinstance(gps, pynmea2.types.talker.GGA):
        gps_value.update(
            (
                gps.latitude if gps else 0.0,
                gps.longitude if gps else 0.0,
                float(gps.gps_qual) if gps else 0.0,
                float(gps.num_sats) if gps else 0.0,
            )
        )
        return True
    return False
Ejemplo n.º 6
0
def test_write_sensor_log():
    start_time = time.time()
    outfile = io.StringIO("")
    data_queue = Queue()
    while data_queue.qsize() < 100:
        data_queue.put((random.random(), random.random(), random.random()))
    continue_running = AtomicValue(True)
    thread = Thread(
        target=write_sensor_log,
        args=(start_time, outfile, data_queue, continue_running,
              continue_running),
    )
    thread.start()
    time.sleep(5)
    continue_running.update(False)
    thread.join()
    contents = outfile.getvalue()
    assert contents
    assert len(contents.split("\n")) > 0
Ejemplo n.º 7
0
def main():
    """Inboard data capture and transmission script"""

    # Load up the system configuration
    configuration = Configuration(os.getenv("AIR_CONFIG_FILE", None),
                                  Configuration.default_air_configuration)

    # Queue to manage data synchronization between sensor reading, transmission, and data logging
    data_queue = Queue(1000)

    # Timestamp to use for log files and log saving cutoff
    start_time = time.time()

    # Thread safe place to store altitude reading
    current_readings = AtomicBuffer(50)

    # Holds the most recent GPS data
    gps_value = AtomicValue((0.0, 0.0, 0.0, 0.0))

    # pcnt counter to runtime limit
    pcnt_to_limit = AtomicValue(0.0)

    # Thread safe place to store continue value
    continue_running = AtomicValue(True)

    # Thread safe place to store continue value
    continue_logging = AtomicValue(True)

    # Setup listener for reset button
    init_reset_button(configuration, continue_running)

    gps_thread = create_gps_thread(configuration, gps_value, continue_running)
    gps_thread.start()

    write_thread = Thread(
        target=sensor_log_writing_loop,
        args=(
            configuration,
            start_time,
            data_queue,
            continue_running,
            continue_logging,
        ),
        daemon=True,
    )
    write_thread.start()

    camera_thread_handle = Thread(
        target=camera_thread,
        args=(configuration, start_time, continue_running, continue_logging),
        daemon=True,
    )
    camera_thread_handle.start()

    transmitter_thread_handle = Thread(
        target=transmitter_thread,
        args=(
            configuration,
            start_time,
            current_readings,
            pcnt_to_limit,
            continue_running,
        ),
        daemon=True,
    )
    transmitter_thread_handle.start()

    sensor_reading_thread = Thread(
        target=sensor_reading_loop,
        args=(
            configuration,
            start_time,
            data_queue,
            current_readings,
            gps_value,
            continue_running,
        ),
        daemon=True,
    )
    sensor_reading_thread.start()

    runtime_limit = configuration.get("runtime_limit")
    while continue_running.get_value(
    ) and time.time() - start_time <= runtime_limit:
        pcnt_to_limit.update((time.time() - start_time) / runtime_limit)
        time.sleep(1)
    logging.info("Stopping write activities")
    continue_logging.update(False)

    write_thread.join()
    camera_thread_handle.join()
    pcnt_to_limit.update(1)

    logging.info("Write activities ended")

    gps_thread.join()
    transmitter_thread_handle.join()
    sensor_reading_thread.join()
Ejemplo n.º 8
0
def main():
    """Inboard data capture and transmission script"""

    # Load up the system configuration
    configuration = Configuration(
        os.getenv("AIR_CONFIG_FILE", None), Configuration.default_air_configuration
    )

    # Queue to manage data synchronization between sensor reading, transmission, and data logging
    data_queue = Queue()

    # Timestamp to use for log files and log saving cutoff
    start_time = time.time()

    # Thread safe place to store altitude reading
    current_reading = AtomicValue()

    # Holds the most recent GPS data
    gps_value = AtomicValue((0.0, 0.0, 0.0, 0.0))

    altimeter_value = AtomicValue()
    altimeter_value.update((0.0, 0.0))

    magnetometer_accelerometer_value = AtomicValue()
    magnetometer_accelerometer_value.update((0.0, 0.0, 0.0, 0.0, 0.0, 0.0))

    gps_thread = create_gps_thread(configuration, gps_value)
    gps_thread.start()

    write_thread = Thread(
        target=sensor_log_writing_loop,
        args=(configuration, start_time, data_queue),
        daemon=True,
    )
    write_thread.start()

    camera_thread_handle = Thread(
        target=camera_thread,
        args=(configuration, start_time),
        daemon=True,
    )
    camera_thread_handle.start()

    transmitter_thread_handle = Thread(
        target=transmitter_thread,
        args=(
            configuration,
            start_time,
            current_reading,
        ),
        daemon=True,
    )
    transmitter_thread_handle.start()

    altimeter_thread = Thread(
        target=altimeter_reading_loop, args=(configuration, altimeter_value)
    )
    altimeter_thread.start()

    magnetometer_accelerometer_thread = Thread(
        target=magnetometer_accelerometer_reading_loop,
        args=(configuration, magnetometer_accelerometer_value),
    )
    magnetometer_accelerometer_thread.start()

    sensor_reading_loop(
        start_time,
        data_queue,
        current_reading,
        gps_value,
        altimeter_value,
        magnetometer_accelerometer_value,
    )
Ejemplo n.º 9
0
def test_atomic_value():
    raw_value = random.random()
    value = AtomicValue(raw_value)
    assert raw_value == value.get_value()
    value.update(random.random())
    assert raw_value != value.get_value()