00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
#include "ki.h"
00026 
00027 
NTSTATUS
00028 KeUserModeCallback (
00029     IN ULONG ApiNumber,
00030     IN PVOID InputBuffer,
00031     IN ULONG InputLength,
00032     OUT PVOID *OutputBuffer,
00033     IN PULONG OutputLength
00034     )
00035 
00036 
00037 
00038 
00039 
00040 
00041 
00042 
00043 
00044 
00045 
00046 
00047 
00048 
00049 
00050 
00051 
00052 
00053 
00054 
00055 
00056 
00057 
00058 
00059 
00060 
00061 
00062 
00063 
00064 
00065 {
00066 
00067     PUCALLOUT_FRAME CalloutFrame;
00068     ULONG Length;
00069     ULONG OldStack;
00070     
NTSTATUS Status;
00071     PKTRAP_FRAME TrapFrame;
00072     PULONG UserStack;
00073     PVOID 
ValueBuffer;
00074     ULONG ValueLength;
00075 
00076     
ASSERT(KeGetPreviousMode() == 
UserMode);
00077 
00078     
00079     
00080     
00081     
00082 
00083     TrapFrame = 
KeGetCurrentThread()->TrapFrame;
00084     OldStack = (ULONG)TrapFrame->XIntSp;
00085     
try {
00086 
00087         
00088         
00089         
00090         
00091 
00092         Length =  (InputLength +
00093                 
sizeof(QUAD) - 1 + 
sizeof(UCALLOUT_FRAME)) & ~(
sizeof(QUAD) - 1);
00094 
00095         CalloutFrame = (PUCALLOUT_FRAME)(OldStack - Length);
00096         
ProbeForWrite(CalloutFrame, Length, 
sizeof(QUAD));
00097         RtlMoveMemory(CalloutFrame + 1, InputBuffer, InputLength);
00098 
00099         
00100         
00101         
00102 
00103         CalloutFrame->Buffer = (PVOID)(CalloutFrame + 1);
00104         CalloutFrame->Length = InputLength;
00105         CalloutFrame->ApiNumber = ApiNumber;
00106         CalloutFrame->Pad = 0;
00107         CalloutFrame->Sp = TrapFrame->XIntSp;
00108         CalloutFrame->Ra = TrapFrame->XIntRa;
00109 
00110     
00111     
00112     
00113     
00114     
00115 
00116     } except (
EXCEPTION_EXECUTE_HANDLER) {
00117         
return GetExceptionCode();
00118     }
00119 
00120     
00121     
00122     
00123 
00124     TrapFrame->XIntSp = (LONG)CalloutFrame;
00125     
Status = 
KiCallUserMode(OutputBuffer, OutputLength);
00126     TrapFrame->XIntSp = (LONG)OldStack;
00127 
00128     
00129     
00130     
00131 
00132     
if (((PTEB)
KeGetCurrentThread()->Teb)->GdiBatchCount > 0) {
00133         
KeGdiFlushUserBatch();
00134     }
00135 
00136     
return Status;
00137 }
00138 
00139 
NTSTATUS
00140 NtW32Call (
00141     IN ULONG ApiNumber,
00142     IN PVOID InputBuffer,
00143     IN ULONG InputLength,
00144     OUT PVOID *OutputBuffer,
00145     OUT PULONG OutputLength
00146     )
00147 
00148 
00149 
00150 
00151 
00152 
00153 
00154 
00155 
00156 
00157 
00158 
00159 
00160 
00161 
00162 
00163 
00164 
00165 
00166 
00167 
00168 
00169 
00170 
00171 
00172 
00173 
00174 
00175 
00176 
00177 {
00178 
00179     PVOID 
ValueBuffer;
00180     ULONG ValueLength;
00181     
NTSTATUS Status;
00182 
00183     
ASSERT(KeGetPreviousMode() == 
UserMode);
00184 
00185     
00186     
00187     
00188     
00189 
00190     
if (
KeGetCurrentThread()->Win32Thread == (PVOID)&
KeServiceDescriptorTable[0]) {
00191         
return STATUS_NOT_IMPLEMENTED;
00192     }
00193 
00194     
00195     
00196     
00197 
00198     
try {
00199         
ProbeForWriteUlong((PULONG)OutputBuffer);
00200         
ProbeForWriteUlong(OutputLength);
00201 
00202     
00203     
00204     
00205     
00206     
00207 
00208     } except(
EXCEPTION_EXECUTE_HANDLER) {
00209         
return GetExceptionCode();
00210     }
00211 
00212     
00213     
00214     
00215 
00216     
Status = 
KeUserModeCallback(ApiNumber,
00217                                 InputBuffer,
00218                                 InputLength,
00219                                 &
ValueBuffer,
00220                                 &ValueLength);
00221 
00222     
00223     
00224     
00225     
00226 
00227     
if (
NT_SUCCESS(
Status)) {
00228         
try {
00229             *OutputBuffer = 
ValueBuffer;
00230             *OutputLength = ValueLength;
00231 
00232         } except(
EXCEPTION_EXECUTE_HANDLER) {
00233         }
00234     }
00235 
00236     
return Status;
00237 }