Link everything in main.cpp
This commit is contained in:
parent
25343e0856
commit
d5a28b1580
1
.gitignore
vendored
1
.gitignore
vendored
@ -1,2 +1,3 @@
|
||||
build
|
||||
test.o
|
||||
test
|
||||
56
src/main.cpp
56
src/main.cpp
@ -22,8 +22,8 @@
|
||||
|
||||
void llvm_hello_world();
|
||||
|
||||
std::string read_file(std::string& filepath) {
|
||||
std::ifstream input{ filepath };
|
||||
std::string read_file(std::string_view filepath) {
|
||||
std::ifstream input{ std::string{filepath} };
|
||||
if (!input) {
|
||||
std::cerr << "Failed to read " << filepath << std::endl;
|
||||
return {};
|
||||
@ -41,8 +41,8 @@ std::string read_file(std::string& filepath) {
|
||||
return out;
|
||||
}
|
||||
|
||||
int write_file(std::string& filepath, std::string& content) {
|
||||
std::ofstream output{ filepath };
|
||||
int write_file(std::string_view filepath, std::string& content) {
|
||||
std::ofstream output{ std::string{filepath} };
|
||||
if (!output) {
|
||||
std::cerr << "Failed to open " << filepath << " for reading" << std::endl;
|
||||
return 1;
|
||||
@ -57,12 +57,12 @@ struct CompileOutput {
|
||||
std::string obj_string;
|
||||
};
|
||||
|
||||
std::optional<CompileOutput> compile(std::string& in_filename) {
|
||||
std::optional<CompileOutput> compile(std::string_view in_filename) {
|
||||
std::string out{ read_file(in_filename) };
|
||||
|
||||
std::cout << out << std::endl;
|
||||
|
||||
auto tokens = token::tokenize(out, in_filename);
|
||||
auto tokens = token::tokenize(out, std::string{ in_filename });
|
||||
for (token::Token token : tokens) {
|
||||
std::cout << token << std::endl;
|
||||
}
|
||||
@ -154,15 +154,59 @@ std::optional<CompileOutput> compile(std::string& in_filename) {
|
||||
};
|
||||
}
|
||||
|
||||
std::string exec(const char* cmd) {
|
||||
std::array<char, 128> buffer;
|
||||
std::string result;
|
||||
std::unique_ptr<FILE, decltype(&pclose)> pipe(popen(cmd, "r"), pclose);
|
||||
if (!pipe) {
|
||||
throw std::runtime_error("popen() failed!");
|
||||
}
|
||||
while (fgets(buffer.data(), static_cast<int>(buffer.size()), pipe.get()) != nullptr) {
|
||||
result += buffer.data();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/// @brief Discovers the path of a given library using POSIX-util "whereis"
|
||||
/// @param libname
|
||||
/// @return path to the library, empty string if nothing was found
|
||||
std::string find_lib(std::string libname) {
|
||||
std::string cmd = "whereis " + libname;
|
||||
auto output = exec(cmd.c_str());
|
||||
output.erase(0, libname.size() + 2);
|
||||
auto path = output.substr(0, output.find('\n'));
|
||||
path = path.substr(0, path.find(' '));
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
int main() {
|
||||
|
||||
std::string in_filename{ "test.c" };
|
||||
std::string out_filename{ "test.o" };
|
||||
std::string exec_filename{ "test" };
|
||||
|
||||
auto out = compile(in_filename);
|
||||
if (out) {
|
||||
// Print LLVM IR, produce Obj-file
|
||||
std::cout << out->llvm_ir_string << std::endl;
|
||||
write_file(out_filename, out->obj_string);
|
||||
|
||||
// Find necessary libraries
|
||||
|
||||
std::string command = "ld";
|
||||
auto linker = find_lib("ld-linux-x86-64.so.2");
|
||||
auto crt1 = find_lib("crt1.o");
|
||||
auto crti = find_lib("crti.o");
|
||||
auto crtn = find_lib("crtn.o");
|
||||
|
||||
|
||||
// Link everything together and produce a file with exec_filename
|
||||
std::string cmd = command + " -dynamic-linker " + linker + " -lc "
|
||||
+ crt1 + " " + crti + " " + crtn + " "
|
||||
+ out_filename + " -o " + exec_filename;
|
||||
std::cout << cmd << std::endl;
|
||||
std::cout << exec(cmd.c_str()) << std::endl;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
Loading…
Reference in New Issue
Block a user