Skip to content

Commit

Permalink
add static link
Browse files Browse the repository at this point in the history
  • Loading branch information
yangminz committed Apr 18, 2021
1 parent eb92bd5 commit febae2c
Show file tree
Hide file tree
Showing 5 changed files with 184 additions and 30 deletions.
94 changes: 65 additions & 29 deletions cmd.py
Original file line number Diff line number Diff line change
Expand Up @@ -135,41 +135,77 @@ def build(key):
make_build_directory()
gcc_map = {
KEY_MACHINE : [
"/usr/bin/gcc-7",
"-Wall", "-g", "-O0", "-Werror", "-std=gnu99", "-Wno-unused-function",
"-I", "./src",
"./src/tests/test_machine.c",
"./src/common/print.c",
"./src/common/convert.c",
"./src/common/cleanup.c",
"./src/datastruct/trie.c",
"./src/datastruct/array.c",
"./src/hardware/cpu/isa.c",
"./src/hardware/cpu/mmu.c",
"./src/hardware/memory/dram.c",
"-o", EXE_BIN_MACHINE],
[
"/usr/bin/gcc-7",
"-Wall", "-g", "-O0", "-Werror", "-std=gnu99", "-Wno-unused-function",
"-I", "./src",
"./src/tests/test_machine.c",
"./src/common/print.c",
"./src/common/convert.c",
"./src/common/cleanup.c",
"./src/datastruct/trie.c",
"./src/datastruct/array.c",
"./src/hardware/cpu/isa.c",
"./src/hardware/cpu/mmu.c",
"./src/hardware/memory/dram.c",
"-o", EXE_BIN_MACHINE
]
],
KEY_LINKER : [
"/usr/bin/gcc-7",
"-Wall", "-g", "-O0", "-Werror", "-std=gnu99", "-Wno-unused-function",
"-I", "./src",
"./src/tests/test_elf.c",
"./src/common/print.c",
"./src/common/convert.c",
"./src/common/tagmalloc.c",
"./src/common/cleanup.c",
"./src/datastruct/array.c",
"./src/datastruct/hashtable.c",
"./src/datastruct/linkedlist.c",
"./src/linker/parseElf.c",
"./src/linker/staticlink.c",
"-o", EXE_BIN_LINKER
]
[
"/usr/bin/gcc-7",
"-Wall", "-g", "-O0", "-Werror", "-std=gnu99", "-Wno-unused-function",
"-I", "./src",
"./src/tests/test_elf.c",
"./src/common/print.c",
"./src/common/convert.c",
"./src/common/tagmalloc.c",
"./src/common/cleanup.c",
"./src/datastruct/array.c",
"./src/datastruct/hashtable.c",
"./src/datastruct/linkedlist.c",
"./src/linker/parseElf.c",
"./src/linker/staticlink.c",
"-o", EXE_BIN_LINKER
],
[
"/usr/bin/gcc-7",
"-Wall", "-g", "-O0", "-Werror", "-std=gnu99", "-Wno-unused-function",
"-I", "./src",
"-shared", "-fPIC",
"./src/common/print.c",
"./src/common/convert.c",
"./src/common/tagmalloc.c",
"./src/common/cleanup.c",
"./src/datastruct/array.c",
"./src/datastruct/hashtable.c",
"./src/datastruct/linkedlist.c",
"./src/linker/parseElf.c",
"./src/linker/staticlink.c",
"-o", "./bin/staticlink.so"
],
[
"/usr/bin/gcc-7",
"-Wall", "-g", "-O0", "-Werror", "-std=gnu99", "-Wno-unused-function",
"-I", "./src",
"./src/common/print.c",
"./src/common/convert.c",
"./src/common/tagmalloc.c",
"./src/common/cleanup.c",
"./src/datastruct/array.c",
"./src/datastruct/hashtable.c",
"./src/datastruct/linkedlist.c",
"./src/linker/linker.c",
"-ldl", "-o", "./bin/link"
],
]
}

if not key in gcc_map:
print("input the correct build key:", gcc_map.keys())
exit()
subprocess.run(gcc_map[key])
for command in gcc_map[key]:
subprocess.run(command)

def run(key):
assert(os.path.isdir("./bin/"))
Expand Down
106 changes: 106 additions & 0 deletions src/linker/linker.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
/* BCST - Introduction to Computer Systems
* Author: [email protected]
* Github: https://github.com/yangminz/bcst_csapp
* Bilibili: https://space.bilibili.com/4564101
* Zhihu: https://www.zhihu.com/people/zhao-yang-min
* This project (code repository and videos) is exclusively owned by yangminz
* and shall not be used for commercial and profitting purpose
* without yangminz's permission.
*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <dlfcn.h>
#include <headers/linker.h>
#include <headers/common.h>

const char *EXECUTABLE_DIRECTORY = "./files/exe";

// linker front end
int main(int argc, char **argv)
{
char *elf_fn[64];
char *eof_fn;
int elf_num = 0;

// parse the arguments
int eof_flag = 0;
for (int i = 1; i < argc; ++ i)
{
char *str = argv[i];
if (strcmp(str, "-h") == 0 || strcmp(str, "--help") == 0)
{
printf("./bin/link <ELF file> ... <ELF file> -o <EOF file>\n");
exit(0);
}
else if (strcmp(argv[i], "-o") == 0)
{
eof_flag = 1;
continue;
}

if (eof_flag == 0)
{
// elf files
elf_fn[elf_num] = str;
elf_num ++;
}
else
{
// eof file
eof_fn = str;
}
}

// parsed the arguments

// dynamically loading the shared library
void *linklib = dlopen("./bin/staticLinker.so", RTLD_LAZY);
if (linklib == NULL)
{
printf("%s\n", dlerror());
exit(1);
}

// functions from shared library
void (*link_elf)(elf_t **, int, elf_t *);
void (*write_eof)(const char *, elf_t *);
void (*parse_elf)(const char *, elf_t *);
link_elf = dlsym(linklib, "link_elf");
write_eof = dlsym(linklib, "write_eof");
parse_elf = dlsym(linklib, "parse_elf");

// do front end logic

printf("we are DYNAMICALLY LINKING ./bin/linker.so to do STATIC linking:\nlinking ");
elf_t **srcs = malloc(elf_num * sizeof(elf_t *));
for (int i = 0; i < elf_num; ++ i)
{
char elf_fullpath[100];
sprintf(elf_fullpath, "%s/%s.elf.txt", EXECUTABLE_DIRECTORY, elf_fn[i]);
printf("%s ", elf_fullpath);

srcs[i] = malloc(sizeof(elf_t));
parse_elf(elf_fullpath, srcs[i]);
}

elf_t linked;
link_elf(srcs, elf_num, &linked);

char eof_fullpath[100];
sprintf(eof_fullpath, "%s/%s.eof.txt", EXECUTABLE_DIRECTORY, eof_fn);
printf("into %s\n", eof_fullpath);

write_eof(eof_fullpath, &linked);

// releaes elf heap
for (int i = 0; i < elf_num; ++ i)
{
free(srcs[i]);
}
free(srcs);

return 0;
}
6 changes: 5 additions & 1 deletion src/linker/parseElf.c
Original file line number Diff line number Diff line change
Expand Up @@ -410,5 +410,9 @@ void free_elf(elf_t *elf)
{
assert(elf != NULL);

tag_sweep("parse_elf");
tag_free(elf->sht);
tag_free(elf->symt);
tag_free(elf->reltext);
tag_free(elf->reldata);
tag_free(elf);
}
6 changes: 6 additions & 0 deletions src/linker/staticlink.c
Original file line number Diff line number Diff line change
Expand Up @@ -753,6 +753,12 @@ static void relocation_processing(elf_t **srcs, int num_srcs, elf_t *dst,

// relocating handlers

static uint64_t get_symbol_runtime_address(elf_t *dst, st_entry_t *sym)
{
// TODO: get the run-time address of symbol
return 0;
}

static void R_X86_64_32_handler(elf_t *dst, sh_entry_t *sh,
int row_referencing, int col_referencing, int addend,
st_entry_t *sym_referenced)
Expand Down
2 changes: 2 additions & 0 deletions src/tests/test_elf.c
Original file line number Diff line number Diff line change
Expand Up @@ -32,5 +32,7 @@ int main()
free_elf(&src[1]);
free_elf(&dst);

finally_cleanup();

return 0;
}

0 comments on commit febae2c

Please sign in to comment.