mirror of
https://github.com/dankamongmen/notcurses
synced 2025-03-09 17:19:03 -04:00
Create mstreamfp before registering signal handlers
We use mstreamfp in notcurses_stop_minimal(), so we can't register that function as a fatal signal handler until we've opened mstreamfp. Move it before the registration. Eliminates a coredump when we ctrl+c during init.
This commit is contained in:
parent
4a3e536c66
commit
212da290ae
@ -49,7 +49,8 @@ int reset_term_attributes(const tinfo* ti, FILE* fp){
|
|||||||
|
|
||||||
// Do the minimum necessary stuff to restore the terminal, then return. This is
|
// Do the minimum necessary stuff to restore the terminal, then return. This is
|
||||||
// the end of the line for fatal signal handlers. notcurses_stop() will go on
|
// the end of the line for fatal signal handlers. notcurses_stop() will go on
|
||||||
// to tear down and account for internal structures.
|
// to tear down and account for internal structures. note that we do lots of
|
||||||
|
// shit here that is unsafe within a signal handler =[ FIXME.
|
||||||
static int
|
static int
|
||||||
notcurses_stop_minimal(void* vnc){
|
notcurses_stop_minimal(void* vnc){
|
||||||
notcurses* nc = vnc;
|
notcurses* nc = vnc;
|
||||||
@ -1085,9 +1086,18 @@ notcurses* notcurses_core_init(const notcurses_options* opts, FILE* outfp){
|
|||||||
free(ret);
|
free(ret);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
// mstreamfp is needed by notcurses_stop_minimal, so this must be done
|
||||||
|
// before registering fatal signal handlers.
|
||||||
|
if((ret->rstate.mstreamfp = open_memstream(&ret->rstate.mstream, &ret->rstate.mstrsize)) == NULL){
|
||||||
|
pthread_mutex_destroy(&ret->pilelock);
|
||||||
|
pthread_mutex_destroy(&ret->statlock);
|
||||||
|
free(ret);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
if(setup_signals(ret, (opts->flags & NCOPTION_NO_QUIT_SIGHANDLERS),
|
if(setup_signals(ret, (opts->flags & NCOPTION_NO_QUIT_SIGHANDLERS),
|
||||||
(opts->flags & NCOPTION_NO_WINCH_SIGHANDLER),
|
(opts->flags & NCOPTION_NO_WINCH_SIGHANDLER),
|
||||||
notcurses_stop_minimal)){
|
notcurses_stop_minimal)){
|
||||||
|
fclose(ret->rstate.mstreamfp);
|
||||||
pthread_mutex_destroy(&ret->pilelock);
|
pthread_mutex_destroy(&ret->pilelock);
|
||||||
pthread_mutex_destroy(&ret->statlock);
|
pthread_mutex_destroy(&ret->statlock);
|
||||||
free(ret);
|
free(ret);
|
||||||
@ -1100,6 +1110,7 @@ notcurses* notcurses_core_init(const notcurses_options* opts, FILE* outfp){
|
|||||||
if(setupterm(opts->termtype, ret->ttyfd, &termerr) != OK){
|
if(setupterm(opts->termtype, ret->ttyfd, &termerr) != OK){
|
||||||
fprintf(stderr, "Terminfo error %d (see terminfo(3ncurses))\n", termerr);
|
fprintf(stderr, "Terminfo error %d (see terminfo(3ncurses))\n", termerr);
|
||||||
drop_signals(ret);
|
drop_signals(ret);
|
||||||
|
fclose(ret->rstate.mstreamfp);
|
||||||
pthread_mutex_destroy(&ret->statlock);
|
pthread_mutex_destroy(&ret->statlock);
|
||||||
pthread_mutex_destroy(&ret->pilelock);
|
pthread_mutex_destroy(&ret->pilelock);
|
||||||
free(ret);
|
free(ret);
|
||||||
@ -1139,10 +1150,6 @@ notcurses* notcurses_core_init(const notcurses_options* opts, FILE* outfp){
|
|||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if((ret->rstate.mstreamfp = open_memstream(&ret->rstate.mstream, &ret->rstate.mstrsize)) == NULL){
|
|
||||||
free_plane(ret->stdplane);
|
|
||||||
goto err;
|
|
||||||
}
|
|
||||||
const char* smkx = get_escape(&ret->tcache, ESCAPE_SMKX);
|
const char* smkx = get_escape(&ret->tcache, ESCAPE_SMKX);
|
||||||
if(smkx && term_emit(smkx, ret->ttyfp, false)){
|
if(smkx && term_emit(smkx, ret->ttyfp, false)){
|
||||||
free_plane(ret->stdplane);
|
free_plane(ret->stdplane);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user