void *waitevent (void *et) { int r; struct event_thread *waiter; mlockall(MCL_CURRENT | MCL_FUTURE); waiter = (struct event_thread *)et; pthread_cleanup_push(signal_waiter, et); block_signal(SIGUSR1, NULL); block_signal(SIGHUP, NULL); while (1) { r = waiteventloop(waiter); if (r < 0) break; sleep(r); } pthread_cleanup_pop(1); free_waiter(waiter); return NULL; }
void free_waiter (void *data) { sigset_t old; struct event_thread *wp = (struct event_thread *)data; /* * indicate in mpp that the wp is already freed storage */ block_signal(SIGHUP, &old); lock(wp->vecs->lock); if (wp->mpp) /* * be careful, mpp may already be freed -- null if so */ wp->mpp->waiter = NULL; else /* * This is OK condition during shutdown. */ condlog(3, "free_waiter, mpp freed before wp=%p (%s).", wp, wp->mapname); unlock(wp->vecs->lock); pthread_sigmask(SIG_SETMASK, &old, NULL); if (wp->dmt) dm_task_destroy(wp->dmt); FREE(wp); }
/* This function is reentrant */ static int handle_signal (Signal_Type *s) { int status = 0; int was_blocked; (void) block_signal (s->sig, &was_blocked); /* At this point, sig is blocked and the handler is about to be called. * The pending flag can be safely set to 0 here. */ s->pending = 0; if (s->handler != NULL) { int depth = SLstack_depth (); if ((-1 == SLang_start_arg_list ()) || (-1 == SLang_push_integer (s->sig)) || (-1 == SLang_end_arg_list ()) || (-1 == SLexecute_function (s->handler))) status = -1; if ((status == 0) && (depth != SLstack_depth ())) { SLang_verror (SL_Application_Error, "The signal handler %s corrupted the stack", s->handler->name); status = -1; } } if (was_blocked == 0) (void) unblock_signal (s->sig); return status; }
void thread_kill() { sigset_t mask; ll* temp; ll* prev; while(thread_count != 0) { prev = temp = head; while(temp != NULL) { if(cur_thread == &temp->thr) { block_signal(&mask); if(temp == head) head = head->next; else prev->next = temp->next; thread_count--; printf("Thread %d with priority %d is exiting\n", cur_thread->id, cur_thread->prt); unblock_signal(&mask); } prev = temp; temp = temp->next; } } }
/* The gtthread_exit() function is analogous to pthread_exit. */ void gtthread_exit(void* retval) { int flag = 0, i = 0; //Node to be deleted steque_node_t* temp = q->front; void* exit_item = steque_front(q); block_signal(); //Setting the canceled flag and return value ((node_t*)exit_item) -> returns = retval; ((node_t*)exit_item) -> canceled = 1; //Check if this is the only executing thread. Exit. for (i = 0; (i < q->N); i++) { if(((node_t*)temp -> item) -> canceled == 0){ flag = 1 ; break; } temp = temp -> next; } if(flag == 0){ steque_destroy(q); exit(0); } unblock_signal(); raise(SIGVTALRM); }
void clock_stop(void){ if (clock_state == TIMER_STOPPED) return; block_signal(SIGALRM); clock_state = TIMER_STOPPED; struct itimerval it_val = {{0,0},{0,0}}; setitimer(ITIMER_REAL,&it_val,NULL); unblock_signal(SIGALRM); }
//start server NEINT32 start_server(NEINT32 argc, NEINT8 *argv[]) { NEINT32 i ; NEINT8 *config_file = NULL; struct srv_config readcfg = {0} ; #ifndef WIN32 //prctl(PR_SET_DUMPABLE, 1); #ifdef HANDLE_UNIX_SIGNAL block_signal() ; #endif #endif ne_arg(argc, argv); if(-1==init_module() ) return -1 ; //get config file for (i=1; i<argc-1; i++){ if(0 == nestrcmp(argv[i],"-f")) { config_file = argv[i+1] ; break ; } } if(!config_file) { neprintf("usage: -f config-file\n press ANY key to continue\n") ; getch() ; exit(1) ; //return -1 ; } __config_file = config_file ; if(-1==read_config(config_file, &readcfg) ) { neprintf("press ANY key to continue\n") ; getch() ; exit(1) ; } //end get config file if(-1==init_server_app(&readcfg) ) { return -1 ; } return 0; }
void *run(void *attr){ block_signal(); struct request *r = (struct request *)attr; struct node *temp = HEAD; while(1){ while(temp->next!=NULL){ char buff[100]; sprintf(buff, "%d", temp->data); printf("Sending %s\n", buff); send(r->sock, buff, 100, 0); temp=temp->next; sleep(2); } } }
void SIGINT_handler(int sig) { block_signal(sig); int i; pthread_t thread; // signal(sig, SIG_IGN); printf("From SIGINT: just got a %d (SIGUSR1) signal\n", sig); for(i=0;message_box->client[i]!=0;i++); printf("Creating Thread for - Client with PID %d, Index: %d\n",(int)message_box->client[i-1],i-1); // signal(sig, SIGINT_handler); pthread_create(&thread,NULL,server_thread,(void*) (i-1)); pthread_detach(thread); unblock_signal(sig); }
void alarm_handler(int sig) { void* current = (node_t*)malloc(sizeof(node_t)); void* next = (node_t*)malloc(sizeof(node_t)); block_signal(); current = steque_front(q); steque_cycle(q); while(1) { next = steque_front(q); if((((node_t*)next)->canceled) == 0){ break; } steque_cycle(q); } set_alarm(); swapcontext (((node_t*)current)->thread_ctx, ((node_t*)next)->thread_ctx); unblock_signal(); }
void commit_comes(int sessionfd, const char* msg, int RW){ long pageaddr = *(long*)msg; block_signal(SIGALRM); // printf(" invalidation responce at %lx\n", pageaddr); q_dta_t* the_queue = &req_queues[addr_to_pagenum (dsm_heaptop, pageaddr, dsm_pagesize)]; if (RW == QUEUE_WRITE){ memcpy((void*)pageaddr, msg + sizeof(long), dsm_pagesize); assert(the_queue->update_pending); if (the_queue->listlen){ if (the_queue->num_parallel_readers){ for (int i = 0;i < the_queue->num_parallel_readers;i++){ int posval = the_queue->fd_queue[(i + the_queue->currhead) % (2*NumNode)]; dsm_send(0,dsm_pagesize,SERVER_PAGE,(char*)pageaddr,ABS(posval)); } }else{ dsm_send(0, dsm_pagesize, SERVER_PAGE, (char*)pageaddr, ABS(queue_top(the_queue))); } } } the_queue->update_pending = 0; unblock_signal(SIGALRM); }
/* The gtthread_cancel() function is analogous to pthread_cancel, allowing one thread to terminate another asynchronously. */ int gtthread_cancel(gtthread_t thread){ int i = 0; steque_node_t* current = q->front; block_signal(); if (gtthread_equal(thread, gtthread_self())){ gtthread_exit((void*)GTTHREAD_CANCELED); } for (i = 0; (i < q->N); i++) { if(gtthread_equal(thread, ((node_t*)current -> item) -> id)) { if (((node_t*)current -> item) -> canceled == 1){ return ESRCH; } else{ ((node_t*)current -> item) -> canceled = 1; ((node_t*)current -> item) -> returns = (void*)GTTHREAD_CANCELED; break; } } current = current -> next; } unblock_signal(); return 0; }
int eval_line(char *cmdline, int e_flag) { char *_argv[MAXARGS]; /* _argv for execve(), denoted by underscore to distinguish from main argv array*/ char buf[MAXLINE]; /* holds modified command line */ int background; /* should the job run in background or foreground? */ pid_t pid; /* process id */ int ret = EXIT_SUCCESS; strcpy(buf, cmdline); /* buf[] will be modified by parse() */ /* build the argv array */ background = parse(buf, _argv); if(e_flag > 0) Echo(_argv); if (_argv[0] == NULL) /* ignore empty lines */ { return ret; } if (builtin(_argv, process_table) == 1) /* the work is done */ { return ret; } if(background) { block_signal(SIGINT, 1); } /* child runs user job */ if ((pid = fork()) == 0) { if (execvp(_argv[0], _argv/*, environ*/) == -1) { printf("%s: execve failed: %s\n", _argv[0], strerror(errno)); _exit(EXIT_FAILURE); } } if (background && pid != 0) /* parent waits for foreground job to terminate */ { printf("background process %d: %s", (int) pid, cmdline); // Add to process table: int err; if( (err = insert_process_table(process_table, pid)) == -1) { fprintf(stderr, "insert_process_table failed: line %d: %s\n", __LINE__, strerror(errno)); } // Passing 0 unblocks the signal. block_signal(SIGINT, 0); } else { if (waitpid(pid, &ret, 0) == -1) { printf("%s: waitpid failed: %s\n", _argv[0], strerror(errno)); exit(EXIT_FAILURE); } // If in verbose mode, print out a detailed message: if(verbose) { printf("process %d, completed normally, status %d\n", pid, ret); } } return ret; }
/* * Called to set up the pty. * * Returns an error message, or NULL on success. * * Also places the canonical host name into `realhost'. It must be * freed by the caller. */ static const char *pty_init(void *frontend, void **backend_handle, Conf *conf, char *host, int port, char **realhost, int nodelay, int keepalive) { int slavefd; pid_t pid, pgrp; #ifndef NOT_X_WINDOWS /* for Mac OS X native compilation */ long windowid; #endif Pty pty; if (single_pty) { pty = single_pty; assert(pty->conf == NULL); } else { pty = snew(struct pty_tag); pty->master_fd = pty->slave_fd = -1; #ifndef OMIT_UTMP pty_stamped_utmp = FALSE; #endif } pty->frontend = frontend; *backend_handle = NULL; /* we can't sensibly use this, sadly */ pty->conf = conf_copy(conf); pty->term_width = conf_get_int(conf, CONF_width); pty->term_height = conf_get_int(conf, CONF_height); if (pty->master_fd < 0) pty_open_master(pty); /* * Set the backspace character to be whichever of ^H and ^? is * specified by bksp_is_delete. */ { struct termios attrs; tcgetattr(pty->master_fd, &attrs); attrs.c_cc[VERASE] = conf_get_int(conf, CONF_bksp_is_delete) ? '\177' : '\010'; tcsetattr(pty->master_fd, TCSANOW, &attrs); } #ifndef OMIT_UTMP /* * Stamp utmp (that is, tell the utmp helper process to do so), * or not. */ if (pty_utmp_helper_pipe >= 0) { /* if it's < 0, we can't anyway */ if (!conf_get_int(conf, CONF_stamp_utmp)) { close(pty_utmp_helper_pipe); /* just let the child process die */ pty_utmp_helper_pipe = -1; } else { char *location = get_x_display(pty->frontend); int len = strlen(location)+1, pos = 0; /* +1 to include NUL */ while (pos < len) { int ret = write(pty_utmp_helper_pipe, location+pos, len - pos); if (ret < 0) { perror("pterm: writing to utmp helper process"); close(pty_utmp_helper_pipe); /* arrgh, just give up */ pty_utmp_helper_pipe = -1; break; } pos += ret; } } } #endif #ifndef NOT_X_WINDOWS /* for Mac OS X native compilation */ windowid = get_windowid(pty->frontend); #endif /* * Fork and execute the command. */ pid = fork(); if (pid < 0) { perror("fork"); exit(1); } if (pid == 0) { /* * We are the child. */ slavefd = pty_open_slave(pty); if (slavefd < 0) { perror("slave pty: open"); _exit(1); } close(pty->master_fd); noncloexec(slavefd); dup2(slavefd, 0); dup2(slavefd, 1); dup2(slavefd, 2); close(slavefd); setsid(); #ifdef TIOCSCTTY ioctl(0, TIOCSCTTY, 1); #endif pgrp = getpid(); tcsetpgrp(0, pgrp); setpgid(pgrp, pgrp); { int ptyfd = open(pty->name, O_WRONLY, 0); if (ptyfd >= 0) close(ptyfd); } setpgid(pgrp, pgrp); { char *term_env_var = dupprintf("TERM=%s", conf_get_str(conf, CONF_termtype)); putenv(term_env_var); /* We mustn't free term_env_var, as putenv links it into the * environment in place. */ } #ifndef NOT_X_WINDOWS /* for Mac OS X native compilation */ { char *windowid_env_var = dupprintf("WINDOWID=%ld", windowid); putenv(windowid_env_var); /* We mustn't free windowid_env_var, as putenv links it into the * environment in place. */ } #endif { char *key, *val; for (val = conf_get_str_strs(conf, CONF_environmt, NULL, &key); val != NULL; val = conf_get_str_strs(conf, CONF_environmt, key, &key)) { char *varval = dupcat(key, "=", val, NULL); putenv(varval); /* * We must not free varval, since putenv links it * into the environment _in place_. Weird, but * there we go. Memory usage will be rationalised * as soon as we exec anyway. */ } } /* * SIGINT, SIGQUIT and SIGPIPE may have been set to ignored by * our parent, particularly by things like sh -c 'pterm &' and * some window or session managers. SIGCHLD, meanwhile, was * blocked during pt_main() startup. Reverse all this for our * child process. */ putty_signal(SIGINT, SIG_DFL); putty_signal(SIGQUIT, SIG_DFL); putty_signal(SIGPIPE, SIG_DFL); block_signal(SIGCHLD, 0); if (pty_argv) { /* * Exec the exact argument list we were given. */ execvp(pty_argv[0], pty_argv); /* * If that fails, and if we had exactly one argument, pass * that argument to $SHELL -c. * * This arranges that we can _either_ follow 'pterm -e' * with a list of argv elements to be fed directly to * exec, _or_ with a single argument containing a command * to be parsed by a shell (but, in cases of doubt, the * former is more reliable). * * A quick survey of other terminal emulators' -e options * (as of Debian squeeze) suggests that: * * - xterm supports both modes, more or less like this * - gnome-terminal will only accept a one-string shell command * - Eterm, kterm and rxvt will only accept a list of * argv elements (as did older versions of pterm). * * It therefore seems important to support both usage * modes in order to be a drop-in replacement for either * xterm or gnome-terminal, and hence for anyone's * plausible uses of the Debian-style alias * 'x-terminal-emulator'... */ if (pty_argv[1] == NULL) { char *shell = getenv("SHELL"); if (shell) execl(shell, shell, "-c", pty_argv[0], (void *)NULL); } } else { char *shell = getenv("SHELL"); char *shellname; if (conf_get_int(conf, CONF_login_shell)) { char *p = strrchr(shell, '/'); shellname = snewn(2+strlen(shell), char); p = p ? p+1 : shell; sprintf(shellname, "-%s", p); } else shellname = shell; execl(getenv("SHELL"), shellname, (void *)NULL); }
void HandleSyscalls() { register int cnt; fd_set readfds; int nfds = -1; time_t periodic_interval_len = 20; /* secs, empirically found :) */ nfds = (RSC_SOCK > CLIENT_LOG ) ? (RSC_SOCK + 1) : (CLIENT_LOG + 1); init_user_ids(Proc->owner, NULL); set_user_priv(); dprintf(D_FULLDEBUG, "HandleSyscalls: about to chdir(%s)\n", Proc->iwd); if( chdir(Proc->iwd) < 0 ) { sprintf( ErrBuf, "Can't chdir() to \"%s\"! [%s(%d)]", Proc->iwd, strerror(errno), errno ); HadErr = TRUE; return; } dprintf(D_SYSCALLS, "Shadow: Starting to field syscall requests\n"); errno = 0; time_t current_time = time(0); time_t next_periodic_update = current_time + periodic_interval_len; for(;;) { /* get a request and fulfill it */ FD_ZERO(&readfds); FD_SET(RSC_SOCK, &readfds); FD_SET(CLIENT_LOG, &readfds); struct timeval *ptimer = NULL, timer; timer.tv_sec = next_periodic_update - current_time; timer.tv_usec = 0; ptimer = &timer; /* if the current timer is set for a time longer than this, than truncate the timer required to the periodic limit. After inspection of the bandwidth timer, it seems that it will recorrect itself if select comes out of the loop before the timer goes off anyway to handle syscalls */ if ( timer.tv_sec > periodic_interval_len) { timer.tv_sec = next_periodic_update - current_time; ptimer = &timer; } unblock_signal(SIGCHLD); unblock_signal(SIGUSR1); #if defined(LINUX) || defined(Solaris) cnt = select(nfds, &readfds, (fd_set *)0, (fd_set *)0, ptimer); #else cnt = select(nfds, &readfds, 0, 0, ptimer); #endif block_signal(SIGCHLD); block_signal(SIGUSR1); if( cnt < 0 && errno != EINTR ) { EXCEPT("HandleSyscalls: select: errno=%d, rsc_sock=%d, client_log=%d",errno,RSC_SOCK,CLIENT_LOG); } if( cnt < 0 && errno == EINTR ) { continue; } if( FD_ISSET(CLIENT_LOG, &readfds) ) { if( HandleLog() < 0 ) { EXCEPT( "Peer went away" ); } } if( FD_ISSET(RSC_SOCK, &readfds) ) { if( do_REMOTE_syscall() < 0 ) { dprintf(D_SYSCALLS, "Shadow: do_REMOTE_syscall returned < 0\n"); break; } } if( FD_ISSET(UMBILICAL, &readfds) ) { dprintf(D_ALWAYS, "Shadow: Local scheduler apparently died, so I die too\n"); exit(1); } current_time = time(0); /* if this is true, then do the periodic_interval_len events */ if (current_time >= next_periodic_update) { next_periodic_update = current_time + periodic_interval_len; /* evaluate some attributes for policies like determining what to do if a job suspends wierdly or some such thing. This function has the possibility of making the shadow exit with JOB_SHOULD_HOLD or futzing up some global variables about how the job could've exited and letting Wraup take care of it. */ if (periodic_policy() == true) { break; } } #if defined(SYSCALL_DEBUG) strcpy( SyscallLabel, "shadow" ); #endif } /* The user job might exit while there is still unread data in the log. So, select with a timeout of zero, and flush everything from the log. */ /* NOTE: Since HandleLog does it's own loop to make sure it's read everything, we don't need a loop here, and should only call HandleLog once. In fact, if there's a problem w/ select(), a loop here can cause an infinite loop. -Derek Wright and Jim Basney, 2/17/99. */ HandleLog(); /* Take back normal condor privileges */ set_condor_priv(); /* If we are debugging with named pipes as our communications medium, won't have a condor_startd running - don't try to send to it. */ if( !UsePipes ) { send_quit( ExecutingHost, GlobalCap ); } dprintf(D_ALWAYS, "Shadow: Job %d.%d exited, termsig = %d, coredump = %d, retcode = %d\n", Proc->id.cluster, Proc->id.proc, WTERMSIG(JobStatus), WCOREDUMP(JobStatus), WEXITSTATUS(JobStatus)); }
/*ARGSUSED*/ int main(int argc, char *argv[] ) { char *tmp = NULL; int reserved_swap, free_swap; char *host = NULL, *cluster = NULL, *proc = NULL; char *bogus_capability; int i; set_mySubSystem( "SHADOW", SUBSYSTEM_TYPE_SHADOW ); myDistro->Init( argc, argv ); if( argc == 2 && strncasecmp(argv[1], "-cl", 3) == MATCH ) { printClassAd(); exit( 0 ); } #if defined(SYSCALL_DEBUG) SyscallLabel = argv[0] + 7; #endif #if !defined(WIN32) install_sig_handler(SIGPIPE, (SIG_HANDLER)SIG_IGN ); #endif if( argc > 1 ) { if( strcmp("-t",argv[1]) == MATCH ) { Termlog = 1; argv++; argc--; } } ShadowBDate = LastRestartTime = time(0); _EXCEPT_Cleanup = ExceptCleanup; MyPid = getpid(); config(); /* Start up with condor.condor privileges. */ /* we need to do this AFTER we call config() so that if CONDOR_IDS is being defined in the config file, we'll get the right value */ set_condor_priv(); if(Termlog) dprintf_set_tool_debug(get_mySubSystem()->getName(), 0); else dprintf_config( get_mySubSystem()->getName() ); DebugId = whoami; // create a database connection object dprintf( D_ALWAYS, "******* Standard Shadow starting up *******\n" ); dprintf( D_ALWAYS, "** %s\n", CondorVersion() ); dprintf( D_ALWAYS, "** %s\n", CondorPlatform() ); dprintf( D_ALWAYS, "*******************************************\n" ); reserved_swap = param_integer("RESERVED_SWAP", 0); reserved_swap *= 1024; /* megabytes -> kb */ bool use_sql_log = param_boolean("QUILL_USE_SQL_LOG", false); FILEObj = FILESQL::createInstance(use_sql_log); free_swap = sysapi_swap_space(); dprintf( D_FULLDEBUG, "*** Reserved Swap = %d\n", reserved_swap ); dprintf( D_FULLDEBUG, "*** Free Swap = %d\n", free_swap ); if( reserved_swap && free_swap < reserved_swap ) { dprintf( D_ALWAYS, "Not enough reserved swap space\n" ); if(FILEObj) { delete FILEObj; } exit( JOB_NO_MEM ); } dprintf(D_ALWAYS, "uid=%d, euid=%d, gid=%d, egid=%d\n", getuid(), geteuid(), getgid(), getegid()); dprintf(D_FULLDEBUG, "argc = %d\n", argc); for(i = 0; i < argc; i++) { dprintf(D_FULLDEBUG, "argv[%d] = %s\n", i, argv[i]); } if( argc < 6 ) { usage(); } if (param_boolean("SHADOW_DEBUG_WAIT", false, false)) { int debug_wait = 1; dprintf(D_ALWAYS, "SHADOW_DEBUG_WAIT is TRUE, waiting for debugger to attach to pid %d.\n", (int)::getpid()); while (debug_wait) { sleep(1); } } CheckSpoolVersion(SPOOL_MIN_VERSION_SHADOW_SUPPORTS,SPOOL_CUR_VERSION_SHADOW_SUPPORTS); if( strcmp("-pipe",argv[1]) == 0 ) { bogus_capability = argv[2]; cluster = argv[3]; proc = argv[4]; // read the big comment in the function for why this is here. RemoveNewShadowDroppings(cluster, proc); pipe_setup( cluster, proc, bogus_capability ); } else { schedd = argv[1]; host = argv[2]; bogus_capability = argv[3]; cluster = argv[4]; proc = argv[5]; if ( argc > 6 ) { IpcFile = argv[6]; dprintf(D_FULLDEBUG,"Setting IpcFile to %s\n",IpcFile); } else { IpcFile = NULL; } // read the big comment in the function for why this is here. RemoveNewShadowDroppings(cluster, proc); regular_setup( host, cluster, proc ); } scheddName = getenv( EnvGetName( ENV_SCHEDD_NAME ) ); #if 0 /* Don't want to share log file lock between child and pnarent */ (void)close( LockFd ); LockFd = -1; #endif // initialize the user log initializeUserLog(); My_Filesystem_Domain = param( "FILESYSTEM_DOMAIN" ); dprintf( D_ALWAYS, "My_Filesystem_Domain = \"%s\"\n", My_Filesystem_Domain ); My_UID_Domain = param( "UID_DOMAIN" ); dprintf( D_ALWAYS, "My_UID_Domain = \"%s\"\n", My_UID_Domain ); UseAFS = param_boolean_crufty( "USE_AFS", false ) ? TRUE : FALSE; UseNFS = param_boolean_crufty( "USE_NFS", false ) ? TRUE : FALSE; // if job specifies a checkpoint server host, this overrides // the config file parameters tmp = NULL; if (JobAd->LookupString(ATTR_CKPT_SERVER, &tmp) == 1) { if (CkptServerHost) free(CkptServerHost); UseCkptServer = TRUE; CkptServerHost = strdup(tmp); StarterChoosesCkptServer = FALSE; free(tmp); } else { free(tmp); if (CkptServerHost) { free(CkptServerHost); } CkptServerHost = param( "CKPT_SERVER_HOST" ); UseCkptServer = FALSE; if( CkptServerHost && param_boolean_crufty( "USE_CKPT_SERVER", true ) ) { UseCkptServer = TRUE; } StarterChoosesCkptServer = param_boolean_crufty("STARTER_CHOOSES_CKPT_SERVER", true) ? TRUE : FALSE; } // Initialize location of our checkpoint file. If we stored it // on a checkpoint server then set LastCkptServer. Otherwise, // LastCkptServer should be NULL to indicate that we should // look on the local disk for our checkpoint file. LastCkptServer = NULL; if (JobAd->LookupString(ATTR_LAST_CKPT_SERVER, &LastCkptServer) == 0) { free(LastCkptServer); LastCkptServer = NULL; } // LIGO if (param_boolean("ALWAYS_USE_LOCAL_CKPT_SERVER", false)) { if (LastCkptServer) { char *remoteHost = NULL; JobAd->LookupString(ATTR_REMOTE_HOST, &remoteHost); char *machineName = strrchr(remoteHost, '@'); if (machineName == NULL) { machineName = remoteHost; } else { machineName++; } LastCkptServer = strdup(machineName); CkptServerHost = strdup(machineName); dprintf(D_ALWAYS, "ALWAYS_USE_LOCAL_CKPT_SERVER is true, forcing LastCkptServer to %s\n", LastCkptServer); } else { dprintf(D_ALWAYS, "ALWAYS_USE_LOCAL_CKPT_SERVER is true, but checkpoint is not on server, restoring file local file\n"); } } MaxDiscardedRunTime = param_integer( "MAX_DISCARDED_RUN_TIME", 3600 ); CompressPeriodicCkpt = param_boolean( "COMPRESS_PERIODIC_CKPT", false ); PeriodicSync = param_boolean( "PERIODIC_MEMORY_SYNC", false ); CompressVacateCkpt = param_boolean( "COMPRESS_VACATE_CKPT", false ); SlowCkptSpeed = param_integer( "SLOW_CKPT_SPEED", 0 ); // Install signal handlers such that all signals are blocked when inside // the handler. sigset_t fullset; sigfillset(&fullset); install_sig_handler_with_mask( SIGCHLD,&fullset, reaper ); // SIGUSR1 is sent by the schedd when a job is removed with // condor_rm. install_sig_handler_with_mask( SIGUSR1, &fullset, handle_sigusr1 ); // SIGQUIT is sent for a fast shutdow. install_sig_handler_with_mask( SIGQUIT, &fullset, handle_sigquit ); // SIGTERM is sent for a graceful shutdow. install_sig_handler_with_mask( SIGTERM, &fullset, handle_sigterm ); /* Here we block the async signals. We do this mainly because on HPUX, * XDR wigs out if it is interrupted by a signal. We do it on all * platforms because it seems like a safe idea. We unblock the signals * during before select(), which is where we spend most of our time. */ block_signal(SIGCHLD); block_signal(SIGUSR1); /* If the completed job had been committed to the job queue, but for some reason the shadow exited wierdly and the schedd is trying to run it again, then simply write the job termination events and send the email as if the job had just ended. */ if (terminate_is_pending() == TRUE) { /* This function will exit()! */ handle_terminate_pending(); } HandleSyscalls(); Wrapup(); /* HACK! WHOOO!!!!! Throw the old shadow away already! */ /* This will figure out whether or not the job should go on hold AFTER the job has exited for whatever reason, or if the job should be allowed to exit. It modifies ExitReason approriately for job holding, or, get this, just EXCEPTs if the jobs is supposed to go into idle state and not leave. :) */ /* Small change by Todd : only check the static policy if the job really exited of its own accord -- we don't want to even evaluate the static policy if the job exited because it was preempted, for instance */ if (check_static_policy && (ExitReason == JOB_EXITED || ExitReason == JOB_KILLED || ExitReason == JOB_COREDUMPED)) { static_policy(); } if( My_UID_Domain ) { free( My_UID_Domain ); } if( My_Filesystem_Domain ) { free( My_Filesystem_Domain ); } if(FILEObj) { delete FILEObj; } dprintf( D_ALWAYS, "********** Shadow Exiting(%d) **********\n", ExitReason ); exit( ExitReason ); }
void queue_for_page(int sessionfd, long pagenum, int RW){ block_signal(SIGALRM); q_dta_t* the_queue = &(req_queues[pagenum]); assert(the_queue->num_parallel_readers <= the_queue->listlen); int make_active = 0; qaddr = pagenum_to_addr(dsm_heaptop, pagenum, dsm_pagesize); add_to_queue(RW*sessionfd, the_queue); if (RW == QUEUE_READ){ switch (the_queue->q_state){ case QUEUE_EMPTY: { int found; curr_owners[pagenum] = (short)(long)hash_get((void*)(long)sessionfd, sessionfd_to_nid,&found); assert(found); the_queue->q_state = QUEUE_READERS; if (!the_queue->update_pending){ long pagebegin = pagenum_to_addr(dsm_heaptop,pagenum, dsm_pagesize); dsm_send(0,dsm_pagesize,SERVER_PAGE,(char*)pagebegin,sessionfd); } the_queue->num_parallel_readers = 1; break; } case QUEUE_WRITERS: { break; } case QUEUE_READERS: { if (!the_queue->update_pending){ long pagebegin = pagenum_to_addr(dsm_heaptop,pagenum, dsm_pagesize); dsm_send(0,dsm_pagesize,SERVER_PAGE,(char*)pagebegin,sessionfd); } the_queue->num_parallel_readers++; break; } default:break; } }else{ the_queue->num_writers ++; switch (the_queue->q_state){ case QUEUE_EMPTY: { int found; curr_owners[pagenum] = (short)(long)hash_get((void*)(long)sessionfd, sessionfd_to_nid,&found); assert(found); the_queue->q_state = QUEUE_WRITERS; make_active = 1; if (!the_queue->update_pending){ long pagebegin = pagenum_to_addr(dsm_heaptop,pagenum, dsm_pagesize); dsm_send(0,dsm_pagesize,SERVER_PAGE,(char*)pagebegin,sessionfd); } break; } case QUEUE_WRITERS: { break; } case QUEUE_READERS: { the_queue->q_state = QUEUE_WRITERS; make_active = 1; break; } default:break; } } if (make_active){ req_queues[pagenum].next_active = activehead; activehead = pagenum; clock_start(); } unblock_signal(SIGALRM); }
/* * Called to set up the pty. * * Returns an error message, or NULL on success. * * Also places the canonical host name into `realhost'. It must be * freed by the caller. */ static const char *pty_init(void *frontend, void **backend_handle, Config *cfg, char *host, int port, char **realhost, int nodelay, int keepalive) { int slavefd; pid_t pid, pgrp; #ifndef NOT_X_WINDOWS /* for Mac OS X native compilation */ long windowid; #endif Pty pty; if (single_pty) { pty = single_pty; } else { pty = snew(struct pty_tag); pty->master_fd = pty->slave_fd = -1; #ifndef OMIT_UTMP pty_stamped_utmp = FALSE; #endif } pty->frontend = frontend; *backend_handle = NULL; /* we can't sensibly use this, sadly */ pty->cfg = *cfg; /* structure copy */ pty->term_width = cfg->width; pty->term_height = cfg->height; if (pty->master_fd < 0) pty_open_master(pty); /* * Set the backspace character to be whichever of ^H and ^? is * specified by bksp_is_delete. */ { struct termios attrs; tcgetattr(pty->master_fd, &attrs); attrs.c_cc[VERASE] = cfg->bksp_is_delete ? '\177' : '\010'; tcsetattr(pty->master_fd, TCSANOW, &attrs); } #ifndef OMIT_UTMP /* * Stamp utmp (that is, tell the utmp helper process to do so), * or not. */ if (!cfg->stamp_utmp) { close(pty_utmp_helper_pipe); /* just let the child process die */ pty_utmp_helper_pipe = -1; } else { char *location = get_x_display(pty->frontend); int len = strlen(location)+1, pos = 0; /* +1 to include NUL */ while (pos < len) { int ret = write(pty_utmp_helper_pipe, location+pos, len - pos); if (ret < 0) { perror("pterm: writing to utmp helper process"); close(pty_utmp_helper_pipe); /* arrgh, just give up */ pty_utmp_helper_pipe = -1; break; } pos += ret; } } #endif #ifndef NOT_X_WINDOWS /* for Mac OS X native compilation */ windowid = get_windowid(pty->frontend); #endif /* * Fork and execute the command. */ pid = fork(); if (pid < 0) { perror("fork"); exit(1); } if (pid == 0) { /* * We are the child. */ slavefd = pty_open_slave(pty); if (slavefd < 0) { perror("slave pty: open"); _exit(1); } close(pty->master_fd); fcntl(slavefd, F_SETFD, 0); /* don't close on exec */ dup2(slavefd, 0); dup2(slavefd, 1); dup2(slavefd, 2); close(slavefd); setsid(); #ifdef TIOCSCTTY ioctl(0, TIOCSCTTY, 1); #endif pgrp = getpid(); tcsetpgrp(0, pgrp); setpgid(pgrp, pgrp); close(open(pty->name, O_WRONLY, 0)); setpgid(pgrp, pgrp); { char *term_env_var = dupprintf("TERM=%s", cfg->termtype); putenv(term_env_var); /* We mustn't free term_env_var, as putenv links it into the * environment in place. */ } #ifndef NOT_X_WINDOWS /* for Mac OS X native compilation */ { char *windowid_env_var = dupprintf("WINDOWID=%ld", windowid); putenv(windowid_env_var); /* We mustn't free windowid_env_var, as putenv links it into the * environment in place. */ } #endif { char *e = cfg->environmt; char *var, *varend, *val, *varval; while (*e) { var = e; while (*e && *e != '\t') e++; varend = e; if (*e == '\t') e++; val = e; while (*e) e++; e++; varval = dupprintf("%.*s=%s", varend-var, var, val); putenv(varval); /* * We must not free varval, since putenv links it * into the environment _in place_. Weird, but * there we go. Memory usage will be rationalised * as soon as we exec anyway. */ } } /* * SIGINT, SIGQUIT and SIGPIPE may have been set to ignored by * our parent, particularly by things like sh -c 'pterm &' and * some window or session managers. SIGCHLD, meanwhile, was * blocked during pt_main() startup. Reverse all this for our * child process. */ putty_signal(SIGINT, SIG_DFL); putty_signal(SIGQUIT, SIG_DFL); putty_signal(SIGPIPE, SIG_DFL); block_signal(SIGCHLD, 0); if (pty_argv) execvp(pty_argv[0], pty_argv); else { char *shell = getenv("SHELL"); char *shellname; if (cfg->login_shell) { char *p = strrchr(shell, '/'); shellname = snewn(2+strlen(shell), char); p = p ? p+1 : shell; sprintf(shellname, "-%s", p); } else
int main(int argc, char *argv[]) { /* Packet Thread */ /* Initialize the mutex */ pthread_mutex_init(&m, 0); int i; char *lambda = "0.5"; char *mu = "0.35"; char *r = "1.5"; char *B = "10"; char *P = "3"; char *n = "20"; char *FILENAME = NULL; AVAILABLE = 0; DROPPED = 0; DROPPED_PKT = 0; TOTAL = 0; TOTAL_SERVED = 0; SERVER_DIE = 0; /* Read Options */ for(i=1;i<argc;i=i+2){ if (i%2!=0 && argv[i][0]=='-'){ if ((strcmp(argv[i]+1, "lambda") == 0) && ((i+1)<argc)){ lambda = argv[i+1]; if(check_num(lambda)== -1){ fprintf(stderr, "Value of lambda is not a number.\n"); exit(0); } continue; } else if ((strcmp(argv[i]+1, "mu") == 0) && ((i+1)<argc)){ mu = argv[i+1]; if(check_num(mu)== -1){ fprintf(stderr, "Value of mu is not a number.\n"); exit(0); } continue; } else if ((strcmp(argv[i]+1, "r") == 0) && ((i+1)<argc)){ r = argv[i+1]; if(check_num(r)== -1){ fprintf(stderr, "Value of r is not a number.\n"); exit(0); } continue; } else if ((strcmp(argv[i]+1, "B") == 0) && ((i+1)<argc)){ B = argv[i+1]; if(isNum(B)==-1){ fprintf(stderr, "Value of B is not a number.\n"); exit(0); } continue; } else if((strcmp(argv[i]+1, "P") == 0) && ((i+1)<argc)){ P = argv[i+1]; if(isNum(P) == -1){ fprintf(stderr, "Value of P is not a number.\n"); exit(0); } continue; } else if ((strcmp(argv[i]+1, "n") == 0) && ((i+1)<argc)){ n = argv[i+1]; if(isNum(n)==-1){ fprintf(stderr, "Value of n is not a number.\n"); exit(0); } continue; } else if ((strcmp(argv[i]+1, "t") == 0) && ((i+1)<argc)){ FILENAME = argv[i+1]; continue; } } fprintf(stderr, "Wrong command line argument\n"); exit(0); break; } /*Allocate memory to list*/ Q1 = malloc(sizeof(My402List)); Q2 = malloc(sizeof(My402List)); /*Initilialize the list*/ My402ListInit(Q1); My402ListInit(Q2); /* Block Signal from Main thread */ block_signal(); if(FILENAME!=NULL){ FILE *fp = fopen(FILENAME, "r"); if(fp==NULL){ perror("Error: Unable to open the file "); exit(0); } fclose(fp); } print_input(lambda, mu, FILENAME, r, B, P, n); /* Create packet thread */ fprintf(stdout, "\n"); /* Initialize the stats */ init_stats(); struct timeval current = diff_timeval(START_TIMEVAL, PKT_BEFORE); fprintf(stdout, "%08llu.%03ldms: emulation begins\n", toMilliSeconds(current), current.tv_usec%MILLI); /* Create threads */ create_packet_thread(lambda, mu, FILENAME, r, B, P, n); /* Print statistics */ //print_stats(); return(0); }
/* * get_child_exit: This looks for dead child processes of the client. * There are two main sources of dead children: Either an /exec'd process * has exited, or the client has attempted to fork() off a helper process * (such as wserv or gzip) and that process has choked on itself. * * When SIGCHLD is recieved, the global variable 'dead_children_processes' * is incremented. When this function is called, we go through and call * waitpid() on all of the outstanding zombies, conditionally stopping when * we reach a specific wanted sub-process. * * If you want to stop reaping children when a specific subprocess is * reached, specify the process in 'wanted'. If all youre doing is cleaning * up after zombies and /exec's, then 'wanted' should be -1. */ int get_child_exit (pid_t wanted) { Process *proc; pid_t pid; int status, i; /* * Iterate until we've reaped all of the dead processes * or we've found the one asked for. */ if (dead_children_processes) { block_signal(SIGCHLD); while ((pid = waitpid(wanted, &status, WNOHANG)) > 0) { /* * First thing we do is look to see if the process we're * working on is the one that was asked for. If it is, * then we get its exit status information and return it. */ if (wanted != -1 && pid == wanted) { /* * We do not clear 'dead_children_processes' here * because we do not know if we've reaped all of * the children yet! Leaving it set means this * function is called again, and then if there are * no more left, it is cleared (below). */ unblock_signal(SIGCHLD); if (WIFEXITED(status)) return WEXITSTATUS(status); if (WIFSTOPPED(status)) return -(WSTOPSIG(status)); if (WIFSIGNALED(status)) return -(WTERMSIG(status)); } /* * If it wasnt the process asked for, then we've probably * stumbled across a dead /exec'd process. Look for the * corresponding child process, and mark it as being dead. */ else { for (i = 0; i < process_list_size; i++) { proc = process_list[i]; if (proc && proc->pid == pid) { proc->exited = 1; proc->termsig = WTERMSIG(status); proc->retcode = WEXITSTATUS(status); break; } } } } dead_children_processes = 0; unblock_signal(SIGCHLD); } /* * Now we may have reaped some /exec'd processes that were previously * dumb and have now exited. So we call cleanup_dead_processes() to * find and delete any such processes. */ cleanup_dead_processes(); /* * If 'wanted' is not -1, then we didnt find that process, and * if 'wanted' is -1, then you should ignore the retval anyhow. ;-) */ return -1; }