From 74e577ac110513669a6d677842ceca4c5b1252ca Mon Sep 17 00:00:00 2001 From: fishsoupisgood Date: Sat, 4 May 2019 12:37:04 +0100 Subject: cut #1 --- Makefile.include | 2 +- app/Makefile | 39 +- app/bits.c | 2 +- app/dcf77.c | 89 ++-- app/events.h | 10 +- app/gps.c | 316 +++++++++-- app/gps_neo8.c | 1204 ++++++++++++++++++++++++++++++++++++++++++ app/led.c | 76 ++- app/lwip_glue.c | 11 +- app/main.c | 160 +++++- app/max7219.c | 143 +++++ app/msf.c | 96 ++-- app/new_almanac.c | 53 ++ app/parse_alamanc.pl | 91 ++++ app/pll.c | 2 +- app/project.h | 5 +- app/prototypes.h | 36 +- app/report.c | 15 + app/stdio.c | 4 +- app/steth.c | 13 +- app/steth.h | 16 +- app/ticker.c | 5 +- app/time_fn.c | 8 +- app/time_fn.h | 4 +- app/ubx.h | 8 + app/usart.c | 87 +-- oocd/board/stm32f407zet6.cfg | 5 + oocd/stm32-f407.cfg | 6 - 28 files changed, 2277 insertions(+), 229 deletions(-) create mode 100644 app/gps_neo8.c create mode 100644 app/max7219.c create mode 100644 app/new_almanac.c create mode 100755 app/parse_alamanc.pl create mode 100644 app/report.c create mode 100644 oocd/board/stm32f407zet6.cfg delete mode 100644 oocd/stm32-f407.cfg diff --git a/Makefile.include b/Makefile.include index 9225b89..5f26c34 100644 --- a/Makefile.include +++ b/Makefile.include @@ -32,7 +32,7 @@ OOCD ?= openocd #OOCD_INTERFACE ?= cmsis-dap #OOCD_BOARD ?= arch_max OOCD_INTERFACE ?= stlink-v2 -OOCD_BOARD ?= stm32f407vet6 +OOCD_BOARD ?= stm32f407zet6 ################################################################################ # Black Magic Probe specific variables diff --git a/app/Makefile b/app/Makefile index 20e34f1..c0bbf4c 100644 --- a/app/Makefile +++ b/app/Makefile @@ -25,8 +25,9 @@ PROG=msf V=1 default: ${PROG}.elf -CSRCS=led.c ticker.c ring.c usart.c stdio.c lwip_glue.c steth.c msf.c abs.c pll.c main.c time_fn.c ntp.c dcf77.c util.c stats.c gps.c hexdump.c bits.c -HSRCS=project.h ring.h pins.h gps.h ubx.h +CSRCS=led.c ticker.c ring.c usart.c stdio.c lwip_glue.c steth.c msf.c abs.c pll.c main.c time_fn.c ntp.c dcf77.c util.c stats.c gps.c hexdump.c bits.c max7219.c report.c +HSRCS= events.h gps.h project.h ring.h steth.h time_fn.h ubx.h + @@ -63,7 +64,7 @@ objs:${OBJS} ${MYOBJS}: project.h prototypes.h ${LWIP_OBJS}: lwip/lwipopts.h -OBJS=${MYOBJS} ${LWIP_OBJS} almanac.o +OBJS=${MYOBJS} ${LWIP_OBJS} include ../Makefile.include @@ -73,11 +74,26 @@ CPPFLAGS += -I../libopencm3-local -I${LWIP_PATH}/${LWIP}/src/include -Il fish: ${OBJS} echo ${OBJS} +HOST=clock-lnx +#HOST=10.32.91.140 + + +reset: + $(Q)$(OOCD) -f ../oocd/interface/$(OOCD_INTERFACE).cfg \ + -f ../oocd/board/$(OOCD_BOARD).cfg \ + -c "init" -c "reset run" \ + -c shutdown + + +fl: ${PROG}.hex + ssh ${HOST} flash_stm32 < ${PROG}.hex + program: ${PROG}.hex - echo init | nc -t localhost 4444 - echo reset init | nc -t localhost 4444 - echo flash write_image erase ${PWD}/$< | nc -t localhost 4444 - echo reset run | nc -t localhost 4444 + scp $< ${HOST}:/tmp/img.hex + echo init | nc -t ${HOST} 4444 + echo reset init | nc -t ${HOST} 4444 + echo flash write_image erase /tmp/img.hex | nc -t ${HOST} 4444 + echo reset run | nc -t ${HOST} 4444 ds: $(Q)$(OOCD) -f ../oocd/interface/$(OOCD_INTERFACE).cfg \ @@ -93,9 +109,12 @@ protos: ${CSRCS} ${CPROTO} -E "${CPP} $(CPPFLAGS)" -e -v ${CSRCS} > prototypes.h.tmp mv -f prototypes.h.tmp prototypes.h -almanac.c:almanac.alp - echo const > $@ - xxd -i $< >> $@ +almanac.txt: + wget -O $@ 'https://navcen.uscg.gov/?pageName=currentAlmanac&format=yuma' + +almanac.h:alamanc.txt parse_alamanc.pl + ./parse_alamanc.pl < almanac.txt > $@ || /bin/rm -f $@ + almanac.alp: almanac diff --git a/app/bits.c b/app/bits.c index 6978c74..3fe7833 100644 --- a/app/bits.c +++ b/app/bits.c @@ -17,6 +17,6 @@ void dump_bits (char *wot, uint8_t *bits) * (ptr++) = '\r'; * (ptr++) = '\n'; *ptr = 0; - usart1_write (buf, (unsigned) (ptr - buf), 1); + usart2_write (buf, (unsigned) (ptr - buf), 1); } diff --git a/app/dcf77.c b/app/dcf77.c index 2a952cd..e55fcfc 100644 --- a/app/dcf77.c +++ b/app/dcf77.c @@ -1,37 +1,54 @@ #include "project.h" -#define P1 (GPIO11) -#define P1_PORT GPIOD +#define J2(a,b) a ## b +#define J3(a,b,c) a ## b ## c -#define T (GPIO12) -#define T_PORT GPIOD +#define P1 (GPIO4) +#define P1_PORT GPIOE + +#define T_BIT 2 +#define T_PORT GPIOE +#define T_EXTI_LINE T_BIT + + + +#define M_T(a) J2(GPIO,a) +#define T M_T(T_BIT) +#define M_EXTI_T(a) J2(EXTI,a) +#define EXTI_T M_EXTI_T(T_EXTI_LINE) +#define M_exti_t_isr(a) J3(exti,a,_isr) +#define exti_t_isr M_exti_t_isr(T_EXTI_LINE) +#define M_NVIC_EXTI_T_IRQ(a) J3(NVIC_EXTI,a,_IRQ) +#define NVIC_EXTI_T_IRQ M_NVIC_EXTI_T_IRQ(T_EXTI_LINE) static Event_ring dcf77_ring; +static EPOCH dcf77_time; static uint64_t dcf77_last_second; uint64_t dcf77_last_happy; -void exti15_10_isr (void) +static char dcf77_info[40]; + +void exti_t_isr (void) { uint32_t now = SCS_DWT_CYCCNT; int v; v = !!gpio_get (T_PORT, T); - nvic_disable_irq (NVIC_EXTI15_10_IRQ); - exti_reset_request (EXTI12); + nvic_disable_irq (NVIC_EXTI_T_IRQ); + + exti_reset_request (EXTI_T); dcf77_ring.events[dcf77_ring.tx_ptr].when = now; dcf77_ring.events[dcf77_ring.tx_ptr].value = v; dcf77_ring.tx_ptr = (dcf77_ring.tx_ptr + 1) & ERING_MASK; - nvic_enable_irq (NVIC_EXTI15_10_IRQ); -} - - + nvic_enable_irq (NVIC_EXTI_T_IRQ); +} static uint8_t bits[60]; @@ -39,7 +56,7 @@ static uint8_t bits[60]; static void process_bits (uint64_t abs) { UTC u; - EPOCH dcf77_time; + EPOCH e; if (bits[0]) return; @@ -63,23 +80,28 @@ static void process_bits (uint64_t abs) - dcf77_time = time_utc_to_epoch (u); + e = time_utc_to_epoch (u); + + + e.s -= 3600; /*CET*/ - dcf77_time.s -= 2; /*Message arrives 2s early*/ + if (bits[17]) e.s -= 3600; /*CEST*/ - dcf77_time.s -= 3600; /*CET*/ - if (bits[17]) dcf77_time.s -= 3600; /*CEST*/ + e.s -= 2; /*Message arrives 2s early*/ + + dcf77_time = e; dcf77_last_happy = make_happy (abs, 60); - pll_set_offset (dcf77_time, abs); + pll_set_offset (e, abs); + printf ("DCF77: Next minute is: %02d-%02d-%02d %02d:%02d\r\n", u.year, u.month, u.mday, u.hour, u.minute); - time_print_epoch ("DCF77: ", dcf77_time); + time_print_epoch ("DCF77: ", e, dcf77_info); dump_bits ("dcf77", bits); } @@ -97,14 +119,6 @@ static void report_bit (uint64_t abs, int second, int b) } -static void report_time (uint64_t abs) -{ -#if 1 - EPOCH e = pll_decompose (abs); - time_print_epoch ("DCF77: ", e); -#endif -} - void dcf77_dispatch (void) { @@ -117,6 +131,7 @@ void dcf77_dispatch (void) uint32_t now; int v; + led2_set (!!gpio_get (T_PORT, T)); @@ -125,6 +140,9 @@ void dcf77_dispatch (void) v = dcf77_ring.events[dcf77_ring.rx_ptr].value; now = dcf77_ring.events[dcf77_ring.rx_ptr].when; + + //led2_set(v); + dcf77_ring.rx_ptr = (dcf77_ring.rx_ptr + 1) & ERING_MASK; if (v) { @@ -137,6 +155,7 @@ void dcf77_dispatch (void) last_s = now; is_s = 1; second++; + dcf77_time.s++; } if (pulse_w > 1300) { @@ -153,6 +172,9 @@ void dcf77_dispatch (void) else bit = 0; + + sprintf (dcf77_info, "m=%d s=%02d b=%d", had_m, second, bit); + if (had_m) report_bit (abs, second, bit); @@ -168,8 +190,7 @@ void dcf77_dispatch (void) pll_dispatch (dcf77_last_happy, abs, "DCF77"); - if (time_known) - report_time (abs); + report_time ("DCF", dcf77_time, abs, dcf77_info); } @@ -183,12 +204,16 @@ dcf77_init (void) MAP_INPUT (T); MAP_OUTPUT_PP (P1); + + gpio_set (P1_PORT, P1); + delay_ms (50); gpio_clear (P1_PORT, P1); - exti_select_source (EXTI12, T_PORT); - exti_set_trigger (EXTI12, EXTI_TRIGGER_BOTH); - exti_enable_request (EXTI12); - nvic_enable_irq (NVIC_EXTI15_10_IRQ); + exti_select_source (EXTI_T, T_PORT); + exti_set_trigger (EXTI_T, EXTI_TRIGGER_BOTH); + exti_enable_request (EXTI_T); + + nvic_enable_irq (NVIC_EXTI_T_IRQ); } diff --git a/app/events.h b/app/events.h index eb0fe89..8468851 100644 --- a/app/events.h +++ b/app/events.h @@ -2,13 +2,13 @@ #define ERING_MASK (ERING_SIZE -1) typedef struct { - uint32_t when; - int value; + uint32_t when; + int value; } Event; typedef struct { - Event events[ERING_SIZE]; - uint32_t rx_ptr,tx_ptr; + Event events[ERING_SIZE]; + uint32_t rx_ptr, tx_ptr; } Event_ring; - + diff --git a/app/gps.c b/app/gps.c index 39bb13f..9d5a992 100644 --- a/app/gps.c +++ b/app/gps.c @@ -1,12 +1,15 @@ #include "project.h" -#define PPS (GPIO2) -#define PPS_PORT GPIOD +#define PPS (GPIO9) +#define PPS_PORT GPIOC #define UBX_BUF_LEN 256 #define TIMEOUT 4000 + +static EPOCH next_sec; + static int ubx_ack = 0; static int ubx_ack_xfer = 0; @@ -24,22 +27,24 @@ static const int fish[] = { 1, 2, 3, 4, 5, 6, 7 }; static Event_ring gps_ring; +static char gps_info[60]; -void exti2_isr (void) + +void exti9_5_isr (void) { uint32_t now = SCS_DWT_CYCCNT; int v; v = !!gpio_get (PPS_PORT, PPS); - nvic_disable_irq (NVIC_EXTI2_IRQ); - exti_reset_request (EXTI2); + nvic_disable_irq (NVIC_EXTI9_5_IRQ); + exti_reset_request (EXTI9); gps_ring.events[gps_ring.tx_ptr].when = now; gps_ring.events[gps_ring.tx_ptr].value = v; gps_ring.tx_ptr = (gps_ring.tx_ptr + 1) & ERING_MASK; - nvic_enable_irq (NVIC_EXTI2_IRQ); + nvic_enable_irq (NVIC_EXTI9_5_IRQ); } @@ -48,19 +53,51 @@ void exti2_isr (void) static inline int ubx_recv_byte (uint8_t *v) { - return !ring_read_byte (&rx3_ring, v); + return !ring_read_byte (&rx1_ring, v); } static inline void ubx_send_byte (uint8_t v) { - usart3_queue (v); + usart1_queue (v); +} + +#define ALMANAC_SIZE + +static int ubx_recv_almanac (uint8_t *ptr, unsigned len) +{ + uint32_t sv, week; + uint32_t almanac[8]; + + ptr += ubx_get_u32 (ptr, &sv); + len -= 4; + ptr += ubx_get_u32 (ptr, &week); + len -= 4; + + if (len > sizeof (almanac)) + len = sizeof (almanac); + + bzero (almanac, sizeof (almanac)); + memcpy (almanac, ptr, len); + + printf (" Almanac: %2d %d %06x %06x %06x %06x %06x %06x %06x %06x\r\n", + (int) sv, (int) week, + (unsigned) almanac[0], + (unsigned) almanac[1], + (unsigned) almanac[2], + (unsigned) almanac[3], + (unsigned) almanac[4], + (unsigned) almanac[5], + (unsigned) almanac[6], + (unsigned) almanac[7]); + + return 0; } static int ubx_recv_nav_status (uint8_t *ptr, unsigned len) { - uint8_t gps_fix, flags; + uint8_t gps_fix, flags, fix_stat, flags2; uint32_t d; if ((!ptr) || (len != 16)) @@ -69,6 +106,8 @@ ubx_recv_nav_status (uint8_t *ptr, unsigned len) ptr += ubx_get_u32 (ptr, &d); //TOW ptr += ubx_get_u8 (ptr, &gps_fix); //fix type ptr += ubx_get_u8 (ptr, &flags); //fix type + ptr += ubx_get_u8 (ptr, &fix_stat); + ptr += ubx_get_u8 (ptr, &flags2); switch (gps_fix) { @@ -170,7 +209,7 @@ ubx_recv_utc (uint8_t *ptr, unsigned len) int32_t nano; uint32_t acc; uint16_t year; - uint8_t hour, min, sec, day, month; + uint8_t hour, min, sec, day, month, valid; uint32_t d; // char buf[40]; @@ -186,15 +225,31 @@ ubx_recv_utc (uint8_t *ptr, unsigned len) ptr += ubx_get_u8 (ptr, &hour); ptr += ubx_get_u8 (ptr, &min); ptr += ubx_get_u8 (ptr, &sec); + ptr += ubx_get_u8 (ptr, &valid); - printf ("GPS META-DATA %04d-%02d-%02d %02d:%02d:%02d Fix:%c%c TXCO %+8dE-12\r\n", - year, - month, - day, - hour, - min, - sec, +#if 0 + printf ("GPS META-DATA %04d-%02d-%02d %02d:%02d:%02d V:%02x Fix:%c%c TXCO %+8dE-12\r\n", + (int) year, + (int) month, + (int) day, + (int) hour, + (int) min, + (int) sec, + (unsigde) valid, fix, fix2, (int) freq); +#endif + + sprintf (gps_info, " %04d-%02d-%02d %02d:%02d:%02d V:%02x Fix:%c%c TXCO %+8dE-12", + + (int)year, + (int)month, + (int)day, + (int)hour, + (int)min, + (int)sec, + (unsigned) valid, fix, fix2, (int) freq); + + if (gps_happy > 3) { UTC u; @@ -213,6 +268,7 @@ ubx_recv_utc (uint8_t *ptr, unsigned len) gps_time = time_utc_to_epoch (u); + next_sec = gps_time; now = SCS_DWT_CYCCNT; abs = abs_extend (now); @@ -234,6 +290,60 @@ ubx_recv_utc (uint8_t *ptr, unsigned len) return 0; } + + +static int ubx_recv_nav_sbas (uint8_t *ptr, unsigned len) +{ + uint8_t prn, mode, service; + int8_t sys; + uint8_t n; + + ptr += 4; + + ptr += ubx_get_u8 (ptr, &prn); + ptr += ubx_get_u8 (ptr, &mode); + ptr += ubx_get_i8 (ptr, &sys); + ptr += ubx_get_u8 (ptr, &service); + + ptr += ubx_get_u8 (ptr, &n); + ptr += 3; + + printf ("GPS SBAS PRN:%d M:%d S:%d SVC:%02x\r\n", prn, mode, sys, service); + + while (n--) { + ptr += ubx_get_u8 (ptr, &prn); + ptr += 11; + printf ("GPS SBAS SV:%d\r\n", prn); + } + + return 0; +} + +static int ubx_recv_nav_sat (uint8_t *ptr, unsigned len) +{ + uint8_t gnssid, prn, cno, ver; + uint8_t n; + + ptr += 4; + + ptr += ubx_get_u8 (ptr, &ver); + ptr += ubx_get_u8 (ptr, &n); + ptr += 2; + + while (n--) { + ptr += ubx_get_u8 (ptr, &gnssid); + ptr += ubx_get_u8 (ptr, &prn); + ptr += ubx_get_u8 (ptr, &cno); + ptr += 9; + + printf ("GPS GNSS:%2d PRN:%3d CNO:%3d\r\n", gnssid, prn, cno); + } + + + return 0; +} + + static int ubx_recv_rinex (uint8_t *payload, unsigned len) { @@ -263,6 +373,14 @@ ubx_recv (uint8_t class, uint8_t id, uint8_t *payload, unsigned len) ubx_recv_clock_stats (payload, len); break; + case 0x32: + ubx_recv_nav_sbas (payload, len); + break; + + case 0x35: + ubx_recv_nav_sat (payload, len); + break; + default: printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); hexdump (payload, len); @@ -280,6 +398,20 @@ ubx_recv (uint8_t class, uint8_t id, uint8_t *payload, unsigned len) break; + case 4: + switch (id) { + case 0x4: + break; + + default: + printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); + hexdump (payload, len); + } + + break; + + + case 5: ubx_ack++; printf (" %s for %02x.%02x\r\n", id ? "ACK" : "NAK", payload[0], @@ -289,6 +421,10 @@ ubx_recv (uint8_t class, uint8_t id, uint8_t *payload, unsigned len) case 0x0b: switch (id) { + case 0x30: + ubx_recv_almanac (payload, len); + break; + case 0x50: printf ("xfer ack\r\n"); ubx_ack_xfer++; @@ -450,6 +586,9 @@ static void gps_pps_dispatch (void) v = gps_ring.events[gps_ring.rx_ptr].value; now = gps_ring.events[gps_ring.rx_ptr].when; + if (gps_happy) + led3_set (v); + gps_ring.rx_ptr = (gps_ring.rx_ptr + 1) & ERING_MASK; @@ -459,14 +598,16 @@ static void gps_pps_dispatch (void) - if (gps_happy) + if (gps_happy > 30) pll_dispatch (gps_last_happy, abs, "GPS"); e = pll_decompose (abs); //u = time_epoch_to_utc (e); - time_print_epoch ("GPS : ", e); + //time_print_epoch ("GPS : ", e, gps_info); + + report_time ("GPS", next_sec, abs, gps_info); } @@ -476,6 +617,7 @@ gps_dispatch (void) { ubx_dispatch_search (-1, -1, NULL); gps_pps_dispatch(); + } static void @@ -525,7 +667,7 @@ ubx_handshake (uint8_t class, uint8_t id, const void *payload, unsigned len) if (ticks > timeout) { printf ("GPS timeout resending packet\r\n"); - usart3_drain(); + usart1_drain(); ubx_send (class, id, payload, len); timeout = ticks + TIMEOUT; } @@ -546,7 +688,7 @@ ubx_handshake_xfer (uint8_t class, uint8_t id, const void *payload, uint32_t timeout; ubx_ack_xfer = 0; - // usart3_drain(); + // usart1_drain(); ubx_send (class, id, payload, len); @@ -557,7 +699,7 @@ ubx_handshake_xfer (uint8_t class, uint8_t id, const void *payload, if (ticks > timeout) { printf ("GPS timeout resending packet\r\n"); - // usart3_drain(); + // usart1_drain(); ubx_send (class, id, payload, len); timeout = ticks + TIMEOUT; } @@ -580,7 +722,7 @@ ubx_fetch (uint8_t class, uint8_t id, void *payload, unsigned len, { uint8_t *ret; - while (!ring_empty (&tx3_ring) || !ring_empty (&rx3_ring)) + while (!ring_empty (&tx1_ring) || !ring_empty (&rx1_ring)) gps_dispatch(); ubx_send (class, id, payload, len); @@ -591,6 +733,19 @@ ubx_fetch (uint8_t class, uint8_t id, void *payload, unsigned len, return ret; } +static int ubx_set_nav_rate (uint16_t ms) +{ + uint8_t buf[6], *ptr; + + ptr = buf; + + ptr += ubx_put_u16 (ptr, ms); + ptr += ubx_put_u16 (ptr, 1); /*1:1*/ + ptr += ubx_put_u16 (ptr, 0); /*UTC*/ + + return ubx_handshake (0x06, 0x08, buf, (unsigned) (ptr - buf)); +} + static int ubx_set_message_rate_port1 (uint8_t class, uint8_t id, uint8_t rate) { @@ -640,7 +795,7 @@ gps_set_ref (int ref_hz) ptr = buf; ptr += ubx_put_u8 (ptr, 0); //timepluse 1 - ptr += ubx_put_u8 (ptr, 0); //reserved + ptr += ubx_put_u8 (ptr, 0); //version 0 ptr += ubx_put_u16 (ptr, 0); //reserved // ptr += ubx_put_u16 (ptr, 32); //ant cable delay ns @@ -650,8 +805,8 @@ gps_set_ref (int ref_hz) ptr += ubx_put_u32 (ptr, 1000000 / ref_hz); //period locked/us // ptr += ubx_put_u32 (ptr, 0); //pulse width unlocked/us - ptr += ubx_put_u32 (ptr, 500000 / ref_hz); //pulse width unlocked/us - ptr += ubx_put_u32 (ptr, 500000 / ref_hz); //pulse width locked/us + ptr += ubx_put_u32 (ptr, 100000 / ref_hz); //pulse width unlocked/us + ptr += ubx_put_u32 (ptr, 100000 / ref_hz); //pulse width locked/us ptr += ubx_put_i32 (ptr, 0); // ? delay @@ -660,7 +815,7 @@ gps_set_ref (int ref_hz) ptr += ubx_put_u32 (ptr, 0xf7); #else /*Same numbers for locked/unlocked*/ - ptr += ubx_put_u32 (ptr, 0xf3); + ptr += ubx_put_u32 (ptr, 0xf7); #endif @@ -677,15 +832,16 @@ gps_init (void) unsigned len; // uint16_t u2; - usart3_drain(); + usart1_drain(); - while (!ring_empty (&tx3_ring) || !ring_empty (&rx3_ring)) + while (!ring_empty (&tx1_ring) || !ring_empty (&rx1_ring)) gps_dispatch(); printf ("Testing GNSS...\r\n"); ubx_handshake (0x06, 0x00, NULL, 0); printf ("GNSS there\r\n"); + // Set up port ptr = buf; ptr += ubx_put_u8 (ptr, 1); //uart1 @@ -693,7 +849,7 @@ gps_init (void) ptr += ubx_put_u16 (ptr, 0x0); //flow control off ptr += ubx_put_u32 (ptr, 0x8c0); //no parity, 8 bits ptr += ubx_put_u32 (ptr, 9600); // baudrate - ptr += ubx_put_u16 (ptr, 0x7); // receive RTCM, NMEA, UBX + ptr += ubx_put_u16 (ptr, 0x3); // receive NMEA, UBX ptr += ubx_put_u16 (ptr, 0x1); // transmit UBX ptr += ubx_put_u16 (ptr, 0x0); // no txtimeout ptr += ubx_put_u16 (ptr, 0x0); // reserved @@ -701,7 +857,7 @@ gps_init (void) printf ("configured GNSS protocol\r\n"); -#if 1 +#if 0 ptr = buf; ptr += ubx_put_u16 (ptr, 0x14); ptr += ubx_put_u16 (ptr, 0x00); @@ -749,17 +905,30 @@ gps_init (void) printf ("configured GNSS data\r\n"); + gps_set_ref (1); + ubx_fetch (0x06, 0x31, NULL, 0, &len); printf ("configured GNSS 6.31\r\n"); + + ubx_set_nav_rate (1000); + #if 1 ubx_set_message_rate_port1 (0x01, 0x03, 1); + ubx_set_message_rate_port1 (0x01, 0x06, 0); ubx_set_message_rate_port1 (0x01, 0x21, 1); ubx_set_message_rate_port1 (0x01, 0x22, 1); ubx_set_message_rate_port1 (0x01, 0x32, 0); + + ubx_set_message_rate_port1 (0x01, 0x32, 0); /*SBAS*/ + ubx_set_message_rate_port1 (0x01, 0x35, 0); /*SV in view*/ + ubx_set_message_rate_port1 (0x03, 0x0a, 0); - //ubx_set_message_rate_port1 (0x03, 0x10, 0); + ubx_set_message_rate_port1 (0x03, 0x10, 0); + ubx_set_message_rate_port1 (0x03, 0x21, 0); + ubx_set_message_rate_port1 (0x04, 0x04, 0); + printf ("GNSS ready\r\n"); #else ubx_set_message_rate_port1 (0x01, 0x03, 0); @@ -771,7 +940,7 @@ gps_init (void) printf ("GNSS ready\r\n"); #endif -#if 1 +#if 0 ptr = buf; ptr += ubx_put_u8 (ptr, 0x1); ptr += ubx_put_u8 (ptr, 0x7); @@ -791,16 +960,16 @@ gps_init (void) MAP_INPUT (PPS); - exti_select_source (EXTI2, PPS_PORT); - exti_set_trigger (EXTI2, EXTI_TRIGGER_BOTH); - exti_enable_request (EXTI2); - nvic_enable_irq (NVIC_EXTI2_IRQ); + exti_select_source (EXTI9, PPS_PORT); + exti_set_trigger (EXTI9, EXTI_TRIGGER_BOTH); + exti_enable_request (EXTI9); + nvic_enable_irq (NVIC_EXTI9_5_IRQ); return 0; } -#define ALMANAC_LUMP 128 +#define ALMANAC_LUMP 64 int gps_almanac (void) @@ -831,6 +1000,75 @@ gps_almanac (void) return 0; } +void gps_dump_almanac (void) +{ + ubx_send (0xb, 0x30, NULL, 0); +} + + +#if 1 +int gps_bs (void) +{ + uint32_t now = SCS_DWT_CYCCNT; + uint64_t abs = abs_extend (now); + EPOCH e = pll_decompose (abs); + UTC u = time_epoch_to_utc (e); + + uint8_t buf[80], *ptr; + int ret; + + ptr = buf; + + ptr += ubx_put_u32 (ptr, 391706007); /*19 sleaford st*/ + ptr += ubx_put_u32 (ptr, 955140); + ptr += ubx_put_u32 (ptr, 501672842); + ptr += ubx_put_u32 (ptr, 100000); /*1km std dev*/ + + ptr += ubx_put_u16 (ptr, 0); /*no time mark*/ + + ptr += ubx_put_u16 (ptr, (u.year - 2000) * 100 + u.month); + ptr += ubx_put_u32 (ptr, (u.mday * 1000000) + (u.hour * 10000) + (u.minute * 100) + u.second); + ptr += ubx_put_u32 (ptr, u.nanosecond); + + ptr += ubx_put_u32 (ptr, 2000); /* time good to 2s */ + ptr += ubx_put_u32 (ptr, 0); + + ptr += ubx_put_u32 (ptr, 0); + ptr += ubx_put_u32 (ptr, 0); + + ptr += ubx_put_u32 (ptr, 0x403); + + printf ("Bootstrapping GPS\r\n"); + + hexdump (buf, (unsigned) (ptr - buf)); + + ubx_send (0x0b, 0x01, buf, (unsigned) (ptr - buf)); + + + ret = 0; + + + /* + 00000: 97 f5 58 17 + 04 93 0e 00 + 8a eb e6 1d + a0 86 01 00 + 00010: 00 00 + 6f 07 19/03 + 03 cb 06 01 /17 22:24:03 + 65 ca af 02 45075045ns + + d0 07 00 00 2000ms + 00020: 00 00 00 00 0ns + 00 00 00 00 + 00 00 00 00 + 03 04 00 00 + */ + + return ret; +} + +#endif void @@ -846,7 +1084,7 @@ gps_reset (void) ubx_cfg_rst (REPHEMERIDIES | RALMANAC | RPOS | RRTC); delay_ms (1000); - usart3_drain(); + usart1_drain(); printf ("Testing GNSS...\r\n"); diff --git a/app/gps_neo8.c b/app/gps_neo8.c new file mode 100644 index 0000000..ea5d984 --- /dev/null +++ b/app/gps_neo8.c @@ -0,0 +1,1204 @@ +#include "project.h" + +#define PPS (GPIO9) +#define PPS_PORT GPIOC + +#define UBX_BUF_LEN 256 + +#define TIMEOUT 4000 + +static int ubx_ack = 0; +static int ubx_ack_xfer = 0; + +static int current_ref_hz = 1; + +static int gps_locked; +static int gps_happy; + +uint64_t gps_last_happy; + +static char fix, fix2; +static int32_t freq = 0; + +static const int fish[] = { 1, 2, 3, 4, 5, 6, 7 }; + +static Event_ring gps_ring; + +static char gps_info[60]; + + +void exti9_5_isr (void) +{ + uint32_t now = SCS_DWT_CYCCNT; + int v; + + v = !!gpio_get (PPS_PORT, PPS); + + nvic_disable_irq (NVIC_EXTI9_5_IRQ); + exti_reset_request (EXTI9); + + gps_ring.events[gps_ring.tx_ptr].when = now; + gps_ring.events[gps_ring.tx_ptr].value = v; + gps_ring.tx_ptr = (gps_ring.tx_ptr + 1) & ERING_MASK; + + nvic_enable_irq (NVIC_EXTI9_5_IRQ); + +} + + + +static inline int +ubx_recv_byte (uint8_t *v) +{ + return !ring_read_byte (&rx1_ring, v); +} + +static inline void +ubx_send_byte (uint8_t v) +{ + usart1_queue (v); +} + +#define ALMANAC_SIZE + +static int ubx_recv_almanac(uint8_t *ptr,unsigned len) +{ +uint32_t sv,week; +uint32_t almanac[8]; + +ptr+=ubx_get_u32(ptr,&sv); +len-=4; +ptr+=ubx_get_u32(ptr,&week); +len-=4; + +if (len>sizeof(almanac)) + len=sizeof(almanac); + +bzero(almanac,sizeof(almanac)); +memcpy(almanac,ptr,len); + +printf(" Almanac: %2d %d %06x %06x %06x %06x %06x %06x %06x %06x\r\n", + (int) sv,(int) week, + (unsigned) almanac[0], + (unsigned) almanac[1], + (unsigned) almanac[2], + (unsigned) almanac[3], + (unsigned) almanac[4], + (unsigned) almanac[5], + (unsigned) almanac[6], + (unsigned) almanac[7]); + +return 0; +} + +static int +ubx_recv_nav_status (uint8_t *ptr, unsigned len) +{ + uint8_t gps_fix, flags,fix_stat,flags2; + uint32_t d; + + if ((!ptr) || (len != 16)) + return -1; + + ptr += ubx_get_u32 (ptr, &d); //TOW + ptr += ubx_get_u8 (ptr, &gps_fix); //fix type + ptr += ubx_get_u8 (ptr, &flags); //fix type + ptr += ubx_get_u8 (ptr, &fix_stat); + ptr += ubx_get_u8 (ptr, &flags2); + + + switch (gps_fix) { + case 0: + case 1: + fix = '-'; + gps_locked = 0; + break; + + case 2: + fix = '2'; + gps_locked = 0; + break; + + case 3: + fix = 'L'; + gps_locked = 1; + break; + + case 4: + fix = 'R'; + gps_locked = 0; + break; + + case 5: + fix = 'T'; + gps_locked = 0; + break; + + default: + fix = '?'; + gps_locked = 0; + } + + switch (flags & 3) { + case 0: + case 2: + fix2 = '!'; + break; + + case 1: + fix2 = '-'; + break; + + case 3: + fix2 = 'D'; + + if (gps_locked == 1) + gps_locked = 2; + + break; + + default: + fix2 = '?'; + } + + + // printf ("fix: %c%c\r\n",fix,fix2); + + + if ((gps_locked) && (gps_happy < 10000)) + gps_happy++; + else + gps_happy = 0; + + return 0; +} + + +static int +ubx_recv_clock_stats (uint8_t *ptr, unsigned len) +{ + //char buf[40]; + int32_t drift; + uint32_t d; + + if ((!ptr) || (len != 20)) + return -1; + + ptr += ubx_get_u32 (ptr, &d); //TOW + ptr += ubx_get_u32 (ptr, &d); //bias + ptr += ubx_get_i32 (ptr, &drift); //drift + ptr += ubx_get_u32 (ptr, &d); //time acc estimate + ptr += ubx_get_i32 (ptr, &freq); //freq acc estimate + + // printf ("TCXO %+8dE-12\r\n", (int) freq); +#if 0 + sprintf (buf, "TCXO %+8dE-12", (int) freq); + lcd_erase_line (18, 0); + lcd_write (buf, 0, 0); +#endif + return 0; + +} + +static int +ubx_recv_utc (uint8_t *ptr, unsigned len) +{ + int32_t nano; + uint32_t acc; + uint16_t year; + uint8_t hour, min, sec, day, month,valid; + uint32_t d; + // char buf[40]; + + if ((!ptr) || (len != 20)) + return -1; + + ptr += ubx_get_u32 (ptr, &d); //TOW + ptr += ubx_get_u32 (ptr, &acc); //bias + ptr += ubx_get_i32 (ptr, &nano); + ptr += ubx_get_u16 (ptr, &year); + ptr += ubx_get_u8 (ptr, &month); + ptr += ubx_get_u8 (ptr, &day); + ptr += ubx_get_u8 (ptr, &hour); + ptr += ubx_get_u8 (ptr, &min); + ptr += ubx_get_u8 (ptr, &sec); + ptr += ubx_get_u8 (ptr, &valid); + +#if 0 + printf ("GPS META-DATA %04d-%02d-%02d %02d:%02d:%02d V:%02x Fix:%c%c TXCO %+8dE-12\r\n", + (int) year, + (int) month, + (int) day, + (int) hour, + (int) min, + (int) sec, + (unsigde) valid, + fix, fix2, (int) freq); +#endif + + sprintf(gps_info, " %04d-%02d-%02d %02d:%02d:%02d V:%02x Fix:%c%c TXCO %+8dE-12", + + (int )year, + (int )month, + (int )day, + (int )hour, + (int )min, + (int )sec, +(unsigned) valid, fix, fix2, (int) freq); + + + + if (gps_happy > 3) { + UTC u; + EPOCH gps_time; + uint32_t now; + uint64_t abs; + + u.jday = 0; + u.year = year; + u.month = month; + u.mday = day; + u.hour = hour; + u.minute = min; + u.second = sec; + u.nanosecond = 0; + + gps_time = time_utc_to_epoch (u); + + + now = SCS_DWT_CYCCNT; + abs = abs_extend (now); + + gps_last_happy = make_happy (abs, 180); + + pll_set_offset (gps_time, abs); + + } + + +#if 0 + sprintf (buf, "%+6dE-12 %02d%02d%02d", (int) freq, + (int) hour, (int)min, (int) sec); + lcd_erase_line (18, 0); + lcd_write (buf, 0, 0); +#endif + + return 0; +} + + + +static int ubx_recv_nav_sbas(uint8_t *ptr,unsigned len) +{ +uint8_t prn,mode,service; +int8_t sys; +uint8_t n; + + ptr+=4; + + ptr += ubx_get_u8 (ptr, &prn); + ptr += ubx_get_u8 (ptr, &mode); + ptr += ubx_get_i8 (ptr, &sys); + ptr += ubx_get_u8 (ptr, &service); + + ptr += ubx_get_u8 (ptr, &n); + ptr+=3; + + printf("GPS SBAS PRN:%d M:%d S:%d SVC:%02x\r\n",prn,mode,sys,service); + + while (n--) { + ptr += ubx_get_u8 (ptr, &prn); + ptr+=11; + printf("GPS SBAS SV:%d\r\n",prn); + } + +return 0; +} + +static int ubx_recv_nav_sat(uint8_t *ptr,unsigned len) +{ +uint8_t gnssid,prn,cno,ver; +uint8_t n; + + ptr+=4; + + ptr += ubx_get_u8 (ptr, &ver); + ptr += ubx_get_u8 (ptr, &n); + ptr+=2; + + while (n--) { + ptr += ubx_get_u8 (ptr, &gnssid); + ptr += ubx_get_u8 (ptr, &prn); + ptr += ubx_get_u8 (ptr, &cno); + ptr+=9; + + printf("GPS GNSS:%2d PRN:%3d CNO:%3d\r\n",gnssid,prn,cno); + } + + +return 0; +} + + +static int ubx_recv_rinex (uint8_t *payload, unsigned len) +{ + + printf ("Rinex\r\n"); + return 0; +} + + + +static void +ubx_recv (uint8_t class, uint8_t id, uint8_t *payload, unsigned len) +{ + // printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); + + switch (class) { + case 1: + switch (id) { + case 0x3: + ubx_recv_nav_status (payload, len); + break; + + case 0x21: + ubx_recv_utc (payload, len); + break; + + case 0x22: + ubx_recv_clock_stats (payload, len); + break; + + case 0x32: + ubx_recv_nav_sbas(payload,len); + break; + + case 0x35: + ubx_recv_nav_sat(payload,len); + break; + + default: + printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); + hexdump (payload, len); + } + + break; + + case 2: + switch (id) { + case 0x10: + ubx_recv_rinex (payload, len); + + break; + } + + break; + + case 4: + switch (id) { + case 0x4: + break; + default: + printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); + hexdump (payload, len); + } + + break; + + + + case 5: + ubx_ack++; + printf (" %s for %02x.%02x\r\n", id ? "ACK" : "NAK", payload[0], + payload[1]); + + break; + + case 0x0b: + switch (id) { + case 0x30: + ubx_recv_almanac(payload,len); + break; + case 0x50: + printf ("xfer ack\r\n"); + ubx_ack_xfer++; + break; + + default: + printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); + hexdump (payload, len); + } + + break; + + default: + printf ("RX> %02x.%02x (%d bytes)\r\n", class, id, len); + + if (class != 0x03) + hexdump (payload, len); + } + + +} + + +typedef enum { + UBX_SM_LOST = 0, + UBX_SM_S2, + UBX_SM_C, + UBX_SM_I, + UBX_SM_L1, + UBX_SM_L2, + UBX_SM_DATA, + UBX_SM_CKA, + UBX_SM_CKB +} ubx_sm_t; + + + + +static uint8_t * +ubx_dispatch_search (int s_class, int s_id, unsigned *len_ptr) +{ + static uint8_t buf[UBX_BUF_LEN]; + static ubx_sm_t sm = UBX_SM_LOST; + static uint8_t class, id; + static unsigned ptr; + static unsigned len; + static uint8_t ck_a, ck_b; + + + void ubx_ck (uint8_t v) { + ck_a += v; + ck_b = ck_b + ck_a; + } + + + uint8_t c; + + while (ubx_recv_byte (&c)) { + + switch (sm) { + case UBX_SM_LOST: + if (c == 0xb5) + sm = UBX_SM_S2; + + break; + + case UBX_SM_S2: + if (c == 0x62) + sm = UBX_SM_C; + else + sm = UBX_SM_LOST; + + break; + + case UBX_SM_C: + ck_a = ck_b = class = c; + sm = UBX_SM_I; + break; + + case UBX_SM_I: + ubx_ck (c); + id = c; + sm = UBX_SM_L1; + break; + + case UBX_SM_L1: + ubx_ck (c); + len = c; + sm = UBX_SM_L2; + break; + + case UBX_SM_L2: + ubx_ck (c); + len |= c << 8; + + ptr = 0; + + if (len) + sm = UBX_SM_DATA; + else + sm = UBX_SM_CKA; + + break; + + case UBX_SM_DATA: + ubx_ck (c); + + if (ptr < UBX_BUF_LEN) + buf[ptr] = c; + + ptr++; + + if (ptr == len) + sm = UBX_SM_CKA; + + break; + + case UBX_SM_CKA: + if (c == ck_a) + sm = UBX_SM_CKB; + else + sm = UBX_SM_LOST; + + break; + + case UBX_SM_CKB: + sm = UBX_SM_LOST; + + if (c != ck_b) + break; + + ubx_recv (class, id, buf, len); + + if ((class == s_class) && (id == s_id)) { + if (len_ptr) + *len_ptr = len; + + return buf; + } + + break; + } + + } + + return NULL; +} +static void gps_pps_dispatch (void) +{ + //char buf[80]; + uint32_t now; + uint64_t abs; + int v; + EPOCH e; + //UTC u; + + if (gps_ring.rx_ptr == gps_ring.tx_ptr) return; + + v = gps_ring.events[gps_ring.rx_ptr].value; + now = gps_ring.events[gps_ring.rx_ptr].when; + + led3_set(v); + + gps_ring.rx_ptr = (gps_ring.rx_ptr + 1) & ERING_MASK; + + + if (!v) return; + + abs = abs_extend (now); + + if (gps_happy) + pll_dispatch (gps_last_happy, abs, "GPS"); + + e = pll_decompose (abs); + + + //u = time_epoch_to_utc (e); + time_print_epoch ("GPS : ", e, gps_info); + +} + + +void +gps_dispatch (void) +{ + ubx_dispatch_search (-1, -1, NULL); + gps_pps_dispatch(); + +} + +static void +ubx_send (uint8_t class, uint8_t id, const void *_payload, unsigned len) +{ + uint8_t ck_a = 0, ck_b = 0; + uint8_t *payload = (uint8_t *) _payload; + + void ubx_send_byte_ck (uint8_t v) { + ubx_send_byte (v); + ck_a += v; + ck_b = ck_b + ck_a; + } + + + ubx_send_byte (0xb5); + ubx_send_byte (0x62); + + ubx_send_byte_ck (class); + ubx_send_byte_ck (id); + ubx_send_byte_ck (len & 0xff); + ubx_send_byte_ck (len >> 8); + + while (len--) + ubx_send_byte_ck (* (payload++)); + + ubx_send_byte (ck_a); + ubx_send_byte (ck_b); + + // printf ("TX> %02x.%02x\r\n", class, id); + +} + +static int +ubx_handshake (uint8_t class, uint8_t id, const void *payload, unsigned len) +{ + uint32_t timeout; + + ubx_ack = 0; + ubx_send (class, id, payload, len); + + + + timeout = ticks + TIMEOUT; + + while (!ubx_ack) { + + if (ticks > timeout) { + printf ("GPS timeout resending packet\r\n"); + usart1_drain(); + ubx_send (class, id, payload, len); + timeout = ticks + TIMEOUT; + } + + + + + gps_dispatch(); + } + + return 0; +} + +static int +ubx_handshake_xfer (uint8_t class, uint8_t id, const void *payload, + unsigned len) +{ + uint32_t timeout; + + ubx_ack_xfer = 0; + // usart1_drain(); + ubx_send (class, id, payload, len); + + + + timeout = ticks + TIMEOUT; + + while (!ubx_ack_xfer) { + + if (ticks > timeout) { + printf ("GPS timeout resending packet\r\n"); + // usart1_drain(); + ubx_send (class, id, payload, len); + timeout = ticks + TIMEOUT; + } + + + + + gps_dispatch(); + } + + return 0; +} + + + + +static uint8_t * +ubx_fetch (uint8_t class, uint8_t id, void *payload, unsigned len, + unsigned *len_ptr) +{ + uint8_t *ret; + + while (!ring_empty (&tx1_ring) || !ring_empty (&rx1_ring)) + gps_dispatch(); + + ubx_send (class, id, payload, len); + + while (! (ret = ubx_dispatch_search (class, id, len_ptr))); + + + return ret; +} + +static int ubx_set_nav_rate (uint16_t ms) +{ + uint8_t buf[6], *ptr; + + ptr = buf; + + ptr += ubx_put_u16 (ptr, ms); + ptr += ubx_put_u16 (ptr, 1); /*1:1*/ + ptr += ubx_put_u16 (ptr, 0); /*UTC*/ + + return ubx_handshake (0x06, 0x08, buf, (unsigned) (ptr - buf)); +} + +static int +ubx_set_message_rate_port1 (uint8_t class, uint8_t id, uint8_t rate) +{ + uint8_t buf[8], *ptr; + + ptr = buf; + + ptr += ubx_put_u8 (ptr, class); + ptr += ubx_put_u8 (ptr, id); //reserved + ptr += ubx_put_u8 (ptr, 0); //nothing on port i2c + ptr += ubx_put_u8 (ptr, rate); //rate on uart + ptr += ubx_put_u8 (ptr, 0); //nothing on port 2 + ptr += ubx_put_u8 (ptr, 0); //nothing on usb + ptr += ubx_put_u8 (ptr, 0); //nothing on spi + ptr += ubx_put_u8 (ptr, 0); //nothing on port 5 + + return ubx_handshake (0x06, 0x01, buf, (unsigned) (ptr - buf)); +} + + +static int +ubx_cfg_rst (uint16_t flags) +{ + uint8_t buf[8], *ptr; + + ptr = buf; + + ptr += ubx_put_u16 (ptr, flags); //Flags + ptr += ubx_put_u8 (ptr, 0x4); //Hardware reset after shutdown + ptr += ubx_put_u8 (ptr, 0); //reserved + + ubx_send (0x06, 0x04, buf, (unsigned) (ptr - buf)); + return 0; +} + + +static int +gps_set_ref (int ref_hz) +{ + uint8_t buf[80], *ptr; + int ret; + + printf ("setting gps ref to %d hz\r\n", ref_hz); + + current_ref_hz = ref_hz; + + ptr = buf; + + ptr += ubx_put_u8 (ptr, 0); //timepluse 1 + ptr += ubx_put_u8 (ptr, 0); //version 0 + ptr += ubx_put_u16 (ptr, 0); //reserved + + // ptr += ubx_put_u16 (ptr, 32); //ant cable delay ns + ptr += ubx_put_u16 (ptr, 0); //ant cable delay ns + ptr += ubx_put_u16 (ptr, 0); //rf group delay ns + ptr += ubx_put_u32 (ptr, 1000000 / ref_hz); //period unlocked/us + ptr += ubx_put_u32 (ptr, 1000000 / ref_hz); //period locked/us + + // ptr += ubx_put_u32 (ptr, 0); //pulse width unlocked/us + ptr += ubx_put_u32 (ptr, 100000 / ref_hz); //pulse width unlocked/us + ptr += ubx_put_u32 (ptr, 100000 / ref_hz); //pulse width locked/us + + ptr += ubx_put_i32 (ptr, 0); // ? delay + +#if 0 + /*Separate numbers for locked/unlocked*/ + ptr += ubx_put_u32 (ptr, 0xf7); +#else + /*Same numbers for locked/unlocked*/ + ptr += ubx_put_u32 (ptr, 0xf7); +#endif + + + ret = ubx_handshake (0x06, 0x31, buf, (unsigned) (ptr - buf)); + + return ret; +} + + +static inline int +ubx_put_gnss_cfg (uint8_t *buf, uint8_t gnss_id,uint8_t r_chan,uint8_t m_chan, +uint16_t enable, uint16_t sig_mask) +{ + uint8_t *ptr=buf; + + ptr += ubx_put_u8(ptr,gnss_id); + ptr += ubx_put_u8(ptr,r_chan); + ptr += ubx_put_u8(ptr,m_chan); + ptr += ubx_put_u8(ptr,0); + ptr += ubx_put_u16(ptr,enable); + ptr += ubx_put_u16(ptr,sig_mask); + + return (unsigned) (ptr - buf); +} + +void gps_set_gnss(void) +{ + uint8_t buf[80], *ptr; + + ptr = buf; + ptr += ubx_put_u8 (ptr, 0x0); /* Ver 0 */ + ptr += ubx_put_u8 (ptr, 0x20); + ptr += ubx_put_u8 (ptr, 0x20); + ptr += ubx_put_u8 (ptr, 0x7); + + ptr += ubx_put_gnss_cfg(ptr,0,8,16,1,0x101); + ptr += ubx_put_gnss_cfg(ptr,1,1,3,1,0x101); + ptr += ubx_put_gnss_cfg(ptr,2,4,8,0,0x101); + ptr += ubx_put_gnss_cfg(ptr,3,8,16,0,0x101); + ptr += ubx_put_gnss_cfg(ptr,4,0,7,0,0x301); + ptr += ubx_put_gnss_cfg(ptr,5,0,3,1,0x501); + ptr += ubx_put_gnss_cfg(ptr,6,8,14,1,0x101); + + ubx_handshake (0x06, 0x3e, buf, (unsigned) (ptr - buf)); + + printf ("configured SBAS\r\n"); + + ubx_handshake (0x06, 0x3e, buf, 0); +} + + +int +gps_init (void) +{ + uint8_t buf[80], *ptr; + unsigned len; + // uint16_t u2; + + usart1_drain(); + + while (!ring_empty (&tx1_ring) || !ring_empty (&rx1_ring)) + gps_dispatch(); + + + printf ("Testing GNSS...\r\n"); + ubx_handshake (0x06, 0x00, NULL, 0); + printf ("GNSS there\r\n"); + + //reset GNSS + +#if 0 + ptr=buf; + ptr += ubx_put_u32 (ptr, 0xe1f ); //uart1 + ptr += ubx_put_u32 (ptr, 0 ); //uart1 + ptr += ubx_put_u32 (ptr, 0 ); //uart1 + ubx_handshake (0x06, 0x09, buf, (unsigned) (ptr - buf)); + + printf ("reset\r\n"); +#endif + + + // Set up port + ptr = buf; + ptr += ubx_put_u8 (ptr, 1); //uart1 + ptr += ubx_put_u8 (ptr, 0); //reserved + ptr += ubx_put_u16 (ptr, 0x0); //flow control off + ptr += ubx_put_u32 (ptr, 0x8c0); //no parity, 8 bits + ptr += ubx_put_u32 (ptr, 9600); // baudrate + ptr += ubx_put_u16 (ptr, 0x7); // receive RTCM, NMEA, UBX + ptr += ubx_put_u16 (ptr, 0x1); // transmit UBX + ptr += ubx_put_u16 (ptr, 0x0); // no txtimeout + ptr += ubx_put_u16 (ptr, 0x0); // reserved + ubx_handshake (0x06, 0x00, buf, (unsigned) (ptr - buf)); + + printf ("configured GNSS protocol\r\n"); + + +#if 0 + ptr = buf; + ptr += ubx_put_u16 (ptr, 0x1b); + ptr += ubx_put_u16 (ptr, 0x00); + ubx_handshake (0x06, 0x13, buf, (unsigned) (ptr - buf)); + + printf ("configured antenna pins\r\n"); +#endif + + + +#if 0 + // Check we're in WGS84 + ptr = ubx_fetch (0x06, 0x06, NULL, 0, &len); + ptr += ubx_get_u16 (ptr, &u2); + + if (u2) + return -1; + + printf ("configured GNSS datum\r\n"); +#endif + + ptr = buf; + + ptr += ubx_put_u8 (ptr, 0); //UBX + ptr += ubx_put_u8 (ptr, 0); //reserved + ptr += ubx_put_u16 (ptr, 0); //reserved + ptr += ubx_put_u8 (ptr, 0); //nothing on port i2c + ptr += ubx_put_u8 (ptr, 0x18); //everything on uart + ptr += ubx_put_u8 (ptr, 0); //nothing on port 2 + ptr += ubx_put_u8 (ptr, 0); //nothing on usb + ptr += ubx_put_u8 (ptr, 0); //nothing on spi + ptr += ubx_put_u8 (ptr, 0); //nothing on port 5 + + ptr += ubx_put_u8 (ptr, 1); //NMEA + ptr += ubx_put_u8 (ptr, 0); //reserved + ptr += ubx_put_u16 (ptr, 0); //reserved + ptr += ubx_put_u8 (ptr, 0); //nothing on port i2c + ptr += ubx_put_u8 (ptr, 0); //nothing on uart + ptr += ubx_put_u8 (ptr, 0); //nothing on port 2 + ptr += ubx_put_u8 (ptr, 0); //nothing on usb + ptr += ubx_put_u8 (ptr, 0); //nothing on spi + ptr += ubx_put_u8 (ptr, 0); //nothing on port 5 + + ubx_handshake (0x06, 0x02, buf, (unsigned) (ptr - buf)); + + printf ("configured GNSS data\r\n"); + + gps_set_ref (1); + + ubx_fetch (0x06, 0x31, NULL, 0, &len); + + printf ("configured GNSS 6.31\r\n"); + + + ubx_set_nav_rate(1000); + +#if 1 + ubx_set_message_rate_port1 (0x01, 0x03, 1); + ubx_set_message_rate_port1 (0x01, 0x21, 1); + ubx_set_message_rate_port1 (0x01, 0x22, 1); + ubx_set_message_rate_port1 (0x01, 0x32, 0); + + ubx_set_message_rate_port1 (0x01, 0x32, 0); /*SBAS*/ + ubx_set_message_rate_port1 (0x01, 0x35, 0); /*SV in view*/ + + ubx_set_message_rate_port1 (0x03, 0x0a, 0); + ubx_set_message_rate_port1 (0x03, 0x10, 0); + ubx_set_message_rate_port1 (0x03, 0x21, 0); + ubx_set_message_rate_port1 (0x04, 0x04, 0); + + printf ("GNSS ready\r\n"); +#else + ubx_set_message_rate_port1 (0x01, 0x03, 0); + ubx_set_message_rate_port1 (0x01, 0x21, 0); + ubx_set_message_rate_port1 (0x01, 0x22, 0); + ubx_set_message_rate_port1 (0x01, 0x32, 0); + ubx_set_message_rate_port1 (0x03, 0x0a, 0); + //ubx_set_message_rate_port1 (0x03, 0x10, 0); + printf ("GNSS ready\r\n"); +#endif + + + + // printf ("GPS ready\r\n"); + // ubx_get_clock_stats(); + + MAP_INPUT (PPS); + + exti_select_source (EXTI9, PPS_PORT); + exti_set_trigger (EXTI9, EXTI_TRIGGER_BOTH); + exti_enable_request (EXTI9); + nvic_enable_irq (NVIC_EXTI9_5_IRQ); + + return 0; +} + + +#define ALMANAC_LUMP 64 + +int +gps_almanac (void) +{ + uint32_t len = almanac_alp_len; + const uint8_t *ptr = almanac_alp; + uint32_t lumpsz; + uint8_t dummy; + + printf ("Downloading GPS almanac %x %x %x\r\n", (int) ptr[0], (int) ptr[1], + (int) ptr[2]); + + + while (len) { + printf ("%d bytes to go\r\n", (int) len); + + lumpsz = len > ALMANAC_LUMP ? ALMANAC_LUMP : len; + + ubx_handshake_xfer (0x0b, 0x50, ptr, lumpsz); + + ptr += lumpsz; + len -= lumpsz; + + } + + ubx_handshake_xfer (0x0b, 0x50, &dummy, 1); + + return 0; +} + +void gps_dump_almanac(void) +{ + ubx_send (0xb, 0x30, NULL,0); +} + + +#if 0 +int gps_bs(void) +{ + uint32_t now = SCS_DWT_CYCCNT; + uint64_t abs = abs_extend (now); + EPOCH e = pll_decompose (abs); + UTC u = time_epoch_to_utc (e); + + uint8_t buf[80], *ptr; + int ret; + + ptr = buf; + + ptr += ubx_put_u32 (ptr, 391706007); /*19 sleaford st*/ + ptr += ubx_put_u32 (ptr, 955140); + ptr += ubx_put_u32 (ptr, 501672842); + ptr += ubx_put_u32 (ptr, 100000); /*1km std dev*/ + + ptr += ubx_put_u16 (ptr, 0); /*no time mark*/ + + ptr += ubx_put_u16 (ptr, (u.year-2000)*100 + u.month); + ptr += ubx_put_u32 (ptr, (u.mday*1000000) + (u.hour*10000) + (u.minute *100) +u.second); + ptr += ubx_put_u32 (ptr, u.nanosecond); + + ptr += ubx_put_u32 (ptr, 2000); /* time good to 2s */ + ptr += ubx_put_u32 (ptr, 0); + + ptr += ubx_put_u32 (ptr, 0); + ptr += ubx_put_u32 (ptr, 0); + + ptr += ubx_put_u32 (ptr, 0x403); + + printf("Bootstrapping GPS\r\n"); + + hexdump (buf, (unsigned) (ptr-buf)); + + ubx_send (0x0b, 0x01, buf, (unsigned) (ptr - buf)); + + + ret = 0; + + +/* + 00000: 97 f5 58 17 + 04 93 0e 00 + 8a eb e6 1d + a0 86 01 00 + 00010: 00 00 + 6f 07 19/03 + 03 cb 06 01 /17 22:24:03 + 65 ca af 02 45075045ns + + d0 07 00 00 2000ms + 00020: 00 00 00 00 0ns + 00 00 00 00 + 00 00 00 00 + 03 04 00 00 +*/ + + return ret; +} + +#endif + +int gps_bs(void) +{ + uint32_t now = SCS_DWT_CYCCNT; + uint64_t abs = abs_extend (now); + EPOCH e = pll_decompose (abs); + UTC u = time_epoch_to_utc (e); + + uint8_t buf[80], *ptr; + int ret; + + ptr = buf; + + ptr += ubx_put_u8 (ptr, 0x0); + ptr += ubx_put_u8 (ptr, 0x0); + ptr += ubx_put_u8 (ptr, 0x0); + ptr += ubx_put_u8 (ptr, 0x0); + + ptr += ubx_put_u32 (ptr, 391706007); /*19 sleaford st*/ + ptr += ubx_put_u32 (ptr, 955140); + ptr += ubx_put_u32 (ptr, 501672842); + ptr += ubx_put_u32 (ptr, 100000); /*1km std dev*/ + + hexdump (buf, (unsigned) (ptr-buf)); + ubx_send (0x13, 0x40, buf, (unsigned) (ptr-buf)); + + + ptr = buf; + + ptr += ubx_put_u8 (ptr, 0x10); + ptr += ubx_put_u8 (ptr, 0x0); + ptr += ubx_put_u8 (ptr, 0x0); + ptr += ubx_put_u8 (ptr, 0x80); + + ptr += ubx_put_u16 (ptr,u.year-2000); + ptr += ubx_put_u8 (ptr,u.month); + ptr += ubx_put_u8 (ptr,u.mday); + + ptr += ubx_put_u8 (ptr,u.hour); + ptr += ubx_put_u8 (ptr,u.minute); + ptr += ubx_put_u8 (ptr,u.second); + ptr += ubx_put_u8 (ptr,0); + + ptr += ubx_put_u32 (ptr,u.nanosecond); + + ptr += ubx_put_u16 (ptr, 2); /* time good to 2s */ + ptr += ubx_put_u8 (ptr,0); + ptr += ubx_put_u8 (ptr,0); + + ptr += ubx_put_u32 (ptr, 0); + + hexdump (buf, (unsigned) (ptr-buf)); + ubx_send (0x13, 0x40, buf, (unsigned) (ptr-buf)); + + + ret = 0; + + return ret; +} + + +void +gps_reset (void) +{ + printf ("Restting gps..\r\n"); + +#define REPHEMERIDIES (1UL << 0) +#define RALMANAC (1UL << 1) +#define RPOS (1UL << 4) +#define RRTC (1UL << 8) + + ubx_cfg_rst (REPHEMERIDIES | RALMANAC | RPOS | RRTC); + + delay_ms (1000); + usart1_drain(); + + + printf ("Testing GNSS...\r\n"); + ubx_handshake (0x06, 0x00, NULL, 0); + printf ("GNSS there\r\n"); + + gps_init(); + + gps_set_ref (current_ref_hz); + + gps_set_gnss(); +} + +#if 0 +static int +ubx_get_clock_stats (void) +{ + uint8_t *ptr; + + unsigned len; + + ptr = ubx_fetch (0x01, 0x22, NULL, 0, &len); + + //return ubx_recv_clock_stats(ptr,len); + return ptr ? 0 : -1; +} +#endif diff --git a/app/led.c b/app/led.c index b7f34a0..2dc285b 100644 --- a/app/led.c +++ b/app/led.c @@ -1,29 +1,83 @@ #include "project.h" -#define LED (GPIO6) -#define LED_PORT GPIOA - +#define LED1 (GPIO8) +#define LED1_PORT GPIOE +#define LED2 (GPIO9) +#define LED2_PORT GPIOE +#define LED3 (GPIO10) +#define LED3_PORT GPIOE +#define LED4 (GPIO11) +#define LED4_PORT GPIOE +#define LED5 (GPIO10) +#define LED5_PORT GPIOB +#define LED6 (GPIO11) +#define LED6_PORT GPIOB +#define LED7 (GPIO12) +#define LED7_PORT GPIOB +#define LED8 (GPIO13) +#define LED8_PORT GPIOB +#define LED9 (GPIO0) +#define LED9_PORT GPIOD +#define LED10 (GPIO1) +#define LED10_PORT GPIOD static unsigned led_ms; void led_init (void) { + MAP_OUTPUT_PP (LED1); + MAP_OUTPUT_PP (LED2); + MAP_OUTPUT_PP (LED3); + MAP_OUTPUT_PP (LED4); + MAP_OUTPUT_PP (LED5); + MAP_OUTPUT_PP (LED6); + MAP_OUTPUT_PP (LED7); + MAP_OUTPUT_PP (LED8); + MAP_OUTPUT_PP (LED9); + MAP_OUTPUT_PP (LED10); + + SET (LED1); + SET (LED2); + SET (LED3); + SET (LED4); + SET (LED5); + SET (LED6); + SET (LED7); + SET (LED8); + SET (LED9); + SET (LED10); + +} + +void led1_set (int v) +{ + if (!v) SET (LED1); + else CLEAR (LED1); +} - MAP_OUTPUT_PP (LED); +void led2_set (int v) +{ + if (!v) SET (LED2); + else CLEAR (LED2); } +void led3_set (int v) +{ + if (!v) SET (LED3); + else CLEAR (LED3); +} void led_clear (void) { - SET (LED); + SET (LED4); } void led_set() { - CLEAR (LED); + CLEAR (LED4); } void led_blink (unsigned ms) @@ -43,3 +97,13 @@ led_tick (void) if (!led_ms) led_clear(); } + +void led_slow_tick (void) +{ + static int c; + + + c++; + c &= 7; +} + diff --git a/app/lwip_glue.c b/app/lwip_glue.c index 556fa0e..03380a4 100644 --- a/app/lwip_glue.c +++ b/app/lwip_glue.c @@ -59,10 +59,15 @@ void start_lwip (void) lwip_init(); - IP4_ADDR (&ipaddr, 10, 32, 94, 9); +#if 1 + IP4_ADDR (&ipaddr, 10, 32, 99, 73); IP4_ADDR (&netmask, 255, 255, 255, 0); - IP4_ADDR (&gw, 10, 32, 94, 1); - + IP4_ADDR (&gw, 10, 32, 99, 1); +#else + IP4_ADDR (&ipaddr, 192, 168, 1, 1); + IP4_ADDR (&netmask, 255, 255, 255, 0); + IP4_ADDR (&gw, 192, 168, 1, 254); +#endif netif_add (&if0, &ipaddr, &netmask, &gw, NULL, steth_lwip_init , ethernet_input); diff --git a/app/main.c b/app/main.c index 356d4da..707d230 100644 --- a/app/main.c +++ b/app/main.c @@ -2,12 +2,24 @@ int time_known; +#if 0 +void exti15_10_isr (void) +{ + nvic_disable_irq (NVIC_EXTI15_10_IRQ); + + if (exti_get_flag_status (EXTI10)) exti10_isr(); + + if (exti_get_flag_status (EXTI11)) exti11_isr(); + + nvic_enable_irq (NVIC_EXTI15_10_IRQ); +} +#endif static void cmd_dispatch (void) { uint8_t c; - while (!ring_read_byte (&rx1_ring, &c)) { + while (!ring_read_byte (&rx2_ring, &c)) { printf ("KEY> %c\r\n", c); @@ -21,8 +33,13 @@ static void cmd_dispatch (void) gps_reset(); break; + case 'I': + gps_bs(); + break; + case 'A': - gps_almanac(); + //gps_almanac(); + gps_dump_almanac(); break; } } @@ -43,7 +60,123 @@ static const clock_scale_t hse_10mhz_3v3_168 = { .apb2_frequency = 84000000, }; +static const clock_scale_t hse_10mhz_3v3_120 = { + /* 120 */ + .pllm = 10, + .plln = 240, + .pllp = 2, + .pllq = 5, + .hpre = RCC_CFGR_HPRE_DIV_NONE, + .ppre1 = RCC_CFGR_PPRE_DIV_4, + .ppre2 = RCC_CFGR_PPRE_DIV_2, + .power_save = 1, + .flash_config = FLASH_ACR_ICE | FLASH_ACR_DCE | + FLASH_ACR_LATENCY_3WS, + .apb1_frequency = 30000000, + .apb2_frequency = 60000000, +}; + +static const clock_scale_t hse_10mhz_3v3_84 = { + .pllm = 10, + .plln = 336, + .pllp = 4, + .pllq = 7, + .hpre = RCC_CFGR_HPRE_DIV_NONE, + .ppre1 = RCC_CFGR_PPRE_DIV_2, + .ppre2 = RCC_CFGR_PPRE_DIV_NONE, + .flash_config = FLASH_ACR_ICE | FLASH_ACR_DCE | + FLASH_ACR_LATENCY_2WS, + .apb1_frequency = 42000000, + .apb2_frequency = 84000000, +}; + + +static const clock_scale_t hse_10mhz_3v3_48 = { + .pllm = 10, + .plln = 96, + .pllp = 2, + .pllq = 2, + .hpre = RCC_CFGR_HPRE_DIV_NONE, + .ppre1 = RCC_CFGR_PPRE_DIV_4, + .ppre2 = RCC_CFGR_PPRE_DIV_2, + .power_save = 1, + .flash_config = FLASH_ACR_ICE | FLASH_ACR_DCE | + FLASH_ACR_LATENCY_3WS, + .apb1_frequency = 12000000, + .apb2_frequency = 24000000, +}; + +static void pd_port (uint32_t p) +{ + unsigned c; + + for (c = 0; c < 32; ++c) { + + if ((p == GPIOA) && ((c == 13) || (c == 14))) continue; + + gpio_mode_setup (p, GPIO_MODE_INPUT, GPIO_PUPD_NONE, 1UL << c); + } +} + + +static void pd_clear (uint32_t g, uint32_t b) +{ + gpio_mode_setup (g, GPIO_MODE_OUTPUT, GPIO_PUPD_NONE, b); + gpio_set_output_options (g, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, b); + gpio_clear (g, b); +} + + +static void pd_set (uint32_t g, uint32_t b) +{ + gpio_mode_setup (g, GPIO_MODE_OUTPUT, GPIO_PUPD_NONE, b); + gpio_set_output_options (g, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, b); + gpio_set (g, b); +} + + +static void pd(void) +{ + pd_port (GPIOA); + pd_port (GPIOB); + pd_port (GPIOC); + pd_port (GPIOD); + pd_port (GPIOE); + pd_port (GPIOF); + pd_port (GPIOG); + + pd_set (GPIOB, GPIO10); + + pd_set (GPIOG, GPIO4); + pd_set (GPIOD, GPIO10); + + pd_set (GPIOD, GPIO1); + pd_set (GPIOB, GPIO13); + + pd_set (GPIOE, GPIO3); + pd_set (GPIOE, GPIO4); + + + rcc_periph_clock_disable (RCC_ETHMACPTP); + rcc_periph_clock_disable (RCC_ETHMACRX); + rcc_periph_clock_disable (RCC_ETHMACTX); + rcc_periph_clock_disable (RCC_ETHMAC); + rcc_periph_clock_disable (RCC_USART2); + rcc_periph_clock_disable (RCC_USART1); + rcc_periph_clock_disable (RCC_GPIOG); + rcc_periph_clock_disable (RCC_GPIOF); + rcc_periph_clock_disable (RCC_GPIOE); + rcc_periph_clock_disable (RCC_GPIOD); + rcc_periph_clock_disable (RCC_GPIOC); + rcc_periph_clock_disable (RCC_GPIOB); + rcc_periph_clock_disable (RCC_GPIOA); + rcc_periph_clock_disable (RCC_SYSCFG); + + + + for (;;); +} static void board_setup (void) @@ -58,22 +191,24 @@ board_setup (void) rcc_periph_clock_enable (RCC_GPIOC); rcc_periph_clock_enable (RCC_GPIOD); rcc_periph_clock_enable (RCC_GPIOE); + rcc_periph_clock_enable (RCC_GPIOF); + rcc_periph_clock_enable (RCC_GPIOG); rcc_periph_clock_enable (RCC_USART1); - rcc_periph_clock_enable (RCC_USART3); + rcc_periph_clock_enable (RCC_USART2); rcc_periph_clock_enable (RCC_ETHMAC); rcc_periph_clock_enable (RCC_ETHMACTX); rcc_periph_clock_enable (RCC_ETHMACRX); rcc_periph_clock_enable (RCC_ETHMACPTP); - - - nvic_set_priority (NVIC_EXTI2_IRQ, 0x0); - nvic_set_priority (NVIC_EXTI0_IRQ, 0x10); - nvic_set_priority (NVIC_EXTI15_10_IRQ, 0x20); + nvic_set_priority (NVIC_EXTI9_5_IRQ, 0x00); + nvic_set_priority (NVIC_EXTI3_IRQ, 0x10); + nvic_set_priority (NVIC_EXTI4_IRQ, 0x20); nvic_set_priority (NVIC_USART1_IRQ, 0x30); - nvic_set_priority (NVIC_USART3_IRQ, 0x30); + nvic_set_priority (NVIC_USART2_IRQ, 0x30); nvic_set_priority (NVIC_ETH_IRQ, 0x40); nvic_set_priority (NVIC_SYSTICK_IRQ, 0x50); + + // nvic_enable_irq (NVIC_EXTI15_10_IRQ); } @@ -95,6 +230,8 @@ system_init (void) printf ("STETH\r\n"); steth_init(); + max7219_init (1); + gps_init(); ntp_init(); @@ -123,9 +260,6 @@ main (void) - - - while (1) { #if 0 { @@ -147,6 +281,8 @@ main (void) cmd_dispatch(); dispatch_lwip(); + max7219_dispatch(); + } return 0; diff --git a/app/max7219.c b/app/max7219.c new file mode 100644 index 0000000..fbba10d --- /dev/null +++ b/app/max7219.c @@ -0,0 +1,143 @@ +#include "project.h" + +#define NCS (GPIO7) +#define NCS_PORT GPIOG + +#define SCK (GPIO3) +#define SCK_PORT GPIOB + +#define MOSI (GPIO5) +#define MOSI_PORT GPIOB + + +static void +set (int sck, int ncs, int mosi) +{ + if (sck) + SET (SCK); + else + CLEAR (SCK); + + + if (ncs) + SET (NCS); + else + CLEAR (NCS); + + + if (mosi) + SET (MOSI); + else + CLEAR (MOSI); + + //delay_us(10); + +} + +static void +spip_send_8 (uint8_t wot) +{ + int i; + + for (i = 0; i < 8; ++i) { + set (0, 0, wot & 0x80); + set (1, 0, wot & 0x80); + set (0, 0, wot & 0x80); + wot <<= 1; + } +} + + +static int mutex = 0; + +static int +lock (void) +{ + if (__sync_add_and_fetch (&mutex, 1) != 1) { + __sync_sub_and_fetch (&mutex, 1); + return -1; + } + + return 0; +} + + +static void +unlock (void) +{ + __sync_sub_and_fetch (&mutex, 1); +} + + +static void +write_reg (uint8_t reg, uint8_t data) +{ + while (lock()); + + set (0, 1, 0); + set (0, 0, 0); + + spip_send_8 (reg); + spip_send_8 (data); + + set (0, 0, 0); + set (0, 1, 0); + unlock(); +} + +static void write_pair (uint8_t reg, int d) +{ + write_reg (reg, d / 10); + write_reg (reg - 1, (d % 10) | 0x80); +} + +void max7219_write (int d, int h, int m, int s) +{ + + write_pair (8, d); + write_pair (6, h); + write_pair (4, m); + write_pair (2, s); + +} + +void max7219_dispatch (void) +{ + uint32_t now = SCS_DWT_CYCCNT; + uint64_t abs = abs_extend (now); + EPOCH e = pll_decompose (abs); + UTC u = time_epoch_to_utc (e); + + + max7219_write (u.mday, u.hour, u.minute, u.second); +} + +void +max7219_init (int on) +{ + MAP_OUTPUT_PP (SCK); + MAP_OUTPUT_PP (NCS); + MAP_OUTPUT_PP (MOSI); + + set (0, 1, 0); + + + if (on) { + + write_reg (0xc, 0x1); //Power up + write_reg (0xf, 0x0); //normal mode + + write_reg (0x9, 0xff); //BCD decode + write_reg (0xb, 0x7); //8 digits + write_reg (0xa, 0x8); //intensity + } else { + write_reg (0xc, 0x0); //Power up + } + + + +} + + + + diff --git a/app/msf.c b/app/msf.c index 82dea7d..954e57f 100644 --- a/app/msf.c +++ b/app/msf.c @@ -1,47 +1,51 @@ #include "project.h" -#define P1 (GPIO1) +#define J2(a,b) a ## b +#define J3(a,b,c) a ## b ## c + +#define P1 (GPIO3) #define P1_PORT GPIOE -#define T (GPIO0) +#define T_BIT 1 #define T_PORT GPIOE +#define T_EXTI_LINE T_BIT + + +#define M_T(a) J2(GPIO,a) +#define T M_T(T_BIT) +#define M_EXTI_T(a) J2(EXTI,a) +#define EXTI_T M_EXTI_T(T_EXTI_LINE) +#define M_exti_t_isr(a) J3(exti,a,_isr) +#define exti_t_isr M_exti_t_isr(T_EXTI_LINE) +#define M_NVIC_EXTI_T_IRQ(a) J3(NVIC_EXTI,a,_IRQ) +#define NVIC_EXTI_T_IRQ M_NVIC_EXTI_T_IRQ(T_EXTI_LINE) + static Event_ring msf_ring; static uint64_t msf_last_second; uint64_t msf_last_happy; +static char msf_info[40]; +static EPOCH msf_time; -void exti0_isr (void) +void exti_t_isr (void) { uint32_t now = SCS_DWT_CYCCNT; int v; v = !!gpio_get (T_PORT, T); - nvic_disable_irq (NVIC_EXTI0_IRQ); - exti_reset_request (EXTI0); + nvic_disable_irq (NVIC_EXTI_T_IRQ); + + exti_reset_request (EXTI_T); msf_ring.events[msf_ring.tx_ptr].when = now; msf_ring.events[msf_ring.tx_ptr].value = v; msf_ring.tx_ptr = (msf_ring.tx_ptr + 1) & ERING_MASK; -#if 0 - - if (time_known) { - uint64_t abs = abs_extend (now); - EPOCH e = pll_decompose (abs); - UTC u = time_epoch_to_utc (e); - - printf ("QRR %d.%09d %d\r\n", (u.minute * 60) + u.second, u.nanosecond, (int) !v); - printf ("QRR %d.%09d %d\r\n", (u.minute * 60) + u.second, u.nanosecond, (int) v); - } - -#endif - - nvic_enable_irq (NVIC_EXTI0_IRQ); - + nvic_enable_irq (NVIC_EXTI_T_IRQ); } @@ -78,7 +82,7 @@ static int check_min_ident (uint8_t *i) static void process_bits (uint64_t abs) { UTC u; - EPOCH msf_time; + EPOCH e; if (check_min_ident (&bitsa[52])) return; @@ -102,17 +106,23 @@ static void process_bits (uint64_t abs) /* This is always valid a check_min_ident will fail for leap seconds*/ - msf_time = time_utc_to_epoch (u); + e = time_utc_to_epoch (u); + + if (bitsb[58]) e.s -= 3600; /*BST*/ msf_last_happy = make_happy (abs, 0); - pll_set_offset (msf_time, abs); + pll_set_offset (e, abs); dump_bits ("msfa", bitsa); dump_bits ("msfb", bitsb); printf ("MSF: Next minute is: %02d-%02d-%02d %02d:%02d\r\n", u.year, u.month, u.mday, u.hour, u.minute); - //time_print_epoch (msf_time); + + msf_time = e; + msf_time.s -= 1; + + //time_print_epoch (e); } @@ -127,15 +137,6 @@ static void report_bits (uint64_t abs, int second, int a, int b) } -static void report_time (uint64_t abs) -{ -#if 1 - EPOCH e = pll_decompose (abs); - time_print_epoch ("MSF : ", e); -#endif -} - - void msf_dispatch (void) { static uint32_t last_0, last_1, last_s; @@ -153,8 +154,21 @@ void msf_dispatch (void) v = msf_ring.events[msf_ring.rx_ptr].value; now = msf_ring.events[msf_ring.rx_ptr].when; + led1_set (v); + msf_ring.rx_ptr = (msf_ring.rx_ptr + 1) & ERING_MASK; +#if 0 + { + abs = abs_extend (now); + EPOCH e = pll_decompose (abs); + UTC u = time_epoch_to_utc (e); + + printf (" MSF %d %02d:%02d.%06d\r\n", v, u.minute, u.second, (int) (u.nanosecond / 1000)); + } +#endif + + if (v) { pulse_w = now - last_0; pulse_w /= (HZ / 1000); @@ -162,6 +176,7 @@ void msf_dispatch (void) if (pulse_w > 300) { last_s = now; is_s = 1; + msf_time.s++; } last_1 = now; @@ -189,14 +204,14 @@ void msf_dispatch (void) pll_dispatch (msf_last_happy, abs, "MSF"); + sprintf (msf_info, "m=%d s=%02d b=%d%d", had_m, second, bita, bitb); if (had_m) { report_bits (abs, second, bita, bitb); second++; } - if (time_known) - report_time (abs); + report_time ("MSF", msf_time, abs, msf_info); // stats(); } @@ -229,12 +244,15 @@ msf_init (void) MAP_INPUT (T); MAP_OUTPUT_PP (P1); + gpio_set (P1_PORT, P1); + delay_ms (50); gpio_clear (P1_PORT, P1); - exti_select_source (EXTI0, T_PORT); - exti_set_trigger (EXTI0, EXTI_TRIGGER_BOTH); - exti_enable_request (EXTI0); - nvic_enable_irq (NVIC_EXTI0_IRQ); + exti_select_source (EXTI_T, T_PORT); + exti_set_trigger (EXTI_T, EXTI_TRIGGER_BOTH); + exti_enable_request (EXTI_T); + + nvic_enable_irq (NVIC_EXTI_T_IRQ); } diff --git a/app/new_almanac.c b/app/new_almanac.c new file mode 100644 index 0000000..f31d51d --- /dev/null +++ b/app/new_almanac.c @@ -0,0 +1,53 @@ + +/* + +201343145 m=1 s=26 b=0 +MSF : Thr 1970-Jan-01 00:00:32.207630295 m=1 s=26 b=11 +GPS : Thr 1970-Jan-01 00:00:33.165197086 V:37 Fix:-! TXCO +186919E-12 +MSF : Thr 1970-Jan-01 00:00:33.213616575 m=1 s=27 b=10 +GPS : Thr 1970-Jan-01 00:00:34.165197586 V:37 Fix:-! TXCO +187035E-12 +MSF : Thr 1970-Jan-01 00:00:34.210351926 m=1 s=28 b=00 +DCF77: Thr 1970-Jan-01 00:00:34.219091892 m=1 s=27 b=0 +GPS : Thr 1970-Jan-01 00:00:35.165198092 V:37 Fix:-! TXCO +187150E-12 +DCF77: Thr 1970-Jan-01 00:00:35.201664603 m=1 s=00 b=0 +MSF : Thr 1970-Jan-01 00:00:35.212095260 m=1 s=00 b=11 +KEY> A + Almanac: 1 2045 4145ce 3914d0 fd2a00 a10ccc b9a536 1bda53 8963ea e7ffdc + Almanac: 2 2045 429b0b 390736 fd1b00 a10ce2 b6e6de b85dab 955a7a eaffa0 + Almanac: 3 2045 430fe4 390d29 fd4800 a10c1c e42323 17f9b8 62b239 180010 + Almanac: 4 0 000000 000000 000000 000000 000000 000000 000000 000000 + Almanac: 5 2045 452da0 390498 fd3c00 a10ccc e31523 1cc9aa 01918b 000004 + Almanac: 6 2045 460d3e 391499 fd2a00 a10bec b94ec9 d12419 915098 21ffc0 + Almanac: 7 2045 476511 390898 fd2700 a10c48 3a0ba3 9b355c 707ac6 01ffd0 + Almanac: 8 2045 4823cf 39123f fd5a00 a10d5c 8e3279 f3a1f4 ecd967 ee0004 + Almanac: 9 2045 490b51 3906d7 fd5000 a10d59 0e2fd6 46ade7 ef5573 3affc0 + Almanac: 10 2045 4a242a 390d2f fd4c00 a10cf2 e40114 913453 34ffea 0cffc8 + Almanac: 11 2045 4b8770 39e9ef fd0100 a10cfd a773e2 4c3b4e 6c97aa ab005c + Almanac: 12 2045 4c3e21 391acf fd6300 a10d19 66d384 2abce7 5226da 21fffc + Almanac: 13 2045 4d1df9 3910e4 fd5b00 a10cf2 13bbb3 36e767 b5dc0e f60014 +GPS : Thr 1970-Jan-01 00:00:36.165198597 V:37 Fix:-! TXCO +189311E-12 + Almanac: 14 2045 4e545e 390c12 fd5500 a10d14 11f1aa b0aece d7fa67 f40010 +MSF : Thr 1970-Jan-01 00:00:36.209535367 m=1 s=01 b=00 +DCF77: Thr 1970-Jan-01 00:00:36.221746226 m=1 s=01 b=0 + Almanac: 15 2045 4f5c1d 39f6e6 fd4000 a10cd1 0affca 1f3bf7 bde400 d50038 + Almanac: 16 2045 50587c 391b0e fd6600 a10c02 6798bd 16957f 041094 fcfff0 + Almanac: 17 2045 5169b8 391b32 fd6000 a10d62 90e872 ba1b87 df6525 03004c + Almanac: 18 2045 527bbf 3906d0 fd1900 a10d47 b775a0 382ff7 7f7598 040038 + Almanac: 19 2045 534d54 3919bb fd5e00 a10cb2 92cc0e 376849 51e9ee d3002c + Almanac: 20 2045 5423b2 39f808 fd2700 a10cfb df459e 5e294a 7b9ab3 440014 + Almanac: 21 2045 55cb07 39031d fd1600 a10db2 b71a2d c46c6b 405027 e1005c + Almanac: 22 2045 563b9a 39f5ee fd2600 a10bf7 e143b9 c70a7b c2ce9d a8ffd0 + Almanac: 23 2045 576a02 3900db fd4b00 a10c93 0e0162 a2dedb a8436e e60014 + Almanac: 24 2045 584380 39fda1 fd1500 a10d3b 376775 18921c 94aa72 f70014 + Almanac: 25 2045 594482 391299 fd5400 a10d8a 643dbf 23858e 44f767 9ffff4 + Almanac: 26 2045 5a1e67 39066c fd4500 a10c29 6320f6 05cf4c 29e18b 140064 + Almanac: 27 2045 5b384f 3917a4 fd6000 a10cc8 8ea338 121aed e1e112 f4ffc8 + Almanac: 28 2045 5c9cdb 391a5d fd6600 a10d45 67c27b c4112b 038947 640010 + Almanac: 29 2045 5d06a1 391c21 fd6100 a10c16 915b70 3b6ed0 03bbec 20ffc8 + Almanac: 30 2045 5e1ed8 39ff21 fd1800 a10c58 3b3c5a 8515d5 70d4f6 f6ffd4 + Almanac: 31 2045 5f4b9e 390b92 fd2a00 a10c1d 3a9b64 ffcada 601fce 06fff8 + Almanac: 32 2045 60165d 3909a2 fd5400 a10dc2 0e7261 96ae2c fe3295 e900a8 +GPS : Thr 1970-Jan-01 00:00:37.165199103 V:37 Fix:-! TXCO +189311E-12 +DCF77: Thr 1970-Jan-01 00:00:37.206403420 m=1 s=02 b=0 + +*/ diff --git a/app/parse_alamanc.pl b/app/parse_alamanc.pl new file mode 100755 index 0000000..ee946b7 --- /dev/null +++ b/app/parse_alamanc.pl @@ -0,0 +1,91 @@ +#!/usr/bin/env perl + +use strict; +use Data::Dumper; +use Math::Trig; + + + +sub rad_to_ss($) +{ +my $r=shift; +return undef unless defined $r; +return $r/pi; +} + + +sub rad_to_d_ss($) +{ +my $r=shift; +return undef unless defined $r; +return ($r/pi)-0.3; +} + + +sub squirt_bits($$$) +{ +my ($v,$n,$s)=@_; + +#die unless defined $v; + +$s=2.0**-$s; + +my $i=int(($v*$s) +.5); + +my $m=1 << $n; +if ($i<0) { + $i+=$m; +} + +print "v=$v became 0<=$i<$m\n"; + +my $b=reverse(sprintf ("%0".$n."B",$i)); + +return $b ." "; +} + + + +sub process_sv($) +{ +my $h=shift; +my $a=""; + + +$a.=squirt_bits($h->{'ID'},32,0); +$a.=squirt_bits($h->{'week'},32,0); +$a.=squirt_bits($h->{'Eccentricity'},16,-21); +$a.=squirt_bits($h->{'Time of Applicability(s)'},8,12); + + +$a.=squirt_bits(rad_to_d_ss($h->{'Orbital Inclination(rad)'}),16,-19); +$a.=squirt_bits(rad_to_ss($h->{'Rate of Right Ascen(r/s)'}),16,-38); +$a.=squirt_bits($h->{'SQRT(A) (m 1/2)'},16,-11); +$a.=squirt_bits(rad_to_ss($h->{'Right Ascen at Week(rad)'}),24,-23); +$a.=squirt_bits(rad_to_ss($h->{'Argument of Perigee(rad)'}),24,-23); +$a.=squirt_bits(rad_to_ss($h->{'Mean Anom(rad)'}),24,-23); +$a.=squirt_bits($h->{'Af0(s)'},11,-20); +$a.=squirt_bits($h->{'Af1(s/s)'},11,-38); + + +print Dumper($h); +} + + + +my $hash={}; + + +while (<>) { +chomp; + +if (/^\*{5}/) { + process_sv($hash); + $hash={}; +} elsif (/^([^:]+):\s*([^\r\n]+)[\r\n]*$/) { + $hash->{$1}=$2; +} +} + + + diff --git a/app/pll.c b/app/pll.c index 460b789..986034c 100644 --- a/app/pll.c +++ b/app/pll.c @@ -176,7 +176,7 @@ void pll_dispatch (uint64_t happy, uint64_t edge, const char *src) led_blink (100); -#if 1 +#if 0 printf ("EDGE %08x%08x\r\n", (unsigned) (edge >> 32), (unsigned) (edge & 0xffffffff)); diff --git a/app/project.h b/app/project.h index 869cb3d..47eecb3 100644 --- a/app/project.h +++ b/app/project.h @@ -14,6 +14,7 @@ #include #include #include +#include #include #include #include @@ -23,6 +24,7 @@ #include #include + #include #include #include @@ -43,7 +45,8 @@ #include "prototypes.h" -#define HZ 167999973 +#define HZ 10000000 +//#define HZ 167999973 //#define HZ 168000000 //#define HZ 167968615 //#define HZ 165925490 diff --git a/app/prototypes.h b/app/prototypes.h index 933e583..667262b 100644 --- a/app/prototypes.h +++ b/app/prototypes.h @@ -1,9 +1,13 @@ /* led.c */ extern void led_init(void); +extern void led1_set(int v); +extern void led2_set(int v); +extern void led3_set(int v); extern void led_clear(void); extern void led_set(void); extern void led_blink(unsigned ms); extern void led_tick(void); +extern void led_slow_tick(void); /* ticker.c */ extern volatile uint32_t ticks; extern void delay_us(uint32_t d); @@ -17,14 +21,14 @@ extern int ring_read_byte(volatile ring_t *r, uint8_t *c); extern int ring_write(volatile ring_t *r, uint8_t *buf, size_t len, int blocking); extern int ring_empty(volatile ring_t *r); /* usart.c */ -extern volatile ring_t rx3_ring; -extern volatile ring_t tx3_ring; +extern volatile ring_t rx2_ring; +extern volatile ring_t tx2_ring; extern volatile ring_t rx1_ring; extern volatile ring_t tx1_ring; -extern void usart3_isr(void); -extern void usart3_queue(uint8_t d); -extern void usart3_drain(void); -extern int usart3_write(char *ptr, int len, int blocking); +extern void usart2_isr(void); +extern void usart2_queue(uint8_t d); +extern void usart2_drain(void); +extern int usart2_write(char *ptr, int len, int blocking); extern void usart1_isr(void); extern void usart1_queue(uint8_t d); extern void usart1_drain(void); @@ -52,7 +56,7 @@ extern void steth_init(void); extern void steth_slow_tick(void); /* msf.c */ extern uint64_t msf_last_happy; -extern void exti0_isr(void); +extern void exti1_isr(void); extern void msf_dispatch(void); extern void msf_init(void); /* abs.c */ @@ -64,6 +68,7 @@ extern void abs_slow_tick(void); extern int64_t pll_freq; extern uint64_t pll_last_update; extern int pll_valid; +extern int pll_ready; extern void pll_meh(void); extern uint64_t make_happy(uint64_t abs, int64_t shift); extern void pll_dispatch(uint64_t happy, uint64_t edge, const char *src); @@ -73,18 +78,19 @@ extern EPOCH pll_decompose_diff(int64_t diff); extern EPOCH pll_decompose(uint64_t abs); /* main.c */ extern int time_known; +extern void rcc_clock_setup_hse_3v3_no_pll(const clock_scale_t *clock); extern int main(void); /* time_fn.c */ extern UTC time_epoch_to_utc(EPOCH epoch); extern EPOCH time_utc_to_epoch(UTC u); extern void utc_to_str(char *dst, UTC u); -extern void time_print_utc(const char *p, UTC u); -extern void time_print_epoch(const char *p, EPOCH e); +extern void time_print_utc(const char *p, UTC u, const char *t); +extern void time_print_epoch(const char *p, EPOCH e, const char *t); /* ntp.c */ extern void ntp_init(void); /* dcf77.c */ extern uint64_t dcf77_last_happy; -extern void exti15_10_isr(void); +extern void exti2_isr(void); extern void dcf77_dispatch(void); extern void dcf77_init(void); /* util.c */ @@ -94,12 +100,20 @@ extern unsigned le_bcd(uint8_t *d, unsigned s, unsigned e); /* stats.c */ /* gps.c */ extern uint64_t gps_last_happy; -extern void exti2_isr(void); +extern void exti9_5_isr(void); extern void gps_dispatch(void); extern int gps_init(void); extern int gps_almanac(void); +extern void gps_dump_almanac(void); +extern int gps_bs(void); extern void gps_reset(void); /* hexdump.c */ extern void hexdump(void *_d, int len); /* bits.c */ extern void dump_bits(char *wot, uint8_t *bits); +/* max7219.c */ +extern void max7219_write(int d, int h, int m, int s); +extern void max7219_dispatch(void); +extern void max7219_init(int on); +/* report.c */ +extern void report_time(const char *src, EPOCH e, uint64_t abs, const char *info); diff --git a/app/report.c b/app/report.c new file mode 100644 index 0000000..a7bd4db --- /dev/null +++ b/app/report.c @@ -0,0 +1,15 @@ +#include "project.h" + + +void report_time (const char *src, EPOCH e, uint64_t abs, const char *info) +{ + printf ("%s %08x%08x %08x%08x %s\r\n", + src, + (unsigned) (abs >> 32), + (unsigned) (abs & 0xffffffff), + (unsigned) (e.s >> 32), + (unsigned) (e.s & 0xffffffff), + info); +} + + diff --git a/app/stdio.c b/app/stdio.c index 4a46f3f..9a8c74a 100644 --- a/app/stdio.c +++ b/app/stdio.c @@ -27,7 +27,7 @@ _write (int file, int ret; - ret = usart1_write (buf, nbytes, 1); + ret = usart2_write (buf, nbytes, 1); if (ret < 0) { errno = -ret; @@ -77,5 +77,5 @@ isatty (int file) void stdio_drain (void) { - usart1_drain(); + usart2_drain(); } diff --git a/app/steth.c b/app/steth.c index ead4efd..7b23b3c 100644 --- a/app/steth.c +++ b/app/steth.c @@ -260,11 +260,16 @@ static void eth_reset (void) rcc_periph_reset_release (RST_ETHMAC); +#ifdef NRST +#if 0 delay_us (1000); CLEAR (NRST); delay_us (1); SET (NRST); delay_us (1000); +#endif +#endif + TRACE; ETH_DMABMR |= ETH_DMABMR_SR; @@ -285,7 +290,7 @@ static void eth_reset (void) TRACE; my_eth_init (PHY, ETH_CLK_150_168MHZ); - phy_set_ignore_address(); + //phy_set_ignore_address(); TRACE; phy_stat(); @@ -323,7 +328,9 @@ steth_init (void) delay_ms (1); rcc_periph_reset_release (RST_ETHMAC); +#ifdef NRST MAP_OUTPUT_PP (NRST); +#endif MAP_OUTPUT_PP (RXD0); MAP_OUTPUT_PP (RXD1); @@ -335,16 +342,20 @@ steth_init (void) SET (RXD1); SET (CRS_DV); +#ifdef NRST delay_ms (1); CLEAR (NRST); delay_ms (1); SET (NRST); delay_ms (1); +#endif MAP_AF_100 (MDIO, GPIO_AF11); MAP_AF_100 (CRS_DV, GPIO_AF11); +#ifdef RXER MAP_AF_100 (RXER, GPIO_AF11); +#endif MAP_AF_100 (TXEN, GPIO_AF11); MAP_AF_100 (TXD0, GPIO_AF11); MAP_AF_100 (TXD1, GPIO_AF11); diff --git a/app/steth.h b/app/steth.h index d2a1352..ca752a7 100644 --- a/app/steth.h +++ b/app/steth.h @@ -1,17 +1,14 @@ #define PHY PHY0 -#define RXER GPIO10 -#define RXER_PORT GPIOB - #define TXEN GPIO11 -#define TXEN_PORT GPIOB +#define TXEN_PORT GPIOG -#define TXD0 GPIO12 -#define TXD0_PORT GPIOB +#define TXD0 GPIO13 +#define TXD0_PORT GPIOG -#define TXD1 GPIO13 -#define TXD1_PORT GPIOB +#define TXD1 GPIO14 +#define TXD1_PORT GPIOG #define RXD0 GPIO4 #define RXD0_PORT GPIOC @@ -31,9 +28,6 @@ #define REF_CLK GPIO1 #define REF_CLK_PORT GPIOA -#define NRST GPIO2 -#define NRST_PORT GPIOE - #define DESC_SZ ETH_DES_EXT_SIZE #define FRAME_SZ 1516 diff --git a/app/ticker.c b/app/ticker.c index 0f2b3e3..2016058 100644 --- a/app/ticker.c +++ b/app/ticker.c @@ -35,6 +35,7 @@ sys_tick_handler (void) abs_slow_tick(); steth_slow_tick(); + led_slow_tick(); } @@ -53,8 +54,8 @@ ticker_init (void) { uint32_t v, w; - /*168MHz / 168000 -> 1ms */ - systick_set_reload (168000); + /*10MHz / 10000 -> 1ms */ + systick_set_reload (10000); systick_set_clocksource (STK_CSR_CLKSOURCE_AHB); systick_counter_enable(); /* this done last */ diff --git a/app/time_fn.c b/app/time_fn.c index 957bc47..87fb48f 100644 --- a/app/time_fn.c +++ b/app/time_fn.c @@ -217,16 +217,16 @@ void utc_to_str (char *dst, UTC u) } -void time_print_utc (const char *p, UTC u) +void time_print_utc (const char *p, UTC u, const char *t) { const char *dname[] = {"Sun", "Mon", "Tue", "Wed", "Thr", "Fri", "Sat", "Sun"}; const char *mname[] = {"", "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"}; - printf ("%s%s %04d-%s-%02d %02d:%02d:%02d.%09d\r\n", p ? p : "", dname[u.wday], u.year, mname[u.month], u.mday, u.hour, u.minute, u.second, u.nanosecond); + printf ("%s%s %04d-%s-%02d %02d:%02d:%02d.%09d %s\r\n", p ? p : "", dname[u.wday], u.year, mname[u.month], u.mday, u.hour, u.minute, u.second, u.nanosecond , t ? t : ""); } -void time_print_epoch (const char *p, EPOCH e) +void time_print_epoch (const char *p, EPOCH e, const char *t) { UTC u = time_epoch_to_utc (e); - time_print_utc (p, u); + time_print_utc (p, u, t); } diff --git a/app/time_fn.h b/app/time_fn.h index a1a4602..2409eeb 100644 --- a/app/time_fn.h +++ b/app/time_fn.h @@ -12,8 +12,8 @@ typedef struct { } UTC; typedef struct { - int64_t s; - int64_t ns; + int64_t s; + int64_t ns; } EPOCH; diff --git a/app/ubx.h b/app/ubx.h index 44c4782..4874e92 100644 --- a/app/ubx.h +++ b/app/ubx.h @@ -5,6 +5,14 @@ ubx_get_u8 (uint8_t *ptr, uint8_t *v) return 1; } +static inline int +ubx_get_i8 (uint8_t *ptr, int8_t *v) +{ + *v = (int8_t) * ptr; + return 1; +} + + static inline int ubx_get_u16 (uint8_t *ptr, uint16_t *v) { diff --git a/app/usart.c b/app/usart.c index e826a22..5d5614d 100644 --- a/app/usart.c +++ b/app/usart.c @@ -4,11 +4,11 @@ #define BIG_BUFFER_SIZE 600 -volatile ring_t rx3_ring; -static uint8_t rx3_ring_buf[BUFFER_SIZE]; +volatile ring_t rx2_ring; +static uint8_t rx2_ring_buf[BUFFER_SIZE]; -volatile ring_t tx3_ring; -static uint8_t tx3_ring_buf[BUFFER_SIZE]; +volatile ring_t tx2_ring; +static uint8_t tx2_ring_buf[BUFFER_SIZE]; volatile ring_t rx1_ring; static uint8_t rx1_ring_buf[BUFFER_SIZE]; @@ -23,62 +23,64 @@ static uint8_t tx1_ring_buf[BUFFER_SIZE]; #define RX1 GPIO10 #define RX1_PORT GPIOA -#define TX3 GPIO10 -#define TX3_PORT GPIOC +#define TX2 GPIO5 +#define TX2_PORT GPIOD -#define RX3 GPIO11 -#define RX3_PORT GPIOC +#define RX2 GPIO6 +#define RX2_PORT GPIOD +#define RX2_EN GPIO4 +#define RX2_EN_PORT GPIOG -void usart3_isr (void) +void usart2_isr (void) { uint8_t data; /* Check if we were called because of RXNE. */ - if (((USART_CR1 (USART3) & USART_CR1_RXNEIE) != 0) && - ((USART_SR (USART3) & USART_SR_RXNE) != 0)) { + if (((USART_CR1 (USART2) & USART_CR1_RXNEIE) != 0) && + ((USART_SR (USART2) & USART_SR_RXNE) != 0)) { /* Retrieve the data from the peripheral. */ - data = usart_recv (USART3); + data = usart_recv (USART2); - ring_write_byte (&rx3_ring, data); + ring_write_byte (&rx2_ring, data); //usart6_queue(data); } /* Check if we were called because of TXE. */ - if (((USART_CR1 (USART3) & USART_CR1_TXEIE) != 0) && - ((USART_SR (USART3) & USART_SR_TXE) != 0)) { + if (((USART_CR1 (USART2) & USART_CR1_TXEIE) != 0) && + ((USART_SR (USART2) & USART_SR_TXE) != 0)) { - if (ring_read_byte (&tx3_ring, &data)) { + if (ring_read_byte (&tx2_ring, &data)) { /*No more data, Disable the TXE interrupt, it's no longer needed. */ - usart_disable_tx_interrupt (USART3); + usart_disable_tx_interrupt (USART2); } else - usart_send_blocking (USART3, data); + usart_send_blocking (USART2, data); } } void -usart3_queue (uint8_t d) +usart2_queue (uint8_t d) { - ring_write_byte (&tx3_ring, d); - usart_enable_tx_interrupt (USART3); + ring_write_byte (&tx2_ring, d); + usart_enable_tx_interrupt (USART2); } void -usart3_drain (void) +usart2_drain (void) { - while (!ring_empty (&tx3_ring)); + while (!ring_empty (&tx2_ring)); } int -usart3_write (char *ptr, int len, int blocking) +usart2_write (char *ptr, int len, int blocking) { int ret; - ret = ring_write (&tx3_ring, (uint8_t *) ptr, len, blocking); - usart_enable_tx_interrupt (USART3); + ret = ring_write (&tx2_ring, (uint8_t *) ptr, len, blocking); + usart_enable_tx_interrupt (USART2); return ret; } @@ -140,33 +142,38 @@ void usart_init (void) { - ring_init (&rx3_ring, rx3_ring_buf, sizeof (rx3_ring_buf)); - ring_init (&tx3_ring, tx3_ring_buf, sizeof (tx3_ring_buf)); + ring_init (&rx2_ring, rx2_ring_buf, sizeof (rx2_ring_buf)); + ring_init (&tx2_ring, tx2_ring_buf, sizeof (tx2_ring_buf)); - MAP_AF (TX3, GPIO_AF7); - MAP_AF_PU (RX3, GPIO_AF7); + MAP_OUTPUT_PP (RX2_EN); + SET (RX2_EN); - usart_set_baudrate (USART3, 9600); - usart_set_databits (USART3, 8); - usart_set_stopbits (USART3, USART_STOPBITS_1); - usart_set_parity (USART3, USART_PARITY_NONE); - usart_set_flow_control (USART3, USART_FLOWCONTROL_NONE); - usart_set_mode (USART3, USART_MODE_TX_RX); + MAP_INPUT (RX2); + MAP_AF (TX2, GPIO_AF7); + MAP_AF_PU (RX2, GPIO_AF7); - usart_enable_rx_interrupt (USART3); + usart_set_baudrate (USART2, 38400); + usart_set_databits (USART2, 8); + usart_set_stopbits (USART2, USART_STOPBITS_1); + usart_set_parity (USART2, USART_PARITY_NONE); + usart_set_flow_control (USART2, USART_FLOWCONTROL_NONE); + usart_set_mode (USART2, USART_MODE_TX_RX); - usart_enable (USART3); + usart_enable_rx_interrupt (USART2); - nvic_enable_irq (NVIC_USART3_IRQ); + usart_enable (USART2); + + nvic_enable_irq (NVIC_USART2_IRQ); ring_init (&rx1_ring, rx1_ring_buf, sizeof (rx1_ring_buf)); ring_init (&tx1_ring, tx1_ring_buf, sizeof (tx1_ring_buf)); + MAP_INPUT (RX1); MAP_AF (TX1, GPIO_AF7); MAP_AF_PU (RX1, GPIO_AF7); - usart_set_baudrate (USART1, 38400); + usart_set_baudrate (USART1, 9600); usart_set_databits (USART1, 8); usart_set_stopbits (USART1, USART_STOPBITS_1); usart_set_parity (USART1, USART_PARITY_NONE); diff --git a/oocd/board/stm32f407zet6.cfg b/oocd/board/stm32f407zet6.cfg new file mode 100644 index 0000000..9be7ac5 --- /dev/null +++ b/oocd/board/stm32f407zet6.cfg @@ -0,0 +1,5 @@ + +source [find target/stm32f4x.cfg] + +#reset_config srst_only +reset_config trst_only diff --git a/oocd/stm32-f407.cfg b/oocd/stm32-f407.cfg deleted file mode 100644 index 0809223..0000000 --- a/oocd/stm32-f407.cfg +++ /dev/null @@ -1,6 +0,0 @@ -# -telnet_port 4444 -gdb_port 3333 - -source [find interface/jlink.cfg] -source [find target/stm32f1x.cfg] -- cgit v1.2.3