summaryrefslogtreecommitdiff
path: root/flash.c
diff options
context:
space:
mode:
Diffstat (limited to 'flash.c')
-rw-r--r--flash.c57
1 files changed, 56 insertions, 1 deletions
diff --git a/flash.c b/flash.c
index db5a870..a46a511 100644
--- a/flash.c
+++ b/flash.c
@@ -1,6 +1,7 @@
#include "globals.h"
#include "lcd.h"
#include "version.h"
+#include "flash.h"
#include <stdint.h>
#include <stdio.h>
#include <stdbool.h>
@@ -28,6 +29,16 @@
#define PERSIST_ERR_COULDNTWRITE 9
#define PERSIST_ERR_COUNDNTOPENFILE 10
+typedef struct {
+ FlashStruct *mem;
+ int addr;
+ int numbytes;
+} userflashjob;
+
+static bool alive = true;
+static GThread* userflashwritethread;
+static GAsyncQueue* userflashwritequeue;
+
// crc32 routine
static uint32_t crc32(uint8_t* buf, int count)
@@ -287,7 +298,7 @@ static int readUserBlock(FlashStruct *mem)
return 0;
}
-void writeUserBlock(FlashStruct *mem, int addr, int numbytes)
+void writeUserBlockNow(FlashStruct *mem, int addr, int numbytes)
{
// *** There is a potential issue here.. if the mainfile is corrupt ***
// *** and this gets called before readUserBlock then the ***
@@ -327,6 +338,19 @@ void writeUserBlock(FlashStruct *mem, int addr, int numbytes)
g_static_mutex_unlock (&mutex);
}
+void writeUserBlock(FlashStruct *mem, int addr, int numbytes) {
+ if (alive) {
+ userflashjob* job = g_malloc(sizeof(userflashjob));
+ job->mem = mem;
+ job->addr = addr;
+ job->numbytes = numbytes;
+ g_async_queue_push(userflashwritequeue, job);
+ while (g_async_queue_length(userflashwritequeue) > 1) {
+ // spin
+ }
+ }
+}
+
static void initFlashValues(FlashStruct *mem)
{
@@ -774,9 +798,35 @@ static void initFlashValues(FlashStruct *mem)
}
+static gpointer userflashwritethreadfunc(gpointer data) {
+
+ printf("userflash write thread start\n");
+ while (alive || g_async_queue_length(userflashwritequeue) > 0) { // make sure the last job in the queue gets written
+ GTimeVal whentotimeout;
+ g_get_current_time(&whentotimeout);
+ g_time_val_add(&whentotimeout, 250 * 1000);
+ userflashjob* job = (userflashjob*) g_async_queue_timed_pop(userflashwritequeue, &whentotimeout);
+ if(job != NULL){
+ // process job
+ writeUserBlockNow(job->mem, job->addr, job->numbytes);
+ g_free(job);
+ }
+ }
+ printf("userflash write thread stop\n");
+
+ return NULL ;
+}
+
+void startFlashWriterThread(){
+ alive= true;
+ userflashwritequeue = g_async_queue_new();
+ userflashwritethread = g_thread_create(userflashwritethreadfunc, NULL, true, NULL);
+}
void initFlash(FlashStruct *mem, gboolean reset_to_defaults, int starting_location)
{
+ startFlashWriterThread();
+
int read_size = readUserBlock(mem);
if ( (read_size == 0) ||
@@ -806,9 +856,14 @@ void initFlash(FlashStruct *mem, gboolean reset_to_defaults, int starting_locati
}
}
+void stopFlashWriterThread(){
+ alive = false;
+ g_thread_join(userflashwritethread); // block until the write thread is totally finished.
+}
void fixFlash(FlashStruct *mem)
{
+
int i, fix_initial_constants;
float composite_min_burst_time[max_channels];