authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2016-09-01 11:05:36-07:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2016-09-01 11:05:36-07:00
logf18e34c2c6b7884a76d98d86b41857044dbe0f06
tree010a1f7d5a7689fb5ab31a56ad52aaa50e255a42
parent320e26590a31351301992dc7067eb287e4f565f4

restore shared library functionality


4 files changed, 128 insertions(+), 34 deletions(-)

example/shared_library/mathtest.zig-3
...@@ -1,6 +1,3 @@...@@ -1,6 +1,3 @@
1#version("2.0.0")
2export library "mathtest";
3
4export fn add(a: i32, b: i32) -> i32 {1export fn add(a: i32, b: i32) -> i32 {
5 a + b2 a + b
6}3}
src/all_types.hpp+2-1
...@@ -1288,7 +1288,8 @@ struct CodeGen {...@@ -1288,7 +1288,8 @@ struct CodeGen {
1288 LLVMValueRef cur_ret_ptr;1288 LLVMValueRef cur_ret_ptr;
1289 ZigList<LLVMBasicBlockRef> break_block_stack;1289 ZigList<LLVMBasicBlockRef> break_block_stack;
1290 ZigList<LLVMBasicBlockRef> continue_block_stack;1290 ZigList<LLVMBasicBlockRef> continue_block_stack;
1291 bool c_stdint_used;1291 bool c_want_stdint;
1292 bool c_want_stdbool;
1292 AstNode *root_export_decl;1293 AstNode *root_export_decl;
1293 int version_major;1294 int version_major;
1294 int version_minor;1295 int version_minor;
src/codegen.cpp+116-24
...@@ -4992,31 +4992,121 @@ void codegen_add_root_code(CodeGen *g, Buf *src_dir, Buf *src_basename, Buf *sou...@@ -4992,31 +4992,121 @@ void codegen_add_root_code(CodeGen *g, Buf *src_dir, Buf *src_basename, Buf *sou
4992 do_code_gen(g);4992 do_code_gen(g);
4993}4993}
49944994
4995static void to_c_type(CodeGen *g, AstNode *type_node, Buf *out_buf) {4995static const char *c_int_type_names[] = {
4996 zig_panic("TODO this function needs some love");4996 [CIntTypeShort] = "short",
4997 TypeTableEntry *type_entry = get_resolved_expr(type_node)->type_entry;4997 [CIntTypeUShort] = "unsigned short",
4998 [CIntTypeInt] = "int",
4999 [CIntTypeUInt] = "unsigned int",
5000 [CIntTypeLong] = "long",
5001 [CIntTypeULong] = "unsigned long",
5002 [CIntTypeLongLong] = "long long",
5003 [CIntTypeULongLong] = "unsigned long long",
5004};
5005
5006static void get_c_type(CodeGen *g, TypeTableEntry *type_entry, Buf *out_buf) {
4998 assert(type_entry);5007 assert(type_entry);
49995008
5000 if (type_entry == g->builtin_types.entry_u8) {5009 for (int i = 0; i < array_length(c_int_type_names); i += 1) {
5001 g->c_stdint_used = true;5010 if (type_entry == g->builtin_types.entry_c_int[i]) {
5002 buf_init_from_str(out_buf, "uint8_t");5011 buf_init_from_str(out_buf, c_int_type_names[i]);
5003 } else if (type_entry == g->builtin_types.entry_i32) {5012 return;
5004 g->c_stdint_used = true;5013 }
5005 buf_init_from_str(out_buf, "int32_t");5014 }
5006 } else if (type_entry == g->builtin_types.entry_isize) {5015 if (type_entry == g->builtin_types.entry_c_long_double) {
5007 g->c_stdint_used = true;5016 buf_init_from_str(out_buf, "long double");
5008 buf_init_from_str(out_buf, "intptr_t");5017 return;
5009 } else if (type_entry == g->builtin_types.entry_f32) {5018 }
5010 buf_init_from_str(out_buf, "float");5019 if (type_entry == g->builtin_types.entry_c_void) {
5011 } else if (type_entry == g->builtin_types.entry_unreachable) {
5012 buf_init_from_str(out_buf, "__attribute__((__noreturn__)) void");
5013 } else if (type_entry == g->builtin_types.entry_bool) {
5014 buf_init_from_str(out_buf, "unsigned char");
5015 } else if (type_entry == g->builtin_types.entry_void) {
5016 buf_init_from_str(out_buf, "void");5020 buf_init_from_str(out_buf, "void");
5017 } else {5021 return;
5018 zig_panic("TODO to_c_type");5022 }
5023 if (type_entry == g->builtin_types.entry_isize) {
5024 g->c_want_stdint = true;
5025 buf_init_from_str(out_buf, "intptr_t");
5026 return;
5019 }5027 }
5028 if (type_entry == g->builtin_types.entry_usize) {
5029 g->c_want_stdint = true;
5030 buf_init_from_str(out_buf, "uintptr_t");
5031 return;
5032 }
5033
5034 switch (type_entry->id) {
5035 case TypeTableEntryIdVoid:
5036 buf_init_from_str(out_buf, "void");
5037 break;
5038 case TypeTableEntryIdBool:
5039 buf_init_from_str(out_buf, "bool");
5040 g->c_want_stdbool = true;
5041 break;
5042 case TypeTableEntryIdUnreachable:
5043 buf_init_from_str(out_buf, "__attribute__((__noreturn__)) void");
5044 break;
5045 case TypeTableEntryIdFloat:
5046 switch (type_entry->data.floating.bit_count) {
5047 case 32:
5048 buf_init_from_str(out_buf, "float");
5049 break;
5050 case 64:
5051 buf_init_from_str(out_buf, "double");
5052 break;
5053 default:
5054 zig_unreachable();
5055 }
5056 break;
5057 case TypeTableEntryIdInt:
5058 g->c_want_stdint = true;
5059 buf_resize(out_buf, 0);
5060 buf_appendf(out_buf, "%sint%d_t",
5061 type_entry->data.integral.is_signed ? "" : "u",
5062 type_entry->data.integral.bit_count);
5063 break;
5064 case TypeTableEntryIdPointer:
5065 {
5066 Buf child_buf = BUF_INIT;
5067 TypeTableEntry *child_type = type_entry->data.pointer.child_type;
5068 get_c_type(g, child_type, &child_buf);
5069
5070 const char *const_str = type_entry->data.pointer.is_const ? "const " : "";
5071 buf_resize(out_buf, 0);
5072 buf_appendf(out_buf, "%s*%s", const_str, buf_ptr(&child_buf));
5073 break;
5074 }
5075 case TypeTableEntryIdArray:
5076 case TypeTableEntryIdStruct:
5077 case TypeTableEntryIdMaybe:
5078 case TypeTableEntryIdErrorUnion:
5079 case TypeTableEntryIdPureError:
5080 case TypeTableEntryIdEnum:
5081 case TypeTableEntryIdUnion:
5082 case TypeTableEntryIdFn:
5083 case TypeTableEntryIdTypeDecl:
5084 zig_panic("TODO");
5085 case TypeTableEntryIdInvalid:
5086 case TypeTableEntryIdMetaType:
5087 case TypeTableEntryIdGenericFn:
5088 case TypeTableEntryIdNamespace:
5089 case TypeTableEntryIdNumLitFloat:
5090 case TypeTableEntryIdNumLitInt:
5091 case TypeTableEntryIdUndefLit:
5092 case TypeTableEntryIdNullLit:
5093 zig_unreachable();
5094 }
5095}
5096
5097static void get_c_type_node(CodeGen *g, AstNode *type_node, Buf *out_buf) {
5098 assert(type_node->type != NodeTypeSymbol || !type_node->data.symbol_expr.override_type_entry);
5099
5100 Expr *expr = get_resolved_expr(type_node);
5101 assert(expr->type_entry);
5102 assert(expr->type_entry->id == TypeTableEntryIdMetaType);
5103
5104 ConstExprValue *const_val = &expr->const_val;
5105 assert(const_val->ok);
5106
5107 TypeTableEntry *type_entry = const_val->data.x_type;
5108
5109 return get_c_type(g, type_entry, out_buf);
5020}5110}
50215111
5022void codegen_generate_h_file(CodeGen *g) {5112void codegen_generate_h_file(CodeGen *g) {
...@@ -5045,7 +5135,7 @@ void codegen_generate_h_file(CodeGen *g) {...@@ -5045,7 +5135,7 @@ void codegen_generate_h_file(CodeGen *g) {
5045 continue;5135 continue;
50465136
5047 Buf return_type_c = BUF_INIT;5137 Buf return_type_c = BUF_INIT;
5048 to_c_type(g, fn_proto->return_type, &return_type_c);5138 get_c_type_node(g, fn_proto->return_type, &return_type_c);
50495139
5050 buf_appendf(&h_buf, "%s %s %s(",5140 buf_appendf(&h_buf, "%s %s %s(",
5051 buf_ptr(export_macro),5141 buf_ptr(export_macro),
...@@ -5057,7 +5147,7 @@ void codegen_generate_h_file(CodeGen *g) {...@@ -5057,7 +5147,7 @@ void codegen_generate_h_file(CodeGen *g) {
5057 for (int param_i = 0; param_i < fn_proto->params.length; param_i += 1) {5147 for (int param_i = 0; param_i < fn_proto->params.length; param_i += 1) {
5058 AstNode *param_decl_node = fn_proto->params.at(param_i);5148 AstNode *param_decl_node = fn_proto->params.at(param_i);
5059 AstNode *param_type = param_decl_node->data.param_decl.type;5149 AstNode *param_type = param_decl_node->data.param_decl.type;
5060 to_c_type(g, param_type, &param_type_c);5150 get_c_type_node(g, param_type, &param_type_c);
5061 buf_appendf(&h_buf, "%s %s",5151 buf_appendf(&h_buf, "%s %s",
5062 buf_ptr(&param_type_c),5152 buf_ptr(&param_type_c),
5063 buf_ptr(param_decl_node->data.param_decl.name));5153 buf_ptr(param_decl_node->data.param_decl.name));
...@@ -5080,7 +5170,9 @@ void codegen_generate_h_file(CodeGen *g) {...@@ -5080,7 +5170,9 @@ void codegen_generate_h_file(CodeGen *g) {
5080 fprintf(out_h, "#ifndef %s\n", buf_ptr(ifdef_dance_name));5170 fprintf(out_h, "#ifndef %s\n", buf_ptr(ifdef_dance_name));
5081 fprintf(out_h, "#define %s\n\n", buf_ptr(ifdef_dance_name));5171 fprintf(out_h, "#define %s\n\n", buf_ptr(ifdef_dance_name));
50825172
5083 if (g->c_stdint_used)5173 if (g->c_want_stdbool)
5174 fprintf(out_h, "#include <stdbool.h>\n");
5175 if (g->c_want_stdint)
5084 fprintf(out_h, "#include <stdint.h>\n");5176 fprintf(out_h, "#include <stdint.h>\n");
50855177
5086 fprintf(out_h, "\n");5178 fprintf(out_h, "\n");
src/link.cpp+10-6
...@@ -159,6 +159,7 @@ static void construct_linker_job_linux(LinkJob *lj) {...@@ -159,6 +159,7 @@ static void construct_linker_job_linux(LinkJob *lj) {
159159
160 bool is_lib = g->out_type == OutTypeLib;160 bool is_lib = g->out_type == OutTypeLib;
161 bool shared = !g->is_static && is_lib;161 bool shared = !g->is_static && is_lib;
162 Buf *soname = nullptr;
162 if (g->is_static) {163 if (g->is_static) {
163 if (g->zig_target.arch.arch == ZigLLVM_arm || g->zig_target.arch.arch == ZigLLVM_armeb ||164 if (g->zig_target.arch.arch == ZigLLVM_arm || g->zig_target.arch.arch == ZigLLVM_armeb ||
164 g->zig_target.arch.arch == ZigLLVM_thumb || g->zig_target.arch.arch == ZigLLVM_thumbeb)165 g->zig_target.arch.arch == ZigLLVM_thumb || g->zig_target.arch.arch == ZigLLVM_thumbeb)
...@@ -169,6 +170,11 @@ static void construct_linker_job_linux(LinkJob *lj) {...@@ -169,6 +170,11 @@ static void construct_linker_job_linux(LinkJob *lj) {
169 }170 }
170 } else if (shared) {171 } else if (shared) {
171 lj->args.append("-shared");172 lj->args.append("-shared");
173
174 buf_resize(&lj->out_file, 0);
175 buf_appendf(&lj->out_file, "lib%s.so.%d.%d.%d",
176 buf_ptr(g->root_out_name), g->version_major, g->version_minor, g->version_patch);
177 soname = buf_sprintf("lib%s.so.%d", buf_ptr(g->root_out_name), g->version_major);
172 }178 }
173179
174 lj->args.append("-o");180 lj->args.append("-o");
...@@ -211,11 +217,7 @@ static void construct_linker_job_linux(LinkJob *lj) {...@@ -211,11 +217,7 @@ static void construct_linker_job_linux(LinkJob *lj) {
211 lj->args.append(buf_ptr(get_dynamic_linker(g->target_machine)));217 lj->args.append(buf_ptr(get_dynamic_linker(g->target_machine)));
212 }218 }
213219
214 if (g->out_type == OutTypeLib) {220 if (shared) {
215 buf_resize(&lj->out_file, 0);
216 buf_appendf(&lj->out_file, "lib%s.so.%d.%d.%d",
217 buf_ptr(g->root_out_name), g->version_major, g->version_minor, g->version_patch);
218 Buf *soname = buf_sprintf("lib%s.so.%d", buf_ptr(g->root_out_name), g->version_major);
219 lj->args.append("-soname");221 lj->args.append("-soname");
220 lj->args.append(buf_ptr(soname));222 lj->args.append(buf_ptr(soname));
221 }223 }
...@@ -849,7 +851,9 @@ void codegen_link(CodeGen *g, const char *out_file) {...@@ -849,7 +851,9 @@ void codegen_link(CodeGen *g, const char *out_file) {
849 fprintf(stderr, "%s\n", buf_ptr(&ld_stderr));851 fprintf(stderr, "%s\n", buf_ptr(&ld_stderr));
850 }852 }
851853
852 if (g->out_type == OutTypeLib) {854 if (g->out_type == OutTypeLib ||
855 g->out_type == OutTypeObj)
856 {
853 codegen_generate_h_file(g);857 codegen_generate_h_file(g);
854 }858 }
855859