Daiki Kato / mbed-os-lychee

Dependents:   mbed-os-example-blinky-gr-lychee GR-Boads_Camera_sample GR-Boards_Audio_Recoder GR-Boads_Camera_DisplayApp ... more

Committer:
dkato
Date:
Fri Feb 02 05:42:23 2018 +0000
Revision:
0:f782d9c66c49
mbed-os for GR-LYCHEE

Who changed what in which revision?

UserRevisionLine numberNew contents of line
dkato 0:f782d9c66c49 1 import os
dkato 0:f782d9c66c49 2 from os.path import sep, join, exists
dkato 0:f782d9c66c49 3 from itertools import groupby
dkato 0:f782d9c66c49 4 from xml.etree.ElementTree import Element, tostring
dkato 0:f782d9c66c49 5 import ntpath
dkato 0:f782d9c66c49 6 import re
dkato 0:f782d9c66c49 7 import json
dkato 0:f782d9c66c49 8
dkato 0:f782d9c66c49 9 from tools.arm_pack_manager import Cache
dkato 0:f782d9c66c49 10 from tools.targets import TARGET_MAP
dkato 0:f782d9c66c49 11 from tools.export.exporters import Exporter, TargetNotSupportedException
dkato 0:f782d9c66c49 12
dkato 0:f782d9c66c49 13 class fileCMSIS():
dkato 0:f782d9c66c49 14 """CMSIS file class.
dkato 0:f782d9c66c49 15
dkato 0:f782d9c66c49 16 Encapsulates information necessary for files in cpdsc project file"""
dkato 0:f782d9c66c49 17 file_types = {'.cpp': 'sourceCpp', '.c': 'sourceC', '.s': 'sourceAsm',
dkato 0:f782d9c66c49 18 '.obj': 'object', '.o': 'object', '.lib': 'library',
dkato 0:f782d9c66c49 19 '.ar': 'linkerScript', '.h': 'header', '.sct': 'linkerScript'}
dkato 0:f782d9c66c49 20
dkato 0:f782d9c66c49 21 def __init__(self, loc, name):
dkato 0:f782d9c66c49 22 #print loc
dkato 0:f782d9c66c49 23 _, ext = os.path.splitext(loc)
dkato 0:f782d9c66c49 24 self.type = self.file_types[ext.lower()]
dkato 0:f782d9c66c49 25 self.loc = loc
dkato 0:f782d9c66c49 26 self.name = name
dkato 0:f782d9c66c49 27
dkato 0:f782d9c66c49 28
dkato 0:f782d9c66c49 29 class DeviceCMSIS():
dkato 0:f782d9c66c49 30 """CMSIS Device class
dkato 0:f782d9c66c49 31
dkato 0:f782d9c66c49 32 Encapsulates target information retrieved by arm-pack-manager"""
dkato 0:f782d9c66c49 33
dkato 0:f782d9c66c49 34 CACHE = Cache(True, False)
dkato 0:f782d9c66c49 35 def __init__(self, target):
dkato 0:f782d9c66c49 36 target_info = self.check_supported(target)
dkato 0:f782d9c66c49 37 if not target_info:
dkato 0:f782d9c66c49 38 raise TargetNotSupportedException("Target not supported in CMSIS pack")
dkato 0:f782d9c66c49 39 self.url = target_info['pdsc_file']
dkato 0:f782d9c66c49 40 self.pack_url, self.pack_id = ntpath.split(self.url)
dkato 0:f782d9c66c49 41 self.dname = target_info["_cpu_name"]
dkato 0:f782d9c66c49 42 self.core = target_info["_core"]
dkato 0:f782d9c66c49 43 self.dfpu = target_info['processor']['fpu']
dkato 0:f782d9c66c49 44 self.debug, self.dvendor = self.vendor_debug(target_info['vendor'])
dkato 0:f782d9c66c49 45 self.dendian = target_info['processor'].get('endianness','Little-endian')
dkato 0:f782d9c66c49 46 self.debug_svd = target_info.get('debug', '')
dkato 0:f782d9c66c49 47 self.compile_header = target_info['compile']['header']
dkato 0:f782d9c66c49 48 self.target_info = target_info
dkato 0:f782d9c66c49 49
dkato 0:f782d9c66c49 50 @staticmethod
dkato 0:f782d9c66c49 51 def check_supported(target):
dkato 0:f782d9c66c49 52 t = TARGET_MAP[target]
dkato 0:f782d9c66c49 53 try:
dkato 0:f782d9c66c49 54 cpu_name = t.device_name
dkato 0:f782d9c66c49 55 target_info = DeviceCMSIS.CACHE.index[cpu_name]
dkato 0:f782d9c66c49 56 # Target does not have device name or pdsc file
dkato 0:f782d9c66c49 57 except:
dkato 0:f782d9c66c49 58 try:
dkato 0:f782d9c66c49 59 # Try to find the core as a generic CMSIS target
dkato 0:f782d9c66c49 60 cpu_name = DeviceCMSIS.cpu_cmsis(t.core)
dkato 0:f782d9c66c49 61 target_info = DeviceCMSIS.CACHE.index[cpu_name]
dkato 0:f782d9c66c49 62 except:
dkato 0:f782d9c66c49 63 return False
dkato 0:f782d9c66c49 64 target_info["_cpu_name"] = cpu_name
dkato 0:f782d9c66c49 65 target_info["_core"] = t.core
dkato 0:f782d9c66c49 66 return target_info
dkato 0:f782d9c66c49 67
dkato 0:f782d9c66c49 68 def vendor_debug(self, vendor):
dkato 0:f782d9c66c49 69 """Reads the vendor from a PDSC <dvendor> tag.
dkato 0:f782d9c66c49 70 This tag contains some additional numeric information that is meaningless
dkato 0:f782d9c66c49 71 for our purposes, so we use a regex to filter.
dkato 0:f782d9c66c49 72
dkato 0:f782d9c66c49 73 Positional arguments:
dkato 0:f782d9c66c49 74 Vendor - information in <dvendor> tag scraped from ArmPackManager
dkato 0:f782d9c66c49 75
dkato 0:f782d9c66c49 76 Returns a tuple of (debugger, vendor)
dkato 0:f782d9c66c49 77 """
dkato 0:f782d9c66c49 78 reg = "([\w\s]+):?\d*?"
dkato 0:f782d9c66c49 79 m = re.search(reg, vendor)
dkato 0:f782d9c66c49 80 vendor_match = m.group(1) if m else None
dkato 0:f782d9c66c49 81 debug_map ={
dkato 0:f782d9c66c49 82 'STMicroelectronics':'ST-Link',
dkato 0:f782d9c66c49 83 'Silicon Labs':'J-LINK',
dkato 0:f782d9c66c49 84 'Nuvoton':'NULink'
dkato 0:f782d9c66c49 85 }
dkato 0:f782d9c66c49 86 return debug_map.get(vendor_match, "CMSIS-DAP"), vendor_match
dkato 0:f782d9c66c49 87
dkato 0:f782d9c66c49 88 @staticmethod
dkato 0:f782d9c66c49 89 def cpu_cmsis(cpu):
dkato 0:f782d9c66c49 90 """
dkato 0:f782d9c66c49 91 Transforms information from targets.json to the way the generic cores are named
dkato 0:f782d9c66c49 92 in CMSIS PDSC files.
dkato 0:f782d9c66c49 93 Ex:
dkato 0:f782d9c66c49 94 Cortex-M4F => ARMCM4_FP, Cortex-M0+ => ARMCM0P
dkato 0:f782d9c66c49 95 Returns formatted CPU
dkato 0:f782d9c66c49 96 """
dkato 0:f782d9c66c49 97 cpu = cpu.replace("Cortex-","ARMC")
dkato 0:f782d9c66c49 98 cpu = cpu.replace("+","P")
dkato 0:f782d9c66c49 99 cpu = cpu.replace("F","_FP")
dkato 0:f782d9c66c49 100 return cpu
dkato 0:f782d9c66c49 101
dkato 0:f782d9c66c49 102
dkato 0:f782d9c66c49 103 class CMSIS(Exporter):
dkato 0:f782d9c66c49 104 NAME = 'cmsis'
dkato 0:f782d9c66c49 105 TOOLCHAIN = 'ARM'
dkato 0:f782d9c66c49 106 TARGETS = [target for target, obj in TARGET_MAP.iteritems()
dkato 0:f782d9c66c49 107 if "ARM" in obj.supported_toolchains]
dkato 0:f782d9c66c49 108
dkato 0:f782d9c66c49 109 def make_key(self, src):
dkato 0:f782d9c66c49 110 """turn a source file into its group name"""
dkato 0:f782d9c66c49 111 key = src.name.split(sep)[0]
dkato 0:f782d9c66c49 112 if key == ".":
dkato 0:f782d9c66c49 113 key = os.path.basename(os.path.realpath(self.export_dir))
dkato 0:f782d9c66c49 114 return key
dkato 0:f782d9c66c49 115
dkato 0:f782d9c66c49 116 def group_project_files(self, sources, root_element):
dkato 0:f782d9c66c49 117 """Recursively group the source files by their encompassing directory"""
dkato 0:f782d9c66c49 118
dkato 0:f782d9c66c49 119 data = sorted(sources, key=self.make_key)
dkato 0:f782d9c66c49 120 for group, files in groupby(data, self.make_key):
dkato 0:f782d9c66c49 121 new_srcs = []
dkato 0:f782d9c66c49 122 for f in list(files):
dkato 0:f782d9c66c49 123 spl = f.name.split(sep)
dkato 0:f782d9c66c49 124 if len(spl)==2:
dkato 0:f782d9c66c49 125 file_element = Element('file',
dkato 0:f782d9c66c49 126 attrib={
dkato 0:f782d9c66c49 127 'category':f.type,
dkato 0:f782d9c66c49 128 'name': f.loc})
dkato 0:f782d9c66c49 129 root_element.append(file_element)
dkato 0:f782d9c66c49 130 else:
dkato 0:f782d9c66c49 131 f.name = os.path.join(*spl[1:])
dkato 0:f782d9c66c49 132 new_srcs.append(f)
dkato 0:f782d9c66c49 133 if new_srcs:
dkato 0:f782d9c66c49 134 group_element = Element('group',attrib={'name':group})
dkato 0:f782d9c66c49 135 root_element.append(self.group_project_files(new_srcs,
dkato 0:f782d9c66c49 136 group_element))
dkato 0:f782d9c66c49 137 return root_element
dkato 0:f782d9c66c49 138
dkato 0:f782d9c66c49 139 def generate(self):
dkato 0:f782d9c66c49 140 srcs = self.resources.headers + self.resources.s_sources + \
dkato 0:f782d9c66c49 141 self.resources.c_sources + self.resources.cpp_sources + \
dkato 0:f782d9c66c49 142 self.resources.objects + self.resources.libraries + \
dkato 0:f782d9c66c49 143 [self.resources.linker_script]
dkato 0:f782d9c66c49 144 srcs = [fileCMSIS(src, src) for src in srcs if src]
dkato 0:f782d9c66c49 145 ctx = {
dkato 0:f782d9c66c49 146 'name': self.project_name,
dkato 0:f782d9c66c49 147 'project_files': tostring(self.group_project_files(srcs, Element('files'))),
dkato 0:f782d9c66c49 148 'device': DeviceCMSIS(self.target),
dkato 0:f782d9c66c49 149 'date': ''
dkato 0:f782d9c66c49 150 }
dkato 0:f782d9c66c49 151 # TODO: find how to keep prettyxml from adding xml version to this blob
dkato 0:f782d9c66c49 152 #dom = parseString(ctx['project_files'])
dkato 0:f782d9c66c49 153 #ctx['project_files'] = dom.toprettyxml(indent="\t")
dkato 0:f782d9c66c49 154
dkato 0:f782d9c66c49 155 self.gen_file('cmsis/cpdsc.tmpl', ctx, 'project.cpdsc')