Skip to content

Instantly share code, notes, and snippets.

@donn
Last active October 28, 2019 22:43
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save donn/30b1c63d863e836ed01c26bcf713040a to your computer and use it in GitHub Desktop.
Save donn/30b1c63d863e836ed01c26bcf713040a to your computer and use it in GitHub Desktop.
TM4C123GH6PM Environment Mac Setup
#!/usr/bin/env ruby
# TM4C123GH6PM Environment Mac Setup
#
# This is what I do when I procrastinate.
#
# I recommend you have homebrew pre-installed for this, but the script
# will try to install it anyway.
#
# (To get STM32 working on Mac instead, try
# https://github.com/glegrain/STM32-with-macOS)
#
# Ruby
# --
# ©Mohamed Gaber 2019
#
# Permission is hereby granted, free of charge, to any person obtaining a
# copy of this software and associated documentation files (the "Software"),
# to deal in the Software without restriction, including without limitation
# the rights to use, copy, modify, merge, publish, distribute, sublicense,
# and/or sell copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
# DEALINGS IN THE SOFTWARE.
require 'tmpdir'
require 'fileutils'
macOS = Gem::Version.new(`sw_vers -productVersion`.chomp)
ftdi_needed = false
if macOS < Gem::Version.new('10.15') and macOS > Gem::Version.new('10.8')
ftdi_needed = true
end
puts "TM4C123 macOS Environment Setup"
puts "You can exit at any time by using Ctrl+C."
puts ""
puts "By installing, you agree to ALL OF:"
puts ""
counter = 0
puts "#{counter}. The FT Driver License Terms\n\t(https://www.ftdichip.com/Drivers/FTDriverLicenceTerms.htm)" if ftdi_needed; counter += 1 if ftdi_needed
puts "#{counter}. The ARM MDK EULA\n\t(https://www.keil.com/Content/eula/mdkeula.html)"; counter += 1
puts ""
puts "This setup script includes no implied or explicit warranty of any kind."
puts "The author is not liable for any damages incurred to your computer or device."
puts ""
puts "Checking for SW-TM4C-*.exe in local folder…"
files = Dir["SW-TM4C-*.exe"]
if files.count == 0
puts "Cannot find the Tivaware for Windows installer. You will need to download this yourself.\n\t(http://software-dl.ti.com/tiva-c/SW-TM4C/latest/index_FDS.html)"
exit 66
else
puts "Found."
end
puts ""
tivaware_installer = files[0]
keil_tm4c_pack = 'https://keilpack.azureedge.net/pack/Keil.TM4C_DFP.1.1.0.pack'
print "Where would you like to install your files? [Default: ~/Embedded]> "
install_dir = gets("\n").chomp
install_dir = "#{ENV["HOME"]}/Embedded" if install_dir.empty?
FileUtils.mkdir_p install_dir
puts "Starting."
puts ""
if ftdi_needed
puts "[SETUP] macOS version is > 10.8 and < 10.15, FTDI driver needed…"
Dir.mktmpdir("D2xx") { |dir|
`curl -sL https://www.ftdichip.com/Drivers/D2XX/MacOSX/D2xxHelper_v2.0.0.pkg > '#{dir}/package.pkg'`
`tar -C '#{dir}' -xf '#{dir}/package.pkg'`
`tar -C '#{dir}' -xf '#{dir}/dst.pkg/Payload'`
puts "[SETUP] The program may ask you for sudo permission to install the driver."
`sudo cp -r '#{dir}/Library/Extensions/D2xxHelper.kext' /System/Library/Extensions/`
`sudo kextload /System/Library/Extensions/D2xxHelper.kext`
}
end
brew_result = `which brew`
if $?.exitstatus != 0
puts "[SETUP] Homebrew not found, installing… (brew setup script may ask you for superuser permission)"
system("/usr/bin/ruby -e \"$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)\"")
end
puts "[SETUP] Installing dependencies. This may take a while."
system("brew install donn/lm4tools/lm4tools open-ocd")
puts ""
puts "[SETUP] Placing middleware…"
# CMSIS
puts "[SETUP] Checking out CMSIS Core…"
cmsis_core_dir = "#{install_dir}/CMSISCore"
FileUtils.mkdir_p cmsis_core_dir
`svn checkout --force https://github.com/ARM-software/CMSIS_5/trunk/CMSIS/Core/Include '#{cmsis_core_dir}'`
# Tivaware
puts "[SETUP] Unzipping Tivaware…"
tivaware_dir = "#{install_dir}/Tivaware"
FileUtils.mkdir_p tivaware_dir
`unzip '#{tivaware_installer}' -d '#{tivaware_dir}'`
# Pack
puts "[SETUP] Getting TM4C Device Family Pack…"
dfp_dir = "#{install_dir}/DFP"
FileUtils.mkdir_p dfp_dir
`curl -L '#{keil_tm4c_pack}' > '#{dfp_dir}/tm4c.pack'`
`tar -C '#{dfp_dir}' -xf '#{dfp_dir}/tm4c.pack'`
new_proj_script = <<NEWPROJSCRIPT
#!/usr/bin/env ruby
require 'fileutils'
if ARGV.count != 1
puts "Usage: \#{$0} <name of new project>"
exit 64
end
name = ARGV[0]
FileUtils.mkdir_p name
# TI
ti_dir = "\#{name}/TI"
FileUtils.mkdir_p ti_dir
`cp '#{tivaware_dir}/examples/boards/dk-tm4c123g/blinky/blinky.ld' '\#{ti_dir}/link.ld'`
`cp '#{tivaware_dir}/examples/boards/dk-tm4c123g/blinky/startup_gcc.c' '\#{ti_dir}/startup.c'`
# Main
src_dir = "\#{name}/Sources"
FileUtils.mkdir_p src_dir
File.open("\#{src_dir}/main.c", "w") { |file|
file << <<-MAIN_C
#include "TM4C123GH6PM.h"
int main(void) {
// Enable clocks
SYSCTL->RCGCGPIO |= 0b00100000; // GPIO F
// GPIO F
GPIOF->DEN = 0b00001110; // Set LEDs to output
GPIOF->DIR = 0b00001110; // Set LEDs to output
GPIOF->DATA = 0b00001110; // Set LEDs to white
while(1) {}
}
MAIN_C
}
# Header Directory
hdr_dir = "\#{name}/Includes"
FileUtils.mkdir_p hdr_dir
# Makefile
File.open("\#{name}/Makefile", "w") { |file|
file << <<-MAKEFILE
# Adapted from Tiva Makefile from uCtools project
# (uctools.github.com)
MCU = TM4C123GH6PM
SOURCES = TI/startup.c $(shell find Sources | grep '\\\\.c')
OBJECTS = $(addprefix $(BUILD_DIR)/, $(patsubst %.c,%.o,$(SOURCES)))
LD_SCRIPT = TI/link.ld
BUILD_DIR = build
OUT_FILE = flashable.bin
TIVAWARE_PATH = #{tivaware_dir}
CMSIS_PATH = #{cmsis_core_dir}
TM4C123_PATH = #{dfp_dir}/Device/Include/TM4C123
CFLAGS = -g -mthumb -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=softfp
CFLAGS += -Os -ffunction-sections -fdata-sections -MD -std=c11 -Wall
CFLAGS += -Wno-unused-variable -DPART_$(MCU) -c
CFLAGS += -I$(TIVAWARE_PATH) -I$(CMSIS_PATH) -I$(TM4C123_PATH) -IIncludes
CFLAGS += -DTARGET_IS_BLIZZARD_RA1
LDFLAGS = -T $(LD_SCRIPT) --entry ResetISR --gc-sections
#######################################
CC = arm-none-eabi-gcc
LD = arm-none-eabi-ld
OBJCOPY = arm-none-eabi-objcopy
#######################################
# default: build bin
all: $(OUT_FILE)
$(OBJECTS): $(BUILD_DIR)/%.o: %.c
mkdir -p $(@D)
$(CC) $(CFLAGS) -o $@ $^
$(BUILD_DIR)/a.out: $(OBJECTS)
$(LD) -o $@ $^ $(LDFLAGS)
$(OUT_FILE): $(BUILD_DIR)/a.out
$(OBJCOPY) -O binary $< $@
.PHONY: clean
clean:
rm -rf $(BUILD_DIR)
MAKEFILE
}
# Readme
File.open("\#{name}/Readme.md", "w") { |file|
file << <<-README
# \#{name}
This is an automatically generated README file.
# Usage
Invoke `make` to build.
Invoke `lm4flash flashable.bin` to flash the compiled file to memory.
Invoke `screen /dev/cu.usbmodem<something>` for serial terminals. (You'll need to try a couple.)
To use the Open On-chip debugger:
```
arm-none-eabi-gdb -ex 'target extended-remote | openocd -f board/ek-tm4c1294xl.cfg -c "gdb_port pipe; log_output openocd.log"; monitor reset; monitor halt'
```
# Programming differences from Keil
The most notable differences are:
* You need to add the interrupts manually to the IVT in TI/startup.c
* You must perform your clock configuration manually.
This is because we're not using Keil startup files, we're using TI's.
# Acknowledgements
* The Makefile is based on [uctools/tiva-template](https://github.com/uctools/tiva-template).
* Guide used: http://chrisrm.com/howto-develop-on-the-ti-tiva-launchpad-using-linux/
README
}
NEWPROJSCRIPT
new_proj_path = "#{install_dir}/new_tivac_project"
File.open(new_proj_path, "w") { |file|
file << new_proj_script
}
File.chmod(0o755, new_proj_path)
puts "[SETUP] Done."
puts ""
puts "To create a new project, write this in the terminal:"
puts "\t#{new_proj_path} <name of your project>"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment