/* * Set the process priority */ static void set_process_priority(void) { #ifdef DEBUG if (debug > 1) msyslog(LOG_DEBUG, "set_process_priority: %s: priority_done is <%d>", ((priority_done) ? "Leave priority alone" : "Attempt to set priority" ), priority_done); #endif /* DEBUG */ #if defined(HAVE_SCHED_SETSCHEDULER) if (!priority_done) { extern int config_priority_override, config_priority; int pmax, pmin; struct sched_param sched; pmax = sched_get_priority_max(SCHED_FIFO); sched.sched_priority = pmax; if ( config_priority_override ) { pmin = sched_get_priority_min(SCHED_FIFO); if ( config_priority > pmax ) sched.sched_priority = pmax; else if ( config_priority < pmin ) sched.sched_priority = pmin; else sched.sched_priority = config_priority; } if ( sched_setscheduler(0, SCHED_FIFO, &sched) == -1 ) msyslog(LOG_ERR, "sched_setscheduler(): %m"); else ++priority_done; } #endif /* HAVE_SCHED_SETSCHEDULER */ #if defined(HAVE_RTPRIO) # ifdef RTP_SET if (!priority_done) { struct rtprio srtp; srtp.type = RTP_PRIO_REALTIME; /* was: RTP_PRIO_NORMAL */ srtp.prio = 0; /* 0 (hi) -> RTP_PRIO_MAX (31,lo) */ if (rtprio(RTP_SET, getpid(), &srtp) < 0) msyslog(LOG_ERR, "rtprio() error: %m"); else ++priority_done; } # else /* not RTP_SET */ if (!priority_done) { if (rtprio(0, 120) < 0) msyslog(LOG_ERR, "rtprio() error: %m"); else ++priority_done; } # endif /* not RTP_SET */ #endif /* HAVE_RTPRIO */ #if defined(NTPD_PRIO) && NTPD_PRIO != 0 # ifdef HAVE_ATT_NICE if (!priority_done) { errno = 0; if (-1 == nice (NTPD_PRIO) && errno != 0) msyslog(LOG_ERR, "nice() error: %m"); else ++priority_done; } # endif /* HAVE_ATT_NICE */ # ifdef HAVE_BSD_NICE if (!priority_done) { if (-1 == setpriority(PRIO_PROCESS, 0, NTPD_PRIO)) msyslog(LOG_ERR, "setpriority() error: %m"); else ++priority_done; } # endif /* HAVE_BSD_NICE */ #endif /* NTPD_PRIO && NTPD_PRIO != 0 */ if (!priority_done) msyslog(LOG_ERR, "set_process_priority: No way found to improve our priority"); }
void *POSIX_Init( void *argument ) { uint32_t end_time; int status; int i; pthread_t threadId; pthread_attr_t attr; struct sched_param param; int policy; TEST_BEGIN(); /* Setup variables */ status = pthread_create( &threadId, NULL, Blocker, NULL ); rtems_test_assert( status == 0 ); status = pthread_mutex_init(&MutexID, NULL); rtems_test_assert( status == 0 ); status = pthread_cond_init(&CondID, NULL); rtems_test_assert( status == 0 ); /* Setup so threads are created with a high enough priority to preempt * as they get created. */ status = pthread_attr_init( &attr ); rtems_test_assert( status == 0 ); status = pthread_attr_setinheritsched( &attr, PTHREAD_EXPLICIT_SCHED ); rtems_test_assert( status == 0 ); status = pthread_attr_setschedpolicy( &attr, SCHED_FIFO ); rtems_test_assert( status == 0 ); param.sched_priority = sched_get_priority_max(SCHED_FIFO) / 2; status = pthread_attr_setschedparam( &attr, ¶m ); rtems_test_assert( status == 0 ); for ( i=0 ; i < N ; i++) { /* Threads will preempt as they are created, start up, and block */ status = pthread_create(&threadId, &attr, Blocker, NULL); rtems_test_assert( status == 0 ); } /* Now that all the threads have been created, adjust our priority * so we don't get preempted on broadcast. */ status = pthread_getschedparam(pthread_self(), &policy, ¶m); rtems_test_assert( status == 0 ); param.sched_priority = sched_get_priority_max(policy) - 1; status = pthread_setschedparam(pthread_self(), policy, ¶m); rtems_test_assert( status == 0 ); benchmark_timer_initialize(); status = pthread_cond_broadcast(&CondID); end_time = benchmark_timer_read(); rtems_test_assert( status == 0 ); put_time( "pthread_cond_broadcast: threads waiting no preempt", end_time, 1, 0, 0 ); TEST_END(); rtems_test_exit( 0 ); return NULL; }
int main( int argc, char * * argv ) { #ifdef LMMS_DEBUG_FPE // Enable exceptions for certain floating point results feenableexcept( FE_INVALID | FE_DIVBYZERO | FE_OVERFLOW | FE_UNDERFLOW); // Install the trap handler // register signal SIGFPE and signal handler signal(SIGFPE, signalHandler); #endif #ifdef LMMS_BUILD_WIN32 // Don't touch redirected streams here // GetStdHandle should be called before AttachConsole HANDLE hStdIn = GetStdHandle(STD_INPUT_HANDLE); HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE); HANDLE hStdErr = GetStdHandle(STD_ERROR_HANDLE); FILE *fIn, *fOut, *fErr; // Enable console output if available if (AttachConsole(ATTACH_PARENT_PROCESS)) { if (!hStdIn) { freopen_s(&fIn, "CONIN$", "r", stdin); } if (!hStdOut) { freopen_s(&fOut, "CONOUT$", "w", stdout); } if (!hStdErr) { freopen_s(&fErr, "CONOUT$", "w", stderr); } } // Make Qt's debug message handlers work qInstallMessageHandler(consoleMessageHandler); #endif // initialize memory managers NotePlayHandleManager::init(); // intialize RNG srand( getpid() + time( 0 ) ); disable_denormals(); bool coreOnly = false; bool fullscreen = true; bool exitAfterImport = false; bool allowRoot = false; bool renderLoop = false; bool renderTracks = false; QString fileToLoad, fileToImport, renderOut, profilerOutputFile, configFile; // first of two command-line parsing stages for( int i = 1; i < argc; ++i ) { QString arg = argv[i]; if( arg == "--help" || arg == "-h" || arg == "--version" || arg == "-v" || arg == "render" || arg == "--render" || arg == "-r" ) { coreOnly = true; } else if( arg == "rendertracks" || arg == "--rendertracks" ) { coreOnly = true; renderTracks = true; } else if( arg == "--allowroot" ) { allowRoot = true; } else if( arg == "--geometry" || arg == "-geometry") { if( arg == "--geometry" ) { // Delete the first "-" so Qt recognize the option strcpy(argv[i], "-geometry"); } // option -geometry is filtered by Qt later, // so we need to check its presence now to // determine, if the application should run in // fullscreen mode (default, no -geometry given). fullscreen = false; } } #if !defined(LMMS_BUILD_WIN32) && !defined(LMMS_BUILD_HAIKU) if ( ( getuid() == 0 || geteuid() == 0 ) && !allowRoot ) { printf( "LMMS cannot be run as root.\nUse \"--allowroot\" to override.\n\n" ); return EXIT_FAILURE; } #endif #ifdef LMMS_BUILD_LINUX // don't let OS steal the menu bar. FIXME: only effective on Qt4 QCoreApplication::setAttribute( Qt::AA_DontUseNativeMenuBar ); #endif #if QT_VERSION >= QT_VERSION_CHECK(5, 6, 0) QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling); #endif QCoreApplication * app = coreOnly ? new QCoreApplication( argc, argv ) : new MainApplication( argc, argv ); Mixer::qualitySettings qs( Mixer::qualitySettings::Mode_HighQuality ); OutputSettings os( 44100, OutputSettings::BitRateSettings(160, false), OutputSettings::Depth_16Bit, OutputSettings::StereoMode_JointStereo ); ProjectRenderer::ExportFileFormats eff = ProjectRenderer::WaveFile; // second of two command-line parsing stages for( int i = 1; i < argc; ++i ) { QString arg = argv[i]; if( arg == "--version" || arg == "-v" ) { printVersion( argv[0] ); return EXIT_SUCCESS; } else if( arg == "--help" || arg == "-h" ) { printHelp(); return EXIT_SUCCESS; } else if( arg == "upgrade" || arg == "--upgrade" || arg == "-u") { ++i; if( i == argc ) { return noInputFileError(); } DataFile dataFile( QString::fromLocal8Bit( argv[i] ) ); if( argc > i+1 ) // output file specified { dataFile.writeFile( QString::fromLocal8Bit( argv[i+1] ) ); } else // no output file specified; use stdout { QTextStream ts( stdout ); dataFile.write( ts ); fflush( stdout ); } return EXIT_SUCCESS; } else if( arg == "--allowroot" ) { // Ignore, processed earlier #ifdef LMMS_BUILD_WIN32 if( allowRoot ) { printf( "\nOption \"--allowroot\" will be ignored on this platform.\n\n" ); } #endif } else if( arg == "dump" || arg == "--dump" || arg == "-d" ) { ++i; if( i == argc ) { return noInputFileError(); } QFile f( QString::fromLocal8Bit( argv[i] ) ); f.open( QIODevice::ReadOnly ); QString d = qUncompress( f.readAll() ); printf( "%s\n", d.toUtf8().constData() ); return EXIT_SUCCESS; } else if( arg == "render" || arg == "--render" || arg == "-r" || arg == "rendertracks" || arg == "--rendertracks" ) { ++i; if( i == argc ) { return noInputFileError(); } fileToLoad = QString::fromLocal8Bit( argv[i] ); renderOut = fileToLoad; } else if( arg == "--loop" || arg == "-l" ) { renderLoop = true; } else if( arg == "--output" || arg == "-o" ) { ++i; if( i == argc ) { return usageError( "No output file specified" ); } renderOut = QString::fromLocal8Bit( argv[i] ); } else if( arg == "--format" || arg == "-f" ) { ++i; if( i == argc ) { return usageError( "No output format specified" ); } const QString ext = QString( argv[i] ); if( ext == "wav" ) { eff = ProjectRenderer::WaveFile; } #ifdef LMMS_HAVE_OGGVORBIS else if( ext == "ogg" ) { eff = ProjectRenderer::OggFile; } #endif #ifdef LMMS_HAVE_MP3LAME else if( ext == "mp3" ) { eff = ProjectRenderer::MP3File; } #endif else if (ext == "flac") { eff = ProjectRenderer::FlacFile; } else { return usageError( QString( "Invalid output format %1" ).arg( argv[i] ) ); } } else if( arg == "--samplerate" || arg == "-s" ) { ++i; if( i == argc ) { return usageError( "No samplerate specified" ); } sample_rate_t sr = QString( argv[i] ).toUInt(); if( sr >= 44100 && sr <= 192000 ) { os.setSampleRate(sr); } else { return usageError( QString( "Invalid samplerate %1" ).arg( argv[i] ) ); } } else if( arg == "--bitrate" || arg == "-b" ) { ++i; if( i == argc ) { return usageError( "No bitrate specified" ); } int br = QString( argv[i] ).toUInt(); if( br >= 64 && br <= 384 ) { OutputSettings::BitRateSettings bitRateSettings = os.getBitRateSettings(); bitRateSettings.setBitRate(br); os.setBitRateSettings(bitRateSettings); } else { return usageError( QString( "Invalid bitrate %1" ).arg( argv[i] ) ); } } else if( arg == "--mode" || arg == "-m" ) { ++i; if( i == argc ) { return usageError( "No stereo mode specified" ); } QString const mode( argv[i] ); if( mode == "s" ) { os.setStereoMode(OutputSettings::StereoMode_Stereo); } else if( mode == "j" ) { os.setStereoMode(OutputSettings::StereoMode_JointStereo); } else if( mode == "m" ) { os.setStereoMode(OutputSettings::StereoMode_Mono); } else { return usageError( QString( "Invalid stereo mode %1" ).arg( argv[i] ) ); } } else if( arg =="--float" || arg == "-a" ) { os.setBitDepth(OutputSettings::Depth_32Bit); } else if( arg == "--interpolation" || arg == "-i" ) { ++i; if( i == argc ) { return usageError( "No interpolation method specified" ); } const QString ip = QString( argv[i] ); if( ip == "linear" ) { qs.interpolation = Mixer::qualitySettings::Interpolation_Linear; } else if( ip == "sincfastest" ) { qs.interpolation = Mixer::qualitySettings::Interpolation_SincFastest; } else if( ip == "sincmedium" ) { qs.interpolation = Mixer::qualitySettings::Interpolation_SincMedium; } else if( ip == "sincbest" ) { qs.interpolation = Mixer::qualitySettings::Interpolation_SincBest; } else { return usageError( QString( "Invalid interpolation method %1" ).arg( argv[i] ) ); } } else if( arg == "--oversampling" || arg == "-x" ) { ++i; if( i == argc ) { return usageError( "No oversampling specified" ); } int o = QString( argv[i] ).toUInt(); switch( o ) { case 1: qs.oversampling = Mixer::qualitySettings::Oversampling_None; break; case 2: qs.oversampling = Mixer::qualitySettings::Oversampling_2x; break; case 4: qs.oversampling = Mixer::qualitySettings::Oversampling_4x; break; case 8: qs.oversampling = Mixer::qualitySettings::Oversampling_8x; break; default: return usageError( QString( "Invalid oversampling %1" ).arg( argv[i] ) ); } } else if( arg == "--import" ) { ++i; if( i == argc ) { return usageError( "No file specified for importing" ); } fileToImport = QString::fromLocal8Bit( argv[i] ); // exit after import? (only for debugging) if( QString( argv[i + 1] ) == "-e" ) { exitAfterImport = true; ++i; } } else if( arg == "--profile" || arg == "-p" ) { ++i; if( i == argc ) { return usageError( "No profile specified" ); } profilerOutputFile = QString::fromLocal8Bit( argv[i] ); } else if( arg == "--config" || arg == "-c" ) { ++i; if( i == argc ) { return usageError( "No configuration file specified" ); } configFile = QString::fromLocal8Bit( argv[i] ); } else { if( argv[i][0] == '-' ) { return usageError( QString( "Invalid option %1" ).arg( argv[i] ) ); } fileToLoad = QString::fromLocal8Bit( argv[i] ); } } // Test file argument before continuing if( !fileToLoad.isEmpty() ) { fileCheck( fileToLoad ); } else if( !fileToImport.isEmpty() ) { fileCheck( fileToImport ); } ConfigManager::inst()->loadConfigFile(configFile); // Hidden settings MixHelpers::setNaNHandler( ConfigManager::inst()->value( "app", "nanhandler", "1" ).toInt() ); // set language QString pos = ConfigManager::inst()->value( "app", "language" ); if( pos.isEmpty() ) { pos = QLocale::system().name().left( 2 ); } #ifdef LMMS_BUILD_WIN32 #undef QT_TRANSLATIONS_DIR #define QT_TRANSLATIONS_DIR ConfigManager::inst()->localeDir() #endif #ifdef QT_TRANSLATIONS_DIR // load translation for Qt-widgets/-dialogs loadTranslation( QString( "qt_" ) + pos, QString( QT_TRANSLATIONS_DIR ) ); #endif // load actual translation for LMMS loadTranslation( pos ); // try to set realtime priority #ifdef LMMS_BUILD_LINUX #ifdef LMMS_HAVE_SCHED_H #ifndef __OpenBSD__ struct sched_param sparam; sparam.sched_priority = ( sched_get_priority_max( SCHED_FIFO ) + sched_get_priority_min( SCHED_FIFO ) ) / 2; if( sched_setscheduler( 0, SCHED_FIFO, &sparam ) == -1 ) { printf( "Notice: could not set realtime priority.\n" ); } #endif #endif #endif #ifdef LMMS_BUILD_WIN32 if( !SetPriorityClass( GetCurrentProcess(), HIGH_PRIORITY_CLASS ) ) { printf( "Notice: could not set high priority.\n" ); } #endif #if _POSIX_C_SOURCE >= 1 || _XOPEN_SOURCE || _POSIX_SOURCE struct sigaction sa; sa.sa_handler = SIG_IGN; sa.sa_flags = SA_SIGINFO; if ( sigemptyset( &sa.sa_mask ) ) { fprintf( stderr, "Signal initialization failed.\n" ); } if ( sigaction( SIGPIPE, &sa, NULL ) ) { fprintf( stderr, "Signal initialization failed.\n" ); } #endif bool destroyEngine = false; // if we have an output file for rendering, just render the song // without starting the GUI if( !renderOut.isEmpty() ) { Engine::init( true ); destroyEngine = true; printf( "Loading project...\n" ); Engine::getSong()->loadProject( fileToLoad ); if( Engine::getSong()->isEmpty() ) { printf("The project %s is empty, aborting!\n", fileToLoad.toUtf8().constData() ); exit( EXIT_FAILURE ); } printf( "Done\n" ); Engine::getSong()->setExportLoop( renderLoop ); // when rendering multiple tracks, renderOut is a directory // otherwise, it is a file, so we need to append the file extension if ( !renderTracks ) { renderOut = baseName( renderOut ) + ProjectRenderer::getFileExtensionFromFormat(eff); } // create renderer RenderManager * r = new RenderManager( qs, os, eff, renderOut ); QCoreApplication::instance()->connect( r, SIGNAL( finished() ), SLOT( quit() ) ); // timer for progress-updates QTimer * t = new QTimer( r ); r->connect( t, SIGNAL( timeout() ), SLOT( updateConsoleProgress() ) ); t->start( 200 ); if( profilerOutputFile.isEmpty() == false ) { Engine::mixer()->profiler().setOutputFile( profilerOutputFile ); } // start now! if ( renderTracks ) { r->renderTracks(); } else { r->renderProject(); } } else // otherwise, start the GUI { new GuiApplication(); // re-intialize RNG - shared libraries might have srand() or // srandom() calls in their init procedure srand( getpid() + time( 0 ) ); // recover a file? QString recoveryFile = ConfigManager::inst()->recoveryFile(); bool recoveryFilePresent = QFileInfo( recoveryFile ).exists() && QFileInfo( recoveryFile ).isFile(); bool autoSaveEnabled = ConfigManager::inst()->value( "ui", "enableautosave" ).toInt(); if( recoveryFilePresent ) { QMessageBox mb; mb.setWindowTitle( MainWindow::tr( "Project recovery" ) ); mb.setText( QString( "<html>" "<p style=\"margin-left:6\">%1</p>" "<table cellpadding=\"3\">" " <tr>" " <td><b>%2</b></td>" " <td>%3</td>" " </tr>" " <tr>" " <td><b>%4</b></td>" " <td>%5</td>" " </tr>" "</table>" "</html>" ).arg( MainWindow::tr( "There is a recovery file present. " "It looks like the last session did not end " "properly or another instance of LMMS is " "already running. Do you want to recover the " "project of this session?" ), MainWindow::tr( "Recover" ), MainWindow::tr( "Recover the file. Please don't run " "multiple instances of LMMS when you do this." ), MainWindow::tr( "Discard" ), MainWindow::tr( "Launch a default session and delete " "the restored files. This is not reversible." ) ) ); mb.setIcon( QMessageBox::Warning ); mb.setWindowIcon( embed::getIconPixmap( "icon_small" ) ); mb.setWindowFlags( Qt::WindowCloseButtonHint ); QPushButton * recover; QPushButton * discard; QPushButton * exit; // setting all buttons to the same roles allows us // to have a custom layout discard = mb.addButton( MainWindow::tr( "Discard" ), QMessageBox::AcceptRole ); recover = mb.addButton( MainWindow::tr( "Recover" ), QMessageBox::AcceptRole ); // have a hidden exit button exit = mb.addButton( "", QMessageBox::RejectRole); exit->setVisible(false); // set icons recover->setIcon( embed::getIconPixmap( "recover" ) ); discard->setIcon( embed::getIconPixmap( "discard" ) ); mb.setDefaultButton( recover ); mb.setEscapeButton( exit ); mb.exec(); if( mb.clickedButton() == discard ) { gui->mainWindow()->sessionCleanup(); } else if( mb.clickedButton() == recover ) // Recover { fileToLoad = recoveryFile; gui->mainWindow()->setSession( MainWindow::SessionState::Recover ); } else // Exit { return 0; } } // first show the Main Window and then try to load given file // [Settel] workaround: showMaximized() doesn't work with // FVWM2 unless the window is already visible -> show() first gui->mainWindow()->show(); if( fullscreen ) { gui->mainWindow()->showMaximized(); } // Handle macOS-style FileOpen QEvents QString queuedFile = static_cast<MainApplication *>( app )->queuedFile(); if ( !queuedFile.isEmpty() ) { fileToLoad = queuedFile; } if( !fileToLoad.isEmpty() ) { if( fileToLoad == recoveryFile ) { Engine::getSong()->createNewProjectFromTemplate( fileToLoad ); } else { Engine::getSong()->loadProject( fileToLoad ); } } else if( !fileToImport.isEmpty() ) { ImportFilter::import( fileToImport, Engine::getSong() ); if( exitAfterImport ) { return EXIT_SUCCESS; } } // If enabled, open last project if there is one. Else, create // a new one. else if( ConfigManager::inst()-> value( "app", "openlastproject" ).toInt() && !ConfigManager::inst()-> recentlyOpenedProjects().isEmpty() && !recoveryFilePresent ) { QString f = ConfigManager::inst()-> recentlyOpenedProjects().first(); QFileInfo recentFile( f ); if ( recentFile.exists() && recentFile.suffix().toLower() != "mpt" ) { Engine::getSong()->loadProject( f ); } else { Engine::getSong()->createNewProject(); } } else { Engine::getSong()->createNewProject(); } // Finally we start the auto save timer and also trigger the // autosave one time as recover.mmp is a signal to possible other // instances of LMMS. if( autoSaveEnabled ) { gui->mainWindow()->autoSaveTimerReset(); } } const int ret = app->exec(); delete app; if( destroyEngine ) { Engine::destroy(); } // ProjectRenderer::updateConsoleProgress() doesn't return line after render if( coreOnly ) { printf( "\n" ); } #ifdef LMMS_BUILD_WIN32 // Cleanup console HWND hConsole = GetConsoleWindow(); if (hConsole) { SendMessage(hConsole, WM_CHAR, (WPARAM)VK_RETURN, (LPARAM)0); FreeConsole(); } #endif return ret; }
/* The main test function. */ int main(int argc, char * argv[]) { int ret, param, status; pid_t child, ctl; struct sched_param sp; /* Initialize output */ output_init(); /* Change process policy and parameters */ sp.sched_priority = param = sched_get_priority_max(POLICY); if (sp.sched_priority == -1) { UNRESOLVED(errno, "Failed to get max priority value"); } ret = sched_setscheduler(0, POLICY, &sp); if (ret == -1) { UNRESOLVED(errno, "Failed to change process scheduling policy"); } /* Create the child */ child = fork(); if (child == -1) { UNRESOLVED(errno, "Failed to fork"); } /* child */ if (child == 0) { /* Check the scheduling policy */ ret = sched_getscheduler(0); if (ret == -1) { UNRESOLVED(errno, "Failed to read scheduling policy in child"); } if (ret != POLICY) { FAILED("The scheduling policy was not inherited"); } ret = sched_getparam(0, &sp); if (ret != 0) { UNRESOLVED(errno, "Failed to read scheduling parameter in child"); } if (sp.sched_priority != param) { FAILED("The scheduling parameter was not inherited"); } /* We're done */ exit(PTS_PASS); } /* Parent joins the child */ ctl = waitpid(child, &status, 0); if (ctl != child) { UNRESOLVED(errno, "Waitpid returned the wrong PID"); } if (!WIFEXITED(status) || (WEXITSTATUS(status) != PTS_PASS)) { FAILED("Child exited abnormally"); } /* Test passed */ #if VERBOSE > 0 output("Test passed\n"); #endif PASSED; }
static int vlc_clone_attr (vlc_thread_t *th, pthread_attr_t *attr, void *(*entry) (void *), void *data, int priority) { int ret; /* Block the signals that signals interface plugin handles. * If the LibVLC caller wants to handle some signals by itself, it should * block these before whenever invoking LibVLC. And it must obviously not * start the VLC signals interface plugin. * * LibVLC will normally ignore any interruption caused by an asynchronous * signal during a system call. But there may well be some buggy cases * where it fails to handle EINTR (bug reports welcome). Some underlying * libraries might also not handle EINTR properly. */ sigset_t oldset; { sigset_t set; sigemptyset (&set); sigdelset (&set, SIGHUP); sigaddset (&set, SIGINT); sigaddset (&set, SIGQUIT); sigaddset (&set, SIGTERM); sigaddset (&set, SIGPIPE); /* We don't want this one, really! */ pthread_sigmask (SIG_BLOCK, &set, &oldset); } #if defined (_POSIX_PRIORITY_SCHEDULING) && (_POSIX_PRIORITY_SCHEDULING >= 0) \ && defined (_POSIX_THREAD_PRIORITY_SCHEDULING) \ && (_POSIX_THREAD_PRIORITY_SCHEDULING >= 0) if (rt_priorities) { struct sched_param sp = { .sched_priority = priority + rt_offset, }; int policy; if (sp.sched_priority <= 0) sp.sched_priority += sched_get_priority_max (policy = SCHED_OTHER); else sp.sched_priority += sched_get_priority_min (policy = SCHED_RR); pthread_attr_setschedpolicy (attr, policy); pthread_attr_setschedparam (attr, &sp); } #else (void) priority; #endif /* The thread stack size. * The lower the value, the less address space per thread, the highest * maximum simultaneous threads per process. Too low values will cause * stack overflows and weird crashes. Set with caution. Also keep in mind * that 64-bits platforms consume more stack than 32-bits one. * * Thanks to on-demand paging, thread stack size only affects address space * consumption. In terms of memory, threads only use what they need * (rounded up to the page boundary). * * For example, on Linux i386, the default is 2 mega-bytes, which supports * about 320 threads per processes. */ #define VLC_STACKSIZE (128 * sizeof (void *) * 1024) #ifdef VLC_STACKSIZE ret = pthread_attr_setstacksize (attr, VLC_STACKSIZE); assert (ret == 0); /* fails iif VLC_STACKSIZE is invalid */ #endif ret = pthread_create (th, attr, entry, data); pthread_sigmask (SIG_SETMASK, &oldset, NULL); pthread_attr_destroy (attr); return ret; } /** * Creates and starts new thread. * * The thread must be <i>joined</i> with vlc_join() to reclaim resources * when it is not needed anymore. * * @param th [OUT] pointer to write the handle of the created thread to * (mandatory, must be non-NULL) * @param entry entry point for the thread * @param data data parameter given to the entry point * @param priority thread priority value * @return 0 on success, a standard error code on error. */ int vlc_clone (vlc_thread_t *th, void *(*entry) (void *), void *data, int priority) { pthread_attr_t attr; pthread_attr_init (&attr); return vlc_clone_attr (th, &attr, entry, data, priority); }
/* * The main method initializes the gpios and starts a thread and checks the content * of the files. */ int main() { int res; int count, statusBefore, statusAfter, sensorBefore, sensorAfter; struct timespec sleeptime, result, sensorResult; struct timespec before, measureSensorBefore; struct timespec after, measureSensorAfter; uint16_t distance; sleeptime.tv_sec = 0; sleeptime.tv_nsec = 000010000L; // sleep 10µs int maxPriority; int status; // get max available priority maxPriority = sched_get_priority_max(SCHED_FIFO); if (maxPriority == -1) { perror("Could not determine the maximum priority available."); exit(EXIT_FAILURE); } // set scheduler to SCHED_FIFO and priority to max priority struct sched_param sched; sched.sched_priority = maxPriority; status = sched_setscheduler(0, SCHED_FIFO, &sched); if (status) { perror("ERROR: Could not set real time priority (are you running this as root?)"); exit(EXIT_FAILURE); } // TODO: Add comment for the above sleeptime: How much µs / ms whatever is this? -> use human readable unit here! /*signal(SIGINT, sigfunc); */ wiringPiSetupGpio(); pinMode(GPIO_TRIGGER, OUTPUT); pinMode(GPIO_ECHO, INPUT); statusBefore = clock_gettime(CLOCK_MONOTONIC, &before); digitalWrite(GPIO_TRIGGER, 1); if(clock_nanosleep(CLOCK_MONOTONIC, 0, &sleeptime, NULL)) { perror("nanosleep failed\n"); exit(EXIT_FAILURE); } digitalWrite(GPIO_TRIGGER, 0); while(1) { if(digitalRead(GPIO_ECHO) == 1) { sensorBefore = clock_gettime(CLOCK_MONOTONIC, &measureSensorBefore); break; } } while(1) { if(digitalRead(GPIO_ECHO) == 0) { sensorAfter = clock_gettime(CLOCK_MONOTONIC, &measureSensorAfter); break; } } /* A bit of theory: * Max distance of ultrasonic sensor: about 3m * -> So the max time for the sound to travel to a barrier * and back for this distance is (at 19.2 degree celsius): * 6m / 343m/s = 0.017492711s = 17492711ns * => max number in result.tv_nsec is 17492711ns * * 17492711 * 343 = 5999999873 ==> this is the max number which must be * stored in the meantime during the calculation. * Max no to be stored: 5999999873 * Max no in long : 4294967295 * --> so we need to use an usigned *long long* in the following.. */ sensorResult = diffTime(measureSensorBefore, measureSensorAfter); distance = (uint64_t) sensorResult.tv_nsec * 343 / 1000000 / 2; statusAfter = clock_gettime(CLOCK_MONOTONIC, &after); result = diffTime(before, after); printf("seconds: %ld nanoseconds %ld\n", result.tv_sec, result.tv_nsec); printf("Result: %hu\n\n", distance); delay(20); return(EXIT_SUCCESS); }
bool OThread::Start(void *pParam, int Priority, int affinity) { if(m_bRunning) return true; m_pParam = pParam; m_bShutdown = false; int max_priority; int min_priority; int mid_priority; int min_max_diff; int min_max_diff_quarter; struct sched_param SchedVal; int iRetVal; pthread_attr_t attr; pthread_attr_init(&attr); iRetVal = pthread_attr_setschedpolicy(&attr, SCHED_OTHER); if(iRetVal != 0) return false; max_priority = sched_get_priority_max(SCHED_OTHER); min_priority = sched_get_priority_min(SCHED_OTHER); min_max_diff = max_priority - min_priority; mid_priority = (min_max_diff / 2) + min_priority; min_max_diff_quarter = min_max_diff / 4; switch(Priority) { case THREAD_PRIORITY_ABOVE_NORMAL: SchedVal.sched_priority = max_priority - min_max_diff_quarter; break; case THREAD_PRIORITY_BELOW_NORMAL: SchedVal.sched_priority = min_priority + min_max_diff_quarter; break; case THREAD_PRIORITY_HIGHEST: case THREAD_PRIORITY_TIME_CRITICAL: SchedVal.sched_priority = max_priority; break; case THREAD_PRIORITY_IDLE: SchedVal.sched_priority = min_priority; break; case THREAD_PRIORITY_NORMAL: default: SchedVal.sched_priority = mid_priority; break; } if(SchedVal.sched_priority < min_priority) SchedVal.sched_priority = min_priority; if(SchedVal.sched_priority > max_priority) SchedVal.sched_priority = max_priority; iRetVal = pthread_attr_setschedparam(&attr, &SchedVal); if(iRetVal != 0) return false; iRetVal = pthread_create(&m_thread, NULL, CThreadRunFunction, this); if(iRetVal != 0) return false; m_bRunning = true; return true; }
/** * \brief 쓰레드를 시작 * * \param priority 우선순위 * * \return 0:ok, -1:error */ int Thread::start(Priority priority/*=InheritPriority*/) { setPriority(priority); d->stop = false; #ifndef WIN32 pthread_attr_t attr; pthread_attr_init(&attr); //does not work pthread_join with PTHRAD_CREATE_DETACHED //pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); if (d->priority == InheritPriority) { pthread_attr_setinheritsched(&attr, PTHREAD_INHERIT_SCHED); } else { int prio; int schedPolicy; if (pthread_attr_getschedpolicy(&attr, &schedPolicy) == 0) { int prioMin = sched_get_priority_min(schedPolicy); int prioMax = sched_get_priority_max(schedPolicy); if (prioMin != -1 && prioMax != -1) { if (d->priority == IdlePriority) prio = prioMin; else if (d->priority == TimeCriticalPriority) prio = prioMax; else { prio = (((prioMax - prioMin) / TimeCriticalPriority) * d->priority) + prioMin; prio = std::max(prioMin, std::min(prioMax, prio)); } sched_param sp; sp.sched_priority = prio; if (pthread_attr_setinheritsched(&attr, PTHREAD_EXPLICIT_SCHED) != 0 || pthread_attr_setschedpolicy(&attr, schedPolicy) != 0 || pthread_attr_setschedparam(&attr, &sp) != 0) { pthread_attr_setinheritsched(&attr, PTHREAD_INHERIT_SCHED); } } //if (prioMin != -1 && prioMax != -1) } //if (pthread_attr_getschedpolicy(&attr, &schedPolicy) == 0) } int n = ::pthread_create(&d->handle, &attr, Thread::run2, this); if (n == EPERM) { // permission error pthread_attr_setinheritsched(&attr, PTHREAD_INHERIT_SCHED); n = pthread_create(&d->handle, &attr, Thread::run2, this); } pthread_attr_destroy(&attr); if (n) { return -1; } #else unsigned int thrdAddr = 0; d->handle = (HANDLE)_beginthreadex(NULL,0,Thread::run2,this,0,&thrdAddr); if (d->handle == 0) return -1; SetThreadPriority(d->handle,THREAD_PRIORITY_BELOW_NORMAL); #endif return 0; }
DirectThread * direct_thread_create( DirectThreadType thread_type, DirectThreadMainFunc thread_main, void *arg, const char *name ) { DirectThread *thread; pthread_attr_t attr; struct sched_param param; int policy; int priority; size_t stack_size; D_ASSERT( thread_main != NULL ); D_ASSERT( name != NULL ); D_DEBUG_AT( Direct_Thread, "%s( %s, %p(%p), '%s' )\n", __FUNCTION__, direct_thread_type_name(thread_type), thread_main, arg, name ); /* Create the key for the TSD (thread specific data). */ pthread_mutex_lock( &key_lock ); if (thread_key == -1) pthread_key_create( &thread_key, NULL ); pthread_mutex_unlock( &key_lock ); /* Allocate thread structure. */ thread = D_CALLOC( 1, sizeof(DirectThread) ); if (!thread) { D_OOM(); return NULL; } /* Write thread information to structure. */ thread->name = D_STRDUP( name ); thread->type = thread_type; thread->main = thread_main; thread->arg = arg; /* Initialize to -1 for synchronization. */ thread->thread = (pthread_t) -1; thread->tid = (pid_t) -1; /* Initialize mutex and condition. */ direct_util_recursive_pthread_mutex_init( &thread->lock ); pthread_cond_init( &thread->cond, NULL ); D_MAGIC_SET( thread, DirectThread ); /* Initialize scheduling and other parameters. */ pthread_attr_init( &attr ); pthread_attr_setinheritsched( &attr, PTHREAD_EXPLICIT_SCHED ); /* Select scheduler. */ switch (direct_config->thread_scheduler) { case DCTS_FIFO: policy = SCHED_FIFO; break; case DCTS_RR: policy = SCHED_RR; break; default: policy = SCHED_OTHER; break; } if (pthread_attr_setschedpolicy( &attr, policy )) D_PERROR( "Direct/Thread: Could not set scheduling policy to %s!\n", direct_thread_policy_name(policy) ); /* Read (back) value. */ pthread_attr_getschedpolicy( &attr, &policy ); /* Select priority. */ switch (thread->type) { case DTT_CLEANUP: case DTT_INPUT: case DTT_OUTPUT: case DTT_MESSAGING: case DTT_CRITICAL: priority = thread->type * direct_config->thread_priority_scale / 100; break; default: priority = direct_config->thread_priority; break; } D_DEBUG_AT( Direct_ThreadInit, " -> %s (%d) [%d;%d]\n", direct_thread_policy_name(policy), priority, sched_get_priority_min( policy ), sched_get_priority_max( policy ) ); if (priority < sched_get_priority_min( policy )) priority = sched_get_priority_min( policy ); if (priority > sched_get_priority_max( policy )) priority = sched_get_priority_max( policy ); param.sched_priority = priority; if (pthread_attr_setschedparam( &attr, ¶m )) D_PERROR( "Direct/Thread: Could not set scheduling priority to %d!\n", priority ); /* Select stack size? */ if (direct_config->thread_stack_size > 0) { if (pthread_attr_setstacksize( &attr, direct_config->thread_stack_size )) D_PERROR( "Direct/Thread: Could not set stack size to %d!\n", direct_config->thread_stack_size ); } /* Read (back) value. */ pthread_attr_getstacksize( &attr, &stack_size ); /* Lock the thread mutex. */ D_DEBUG_AT( Direct_ThreadInit, " -> locking...\n" ); pthread_mutex_lock( &thread->lock ); /* Create and run the thread. */ D_DEBUG_AT( Direct_ThreadInit, " -> creating...\n" ); pthread_create( &thread->thread, &attr, direct_thread_main, thread ); pthread_attr_destroy( &attr ); pthread_getschedparam( thread->thread, &policy, ¶m ); D_INFO( "Direct/Thread: Started '%s' (%d) [%s %s/%s %d/%d] <%zu>...\n", name, thread->tid, direct_thread_type_name(thread_type), direct_thread_policy_name(policy), direct_thread_scheduler_name(direct_config->thread_scheduler), param.sched_priority, priority, stack_size ); #ifdef DIRECT_THREAD_WAIT_INIT /* Wait for completion of the thread's initialization. */ while (!thread->init) { D_DEBUG_AT( Direct_ThreadInit, " -> waiting...\n" ); pthread_cond_wait( &thread->cond, &thread->lock ); } D_DEBUG_AT( Direct_ThreadInit, " -> ...thread is running.\n" ); #endif /* Unlock the thread mutex. */ D_DEBUG_AT( Direct_ThreadInit, " -> unlocking...\n" ); pthread_mutex_unlock( &thread->lock ); D_DEBUG_AT( Direct_ThreadInit, " -> returning %p\n", thread ); return thread; }
int main(int argc, char **argv) { int i, len; double eval, clk; long long ncycles_ref, counter; double eptime; double add_delay; struct cfg cf; char buf[256]; struct recfilter loop_error; struct PFD phase_detector; useconds_t usleep_time; struct sched_param sparam; #if RTPP_DEBUG double sleep_time, filter_lastval; #endif memset(&cf, 0, sizeof(cf)); cf.stable = malloc(sizeof(struct rtpp_cfg_stable)); if (cf.stable == NULL) { err(1, "can't allocate memory for the struct rtpp_cfg_stable"); /* NOTREACHED */ } memset(cf.stable, '\0', sizeof(struct rtpp_cfg_stable)); cf.stable->ctrl_socks = malloc(sizeof(struct rtpp_list)); if (cf.stable->ctrl_socks == NULL) { err(1, "can't allocate memory for the struct rtpp_cfg_stable"); /* NOTREACHED */ } memset(cf.stable->ctrl_socks, '\0', sizeof(struct rtpp_list)); RTPP_LIST_RESET(cf.stable->ctrl_socks); init_config(&cf, argc, argv); seedrandom(); cf.stable->sessions_ht = rtpp_hash_table_ctor(); if (cf.stable->sessions_ht == NULL) { err(1, "can't allocate memory for the hash table"); /* NOTREACHED */ } cf.stable->rtpp_stats = rtpp_stats_ctor(); if (cf.stable->rtpp_stats == NULL) { err(1, "can't allocate memory for the stats data"); /* NOTREACHED */ } init_port_table(&cf); if (rtpp_controlfd_init(&cf) != 0) { err(1, "can't inilialize control socket%s", cf.stable->ctrl_socks->len > 1 ? "s" : ""); } if (cf.stable->nodaemon == 0) { if (rtpp_daemon(0, 0) == -1) err(1, "can't switch into daemon mode"); /* NOTREACHED */ } if (rtpp_notify_init() != 0) errx(1, "can't start notification thread"); cf.stable->glog = rtpp_log_open(cf.stable, "rtpproxy", NULL, LF_REOPEN); rtpp_log_setlevel(cf.stable->glog, cf.stable->log_level); _sig_cf = &cf; atexit(ehandler); rtpp_log_write(RTPP_LOG_INFO, cf.stable->glog, "rtpproxy started, pid %d", getpid()); i = open(cf.stable->pid_file, O_WRONLY | O_CREAT | O_TRUNC, DEFFILEMODE); if (i >= 0) { len = sprintf(buf, "%u\n", (unsigned int)getpid()); write(i, buf, len); close(i); } else { rtpp_log_ewrite(RTPP_LOG_ERR, cf.stable->glog, "can't open pidfile for writing"); } signal(SIGHUP, sighup); signal(SIGINT, fatsignal); signal(SIGKILL, fatsignal); signal(SIGPIPE, SIG_IGN); signal(SIGTERM, fatsignal); signal(SIGXCPU, fatsignal); signal(SIGXFSZ, fatsignal); signal(SIGVTALRM, fatsignal); signal(SIGPROF, fatsignal); signal(SIGUSR1, fatsignal); signal(SIGUSR2, fatsignal); if (cf.stable->sched_policy != SCHED_OTHER) { sparam.sched_priority = sched_get_priority_max(cf.stable->sched_policy); if (sched_setscheduler(0, cf.stable->sched_policy, &sparam) == -1) { rtpp_log_ewrite(RTPP_LOG_ERR, cf.stable->glog, "sched_setscheduler(SCHED_%s, %d)", (cf.stable->sched_policy == SCHED_FIFO) ? "FIFO" : "RR", sparam.sched_priority); } } if (cf.stable->run_uname != NULL || cf.stable->run_gname != NULL) { if (drop_privileges(&cf) != 0) { rtpp_log_ewrite(RTPP_LOG_ERR, cf.stable->glog, "can't switch to requested user/group"); exit(1); } } set_rlimits(&cf); cf.sessinfo.sessions[0] = NULL; cf.sessinfo.nsessions = 0; cf.rtp_nsessions = 0; rtpp_command_async_init(&cf); rtpp_proc_async_init(&cf); counter = 0; recfilter_init(&loop_error, 0.96, 0.0, 0); PFD_init(&phase_detector, 2.0); #ifdef HAVE_SYSTEMD_SD_DAEMON_H sd_notify(0, "READY=1"); #endif #ifdef RTPP_CHECK_LEAKS rtpp_memdeb_setbaseln(); #endif for (;;) { eptime = getdtime(); clk = (eptime + cf.stable->sched_offset) * cf.stable->target_pfreq; ncycles_ref = llrint(clk); eval = PFD_get_error(&phase_detector, clk); #if RTPP_DEBUG filter_lastval = loop_error.lastval; #endif if (eval != 0.0) { recfilter_apply(&loop_error, sigmoid(eval)); } #if RTPP_DEBUG if (counter % (unsigned int)cf.stable->target_pfreq == 0 || counter < 1000) { rtpp_log_write(RTPP_LOG_DBUG, cf.stable->glog, "run %lld ncycles %f raw error1 %f, filter lastval %f, filter nextval %f", counter, clk, eval, filter_lastval, loop_error.lastval); } #endif add_delay = freqoff_to_period(cf.stable->target_pfreq, 1.0, loop_error.lastval); usleep_time = add_delay * 1000000.0; #if RTPP_DEBUG if (counter % (unsigned int)cf.stable->target_pfreq == 0 || counter < 1000) { rtpp_log_write(RTPP_LOG_DBUG, cf.stable->glog, "run %lld filter lastval %f, filter nextval %f, error %f", counter, filter_lastval, loop_error.lastval, sigmoid(eval)); rtpp_log_write(RTPP_LOG_DBUG, cf.stable->glog, "run %lld extra sleeping time %llu", counter, usleep_time); } sleep_time = getdtime(); #endif rtpp_proc_async_wakeup(cf.stable->rtpp_proc_cf, counter, ncycles_ref); usleep(usleep_time); #if RTPP_DEBUG sleep_time = getdtime() - sleep_time; if (counter % (unsigned int)cf.stable->target_pfreq == 0 || counter < 1000 || sleep_time > add_delay * 2.0) { rtpp_log_write(RTPP_LOG_DBUG, cf.stable->glog, "run %lld sleeping time required %llu sleeping time actual %f, CSV: %f,%f,%f", \ counter, usleep_time, sleep_time, (double)counter / cf.stable->target_pfreq, ((double)usleep_time) / 1000.0, sleep_time * 1000.0); } #endif counter += 1; if (cf.stable->slowshutdown != 0) { pthread_mutex_lock(&cf.sessinfo.lock); if (cf.sessinfo.nsessions == 0) { /* The below unlock is not necessary, but does not hurt either */ pthread_mutex_unlock(&cf.sessinfo.lock); rtpp_log_write(RTPP_LOG_INFO, cf.stable->glog, "deorbiting-burn sequence completed, exiting"); break; } pthread_mutex_unlock(&cf.sessinfo.lock); } } #ifdef HAVE_SYSTEMD_SD_DAEMON_H sd_notify(0, "STATUS=Exited"); #endif #ifdef RTPP_CHECK_LEAKS exit(rtpp_memdeb_dumpstats(&cf) == 0 ? 0 : 1); #else exit(0); #endif }
void initialize_thread_priority(omrthread_t thread) { int policy, priority, i; struct sched_param sched_param; /* set the default value */ thread->priority = J9THREAD_PRIORITY_NORMAL; /* are we using priorities at all? */ if (priority_map[J9THREAD_PRIORITY_MIN] == priority_map[J9THREAD_PRIORITY_MAX]) { return; } if (pthread_getschedparam(thread->handle, &policy, &sched_param)) { /* the call failed */ return; } #if defined(J9_PRIORITY_MAP) if (policy != J9_DEFAULT_SCHED) { /* incompatible policy for our priority mapping */ return; } #endif /* * Similar story for AIX as IRIX, except AIX uses 1 instead of 0. * * Each thread in AIX starts out as a floating priority SCHED_OTHER thread. * Once we assign a pthread priority it becomes a fixed priority thread with * policy SCHED_OTHER, SCHED_FIFO, SCHED_RR or other. */ if (sched_param.sched_priority == 1) { set_pthread_priority(thread->handle, thread->priority); return; } #ifndef J9OS_I5 /* explicitly disabled by iSeries team */ /* on some platforms (i.e. Solaris) we get out of range values (e.g. 0) for threads with no explicitly set priority */ if (sched_param.sched_priority < sched_get_priority_min(policy) || sched_param.sched_priority > sched_get_priority_max(policy)) { return; } #endif thread->priority = omrthread_map_native_priority(sched_param.sched_priority); }
/** * Reads a NOAAPORT data stream, creates LDM data-products from the stream, and * inserts the data-products into an LDM product-queue. The NOAAPORT data * stream can take the form of multicast UDP packets from (for example) a * Novra S300 DVB-S2 receiver or the standard input stream. * * Usage: * noaaportIngester [-l <em>log</em>] [-n|-v|-x] [-q <em>queue</em>] [-u <em>n</em>] [-m <em>mcastAddr</em>] [-I <em>iface</em>] [-b <em>npages</em>]\n * * Where: * <dl> * <dt>-b <em>npages</em></dt> * <dd>Allocate \e npages pages of memory for the internal buffer.</dd> * * <dt>-I <em>iface</em></dt> * <dd>Listen for multicast packets on interface \e iface.</dd> * * <dt>-l <em>log</em></dt> * <dd>Log to file \e log. The default is to use the system logging daemon * if the current process is a daemon; otherwise, the standard error * stream is used.</dd> * * <dt>-m <em>mcastAddr</em></dt> * <dd>Use the multicast address \e mcastAddr. The default is to * read from the standard input stream.</dd> * * <dt>-n</dt> * <dd>Log messages of level NOTE and higher priority. Each data-product * will generate a log message.</dd> * * <dt>-q <em>queue</em></dt> * <dd>Use \e queue as the pathname of the LDM product-queue. The default * is to use the default LDM pathname of the product-queue.</dd> * * <dt>-u <em>n</em></dt> * <dd>If logging is to the system logging daemon, then use facility * <b>local</b><em>n</em>. The default is to use the LDM facility.</dd> * * <dt>-v</dt> * <dd>Log messages of level INFO and higher priority.</dd> * * <dt>-x</dt> * <dd>Log messages of level DEBUG and higher priority.</dd> * </dl> * * If neither -n, -v, nor -x is specified, then logging will be restricted to * levels ERROR and WARN only. * * @retval 0 if successful. * @retval 1 if an error occurred. At least one error-message will be logged. */ int main( const int argc, /**< [in] Number of arguments */ char* const argv[]) /**< [in] Arguments */ { int status = 0; /* default success */ extern int optind; extern int opterr; int ch; const char* const progName = ubasename(argv[0]); const char* interface = NULL; int logmask = LOG_UPTO(LOG_WARNING); const unsigned logOptions = LOG_CONS | LOG_PID; const char* mcastSpec = NULL; const char* prodQueuePath = NULL; size_t npages = DEFAULT_NPAGES; Fifo* fifo; int ttyFd = open("/dev/tty", O_RDONLY); int processPriority = 0; int idx; const char* logPath = (-1 == ttyFd) ? NULL /* log to system logging daemon */ : "-"; /* log to standard error stream */ (void)close(ttyFd); (void)setulogmask(logmask); status = initLogging(progName, logOptions, logFacility, logPath); opterr = 0; /* no error messages from getopt(3) */ while (0 == status && (ch = getopt(argc, argv, "b:I:l:m:np:q:r:s:t:u:vx")) != -1) { switch (ch) { extern char* optarg; extern int optopt; case 'b': { unsigned long n; if (sscanf(optarg, "%lu", &n) != 1) { LOG_SERROR1("Couldn't decode FIFO size in pages: \"%s\"", optarg); status = 1; } else { npages = n; } break; } case 'I': interface = optarg; break; case 'l': logPath = optarg; status = initLogging(progName, logOptions, logFacility, logPath); break; case 'm': mcastSpec = optarg; break; case 'n': logmask |= LOG_MASK(LOG_NOTICE); (void)setulogmask(logmask); break; case 'p': { char* cp; errno = 0; processPriority = (int)strtol(optarg, &cp, 0); if (0 != errno) { LOG_SERROR1("Couldn't decode priority \"%s\"", optarg); log_log(LOG_ERR); } else { if (processPriority < -20) processPriority = -20; else if (processPriority > 20) processPriority = 20; } break; } case 'q': prodQueuePath = optarg; break; case 'r': #ifdef RETRANS_SUPPORT retrans_xmit_enable = atoi(optarg); if(retrans_xmit_enable == 1) retrans_xmit_enable = OPTION_ENABLE; else retrans_xmit_enable = OPTION_DISABLE; #endif break; case 's': { #ifdef RETRANS_SUPPORT strcpy(sbn_channel_name, optarg); if(!strcmp(optarg,NAME_SBN_TYP_GOES)) { sbn_type = SBN_TYP_GOES; break; } if(!strcmp(optarg,NAME_SBN_TYP_NOAAPORT_OPT)) { sbn_type = SBN_TYP_NOAAPORT_OPT; break; } if(!strcmp(optarg,"NWSTG")) { sbn_type = SBN_TYP_NMC; break; } if(!strcmp(optarg,NAME_SBN_TYP_NMC)) { sbn_type = SBN_TYP_NMC; break; } if(!strcmp(optarg,NAME_SBN_TYP_NMC2)) { sbn_type = SBN_TYP_NMC2; break; } if(!strcmp(optarg,NAME_SBN_TYP_NMC3)) { sbn_type = SBN_TYP_NMC3; break; } if(!strcmp(optarg,NAME_SBN_TYP_NWWS)) { sbn_type = SBN_TYP_NWWS; break; } if(!strcmp(optarg,NAME_SBN_TYP_ADD)) { sbn_type = SBN_TYP_ADD; break; } if(!strcmp(optarg,NAME_SBN_TYP_ENC)) { sbn_type = SBN_TYP_ENC; break; } if(!strcmp(optarg,NAME_SBN_TYP_EXP)) { sbn_type = SBN_TYP_EXP; break; } if(!strcmp(optarg,NAME_SBN_TYP_GRW)) { sbn_type = SBN_TYP_GRW; break; } if(!strcmp(optarg,NAME_SBN_TYP_GRE)) { sbn_type = SBN_TYP_GRE; break; } printf("Operator input: UNKNOWN type must be\n"); printf(" %s, %s, %s, %s, %s, %s, %s, %s, %s, %s or %s \n", NAME_SBN_TYP_NMC, NAME_SBN_TYP_GOES, NAME_SBN_TYP_NOAAPORT_OPT, NAME_SBN_TYP_NMC2, NAME_SBN_TYP_NMC3, NAME_SBN_TYP_NWWS, NAME_SBN_TYP_ADD, NAME_SBN_TYP_ENC, NAME_SBN_TYP_EXP, NAME_SBN_TYP_GRW, NAME_SBN_TYP_GRE); #endif break; } case 't': #ifdef RETRANS_SUPPORT strcpy(transfer_type, optarg); if(!strcmp(transfer_type,"MHS") || !strcmp(transfer_type,"mhs")){ /** Using MHS for communication with NCF **/ }else{ uerror("No other mechanism other than MHS is currently supported\n"); status = 1; } #endif break; case 'u': { int i = atoi(optarg); if (0 > i || 7 < i) { LOG_START1("Invalid logging facility number: %d", i); status = 1; } else { static int logFacilities[] = {LOG_LOCAL0, LOG_LOCAL1, LOG_LOCAL2, LOG_LOCAL3, LOG_LOCAL4, LOG_LOCAL5, LOG_LOCAL6, LOG_LOCAL7}; logFacility = logFacilities[i]; status = initLogging(progName, logOptions, logFacility, logPath); } break; } case 'v': logmask |= LOG_MASK(LOG_INFO); (void)setulogmask(logmask); break; case 'x': logmask |= LOG_MASK(LOG_DEBUG); (void)setulogmask(logmask); break; default: optopt = ch; /*FALLTHROUGH*/ /* no break */ case '?': { uerror("Unknown option: \"%c\"", optopt); status = 1; break; } } /* option character switch */ } /* getopt() loop */ if (0 == status) { if (optind < argc) { uerror("Extraneous command-line argument: \"%s\"", argv[optind]); status = 1; } } if (0 != status) { uerror("Error decoding command-line"); usage(progName); } else { unotice("Starting Up %s", PACKAGE_VERSION); unotice("%s", COPYRIGHT_NOTICE); if ((status = fifoNew(npages, &fifo)) != 0) { LOG_ADD0("Couldn't create FIFO"); log_log(LOG_ERR); } else { LdmProductQueue* prodQueue; if ((status = lpqGet(prodQueuePath, &prodQueue)) != 0) { LOG_ADD0("Couldn't open LDM product-queue"); log_log(LOG_ERR); } else { if (NULL == mcastSpec) { if (0 == (status = spawnProductMaker(NULL, fifo, prodQueue, &productMaker, &productMakerThread))) { status = spawnFileReader(NULL, NULL, fifo, &reader, &readerThread); } } /* reading file */ else { pthread_attr_t attr; if (0 != (status = pthread_attr_init(&attr))) { LOG_ERRNUM0(status, "Couldn't initialize thread attribute"); } else { #ifndef _POSIX_THREAD_PRIORITY_SCHEDULING uwarn("Can't adjust thread priorities due to lack of " "necessary support from environment"); #else /* * In order to not miss any data, the reader thread * should preempt the product-maker thread as soon as * data is available and run as long as data is * available. */ const int SCHED_POLICY = SCHED_FIFO; struct sched_param param; param.sched_priority = sched_get_priority_max(SCHED_POLICY) - 1; (void)pthread_attr_setinheritsched(&attr, PTHREAD_EXPLICIT_SCHED); (void)pthread_attr_setschedpolicy(&attr, SCHED_POLICY); (void)pthread_attr_setschedparam(&attr, ¶m); (void)pthread_attr_setscope(&attr, PTHREAD_SCOPE_SYSTEM); #endif #ifdef RETRANS_SUPPORT if (retrans_xmit_enable == OPTION_ENABLE){ /* Copy mcastAddress needed to obtain the cpio entries */ strcpy(mcastAddr, mcastSpec); } #endif if (0 == (status = spawnProductMaker(&attr, fifo, prodQueue, &productMaker, &productMakerThread))) { #ifdef _POSIX_THREAD_PRIORITY_SCHEDULING param.sched_priority++; (void)pthread_attr_setschedparam(&attr, ¶m); #endif status = spawnMulticastReader(&attr, mcastSpec, interface, fifo, &reader, &readerThread); } /* product-maker spawned */ } /* "attr" initialized */ } /* reading multicast packets */ if (0 != status) { log_log(LOG_ERR); status = 1; } else { pthread_t statThread; (void)gettimeofday(&startTime, NULL); reportTime = startTime; (void)pthread_create(&statThread, NULL, reportStatsWhenSignaled, NULL); set_sigactions(); (void)pthread_join(readerThread, NULL); status = readerStatus(reader); (void)pthread_cancel(statThread); (void)pthread_join(statThread, NULL); (void)fifoCloseWhenEmpty(fifo); (void)pthread_join(productMakerThread, NULL); if (0 != status) status = pmStatus(productMaker); reportStats(); readerFree(reader); #ifdef RETRANS_SUPPORT /** Release buffer allocated for retransmission **/ if(retrans_xmit_enable == OPTION_ENABLE){ freeRetransMem(); } #endif } /* "reader" spawned */ (void)lpqClose(prodQueue); } /* "prodQueue" open */ } /* "fifo" created */ } /* command line decoded */ return status; }
int nsh_parse(FAR struct nsh_vtbl_s *vtbl, char *cmdline) { FAR char *argv[MAX_ARGV_ENTRIES]; FAR char *saveptr; FAR char *cmd; #if CONFIG_NFILE_STREAMS > 0 FAR char *redirfile = NULL; int oflags = 0; int fd = -1; #endif int argc; int ret; /* Initialize parser state */ memset(argv, 0, MAX_ARGV_ENTRIES*sizeof(FAR char *)); #ifndef CONFIG_NSH_DISABLEBG vtbl->np.np_bg = false; #endif #if CONFIG_NFILE_STREAMS > 0 vtbl->np.np_redirect = false; #endif /* Parse out the command at the beginning of the line */ saveptr = cmdline; cmd = nsh_argument(vtbl, &saveptr); /* Handler if-then-else-fi */ #ifndef CONFIG_NSH_DISABLESCRIPT if (nsh_ifthenelse(vtbl, &cmd, &saveptr) != 0) { goto errout; } #endif /* Handle nice */ #ifndef CONFIG_NSH_DISABLEBG if (nsh_nice(vtbl, &cmd, &saveptr) != 0) { goto errout; } #endif /* Check if any command was provided -OR- if command processing is * currently disabled. */ #ifndef CONFIG_NSH_DISABLESCRIPT if (!cmd || !nsh_cmdenabled(vtbl)) #else if (!cmd) #endif { /* An empty line is not an error and an unprocessed command cannot * generate an error, but neither should they change the last * command status. */ return OK; } /* Parse all of the arguments following the command name. The form * of argv is: * * argv[0]: The command name. * argv[1]: The beginning of argument (up to CONFIG_NSH_MAXARGUMENTS) * argv[argc-3]: Possibly '>' or '>>' * argv[argc-2]: Possibly <file> * argv[argc-1]: Possibly '&' * argv[argc]: NULL terminating pointer * * Maximum size is CONFIG_NSH_MAXARGUMENTS+5 */ argv[0] = cmd; for (argc = 1; argc < MAX_ARGV_ENTRIES-1; argc++) { argv[argc] = nsh_argument(vtbl, &saveptr); if (!argv[argc]) { break; } } argv[argc] = NULL; /* Check if the command should run in background */ #ifndef CONFIG_NSH_DISABLEBG if (argc > 1 && strcmp(argv[argc-1], "&") == 0) { vtbl->np.np_bg = true; argv[argc-1] = NULL; argc--; } #endif #if CONFIG_NFILE_STREAMS > 0 /* Check if the output was re-directed using > or >> */ if (argc > 2) { /* Check for redirection to a new file */ if (strcmp(argv[argc-2], g_redirect1) == 0) { vtbl->np.np_redirect = true; oflags = O_WRONLY|O_CREAT|O_TRUNC; redirfile = nsh_getfullpath(vtbl, argv[argc-1]); argc -= 2; } /* Check for redirection by appending to an existing file */ else if (strcmp(argv[argc-2], g_redirect2) == 0) { vtbl->np.np_redirect = true; oflags = O_WRONLY|O_CREAT|O_APPEND; redirfile = nsh_getfullpath(vtbl, argv[argc-1]); argc -= 2; } } #endif /* Check if the maximum number of arguments was exceeded */ if (argc > CONFIG_NSH_MAXARGUMENTS) { nsh_output(vtbl, g_fmttoomanyargs, cmd); } /* Does this command correspond to an application filename? * nsh_fileapp() returns: * * -1 (ERROR) if the application task corresponding to 'argv[0]' could not * be started (possibly because it doesn not exist). * 0 (OK) if the application task corresponding to 'argv[0]' was * and successfully started. If CONFIG_SCHED_WAITPID is * defined, this return value also indicates that the * application returned successful status (EXIT_SUCCESS) * 1 If CONFIG_SCHED_WAITPID is defined, then this return value * indicates that the application task was spawned successfully * but returned failure exit status. * * Note the priority if not effected by nice-ness. */ #ifdef CONFIG_NSH_FILE_APPS ret = nsh_fileapp(vtbl, argv[0], argv, redirfile, oflags); if (ret >= 0) { /* nsh_fileapp() returned 0 or 1. This means that the builtin * command was successfully started (although it may not have ran * successfully). So certainly it is not an NSH command. */ /* Free the redirected output file path */ if (redirfile) { nsh_freefullpath(redirfile); } /* Save the result: success if 0; failure if 1 */ return nsh_saveresult(vtbl, ret != OK); } /* No, not a built in command (or, at least, we were unable to start a * builtin command of that name). Treat it like an NSH command. */ #endif /* Does this command correspond to a builtin command? * nsh_builtin() returns: * * -1 (ERROR) if the application task corresponding to 'argv[0]' could not * be started (possibly because it doesn not exist). * 0 (OK) if the application task corresponding to 'argv[0]' was * and successfully started. If CONFIG_SCHED_WAITPID is * defined, this return value also indicates that the * application returned successful status (EXIT_SUCCESS) * 1 If CONFIG_SCHED_WAITPID is defined, then this return value * indicates that the application task was spawned successfully * but returned failure exit status. * * Note the priority if not effected by nice-ness. */ #if defined(CONFIG_NSH_BUILTIN_APPS) && (!defined(CONFIG_NSH_FILE_APPS) || !defined(CONFIG_FS_BINFS)) #if CONFIG_NFILE_STREAMS > 0 ret = nsh_builtin(vtbl, argv[0], argv, redirfile, oflags); #else ret = nsh_builtin(vtbl, argv[0], argv, NULL, 0); #endif if (ret >= 0) { /* nsh_builtin() returned 0 or 1. This means that the builtin * command was successfully started (although it may not have ran * successfully). So certainly it is not an NSH command. */ #if CONFIG_NFILE_STREAMS > 0 /* Free the redirected output file path */ if (redirfile) { nsh_freefullpath(redirfile); } #endif /* Save the result: success if 0; failure if 1 */ return nsh_saveresult(vtbl, ret != OK); } /* No, not a built in command (or, at least, we were unable to start a * builtin command of that name). Treat it like an NSH command. */ #endif #if CONFIG_NFILE_STREAMS > 0 /* Redirected output? */ if (vtbl->np.np_redirect) { /* Open the redirection file. This file will eventually * be closed by a call to either nsh_release (if the command * is executed in the background) or by nsh_undirect if the * command is executed in the foreground. */ fd = open(redirfile, oflags, 0666); nsh_freefullpath(redirfile); redirfile = NULL; if (fd < 0) { nsh_output(vtbl, g_fmtcmdfailed, cmd, "open", NSH_ERRNO); goto errout; } } #endif /* Handle the case where the command is executed in background. * However is app is to be started as builtin new process will * be created anyway, so skip this step. */ #ifndef CONFIG_NSH_DISABLEBG if (vtbl->np.np_bg) { struct sched_param param; struct nsh_vtbl_s *bkgvtbl; struct cmdarg_s *args; pthread_attr_t attr; pthread_t thread; /* Get a cloned copy of the vtbl with reference count=1. * after the command has been processed, the nsh_release() call * at the end of nsh_child() will destroy the clone. */ bkgvtbl = nsh_clone(vtbl); if (!bkgvtbl) { goto errout_with_redirect; } /* Create a container for the command arguments */ args = nsh_cloneargs(bkgvtbl, fd, argc, argv); if (!args) { nsh_release(bkgvtbl); goto errout_with_redirect; } #if CONFIG_NFILE_STREAMS > 0 /* Handle redirection of output via a file descriptor */ if (vtbl->np.np_redirect) { (void)nsh_redirect(bkgvtbl, fd, NULL); } #endif /* Get the execution priority of this task */ ret = sched_getparam(0, ¶m); if (ret != 0) { nsh_output(vtbl, g_fmtcmdfailed, cmd, "sched_getparm", NSH_ERRNO); nsh_releaseargs(args); nsh_release(bkgvtbl); goto errout; } /* Determine the priority to execute the command */ if (vtbl->np.np_nice != 0) { int priority = param.sched_priority - vtbl->np.np_nice; if (vtbl->np.np_nice < 0) { int max_priority = sched_get_priority_max(SCHED_NSH); if (priority > max_priority) { priority = max_priority; } } else { int min_priority = sched_get_priority_min(SCHED_NSH); if (priority < min_priority) { priority = min_priority; } } param.sched_priority = priority; } /* Set up the thread attributes */ (void)pthread_attr_init(&attr); (void)pthread_attr_setschedpolicy(&attr, SCHED_NSH); (void)pthread_attr_setschedparam(&attr, ¶m); /* Execute the command as a separate thread at the appropriate priority */ ret = pthread_create(&thread, &attr, nsh_child, (pthread_addr_t)args); if (ret != 0) { nsh_output(vtbl, g_fmtcmdfailed, cmd, "pthread_create", NSH_ERRNO_OF(ret)); nsh_releaseargs(args); nsh_release(bkgvtbl); goto errout; } /* Detach from the pthread since we are not going to join with it. * Otherwise, we would have a memory leak. */ (void)pthread_detach(thread); nsh_output(vtbl, "%s [%d:%d]\n", cmd, thread, param.sched_priority); } else #endif { #if CONFIG_NFILE_STREAMS > 0 uint8_t save[SAVE_SIZE]; /* Handle redirection of output via a file descriptor */ if (vtbl->np.np_redirect) { nsh_redirect(vtbl, fd, save); } #endif /* Then execute the command in "foreground" -- i.e., while the user waits * for the next prompt. nsh_execute will return: * * -1 (ERRROR) if the command was unsuccessful * 0 (OK) if the command was successful */ ret = nsh_execute(vtbl, argc, argv); #if CONFIG_NFILE_STREAMS > 0 /* Restore the original output. Undirect will close the redirection * file descriptor. */ if (vtbl->np.np_redirect) { nsh_undirect(vtbl, save); } #endif /* Mark errors so that it is possible to test for non-zero return values * in nsh scripts. */ if (ret < 0) { goto errout; } } /* Return success if the command succeeded (or at least, starting of the * command task succeeded). */ return nsh_saveresult(vtbl, false); #ifndef CONFIG_NSH_DISABLEBG errout_with_redirect: #if CONFIG_NFILE_STREAMS > 0 if (vtbl->np.np_redirect) { close(fd); } #endif #endif errout: return nsh_saveresult(vtbl, true); }
void *DemodulatorPreThread::threadMain() { #else void DemodulatorPreThread::threadMain() { #endif #ifdef __APPLE__ pthread_t tID = pthread_self(); // ID of this thread int priority = sched_get_priority_max( SCHED_FIFO) - 1; sched_param prio = {priority}; // scheduling priority of thread pthread_setschedparam(tID, SCHED_FIFO, &prio); #endif if (!initialized) { initialize(); } std::cout << "Demodulator preprocessor thread started.." << std::endl; std::deque<DemodulatorThreadPostIQData *> buffers; std::deque<DemodulatorThreadPostIQData *>::iterator buffers_i; std::vector<liquid_float_complex> in_buf_data; std::vector<liquid_float_complex> out_buf_data; // liquid_float_complex carrySample; // Keep the stream count even to simplify some demod operations // bool carrySampleFlag = false; terminated = false; while (!terminated) { DemodulatorThreadIQData *inp; iqInputQueue->pop(inp); bool bandwidthChanged = false; bool rateChanged = false; DemodulatorThreadParameters tempParams = params; if (!commandQueue->empty()) { while (!commandQueue->empty()) { DemodulatorThreadCommand command; commandQueue->pop(command); switch (command.cmd) { case DemodulatorThreadCommand::DEMOD_THREAD_CMD_SET_BANDWIDTH: if (command.llong_value < 1500) { command.llong_value = 1500; } if (command.llong_value > params.sampleRate) { tempParams.bandwidth = params.sampleRate; } else { tempParams.bandwidth = command.llong_value; } bandwidthChanged = true; break; case DemodulatorThreadCommand::DEMOD_THREAD_CMD_SET_FREQUENCY: params.frequency = tempParams.frequency = command.llong_value; break; case DemodulatorThreadCommand::DEMOD_THREAD_CMD_SET_AUDIO_RATE: tempParams.audioSampleRate = (int)command.llong_value; rateChanged = true; break; default: break; } } } if (inp->sampleRate != tempParams.sampleRate && inp->sampleRate) { tempParams.sampleRate = inp->sampleRate; rateChanged = true; } if (bandwidthChanged || rateChanged) { DemodulatorWorkerThreadCommand command(DemodulatorWorkerThreadCommand::DEMOD_WORKER_THREAD_CMD_BUILD_FILTERS); command.sampleRate = tempParams.sampleRate; command.audioSampleRate = tempParams.audioSampleRate; command.bandwidth = tempParams.bandwidth; command.frequency = tempParams.frequency; workerQueue->push(command); } if (!initialized) { continue; } // Requested frequency is not center, shift it into the center! if ((params.frequency - inp->frequency) != shiftFrequency || rateChanged) { shiftFrequency = params.frequency - inp->frequency; if (abs(shiftFrequency) <= (int) ((double) (wxGetApp().getSampleRate() / 2) * 1.5)) { nco_crcf_set_frequency(freqShifter, (2.0 * M_PI) * (((double) abs(shiftFrequency)) / ((double) wxGetApp().getSampleRate()))); } } if (abs(shiftFrequency) > (int) ((double) (wxGetApp().getSampleRate() / 2) * 1.5)) { continue; } // std::lock_guard < std::mutex > lock(inp->m_mutex); std::vector<liquid_float_complex> *data = &inp->data; if (data->size() && (inp->sampleRate == params.sampleRate)) { int bufSize = data->size(); if (in_buf_data.size() != bufSize) { if (in_buf_data.capacity() < bufSize) { in_buf_data.reserve(bufSize); out_buf_data.reserve(bufSize); } in_buf_data.resize(bufSize); out_buf_data.resize(bufSize); } in_buf_data.assign(inp->data.begin(), inp->data.end()); liquid_float_complex *in_buf = &in_buf_data[0]; liquid_float_complex *out_buf = &out_buf_data[0]; liquid_float_complex *temp_buf = NULL; if (shiftFrequency != 0) { if (shiftFrequency < 0) { nco_crcf_mix_block_up(freqShifter, in_buf, out_buf, bufSize); } else { nco_crcf_mix_block_down(freqShifter, in_buf, out_buf, bufSize); } temp_buf = in_buf; in_buf = out_buf; out_buf = temp_buf; } DemodulatorThreadPostIQData *resamp = NULL; for (buffers_i = buffers.begin(); buffers_i != buffers.end(); buffers_i++) { if ((*buffers_i)->getRefCount() <= 0) { resamp = (*buffers_i); break; } } if (resamp == NULL) { resamp = new DemodulatorThreadPostIQData; buffers.push_back(resamp); } int out_size = ceil((double) (bufSize) * iqResampleRatio) + 512; if (resampledData.size() != out_size) { if (resampledData.capacity() < out_size) { resampledData.reserve(out_size); } resampledData.resize(out_size); } unsigned int numWritten; msresamp_crcf_execute(iqResampler, in_buf, bufSize, &resampledData[0], &numWritten); resamp->setRefCount(1); resamp->data.assign(resampledData.begin(), resampledData.begin() + numWritten); // bool uneven = (numWritten % 2 != 0); // if (!carrySampleFlag && !uneven) { // resamp->data.assign(resampledData.begin(), resampledData.begin() + numWritten); // carrySampleFlag = false; // } else if (!carrySampleFlag && uneven) { // resamp->data.assign(resampledData.begin(), resampledData.begin() + (numWritten-1)); // carrySample = resampledData.back(); // carrySampleFlag = true; // } else if (carrySampleFlag && uneven) { // resamp->data.resize(numWritten+1); // resamp->data[0] = carrySample; // memcpy(&resamp->data[1],&resampledData[0],sizeof(liquid_float_complex)*numWritten); // carrySampleFlag = false; // } else if (carrySampleFlag && !uneven) { // resamp->data.resize(numWritten); // resamp->data[0] = carrySample; // memcpy(&resamp->data[1],&resampledData[0],sizeof(liquid_float_complex)*(numWritten-1)); // carrySample = resampledData.back(); // carrySampleFlag = true; // } resamp->audioResampleRatio = audioResampleRatio; resamp->audioResampler = audioResampler; resamp->audioSampleRate = params.audioSampleRate; resamp->stereoResampler = stereoResampler; resamp->firStereoLeft = firStereoLeft; resamp->firStereoRight = firStereoRight; resamp->iirStereoPilot = iirStereoPilot; resamp->sampleRate = params.bandwidth; iqOutputQueue->push(resamp); } inp->decRefCount(); if (!workerResults->empty()) { while (!workerResults->empty()) { DemodulatorWorkerThreadResult result; workerResults->pop(result); switch (result.cmd) { case DemodulatorWorkerThreadResult::DEMOD_WORKER_THREAD_RESULT_FILTERS: msresamp_crcf_destroy(iqResampler); if (result.iqResampler) { iqResampler = result.iqResampler; iqResampleRatio = result.iqResampleRatio; } if (result.firStereoLeft) { firStereoLeft = result.firStereoLeft; } if (result.firStereoRight) { firStereoRight = result.firStereoRight; } if (result.iirStereoPilot) { iirStereoPilot = result.iirStereoPilot; } if (result.audioResampler) { audioResampler = result.audioResampler; audioResampleRatio = result.audioResamplerRatio; stereoResampler = result.stereoResampler; } if (result.audioSampleRate) { params.audioSampleRate = result.audioSampleRate; } if (result.bandwidth) { params.bandwidth = result.bandwidth; } if (result.sampleRate) { params.sampleRate = result.sampleRate; } break; default: break; } } } } while (!buffers.empty()) { DemodulatorThreadPostIQData *iqDataDel = buffers.front(); buffers.pop_front(); delete iqDataDel; } DemodulatorThreadCommand tCmd(DemodulatorThreadCommand::DEMOD_THREAD_CMD_DEMOD_PREPROCESS_TERMINATED); tCmd.context = this; threadQueueNotify->push(tCmd); std::cout << "Demodulator preprocessor thread done." << std::endl; #ifdef __APPLE__ return this; #endif }
void priority_inheritance(void) { #if defined(CONFIG_PRIORITY_INHERITANCE) && !defined(CONFIG_DISABLE_SIGNALS) && !defined(CONFIG_DISABLE_PTHREAD) pthread_t lowpri[NLOWPRI_THREADS]; pthread_t medpri; pthread_t highpri[NHIGHPRI_THREADS]; pthread_addr_t result; pthread_attr_t attr; struct sched_param sparam; int my_pri; int status; int i; printf("priority_inheritance: Started\n"); g_middlestate = NOTSTARTED; for (i = 0; i < NHIGHPRI_THREADS; i++) g_highstate[i] = NOTSTARTED; for (i = 0; i < NLOWPRI_THREADS; i++) g_lowstate[i] = NOTSTARTED; status = sched_getparam (getpid(), &sparam); if (status != 0) { printf("priority_inheritance: sched_getparam failed\n"); sparam.sched_priority = PTHREAD_DEFAULT_PRIORITY; } my_pri = sparam.sched_priority; g_highpri = sched_get_priority_max(SCHED_FIFO); g_lowpri = sched_get_priority_min(SCHED_FIFO); g_medpri = my_pri - 1; sem_init(&g_sem, 0, NLOWPRI_THREADS); dump_nfreeholders("priority_inheritance:"); /* Start the low priority threads */ for (i = 0; i < NLOWPRI_THREADS; i++) { int threadno = i+1; printf("priority_inheritance: Starting lowpri_thread-%d (of %d) at %d\n", threadno, NLOWPRI_THREADS, g_lowpri); status = pthread_attr_init(&attr); if (status != 0) { printf("priority_inheritance: pthread_attr_init failed, status=%d\n", status); } sparam.sched_priority = g_lowpri; status = pthread_attr_setschedparam(&attr,& sparam); if (status != OK) { printf("priority_inheritance: pthread_attr_setschedparam failed, status=%d\n", status); } else { printf("priority_inheritance: Set lowpri_thread-%d priority to %d\n", threadno, sparam.sched_priority); } status = pthread_create(&lowpri[i], &attr, lowpri_thread, (void*)threadno); if (status != 0) { printf("priority_inheritance: pthread_create failed, status=%d\n", status); } } printf("priority_inheritance: Waiting...\n"); sleep(2); dump_nfreeholders("priority_inheritance:"); /* Start the medium priority thread */ printf("priority_inheritance: Starting medpri_thread at %d\n", g_medpri); status = pthread_attr_init(&attr); if (status != 0) { printf("priority_inheritance: pthread_attr_init failed, status=%d\n", status); } sparam.sched_priority = g_medpri; status = pthread_attr_setschedparam(&attr,& sparam); if (status != OK) { printf("priority_inheritance: pthread_attr_setschedparam failed, status=%d\n", status); } else { printf("priority_inheritance: Set medpri_thread priority to %d\n", sparam.sched_priority); } FFLUSH(); status = pthread_create(&medpri, &attr, medpri_thread, NULL); if (status != 0) { printf("priority_inheritance: pthread_create failed, status=%d\n", status); } printf("priority_inheritance: Waiting...\n"); sleep(1); dump_nfreeholders("priority_inheritance:"); /* Start the high priority threads */ for (i = 0; i < NHIGHPRI_THREADS; i++) { int threadno = i+1; printf("priority_inheritance: Starting highpri_thread-%d (of %d) at %d\n", threadno, NHIGHPRI_THREADS, g_highpri); status = pthread_attr_init(&attr); if (status != 0) { printf("priority_inheritance: pthread_attr_init failed, status=%d\n", status); } sparam.sched_priority = g_highpri - i; status = pthread_attr_setschedparam(&attr,& sparam); if (status != OK) { printf("priority_inheritance: pthread_attr_setschedparam failed, status=%d\n", status); } else { printf("priority_inheritance: Set highpri_thread-%d priority to %d\n", threadno, sparam.sched_priority); } FFLUSH(); status = pthread_create(&highpri[i], &attr, highpri_thread, (void*)threadno); if (status != 0) { printf("priority_inheritance: pthread_create failed, status=%d\n", status); } } dump_nfreeholders("priority_inheritance:"); FFLUSH(); /* Wait for all thread instances to complete */ for (i = 0; i < NHIGHPRI_THREADS; i++) { printf("priority_inheritance: Waiting for highpri_thread-%d to complete\n", i+1); FFLUSH(); (void)pthread_join(highpri[i], &result); dump_nfreeholders("priority_inheritance:"); } printf("priority_inheritance: Waiting for medpri_thread to complete\n"); FFLUSH(); (void)pthread_join(medpri, &result); dump_nfreeholders("priority_inheritance:"); for (i = 0; i < NLOWPRI_THREADS; i++) { printf("priority_inheritance: Waiting for lowpri_thread-%d to complete\n", i+1); FFLUSH(); (void)pthread_join(lowpri[i], &result); dump_nfreeholders("priority_inheritance:"); } printf("priority_inheritance: Finished\n"); sem_destroy(&g_sem); dump_nfreeholders("priority_inheritance:"); FFLUSH(); #endif /* CONFIG_PRIORITY_INHERITANCE && !CONFIG_DISABLE_SIGNALS && !CONFIG_DISABLE_PTHREAD */ }
int main(int argc, char* argv[]){ long i; long iterations = DEFAULT_ITERATIONS; struct sched_param param; int rv, policy, num_processes, status; int inputFD; int outputFD; double x, y; double inCircle = 0.0; double inSquare = 0.0; double pCircle = 0.0; double piCalc = 0.0; ssize_t transfersize = DEFAULT_TRANSFERSIZE; ssize_t blocksize = DEFAULT_BLOCKSIZE; char* transferBuffer = NULL; ssize_t buffersize; char inputFilename[MAXFILENAMELENGTH]; char outputFilename[MAXFILENAMELENGTH]; char outputFilenameBase[MAXFILENAMELENGTH]; ssize_t bytesRead = 0; ssize_t totalBytesRead = 0; int totalReads = 0; ssize_t bytesWritten = 0; ssize_t totalBytesWritten = 0; int totalWrites = 0; int inputFileResets = 0; pid_t pid, wpid; int j = 0; strncpy(inputFilename, DEFAULT_INPUTFILENAME, MAXFILENAMELENGTH); strncpy(outputFilenameBase, DEFAULT_OUTPUTFILENAMEBASE, MAXFILENAMELENGTH); if(argc < 2){ policy = SCHED_OTHER; } if(argc < 3){ num_processes = MED; } /* Set policy if supplied */ if(argc > 1){ if(!strcmp(argv[1], "SCHED_OTHER")){ policy = SCHED_OTHER; } else if(!strcmp(argv[1], "SCHED_FIFO")){ policy = SCHED_FIFO; } else if(!strcmp(argv[1], "SCHED_RR")){ policy = SCHED_RR; } else{ fprintf(stderr, "Unhandeled scheduling policy\n"); exit(EXIT_FAILURE); } } if(argc > 2){ if(!strcmp(argv[2], "LOW")){ num_processes = LOW; } else if(!strcmp(argv[2], "MED")){ num_processes = MED; } else if(!strcmp(argv[2], "HI")){ num_processes = HI; } else{ fprintf(stderr, "Unhandeled number of processes\n"); exit(EXIT_FAILURE); } } param.sched_priority = sched_get_priority_max(policy); /* Set new scheduler policy */ fprintf(stdout, "Current Scheduling Policy: %d\n", sched_getscheduler(0)); fprintf(stdout, "Setting Scheduling Policy to: %d\n", policy); if(sched_setscheduler(0, policy, ¶m)){ perror("Error setting scheduler policy"); exit(EXIT_FAILURE); } fprintf(stdout, "New Scheduling Policy: %d\n", sched_getscheduler(0)); printf("# Forks%d \n", num_processes); for(i = 0; i < num_processes; i++){ if((pid = fork())==-1){ fprintf(stderr, "Error Forking Child Process"); exit(EXIT_FAILURE); /*Fork Failed*/ } if(pid == 0){ /* Child Process */ /* Calculate pi using statistical methode across all iterations*/ for(i=0; i<iterations; i++){ x = (random() % (RADIUS * 2)) - RADIUS; y = (random() % (RADIUS * 2)) - RADIUS; if(zeroDist(x,y) < RADIUS){ inCircle++; } inSquare++; } /* Finish calculation */ pCircle = inCircle/inSquare; piCalc = pCircle * 4.0; /* Print result */ fprintf(stdout, "pi = %f\n", piCalc); /* Confirm blocksize is multiple of and less than transfersize*/ if(blocksize > transfersize){ fprintf(stderr, "blocksize can not exceed transfersize\n"); exit(EXIT_FAILURE); } if(transfersize % blocksize){ fprintf(stderr, "blocksize must be multiple of transfersize\n"); exit(EXIT_FAILURE); } /* Allocate buffer space */ buffersize = blocksize; if(!(transferBuffer = malloc(buffersize*sizeof(*transferBuffer)))){ perror("Failed to allocate transfer buffer"); exit(EXIT_FAILURE); } /* Open Input File Descriptor in Read Only mode */ if((inputFD = open(inputFilename, O_RDONLY | O_SYNC)) < 0){ perror("Failed to open input file"); exit(EXIT_FAILURE); } /* Open Output File Descriptor in Write Only mode with standard permissions*/ rv = snprintf(outputFilename, MAXFILENAMELENGTH, "%s-%d", outputFilenameBase, getpid()); if(rv > MAXFILENAMELENGTH){ fprintf(stderr, "Output filenmae length exceeds limit of %d characters.\n", MAXFILENAMELENGTH); exit(EXIT_FAILURE); } else if(rv < 0){ perror("Failed to generate output filename"); exit(EXIT_FAILURE); } if((outputFD = open(outputFilename, O_WRONLY | O_CREAT | O_TRUNC | O_SYNC, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH)) < 0){ perror("Failed to open output file"); exit(EXIT_FAILURE); } /* Print Status */ fprintf(stdout, "Reading from %s and writing to %s\n", inputFilename, outputFilename); /* Read from input file and write to output file*/ do{ /* Read transfersize bytes from input file*/ bytesRead = read(inputFD, transferBuffer, buffersize); if(bytesRead < 0){ perror("Error reading input file"); exit(EXIT_FAILURE); } else{ totalBytesRead += bytesRead; totalReads++; } /* If all bytes were read, write to output file*/ if(bytesRead == blocksize){ bytesWritten = write(outputFD, transferBuffer, bytesRead); if(bytesWritten < 0){ perror("Error writing output file"); exit(EXIT_FAILURE); } else{ totalBytesWritten += bytesWritten; totalWrites++; } } /* Otherwise assume we have reached the end of the input file and reset */ else{ if(lseek(inputFD, 0, SEEK_SET)){ perror("Error resetting to beginning of file"); exit(EXIT_FAILURE); } inputFileResets++; } }while(totalBytesWritten < transfersize); /* Output some possibly helpfull info to make it seem like we were doing stuff */ fprintf(stdout, "Read: %zd bytes in %d reads\n", totalBytesRead, totalReads); fprintf(stdout, "Written: %zd bytes in %d writes\n", totalBytesWritten, totalWrites); fprintf(stdout, "Read input file in %d pass%s\n", (inputFileResets + 1), (inputFileResets ? "es" : "")); fprintf(stdout, "Processed %zd bytes in blocks of %zd bytes\n", transfersize, blocksize); } } while((wpid = wait(&status)) > 0){ if(WIFEXITED(status)){ j++; } } printf("Total # forks terminated%d\n", j); return EXIT_SUCCESS; }
int test_control_priority() { int nzero = 0; int pri = 0; int ret; int pri_min, pri_max; int policy; pthread_attr_t attr; pid_t pid; struct sched_param s_param; cpu_set_t cpu_set; int cpu_total; int i; pthread_t thr; unsigned long long count = 0; #if 0 //设置CPU亲和性 cpu_total = get_nprocs(); printf("total cpu number: %d\n", cpu_total); CPU_ZERO(&cpu_set); CPU_SET(0, &cpu_set); // CPU_SET(1, &cpu_set); ret = sched_setaffinity(0, sizeof(cpu_set_t), &cpu_set); if (ret < 0) err_sys("sched_setaffinity"); CPU_ZERO(&cpu_set); ret = sched_getaffinity(0, sizeof(cpu_set_t), &cpu_set); for (i = 0; i < cpu_total; ++i) { if (CPU_ISSET(i, &cpu_set)) { printf("current process affinity cpu %d\n", i); } } // printf("sizeof(cpu_set_t) = %d\n", sizeof(cpu_set_t)); #endif #if defined(NZERO) nzero = NZERO; #elif defined(_SC_NZERO) nzero = sysconf(_SC_NZERO); #else #error NZERO undefined #endif //设置非实时进程优先级 // pri = getpriority(PRIO_PROCESS, 0); // printf("current priority: %d\n", pri); // ret = setpriority(PRIO_PROCESS, 0, -1); //优先级值越低,占有越多的CPU时间 // if (ret < 0) // err_sys("setpriority"); // pri = getpriority(PRIO_PROCESS, 0); // printf("current priority: %d\n", pri); #if 1 /////////////////////////////////// //创建测试线程 pthread_mutex_init(&priority_mutex, NULL); pthread_cond_init(&priority_cond, NULL); ret = pthread_barrier_init(&barrier, NULL, 2); if (ret != 0) err_exit(ret, "pthread_barrier_init"); ret = pthread_attr_init(&attr); if (ret != 0) err_exit(ret, "pthread_attr_init"); pthread_attr_setinheritsched(&attr, PTHREAD_EXPLICIT_SCHED); pthread_attr_setschedpolicy(&attr, SCHED_OTHER); s_param.__sched_priority = 0;//sched_get_priority_max(SCHED_RR)-11; pthread_attr_setschedparam(&attr, &s_param); gettimeofday(&end, NULL); end.tv_sec += 5; ret = pthread_create(&thr, &attr, priority_test_thread, NULL); if (ret != 0) err_exit(ret, "pthread_create"); pthread_attr_destroy(&attr); // ret= pthread_barrier_wait(&barrier); // printf("pthread_barrier_wait return %d\n", ret); // printf("main thread continue...\n"); // pthread_mutex_lock(&priority_mutex); // notify_signal = 1; // pthread_mutex_unlock(&priority_mutex); // ret = pthread_cond_signal(&priority_cond); // if (ret != 0) // err_exit(ret, "pthread_cond_signal"); //////////////////////////// //设置为实时进程 s_param.__sched_priority = sched_get_priority_max(SCHED_RR) - 10; ret = sched_setscheduler(0, SCHED_RR, &s_param); if (ret < 0) err_sys("sched_setscheduler"); policy = sched_getscheduler(0); if (policy < 0) err_sys("policy"); printf("main thread "); switch (policy) { case SCHED_FIFO: printf("policy SCHED_FIFO!\n"); break; case SCHED_RR: printf("policy SCHED_RR!\n"); break; case SCHED_OTHER: printf("policy SCHED_OTHER!\n"); break; default: printf("policy unknown!\n"); break; } ret = sched_getparam(0, &s_param); if (ret < 0) err_sys("sched_getparam"); printf("main thread priority: %d\n", s_param.__sched_priority); /////////////////////////// printf("main begin test...\n"); for (;;) { ++count; if (count == 0) err_quit("main count wrap"); if (checktime("main ", count) < 0) break; } printf("main wait for exit...\n"); pthread_join(thr, NULL); exit(0); #endif //////////////////////////////////// pri_max = sched_get_priority_max(SCHED_OTHER); //pri_max和pri_min都是0,分时调度由nice值影响优先级 pri_min = sched_get_priority_min(SCHED_OTHER); pri_max = sched_get_priority_max(SCHED_RR); pri_min = sched_get_priority_min(SCHED_RR); pri_max = sched_get_priority_max(SCHED_FIFO); pri_min = sched_get_priority_min(SCHED_FIFO); gettimeofday(&end, NULL); end.tv_sec += 10; pid = fork(); if (pid < 0) err_sys("fork"); else if (pid == 0) { policy = sched_getscheduler(0); printf("child process policy = %d\n", policy); ret = sched_getparam(0, &s_param); printf("child prirotiy: %d\n", s_param.__sched_priority); s_param.__sched_priority--; ret = sched_setparam(0, &s_param); if (ret < 0) err_sys("sched_setparam"); ret = sched_getparam(0, &s_param); printf("reset child prirotiy: %d\n", s_param.__sched_priority); // #if 1 // ret = setpriority(PRIO_PROCESS, 0, 19); // if (ret < 0) // err_sys("setpriority"); // #else // errno = 0; // if ((pri = nice(19)) == -1 && errno != 0) //nice函数被setpriority取代 // err_sys("nice"); // #endif // // errno = 0; // pri = getpriority(PRIO_PROCESS, 0); // if (pri == -1 && errno != 0) { // err_sys("getpriority"); // } // printf("child priority: %d\n", pri); for (;;) { ++count; if (count == 0) err_quit("child count wrap"); checktime("child ", count); } } else { // errno = 0; // pri = getpriority(PRIO_PROCESS, 0); // if (pri == -1 && errno != 0) { // err_sys("getpriority"); // } // printf("parent priority: %d\n", pri); for (;;) { ++count; if (count == 0) err_quit("parent count wrap"); checktime("parent", count); } } return 0; }
int main(){ int max_priority, old_priority, old_policy, new_policy, policy; struct sched_param param; /* We assume process Number 1 is created by root */ /* and can only be accessed by root */ /* This test should be run under standard user permissions */ if (getuid() == 0) { puts("Run this test case as a Regular User, but not ROOT"); return PTS_PASS; } if(sched_getparam(getpid(), ¶m) == -1) { perror("An error occurs when calling sched_getparam()"); return PTS_UNRESOLVED; } old_priority = param.sched_priority; old_policy = sched_getscheduler(getpid()); if(old_policy == -1) { perror("An error occurs when calling sched_getscheduler()"); return PTS_UNRESOLVED; } /* Make sure that policy != old_policy */ policy = old_policy == SCHED_FIFO ? SCHED_RR : SCHED_FIFO; /* Make sure that param.sched_priority != old_priority */ max_priority = sched_get_priority_max(policy); param.sched_priority = (old_priority == max_priority) ? sched_get_priority_min(policy) : max_priority; sched_setscheduler(1, policy, ¶m); if(sched_getparam(getpid(), ¶m) != 0) { perror("An error occurs when calling sched_getparam()"); return PTS_UNRESOLVED; } new_policy = sched_getscheduler(getpid()); if(new_policy == -1) { perror("An error occurs when calling sched_getscheduler()"); return PTS_UNRESOLVED; } if(old_policy == new_policy && old_priority == param.sched_priority) { printf("Test PASSED\n"); return PTS_PASS; } if(param.sched_priority != old_priority) { printf("The param has changed\n"); } if(new_policy != old_policy) { printf("The policy has changed\n"); } return PTS_FAIL; }
void timedwait_test(void) { pthread_t waiter; pthread_attr_t attr; struct sched_param sparam; void *result; int prio_max; int status; /* Initialize the mutex */ printf("thread_waiter: Initializing mutex\n"); status = pthread_mutex_init(&mutex, NULL); if (status != 0) { printf("timedwait_test: ERROR pthread_mutex_init failed, status=%d\n", status); } /* Initialize the condition variable */ printf("timedwait_test: Initializing cond\n"); status = pthread_cond_init(&cond, NULL); if (status != 0) { printf("timedwait_test: ERROR pthread_condinit failed, status=%d\n", status); } /* Start the waiter thread at higher priority */ printf("timedwait_test: Starting waiter\n"); status = pthread_attr_init(&attr); if (status != 0) { printf("timedwait_test: pthread_attr_init failed, status=%d\n", status); } prio_max = sched_get_priority_max(SCHED_FIFO); status = sched_getparam (getpid(), &sparam); if (status != 0) { printf("timedwait_test: sched_getparam failed\n"); sparam.sched_priority = PTHREAD_DEFAULT_PRIORITY; } sparam.sched_priority = (prio_max + sparam.sched_priority) / 2; status = pthread_attr_setschedparam(&attr,&sparam); if (status != OK) { printf("timedwait_test: pthread_attr_setschedparam failed, status=%d\n", status); } else { printf("timedwait_test: Set thread 2 priority to %d\n", sparam.sched_priority); } status = pthread_create(&waiter, &attr, thread_waiter, NULL); if (status != 0) { printf("timedwait_test: pthread_create failed, status=%d\n", status); } printf("timedwait_test: Joining\n"); FFLUSH(); status = pthread_join(waiter, &result); if (status != 0) { printf("timedwait_test: ERROR pthread_join failed, status=%d\n", status); } else { printf("timedwait_test: waiter exited with result=%p\n", result); } }
int mono_threads_platform_create_thread (MonoThreadStart thread_fn, gpointer thread_data, gsize* const stack_size, MonoNativeThreadId *out_tid) { pthread_attr_t attr; pthread_t thread; int policy; struct sched_param param; gint res; gsize set_stack_size; size_t min_size; res = pthread_attr_init (&attr); g_assert (!res); if (stack_size) set_stack_size = *stack_size; else set_stack_size = 0; #ifdef HAVE_PTHREAD_ATTR_SETSTACKSIZE if (set_stack_size == 0) { #if HAVE_VALGRIND_MEMCHECK_H if (RUNNING_ON_VALGRIND) set_stack_size = 1 << 20; else set_stack_size = (SIZEOF_VOID_P / 4) * 1024 * 1024; #else set_stack_size = (SIZEOF_VOID_P / 4) * 1024 * 1024; #endif } #ifdef PTHREAD_STACK_MIN if (set_stack_size < PTHREAD_STACK_MIN) set_stack_size = PTHREAD_STACK_MIN; #endif res = pthread_attr_setstacksize (&attr, set_stack_size); g_assert (!res); #endif /* HAVE_PTHREAD_ATTR_SETSTACKSIZE */ memset (¶m, 0, sizeof (param)); res = pthread_attr_getschedpolicy (&attr, &policy); if (res != 0) g_error ("%s: pthread_attr_getschedpolicy failed, error: \"%s\" (%d)", g_strerror (res), res); #ifdef _POSIX_PRIORITY_SCHEDULING int max, min; /* Necessary to get valid priority range */ min = sched_get_priority_min (policy); max = sched_get_priority_max (policy); if (max > 0 && min >= 0 && max > min) param.sched_priority = (max - min) / 2 + min; else #endif { switch (policy) { case SCHED_FIFO: case SCHED_RR: param.sched_priority = 50; break; #ifdef SCHED_BATCH case SCHED_BATCH: #endif case SCHED_OTHER: param.sched_priority = 0; break; default: g_error ("%s: unknown policy %d", __func__, policy); } } res = pthread_attr_setschedparam (&attr, ¶m); if (res != 0) g_error ("%s: pthread_attr_setschedparam failed, error: \"%s\" (%d)", g_strerror (res), res); if (stack_size) { res = pthread_attr_getstacksize (&attr, &min_size); if (res != 0) g_error ("%s: pthread_attr_getstacksize failed, error: \"%s\" (%d)", g_strerror (res), res); else *stack_size = min_size; } /* Actually start the thread */ res = mono_gc_pthread_create (&thread, &attr, (gpointer (*)(gpointer)) thread_fn, thread_data); if (res) return -1; if (out_tid) *out_tid = thread; return 0; }
static int ca_thread_func (void *arg) { struct alsa_stream* stream = (struct alsa_stream*) arg; snd_pcm_t* pcm = stream->ca_pcm; int size = stream->ca_buf_size; snd_pcm_uframes_t nframes = stream->ca_frames; void* user_data = stream->user_data; char* buf = stream->ca_buf; pj_timestamp tstamp; int result; struct sched_param param; pthread_t* thid; thid = (pthread_t*) pj_thread_get_os_handle (pj_thread_this()); param.sched_priority = sched_get_priority_max (SCHED_RR); PJ_LOG (5,(THIS_FILE, "ca_thread_func(%u): Set thread priority " "for audio capture thread.", (unsigned)syscall(SYS_gettid))); result = pthread_setschedparam (*thid, SCHED_RR, ¶m); if (result) { if (result == EPERM) PJ_LOG (5,(THIS_FILE, "Unable to increase thread priority, " "root access needed.")); else PJ_LOG (5,(THIS_FILE, "Unable to increase thread priority, " "error: %d", result)); } pj_bzero (buf, size); tstamp.u64 = 0; TRACE_((THIS_FILE, "ca_thread_func(%u): Started", (unsigned)syscall(SYS_gettid))); snd_pcm_prepare (pcm); while (!stream->quit) { pjmedia_frame frame; pj_bzero (buf, size); result = snd_pcm_readi (pcm, buf, nframes); if (result == -EPIPE) { PJ_LOG (4,(THIS_FILE, "ca_thread_func: overrun!")); snd_pcm_prepare (pcm); continue; } else if (result < 0) { PJ_LOG (4,(THIS_FILE, "ca_thread_func: error reading data!")); } if (stream->quit) break; frame.type = PJMEDIA_FRAME_TYPE_AUDIO; frame.buf = (void*) buf; frame.size = size; frame.timestamp.u64 = tstamp.u64; frame.bit_info = 0; result = stream->ca_cb (user_data, &frame); if (result != PJ_SUCCESS || stream->quit) break; tstamp.u64 += nframes; } snd_pcm_drain (pcm); TRACE_((THIS_FILE, "ca_thread_func: Stopped")); return PJ_SUCCESS; }
static int set_high_prio(MSTicker *obj){ int precision=2; int result=0; char* env_prio_c=NULL; //int min_prio, max_prio, env_prio; int prio=obj->prio; if (prio>MS_TICKER_PRIO_NORMAL){ #ifdef WIN32 MMRESULT mm; TIMECAPS ptc; mm=timeGetDevCaps(&ptc,sizeof(ptc)); if (mm==0){ if (ptc.wPeriodMin<(UINT)precision) ptc.wPeriodMin=precision; else precision = ptc.wPeriodMin; mm=timeBeginPeriod(ptc.wPeriodMin); if (mm!=TIMERR_NOERROR){ ms_warning("timeBeginPeriod failed."); } ms_message("win32 timer resolution set to %i ms",ptc.wPeriodMin); }else{ ms_warning("timeGetDevCaps failed."); } if(!SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_HIGHEST)){ ms_warning("SetThreadPriority() failed (%d)\n", GetLastError()); } #else struct sched_param param; int policy=SCHED_RR; memset(¶m,0,sizeof(param)); if (prio==MS_TICKER_PRIO_REALTIME) policy=SCHED_FIFO; min_prio = sched_get_priority_min(policy); max_prio = sched_get_priority_max(policy); env_prio_c = getenv("MS_TICKER_SCHEDPRIO"); env_prio = (env_prio_c == NULL)?max_prio:atoi(env_prio_c); env_prio = MAX(MIN(env_prio, max_prio), min_prio); ms_message("Priority used: %d", env_prio); param.sched_priority=env_prio; if((result=pthread_setschedparam(pthread_self(),policy, ¶m))) { if (result==EPERM){ /* The linux kernel has sched_get_priority_max(SCHED_OTHER)=sched_get_priority_max(SCHED_OTHER)=0. As long as we can't use SCHED_RR or SCHED_FIFO, the only way to increase priority of a calling thread is to use setpriority(). */ if (setpriority(PRIO_PROCESS,0,-20)==-1){ ms_message("%s setpriority() failed: %s, nevermind.",obj->name,strerror(errno)); }else{ ms_message("%s priority increased to maximum.",obj->name); } }else ms_warning("%s: Set pthread_setschedparam failed: %s",obj->name,strerror(result)); } else { ms_message("%s priority set to %s and value (%i)",obj->name, policy==SCHED_FIFO ? "SCHED_FIFO" : "SCHED_RR", param.sched_priority); } #endif } return precision; }
int main(int argc, char **argv) { bool slow = false, invoke_cpp = false, reseed = true, cpustats = true; bool prio_high = false, set_irq_aff = true; int c, opt_index, vals[4] = {0}, irq; uint64_t gap = 0; unsigned int i, j; char *confname = NULL, *ptr; unsigned long cpus_tmp, orig_num = 0; unsigned long long tx_packets, tx_bytes; struct ctx ctx; fmemset(&ctx, 0, sizeof(ctx)); ctx.cpus = get_number_cpus_online(); ctx.uid = getuid(); ctx.gid = getgid(); ctx.qdisc_path = false; while ((c = getopt_long(argc, argv, short_options, long_options, &opt_index)) != EOF) { switch (c) { case 'h': help(); break; case 'v': version(); break; case 'C': cpustats = false; break; case 'e': example(); break; case 'p': invoke_cpp = true; break; case 'V': ctx.verbose = true; break; case 'P': cpus_tmp = strtoul(optarg, NULL, 0); if (cpus_tmp > 0 && cpus_tmp < ctx.cpus) ctx.cpus = cpus_tmp; break; case 'd': case 'o': ctx.device = xstrndup(optarg, IFNAMSIZ); break; case 'H': prio_high = true; break; case 'Q': set_irq_aff = false; break; case 'q': ctx.qdisc_path = true; break; case 'r': ctx.rand = true; break; case 's': slow = true; ctx.cpus = 1; ctx.smoke_test = true; ctx.rhost = xstrdup(optarg); break; case 'R': ctx.rfraw = true; break; case 'J': ctx.jumbo_support = true; break; case 'c': case 'i': confname = xstrdup(optarg); if (!strncmp("-", confname, strlen("-"))) ctx.cpus = 1; break; case 'u': ctx.uid = strtoul(optarg, NULL, 0); ctx.enforce = true; break; case 'g': ctx.gid = strtoul(optarg, NULL, 0); ctx.enforce = true; break; case 'k': ctx.kpull = strtoul(optarg, NULL, 0); break; case 'E': seed = strtoul(optarg, NULL, 0); reseed = false; break; case 'n': orig_num = strtoul(optarg, NULL, 0); ctx.num = orig_num; break; case 't': slow = true; ptr = optarg; gap = strtoul(optarg, NULL, 0); for (j = i = strlen(optarg); i > 0; --i) { if (!isdigit(optarg[j - i])) break; ptr++; } if (!strncmp(ptr, "ns", strlen("ns"))) { ctx.gap.tv_sec = gap / 1000000000; ctx.gap.tv_nsec = gap % 1000000000; } else if (*ptr == '\0' || !strncmp(ptr, "us", strlen("us"))) { /* Default to microseconds for backwards * compatibility if no postfix is given. */ ctx.gap.tv_sec = gap / 1000000; ctx.gap.tv_nsec = (gap % 1000000) * 1000; } else if (!strncmp(ptr, "ms", strlen("ms"))) { ctx.gap.tv_sec = gap / 1000; ctx.gap.tv_nsec = (gap % 1000) * 1000000; } else if (!strncmp(ptr, "s", strlen("s"))) { ctx.gap.tv_sec = gap; ctx.gap.tv_nsec = 0; } else panic("Syntax error in time param!\n"); if (gap > 0) /* Fall back to single core to not mess up * correct timing. We are slow anyway! */ ctx.cpus = 1; break; case 'S': ptr = optarg; ctx.reserve_size = 0; for (j = i = strlen(optarg); i > 0; --i) { if (!isdigit(optarg[j - i])) break; ptr++; } if (!strncmp(ptr, "KiB", strlen("KiB"))) ctx.reserve_size = 1 << 10; else if (!strncmp(ptr, "MiB", strlen("MiB"))) ctx.reserve_size = 1 << 20; else if (!strncmp(ptr, "GiB", strlen("GiB"))) ctx.reserve_size = 1 << 30; else panic("Syntax error in ring size param!\n"); ctx.reserve_size *= strtol(optarg, NULL, 0); break; case '?': switch (optopt) { case 'd': case 'c': case 'n': case 'S': case 's': case 'P': case 'o': case 'E': case 'i': case 'k': case 'u': case 'g': case 't': panic("Option -%c requires an argument!\n", optopt); default: if (isprint(optopt)) printf("Unknown option character `0x%X\'!\n", optopt); die(); } default: break; } } if (argc < 5) help(); if (ctx.device == NULL) panic("No networking device given!\n"); if (confname == NULL) panic("No configuration file given!\n"); if (device_mtu(ctx.device) == 0) panic("This is no networking device!\n"); register_signal(SIGINT, signal_handler); register_signal(SIGQUIT, signal_handler); register_signal(SIGTERM, signal_handler); register_signal(SIGHUP, signal_handler); register_signal_f(SIGALRM, timer_elapsed, SA_SIGINFO); if (prio_high) { set_proc_prio(-20); set_sched_status(SCHED_FIFO, sched_get_priority_max(SCHED_FIFO)); } set_system_socket_memory(vals, array_size(vals)); xlockme(); if (ctx.rfraw) { ctx.device_trans = xstrdup(ctx.device); xfree(ctx.device); enter_rfmon_mac80211(ctx.device_trans, &ctx.device); sleep(0); } irq = device_irq_number(ctx.device); if (set_irq_aff) device_set_irq_affinity_list(irq, 0, ctx.cpus - 1); stats = setup_shared_var(ctx.cpus); for (i = 0; i < ctx.cpus; i++) { pid_t pid = fork(); switch (pid) { case 0: if (reseed) seed = generate_srand_seed(); srand(seed); cpu_affinity(i); main_loop(&ctx, confname, slow, i, invoke_cpp, orig_num); goto thread_out; case -1: panic("Cannot fork processes!\n"); } } for (i = 0; i < ctx.cpus; i++) { int status; wait(&status); if (WEXITSTATUS(status) == EXIT_FAILURE) die(); } if (ctx.rfraw) leave_rfmon_mac80211(ctx.device); reset_system_socket_memory(vals, array_size(vals)); for (i = 0, tx_packets = tx_bytes = 0; i < ctx.cpus; i++) { while ((__get_state(i) & CPU_STATS_STATE_RES) == 0) sched_yield(); tx_packets += stats[i].tx_packets; tx_bytes += stats[i].tx_bytes; } fflush(stdout); printf("\n"); printf("\r%12llu packets outgoing\n", tx_packets); printf("\r%12llu bytes outgoing\n", tx_bytes); for (i = 0; cpustats && i < ctx.cpus; i++) { printf("\r%12lu sec, %lu usec on CPU%d (%llu packets)\n", stats[i].tv_sec, stats[i].tv_usec, i, stats[i].tx_packets); } thread_out: xunlockme(); destroy_shared_var(stats, ctx.cpus); if (set_irq_aff) device_restore_irq_affinity_list(); free(ctx.device); free(ctx.device_trans); free(ctx.rhost); free(confname); return 0; }
/* Main function */ int main (int argc, char * argv[]) { int ret = 0, i; struct sigaction sa; pthread_barrier_t bar; pthread_attr_t ta[ 4 ]; pthread_t th[ NTHREADS ]; struct sched_param sp; /* Initialize output routine */ output_init(); /* Initialize barrier */ ret = pthread_barrier_init(&bar, NULL, 5); if (ret != 0) { UNRESOLVED(ret, "Failed to init barrier"); } /* Register the signal handler for SIGUSR1 */ sigemptyset (&sa.sa_mask); sa.sa_flags = 0; sa.sa_handler = sighdl; if ((ret = sigaction (SIGUSR1, &sa, NULL))) { UNRESOLVED(ret, "Unable to register signal handler"); } if ((ret = sigaction (SIGALRM, &sa, NULL))) { UNRESOLVED(ret, "Unable to register signal handler"); } #if VERBOSE > 1 output("[parent] Signal handler registered\n"); #endif td[ 0 ].policy = td[ 1 ].policy = SCHED_FIFO; td[ 2 ].policy = td[ 3 ].policy = SCHED_RR; td[ 0 ].prio = sched_get_priority_min(SCHED_FIFO); if (td[ 0 ].prio == -1) { UNRESOLVED(errno, "Failed to get scheduler range value"); } td[ 1 ].prio = sched_get_priority_max(SCHED_FIFO); if (td[ 1 ].prio == -1) { UNRESOLVED(errno, "Failed to get scheduler range value"); } td[ 2 ].prio = sched_get_priority_min(SCHED_RR); if (td[ 2 ].prio == -1) { UNRESOLVED(errno, "Failed to get scheduler range value"); } td[ 3 ].prio = sched_get_priority_max(SCHED_RR); if (td[ 3 ].prio == -1) { UNRESOLVED(errno, "Failed to get scheduler range value"); } /* Initialize the threads attributes and create the RT threads */ for (i = 0; i < 4; i++) { ret = pthread_attr_init(&ta[ i ]); if (ret != 0) { UNRESOLVED(ret, "Failed to initialize thread attribute"); } ret = pthread_attr_setinheritsched(&ta[ i ], PTHREAD_EXPLICIT_SCHED); if (ret != 0) { UNRESOLVED(ret, "Failed to set explicit scheduling attribute"); } sp.sched_priority = td[ i ].prio; ret = pthread_attr_setschedparam(&ta[ i ], &sp); if (ret != 0) { UNRESOLVED(ret, "failed to set thread attribute sched param"); } ret = pthread_attr_setschedpolicy(&ta[ i ], td[ i ].policy); if (ret != 0) { UNRESOLVED(ret, "failed to set thread attribute sched prio"); } ret = pthread_create(&td[ i ].thread, &ta[ i ], rt_thread, &bar); if (ret != 0) { UNRESOLVED(ret, "Failed to create a RT thread -- need more privilege?"); } } /* Create the worker threads */ for (i = 0; i < NTHREADS; i++) { ret = pthread_create(&th[ i ], NULL, threaded, NULL); if (ret != 0) { UNRESOLVED(ret, "failed to create a worker thread"); } } /* Wait for the worker threads to finish */ for (i = 0; i < NTHREADS; i++) { ret = pthread_join(th[ i ], NULL); if (ret != 0) { UNRESOLVED(ret, "failed to join a worker thread"); } } /* Join the barrier to terminate the RT threads */ ret = pthread_barrier_wait(&bar); if ((ret != 0) && (ret != PTHREAD_BARRIER_SERIAL_THREAD)) { UNRESOLVED(ret, "Failed to wait for the barrier"); } /* Join the RT threads */ for (i = 0; i < 4; i++) { ret = pthread_join(td[ i ].thread, NULL); if (ret != 0) { UNRESOLVED(ret, "Failed to join a thread"); } } /* Done! */ output("pthread_getschedparam stress test PASSED -- %llu iterations\n", iterations); ret = pthread_barrier_destroy(&bar); if (ret != 0) { UNRESOLVED(ret, "Failed to destroy the barrier"); } PASSED; }
/* This function will initialize every pthread_attr_t object in the scenarii array */ void scenar_init() { int ret=0; int i; int old; long pagesize, minstacksize; long tsa, tss, tps; pagesize =sysconf(_SC_PAGESIZE); minstacksize =sysconf(_SC_THREAD_STACK_MIN); tsa =sysconf(_SC_THREAD_ATTR_STACKADDR); tss =sysconf(_SC_THREAD_ATTR_STACKSIZE); tps =sysconf(_SC_THREAD_PRIORITY_SCHEDULING); #if VERBOSE > 0 output("System abilities:\n"); output(" TSA: %li\n", tsa); output(" TSS: %li\n", tss); output(" TPS: %li\n", tps); output(" pagesize: %li\n", pagesize); output(" min stack size: %li\n", minstacksize); #endif if (minstacksize % pagesize) { UNTESTED("The min stack size is not a multiple of the page size"); } for (i=0; i<NSCENAR; i++) { #if VERBOSE > 2 output("Initializing attribute for scenario %i: %s\n", i, scenarii[i].descr); #endif ret = pthread_attr_init(&scenarii[i].ta); if (ret != 0) { UNRESOLVED(ret, "Failed to initialize a thread attribute object"); } /* Set the attributes according to the scenario */ if (scenarii[i].detached == 1) { ret = pthread_attr_setdetachstate(&scenarii[i].ta, PTHREAD_CREATE_DETACHED); if (ret != 0) { UNRESOLVED(ret, "Unable to set detachstate"); } } else { ret = pthread_attr_getdetachstate(&scenarii[i].ta, &old); if (ret != 0) { UNRESOLVED(ret, "Unable to get detachstate from initialized attribute"); } if (old != PTHREAD_CREATE_JOINABLE) { FAILED("The default attribute is not PTHREAD_CREATE_JOINABLE"); } } #if VERBOSE > 4 output("Detach state was set sucessfully\n"); #endif /* Sched related attributes */ if (tps>0) /* This routine is dependent on the Thread Execution Scheduling option */ { if (scenarii[i].explicitsched == 1) ret = pthread_attr_setinheritsched(&scenarii[i].ta, PTHREAD_EXPLICIT_SCHED); else ret = pthread_attr_setinheritsched(&scenarii[i].ta, PTHREAD_INHERIT_SCHED); if (ret != 0) { UNRESOLVED(ret, "Unable to set inheritsched attribute"); } #if VERBOSE > 4 output("inheritsched state was set sucessfully\n"); #endif } #if VERBOSE > 4 else { output("TPS unsupported => inheritsched parameter untouched\n"); } #endif if (tps>0) /* This routine is dependent on the Thread Execution Scheduling option */ { if (scenarii[i].schedpolicy == 1) { ret = pthread_attr_setschedpolicy(&scenarii[i].ta, SCHED_FIFO); } if (scenarii[i].schedpolicy == 2) { ret = pthread_attr_setschedpolicy(&scenarii[i].ta, SCHED_RR); } if (ret != 0) { UNRESOLVED(ret, "Unable to set the sched policy"); } #if VERBOSE > 4 if (scenarii[i].schedpolicy) output("Sched policy was set sucessfully\n"); else output("Sched policy untouched\n"); #endif } #if VERBOSE > 4 else output("TPS unsupported => sched policy parameter untouched\n"); #endif if (scenarii[i].schedparam != 0) { struct sched_param sp; ret = pthread_attr_getschedpolicy(&scenarii[i].ta, &old); if (ret != 0) { UNRESOLVED(ret, "Unable to get sched policy from attribute"); } if (scenarii[i].schedparam == 1) sp.sched_priority = sched_get_priority_max(old); if (scenarii[i].schedparam == -1) sp.sched_priority = sched_get_priority_min(old); ret = pthread_attr_setschedparam(&scenarii[i].ta, &sp); if (ret != 0) { UNRESOLVED(ret, "Failed to set the sched param"); } #if VERBOSE > 4 output("Sched param was set sucessfully to %i\n", sp.sched_priority); } else { output("Sched param untouched\n"); #endif } if (tps>0) /* This routine is dependent on the Thread Execution Scheduling option */ { ret = pthread_attr_getscope(&scenarii[i].ta, &old); if (ret != 0) { UNRESOLVED(ret, "Failed to get contension scope from thread attribute"); } if (scenarii[i].altscope != 0) { if (old == PTHREAD_SCOPE_PROCESS) old = PTHREAD_SCOPE_SYSTEM; else old = PTHREAD_SCOPE_PROCESS; ret = pthread_attr_setscope(&scenarii[i].ta, old); //if (ret != 0) { UNRESOLVED(ret, "Failed to set contension scope"); } if (ret != 0) { output("WARNING: The TPS option is claimed to be supported but setscope fails\n"); } #if VERBOSE > 4 output("Contension scope set to %s\n", old==PTHREAD_SCOPE_PROCESS?"PTHREAD_SCOPE_PROCESS":"PTHREAD_SCOPE_SYSTEM"); } else { output("Contension scope untouched (%s)\n", old==PTHREAD_SCOPE_PROCESS?"PTHREAD_SCOPE_PROCESS":"PTHREAD_SCOPE_SYSTEM"); #endif } } #if VERBOSE > 4 else output("TPS unsupported => sched contension scope parameter untouched\n"); #endif /* Stack related attributes */ if ((tss>0) && (tsa>0)) /* This routine is dependent on the Thread Stack Address Attribute and Thread Stack Size Attribute options */ { if (scenarii[i].altstack != 0) { /* This is slightly more complicated. We need to alloc a new stack and free it upon test termination */ /* We will alloc with a simulated guardsize of 1 pagesize */ scenarii[i].bottom = malloc(minstacksize + pagesize); if (scenarii[i].bottom == NULL) { fprintf(stderr, "test %d\n", i); UNRESOLVED(errno,"Unable to alloc enough memory for alternative stack"); } ret = pthread_attr_setstack(&scenarii[i].ta, scenarii[i].bottom, minstacksize); if (ret != 0) { fprintf(stderr, "test %d pthread_attr_setstack did not return 0, returned %d\n", i, ret); UNRESOLVED(ret, "Failed to specify alternate stack, pthread_attr_setstack"); } #if VERBOSE > 1 output("Alternate stack created successfully. Bottom=%p, Size=%i\n", scenarii[i].bottom, minstacksize); #endif } } #if VERBOSE > 4 else { output("TSA or TSS unsupported => No alternative stack\n"); } #endif #ifndef WITHOUT_XOPEN if (scenarii[i].guard != 0) { if (scenarii[i].guard == 1){ ret = pthread_attr_setguardsize(&scenarii[i].ta, 0); } if (scenarii[i].guard == 2){ ret = pthread_attr_setguardsize(&scenarii[i].ta, pagesize); } if (ret != 0) { fprintf(stderr, "test %d, ret %d\n", i, ret); UNRESOLVED(ret, "Unable to set guard area size in thread stack"); } #if VERBOSE > 4 output("Guard size set to %i\n", (scenarii[i].guard==1)?1:pagesize); #endif } #endif if (tss>0) /* This routine is dependent on the Thread Stack Size Attribute option */ { if (scenarii[i].altsize != 0) { ret = pthread_attr_setstacksize(&scenarii[i].ta, minstacksize); if (ret != 0) { fprintf(stderr, "test %d, ret %d\n", i, ret); UNRESOLVED(ret, "Unable to change stack size"); } #if VERBOSE > 4 output("Stack size set to %i (this is the min)\n", minstacksize); #endif } } #if VERBOSE > 4 else output("TSS unsupported => stack size unchanged\n"); #endif ret = sem_init(&scenarii[i].sem, 0,0); if (ret == -1) { UNRESOLVED(errno, "Unable to init a semaphore"); } } #if VERBOSE > 0 output("All %i thread attribute objects were initialized\n\n", NSCENAR); #endif }