You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

774 lines
15 KiB
Rust

use config::{Config, Environment, Value};
use std::collections::HashMap;
use std::io::prelude::*;
use std::fs::File;
use std::fs::OpenOptions;
use std::path::Path;
fn main()
{
let mut mcu_lookup_table = Config::new();
let mut make_manifest: Config = Config::new();
mcu_lookup_table.merge(config::File::with_name("\
/storage/Shared/Documents/Projects/ePenguin/\
ePenguin-Software-Framework/arch/mcu-lookup.toml")).unwrap();
make_manifest.merge(config::File::with_name("\
/storage/Shared/Documents/Projects/ePenguin/\
ePenguin-Software-Framework/arch/make-manifest.toml")).unwrap();
let mut _table_name = mcu_lookup_table.get_str("make.mcu.samd21j18a").unwrap();
let mut table_head = &_table_name[0.._table_name.len()];
let mut makefile: HashMap<String, config::Value> = HashMap::new();
let mut b_quit: bool = false;
loop
{
let mut _active_table = make_manifest.get_table(&table_head).unwrap();
for (name, val) in _active_table
{
match val.clone().into_table()
{
Err(_e) =>
{
if !makefile.contains_key(&name)
{
makefile.insert(name, val);
}
else
{
let mut newval = val.clone().into_array().unwrap();
let mut newvec = makefile.get_key_value(&name).unwrap().1.clone().into_array().unwrap();
newvec.append(&mut newval);
makefile.insert(name, config::Value::from(newvec));
}
}
Ok(_v) => {}
}
}
match table_head.rfind('.')
{
None => b_quit = true,
Some(v) => table_head = &table_head[0..v],
}
if b_quit
{
break;
}
}
// for (key_id, val) in &makefile
// {
// println!("\n{}: {:?}", key_id, val);
// }
gen_makefile(&makefile);
}
fn gen_makefile(mkfile: &HashMap<String, config::Value>) -> bool
{
// If the Makefile already exists, trash it
if Path::new("Makefile").exists()
{
std::fs::remove_file("Makefile");
}
// Make our Makefile, set it to append mode
File::create("Makefile").unwrap();
let mut app_file = OpenOptions::new()
.write(true)
.append(true)
.open("Makefile")
.unwrap();
//
writeln!(app_file, "# ePenguin Generated Variables").unwrap();
// Get our knowns out of the way
match mkfile.get("PROJECT_NAME")
{
None =>
{
println!("PROJECT_NAME not found");
}
Some(v) =>
{
write!(app_file, "PROJECT_NAME=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("TOOLCHAIN")
{
None =>
{
println!("TOOLCHAIN Not found");
}
Some(v) =>
{
write!(app_file, "TOOLCHAIN=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("CC")
{
None =>
{
println!("CC Not found");
}
Some(v) =>
{
write!(app_file, "CC=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("CXX")
{
None =>
{
println!("CXX Not found");
}
Some(v) =>
{
write!(app_file, "CXX=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("OBJCOPY")
{
None =>
{
println!("OBJCOPY Not found");
}
Some(v) =>
{
write!(app_file, "OBJCOPY=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("OBJDUMP")
{
None =>
{
println!("OBJDUMP Not found");
}
Some(v) =>
{
write!(app_file, "OBJDUMP=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("GDB")
{
None =>
{
println!("GDB Not found");
}
Some(v) =>
{
write!(app_file, "GDB=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("SIZE")
{
None =>
{
println!("SIZE Not found");
}
Some(v) =>
{
write!(app_file, "SIZE=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("AS")
{
None =>
{
println!("AS Not found");
}
Some(v) =>
{
write!(app_file, "AS=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
writeln!(app_file, "\n").unwrap();
// MCU Specifics now
match mkfile.get("MCPU")
{
None =>
{
println!("MCPU Not found");
}
Some(v) =>
{
write!(app_file, "MCPU=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("MCU")
{
None =>
{
println!("MCU Not found");
}
Some(v) =>
{
write!(app_file, "MCU=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("LD_PATH")
{
None =>
{
println!("LD_PATH Not found");
}
Some(v) =>
{
write!(app_file, "LD_PATH=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
match mkfile.get("LD_SCRIPT")
{
None =>
{
println!("LD_SCRIPT Not found");
}
Some(v) =>
{
write!(app_file, "LD_SCRIPT=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
writeln!(app_file, "\n").unwrap();
// CFLAGS
match mkfile.get("CFLAGS")
{
None =>
{
println!("CFLAGS Not found");
}
Some(v) =>
{
write!(app_file, "CFLAGS=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
// ELF FLAGS
match mkfile.get("ELF_FLAGS")
{
None =>
{
println!("ELF_FLAGS Not found");
}
Some(v) =>
{
write!(app_file, "ELF_FLAGS=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
// HEX FLAGS
match mkfile.get("HEX_FLAGS")
{
None =>
{
println!("HEX_FLAGS Not found");
}
Some(v) =>
{
write!(app_file, "HEX_FLAGS=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
match mkfile.get("EEP_FLAGS")
{
None =>
{
println!("EEP_FLAGS Not found");
}
Some(v) =>
{
write!(app_file, "EEP_FLAGS=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
// Write SystemRoot config stuff for cross compatibility
let sysroot: String = String::from("
ifdef SystemRoot
SHELL = cmd.exe
MK_DIR = mkdir
else
ifeq ($(shell uname), Linux)
MK_DIR = mkdir -p
endif
ifeq ($(shell uname | cut -d _ -f 1), CYGWIN)
MK_DIR = mkdir -p
endif
ifeq ($(shell uname | cut -d _ -f 1), MINGW32)
MK_DIR = mkdir -p
endif
ifeq ($(shell uname | cut -d _ -f 1), MINGW64)
MK_DIR = mkdir -p
endif
ifeq ($(shell uname | cut -d _ -f 1), DARWIN)
MK_DIR = mkdir -p
endif
endif");
writeln!(app_file, "{}", sysroot).unwrap();
match mkfile.get("SUB_DIRS")
{
None =>
{
println!("SUB_DIRS Not found");
}
Some(v) =>
{
write!(app_file, "SUB_DIRS+=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
match mkfile.get("OBJS")
{
None =>
{
println!("OBJS Not found");
}
Some(v) =>
{
write!(app_file, "OBJS+=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
match mkfile.get("OBJS_AS_ARGS")
{
None =>
{
println!("OBJS_AS_ARGS Not found");
}
Some(v) =>
{
write!(app_file, "OBJS_AS_ARGS+=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
writeln!(app_file, "\n").unwrap();
match mkfile.get("DIR_INCLUDES")
{
None =>
{
println!("DIR_INCLUDES Not found");
}
Some(v) =>
{
write!(app_file, "DIR_INCLUDES+=").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
write!(app_file, "\n\n").unwrap();
match mkfile.get("DEPS")
{
None =>
{
println!("DEPS Not found");
}
Some(v) =>
{
write!(app_file, "DEPS:=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
write!(app_file, "\n").unwrap();
match mkfile.get("DEPS_AS_ARGS")
{
None =>
{
println!("DEPS_AS_ARGS Not found");
}
Some(v) =>
{
write!(app_file, "DEPS_AS_ARGS:=").unwrap();
writeln!(app_file, "{}", v.to_string()).unwrap();
},
}
writeln!(app_file, "\nvpath %.c ../").unwrap();
writeln!(app_file, "vpath %.s ../").unwrap();
writeln!(app_file, "vpath %.S ../\n").unwrap();
writeln!(app_file, ".PHONY: debug clean\n").unwrap();
match mkfile.get("ALL_PREREQS")
{
None =>
{
println!("ALL_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "all:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
match mkfile.get("ALL_CMDS")
{
None =>
{
println!("ALL_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "\t{}", cflag).unwrap();
}
},
}
write!(app_file, "\n\n").unwrap();
match mkfile.get("ELF_TARGET_PREREQS")
{
None =>
{
println!("ELF_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "$(PROJECT_NAME).elf:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
match mkfile.get("ELF_TARGET_CMDS")
{
None =>
{
println!("ELF_TARGET_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "\t{}", cflag).unwrap();
}
},
}
write!(app_file, "\n\n").unwrap();
match mkfile.get("BIN_TARGET_PREREQS")
{
None =>
{
println!("BIN_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "$(PROJECT_NAME).bin:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
match mkfile.get("BIN_TARGET_CMDS")
{
None =>
{
println!("BIN_TARGET_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "\t{}", cflag).unwrap();
}
},
}
write!(app_file, "\n\n").unwrap();
match mkfile.get("HEX_TARGET_PREREQS")
{
None =>
{
println!("HEX_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "$(PROJECT_NAME).hex:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
match mkfile.get("HEX_TARGET_CMDS")
{
None =>
{
println!("HEX_TARGET_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "\t{}", cflag).unwrap();
}
},
}
write!(app_file, "\n\n").unwrap();
match mkfile.get("EEP_TARGET_PREREQS")
{
None =>
{
println!("EEP_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "$(PROJECT_NAME).eep:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
match mkfile.get("EEP_TARGET_CMDS")
{
None =>
{
println!("EEP_TARGET_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "\t{}", cflag).unwrap();
}
},
}
write!(app_file, "\n\n").unwrap();
match mkfile.get("LSS_TARGET_PREREQS")
{
None =>
{
println!("LSS_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "$(PROJECT_NAME).lss:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap();
}
},
}
match mkfile.get("LSS_TARGET_CMDS")
{
None =>
{
println!("LSS_TARGET_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "\t{}", cflag).unwrap();
}
},
}
// Compiler Targets
writeln!(app_file, "").unwrap();
writeln!(app_file, "
# Compiler targets
%.o: %.c
@echo Building file: $<
@echo ARM/GNU C Compiler
$(QUOTE)$(CC)$(QUOTE) $(CFLAGS) -o $(QUOTE)$@$(QUOTE) $(QUOTE)$<$(QUOTE)
@echo Finished building: $<").unwrap();
writeln!(app_file, "
%.o: %.s
@echo Building file: $<
@echo ARM/GNU Assembler
$(QUOTE)$(AS)$(QUOTE) $(CFLAGS) -o $(QUOTE)$@$(QUOTE) $(QUOTE)$<$(QUOTE)
@echo Finished building: $<").unwrap();
writeln!(app_file, "
%.o: %.S
@echo Building file: $<
@echo ARM/GNU Preprocessing Assembler
$(QUOTE)$(CC)$(QUOTE) $(CFLAGS) -o $(QUOTE)$@$(QUOTE) $(QUOTE)$<$(QUOTE)
@echo Finished building: $<").unwrap();
writeln!(app_file, "\n").unwrap();
writeln!(app_file, "$(SUB_DIRS):\n\t$(MK_DIR) $(QUOTE)$@$(QUOTE)").unwrap();
writeln!(app_file, "
ifneq ($(MAKECMDGOALS),clean)
ifneq ($(strip $(DEPS)),)
-include $(DEPS)
endif
endif\n").unwrap();
match mkfile.get("CLEAN_PREREQS")
{
None =>
{
println!("CLEAN_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "clean:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
if !cflag.to_string().is_empty()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap()
}
}
},
}
match mkfile.get("CLEAN_CMDS")
{
None =>
{
println!("CLEAN_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
if !cflag.to_string().is_empty()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "\t{}", cflag).unwrap()
}
}
},
}
writeln!(app_file, "\n").unwrap();
match mkfile.get("DEBUG_PREREQS")
{
None =>
{
println!("DEBUG_TARGET_PREREQS Not found");
}
Some(v) =>
{
write!(app_file, "debug:").unwrap();
for cflag in v.clone().into_array().unwrap()
{
if !cflag.to_string().is_empty()
{
writeln!(app_file, "\\").unwrap();
write!(app_file, "{}", cflag).unwrap()
}
}
},
}
match mkfile.get("DEBUG_CMDS")
{
None =>
{
println!("DEBUG_CMDS Not found");
}
Some(v) =>
{
write!(app_file, "\n\t").unwrap();
for cflag in v.clone().into_array().unwrap()
{
if !cflag.to_string().is_empty()
{
writeln!(app_file, " \\").unwrap();
write!(app_file, "\t{}", cflag).unwrap()
}
}
},
}
writeln!(app_file, "\n\nQUOTE:=\"").unwrap();
true
}