@@ -5632,6 +5632,7 @@ fn create_main_wrapper(ccx: @crate_ctxt, sp: span, main_llfn: ValueRef,
5632
5632
5633
5633
let llfn = create_main ( ccx, sp, main_llfn, main_takes_argv) ;
5634
5634
ccx. main_fn = some ( llfn) ;
5635
+ create_entry_fn ( ccx, llfn) ;
5635
5636
5636
5637
fn create_main ( ccx : @crate_ctxt , sp : span , main_llfn : ValueRef ,
5637
5638
takes_argv : bool ) -> ValueRef {
@@ -5664,6 +5665,35 @@ fn create_main_wrapper(ccx: @crate_ctxt, sp: span, main_llfn: ValueRef,
5664
5665
5665
5666
ret llfdecl;
5666
5667
}
5668
+
5669
+ fn create_entry_fn ( ccx : @crate_ctxt , rust_main : ValueRef ) {
5670
+ #[ cfg( target_os = "win32" ) ]
5671
+ fn main_name ( ) -> str { ret "WinMain@16" ; }
5672
+ #[ cfg( target_os = "macos" ) ]
5673
+ fn main_name ( ) -> str { ret "main" ; }
5674
+ #[ cfg( target_os = "linux" ) ]
5675
+ fn main_name ( ) -> str { ret "main" ; }
5676
+ let llfty = T_fn ( [ T_int ( ) , T_int ( ) ] , T_int ( ) ) ;
5677
+ let llfn = decl_cdecl_fn ( ccx. llmod , main_name ( ) , llfty) ;
5678
+ let llbb = str:: as_buf ( "top" , { |buf|
5679
+ llvm:: LLVMAppendBasicBlock ( llfn, buf)
5680
+ } ) ;
5681
+ let bld = * ccx. builder ;
5682
+ llvm:: LLVMPositionBuilderAtEnd ( bld, llbb) ;
5683
+ let crate_map = ccx. crate_map ;
5684
+ let start_ty = T_fn ( [ val_ty ( rust_main) , T_int ( ) , T_int ( ) ,
5685
+ val_ty ( crate_map) ] , T_int ( ) ) ;
5686
+ let start = str:: as_buf ( "rust_start" , { |buf|
5687
+ llvm:: LLVMAddGlobal ( ccx. llmod , start_ty, buf)
5688
+ } ) ;
5689
+ let args = [ rust_main, llvm:: LLVMGetParam ( llfn, 0 u) ,
5690
+ llvm:: LLVMGetParam ( llfn, 1 u) , crate_map] ;
5691
+ let result = unsafe {
5692
+ llvm:: LLVMBuildCall ( bld, start, vec:: to_ptr ( args) ,
5693
+ vec:: len ( args) , noname ( ) )
5694
+ } ;
5695
+ llvm:: LLVMBuildRet ( bld, result) ;
5696
+ }
5667
5697
}
5668
5698
5669
5699
// Create a /real/ closure: this is like create_fn_pair, but creates a
@@ -6146,38 +6176,39 @@ fn create_module_map(ccx: @crate_ctxt) -> ValueRef {
6146
6176
}
6147
6177
6148
6178
6179
+ fn decl_crate_map ( sess : session:: session , mapname : str ,
6180
+ llmod : ModuleRef ) -> ValueRef {
6181
+ let n_subcrates = 1 ;
6182
+ let cstore = sess. get_cstore ( ) ;
6183
+ while cstore:: have_crate_data ( cstore, n_subcrates) { n_subcrates += 1 ; }
6184
+ if !sess. get_opts ( ) . library { mapname = "toplevel" ; }
6185
+ let sym_name = "_rust_crate_map_" + mapname;
6186
+ let arrtype = T_array ( T_int ( ) , n_subcrates as uint ) ;
6187
+ let maptype = T_struct ( [ T_int ( ) , arrtype] ) ;
6188
+ let map = str:: as_buf ( sym_name, { |buf|
6189
+ llvm:: LLVMAddGlobal ( llmod, maptype, buf)
6190
+ } ) ;
6191
+ llvm:: LLVMSetLinkage ( map, lib:: llvm:: LLVMExternalLinkage
6192
+ as llvm:: Linkage ) ;
6193
+ ret map;
6194
+ }
6195
+
6149
6196
// FIXME use hashed metadata instead of crate names once we have that
6150
- fn create_crate_map ( ccx : @crate_ctxt ) -> ValueRef {
6197
+ fn fill_crate_map ( ccx : @crate_ctxt , map : ValueRef ) {
6151
6198
let subcrates: [ ValueRef ] = [ ] ;
6152
6199
let i = 1 ;
6153
6200
let cstore = ccx. sess . get_cstore ( ) ;
6154
6201
while cstore:: have_crate_data ( cstore, i) {
6155
6202
let nm = "_rust_crate_map_" + cstore:: get_crate_data ( cstore, i) . name ;
6156
- let cr =
6157
- str:: as_buf ( nm,
6158
- { |buf|
6159
- llvm:: LLVMAddGlobal ( ccx. llmod , T_int ( ) , buf)
6160
- } ) ;
6203
+ let cr = str:: as_buf ( nm, { |buf|
6204
+ llvm:: LLVMAddGlobal ( ccx. llmod , T_int ( ) , buf)
6205
+ } ) ;
6161
6206
subcrates += [ p2i ( cr) ] ;
6162
6207
i += 1 ;
6163
6208
}
6164
6209
subcrates += [ C_int ( 0 ) ] ;
6165
- let mapname;
6166
- if ccx. sess . get_opts ( ) . library {
6167
- mapname = ccx. link_meta . name ;
6168
- } else { mapname = "toplevel" ; }
6169
- let sym_name = "_rust_crate_map_" + mapname;
6170
- let arrtype = T_array ( T_int ( ) , std:: vec:: len :: < ValueRef > ( subcrates) ) ;
6171
- let maptype = T_struct ( [ T_int ( ) , arrtype] ) ;
6172
- let map =
6173
- str:: as_buf ( sym_name,
6174
- { |buf| llvm:: LLVMAddGlobal ( ccx. llmod , maptype, buf) } ) ;
6175
- llvm:: LLVMSetLinkage ( map,
6176
- lib:: llvm:: LLVMExternalLinkage as llvm:: Linkage ) ;
6177
- llvm:: LLVMSetInitializer ( map,
6178
- C_struct ( [ p2i ( create_module_map ( ccx) ) ,
6179
- C_array ( T_int ( ) , subcrates) ] ) ) ;
6180
- ret map;
6210
+ llvm:: LLVMSetInitializer ( map, C_struct ( [ p2i ( create_module_map ( ccx) ) ,
6211
+ C_array ( T_int ( ) , subcrates) ] ) ) ;
6181
6212
}
6182
6213
6183
6214
fn write_metadata ( cx : @crate_ctxt , crate : @ast:: crate ) {
@@ -6242,6 +6273,8 @@ fn trans_crate(sess: session::session, crate: @ast::crate, tcx: ty::ctxt,
6242
6273
let sha1s = map:: mk_hashmap :: < ty:: t , str > ( hasher, eqer) ;
6243
6274
let short_names = map:: mk_hashmap :: < ty:: t , str > ( hasher, eqer) ;
6244
6275
let sha = std:: sha1:: mk_sha1 ( ) ;
6276
+ let link_meta = link:: build_link_meta ( sess, * crate , output, sha) ;
6277
+ let crate_map = decl_crate_map ( sess, link_meta. name , llmod) ;
6245
6278
let ccx =
6246
6279
@{ sess: sess,
6247
6280
llmod: llmod,
@@ -6253,7 +6286,7 @@ fn trans_crate(sess: session::session, crate: @ast::crate, tcx: ty::ctxt,
6253
6286
ast_map: amap,
6254
6287
item_symbols: new_int_hash :: < str > ( ) ,
6255
6288
mutable main_fn: none :: < ValueRef > ,
6256
- link_meta: link :: build_link_meta ( sess , * crate , output , sha ) ,
6289
+ link_meta: link_meta ,
6257
6290
tag_sizes: tag_sizes,
6258
6291
discrims: new_int_hash :: < ValueRef > ( ) ,
6259
6292
discrim_symbols: new_int_hash :: < str > ( ) ,
@@ -6283,13 +6316,14 @@ fn trans_crate(sess: session::session, crate: @ast::crate, tcx: ty::ctxt,
6283
6316
task_type: task_type,
6284
6317
builder: BuilderRef_res ( llvm:: LLVMCreateBuilder ( ) ) ,
6285
6318
shape_cx: shape:: mk_ctxt ( llmod) ,
6286
- gc_cx: gc:: mk_ctxt ( ) } ;
6319
+ gc_cx: gc:: mk_ctxt ( ) ,
6320
+ crate_map: crate_map} ;
6287
6321
let cx = new_local_ctxt ( ccx) ;
6288
6322
collect_items ( ccx, crate ) ;
6289
6323
collect_tag_ctors ( ccx, crate ) ;
6290
6324
trans_constants ( ccx, crate ) ;
6291
6325
trans_mod ( cx, crate . node. module ) ;
6292
- create_crate_map ( ccx) ;
6326
+ fill_crate_map ( ccx, crate_map ) ;
6293
6327
emit_tydescs ( ccx) ;
6294
6328
shape:: gen_shape_tables ( ccx) ;
6295
6329
write_abi_version ( ccx) ;
0 commit comments