static void* dist_table_alloc(void *dep_tmpl) { Eterm chnl_nr; Eterm sysname; DistEntry *dep; erts_smp_rwmtx_opt_t rwmtx_opt = ERTS_SMP_RWMTX_OPT_DEFAULT_INITER; rwmtx_opt.type = ERTS_SMP_RWMTX_TYPE_FREQUENT_READ; sysname = ((DistEntry *) dep_tmpl)->sysname; chnl_nr = make_small((Uint) atom_val(sysname)); dep = (DistEntry *) erts_alloc(ERTS_ALC_T_DIST_ENTRY, sizeof(DistEntry)); dist_entries++; dep->prev = NULL; erts_refc_init(&dep->refc, -1); erts_smp_rwmtx_init_opt_x(&dep->rwmtx, &rwmtx_opt, "dist_entry", chnl_nr); dep->sysname = sysname; dep->cid = NIL; dep->connection_id = 0; dep->status = 0; dep->flags = 0; dep->version = 0; erts_smp_mtx_init_x(&dep->lnk_mtx, "dist_entry_links", chnl_nr); dep->node_links = NULL; dep->nlinks = NULL; dep->monitors = NULL; erts_smp_mtx_init_x(&dep->qlock, "dist_entry_out_queue", chnl_nr); dep->qflgs = 0; dep->qsize = 0; dep->out_queue.first = NULL; dep->out_queue.last = NULL; dep->suspended = NULL; dep->finalized_out_queue.first = NULL; dep->finalized_out_queue.last = NULL; erts_smp_atomic_init_nob(&dep->dist_cmd_scheduled, 0); erts_port_task_handle_init(&dep->dist_cmd); dep->send = NULL; dep->cache = NULL; /* Link in */ /* All new dist entries are "not connected". * erts_this_dist_entry is also always included among "not connected" */ dep->next = erts_not_connected_dist_entries; if(erts_not_connected_dist_entries) { ASSERT(erts_not_connected_dist_entries->prev == NULL); erts_not_connected_dist_entries->prev = dep; } erts_not_connected_dist_entries = dep; erts_no_of_not_connected_dist_entries++; return (void *) dep; }
/* * Initialize the module. */ void erts_port_task_init(void) { erts_smp_atomic_init_nob(&erts_port_task_outstanding_io_tasks, (erts_aint_t) 0); init_port_task_alloc(); init_port_taskq_alloc(); }
/* ** Init a pre allocated or static hash structure ** and allocate buckets. NOT SAFE */ SafeHash* safe_hash_init(ErtsAlcType_t type, SafeHash* h, char* name, int size, SafeHashFunctions fun) { int i, bytes; size = align_up_pow2(size); bytes = size * sizeof(SafeHashBucket*); h->type = type; h->tab = (SafeHashBucket**) erts_alloc(h->type, bytes); sys_memzero(h->tab, bytes); h->name = name; h->fun = fun; set_size(h,size); erts_smp_atomic_init_nob(&h->is_rehashing, 0); erts_smp_atomic_init_nob(&h->nitems, 0); for (i=0; i<SAFE_HASH_LOCK_CNT; i++) { erts_smp_mtx_init(&h->lock_vec[i].mtx,"safe_hash"); } return h; }
static void table_init_ranges(struct ranges* r) { Sint i; for (i = 0; i < ERTS_NUM_CODE_IX; i++) { r[i].modules = 0; r[i].n = 0; r[i].allocated = 0; erts_smp_atomic_init_nob(&r[i].mid, 0); } }
void erts_beam_bif_load_init(void) { erts_smp_mtx_init(&release_literal_areas.mtx, "release_literal_areas"); release_literal_areas.first = NULL; release_literal_areas.last = NULL; erts_smp_atomic_init_nob(&erts_copy_literal_area__, (erts_aint_t) NULL); init_purge_state(); }
void init_export_table(void) { int i; erts_smp_mtx_init(&export_staging_lock, "export_tab"); erts_smp_atomic_init_nob(&total_entries_bytes, 0); export_tables = erts_alloc(ERTS_ALC_T_EXPORT_TABLE, sizeof(IndexTable)*ERTS_NUM_CODE_IX); for (i=0; i<ERTS_NUM_CODE_IX; i++) { erts_index_init(ERTS_ALC_T_EXPORT_TABLE, &export_tables[i], "export_list", EXPORT_INITIAL_SIZE, EXPORT_LIMIT, fun); } }
void erts_sys_pre_init(void) { erts_printf_add_cr_to_stdout = 1; erts_printf_add_cr_to_stderr = 1; #ifdef USE_THREADS { erts_thr_init_data_t eid = ERTS_THR_INIT_DATA_DEF_INITER; eid.thread_create_child_func = thr_create_prepare_child; /* Before creation in parent */ eid.thread_create_prepare_func = thr_create_prepare; /* After creation in parent */ eid.thread_create_parent_func = thr_create_cleanup, erts_thr_init(&eid); report_exit_list = NULL; #ifdef ERTS_ENABLE_LOCK_COUNT erts_lcnt_init(); #endif #if defined(ERTS_SMP) erts_mtx_init(&chld_stat_mtx, "child_status"); #endif } #ifdef ERTS_SMP erts_smp_atomic32_init_nob(&erts_break_requested, 0); erts_smp_atomic32_init_nob(&have_prepared_crash_dump, 0); #else erts_break_requested = 0; have_prepared_crash_dump = 0; #endif #if !defined(ERTS_SMP) children_died = 0; #endif #endif /* USE_THREADS */ erts_printf_stdout_func = erts_sys_ramlog_printf; erts_smp_atomic_init_nob(&sys_misc_mem_sz, 0); }
void erts_sys_pre_init(void) { #ifdef USE_THREADS erts_thr_init_data_t eid = ERTS_THR_INIT_DATA_DEF_INITER; #endif erts_printf_add_cr_to_stdout = 1; erts_printf_add_cr_to_stderr = 1; #ifdef USE_THREADS eid.thread_create_child_func = thr_create_prepare_child; /* Before creation in parent */ eid.thread_create_prepare_func = thr_create_prepare; /* After creation in parent */ eid.thread_create_parent_func = thr_create_cleanup, #ifdef ERTS_THR_HAVE_SIG_FUNCS sigemptyset(&thr_create_sigmask); sigaddset(&thr_create_sigmask, SIGINT); /* block interrupt */ sigaddset(&thr_create_sigmask, SIGUSR1); /* block user defined signal */ #endif erts_thr_init(&eid); #ifdef ERTS_ENABLE_LOCK_COUNT erts_lcnt_init(); #endif #endif /* USE_THREADS */ erts_init_sys_time_sup(); #ifdef USE_THREADS #ifdef ERTS_SMP erts_smp_atomic32_init_nob(&erts_break_requested, 0); erts_smp_atomic32_init_nob(&erts_got_sigusr1, 0); erts_smp_atomic32_init_nob(&have_prepared_crash_dump, 0); #else erts_break_requested = 0; erts_got_sigusr1 = 0; have_prepared_crash_dump = 0; #endif #endif /* USE_THREADS */ erts_smp_atomic_init_nob(&sys_misc_mem_sz, 0); { /* * Unfortunately we depend on fd 0,1,2 in the old shell code. * So if for some reason we do not have those open when we start * we have to open them here. Not doing this can cause the emulator * to deadlock when reaping the fd_driver ports :( */ int fd; /* Make sure fd 0 is open */ if ((fd = open("/dev/null", O_RDONLY)) != 0) close(fd); /* Make sure fds 1 and 2 are open */ while (fd < 3) { fd = open("/dev/null", O_WRONLY); } close(fd); } /* We need a file descriptor to close in the crashdump creation. * We close this one to be sure we can get a fd for our real file ... * so, we create one here ... a stone to carry all the way home. */ crashdump_companion_cube_fd = open("/dev/null", O_RDONLY); /* don't lose it, there will be cake */ }
void erts_init_port_data(Port *prt) { erts_smp_atomic_init_nob(&prt->data, (erts_aint_t) am_undefined); }
static void table_update_ranges(ErtsAlcType_t alctr, struct ranges* r, BeamInstr* code, Uint size) { ErtsCodeIndex dst = erts_staging_code_ix(); ErtsCodeIndex src = erts_active_code_ix(); Sint i; Sint n; Sint need; if (src == dst) { ASSERT(!erts_initialized); /* * During start-up of system, the indices are the same. * Handle this by faking a source area. */ src = (src+1) % ERTS_NUM_CODE_IX; if (r[src].modules) { erts_smp_atomic_add_nob(&mem_used, -r[src].allocated); erts_free(alctr, r[src].modules); } r[src] = r[dst]; r[dst].modules = 0; } CHECK(&r[src]); ASSERT(r[dst].modules == NULL); need = r[dst].allocated = r[src].n + 1; erts_smp_atomic_add_nob(&mem_used, need); r[dst].modules = (Range *) erts_alloc(alctr, need * sizeof(Range)); n = 0; for (i = 0; i < r[src].n; i++) { Range* rp = r[src].modules+i; if (code < rp->start) { r[dst].modules[n].start = code; erts_smp_atomic_init_nob(&r[dst].modules[n].end, (erts_aint_t)(((byte *)code) + size)); ASSERT(!n || RANGE_END(&r[dst].modules[n-1]) < code); n++; break; } if (rp->start < RANGE_END(rp)) { /* Only insert a module that has not been purged. */ r[dst].modules[n].start = rp->start; erts_smp_atomic_init_nob(&r[dst].modules[n].end, (erts_aint_t)(RANGE_END(rp))); ASSERT(!n || RANGE_END(&r[dst].modules[n-1]) < rp->start); n++; } } while (i < r[src].n) { Range* rp = r[src].modules+i; if (rp->start < RANGE_END(rp)) { /* Only insert a module that has not been purged. */ r[dst].modules[n].start = rp->start; erts_smp_atomic_init_nob(&r[dst].modules[n].end, (erts_aint_t)(RANGE_END(rp))); ASSERT(!n || RANGE_END(&r[dst].modules[n-1]) < rp->start); n++; } i++; } if (n == 0 || code > r[dst].modules[n-1].start) { r[dst].modules[n].start = code; erts_smp_atomic_init_nob(&r[dst].modules[n].end, (erts_aint_t)(((byte *)code) + size)); ASSERT(!n || RANGE_END(&r[dst].modules[n-1]) < code); n++; } ASSERT(n <= r[src].n+1); r[dst].n = n; erts_smp_atomic_set_nob(&r[dst].mid, (erts_aint_t) (r[dst].modules + n / 2)); CHECK(&r[dst]); CHECK(&r[src]); }
void erts_init_ranges(void) { erts_smp_atomic_init_nob(&mem_used, 0); table_init_ranges(range_tables); }
void erts_init_node_tables(int dd_sec) { erts_smp_rwmtx_opt_t rwmtx_opt = ERTS_SMP_RWMTX_OPT_DEFAULT_INITER; HashFunctions f; if (dd_sec == ERTS_NODE_TAB_DELAY_GC_INFINITY) node_tab_delete_delay = (ErtsMonotonicTime) -1; else node_tab_delete_delay = ((ErtsMonotonicTime) dd_sec)*1000; orig_node_tab_delete_delay = node_tab_delete_delay; rwmtx_opt.type = ERTS_SMP_RWMTX_TYPE_FREQUENT_READ; rwmtx_opt.lived = ERTS_SMP_RWMTX_LONG_LIVED; f.hash = (H_FUN) dist_table_hash; f.cmp = (HCMP_FUN) dist_table_cmp; f.alloc = (HALLOC_FUN) dist_table_alloc; f.free = (HFREE_FUN) dist_table_free; erts_this_dist_entry = erts_alloc(ERTS_ALC_T_DIST_ENTRY, sizeof(DistEntry)); dist_entries = 1; hash_init(ERTS_ALC_T_DIST_TABLE, &erts_dist_table, "dist_table", 11, f); erts_hidden_dist_entries = NULL; erts_visible_dist_entries = NULL; erts_not_connected_dist_entries = NULL; erts_no_of_hidden_dist_entries = 0; erts_no_of_visible_dist_entries = 0; erts_no_of_not_connected_dist_entries = 0; erts_this_dist_entry->next = NULL; erts_this_dist_entry->prev = NULL; erts_refc_init(&erts_this_dist_entry->refc, 1); /* erts_this_node */ erts_smp_rwmtx_init_opt_x(&erts_this_dist_entry->rwmtx, &rwmtx_opt, "dist_entry", make_small(ERST_INTERNAL_CHANNEL_NO)); erts_this_dist_entry->sysname = am_Noname; erts_this_dist_entry->cid = NIL; erts_this_dist_entry->connection_id = 0; erts_this_dist_entry->status = 0; erts_this_dist_entry->flags = 0; erts_this_dist_entry->version = 0; erts_smp_mtx_init_x(&erts_this_dist_entry->lnk_mtx, "dist_entry_links", make_small(ERST_INTERNAL_CHANNEL_NO)); erts_this_dist_entry->node_links = NULL; erts_this_dist_entry->nlinks = NULL; erts_this_dist_entry->monitors = NULL; erts_smp_mtx_init_x(&erts_this_dist_entry->qlock, "dist_entry_out_queue", make_small(ERST_INTERNAL_CHANNEL_NO)); erts_this_dist_entry->qflgs = 0; erts_this_dist_entry->qsize = 0; erts_this_dist_entry->out_queue.first = NULL; erts_this_dist_entry->out_queue.last = NULL; erts_this_dist_entry->suspended = NULL; erts_this_dist_entry->finalized_out_queue.first = NULL; erts_this_dist_entry->finalized_out_queue.last = NULL; erts_smp_atomic_init_nob(&erts_this_dist_entry->dist_cmd_scheduled, 0); erts_port_task_handle_init(&erts_this_dist_entry->dist_cmd); erts_this_dist_entry->send = NULL; erts_this_dist_entry->cache = NULL; (void) hash_put(&erts_dist_table, (void *) erts_this_dist_entry); f.hash = (H_FUN) node_table_hash; f.cmp = (HCMP_FUN) node_table_cmp; f.alloc = (HALLOC_FUN) node_table_alloc; f.free = (HFREE_FUN) node_table_free; hash_init(ERTS_ALC_T_NODE_TABLE, &erts_node_table, "node_table", 11, f); erts_this_node = erts_alloc(ERTS_ALC_T_NODE_ENTRY, sizeof(ErlNode)); node_entries = 1; erts_refc_init(&erts_this_node->refc, 1); /* The system itself */ erts_this_node->sysname = am_Noname; erts_this_node->creation = 0; erts_this_node->dist_entry = erts_this_dist_entry; erts_this_node_sysname = erts_this_node_sysname_BUFFER; erts_snprintf(erts_this_node_sysname, sizeof(erts_this_node_sysname_BUFFER), "%T", erts_this_node->sysname); (void) hash_put(&erts_node_table, (void *) erts_this_node); erts_smp_rwmtx_init_opt(&erts_node_table_rwmtx, &rwmtx_opt, "node_table"); erts_smp_rwmtx_init_opt(&erts_dist_table_rwmtx, &rwmtx_opt, "dist_table"); references_atoms_need_init = 1; }
void erts_init_monitors(void) { erts_smp_atomic_init_nob(&tot_link_lh_size, 0); }
static ERTS_INLINE void do_time_init(void) { erts_smp_atomic_init_nob(&do_time, 0L); }