in sev state

This commit is contained in:
2026-08-14 08:24:33 -06:00
parent e06b429db9
commit 3d26b66490
27 changed files with 2578 additions and 108 deletions
+62 -22
View File
@@ -1,12 +1,17 @@
#include "storage_task.h"
#include <esp_system.h>
#include "../storage/storage_config.h"
StorageTask::StorageTask(SDManager& manager, StorageState& state)
StorageTask::StorageTask(SDManager& manager, StorageState& state,
DataLogger& logger, RecordingController& recorder)
:
storage(manager),
storageState(state),
logger(logger),
recorder(recorder),
taskHandle(nullptr)
{
}
@@ -16,8 +21,7 @@ void StorageTask::start()
{
// Dedicated task on core 0 so SD card work never blocks the services
// running on core 1 (SystemTask / DiagnosticsTask). The 8 KB stack is
// sized for the recursive boot-time file listing; the eventual
// producer/consumer logging loop will also live here.
// sized for the recursive boot-time file listing and the logger loop.
xTaskCreatePinnedToCore(
taskEntry,
"StorageTask",
@@ -50,8 +54,7 @@ void StorageTask::run()
// Retry the mount until it succeeds. This keeps the card dead-pin-capable:
// reseating the card, fixing a wire, or powering the module will bring it
// up without rebooting the Hub. (The SD init handshake runs at 400 kHz, so
// a failure here is wiring/power/seating/pull-up related, not speed.)
// up without rebooting the Hub.
while (!storage.begin())
{
Serial.println("[Storage] SD card mount FAILED.");
@@ -67,32 +70,69 @@ void StorageTask::run()
storage.printCardInfo();
storage.listFiles();
// Initial write-speed estimate for the dashboard.
storage.writeTestFile();
// Initial write-speed estimate for the dashboard until real logging data
// is available.
storageState.setWriteSpeedBps(storage.measureWriteSpeed());
storageState.setCapacity(storage.totalBytes(), storage.usedBytes());
TickType_t lastWake =
xTaskGetTickCount();
if (!logger.begin(storage.fs()))
{
Serial.println("[Storage] DataLogger failed to initialize, no recording");
}
uint32_t lastSpeedMeasure = millis();
Serial.println("[Storage] Waiting for recording sessions...");
while (true)
{
// Periodically re-estimate write speed and refresh capacity so the
// dashboard stays current. An interval of 0 disables re-measuring.
if (STORAGE_SPEED_MEASURE_INTERVAL_MS != 0 &&
millis() - lastSpeedMeasure >= STORAGE_SPEED_MEASURE_INTERVAL_MS)
// Open a WAV session as soon as recording starts; finalize and close
// it once recording has stopped and the queue has drained.
if (recorder.isRecording() && !logger.hasSession())
{
lastSpeedMeasure = millis();
storageState.setWriteSpeedBps(storage.measureWriteSpeed());
storageState.setCapacity(storage.totalBytes(), storage.usedBytes());
if (!logger.openSession())
{
Serial.println("[Storage] Could not open session (card full?)");
}
}
// Future integration point: a producer/consumer queue will feed
// audio data here to be flushed to the card.
vTaskDelayUntil(
&lastWake,
pdMS_TO_TICKS(1000)
);
if (!recorder.isRecording() && logger.hasSession() && logger.isEmpty())
{
logger.closeSession();
}
// Block for the next filled chunk (100 ms so the session lifecycle and
// stats stay responsive even when idle).
AudioChunk* chunk = logger.nextChunk(pdMS_TO_TICKS(100));
if (chunk != nullptr)
{
if (!logger.writeChunk(chunk))
{
// design.md: SD failure is fatal - halt with a message. Reboot
// cleanly so the Hub comes back (a dead card simply loops in
// the mount retry at the top of this task).
Serial.println("[Storage] FATAL: card write failed, "
"halting storage.");
vTaskDelay(pdMS_TO_TICKS(100));
esp_restart();
}
logger.releaseChunk(chunk);
}
logger.rotateIfNeeded();
// Publish real logging stats to the dashboard.
storageState.setWriteSpeedBps(logger.writeSpeedBps());
storageState.setLoggingStats(logger.droppedChunks(), logger.bytesWritten());
storageState.setCapacity(storage.totalBytes(), storage.usedBytes());
// Yield a tick even while saturated: when the SD card cannot keep up
// the filled queue never empties, so nextChunk() returns instantly and
// this task would otherwise starve the IDLE0 task, tripping the task
// watchdog and aborting the Hub. The 1 ms per chunk costs <2% of the
// write budget and the overflow path already drops chunks by design.
vTaskDelay(pdMS_TO_TICKS(1));
}
}
+6 -1
View File
@@ -3,13 +3,16 @@
#include <Arduino.h>
#include "../core/storage_state.h"
#include "../core/node_registry.h"
#include "../storage/sd_manager.h"
#include "../storage/data_logger.h"
class StorageTask
{
public:
StorageTask(SDManager& manager, StorageState& state);
StorageTask(SDManager& manager, StorageState& state,
DataLogger& logger, RecordingController& recorder);
void start();
@@ -19,6 +22,8 @@ private:
SDManager& storage;
StorageState& storageState;
DataLogger& logger;
RecordingController& recorder;
TaskHandle_t taskHandle = nullptr;
};
+3 -1
View File
@@ -22,10 +22,12 @@ taskHandle(nullptr)
// );
void SystemTask::start()
{
// 8 KB stack: the services now include UDP handling (discovery/collection)
// which needs a few KB of stack for packet buffers.
xTaskCreatePinnedToCore(
taskEntry,
"SystemTask",
4096,
8192,
this,
2,
&taskHandle,