diff --git a/Font5x7.c b/Font5x7.c index a69bcc7..87b9127 100644 --- a/Font5x7.c +++ b/Font5x7.c @@ -11,6 +11,7 @@ #define FONT_GET_DATA(ch) (&x5x7_bits[ch*7]) #define FONT_GET_WIDTH(ch) (8-x5x7_bits[ch*7]&7) +#define FONT_MAX_WIDTH 7 #define FONT_GET_HEIGHT 7 #define CHAR5x7_WIDTH_1px 0x07 diff --git a/Makefile b/Makefile index 73ebbd9..bd17844 100644 --- a/Makefile +++ b/Makefile @@ -100,9 +100,9 @@ include $(CHIBIOS)/os/hal/osal/rt/osal.mk include $(CHIBIOS)/os/rt/rt.mk include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v6m.mk # Other files (optional). -include $(CHIBIOS)/test/rt/test.mk +#include $(CHIBIOS)/test/rt/test.mk include $(CHIBIOS)/os/hal/lib/streams/streams.mk -include $(CHIBIOS)/os/various/shell/shell.mk +#include $(CHIBIOS)/os/various/shell/shell.mk # Define linker script file here #LDSCRIPT= $(STARTUPLD)/STM32F072xB.ld diff --git a/chconf.h b/chconf.h index 34e6afe..5e5ce40 100644 --- a/chconf.h +++ b/chconf.h @@ -156,7 +156,7 @@ * * @note The default is @p TRUE. */ -#define CH_CFG_USE_WAITEXIT TRUE +#define CH_CFG_USE_WAITEXIT FALSE /** * @brief Semaphores APIs. @@ -193,7 +193,7 @@ * @note The default is @p FALSE. * @note Requires @p CH_CFG_USE_MUTEXES. */ -#define CH_CFG_USE_MUTEXES_RECURSIVE TRUE +#define CH_CFG_USE_MUTEXES_RECURSIVE FALSE /** * @brief Conditional Variables APIs. @@ -221,7 +221,7 @@ * * @note The default is @p TRUE. */ -#define CH_CFG_USE_EVENTS TRUE +#define CH_CFG_USE_EVENTS FALSE /** * @brief Events Flags APIs with timeout. @@ -231,7 +231,7 @@ * @note The default is @p TRUE. * @note Requires @p CH_CFG_USE_EVENTS. */ -#define CH_CFG_USE_EVENTS_TIMEOUT TRUE +#define CH_CFG_USE_EVENTS_TIMEOUT FALSE /** * @brief Synchronous Messages APIs. diff --git a/chprintf.c b/chprintf.c index 39b4fc9..7906dc9 100644 --- a/chprintf.c +++ b/chprintf.c @@ -29,7 +29,7 @@ #include "hal.h" #include "chprintf.h" -#include "memstreams.h" +//#include "memstreams.h" #include // Enable [flags], support: @@ -56,7 +56,6 @@ static char smallPrefix[]= { 'm', 0x1d, 'n', 'p', 'f', 'a', 'z', 'y', #pragma pack(pop) -//86066 5116 11456 102622 190de build/ch.elf static char *long_to_string_with_divisor(char *p, uint32_t num, uint32_t radix, @@ -66,7 +65,7 @@ static char *long_to_string_with_divisor(char *p, // convert to string from end buffer to begin do { uint8_t c = num % radix; - num /= radix; + num /= radix; *--q = c + ((c > 9) ? ('A'-10) : '0'); }while((precision && --precision) || num); // copy string at begin @@ -106,7 +105,7 @@ static char *ulong_freq(char *p, uint32_t freq, uint32_t precision){ // freq = freq / 10; uint32_t c = freq; freq>>=1; - freq+=freq>>1; + freq+=freq>>1; freq+=freq>>4; freq+=freq>>8; freq+=freq>>16; // freq = 858993459*freq/1073741824 = freq * 0,799999999813735485076904296875 @@ -114,12 +113,12 @@ static char *ulong_freq(char *p, uint32_t freq, uint32_t precision){ c-= freq*10; // freq*10 = (freq*4+freq)*2 = ((freq<<2)+freq)<<1 while (c>=10) {freq++;c-=10;} #endif - *--q = c + '0'; - if (freq==0) - break; - // Add spaces, calculate prefix - if (format&1) {*--q = ' '; s++;} - format>>=1; + *--q = c + '0'; + if (freq==0) + break; + // Add spaces, calculate prefix + if (format&1) {*--q = ' '; s++;} + format>>=1; } while (1); s = bigPrefix[s]; @@ -147,7 +146,7 @@ static char *ulong_freq(char *p, uint32_t freq, uint32_t precision){ }while (--i); // Put pref (amd space before it if need) if (flag&FREQ_PREFIX_SPACE && s!=' ') - *p++ = ' '; + *p++ = ' '; *p++ = s; return p; } @@ -165,10 +164,10 @@ static char *ftoa(char *p, float num, uint32_t precision) { if (k>=multi){k-=multi;l++;} p = long_to_string_with_divisor(p, l, 10, 0); if (precision){ - *p++ = '.'; - p=long_to_string_with_divisor(p, k, 10, precision); + *p++ = '.'; + p=long_to_string_with_divisor(p, k, 10, precision); #ifndef CHPRINTF_FORCE_TRAILING_ZEROS - // remove zeros at end + // remove zeros at end while (p[-1]=='0') p--; if (p[-1]=='.') p--; #endif @@ -180,14 +179,14 @@ static char *ftoaS(char *p, float num, uint32_t precision) { char prefix=0; char *ptr; if (num > 1000.0){ - for (ptr = bigPrefix+1; *ptr && num > 1000.0; num/=1000, ptr++) - ; - prefix = ptr[-1]; + for (ptr = bigPrefix+1; *ptr && num > 1000.0; num/=1000, ptr++) + ; + prefix = ptr[-1]; } else if (num < 1){ - for (ptr = smallPrefix; *ptr && num < 1.0; num*=1000, ptr++) - ; - prefix = num > 1e-3 ? ptr[-1] : 0; + for (ptr = smallPrefix; *ptr && num < 1.0; num*=1000, ptr++) + ; + prefix = num > 1e-3 ? ptr[-1] : 0; } // Auto set prescision uint32_t l = num; @@ -279,13 +278,13 @@ int chvprintf(BaseSequentialStream *chp, const char *fmt, va_list ap) { else if (*fmt == '+') state|=POSITIVE; else if (*fmt == '0') - state|=PAD_ZERO; + state|=PAD_ZERO; #ifdef CHPRINTF_USE_SPACE_FLAG else if (*fmt == ' ') - state|=PLUS_SPACE; + state|=PLUS_SPACE; #endif else - break; + break; fmt++; } // Get [width] - The Width field specifies a minimum number of characters to output @@ -314,7 +313,7 @@ int chvprintf(BaseSequentialStream *chp, const char *fmt, va_list ap) { } } else - state|=DEFAULT_PRESCISION; + state|=DEFAULT_PRESCISION; //Get [length] /* if (c == 'l' || c == 'L') { @@ -347,42 +346,42 @@ int chvprintf(BaseSequentialStream *chp, const char *fmt, va_list ap) { if (state & IS_LONG) value.l = va_arg(ap, long); else*/ - value.l = va_arg(ap, uint32_t); + value.l = va_arg(ap, uint32_t); if (value.l < 0) { - state|=NEGATIVE; + state|=NEGATIVE; *p++ = '-'; value.l = -value.l; } else if (state & POSITIVE) - *p++ = '+'; + *p++ = '+'; #ifdef CHPRINTF_USE_SPACE_FLAG else if (state & PLUS_SPACE) - *p++ = ' '; + *p++ = ' '; #endif p = long_to_string_with_divisor(p, value.l, 10, 0); break; - case 'q': - value.u = va_arg(ap, uint32_t); - p=ulong_freq(p, value.u, precision); - break; + case 'q': + value.u = va_arg(ap, uint32_t); + p=ulong_freq(p, value.u, precision); + break; #if CHPRINTF_USE_FLOAT case 'F': case 'f': value.f = va_arg(ap, double); if (value.f < 0) { - state|=NEGATIVE; + state|=NEGATIVE; *p++ = '-'; value.f = -value.f; } else if (state & POSITIVE) - *p++ = '+'; + *p++ = '+'; #ifdef CHPRINTF_USE_SPACE_FLAG else if (state & PLUS_SPACE) *p++ = ' '; #endif if (value.f == INFINITY){ - *p++ = 0x19; - break; + *p++ = 0x19; + break; } p = (c=='F') ? ftoaS(p, value.f, precision) : ftoa(p, value.f, state&DEFAULT_PRESCISION ? FLOAT_PRECISION : precision); break; @@ -427,7 +426,7 @@ unsigned_common:/* while (width){ streamPut(chp, (uint8_t)filler); n++; - width--; + width--; } } // put data @@ -467,6 +466,7 @@ unsigned_common:/* * * @api */ +#if 0 int chprintf(BaseSequentialStream *chp, const char *fmt, ...) { va_list ap; int formatted_bytes; @@ -477,7 +477,7 @@ int chprintf(BaseSequentialStream *chp, const char *fmt, ...) { return formatted_bytes; } - +#endif /** * @brief System formatted output function. * @details This function implements a minimal @p vprintf()-like functionality @@ -506,6 +506,7 @@ int chprintf(BaseSequentialStream *chp, const char *fmt, ...) { * * @api */ +#if 0 int chsnprintf(char *str, size_t size, const char *fmt, ...) { va_list ap; MemoryStream ms; @@ -535,5 +536,52 @@ int chsnprintf(char *str, size_t size, const char *fmt, ...) { /* Return number of bytes that would have been written.*/ return retval; } +#endif + +// +// Small memory stream object, only put function +// +struct printStreamVMT { + _base_sequential_stream_methods +}; + +typedef struct { + const struct printStreamVMT *vmt; + uint8_t *buffer; + uint16_t size; +} printStream; + +static msg_t put(void *ip, uint8_t b) { + printStream *ps = ip; + if (ps->size > 1){ + *(ps->buffer++) = b; + ps->size--; + } + return MSG_OK; +} + +static const struct printStreamVMT vmt = {NULL, NULL, put, NULL}; +void printObjectInit(printStream *ps, int size, uint8_t *buffer){ + ps->vmt = &vmt; + ps->buffer = buffer; + ps->size = size; +} +// Simple print in buffer function +int plot_printf(char *str, int size, const char *fmt, ...) { + va_list ap; + printStream ps; + int retval; + if (size <= 0) return 0; + // Init small memory stream for print + printObjectInit(&ps, size, (uint8_t *)str); + // Performing the print operation using the common code. + va_start(ap, fmt); + retval = chvprintf((BaseSequentialStream *)(void *)&ps, fmt, ap); + va_end(ap); + *(ps.buffer)=0; + if (retval > size-1) retval = size-1; + // Return number of bytes that would have been written. + return retval; +} /** @} */ diff --git a/flash.c b/flash.c index 79ab95e..9888cb5 100644 --- a/flash.c +++ b/flash.c @@ -32,12 +32,12 @@ static int flash_wait_for_last_operation(void) static void flash_erase_page0(uint32_t page_address) { - flash_wait_for_last_operation(); - FLASH->CR |= FLASH_CR_PER; - FLASH->AR = page_address; - FLASH->CR |= FLASH_CR_STRT; - flash_wait_for_last_operation(); - FLASH->CR &= ~FLASH_CR_PER; + flash_wait_for_last_operation(); + FLASH->CR |= FLASH_CR_PER; + FLASH->AR = page_address; + FLASH->CR |= FLASH_CR_STRT; + flash_wait_for_last_operation(); + FLASH->CR &= ~FLASH_CR_PER; } int flash_erase_page(uint32_t page_address) @@ -50,11 +50,11 @@ int flash_erase_page(uint32_t page_address) void flash_program_half_word(uint32_t address, uint16_t data) { - flash_wait_for_last_operation(); - FLASH->CR |= FLASH_CR_PG; - *(__IO uint16_t*)address = data; - flash_wait_for_last_operation(); - FLASH->CR &= ~FLASH_CR_PG; + flash_wait_for_last_operation(); + FLASH->CR |= FLASH_CR_PG; + *(__IO uint16_t*)address = data; + flash_wait_for_last_operation(); + FLASH->CR &= ~FLASH_CR_PG; } void flash_unlock(void) @@ -64,8 +64,6 @@ void flash_unlock(void) FLASH->KEYR = 0xCDEF89AB; } -#define rotate(x) (((x)<<1) | ((x)&(1<<31)?1:0)) - static uint32_t checksum(const void *start, size_t len) { @@ -73,14 +71,14 @@ checksum(const void *start, size_t len) uint32_t *tail = (uint32_t*)(start + len); uint32_t value = 0; while (p < tail) - value = rotate(value) + *p++; + value = __ROR(value, 31) + *p++; return value; } #define FLASH_PAGESIZE 0x800 -const uint32_t save_config_area = 0x08018000; +const uint32_t save_config_area = SAVE_CONFIG_ADDR; int config_save(void) @@ -122,14 +120,15 @@ config_recall(void) return 0; } -#define SAVEAREA_MAX 5 - -const uint32_t saveareas[] = - { 0x08018800, 0x0801a000, 0x0801b800, 0x0801d000, 0x0801e800 }; +const uint32_t saveareas[SAVEAREA_MAX] = { + SAVE_PROP_CONFIG_0_ADDR, + SAVE_PROP_CONFIG_1_ADDR, + SAVE_PROP_CONFIG_2_ADDR, + SAVE_PROP_CONFIG_3_ADDR, + SAVE_PROP_CONFIG_4_ADDR }; int16_t lastsaveid = 0; - int caldata_save(int id) { @@ -174,15 +173,15 @@ caldata_recall(int id) void *dst = ¤t_props; if (id < 0 || id >= SAVEAREA_MAX) - return -1; + goto load_default; // point to saved area on the flash memory src = (properties_t*)saveareas[id]; if (src->magic != CONFIG_MAGIC) - return -1; + goto load_default; if (checksum(src, sizeof *src - sizeof src->checksum) != src->checksum) - return -1; + goto load_default; /* active configuration points to save data on flash memory */ active_props = src; @@ -190,8 +189,10 @@ caldata_recall(int id) /* duplicated saved data onto sram to be able to modify marker/trace */ memcpy(dst, src, sizeof(properties_t)); - return 0; +load_default: + loadDefaultProps(); + return -1; } const properties_t * @@ -209,7 +210,7 @@ caldata_ref(int id) return src; } -const uint32_t save_config_prop_area_size = 0x8000; +const uint32_t save_config_prop_area_size = SAVE_CONFIG_AREA_SIZE; void clear_all_config_prop_data(void) diff --git a/halconf.h b/halconf.h index 9a44c8b..38341a0 100644 --- a/halconf.h +++ b/halconf.h @@ -118,7 +118,7 @@ * @brief Enables the RTC subsystem. */ #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__) -#define HAL_USE_RTC TRUE +#define HAL_USE_RTC FALSE #endif /** diff --git a/ili9341.c b/ili9341.c index e134025..3c7568b 100644 --- a/ili9341.c +++ b/ili9341.c @@ -21,7 +21,7 @@ #include "hal.h" #include "nanovna.h" -uint16_t spi_buffer[2048]; +uint16_t spi_buffer[SPI_BUFFER_SIZE]; // Default foreground & background colors uint16_t foreground_color=DEFAULT_FG_COLOR; uint16_t background_color=DEFAULT_BG_COLOR; @@ -487,6 +487,10 @@ void ili9341_read_memory(int x, int y, int w, int h, int len, uint16_t *out) } #endif +void clearScreen(void){ + ili9341_fill(0, 0, ILI9341_WIDTH, ILI9341_HEIGHT, background_color); +} + void setForegroundColor(uint16_t fg) {foreground_color = fg;} void setBackgroundColor(uint16_t bg) {background_color = bg;} diff --git a/main.c b/main.c index c34d85c..9b58d78 100644 --- a/main.c +++ b/main.c @@ -46,14 +46,17 @@ static BaseSequentialStream *shell_stream = (BaseSequentialStream *)&SDU1; // Shell max arguments #define VNA_SHELL_MAX_ARGUMENTS 4 // Shell max command line size -#define VNA_SHELL_MAX_LENGTH 64 +#define VNA_SHELL_MAX_LENGTH 48 // Shell command functions prototypes -typedef void (*vna_shellcmd_t)(BaseSequentialStream *chp, int argc, char *argv[]); -#define VNA_SHELL_FUNCTION(command_name) static void command_name(BaseSequentialStream *chp, int argc, char *argv[]) +typedef void (*vna_shellcmd_t)(int argc, char *argv[]); +#define VNA_SHELL_FUNCTION(command_name) static void command_name(int argc, char *argv[]) + +// Shell command line buffer +static char shell_line[VNA_SHELL_MAX_LENGTH]; //#define ENABLED_DUMP //#define ENABLE_THREADS_COMMAND - +//#define ENABLE_TIME_COMMAND static void apply_error_term_at(int i); static void apply_edelay_at(int i); @@ -61,7 +64,8 @@ static void cal_interpolate(int s); void update_frequencies(void); void set_frequencies(uint32_t start, uint32_t stop, uint16_t points); -bool sweep(bool break_on_operation); +static bool sweep(bool break_on_operation); +static void transform_domain(void); static MUTEX_DECL(mutex); @@ -73,67 +77,74 @@ int32_t frequency_offset = 5000; uint32_t frequency = 10000000; int8_t drive_strength = DRIVE_STRENGTH_AUTO; int8_t sweep_enabled = TRUE; -int8_t sweep_once = FALSE; +volatile int8_t sweep_once = FALSE; int8_t cal_auto_interpolate = TRUE; uint16_t redraw_request = 0; // contains REDRAW_XXX flags int16_t vbat = 0; +// +// Profile stack usage (enable threads command by def ENABLE_THREADS_COMMAND) show: +// Stack maximum usage = 576 bytes, free stack = 64 bytes +// static THD_WORKING_AREA(waThread1, 640); static THD_FUNCTION(Thread1, arg) { - (void)arg; - chRegSetThreadName("sweep"); - - while (1) { - bool completed = false; - if (sweep_enabled || sweep_once) { - chMtxLock(&mutex); - completed = sweep(true); - sweep_once = FALSE; - chMtxUnlock(&mutex); - } else { - __WFI(); - } + (void)arg; + chRegSetThreadName("sweep"); + while (1) { + bool completed = false; + if (sweep_enabled || sweep_once) { chMtxLock(&mutex); - ui_process(); - - if (sweep_enabled) { - if (vbat != -1) { - adc_stop(ADC1); - vbat = adc_vbat_read(ADC1); - touch_start_watchdog(); - draw_battery_status(); - } + // Sweep require 8367 system tick + completed = sweep(true); + sweep_once = FALSE; + chMtxUnlock(&mutex); + } else { + __WFI(); + } - /* calculate trace coordinates and plot only if scan completed */ - if (completed) { - plot_into_index(measured); - redraw_request |= REDRAW_CELLS; - - if (marker_tracking) { - int i = marker_search(); - if (i != -1 && active_marker != -1) { - markers[active_marker].index = i; - redraw_request |= REDRAW_MARKER; - } + chMtxLock(&mutex); + // Ui and render require 800 system tick + ui_process(); + + if (sweep_enabled) { + if (vbat != -1) { + adc_stop(ADC1); + vbat = adc_vbat_read(ADC1); + touch_start_watchdog(); + draw_battery_status(); + } + + // calculate trace coordinates and plot only if scan completed + if (completed) { + if ((domain_mode & DOMAIN_MODE) == DOMAIN_TIME) + transform_domain(); + plot_into_index(measured); + redraw_request |= REDRAW_CELLS; + + if (marker_tracking) { + int i = marker_search(); + if (i != -1 && active_marker != -1) { + markers[active_marker].index = i; + redraw_request |= REDRAW_MARKER; } } } - - /* plot trace and other indications as raster */ - draw_all(completed); // flush markmap only if scan completed to prevent remaining traces - chMtxUnlock(&mutex); } + // plot trace and other indications as raster + draw_all(completed); // flush markmap only if scan completed to prevent remaining traces + chMtxUnlock(&mutex); + } } -void +static inline void pause_sweep(void) { sweep_enabled = FALSE; } -void +static inline void resume_sweep(void) { sweep_enabled = TRUE; @@ -171,7 +182,6 @@ kaiser_window(float k, float n, float beta) { static void transform_domain(void) { - if ((domain_mode & DOMAIN_MODE) != DOMAIN_TIME) return; // nothing to do for freq domain // use spi_buffer as temporary buffer // and calculate ifft for time domain float* tmp = (float*)spi_buffer; @@ -242,60 +252,56 @@ transform_domain(void) } // Shell commands output -static int shell_printf(BaseSequentialStream *chp, const char *fmt, ...) { +static int shell_printf(const char *fmt, ...) { va_list ap; int formatted_bytes; va_start(ap, fmt); - formatted_bytes = chvprintf(chp, fmt, ap); + formatted_bytes = chvprintf(shell_stream, fmt, ap); va_end(ap); return formatted_bytes; } -static void cmd_pause(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_pause) { - (void)chp; - (void)argc; - (void)argv; - pause_sweep(); + (void)argc; + (void)argv; + pause_sweep(); } -static void cmd_resume(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_resume) { - (void)chp; - (void)argc; - (void)argv; + (void)argc; + (void)argv; - // restore frequencies array and cal - update_frequencies(); - if (cal_auto_interpolate && (cal_status & CALSTAT_APPLY)) - cal_interpolate(lastsaveid); + // restore frequencies array and cal + update_frequencies(); + if (cal_auto_interpolate && (cal_status & CALSTAT_APPLY)) + cal_interpolate(lastsaveid); - resume_sweep(); + resume_sweep(); } -static void cmd_reset(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_reset) { - (void)argc; - (void)argv; + (void)argc; + (void)argv; - if (argc == 1) { - if (strcmp(argv[0], "dfu") == 0) { - shell_printf(chp, "Performing reset to DFU mode\r\n"); - enter_dfu(); - return; - } + if (argc == 1) { + if (strcmp(argv[0], "dfu") == 0) { + shell_printf("Performing reset to DFU mode\r\n"); + enter_dfu(); + return; } + } + shell_printf("Performing reset\r\n"); - shell_printf(chp, "Performing reset\r\n"); - - rccEnableWWDG(FALSE); - - WWDG->CFR = 0x60; - WWDG->CR = 0xff; + rccEnableWWDG(FALSE); + WWDG->CFR = 0x60; + WWDG->CR = 0xff; - /* wait forever */ - while (1) - ; + /* wait forever */ + while (1) + ; } const int8_t gain_table[] = { @@ -327,15 +333,15 @@ adjust_gain(int newfreq) int set_frequency(uint32_t freq) { - int delay = adjust_gain(freq); - int8_t ds = drive_strength; - if (ds == DRIVE_STRENGTH_AUTO) { - ds = freq > FREQ_HARMONICS ? SI5351_CLK_DRIVE_STRENGTH_8MA : SI5351_CLK_DRIVE_STRENGTH_2MA; - } - delay += si5351_set_frequency_with_offset(freq, frequency_offset, ds); + int delay = adjust_gain(freq); + int8_t ds = drive_strength; + if (ds == DRIVE_STRENGTH_AUTO) { + ds = freq > FREQ_HARMONICS ? SI5351_CLK_DRIVE_STRENGTH_8MA : SI5351_CLK_DRIVE_STRENGTH_2MA; + } + delay += si5351_set_frequency_with_offset(freq, frequency_offset, ds); - frequency = freq; - return delay; + frequency = freq; + return delay; } // Use macro, std isdigit more big @@ -402,17 +408,47 @@ my_atof(const char *p) return x; } -static void cmd_offset(BaseSequentialStream *chp, int argc, char *argv[]) +// +// Function used for search substring v in list +// Example need search parameter "center" in "start|stop|center|span|cw" getStringIndex return 2 +// If not found return -1 +// Used for easy parse command arguments +static int getStringIndex(char *v, const char *list){ + int i = 0; + while(1){ + char *p = v; + while (1){ + char c = *list; if (c == '|') c = 0; + if (c == *p++){ + // Found, return index + if (c == 0) return i; + list++; // Compare next symbol + continue; + } + break; // Not equal, break + } + // Set new substring ptr + while (1){ + // End of string, not found + if (*list == 0 ) return -1; + if (*list++ == '|') break; + } + i++; + } + return -1; +} + +VNA_SHELL_FUNCTION(cmd_offset) { if (argc != 1) { - shell_printf(chp, "usage: offset {frequency offset(Hz)}\r\n"); + shell_printf("usage: offset {frequency offset(Hz)}\r\n"); return; } frequency_offset = my_atoui(argv[0]); set_frequency(frequency); } -static void cmd_freq(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_freq) { if (argc != 1) { goto usage; @@ -420,82 +456,84 @@ static void cmd_freq(BaseSequentialStream *chp, int argc, char *argv[]) uint32_t freq = my_atoui(argv[0]); pause_sweep(); - chMtxLock(&mutex); set_frequency(freq); - chMtxUnlock(&mutex); return; usage: - shell_printf(chp, "usage: freq {frequency(Hz)}\r\n"); + shell_printf("usage: freq {frequency(Hz)}\r\n"); } -static void cmd_power(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_power) { - if (argc != 1) { - shell_printf(chp, "usage: power {0-3|-1}\r\n"); - return; - } - drive_strength = my_atoi(argv[0]); - set_frequency(frequency); + if (argc != 1) { + shell_printf("usage: power {0-3|-1}\r\n"); + return; + } + drive_strength = my_atoi(argv[0]); + set_frequency(frequency); } -static void cmd_time(BaseSequentialStream *chp, int argc, char *argv[]) +#ifdef ENABLE_TIME_COMMAND +#if HAL_USE_RTC == FALSE +#error "Error cmd_time require ENABLE_TIME_COMMAND = TRUE in halconf.h" +#endif +VNA_SHELL_FUNCTION(cmd_time) { - RTCDateTime timespec; - (void)argc; - (void)argv; - rtcGetTime(&RTCD1, ×pec); - shell_printf(chp, "%d/%d/%d %d\r\n", timespec.year+1980, timespec.month, timespec.day, timespec.millisecond); + RTCDateTime timespec; + (void)argc; + (void)argv; + rtcGetTime(&RTCD1, ×pec); + shell_printf("%d/%d/%d %d\r\n", timespec.year+1980, timespec.month, timespec.day, timespec.millisecond); } +#endif - -static void cmd_dac(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_dac) { - int value; - if (argc != 1) { - shell_printf(chp, "usage: dac {value(0-4095)}\r\n"\ - "current value: %d\r\n", config.dac_value); - return; - } - value = my_atoi(argv[0]); - config.dac_value = value; - dacPutChannelX(&DACD2, 0, value); + int value; + if (argc != 1) { + shell_printf("usage: dac {value(0-4095)}\r\n"\ + "current value: %d\r\n", config.dac_value); + return; + } + value = my_atoi(argv[0]); + config.dac_value = value; + dacPutChannelX(&DACD2, 0, value); } -static void cmd_threshold(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_threshold) { - uint32_t value; - if (argc != 1) { - shell_printf(chp, "usage: threshold {frequency in harmonic mode}\r\n"\ - "current: %d\r\n", config.harmonic_freq_threshold); - return; - } - value = my_atoui(argv[0]); - config.harmonic_freq_threshold = value; + uint32_t value; + if (argc != 1) { + shell_printf("usage: threshold {frequency in harmonic mode}\r\n"\ + "current: %d\r\n", config.harmonic_freq_threshold); + return; + } + value = my_atoui(argv[0]); + config.harmonic_freq_threshold = value; } -static void cmd_saveconfig(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_saveconfig) { (void)argc; (void)argv; config_save(); - shell_printf(chp, "Config saved.\r\n"); + shell_printf("Config saved.\r\n"); } -static void cmd_clearconfig(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_clearconfig) { if (argc != 1) { - shell_printf(chp, "usage: clearconfig {protection key}\r\n"); + shell_printf("usage: clearconfig {protection key}\r\n"); return; } if (strcmp(argv[0], "1234") != 0) { - shell_printf(chp, "Key unmatched.\r\n"); + shell_printf("Key unmatched.\r\n"); return; } clear_all_config_prop_data(); - shell_printf(chp, "Config and all cal data cleared.\r\n"\ - "Do reset manually to take effect. Then do touch cal and save.\r\n"); + shell_printf("Config and all cal data cleared.\r\n"\ + "Do reset manually to take effect. Then do touch cal and save.\r\n"); } static struct { @@ -580,34 +618,29 @@ static const I2SConfig i2sconfig = { 2 // i2spr }; -static void cmd_data(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_data) { int i; int sel = 0; - + float (*array)[2]; if (argc == 1) sel = my_atoi(argv[0]); - if (sel == 0 || sel == 1) { - chMtxLock(&mutex); - for (i = 0; i < sweep_points; i++) { - if (frequencies[i] != 0) - shell_printf(chp, "%f %f\r\n", measured[sel][i][0], measured[sel][i][1]); - } - chMtxUnlock(&mutex); - } else if (sel >= 2 && sel < 7) { - chMtxLock(&mutex); - for (i = 0; i < sweep_points; i++) { - if (frequencies[i] != 0) - shell_printf(chp, "%f %f\r\n", cal_data[sel-2][i][0], cal_data[sel-2][i][1]); - } - chMtxUnlock(&mutex); - } else { - shell_printf(chp, "usage: data [array]\r\n"); - } + + if (sel == 0 || sel == 1) + array = measured[sel]; + else if (sel >= 2 && sel < 7) + array = cal_data[sel-2]; + else + goto usage; + for (i = 0; i < sweep_points; i++) + shell_printf("%f %f\r\n", array[i][0], array[i][1]); + return; +usage: + shell_printf("usage: data [array]\r\n"); } #ifdef ENABLED_DUMP -static void cmd_dump(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_dump) { int i, j; int len; @@ -622,37 +655,35 @@ static void cmd_dump(BaseSequentialStream *chp, int argc, char *argv[]) len /= 2; for (i = 0; i < len; ) { for (j = 0; j < 16; j++, i++) { - shell_printf(chp, "%04x ", 0xffff & (int)dump_buffer[i]); + shell_printf("%04x ", 0xffff & (int)dump_buffer[i]); } - shell_printf(chp, "\r\n"); + shell_printf("\r\n"); } } #endif -static void cmd_capture(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_capture) { // read pixel count at one time (PART*2 bytes required for read buffer) - (void)argc; - (void)argv; - - chMtxLock(&mutex); - - // read 2 row pixel time (read buffer limit by 2/3 + 1 from spi_buffer size) - for (int y=0; y < 240; y+=2) - { - // use uint16_t spi_buffer[2048] (defined in ili9341) for read buffer - uint8_t *buf = (uint8_t *)spi_buffer; - ili9341_read_memory(0, y, 320, 2, 2*320, spi_buffer); - for (int i = 0; i < 4*320; i++) { - streamPut(chp, *buf++); - } + (void)argc; + (void)argv; + int i, y; +#if SPI_BUFFER_SIZE < (3*320 + 1) +#error "Low size of spi_buffer for cmd_capture" +#endif + // read 2 row pixel time (read buffer limit by 2/3 + 1 from spi_buffer size) + for (y=0; y < 240; y+=2){ + // use uint16_t spi_buffer[2048] (defined in ili9341) for read buffer + uint8_t *buf = (uint8_t *)spi_buffer; + ili9341_read_memory(0, y, 320, 2, 2*320, spi_buffer); + for (i = 0; i < 4*320; i++) { + streamPut(shell_stream, *buf++); } - - chMtxUnlock(&mutex); + } } #if 0 -static void cmd_gamma(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_gamma) { float gamma[2]; (void)argc; @@ -664,27 +695,25 @@ static void cmd_gamma(BaseSequentialStream *chp, int argc, char *argv[]) calculate_gamma(gamma); chMtxUnlock(&mutex); - shell_printf(chp, "%d %d\r\n", gamma[0], gamma[1]); + shell_printf("%d %d\r\n", gamma[0], gamma[1]); } #endif static void (*sample_func)(float *gamma) = calculate_gamma; -static void cmd_sample(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_sample) { - if (argc == 1) { - if (strcmp(argv[0], "ref") == 0) { - sample_func = fetch_amplitude_ref; - return; - } else if (strcmp(argv[0], "ampl") == 0) { - sample_func = fetch_amplitude; - return; - } else if (strcmp(argv[0], "gamma") == 0) { - sample_func = calculate_gamma; - return; - } + if (argc!=1) goto usage; + // 0 1 2 + static const char cmd_sample_list[] = "gamma|ampl|ref"; + switch (getStringIndex(argv[1], cmd_sample_list)){ + case 0:sample_func = calculate_gamma; return; + case 1:sample_func = fetch_amplitude; return; + case 2:sample_func = fetch_amplitude_ref; return; + default:break; } - shell_printf(chp, "usage: sample {gamma|ampl|ref}\r\n"); +usage: + shell_printf("usage: sample {%s}\r\n", cmd_sample_list); } config_t config = { @@ -696,29 +725,44 @@ config_t config = { .trace_color = { DEFAULT_TRACE_1_COLOR, DEFAULT_TRACE_2_COLOR, DEFAULT_TRACE_3_COLOR, DEFAULT_TRACE_4_COLOR }, // .touch_cal = { 693, 605, 124, 171 }, // 2.4 inch LCD panel .touch_cal = { 338, 522, 153, 192 }, // 2.8 inch LCD panel - .default_loadcal = 0, .harmonic_freq_threshold = 300000000 }; -properties_t current_props = { - .magic = CONFIG_MAGIC, - ._frequency0 = 50000, // start = 50kHz - ._frequency1 = 900000000, // end = 900MHz - ._sweep_points = POINTS_COUNT, - ._trace = {/*enable, type, channel, reserved, scale, refpos*/ - { 1, TRC_LOGMAG, 0, 0, 10.0, NGRIDY-1 }, - { 1, TRC_LOGMAG, 1, 0, 10.0, NGRIDY-1 }, - { 1, TRC_SMITH, 0, 0, 1.0, 0 }, - { 1, TRC_PHASE, 1, 0, 90.0, NGRIDY/2 } - }, - ._markers = { - { 1, 30, 0 }, { 0, 40, 0 }, { 0, 60, 0 }, { 0, 80, 0 } - }, - ._velocity_factor = 0.7, - ._marker_smith_format = MS_RLC -}; +properties_t current_props; properties_t *active_props = ¤t_props; +// NanoVNA Default settings +static const trace_t def_trace[TRACES_MAX] = {//enable, type, channel, reserved, scale, refpos + { 1, TRC_LOGMAG, 0, 0, 10.0, NGRIDY-1 }, + { 1, TRC_LOGMAG, 1, 0, 10.0, NGRIDY-1 }, + { 1, TRC_SMITH, 0, 0, 1.0, 0 }, + { 1, TRC_PHASE, 1, 0, 90.0, NGRIDY/2 } +}; + +static const marker_t def_markers[MARKERS_MAX] = { + { 1, 30, 0 }, { 0, 40, 0 }, { 0, 60, 0 }, { 0, 80, 0 } +}; + +// Load propeties default settings +void loadDefaultProps(void){ + current_props.magic = CONFIG_MAGIC; + current_props._frequency0 = 50000; // start = 50kHz + current_props._frequency1 = 900000000; // end = 900MHz + current_props._sweep_points = POINTS_COUNT; + current_props._cal_status = 0; +//This data not loaded by default +//current_props._frequencies[POINTS_COUNT]; +//current_props._cal_data[5][POINTS_COUNT][2]; +//============================================= + current_props._electrical_delay = 0.0; + memcpy(current_props._trace, def_trace, sizeof(def_trace)); + memcpy(current_props._markers, def_markers, sizeof(def_markers)); + current_props._velocity_factor = 0.7; + current_props._active_marker = 0; + current_props._domain_mode = 0; + current_props._marker_smith_format = MS_RLC; +} + void ensure_edit_config(void) { @@ -737,27 +781,21 @@ ensure_edit_config(void) bool sweep(bool break_on_operation) { int i; - - for (i = 0; i < sweep_points; i++) { - int delay = set_frequency(frequencies[i]); - tlv320aic3204_select(0); // CH0:REFLECT - wait_dsp(delay); - - // blink LED while scanning - palClearPad(GPIOC, GPIOC_LED); - - /* calculate reflection coeficient */ - (*sample_func)(measured[0][i]); - - tlv320aic3204_select(1); // CH1:TRANSMISSION - wait_dsp(DELAY_CHANNEL_CHANGE); - - /* calculate transmission coeficient */ - (*sample_func)(measured[1][i]); - - // blink LED while scanning - palSetPad(GPIOC, GPIOC_LED); - + // blink LED while scanning + palClearPad(GPIOC, GPIOC_LED); + for (i = 0; i < sweep_points; i++) { // 8365 + int delay = set_frequency(frequencies[i]); // 1560 + tlv320aic3204_select(0); // 60 CH0:REFLECT + + wait_dsp(delay); // 3270 + // calculate reflection coefficient + (*sample_func)(measured[0][i]); // 60 + + tlv320aic3204_select(1); // 60 CH1:TRANSMISSION + wait_dsp(DELAY_CHANNEL_CHANGE); // 2700 + // calculate transmission coefficient + (*sample_func)(measured[1][i]); // 60 + // ======== 170 =========== if (cal_status & CALSTAT_APPLY) apply_error_term_at(i); @@ -768,31 +806,31 @@ bool sweep(bool break_on_operation) if (operation_requested && break_on_operation) return false; } - - transform_domain(); + // blink LED while scanning + palSetPad(GPIOC, GPIOC_LED); return true; } -static void cmd_scan(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_scan) { uint32_t start, stop; int16_t points = sweep_points; if (argc != 2 && argc != 3) { - shell_printf(chp, "usage: scan {start(Hz)} {stop(Hz)} [points]\r\n"); + shell_printf("usage: scan {start(Hz)} {stop(Hz)} [points]\r\n"); return; } start = my_atoui(argv[0]); stop = my_atoui(argv[1]); if (start == 0 || stop == 0 || start > stop) { - shell_printf(chp, "frequency range is invalid\r\n"); + shell_printf("frequency range is invalid\r\n"); return; } if (argc == 3) { points = my_atoi(argv[2]); if (points <= 0 || points > sweep_points) { - shell_printf(chp, "sweep points exceeds range\r\n"); + shell_printf("sweep points exceeds range\r\n"); return; } } @@ -820,21 +858,18 @@ update_marker_index(void) if (!markers[m].enabled) continue; uint32_t f = markers[m].frequency; - if (f < frequencies[0]) { + uint32_t fstart = get_sweep_frequency(ST_START); + uint32_t fstop = get_sweep_frequency(ST_STOP); + if (f < fstart) { markers[m].index = 0; - markers[m].frequency = frequencies[0]; - } else if (f >= frequencies[sweep_points-1]) { + markers[m].frequency = fstart; + } else if (f >= fstop) { markers[m].index = sweep_points-1; - markers[m].frequency = frequencies[sweep_points-1]; + markers[m].frequency = fstop; } else { for (i = 0; i < sweep_points-1; i++) { if (frequencies[i] <= f && f < frequencies[i+1]) { - uint32_t mid = (frequencies[i] + frequencies[i+1])/2; - if (f < mid) { - markers[m].index = i; - } else { - markers[m].index = i + 1; - } + markers[m].index = f < (frequencies[i]/2 + frequencies[i+1]/2) ? i : i+1; break; } } @@ -907,9 +942,6 @@ freq_mode_centerspan(void) } } -#define START_MIN 50000 -#define STOP_MAX 2700000000U - void set_sweep_frequency(int type, uint32_t freq) { @@ -1010,10 +1042,10 @@ get_sweep_frequency(int type) return 0; } -static void cmd_sweep(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_sweep) { if (argc == 0) { - shell_printf(chp, "%d %d %d\r\n", frequency0, frequency1, sweep_points); + shell_printf("%d %d %d\r\n", frequency0, frequency1, sweep_points); return; } else if (argc > 3) { goto usage; @@ -1022,21 +1054,15 @@ static void cmd_sweep(BaseSequentialStream *chp, int argc, char *argv[]) uint32_t value1 = 0; if (argc >=1) value0 = my_atoui(argv[0]); if (argc >=2) value1 = my_atoui(argv[1]); - +#if MAX_FREQ_TYPE!=5 +#error "Sweep mode possibly changed, check cmd_sweep function" +#endif // Parse sweep {start|stop|center|span|cw} {freq(Hz)} + // get enum ST_START, ST_STOP, ST_CENTER, ST_SPAN, ST_CW + static const char sweep_cmd[] = "start|stop|center|span|cw"; if (argc == 2 && value0 == 0) { - int type; - if (strcmp(argv[0], "start") == 0) - type = ST_START; - else if (strcmp(argv[0], "stop") == 0) - type = ST_STOP; - else if (strcmp(argv[0], "center") == 0) - type = ST_CENTER; - else if (strcmp(argv[0], "span") == 0) - type = ST_SPAN; - else if (strcmp(argv[0], "cw") == 0) - type = ST_CW; - else + int type = getStringIndex(argv[0], sweep_cmd); + if (type == -1) goto usage; set_sweep_frequency(type, value1); return; @@ -1048,8 +1074,8 @@ static void cmd_sweep(BaseSequentialStream *chp, int argc, char *argv[]) set_sweep_frequency(ST_STOP, value1); return; usage: - shell_printf(chp, "usage: sweep {start(Hz)} [stop(Hz)]\r\n"\ - "\tsweep {start|stop|center|span|cw} {freq(Hz)}\r\n"); + shell_printf("usage: sweep {start(Hz)} [stop(Hz)]\r\n"\ + "\tsweep {%s} {freq(Hz)}\r\n", sweep_cmd); } @@ -1069,13 +1095,14 @@ eterm_copy(int dst, int src) memcpy(cal_data[dst], cal_data[src], sizeof cal_data[dst]); } - +#if 0 const struct open_model { float c0; float c1; float c2; float c3; } open_model = { 50, 0, -300, 27 }; +#endif #if 0 static void @@ -1259,7 +1286,6 @@ void cal_collect(int type) { ensure_edit_config(); - chMtxLock(&mutex); switch (type) { case CAL_LOAD: @@ -1289,7 +1315,6 @@ cal_collect(int type) memcpy(cal_data[CAL_ISOLN], measured[1], sizeof measured[0]); break; } - chMtxUnlock(&mutex); redraw_request |= REDRAW_CAL_STATUS; } @@ -1392,70 +1417,50 @@ cal_interpolate(int s) redraw_request |= REDRAW_CAL_STATUS; } -static void cmd_cal(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_cal) { - const char *items[] = { "load", "open", "short", "thru", "isoln", "Es", "Er", "Et", "cal'ed" }; + static const char *items[] = { "load", "open", "short", "thru", "isoln", "Es", "Er", "Et", "cal'ed" }; if (argc == 0) { int i; for (i = 0; i < 9; i++) { if (cal_status & (1< 1) - s = my_atoi(argv[1]); - cal_interpolate(s); - redraw_request |= REDRAW_CAL_STATUS; - return; - } else { - shell_printf(chp, "usage: cal [load|open|short|thru|isoln|done|reset|on|off|in]\r\n"); - return; + // 0 1 2 3 4 5 6 7 8 9 10 + static const char cmd_cal_list[] = "load|open|short|thru|isoln|done|on|off|reset|data|in"; + switch (getStringIndex(argv[0], cmd_cal_list)){ + case 0:cal_collect(CAL_LOAD ); return; + case 1:cal_collect(CAL_OPEN ); return; + case 2:cal_collect(CAL_SHORT); return; + case 3:cal_collect(CAL_THRU ); return; + case 4:cal_collect(CAL_ISOLN); return; + case 5:cal_done(); return; + case 6:cal_status|= CALSTAT_APPLY;redraw_request|=REDRAW_CAL_STATUS; return; + case 7:cal_status&=~CALSTAT_APPLY;redraw_request|=REDRAW_CAL_STATUS; return; + case 8:cal_status = 0; redraw_request|=REDRAW_CAL_STATUS; return; + case 9: + shell_printf("%f %f\r\n", cal_data[CAL_LOAD ][0][0], cal_data[CAL_LOAD ][0][1]); + shell_printf("%f %f\r\n", cal_data[CAL_OPEN ][0][0], cal_data[CAL_OPEN ][0][1]); + shell_printf("%f %f\r\n", cal_data[CAL_SHORT][0][0], cal_data[CAL_SHORT][0][1]); + shell_printf("%f %f\r\n", cal_data[CAL_THRU ][0][0], cal_data[CAL_THRU ][0][1]); + shell_printf("%f %f\r\n", cal_data[CAL_ISOLN][0][0], cal_data[CAL_ISOLN][0][1]); + return; + case 10: + cal_interpolate((argc > 1) ? my_atoi(argv[1]) : 0); + redraw_request|=REDRAW_CAL_STATUS; + return; + default:break; } + + shell_printf("usage: cal [%s]\r\n", cmd_cal_list); } -static void cmd_save(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_save) { - (void)chp; - if (argc != 1) goto usage; @@ -1467,32 +1472,25 @@ static void cmd_save(BaseSequentialStream *chp, int argc, char *argv[]) return; usage: - shell_printf(chp, "save {id}\r\n"); + shell_printf("save {id}\r\n"); } -static void cmd_recall(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_recall) { - (void)chp; if (argc != 1) goto usage; int id = my_atoi(argv[0]); if (id < 0 || id >= SAVEAREA_MAX) goto usage; - - pause_sweep(); - chMtxLock(&mutex); - if (caldata_recall(id) == 0) { - // success - update_frequencies(); - redraw_request |= REDRAW_CAL_STATUS; - } - chMtxUnlock(&mutex); - resume_sweep(); + // Check for success + if (caldata_recall(id) == -1) + shell_printf("Err, default load\r\n"); + update_frequencies(); + redraw_request |= REDRAW_CAL_STATUS; return; - usage: - shell_printf(chp, "recall {id}\r\n"); + shell_printf("recall {id}\r\n"); } static const struct { @@ -1500,20 +1498,20 @@ static const struct { uint16_t refpos; float scale_unit; } trace_info[] = { - { "LOGMAG", 9, 10 }, - { "PHASE", 5, 90 }, - { "DELAY", 5, 1e-9 }, - { "SMITH", 0, 1 }, - { "POLAR", 0, 1 }, - { "LINEAR", 0, 0.125 }, - { "SWR", 0, 1 }, - { "REAL", 5, 0.25 }, - { "IMAG", 5, 0.25 }, - { "R", 0, 100 }, - { "X", 5, 100 } + { "LOGMAG", NGRIDY-1, 10.0 }, + { "PHASE", NGRIDY/2, 90.0 }, + { "DELAY", NGRIDY/2, 1e-9 }, + { "SMITH", 0, 1.00 }, + { "POLAR", 0, 1.00 }, + { "LINEAR", 0, 0.125}, + { "SWR", 0, 0.25 }, + { "REAL", NGRIDY/2, 0.25 }, + { "IMAG", NGRIDY/2, 0.25 }, + { "R", NGRIDY/2, 100.0 }, + { "X", NGRIDY/2, 100.0 } }; -const char * const trc_channel_name[] = { +static const char * const trc_channel_name[] = { "CH0", "CH1" }; @@ -1533,7 +1531,10 @@ void set_trace_type(int t, int type) } if (trace[t].type != type) { trace[t].type = type; + // Set default trace refpos trace[t].refpos = trace_info[type].refpos; + // Set default trace scale + trace[t].scale = trace_info[type].scale_unit; force = TRUE; } if (force) { @@ -1552,7 +1553,6 @@ void set_trace_channel(int t, int channel) void set_trace_scale(int t, float scale) { -// scale /= trace_info[trace[t].type].scale_unit; if (trace[t].scale != scale) { trace[t].scale = scale; force_set_markmap(); @@ -1561,7 +1561,7 @@ void set_trace_scale(int t, float scale) float get_trace_scale(int t) { - return trace[t].scale;// * trace_info[trace[t].type].scale_unit; + return trace[t].scale; } void set_trace_refpos(int t, float refpos) @@ -1577,22 +1577,17 @@ float get_trace_refpos(int t) return trace[t].refpos; } -typedef struct { - char *tracename; - uint8_t type; -} type_list; - -static void cmd_trace(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_trace) { int t; if (argc == 0) { for (t = 0; t < TRACES_MAX; t++) { if (trace[t].enabled) { - const char *type = trace_info[trace[t].type].name; + const char *type = get_trace_typename(t); const char *channel = trc_channel_name[trace[t].channel]; float scale = get_trace_scale(t); float refpos = get_trace_refpos(t); - shell_printf(chp, "%d %s %s %f %f\r\n", t, type, channel, scale, refpos); + shell_printf("%d %s %s %f %f\r\n", t, type, channel, scale, refpos); } } return; @@ -1611,53 +1606,47 @@ static void cmd_trace(BaseSequentialStream *chp, int argc, char *argv[]) if (argc == 1) { const char *type = get_trace_typename(t); const char *channel = trc_channel_name[trace[t].channel]; - shell_printf(chp, "%d %s %s\r\n", t, type, channel); + shell_printf("%d %s %s\r\n", t, type, channel); return; } - static const type_list t_list[] = { - {"logmag", TRC_LOGMAG}, - {"phase", TRC_PHASE}, - {"delay", TRC_DELAY}, - {"smith", TRC_SMITH}, - {"polar", TRC_POLAR}, - {"linear", TRC_LINEAR}, - {"swr", TRC_SWR}, - {"real", TRC_REAL}, - {"imag", TRC_IMAG}, - {"r", TRC_R}, - {"x", TRC_X}, - {"off", TRC_OFF}, - }; - for (uint16_t i=0; i= 0){ + set_trace_type(t, type); + goto check_ch_num; + } + // 0 1 + static const char cmd_scale_ref_list[] = "scale|refpos"; + if (argc >= 3){ + switch (getStringIndex(argv[1], cmd_scale_ref_list)){ + case 0: + //trace[t].scale = my_atof(argv[2]); + set_trace_scale(t, my_atof(argv[2])); + goto exit; + case 1: + //trace[t].refpos = my_atof(argv[2]); + set_trace_refpos(t, my_atof(argv[2])); + goto exit; + default: + goto usage; } } - if (strcmp(argv[1], "scale") == 0 && argc >= 3) { - //trace[t].scale = my_atof(argv[2]); - set_trace_scale(t, my_atof(argv[2])); - goto exit; - } else if (strcmp(argv[1], "refpos") == 0 && argc >= 3) { - //trace[t].refpos = my_atof(argv[2]); - set_trace_refpos(t, my_atof(argv[2])); - goto exit; - } else { - goto usage; - } - - check_ch_num: +check_ch_num: if (argc > 2) { int src = my_atoi(argv[2]); if (src != 0 && src != 1) goto usage; trace[t].channel = src; } - exit: +exit: return; - usage: - shell_printf(chp, "trace {0|1|2|3|all} [logmag|phase|polar|smith|linear|delay|swr|real|imag|r|x|off] [src]\r\n"\ - "trace {0|1|2|3} {scale|refpos} {value}\r\n"); +usage: + shell_printf("trace {0|1|2|3|all} [%s] [src]\r\n"\ + "trace {0|1|2|3} {%s} {value}\r\n", cmd_type_list, cmd_scale_ref_list); } @@ -1674,10 +1663,10 @@ float get_electrical_delay(void) return electrical_delay; } -static void cmd_edelay(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_edelay) { if (argc == 0) { - shell_printf(chp, "%f\r\n", electrical_delay); + shell_printf("%f\r\n", electrical_delay); return; } if (argc > 0) { @@ -1686,17 +1675,17 @@ static void cmd_edelay(BaseSequentialStream *chp, int argc, char *argv[]) } -static void cmd_marker(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_marker) { int t; if (argc == 0) { for (t = 0; t < MARKERS_MAX; t++) { if (markers[t].enabled) { - shell_printf(chp, "%d %d %d\r\n", t+1, markers[t].index, markers[t].frequency); + shell_printf("%d %d %d\r\n", t+1, markers[t].index, markers[t].frequency); } } return; - } + } if (strcmp(argv[0], "off") == 0) { active_marker = -1; for (t = 0; t < MARKERS_MAX; t++) @@ -1709,24 +1698,18 @@ static void cmd_marker(BaseSequentialStream *chp, int argc, char *argv[]) if (t < 0 || t >= MARKERS_MAX) goto usage; if (argc == 1) { - shell_printf(chp, "%d %d %d\r\n", t+1, markers[t].index, frequency); + shell_printf("%d %d %d\r\n", t+1, markers[t].index, frequency); active_marker = t; // select active marker markers[t].enabled = TRUE; redraw_request |= REDRAW_MARKER; return; } - if (argc > 1) { - if (strcmp(argv[1], "off") == 0) { - markers[t].enabled = FALSE; - if (active_marker == t) - active_marker = -1; - redraw_request |= REDRAW_MARKER; - } else if (strcmp(argv[1], "on") == 0) { - markers[t].enabled = TRUE; - active_marker = t; - redraw_request |= REDRAW_MARKER; - } else { + static const char cmd_marker_list[] = "on|off"; + switch (getStringIndex(argv[1], cmd_marker_list)){ + case 0: markers[t].enabled = TRUE; active_marker = t; redraw_request |= REDRAW_MARKER; return; + case 1: markers[t].enabled =FALSE; if (active_marker == t) active_marker = -1; redraw_request|=REDRAW_MARKER; return; + default: // select active marker and move to index markers[t].enabled = TRUE; int index = my_atoi(argv[1]); @@ -1734,55 +1717,47 @@ static void cmd_marker(BaseSequentialStream *chp, int argc, char *argv[]) markers[t].frequency = frequencies[index]; active_marker = t; redraw_request |= REDRAW_MARKER; - } + return; } - return; usage: - shell_printf(chp, "marker [n] [off|{index}]\r\n"); + shell_printf("marker [n] [%s|{index}]\r\n", cmd_marker_list); } -static void cmd_touchcal(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_touchcal) { (void)argc; (void)argv; //extern int16_t touch_cal[4]; int i; - chMtxLock(&mutex); - shell_printf(chp, "first touch upper left, then lower right..."); + shell_printf("first touch upper left, then lower right..."); touch_cal_exec(); - shell_printf(chp, "done\r\n"); + shell_printf("done\r\n"); - shell_printf(chp, "touch cal params: "); + shell_printf("touch cal params: "); for (i = 0; i < 4; i++) { - shell_printf(chp, "%d ", config.touch_cal[i]); + shell_printf("%d ", config.touch_cal[i]); } - shell_printf(chp, "\r\n"); - chMtxUnlock(&mutex); + shell_printf("\r\n"); } -static void cmd_touchtest(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_touchtest) { - (void)chp; (void)argc; (void)argv; - chMtxLock(&mutex); do { touch_draw_test(); } while(argc); - chMtxUnlock(&mutex); - } -static void cmd_frequencies(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_frequencies) { int i; - (void)chp; (void)argc; (void)argv; for (i = 0; i < sweep_points; i++) { if (frequencies[i] != 0) - shell_printf(chp, "%d\r\n", frequencies[i]); + shell_printf("%d\r\n", frequencies[i]); } } @@ -1808,44 +1783,34 @@ set_timedomain_window(int func) // accept TD_WINDOW_MINIMUM/TD_WINDOW_NORMAL/TD_ domain_mode = (domain_mode & ~TD_WINDOW) | (func & TD_WINDOW); } -static void cmd_transform(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_transform) { int i; if (argc == 0) { goto usage; } - + // 0 1 2 3 4 5 6 7 + static const char cmd_transform_list[] = "on|off|impulse|step|bandpass|minimum|normal|maximum"; for (i = 0; i < argc; i++) { - char *cmd = argv[i]; - if (strcmp(cmd, "on") == 0) { - set_domain_mode(DOMAIN_TIME); - } else if (strcmp(cmd, "off") == 0) { - set_domain_mode(DOMAIN_FREQ); - } else if (strcmp(cmd, "impulse") == 0) { - set_timedomain_func(TD_FUNC_LOWPASS_IMPULSE); - } else if (strcmp(cmd, "step") == 0) { - set_timedomain_func(TD_FUNC_LOWPASS_STEP); - } else if (strcmp(cmd, "bandpass") == 0) { - set_timedomain_func(TD_FUNC_BANDPASS); - } else if (strcmp(cmd, "minimum") == 0) { - set_timedomain_window(TD_WINDOW_MINIMUM); - } else if (strcmp(cmd, "normal") == 0) { - set_timedomain_window(TD_WINDOW_NORMAL); - } else if (strcmp(cmd, "maximum") == 0) { - set_timedomain_window(TD_WINDOW_MAXIMUM); - } else { - goto usage; + switch (getStringIndex(argv[i], cmd_transform_list)){ + case 0:set_domain_mode(DOMAIN_TIME);return; + case 1:set_domain_mode(DOMAIN_FREQ);return; + case 2:set_timedomain_func(TD_FUNC_LOWPASS_IMPULSE);return; + case 3:set_timedomain_func(TD_FUNC_LOWPASS_STEP);return; + case 4:set_timedomain_func(TD_FUNC_BANDPASS);return; + case 5:set_timedomain_window(TD_WINDOW_MINIMUM);return; + case 6:set_timedomain_window(TD_WINDOW_NORMAL);return; + case 7:set_timedomain_window(TD_WINDOW_MAXIMUM);return; + default: goto usage; } } return; - usage: - shell_printf(chp, "usage: transform {on|off|impulse|step|bandpass|minimum|normal|maximum} [...]\r\n"); + shell_printf("usage: transform {%s} [...]\r\n", cmd_transform_list); } -static void cmd_test(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_test) { - (void)chp; (void)argc; (void)argv; @@ -1880,32 +1845,32 @@ static void cmd_test(BaseSequentialStream *chp, int argc, char *argv[]) #if 0 //extern adcsample_t adc_samples[2]; - //shell_printf(chp, "adc: %d %d\r\n", adc_samples[0], adc_samples[1]); + //shell_printf("adc: %d %d\r\n", adc_samples[0], adc_samples[1]); int i; int x, y; for (i = 0; i < 50; i++) { test_touch(&x, &y); - shell_printf(chp, "adc: %d %d\r\n", x, y); + shell_printf("adc: %d %d\r\n", x, y); chThdSleepMilliseconds(200); } //extern int touch_x, touch_y; - //shell_printf(chp, "adc: %d %d\r\n", touch_x, touch_y); + //shell_printf("adc: %d %d\r\n", touch_x, touch_y); #endif while (argc > 1) { int x, y; touch_position(&x, &y); - shell_printf(chp, "touch: %d %d\r\n", x, y); + shell_printf("touch: %d %d\r\n", x, y); chThdSleepMilliseconds(200); } } -static void cmd_gain(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_gain) { int rvalue; int lvalue = 0; if (argc != 1 && argc != 2) { - shell_printf(chp, "usage: gain {lgain(0-95)} [rgain(0-95)]\r\n"); + shell_printf("usage: gain {lgain(0-95)} [rgain(0-95)]\r\n"); return; } rvalue = my_atoi(argv[0]); @@ -1914,18 +1879,18 @@ static void cmd_gain(BaseSequentialStream *chp, int argc, char *argv[]) tlv320aic3204_set_gain(lvalue, rvalue); } -static void cmd_port(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_port) { int port; if (argc != 1) { - shell_printf(chp, "usage: port {0:TX 1:RX}\r\n"); + shell_printf("usage: port {0:TX 1:RX}\r\n"); return; } port = my_atoi(argv[0]); tlv320aic3204_select(port); } -static void cmd_stat(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_stat) { int16_t *p = &rx_buffer[0]; int32_t acc0, acc1; @@ -1951,14 +1916,14 @@ static void cmd_stat(BaseSequentialStream *chp, int argc, char *argv[]) stat.ave[0] = ave0; stat.ave[1] = ave1; - shell_printf(chp, "average: %d %d\r\n", stat.ave[0], stat.ave[1]); - shell_printf(chp, "rms: %d %d\r\n", stat.rms[0], stat.rms[1]); - shell_printf(chp, "callback count: %d\r\n", stat.callback_count); - //shell_printf(chp, "interval cycle: %d\r\n", stat.interval_cycles); - //shell_printf(chp, "busy cycle: %d\r\n", stat.busy_cycles); - //shell_printf(chp, "load: %d\r\n", stat.busy_cycles * 100 / stat.interval_cycles); + shell_printf("average: %d %d\r\n", stat.ave[0], stat.ave[1]); + shell_printf("rms: %d %d\r\n", stat.rms[0], stat.rms[1]); + shell_printf("callback count: %d\r\n", stat.callback_count); + //shell_printf("interval cycle: %d\r\n", stat.interval_cycles); + //shell_printf("busy cycle: %d\r\n", stat.busy_cycles); + //shell_printf("load: %d\r\n", stat.busy_cycles * 100 / stat.interval_cycles); extern int awd_count; - shell_printf(chp, "awd: %d\r\n", awd_count); + shell_printf("awd: %d\r\n", awd_count); } @@ -1968,39 +1933,45 @@ static void cmd_stat(BaseSequentialStream *chp, int argc, char *argv[]) const char NANOVNA_VERSION[] = VERSION; -static void cmd_version(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_version) { (void)argc; (void)argv; - shell_printf(chp, "%s\r\n", NANOVNA_VERSION); + shell_printf("%s\r\n", NANOVNA_VERSION); } -static void cmd_vbat(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_vbat) { (void)argc; (void)argv; - shell_printf(chp, "%d mV\r\n", vbat); + shell_printf("%d mV\r\n", vbat); } #ifdef ENABLE_THREADS_COMMAND #if CH_CFG_USE_REGISTRY == FALSE #error "Threads Requite enabled CH_CFG_USE_REGISTRY in chconf.h" #endif -static void cmd_threads(BaseSequentialStream *chp, int argc, char *argv[]) { +VNA_SHELL_FUNCTION(cmd_threads) { static const char *states[] = {CH_STATE_NAMES}; thread_t *tp; - + (void)argc; (void)argv; - if (argc > 0) { - shellUsage(chp, "threads"); - return; - } - chprintf(chp, "stklimit stack addr refs prio state name\r\n"SHELL_NEWLINE_STR); + shell_printf("stklimit| stack|stk free| addr|refs|prio| state| name"VNA_SHELL_NEWLINE_STR); tp = chRegFirstThread(); do { + uint32_t max_stack_use = 0U; +#if (CH_DBG_ENABLE_STACK_CHECK == TRUE) || (CH_CFG_USE_DYNAMIC == TRUE) uint32_t stklimit = (uint32_t)tp->wabase; - shell_printf(chp, "%08x %08x %08x %4u %4u %9s %12s"SHELL_NEWLINE_STR, - stklimit, (uint32_t)tp->ctx.sp, (uint32_t)tp, +#if CH_DBG_FILL_THREADS == TRUE + uint8_t *p = (uint8_t *)tp->wabase; while(p[max_stack_use]==CH_DBG_STACK_FILL_VALUE) max_stack_use++; +#endif +#else + uint32_t stklimit = 0U; +#endif + + + shell_printf("%08x|%08x|%08x|%08x|%4u|%4u|%9s|%12s"VNA_SHELL_NEWLINE_STR, + stklimit, (uint32_t)tp->ctx.sp, max_stack_use, (uint32_t)tp, (uint32_t)tp->refs - 1, (uint32_t)tp->prio, states[tp->state], tp->name == NULL ? "" : tp->name); tp = chRegNextThread(tp); @@ -2009,68 +1980,76 @@ static void cmd_threads(BaseSequentialStream *chp, int argc, char *argv[]) { #endif //============================================================================= -static void cmd_help(BaseSequentialStream *chp, int argc, char *argv[]); +VNA_SHELL_FUNCTION(cmd_help); + +#pragma pack(push, 2) typedef struct { const char *sc_name; vna_shellcmd_t sc_function; + uint16_t flags; } VNAShellCommand; +#pragma pack(pop) +// Some commands can executed only if process thread not in main cycle +#define CMD_WAIT_MUTEX 1 static const VNAShellCommand commands[] = { - { "version" , cmd_version }, - { "reset" , cmd_reset }, - { "freq" , cmd_freq }, - { "offset" , cmd_offset }, - { "time" , cmd_time }, - { "dac" , cmd_dac }, - { "saveconfig" , cmd_saveconfig }, - { "clearconfig" , cmd_clearconfig }, - { "data" , cmd_data }, + {"version" , cmd_version , 0}, + {"reset" , cmd_reset , 0}, + {"freq" , cmd_freq , CMD_WAIT_MUTEX}, + {"offset" , cmd_offset , 0}, +#ifdef ENABLE_TIME_COMMAND + {"time" , cmd_time , 0}, +#endif + {"dac" , cmd_dac , 0}, + {"saveconfig" , cmd_saveconfig , 0}, + {"clearconfig" , cmd_clearconfig , 0}, + {"data" , cmd_data , CMD_WAIT_MUTEX}, #ifdef ENABLED_DUMP - { "dump" , cmd_dump }, + {"dump" , cmd_dump , 0}, #endif - { "frequencies" , cmd_frequencies }, - { "port" , cmd_port }, - { "stat" , cmd_stat }, - { "gain" , cmd_gain }, - { "power" , cmd_power }, - { "sample" , cmd_sample }, -// { "gamma" , cmd_gamma }, - { "scan" , cmd_scan }, - { "sweep" , cmd_sweep }, - { "test" , cmd_test }, - { "touchcal" , cmd_touchcal }, - { "touchtest" , cmd_touchtest }, - { "pause" , cmd_pause }, - { "resume" , cmd_resume }, - { "cal" , cmd_cal }, - { "save" , cmd_save }, - { "recall" , cmd_recall }, - { "trace" , cmd_trace }, - { "marker" , cmd_marker }, - { "edelay" , cmd_edelay }, - { "capture" , cmd_capture }, - { "vbat" , cmd_vbat }, - { "transform" , cmd_transform }, - { "threshold" , cmd_threshold }, - { "help" , cmd_help }, + {"frequencies" , cmd_frequencies , 0}, + {"port" , cmd_port , 0}, + {"stat" , cmd_stat , 0}, + {"gain" , cmd_gain , 0}, + {"power" , cmd_power , 0}, + {"sample" , cmd_sample , 0}, +// {"gamma" , cmd_gamma , 0}, + {"scan" , cmd_scan , 0}, // Wait mutex hardcoded in cmd, need wait one sweep manually + {"sweep" , cmd_sweep , 0}, + {"test" , cmd_test , 0}, + {"touchcal" , cmd_touchcal , CMD_WAIT_MUTEX}, + {"touchtest" , cmd_touchtest , CMD_WAIT_MUTEX}, + {"pause" , cmd_pause , 0}, + {"resume" , cmd_resume , 0}, + {"cal" , cmd_cal , CMD_WAIT_MUTEX}, + {"save" , cmd_save , 0}, + {"recall" , cmd_recall , CMD_WAIT_MUTEX}, + {"trace" , cmd_trace , 0}, + {"marker" , cmd_marker , 0}, + {"edelay" , cmd_edelay , 0}, + {"capture" , cmd_capture , CMD_WAIT_MUTEX}, + {"vbat" , cmd_vbat , 0}, + {"transform" , cmd_transform , 0}, + {"threshold" , cmd_threshold , 0}, + {"help" , cmd_help , 0}, #ifdef ENABLE_THREADS_COMMAND -// { "threads" , cmd_threads }, + {"threads" , cmd_threads , 0}, #endif - { NULL , NULL } + {NULL , NULL , 0} }; -static void cmd_help(BaseSequentialStream *chp, int argc, char *argv[]) +VNA_SHELL_FUNCTION(cmd_help) { (void)argc; (void)argv; const VNAShellCommand *scp = commands; - shell_printf(chp, "Commands:"); + shell_printf("Commands:"); while (scp->sc_name != NULL) { - shell_printf(chp, " %s", scp->sc_name); + shell_printf(" %s", scp->sc_name); scp++; } - shell_printf(chp, VNA_SHELL_NEWLINE_STR); + shell_printf(VNA_SHELL_NEWLINE_STR); return; } @@ -2089,18 +2068,18 @@ static int VNAShell_readLine(char *line, int max_size){ // Return 0 only if stream not active if (streamRead(shell_stream, &c, 1) == 0) return 0; - // Backspace + // Backspace or Delete if (c == 8 || c == 0x7f) { if (ptr != line) { static const char backspace[] = {0x08,0x20,0x08,0x00}; - shell_printf(shell_stream, backspace); + shell_printf(backspace); ptr--; } continue; } // New line (Enter) if (c == '\r') { - shell_printf(shell_stream, VNA_SHELL_NEWLINE_STR); + shell_printf(VNA_SHELL_NEWLINE_STR); *ptr = 0; return 1; } @@ -2116,6 +2095,9 @@ static int VNAShell_readLine(char *line, int max_size){ return 0; } +// Macros for convert define value to string +#define STR1(x) #x +#define define_to_STR(x) STR1(x) // // Parse and run command line // @@ -2136,7 +2118,7 @@ static void VNAShell_executeLine(char *line){ break; // Argument limits check if (n > VNA_SHELL_MAX_ARGUMENTS) { - shell_printf(shell_stream, "too many arguments, max 4"VNA_SHELL_NEWLINE_STR); + shell_printf("too many arguments, max "define_to_STR(VNA_SHELL_MAX_ARGUMENTS)""VNA_SHELL_NEWLINE_STR); return; } // Set zero at the end of string and continue check @@ -2148,13 +2130,17 @@ static void VNAShell_executeLine(char *line){ const VNAShellCommand *scp; for (scp = commands; scp->sc_name!=NULL;scp++) { if (strcmp(scp->sc_name, args[0]) == 0) { -// chMtxLock(&mutex); - scp->sc_function(shell_stream, n-1, &args[1]); -// chMtxUnlock(&mutex); + if (scp->flags&CMD_WAIT_MUTEX) { + chMtxLock(&mutex); + scp->sc_function(n-1, &args[1]); + chMtxUnlock(&mutex); + } + else + scp->sc_function(n-1, &args[1]); return; } } - shell_printf(shell_stream, "%s?"VNA_SHELL_NEWLINE_STR, args[0]); + shell_printf("%s?"VNA_SHELL_NEWLINE_STR, args[0]); } #ifdef VNA_SHELL_THREAD @@ -2162,12 +2148,11 @@ static THD_WORKING_AREA(waThread2, /* cmd_* max stack size + alpha */442); THD_FUNCTION(myshellThread, p) { (void)p; chRegSetThreadName("shell"); - char line[VNA_SHELL_MAX_LENGTH]; - shell_printf(shell_stream, VNA_SHELL_NEWLINE_STR"NanoVNA Shell"VNA_SHELL_NEWLINE_STR); + shell_printf(VNA_SHELL_NEWLINE_STR"NanoVNA Shell"VNA_SHELL_NEWLINE_STR); while (true) { - shell_printf(shell_stream, VNA_SHELL_PROMPT_STR); - if (VNAShell_readLine(line, VNA_SHELL_MAX_LENGTH)) - VNAShell_executeLine(line); + shell_printf(VNA_SHELL_PROMPT_STR); + if (VNAShell_readLine(shell_line, VNA_SHELL_MAX_LENGTH)) + VNAShell_executeLine(shell_line); else // Putting a delay in order to avoid an endless loop trying to read an unavailable stream. osalThreadSleepMilliseconds(100); } @@ -2186,68 +2171,63 @@ static DACConfig dac1cfg1 = { datamode: DAC_DHRM_12BIT_RIGHT }; + +// Main thread stack size defined in makefile USE_PROCESS_STACKSIZE = 0x200 +// Profile stack usage (enable threads command by def ENABLE_THREADS_COMMAND) show: +// Stack maximum usage = 472 bytes (need test more and run all commands), free stack = 40 bytes +// int main(void) { - halInit(); - chSysInit(); - - chMtxObjectInit(&mutex); - - //palSetPadMode(GPIOB, 8, PAL_MODE_ALTERNATE(1) | PAL_STM32_OTYPE_OPENDRAIN); - //palSetPadMode(GPIOB, 9, PAL_MODE_ALTERNATE(1) | PAL_STM32_OTYPE_OPENDRAIN); - i2cStart(&I2CD1, &i2ccfg); - si5351_init(); - - // MCO on PA8 - //palSetPadMode(GPIOA, 8, PAL_MODE_ALTERNATE(0)); - /* - * Initializes a serial-over-USB CDC driver. - */ - sduObjectInit(&SDU1); - sduStart(&SDU1, &serusbcfg); - - /* - * Activates the USB driver and then the USB bus pull-up on D+. - * Note, a delay is inserted in order to not have to disconnect the cable - * after a reset. - */ - usbDisconnectBus(serusbcfg.usbp); - chThdSleepMilliseconds(100); - usbStart(serusbcfg.usbp, &usbcfg); - usbConnectBus(serusbcfg.usbp); - - /* - * SPI LCD Initialize - */ - ili9341_init(); + halInit(); + chSysInit(); - /* - * Initialize graph plotting - */ - plot_init(); + chMtxObjectInit(&mutex); + + //palSetPadMode(GPIOB, 8, PAL_MODE_ALTERNATE(1) | PAL_STM32_OTYPE_OPENDRAIN); + //palSetPadMode(GPIOB, 9, PAL_MODE_ALTERNATE(1) | PAL_STM32_OTYPE_OPENDRAIN); + i2cStart(&I2CD1, &i2ccfg); + si5351_init(); + + // MCO on PA8 + //palSetPadMode(GPIOA, 8, PAL_MODE_ALTERNATE(0)); +/* + * Initializes a serial-over-USB CDC driver. + */ + sduObjectInit(&SDU1); + sduStart(&SDU1, &serusbcfg); +/* + * Activates the USB driver and then the USB bus pull-up on D+. + * Note, a delay is inserted in order to not have to disconnect the cable + * after a reset. + */ + usbDisconnectBus(serusbcfg.usbp); + chThdSleepMilliseconds(100); + usbStart(serusbcfg.usbp, &usbcfg); + usbConnectBus(serusbcfg.usbp); + +/* + * SPI LCD Initialize + */ + ili9341_init(); - /* restore config */ +/* restore config */ config_recall(); +/* restore frequencies and calibration 0 slot properties from flash memory */ + caldata_recall(0); dac1cfg1.init = config.dac_value; - /* - * Starting DAC1 driver, setting up the output pin as analog as suggested - * by the Reference Manual. - */ +/* + * Starting DAC1 driver, setting up the output pin as analog as suggested + * by the Reference Manual. + */ dacStart(&DACD2, &dac1cfg1); - /* initial frequencies */ +/* initial frequencies */ update_frequencies(); - /* restore frequencies and calibration properties from flash memory */ - if (config.default_loadcal >= 0) - caldata_recall(config.default_loadcal); - - redraw_frame(); - - /* - * I2S Initialize - */ +/* + * I2S Initialize + */ tlv320aic3204_init(); i2sInit(); i2sObjectInit(&I2SD2); @@ -2255,23 +2235,27 @@ int main(void) i2sStartExchange(&I2SD2); ui_init(); - + //Initialize graph plotting + plot_init(); + redraw_frame(); chThdCreateStatic(waThread1, sizeof(waThread1), NORMALPRIO-1, Thread1, NULL); while (1) { if (SDU1.config->usbp->state == USB_ACTIVE) { #ifdef VNA_SHELL_THREAD +#if CH_CFG_USE_WAITEXIT == FALSE +#error "VNA_SHELL_THREAD use chThdWait, need enable CH_CFG_USE_WAITEXIT in chconf.h" +#endif thread_t *shelltp = chThdCreateStatic(waThread2, sizeof(waThread2), NORMALPRIO + 1, myshellThread, NULL); chThdWait(shelltp); #else - char line[VNA_SHELL_MAX_LENGTH]; - shell_printf(shell_stream, VNA_SHELL_NEWLINE_STR"NanoVNA Shell"VNA_SHELL_NEWLINE_STR); + shell_printf(VNA_SHELL_NEWLINE_STR"NanoVNA Shell"VNA_SHELL_NEWLINE_STR); do { - shell_printf(shell_stream, VNA_SHELL_PROMPT_STR); - if (VNAShell_readLine(line, VNA_SHELL_MAX_LENGTH)) - VNAShell_executeLine(line); + shell_printf(VNA_SHELL_PROMPT_STR); + if (VNAShell_readLine(shell_line, VNA_SHELL_MAX_LENGTH)) + VNAShell_executeLine(shell_line); else chThdSleepMilliseconds(200); } while (SDU1.config->usbp->state == USB_ACTIVE); diff --git a/nanovna.h b/nanovna.h index f0a903d..f9e31ae 100644 --- a/nanovna.h +++ b/nanovna.h @@ -25,6 +25,8 @@ /* * main.c */ +#define START_MIN 50000 +#define STOP_MAX 2700000000U #define POINTS_COUNT 101 extern float measured[2][POINTS_COUNT][2]; @@ -71,8 +73,9 @@ extern float measured[2][POINTS_COUNT][2]; void cal_collect(int type); void cal_done(void); +#define MAX_FREQ_TYPE 5 enum { - ST_START, ST_STOP, ST_CENTER, ST_SPAN, ST_CW + ST_START=0, ST_STOP, ST_CENTER, ST_SPAN, ST_CW }; void set_sweep_frequency(int type, uint32_t frequency); @@ -81,9 +84,25 @@ uint32_t get_sweep_frequency(int type); double my_atof(const char *p); void toggle_sweep(void); +void loadDefaultProps(void); extern int8_t sweep_enabled; +/* + * flash.c + */ +#define SAVEAREA_MAX 5 +// Begin addr 0x08018000 +#define SAVE_CONFIG_AREA_SIZE 0x00008000 +// config save area +#define SAVE_CONFIG_ADDR 0x08018000 +// properties_t save area +#define SAVE_PROP_CONFIG_0_ADDR 0x08018800 +#define SAVE_PROP_CONFIG_1_ADDR 0x0801a000 +#define SAVE_PROP_CONFIG_2_ADDR 0x0801b800 +#define SAVE_PROP_CONFIG_3_ADDR 0x0801d000 +#define SAVE_PROP_CONFIG_4_ADDR 0x0801e800 + /* * ui.c */ @@ -144,7 +163,7 @@ extern void tlv320aic3204_select(int channel); #define FREQUENCIES_XPOS1 OFFSETX #define FREQUENCIES_XPOS2 200 -#define FREQUENCIES_YPOS (HEIGHT+1) +#define FREQUENCIES_YPOS (240-7) // GRIDX calculated depends from frequency span //#define GRIDY 29 @@ -167,6 +186,7 @@ extern int16_t area_height; extern const uint8_t x5x7_bits []; #define FONT_GET_DATA(ch) (&x5x7_bits[ch*7]) #define FONT_GET_WIDTH(ch) (8-(x5x7_bits[ch*7]&7)) +#define FONT_MAX_WIDTH 7 #define FONT_GET_HEIGHT 7 extern const uint16_t numfont16x22[]; @@ -187,8 +207,9 @@ extern const uint16_t numfont16x22[]; #define TRACES_MAX 4 +#define MAX_TRACE_TYPE 12 enum { - TRC_LOGMAG, TRC_PHASE, TRC_DELAY, TRC_SMITH, TRC_POLAR, TRC_LINEAR, TRC_SWR, TRC_REAL, TRC_IMAG, TRC_R, TRC_X, TRC_OFF + TRC_LOGMAG=0, TRC_PHASE, TRC_DELAY, TRC_SMITH, TRC_POLAR, TRC_LINEAR, TRC_SWR, TRC_REAL, TRC_IMAG, TRC_R, TRC_X, TRC_OFF }; // Mask for define rectangular plot #define RECTANGULAR_GRID_MASK ((1<>5) ) #define RGBHEX(hex) ( (((hex)&0x001c00)<<3) | (((hex)&0x0000f8)<<5) | (((hex)&0xf80000)>>16) | (((hex)&0x00e000)>>13) ) +// Define size of screen buffer in pixels (one pixel 16bit size) +#define SPI_BUFFER_SIZE 2048 + #define DEFAULT_FG_COLOR RGB565(255,255,255) #define DEFAULT_BG_COLOR RGB565( 0, 0, 0) #define DEFAULT_GRID_COLOR RGB565(128,128,128) @@ -315,7 +339,7 @@ extern int16_t vbat; extern uint16_t foreground_color; extern uint16_t background_color; -extern uint16_t spi_buffer[2048]; +extern uint16_t spi_buffer[SPI_BUFFER_SIZE]; void ili9341_init(void); //void ili9341_setRotation(uint8_t r); @@ -324,6 +348,7 @@ void ili9341_bulk(int x, int y, int w, int h); void ili9341_fill(int x, int y, int w, int h, int color); void setForegroundColor(uint16_t fg); void setBackgroundColor(uint16_t fg); +void clearScreen(void); void blit8BitWidthBitmap(uint16_t x, uint16_t y, uint16_t width, uint16_t height, const uint8_t *bitmap); void blit16BitWidthBitmap(uint16_t x, uint16_t y, uint16_t width, uint16_t height, const uint16_t *bitmap); void ili9341_drawchar(uint8_t ch, int x, int y); @@ -458,6 +483,10 @@ int16_t adc_vbat_read(ADC_TypeDef *adc); /* * misclinous */ +int plot_printf(char *str, int, const char *fmt, ...); #define PULSE do { palClearPad(GPIOC, GPIOC_LED); palSetPad(GPIOC, GPIOC_LED);} while(0) +// Speed profile definition +#define START_PROFILE systime_t time = chVTGetSystemTimeX(); +#define STOP_PROFILE {char string_buf[12];plot_printf(string_buf, sizeof string_buf, "T:%06d", chVTGetSystemTimeX() - time);ili9341_drawstringV(string_buf, 1, 60);} /*EOF*/ diff --git a/numfont20x22.c b/numfont20x22.c index 924d1aa..34ce947 100644 --- a/numfont20x22.c +++ b/numfont20x22.c @@ -98,8 +98,8 @@ const uint16_t numfont16x22[] = { 0b0111111111111110, 0b0111110000111110, 0b1111100000011111, - 0b1111000000011111, - 0b1111000000011111, + 0b1111000000001111, + 0b1111000000001111, 0b0000000000011110, 0b0000000000111110, 0b0000000111111100, @@ -305,7 +305,7 @@ const uint16_t numfont16x22[] = { 0b0000000000001111, 0b0000000000011111, 0b0000000000111111, - 0b0000000000111111, + 0b0000000001111111, 0b0000000000001111, 0b0000000000001111, 0b0000000000001111, @@ -381,10 +381,10 @@ const uint16_t numfont16x22[] = { 0b1111000000000000, 0b1111000000000000, 0b1111000000000000, - 0b1111000000000000, - 0b1111000001111111, - 0b1111000001111111, - 0b1111000001111111, + 0b1111000000111111, + 0b1111000000111111, + 0b1111000000111111, + 0b1111000000000111, 0b1111000000001111, 0b1111100000011111, 0b0111110000111111, diff --git a/plot.c b/plot.c index 3c48dd4..b696397 100644 --- a/plot.c +++ b/plot.c @@ -5,7 +5,7 @@ #include "chprintf.h" #include "nanovna.h" -static void cell_draw_marker_info(int m, int n, int w, int h); +static void cell_draw_marker_info(int x0, int y0); int16_t grid_offset; int16_t grid_width; @@ -16,6 +16,10 @@ int16_t area_height = AREA_HEIGHT_NORMAL; // Depends from spi_buffer size, CELLWIDTH*CELLHEIGHT <= sizeof(spi_buffer) #define CELLWIDTH (64) #define CELLHEIGHT (32) +// Check buffer size +#if CELLWIDTH*CELLHEIGHT > SPI_BUFFER_SIZE +#error "Too small spi_buffer size SPI_BUFFER_SIZE < CELLWIDTH*CELLHEIGH" +#endif // indicate dirty cells (not redraw if cell data not changed) #define MAX_MARKMAP_X ((320+CELLWIDTH-1)/CELLWIDTH) @@ -565,23 +569,23 @@ format_smith_value(char *buf, int len, const float coeff[2], uint32_t frequency) float value; switch (marker_smith_format) { case MS_LIN: - chsnprintf(buf, len, "%.2f %.1f" S_DEGREE, linear(coeff), phase(coeff)); + plot_printf(buf, len, "%.2f %.1f" S_DEGREE, linear(coeff), phase(coeff)); break; case MS_LOG: { float v = logmag(coeff); if (v == -INFINITY) - chsnprintf(buf, len, "-"S_INFINITY" dB"); + plot_printf(buf, len, "-"S_INFINITY" dB"); else - chsnprintf(buf, len, "%.1fdB %.1f" S_DEGREE, v, phase(coeff)); + plot_printf(buf, len, "%.1fdB %.1f" S_DEGREE, v, phase(coeff)); } break; case MS_REIM: - chsnprintf(buf, len, "%F%+Fj", coeff[0], coeff[1]); + plot_printf(buf, len, "%F%+Fj", coeff[0], coeff[1]); break; case MS_RX: - chsnprintf(buf, len, "%F"S_OHM"%+Fj", zr, zi); + plot_printf(buf, len, "%F"S_OHM"%+Fj", zr, zi); break; case MS_RLC: @@ -593,7 +597,7 @@ format_smith_value(char *buf, int len, const float coeff[2], uint32_t frequency) prefix = 'H'; value = zi / (2 * M_PI * frequency); } - chsnprintf(buf, len, "%F"S_OHM" %F%c", zr, value, prefix); + plot_printf(buf, len, "%F"S_OHM" %F%c", zr, value, prefix); break; } } @@ -646,11 +650,11 @@ trace_get_value_string(int t, char *buf, int len, float array[POINTS_COUNT][2], return; //case TRC_ADMIT: case TRC_POLAR: - chsnprintf(buf, len, "%.2f%+.2fj", coeff[0], coeff[1]); + plot_printf(buf, len, "%.2f%+.2fj", coeff[0], coeff[1]); default: return; } - chsnprintf(buf, len, format, v); + plot_printf(buf, len, format, v); } static void @@ -704,12 +708,12 @@ trace_get_value_string_delta(int t, char *buf, int len, float array[POINTS_COUNT break; //case TRC_ADMIT: case TRC_POLAR: - chsnprintf(buf, len, "%.2f%+.2fj", coeff[0], coeff[1]); + plot_printf(buf, len, "%.2f%+.2fj", coeff[0], coeff[1]); return; default: return; } - chsnprintf(buf, len, format, v); + plot_printf(buf, len, format, v); } static int @@ -719,18 +723,18 @@ trace_get_info(int t, char *buf, int len) float scale = get_trace_scale(t); switch (trace[t].type) { case TRC_LOGMAG: - return chsnprintf(buf, len, "%s %ddB/", name, (int)scale); + return plot_printf(buf, len, "%s %ddB/", name, (int)scale); case TRC_PHASE: - return chsnprintf(buf, len, "%s %d" S_DEGREE "/", name, (int)scale); + return plot_printf(buf, len, "%s %d" S_DEGREE "/", name, (int)scale); case TRC_SMITH: //case TRC_ADMIT: case TRC_POLAR: if (scale != 1.0) - return chsnprintf(buf, len, "%s %.1fFS", name, scale); + return plot_printf(buf, len, "%s %.1fFS", name, scale); else - return chsnprintf(buf, len, "%s ", name); + return plot_printf(buf, len, "%s ", name); default: - return chsnprintf(buf, len, "%s %F/", name, scale); + return plot_printf(buf, len, "%s %F/", name, scale); } return 0; } @@ -835,98 +839,37 @@ markmap_upperarea(void) invalidateRect(0, 0, AREA_WIDTH_NORMAL, 31); } -#define INSIDE 0b0000; -#define LEFT 0b0001; -#define RIGHT 0b0010; -#define BOTTOM 0b0100; -#define TOP 0b1000; - -static uint32_t -_compute_outcode(int w, int h, int x, int y) +#define SWAP(x,y) {int t=x;x=y;y=t;} +// +// in most cases _compute_outcode clip calculation not give render line speedup +// +static inline void +cell_drawline(int x0, int y0, int x1, int y1, int c) { - uint32_t code = INSIDE; - if (x < 0) { - code |= LEFT; - } else - if (x > w) { - code |= RIGHT; - } - if (y < 0) { - code |= BOTTOM; - } else - if (y > h) { - code |= TOP; - } - return code; -} + if (x0<0 && x1<0) return; + if (y0<0 && y1<0) return; + if (x0>=CELLWIDTH && x1>=CELLWIDTH )return; + if (y0>=CELLHEIGHT && y1>=CELLHEIGHT)return; -static void -cell_drawline(int w, int h, int x0, int y0, int x1, int y1, int c) -{ - uint32_t outcode1 = _compute_outcode(w, h, x0, y0); - uint32_t outcode2 = _compute_outcode(w, h, x1, y1); - if (outcode1 & outcode2) { - // this line is out of requested area. early return - return; - } - // If outcode1 == 0 && outcode2 == 0, no clipping, not need check - //outcode1+=outcode2; // modifed Bresenham's line algorithm, see https://en.wikipedia.org/wiki/Bresenham%27s_line_algorithm - int dx = x1 - x0, sx = 1; if (dx < 0) {dx = -dx; sx = -1;} + if (x1 < x0) {SWAP(x0,x1);SWAP(y0,y1);} + int dx = x1 - x0; int dy = y1 - y0, sy = 1; if (dy < 0) {dy = -dy; sy = -1;} int err = (dx > dy ? dx : -dy) / 2; while (1){ - if (//outcode1 == 0 || - (y0 >= 0 && y0 < h && x0 >= 0 && x0 < w)) - spi_buffer[y0*w+x0] |= c; + if (y0>=0 && y0=0 && x0 -dx) { err -= dy; x0 += sx; } - if (e2 < dy) { err += dx; y0 += sy; } - } -} - -#if 0 -int -search_index_range(int x, int y, uint32_t index[POINTS_COUNT], int *i0, int *i1) -{ - int i, j; - int head = 0; - int tail = sweep_points; - i = 0; - x &= 0x03e0; - y &= 0x03e0; - while (head < tail) { - i = (head + tail) / 2; - if (x < CELL_X0(index[i])) - tail = i+1; - else if (x > CELL_X0(index[i])) - head = i; - else if (y < CELL_Y0(index[i])) - tail = i+1; - else if (y > CELL_Y0(index[i])) - head = i; - else - break; + if (e2 > -dx) { err -= dy; x0++; } + if (e2 < dy) { err += dx; y0+=sy;} } - - if (x != CELL_X0(index[i]) || y != CELL_Y0(index[i])) - return FALSE; - - j = i; - while (j > 0 && x == CELL_X0(index[j-1]) && y == CELL_Y0(index[j-1])) - j--; - *i0 = j; - j = i; - while (j < POINTS_COUNT-1 && x == CELL_X0(index[j+1]) && y == CELL_Y0(index[j+1])) - j++; - *i1 = j; - return TRUE; } -#endif +// Give a little speedup then draw rectangular plot (50 systick on all calls, all render req 700 systick) +// Write more difficult algoritm for seach indexes not give speedup static int search_index_range_x(int x1, int x2, uint32_t index[POINTS_COUNT], int *i0, int *i1) { @@ -967,7 +910,7 @@ search_index_range_x(int x1, int x2, uint32_t index[POINTS_COUNT], int *i0, int return TRUE; } -#define REFERENCE_WIDTH 5 +#define REFERENCE_WIDTH 6 #define REFERENCE_HEIGHT 5 #define REFERENCE_X_OFFSET 5 #define REFERENCE_Y_OFFSET 2 @@ -982,17 +925,17 @@ static const uint8_t reference_bitmap[]={ }; static void -draw_refpos(int w, int h, int x, int y, int c) +draw_refpos(int x, int y, int c) { int y0=y, j; for (j=0; j= h) + if (y0 < 0 || y0 >= CELLHEIGHT) continue; int x0=x; uint8_t bits = reference_bitmap[j]; while (bits){ - if (x0 >= 0 && x0 < w) - spi_buffer[y0*w+x0] = (bits&0x80) ? c : DEFAULT_BG_COLOR; + if (x0 >= 0 && x0 < CELLWIDTH) + spi_buffer[y0*CELLWIDTH+x0] = (bits&0x80) ? c : DEFAULT_BG_COLOR; x0++; bits<<=1; } @@ -1051,21 +994,21 @@ static const uint8_t marker_bitmap[]={ }; static void -draw_marker(int w, int h, int x, int y, int c, int ch) +draw_marker(int x, int y, int c, int ch) { int y0=y, j; for (j=0;j= 0 && x0 < w && y0 >= 0 && y0 < h){ + if (x0 >= 0 && x0 < CELLWIDTH && y0 >= 0 && y0 < CELLHEIGHT){ if (bits&0x80) - spi_buffer[y0*w+x0] = c; + spi_buffer[y0*CELLWIDTH+x0] = c; else if (force_color) - spi_buffer[y0*w+x0] = DEFAULT_BG_COLOR; + spi_buffer[y0*CELLWIDTH+x0] = DEFAULT_BG_COLOR; } x0++; bits<<=1; @@ -1253,6 +1196,7 @@ draw_cell(int m, int n) int x, y; int i0, i1, i; int t; + uint16_t c; // Clip cell by area if (x0 + w > area_width) w = area_width - x0; @@ -1260,62 +1204,81 @@ draw_cell(int m, int n) h = area_height - y0; if (w <= 0 || h <= 0) return; +// PULSE; - PULSE; - // Clear buffer - memset(spi_buffer, DEFAULT_BG_COLOR, sizeof spi_buffer); - uint16_t c = config.grid_color; - // Draw grid - for (t = 0; t < TRACES_MAX; t++) { - if (!trace[t].enabled) - continue; - uint32_t trace_type = (1<= CELLOFFSETX && x+x0 <= WIDTH+CELLOFFSETX) - spi_buffer[y * w + x] = c; - } + // Clear buffer ("0 : height" lines) +#if 0 + // use memset 350 system ticks for all screen calls + // as understand it use 8 bit set, slow down on 32 bit systems + memset(spi_buffer, DEFAULT_BG_COLOR, (h*CELLWIDTH)*sizeof(uint16_t)); +#else + // use direct set 35 system ticks for all screen calls +#if CELLWIDTH%8 != 0 +#error "CELLWIDTH % 8 should be == 0 for speed, or need rewrite cell cleanup" +#endif + // Set DEFAULT_BG_COLOR for 8 pixels in one cycle + int count = h*CELLWIDTH / 8; + uint32_t *p = (uint32_t *)spi_buffer; + while (count--) { + p[0] = DEFAULT_BG_COLOR|(DEFAULT_BG_COLOR<<16); + p[1] = DEFAULT_BG_COLOR|(DEFAULT_BG_COLOR<<16); + p[2] = DEFAULT_BG_COLOR|(DEFAULT_BG_COLOR<<16); + p[3] = DEFAULT_BG_COLOR|(DEFAULT_BG_COLOR<<16); + p+=4; + } +#endif + +// Draw grid +#if 1 + c = config.grid_color; + // Generate grid type list + uint32_t trace_type = 0; + for (t = 0; t < TRACES_MAX; t++) + if (trace[t].enabled) + trace_type|=(1<= CELLOFFSETX && x+x0 <= WIDTH+CELLOFFSETX) + spi_buffer[y * CELLWIDTH + x] = c; + } } + } + // Smith greed line (1000 system ticks for all screen calls) + if(trace_type&(1<=0 && x-MARKER_WIDTH=0 && y-MARKER_HEIGHT=0 && x-MARKER_WIDTH=0 && y-MARKER_HEIGHT=0 && x-REFERENCE_WIDTH=0 && x-REFERENCE_WIDTH=0 && y-REFERENCE_HEIGHT=0 && y-REFERENCE_HEIGHT= h || x <= -ch_size || x >= w) +// if (y <= -FONT_GET_HEIGHT || y >= CELLHEIGHT || x <= -ch_size || x >= CELLWIDTH) +// return ch_size; + if (x <= -ch_size) return ch_size; for(c = 0; c < FONT_GET_HEIGHT; c++) { bits = *char_buf++; - if ((y + c) < 0 || (y + c) >= h) + if ((y + c) < 0 || (y + c) >= CELLHEIGHT) continue; for (r = 0; r < ch_size; r++) { - if ((x+r) >= 0 && (x+r) < w && (0x80 & bits)) - spi_buffer[(y+c)*w + (x+r)] = foreground_color; + if ((x+r) >= 0 && (x+r) < CELLWIDTH && (0x80 & bits)) + spi_buffer[(y+c)*CELLWIDTH + (x+r)] = foreground_color; bits <<= 1; } } @@ -1467,142 +1448,136 @@ cell_drawchar(int w, int h, uint8_t ch, int x, int y) } static void -cell_drawstring(int w, int h, char *str, int x, int y) +cell_drawstring(char *str, int x, int y) { + if (y <= -FONT_GET_HEIGHT || y >= CELLHEIGHT) + return; while (*str) { - x += cell_drawchar(w, h, *str, x, y); - str++; + if (x >= CELLWIDTH) + return; + x += cell_drawchar(*str++, x, y); } } static void -cell_draw_marker_info(int m, int n, int w, int h) +cell_draw_marker_info(int x0, int y0) { - char buf[32]; + char buf[24]; int t; - if (n != 0) - return; if (active_marker < 0) return; int idx = markers[active_marker].index; int j = 0; - if (active_marker != -1 && previous_marker != -1 && uistat.current_trace != -1) { + if (previous_marker != -1 && uistat.current_trace != -1) { int t = uistat.current_trace; int mk; for (mk = 0; mk < MARKERS_MAX; mk++) { if (!markers[mk].enabled) continue; - int xpos = 1 + (j%2)*146; - int ypos = 1 + (j/2)*8; - xpos -= m * CELLWIDTH - CELLOFFSETX; - ypos -= n * CELLHEIGHT; + int xpos = 1 + (j%2)*(WIDTH/2) + CELLOFFSETX - x0; + int ypos = 1 + (j/2)*(FONT_GET_HEIGHT+1) - y0; setForegroundColor(config.trace_color[t]); if (mk == active_marker) - cell_drawstring(w, h, S_SARROW, xpos, ypos); + cell_drawstring(S_SARROW, xpos, ypos); xpos += 5; - chsnprintf(buf, sizeof buf, "M%d", mk+1); - cell_drawstring(w, h, buf, xpos, ypos); + plot_printf(buf, sizeof buf, "M%d", mk+1); + cell_drawstring(buf, xpos, ypos); xpos += 13; //trace_get_info(t, buf, sizeof buf); uint32_t freq = frequencies[markers[mk].index]; if (uistat.marker_delta && mk != active_marker) { uint32_t freq1 = frequencies[markers[active_marker].index]; uint32_t delta = freq > freq1 ? freq - freq1 : freq1 - freq; - chsnprintf(buf, sizeof buf, S_DELTA"%.9qHz", delta); + plot_printf(buf, sizeof buf, S_DELTA"%.9qHz", delta); } else { - chsnprintf(buf, sizeof buf, "%.10qHz", freq); + plot_printf(buf, sizeof buf, "%.10qHz", freq); } - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); xpos += 67; if (uistat.marker_delta && mk != active_marker) trace_get_value_string_delta(t, buf, sizeof buf, measured[trace[t].channel], markers[mk].index, markers[active_marker].index); else trace_get_value_string(t, buf, sizeof buf, measured[trace[t].channel], markers[mk].index); setForegroundColor(DEFAULT_FG_COLOR); - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); j++; } // draw marker delta if (!uistat.marker_delta && previous_marker >= 0 && active_marker != previous_marker && markers[previous_marker].enabled) { int idx0 = markers[previous_marker].index; - int xpos = 180; - int ypos = 1 + (j/2)*8; - xpos -= m * CELLWIDTH -CELLOFFSETX; - ypos -= n * CELLHEIGHT; - chsnprintf(buf, sizeof buf, S_DELTA"%d-%d", active_marker+1, previous_marker+1); + int xpos = (WIDTH/2+30) + CELLOFFSETX - x0; + int ypos = 1 + (j/2)*(FONT_GET_HEIGHT+1) - y0; + + plot_printf(buf, sizeof buf, S_DELTA"%d-%d:", active_marker+1, previous_marker+1); setForegroundColor(DEFAULT_FG_COLOR); - cell_drawstring(w, h, buf, xpos, ypos); - xpos += 24; + cell_drawstring(buf, xpos, ypos); + xpos += 27; if ((domain_mode & DOMAIN_MODE) == DOMAIN_FREQ) { uint32_t freq = frequencies[idx]; uint32_t freq1 = frequencies[idx0]; uint32_t delta = freq > freq1 ? freq - freq1 : freq1 - freq; - chsnprintf(buf, sizeof buf, "%c%.13qHz", freq >= freq1 ? '+' : '-', delta); + plot_printf(buf, sizeof buf, "%c%.13qHz", freq >= freq1 ? '+' : '-', delta); } else { - chsnprintf(buf, sizeof buf, "%Fs (%Fm)", time_of_index(idx) - time_of_index(idx0), distance_of_index(idx) - distance_of_index(idx0)); + plot_printf(buf, sizeof buf, "%Fs (%Fm)", time_of_index(idx) - time_of_index(idx0), distance_of_index(idx) - distance_of_index(idx0)); } - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); } } else { for (t = 0; t < TRACES_MAX; t++) { if (!trace[t].enabled) continue; - int xpos = 1 + (j%2)*146; - int ypos = 1 + (j/2)*8; - xpos -= m * CELLWIDTH -CELLOFFSETX; - ypos -= n * CELLHEIGHT; + int xpos = 1 + (j%2)*(WIDTH/2) + CELLOFFSETX - x0; + int ypos = 1 + (j/2)*(FONT_GET_HEIGHT+1) - y0; + setForegroundColor(config.trace_color[t]); if (t == uistat.current_trace) - cell_drawstring(w, h, S_SARROW, xpos, ypos); + cell_drawstring(S_SARROW, xpos, ypos); xpos += 5; - chsnprintf(buf, sizeof buf, "CH%d", trace[t].channel); - cell_drawstring(w, h, buf, xpos, ypos); + plot_printf(buf, sizeof buf, "CH%d", trace[t].channel); + cell_drawstring(buf, xpos, ypos); xpos += 19; int n = trace_get_info(t, buf, sizeof buf); - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); xpos += n * 5 + 2; //xpos += 60; trace_get_value_string(t, buf, sizeof buf, measured[trace[t].channel], idx); setForegroundColor(DEFAULT_FG_COLOR); - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); j++; } // draw marker frequency - int xpos = 185; - int ypos = 1 + (j/2)*8; - xpos -= m * CELLWIDTH -CELLOFFSETX; - ypos -= n * CELLHEIGHT; + int xpos = (WIDTH/2+40) + CELLOFFSETX - x0; + int ypos = 1 + (j/2)*(FONT_GET_HEIGHT+1) - y0; + setForegroundColor(DEFAULT_FG_COLOR); if (uistat.lever_mode == LM_MARKER) - cell_drawstring(w, h, S_SARROW, xpos, ypos); + cell_drawstring(S_SARROW, xpos, ypos); xpos += 5; - chsnprintf(buf, sizeof buf, "M%d:", active_marker+1); - cell_drawstring(w, h, buf, xpos, ypos); + plot_printf(buf, sizeof buf, "M%d:", active_marker+1); + cell_drawstring(buf, xpos, ypos); xpos += 19; if ((domain_mode & DOMAIN_MODE) == DOMAIN_FREQ) { - chsnprintf(buf, sizeof buf, "%qHz", frequencies[idx]); + plot_printf(buf, sizeof buf, "%qHz", frequencies[idx]); } else { - chsnprintf(buf, sizeof buf, "%Fs (%Fm)", time_of_index(idx), distance_of_index(idx)); + plot_printf(buf, sizeof buf, "%Fs (%Fm)", time_of_index(idx), distance_of_index(idx)); } - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); } setForegroundColor(DEFAULT_FG_COLOR); if (electrical_delay != 0) { // draw electrical delay - int xpos = 21; - int ypos = 1 + ((j+1)/2)*8; - xpos -= m * CELLWIDTH -CELLOFFSETX; - ypos -= n * CELLHEIGHT; + int xpos = 21 + CELLOFFSETX - x0; + int ypos = 1 + ((j+1)/2)*(FONT_GET_HEIGHT+1) - y0; float light_speed_ps = 299792458e-12; //(m/ps) - chsnprintf(buf, sizeof buf, "Edelay %Fs %Fm", electrical_delay * 1e-12, + plot_printf(buf, sizeof buf, "Edelay %Fs %Fm", electrical_delay * 1e-12, electrical_delay * light_speed_ps * velocity_factor); - cell_drawstring(w, h, buf, xpos, ypos); + cell_drawstring(buf, xpos, ypos); } } @@ -1613,25 +1588,25 @@ draw_frequencies(void) char buf2[32];buf2[0]=0; if ((domain_mode & DOMAIN_MODE) == DOMAIN_FREQ) { if (FREQ_IS_STARTSTOP()) { - chsnprintf(buf1, sizeof(buf1), " START %qHz", frequency0); - chsnprintf(buf2, sizeof(buf2), " STOP %qHz", frequency1); + plot_printf(buf1, sizeof(buf1), " START %qHz", frequency0); + plot_printf(buf2, sizeof(buf2), " STOP %qHz", frequency1); } else if (FREQ_IS_CENTERSPAN()) { - chsnprintf(buf1, sizeof(buf1), " CENTER %qHz", FREQ_CENTER()); - chsnprintf(buf2, sizeof(buf2), " SPAN %qHz", FREQ_SPAN()); + plot_printf(buf1, sizeof(buf1), " CENTER %qHz", FREQ_CENTER()); + plot_printf(buf2, sizeof(buf2), " SPAN %qHz", FREQ_SPAN()); } else { - chsnprintf(buf1, sizeof(buf1), " CW %qHz", frequency0); + plot_printf(buf1, sizeof(buf1), " CW %qHz", frequency0); } } else { - chsnprintf(buf1, sizeof(buf1), " START 0s"); - chsnprintf(buf2, sizeof(buf2), "STOP %Fs (%Fm)", time_of_index(POINTS_COUNT-1), distance_of_index(POINTS_COUNT-1)); + plot_printf(buf1, sizeof(buf1), " START 0s"); + plot_printf(buf2, sizeof(buf2), "STOP %Fs (%Fm)", time_of_index(POINTS_COUNT-1), distance_of_index(POINTS_COUNT-1)); } setForegroundColor(DEFAULT_FG_COLOR); setBackgroundColor(DEFAULT_BG_COLOR); - ili9341_fill(0, 232, 320, 8, DEFAULT_BG_COLOR); + ili9341_fill(0, FREQUENCIES_YPOS, 320, FONT_GET_HEIGHT, DEFAULT_BG_COLOR); if (uistat.lever_mode == LM_CENTER) - buf1[0] = S_SARROW[0]; + buf1[0] = S_SARROW[0]; if (uistat.lever_mode == LM_SPAN) - buf2[0] = S_SARROW[0]; + buf2[0] = S_SARROW[0]; ili9341_drawstring(buf1, FREQUENCIES_XPOS1, FREQUENCIES_YPOS); ili9341_drawstring(buf2, FREQUENCIES_XPOS2, FREQUENCIES_YPOS); } @@ -1688,11 +1663,11 @@ draw_battery_status(void) { if (vbat<=0) return; - uint8_t string_buf[25]; + uint8_t string_buf[16]; // Set battery color setForegroundColor(vbat < BATTERY_WARNING_LEVEL ? DEFAULT_LOW_BAT_COLOR : DEFAULT_NORMAL_BAT_COLOR); setBackgroundColor(DEFAULT_BG_COLOR); -// chsnprintf(string_buf, sizeof string_buf, "V:%d", vbat); +// plot_printf(string_buf, sizeof string_buf, "V:%d", vbat); // ili9341_drawstringV(string_buf, 1, 60); // Prepare battery bitmap image // Battery top @@ -1709,7 +1684,7 @@ draw_battery_status(void) // string_buf[x++] = 0b10000001; string_buf[x++] = 0b11111111; // Draw battery - blit8BitWidthBitmap(0, 1, 8, x, string_buf); + blit8BitWidthBitmap(1, 1, 8, x, string_buf); } void @@ -1722,7 +1697,8 @@ request_to_redraw_grid(void) void redraw_frame(void) { - ili9341_fill(0, 0, 320, 240, DEFAULT_BG_COLOR); + setBackgroundColor(DEFAULT_BG_COLOR); + clearScreen(); draw_frequencies(); draw_cal_status(); } diff --git a/si5351.c b/si5351.c index 8c548a3..56ba597 100644 --- a/si5351.c +++ b/si5351.c @@ -69,15 +69,17 @@ si5351_init(void) } } +static const uint8_t disable_output[] = { + SI5351_REG_16_CLK0_CONTROL, + SI5351_CLK_POWERDOWN, + SI5351_CLK_POWERDOWN, + SI5351_CLK_POWERDOWN +}; + void si5351_disable_output(void) { - uint8_t reg[4]; si5351_write(SI5351_REG_3_OUTPUT_ENABLE_CONTROL, 0xff); - reg[0] = SI5351_REG_16_CLK0_CONTROL; - reg[1] = SI5351_CLK_POWERDOWN; - reg[2] = SI5351_CLK_POWERDOWN; - reg[3] = SI5351_CLK_POWERDOWN; - si5351_bulk_write(reg, 4); + si5351_bulk_write(disable_output, sizeof(disable_output)); } void si5351_enable_output(void) @@ -85,19 +87,19 @@ void si5351_enable_output(void) si5351_write(SI5351_REG_3_OUTPUT_ENABLE_CONTROL, 0x00); } -void si5351_reset_pll(void) +static void si5351_reset_pll(void) { //si5351_write(SI5351_REG_177_PLL_RESET, SI5351_PLL_RESET_A | SI5351_PLL_RESET_B); si5351_write(SI5351_REG_177_PLL_RESET, 0xAC); } -void si5351_setupPLL(uint8_t pll, /* SI5351_PLL_A or SI5351_PLL_B */ +static void si5351_setupPLL(uint8_t pll, /* SI5351_PLL_A or SI5351_PLL_B */ uint8_t mult, uint32_t num, uint32_t denom) { /* Get the appropriate starting point for the PLL registers */ - const uint8_t pllreg_base[] = { + static const uint8_t pllreg_base[] = { SI5351_REG_26_PLL_A, SI5351_REG_34_PLL_B }; @@ -147,9 +149,9 @@ void si5351_setupPLL(uint8_t pll, /* SI5351_PLL_A or SI5351_PLL_B */ si5351_bulk_write(reg, 9); } -void +static void si5351_setupMultisynth(uint8_t output, - uint8_t pllSource, + uint8_t pllSource, uint32_t div, // 4,6,8, 8+ ~ 900 uint32_t num, uint32_t denom, @@ -157,12 +159,12 @@ si5351_setupMultisynth(uint8_t output, uint8_t drive_strength) { /* Get the appropriate starting point for the PLL registers */ - const uint8_t msreg_base[] = { + static const uint8_t msreg_base[] = { SI5351_REG_42_MULTISYNTH0, SI5351_REG_50_MULTISYNTH1, SI5351_REG_58_MULTISYNTH2, }; - const uint8_t clkctrl[] = { + static const uint8_t clkctrl[] = { SI5351_REG_16_CLK0_CONTROL, SI5351_REG_17_CLK1_CONTROL, SI5351_REG_18_CLK2_CONTROL @@ -226,7 +228,7 @@ si5351_setupMultisynth(uint8_t output, #define PLL_N 32 #define PLLFREQ (XTALFREQ * PLL_N) -void +static void si5351_set_frequency_fixedpll(int channel, int pll, uint32_t pllfreq, uint32_t freq, int rdiv, uint8_t drive_strength, int mul) { @@ -255,7 +257,7 @@ si5351_set_frequency_fixedpll(int channel, int pll, uint32_t pllfreq, uint32_t f si5351_setupMultisynth(channel, pll, div, num, denom, rdiv, drive_strength); } -void +static void si5351_set_frequency_fixeddiv(int channel, int pll, uint32_t freq, int div, uint8_t drive_strength, int mul) { @@ -291,6 +293,7 @@ si5351_set_frequency_fixeddiv(int channel, int pll, uint32_t freq, int div, * 100~150MHz fractional PLL 600-900MHz, fixed divider 6 * 150~200MHz fractional PLL 600-900MHz, fixed divider 4 */ +#if 0 void si5351_set_frequency(int channel, int freq, uint8_t drive_strength) { @@ -303,7 +306,7 @@ si5351_set_frequency(int channel, int freq, uint8_t drive_strength) si5351_set_frequency_fixeddiv(channel, SI5351_PLL_B, freq, 4, drive_strength, 1); } } - +#endif int current_band = -1; diff --git a/si5351.h b/si5351.h index 6606454..0a10c96 100644 --- a/si5351.h +++ b/si5351.h @@ -74,16 +74,4 @@ void si5351_init(void); -void si5351_setupPLL(uint8_t pll, /* SI5351_PLL_A or SI5351_PLL_B */ - uint8_t mult, - uint32_t num, - uint32_t denom); -void si5351_setupMultisynth(uint8_t output, - uint8_t pllSource, - uint32_t div, - uint32_t num, - uint32_t denom, - uint32_t rdiv, - uint8_t drive_strength); - void si5351_set_frequency(int channel, int freq, uint8_t drive_strength); diff --git a/ui.c b/ui.c index bd00964..24c59a6 100644 --- a/ui.c +++ b/ui.c @@ -86,16 +86,17 @@ typedef struct { #pragma pack(pop) // Touch screen -static int8_t last_touch_status = FALSE; +#define EVT_TOUCH_NONE 0 +#define EVT_TOUCH_DOWN 1 +#define EVT_TOUCH_PRESSED 2 +#define EVT_TOUCH_RELEASED 3 + +static int8_t last_touch_status = EVT_TOUCH_NONE; static int16_t last_touch_x; static int16_t last_touch_y; //int16_t touch_cal[4] = { 1000, 1000, 10*16, 12*16 }; //int16_t touch_cal[4] = { 620, 600, 130, 180 }; -#define EVT_TOUCH_NONE 0 -#define EVT_TOUCH_DOWN 1 -#define EVT_TOUCH_PRESSED 2 -#define EVT_TOUCH_RELEASED 3 int awd_count; //int touch_x, touch_y; @@ -287,57 +288,44 @@ touch_check(void) if (stat != last_touch_status) { last_touch_status = stat; - if (stat) { - return EVT_TOUCH_PRESSED; - } else { - return EVT_TOUCH_RELEASED; - } - } else { - if (stat) - return EVT_TOUCH_DOWN; - else - return EVT_TOUCH_NONE; + return stat ? EVT_TOUCH_PRESSED : EVT_TOUCH_RELEASED; } + return stat ? EVT_TOUCH_DOWN : EVT_TOUCH_NONE; } -static void -touch_wait_release(void) -{ - int status; - /* wait touch release */ - do { - status = touch_check(); - } while(status != EVT_TOUCH_RELEASED); +static inline void +touch_wait_release(void) { + while(touch_check()!=EVT_TOUCH_RELEASED); +} + +static inline void +touch_wait_pressed(void) { + while(touch_check()!=EVT_TOUCH_PRESSED); } void touch_cal_exec(void) { - int status; int x1, x2, y1, y2; adc_stop(ADC1); setForegroundColor(DEFAULT_FG_COLOR); setBackgroundColor(DEFAULT_BG_COLOR); - ili9341_fill(0, 0, 320, 240, DEFAULT_BG_COLOR); + clearScreen(); ili9341_line(0, 0, 0, 32); ili9341_line(0, 0, 32, 0); ili9341_drawstring("TOUCH UPPER LEFT", 10, 10); - do { - status = touch_check(); - } while(status != EVT_TOUCH_RELEASED); + touch_wait_release(); x1 = last_touch_x; y1 = last_touch_y; - ili9341_fill(0, 0, 320, 240, DEFAULT_BG_COLOR); + clearScreen(); ili9341_line(320-1, 240-1, 320-1, 240-32); ili9341_line(320-1, 240-1, 320-32, 240-1); ili9341_drawstring("TOUCH LOWER RIGHT", 230, 220); - do { - status = touch_check(); - } while(status != EVT_TOUCH_RELEASED); + touch_wait_release(); x2 = last_touch_x; y2 = last_touch_y; @@ -353,30 +341,26 @@ touch_cal_exec(void) void touch_draw_test(void) { - int status; int x0, y0; int x1, y1; adc_stop(ADC1); - ili9341_fill(0, 0, 320, 240, DEFAULT_BG_COLOR); setForegroundColor(DEFAULT_FG_COLOR); setBackgroundColor(DEFAULT_BG_COLOR); + clearScreen(); ili9341_drawstring("TOUCH TEST: DRAG PANEL", OFFSETX, 233); - do { - status = touch_check(); - } while(status != EVT_TOUCH_PRESSED); + touch_wait_pressed(); touch_position(&x0, &y0); do { - status = touch_check(); touch_position(&x1, &y1); ili9341_line(x0, y0, x1, y1); x0 = x1; y0 = y1; chThdSleepMilliseconds(50); - } while(status != EVT_TOUCH_RELEASED); + } while(touch_check()!=EVT_TOUCH_RELEASED); touch_start_watchdog(); } @@ -394,12 +378,11 @@ void show_version(void) { int x = 5, y = 5; - adc_stop(ADC1); - ili9341_fill(0, 0, 320, 240, DEFAULT_BG_COLOR); - setForegroundColor(DEFAULT_FG_COLOR); setBackgroundColor(DEFAULT_BG_COLOR); + + clearScreen(); ili9341_drawstring_size(BOARD_NAME, x, y, 4); y += 25; @@ -433,7 +416,7 @@ enter_dfu(void) setForegroundColor(DEFAULT_FG_COLOR); setBackgroundColor(DEFAULT_BG_COLOR); // leave a last message - ili9341_fill(0, 0, 320, 240, DEFAULT_BG_COLOR); + clearScreen(); ili9341_drawstring("DFU: Device Firmware Update Mode", x, y += 10); ili9341_drawstring("To exit DFU mode, please reset device yourself.", x, y += 10); @@ -496,9 +479,9 @@ menu_cal2_cb(int item, uint8_t data) case 3: // CORRECTION // toggle applying correction cal_status ^= CALSTAT_APPLY; - draw_menu(); break; } + draw_menu(); draw_cal_status(); //menu_move_back(); } @@ -507,12 +490,11 @@ static void menu_recall_cb(int item, uint8_t data) { (void)item; - if (caldata_recall(data) == 0) { - menu_move_back(); - ui_mode_normal(); - update_grid(); - draw_cal_status(); - } + caldata_recall(data); + menu_move_back(); + ui_mode_normal(); + update_grid(); + draw_cal_status(); } static void @@ -642,8 +624,7 @@ static void menu_velocity_cb(int item, uint8_t data){ (void)item; (void)data; - int status = btn_wait_release(); - if (status & EVT_BUTTON_DOWN_LONG) { + if (btn_wait_release() & EVT_BUTTON_DOWN_LONG) { ui_mode_numeric(KM_VELOCITY_FACTOR); ui_process_numeric(); } else { @@ -664,7 +645,7 @@ static void choose_active_marker(void) { int i; - for (i = 0; i < 4; i++) + for (i = 0; i < MARKERS_MAX; i++) if (markers[i].enabled) { active_marker = i; return; @@ -679,8 +660,7 @@ menu_scale_cb(int item, uint8_t data) if (data == KM_SCALE && trace[uistat.current_trace].type == TRC_DELAY) { data = KM_SCALEDELAY; } - int status = btn_wait_release(); - if (status & EVT_BUTTON_DOWN_LONG) { + if (btn_wait_release() & EVT_BUTTON_DOWN_LONG) { ui_mode_numeric(data); ui_process_numeric(); } else { @@ -693,15 +673,13 @@ static void menu_stimulus_cb(int item, uint8_t data) { (void)data; - int status; switch (item) { case 0: /* START */ case 1: /* STOP */ case 2: /* CENTER */ case 3: /* SPAN */ case 4: /* CW */ - status = btn_wait_release(); - if (status & EVT_BUTTON_DOWN_LONG) { + if (btn_wait_release() & EVT_BUTTON_DOWN_LONG) { ui_mode_numeric(item); ui_process_numeric(); } else { @@ -718,11 +696,10 @@ menu_stimulus_cb(int item, uint8_t data) } } - static uint32_t get_marker_frequency(int marker) { - if (marker < 0 || marker >= 4) + if (marker < 0 || marker >= MARKERS_MAX) return 0; if (!markers[marker].enabled) return 0; @@ -782,7 +759,7 @@ static void menu_marker_search_cb(int item, uint8_t data) { (void)data; - int i; + int i = -1; if (active_marker == -1) return; @@ -791,23 +768,19 @@ menu_marker_search_cb(int item, uint8_t data) case 1: /* minimum */ set_marker_search(item); i = marker_search(); - if (i != -1) - markers[active_marker].index = i; break; case 2: /* search Left */ i = marker_search_left(markers[active_marker].index); - if (i != -1) - markers[active_marker].index = i; break; case 3: /* search right */ i = marker_search_right(markers[active_marker].index); - if (i != -1) - markers[active_marker].index = i; break; case 4: /* tracking */ marker_tracking = !marker_tracking; break; } + if (i != -1) + markers[active_marker].index = i; draw_menu(); redraw_marker(active_marker, TRUE); select_lever_mode(LM_SEARCH); @@ -842,7 +815,8 @@ static void menu_marker_sel_cb(int item, uint8_t data) { (void)data; - if (item >= 0 && item < 4) { + int t; + if (item >= 0 && item < MARKERS_MAX) { if (markers[item].enabled) { if (item == active_marker) { // disable if active trace is selected @@ -856,10 +830,8 @@ menu_marker_sel_cb(int item, uint8_t data) active_marker_select(item); } } else if (item == 4) { /* all off */ - markers[0].enabled = FALSE; - markers[1].enabled = FALSE; - markers[2].enabled = FALSE; - markers[3].enabled = FALSE; + for (t = 0; t < MARKERS_MAX; t++) + markers[t].enabled = FALSE; previous_marker = -1; active_marker = -1; } else if (item == 5) { /* marker delta */ @@ -1076,7 +1048,7 @@ const menuitem_t menu_top[] = { #define MENU_STACK_DEPTH_MAX 4 uint8_t menu_current_level = 0; -const menuitem_t *menu_stack[4] = { +const menuitem_t *menu_stack[MENU_STACK_DEPTH_MAX] = { menu_top, NULL, NULL, NULL }; @@ -1157,6 +1129,10 @@ menu_invoke(int item) } } +#define MENU_BUTTON_WIDTH 60 +#define MENU_BUTTON_HEIGHT 30 +#define NUM_INPUT_HEIGHT 30 + #define KP_WIDTH 48 #define KP_HEIGHT 48 // Key x, y position (0 - 15) on screen @@ -1291,10 +1267,10 @@ draw_keypad(void) static void draw_numeric_area_frame(void) { - ili9341_fill(0, 208, 320, 32, DEFAULT_MENU_COLOR); + ili9341_fill(0, 240-NUM_INPUT_HEIGHT, 320, NUM_INPUT_HEIGHT, DEFAULT_MENU_COLOR); setForegroundColor(DEFAULT_MENU_TEXT_COLOR); setBackgroundColor(DEFAULT_MENU_COLOR); - ili9341_drawstring(keypad_mode_label[keypad_mode], 10, 220); + ili9341_drawstring(keypad_mode_label[keypad_mode], 10, 240-(FONT_GET_HEIGHT+NUM_INPUT_HEIGHT)/2); //ili9341_drawfont(KP_KEYPAD, 300, 216); } @@ -1320,22 +1296,22 @@ draw_numeric_input(const char *buf) if (ui_mode == UI_NUMERIC && uistat.digit == 8-i) { fg = DEFAULT_SPEC_INPUT_COLOR; focused = TRUE; - if (uistat.digit_mode) - bg = DEFAULT_MENU_COLOR; +// if (uistat.digit_mode) +// bg = DEFAULT_MENU_COLOR; } setForegroundColor(fg); setBackgroundColor(bg); if (c >= 0) // c is number - ili9341_drawfont(c, x, 208+4); + ili9341_drawfont(c, x, 240-NUM_INPUT_HEIGHT+4); else if (focused) // c not number, but focused - ili9341_drawfont(0, x, 208+4); + ili9341_drawfont(0, x, 240-NUM_INPUT_HEIGHT+4); else // erase - ili9341_fill(x, 208+4, 20, 24, bg); + ili9341_fill(x, 240-NUM_INPUT_HEIGHT+4, NUM_FONT_GET_HEIGHT, NUM_FONT_GET_WIDTH+2+8, bg); x += xsim&0x8000 ? NUM_FONT_GET_WIDTH+2+8 : NUM_FONT_GET_WIDTH+2; } // erase last - ili9341_fill(x, 208+4, NUM_FONT_GET_WIDTH+2+8, 24, DEFAULT_MENU_COLOR); + ili9341_fill(x, 240-NUM_INPUT_HEIGHT+4, NUM_FONT_GET_WIDTH+2+8, NUM_FONT_GET_WIDTH+2+8, DEFAULT_MENU_COLOR); } static int @@ -1353,7 +1329,7 @@ static void menu_item_modify_attribute(const menuitem_t *menu, int item, uint16_t *fg, uint16_t *bg) { - if (menu == menu_trace && item < 4) { + if (menu == menu_trace && item < TRACES_MAX) { if (trace[item].enabled) *bg = config.trace_color[item]; } else if (menu == menu_marker_sel) { @@ -1427,26 +1403,26 @@ draw_menu_buttons(const menuitem_t *menu) const char *l1, *l2; if (menu[i].type == MT_NONE) break; - if (menu[i].type == MT_BLANK) + if (menu[i].type == MT_BLANK) continue; - int y = 32*i; + int y = MENU_BUTTON_HEIGHT*i; uint16_t bg = config.menu_normal_color; uint16_t fg = DEFAULT_MENU_TEXT_COLOR; // focus only in MENU mode but not in KEYPAD mode if (ui_mode == UI_MENU && i == selection) bg = config.menu_active_color; - ili9341_fill(320-60, y, 60, 30, bg); + ili9341_fill(320-MENU_BUTTON_WIDTH, y, MENU_BUTTON_WIDTH, MENU_BUTTON_HEIGHT-2, bg); menu_item_modify_attribute(menu, i, &fg, &bg); setForegroundColor(fg); setBackgroundColor(bg); if (menu_is_multiline(menu[i].label, &l1, &l2)) { - ili9341_fill(320-57, y+6, 54, 19, bg); - ili9341_drawstring(l1, 320-55, y+8); - ili9341_drawstring(l2, 320-55, y+16); + ili9341_fill(320-MENU_BUTTON_WIDTH+3, y+5, MENU_BUTTON_WIDTH-6, 2+FONT_GET_HEIGHT+1+FONT_GET_HEIGHT+2, bg); + ili9341_drawstring(l1, 320-MENU_BUTTON_WIDTH+5, y+7); + ili9341_drawstring(l2, 320-MENU_BUTTON_WIDTH+5, y+7+FONT_GET_HEIGHT+1); } else { - ili9341_fill(320-57, y+10, 54, 11, bg); - ili9341_drawstring(menu[i].label, 320-55, y+12); + ili9341_fill(320-MENU_BUTTON_WIDTH+3, y+8, MENU_BUTTON_WIDTH-6, 2+FONT_GET_HEIGHT+2, bg); + ili9341_drawstring(menu[i].label, 320-MENU_BUTTON_WIDTH+5, y+10); } } } @@ -1474,9 +1450,8 @@ menu_apply_touch(void) break; if (menu[i].type == MT_BLANK) continue; - int y = 32*i; - if (y-2 < touch_y && touch_y < y+30+2 - && 320-60 < touch_x) { + int y = MENU_BUTTON_HEIGHT*i; + if (y < touch_y && touch_y < y+MENU_BUTTON_HEIGHT && 320-MENU_BUTTON_WIDTH < touch_x) { menu_select_touch(i); return; } @@ -1495,13 +1470,13 @@ draw_menu(void) static void erase_menu_buttons(void) { - ili9341_fill(320-60, 0, 60, 32*7, DEFAULT_BG_COLOR); + ili9341_fill(320-MENU_BUTTON_WIDTH, 0, MENU_BUTTON_WIDTH, MENU_BUTTON_HEIGHT*7, DEFAULT_BG_COLOR); } static void erase_numeric_input(void) { - ili9341_fill(0, 240-32, 320, 32, DEFAULT_BG_COLOR); + ili9341_fill(0, 240-NUM_INPUT_HEIGHT, 320, NUM_INPUT_HEIGHT, DEFAULT_BG_COLOR); } static void @@ -1601,7 +1576,7 @@ static void draw_numeric_area(void) { char buf[10]; - chsnprintf(buf, sizeof buf, "%9d", uistat.value); + plot_printf(buf, sizeof buf, "%9d", uistat.value); draw_numeric_input(buf); } @@ -1613,7 +1588,7 @@ ui_mode_menu(void) ui_mode = UI_MENU; /* narrowen plotting area */ - area_width = AREA_WIDTH_NORMAL - 60; + area_width = AREA_WIDTH_NORMAL - MENU_BUTTON_WIDTH; area_height = AREA_HEIGHT_NORMAL; ensure_selection(); draw_menu(); @@ -1631,7 +1606,7 @@ ui_mode_numeric(int _keypad_mode) keypad_mode = _keypad_mode; ui_mode = UI_NUMERIC; area_width = AREA_WIDTH_NORMAL; - area_height = 240-32;//AREA_HEIGHT_NORMAL - 32; + area_height = 240-NUM_INPUT_HEIGHT;//AREA_HEIGHT_NORMAL - 32; draw_numeric_area_frame(); fetch_numeric_target(); @@ -1653,7 +1628,7 @@ ui_mode_keypad(int _keypad_mode) keypads_last_index = i; ui_mode = UI_KEYPAD; - area_width = AREA_WIDTH_NORMAL - 60; + area_width = AREA_WIDTH_NORMAL - MENU_BUTTON_WIDTH; area_height = HEIGHT - 32; draw_menu(); draw_keypad(); @@ -1718,7 +1693,7 @@ step_round(uint32_t v) { // decade step uint32_t x = 1; - for (x = 1; x*10 < v; x *= 10) + for (x = 1; x*10 < v; x*= 10) ; // 1-2-5 step @@ -1764,7 +1739,7 @@ ui_process_normal(void) if (status & EVT_BUTTON_SINGLE_CLICK) { ui_mode_menu(); } else { - switch (uistat.lever_mode) { + switch (uistat.lever_mode) { case LM_MARKER: lever_move_marker(status); break; case LM_SEARCH: lever_search_marker(status); break; case LM_CENTER: @@ -1896,8 +1871,7 @@ keypad_apply_touch(void) while (keypads[i].c>=0) { int x = KP_GET_X(keypads[i].x); int y = KP_GET_Y(keypads[i].y); - if (x < touch_x && touch_x < x+KP_WIDTH - && y < touch_y && touch_y < y+KP_HEIGHT) { + if (x < touch_x && touch_x < x+KP_WIDTH && y < touch_y && touch_y < y+KP_HEIGHT) { // draw focus selection = i; draw_keypad(); @@ -2042,8 +2016,7 @@ ui_process_keypad(void) break; } - status = touch_check(); - if (status == EVT_TOUCH_PRESSED) { + if (touch_check() == EVT_TOUCH_PRESSED) { int key = keypad_apply_touch(); if (key >= 0 && keypad_click(key)) /* exit loop on done or cancel */ @@ -2077,11 +2050,9 @@ ui_process_lever(void) } } - static void drag_marker(int t, int m) { - int status; /* wait touch release */ do { int touch_x, touch_y; @@ -2095,9 +2066,7 @@ drag_marker(int t, int m) markers[m].frequency = frequencies[index]; redraw_marker(m, TRUE); } - - status = touch_check(); - } while(status != EVT_TOUCH_RELEASED); + } while(touch_check()!=EVT_TOUCH_RELEASED); } static int @@ -2147,21 +2116,15 @@ touch_lever_mode_select(void) int touch_x, touch_y; touch_position(&touch_x, &touch_y); if (touch_y > HEIGHT) { - if (touch_x < 160) { - select_lever_mode(LM_CENTER); - } else { - select_lever_mode(LM_SPAN); - } + select_lever_mode(touch_x < FREQUENCIES_XPOS2 ? LM_CENTER : LM_SPAN); return TRUE; } - if (touch_y < 15) { select_lever_mode(LM_MARKER); return TRUE; } - - return FALSE; - } + return FALSE; +} static void ui_process_touch(void) @@ -2173,10 +2136,9 @@ void ui_process_touch(void) if (status == EVT_TOUCH_PRESSED || status == EVT_TOUCH_DOWN) { switch (ui_mode) { case UI_NORMAL: - - if (touch_pickup_marker()) { + if (touch_pickup_marker()) break; - } else if (touch_lever_mode_select()) { + if (touch_lever_mode_select()) { draw_all(FALSE); touch_wait_release(); break;