📄 misc.c
字号:
/* Convince lint that some things are used */# ifdef LINT { extern char * GC_copyright[]; extern int GC_read(); extern void GC_register_finalizer_no_order(); GC_noop(GC_copyright, GC_find_header, GC_push_one, GC_call_with_alloc_lock, GC_read, GC_dont_expand,# ifndef NO_DEBUGGING GC_dump,# endif GC_register_finalizer_no_order); }# endif}void GC_enable_incremental GC_PROTO(()){# if !defined(SMALL_CONFIG) && !defined(KEEP_BACK_PTRS) /* If we are keeping back pointers, the GC itself dirties all */ /* pages on which objects have been marked, making */ /* incremental GC pointless. */ if (!GC_find_leak) { DCL_LOCK_STATE; DISABLE_SIGNALS(); LOCK(); if (GC_incremental) goto out; GC_setpagesize(); if (GC_no_win32_dlls) goto out;# ifndef GC_SOLARIS_THREADS maybe_install_looping_handler(); /* Before write fault handler! */ GC_dirty_init();# endif if (!GC_is_initialized) { GC_init_inner(); } if (GC_incremental) goto out; if (GC_dont_gc) { /* Can't easily do it. */ UNLOCK(); ENABLE_SIGNALS(); return; } if (GC_words_allocd > 0) { /* There may be unmarked reachable objects */ GC_gcollect_inner(); } /* else we're OK in assuming everything's */ /* clean since nothing can point to an */ /* unmarked object. */ GC_read_dirty(); GC_incremental = TRUE;out: UNLOCK(); ENABLE_SIGNALS(); }# endif}#if defined(MSWIN32) || defined(MSWINCE)# define LOG_FILE _T("gc.log") HANDLE GC_stdout = 0; void GC_deinit() { if (GC_is_initialized) { DeleteCriticalSection(&GC_write_cs); } } int GC_write(buf, len) GC_CONST char * buf; size_t len; { BOOL tmp; DWORD written; if (len == 0) return 0; EnterCriticalSection(&GC_write_cs); if (GC_stdout == INVALID_HANDLE_VALUE) { return -1; } else if (GC_stdout == 0) { GC_stdout = CreateFile(LOG_FILE, GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, CREATE_ALWAYS, FILE_FLAG_WRITE_THROUGH, NULL); if (GC_stdout == INVALID_HANDLE_VALUE) ABORT("Open of log file failed"); } tmp = WriteFile(GC_stdout, buf, len, &written, NULL); if (!tmp) DebugBreak(); LeaveCriticalSection(&GC_write_cs); return tmp ? (int)written : -1; }#endif#if defined(OS2) || defined(MACOS)FILE * GC_stdout = NULL;FILE * GC_stderr = NULL;int GC_tmp; /* Should really be local ... */ void GC_set_files() { if (GC_stdout == NULL) { GC_stdout = stdout; } if (GC_stderr == NULL) { GC_stderr = stderr; } }#endif#if !defined(OS2) && !defined(MACOS) && !defined(MSWIN32) && !defined(MSWINCE) int GC_stdout = 1; int GC_stderr = 2;# if !defined(AMIGA)# include <unistd.h># endif#endif#if !defined(MSWIN32) && !defined(MSWINCE) && !defined(OS2) \ && !defined(MACOS) && !defined(ECOS) && !defined(NOSYS)int GC_write(fd, buf, len)int fd;GC_CONST char *buf;size_t len;{ register int bytes_written = 0; register int result; while (bytes_written < len) {# ifdef GC_SOLARIS_THREADS result = syscall(SYS_write, fd, buf + bytes_written, len - bytes_written);# else result = write(fd, buf + bytes_written, len - bytes_written);# endif if (-1 == result) return(result); bytes_written += result; } return(bytes_written);}#endif /* UN*X */#ifdef ECOSint GC_write(fd, buf, len){ _Jv_diag_write (buf, len); return len;}#endif#ifdef NOSYSint GC_write(fd, buf, len){ /* No writing. */ return len;}#endif#if defined(MSWIN32) || defined(MSWINCE)# define WRITE(f, buf, len) GC_write(buf, len)#else# if defined(OS2) || defined(MACOS)# define WRITE(f, buf, len) (GC_set_files(), \ GC_tmp = fwrite((buf), 1, (len), (f)), \ fflush(f), GC_tmp)# else# define WRITE(f, buf, len) GC_write((f), (buf), (len))# endif#endif/* A version of printf that is unlikely to call malloc, and is thus safer *//* to call from the collector in case malloc has been bound to GC_malloc. *//* Assumes that no more than 1023 characters are written at once. *//* Assumes that all arguments have been converted to something of the *//* same size as long, and that the format conversions expect something *//* of that size. */void GC_printf(format, a, b, c, d, e, f)GC_CONST char * format;long a, b, c, d, e, f;{ char buf[1025]; if (GC_quiet) return; buf[1024] = 0x15; (void) sprintf(buf, format, a, b, c, d, e, f); if (buf[1024] != 0x15) ABORT("GC_printf clobbered stack"); if (WRITE(GC_stdout, buf, strlen(buf)) < 0) ABORT("write to stdout failed");}void GC_err_printf(format, a, b, c, d, e, f)GC_CONST char * format;long a, b, c, d, e, f;{ char buf[1025]; buf[1024] = 0x15; (void) sprintf(buf, format, a, b, c, d, e, f); if (buf[1024] != 0x15) ABORT("GC_err_printf clobbered stack"); if (WRITE(GC_stderr, buf, strlen(buf)) < 0) ABORT("write to stderr failed");}void GC_err_puts(s)GC_CONST char *s;{ if (WRITE(GC_stderr, s, strlen(s)) < 0) ABORT("write to stderr failed");}#if defined(LINUX) && !defined(SMALL_CONFIG)void GC_err_write(buf, len)GC_CONST char *buf;size_t len;{ if (WRITE(GC_stderr, buf, len) < 0) ABORT("write to stderr failed");}#endif# if defined(__STDC__) || defined(__cplusplus) void GC_default_warn_proc(char *msg, GC_word arg)# else void GC_default_warn_proc(msg, arg) char *msg; GC_word arg;# endif{ GC_err_printf1(msg, (unsigned long)arg);}GC_warn_proc GC_current_warn_proc = GC_default_warn_proc;# if defined(__STDC__) || defined(__cplusplus) GC_warn_proc GC_set_warn_proc(GC_warn_proc p)# else GC_warn_proc GC_set_warn_proc(p) GC_warn_proc p;# endif{ GC_warn_proc result;# ifdef GC_WIN32_THREADS GC_ASSERT(GC_is_initialized);# endif LOCK(); result = GC_current_warn_proc; GC_current_warn_proc = p; UNLOCK(); return(result);}# if defined(__STDC__) || defined(__cplusplus) GC_word GC_set_free_space_divisor (GC_word value)# else GC_word GC_set_free_space_divisor (value) GC_word value;# endif{ GC_word old = GC_free_space_divisor; GC_free_space_divisor = value; return old;}#ifndef PCRvoid GC_abort(msg)GC_CONST char * msg;{# if defined(MSWIN32) (void) MessageBoxA(NULL, msg, "Fatal error in gc", MB_ICONERROR|MB_OK);# else GC_err_printf1("%s\n", msg);# endif if (GETENV("GC_LOOP_ON_ABORT") != NULL) { /* In many cases it's easier to debug a running process. */ /* It's arguably nicer to sleep, but that makes it harder */ /* to look at the thread if the debugger doesn't know much */ /* about threads. */ for(;;) {} }# if defined(MSWIN32) || defined(MSWINCE) DebugBreak();# else (void) abort();# endif}#endifvoid GC_enable(){ LOCK(); GC_dont_gc--; UNLOCK();}void GC_disable(){ LOCK(); GC_dont_gc++; UNLOCK();}/* Helper procedures for new kind creation. */void ** GC_new_free_list_inner(){ void *result = GC_INTERNAL_MALLOC((MAXOBJSZ+1)*sizeof(ptr_t), PTRFREE); if (result == 0) ABORT("Failed to allocate freelist for new kind"); BZERO(result, (MAXOBJSZ+1)*sizeof(ptr_t)); return result;}void ** GC_new_free_list(){ void *result; LOCK(); DISABLE_SIGNALS(); result = GC_new_free_list_inner(); UNLOCK(); ENABLE_SIGNALS(); return result;}int GC_new_kind_inner(fl, descr, adjust, clear)void **fl;GC_word descr;int adjust;int clear;{ int result = GC_n_kinds++; if (GC_n_kinds > MAXOBJKINDS) ABORT("Too many kinds"); GC_obj_kinds[result].ok_freelist = (ptr_t *)fl; GC_obj_kinds[result].ok_reclaim_list = 0; GC_obj_kinds[result].ok_descriptor = descr; GC_obj_kinds[result].ok_relocate_descr = adjust; GC_obj_kinds[result].ok_init = clear; return result;}int GC_new_kind(fl, descr, adjust, clear)void **fl;GC_word descr;int adjust;int clear;{ int result; LOCK(); DISABLE_SIGNALS(); result = GC_new_kind_inner(fl, descr, adjust, clear); UNLOCK(); ENABLE_SIGNALS(); return result;}int GC_new_proc_inner(proc)GC_mark_proc proc;{ int result = GC_n_mark_procs++; if (GC_n_mark_procs > MAX_MARK_PROCS) ABORT("Too many mark procedures"); GC_mark_procs[result] = proc; return result;}int GC_new_proc(proc)GC_mark_proc proc;{ int result; LOCK(); DISABLE_SIGNALS(); result = GC_new_proc_inner(proc); UNLOCK(); ENABLE_SIGNALS(); return result;}#if !defined(NO_DEBUGGING)void GC_dump(){ GC_printf0("***Static roots:\n"); GC_print_static_roots(); GC_printf0("\n***Heap sections:\n"); GC_print_heap_sects(); GC_printf0("\n***Free blocks:\n"); GC_print_hblkfreelist(); GC_printf0("\n***Blocks in use:\n"); GC_print_block_list(); GC_printf0("\n***Finalization statistics:\n"); GC_print_finalization_stats();}#endif /* NO_DEBUGGING */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -