|
HP OpenVMS System Services Reference Manual
$CMEXEC
Changes the access mode of the calling process to executive mode.
Format
SYS$CMEXEC routin ,[arglst]
C Prototype
int sys$cmexec (int (*routin)(__unknown_params), unsigned int *arglst);
Arguments
routin
OpenVMS usage: |
procedure |
type: |
procedure value |
access: |
call without stack unwinding |
mechanism: |
by reference |
Routine to be executed while the process is in executive mode. The
routin argument is the address of this routine.
arglst
OpenVMS usage: |
arg_list |
type: |
longword (unsigned) |
access: |
read only |
mechanism: |
by reference |
Argument list to be passed to the routine specified by the
routin argument. The arglst argument
is the address of this argument list.
If the arglst value is nonzero and is not accessible
as an address or if the routine is inaccessible, the service returns
SS$_ACCVIO.
Alpha and I64 systems require a pointer to a valid argument list or a
value of 0 in the arglst argument. This means that the
arglst argument must contain an accessible virtual
address for an argument list, the first longword of which must be a
valid list size.
Description
The Change to Executive Mode service allows a process to change its
access mode to executive, execute a specified routine, and then return
to the access mode in effect before the call was issued.
The $CMEXEC service uses standard procedure calling conventions to pass
control to the specified routine.
On Alpha and I64 systems, to conform to the OpenVMS calling standard,
you must not omit the arglst argument.
On VAX systems, if no argument list is specified, the argument pointer
(AP) contains a 0. However, to conform to the OpenVMS calling standard,
you must not omit the arglst argument.
On Alpha, and I64, and VAX systems, when you use the $CMEXEC service,
the system service dispatcher modifies the registers before entry into
the target routine. The specified routine must exit with a RET
instruction and should place a status value in R0 before returning.
All of the Change Mode system services are intended to allow for the
execution of a routine at an access mode more (not less) privileged
than the access mode from which the call is made. If $CMEXEC is called
while a process is executing in kernel mode, the routine specified by
the routin argument executes in kernel mode, not
executive mode.
Required Access or Privileges
To call this service, the process must either have CMEXEC or CMKRNL
privilege or be currently executing in executive or kernel mode.
Required Quota
None
Related Services
None
Condition Values Returned
SS$_ACCVIO
|
The
arglst or routine argument is not accessible.
|
SS$_BADPARAM
|
The routine specified is in a translated image.
|
SS$_NOPRIV
|
The process does not have the privilege to change mode to executive.
|
All other values
|
The routine executed returns all other values.
|
$CMEXEC_64 (Alpha and I64)
On Alpha and I64 systems, changes the access mode of the calling
process to executive mode.
This service accepts 64-bit addresses.
Format
SYS$CMEXEC_64 routin_64 ,arglst_64
C Prototype
int sys$cmexec_64 (int (*routin_64)(__unknown_params), unsigned __int64
*arglst_64);
Arguments
routin_64
OpenVMS usage: |
procedure |
type: |
procedure value |
access: |
call without stack unwinding |
mechanism: |
by 32- or 64-bit reference |
Routine to be executed while the process is in executive mode. The
routin_64 argument is the 32- or 64-bit address of
this routine.
arglst_64
OpenVMS usage: |
arg_list |
type: |
quadword (unsigned) |
access: |
read only |
mechanism: |
by 32- or 64-bit reference |
Argument list to be passed to the routine specified by the
routin_64 argument. The arglst_64
argument is the 32- or 64-bit address of this argument list.
If the arglst value is nonzero and is not accessible
as an address or if the routine is inaccessible, the service returns
SS$_ACCVIO.
Alpha and I64 systems require a pointer to a valid argument list or a
value of 0 in the arglst_64 argument. This means that
the arglst_64 argument, if nonzero, must contain an
accessible virtual address for an argument list, the first quadword of
which must be a number between 0 and 255 specifying the number of
quadwords that follow it on the list.
Description
The Change to Executive Mode with Quadword Argument List service allows
a process to change its access mode to executive, execute a specified
routine, and then return to the access mode in effect before the call
was issued.
The $CMEXEC_64 service uses standard procedure-calling conventions to
pass control to the specified routine.
When you use the $CMEXEC_64 service, the system modifies the registers
before entry into the target routine. The specified routine must exit
with a RET instruction.
All of the Change Mode system services are intended to allow for the
execution of a routine at an access mode more (not less) privileged
than the access mode from which the call is made. If $CMEXEC_64 is
called while a process is executing in kernel mode, the routine
specified by the routin_64 argument executes in kernel
mode, not executive mode.
Required Access or Privileges
To call this service, the process must either have CMEXEC or CMKRNL
privilege or be currently executing in executive or kernel mode.
Required Quota
None
Related Services
$CMEXEC, $CMKRNL, $CMKRNL_64
Condition Values Returned
SS$_ACCVIO
|
The
arglst argument or routine is not accessible.
|
SS$_BADPARAM
|
The routine specified is in a translated image.
|
SS$_NOCMEXEC
|
The process does not have the privilege to change mode to executive.
|
All other values
|
The routine executed returns all other values.
|
$CMKRNL
Changes the access mode of the calling process to kernel mode. This
service allows a process to change its access mode to kernel, execute a
specified routine, and then return to the access mode in effect before
the call was issued.
Format
SYS$CMKRNL routin ,[arglst]
C Prototype
int sys$cmkrnl (int (*routin)(__unknown_params), unsigned int *arglst);
Arguments
routin
OpenVMS usage: |
procedure |
type: |
procedure value |
access: |
call without stack unwinding |
mechanism: |
by reference |
Routine to be executed while the process is in kernel mode. The
routin argument is the address of this routine.
arglst
OpenVMS usage: |
arg_list |
type: |
longword (unsigned) |
access: |
read only |
mechanism: |
by reference |
Argument list to be passed to the routine specified by the
routin argument. The arglst argument
is the address of this argument list.
If the arglst value is nonzero and is not accessible
as an address or if the routine is inaccessible, the service returns
SS$_ACCVIO.
Alpha systems require a pointer to a valid argument list or a value of
0 in the arglst argument. This means that the
arglst argument must contain an accessible virtual
address for an argument list, the first longword of which must be a
valid list size.
Description
The Change Mode to Kernel ($CMKRNL) and the Change Mode to Executive
($CMEXEC) system services provide a simple and secure path for
applications to execute code in the privileged kernel and executive
processor modes. These services first check for the necessary CMKRNL or
CMEXEC privileges, and then call the routine specified in the argument
list in the specified processor mode.
When code is executing in a privileged processor mode, such as
executive or kernel mode, the code executes with full OpenVMS
privileges. Furthermore, specific protection checks can also be
bypassed. For example, $CMKRNL bypasses the check for CMKRNL privilege
that is normally required when $CMKRNL is called from executive mode,
and $SETPRV calls are processed without SETPRV privilege when called
from executive or kernel mode.
The condition value returned from the procedure specified in the
argument list is used as the return status from the $CMKRNL or $CMEXEC
system service call. Based on the OpenVMS calling standard, this
condition value is returned by register R0, using a language-specific
mechanism.
Note
The $CMKRNL and $CMEXEC system services are typically used to access
privileged or internal OpenVMS routines or data structures. The code to
access these data structures can be OpenVMS version-dependent,
particularly if the internal routines or data structures change. Errors
that occur in code executing in a privileged processor mode can lead to
one or more possible situations: data corruptions, process deletions,
or system crashes.
The particular library routines and libraries that can be called from
code executing in executive or kernel mode can also be limited, because
not all library routines accessible from user mode can be called from
kernel mode.
|
Code Example
The following code example shows how to call a specified routine in
kernel mode using this service:
/*
// cmkrnl.c
//
// OpenVMS example of calling a specified routine in kernel mode,
// using the SYS$CMKRNL system service.
//
// Requires CMKRNL privilege.
//
// Errors in kernel-mode code can corrupt critical data structures,
// can cause process deletions, and can potentially crash the OpenVMS
// operating system.
//
// To build:
//
// $ CC/DECC CMKRNL
// $ LINK CMKRNL
// $ RUN CMKRNL
*/
#include <ssdef.h>
#include <starlet.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stsdef.h>
/*
// The KernelRoutine routine executes in kernel mode, but does
// absolutely nothing useful.
*/
int KernelRoutine( int *UsrArg1, int *UsrArg2)
{
return SS$_NORMAL;
}
main()
{
int RetStat;
int ArgList[3];
int i = 0;
printf("OpenVMS Alpha example of calling sys$cmkrnl\n");
/*
// Build the routine argument list in an array -- the KernelRoutine
// call expects two arguments, necessitating an array containing the
// count and the two arguments.
*/
ArgList[++i] = 1;
ArgList[++i] = 2;
ArgList[0] = i;
/*
// Now invoke the KernelRoutine in kernel mode...
*/
RetStat = sys$cmkrnl( KernelRoutine, ArgList );
if (!$VMS_STATUS_SUCCESS( RetStat ))
return RetStat;
printf("Now successfully back in user mode.\n");
return SS$_NORMAL;
}
|
Required Access or Privileges
To call the $CMKRNL service, a process must either have CMKRNL
privilege or be currently executing in executive or kernel mode.
Required Quota
None
Related Services
$CMEXEC, $CMEXEC_64, $CMKRNL_64, $SETPRV
Condition Values Returned
SS$_ACCVIO
|
The
arglst argument or routine is not accessible.
|
SS$_BADPARAM
|
The routine specified is in a translated image.
|
SS$_NOCMKRNL
|
The process does not have the privilege to change mode to kernel.
|
All other values
|
The routine executed returns all other values.
|
$CMKRNL_64 (Alpha and I64)
On Alpha and I64 systems, changes the access mode of the calling
process to kernel mode. This service allows a process to change its
access mode to kernel, execute a specified routine, and then return to
the access mode in effect before the call was issued.
This service accepts 64-bit addresses.
Format
SYS$CMKRNL_64 routin_64 ,arglst_64
C Prototype
int sys$cmkrnl_64 (int (*routin_64)(__unknown_params), unsigned __int64
*arglst_64);
Arguments
routin_64
OpenVMS usage: |
procedure |
type: |
procedure value |
access: |
call without stack unwinding |
mechanism: |
by 32- or 64-bit reference |
Routine to be executed while the process is in kernel mode. The
routin_64 argument is the 32- or 64-bit address of
this routine.
arglst_64
OpenVMS usage: |
arg_list |
type: |
quadword (unsigned) |
access: |
read only |
mechanism: |
by 32- or 64-bit reference |
Quadword argument list to be passed to the routine specified by the
routin_64 argument. The routin_64
argument is the 32- or 64-bit address of this routine.
If the arglst value is nonzero and is not accessible
as an address or if the routine is inaccessible, the service returns
SS$_ACCVIO.
Alpha and I64 systems require a pointer to a valid argument list or a
value of 0 in the arglst_64 argument. This means that
the arglst_64 argument, if nonzero, must contain an
accessible virtual address for an argument list, the first quadword of
which must be a number between 0 and 255 specifying the number of
quadwords that follow it on the list.
Description
The Change to Kernel Mode with Quadword Argument List service allows a
process to change its access mode to kernel, execute a specified
routine, and then return to the access mode in effect before the call
was issued.
The $CMKRNL_64 service uses standard procedure calling conventions to
pass control to the specified routine.
When you use the $CMKRNL_64 service, the system modifies the registers
before entry into the target routine. The system loads R4 with the
address of the process control block (PCB). The specified routine (if
programmed in MACRO-32) must exit with a RET instruction.
Required Access or Privileges
To call the $CMKRNL_64 service, a process must either have CMKRNL
privilege or be currently executing in executive or kernel mode.
Required Quota
None
Related Services
$CMEXEC, $CMEXEC_64, $CMKRNL, $SETPRV
Condition Values Returned
SS$_ACCVIO
|
The
arglst argument or routine is not accessible.
|
SS$_BADPARAM
|
The routine specified is in a translated image.
|
SS$_NOCMKRNL
|
The process does not have the privilege to change mode to kernel.
|
All other values
|
The routine executed returns all other values.
|
$CONNECT
The Connect service establishes a record stream by associating and
connecting a RAB with a FAB. You can invoke the Connect service only
for files that are already open.
Refer to the OpenVMS Record Management Services Reference Manual for additional information about this service.
$CPU_CAPABILITIES (Alpha and I64)
On Alpha and I64 systems, allows modification of the user capability
set for a specified CPU, or for the global user capability CPU default.
This service accepts 64-bit addresses.
Format
SYS$CPU_CAPABILITIES cpu_id [,select_mask] [,modify_mask] [,prev_mask]
[,flags]
C Prototype
int sys$cpu_capabilities (int cpu_id, struct _generic_64 *select_mask,
struct _generic_64 *modify_mask, struct _generic_64 *prev_mask, struct
_generic_64 *flags);
Arguments
cpu_id
OpenVMS usage: |
longword |
type: |
longword (unsigned) |
access: |
read only |
mechanism: |
by value |
Identifier of the CPU whose user capability mask is to be modified or
returned. The cpu_id argument is a longword containing
this number, which is in the supported range of individual CPUs from 0
to SYI$_MAX_CPUS - 1 .
Specifying the constant CAP$K_ALL_ACTIVE_CPUS applies the current
modification operation to all CPUs currently in the active set, and to
the default CPU initialization context in SCH$GL_DEFAULT_CPU_CAP. If
the prev_mask argument is also supplied, the previous
default CPU initialization context in SCH$GL_DEFAULT_CPU_CAP will be
returned rather than any specific CPU state.
To modify only the user capabilities in SCH$GL_DEFAULT_CPU_CAP, the
flags argument has a bit constant
CAP$M_FLAG_DEFAULT_ONLY. When this bit is set, all service operations
are performed on the global cell rather than on an individual CPU
specified in the cpu_id argument. This bit does not
supersede the CAP$K_ALL_ACTIVE_CPUS constant, however. If both
constants are specified, CAP$K_ALL_ACTIVE_CPUS take precedence;
nevertheless, the operations to SCH$GL_DEFAULT_CPU are identical
because that function is a direct subset of the other.
select_mask
OpenVMS usage: |
mask_quadword |
type: |
quadword (unsigned) |
access: |
read only |
mechanism: |
by 32- or 64-bit reference |
Mask specifying which bits of the specified CPU's user capability mask
are to be modified. The select_mask argument is the
32- or 64-bit address of a quadword bit vector wherein a bit, when set,
specifies that the corresponding user capability is to be modified.
The individual user capability bits in select_mask can
be referenced by their symbolic constant names, CAP$M_USER1 through
CAP$M_USER16. These constants (not zero-relative) specify the position
in the mask quadword that corresponds to the bit name. Multiple
capabilities can be selected by connecting the appropriate bits with a
logical OR operation.
The constant CAP$K_ALL_USER, when specified in the
select_mask argument, selects all user capability bits.
modify_mask
OpenVMS usage: |
mask_quadword |
type: |
quadword (unsigned) |
access: |
read only |
mechanism: |
by 32- or 64-bit reference |
Mask specifying the settings for those capabilities selected in the
select_mask argument. The modify_mask
argument is the 32- or 64-bit address of a quadword bit vector wherein
a bit, when set, specifies that the corresponding user capability is to
be added to the specified CPU; when clear, the corresponding user
capability is to be removed from the specified CPU.
The bit constants CAP$M_USER1 through CAP$M_USER16 can be used to
modify the appropriate bit position in modify_mask.
Multiple capabilities can be modified by connecting the appropriate
bits with OR.
To add a specific user capability to the specified CPU, that bit
position must be set in both select_mask and
modify_mask. To remove a specific user capability from
the specified CPU, that bit position must be set in
select_mask and cleared in
modify_mask.
The symbolic constant CAP$K_ALL_USER_ADD, when specified in
modify_mask, indicates that all capabilities specified
in select_mask are to be added to the current user
capability set. The constant CAP$K_ALL_USER_REMOVE indicates that all
capabilities specified are to be cleared from the set.
prev_mask
OpenVMS usage: |
mask_quadword |
type: |
quadword (unsigned) |
access: |
write only |
mechanism: |
by 32- or 64-bit reference |
Previous user capability mask for the specified CPU before execution of
this call to $CPU_CAPABILITIES. The prev_mask argument
is the 32- or 64-bit address of a quadword into which $CPU_CAPABILITIES
writes a quadword bit mask specifying the previous user capabilities.
If this argument is specified in conjunction with CAP$K_ALL_ACTIVE_CPUS
as the cpu_id selection constant or with
CAP$M_FLAG_DEFAULT_ONLY, the user capability portion of the default
boot initialization state context SCH$GL_DEFAULT_CPU_CAP will be
returned.
flags
OpenVMS usage: |
mask_quadword |
type: |
quadword (unsigned) |
access: |
read only |
mechanism: |
by 32- or 64-bit reference |
Options selected for the user capability modification. The
flags argument is a quadword bit vector wherein a bit
corresponds to an option. Only the bits specified in the following
table are used; the remainder of the quadword bits are reserved and
must be 0.
Each option (bit) has a symbolic name, defined by the $CAPDEF macro.
The flags argument is constructed by performing a
logical OR operation using the symbolic names of each desired option.
The following table describes the symbolic name of each option:
Symbolic Name |
Description |
CAP$M_FLAG_DEFAULT_ONLY
|
Indicates that the specified operations are to be performed on the
global context cell instead of on a specific CPU. This bit supersedes
any individual CPU specified in
cpu_id but does not override the all active set
behavior (CAP$K_ALL_ACTIVE_CPUS). Specifying this bit constant applies
this operation to the default startup capabilities for all CPUs booted
for the first time.
|
CAP$M_FLAG_CHECK_CPU
|
Determines whether the kernel thread can be left in a nonrunnable state
under some circumstances. No operation of this service allows a
transition from a runnable to blocked state; however, if the kernel
thread is already at a blocked state, this bit determines whether the
result of the operation must leave it runnable. If CAP$M_FLAG_CHECK_CPU
is set or
flags is not specified, the kernel thread is checked
to ensure that it can safely run on one of the CPUs in the active set.
If CAP$M_FLAG_CHECK_CPU is not set, any state operations on kernel
threads already in a blocked state are allowed.
|
Description
The Modify CPU User Capabilities system service, based on the arguments
select_mask and modify_mask, adds or
removes user capabilities for the specified cpu_id. If
specified, the previous capability mask is returned in
prev_mask. With the modify_mask
argument, multiple user capabilities for a CPU can be added or removed
in the same system service call.
Either modify_mask or prev_mask, or
both, must be specified as arguments. If modify_mask
is specified, select_mask must be specified as an
argument. If modify_mask is not specified, no
modifications are made to the user capability mask for the specified
CPU. In this case, select_mask is ignored. If
prev_mask is not specified, no previous mask is
returned.
No service state changes that will place any currently runnable kernel
thread into a blocked state are allowed.
If CAP$K_ALL_ACTIVE_CPUS is specified in cpu_id, the
user capability modifications are performed on all CPUs currently in
the active set, as well as the global initialization cell. If the bit
constant CAP$M_FLAG_DEFAULT_ONLY is set in the flags
argument, the user capability modifications are made only to the global
initialization cell, regardless of what individual CPU is specified in
cpu_id.
|