Implement a secure ICS protocol targeting LoRa Node151 microcontroller for controlling irrigation.
Du kannst nicht mehr als 25 Themen auswählen Themen müssen entweder mit einem Buchstaben oder einer Ziffer beginnen. Sie können Bindestriche („-“) enthalten und bis zu 35 Zeichen lang sein.
 
 
 
 
 
 

257 Zeilen
8.2 KiB

  1. # Copyright 2021 John-Mark Gurney.
  2. #
  3. # Redistribution and use in source and binary forms, with or without
  4. # modification, are permitted provided that the following conditions
  5. # are met:
  6. # 1. Redistributions of source code must retain the above copyright
  7. # notice, this list of conditions and the following disclaimer.
  8. # 2. Redistributions in binary form must reproduce the above copyright
  9. # notice, this list of conditions and the following disclaimer in the
  10. # documentation and/or other materials provided with the distribution.
  11. #
  12. # THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
  13. # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  14. # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  15. # ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
  16. # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  17. # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  18. # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  19. # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  20. # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  21. # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  22. # SUCH DAMAGE.
  23. #
  24. ARMOBJDUMP?= arm-none-eabi-objdump
  25. ARMCC?= arm-none-eabi-gcc
  26. ARMTARGET?= -mcpu=cortex-m3 -mthumb -DSTROBE_SINGLE_THREAD=1
  27. # Clang doesn't work due to no-nano libc
  28. #ARMCC?=clang-mp-9.0
  29. #ARMTARGET?= -nostdlib -ffreestanding -target arm-none-eabi -mcpu=cortex-m3 -mfloat-abi=soft -mthumb
  30. .if $(.OBJDIR) == $(.CURDIR)
  31. .error Need to set MAKEOBJDIR.
  32. .endif
  33. PLATFORM != uname -s
  34. .if $(PLATFORM) == "Darwin"
  35. SOEXT=dylib
  36. .else
  37. .error Unsupported platform: $(PLATFORM)
  38. .endif
  39. PROGEXT = .elf
  40. PROGS = lora.gw lora.irr
  41. SRCS.lora.gw = main.c
  42. SRCS.lora.irr = irr_main.c
  43. SRCS.lora.irr+= comms.c
  44. SRCS.lora.irr+= strobe_rng_init.c
  45. SRCS.lora.irr+= $(STROBE_SRCS)
  46. SRCS+= board.c
  47. SRCS+= misc.c
  48. .if 0
  49. SRCS+= rng_save.c
  50. .endif
  51. CFLAGS+= -I$(.CURDIR)
  52. CFLAGS+= -g
  53. #CFLAGS+= -DNDEBUG
  54. CFLAGS+= -I$(.OBJDIR) # for shared_key.h
  55. # Strobe
  56. .PATH: $(.CURDIR)/strobe
  57. CFLAGS+= -I$(.CURDIR)/strobe
  58. STROBE_SRCS+= strobe.c \
  59. x25519.c
  60. # LoRamac (SX1276) radio code
  61. LORAMAC_SRC = $(.CURDIR)/loramac/src
  62. .PATH: $(LORAMAC_SRC)/radio/sx1276 $(LORAMAC_SRC)/system $(LORAMAC_SRC)/boards/mcu $(LORAMAC_SRC)/boards/NucleoL152
  63. CFLAGS+= -I$(LORAMAC_SRC)/boards
  64. CFLAGS+= -I$(LORAMAC_SRC)/system
  65. CFLAGS+= -I$(LORAMAC_SRC)/radio
  66. CFLAGS+= -DUSE_HAL_DRIVER -DSX1276MB1LAS
  67. SRCS+= sx1276.c
  68. SRCS+= utilities.c
  69. SRCS+= adc.c timer.c delay.c gpio.c uart.c fifo.c
  70. SRCS+= adc-board.c delay-board.c gpio-board.c rtc-board.c lpm-board.c sx1276mb1las-board.c spi-board.c uart-board.c
  71. # Microcontroller
  72. STM32=$(.CURDIR)/stm32
  73. .PATH: $(STM32)/l151ccux
  74. LINKER_SCRIPT=$(STM32)/l151ccux/STM32L151CCUX_FLASH.ld
  75. SRCS+= \
  76. startup_stm32l151ccux.s \
  77. stm32l1xx_hal.c \
  78. stm32l1xx_hal_adc.c \
  79. stm32l1xx_hal_adc_ex.c \
  80. stm32l1xx_hal_cortex.c \
  81. stm32l1xx_hal_dma.c \
  82. stm32l1xx_hal_flash.c \
  83. stm32l1xx_hal_flash_ex.c \
  84. stm32l1xx_hal_gpio.c \
  85. stm32l1xx_hal_pcd.c \
  86. stm32l1xx_hal_pcd_ex.c \
  87. stm32l1xx_hal_pwr.c \
  88. stm32l1xx_hal_pwr_ex.c \
  89. stm32l1xx_hal_rcc.c \
  90. stm32l1xx_hal_rcc_ex.c \
  91. stm32l1xx_hal_rtc.c \
  92. stm32l1xx_hal_rtc_ex.c \
  93. stm32l1xx_hal_spi.c \
  94. stm32l1xx_hal_uart.c \
  95. system_stm32l1xx.c
  96. SRCS+= \
  97. stm32l1xx_it.c \
  98. stm32l1xx_hal_msp.c
  99. CFLAGS+= -I$(STM32)
  100. CFLAGS+= -I$(STM32)/l151ccux
  101. CFLAGS+= -DSTM32L151xC
  102. # USB
  103. .PATH: $(STM32)/usb
  104. SRCS+= \
  105. stm32l1xx_ll_usb.c \
  106. usb_device.c \
  107. usbd_cdc.c \
  108. usbd_cdc_if.c \
  109. usbd_conf.c \
  110. usbd_core.c \
  111. usbd_ctlreq.c \
  112. usbd_desc.c \
  113. usbd_ioreq.c
  114. CFLAGS+= -I$(STM32)/usb
  115. CFLAGS+= -Werror -Wall
  116. LIBLORA_TEST_SRCS= comms.c strobe.c x25519.c
  117. LIBLORA_TEST_OBJS= $(LIBLORA_TEST_SRCS:C/.c$/.no/)
  118. LIBLORA_TEST = liblora_test.$(SOEXT)
  119. $(LIBLORA_TEST): $(LIBLORA_TEST_OBJS)
  120. $(CC) -shared -o $@ $(.ALLSRC)
  121. .MAIN: all
  122. .PHONY: all
  123. DEPENDS = .arm_deps .test_deps
  124. .PHONY: $(DEPENDS)
  125. depend: $(DEPENDS)
  126. .for i in $(DEPENDS)
  127. .sinclude "$i"
  128. .endfor
  129. # Temporarily disabled as OpenOCD can't program EEPROM on the STM32L1.
  130. # This could be used to add the data to flash.
  131. rng_save.c: Makefile
  132. ( echo '#include <strobe_rng_init.h>'; \
  133. echo 'const rng_word_t rng_save[roundup(32, sizeof(rng_word_t)) / sizeof(rng_word_t)] __attribute__ ((section (".eeprom"))) = {'; \
  134. dd if=/dev/random bs=32 count=1 | hexdump -e '4/4 " %3u," "\n"'; \
  135. echo '};' \
  136. ) > $@ || (rm $@ && false)
  137. .arm_deps:
  138. $(ARMCC) $(ARMTARGET) $(CFLAGS) $(.ALLSRC) -MM > $@ || (rm -f $@ && false)
  139. .test_deps: $(LIBLORA_TEST_SRCS)
  140. $(CC) $(CFLAGS) $(.ALLSRC) -MM | sed -e 's/\.o:/\.no:/' > $@ || (rm -f $@ && false)
  141. .for i in $(PROGS)
  142. ALLTGTS+= $(i)$(PROGEXT) $(i).list
  143. ASRCS.$(i) = $(SRCS) $(SRCS.$(i))
  144. OBJS.$(i) = $(ASRCS.$(i):C/.c$/.o/)
  145. .arm_deps: $(ASRCS.$(i))
  146. $(i)$(PROGEXT) $(i).map: $(OBJS.$(i))
  147. $(ARMCC) $(ARMTARGET) -o $(i)$(PROGEXT) $(.ALLSRC) -T$(LINKER_SCRIPT) --specs=nosys.specs -Wl,-Map="$(i).map" -Wl,--gc-sections -static --specs=nano.specs -Wl,--start-group -lc -lm -Wl,--end-group
  148. $(i).list: $(i)$(PROGEXT)
  149. $(ARMOBJDUMP) -h -S $(.ALLSRC) > $@ || (rm -f $@ && false)
  150. .endfor
  151. all: $(ALLTGTS)
  152. .PHONY: runbuild
  153. runbuild: $(SRCS)
  154. for i in $(.MAKEFILE_LIST) $(.ALLSRC) $$(cat $(DEPENDS) | gsed ':x; /\\$$/ { N; s/\\\n//; tx }' | sed -e 's/^[^:]*://'); do if [ "$$i" != ".." ]; then echo $$i; fi; done | sort -u | entr -d sh -c 'echo starting...; cd $(.CURDIR) && $(MAKE) $(.MAKEFLAGS) depend && $(MAKE) $(.MAKEFLAGS) all'
  155. .PHONY: runtests
  156. runtests: Makefile lora_comms.py lora.py loraserv.py multicast.py $(LIBLORA_TEST) $(LIBLORA_TEST_SRCS)
  157. ls $(.ALLSRC) | entr sh -c '(cd $(.CURDIR) && $(MAKE) $(.MAKEFLAGS) $(LIBLORA_TEST)) && ((PYTHONPATH="$(.CURDIR)" python3 -m coverage run -m unittest lora multicast loraserv && coverage report --omit=$(.CURDIR)/p/\* -m -i) 2>&1 | head -n 30)'
  158. .if empty(IRR_KEY) && exists($(.CURDIR)/.irr_key)
  159. IRR_KEY!= cat $(.CURDIR)/.irr_key
  160. .endif
  161. .PHONY: irrigation_key
  162. irrigation_key:
  163. @LANG=C tr -c -d a-zA-Z0-9 < /dev/urandom | dd bs=1 of=$(.CURDIR)/.irr_key count=32 2>/dev/null
  164. @echo 'Irrgation key created and put into .irr_key.'
  165. # make this a phony target so it's always run
  166. # dependancies will only be made when it's updated
  167. .PHONY: $(.OBJDIR)/shared_key.h
  168. $(.OBJDIR)/shared_key.h:
  169. @if [ "$(IRR_KEY)" = "" ]; then echo 'Must provide IRR_KEY make variable or have a non-empty file ".irr_key".'; false; fi
  170. @echo 'static uint8_t shared_key[] = {' $$(python3 -c 'import sys; print(", ".join(str(x) for x in sys.argv[1].encode("utf-8")))' $(IRR_KEY) ) "};" > shared_key.h.tmp
  171. @echo 'static struct pktbuf shared_key_buf = (struct pktbuf){ .pkt = shared_key, .pktlen = sizeof shared_key, };' >> shared_key.h.tmp
  172. (cmp shared_key.h.tmp shared_key.h >/dev/null 2>&1 && rm shared_key.h.tmp) || mv shared_key.h.tmp shared_key.h
  173. # native objects
  174. .SUFFIXES: .no
  175. .c.no:
  176. $(CC) $(CFLAGS) -c $< -o $@
  177. .c.o:
  178. $(ARMCC) $(ARMTARGET) $(CFLAGS) -c $< -o $@
  179. STROBE_NAME = strobe
  180. STROBE_REPO = https://git.code.sf.net/p/strobe/code
  181. STROBE_BRANCH = master
  182. LORAMAC_NAME = loramac
  183. LORAMAC_REPO = https://github.com/Lora-net/LoRaMac-node.git
  184. LORAMAC_BRANCH = master
  185. .for module in STROBE LORAMAC
  186. .PHONY: init-$($(module)_NAME)
  187. init-$($(module)_NAME):
  188. git subtree add -P $($(module)_NAME) --squash $($(module)_REPO) $($(module)_BRANCH)
  189. .PHONY: update-$($(module)_NAME)
  190. update-$($(module)_NAME):
  191. git subtree pull -P $($(module)_NAME) --squash $($(module)_REPO) $($(module)_BRANCH)
  192. .endfor
  193. # Making diagrams, imported from fbsdembdev
  194. # =========================================
  195. # https://github.com/ironcamel/Graph-Easy
  196. .SUFFIXES: .getxt .diag .html
  197. .getxt.diag: box.sh
  198. graph-easy < $< | sh $(.CURDIR)/box.sh > $@
  199. .diag.html:
  200. (cat $<; echo; echo '<!-- Markdeep: --><style class="fallback">body{visibility:hidden;white-space:pre;font-family:monospace}</style><script src="markdeep.min.js" charset="utf-8"></script><script src="https://casual-effects.com/markdeep/latest/markdeep.min.js" charset="utf-8"></script><script>window.alreadyProcessedMarkdeep||(document.body.style.visibility="visible")</script>') > $@
  201. DIAG?=diag
  202. test-diag:
  203. ls $(.CURDIR)/box.sh $(.CURDIR)/$(DIAG).getxt $(.CURDIR)/Makefile | entr sh -c 'cd $(.CURDIR) && $(MAKE) $(.MAKEFLAGS) $(DIAG).diag && cat $(.OBJDIR)/$(DIAG).diag'
  204. # hard coded dependancy for when "make depend" has not been run.
  205. irr_main.o: $(.OBJDIR)/shared_key.h