static void xmit_ax25_frames (int c, int p, packet_t pp) { unsigned char fbuf[AX25_MAX_PACKET_LEN+2]; int flen; char stemp[1024]; /* max size needed? */ int info_len; unsigned char *pinfo; int pre_flags, post_flags; int num_bits; /* Total number of bits in transmission */ /* including all flags and bit stuffing. */ int duration; /* Transmission time in milliseconds. */ int already; int wait_more; int maxframe; /* Maximum number of frames for one transmission. */ int numframe; /* Number of frames sent during this transmission. */ /* * These are for timing of a transmission. * All are in usual unix time (seconds since 1/1/1970) but higher resolution */ double time_ptt; /* Time when PTT is turned on. */ double time_now; /* Current time. */ int nb; maxframe = (p == TQ_PRIO_0_HI) ? 1 : 7; /* * Print trasmitted packet. Prefix by channel and priority. * Do this before we get into the time critical part. */ ax25_format_addrs (pp, stemp); info_len = ax25_get_info (pp, &pinfo); text_color_set(DW_COLOR_XMIT); dw_printf ("[%d%c] ", c, p==TQ_PRIO_0_HI ? 'H' : 'L'); dw_printf ("%s", stemp); /* stations followed by : */ ax25_safe_print ((char *)pinfo, info_len, ! ax25_is_aprs(pp)); dw_printf ("\n"); (void)ax25_check_addresses (pp); /* Optional hex dump of packet. */ if (g_debug_xmit_packet) { text_color_set(DW_COLOR_DEBUG); dw_printf ("------\n"); ax25_hex_dump (pp); dw_printf ("------\n"); } /* * Turn on transmitter. * Start sending leading flag bytes. */ time_ptt = dtime_now (); #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: Turn on PTT now for channel %d. speed = %d\n", c, xmit_bits_per_sec[c]); #endif ptt_set (OCTYPE_PTT, c, 1); pre_flags = MS_TO_BITS(xmit_txdelay[c] * 10, c) / 8; num_bits = hdlc_send_flags (c, pre_flags, 0); #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: txdelay=%d [*10], pre_flags=%d, num_bits=%d\n", xmit_txdelay[c], pre_flags, num_bits); #endif /* * Transmit the frame. */ flen = ax25_pack (pp, fbuf); assert (flen >= 1 && flen <= sizeof(fbuf)); nb = hdlc_send_frame (c, fbuf, flen); num_bits += nb; numframe = 1; #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: flen=%d, nb=%d, num_bits=%d, numframe=%d\n", flen, nb, num_bits, numframe); #endif ax25_delete (pp); /* * Additional packets if available and not exceeding max. */ while (numframe < maxframe && tq_count (c,p) > 0) { pp = tq_remove (c, p); #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: tq_remove(chan=%d, prio=%d) returned %p\n", c, p, pp); #endif ax25_format_addrs (pp, stemp); info_len = ax25_get_info (pp, &pinfo); text_color_set(DW_COLOR_XMIT); dw_printf ("[%d%c] ", c, p==TQ_PRIO_0_HI ? 'H' : 'L'); dw_printf ("%s", stemp); /* stations followed by : */ ax25_safe_print ((char *)pinfo, info_len, ! ax25_is_aprs(pp)); dw_printf ("\n"); (void)ax25_check_addresses (pp); if (g_debug_xmit_packet) { text_color_set(DW_COLOR_DEBUG); dw_printf ("------\n"); ax25_hex_dump (pp); dw_printf ("------\n"); } /* * Transmit the frame. */ flen = ax25_pack (pp, fbuf); assert (flen >= 1 && flen <= sizeof(fbuf)); nb = hdlc_send_frame (c, fbuf, flen); num_bits += nb; numframe++; #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: flen=%d, nb=%d, num_bits=%d, numframe=%d\n", flen, nb, num_bits, numframe); #endif ax25_delete (pp); } /* * Need TXTAIL because we don't know exactly when the sound is done. */ post_flags = MS_TO_BITS(xmit_txtail[c] * 10, c) / 8; nb = hdlc_send_flags (c, post_flags, 1); num_bits += nb; #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: txtail=%d [*10], post_flags=%d, nb=%d, num_bits=%d\n", xmit_txtail[c], post_flags, nb, num_bits); #endif /* * While demodulating is CPU intensive, generating the tones is not. * Example: on the RPi, with 50% of the CPU taken with two receive * channels, a transmission of more than a second is generated in * about 40 mS of elapsed real time. */ audio_wait(ACHAN2ADEV(c)); /* * Ideally we should be here just about the time when the audio is ending. * However, the innards of "audio_wait" are not satisfactory in all cases. * * Calculate how long the frame(s) should take in milliseconds. */ duration = BITS_TO_MS(num_bits, c); /* * See how long it has been since PTT was turned on. * Wait additional time if necessary. */ time_now = dtime_now(); already = (int) ((time_now - time_ptt) * 1000.); wait_more = duration - already; #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: xmit duration=%d, %d already elapsed since PTT, wait %d more\n", duration, already, wait_more ); #endif if (wait_more > 0) { SLEEP_MS(wait_more); } else if (wait_more < -100) { /* If we run over by 10 mSec or so, it's nothing to worry about. */ /* However, if PTT is still on about 1/10 sec after audio */ /* should be done, something is wrong. */ /* Looks like a bug with the RPi audio system. Never an issue with Ubuntu. */ /* This runs over randomly sometimes. TODO: investigate more fully sometime. */ #ifndef __arm__ text_color_set(DW_COLOR_ERROR); dw_printf ("Transmit timing error: PTT is on %d mSec too long.\n", -wait_more); #endif } /* * Turn off transmitter. */ #if DEBUG text_color_set(DW_COLOR_DEBUG); time_now = dtime_now(); dw_printf ("xmit_thread: Turn off PTT now. Actual time on was %d mS, vs. %d desired\n", (int) ((time_now - time_ptt) * 1000.), duration); #endif ptt_set (OCTYPE_PTT, c, 0); } /* end xmit_ax25_frames */
static int sudoers_policy_open(unsigned int version, sudo_conv_t conversation, sudo_printf_t plugin_printf, char * const settings[], char * const user_info[], char * const envp[], char * const args[]) { volatile int sources = 0; sigaction_t sa; struct sudo_nss *nss; struct sudo_nss *nss_next; debug_decl(sudoers_policy_open, SUDO_DEBUG_PLUGIN) sudo_version = version; if (!sudo_conv) sudo_conv = conversation; if (!sudo_printf) sudo_printf = plugin_printf; /* Plugin args are only specified for API version 1.2 and higher. */ if (sudo_version < SUDO_API_MKVERSION(1, 2)) args = NULL; if (sigsetjmp(error_jmp, 1)) { /* called via error(), errorx() or log_fatal() */ rewind_perms(); debug_return_bool(-1); } bindtextdomain("sudoers", LOCALEDIR); /* * Signal setup: * Ignore keyboard-generated signals so the user cannot interrupt * us at some point and avoid the logging. * Install handler to wait for children when they exit. */ zero_bytes(&sa, sizeof(sa)); sigemptyset(&sa.sa_mask); sa.sa_flags = SA_RESTART; sa.sa_handler = SIG_IGN; (void) sigaction(SIGINT, &sa, &saved_sa_int); (void) sigaction(SIGQUIT, &sa, &saved_sa_quit); (void) sigaction(SIGTSTP, &sa, &saved_sa_tstp); sudo_setpwent(); sudo_setgrent(); /* Initialize environment functions (including replacements). */ env_init(envp); /* Setup defaults data structures. */ init_defaults(); /* Parse args, settings and user_info */ sudo_mode = deserialize_info(args, settings, user_info); init_vars(envp); /* XXX - move this later? */ /* Parse nsswitch.conf for sudoers order. */ snl = sudo_read_nss(); /* LDAP or NSS may modify the euid so we need to be root for the open. */ set_perms(PERM_INITIAL); set_perms(PERM_ROOT); /* Open and parse sudoers, set global defaults */ for (nss = snl->first; nss != NULL; nss = nss_next) { nss_next = nss->next; if (nss->open(nss) == 0 && nss->parse(nss) == 0) { sources++; if (nss->setdefs(nss) != 0) log_error(NO_STDERR, _("problem with defaults entries")); } else { tq_remove(snl, nss); } } if (sources == 0) { warningx(_("no valid sudoers sources found, quitting")); debug_return_bool(-1); } /* XXX - collect post-sudoers parse settings into a function */ /* * Initialize external group plugin, if any. */ if (def_group_plugin) { if (group_plugin_load(def_group_plugin) != true) def_group_plugin = NULL; } /* * Set runas passwd/group entries based on command line or sudoers. * Note that if runas_group was specified without runas_user we * defer setting runas_pw so the match routines know to ignore it. */ if (runas_group != NULL) { set_runasgr(runas_group); if (runas_user != NULL) set_runaspw(runas_user); } else set_runaspw(runas_user ? runas_user : def_runas_default); if (!update_defaults(SETDEF_RUNAS)) log_error(NO_STDERR, _("problem with defaults entries")); if (def_fqdn) set_fqdn(); /* deferred until after sudoers is parsed */ /* Set login class if applicable. */ set_loginclass(runas_pw ? runas_pw : sudo_user.pw); restore_perms(); debug_return_bool(true); }
static void * xmit_thread (void *arg) #endif { int c = (int)(long)arg; // channel number. packet_t pp; int p; int ok; /* * These are for timing of a transmission. * All are in usual unix time (seconds since 1/1/1970) but higher resolution */ while (1) { tq_wait_while_empty (c); #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread, channel %d: woke up\n", c); #endif for (p=0; p<TQ_NUM_PRIO; p++) { pp = tq_remove (c, p); #if DEBUG text_color_set(DW_COLOR_DEBUG); dw_printf ("xmit_thread: tq_remove(chan=%d, prio=%d) returned %p\n", c, p, pp); #endif if (pp != NULL) { /* * Wait for the channel to be clear. * For the high priority queue, begin transmitting immediately. * For the low priority queue, wait a random amount of time, in hopes * of minimizing collisions. */ ok = wait_for_clear_channel (c, (p==TQ_PRIO_0_HI), xmit_slottime[c], xmit_persist[c]); if (ok) { /* * Channel is clear and we have lock on output device. * * If destination is "SPEECH" send info part to speech synthesizer. * If destination is "MORSE" send as morse code. */ char dest[AX25_MAX_ADDR_LEN]; int ssid = 0; if (ax25_is_aprs (pp)) { ax25_get_addr_no_ssid(pp, AX25_DESTINATION, dest); ssid = ax25_get_ssid(pp, AX25_DESTINATION); } else { strlcpy (dest, "", sizeof(dest)); } if (strcmp(dest, "SPEECH") == 0) { xmit_speech (c, pp); } else if (strcmp(dest, "MORSE") == 0) { int wpm = ssid * 2; if (wpm == 0) wpm = MORSE_DEFAULT_WPM; // This is a bit of a hack so we don't respond too quickly for APRStt. // It will be sent in high priority queue while a beacon wouldn't. // Add a little delay so user has time release PTT after sending #. // This and default txdelay would give us a second. if (p == TQ_PRIO_0_HI) { //text_color_set(DW_COLOR_DEBUG); //dw_printf ("APRStt morse xmit delay hack...\n"); SLEEP_MS (700); } xmit_morse (c, pp, wpm); } else { xmit_ax25_frames (c, p, pp); } dw_mutex_unlock (&(audio_out_dev_mutex[ACHAN2ADEV(c)])); } else { /* * Timeout waiting for clear channel. * Discard the packet. * Display with ERROR color rather than XMIT color. */ char stemp[1024]; /* max size needed? */ int info_len; unsigned char *pinfo; text_color_set(DW_COLOR_ERROR); dw_printf ("Waited too long for clear channel. Discarding packet below.\n"); ax25_format_addrs (pp, stemp); info_len = ax25_get_info (pp, &pinfo); text_color_set(DW_COLOR_INFO); dw_printf ("[%d%c] ", c, p==TQ_PRIO_0_HI ? 'H' : 'L'); dw_printf ("%s", stemp); /* stations followed by : */ ax25_safe_print ((char *)pinfo, info_len, ! ax25_is_aprs(pp)); dw_printf ("\n"); ax25_delete (pp); } /* wait for clear channel. */ } /* for high priority then low priority */ } } return 0; /* unreachable but quiet the warning. */ } /* end xmit_thread */