adi_loadfdt_multiple=\
  fdt addr ${fit_load_address}; \
  fdt get value fdt_choosen /configurations/${fit_config}/ fdt; \
  fdt get addr fdtaddr /images/${fdt_choosen} data; \
  fdt addr ${fdtaddr}; \
  fdt get value model / model;

adi_loadfdt_simple=\
  fdt addr ${devicetree_load_address};

adi_loadfdt=\
  if test "${modeboot}" = "sdboot"; then \
    echo "Loading devicetree using simple method..."; \
    run adi_loadfdt_simple; \
  else \
    echo "Loading devicetree from FIT image..."; \
    run adi_loadfdt_multiple; \
  fi; \
  fdt resize;

adi_config_clocks=\
  if test -n "${ad936x_ext_refclk}" && test ! -n "${ad936x_skip_ext_refclk}"; then \
    echo "Setting ext refclk to ${ad936x_ext_refclk}"; \
    fdt set /clocks/clock@0 clock-frequency <${ad936x_ext_refclk}>; \
  else \
    echo "WARN: ad936x_ext_refclk not set or skipped"; \
  fi; \
  if test -n "${ad936x_ext_refclk_override}"; then \
    echo "Overriding refclk to ${ad936x_ext_refclk_override}"; \
    fdt set /clocks/clock@0 clock-frequency <${ad936x_ext_refclk_override}>; \
  fi;

adi_config_gpio_by_refclk=\
  if test "${refclk_source}" = "internal"; then \
    echo "Setting refclk internal"; \
    fdt rm /amba/gpio@e000a000/clock_extern_en; \
  elif test "${refclk_source}" = "external"; then \
    echo "Setting refclk external"; \
    fdt rm /amba/gpio@e000a000/clock_internal_en; \
  fi;

adi_config_rf_mode=\
  if test "${mode}" != "1r1t" && test "${mode}" != "2r2t"; then \
    setenv mode 1r1t; \
    saveenv; \
  fi;

adi_config_devicetree=\
  if test "${mode}" = "1r1t"; then \
    echo "Setting mode 1r1t"; \
    fdt rm /amba/spi@e0006000/ad9361-phy@0 adi,2rx-2tx-mode-enable; \
    fdt set /fpga-axi/cf-ad9361-dds-core-lpc@79024000 compatible adi,axi-ad9364-dds-6.00.a; \
  else \
    echo "Setting mode 2r2t"; \
  fi; \
  if test -n "${cs_gpio}"; then \
    fdt set /amba/axi_quad_spi@7C430000/ cs-gpios "<0x06 ${cs_gpio} 0>"; \
  fi; \
  if test -n "${attr_name}" && test -n "${attr_val}"; then \
    echo "Setting admodel ${attr_val}"; \
    fdt set /amba/spi@e0006000/ad9361-phy@0 ${attr_name} ${attr_val}; \
  fi;

adi_loadvals=\
  echo "Loading ADI vars..."; \
  run adi_loadfdt; \
  run adi_config_clocks; \
  run adi_config_gpio_by_refclk; \
  run adi_config_rf_mode; \
  run adi_config_devicetree; \
  setenv stdout serial@e0001000; setenv stdin serial@e0001000; setenv stderr serial@e0001000;

banner=\
  echo "___________                  __            "; \
  echo "\\__    ___/___ __________ __|  | _______   "; \
  echo "  |    |_/ __ \\\\___   /  |  \\  |/ /\\__  \\  "; \
  echo "  |    |\\  ___/ /    /|  |  /    <  / __ \\_"; \
  echo "  |____| \\___  >_____ \\____/|__|_ \\(____  /"; \
  echo "             \\/      \\/          \\/     \\/ "; \
  echo "Universal Zynq70x/AD936x firmware builder"; \
  echo "Version v0.3.20"; \
  echo "By F5OEO and contributors"; \
  meminfo; \
  echo "";

bootmenu_0=Boot normaly=boot
bootmenu_1=Reset Environment factory=run resetenv; bootmenu
bootmenu_2=Boot mode=run bootmode_submenu
bootmenu_3=Update SD card=run ums_sd; bootmenu
bootmenu_4=Set dfu mode=run dfu_sf
bootmenu_5=Allow boot udpate (Risky!)=sf probe && sf protect unlock 0 100000 ; bootmenu

bootmenu_restore_top=\
  setenv bootmenu_0 "Boot normaly (${modeboot})=boot"; \
  setenv bootmenu_1 "Reset Environment factory=run resetenv; bootmenu"; \
  setenv bootmenu_2 "Boot mode=run bootmode_submenu"; \
  setenv bootmenu_3 "Update SD card=run ums_sd; bootmenu"; \
  setenv bootmenu_4 "Set dfu mode=run dfu_sf"; \
  setenv bootmenu_5 "Unprotect boot for udpate (Risky!)=sf probe && sf protect unlock 0 100000 ; bootmenu";

bootmode_submenu=\
  setenv bootmenu_0 "Boot from SD=setenv modeboot sdboot; run sdboot_ram"; \
  setenv bootmenu_1 "Boot from QSPI=setenv modeboot qspiboot; run qspiboot"; \
  setenv bootmenu_2 "Boot from USB=run usbboot"; \
  setenv bootmenu_3 "Boot from SD card TezukaSumo=mmc dev 1; run sdboot_kuiper"; \
  setenv bootmenu_4 "Back=echo"; \
  setenv bootmenu_5; \
  bootmenu; \
  run bootmenu_restore_top; \
  bootmenu;

baudrate=115200
stdin=serial@e0001000,usbacm
stdout=serial@e0001000,usbacm
stderr=serial@e0001000,usbacm
bitstream_image=system_top.bin
bitstream_size=0x400000
bootcmd=if test -n "${modeboot}"; then run ${modeboot}; else adi_hwref; run ${modeboot}; fi
bootdelay=10
bootenv=uEnv.txt
boot_image=BOOT.bin
boot_size=0xF00000
clear_reset_cause=mw f8000008 df0d && mw f8000258 00400000 && mw f8000004 767b
devicetree_image=devicetree.dtb
devicetree_load_address=0x2000000
devicetree_size=0x20000
dfu_mmc_info=set dfu_alt_info ${kernel_image} fat 0 1\\;${devicetree_image} fat 0 1\\;${ramdisk_image} fat 0 1
dfu_mmc=run dfu_mmc_info && dfu 0 mmc 0
dfu_ram=echo Entering DFU RAM mode ... && run dfu_ram_info && dfu 0 ram 0
dfu_ram_info=set dfu_alt_info dummy.dfu ram 0 0\\;firmware.dfu ram ${fit_load_address} 0x1E00000
dfu_sf=run dfu_led;gpio set 0;setenv stdout serial@e0001000; setenv stdin serial@e0001000; setenv stderr serial@e0001000;echo Entering DFU SF mode ... && run dfu_sf_info && dfu 0 sf 0:0:40000000:0 && if test -n ${dfu_alt_num} && test ${dfu_alt_num} = 1; then set fit_size ${filesize} && set dfu_alt_num && env save; fi;setenv stdout serial@e0001000,usbacm; setenv stdin serial@e0001000,usbacm; setenv stderr serial@e0001000,usbacm;gpio clear 0;
dfu_sf_info=set dfu_alt_info boot.dfu raw 0x0 0x100000\\;firmware.dfu raw 0x200000 0x1E00000\\;uboot-extra-env.dfu raw 0xFF000 0x1000\\;uboot-env.dfu raw 0x100000 0x20000\\;spare.dfu raw 0x120000 0xE0000
extraenv_load_address=0x207E000
fdt_high=0x20000000
fit_config=config@0
fit_load_address=0x2080000
fit_size=0x1E00000
fpgaload=fatload usb 0 0xF000000 ${bitstream_image};fpga load 0 0xF000000 ${filesize}
importbootenv=env import -t ${loadbootenv_addr} $filesize
initrd_high=0x20000000
ipaddr=192.168.2.1
ipaddr_host=192.168.2.10
jtagboot=env default -a;sf probe && sf protect unlock 0 100000 ; run dfu_sf; run jtagboot;
kernel_image=uImage
loadbit_addr=0x100000
loadbootenv_addr=0x2000000
loadbootenv=echo Importing environment from SD ...; load mmc 0 ${loadbootenv_addr} ${bootenv}
loadbootenv_usb=echo Importing environment from USB ...;load usb 0 ${loadbootenv_addr} ${bootenv}
loaddfu=\
  if mmc rescan; then \
    fatload mmc 0 ${fit_load_address} pluto.dfu; \
    sf probe; \
    sf update ${fit_load_address} 0x200000 0x0E00000; \
    fatload mmc 0 0x20000 uboot-env.dfu; \
    sf update 0x20000 0x100000 0x20000; \
    bootm ${fit_load_address}#${fit_config}; \
  fi
maxcpus=2

netmask=255.255.255.0

preboot_main=\
  run banner; \
  adi_hwref; \
  if test "${modeboot}" = "sdboot"; then \
    if env run sd_uEnvtxt_existence_test; then \
      if env run loadbootenv; then \
          env run importbootenv; \
      fi; \
    fi; \
  elif test "${modeboot}" = "qspiboot" ; then \
    if env run qspiboot_bootenv; then \
        env import -t ${loadbootenv_addr} 0x20000; \
        run dfu_button; \
    fi; \
  elif test "${modeboot}" = "usbboot" ; then \
    if env run loadbootenv_usb; then \
        env run importbootenv; \
    fi; \
  elif test "${modeboot}" = "jtagboot" ; then \
    run jtagboot; \
  fi; \
  setenv bootmenu_0 "Boot normaly (${modeboot})=boot";

soft_reboot_cause=itest *f8000258 == 480003 && run clear_reset_cause && run dfu_sf; \
		itest *f8000258 == 480007 && run clear_reset_cause && run ramboot_verbose;  \
		itest *f8000258 == 480006 && run clear_reset_cause && run qspiboot;  \
		itest *f8000258 == 480002 && run clear_reset_cause && exit;


my_led=15
dfu_led=gpio set ${my_led}; sleep 1; gpio clear ${my_led}; sleep 0.5; gpio set ${my_led}; sleep 0.5; gpio clear ${my_led}; sleep 0.5; gpio set ${my_led};gpio clear ${my_led};
# SKIP DFU BUTTON AS NOT SUPPROTED BY ALL BOARDS
# dfu_button=gpio input 14 && run dfu_sf;
dfu_button=echo "Skipping DFU button";
preboot=run soft_reboot_cause; adi_hwref; run preboot_main ; adi_hwref;

pl_init=\
  echo "Initializing PL infrastructure..."; \
  mw 0xF8000008 0xDF0D; \
  mw 0xF8000900 0x0000000F; \
  mw 0xF8000240 0x00000000; \
  mw 0xF8000004 0x767B; \
  echo "PL level shifters and clocks enabled";

qspiboot_bootenv=sf probe && sf read ${extraenv_load_address} 0x100000 0x20000;
qspiboot_extraenv=sf read ${extraenv_load_address} 0xFF000 0x1000;
qspiboot=\
  adi_hwref; \
  echo Copying Linux from QSPI flash to RAM... && run read_sf && if run adi_loadvals; then \
    echo Loaded AD936x refclk frequency and model into devicetree; \
  fi; \
  run pl_init; \
  setenv bootargs console=ttyPS0,115200 maxcpus=${maxcpus} rootfstype=ramfs root=/dev/ram0 rw earlyprintk clk_ignore_unused cpuidle.off=1 uio_pdrv_genirq.of_id=uio_pdrv_genirq UBOOT_MODEBOOT=$modeboot UBOOT_VERSION='\"'${uboot-version}'\"' \
  && bootm ${fit_load_address}#${fit_config} || echo BOOT failed entering DFU mode && run dfu_sf

ramboot_verbose=\
  adi_hwref; \
  echo Copying Linux from DFU to RAM... && run dfu_ram;if run adi_loadvals; then \
    echo Loaded AD936x refclk frequency and model into devicetree; \
  fi; \
  run pl_init; \
  setenv bootargs console=ttyPS0,115200 maxcpus=${maxcpus} rootfstype=ramfs root=/dev/ram0 rw earlyprintk clk_ignore_unused cpuidle.off=1 uio_pdrv_genirq.of_id=uio_pdrv_genirq UBOOT_MODEBOOT=$modeboot UBOOT_VERSION='\"'${uboot-version}'\"' \
  && bootm ${fit_load_address}#${fit_config}

ramdisk_image=uramdisk.image.xz
ramdisk_load_address=0x4000000
ramdisk_size=0x400000
read_sf=sf probe 0:0 50000000 0 && run qspiboot_extraenv && sf read ${fit_load_address} 0x200000 ${fit_size} && iminfo ${fit_load_address} || sf read ${fit_load_address} 0x200000 0x1E00000;
refclk_source=internal
resetenv=env default -f -a; env save
sdboot=\
  if test -n "${mode_rootfs}" && test "${mode_rootfs}" = "kuiper"; then \
    run sdboot_kuiper; \
  else \
    run sdboot_ram; \
  fi

sdboot_ram=\
  if mmcinfo; then \
    run uenvboot; \
    echo Copying Linux from SD to RAM... \
    && load mmc 0 ${fit_load_address} ${kernel_image} \
    && load mmc 0 ${devicetree_load_address} ${devicetree_image} \
    && load mmc 0 ${ramdisk_load_address} ${ramdisk_image} \
    && run adi_loadvals; \
    setenv bootargs console=ttyPS0,115200 rootfstype=ramfs root=/dev/ram0 rw rootwait earlycon clk_ignore_unused cpuidle.off=1 uio_pdrv_genirq.of_id=uio_pdrv_genirq UBOOT_MODEBOOT=$modeboot UBOOT_VERSION='"\'${uboot-version}'\"' \
    && bootm ${fit_load_address} ${ramdisk_load_address} ${devicetree_load_address}; \
  fi

bootargs=console=ttyPS0,115200 root=/dev/mmcblk0p2 rw earlycon rootfstype=ext4 rootwait clk_ignore_unused cpuidle.off=1 uio_pdrv_genirq.of_id=uio_pdrv_genirq UBOOT_MODEBOOT=$modeboot UBOOT_VERSION='\"'${uboot-version}'\"'

sdboot_kuiper=if mmcinfo && fstype mmc 0:2 kuiper_fstype && test "${kuiper_fstype}" = "ext4"; then \
    run uenvboot; \
    echo Copying Linux from SD to RAM...\
    && load mmc 0 ${fit_load_address} ${kernel_image} \
    && load mmc 0 ${devicetree_load_address} ${devicetree_image} \
    && run adi_loadvals; \
    setenv bootargs console=ttyPS0,115200 rootfstype=ext4 root=/dev/mmcblk0p2 rootwait rw earlycon clk_ignore_unused cpuidle.off=1 uio_pdrv_genirq.of_id=uio_pdrv_genirq UBOOT_MODEBOOT=$modeboot UBOOT_VERSION='\"'${uboot-version}'\"' \
    && bootm ${fit_load_address} - ${devicetree_load_address}; \
  else \
    echo "sdboot_kuiper: no ext4 partition on mmc 0:2, aborting"; \
  fi

sd_uEnvtxt_existence_test=test -e mmc 0 /uEnv.txt
thor_mmc=run dfu_mmc_info && thordown 0 mmc 0
thor_ram=run dfu_ram_info && thordown 0 ram 0
uenvboot=\
  if run loadbootenv; then \
    echo Loaded environment from ${bootenv}; \
    run importbootenv; \
  fi; \
  if test -n $uenvcmd; \
    then echo Running uenvcmd ...; \
    run uenvcmd; \
  fi

ums_sd=\
  setenv stdout serial@e0001000; setenv stdin serial@e0001000; setenv stderr serial@e0001000; \
  ums 0 mmc 0; \
  setenv stdout serial@e0001000,usbacm; setenv stdin serial@e0001000,usbacm; setenv stderr serial@e0001000,usbacm;

usbboot=\
  setenv stdout serial@e0001000; setenv stdin serial@e0001000; setenv stderr serial@e0001000; \
  if usb start && usb storage; then \
    sleep 1; \
    if env run loadbootenv_usb; then env run importbootenv; fi; \
    if test -e usb 0 /${kernel_image} && test -e usb 0 /${devicetree_image} && test -e usb 0 /${ramdisk_image}; then \
      echo Copying Linux from USB to RAM... \
      && load usb 0 ${fit_load_address} ${kernel_image} \
      && sleep 0.2 \
      && load usb 0 ${devicetree_load_address} ${devicetree_image} \
      && sleep 0.2 \
      && load usb 0 ${ramdisk_load_address} ${ramdisk_image} \
      && sleep 0.2 \
      && run fpgaload \
      && run adi_loadvals; \
      run pl_init; \
      setenv bootargs console=ttyPS0,115200 rootfstype=ramfs root=/dev/ram0 rw rootwait earlycon clk_ignore_unused cpuidle.off=1 uio_pdrv_genirq.of_id=uio_pdrv_genirq UBOOT_MODEBOOT=$modeboot UBOOT_VERSION='"\'${uboot-version}'\"' \
      && bootm ${fit_load_address} ${ramdisk_load_address} ${devicetree_load_address}; \
    else \
      echo "usbboot: ${kernel_image}/${devicetree_image}/${ramdisk_image} not found on USB device, skipping USB boot"; \
    fi; \
    usb stop; \
   else \
      usb stop; \
  fi; \
  setenv stdout serial@e0001000,usbacm; setenv stdin serial@e0001000,usbacm; setenv stderr serial@e0001000,usbacm;


usbacm_console=setenv stdout usbacm; setenv stdin usbacm; setenv stderr usbacm
