hotspot/src/os/solaris/vm/os_solaris.cpp
changeset 11601 f359304c1856
parent 11483 4d3f4bca0019
child 11719 24a1d0e00c7e
equal deleted inserted replaced
11600:48468ad48e4c 11601:f359304c1856
     1 /*
     1 /*
     2  * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
     2  * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.
     7  * published by the Free Software Foundation.
   112 # include <unistd.h>
   112 # include <unistd.h>
   113 # include <sys/priocntl.h>
   113 # include <sys/priocntl.h>
   114 # include <sys/rtpriocntl.h>
   114 # include <sys/rtpriocntl.h>
   115 # include <sys/tspriocntl.h>
   115 # include <sys/tspriocntl.h>
   116 # include <sys/iapriocntl.h>
   116 # include <sys/iapriocntl.h>
       
   117 # include <sys/fxpriocntl.h>
   117 # include <sys/loadavg.h>
   118 # include <sys/loadavg.h>
   118 # include <string.h>
   119 # include <string.h>
   119 # include <stdio.h>
   120 # include <stdio.h>
   120 
   121 
   121 # define _STRUCTURED_PROC 1  //  this gets us the new structured proc interfaces of 5.6 & later
   122 # define _STRUCTURED_PROC 1  //  this gets us the new structured proc interfaces of 5.6 & later
   127 #define ALL_64_BITS CONST64(0xFFFFFFFFFFFFFFFF)
   128 #define ALL_64_BITS CONST64(0xFFFFFFFFFFFFFFFF)
   128 
   129 
   129 #ifdef _GNU_SOURCE
   130 #ifdef _GNU_SOURCE
   130 // See bug #6514594
   131 // See bug #6514594
   131 extern "C" int madvise(caddr_t, size_t, int);
   132 extern "C" int madvise(caddr_t, size_t, int);
   132 extern "C"  int memcntl(caddr_t addr, size_t len, int cmd, caddr_t  arg,
   133 extern "C" int memcntl(caddr_t addr, size_t len, int cmd, caddr_t arg,
   133      int attr, int mask);
   134                        int attr, int mask);
   134 #endif //_GNU_SOURCE
   135 #endif //_GNU_SOURCE
   135 
   136 
   136 /*
   137 /*
   137   MPSS Changes Start.
   138   MPSS Changes Start.
   138   The JVM binary needs to be built and run on pre-Solaris 9
   139   The JVM binary needs to be built and run on pre-Solaris 9
   213 #define MinimumPriority 0
   214 #define MinimumPriority 0
   214 #define NormalPriority  64
   215 #define NormalPriority  64
   215 #define MaximumPriority 127
   216 #define MaximumPriority 127
   216 
   217 
   217 // Values for ThreadPriorityPolicy == 1
   218 // Values for ThreadPriorityPolicy == 1
   218 int prio_policy1[MaxPriority+1] = { -99999, 0, 16, 32, 48, 64,
   219 int prio_policy1[CriticalPriority+1] = {
   219                                         80, 96, 112, 124, 127 };
   220   -99999,  0, 16,  32,  48,  64,
       
   221           80, 96, 112, 124, 127, 127 };
   220 
   222 
   221 // System parameters used internally
   223 // System parameters used internally
   222 static clock_t clock_tics_per_sec = 100;
   224 static clock_t clock_tics_per_sec = 100;
   223 
   225 
   224 // Track if we have called enable_extended_FILE_stdio (on Solaris 10u4+)
   226 // Track if we have called enable_extended_FILE_stdio (on Solaris 10u4+)
  1046       thread->set_lgrp_id(lgrp_id);
  1048       thread->set_lgrp_id(lgrp_id);
  1047     }
  1049     }
  1048   }
  1050   }
  1049 
  1051 
  1050   // If the creator called set priority before we started,
  1052   // If the creator called set priority before we started,
  1051   // we need to call set priority now that we have an lwp.
  1053   // we need to call set_native_priority now that we have an lwp.
  1052   // Get the priority from libthread and set the priority
  1054   // We used to get the priority from thr_getprio (we called
  1053   // for the new Solaris lwp.
  1055   // thr_setprio way back in create_thread) and pass it to
       
  1056   // set_native_priority, but Solaris scales the priority
       
  1057   // in java_to_os_priority, so when we read it back here,
       
  1058   // we pass trash to set_native_priority instead of what's
       
  1059   // in java_to_os_priority. So we save the native priority
       
  1060   // in the osThread and recall it here.
       
  1061 
  1054   if ( osthr->thread_id() != -1 ) {
  1062   if ( osthr->thread_id() != -1 ) {
  1055     if ( UseThreadPriorities ) {
  1063     if ( UseThreadPriorities ) {
  1056       thr_getprio(osthr->thread_id(), &prio);
  1064       int prio = osthr->native_priority();
  1057       if (ThreadPriorityVerbose) {
  1065       if (ThreadPriorityVerbose) {
  1058         tty->print_cr("Starting Thread " INTPTR_FORMAT ", LWP is " INTPTR_FORMAT ", setting priority: %d\n",
  1066         tty->print_cr("Starting Thread " INTPTR_FORMAT ", LWP is "
  1059                       osthr->thread_id(), osthr->lwp_id(), prio );
  1067                       INTPTR_FORMAT ", setting priority: %d\n",
       
  1068                       osthr->thread_id(), osthr->lwp_id(), prio);
  1060       }
  1069       }
  1061       os::set_native_priority(thread, prio);
  1070       os::set_native_priority(thread, prio);
  1062     }
  1071     }
  1063   } else if (ThreadPriorityVerbose) {
  1072   } else if (ThreadPriorityVerbose) {
  1064     warning("Can't set priority in _start routine, thread id hasn't been set\n");
  1073     warning("Can't set priority in _start routine, thread id hasn't been set\n");
  1351   osthread->set_thread_id(tid);
  1360   osthread->set_thread_id(tid);
  1352 
  1361 
  1353   // Remember that we created this thread so we can set priority on it
  1362   // Remember that we created this thread so we can set priority on it
  1354   osthread->set_vm_created();
  1363   osthread->set_vm_created();
  1355 
  1364 
  1356   // Set the default thread priority otherwise use NormalPriority
  1365   // Set the default thread priority.  If using bound threads, setting
  1357 
  1366   // lwp priority will be delayed until thread start.
  1358   if ( UseThreadPriorities ) {
  1367   set_native_priority(thread,
  1359      thr_setprio(tid, (DefaultThreadPriority == -1) ?
  1368                       DefaultThreadPriority == -1 ?
  1360                         java_to_os_priority[NormPriority] :
  1369                         java_to_os_priority[NormPriority] :
  1361                         DefaultThreadPriority);
  1370                         DefaultThreadPriority);
  1362   }
       
  1363 
  1371 
  1364   // Initial thread state is INITIALIZED, not SUSPENDED
  1372   // Initial thread state is INITIALIZED, not SUSPENDED
  1365   osthread->set_state(INITIALIZED);
  1373   osthread->set_state(INITIALIZED);
  1366 
  1374 
  1367   // The thread is returned suspended (in state INITIALIZED), and is started higher up in the call chain
  1375   // The thread is returned suspended (in state INITIALIZED), and is started higher up in the call chain
  3726         int   maxPrio;
  3734         int   maxPrio;
  3727         int   minPrio;
  3735         int   minPrio;
  3728 } SchedInfo;
  3736 } SchedInfo;
  3729 
  3737 
  3730 
  3738 
  3731 static SchedInfo tsLimits, iaLimits, rtLimits;
  3739 static SchedInfo tsLimits, iaLimits, rtLimits, fxLimits;
  3732 
  3740 
  3733 #ifdef ASSERT
  3741 #ifdef ASSERT
  3734 static int  ReadBackValidate = 1;
  3742 static int  ReadBackValidate = 1;
  3735 #endif
  3743 #endif
  3736 static int  myClass     = 0;
  3744 static int  myClass     = 0;
  3737 static int  myMin       = 0;
  3745 static int  myMin       = 0;
  3738 static int  myMax       = 0;
  3746 static int  myMax       = 0;
  3739 static int  myCur       = 0;
  3747 static int  myCur       = 0;
  3740 static bool priocntl_enable = false;
  3748 static bool priocntl_enable = false;
  3741 
  3749 
       
  3750 static const int criticalPrio = 60; // FX/60 is critical thread class/priority on T4
       
  3751 static int java_MaxPriority_to_os_priority = 0; // Saved mapping
  3742 
  3752 
  3743 // Call the version of priocntl suitable for all supported versions
  3753 // Call the version of priocntl suitable for all supported versions
  3744 // of Solaris. We need to call through this wrapper so that we can
  3754 // of Solaris. We need to call through this wrapper so that we can
  3745 // build on Solaris 9 and run on Solaris 8, 9 and 10.
  3755 // build on Solaris 9 and run on Solaris 8, 9 and 10.
  3746 //
  3756 //
  3781 
  3791 
  3782   // We are using Bound threads, we need to determine our priority ranges
  3792   // We are using Bound threads, we need to determine our priority ranges
  3783   if (os::Solaris::T2_libthread() || UseBoundThreads) {
  3793   if (os::Solaris::T2_libthread() || UseBoundThreads) {
  3784     // If ThreadPriorityPolicy is 1, switch tables
  3794     // If ThreadPriorityPolicy is 1, switch tables
  3785     if (ThreadPriorityPolicy == 1) {
  3795     if (ThreadPriorityPolicy == 1) {
  3786       for (i = 0 ; i < MaxPriority+1; i++)
  3796       for (i = 0 ; i < CriticalPriority+1; i++)
  3787         os::java_to_os_priority[i] = prio_policy1[i];
  3797         os::java_to_os_priority[i] = prio_policy1[i];
       
  3798     }
       
  3799     if (UseCriticalJavaThreadPriority) {
       
  3800       // MaxPriority always maps to the FX scheduling class and criticalPrio.
       
  3801       // See set_native_priority() and set_lwp_class_and_priority().
       
  3802       // Save original MaxPriority mapping in case attempt to
       
  3803       // use critical priority fails.
       
  3804       java_MaxPriority_to_os_priority = os::java_to_os_priority[MaxPriority];
       
  3805       // Set negative to distinguish from other priorities
       
  3806       os::java_to_os_priority[MaxPriority] = -criticalPrio;
  3788     }
  3807     }
  3789   }
  3808   }
  3790   // Not using Bound Threads, set to ThreadPolicy 1
  3809   // Not using Bound Threads, set to ThreadPolicy 1
  3791   else {
  3810   else {
  3792     for ( i = 0 ; i < MaxPriority+1; i++ ) {
  3811     for ( i = 0 ; i < CriticalPriority+1; i++ ) {
  3793       os::java_to_os_priority[i] = prio_policy1[i];
  3812       os::java_to_os_priority[i] = prio_policy1[i];
  3794     }
  3813     }
  3795     return 0;
  3814     return 0;
  3796   }
  3815   }
  3797 
       
  3798 
  3816 
  3799   // Get IDs for a set of well-known scheduling classes.
  3817   // Get IDs for a set of well-known scheduling classes.
  3800   // TODO-FIXME: GETCLINFO returns the current # of classes in the
  3818   // TODO-FIXME: GETCLINFO returns the current # of classes in the
  3801   // the system.  We should have a loop that iterates over the
  3819   // the system.  We should have a loop that iterates over the
  3802   // classID values, which are known to be "small" integers.
  3820   // classID values, which are known to be "small" integers.
  3826   assert(ClassInfo.pc_cid != -1, "cid for RT class is -1");
  3844   assert(ClassInfo.pc_cid != -1, "cid for RT class is -1");
  3827   rtLimits.schedPolicy = ClassInfo.pc_cid;
  3845   rtLimits.schedPolicy = ClassInfo.pc_cid;
  3828   rtLimits.maxPrio = ((rtinfo_t*)ClassInfo.pc_clinfo)->rt_maxpri;
  3846   rtLimits.maxPrio = ((rtinfo_t*)ClassInfo.pc_clinfo)->rt_maxpri;
  3829   rtLimits.minPrio = 0;
  3847   rtLimits.minPrio = 0;
  3830 
  3848 
       
  3849   strcpy(ClassInfo.pc_clname, "FX");
       
  3850   ClassInfo.pc_cid = -1;
       
  3851   rslt = (*priocntl_ptr)(PC_VERSION, P_ALL, 0, PC_GETCID, (caddr_t)&ClassInfo);
       
  3852   if (rslt < 0) return errno;
       
  3853   assert(ClassInfo.pc_cid != -1, "cid for FX class is -1");
       
  3854   fxLimits.schedPolicy = ClassInfo.pc_cid;
       
  3855   fxLimits.maxPrio = ((fxinfo_t*)ClassInfo.pc_clinfo)->fx_maxupri;
       
  3856   fxLimits.minPrio = 0;
  3831 
  3857 
  3832   // Query our "current" scheduling class.
  3858   // Query our "current" scheduling class.
  3833   // This will normally be IA,TS or, rarely, RT.
  3859   // This will normally be IA, TS or, rarely, FX or RT.
  3834   memset (&ParmInfo, 0, sizeof(ParmInfo));
  3860   memset(&ParmInfo, 0, sizeof(ParmInfo));
  3835   ParmInfo.pc_cid = PC_CLNULL;
  3861   ParmInfo.pc_cid = PC_CLNULL;
  3836   rslt = (*priocntl_ptr) (PC_VERSION, P_PID, P_MYID, PC_GETPARMS, (caddr_t)&ParmInfo );
  3862   rslt = (*priocntl_ptr) (PC_VERSION, P_PID, P_MYID, PC_GETPARMS, (caddr_t)&ParmInfo);
  3837   if ( rslt < 0 ) return errno;
  3863   if (rslt < 0) return errno;
  3838   myClass = ParmInfo.pc_cid;
  3864   myClass = ParmInfo.pc_cid;
  3839 
  3865 
  3840   // We now know our scheduling classId, get specific information
  3866   // We now know our scheduling classId, get specific information
  3841   // the class.
  3867   // about the class.
  3842   ClassInfo.pc_cid = myClass;
  3868   ClassInfo.pc_cid = myClass;
  3843   ClassInfo.pc_clname[0] = 0;
  3869   ClassInfo.pc_clname[0] = 0;
  3844   rslt = (*priocntl_ptr) (PC_VERSION, (idtype)0, 0, PC_GETCLINFO, (caddr_t)&ClassInfo );
  3870   rslt = (*priocntl_ptr) (PC_VERSION, (idtype)0, 0, PC_GETCLINFO, (caddr_t)&ClassInfo);
  3845   if ( rslt < 0 ) return errno;
  3871   if (rslt < 0) return errno;
  3846 
  3872 
  3847   if (ThreadPriorityVerbose)
  3873   if (ThreadPriorityVerbose) {
  3848     tty->print_cr ("lwp_priocntl_init: Class=%d(%s)...", myClass, ClassInfo.pc_clname);
  3874     tty->print_cr("lwp_priocntl_init: Class=%d(%s)...", myClass, ClassInfo.pc_clname);
       
  3875   }
  3849 
  3876 
  3850   memset(&ParmInfo, 0, sizeof(pcparms_t));
  3877   memset(&ParmInfo, 0, sizeof(pcparms_t));
  3851   ParmInfo.pc_cid = PC_CLNULL;
  3878   ParmInfo.pc_cid = PC_CLNULL;
  3852   rslt = (*priocntl_ptr)(PC_VERSION, P_PID, P_MYID, PC_GETPARMS, (caddr_t)&ParmInfo);
  3879   rslt = (*priocntl_ptr)(PC_VERSION, P_PID, P_MYID, PC_GETPARMS, (caddr_t)&ParmInfo);
  3853   if (rslt < 0) return errno;
  3880   if (rslt < 0) return errno;
  3863   } else if (ParmInfo.pc_cid == tsLimits.schedPolicy) {
  3890   } else if (ParmInfo.pc_cid == tsLimits.schedPolicy) {
  3864     tsparms_t *tsInfo  = (tsparms_t*)ParmInfo.pc_clparms;
  3891     tsparms_t *tsInfo  = (tsparms_t*)ParmInfo.pc_clparms;
  3865     myMin = tsLimits.minPrio;
  3892     myMin = tsLimits.minPrio;
  3866     myMax = tsLimits.maxPrio;
  3893     myMax = tsLimits.maxPrio;
  3867     myMax = MIN2(myMax, (int)tsInfo->ts_uprilim);       // clamp - restrict
  3894     myMax = MIN2(myMax, (int)tsInfo->ts_uprilim);       // clamp - restrict
       
  3895   } else if (ParmInfo.pc_cid == fxLimits.schedPolicy) {
       
  3896     fxparms_t *fxInfo = (fxparms_t*)ParmInfo.pc_clparms;
       
  3897     myMin = fxLimits.minPrio;
       
  3898     myMax = fxLimits.maxPrio;
       
  3899     myMax = MIN2(myMax, (int)fxInfo->fx_uprilim);       // clamp - restrict
  3868   } else {
  3900   } else {
  3869     // No clue - punt
  3901     // No clue - punt
  3870     if (ThreadPriorityVerbose)
  3902     if (ThreadPriorityVerbose)
  3871       tty->print_cr ("Unknown scheduling class: %s ... \n", ClassInfo.pc_clname);
  3903       tty->print_cr ("Unknown scheduling class: %s ... \n", ClassInfo.pc_clname);
  3872     return EINVAL;      // no clue, punt
  3904     return EINVAL;      // no clue, punt
  3873   }
  3905   }
  3874 
  3906 
  3875   if (ThreadPriorityVerbose)
  3907   if (ThreadPriorityVerbose) {
  3876         tty->print_cr ("Thread priority Range: [%d..%d]\n", myMin, myMax);
  3908     tty->print_cr ("Thread priority Range: [%d..%d]\n", myMin, myMax);
       
  3909   }
  3877 
  3910 
  3878   priocntl_enable = true;  // Enable changing priorities
  3911   priocntl_enable = true;  // Enable changing priorities
  3879   return 0;
  3912   return 0;
  3880 }
  3913 }
  3881 
  3914 
  3882 #define IAPRI(x)        ((iaparms_t *)((x).pc_clparms))
  3915 #define IAPRI(x)        ((iaparms_t *)((x).pc_clparms))
  3883 #define RTPRI(x)        ((rtparms_t *)((x).pc_clparms))
  3916 #define RTPRI(x)        ((rtparms_t *)((x).pc_clparms))
  3884 #define TSPRI(x)        ((tsparms_t *)((x).pc_clparms))
  3917 #define TSPRI(x)        ((tsparms_t *)((x).pc_clparms))
       
  3918 #define FXPRI(x)        ((fxparms_t *)((x).pc_clparms))
  3885 
  3919 
  3886 
  3920 
  3887 // scale_to_lwp_priority
  3921 // scale_to_lwp_priority
  3888 //
  3922 //
  3889 // Convert from the libthread "thr_setprio" scale to our current
  3923 // Convert from the libthread "thr_setprio" scale to our current
  3898     v = (((x*(rMax-rMin)))/128)+rMin;
  3932     v = (((x*(rMax-rMin)))/128)+rMin;
  3899   return v;
  3933   return v;
  3900 }
  3934 }
  3901 
  3935 
  3902 
  3936 
  3903 // set_lwp_priority
  3937 // set_lwp_class_and_priority
  3904 //
  3938 //
  3905 // Set the priority of the lwp.  This call should only be made
  3939 // Set the class and priority of the lwp.  This call should only
  3906 // when using bound threads (T2 threads are bound by default).
  3940 // be made when using bound threads (T2 threads are bound by default).
  3907 //
  3941 //
  3908 int     set_lwp_priority (int ThreadID, int lwpid, int newPrio )
  3942 int set_lwp_class_and_priority(int ThreadID, int lwpid,
  3909 {
  3943                                int newPrio, int new_class, bool scale) {
  3910   int rslt;
  3944   int rslt;
  3911   int Actual, Expected, prv;
  3945   int Actual, Expected, prv;
  3912   pcparms_t ParmInfo;                   // for GET-SET
  3946   pcparms_t ParmInfo;                   // for GET-SET
  3913 #ifdef ASSERT
  3947 #ifdef ASSERT
  3914   pcparms_t ReadBack;                   // for readback
  3948   pcparms_t ReadBack;                   // for readback
  3925     if (ThreadPriorityVerbose)
  3959     if (ThreadPriorityVerbose)
  3926       tty->print_cr("Trying to set priority but init failed, ignoring");
  3960       tty->print_cr("Trying to set priority but init failed, ignoring");
  3927     return EINVAL;
  3961     return EINVAL;
  3928   }
  3962   }
  3929 
  3963 
  3930 
       
  3931   // If lwp hasn't started yet, just return
  3964   // If lwp hasn't started yet, just return
  3932   // the _start routine will call us again.
  3965   // the _start routine will call us again.
  3933   if ( lwpid <= 0 ) {
  3966   if ( lwpid <= 0 ) {
  3934     if (ThreadPriorityVerbose) {
  3967     if (ThreadPriorityVerbose) {
  3935       tty->print_cr ("deferring the set_lwp_priority of thread " INTPTR_FORMAT " to %d, lwpid not set",
  3968       tty->print_cr ("deferring the set_lwp_class_and_priority of thread "
       
  3969                      INTPTR_FORMAT " to %d, lwpid not set",
  3936                      ThreadID, newPrio);
  3970                      ThreadID, newPrio);
  3937     }
  3971     }
  3938     return 0;
  3972     return 0;
  3939   }
  3973   }
  3940 
  3974 
  3941   if (ThreadPriorityVerbose) {
  3975   if (ThreadPriorityVerbose) {
  3942     tty->print_cr ("set_lwp_priority(" INTPTR_FORMAT "@" INTPTR_FORMAT " %d) ",
  3976     tty->print_cr ("set_lwp_class_and_priority("
       
  3977                    INTPTR_FORMAT "@" INTPTR_FORMAT " %d) ",
  3943                    ThreadID, lwpid, newPrio);
  3978                    ThreadID, lwpid, newPrio);
  3944   }
  3979   }
  3945 
  3980 
  3946   memset(&ParmInfo, 0, sizeof(pcparms_t));
  3981   memset(&ParmInfo, 0, sizeof(pcparms_t));
  3947   ParmInfo.pc_cid = PC_CLNULL;
  3982   ParmInfo.pc_cid = PC_CLNULL;
  3948   rslt = (*priocntl_ptr)(PC_VERSION, P_LWPID, lwpid, PC_GETPARMS, (caddr_t)&ParmInfo);
  3983   rslt = (*priocntl_ptr)(PC_VERSION, P_LWPID, lwpid, PC_GETPARMS, (caddr_t)&ParmInfo);
  3949   if (rslt < 0) return errno;
  3984   if (rslt < 0) return errno;
  3950 
  3985 
  3951   if (ParmInfo.pc_cid == rtLimits.schedPolicy) {
  3986   int cur_class = ParmInfo.pc_cid;
       
  3987   ParmInfo.pc_cid = (id_t)new_class;
       
  3988 
       
  3989   if (new_class == rtLimits.schedPolicy) {
  3952     rtparms_t *rtInfo  = (rtparms_t*)ParmInfo.pc_clparms;
  3990     rtparms_t *rtInfo  = (rtparms_t*)ParmInfo.pc_clparms;
  3953     rtInfo->rt_pri     = scale_to_lwp_priority (rtLimits.minPrio, rtLimits.maxPrio, newPrio);
  3991     rtInfo->rt_pri     = scale ? scale_to_lwp_priority(rtLimits.minPrio,
       
  3992                                                        rtLimits.maxPrio, newPrio)
       
  3993                                : newPrio;
  3954     rtInfo->rt_tqsecs  = RT_NOCHANGE;
  3994     rtInfo->rt_tqsecs  = RT_NOCHANGE;
  3955     rtInfo->rt_tqnsecs = RT_NOCHANGE;
  3995     rtInfo->rt_tqnsecs = RT_NOCHANGE;
  3956     if (ThreadPriorityVerbose) {
  3996     if (ThreadPriorityVerbose) {
  3957       tty->print_cr("RT: %d->%d\n", newPrio, rtInfo->rt_pri);
  3997       tty->print_cr("RT: %d->%d\n", newPrio, rtInfo->rt_pri);
  3958     }
  3998     }
  3959   } else if (ParmInfo.pc_cid == iaLimits.schedPolicy) {
  3999   } else if (new_class == iaLimits.schedPolicy) {
  3960     iaparms_t *iaInfo  = (iaparms_t*)ParmInfo.pc_clparms;
  4000     iaparms_t* iaInfo  = (iaparms_t*)ParmInfo.pc_clparms;
  3961     int maxClamped     = MIN2(iaLimits.maxPrio, (int)iaInfo->ia_uprilim);
  4001     int maxClamped     = MIN2(iaLimits.maxPrio,
  3962     iaInfo->ia_upri    = scale_to_lwp_priority(iaLimits.minPrio, maxClamped, newPrio);
  4002                               cur_class == new_class
  3963     iaInfo->ia_uprilim = IA_NOCHANGE;
  4003                                 ? (int)iaInfo->ia_uprilim : iaLimits.maxPrio);
       
  4004     iaInfo->ia_upri    = scale ? scale_to_lwp_priority(iaLimits.minPrio,
       
  4005                                                        maxClamped, newPrio)
       
  4006                                : newPrio;
       
  4007     iaInfo->ia_uprilim = cur_class == new_class
       
  4008                            ? IA_NOCHANGE : (pri_t)iaLimits.maxPrio;
  3964     iaInfo->ia_mode    = IA_NOCHANGE;
  4009     iaInfo->ia_mode    = IA_NOCHANGE;
       
  4010     iaInfo->ia_nice    = cur_class == new_class ? IA_NOCHANGE : NZERO;
  3965     if (ThreadPriorityVerbose) {
  4011     if (ThreadPriorityVerbose) {
  3966       tty->print_cr ("IA: [%d...%d] %d->%d\n",
  4012       tty->print_cr("IA: [%d...%d] %d->%d\n",
  3967                iaLimits.minPrio, maxClamped, newPrio, iaInfo->ia_upri);
  4013                     iaLimits.minPrio, maxClamped, newPrio, iaInfo->ia_upri);
  3968     }
  4014     }
  3969   } else if (ParmInfo.pc_cid == tsLimits.schedPolicy) {
  4015   } else if (new_class == tsLimits.schedPolicy) {
  3970     tsparms_t *tsInfo  = (tsparms_t*)ParmInfo.pc_clparms;
  4016     tsparms_t* tsInfo  = (tsparms_t*)ParmInfo.pc_clparms;
  3971     int maxClamped     = MIN2(tsLimits.maxPrio, (int)tsInfo->ts_uprilim);
  4017     int maxClamped     = MIN2(tsLimits.maxPrio,
  3972     prv                = tsInfo->ts_upri;
  4018                               cur_class == new_class
  3973     tsInfo->ts_upri    = scale_to_lwp_priority(tsLimits.minPrio, maxClamped, newPrio);
  4019                                 ? (int)tsInfo->ts_uprilim : tsLimits.maxPrio);
  3974     tsInfo->ts_uprilim = IA_NOCHANGE;
  4020     tsInfo->ts_upri    = scale ? scale_to_lwp_priority(tsLimits.minPrio,
       
  4021                                                        maxClamped, newPrio)
       
  4022                                : newPrio;
       
  4023     tsInfo->ts_uprilim = cur_class == new_class
       
  4024                            ? TS_NOCHANGE : (pri_t)tsLimits.maxPrio;
  3975     if (ThreadPriorityVerbose) {
  4025     if (ThreadPriorityVerbose) {
  3976       tty->print_cr ("TS: %d [%d...%d] %d->%d\n",
  4026       tty->print_cr("TS: [%d...%d] %d->%d\n",
  3977                prv, tsLimits.minPrio, maxClamped, newPrio, tsInfo->ts_upri);
  4027                     tsLimits.minPrio, maxClamped, newPrio, tsInfo->ts_upri);
  3978     }
  4028     }
  3979     if (prv == tsInfo->ts_upri) return 0;
  4029   } else if (new_class == fxLimits.schedPolicy) {
       
  4030     fxparms_t* fxInfo  = (fxparms_t*)ParmInfo.pc_clparms;
       
  4031     int maxClamped     = MIN2(fxLimits.maxPrio,
       
  4032                               cur_class == new_class
       
  4033                                 ? (int)fxInfo->fx_uprilim : fxLimits.maxPrio);
       
  4034     fxInfo->fx_upri    = scale ? scale_to_lwp_priority(fxLimits.minPrio,
       
  4035                                                        maxClamped, newPrio)
       
  4036                                : newPrio;
       
  4037     fxInfo->fx_uprilim = cur_class == new_class
       
  4038                            ? FX_NOCHANGE : (pri_t)fxLimits.maxPrio;
       
  4039     fxInfo->fx_tqsecs  = FX_NOCHANGE;
       
  4040     fxInfo->fx_tqnsecs = FX_NOCHANGE;
       
  4041     if (ThreadPriorityVerbose) {
       
  4042       tty->print_cr("FX: [%d...%d] %d->%d\n",
       
  4043                     fxLimits.minPrio, maxClamped, newPrio, fxInfo->fx_upri);
       
  4044     }
  3980   } else {
  4045   } else {
  3981     if ( ThreadPriorityVerbose ) {
  4046     if (ThreadPriorityVerbose) {
  3982       tty->print_cr ("Unknown scheduling class\n");
  4047       tty->print_cr("Unknown new scheduling class %d\n", new_class);
  3983     }
  4048     }
  3984       return EINVAL;    // no clue, punt
  4049     return EINVAL;    // no clue, punt
  3985   }
  4050   }
  3986 
  4051 
  3987   rslt = (*priocntl_ptr)(PC_VERSION, P_LWPID, lwpid, PC_SETPARMS, (caddr_t)&ParmInfo);
  4052   rslt = (*priocntl_ptr)(PC_VERSION, P_LWPID, lwpid, PC_SETPARMS, (caddr_t)&ParmInfo);
  3988   if (ThreadPriorityVerbose && rslt) {
  4053   if (ThreadPriorityVerbose && rslt) {
  3989     tty->print_cr ("PC_SETPARMS ->%d %d\n", rslt, errno);
  4054     tty->print_cr ("PC_SETPARMS ->%d %d\n", rslt, errno);
  4014     Actual   = IAPRI(ReadBack)->ia_upri;
  4079     Actual   = IAPRI(ReadBack)->ia_upri;
  4015     Expected = IAPRI(ParmInfo)->ia_upri;
  4080     Expected = IAPRI(ParmInfo)->ia_upri;
  4016   } else if (ParmInfo.pc_cid == tsLimits.schedPolicy) {
  4081   } else if (ParmInfo.pc_cid == tsLimits.schedPolicy) {
  4017     Actual   = TSPRI(ReadBack)->ts_upri;
  4082     Actual   = TSPRI(ReadBack)->ts_upri;
  4018     Expected = TSPRI(ParmInfo)->ts_upri;
  4083     Expected = TSPRI(ParmInfo)->ts_upri;
       
  4084   } else if (ParmInfo.pc_cid == fxLimits.schedPolicy) {
       
  4085     Actual   = FXPRI(ReadBack)->fx_upri;
       
  4086     Expected = FXPRI(ParmInfo)->fx_upri;
  4019   } else {
  4087   } else {
  4020     if ( ThreadPriorityVerbose ) {
  4088     if (ThreadPriorityVerbose) {
  4021       tty->print_cr("set_lwp_priority: unexpected class in readback: %d\n", ParmInfo.pc_cid);
  4089       tty->print_cr("set_lwp_class_and_priority: unexpected class in readback: %d\n",
       
  4090                     ParmInfo.pc_cid);
  4022     }
  4091     }
  4023   }
  4092   }
  4024 
  4093 
  4025   if (Actual != Expected) {
  4094   if (Actual != Expected) {
  4026     if ( ThreadPriorityVerbose ) {
  4095     if (ThreadPriorityVerbose) {
  4027       tty->print_cr ("set_lwp_priority(%d %d) Class=%d: actual=%d vs expected=%d\n",
  4096       tty->print_cr ("set_lwp_class_and_priority(%d %d) Class=%d: actual=%d vs expected=%d\n",
  4028              lwpid, newPrio, ReadBack.pc_cid, Actual, Expected);
  4097                      lwpid, newPrio, ReadBack.pc_cid, Actual, Expected);
  4029     }
  4098     }
  4030   }
  4099   }
  4031 #endif
  4100 #endif
  4032 
  4101 
  4033   return 0;
  4102   return 0;
  4034 }
  4103 }
  4035 
       
  4036 
       
  4037 
  4104 
  4038 // Solaris only gives access to 128 real priorities at a time,
  4105 // Solaris only gives access to 128 real priorities at a time,
  4039 // so we expand Java's ten to fill this range.  This would be better
  4106 // so we expand Java's ten to fill this range.  This would be better
  4040 // if we dynamically adjusted relative priorities.
  4107 // if we dynamically adjusted relative priorities.
  4041 //
  4108 //
  4053 // Maximum priority an so on.  This will cause VM threads
  4120 // Maximum priority an so on.  This will cause VM threads
  4054 // to get unfair treatment against other Solaris processes
  4121 // to get unfair treatment against other Solaris processes
  4055 // which do not explicitly alter their thread priorities.
  4122 // which do not explicitly alter their thread priorities.
  4056 //
  4123 //
  4057 
  4124 
  4058 
  4125 int os::java_to_os_priority[CriticalPriority + 1] = {
  4059 int os::java_to_os_priority[MaxPriority + 1] = {
       
  4060   -99999,         // 0 Entry should never be used
  4126   -99999,         // 0 Entry should never be used
  4061 
  4127 
  4062   0,              // 1 MinPriority
  4128   0,              // 1 MinPriority
  4063   32,             // 2
  4129   32,             // 2
  4064   64,             // 3
  4130   64,             // 3
  4069 
  4135 
  4070   127,            // 7
  4136   127,            // 7
  4071   127,            // 8
  4137   127,            // 8
  4072   127,            // 9 NearMaxPriority
  4138   127,            // 9 NearMaxPriority
  4073 
  4139 
  4074   127             // 10 MaxPriority
  4140   127,            // 10 MaxPriority
       
  4141 
       
  4142   -criticalPrio   // 11 CriticalPriority
  4075 };
  4143 };
  4076 
  4144 
  4077 
       
  4078 OSReturn os::set_native_priority(Thread* thread, int newpri) {
  4145 OSReturn os::set_native_priority(Thread* thread, int newpri) {
       
  4146   OSThread* osthread = thread->osthread();
       
  4147 
       
  4148   // Save requested priority in case the thread hasn't been started
       
  4149   osthread->set_native_priority(newpri);
       
  4150 
       
  4151   // Check for critical priority request
       
  4152   bool fxcritical = false;
       
  4153   if (newpri == -criticalPrio) {
       
  4154     fxcritical = true;
       
  4155     newpri = criticalPrio;
       
  4156   }
       
  4157 
  4079   assert(newpri >= MinimumPriority && newpri <= MaximumPriority, "bad priority mapping");
  4158   assert(newpri >= MinimumPriority && newpri <= MaximumPriority, "bad priority mapping");
  4080   if ( !UseThreadPriorities ) return OS_OK;
  4159   if (!UseThreadPriorities) return OS_OK;
  4081   int status = thr_setprio(thread->osthread()->thread_id(), newpri);
  4160 
  4082   if ( os::Solaris::T2_libthread() || (UseBoundThreads && thread->osthread()->is_vm_created()) )
  4161   int status = 0;
  4083     status |= (set_lwp_priority (thread->osthread()->thread_id(),
  4162 
  4084                     thread->osthread()->lwp_id(), newpri ));
  4163   if (!fxcritical) {
       
  4164     // Use thr_setprio only if we have a priority that thr_setprio understands
       
  4165     status = thr_setprio(thread->osthread()->thread_id(), newpri);
       
  4166   }
       
  4167 
       
  4168   if (os::Solaris::T2_libthread() ||
       
  4169       (UseBoundThreads && osthread->is_vm_created())) {
       
  4170     int lwp_status =
       
  4171       set_lwp_class_and_priority(osthread->thread_id(),
       
  4172                                  osthread->lwp_id(),
       
  4173                                  newpri,
       
  4174                                  fxcritical ? fxLimits.schedPolicy : myClass,
       
  4175                                  !fxcritical);
       
  4176     if (lwp_status != 0 && fxcritical) {
       
  4177       // Try again, this time without changing the scheduling class
       
  4178       newpri = java_MaxPriority_to_os_priority;
       
  4179       lwp_status = set_lwp_class_and_priority(osthread->thread_id(),
       
  4180                                               osthread->lwp_id(),
       
  4181                                               newpri, myClass, false);
       
  4182     }
       
  4183     status |= lwp_status;
       
  4184   }
  4085   return (status == 0) ? OS_OK : OS_ERR;
  4185   return (status == 0) ? OS_OK : OS_ERR;
  4086 }
  4186 }
  4087 
  4187 
  4088 
  4188 
  4089 OSReturn os::get_native_priority(const Thread* const thread, int *priority_ptr) {
  4189 OSReturn os::get_native_priority(const Thread* const thread, int *priority_ptr) {